[asterisk-commits] twilson: branch twilson/config_work r366127 - in /team/twilson/config_work: a...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Thu May 10 13:43:02 CDT 2012


Author: twilson
Date: Thu May 10 13:42:55 2012
New Revision: 366127

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=366127
Log:
Death to boiler plate code

Removes a lot of the boiler-plate allocation stuff for aco_types by having
them just be stack allocated--they never really change and exist for the
lifetime of the module.

Since I'm already using a variable-length array in aco_info for the "preload"
field (which won't be used as often as types), I can't easily define the types
field without an intermediary step. I'll probably switch the variable length
array to handling the types, then come up with something different for preload.

Modified:
    team/twilson/config_work/apps/app_skel.c
    team/twilson/config_work/include/asterisk/config_options.h
    team/twilson/config_work/main/config_options.c
    team/twilson/config_work/main/udptl.c

Modified: team/twilson/config_work/apps/app_skel.c
URL: http://svnview.digium.com/svn/asterisk/team/twilson/config_work/apps/app_skel.c?view=diff&rev=366127&r1=366126&r2=366127
==============================================================================
--- team/twilson/config_work/apps/app_skel.c (original)
+++ team/twilson/config_work/apps/app_skel.c Thu May 10 13:42:55 2012
@@ -142,10 +142,39 @@
 #define PVT_BUCKETS 17
 
 static AO2_GLOBAL_OBJ_STATIC(global_config, NUM_GLOBAL_OBJECTS);
+static void *skel_pvt_cfg_alloc(const char *cat);
+static int skel_containers_alloc(struct ao2_container **newpvts, struct ao2_container **newcfgs);
+static void *skel_find_or_create_pvt(const char *category);
+static void *skel_find_pvt(struct ao2_container *tmp_container, const char *category);
+
+static void *skel_global_alloc(const char *cat);
+
+static struct aco_type general_options = {
+	.type = GLOBAL_OBJ,
+	.global_index = GLOBAL_OPTIONS,
+	.category_allow = ACO_WHITELIST,
+	.category = "general",
+	.cfg_alloc = (aco_type_alloc) skel_global_alloc,
+};
+
+static struct aco_type private_options = {
+	.type = PRIVATE_OBJ,
+	.pvt_index = PVT_CONTAINER,
+	.cfg_index = PVT_CFG_CONTAINER,
+	.category_allow = ACO_BLACKLIST,
+	.category = "general",
+	.cfg_alloc = skel_pvt_cfg_alloc,
+	.containers_alloc = skel_containers_alloc,
+	.find_or_create_pvt = skel_find_or_create_pvt,
+	.find_pvt = skel_find_pvt,
+};
+
+struct aco_type *types[] = { &general_options, &private_options, NULL };
 
 CONFIG_INFO_STANDARD(cfg_info,
 	.filename = "app_skel.conf",
 	.current_array = &global_config.global,
+	.types = types,
 );
 
 static void skel_global_config_destructor(void *obj)
@@ -324,7 +353,7 @@
 	return obj;
 }
 
-static struct skel_pvt_config *skel_pvt_cfg_alloc(const char *cat)
+static void *skel_pvt_cfg_alloc(const char *cat)
 {
 	struct skel_pvt_config *pvtcfg;
 
@@ -347,7 +376,7 @@
 	return pvtcfg;
 }
 
-static struct skel_global_config *skel_global_alloc(const char *cat)
+static void *skel_global_alloc(const char *cat)
 {
 	struct skel_global_config *cfg;
 
@@ -469,66 +498,25 @@
 	return ast_unregister_application(app);
 }
 
