[asterisk-commits] rmudgett: branch group/bridge_construction r385296 - in /team/group/bridge_co...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Wed Apr 10 18:37:06 CDT 2013


Author: rmudgett
Date: Wed Apr 10 18:37:01 2013
New Revision: 385296

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=385296
Log:
* Make ast_bridge_impart() allocate a features struct if one is not
provided.

* Make ast_bridge_join() exit early if a features struct is not provided.
Later when ast_bridge_join() is changed to require the features struct to
be allocated we can allocate one like ast_bridge_impart().

* Fix ConfBridge recording channel to supply a features structure when it
joins the bridge.

* Make the application running on a bridge channel break the bridge if it
returns non-zero like the old bridge code.  An application is supposed to
return non-zero if the channel hangs up.

Modified:
    team/group/bridge_construction/apps/app_confbridge.c
    team/group/bridge_construction/main/bridging.c
    team/group/bridge_construction/main/features.c

Modified: team/group/bridge_construction/apps/app_confbridge.c
URL: http://svnview.digium.com/svn/asterisk/team/group/bridge_construction/apps/app_confbridge.c?view=diff&rev=385296&r1=385295&r2=385296
==============================================================================
--- team/group/bridge_construction/apps/app_confbridge.c (original)
+++ team/group/bridge_construction/apps/app_confbridge.c Wed Apr 10 18:37:01 2013
@@ -649,6 +649,7 @@
 	struct ast_channel *chan;
 	struct ast_str *filename = ast_str_alloca(PATH_MAX);
 	struct ast_str *orig_rec_file = NULL;
+	struct ast_bridge_features features;
 
 	ast_mutex_lock(&conference->record_lock);
 	if (!mixmonapp) {
@@ -658,20 +659,27 @@
 		ao2_ref(conference, -1);
 		return NULL;
 	}
+	if (ast_bridge_features_init(&features)) {
+		conference->record_thread = AST_PTHREADT_NULL;
+		ast_mutex_unlock(&conference->record_lock);
+		ao2_ref(conference, -1);
+		return NULL;
+	}
 
 	/* XXX If we get an EXIT right here, START will essentially be a no-op */
 	while (conference->record_state != CONF_RECORD_EXIT) {
 		set_rec_filename(conference, &filename,
-				 is_new_rec_file(conference->b_profile.rec_file, &orig_rec_file));
+			is_new_rec_file(conference->b_profile.rec_file, &orig_rec_file));
 		chan = ast_channel_ref(conference->record_chan);
 		ast_answer(chan);
 		pbx_exec(chan, mixmonapp, ast_str_buffer(filename));
-		ast_bridge_join(conference->bridge, chan, NULL, NULL, NULL, 0);
+		ast_bridge_join(conference->bridge, chan, NULL, &features, NULL, 0);
 
 		ast_hangup(chan); /* This will eat this thread's reference to the channel as well */
 		/* STOP has been called. Wait for either a START or an EXIT */
 		ast_cond_wait(&conference->record_cond, &conference->record_lock);
 	}
+	ast_bridge_features_cleanup(&features);
 	ast_free(orig_rec_file);
 	ast_mutex_unlock(&conference->record_lock);
 	ao2_ref(conference, -1);

Modified: team/group/bridge_construction/main/bridging.c
URL: http://svnview.digium.com/svn/asterisk/team/group/bridge_construction/main/bridging.c?view=diff&rev=385296&r1=385295&r2=385296
==============================================================================
--- team/group/bridge_construction/main/bridging.c (original)
+++ team/group/bridge_construction/main/bridging.c Wed Apr 10 18:37:01 2013
@@ -572,6 +572,7 @@
 	}
 
 /* BUGBUG the feature hook matching needs to be done here.  Any matching feature hook needs to be queued onto the bridge_channel.  Also the feature hook digit timeout needs to be handled. */
+/* BUGBUG the AMI atxfer action just sends DTMF end events to initiate DTMF atxfer and dial the extension.  Another reason the DTMF hook matching needs rework. */
 	/* See if this DTMF matches the beginnings of any feature hooks, if so we switch to the feature state to either execute the feature or collect more DTMF */
 	dtmf[0] = frame->subclass.integer;
 	dtmf[1] = '\0';
