Asterisk - The Open Source Telephony Project  18.5.0
Typedefs | Enumerations | Functions
bridge_after.h File Reference

After Bridge Execution API. More...

This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Typedefs

typedef void(* ast_bridge_after_cb) (struct ast_channel *chan, void *data)
 After bridge callback function. More...
 
typedef void(* ast_bridge_after_cb_failed) (enum ast_bridge_after_cb_reason reason, void *data)
 After bridge callback failed. More...
 

Enumerations

enum  ast_bridge_after_cb_reason {
  AST_BRIDGE_AFTER_CB_REASON_DESTROY, AST_BRIDGE_AFTER_CB_REASON_REPLACED, AST_BRIDGE_AFTER_CB_REASON_MASQUERADE, AST_BRIDGE_AFTER_CB_REASON_DEPART,
  AST_BRIDGE_AFTER_CB_REASON_REMOVED, AST_BRIDGE_AFTER_CB_REASON_IMPART_FAILED
}
 

Functions

const char * ast_bridge_after_cb_reason_string (enum ast_bridge_after_cb_reason reason)
 Get a string representation of an after bridge callback reason. More...
 
void ast_bridge_discard_after_callback (struct ast_channel *chan, enum ast_bridge_after_cb_reason reason)
 Run discarding any after bridge callbacks. More...
 
void ast_bridge_discard_after_goto (struct ast_channel *chan)
 Discard channel after bridge goto location. More...
 
void ast_bridge_read_after_goto (struct ast_channel *chan, char *buffer, size_t buf_size)
 Read after bridge goto if it exists. More...
 
void ast_bridge_run_after_callback (struct ast_channel *chan)
 Run any after bridge callback. More...
 
void ast_bridge_run_after_goto (struct ast_channel *chan)
 Run a PBX on any after bridge goto location. More...
 
int ast_bridge_set_after_callback (struct ast_channel *chan, ast_bridge_after_cb callback, ast_bridge_after_cb_failed failed, void *data)
 Setup an after bridge callback for when the channel leaves the bridging system. More...
 
void ast_bridge_set_after_go_on (struct ast_channel *chan, const char *context, const char *exten, int priority, const char *parseable_goto)
 Set channel to go on in the dialplan after the bridge. More...
 
void ast_bridge_set_after_goto (struct ast_channel *chan, const char *context, const char *exten, int priority)
 Set channel to goto specific location after the bridge. More...
 
void ast_bridge_set_after_h (struct ast_channel *chan, const char *context)
 Set channel to run the h exten after the bridge. More...
 
int ast_bridge_setup_after_goto (struct ast_channel *chan)
 Setup any after bridge goto location to begin execution. More...
 

Detailed Description

After Bridge Execution API.

Author
Richard Mudgett rmudg.nosp@m.ett@.nosp@m.digiu.nosp@m.m.co.nosp@m.m

See Also:

Definition in file bridge_after.h.

Typedef Documentation

◆ ast_bridge_after_cb

typedef void(* ast_bridge_after_cb) (struct ast_channel *chan, void *data)

After bridge callback function.

Since
12.0.0
Parameters
chanChannel just leaving bridging system.
dataExtra data what setup the callback wanted to pass.
Returns
Nothing

Definition at line 211 of file bridge_after.h.

◆ ast_bridge_after_cb_failed

typedef void(* ast_bridge_after_cb_failed) (enum ast_bridge_after_cb_reason reason, void *data)

After bridge callback failed.

Since
12.0.0
Parameters
reasonReason callback is failing.
dataExtra data what setup the callback wanted to pass.
Note
Called when the channel leaves the bridging system or is destroyed.
Returns
Nothing

Definition at line 200 of file bridge_after.h.

Enumeration Type Documentation

◆ ast_bridge_after_cb_reason

Reason the after bridge callback will not be called.

Enumerator
AST_BRIDGE_AFTER_CB_REASON_DESTROY 