-static struct aco_type general_options = {
-	.type = GLOBAL_OBJ,
-	.name = "global",
-	.global_index = GLOBAL_OPTIONS,
-	.category_allow = ACO_WHITELIST,
-	.category = "general",
-	.cfg_alloc = (aco_type_alloc) skel_global_alloc,
-};
-
-static struct aco_type private_options = {
-	.type = PRIVATE_OBJ,
-	.name = "private",
-	.pvt_index = PVT_CONTAINER,
-	.cfg_index = PVT_CFG_CONTAINER,
-	.category_allow = ACO_BLACKLIST,
-	.category = "general",
-	.cfg_alloc = (aco_type_alloc) skel_pvt_cfg_alloc,
-	.containers_alloc = skel_containers_alloc,
-	.find_or_create_pvt = skel_find_or_create_pvt,
-	.find_pvt = skel_find_pvt,
-};
-
 static int load_module(void)
 {
-	RAII_VAR(struct aco_type *, global_type, NULL, ao2_cleanup);
-	RAII_VAR(struct aco_type *, priv_type, NULL, ao2_cleanup);
-
 	if (aco_info_init(&cfg_info)) {
 		goto error;
 	}
 
-	if (!(global_type = aco_type_object(&general_options))) {
-		goto error;
-	}
-
-	if (!(priv_type = aco_type_object(&private_options))) {
-		goto error;
-	}
-
-	if (aco_type_register(&cfg_info, global_type)) {
-		goto error;
-	}
-
-	if (aco_type_register(&cfg_info, priv_type)) {
-		goto error;
-	}
-
 	/* General Options */
-	aco_option_register(&cfg_info, "foo", global_type, "booya", OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, foo));
-	aco_option_register(&cfg_info, "bar", global_type, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, bar));
-	aco_option_register(&cfg_info, "baz", global_type, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, baz));
-	aco_option_register(&cfg_info, "blah", global_type, NULL, OPT_BOOL_T, 1, FLDSET(struct skel_global_config, blah));
-	aco_option_register(&cfg_info, "bindaddr", global_type, "0.0.0.0:1234", OPT_SOCKADDR_T, PARSE_PORT_REQUIRE, FLDSET(struct skel_global_config, bindaddr));
+	aco_option_register(&cfg_info, "foo", &general_options, "booya", OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, foo));
+	aco_option_register(&cfg_info, "bar", &general_options, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, bar));
+	aco_option_register(&cfg_info, "baz", &general_options, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_global_config, baz));
+	aco_option_register(&cfg_info, "blah", &general_options, NULL, OPT_BOOL_T, 1, FLDSET(struct skel_global_config, blah));
+	aco_option_register(&cfg_info, "bindaddr", &general_options, "0.0.0.0:1234", OPT_SOCKADDR_T, PARSE_PORT_REQUIRE, FLDSET(struct skel_global_config, bindaddr));
 
 	/* Private Options */
-	aco_option_register(&cfg_info, "description", priv_type, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_pvt_config, description));
-	aco_option_register(&cfg_info, "allow", priv_type, "ulaw,alaw", OPT_CODEC_T, 1, FLDSET(struct skel_pvt_config, prefs, caps));
-	aco_option_register(&cfg_info, "permit", priv_type, NULL, OPT_ACL_T, 1, FLDSET(struct skel_pvt_config, permit));
-	aco_option_register_custom(&cfg_info, "bit1", priv_type, "yes", custom_bitfield_handler, 0);
-	aco_option_register_custom(&cfg_info, "bit2", priv_type, "no", custom_bitfield_handler, 0);
+	aco_option_register(&cfg_info, "description", &private_options, NULL, OPT_STRINGFIELD_T, 0, STRFLDSET(struct skel_pvt_config, description));
+	aco_option_register(&cfg_info, "allow", &private_options, "ulaw,alaw", OPT_CODEC_T, 1, FLDSET(struct skel_pvt_config, prefs, caps));
+	aco_option_register(&cfg_info, "permit", &private_options, NULL, OPT_ACL_T, 1, FLDSET(struct skel_pvt_config, permit));
+	aco_option_register_custom(&cfg_info, "bit1", &private_options, "yes", custom_bitfield_handler, 0);
+	aco_option_register_custom(&cfg_info, "bit2", &private_options, "no", custom_bitfield_handler, 0);
 
 	if (aco_process_config(&cfg_info, 0)) {
 		goto error;

Modified: team/twilson/config_work/include/asterisk/config_options.h
URL: http://svnview.digium.com/svn/asterisk/team/twilson/config_work/include/asterisk/config_options.h?view=diff&rev=366127&r1=366126&r2=366127
==============================================================================
--- team/twilson/config_work/include/asterisk/config_options.h (original)
+++ team/twilson/config_work/include/asterisk/config_options.h Thu May 10 13:42:55 2012
@@ -47,8 +47,6 @@
 	ACO_WHITELIST,
 };
 