@@ -689,8 +690,10 @@
 	bridge_channel_write_frame(bridge_channel, &frame);
 }
 
-static void run_app_helper(struct ast_channel *chan, const char *app_name, const char *app_args)
-{
+static int run_app_helper(struct ast_channel *chan, const char *app_name, const char *app_args)
+{
+	int res = 0;
+
 	if (!strcasecmp("Gosub", app_name)) {
 		ast_app_exec_sub(NULL, chan, app_args, 0);
 	} else if (!strcasecmp("Macro", app_name)) {
@@ -702,9 +705,10 @@
 		if (!app) {
 			ast_log(LOG_WARNING, "Could not find application (%s)\n", app_name);
 		} else {
-			pbx_exec(chan, app, app_args);
-		}
-	}
+			res = pbx_exec(chan, app, app_args);
+		}
+	}
+	return res;
 }
 
 void ast_bridge_channel_run_app(struct ast_bridge_channel *bridge_channel, const char *app_name, const char *app_args, const char *moh_class)
@@ -718,7 +722,10 @@
 				moh_class, strlen(moh_class) + 1);
 		}
 	}
-	run_app_helper(bridge_channel->chan, app_name, S_OR(app_args, ""));
+	if (run_app_helper(bridge_channel->chan, app_name, S_OR(app_args, ""))) {
+		/* Break the bridge if the app returns non-zero. */
+		bridge_handle_hangup(bridge_channel);
+	}
 	if (moh_class) {
 		ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD,
 			NULL, 0);
@@ -726,7 +733,7 @@
 }
 
 struct bridge_run_app {
-	/*! Offset into app_name[] where the MOH class name starts.  (zero if no MOH)*/
+	/*! Offset into app_name[] where the MOH class name starts.  (zero if no MOH) */
 	int moh_offset;
 	/*! Offset into app_name[] where the application argument string starts. (zero if no arguments) */
 	int app_args_offset;
@@ -2767,6 +2774,13 @@
 		state = AST_BRIDGE_CHANNEL_STATE_HANGUP;
 		goto join_exit;
 	}
+/* BUGBUG features cannot be NULL when passed in. When it is changed to allocated we can do like ast_bridge_impart() and allocate one. */
+	ast_assert(features != NULL);
+	if (!features) {
+		ao2_ref(bridge_channel, -1);
+		state = AST_BRIDGE_CHANNEL_STATE_HANGUP;
+		goto join_exit;
+	}
 	if (tech_args) {
 		bridge_channel->tech_args = *tech_args;
 	}
@@ -2869,9 +2883,18 @@
 	int res;
 	struct ast_bridge_channel *bridge_channel;
 
+	/* Supply an empty features structure if the caller did not. */
+	if (!features) {
+		features = ast_bridge_features_new();
+		if (!features) {
+			return -1;
+		}
+	}
+
 	/* Try to allocate a structure for the bridge channel */
 	bridge_channel = bridge_channel_alloc(bridge);
 	if (!bridge_channel) {
+		ast_bridge_features_destroy(features);
 		return -1;
 	}
 

Modified: team/group/bridge_construction/main/features.c
URL: http://svnview.digium.com/svn/asterisk/team/group/bridge_construction/main/features.c?view=diff&rev=385296&r1=385295&r2=385296
==============================================================================
--- team/group/bridge_construction/main/features.c (original)
+++ team/group/bridge_construction/main/features.c Wed Apr 10 18:37:01 2013
@@ -4341,7 +4341,6 @@
 #else
 	return 0;
 #endif
-/* BUGBUG dynamic features not handled yet.  App run returns non-zero breaks bridge and ast_bridge_call returns 0.  App returns zero continues bridge. */
 }
 
 static void bridge_config_set_limits_warning_values(struct ast_bridge_config *config, struct ast_bridge_features_limits *limits)




More information about the asterisk-commits mailing list