The datastore is being destroyed. Likely due to hangup. (Enum value must be zero.)

AST_BRIDGE_AFTER_CB_REASON_REPLACED 

Something else replaced the callback with another.

AST_BRIDGE_AFTER_CB_REASON_MASQUERADE 

The callback was removed because of a masquerade. (fixup)

AST_BRIDGE_AFTER_CB_REASON_DEPART 

The channel was departed from the bridge.

AST_BRIDGE_AFTER_CB_REASON_REMOVED 

Was explicitly removed by external code.

AST_BRIDGE_AFTER_CB_REASON_IMPART_FAILED 

The channel failed to enter the bridge.

Definition at line 37 of file bridge_after.h.

37  {
38  /*! The datastore is being destroyed. Likely due to hangup. (Enum value must be zero.) */
40  /*! Something else replaced the callback with another. */
42  /*! The callback was removed because of a masquerade. (fixup) */
44  /*! The channel was departed from the bridge. */
46  /*! Was explicitly removed by external code. */
48  /*! The channel failed to enter the bridge. */
50 };

Function Documentation

◆ ast_bridge_after_cb_reason_string()

const char* ast_bridge_after_cb_reason_string ( enum ast_bridge_after_cb_reason  reason)

Get a string representation of an after bridge callback reason.

Since
12.0.0
Parameters
reasonThe reason to interpret to a string
Return values
NULLUnrecognized reason
non-NULLString representation of reason

Definition at line 296 of file bridge_after.c.

References AST_BRIDGE_AFTER_CB_REASON_DEPART, AST_BRIDGE_AFTER_CB_REASON_DESTROY, AST_BRIDGE_AFTER_CB_REASON_IMPART_FAILED, AST_BRIDGE_AFTER_CB_REASON_MASQUERADE, AST_BRIDGE_AFTER_CB_REASON_REMOVED, and AST_BRIDGE_AFTER_CB_REASON_REPLACED.

Referenced by after_bridge_move_channel_fail(), agent_after_bridge_cb_failed(), bridge_after_cb_failed(), and internal_bridge_after_cb().

297 {
298  switch (reason) {
300  return "Channel destroyed (hungup)";
302  return "Callback was replaced";
304  return "Channel masqueraded";
306  return "Channel was departed from bridge";
308  return "Callback was removed";
310  return "Channel failed joining the bridge";
311  }
312  return "Unknown";
313 }

◆ ast_bridge_discard_after_callback()

void ast_bridge_discard_after_callback ( struct ast_channel chan,
enum ast_bridge_after_cb_reason  reason 
)

Run discarding any after bridge callbacks.

Since
12.0.0
Parameters
chanChannel to run after bridge callback.
Returns
Nothing

Definition at line 247 of file bridge_after.c.

References after_bridge_cb_find(), and after_bridge_cb_run_discard().

Referenced by ast_bridge_impart(), and bridge_channel_depart_thread().

248 {
249  struct after_bridge_cb_ds *after_bridge;
250 
251  after_bridge = after_bridge_cb_find(chan);
252  if (!after_bridge) {
253  return;
254  }
255 
256  after_bridge_cb_run_discard(after_bridge, reason);
257 }
static void after_bridge_cb_run_discard(struct after_bridge_cb_ds *after_bridge, enum ast_bridge_after_cb_reason reason)
Definition: bridge_after.c:85
static struct after_bridge_cb_ds * after_bridge_cb_find(struct ast_channel *chan)
Definition: bridge_after.c:170

◆ ast_bridge_discard_after_goto()

void ast_bridge_discard_after_goto ( struct ast_channel chan)

Discard channel after bridge goto location.

Since
12.0.0
Parameters
chanChannel to discard after bridge goto location.
Note
chan is locked by this function.
Returns
Nothing

Definition at line 396 of file bridge_after.c.

References after_bridge_goto_remove(), and ast_datastore_free().