-struct aco_type *aco_type_object(struct aco_type *type);
-
 /* Callback functions for option parsing via aco_process_config() */
 
 /*! \brief Allocate a configurable ao2 object
@@ -112,7 +110,6 @@
 struct aco_type {
 	/* common stuff */
 	enum aco_type_t type;   /*!< Whether this is a global or private type */
-	const char *name;
 	const char *category;   /*!< A regular expression for matching categories to be allowed or denied */
 	const char *matchfield; /*!< An option name to match for this type (i.e. a 'type'-like column) */
 	const char *matchvalue; /*!< The value of the option to require for matching (i.e. 'peer' for type= in sip.conf) */
@@ -131,29 +128,18 @@
 	aco_type_prelink prelink;             /*!< An optional callback function that is called after config processing, but before applying changes */
 };
 
-/*! \brief Allocate a container for aco_types
- *
- * \note If using aco_process_config, this function is unnecessary as calling aco_info_init
- * will take care of allocating a container for aco_types in the aco_info struct. This is
- * made public in case manual config processing is needed.
- *
- * \retval NULL error
- * \retval non-NULL a new ao2 container for storing aco_type objects
- */
-struct ao2_container *aco_type_container_alloc(void);
-
 /*! \brief A callback function for applying the config changes
  * \retval 0 Success
  * \retval non-zero Failure. Changes not applied
  */
