Loading...
Searching...
No Matches
control_cmd.h
Go to the documentation of this file.
#pragma once
#include <osmocom/core/msgb.h>
#include <osmocom/core/talloc.h>
#include <osmocom/core/write_queue.h>
#include <osmocom/core/logging.h>
#include <osmocom/core/utils.h>
#include <osmocom/vty/vector.h>
#define CTRL_CMD_ERROR -1
#define CTRL_CMD_HANDLED 0
#define CTRL_CMD_REPLY 1
#define CTRL_CMD_TRAP_ID "0"
struct ctrl_handle;
enum ctrl_node_type {
CTRL_NODE_ROOT, /* Root elements */
CTRL_NODE_BTS, /* BTS specific (net.btsN.) */
CTRL_NODE_TRX, /* TRX specific (net.btsN.trxM.) */
CTRL_NODE_TS, /* TS specific (net.btsN.trxM.tsI.) */
CTRL_NODE_FSM, /* Finite State Machine (description) */
CTRL_NODE_FSM_INST, /* Finite State Machine (instance) */
CTRL_NODE_LCHAN, /* LCHAN specific (net.btsN.trxM.tsI.lchanL) */
_LAST_CTRL_NODE
};
enum ctrl_type {
CTRL_TYPE_UNKNOWN,
CTRL_TYPE_GET,
CTRL_TYPE_SET,
CTRL_TYPE_GET_REPLY,
CTRL_TYPE_SET_REPLY,
CTRL_TYPE_TRAP,
CTRL_TYPE_ERROR
};
extern const struct value_string ctrl_type_vals[];
struct ctrl_connection {
struct llist_head list_entry;
struct osmo_wqueue write_queue;
struct msgb *pending_msg;
void (*closed_cb)(struct ctrl_connection *conn);
struct llist_head cmds;
struct llist_head def_cmds;
};
struct ctrl_cmd_def;
struct ctrl_cmd {
struct ctrl_connection *ccon;
enum ctrl_type type;
char *id;
void *node;
char *variable;
char *value;
char *reply;
struct ctrl_cmd_def *defer;
};
#define ctrl_cmd_reply_printf(cmd, fmt, args ...) \
osmo_talloc_asprintf(cmd, cmd->reply, fmt, ## args)
struct ctrl_cmd_struct {
int nr_commands;
char **command;
};
struct ctrl_cmd_element {
const char *name;
struct ctrl_cmd_struct strcmd;
int (*set)(struct ctrl_cmd *cmd, void *data);
int (*get)(struct ctrl_cmd *cmd, void *data);
int (*verify)(struct ctrl_cmd *cmd, const char *value, void *data);
};
struct ctrl_cmd_map {
char *cmd;
enum ctrl_type type;
};
/* deferred control command, i.e. responded asynchronously */
struct ctrl_cmd_def {
struct llist_head list; /* ctrl_connection.def_cmds */
struct ctrl_cmd *cmd;
void *data; /* opaque user data */
};
struct ctrl_cmd_def *
ctrl_cmd_def_make(const void *ctx, struct ctrl_cmd *cmd, void *data, unsigned int secs);
int ctrl_cmd_def_is_zombie(struct ctrl_cmd_def *cd);
int ctrl_cmd_def_send(struct ctrl_cmd_def *cd);
int ctrl_cmd_exec(vector vline, struct ctrl_cmd *command, vector node, void *data);
int ctrl_cmd_install(enum ctrl_node_type node, struct ctrl_cmd_element *cmd);
/* ctrl_cmd_send is also declared in control_if.h, but legacy openbsc.git expects it here */
int ctrl_cmd_send(struct osmo_wqueue *queue, struct ctrl_cmd *cmd);
int ctrl_cmd_send_to_all(struct ctrl_handle *ctrl, struct ctrl_cmd *cmd);
struct ctrl_cmd *ctrl_cmd_parse3(void *ctx, struct msgb *msg, bool *parse_failed);
struct ctrl_cmd *ctrl_cmd_parse2(void *ctx, struct msgb *msg);
struct ctrl_cmd *ctrl_cmd_parse(void *ctx, struct msgb *msg);
struct msgb *ctrl_cmd_make(struct ctrl_cmd *cmd);
struct ctrl_cmd *ctrl_cmd_cpy(void *ctx, struct ctrl_cmd *cmd);
struct ctrl_cmd *ctrl_cmd_create(void *ctx, enum ctrl_type);
struct ctrl_cmd *ctrl_cmd_trap(struct ctrl_cmd *cmd);
#define CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_name) \
static struct ctrl_cmd_element cmd_##cmdname = { \
.name = cmdstr, \
.get = &get_##cmdname, \
.set = &set_##cmdname, \
.verify = verify_name, \
}
#define CTRL_HELPER_GET_INT(cmdname, dtype, element) \
static int get_##cmdname(struct ctrl_cmd *cmd, void *_data) \
{ \
dtype *node = cmd->node; \
cmd->reply = talloc_asprintf(cmd, "%i", node->element); \
if (!cmd->reply) { \
cmd->reply = "OOM"; \
return CTRL_CMD_ERROR; \
} \
return CTRL_CMD_REPLY; \
}
#define CTRL_HELPER_SET_INT(cmdname, dtype, element) \
static int set_##cmdname(struct ctrl_cmd *cmd, void *_data) \
{ \
dtype *node = cmd->node; \
int tmp = atoi(cmd->value); \
node->element = tmp; \
return get_##cmdname(cmd, _data); \
}
#define CTRL_HELPER_VERIFY_RANGE(cmdname, min, max) \
static int verify_##cmdname(struct ctrl_cmd *cmd, const char *value, void *_data) \
{ \
int tmp = atoi(value); \
if ((tmp >= min)&&(tmp <= max)) { \
return 0; \
} \
cmd->reply = "Input not within the range"; \
return -1; \
}
#define CTRL_CMD_DEFINE_RANGE(cmdname, cmdstr, dtype, element, min, max) \
CTRL_HELPER_GET_INT(cmdname, dtype, element) \
CTRL_HELPER_SET_INT(cmdname, dtype, element) \
CTRL_HELPER_VERIFY_RANGE(cmdname, min, max) \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_##cmdname)
#define CTRL_HELPER_GET_STRING(cmdname, dtype, element) \
static int get_##cmdname(struct ctrl_cmd *cmd, void *_data) \
{ \
dtype *data = cmd->node; \
cmd->reply = talloc_asprintf(cmd, "%s", data->element); \
if (!cmd->reply) { \
cmd->reply = "OOM"; \
return CTRL_CMD_ERROR; \
} \
return CTRL_CMD_REPLY; \
}
#define CTRL_HELPER_SET_STRING(cmdname, dtype, element) \
static int set_##cmdname(struct ctrl_cmd *cmd, void *_data) \
{ \
dtype *data = cmd->node; \
osmo_talloc_replace_string(cmd->node, &data->element, cmd->value); \
return get_##cmdname(cmd, _data); \
}
#define CTRL_CMD_DEFINE_STRING(cmdname, cmdstr, dtype, element) \
CTRL_HELPER_GET_STRING(cmdname, dtype, element) \
CTRL_HELPER_SET_STRING(cmdname, dtype, element) \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, NULL)
#define CTRL_CMD_DEFINE(cmdname, cmdstr) \
static int get_##cmdname(struct ctrl_cmd *cmd, void *data); \
static int set_##cmdname(struct ctrl_cmd *cmd, void *data); \
static int verify_##cmdname(struct ctrl_cmd *cmd, const char *value, void *data); \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_##cmdname)
#define CTRL_CMD_DEFINE_RO(cmdname, cmdstr) \
static int get_##cmdname(struct ctrl_cmd *cmd, void *data); \
static int set_##cmdname(struct ctrl_cmd *cmd, void *data) \
{ \
cmd->reply = "Read Only attribute"; \
return CTRL_CMD_ERROR; \
} \
static int verify_##cmdname(struct ctrl_cmd *cmd, const char *value, void *data) \
{ \
cmd->reply = "Read Only attribute"; \
return 1; \
} \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_##cmdname)
#define CTRL_CMD_DEFINE_WO(cmdname, cmdstr) \
static int set_##cmdname(struct ctrl_cmd *cmd, void *data); \
static int get_##cmdname(struct ctrl_cmd *cmd, void *data) \
{ \
cmd->reply = "Write Only attribute"; \
return CTRL_CMD_ERROR; \
} \
static int verify_##cmdname(struct ctrl_cmd *cmd, const char *val, void *data); \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_##cmdname)
#define CTRL_CMD_DEFINE_WO_NOVRF(cmdname, cmdstr) \
static int set_##cmdname(struct ctrl_cmd *cmd, void *data); \
static int get_##cmdname(struct ctrl_cmd *cmd, void *data) \
{ \
cmd->reply = "Write Only attribute"; \
return CTRL_CMD_ERROR; \
} \
static int verify_##cmdname(struct ctrl_cmd *cmd, const char *val, void *data) \
{ \
return 0; \
} \
CTRL_CMD_DEFINE_STRUCT(cmdname, cmdstr, verify_##cmdname)
struct gsm_network;
ctrl_type
ctrl_type
Ctrl command types (GET, SET, ...).
Definition control_cmd.h:32
CTRL_TYPE_GET_REPLY
@ CTRL_TYPE_GET_REPLY
Definition control_cmd.h:36
CTRL_TYPE_ERROR
@ CTRL_TYPE_ERROR
Definition control_cmd.h:39
CTRL_TYPE_SET_REPLY
@ CTRL_TYPE_SET_REPLY
Definition control_cmd.h:37
CTRL_TYPE_SET
@ CTRL_TYPE_SET
Definition control_cmd.h:35
CTRL_TYPE_GET
@ CTRL_TYPE_GET
Definition control_cmd.h:34
CTRL_TYPE_UNKNOWN
@ CTRL_TYPE_UNKNOWN
Definition control_cmd.h:33
CTRL_TYPE_TRAP
@ CTRL_TYPE_TRAP
Definition control_cmd.h:38
ctrl_cmd_parse
struct ctrl_cmd * ctrl_cmd_parse(void *ctx, struct msgb *msg)
Parse/Decode CTRL from Message buffers into command struct.
Definition control_cmd.c:302
ctrl_cmd_create
struct ctrl_cmd * ctrl_cmd_create(void *ctx, enum ctrl_type)
Allocate a control command of given type.
Definition control_cmd.c:245
ctrl_cmd_trap
struct ctrl_cmd * ctrl_cmd_trap(struct ctrl_cmd *cmd)
Copy given cmd and convert copy to CTRL_TYPE_TRAP.
Definition control_if.c:175
ctrl_cmd_make
struct msgb * ctrl_cmd_make(struct ctrl_cmd *cmd)
Encode a given CTRL command from its parsed form into a message buffer.
Definition control_cmd.c:524
ctrl_cmd_parse3
struct ctrl_cmd * ctrl_cmd_parse3(void *ctx, struct msgb *msg, bool *parse_failed)
Parse/Decode CTRL from Message buffers into command struct.
Definition control_cmd.c:343
ctrl_type_vals
const struct value_string ctrl_type_vals[]
human-readable string names for ctrl_type
Definition control_cmd.c:44
ctrl_cmd_send_to_all
int ctrl_cmd_send_to_all(struct ctrl_handle *ctrl, struct ctrl_cmd *cmd)
Send a CTRL command to all connections.
Definition control_if.c:101
ctrl_cmd_def_is_zombie
int ctrl_cmd_def_is_zombie(struct ctrl_cmd_def *cd)
Determine if the given deferred control command is still alive or a zombie.
Definition control_cmd.c:615
ctrl_cmd_def_make
struct ctrl_cmd_def * ctrl_cmd_def_make(const void *ctx, struct ctrl_cmd *cmd, void *data, unsigned int secs)
Build a deferred control command state and keep it the per-connection list of deferred commands.
Definition control_cmd.c:593
ctrl_cmd_def_send
int ctrl_cmd_def_send(struct ctrl_cmd_def *cd)
Send the response to a deferred ctrl command.
Definition control_cmd.c:632
ctrl_cmd_cpy
struct ctrl_cmd * ctrl_cmd_cpy(void *ctx, struct ctrl_cmd *cmd)
Perform a deepl copy of the given cmd, allocating memory from ctx.
Definition control_cmd.c:261
ctrl_cmd_parse2
struct ctrl_cmd * ctrl_cmd_parse2(void *ctx, struct msgb *msg)
Parse/Decode CTRL from Message buffers into command struct.
Definition control_cmd.c:329
ctrl_node_type
ctrl_node_type
The class of node at which a ctrl command is registered to.
Definition control_cmd.h:20
CTRL_NODE_ROOT
@ CTRL_NODE_ROOT
Definition control_cmd.h:21
CTRL_NODE_LCHAN
@ CTRL_NODE_LCHAN
Definition control_cmd.h:27
_LAST_CTRL_NODE
@ _LAST_CTRL_NODE
Definition control_cmd.h:28
CTRL_NODE_FSM
@ CTRL_NODE_FSM
Definition control_cmd.h:25
CTRL_NODE_TS
@ CTRL_NODE_TS
Definition control_cmd.h:24
CTRL_NODE_TRX
@ CTRL_NODE_TRX
Definition control_cmd.h:23
CTRL_NODE_BTS
@ CTRL_NODE_BTS
Definition control_cmd.h:22
CTRL_NODE_FSM_INST
@ CTRL_NODE_FSM_INST
Definition control_cmd.h:26
ctrl_cmd_send
int ctrl_cmd_send(struct osmo_wqueue *queue, struct ctrl_cmd *cmd)
Encode a CTRL command and append it to the given ctrl_connection.
Definition control_if.c:119
ctrl_cmd_install
int ctrl_cmd_install(enum ctrl_node_type node, struct ctrl_cmd_element *cmd)
Install a given command definition at a given CTRL node.
Definition control_cmd.c:210
ctrl_cmd_exec
int ctrl_cmd_exec(vector vline, struct ctrl_cmd *command, vector node, void *data)
Execute a given received command.
Definition control_cmd.c:95
node
struct cmd_node * node
data
uint8_t data[0]
msg
uint8_t msg[0]
logging.h
msgb.h
ctrl_cmd_def
Definition control_cmd.h:114
ctrl_cmd_def::data
void * data
Definition control_cmd.h:117
ctrl_cmd_def::list
struct llist_head list
Definition control_cmd.h:115
ctrl_cmd_def::cmd
struct ctrl_cmd * cmd
Definition control_cmd.h:116
ctrl_cmd_element
Implementation of a given CTRL command.
Definition control_cmd.h:96
ctrl_cmd_element::set
int(* set)(struct ctrl_cmd *cmd, void *data)
call-back function implementing the SET operation
Definition control_cmd.h:101
ctrl_cmd_element::strcmd
struct ctrl_cmd_struct strcmd
Definition control_cmd.h:99
ctrl_cmd_element::name
const char * name
textual name/id of the CTRL command
Definition control_cmd.h:98
ctrl_cmd_element::get
int(* get)(struct ctrl_cmd *cmd, void *data)
call-back function implementing the GET operation
Definition control_cmd.h:103
ctrl_cmd_element::verify
int(* verify)(struct ctrl_cmd *cmd, const char *value, void *data)
call-back function to validate a value; called before SET
Definition control_cmd.h:105
ctrl_cmd_map
Definition control_cmd.h:108
ctrl_cmd_map::cmd
char * cmd
Definition control_cmd.h:109
ctrl_cmd_map::type
enum ctrl_type type
Definition control_cmd.h:110
ctrl_cmd_struct
Definition control_cmd.h:89
ctrl_cmd_struct::command
char ** command
Definition control_cmd.h:91
ctrl_cmd_struct::nr_commands
int nr_commands
Definition control_cmd.h:90
ctrl_cmd
Represents a single ctrl command after parsing.
Definition control_cmd.h:68
ctrl_cmd::defer
struct ctrl_cmd_def * defer
state representing deferred (async) response, if any
Definition control_cmd.h:83
ctrl_cmd::ccon
struct ctrl_connection * ccon
connection through which the command was received
Definition control_cmd.h:70
ctrl_cmd::variable
char * variable
name of the variable
Definition control_cmd.h:77
ctrl_cmd::value
char * value
value of the specified CTRL variable
Definition control_cmd.h:79
ctrl_cmd::type
enum ctrl_type type
command type
Definition control_cmd.h:72
ctrl_cmd::id
char * id
Definition control_cmd.h:73
ctrl_cmd::node
void * node
node of the specified variable
Definition control_cmd.h:75
ctrl_cmd::reply
char * reply
respnse message string
Definition control_cmd.h:81
ctrl_connection
Represents a single ctrl connection.
Definition control_cmd.h:46
ctrl_connection::closed_cb
void(* closed_cb)(struct ctrl_connection *conn)
Callback if the connection was closed.
Definition control_cmd.h:56
ctrl_connection::list_entry
struct llist_head list_entry
Definition control_cmd.h:47
ctrl_connection::write_queue
struct osmo_wqueue write_queue
The queue for sending data back.
Definition control_cmd.h:50
ctrl_connection::pending_msg
struct msgb * pending_msg
Buffer for partial input data.
Definition control_cmd.h:53
ctrl_connection::def_cmds
struct llist_head def_cmds
Pending deferred command responses for this connection.
Definition control_cmd.h:62
ctrl_connection::cmds
struct llist_head cmds
Pending commands for this connection.
Definition control_cmd.h:59
ctrl_handle
Definition control_if.h:14
llist_head
msgb
osmo_wqueue
value_string
talloc.h
utils.h
vector.h
vector
struct _vector * vector
write_queue.h