Referenced by __after_bridge_set_goto(), after_bridge_goto_fixup(), bridge_channel_depart_thread(), feature_blind_transfer(), and func_channel_write_real().

397 {
398  struct ast_datastore *datastore;
399 
400  datastore = after_bridge_goto_remove(chan);
401  if (datastore) {
402  ast_datastore_free(datastore);
403  }
404 }
Structure for a data store object.
Definition: datastore.h:68
int ast_datastore_free(struct ast_datastore *datastore)
Free a data store object.
Definition: datastore.c:68
static struct ast_datastore * after_bridge_goto_remove(struct ast_channel *chan)
Definition: bridge_after.c:382

◆ ast_bridge_read_after_goto()

void ast_bridge_read_after_goto ( struct ast_channel chan,
char *  buffer,
size_t  buf_size 
)

Read after bridge goto if it exists.

Since
12.0.0
Parameters
chanChannel to read the after bridge goto parseable goto string from
bufferBuffer to write the after bridge goto data to
buf_sizesize of the buffer being written to

Definition at line 406 of file bridge_after.c.

References ast_channel_datastore_find(), ast_strlen_zero, after_bridge_goto_ds::context, ast_datastore::data, after_bridge_goto_ds::exten, lock, NULL, after_bridge_goto_ds::parseable_goto, after_bridge_goto_ds::priority, after_bridge_goto_ds::run_h_exten, and SCOPED_CHANNELLOCK.

Referenced by func_channel_read().

407 {
408  struct ast_datastore *datastore;
409  struct after_bridge_goto_ds *after_bridge;
410  char *current_pos = buffer;
411  size_t remaining_size = buf_size;
412 
413  SCOPED_CHANNELLOCK(lock, chan);
414 
416  if (!datastore) {
417  buffer[0] = '\0';
418  return;
419  }
420 
421  after_bridge = datastore->data;
422 
423  if (after_bridge->parseable_goto) {
424  snprintf(buffer, buf_size, "%s", after_bridge->parseable_goto);
425  return;
426  }
427 
428  if (!ast_strlen_zero(after_bridge->context)) {
429  snprintf(current_pos, remaining_size, "%s,", after_bridge->context);
430  remaining_size = remaining_size - strlen(current_pos);
431  current_pos += strlen(current_pos);
432  }
433 
434  if (after_bridge->run_h_exten) {
435  snprintf(current_pos, remaining_size, "h,");
436  remaining_size = remaining_size - strlen(current_pos);
437  current_pos += strlen(current_pos);
438  } else if (!ast_strlen_zero(after_bridge->exten)) {
439  snprintf(current_pos, remaining_size, "%s,", after_bridge->exten);
440  remaining_size = remaining_size - strlen(current_pos);
441  current_pos += strlen(current_pos);
442  }
443 
444  snprintf(current_pos, remaining_size, "%d", after_bridge->priority);
445 }
const char * parseable_goto
Definition: bridge_after.c:317
static const struct ast_datastore_info after_bridge_goto_info
Definition: bridge_after.c:366
Structure for a data store object.
Definition: datastore.h:68
struct ast_datastore * ast_channel_datastore_find(struct ast_channel *chan, const struct ast_datastore_info *info, const char *uid)
Find a datastore on a channel.
Definition: channel.c:2404
#define NULL
Definition: resample.c:96
#define ast_strlen_zero(foo)
Definition: strings.h:52
#define SCOPED_CHANNELLOCK(varname, chan)
scoped lock specialization for channels.
Definition: lock.h:617
ast_mutex_t lock
Definition: app_meetme.c:1091
const char * context
Definition: bridge_after.c:319
const char * exten
Definition: bridge_after.c:321
void * data
Definition: datastore.h:70
unsigned int run_h_exten
Definition: bridge_after.c:325

◆ ast_bridge_run_after_callback()

void ast_bridge_run_after_callback ( struct ast_channel chan)

Run any after bridge callback.

Since
12.0.0
Parameters
chanChannel to run after bridge callback.
Returns
Nothing