-typedef int (*aco_apply_config)(void);
+typedef int (*aco_pre_apply_config)(void);
 
 struct aco_info {
 	const char *module;
 	const char *filename;
 	struct ao2_container *opts;
-	struct ao2_container *types;
-	aco_apply_config apply_config;
+	struct aco_type **types;
+	aco_pre_apply_config pre_apply_config;
 	struct ao2_global_obj *current_array;
 	void **new_array;
 	const char *preload[]; /* Use a sentinel! Even if preload is empty! */
@@ -166,7 +152,7 @@
  * \code
  * CONFIG_INFO_STANDARD(cfg_info,
  *     .filename = "app_skel.conf",
- *     .apply_config = skel_apply_config,
+ *     .pre_apply_config = skel_pre_apply_config,
  * );
  * ...
  * if (aco_info_init(&cfg_info)) {
@@ -195,53 +181,6 @@
  * \param info The address of the aco_info struct to destroy
  */
 void aco_info_destroy(struct aco_info *info);
-
-/*! \brief Register an aco_type with an aco_info struct
- * \param info The address of the aco_info struct to register the aco_info with
- * \param obj The aco_type to register
- * \retval 0 Success
- * \retval non-zero Failure
- */
-int aco_type_register(struct aco_info *info, struct aco_type *obj);
-
-/*! \brief Find an aco_type registered to an aco_info by name
- * \param info The aco_info containing the aco_type
- * \param name The unique name of the aco_type to find
- * \retval NULL aco_type not found
- * \retval non-NULL A referenced pointer to the aco_type
- */
-struct aco_type *aco_type_find(struct aco_info *info, const char *name); 
-
-/*! \brief Get the specified global config after processing
- * \note This function is most likely used in the apply_config callback
- * \param info The aco_info to query for the global config object
- * \param name The unique name of the aco_type associated with the config
- * \retval NULL Not found.
- * \retval non-NULL A referenced pointer to the newly configured global config object
- */
-void *aco_info_new_global_get(struct aco_info *info, const char *name);
-
-/*! \brief Get the specified private container after config processing
- * \note This function is most likely used in the apply_config callback. The container
- * will be a mix of new and existing privates that can be swapped out with the existing
- * live container of privates.
- * \param info The aco_info to query for the container of privates
- * \param name The unique name of the aco_type associated with the privates
- * \retval NULL Not found.
- * \retval non-NULL A referenced pointer to the newly configured container of privates
- */
-struct ao2_container *aco_info_new_privates_get(struct aco_info *info, const char *name);
-
-/*! \brief Get the specified private config container after config processing
- * \note This function is most likely used in the apply_config callback. The container
- * will be of new privates configs that can be swapped out with the existing
- * live container of private configs.
- * \param info The aco_info to query for the container of private configs
- * \param name The unique name of the aco_type associated with the private configs
- * \retval NULL Not found.
- * \retval non-NULL A referenced pointer to the newly configured container of private configs
- */
-struct ao2_container *aco_info_new_configs_get(struct aco_info *info, const char *name);
 
 /*! \brief The option types with default handlers
  *

Modified: team/twilson/config_work/main/config_options.c
URL: http://svnview.digium.com/svn/asterisk/team/twilson/config_work/main/config_options.c?view=diff&rev=366127&r1=366126&r2=366127
==============================================================================
--- team/twilson/config_work/main/config_options.c (original)
+++ team/twilson/config_work/main/config_options.c Thu May 10 13:42:55 2012
@@ -53,10 +53,7 @@
 
 static void config_option_destroy(void *obj)
 {
-	struct aco_option *opt = obj;
-	if (opt->obj) {
-		ao2_ref(opt->obj, -1);
-	}
+	return;
 }
 
 static int ast_config_option_int_fn(const struct aco_option *opt, struct ast_variable *var, void *obj);
@@ -136,7 +133,6 @@
 	va_end(ap);
 
 	opt->name = name;
-	ao2_ref(obj, +1);
 	opt->obj = obj;
 	opt->default_val = default_val;
 	opt->type = type;
@@ -184,88 +180,82 @@
 	return ao2_container_alloc(CONFIG_OPT_BUCKETS, config_opt_hash, config_opt_cmp);
 }
 
-static int allocate_temp_objects(void *obj, void *arg, void *data, int flags)
-{
-	struct aco_type *t = obj;
-	struct aco_info *info = arg;
-	int *error = data;
-
-	switch (t->type) {
-	case GLOBAL_OBJ:
-		if (!(info->new_array[t->global_index] = t->cfg_alloc(NULL))) {
-			*error = -1;
-			return CMP_STOP;
-		}
+static int allocate_temp_objects(struct aco_info *info)
+{
+	struct aco_type *t;
+	size_t x;
+
+	for (x = 0, t = info->types[x]; t; t = info->types[++x]) {
+		switch (t->type) {
+		case GLOBAL_OBJ:
+			if (!(info->new_array[t->global_index] = t->cfg_alloc(NULL))) {
+				return -1;
+			}
+			break;
+		case PRIVATE_OBJ:
+			if (t->containers_alloc((struct ao2_container **) &info->new_array[t->pvt_index], (struct ao2_container **) &info->new_array[t->cfg_index])) {
+				return -1;
+			}
+			break;
+		}
+	}
+	return 0;
+}
+
+static void cleanup_temp_objects(struct aco_info *info)
+{
+	struct aco_type *t;
+	size_t x;
+
+	for (x = 0, t = info->types[x]; t; t = info->types[++x]) {
+		switch (t->type) {
+		case GLOBAL_OBJ:
+			if (info->new_array[t->global_index]) {
+				ao2_ref(info->new_array[t->global_index], -1);
+				info->new_array[t->global_index] = NULL;
+			}
+			break;
+		case PRIVATE_OBJ:
+			if (info->new_array[t->pvt_index]) {
+				ao2_ref(info->new_array[t->pvt_index], -1);
+				info->new_array[t->pvt_index] = NULL;
+			}
+			if (info->new_array[t->cfg_index]) {
+				ao2_ref(info->new_array[t->cfg_index], -1);
+				info->new_array[t->cfg_index] = NULL;
+			}
+			break;
+		}
+	}
+}
+
+static struct aco_type *internal_aco_type_find(struct aco_info *info, struct ast_config *cfg, const char *category)
+{
+	size_t x;
+	struct aco_type *match;
+	const char *val;
+
+	for (x = 0, match = info->types[x]; match; match = info->types[++x]) {
+		/* First make sure we are an object that can service this category */
+		if (!regexec(match->regex, category, 0, NULL, 0) == !match->category_allow) {
+			continue;
+		}
+
+		/* Then, see if we need to match a particular field */
+		if (!ast_strlen_zero(match->matchfield) && !ast_strlen_zero(match->matchvalue)) {
+			if (!(val = ast_variable_retrieve(cfg, category, match->matchfield))) {
+				ast_log(LOG_ERROR, "Required match field '%s' not found\n", match->matchfield);
+				return NULL;
+			}
+			if (strcasecmp(val, match->matchvalue)) {
+				continue;
+			}
+		}
+		/* If we get this far, we're a match */
 		break;
-	case PRIVATE_OBJ:
-		if (t->containers_alloc((struct ao2_container **) &info->new_array[t->pvt_index], (struct ao2_container **) &info->new_array[t->cfg_index])) {
-			*error = -1;
-			return CMP_STOP;
-		}
-		break;
-	}
-	return 0;
-}
-
-static int cleanup_temp_objects(void *obj, void *arg, int flags)
-{
-	struct aco_type *t = obj;
-	struct aco_info *info = arg;
-	if (!t) {
-		return 0;
-	}
-
-	switch (t->type) {
-	case GLOBAL_OBJ:
-		if (info->new_array[t->global_index]) {
-			ao2_ref(info->new_array[t->global_index], -1);
-			info->new_array[t->global_index] = NULL;
-		}
-		break;
-	case PRIVATE_OBJ:
-		if (info->new_array[t->pvt_index]) {
-			ao2_ref(info->new_array[t->pvt_index], -1);
-			info->new_array[t->pvt_index] = NULL;
-		}
-		if (info->new_array[t->cfg_index]) {
-			ao2_ref(info->new_array[t->cfg_index], -1);
-			info->new_array[t->cfg_index] = NULL;
-		}
-		break;
-	}
-
-	return 0;
-}
-
-static int type_category_cmp(void *obj, void *arg, void *data, int flags)
-{
-	struct aco_type *match = obj;
-	const char *category = arg;
-	struct ast_config *cfg = data;
-	const char *val;
-
-	/* First make sure we are an object that can service this category */
-	if (!regexec(match->regex, category, 0, NULL, 0) == !match->category_allow) {
-		return 0;
-	}
-
-	/* Then, see if we need to match a particular field */
-	if (!ast_strlen_zero(match->matchfield) && !ast_strlen_zero(match->matchvalue)) {
-		if (!(val = ast_variable_retrieve(cfg, category, match->matchfield))) {
-			ast_log(LOG_ERROR, "Required match field '%s' not found\n", match->matchfield);
-			return CMP_STOP;
-		}
-		if (strcasecmp(val, match->matchvalue)) {
-			return 0;
-		}
-	}
-
-	return CMP_MATCH | CMP_STOP;
-}
-
-static struct aco_type *internal_aco_type_find(struct ao2_container *container, struct ast_config *cfg, const char *category)
-{
-	return ao2_callback_data(container, 0, type_category_cmp, (void *) category, (void *) cfg);
+	}
+
+	return match;
 }
 
 static int is_preload(struct aco_info *info, const char *cat)
