[asterisk-commits] rmudgett: branch rmudgett/bridge_phase r389971 - in /team/rmudgett/bridge_pha...
SVN commits to the Asterisk project
asterisk-commits at lists.digium.com
Tue May 28 18:39:13 CDT 2013
Author: rmudgett
Date: Tue May 28 18:39:09 2013
New Revision: 389971
URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=389971
Log:
Bridge API: Update BLINDTRANSFER.
* Added needed HOLD/UNHOLD of the peer for DTMF initiated blind and
attended transfers.
* Removed features.c blind transfer code.
Modified:
team/rmudgett/bridge_phase/bridges/bridge_builtin_features.c
team/rmudgett/bridge_phase/main/bridging.c
team/rmudgett/bridge_phase/main/features.c
Modified: team/rmudgett/bridge_phase/bridges/bridge_builtin_features.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/bridge_phase/bridges/bridge_builtin_features.c?view=diff&rev=389971&r1=389970&r2=389971
==============================================================================
--- team/rmudgett/bridge_phase/bridges/bridge_builtin_features.c (original)
+++ team/rmudgett/bridge_phase/bridges/bridge_builtin_features.c Tue May 28 18:39:09 2013
@@ -182,7 +182,8 @@
const char *context;
char *goto_on_blindxfr;
-/* BUGBUG the peer needs to be put on hold for the transfer. */
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_HOLD, NULL, 0);
+
ast_channel_lock(bridge_channel->chan);
context = ast_strdupa(get_transfer_context(bridge_channel->chan,
blind_transfer ? blind_transfer->context : NULL));
@@ -192,6 +193,7 @@
/* Grab the extension to transfer to */
if (grab_transfer(bridge_channel->chan, exten, sizeof(exten), context)) {
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
@@ -200,6 +202,8 @@
ast_channel_name(bridge_channel->chan), goto_on_blindxfr);
ast_after_bridge_set_go_on(bridge_channel->chan, NULL, NULL, 0, goto_on_blindxfr);
}
+
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
if (ast_bridge_transfer_blind(bridge_channel->chan, exten, context, blind_transfer_cb,
bridge_channel->chan) != AST_BRIDGE_TRANSFER_SUCCESS &&
@@ -265,9 +269,10 @@
const char *context;
enum atxfer_code transfer_code = ATXFER_INCOMPLETE;
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_HOLD, NULL, 0);
+
bridge = ast_bridge_channel_merge_inhibit(bridge_channel, +1);
-/* BUGBUG the peer needs to be put on hold for the transfer. */
ast_channel_lock(bridge_channel->chan);
context = ast_strdupa(get_transfer_context(bridge_channel->chan,
attended_transfer ? attended_transfer->context : NULL));
@@ -277,6 +282,7 @@
if (grab_transfer(bridge_channel->chan, exten, sizeof(exten), context)) {
ast_bridge_merge_inhibit(bridge, -1);
ao2_ref(bridge, -1);
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
@@ -287,6 +293,7 @@
ao2_ref(bridge, -1);
/* BUGBUG beeperr needs to be configurable from features.conf */
ast_stream_and_wait(bridge_channel->chan, "beeperr", AST_DIGIT_NONE);
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
@@ -314,6 +321,7 @@
ao2_ref(bridge, -1);
/* BUGBUG beeperr needs to be configurable from features.conf */
ast_stream_and_wait(bridge_channel->chan, "beeperr", AST_DIGIT_NONE);
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
@@ -327,6 +335,7 @@
ao2_ref(bridge, -1);
/* BUGBUG beeperr needs to be configurable from features.conf */
ast_stream_and_wait(bridge_channel->chan, "beeperr", AST_DIGIT_NONE);
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
ast_bridge_merge_inhibit(attended_bridge, +1);
@@ -341,6 +350,7 @@
ao2_ref(bridge, -1);
/* BUGBUG beeperr needs to be configurable from features.conf */
ast_stream_and_wait(bridge_channel->chan, "beeperr", AST_DIGIT_NONE);
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
return 0;
}
@@ -399,6 +409,7 @@
break;
case ATXFER_COMPLETE:
/* The peer takes our place in the bridge. */
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
ast_bridge_change_state(bridge_channel, AST_BRIDGE_CHANNEL_STATE_HANGUP);
xfer_failed = ast_bridge_impart(bridge_channel->bridge, peer, bridge_channel->chan, NULL, 1);
break;
@@ -409,6 +420,7 @@
* Just impart the peer onto the bridge and have us return to it
* as normal.
*/
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
xfer_failed = ast_bridge_impart(bridge_channel->bridge, peer, NULL, NULL, 1);
break;
case ATXFER_ABORT:
@@ -422,6 +434,7 @@
if (!ast_check_hangup_locked(bridge_channel->chan)) {
ast_stream_and_wait(bridge_channel->chan, "beeperr", AST_DIGIT_NONE);
}
+ ast_bridge_channel_write_control_data(bridge_channel, AST_CONTROL_UNHOLD, NULL, 0);
}
return 0;
Modified: team/rmudgett/bridge_phase/main/bridging.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/bridge_phase/main/bridging.c?view=diff&rev=389971&r1=389970&r2=389971
==============================================================================
--- team/rmudgett/bridge_phase/main/bridging.c (original)
+++ team/rmudgett/bridge_phase/main/bridging.c Tue May 28 18:39:09 2013
@@ -585,6 +585,9 @@
ast_bridge_change_state(swap, AST_BRIDGE_CHANNEL_STATE_HANGUP);
bridge_channel_pull(swap);
}
+
+ /* Clear any BLINDTRANSFER since the transfer has completed. */
+ pbx_builtin_setvar_helper(bridge_channel->chan, "BLINDTRANSFER", NULL);
bridge->reconfigured = 1;
ast_bridge_publish_enter(bridge, bridge_channel->chan);
Modified: team/rmudgett/bridge_phase/main/features.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/bridge_phase/main/features.c?view=diff&rev=389971&r1=389970&r2=389971
==============================================================================
--- team/rmudgett/bridge_phase/main/features.c (original)
+++ team/rmudgett/bridge_phase/main/features.c Tue May 28 18:39:09 2013
@@ -888,65 +888,6 @@
ast_channel_priority_set(chan, pri);
}
-/*!
- * \brief Check goto on transfer
- * \param chan
- *
- * Check if channel has 'GOTO_ON_BLINDXFR' set, if not exit.
- * When found make sure the types are compatible. Check if channel is valid
- * if so start the new channel else hangup the call.
- */
-static void check_goto_on_transfer(struct ast_channel *chan)
-{
- struct ast_channel *xferchan;
- const char *val;
- char *goto_on_transfer;
- char *x;
-
- ast_channel_lock(chan);
- val = pbx_builtin_getvar_helper(chan, "GOTO_ON_BLINDXFR");
- if (ast_strlen_zero(val)) {
- ast_channel_unlock(chan);
- return;
- }
- goto_on_transfer = ast_strdupa(val);
- ast_channel_unlock(chan);
-
- ast_debug(1, "Attempting GOTO_ON_BLINDXFR=%s for %s.\n", val, ast_channel_name(chan));
-
- xferchan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", ast_channel_linkedid(chan), 0,
- "%s", ast_channel_name(chan));
- if (!xferchan) {
- return;
- }
-
- /* Make formats okay */
- ast_format_copy(ast_channel_readformat(xferchan), ast_channel_readformat(chan));
- ast_format_copy(ast_channel_writeformat(xferchan), ast_channel_writeformat(chan));
-
- if (ast_channel_masquerade(xferchan, chan)) {
- /* Failed to setup masquerade. */
- ast_hangup(xferchan);
- return;
- }
-
- for (x = goto_on_transfer; *x; ++x) {
- if (*x == '^') {
- *x = ',';
- }
- }
- ast_parseable_goto(xferchan, goto_on_transfer);
- ast_channel_state_set(xferchan, AST_STATE_UP);
- ast_clear_flag(ast_channel_flags(xferchan), AST_FLAGS_ALL);
- ast_channel_clear_softhangup(xferchan, AST_SOFTHANGUP_ALL);
-
- ast_do_masquerade(xferchan);
- if (ast_pbx_start(xferchan)) {
- /* Failed to start PBX. */
- ast_hangup(xferchan);
- }
-}
-
static struct ast_channel *feature_request_and_dial(struct ast_channel *caller,
const char *caller_name, struct ast_channel *requestor,
struct ast_channel *transferee, const char *type, struct ast_format_cap *cap, const char *addr,
@@ -2325,117 +2266,6 @@
}
/*!
- * \brief Blind transfer user to another extension
- * \param chan channel to be transfered
- * \param peer channel initiated blind transfer
- * \param config
- * \param code
- * \param data
- * \param sense feature options
- *
- * Place chan on hold, check if transferred to parkinglot extension,
- * otherwise check extension exists and transfer caller.
- * \retval AST_FEATURE_RETURN_SUCCESS.
- * \retval -1 on failure.
- */
-static int builtin_blindtransfer(struct ast_channel *chan, struct ast_channel *peer, struct ast_bridge_config *config, const char *code, int sense, void *data)
-{
- struct ast_channel *transferer;
- struct ast_channel *transferee;
- struct ast_exten *park_exten;
- const char *transferer_real_context;
- char xferto[256] = "";
- int res;
-
- ast_debug(1, "Executing Blind Transfer %s, %s (sense=%d) \n", ast_channel_name(chan), ast_channel_name(peer), sense);
- set_peers(&transferer, &transferee, peer, chan, sense);
- transferer_real_context = ast_strdupa(real_ctx(transferer, transferee));
-
- /* Start autoservice on transferee while we talk to the transferer */
- ast_autoservice_start(transferee);
- ast_indicate(transferee, AST_CONTROL_HOLD);
-
- /* Transfer */
- res = ast_stream_and_wait(transferer, "pbx-transfer", AST_DIGIT_ANY);
- if (res < 0) {
- finishup(transferee);
- return -1; /* error ? */
- }
- if (res > 0) { /* If they've typed a digit already, handle it */
- xferto[0] = (char) res;
- }
-
- res = ast_app_dtget(transferer, transferer_real_context, xferto, sizeof(xferto), 100, transferdigittimeout);
- if (res < 0) { /* hangup or error, (would be 0 for invalid and 1 for valid) */
- finishup(transferee);
- return -1;
- }
- if (res == 0) {
- if (xferto[0]) {
- ast_log(LOG_WARNING, "Extension '%s' does not exist in context '%s'\n",
- xferto, transferer_real_context);
- } else {
- /* Does anyone care about this case? */
- ast_log(LOG_WARNING, "No digits dialed.\n");
- }
- ast_stream_and_wait(transferer, "pbx-invalid", "");
- finishup(transferee);
- return AST_FEATURE_RETURN_SUCCESS;
- }
-
- park_exten = get_parking_exten(xferto, transferer, transferer_real_context);
- if (park_exten) {
- /* We are transfering the transferee to a parking lot. */
- return xfer_park_call_helper(transferee, transferer, park_exten);
- }
-
- /* Do blind transfer. */
- ast_verb(3, "Blind transferring %s to '%s' (context %s) priority 1\n",
- ast_channel_name(transferee), xferto, transferer_real_context);
- ast_cel_report_event(transferer, AST_CEL_BLINDTRANSFER, NULL, xferto, transferee);
- pbx_builtin_setvar_helper(transferer, "BLINDTRANSFER", ast_channel_name(transferee));
- pbx_builtin_setvar_helper(transferee, "BLINDTRANSFER", ast_channel_name(transferer));
- finishup(transferee);
- ast_channel_lock(transferer);
- if (!ast_channel_cdr(transferer)) {
- /* this code should never get called (in a perfect world) */
- ast_channel_cdr_set(transferer, ast_cdr_alloc());
- if (ast_channel_cdr(transferer)) {
- ast_cdr_init(ast_channel_cdr(transferer), transferer); /* initialize our channel's cdr */
- ast_cdr_start(ast_channel_cdr(transferer));
- }
- }
- ast_channel_unlock(transferer);
- if (ast_channel_cdr(transferer)) {
- struct ast_cdr *swap = ast_channel_cdr(transferer);
-
- ast_debug(1,
- "transferer=%s; transferee=%s; lastapp=%s; lastdata=%s; chan=%s; dstchan=%s\n",
- ast_channel_name(transferer), ast_channel_name(transferee), ast_channel_cdr(transferer)->lastapp,
- ast_channel_cdr(transferer)->lastdata, ast_channel_cdr(transferer)->channel,
- ast_channel_cdr(transferer)->dstchannel);
- ast_debug(1, "TRANSFEREE; lastapp=%s; lastdata=%s, chan=%s; dstchan=%s\n",
- ast_channel_cdr(transferee)->lastapp, ast_channel_cdr(transferee)->lastdata, ast_channel_cdr(transferee)->channel,
- ast_channel_cdr(transferee)->dstchannel);
- ast_debug(1, "transferer_real_context=%s; xferto=%s\n",
- transferer_real_context, xferto);
- /* swap cdrs-- it will save us some time & work */
- ast_channel_cdr_set(transferer, ast_channel_cdr(transferee));
- ast_channel_cdr_set(transferee, swap);
- }
-
- res = ast_channel_pbx(transferee) ? AST_FEATURE_RETURN_SUCCESSBREAK : -1;
-
- /* Doh! Use our handy async_goto functions */
- if (ast_async_goto(transferee, transferer_real_context, xferto, 1)) {
- ast_log(LOG_WARNING, "Async goto failed :-(\n");
- res = -1;
- }
- check_goto_on_transfer(transferer);
- return res;
-}
-
-/*!
* \brief make channels compatible
* \param c
* \param newchan
@@ -2958,7 +2788,6 @@
/*! \note This is protected by features_lock. */
static struct ast_call_feature builtin_features[] = {
- { AST_FEATURE_REDIRECT, "Blind Transfer", "blindxfer", "#", "#", builtin_blindtransfer, AST_FEATURE_FLAG_NEEDSDTMF, "" },
{ AST_FEATURE_REDIRECT, "Attended Transfer", "atxfer", "", "", builtin_atxfer, AST_FEATURE_FLAG_NEEDSDTMF, "" },
{ AST_FEATURE_AUTOMON, "One Touch Monitor", "automon", "", "", builtin_automonitor, AST_FEATURE_FLAG_NEEDSDTMF, "" },
{ AST_FEATURE_DISCONNECT, "Disconnect Call", "disconnect", "*", "*", builtin_disconnect, AST_FEATURE_FLAG_NEEDSDTMF, "" },
@@ -4483,11 +4312,6 @@
/* BUGBUG these channel vars may need to be made dynamic so they update when transfers happen. */
pbx_builtin_setvar_helper(chan, "BRIDGEPEER", ast_channel_name(peer));
pbx_builtin_setvar_helper(peer, "BRIDGEPEER", ast_channel_name(chan));
-
-/* BUGBUG revisit how BLINDTRANSFER operates with the new bridging model. */
- /* Clear any BLINDTRANSFER since the transfer has completed. */
- pbx_builtin_setvar_helper(chan, "BLINDTRANSFER", NULL);
- pbx_builtin_setvar_helper(peer, "BLINDTRANSFER", NULL);
set_bridge_features_on_config(config, pbx_builtin_getvar_helper(chan, "BRIDGE_FEATURES"));
add_features_datastores(chan, peer, config);
More information about the asterisk-commits
mailing list