Definition at line 220 of file bridge_after.c.

References after_bridge_cb_failed(), after_bridge_cb_find(), ast_free, AST_LIST_LOCK, AST_LIST_REMOVE_HEAD, AST_LIST_UNLOCK, after_bridge_cb_node::callback, after_bridge_cb_ds::callbacks, after_bridge_cb_node::data, after_bridge_cb_node::failed, after_bridge_cb_node::list, NULL, and after_bridge_cb_node::reason.

Referenced by ast_bridge_join(), and bridge_channel_ind_thread().

221 {
222  struct after_bridge_cb_ds *after_bridge;
223  struct after_bridge_cb_node *node;
224 
225  after_bridge = after_bridge_cb_find(chan);
226  if (!after_bridge) {
227  return;
228  }
229 
230  for (;;) {
231  AST_LIST_LOCK(&after_bridge->callbacks);
232  node = AST_LIST_REMOVE_HEAD(&after_bridge->callbacks, list);
233  AST_LIST_UNLOCK(&after_bridge->callbacks);
234  if (!node) {
235  break;
236  }
237  if (node->reason) {
239  } else {
240  node->failed = NULL;
241  node->callback(chan, node->data);
242  }
243  ast_free(node);
244  }
245 }
Definition: test_heap.c:38
#define AST_LIST_LOCK(head)
Locks a list.
Definition: linkedlists.h:39
#define AST_LIST_UNLOCK(head)
Attempts to unlock a list.
Definition: linkedlists.h:139
ast_bridge_after_cb callback
Definition: bridge_after.c:44
#define NULL
Definition: resample.c:96
enum ast_bridge_after_cb_reason reason
Definition: bridge_after.c:50
#define AST_LIST_REMOVE_HEAD(head, field)
Removes and returns the head entry from a list.
Definition: linkedlists.h:832
ast_bridge_after_cb_failed failed
Definition: bridge_after.c:46
static struct after_bridge_cb_ds * after_bridge_cb_find(struct ast_channel *chan)
Definition: bridge_after.c:170
struct after_bridge_cb_node::@350 list
#define ast_free(a)
Definition: astmm.h:182
struct after_bridge_cb_ds::@351 callbacks
static void after_bridge_cb_failed(struct after_bridge_cb_node *node)
Definition: bridge_after.c:67

◆ ast_bridge_run_after_goto()

void ast_bridge_run_after_goto ( struct ast_channel chan)

Run a PBX on any after bridge goto location.

Since
12.0.0
Parameters
chanChannel to execute after bridge goto location.
Note
chan is locked by this function.

Pull off any after bridge goto location datastore and run a PBX at that location.

Note
On return, the chan pointer is no longer valid because the channel has hung up.
Returns
Nothing

Definition at line 537 of file bridge_after.c.

References ast_bridge_setup_after_goto(), ast_hangup(), and ast_pbx_run().

Referenced by bridge_channel_ind_thread().

538 {
539  int goto_failed;
540 
541  goto_failed = ast_bridge_setup_after_goto(chan);
542  if (goto_failed || ast_pbx_run(chan)) {
543  ast_hangup(chan);
544  }
545 }
int ast_bridge_setup_after_goto(struct ast_channel *chan)
Setup any after bridge goto location to begin execution.
Definition: bridge_after.c:447
void ast_hangup(struct ast_channel *chan)
Hang up a channel.
Definition: channel.c:2548
enum ast_pbx_result ast_pbx_run(struct ast_channel *c)
Execute the PBX in the current thread.
Definition: pbx.c:4759

◆ ast_bridge_set_after_callback()

int ast_bridge_set_after_callback ( struct ast_channel chan,
ast_bridge_after_cb  callback,
ast_bridge_after_cb_failed  failed,
void *  data 
)

Setup an after bridge callback for when the channel leaves the bridging system.

