[asterisk-commits] file: branch file/sorcery r377990 - in /team/file/sorcery: include/asterisk/ ...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Thu Dec 13 13:49:57 CST 2012


Author: file
Date: Thu Dec 13 13:49:54 2012
New Revision: 377990

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=377990
Log:
Throwing some stuff at the wall to see what sticks.

Modified:
    team/file/sorcery/include/asterisk/sorcery.h
    team/file/sorcery/main/sorcery.c

Modified: team/file/sorcery/include/asterisk/sorcery.h
URL: http://svnview.digium.com/svn/asterisk/team/file/sorcery/include/asterisk/sorcery.h?view=diff&rev=377990&r1=377989&r2=377990
==============================================================================
--- team/file/sorcery/include/asterisk/sorcery.h (original)
+++ team/file/sorcery/include/asterisk/sorcery.h Thu Dec 13 13:49:54 2012
@@ -112,6 +112,23 @@
 struct ast_sorcery *ast_sorcery_open(const char *name);
 
 /*!
+ * \brief Apply default object wizard mappings
+ *
+ * \param sorcery Pointer to a sorcery structure
+ * \param type Type of object to apply to
+ * \param name Name of the wizard to use
+ * \param data Data to be passed to wizard
+ *
+ * \retval 0 success
+ * \retval -1 failure
+ *
+ * \note This should be called *after* applying configuration sourced mappings
+ *
+ * \note Only a single default can exist per object type
+ */
+int ast_sorcery_apply_default(struct ast_sorcery *sorcery, const char *type, const char *name, const char *data);
+
+/*!
  * \brief Increase the reference count of a sorcery structure
  *
  * \param sorcery Pointer to a sorcery structure

Modified: team/file/sorcery/main/sorcery.c
URL: http://svnview.digium.com/svn/asterisk/team/file/sorcery/main/sorcery.c?view=diff&rev=377990&r1=377989&r2=377990
==============================================================================
--- team/file/sorcery/main/sorcery.c (original)
+++ team/file/sorcery/main/sorcery.c Thu Dec 13 13:49:54 2012
@@ -35,6 +35,7 @@
 #include "asterisk/sorcery.h"
 #include "asterisk/astobj2.h"
 #include "asterisk/strings.h"
+#include "asterisk/config_options.h"
 
 /*! \brief Number of buckets for wizards */
 #define WIZARD_BUCKETS 7
@@ -46,6 +47,21 @@
 struct ast_sorcery_object_type {
 	/*! \brief Unqiue name of the object type */
 	char name[MAX_OBJECT_TYPE];
+
+	/*! \brief Wizard instances */
+	struct ao2_container *wizards;
+
+	/*! \brief Pointer to the configuration framework details for the object */
+	struct aco_type *type;
+};
+
+/*! \brief Structure for a wizard instance which operates on objects */
+struct ast_sorcery_object_wizard {
+	/*! \brief Wizard interface itself */
+	struct ast_sorcery_wizard *wizard;
+
+	/*! \brief Unique data for the wizard */
+	void *data;
 };
 
 /*! \brief Full structure for sorcery */
@@ -135,6 +151,27 @@
 /*! \brief Destructor called when sorcery structure is destroyed */
 static void sorcery_destructor(void *obj)
 {
+	struct ast_sorcery *sorcery = obj;
+
+	ao2_cleanup(sorcery->types);
+}
+
+/*! \brief Hashing function for sorcery types */
+static int sorcery_type_hash(const void *obj, const int flags)
+{
+	const struct ast_sorcery_object_type *type = obj;
+	const char *name = obj;
+
+	return ast_str_hash(flags & OBJ_KEY ? name : type->name);
+}
+
+/*! \brief Comparator function for sorcery types */
+static int sorcery_type_cmp(void *obj, void *arg, int flags)
+{
+	struct ast_sorcery_object_type *type1 = obj, *type2 = arg;
+	const char *name = arg;
+
+	return !strcmp(type1->name, flags & OBJ_KEY ? name : type2->name) ? CMP_MATCH | CMP_STOP : 0;
 }
 
 struct ast_sorcery *ast_sorcery_open(const char *name)
