[asterisk-commits] mmichelson: branch mmichelson/atxfer_features r392167 - /team/mmichelson/atxf...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Tue Jun 18 14:53:04 CDT 2013


Author: mmichelson
Date: Tue Jun 18 14:53:03 2013
New Revision: 392167

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=392167
Log:
Fill in some more states.


Modified:
    team/mmichelson/atxfer_features/main/bridging_basic.c

Modified: team/mmichelson/atxfer_features/main/bridging_basic.c
URL: http://svnview.digium.com/svn/asterisk/team/mmichelson/atxfer_features/main/bridging_basic.c?view=diff&rev=392167&r1=392166&r2=392167
==============================================================================
--- team/mmichelson/atxfer_features/main/bridging_basic.c (original)
+++ team/mmichelson/atxfer_features/main/bridging_basic.c Tue Jun 18 14:53:03 2013
@@ -440,6 +440,7 @@
 	STIMULUS_TRANSFEREE_HANGUP,
 	STIMULUS_TRANSFERER_HANGUP,
 	STIMULUS_TARGET_HANGUP,
+	STIMULUS_TRANSFERER_ANSWER,
 	STIMULUS_TARGET_ANSWER,
 	STIMULUS_TIMEOUT,
 	STIMULUS_DTMF_ATXFER_ABORT,
@@ -461,6 +462,7 @@
 	enum attended_transfer_state state;
 	int atxferdropcall;
 	int atxfercallbackretries;
+	int retry_attempts;
 };
 
 /*!
@@ -479,6 +481,7 @@
 	switch (props->stimulus) {
 	default:
 	case STIMULUS_NONE:
+	case STIMULUS_TRANSFERER_ANSWER:
 		ast_assert(0);
 	case STIMULUS_TRANSFEREE_HANGUP:
 		return TRANSFER_FAIL;
@@ -508,6 +511,7 @@
 	switch (props->stimulus) {
 	default:
 	case STIMULUS_NONE:
+	case STIMULUS_TRANSFERER_ANSWER:
 		ast_assert(0);
 	case STIMULUS_TRANSFEREE_HANGUP:
 		return TRANSFER_FAIL;
@@ -527,91 +531,197 @@
 	}
 }
 
-static int rebridge_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
+static int rebridge_enter(struct attended_transfer_properties *props)
+{
+	return ast_bridge_move(props->transferee_bridge, props->target_bridge,
+			props->transferer, NULL, 1);
+}
+
+static int resume_enter(struct attended_transfer_properties *props)
+{
+	return ast_bridge_destroy(props->target_bridge);
+}
+
+static int threeway_enter(struct attended_transfer_properties *props)
+{
+	return ast_bridge_merge(props->transferee_bridge, props->target_bridge, 0, NULL, 0);
+}
+
+static int consulting_enter(struct attended_transfer_properties *props)
+{
+	struct ast_bridge *transferer_bridge;
+
+	ast_channel_lock(props->transferer);
+	transferer_bridge = ast_channel_internal_bridge(props->transferer);
+	ast_channel_unlock(props->transferer);
+
+	ast_assert(transferer_bridge != NULL);
+
+	if (transferer_bridge == props->target_bridge) {
+		return 0;
+	}
+	return ast_bridge_move(props->target_bridge, props->transferee_bridge, props->transferer, NULL, 1);
+}
+
+static enum attended_transfer_state consulting_next(struct attended_transfer_properties *props)
+{
+	switch (props->stimulus) {
+	default:
+	case STIMULUS_NONE:
+	case STIMULUS_TIMEOUT:
+	case STIMULUS_TARGET_ANSWER:
+	case STIMULUS_TRANSFERER_ANSWER:
+		ast_assert(0);
+	case STIMULUS_TRANSFEREE_HANGUP:
+		/* XXX I have absolutely no idea how to handle this case */
+		return TRANSFER_FAIL;
+	case STIMULUS_TRANSFERER_HANGUP:
+	case STIMULUS_DTMF_ATXFER_COMPLETE:
+		 return TRANSFER_COMPLETE;
+	case STIMULUS_TARGET_HANGUP:
+	case STIMULUS_DTMF_ATXFER_ABORT:
+		 return TRANSFER_REBRIDGE;
+	case STIMULUS_DTMF_ATXFER_THREEWAY:
+		 return TRANSFER_THREEWAY;
+	case STIMULUS_DTMF_ATXFER_SWAP:
+		 return TRANSFER_DOUBLECHECKING;
+	}
+}
+
+static int double_checking_enter(struct attended_transfer_properties *props)
+{
+	struct ast_bridge *transferer_bridge;
+
+	ast_channel_lock(props->transferer);
+	transferer_bridge = ast_channel_internal_bridge(props->transferer);
+	ast_channel_unlock(props->transferer);
+
+	ast_assert(transferer_bridge != NULL);
+
+	if (transferer_bridge == props->transferee_bridge) {
+		return 0;
+	}
+	return ast_bridge_move(props->transferee_bridge, props->target_bridge, props->transferer, NULL, 1);
+}
+
+static enum attended_transfer_state double_checking_next(struct attended_transfer_properties *props)
+{
+	switch (props->stimulus) {
+	default:
+	case STIMULUS_NONE:
+	case STIMULUS_TIMEOUT:
+	case STIMULUS_TARGET_ANSWER:
+	case STIMULUS_TRANSFERER_ANSWER:
+		ast_assert(0);
+	case STIMULUS_TRANSFEREE_HANGUP:
+		return TRANSFER_FAIL;
+	case STIMULUS_TRANSFERER_HANGUP:
+	case STIMULUS_DTMF_ATXFER_COMPLETE:
+		 return TRANSFER_COMPLETE;
+	case STIMULUS_TARGET_HANGUP:
+	case STIMULUS_DTMF_ATXFER_ABORT:
+		 return TRANSFER_RESUME;
+	case STIMULUS_DTMF_ATXFER_THREEWAY:
+		 return TRANSFER_THREEWAY;
+	case STIMULUS_DTMF_ATXFER_SWAP:
+		 return TRANSFER_CONSULTING;
+	}
+}
+
+static int complete_enter(struct attended_transfer_properties *props)
+{
+	return ast_bridge_merge(props->transferee_bridge, props->target_bridge, 0, &props->transferer, 1);
+}
+
+static int blond_enter(struct attended_transfer_properties *props)
+{
+	if (ast_check_hangup(props->transferer)) {
+		return 0;
+	}
+	ast_softhangup(props->transferer, AST_SOFTHANGUP_EXPLICIT);
 	return 0;
 }
 