Since
12.0.0
Parameters
chanChannel to setup an after bridge callback on.
callbackFunction to call when the channel leaves the bridging system.
failedFunction to call when it will not be calling the callback.
dataExtra data to pass with the callback.
Note
chan is locked by this function.
failed is called when the channel leaves the bridging system or is destroyed.
Return values
0on success.
-1on error.

Definition at line 259 of file bridge_after.c.

References after_bridge_cb_setup(), ast_assert, AST_BRIDGE_AFTER_CB_REASON_REPLACED, ast_calloc, AST_LIST_INSERT_TAIL, AST_LIST_LAST, AST_LIST_LOCK, AST_LIST_UNLOCK, after_bridge_cb_node::callback, after_bridge_cb_ds::callbacks, after_bridge_cb_node::data, after_bridge_cb_node::failed, after_bridge_cb_node::list, NULL, and after_bridge_cb_node::reason.

Referenced by add_to_dial_bridge(), bridge_agent_hold_push(), bridge_channel_attended_transfer(), bridge_stasis_push(), control_swap_channel_in_bridge(), and stasis_app_bridge_playback_channel_add().

260 {
261  struct after_bridge_cb_ds *after_bridge;
262  struct after_bridge_cb_node *new_node;
263  struct after_bridge_cb_node *last_node;
264 
265  /* Sanity checks. */
266  ast_assert(chan != NULL);
267  if (!chan || !callback) {
268  return -1;
269  }
270 
271  after_bridge = after_bridge_cb_setup(chan);
272  if (!after_bridge) {
273  return -1;
274  }
275 
276  /* Create a new callback node. */
277  new_node = ast_calloc(1, sizeof(*new_node));
278  if (!new_node) {
279  return -1;
280  }
281  new_node->callback = callback;
282  new_node->failed = failed;
283  new_node->data = data;
284 
285  /* Put it in the container disabling any previously active one. */
286  AST_LIST_LOCK(&after_bridge->callbacks);
287  last_node = AST_LIST_LAST(&after_bridge->callbacks);
288  if (last_node && !last_node->reason) {
290  }
291  AST_LIST_INSERT_TAIL(&after_bridge->callbacks, new_node, list);
292  AST_LIST_UNLOCK(&after_bridge->callbacks);
293  return 0;
294 }
#define AST_LIST_LOCK(head)
Locks a list.
Definition: linkedlists.h:39
#define AST_LIST_UNLOCK(head)
Attempts to unlock a list.
Definition: linkedlists.h:139
ast_bridge_after_cb callback
Definition: bridge_after.c:44
#define ast_assert(a)
Definition: utils.h:695
#define NULL
Definition: resample.c:96
enum ast_bridge_after_cb_reason reason
Definition: bridge_after.c:50
ast_bridge_after_cb_failed failed
Definition: bridge_after.c:46
#define AST_LIST_INSERT_TAIL(head, elm, field)
Appends a list entry to the tail of a list.
Definition: linkedlists.h:730
static struct after_bridge_cb_ds * after_bridge_cb_setup(struct ast_channel *chan)
Definition: bridge_after.c:192
#define AST_LIST_LAST(head)
Returns the last entry contained in a list.
Definition: linkedlists.h:428
struct after_bridge_cb_node::@350 list
#define ast_calloc(num, len)
A wrapper for calloc()
Definition: astmm.h:204
struct after_bridge_cb_ds::@351 callbacks

◆ ast_bridge_set_after_go_on()

void ast_bridge_set_after_go_on ( struct ast_channel chan,
const char *  context,
const char *  exten,
int  priority,
const char *  parseable_goto 
)

Set channel to go on in the dialplan after the bridge.

Since
12.0.0
Parameters
chanChannel to setup after bridge goto location.
contextCurrent context of the caller channel.
extenCurrent exten of the caller channel.
priorityCurrent priority of the caller channel
parseable_gotoUser specified goto string from dialplan.
Note
chan is locked by this function.

Add a channel datastore to setup the goto location when the channel leaves the bridge and run a PBX from there.