@@ -287,7 +277,7 @@
 static int process_category(struct ast_config *cfg, struct aco_info *info, const char *cat, int preload) {
 	RAII_VAR(void *, tmppvt, NULL, ao2_cleanup);
 	RAII_VAR(void *, tmpcfg, NULL, ao2_cleanup);
-	RAII_VAR(struct aco_type *, obj, NULL, ao2_cleanup);
+	struct aco_type *obj;
 
 	/* Skip preloaded categories if we aren't preloading */
 	if (!preload && is_preload(info, cat)) {
@@ -295,7 +285,7 @@
 	}
 
 	/* Find config object by category, if not found it is an error */
-	if (!(obj = internal_aco_type_find(info->types, cfg, cat))) {
+	if (!(obj = internal_aco_type_find(info, cfg, cat))) {
 		ast_log(LOG_ERROR, "Could not find config type for category '%s' in '%s'\n", cat, info->filename);
 		return -1;
 	}
@@ -383,7 +373,7 @@
 	struct ast_config *cfg;
 	struct ast_flags cfg_flags = { reload ? CONFIG_FLAG_FILEUNCHANGED : 0, };
 	const char *cat = NULL;
-	int err = 0, res;
+	int res;
 
 	if (ast_strlen_zero(info->filename)) {
 		ast_log(LOG_ERROR, "No filename given, cannot proceed!\n");
@@ -404,9 +394,7 @@
 		return -1;
 	}
 
-	ao2_callback_data(info->types, OBJ_NODATA, allocate_temp_objects, info, &err);
-
-	if (err) {
+	if (allocate_temp_objects(info)) {
 		ast_log(LOG_ERROR, "In %s: Could not allocate temporary objects\n", info->filename);
 		goto error;
 	}
@@ -428,14 +416,18 @@
 
 	ast_config_destroy(cfg);
 
+	if (info->pre_apply_config && info->pre_apply_config()) {
+		goto error;
+	}
+
 	res = apply_config(info); /* The module already knows where the objects are */
-	ao2_callback(info->types, OBJ_NODATA, cleanup_temp_objects, info);
+	cleanup_temp_objects(info);
 
 	return res;
 
 error:
 	ast_config_destroy(cfg);
-	ao2_callback(info->types, OBJ_NODATA, cleanup_temp_objects, info);
+	cleanup_temp_objects(info);
 	return -1;
 }
 
@@ -463,21 +455,53 @@
 	return 0;
 }
 
+static void internal_type_destroy(struct aco_type *type)
+{
+	if (type->regex) {
+		regfree(type->regex);
+		ast_free(type->regex);
+	}
+}
+
+static void internal_info_types_destroy(struct aco_info *info)
+{
+	size_t x;
+	struct aco_type *t;
+
+	for (x = 0, t = info->types[x]; t; t = info->types[++x]) {
+		internal_type_destroy(t);
+		t = NULL;
+	}
+}
+
+static int internal_type_init(struct aco_type *type)
+{
+	if (!(type->regex = build_category_regex(type->category))) {
+		return -1;
+	}
+	return 0;
+}
+
 int aco_info_init(struct aco_info *info)
 {
+	size_t x;
+	struct aco_type *t;
 	if (!(info->opts = aco_option_container_alloc())) {
 		return -1;
 	}
-	if (!(info->types = aco_type_container_alloc())) {
-		ao2_ref(info->opts, -1);
-		info->opts = NULL;
-		return -1;
-	}
+
+	for (x = 0, t = info->types[x]; t; t = info->types[++x]) {
+		if (internal_type_init(t)) {
+			ao2_ref(info->opts, -1);
+			info->opts = NULL;
+			internal_info_types_destroy(info);
+			return -1;
+		}
+	}
+
 	if (!(info->new_array = ast_calloc(info->current_array->num_elements, sizeof(info->new_array)))) {
 		ao2_ref(info->opts, -1);
 		info->opts = NULL;
-		ao2_ref(info->types, -1);
-		info->types = NULL;
 		return -1;
 	}
 	return 0;
@@ -488,9 +512,7 @@
 	if (info->opts) {
 		ao2_ref(info->opts, -1);
 	}
-	if (info->types) {
-		ao2_ref(info->types, -1);
-	}
+	internal_info_types_destroy(info);
 	ast_free(info->new_array);
 }
 
@@ -533,102 +555,6 @@
 	}
 
 	return 0;