@@ -145,9 +182,29 @@
 		return NULL;
 	}
 
+	if (!(sorcery->types = ao2_container_alloc(TYPE_BUCKETS, sorcery_type_hash, sorcery_type_cmp))) {
+		ao2_ref(sorcery, -1);
+		sorcery = NULL;
+	}
+
 	return sorcery;
 }
 
+/*! \brief Internal function which allocates an object type structure */
+
+int ast_sorcery_apply_default(struct ast_sorcery *sorcery, const char *type, const char *name, const char *data)
+{
+	struct ast_sorcery_object_type *object_type = ao2_find(sorcery->types, type, OBJ_KEY);
+
+	/* Defaults can not overrule any existing wizards */
+	if (object_type) {
+		ao2_ref(object_type, -1);
+		return -1;
+	}
+
+	return 0;
+}
+
 void ast_sorcery_ref(struct ast_sorcery *sorcery)
 {
 	ao2_ref(sorcery, +1);
@@ -155,21 +212,75 @@
 
 void *ast_sorcery_alloc(const struct ast_sorcery *sorcery, const char *type, const char *id)
 {
-	return NULL;
+	RAII_VAR(struct ast_sorcery_object_type *, object_type, ao2_find(sorcery->types, type, OBJ_KEY), ao2_cleanup);
+	struct ast_sorcery_object_details *details;
+
+	if (!object_type || !object_type->type ||
+	    !(details = object_type->type->item_alloc(id))) {
+		return NULL;
+	}
+
+	ast_copy_string(details->id, id, sizeof(details->id));
+	ast_copy_string(details->type, type, sizeof(details->type));
+
+	if (aco_set_defaults(object_type->type, id, details)) {
+		ao2_ref(details, -1);
+		return NULL;
+	}
+
+	return details;
+}
+
+/*! \brief Internal function which returns if the wizard has created the object */
+static int sorcery_wizard_create(void *obj, void *arg, int flags)
+{
+	return CMP_MATCH | CMP_STOP;
 }
 
 int ast_sorcery_create(struct ast_sorcery *sorcery, void *object)
 {
+	struct ast_sorcery_object_details *details = object;
+	RAII_VAR(struct ast_sorcery_object_type *, object_type, ao2_find(sorcery->types, details->type, OBJ_KEY), ao2_cleanup);
+	RAII_VAR(struct ast_sorcery_object_wizard *, object_wizard, NULL, ao2_cleanup);
+
+	if (!object_type) {
+		return -1;
+	}
+
+	if ((object_wizard = ao2_callback(object_type->wizards, 0, sorcery_wizard_create, object))) {
+		/* Object was successfully created by the wizard so update the object details to reflect it */
+		details->wizard = object_wizard->wizard;
+		return 0;
+	} else {
+		return -1;
+	}
+}
+
+/*! \brief Internal function which returns the wizard responsible for the object */
+static int sorcery_wizard_match(void *obj, void *arg, int flags)
+{
+	struct ast_sorcery_object_wizard *wizard = obj;
+	struct ast_sorcery_object_details *details = arg;
+
+	return (wizard->wizard == details->wizard) ? CMP_MATCH | CMP_STOP : 0;
+}
+
+int ast_sorcery_update(struct ast_sorcery *sorcery, void *object)
+{
 	return -1;
 }
 
-int ast_sorcery_update(struct ast_sorcery *sorcery, void *object)
-{
-	return -1;
-}
-
 int ast_sorcery_delete(struct ast_sorcery *sorcery, void *object)
 {
+	struct ast_sorcery_object_details *details = object;
+	RAII_VAR(struct ast_sorcery_object_type *, object_type, ao2_find(sorcery->types, details->type, OBJ_KEY), ao2_cleanup);
+	RAII_VAR(struct ast_sorcery_object_wizard *, object_wizard, NULL, ao2_cleanup);
+
+	if (!object_type ||
+	    !(object_wizard = ao2_callback(object_type->wizards, 0, sorcery_wizard_match, details))) {
+		return -1;
+	}
+
 	return -1;
 }
 




More information about the asterisk-commits mailing list