If parseable_goto then use the given context/exten/priority as the relative position for the parseable_goto. Else goto the given context/exten/priority+1.

Returns
Nothing

Definition at line 636 of file bridge_after.c.

References __after_bridge_set_goto(), ast_replace_subargument_delimiter(), ast_strdupa, ast_strlen_zero, and NULL.

Referenced by bridge_exec(), feature_blind_transfer(), func_channel_write_real(), and setup_peer_after_bridge_goto().

637 {
638  char *p_goto;
639 
640  if (!ast_strlen_zero(parseable_goto)) {
641  p_goto = ast_strdupa(parseable_goto);
643  } else {
644  p_goto = NULL;
645  }
646  __after_bridge_set_goto(chan, 0, 0, context, exten, priority, p_goto);
647 }
static char exten[AST_MAX_EXTENSION]
Definition: chan_alsa.c:118
#define NULL
Definition: resample.c:96
static int priority
static void __after_bridge_set_goto(struct ast_channel *chan, int run_h_exten, int specific, const char *context, const char *exten, int priority, const char *parseable_goto)
Definition: bridge_after.c:571
#define ast_strlen_zero(foo)
Definition: strings.h:52
void ast_replace_subargument_delimiter(char *s)
Replace '^' in a string with ','.
Definition: main/utils.c:2095
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition: astmm.h:300
static char context[AST_MAX_CONTEXT]
Definition: chan_alsa.c:116

◆ ast_bridge_set_after_goto()

void ast_bridge_set_after_goto ( struct ast_channel chan,
const char *  context,
const char *  exten,
int  priority 
)

Set channel to goto specific location after the bridge.

Since
12.0.0
Parameters
chanChannel to setup after bridge goto location.
contextContext to goto after bridge.
extenExten to goto after bridge.
priorityPriority to goto after bridge.
Note
chan is locked by this function.

Add a channel datastore to setup the goto location when the channel leaves the bridge and run a PBX from there.

Returns
Nothing

Definition at line 626 of file bridge_after.c.

References __after_bridge_set_goto(), and NULL.

Referenced by action_bridge().

627 {
629 }
static char exten[AST_MAX_EXTENSION]
Definition: chan_alsa.c:118
#define NULL
Definition: resample.c:96
static int priority
static void __after_bridge_set_goto(struct ast_channel *chan, int run_h_exten, int specific, const char *context, const char *exten, int priority, const char *parseable_goto)
Definition: bridge_after.c:571
static char context[AST_MAX_CONTEXT]
Definition: chan_alsa.c:116

◆ ast_bridge_set_after_h()

void ast_bridge_set_after_h ( struct ast_channel chan,
const char *  context 
)

Set channel to run the h exten after the bridge.

Since
12.0.0
Parameters
chanChannel to setup after bridge goto location.
contextContext to goto after bridge.
Note
chan is locked by this function.

Add a channel datastore to setup the goto location when the channel leaves the bridge and run a PBX from there.

Returns
Nothing

Definition at line 631 of file bridge_after.c.

References __after_bridge_set_goto(), and NULL.

Referenced by setup_peer_after_bridge_goto().

632 {
633  __after_bridge_set_goto(chan, 1, 0, context, NULL, 1, NULL);
634 }
#define NULL
Definition: resample.c:96
static void __after_bridge_set_goto(struct ast_channel *chan, int run_h_exten, int specific, const char *context, const char *exten, int priority, const char *parseable_goto)
Definition: bridge_after.c:571
static char context[AST_MAX_CONTEXT]
Definition: chan_alsa.c:116

◆ ast_bridge_setup_after_goto()

int ast_bridge_setup_after_goto ( struct ast_channel chan)

Setup any after bridge goto location to begin execution.

Since
12.0.0
Parameters
chanChannel to setup after bridge goto location.
Note
chan is locked by this function.

Pull off any after bridge goto location datastore and setup for dialplan execution there.

