[svn-commits] mmichelson: branch group/CCSS r230581 - /team/group/CCSS/channels/chan_sip.c

SVN commits to the Digium repositories svn-commits at lists.digium.com
Thu Nov 19 17:15:15 CST 2009


Author: mmichelson
Date: Thu Nov 19 17:15:13 2009
New Revision: 230581

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=230581
Log:
Make the EPA structures less over-engineered.

Pretty much sums it up. An EPA is much different from
an ESC, and so trying to mirror the behavior makes no
sense. 


Modified:
    team/group/CCSS/channels/chan_sip.c

Modified: team/group/CCSS/channels/chan_sip.c
URL: http://svnview.digium.com/svn/asterisk/team/group/CCSS/channels/chan_sip.c?view=diff&rev=230581&r1=230580&r2=230581
==============================================================================
--- team/group/CCSS/channels/chan_sip.c (original)
+++ team/group/CCSS/channels/chan_sip.c Thu Nov 19 17:15:13 2009
@@ -1675,66 +1675,101 @@
    	enum sip_cc_publish_state current_state;
 };
 
+struct sip_epa_entry;
+
+struct epa_static_data {
+	enum subscriptiontype event;
+	const char *name;
+	void (*handle_ok)(struct sip_pvt *, struct sip_request *, struct sip_epa_entry *);
+	void (*handle_error)(struct sip_pvt *, const int resp, struct sip_request *, struct sip_epa_entry *);
+};
+
+struct epa_backend {
+	const struct epa_static_data *static_data;
+	AST_LIST_ENTRY(epa_backend) next;
+};
+AST_LIST_HEAD_STATIC(epa_static_data_list, epa_backend);
+
+static int sip_epa_register(const struct epa_static_data *static_data)
+{
+	struct epa_backend *backend = ast_calloc(1, sizeof(*backend));
+
+	if (!backend) {
+		return -1;
+	}
+
+	backend->static_data = static_data;
+
+	AST_LIST_LOCK(&epa_static_data_list);
+	AST_LIST_INSERT_TAIL(&epa_static_data_list, backend, next);
+	AST_LIST_UNLOCK(&epa_static_data_list);
+	return 0;
+}
+
+static void cc_handle_ok(struct sip_pvt *, struct sip_request *, struct sip_epa_entry *);
+static void cc_handle_error(struct sip_pvt *, const int resp, struct sip_request *, struct sip_epa_entry *);
+
+static const struct epa_static_data cc_epa_static_data  = {
+	.event = CALL_COMPLETION,
+	.name = "call-completion",
+	.handle_ok = cc_handle_ok,
+	.handle_error = cc_handle_error,
+};
+
 struct sip_epa_entry {
 	/* When we send a PUBLISH, we have to be
    	 * sure to include the entity tag that we
    	 * received in the previous response.
    	 */
 	char entity_tag[SIPBUFSIZE];
-	/* The event package to which this
-   	 * entry belongs.
-   	 */
-	const char *event;
 	/* The destination to which this EPA should send
 	 * PUBLISHes. This may be the name of a SIP peer
 	 * or a hostname.
 	 */
 	char destination[SIPBUFSIZE];
-	/* Each event package will have data
-   	 * that pertains only to that event package
-   	 * and doesn't make sense to other event
-   	 * types. It is likely that the hash function
-   	 * and comparison function for a specific EPA
-   	 * will use event specific data
-   	 */
-	void *event_specific_data;
+	/* Every event package has some constant data and
+	 * callbacks that all instances will share. This
+	 * data resides in this field.
+	 */
+	const struct epa_static_data *static_data;
+	/* In addition to the static data that all instances
+	 * of sip_epa_entry will have, each instance will
+	 * require its own instance-specific data.
+	 */
+	void *instance_data;
 };
 