-}
-
-static int type_hash(const void *obj, const int flags)
-{
-	const struct aco_type *object = obj;
-	const char *name = (flags & OBJ_KEY) ? obj : object->name;
-	return ast_str_case_hash(name);
-}
-
-static int type_cmp(void *obj, void *arg, int flags)
-{
-	struct aco_type *obj1 = obj, *obj2 = arg;
-	const char *name = (flags & OBJ_KEY) ? arg : obj2->name;
-	return strcasecmp(obj1->name, name) ? 0 : CMP_STOP | CMP_MATCH;
-}
-
-struct ao2_container *aco_type_container_alloc(void)
-{
-	return ao2_container_alloc(3, type_hash, type_cmp);
-}
-
-static void config_obj_destructor(void *o)
-{
-	struct aco_type *obj = o;
-	if (obj->regex) {
-		regfree(obj->regex);
-		ast_free(obj->regex);
-	}
-	return;
-}
-
-struct aco_type *aco_type_object(struct aco_type *type)
-{
-	struct aco_type *obj;
-
-	if (!(obj = ao2_alloc(sizeof(*obj), config_obj_destructor))) {
-		return NULL;
-	}
-	*obj = *type;
-	if (!(obj->regex = build_category_regex(obj->category))) {
-		ao2_ref(obj, -1);
-		return NULL;
-	}
-	return obj;
-}
-
-int aco_type_register(struct aco_info *info, struct aco_type *obj)
-{
-	if (!info->types) {
-		return -1;
-	}
-	return !ao2_link(info->types, obj);
-}
-
-struct aco_type *aco_type_find(struct aco_info *info, const char *name)
-{
-	if (!info->types) {
-		return NULL;
-	}
-	return ao2_find(info->types, name, OBJ_KEY);
-}
-
-void *aco_info_new_global_get(struct aco_info *info, const char *name)
-{
-	RAII_VAR(struct aco_type *, type, aco_type_find(info, name), ao2_cleanup); 
-	if (!type) {
-		return NULL;
-	}
-	if (info->new_array[type->global_index]) {
-		ao2_ref(info->new_array[type->global_index], +1);
-	}
-	return info->new_array[type->global_index];
-}
-
-struct ao2_container *aco_info_new_privates_get(struct aco_info *info, const char *name)
-{
-	RAII_VAR(struct aco_type *, type, aco_type_find(info, name), ao2_cleanup); 
-	if (!type) {
-		return NULL;
-	}
-	if (info->new_array[type->pvt_index]) {
-		ao2_ref(info->new_array[type->pvt_index], +1);
-	}
-	return info->new_array[type->pvt_index];
-}
-
-struct ao2_container *aco_info_new_configs_get(struct aco_info *info, const char *name)
-{
-	RAII_VAR(struct aco_type *, type, aco_type_find(info, name), ao2_cleanup); 
-	if (!type) {
-		return NULL;
-	}
-	if (info->new_array[type->cfg_index]) {
-		ao2_ref(info->new_array[type->cfg_index], +1);
-	}
-	return info->new_array[type->cfg_index];
 }
 
 /* default config option handlers */