Return values
0on success. The goto location is set for a PBX to run it.
non-zeroon error or no goto location.
Note
If the after bridge goto is set to run an h exten it is run here immediately.

Definition at line 447 of file bridge_after.c.

References after_bridge_goto_remove(), ast_channel_caller(), ast_channel_clear_flag(), ast_channel_clear_softhangup(), ast_channel_context(), ast_channel_context_set(), ast_channel_exten(), ast_channel_exten_set(), ast_channel_flags(), ast_channel_priority(), ast_channel_priority_set(), ast_channel_set_unbridged(), ast_channel_softhangup_internal_flag(), ast_check_hangup(), ast_datastore_free(), ast_debug, ast_exists_extension(), ast_explicit_goto(), AST_FLAG_IN_AUTOLOOP, AST_FLAG_OUTGOING, ast_goto_if_exists(), ast_parseable_goto(), ast_pbx_h_exten_run(), AST_SOFTHANGUP_ASYNCGOTO, ast_strdupa, ast_strlen_zero, ast_test_flag, context, after_bridge_goto_ds::context, ast_datastore::data, exten, after_bridge_goto_ds::exten, NULL, after_bridge_goto_ds::parseable_goto, priority, after_bridge_goto_ds::priority, after_bridge_goto_ds::run_h_exten, S_COR, and after_bridge_goto_ds::specific.

Referenced by app_control_dial(), ast_bridge_join(), ast_bridge_run_after_goto(), bridge_failed_peer_goto(), dial_exec_full(), and internal_bridge_after_cb().