-struct sip_epa_callbacks {
-	void (*handle_ok)(struct sip_pvt *, struct sip_request *, struct sip_epa_entry *);
-	void (*handle_error)(struct sip_pvt *, const int resp, struct sip_request *, struct sip_epa_entry *);
-};
-
-static struct event_publication_agent {
-	enum subscriptiontype event;
-	const char *name;
-	struct ao2_container *entries;
-	struct sip_epa_callbacks *callbacks;
-} event_publication_agents [] = {
-	{.event = CALL_COMPLETION, .name = "call-completion",},
-};
-
-static struct sip_epa_entry *create_epa_entry(struct event_publication_agent *epa, struct sip_request *req, const char * const destination)
+static const struct epa_static_data *find_static_data(const char * const event_package)
+{
+	const struct epa_backend *backend = NULL;
+
+	AST_LIST_LOCK(&epa_static_data_list);
+	AST_LIST_TRAVERSE(&epa_static_data_list, backend, next) {
+		if (!strcmp(backend->static_data->name, event_package)) {
+			break;
+		}
+	}
+	AST_LIST_UNLOCK(&epa_static_data_list);
+	return backend ? backend->static_data : NULL;
+}
+
+static struct sip_epa_entry *create_epa_entry(const char * const event_package, const char * const destination)
 {
 	struct sip_epa_entry *epa_entry;
+	const struct epa_static_data *static_data;
 
 	if (!(epa_entry = ao2_alloc(sizeof(*epa_entry), NULL))) {
 		return NULL;
 	}
 
-	epa_entry->event = epa->name;
+	if (!(static_data = find_static_data(event_package))) {
+		ao2_ref(epa_entry, -1);
+		return NULL;
+	}
+
+	epa_entry->static_data = static_data;
 	ast_copy_string(epa_entry->destination, destination, sizeof(epa_entry->destination));
 	return epa_entry;
-}
-
-static struct event_publication_agent *get_epa(const char * const event_package) {
-	int i;
-	for (i = 0; i < ARRAY_LEN(event_publication_agents); i++) {
-		if (!strcasecmp(event_package, event_publication_agents[i].name)) {
-			return &event_publication_agents[i];
-		}
-	}
-	return NULL;
 }
 
 /*!
@@ -11708,7 +11743,7 @@
 		add_header(&req, pvt->options->authheader, pvt->options->auth);
 	}
 
-	add_header(&req, "Event", epa_entry->event);
+	add_header(&req, "Event", epa_entry->static_data->name);
 
 	snprintf(expires_str, sizeof(expires_str), "%d", publish_type == SIP_PUBLISH_REMOVE ? 0 : DEFAULT_PUBLISH_EXPIRES);
 	add_header(&req, "Expires", expires_str);
@@ -18830,26 +18865,21 @@
 static void handle_response_publish(struct sip_pvt *p, int resp, const char *rest, struct sip_request *req, int seqno)
 {
 	struct sip_epa_entry *epa_entry = p->epa_entry;
-	struct event_publication_agent *epa;
 
 	ast_assert(epa_entry != NULL);
-
-	epa = get_epa(epa_entry->event);
-
-	ast_assert(epa != NULL);
 
 	if (resp == 200) {
 		/* The nominal case. Everything went well. Everybody is happy.
 		 * Each EPA will have a specific action to take as a result of this
 		 * development, so ... callbacks!
 		 */
-		epa->callbacks->handle_ok(p, req, epa_entry);
+		epa_entry->static_data->handle_ok(p, req, epa_entry);
 	} else {
 		/* Rather than try to make individual callbacks for each error
 		 * type, there is just a single error callback. The callback
 		 * can distinguish between error messages and do what it needs to
 		 */
-		epa->callbacks->handle_error(p, resp, req, epa_entry);
+		epa_entry->static_data->handle_error(p, resp, req, epa_entry);
 	}
 }
 
@@ -27598,6 +27628,9 @@
 	sip_send_all_registers();
 	sip_send_all_mwi_subscriptions();
 	initialize_escs();
+	if (sip_epa_register(&cc_epa_static_data)) {
+		return AST_MODULE_LOAD_DECLINE;
+	}
 
 	/* And start the monitor for the first time */
 	restart_monitor();




More information about the svn-commits mailing list