mirror of
https://github.com/asterisk/asterisk.git
synced 2025-09-05 12:16:00 +00:00
Add the ability to set flags via the config options api
Allows the setting of flags via the config options api. For example, code like this: #define OPT1 1 << 0 #define OPT2 1 << 1 #define OPT3 1 << 2 struct thing { unsigned int flags; }; and a config like this: [blah] opt1=yes opt2=no opt3=yes Review: https://reviewboard.asterisk.org/r/2004/ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@369454 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
@@ -9,6 +9,9 @@ uintopt=1
|
|||||||
doubleopt=0.1
|
doubleopt=0.1
|
||||||
sockaddropt=1.2.3.4:1234
|
sockaddropt=1.2.3.4:1234
|
||||||
boolopt=true
|
boolopt=true
|
||||||
|
boolflag1=true
|
||||||
|
boolflag2=false
|
||||||
|
boolflag3=true
|
||||||
acldenyopt=0.0.0.0/0
|
acldenyopt=0.0.0.0/0
|
||||||
aclpermitopt=1.2.3.4/32
|
aclpermitopt=1.2.3.4/32
|
||||||
codecopt=!all,ulaw,g729
|
codecopt=!all,ulaw,g729
|
||||||
@@ -23,6 +26,9 @@ uintopt=1
|
|||||||
doubleopt=0.1
|
doubleopt=0.1
|
||||||
sockaddropt=1.2.3.4:1234
|
sockaddropt=1.2.3.4:1234
|
||||||
boolopt=true
|
boolopt=true
|
||||||
|
boolflag1=true
|
||||||
|
boolflag2=false
|
||||||
|
boolflag3=true
|
||||||
acldenyopt=0.0.0.0/0
|
acldenyopt=0.0.0.0/0
|
||||||
aclpermitopt=1.2.3.4/32
|
aclpermitopt=1.2.3.4/32
|
||||||
codecopt=!all,ulaw,g729
|
codecopt=!all,ulaw,g729
|
||||||
|
@@ -261,6 +261,26 @@ enum aco_option_type {
|
|||||||
*/
|
*/
|
||||||
OPT_BOOL_T,
|
OPT_BOOL_T,
|
||||||
|
|
||||||
|
/*! \brief Type for default option handler for bools (ast_true/ast_false) that are stored in a flag
|
||||||
|
* \note aco_option_register flags:
|
||||||
|
* non-zero : process via ast_true
|
||||||
|
* 0 : process via ast_false
|
||||||
|
* aco_option_register varargs:
|
||||||
|
* FLDSET macro with the field of type of unsigned int.
|
||||||
|
* The flag to set
|
||||||
|
*
|
||||||
|
* Example:
|
||||||
|
* {code}
|
||||||
|
* #define MY_TYPE_ISQUIET 1 << 4
|
||||||
|
* struct test_item {
|
||||||
|
* unsigned int flags;
|
||||||
|
* };
|
||||||
|
aco_option_register(&cfg_info, "quiet", ACO_EXACT, my_types, "no", OPT_BOOLFLAG_T, 1, FLDSET(struct test_item, flags), MY_TYPE_ISQUIET);
|
||||||
|
* {endcode}
|
||||||
|
*/
|
||||||
|
|
||||||
|
OPT_BOOLFLAG_T,
|
||||||
|
|
||||||
/*! \brief Type for default option handler for codec preferences/capabilities
|
/*! \brief Type for default option handler for codec preferences/capabilities
|
||||||
* \note aco_option_register flags:
|
* \note aco_option_register flags:
|
||||||
* non-zero : This is an "allow" style option
|
* non-zero : This is an "allow" style option
|
||||||
|
@@ -92,6 +92,7 @@ static int double_handler_fn(const struct aco_option *opt, struct ast_variable *
|
|||||||
static int sockaddr_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
static int sockaddr_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
static int stringfield_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
static int stringfield_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
static int bool_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
static int bool_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
|
static int boolflag_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
static int acl_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
static int acl_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
static int codec_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
static int codec_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
|
||||||
|
|
||||||
@@ -100,6 +101,7 @@ static aco_option_handler ast_config_option_default_handler(enum aco_option_type
|
|||||||
switch(type) {
|
switch(type) {
|
||||||
case OPT_ACL_T: return acl_handler_fn;
|
case OPT_ACL_T: return acl_handler_fn;
|
||||||
case OPT_BOOL_T: return bool_handler_fn;
|
case OPT_BOOL_T: return bool_handler_fn;
|
||||||
|
case OPT_BOOLFLAG_T: return boolflag_handler_fn;
|
||||||
case OPT_CODEC_T: return codec_handler_fn;
|
case OPT_CODEC_T: return codec_handler_fn;
|
||||||
case OPT_DOUBLE_T: return double_handler_fn;
|
case OPT_DOUBLE_T: return double_handler_fn;
|
||||||
case OPT_INT_T: return int_handler_fn;
|
case OPT_INT_T: return int_handler_fn;
|
||||||
@@ -741,6 +743,23 @@ static int bool_handler_fn(const struct aco_option *opt, struct ast_variable *va
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*! \brief Default option handler for bools (ast_true/ast_false) that are stored as flags
|
||||||
|
* \note For a description of the opt->flags and opt->args values, see the documentation for
|
||||||
|
* enum aco_option_type in config_options.h
|
||||||
|
*/
|
||||||
|
static int boolflag_handler_fn(const struct aco_option *opt, struct ast_variable *var, void *obj)
|
||||||
|
{
|
||||||
|
unsigned int *flags_field = (unsigned int *)(obj + opt->args[0]);
|
||||||
|
unsigned int val = opt->flags ? ast_true(var->value) : ast_false(var->value);
|
||||||
|
unsigned int flag = opt->args[1];
|
||||||
|
if (val) {
|
||||||
|
*flags_field |= flag;
|
||||||
|
} else {
|
||||||
|
*flags_field &= ~flag;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*! \brief Default handler for ast_sockaddrs
|
/*! \brief Default handler for ast_sockaddrs
|
||||||
* \note For a description of the opt->flags and opt->args values, see the documentation for
|
* \note For a description of the opt->flags and opt->args values, see the documentation for
|
||||||
* enum aco_option_type in config_options.h
|
* enum aco_option_type in config_options.h
|
||||||
|
@@ -622,6 +622,7 @@ struct test_item {
|
|||||||
);
|
);
|
||||||
int32_t intopt;
|
int32_t intopt;
|
||||||
uint32_t uintopt;
|
uint32_t uintopt;
|
||||||
|
unsigned int flags;
|
||||||
double doubleopt;
|
double doubleopt;
|
||||||
struct ast_sockaddr sockaddropt;
|
struct ast_sockaddr sockaddropt;
|
||||||
int boolopt;
|
int boolopt;
|
||||||
@@ -784,6 +785,12 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
#define SOCKADDR_CONFIG "1.2.3.4:1234"
|
#define SOCKADDR_CONFIG "1.2.3.4:1234"
|
||||||
#define BOOL_DEFAULT "false"
|
#define BOOL_DEFAULT "false"
|
||||||
#define BOOL_CONFIG "true"
|
#define BOOL_CONFIG "true"
|
||||||
|
#define BOOLFLAG1_DEFAULT "false"
|
||||||
|
#define BOOLFLAG1_CONFIG "true"
|
||||||
|
#define BOOLFLAG2_DEFAULT "false"
|
||||||
|
#define BOOLFLAG2_CONFIG "false"
|
||||||
|
#define BOOLFLAG3_DEFAULT "false"
|
||||||
|
#define BOOLFLAG3_CONFIG "true"
|
||||||
#define ACL_DEFAULT NULL
|
#define ACL_DEFAULT NULL
|
||||||
#define ACL_CONFIG_PERMIT "1.2.3.4/32"
|
#define ACL_CONFIG_PERMIT "1.2.3.4/32"
|
||||||
#define ACL_CONFIG_DENY "0.0.0.0/0"
|
#define ACL_CONFIG_DENY "0.0.0.0/0"
|
||||||
@@ -794,6 +801,10 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
#define CUSTOM_DEFAULT "no"
|
#define CUSTOM_DEFAULT "no"
|
||||||
#define CUSTOM_CONFIG "yes"
|
#define CUSTOM_CONFIG "yes"
|
||||||
|
|
||||||
|
#define BOOLFLAG1 1 << 0
|
||||||
|
#define BOOLFLAG2 1 << 1
|
||||||
|
#define BOOLFLAG3 1 << 2
|
||||||
|
|
||||||
if (aco_info_init(&cfg_info)) {
|
if (aco_info_init(&cfg_info)) {
|
||||||
ast_test_status_update(test, "Could not init cfg info\n");
|
ast_test_status_update(test, "Could not init cfg info\n");
|
||||||
return AST_TEST_FAIL;
|
return AST_TEST_FAIL;
|
||||||
@@ -805,6 +816,9 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
aco_option_register(&cfg_info, "doubleopt", ACO_EXACT, config_test_conf.types, DOUBLE_DEFAULT, OPT_DOUBLE_T, 0, FLDSET(struct test_item, doubleopt));
|
aco_option_register(&cfg_info, "doubleopt", ACO_EXACT, config_test_conf.types, DOUBLE_DEFAULT, OPT_DOUBLE_T, 0, FLDSET(struct test_item, doubleopt));
|
||||||
aco_option_register(&cfg_info, "sockaddropt", ACO_EXACT, config_test_conf.types, SOCKADDR_DEFAULT, OPT_SOCKADDR_T, 0, FLDSET(struct test_item, sockaddropt));
|
aco_option_register(&cfg_info, "sockaddropt", ACO_EXACT, config_test_conf.types, SOCKADDR_DEFAULT, OPT_SOCKADDR_T, 0, FLDSET(struct test_item, sockaddropt));
|
||||||
aco_option_register(&cfg_info, "boolopt", ACO_EXACT, config_test_conf.types, BOOL_DEFAULT, OPT_BOOL_T, 1, FLDSET(struct test_item, boolopt));
|
aco_option_register(&cfg_info, "boolopt", ACO_EXACT, config_test_conf.types, BOOL_DEFAULT, OPT_BOOL_T, 1, FLDSET(struct test_item, boolopt));
|
||||||
|
aco_option_register(&cfg_info, "boolflag1", ACO_EXACT, config_test_conf.types, BOOLFLAG1_DEFAULT, OPT_BOOLFLAG_T, 1, FLDSET(struct test_item, flags), BOOLFLAG1);
|
||||||
|
aco_option_register(&cfg_info, "boolflag2", ACO_EXACT, config_test_conf.types, BOOLFLAG2_DEFAULT, OPT_BOOLFLAG_T, 1, FLDSET(struct test_item, flags), BOOLFLAG2);
|
||||||
|
aco_option_register(&cfg_info, "boolflag3", ACO_EXACT, config_test_conf.types, BOOLFLAG3_DEFAULT, OPT_BOOLFLAG_T, 1, FLDSET(struct test_item, flags), BOOLFLAG3);
|
||||||
aco_option_register(&cfg_info, "aclpermitopt", ACO_EXACT, config_test_conf.types, ACL_DEFAULT, OPT_ACL_T, 1, FLDSET(struct test_item, aclopt));
|
aco_option_register(&cfg_info, "aclpermitopt", ACO_EXACT, config_test_conf.types, ACL_DEFAULT, OPT_ACL_T, 1, FLDSET(struct test_item, aclopt));
|
||||||
aco_option_register(&cfg_info, "acldenyopt", ACO_EXACT, config_test_conf.types, ACL_DEFAULT, OPT_ACL_T, 0, FLDSET(struct test_item, aclopt));
|
aco_option_register(&cfg_info, "acldenyopt", ACO_EXACT, config_test_conf.types, ACL_DEFAULT, OPT_ACL_T, 0, FLDSET(struct test_item, aclopt));
|
||||||
aco_option_register(&cfg_info, "codecopt", ACO_EXACT, config_test_conf.types, CODEC_DEFAULT, OPT_CODEC_T, 1, FLDSET(struct test_item, codecprefopt, codeccapopt));
|
aco_option_register(&cfg_info, "codecopt", ACO_EXACT, config_test_conf.types, CODEC_DEFAULT, OPT_CODEC_T, 1, FLDSET(struct test_item, codecprefopt, codeccapopt));
|
||||||
@@ -826,6 +840,12 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
ast_parse_arg(SOCKADDR_CONFIG, PARSE_ADDR, &configs.sockaddropt);
|
ast_parse_arg(SOCKADDR_CONFIG, PARSE_ADDR, &configs.sockaddropt);
|
||||||
defaults.boolopt = ast_true(BOOL_DEFAULT);
|
defaults.boolopt = ast_true(BOOL_DEFAULT);
|
||||||
configs.boolopt = ast_true(BOOL_CONFIG);
|
configs.boolopt = ast_true(BOOL_CONFIG);
|
||||||
|
ast_set2_flag(&defaults, ast_true(BOOLFLAG1_DEFAULT), BOOLFLAG1);
|
||||||
|
ast_set2_flag(&defaults, ast_true(BOOLFLAG2_DEFAULT), BOOLFLAG2);
|
||||||
|
ast_set2_flag(&defaults, ast_true(BOOLFLAG3_DEFAULT), BOOLFLAG3);
|
||||||
|
ast_set2_flag(&configs, ast_true(BOOLFLAG1_CONFIG), BOOLFLAG1);
|
||||||
|
ast_set2_flag(&configs, ast_true(BOOLFLAG2_CONFIG), BOOLFLAG2);
|
||||||
|
ast_set2_flag(&configs, ast_true(BOOLFLAG3_CONFIG), BOOLFLAG3);
|
||||||
|
|
||||||
defaults.aclopt = NULL;
|
defaults.aclopt = NULL;
|
||||||
configs.aclopt = ast_append_ha("deny", ACL_CONFIG_DENY, configs.aclopt, &error);
|
configs.aclopt = ast_append_ha("deny", ACL_CONFIG_DENY, configs.aclopt, &error);
|
||||||
@@ -865,7 +885,7 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
|
|
||||||
#define NOT_EQUAL_FAIL(field) \
|
#define NOT_EQUAL_FAIL(field) \
|
||||||
if (arr[x]->field != control->field) { \
|
if (arr[x]->field != control->field) { \
|
||||||
ast_test_status_update(test, "%s di not match: %d != %d with x = %d\n", #field, arr[x]->field, control->field, x); \
|
ast_test_status_update(test, "%s did not match: %d != %d with x = %d\n", #field, arr[x]->field, control->field, x); \
|
||||||
res = AST_TEST_FAIL; \
|
res = AST_TEST_FAIL; \
|
||||||
}
|
}
|
||||||
for (x = 0; x < 4; x++) {
|
for (x = 0; x < 4; x++) {
|
||||||
@@ -874,6 +894,7 @@ AST_TEST_DEFINE(config_options_test)
|
|||||||
NOT_EQUAL_FAIL(intopt);
|
NOT_EQUAL_FAIL(intopt);
|
||||||
NOT_EQUAL_FAIL(uintopt);
|
NOT_EQUAL_FAIL(uintopt);
|
||||||
NOT_EQUAL_FAIL(boolopt);
|
NOT_EQUAL_FAIL(boolopt);
|
||||||
|
NOT_EQUAL_FAIL(flags);
|
||||||
NOT_EQUAL_FAIL(customopt);
|
NOT_EQUAL_FAIL(customopt);
|
||||||
if (fabs(arr[x]->doubleopt - control->doubleopt) > 0.001) {
|
if (fabs(arr[x]->doubleopt - control->doubleopt) > 0.001) {
|
||||||
ast_test_status_update(test, "doubleopt did not match: %f vs %f on loop %d\n", arr[x]->doubleopt, control->doubleopt, x);
|
ast_test_status_update(test, "doubleopt did not match: %f vs %f on loop %d\n", arr[x]->doubleopt, control->doubleopt, x);
|
||||||
|
Reference in New Issue
Block a user