448 {
449  struct ast_datastore *datastore;
450  struct after_bridge_goto_ds *after_bridge;
451  int goto_failed = -1;
452 
453  /* We are going to be leaving the bridging system now;
454  * clear any pending unbridge flags
455  */
456  ast_channel_set_unbridged(chan, 0);
457 
458  /* Determine if we are going to setup a dialplan location and where. */
460  /* An async goto has already setup a location. */
461  ast_channel_clear_softhangup(chan, AST_SOFTHANGUP_ASYNCGOTO);
462  if (!ast_check_hangup(chan)) {
463  goto_failed = 0;
464  }
465  return goto_failed;
466  }
467 
468  /* Get after bridge goto datastore. */
469  datastore = after_bridge_goto_remove(chan);
470  if (!datastore) {
471  return goto_failed;
472  }
473 
474  after_bridge = datastore->data;
475  if (after_bridge->run_h_exten) {
476  if (ast_exists_extension(chan, after_bridge->context, "h", 1,
477  S_COR(ast_channel_caller(chan)->id.number.valid,
478  ast_channel_caller(chan)->id.number.str, NULL))) {
479  ast_debug(1, "Running after bridge goto h exten %s,h,1\n",
480  ast_channel_context(chan));
481  ast_pbx_h_exten_run(chan, after_bridge->context);
482  }
483  } else if (!ast_check_hangup(chan)) {
484  /* Clear the outgoing flag */
486 
487  if (after_bridge->specific) {
488  goto_failed = ast_explicit_goto(chan, after_bridge->context,
489  after_bridge->exten, after_bridge->priority);
490  } else if (!ast_strlen_zero(after_bridge->parseable_goto)) {
491  char *context;
492  char *exten;
493  int priority;
494 
495  /* Option F(x) for Bridge(), Dial(), and Queue() */
496 
497  /* Save current dialplan location in case of failure. */
498  context = ast_strdupa(ast_channel_context(chan));
499  exten = ast_strdupa(ast_channel_exten(chan));
500  priority = ast_channel_priority(chan);
501 
502  /* Set current dialplan position to default dialplan position */
503  ast_explicit_goto(chan, after_bridge->context, after_bridge->exten,
504  after_bridge->priority);
505 
506  /* Then perform the goto */
507  goto_failed = ast_parseable_goto(chan, after_bridge->parseable_goto);
508  if (goto_failed) {
509  /* Restore original dialplan location. */
510  ast_channel_context_set(chan, context);
511  ast_channel_exten_set(chan, exten);
512  ast_channel_priority_set(chan, priority);
513  }
514  } else {
515  /* Option F() for Bridge(), Dial(), and Queue() */
516  goto_failed = ast_goto_if_exists(chan, after_bridge->context,
517  after_bridge->exten, after_bridge->priority + 1);
518  }
519  if (!goto_failed) {
522  }
523 
524  ast_debug(1, "Setup after bridge goto location to %s,%s,%d.\n",
525  ast_channel_context(chan),
526  ast_channel_exten(chan),
527  ast_channel_priority(chan));
528  }
529  }
530 
531  /* Discard after bridge goto datastore. */
532  ast_datastore_free(datastore);
533 
534  return goto_failed;
535 }
struct ast_party_caller * ast_channel_caller(struct ast_channel *chan)
void ast_pbx_h_exten_run(struct ast_channel *chan, const char *context)
Run the h exten from the given context.
Definition: pbx.c:4209
static char exten[AST_MAX_EXTENSION]
Definition: chan_alsa.c:118
#define ast_test_flag(p, flag)
Definition: utils.h:63
const char * parseable_goto
Definition: bridge_after.c:317
void ast_channel_clear_flag(struct ast_channel *chan, unsigned int flag)
Definition: channel.c:11235
int ast_explicit_goto(struct ast_channel *chan, const char *context, const char *exten, int priority)
Definition: pbx.c:6987
Structure for a data store object.
Definition: datastore.h:68
#define NULL
Definition: resample.c:96
static int priority
int ast_channel_priority(const struct ast_channel *chan)
int ast_datastore_free(struct ast_datastore *datastore)
Free a data store object.
Definition: datastore.c:68
#define ast_strlen_zero(foo)
Definition: strings.h:52
Number structure.
Definition: app_followme.c:154
#define ast_debug(level,...)
Log a DEBUG message.
Definition: logger.h:452
void ast_channel_clear_softhangup(struct ast_channel *chan, int flag)
Clear a set of softhangup flags from a channel.
Definition: channel.c:2437
int ast_parseable_goto(struct ast_channel *chan, const char *goto_string)
Definition: pbx.c:8859
#define S_COR(a, b, c)
returns the equivalent of logic or for strings, with an additional boolean check: second one if not e...
Definition: strings.h:85
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition: astmm.h:300
static struct ast_datastore * after_bridge_goto_remove(struct ast_channel *chan)
Definition: bridge_after.c:382
int ast_exists_extension(struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid)
Determine whether an extension exists.
Definition: pbx.c:4179
const char * ast_channel_exten(const struct ast_channel *chan)
int ast_check_hangup(struct ast_channel *chan)
Check to see if a channel is needing hang up.
Definition: channel.c:445
unsigned int specific
Definition: bridge_after.c:327
const char * context
Definition: bridge_after.c:319
const char * exten
Definition: bridge_after.c:321
int ast_goto_if_exists(struct ast_channel *chan, const char *context, const char *exten, int priority)
Definition: pbx.c:8793
void ast_channel_exten_set(struct ast_channel *chan, const char *value)
int ast_channel_softhangup_internal_flag(struct ast_channel *chan)
void * data
Definition: datastore.h:70
void ast_channel_context_set(struct ast_channel *chan, const char *value)
const char * ast_channel_context(const struct ast_channel *chan)
static char context[AST_MAX_CONTEXT]
Definition: chan_alsa.c:116
struct ast_flags * ast_channel_flags(struct ast_channel *chan)
void ast_channel_priority_set(struct ast_channel *chan, int value)
unsigned int run_h_exten
Definition: bridge_after.c:325
void ast_channel_set_unbridged(struct ast_channel *chan, int value)
Sets the unbridged flag and queues a NULL frame on the channel to trigger a check by bridge_channel_w...