Modified: team/twilson/config_work/main/udptl.c
URL: http://svnview.digium.com/svn/asterisk/team/twilson/config_work/main/udptl.c?view=diff&rev=366127&r1=366126&r2=366127
==============================================================================
--- team/twilson/config_work/main/udptl.c (original)
+++ team/twilson/config_work/main/udptl.c Thu May 10 13:42:55 2012
@@ -186,8 +186,6 @@
 	unsigned int use_even_ports;
 };
 
-static int udptl_apply_config(void);
-
 enum {
 	UDPTL_GENERAL = 0,
 
@@ -197,10 +195,24 @@
 
 static AO2_GLOBAL_OBJ_STATIC(globals, UDPTL_NUM_GLOBALS);
 
+static void *udptl_cfg_alloc(const char *unused);
+static int udptl_pre_apply_config(void);
+
+static struct aco_type general_options = {
+	.type = GLOBAL_OBJ,
+	.global_index = UDPTL_GENERAL, 
+	.category_allow = ACO_WHITELIST,
+	.category = "general",
+	.cfg_alloc = udptl_cfg_alloc,
+};
+
+static struct aco_type *types[] = { &general_options, NULL };
+
 CONFIG_INFO_STANDARD(cfg_info,
 	.filename = "udptl.conf",
-	.apply_config = udptl_apply_config,
+	.pre_apply_config = udptl_pre_apply_config,
 	.current_array = &globals.global,
+	.types = types,
 );
 
 static inline int udptl_debug_test_addr(const struct ast_sockaddr *addr)
@@ -1398,8 +1410,8 @@
 	}
 }
 