-static int resume_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
+static enum attended_transfer_state blond_next(struct attended_transfer_properties *props)
+{
+	switch (props->stimulus) {
+	default:
+	case STIMULUS_NONE:
+	case STIMULUS_DTMF_ATXFER_ABORT:
+	case STIMULUS_DTMF_ATXFER_COMPLETE:
+	case STIMULUS_DTMF_ATXFER_THREEWAY:
+	case STIMULUS_DTMF_ATXFER_SWAP:
+	case STIMULUS_TRANSFERER_HANGUP:
+	case STIMULUS_TRANSFERER_ANSWER:
+		ast_assert(0);
+	case STIMULUS_TRANSFEREE_HANGUP:
+		return TRANSFER_FAIL;
+	case STIMULUS_TARGET_ANSWER:
+		return TRANSFER_COMPLETE;
+	case STIMULUS_TARGET_HANGUP:
+	case STIMULUS_TIMEOUT:
+		return TRANSFER_RECALLING;
+	}
+}
+
+static int recalling_enter(struct attended_transfer_properties *props)
+{
+	if (props->atxferdropcall) {
+		return -1;
+	}
+	/* XXX Need to:
+	 * 1) Request transferer channel
+	 * 2) Add transferer role to channel
+	 * 3) Place transferer channel into transferee bridge
+	 * 4) Place outgoing call to transferer channel
+	 */
 	return 0;
 }
 
-static int threeway_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
+static enum attended_transfer_state recalling_next(struct attended_transfer_properties *props)
+{
+	switch (props->stimulus) {
+	default:
+	case STIMULUS_NONE:
+	case STIMULUS_DTMF_ATXFER_ABORT:
+	case STIMULUS_DTMF_ATXFER_COMPLETE:
+	case STIMULUS_DTMF_ATXFER_THREEWAY:
+	case STIMULUS_DTMF_ATXFER_SWAP:
+	case STIMULUS_TARGET_HANGUP:
+	case STIMULUS_TARGET_ANSWER:
+	case STIMULUS_TRANSFERER_HANGUP:
+		ast_assert(0);
+	case STIMULUS_TRANSFEREE_HANGUP:
+		return TRANSFER_FAIL;
+	case STIMULUS_TIMEOUT:
+		return TRANSFER_RETRANSFER;
+	case STIMULUS_TRANSFERER_ANSWER:
+		return TRANSFER_RESUME;
+	}
+}
+
+static int retransfer_enter(struct attended_transfer_properties *props)
+{
+	++props->retry_attempts;
+	if (props->retry_attempts >= props->atxfercallbackretries) {
+		return -1;
+	}
+	/* XXX Need to do the following:
+	 * 1) Request new transfer target channel
+	 * 2) Create a new target bridge (or maybe just reuse old one?)
+	 * 3) Place target channel into target bridge
+	 * 4) Place outgoing call to party C
+	 * 5) Stimulate a change to BLOND state
+	 */
 	return 0;
 }
 
-static int consulting_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static enum attended_transfer_state consulting_next(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return TRANSFER_FAIL;
-}
-
-static int double_checking_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static enum attended_transfer_state double_checking_next(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return TRANSFER_FAIL;
-}
-
-static int complete_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static int blond_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static enum attended_transfer_state blond_next(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return TRANSFER_FAIL;
-}
-
-static int recalling_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static enum attended_transfer_state recalling_next(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return TRANSFER_FAIL;
-}
-
-static int retransfer_enter(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return 0;
-}
-
-static enum attended_transfer_state retransfer_next(struct attended_transfer_properties *properties)
-{
-	/* XXX STUB */
-	return TRANSFER_FAIL;
-}
-
-static int fail_enter(struct attended_transfer_properties *properties)
+static enum attended_transfer_state retransfer_next(struct attended_transfer_properties *props)
+{
+	return TRANSFER_BLOND;
+}
+
+static int fail_enter(struct attended_transfer_properties *props)
 {
 	/* XXX STUB */
 	return 0;
@@ -625,8 +735,8 @@
 
 static struct attended_transfer_state_properties {
 	const char *state_name;
-	int (*enter)(struct attended_transfer_properties *properties);
-	enum attended_transfer_state (*next)(struct attended_transfer_properties *properties);
+	int (*enter)(struct attended_transfer_properties *props);
+	enum attended_transfer_state (*next)(struct attended_transfer_properties *props);
 	enum attended_transfer_state_flags flags;
 } state_properties [] = {
 	[TRANSFER_CALLING_TARGET] = {




More information about the asterisk-commits mailing list