-static int udptl_apply_config(void) {
-	RAII_VAR(struct udptl_global_options *, new_global, aco_info_new_global_get(&cfg_info, "global"), ao2_cleanup);
+static int udptl_pre_apply_config(void) {
+	struct udptl_global_options * new_global = cfg_info.new_array[UDPTL_GENERAL];
 
 	if (!new_global) {
 		return -1;
@@ -1443,57 +1455,36 @@
 	return 0;
 }
 
-static struct aco_type general_options = {
-	.type = GLOBAL_OBJ,
-	.name = "global",
-	.global_index = UDPTL_GENERAL, 
-	.category_allow = ACO_WHITELIST,
-	.category = "general",
-	.cfg_alloc = udptl_cfg_alloc,
-};
-
 void ast_udptl_init(void)
 {
-	RAII_VAR(struct aco_type *, global_type, NULL, ao2_cleanup);
-
 	if (aco_info_init(&cfg_info)) {
 		return;
 	}
 
-	if (!(global_type = aco_type_object(&general_options))) {
-		aco_info_destroy(&cfg_info);
-		return;
-	}
-
-	if (aco_type_register(&cfg_info, global_type)) {
-		aco_info_destroy(&cfg_info);
-		return;
-	}
-
-	aco_option_register(&cfg_info, "udptlstart", global_type, STR(DEFAULT_UDPTLSTART),
+	aco_option_register(&cfg_info, "udptlstart", &general_options, STR(DEFAULT_UDPTLSTART),
 		OPT_UINT_T, PARSE_IN_RANGE | PARSE_DEFAULT,
 		FLDSET(struct udptl_global_options, start), DEFAULT_UDPTLSTART, 1024, 65535);
 
-	aco_option_register(&cfg_info, "udptlend", global_type, STR(DEFAULT_UDPTLEND),
+	aco_option_register(&cfg_info, "udptlend", &general_options, STR(DEFAULT_UDPTLEND),
 		OPT_UINT_T, PARSE_IN_RANGE | PARSE_DEFAULT,
 		FLDSET(struct udptl_global_options, end), DEFAULT_UDPTLEND, 1024, 65535);
 
-	aco_option_register(&cfg_info, "udptlfecentries", global_type, NULL,
+	aco_option_register(&cfg_info, "udptlfecentries", &general_options, NULL,
 		OPT_UINT_T, PARSE_IN_RANGE | PARSE_RANGE_DEFAULTS,
 		FLDSET(struct udptl_global_options, fecentries), 1, MAX_FEC_ENTRIES);
 
-	aco_option_register(&cfg_info, "udptlfecspan", global_type, NULL,
+	aco_option_register(&cfg_info, "udptlfecspan", &general_options, NULL,
 		OPT_UINT_T, PARSE_IN_RANGE | PARSE_RANGE_DEFAULTS,
 		FLDSET(struct udptl_global_options, fecspan), 1, MAX_FEC_SPAN);
 
-	aco_option_register(&cfg_info, "udptlchecksums", global_type, "yes",
+	aco_option_register(&cfg_info, "udptlchecksums", &general_options, "yes",
 		OPT_BOOL_T, 0, FLDSET(struct udptl_global_options, nochecksums));
 
-	aco_option_register(&cfg_info, "use_even_ports", global_type, "no",
+	aco_option_register(&cfg_info, "use_even_ports", &general_options, "no",
 		OPT_BOOL_T, 1, FLDSET(struct udptl_global_options, use_even_ports));
 
-	aco_option_register_custom(&cfg_info, "t38faxudpec", global_type, NULL, removed_options_handler, 0);
-	aco_option_register_custom(&cfg_info, "t38faxmaxdatagram", global_type, NULL, removed_options_handler, 0);
+	aco_option_register_custom(&cfg_info, "t38faxudpec", &general_options, NULL, removed_options_handler, 0);
+	aco_option_register_custom(&cfg_info, "t38faxmaxdatagram", &general_options, NULL, removed_options_handler, 0);
 
 	ast_cli_register_multiple(cli_udptl, ARRAY_LEN(cli_udptl));
 




More information about the asterisk-commits mailing list