#include "asterisk/sched.h"
#include "asterisk/channel.h"
#include "asterisk/linkedlists.h"
Go to the source code of this file.
Data Structures | |
struct | ast_custom_function |
Data structure associated with a custom dialplan function. More... | |
struct | ast_pbx |
struct | ast_switch |
struct | ast_timing |
Defines | |
#define | AST_MAX_APP 32 |
#define | AST_PBX_KEEP 0 |
#define | AST_PBX_KEEPALIVE 10 |
Special return values from applications to the PBX {. | |
#define | AST_PBX_NO_HANGUP_PEER 11 |
#define | AST_PBX_REPLACE 1 |
#define | PRIORITY_HINT -1 |
Typedefs | |
typedef int(* | ast_state_cb_type )(char *context, char *id, enum ast_extension_states state, void *data, char *cid_num, char *cid_name) |
Typedef for devicestate and hint callbacks. | |
typedef int( | ast_switch_f )(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data) |
All switch functions have the same interface, so define a type for them. | |
Enumerations | |
enum | ast_extension_states { AST_EXTENSION_REMOVED = -2, AST_EXTENSION_DEACTIVATED = -1, AST_EXTENSION_NOT_INUSE = 0, AST_EXTENSION_INUSE = 1 << 0, AST_EXTENSION_BUSY = 1 << 1, AST_EXTENSION_UNAVAILABLE = 1 << 2, AST_EXTENSION_RINGING = 1 << 3, AST_EXTENSION_ONHOLD = 1 << 4 } |
Extension states. More... | |
enum | ast_pbx_result { AST_PBX_SUCCESS = 0, AST_PBX_FAILED = -1, AST_PBX_CALL_LIMIT = -2 } |
Functions | |
int | ast_active_calls (void) |
Retrieve the number of active calls. | |
int | ast_add_extension (const char *context, int replace, const char *extension, int priority, const char *label, const char *callerid, const char *application, void *data, void(*datad)(void *), const char *registrar) |
Add and extension to an extension context. | |
int | ast_add_extension2 (struct ast_context *con, int replace, const char *extension, int priority, const char *label, const char *callerid, const char *application, void *data, void(*datad)(void *), const char *registrar) |
Add an extension to an extension context, this time with an ast_context *. | |
int | ast_async_goto (struct ast_channel *chan, const char *context, const char *exten, int priority) |
int | ast_async_goto_by_name (const char *chan, const char *context, const char *exten, int priority) |
int | ast_async_goto_if_exists (struct ast_channel *chan, const char *context, const char *exten, int priority) |
int | ast_build_timing (struct ast_timing *i, const char *info) |
int | ast_canmatch_extension (struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid) |
Looks for a valid matching extension. | |
int | ast_check_timing (const struct ast_timing *i) |
int | ast_context_add_ignorepat (const char *context, const char *ignorepat, const char *registrar) |
Add an ignorepat. | |
int | ast_context_add_ignorepat2 (struct ast_context *con, const char *ignorepat, const char *registrar) |
int | ast_context_add_include (const char *context, const char *include, const char *registrar) |
Add a context include. | |
int | ast_context_add_include2 (struct ast_context *con, const char *include, const char *registrar) |
Add a context include. | |
int | ast_context_add_switch (const char *context, const char *sw, const char *data, int eval, const char *registrar) |
Add a switch. | |
int | ast_context_add_switch2 (struct ast_context *con, const char *sw, const char *data, int eval, const char *registrar) |
Adds a switch (first param is a ast_context). | |
struct ast_context * | ast_context_create (struct ast_context **extcontexts, const char *name, const char *registrar) |
Register a new context. | |
void | ast_context_destroy (struct ast_context *con, const char *registrar) |
Destroy a context (matches the specified context (or ANY context if NULL). | |
struct ast_context * | ast_context_find (const char *name) |
Find a context. | |
struct ast_context * | ast_context_find_or_create (struct ast_context **extcontexts, const char *name, const char *registrar) |
int | ast_context_lockmacro (const char *macrocontext) |
locks the macrolock in the given given context | |
int | ast_context_remove_extension (const char *context, const char *extension, int priority, const char *registrar) |
Simply remove extension from context. | |
int | ast_context_remove_extension2 (struct ast_context *con, const char *extension, int priority, const char *registrar) |
This functionc locks given context, search for the right extension and fires out all peer in this extensions with given priority. If priority is set to 0, all peers are removed. After that, unlock context and return. | |
int | ast_context_remove_ignorepat (const char *context, const char *ignorepat, const char *registrar) |
int | ast_context_remove_ignorepat2 (struct ast_context *con, const char *ignorepat, const char *registrar) |
int | ast_context_remove_include (const char *context, const char *include, const char *registrar) |
Remove a context include. | |
int | ast_context_remove_include2 (struct ast_context *con, const char *include, const char *registrar) |
Removes an include by an ast_context structure. | |
int | ast_context_remove_switch (const char *context, const char *sw, const char *data, const char *registrar) |
Remove a switch. | |
int | ast_context_remove_switch2 (struct ast_context *con, const char *sw, const char *data, const char *registrar) |
This function locks given context, removes switch, unlock context and return. | |
int | ast_context_unlockmacro (const char *macrocontext) |
Unlocks the macrolock in the given context. | |
int | ast_context_verify_includes (struct ast_context *con) |
Verifies includes in an ast_contect structure. | |
struct ast_custom_function * | ast_custom_function_find (const char *name) |
int | ast_custom_function_register (struct ast_custom_function *acf) |
Reigster a custom function. | |
int | ast_custom_function_unregister (struct ast_custom_function *acf) |
Unregister a custom function. | |
int | ast_exists_extension (struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid) |
Determine whether an extension exists. | |
int | ast_explicit_goto (struct ast_channel *chan, const char *context, const char *exten, int priority) |
int | ast_extension_close (const char *pattern, const char *data, int needmore) |
int | ast_extension_match (const char *pattern, const char *extension) |
Determine if a given extension matches a given pattern (in NXX format). | |
int | ast_extension_patmatch (const char *pattern, const char *data) |
int | ast_extension_state (struct ast_channel *c, const char *context, const char *exten) |
Uses hint and devicestate callback to get the state of an extension. | |
const char * | ast_extension_state2str (int extension_state) |
Return string representation of the state of an extension. | |
int | ast_extension_state_add (const char *context, const char *exten, ast_state_cb_type callback, void *data) |
Registers a state change callback. | |
int | ast_extension_state_del (int id, ast_state_cb_type callback) |
Deletes a registered state change callback by ID. | |
int | ast_findlabel_extension (struct ast_channel *c, const char *context, const char *exten, const char *label, const char *callerid) |
Find the priority of an extension that has the specified label. | |
int | ast_findlabel_extension2 (struct ast_channel *c, struct ast_context *con, const char *exten, const char *label, const char *callerid) |
Find the priority of an extension that has the specified label. | |
int | ast_func_read (struct ast_channel *chan, char *function, char *workspace, size_t len) |
executes a read operation on a function | |
int | ast_func_write (struct ast_channel *chan, char *function, const char *value) |
executes a write operation on a function | |
const char * | ast_get_context_name (struct ast_context *con) |
const char * | ast_get_context_registrar (struct ast_context *c) |
const char * | ast_get_extension_app (struct ast_exten *e) |
void * | ast_get_extension_app_data (struct ast_exten *e) |
const char * | ast_get_extension_cidmatch (struct ast_exten *e) |
struct ast_context * | ast_get_extension_context (struct ast_exten *exten) |
const char * | ast_get_extension_label (struct ast_exten *e) |
int | ast_get_extension_matchcid (struct ast_exten *e) |
const char * | ast_get_extension_name (struct ast_exten *exten) |
int | ast_get_extension_priority (struct ast_exten *exten) |
const char * | ast_get_extension_registrar (struct ast_exten *e) |
int | ast_get_hint (char *hint, int maxlen, char *name, int maxnamelen, struct ast_channel *c, const char *context, const char *exten) |
If an extension exists, return non-zero. | |
const char * | ast_get_ignorepat_name (struct ast_ignorepat *ip) |
const char * | ast_get_ignorepat_registrar (struct ast_ignorepat *ip) |
const char * | ast_get_include_name (struct ast_include *include) |
const char * | ast_get_include_registrar (struct ast_include *i) |
const char * | ast_get_switch_data (struct ast_sw *sw) |
const char * | ast_get_switch_name (struct ast_sw *sw) |
const char * | ast_get_switch_registrar (struct ast_sw *sw) |
int | ast_goto_if_exists (struct ast_channel *chan, const char *context, const char *exten, int priority) |
void | ast_hint_state_changed (const char *device, char *cid_num, char *cid_name) |
int | ast_ignore_pattern (const char *context, const char *pattern) |
Checks to see if a number should be ignored. | |
int | ast_lock_context (struct ast_context *con) |
Locks a given context. | |
int | ast_lock_contexts (void) |
Locks the context list. | |
int | ast_matchmore_extension (struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid) |
Looks to see if adding anything to this extension might match something. (exists ^ canmatch). | |
void | ast_merge_contexts_and_delete (struct ast_context **extcontexts, const char *registrar) |
Merge the temporary contexts into a global contexts list and delete from the global list the ones that are being added. | |
int | ast_parseable_goto (struct ast_channel *chan, const char *goto_string) |
int | ast_pbx_outgoing_app (const char *type, int format, void *data, int timeout, const char *app, const char *appdata, int *reason, int sync, const char *cid_num, const char *cid_name, struct ast_variable *vars, const char *account, struct ast_channel **locked_channel) |
int | ast_pbx_outgoing_app_uniqueid (const char *type, int format, void *data, int timeout, const char *app, const char *appdata, int *reason, int sync, int callingpres, const char *cid_num, const char *cid_name, struct ast_variable *vars, const char *account, struct ast_channel **locked_channel, char *uniqueid) |
int | ast_pbx_outgoing_exten (const char *type, int format, void *data, int timeout, const char *context, const char *exten, int priority, int *reason, int sync, const char *cid_num, const char *cid_name, struct ast_variable *vars, const char *account, struct ast_channel **locked_channel) |
int | ast_pbx_outgoing_exten_uniqueid (const char *type, int format, void *data, int timeout, const char *context, const char *exten, int priority, int *reason, int sync, int callingpres, const char *cid_num, const char *cid_name, struct ast_variable *vars, const char *account, struct ast_channel **locked_channel, char *uniqueid) |
enum ast_pbx_result | ast_pbx_run (struct ast_channel *c) |
Execute the PBX in the current thread. | |
enum ast_pbx_result | ast_pbx_start (struct ast_channel *c) |
Create a new thread and start the PBX. | |
int | ast_rdlock_contexts (void) |
int | ast_register_application (const char *app, int(*execute)(struct ast_channel *, void *), const char *synopsis, const char *description) |
Register an application. | |
int | ast_register_switch (struct ast_switch *sw) |
Register an alternative dialplan switch. | |
int | ast_spawn_extension (struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid) |
Launch a new extension (i.e. new stack). | |
int | ast_unlock_context (struct ast_context *con) |
int | ast_unlock_contexts (void) |
Unlocks contexts. | |
int | ast_unregister_application (const char *app) |
Unregister an application. | |
void | ast_unregister_switch (struct ast_switch *sw) |
Unregister an alternative switch. | |
struct ast_exten * | ast_walk_context_extensions (struct ast_context *con, struct ast_exten *priority) |
struct ast_ignorepat * | ast_walk_context_ignorepats (struct ast_context *con, struct ast_ignorepat *ip) |
struct ast_include * | ast_walk_context_includes (struct ast_context *con, struct ast_include *inc) |
struct ast_sw * | ast_walk_context_switches (struct ast_context *con, struct ast_sw *sw) |
struct ast_context * | ast_walk_contexts (struct ast_context *con) |
struct ast_exten * | ast_walk_extension_priorities (struct ast_exten *exten, struct ast_exten *priority) |
int | ast_wrlock_contexts (void) |
void | pbx_builtin_clear_globals (void) |
const char * | pbx_builtin_getvar_helper (struct ast_channel *chan, const char *name) |
void | pbx_builtin_pushvar_helper (struct ast_channel *chan, const char *name, const char *value) |
int | pbx_builtin_serialize_variables (struct ast_channel *chan, char *buf, size_t size) |
int | pbx_builtin_setvar (struct ast_channel *chan, void *data) |
void | pbx_builtin_setvar_helper (struct ast_channel *chan, const char *name, const char *value) |
int | pbx_checkcondition (const char *condition) |
Evaluate a condition. | |
int | pbx_exec (struct ast_channel *c, struct ast_app *app, void *data) |
Execute an application. | |
struct ast_app * | pbx_findapp (const char *app) |
Look up an application. | |
void | pbx_retrieve_variable (struct ast_channel *c, const char *var, char **ret, char *workspace, int workspacelen, struct varshead *headp) |
pbx_retrieve_variable: Support for Asterisk built-in variables --- | |
int | pbx_set_autofallthrough (int newval) |
void | pbx_substitute_variables_helper (struct ast_channel *c, const char *cp1, char *cp2, int count) |
void | pbx_substitute_variables_varshead (struct varshead *headp, const char *cp1, char *cp2, int count) |
Definition in file pbx.h.
#define AST_MAX_APP 32 |
Max length of an application
Definition at line 34 of file pbx.h.
Referenced by destroy_station(), handle_show_application(), handle_show_application_deprecated(), handle_show_function(), handle_show_function_deprecated(), and sla_build_station().
#define AST_PBX_KEEPALIVE 10 |
Special return values from applications to the PBX {.
Destroy the thread, but don't hang up the channel
Definition at line 40 of file pbx.h.
Referenced by __ast_pbx_run(), _macro_exec(), agi_handle_command(), builtin_blindtransfer(), builtin_parkcall(), feature_exec_app(), park_call_exec(), queue_exec(), rpt_exec(), and run_agi().
#define AST_PBX_NO_HANGUP_PEER 11 |
Definition at line 41 of file pbx.h.
Referenced by ast_retrieve_call(), builtin_blindtransfer(), builtin_parkcall(), feature_exec_app(), park_exec(), and try_calling().
#define PRIORITY_HINT -1 |
} Special Priority for a hint
Definition at line 44 of file pbx.h.
Referenced by add_extensions(), add_pri(), ast_add_extension2(), ast_hint_extension(), ast_merge_contexts_and_delete(), destroy_exten(), destroy_station(), handle_context_add_extension(), handle_context_add_extension_deprecated(), handle_context_remove_extension(), handle_context_remove_extension_deprecated(), handle_save_dialplan(), park_add_hints(), pbx_load_config(), print_ext(), and sla_build_station().
typedef int(* ast_state_cb_type)(char *context, char *id, enum ast_extension_states state, void *data, char *cid_num, char *cid_name) |
typedef int( ast_switch_f)(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data) |
enum ast_extension_states |
Extension states.
Definition at line 47 of file pbx.h.
00047 { 00048 AST_EXTENSION_REMOVED = -2, /*!< Extension removed */ 00049 AST_EXTENSION_DEACTIVATED = -1, /*!< Extension hint removed */ 00050 AST_EXTENSION_NOT_INUSE = 0, /*!< No device INUSE or BUSY */ 00051 AST_EXTENSION_INUSE = 1 << 0, /*!< One or more devices INUSE */ 00052 AST_EXTENSION_BUSY = 1 << 1, /*!< All devices BUSY */ 00053 AST_EXTENSION_UNAVAILABLE = 1 << 2, /*!< All devices UNAVAILABLE/UNREGISTERED */ 00054 AST_EXTENSION_RINGING = 1 << 3, /*!< All devices RINGING */ 00055 AST_EXTENSION_ONHOLD = 1 << 4, /*!< All devices ONHOLD */ 00056 };
enum ast_pbx_result |
Definition at line 214 of file pbx.h.
00214 { 00215 AST_PBX_SUCCESS = 0, 00216 AST_PBX_FAILED = -1, 00217 AST_PBX_CALL_LIMIT = -2, 00218 };
int ast_active_calls | ( | void | ) |
Retrieve the number of active calls.
Definition at line 2683 of file pbx.c.
References countcalls.
Referenced by handle_chanlist(), and handle_chanlist_deprecated().
02684 { 02685 return countcalls; 02686 }
int ast_add_extension | ( | const char * | context, | |
int | replace, | |||
const char * | extension, | |||
int | priority, | |||
const char * | label, | |||
const char * | callerid, | |||
const char * | application, | |||
void * | data, | |||
void(*)(void *) | datad, | |||
const char * | registrar | |||
) |
Add and extension to an extension context.
context | context to add the extension to | |
replace | ||
extension | extension to add | |
priority | priority level of extension addition | |
label | extension label | |
callerid | pattern to match CallerID, or NULL to match any CallerID | |
application | application to run on the extension with that priority level | |
data | data to pass to the application | |
datad | ||
registrar | who registered the extension |
0 | success | |
-1 | failure |
Definition at line 4560 of file pbx.c.
References ast_add_extension2(), ast_unlock_contexts(), and find_context_locked().
Referenced by handle_context_add_extension(), handle_context_add_extension_deprecated(), park_add_hints(), and register_peer_exten().
04563 { 04564 int ret = -1; 04565 struct ast_context *c = find_context_locked(context); 04566 04567 if (c) { 04568 ret = ast_add_extension2(c, replace, extension, priority, label, callerid, 04569 application, data, datad, registrar); 04570 ast_unlock_contexts(); 04571 } 04572 return ret; 04573 }
int ast_add_extension2 | ( | struct ast_context * | con, | |
int | replace, | |||
const char * | extension, | |||
int | priority, | |||
const char * | label, | |||
const char * | callerid, | |||
const char * | application, | |||
void * | data, | |||
void(*)(void *) | datad, | |||
const char * | registrar | |||
) |
Add an extension to an extension context, this time with an ast_context *.
We sort extensions in order of matching preference, so that we can stop the search as soon as we find a suitable match. This ordering also takes care of wildcards such as '.' (meaning "one or more of any character") and '!' (which is 'earlymatch', meaning "zero or more of any character" but also impacts the return value from CANMATCH and EARLYMATCH.
The extension match rules defined in the devmeeting 2006.05.05 are quite simple: WE SELECT THE LONGEST MATCH. In detail, "longest" means the number of matched characters in the extension. In case of ties (e.g. _XXX and 333) in the length of a pattern, we give priority to entries with the smallest cardinality (e.g, [5-9] comes before [2-8] before the former has only 5 elements, while the latter has 7, etc. In case of same cardinality, the first element in the range counts. If we still have a tie, any final '!' will make this as a possibly less specific pattern.
EBUSY - can't lock EEXIST - extension with the same priority exist and no replace is set
Definition at line 4769 of file pbx.c.
References add_pri(), ast_exten::app, ast_add_hint(), ast_calloc, AST_LIST_FIRST, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), ast_exten::cidmatch, ast_exten::data, ast_exten::datad, el, errno, ext_cmp(), ext_strncpy(), ast_exten::exten, globals, ast_exten::label, ast_context::lock, LOG_DEBUG, ast_exten::matchcid, ast_exten::next, option_debug, option_verbose, ast_exten::parent, pbx_substitute_variables_varshead(), ast_exten::priority, PRIORITY_HINT, ast_exten::registrar, ast_context::root, ast_exten::stuff, VAR_BUF_SIZE, and VERBOSE_PREFIX_3.
Referenced by add_extensions(), ast_add_extension(), ast_autoanswer_login(), autoanswer_reregister_extensions(), do_parking_thread(), load_config(), park_call_full(), pbx_load_config(), pbx_load_users(), sla_build_station(), and sla_build_trunk().
04773 { 04774 /* 04775 * Sort extensions (or patterns) according to the rules indicated above. 04776 * These are implemented by the function ext_cmp()). 04777 * All priorities for the same ext/pattern/cid are kept in a list, 04778 * using the 'peer' field as a link field.. 04779 */ 04780 struct ast_exten *tmp, *e, *el = NULL; 04781 int res; 04782 int length; 04783 char *p; 04784 char expand_buf[VAR_BUF_SIZE] = { 0, }; 04785 04786 /* if we are adding a hint, and there are global variables, and the hint 04787 contains variable references, then expand them 04788 */ 04789 ast_mutex_lock(&globalslock); 04790 if (priority == PRIORITY_HINT && AST_LIST_FIRST(&globals) && strstr(application, "${")) { 04791 pbx_substitute_variables_varshead(&globals, application, expand_buf, sizeof(expand_buf)); 04792 application = expand_buf; 04793 } 04794 ast_mutex_unlock(&globalslock); 04795 04796 length = sizeof(struct ast_exten); 04797 length += strlen(extension) + 1; 04798 length += strlen(application) + 1; 04799 if (label) 04800 length += strlen(label) + 1; 04801 if (callerid) 04802 length += strlen(callerid) + 1; 04803 else 04804 length ++; /* just the '\0' */ 04805 04806 /* Be optimistic: Build the extension structure first */ 04807 if (!(tmp = ast_calloc(1, length))) 04808 return -1; 04809 04810 /* use p as dst in assignments, as the fields are const char * */ 04811 p = tmp->stuff; 04812 if (label) { 04813 tmp->label = p; 04814 strcpy(p, label); 04815 p += strlen(label) + 1; 04816 } 04817 tmp->exten = p; 04818 p += ext_strncpy(p, extension, strlen(extension) + 1) + 1; 04819 tmp->priority = priority; 04820 tmp->cidmatch = p; /* but use p for assignments below */ 04821 if (callerid) { 04822 p += ext_strncpy(p, callerid, strlen(callerid) + 1) + 1; 04823 tmp->matchcid = 1; 04824 } else { 04825 *p++ = '\0'; 04826 tmp->matchcid = 0; 04827 } 04828 tmp->app = p; 04829 strcpy(p, application); 04830 tmp->parent = con; 04831 tmp->data = data; 04832 tmp->datad = datad; 04833 tmp->registrar = registrar; 04834 04835 ast_mutex_lock(&con->lock); 04836 res = 0; /* some compilers will think it is uninitialized otherwise */ 04837 for (e = con->root; e; el = e, e = e->next) { /* scan the extension list */ 04838 res = ext_cmp(e->exten, extension); 04839 if (res == 0) { /* extension match, now look at cidmatch */ 04840 if (!e->matchcid && !tmp->matchcid) 04841 res = 0; 04842 else if (tmp->matchcid && !e->matchcid) 04843 res = 1; 04844 else if (e->matchcid && !tmp->matchcid) 04845 res = -1; 04846 else 04847 res = strcasecmp(e->cidmatch, tmp->cidmatch); 04848 } 04849 if (res >= 0) 04850 break; 04851 } 04852 if (e && res == 0) { /* exact match, insert in the pri chain */ 04853 res = add_pri(con, tmp, el, e, replace); 04854 ast_mutex_unlock(&con->lock); 04855 if (res < 0) { 04856 errno = EEXIST; /* XXX do we care ? */ 04857 return 0; /* XXX should we return -1 maybe ? */ 04858 } 04859 } else { 04860 /* 04861 * not an exact match, this is the first entry with this pattern, 04862 * so insert in the main list right before 'e' (if any) 04863 */ 04864 tmp->next = e; 04865 if (el) 04866 el->next = tmp; 04867 else 04868 con->root = tmp; 04869 ast_mutex_unlock(&con->lock); 04870 if (tmp->priority == PRIORITY_HINT) 04871 ast_add_hint(tmp); 04872 } 04873 if (option_debug) { 04874 if (tmp->matchcid) { 04875 if (option_debug) 04876 ast_log(LOG_DEBUG, "Added extension '%s' priority %d (CID match '%s') to %s\n", 04877 tmp->exten, tmp->priority, tmp->cidmatch, con->name); 04878 } else { 04879 if (option_debug) 04880 ast_log(LOG_DEBUG, "Added extension '%s' priority %d to %s\n", 04881 tmp->exten, tmp->priority, con->name); 04882 } 04883 } 04884 if (option_verbose > 2) { 04885 if (tmp->matchcid) { 04886 ast_verbose( VERBOSE_PREFIX_3 "Added extension '%s' priority %d (CID match '%s')to %s\n", 04887 tmp->exten, tmp->priority, tmp->cidmatch, con->name); 04888 } else { 04889 ast_verbose( VERBOSE_PREFIX_3 "Added extension '%s' priority %d to %s\n", 04890 tmp->exten, tmp->priority, con->name); 04891 } 04892 } 04893 return 0; 04894 }
int ast_async_goto | ( | struct ast_channel * | chan, | |
const char * | context, | |||
const char * | exten, | |||
int | priority | |||
) |
Definition at line 4598 of file pbx.c.
References ast_channel::_state, ast_channel::amaflags, ast_cdr_discard(), ast_cdr_dup(), ast_channel_alloc(), ast_channel_lock, ast_channel_masquerade(), ast_channel_unlock, ast_do_masquerade(), ast_explicit_goto(), ast_hangup(), ast_log(), ast_pbx_start(), AST_SOFTHANGUP_ASYNCGOTO, ast_softhangup_nolock(), ast_channel::cdr, ast_channel::context, ast_channel::exten, LOG_WARNING, ast_channel::pbx, ast_channel::readformat, S_OR, and ast_channel::writeformat.
Referenced by __ast_goto_if_exists(), action_redirect(), ast_async_goto_by_name(), builtin_blindtransfer(), console_transfer(), console_transfer_deprecated(), handle_request_bye(), handle_request_refer(), process_ast_dsp(), socket_process(), and zt_handle_dtmfup().
04599 { 04600 int res = 0; 04601 04602 ast_channel_lock(chan); 04603 04604 if (chan->pbx) { /* This channel is currently in the PBX */ 04605 ast_explicit_goto(chan, context, exten, priority); 04606 ast_softhangup_nolock(chan, AST_SOFTHANGUP_ASYNCGOTO); 04607 } else { 04608 /* In order to do it when the channel doesn't really exist within 04609 the PBX, we have to make a new channel, masquerade, and start the PBX 04610 at the new location */ 04611 struct ast_channel *tmpchan = ast_channel_alloc(0, chan->_state, 0, 0, chan->accountcode, chan->exten, chan->context, chan->amaflags, "AsyncGoto/%s", chan->name); 04612 if (!tmpchan) { 04613 res = -1; 04614 } else { 04615 if (chan->cdr) { 04616 ast_cdr_discard(tmpchan->cdr); 04617 tmpchan->cdr = ast_cdr_dup(chan->cdr); /* share the love */ 04618 } 04619 /* Make formats okay */ 04620 tmpchan->readformat = chan->readformat; 04621 tmpchan->writeformat = chan->writeformat; 04622 /* Setup proper location */ 04623 ast_explicit_goto(tmpchan, 04624 S_OR(context, chan->context), S_OR(exten, chan->exten), priority); 04625 04626 /* Masquerade into temp channel */ 04627 ast_channel_masquerade(tmpchan, chan); 04628 04629 /* Grab the locks and get going */ 04630 ast_channel_lock(tmpchan); 04631 ast_do_masquerade(tmpchan); 04632 ast_channel_unlock(tmpchan); 04633 /* Start the PBX going on our stolen channel */ 04634 if (ast_pbx_start(tmpchan)) { 04635 ast_log(LOG_WARNING, "Unable to start PBX on %s\n", tmpchan->name); 04636 ast_hangup(tmpchan); 04637 res = -1; 04638 } 04639 } 04640 } 04641 ast_channel_unlock(chan); 04642 return res; 04643 }
int ast_async_goto_by_name | ( | const char * | chan, | |
const char * | context, | |||
const char * | exten, | |||
int | priority | |||
) |
Definition at line 4645 of file pbx.c.
References ast_async_goto(), ast_channel_unlock, and ast_get_channel_by_name_locked().
04646 { 04647 struct ast_channel *chan; 04648 int res = -1; 04649 04650 chan = ast_get_channel_by_name_locked(channame); 04651 if (chan) { 04652 res = ast_async_goto(chan, context, exten, priority); 04653 ast_channel_unlock(chan); 04654 } 04655 return res; 04656 }
int ast_async_goto_if_exists | ( | struct ast_channel * | chan, | |
const char * | context, | |||
const char * | exten, | |||
int | priority | |||
) |
Definition at line 6385 of file pbx.c.
References __ast_goto_if_exists().
Referenced by asyncgoto_exec().
06386 { 06387 return __ast_goto_if_exists(chan, context, exten, priority, 1); 06388 }
int ast_build_timing | ( | struct ast_timing * | i, | |
const char * | info | |||
) |
Definition at line 4243 of file pbx.c.
References ast_strlen_zero(), ast_timing::daymask, days, ast_timing::dowmask, get_range(), get_timerange(), ast_timing::monthmask, months, and strsep().
Referenced by ast_context_add_include2(), iftime(), pbx_builtin_execiftime(), and pbx_builtin_gotoiftime().
04244 { 04245 char info_save[256]; 04246 char *info; 04247 04248 /* Check for empty just in case */ 04249 if (ast_strlen_zero(info_in)) 04250 return 0; 04251 /* make a copy just in case we were passed a static string */ 04252 ast_copy_string(info_save, info_in, sizeof(info_save)); 04253 info = info_save; 04254 /* Assume everything except time */ 04255 i->monthmask = 0xfff; /* 12 bits */ 04256 i->daymask = 0x7fffffffU; /* 31 bits */ 04257 i->dowmask = 0x7f; /* 7 bits */ 04258 /* on each call, use strsep() to move info to the next argument */ 04259 get_timerange(i, strsep(&info, "|")); 04260 if (info) 04261 i->dowmask = get_range(strsep(&info, "|"), 7, days, "day of week"); 04262 if (info) 04263 i->daymask = get_range(strsep(&info, "|"), 31, NULL, "day"); 04264 if (info) 04265 i->monthmask = get_range(strsep(&info, "|"), 12, months, "month"); 04266 return 1; 04267 }
int ast_canmatch_extension | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
const char * | callerid | |||
) |
Looks for a valid matching extension.
c | not really important | |
context | context to serach within | |
exten | extension to check | |
priority | priority of extension path | |
callerid | callerid of extension being searched for |
Definition at line 2305 of file pbx.c.
References E_CANMATCH, and pbx_extension_helper().
Referenced by background_detect_exec(), cb_events(), dp_lookup(), dundi_lookup_local(), get_also_info(), get_destination(), handle_link_data(), handle_link_phone_dtmf(), local_dtmf_helper(), loopback_canmatch(), mgcp_ss(), phone_check_exception(), skinny_ss(), ss_thread(), and valid_exit().
02306 { 02307 return pbx_extension_helper(c, NULL, context, exten, priority, NULL, callerid, E_CANMATCH); 02308 }
int ast_check_timing | ( | const struct ast_timing * | i | ) |
Definition at line 4269 of file pbx.c.
References ast_localtime(), ast_log(), ast_timing::daymask, ast_timing::dowmask, LOG_WARNING, ast_timing::minmask, ast_timing::monthmask, and t.
Referenced by iftime(), include_valid(), pbx_builtin_execiftime(), and pbx_builtin_gotoiftime().
04270 { 04271 struct tm tm; 04272 time_t t = time(NULL); 04273 04274 ast_localtime(&t, &tm, NULL); 04275 04276 /* If it's not the right month, return */ 04277 if (!(i->monthmask & (1 << tm.tm_mon))) 04278 return 0; 04279 04280 /* If it's not that time of the month.... */ 04281 /* Warning, tm_mday has range 1..31! */ 04282 if (!(i->daymask & (1 << (tm.tm_mday-1)))) 04283 return 0; 04284 04285 /* If it's not the right day of the week */ 04286 if (!(i->dowmask & (1 << tm.tm_wday))) 04287 return 0; 04288 04289 /* Sanity check the hour just to be safe */ 04290 if ((tm.tm_hour < 0) || (tm.tm_hour > 23)) { 04291 ast_log(LOG_WARNING, "Insane time...\n"); 04292 return 0; 04293 } 04294 04295 /* Now the tough part, we calculate if it fits 04296 in the right time based on min/hour */ 04297 if (!(i->minmask[tm.tm_hour] & (1 << (tm.tm_min / 2)))) 04298 return 0; 04299 04300 /* If we got this far, then we're good */ 04301 return 1; 04302 }
int ast_context_add_ignorepat | ( | const char * | context, | |
const char * | ignorepat, | |||
const char * | registrar | |||
) |
Add an ignorepat.
context | which context to add the ignorpattern to | |
ignorepat | ignorepattern to set up for the extension | |
registrar | registrar of the ignore pattern |
0 | on success | |
-1 | on failure |
Definition at line 4496 of file pbx.c.
References ast_context_add_ignorepat2(), ast_unlock_contexts(), and find_context_locked().
Referenced by handle_context_add_ignorepat(), and handle_context_add_ignorepat_deprecated().
04497 { 04498 int ret = -1; 04499 struct ast_context *c = find_context_locked(context); 04500 04501 if (c) { 04502 ret = ast_context_add_ignorepat2(c, value, registrar); 04503 ast_unlock_contexts(); 04504 } 04505 return ret; 04506 }
int ast_context_add_ignorepat2 | ( | struct ast_context * | con, | |
const char * | ignorepat, | |||
const char * | registrar | |||
) |
Definition at line 4508 of file pbx.c.
References ast_calloc, ast_mutex_lock(), ast_mutex_unlock(), errno, ast_context::ignorepats, ast_context::lock, ast_ignorepat::next, ast_ignorepat::pattern, and ast_ignorepat::registrar.
Referenced by ast_compile_ael2(), ast_context_add_ignorepat(), and pbx_load_config().
04509 { 04510 struct ast_ignorepat *ignorepat, *ignorepatc, *ignorepatl = NULL; 04511 int length; 04512 length = sizeof(struct ast_ignorepat); 04513 length += strlen(value) + 1; 04514 if (!(ignorepat = ast_calloc(1, length))) 04515 return -1; 04516 /* The cast to char * is because we need to write the initial value. 04517 * The field is not supposed to be modified otherwise 04518 */ 04519 strcpy((char *)ignorepat->pattern, value); 04520 ignorepat->next = NULL; 04521 ignorepat->registrar = registrar; 04522 ast_mutex_lock(&con->lock); 04523 for (ignorepatc = con->ignorepats; ignorepatc; ignorepatc = ignorepatc->next) { 04524 ignorepatl = ignorepatc; 04525 if (!strcasecmp(ignorepatc->pattern, value)) { 04526 /* Already there */ 04527 ast_mutex_unlock(&con->lock); 04528 errno = EEXIST; 04529 return -1; 04530 } 04531 } 04532 if (ignorepatl) 04533 ignorepatl->next = ignorepat; 04534 else 04535 con->ignorepats = ignorepat; 04536 ast_mutex_unlock(&con->lock); 04537 return 0; 04538 04539 }
int ast_context_add_include | ( | const char * | context, | |
const char * | include, | |||
const char * | registrar | |||
) |
Add a context include.
context | context to add include to | |
include | new include to add | |
registrar | who's registering it |
0 | on success | |
-1 | on error |
Definition at line 4049 of file pbx.c.
References ast_context_add_include2(), ast_unlock_contexts(), and find_context_locked().
Referenced by handle_context_add_include(), and handle_context_add_include_deprecated().
04050 { 04051 int ret = -1; 04052 struct ast_context *c = find_context_locked(context); 04053 04054 if (c) { 04055 ret = ast_context_add_include2(c, include, registrar); 04056 ast_unlock_contexts(); 04057 } 04058 return ret; 04059 }
int ast_context_add_include2 | ( | struct ast_context * | con, | |
const char * | include, | |||
const char * | registrar | |||
) |
Add a context include.
con | context to add the include to | |
include | include to add | |
registrar | who registered the context |
0 | on success | |
-1 | on failure |
Definition at line 4311 of file pbx.c.
References ast_build_timing(), ast_calloc, ast_get_context_name(), ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), errno, free, ast_include::hastime, ast_context::includes, ast_context::lock, ast_include::name, ast_include::next, option_verbose, ast_include::registrar, ast_include::rname, ast_include::stuff, ast_include::timing, and VERBOSE_PREFIX_3.
Referenced by ast_compile_ael2(), ast_context_add_include(), and pbx_load_config().
04313 { 04314 struct ast_include *new_include; 04315 char *c; 04316 struct ast_include *i, *il = NULL; /* include, include_last */ 04317 int length; 04318 char *p; 04319 04320 length = sizeof(struct ast_include); 04321 length += 2 * (strlen(value) + 1); 04322 04323 /* allocate new include structure ... */ 04324 if (!(new_include = ast_calloc(1, length))) 04325 return -1; 04326 /* Fill in this structure. Use 'p' for assignments, as the fields 04327 * in the structure are 'const char *' 04328 */ 04329 p = new_include->stuff; 04330 new_include->name = p; 04331 strcpy(p, value); 04332 p += strlen(value) + 1; 04333 new_include->rname = p; 04334 strcpy(p, value); 04335 /* Strip off timing info, and process if it is there */ 04336 if ( (c = strchr(p, '|')) ) { 04337 *c++ = '\0'; 04338 new_include->hastime = ast_build_timing(&(new_include->timing), c); 04339 } 04340 new_include->next = NULL; 04341 new_include->registrar = registrar; 04342 04343 ast_mutex_lock(&con->lock); 04344 04345 /* ... go to last include and check if context is already included too... */ 04346 for (i = con->includes; i; i = i->next) { 04347 if (!strcasecmp(i->name, new_include->name)) { 04348 free(new_include); 04349 ast_mutex_unlock(&con->lock); 04350 errno = EEXIST; 04351 return -1; 04352 } 04353 il = i; 04354 } 04355 04356 /* ... include new context into context list, unlock, return */ 04357 if (il) 04358 il->next = new_include; 04359 else 04360 con->includes = new_include; 04361 if (option_verbose > 2) 04362 ast_verbose(VERBOSE_PREFIX_3 "Including context '%s' in context '%s'\n", new_include->name, ast_get_context_name(con)); 04363 ast_mutex_unlock(&con->lock); 04364 04365 return 0; 04366 }
int ast_context_add_switch | ( | const char * | context, | |
const char * | sw, | |||
const char * | data, | |||
int | eval, | |||
const char * | registrar | |||
) |
Add a switch.
context | context to which to add the switch | |
sw | switch to add | |
data | data to pass to switch | |
eval | whether to evaluate variables when running switch | |
registrar | whoever registered the switch |
0 | on success | |
-1 | on failure |
Definition at line 4373 of file pbx.c.
References ast_context_add_switch2(), ast_unlock_contexts(), and find_context_locked().
04374 { 04375 int ret = -1; 04376 struct ast_context *c = find_context_locked(context); 04377 04378 if (c) { /* found, add switch to this context */ 04379 ret = ast_context_add_switch2(c, sw, data, eval, registrar); 04380 ast_unlock_contexts(); 04381 } 04382 return ret; 04383 }
int ast_context_add_switch2 | ( | struct ast_context * | con, | |
const char * | sw, | |||
const char * | data, | |||
int | eval, | |||
const char * | registrar | |||
) |
Adds a switch (first param is a ast_context).
Definition at line 4392 of file pbx.c.
References ast_calloc, ast_get_context_name(), AST_LIST_INSERT_TAIL, AST_LIST_TRAVERSE, ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), ast_sw::data, errno, ast_sw::eval, free, ast_context::lock, ast_sw::name, option_verbose, ast_sw::registrar, and VERBOSE_PREFIX_3.
Referenced by ast_compile_ael2(), ast_context_add_switch(), and pbx_load_config().
04394 { 04395 struct ast_sw *new_sw; 04396 struct ast_sw *i; 04397 int length; 04398 char *p; 04399 04400 length = sizeof(struct ast_sw); 04401 length += strlen(value) + 1; 04402 if (data) 04403 length += strlen(data); 04404 length++; 04405 04406 /* allocate new sw structure ... */ 04407 if (!(new_sw = ast_calloc(1, length))) 04408 return -1; 04409 /* ... fill in this structure ... */ 04410 p = new_sw->stuff; 04411 new_sw->name = p; 04412 strcpy(new_sw->name, value); 04413 p += strlen(value) + 1; 04414 new_sw->data = p; 04415 if (data) { 04416 strcpy(new_sw->data, data); 04417 p += strlen(data) + 1; 04418 } else { 04419 strcpy(new_sw->data, ""); 04420 p++; 04421 } 04422 new_sw->eval = eval; 04423 new_sw->registrar = registrar; 04424 04425 /* ... try to lock this context ... */ 04426 ast_mutex_lock(&con->lock); 04427 04428 /* ... go to last sw and check if context is already swd too... */ 04429 AST_LIST_TRAVERSE(&con->alts, i, list) { 04430 if (!strcasecmp(i->name, new_sw->name) && !strcasecmp(i->data, new_sw->data)) { 04431 free(new_sw); 04432 ast_mutex_unlock(&con->lock); 04433 errno = EEXIST; 04434 return -1; 04435 } 04436 } 04437 04438 /* ... sw new context into context list, unlock, return */ 04439 AST_LIST_INSERT_TAIL(&con->alts, new_sw, list); 04440 04441 if (option_verbose > 2) 04442 ast_verbose(VERBOSE_PREFIX_3 "Including switch '%s/%s' in context '%s'\n", new_sw->name, new_sw->data, ast_get_context_name(con)); 04443 04444 ast_mutex_unlock(&con->lock); 04445 04446 return 0; 04447 }
struct ast_context* ast_context_create | ( | struct ast_context ** | extcontexts, | |
const char * | name, | |||
const char * | registrar | |||
) | [read] |
Register a new context.
extcontexts | pointer to the ast_context structure pointer | |
name | name of the new context | |
registrar | registrar of the context |
Definition at line 3919 of file pbx.c.
References __ast_context_create().
Referenced by ast_autoanswer_login(), ast_compile_ael2(), autoanswer_reregister_extensions(), do_parking_thread(), load_config(), park_call_full(), reload_config(), and set_config().
03920 { 03921 return __ast_context_create(extcontexts, name, registrar, 0); 03922 }
void ast_context_destroy | ( | struct ast_context * | con, | |
const char * | registrar | |||
) |
Destroy a context (matches the specified context (or ANY context if NULL).
con | context to destroy | |
registrar | who registered it |
Definition at line 5369 of file pbx.c.
References __ast_context_destroy(), ast_unlock_contexts(), and ast_wrlock_contexts().
Referenced by cleanup_stale_contexts(), sla_destroy(), and unload_module().
05370 { 05371 ast_wrlock_contexts(); 05372 __ast_context_destroy(con,registrar); 05373 ast_unlock_contexts(); 05374 }
struct ast_context* ast_context_find | ( | const char * | name | ) | [read] |
Find a context.
name | name of the context to find |
Definition at line 895 of file pbx.c.
References ast_rdlock_contexts(), ast_unlock_contexts(), and ast_walk_contexts().
Referenced by _macro_exec(), ast_autoanswer_login(), ast_context_verify_includes(), ast_ignore_pattern(), autoanswer_reregister_extensions(), cleanup_stale_contexts(), do_autoanswer_thread(), do_parking_thread(), load_config(), park_call_full(), park_exec(), register_peer_exten(), reload_config(), and set_config().
00896 { 00897 struct ast_context *tmp = NULL; 00898 00899 ast_rdlock_contexts(); 00900 00901 while ( (tmp = ast_walk_contexts(tmp)) ) { 00902 if (!name || !strcasecmp(name, tmp->name)) 00903 break; 00904 } 00905 00906 ast_unlock_contexts(); 00907 00908 return tmp; 00909 }
struct ast_context* ast_context_find_or_create | ( | struct ast_context ** | extcontexts, | |
const char * | name, | |||
const char * | registrar | |||
) | [read] |
Definition at line 3924 of file pbx.c.
References __ast_context_create().
Referenced by ast_compile_ael2(), pbx_load_config(), pbx_load_users(), sla_build_station(), and sla_build_trunk().
03925 { 03926 return __ast_context_create(extcontexts, name, registrar, 1); 03927 }
int ast_context_lockmacro | ( | const char * | context | ) |
locks the macrolock in the given given context
macrocontext | name of the macro-context to lock |
0 | on success | |
-1 | on failure |
Definition at line 2920 of file pbx.c.
References ast_get_context_name(), ast_mutex_lock(), ast_rdlock_contexts(), ast_unlock_contexts(), and ast_walk_contexts().
Referenced by _macro_exec().
02921 { 02922 struct ast_context *c = NULL; 02923 int ret = -1; 02924 02925 ast_rdlock_contexts(); 02926 02927 while ((c = ast_walk_contexts(c))) { 02928 if (!strcmp(ast_get_context_name(c), context)) { 02929 ret = 0; 02930 break; 02931 } 02932 } 02933 02934 ast_unlock_contexts(); 02935 02936 /* if we found context, lock macrolock */ 02937 if (ret == 0) 02938 ret = ast_mutex_lock(&c->macrolock); 02939 02940 return ret; 02941 }
int ast_context_remove_extension | ( | const char * | context, | |
const char * | extension, | |||
int | priority, | |||
const char * | registrar | |||
) |
Simply remove extension from context.
context | context to remove extension from | |
extension | which extension to remove | |
priority | priority of extension to remove | |
registrar | registrar of the extension |
0 | on success | |
-1 | on failure |
Definition at line 2821 of file pbx.c.
References ast_context_remove_extension2(), ast_unlock_contexts(), and find_context_locked().
Referenced by destroy_station(), destroy_trunk(), handle_context_remove_extension(), handle_context_remove_extension_deprecated(), and register_peer_exten().
02822 { 02823 int ret = -1; /* default error return */ 02824 struct ast_context *c = find_context_locked(context); 02825 02826 if (c) { /* ... remove extension ... */ 02827 ret = ast_context_remove_extension2(c, extension, priority, registrar); 02828 ast_unlock_contexts(); 02829 } 02830 return ret; 02831 }
int ast_context_remove_extension2 | ( | struct ast_context * | con, | |
const char * | extension, | |||
int | priority, | |||
const char * | registrar | |||
) |
This functionc locks given context, search for the right extension and fires out all peer in this extensions with given priority. If priority is set to 0, all peers are removed. After that, unlock context and return.
Definition at line 2843 of file pbx.c.
References ast_mutex_lock(), ast_mutex_unlock(), destroy_exten(), ast_exten::exten, exten, ast_context::lock, ast_exten::next, ast_exten::peer, ast_exten::registrar, and ast_context::root.
Referenced by ast_context_remove_extension(), do_autoanswer_thread(), do_parking_thread(), load_config(), and park_exec().
02844 { 02845 struct ast_exten *exten, *prev_exten = NULL; 02846 struct ast_exten *peer; 02847 02848 ast_mutex_lock(&con->lock); 02849 02850 /* scan the extension list to find matching extension-registrar */ 02851 for (exten = con->root; exten; prev_exten = exten, exten = exten->next) { 02852 if (!strcmp(exten->exten, extension) && 02853 (!registrar || !strcmp(exten->registrar, registrar))) 02854 break; 02855 } 02856 if (!exten) { 02857 /* we can't find right extension */ 02858 ast_mutex_unlock(&con->lock); 02859 return -1; 02860 } 02861 02862 /* should we free all peers in this extension? (priority == 0)? */ 02863 if (priority == 0) { 02864 /* remove this extension from context list */ 02865 if (prev_exten) 02866 prev_exten->next = exten->next; 02867 else 02868 con->root = exten->next; 02869 02870 /* fire out all peers */ 02871 while ( (peer = exten) ) { 02872 exten = peer->peer; /* prepare for next entry */ 02873 destroy_exten(peer); 02874 } 02875 } else { 02876 /* scan the priority list to remove extension with exten->priority == priority */ 02877 struct ast_exten *previous_peer = NULL; 02878 02879 for (peer = exten; peer; previous_peer = peer, peer = peer->peer) { 02880 if (peer->priority == priority && 02881 (!registrar || !strcmp(peer->registrar, registrar) )) 02882 break; /* found our priority */ 02883 } 02884 if (!peer) { /* not found */ 02885 ast_mutex_unlock(&con->lock); 02886 return -1; 02887 } 02888 /* we are first priority extension? */ 02889 if (!previous_peer) { 02890 /* 02891 * We are first in the priority chain, so must update the extension chain. 02892 * The next node is either the next priority or the next extension 02893 */ 02894 struct ast_exten *next_node = peer->peer ? peer->peer : peer->next; 02895 02896 if (!prev_exten) /* change the root... */ 02897 con->root = next_node; 02898 else 02899 prev_exten->next = next_node; /* unlink */ 02900 if (peer->peer) /* XXX update the new head of the pri list */ 02901 peer->peer->next = peer->next; 02902 } else { /* easy, we are not first priority in extension */ 02903 previous_peer->peer = peer->peer; 02904 } 02905 02906 /* now, free whole priority extension */ 02907 destroy_exten(peer); 02908 /* XXX should we return -1 ? */ 02909 } 02910 ast_mutex_unlock(&con->lock); 02911 return 0; 02912 }
int ast_context_remove_ignorepat | ( | const char * | context, | |
const char * | ignorepat, | |||
const char * | registrar | |||
) |
Definition at line 4453 of file pbx.c.
References ast_context_remove_ignorepat2(), ast_unlock_contexts(), and find_context_locked().
Referenced by handle_context_remove_ignorepat(), and handle_context_remove_ignorepat_deprecated().
04454 { 04455 int ret = -1; 04456 struct ast_context *c = find_context_locked(context); 04457 04458 if (c) { 04459 ret = ast_context_remove_ignorepat2(c, ignorepat, registrar); 04460 ast_unlock_contexts(); 04461 } 04462 return ret; 04463 }
int ast_context_remove_ignorepat2 | ( | struct ast_context * | con, | |
const char * | ignorepat, | |||
const char * | registrar | |||
) |
Definition at line 4465 of file pbx.c.
References ast_mutex_lock(), ast_mutex_unlock(), errno, free, ast_context::ignorepats, ast_context::lock, ast_ignorepat::next, ast_ignorepat::pattern, and ast_ignorepat::registrar.
Referenced by ast_context_remove_ignorepat().
04466 { 04467 struct ast_ignorepat *ip, *ipl = NULL; 04468 04469 ast_mutex_lock(&con->lock); 04470 04471 for (ip = con->ignorepats; ip; ip = ip->next) { 04472 if (!strcmp(ip->pattern, ignorepat) && 04473 (!registrar || (registrar == ip->registrar))) { 04474 if (ipl) { 04475 ipl->next = ip->next; 04476 free(ip); 04477 } else { 04478 con->ignorepats = ip->next; 04479 free(ip); 04480 } 04481 ast_mutex_unlock(&con->lock); 04482 return 0; 04483 } 04484 ipl = ip; 04485 } 04486 04487 ast_mutex_unlock(&con->lock); 04488 errno = EINVAL; 04489 return -1; 04490 }
int ast_context_remove_include | ( | const char * | context, | |
const char * | include, | |||
const char * | registrar | |||
) |
Remove a context include.
0 | on success | |
-1 | on failure |
Definition at line 2717 of file pbx.c.
References ast_context_remove_include2(), ast_unlock_contexts(), and find_context_locked().
Referenced by handle_context_dont_include_deprecated(), and handle_context_remove_include().
02718 { 02719 int ret = -1; 02720 struct ast_context *c = find_context_locked(context); 02721 02722 if (c) { 02723 /* found, remove include from this context ... */ 02724 ret = ast_context_remove_include2(c, include, registrar); 02725 ast_unlock_contexts(); 02726 } 02727 return ret; 02728 }
int ast_context_remove_include2 | ( | struct ast_context * | con, | |
const char * | include, | |||
const char * | registrar | |||
) |
Removes an include by an ast_context structure.
0 | on success | |
-1 | on success |
Definition at line 2738 of file pbx.c.
References ast_mutex_lock(), ast_mutex_unlock(), free, ast_context::includes, ast_context::lock, ast_include::name, ast_include::next, and ast_include::registrar.
Referenced by ast_context_remove_include().
02739 { 02740 struct ast_include *i, *pi = NULL; 02741 int ret = -1; 02742 02743 ast_mutex_lock(&con->lock); 02744 02745 /* find our include */ 02746 for (i = con->includes; i; pi = i, i = i->next) { 02747 if (!strcmp(i->name, include) && 02748 (!registrar || !strcmp(i->registrar, registrar))) { 02749 /* remove from list */ 02750 if (pi) 02751 pi->next = i->next; 02752 else 02753 con->includes = i->next; 02754 /* free include and return */ 02755 free(i); 02756 ret = 0; 02757 break; 02758 } 02759 } 02760 02761 ast_mutex_unlock(&con->lock); 02762 return ret; 02763 }
int ast_context_remove_switch | ( | const char * | context, | |
const char * | sw, | |||
const char * | data, | |||
const char * | registrar | |||
) |
Remove a switch.
Removes a switch with the given parameters
0 | on success | |
-1 | on failure |
Definition at line 2770 of file pbx.c.
References ast_context_remove_switch2(), ast_unlock_contexts(), and find_context_locked().
02771 { 02772 int ret = -1; /* default error return */ 02773 struct ast_context *c = find_context_locked(context); 02774 02775 if (c) { 02776 /* remove switch from this context ... */ 02777 ret = ast_context_remove_switch2(c, sw, data, registrar); 02778 ast_unlock_contexts(); 02779 } 02780 return ret; 02781 }
int ast_context_remove_switch2 | ( | struct ast_context * | con, | |
const char * | sw, | |||
const char * | data, | |||
const char * | registrar | |||
) |
This function locks given context, removes switch, unlock context and return.
Definition at line 2791 of file pbx.c.
References AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, ast_mutex_lock(), ast_mutex_unlock(), ast_sw::data, free, ast_context::lock, ast_sw::name, and ast_sw::registrar.
Referenced by ast_context_remove_switch().
02792 { 02793 struct ast_sw *i; 02794 int ret = -1; 02795 02796 ast_mutex_lock(&con->lock); 02797 02798 /* walk switches */ 02799 AST_LIST_TRAVERSE_SAFE_BEGIN(&con->alts, i, list) { 02800 if (!strcmp(i->name, sw) && !strcmp(i->data, data) && 02801 (!registrar || !strcmp(i->registrar, registrar))) { 02802 /* found, remove from list */ 02803 AST_LIST_REMOVE_CURRENT(&con->alts, list); 02804 free(i); /* free switch and return */ 02805 ret = 0; 02806 break; 02807 } 02808 } 02809 AST_LIST_TRAVERSE_SAFE_END 02810 02811 ast_mutex_unlock(&con->lock); 02812 02813 return ret; 02814 }
int ast_context_unlockmacro | ( | const char * | context | ) |
Unlocks the macrolock in the given context.
macrocontext | name of the macro-context to unlock |
0 | on success | |
-1 | on failure |
Definition at line 2948 of file pbx.c.
References ast_get_context_name(), ast_mutex_unlock(), ast_rdlock_contexts(), ast_unlock_contexts(), and ast_walk_contexts().
Referenced by _macro_exec().
02949 { 02950 struct ast_context *c = NULL; 02951 int ret = -1; 02952 02953 ast_rdlock_contexts(); 02954 02955 while ((c = ast_walk_contexts(c))) { 02956 if (!strcmp(ast_get_context_name(c), context)) { 02957 ret = 0; 02958 break; 02959 } 02960 } 02961 02962 ast_unlock_contexts(); 02963 02964 /* if we found context, unlock macrolock */ 02965 if (ret == 0) 02966 ret = ast_mutex_unlock(&c->macrolock); 02967 02968 return ret; 02969 }
int ast_context_verify_includes | ( | struct ast_context * | con | ) |
Verifies includes in an ast_contect structure.
con | context in which to verify the includes |
0 | if no problems found | |
-1 | if there were any missing context |
Definition at line 6342 of file pbx.c.
References ast_context_find(), ast_get_context_name(), ast_log(), ast_walk_context_includes(), LOG_WARNING, and ast_include::rname.
Referenced by pbx_load_module().
06343 { 06344 struct ast_include *inc = NULL; 06345 int res = 0; 06346 06347 while ( (inc = ast_walk_context_includes(con, inc)) ) { 06348 if (ast_context_find(inc->rname)) 06349 continue; 06350 06351 res = -1; 06352 ast_log(LOG_WARNING, "Context '%s' tries to include nonexistent context '%s'\n", 06353 ast_get_context_name(con), inc->rname); 06354 break; 06355 } 06356 06357 return res; 06358 }
struct ast_custom_function* ast_custom_function_find | ( | const char * | name | ) | [read] |
Definition at line 1454 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, and ast_custom_function::name.
Referenced by ast_custom_function_register(), ast_func_read(), ast_func_write(), handle_show_function(), and handle_show_function_deprecated().
01455 { 01456 struct ast_custom_function *acf = NULL; 01457 01458 AST_LIST_LOCK(&acf_root); 01459 AST_LIST_TRAVERSE(&acf_root, acf, acflist) { 01460 if (!strcmp(name, acf->name)) 01461 break; 01462 } 01463 AST_LIST_UNLOCK(&acf_root); 01464 01465 return acf; 01466 }
int ast_custom_function_register | ( | struct ast_custom_function * | acf | ) |
Reigster a custom function.
Definition at line 1490 of file pbx.c.
References ast_custom_function_find(), AST_LIST_INSERT_BEFORE_CURRENT, AST_LIST_INSERT_TAIL, AST_LIST_LOCK, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, ast_log(), ast_verbose(), LOG_ERROR, ast_custom_function::name, option_verbose, and VERBOSE_PREFIX_2.
Referenced by load_module(), odbc_load_module(), and reload().
01491 { 01492 struct ast_custom_function *cur; 01493 01494 if (!acf) 01495 return -1; 01496 01497 AST_LIST_LOCK(&acf_root); 01498 01499 if (ast_custom_function_find(acf->name)) { 01500 ast_log(LOG_ERROR, "Function %s already registered.\n", acf->name); 01501 AST_LIST_UNLOCK(&acf_root); 01502 return -1; 01503 } 01504 01505 /* Store in alphabetical order */ 01506 AST_LIST_TRAVERSE_SAFE_BEGIN(&acf_root, cur, acflist) { 01507 if (strcasecmp(acf->name, cur->name) < 0) { 01508 AST_LIST_INSERT_BEFORE_CURRENT(&acf_root, acf, acflist); 01509 break; 01510 } 01511 } 01512 AST_LIST_TRAVERSE_SAFE_END 01513 if (!cur) 01514 AST_LIST_INSERT_TAIL(&acf_root, acf, acflist); 01515 01516 AST_LIST_UNLOCK(&acf_root); 01517 01518 if (option_verbose > 1) 01519 ast_verbose(VERBOSE_PREFIX_2 "Registered custom function %s\n", acf->name); 01520 01521 return 0; 01522 }
int ast_custom_function_unregister | ( | struct ast_custom_function * | acf | ) |
Unregister a custom function.
Definition at line 1468 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, ast_verbose(), ast_custom_function::name, option_verbose, and VERBOSE_PREFIX_2.
Referenced by odbc_unload_module(), reload(), and unload_module().
01469 { 01470 struct ast_custom_function *cur; 01471 01472 if (!acf) 01473 return -1; 01474 01475 AST_LIST_LOCK(&acf_root); 01476 AST_LIST_TRAVERSE_SAFE_BEGIN(&acf_root, cur, acflist) { 01477 if (cur == acf) { 01478 AST_LIST_REMOVE_CURRENT(&acf_root, acflist); 01479 if (option_verbose > 1) 01480 ast_verbose(VERBOSE_PREFIX_2 "Unregistered custom function %s\n", acf->name); 01481 break; 01482 } 01483 } 01484 AST_LIST_TRAVERSE_SAFE_END 01485 AST_LIST_UNLOCK(&acf_root); 01486 01487 return acf ? 0 : -1; 01488 }
int ast_exists_extension | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
const char * | callerid | |||
) |
Determine whether an extension exists.
c | this is not important | |
context | which context to look in | |
exten | which extension to search for | |
priority | priority of the action within the extension | |
callerid | callerid to search for |
Definition at line 2290 of file pbx.c.
References E_MATCH, and pbx_extension_helper().
Referenced by __ast_goto_if_exists(), __ast_pbx_run(), __login_exec(), _macro_exec(), agentmonitoroutgoing_exec(), answer_call(), ast_app_dtget(), ast_pbx_outgoing_exten_uniqueid(), builtin_atxfer(), builtin_blindtransfer(), cb_events(), console_dial(), console_dial_deprecated(), console_transfer(), console_transfer_deprecated(), disa_exec(), dp_lookup(), dundi_lookup_local(), get_also_info(), get_destination(), get_refer_info(), handle_link_data(), handle_link_phone_dtmf(), handle_stimulus_message(), leave_voicemail(), local_alloc(), local_devicestate(), local_dtmf_helper(), loopback_exists(), metermaidstate(), mgcp_ss(), misdn_overlap_dial_task(), park_call_full(), parkandannounce_exec(), pbx_builtin_waitexten(), phone_check_exception(), process_ast_dsp(), register_peer_exten(), rpt_exec(), skinny_ss(), socket_process(), ss_thread(), waitstream_core(), and zt_handle_dtmfup().
02291 { 02292 return pbx_extension_helper(c, NULL, context, exten, priority, NULL, callerid, E_MATCH); 02293 }
int ast_explicit_goto | ( | struct ast_channel * | chan, | |
const char * | context, | |||
const char * | exten, | |||
int | priority | |||
) |
Definition at line 4575 of file pbx.c.
References ast_channel_lock, ast_channel_unlock, AST_FLAG_IN_AUTOLOOP, ast_strlen_zero(), ast_test_flag, ast_channel::context, ast_channel::exten, and ast_channel::priority.
Referenced by __ast_goto_if_exists(), ast_async_goto(), ast_parseable_goto(), builtin_atxfer(), disa_exec(), do_bridge_masquerade(), and handle_setpriority().
04576 { 04577 if (!chan) 04578 return -1; 04579 04580 ast_channel_lock(chan); 04581 04582 if (!ast_strlen_zero(context)) 04583 ast_copy_string(chan->context, context, sizeof(chan->context)); 04584 if (!ast_strlen_zero(exten)) 04585 ast_copy_string(chan->exten, exten, sizeof(chan->exten)); 04586 if (priority > -1) { 04587 chan->priority = priority; 04588 /* see flag description in channel.h for explanation */ 04589 if (ast_test_flag(chan, AST_FLAG_IN_AUTOLOOP)) 04590 chan->priority--; 04591 } 04592 04593 ast_channel_unlock(chan); 04594 04595 return 0; 04596 }
int ast_extension_close | ( | const char * | pattern, | |
const char * | data, | |||
int | needmore | |||
) |
Definition at line 888 of file pbx.c.
References ast_log(), E_CANMATCH, E_MATCHMORE, extension_match_core(), and LOG_WARNING.
Referenced by realtime_switch_common().
00889 { 00890 if (needmore != E_MATCHMORE && needmore != E_CANMATCH) 00891 ast_log(LOG_WARNING, "invalid argument %d\n", needmore); 00892 return extension_match_core(pattern, data, needmore); 00893 }
int ast_extension_match | ( | const char * | pattern, | |
const char * | extension | |||
) |
Determine if a given extension matches a given pattern (in NXX format).
pattern | pattern to match | |
extension | extension to check against the pattern. |
1 | on match | |
0 | on failure |
Definition at line 883 of file pbx.c.
References E_MATCH, and extension_match_core().
Referenced by ast_ignore_pattern(), do_say(), find_matching_priority(), loopback_canmatch(), loopback_exists(), loopback_matchmore(), matchcid(), misdn_cfg_is_msn_valid(), realtime_switch_common(), and show_dialplan_helper().
00884 { 00885 return extension_match_core(pattern, data, E_MATCH); 00886 }
int ast_extension_patmatch | ( | const char * | pattern, | |
const char * | data | |||
) |
int ast_extension_state | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten | |||
) |
Uses hint and devicestate callback to get the state of an extension.
c | this is not important | |
context | which context to look in | |
exten | which extension to get state |
Definition at line 2014 of file pbx.c.
References ast_extension_state2(), and ast_hint_extension().
Referenced by action_extensionstate(), and handle_request_subscribe().
02015 { 02016 struct ast_exten *e; 02017 02018 e = ast_hint_extension(c, context, exten); /* Do we have a hint for this extension ? */ 02019 if (!e) 02020 return -1; /* No hint, return -1 */ 02021 02022 return ast_extension_state2(e); /* Check all devices in the hint */ 02023 }
const char* ast_extension_state2str | ( | int | extension_state | ) |
Return string representation of the state of an extension.
extension_state | is the numerical state delivered by ast_extension_state |
Definition at line 2002 of file pbx.c.
References extension_states, and cfextension_states::text.
Referenced by __sip_show_channels(), cb_extensionstate(), handle_request_subscribe(), and handle_show_hints().
02003 { 02004 int i; 02005 02006 for (i = 0; (i < (sizeof(extension_states) / sizeof(extension_states[0]))); i++) { 02007 if (extension_states[i].extension_state == extension_state) 02008 return extension_states[i].text; 02009 } 02010 return "Unknown"; 02011 }
int ast_extension_state_add | ( | const char * | context, | |
const char * | exten, | |||
ast_state_cb_type | callback, | |||
void * | data | |||
) |
Registers a state change callback.
context | which context to look in | |
exten | which extension to get state | |
callback | callback to call if state changed | |
data | to pass to callback |
-1 | on failure | |
ID | on success |
Definition at line 2069 of file pbx.c.
References ast_calloc, ast_hint_extension(), AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_state_cb::callback, ast_hint::callbacks, ast_state_cb::data, ast_hint::exten, ast_state_cb::id, ast_state_cb::next, statecbs, and stateid.
Referenced by handle_request_subscribe(), init_manager(), and load_module().
02071 { 02072 struct ast_hint *hint; 02073 struct ast_state_cb *cblist; 02074 struct ast_exten *e; 02075 02076 /* If there's no context and extension: add callback to statecbs list */ 02077 if (!context && !exten) { 02078 AST_LIST_LOCK(&hints); 02079 02080 for (cblist = statecbs; cblist; cblist = cblist->next) { 02081 if (cblist->callback == callback) { 02082 cblist->data = data; 02083 AST_LIST_UNLOCK(&hints); 02084 return 0; 02085 } 02086 } 02087 02088 /* Now insert the callback */ 02089 if (!(cblist = ast_calloc(1, sizeof(*cblist)))) { 02090 AST_LIST_UNLOCK(&hints); 02091 return -1; 02092 } 02093 cblist->id = 0; 02094 cblist->callback = callback; 02095 cblist->data = data; 02096 02097 cblist->next = statecbs; 02098 statecbs = cblist; 02099 02100 AST_LIST_UNLOCK(&hints); 02101 return 0; 02102 } 02103 02104 if (!context || !exten) 02105 return -1; 02106 02107 /* This callback type is for only one hint, so get the hint */ 02108 e = ast_hint_extension(NULL, context, exten); 02109 if (!e) { 02110 return -1; 02111 } 02112 02113 /* Find the hint in the list of hints */ 02114 AST_LIST_LOCK(&hints); 02115 02116 AST_LIST_TRAVERSE(&hints, hint, list) { 02117 if (hint->exten == e) 02118 break; 02119 } 02120 02121 if (!hint) { 02122 /* We have no hint, sorry */ 02123 AST_LIST_UNLOCK(&hints); 02124 return -1; 02125 } 02126 02127 /* Now insert the callback in the callback list */ 02128 if (!(cblist = ast_calloc(1, sizeof(*cblist)))) { 02129 AST_LIST_UNLOCK(&hints); 02130 return -1; 02131 } 02132 cblist->id = stateid++; /* Unique ID for this callback */ 02133 cblist->callback = callback; /* Pointer to callback routine */ 02134 cblist->data = data; /* Data for the callback */ 02135 02136 cblist->next = hint->callbacks; 02137 hint->callbacks = cblist; 02138 02139 AST_LIST_UNLOCK(&hints); 02140 return cblist->id; 02141 }
int ast_extension_state_del | ( | int | id, | |
ast_state_cb_type | callback | |||
) |
Deletes a registered state change callback by ID.
id | of the callback to delete | |
callback | callback |
0 | success | |
-1 | failure |
Definition at line 2144 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_hint::callbacks, free, ast_state_cb::next, and statecbs.
Referenced by __sip_destroy(), and handle_request_subscribe().
02145 { 02146 struct ast_state_cb **p_cur = NULL; /* address of pointer to us */ 02147 int ret = -1; 02148 02149 if (!id && !callback) 02150 return -1; 02151 02152 AST_LIST_LOCK(&hints); 02153 02154 if (!id) { /* id == 0 is a callback without extension */ 02155 for (p_cur = &statecbs; *p_cur; p_cur = &(*p_cur)->next) { 02156 if ((*p_cur)->callback == callback) 02157 break; 02158 } 02159 } else { /* callback with extension, find the callback based on ID */ 02160 struct ast_hint *hint; 02161 AST_LIST_TRAVERSE(&hints, hint, list) { 02162 for (p_cur = &hint->callbacks; *p_cur; p_cur = &(*p_cur)->next) { 02163 if ((*p_cur)->id == id) 02164 break; 02165 } 02166 if (*p_cur) /* found in the inner loop */ 02167 break; 02168 } 02169 } 02170 if (p_cur && *p_cur) { 02171 struct ast_state_cb *cur = *p_cur; 02172 *p_cur = cur->next; 02173 free(cur); 02174 ret = 0; 02175 } 02176 AST_LIST_UNLOCK(&hints); 02177 return ret; 02178 }
int ast_findlabel_extension | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten, | |||
const char * | label, | |||
const char * | callerid | |||
) |
Find the priority of an extension that has the specified label.
c | this is not important | |
context | which context to look in | |
exten | which extension to search for | |
label | label of the action within the extension to match to priority | |
callerid | callerid to search for |
Definition at line 2295 of file pbx.c.
References E_FINDLABEL, and pbx_extension_helper().
Referenced by action_originate(), action_redirect(), ast_parseable_goto(), asyncgoto_exec(), and handle_setpriority().
02296 { 02297 return pbx_extension_helper(c, NULL, context, exten, 0, label, callerid, E_FINDLABEL); 02298 }
int ast_findlabel_extension2 | ( | struct ast_channel * | c, | |
struct ast_context * | con, | |||
const char * | exten, | |||
const char * | label, | |||
const char * | callerid | |||
) |
Find the priority of an extension that has the specified label.
Definition at line 2300 of file pbx.c.
References E_FINDLABEL, and pbx_extension_helper().
Referenced by pbx_load_config().
02301 { 02302 return pbx_extension_helper(c, con, NULL, exten, 0, label, callerid, E_FINDLABEL); 02303 }
int ast_func_read | ( | struct ast_channel * | chan, | |
char * | function, | |||
char * | workspace, | |||
size_t | len | |||
) |
executes a read operation on a function
chan | Channel to execute on | |
function | Data containing the function call string (will be modified) | |
workspace | A pointer to safe memory to use for a return value | |
len | the number of bytes in workspace |
Definition at line 1544 of file pbx.c.
References ast_custom_function_find(), ast_log(), func_args(), LOG_ERROR, and ast_custom_function::read.
Referenced by action_getvar(), handle_getvariable(), and pbx_substitute_variables_helper_full().
01545 { 01546 char *args = func_args(function); 01547 struct ast_custom_function *acfptr = ast_custom_function_find(function); 01548 01549 if (acfptr == NULL) 01550 ast_log(LOG_ERROR, "Function %s not registered\n", function); 01551 else if (!acfptr->read) 01552 ast_log(LOG_ERROR, "Function %s cannot be read\n", function); 01553 else 01554 return acfptr->read(chan, function, args, workspace, len); 01555 return -1; 01556 }
int ast_func_write | ( | struct ast_channel * | chan, | |
char * | function, | |||
const char * | value | |||
) |
executes a write operation on a function
chan | Channel to execute on | |
function | Data containing the function call string (will be modified) | |
value | A value parameter to pass for writing |
Definition at line 1558 of file pbx.c.
References ast_custom_function_find(), ast_log(), func_args(), LOG_ERROR, and ast_custom_function::write.
Referenced by pbx_builtin_pushvar_helper(), and pbx_builtin_setvar_helper().
01559 { 01560 char *args = func_args(function); 01561 struct ast_custom_function *acfptr = ast_custom_function_find(function); 01562 01563 if (acfptr == NULL) 01564 ast_log(LOG_ERROR, "Function %s not registered\n", function); 01565 else if (!acfptr->write) 01566 ast_log(LOG_ERROR, "Function %s cannot be written to\n", function); 01567 else 01568 return acfptr->write(chan, function, args, value); 01569 01570 return -1; 01571 }
const char* ast_get_context_name | ( | struct ast_context * | con | ) |
Definition at line 6199 of file pbx.c.
Referenced by _macro_exec(), ast_context_add_include2(), ast_context_add_switch2(), ast_context_lockmacro(), ast_context_unlockmacro(), ast_context_verify_includes(), complete_context_add_extension(), complete_context_add_extension_deprecated(), complete_context_add_ignorepat(), complete_context_add_ignorepat_deprecated(), complete_context_add_include(), complete_context_add_include_deprecated(), complete_context_dont_include_deprecated(), complete_context_remove_extension(), complete_context_remove_extension_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), complete_show_dialplan_context(), dundi_precache_full(), find_context_locked(), find_matching_endwhile(), find_matching_priority(), handle_save_dialplan(), handle_show_hints(), and show_dialplan_helper().
const char* ast_get_context_registrar | ( | struct ast_context * | c | ) |
Definition at line 6237 of file pbx.c.
References ast_context::registrar.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06238 { 06239 return c ? c->registrar : NULL; 06240 }
const char* ast_get_extension_app | ( | struct ast_exten * | e | ) |
Definition at line 6267 of file pbx.c.
References ast_exten::app.
Referenced by _macro_exec(), ast_add_hint(), ast_extension_state2(), ast_get_hint(), ast_hint_state_changed(), find_matching_endwhile(), handle_save_dialplan(), handle_show_hints(), and print_ext().
06268 { 06269 return e ? e->app : NULL; 06270 }
void* ast_get_extension_app_data | ( | struct ast_exten * | e | ) |
Definition at line 6272 of file pbx.c.
References ast_exten::data.
Referenced by _macro_exec(), ast_get_hint(), handle_save_dialplan(), and print_ext().
06273 { 06274 return e ? e->data : NULL; 06275 }
const char* ast_get_extension_cidmatch | ( | struct ast_exten * | e | ) |
Definition at line 6262 of file pbx.c.
References ast_exten::cidmatch.
Referenced by find_matching_priority(), and handle_save_dialplan().
06263 { 06264 return e ? e->cidmatch : NULL; 06265 }
struct ast_context* ast_get_extension_context | ( | struct ast_exten * | exten | ) | [read] |
Definition at line 6204 of file pbx.c.
References ast_exten::parent.
Referenced by handle_show_hints().
06205 { 06206 return exten ? exten->parent : NULL; 06207 }
const char* ast_get_extension_label | ( | struct ast_exten * | e | ) |
Definition at line 6214 of file pbx.c.
References ast_exten::label.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
int ast_get_extension_matchcid | ( | struct ast_exten * | e | ) |
Definition at line 6257 of file pbx.c.
References ast_exten::matchcid.
Referenced by find_matching_priority(), and handle_save_dialplan().
06258 { 06259 return e ? e->matchcid : 0; 06260 }
const char* ast_get_extension_name | ( | struct ast_exten * | exten | ) |
Definition at line 6209 of file pbx.c.
References ast_exten::exten.
Referenced by ast_add_hint(), complete_context_remove_extension(), complete_context_remove_extension_deprecated(), dundi_precache_full(), find_matching_priority(), handle_save_dialplan(), handle_show_hints(), and show_dialplan_helper().
06210 { 06211 return exten ? exten->exten : NULL; 06212 }
int ast_get_extension_priority | ( | struct ast_exten * | exten | ) |
Definition at line 6229 of file pbx.c.
References ast_exten::priority.
Referenced by complete_context_remove_extension(), complete_context_remove_extension_deprecated(), find_matching_priority(), handle_save_dialplan(), and print_ext().
06230 { 06231 return exten ? exten->priority : -1; 06232 }
const char* ast_get_extension_registrar | ( | struct ast_exten * | e | ) |
Definition at line 6242 of file pbx.c.
References ast_exten::registrar.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06243 { 06244 return e ? e->registrar : NULL; 06245 }
int ast_get_hint | ( | char * | hint, | |
int | hintsize, | |||
char * | name, | |||
int | namesize, | |||
struct ast_channel * | c, | |||
const char * | context, | |||
const char * | exten | |||
) |
If an extension exists, return non-zero.
hint | buffer for hint | |
maxlen | size of hint buffer | |
name | buffer for name portion of hint | |
maxnamelen | size of name buffer | |
c | this is not important | |
context | which context to look in | |
exten | which extension to search for |
Definition at line 2273 of file pbx.c.
References ast_get_extension_app(), ast_get_extension_app_data(), and ast_hint_extension().
Referenced by action_extensionstate(), get_cid_name(), get_destination(), manager_state_cb(), pbx_retrieve_variable(), and transmit_state_notify().
02274 { 02275 struct ast_exten *e = ast_hint_extension(c, context, exten); 02276 02277 if (e) { 02278 if (hint) 02279 ast_copy_string(hint, ast_get_extension_app(e), hintsize); 02280 if (name) { 02281 const char *tmp = ast_get_extension_app_data(e); 02282 if (tmp) 02283 ast_copy_string(name, tmp, namesize); 02284 } 02285 return -1; 02286 } 02287 return 0; 02288 }
const char* ast_get_ignorepat_name | ( | struct ast_ignorepat * | ip | ) |
Definition at line 6224 of file pbx.c.
References ast_ignorepat::pattern.
Referenced by complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), handle_save_dialplan(), lookup_c_ip(), and show_dialplan_helper().
06225 { 06226 return ip ? ip->pattern : NULL; 06227 }
const char* ast_get_ignorepat_registrar | ( | struct ast_ignorepat * | ip | ) |
Definition at line 6252 of file pbx.c.
References ast_ignorepat::registrar.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06253 { 06254 return ip ? ip->registrar : NULL; 06255 }
const char* ast_get_include_name | ( | struct ast_include * | include | ) |
Definition at line 6219 of file pbx.c.
References ast_include::name.
Referenced by complete_context_dont_include_deprecated(), complete_context_remove_include(), find_matching_priority(), handle_save_dialplan(), lookup_ci(), and show_dialplan_helper().
const char* ast_get_include_registrar | ( | struct ast_include * | i | ) |
Definition at line 6247 of file pbx.c.
References ast_include::registrar.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06248 { 06249 return i ? i->registrar : NULL; 06250 }
const char* ast_get_switch_data | ( | struct ast_sw * | sw | ) |
Definition at line 6282 of file pbx.c.
References ast_sw::data.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06283 { 06284 return sw ? sw->data : NULL; 06285 }
const char* ast_get_switch_name | ( | struct ast_sw * | sw | ) |
Definition at line 6277 of file pbx.c.
References ast_sw::name.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06278 { 06279 return sw ? sw->name : NULL; 06280 }
const char* ast_get_switch_registrar | ( | struct ast_sw * | sw | ) |
Definition at line 6287 of file pbx.c.
References ast_sw::registrar.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06288 { 06289 return sw ? sw->registrar : NULL; 06290 }
int ast_goto_if_exists | ( | struct ast_channel * | chan, | |
const char * | context, | |||
const char * | exten, | |||
int | priority | |||
) |
Definition at line 6380 of file pbx.c.
References __ast_goto_if_exists().
Referenced by aqm_exec(), auth_exec(), background_detect_exec(), chanavail_exec(), conf_run(), controlplayback_exec(), do_directory(), hasvoicemail_exec(), leave_voicemail(), lookupblacklist_exec(), onedigit_goto(), ospauth_exec(), ospfinished_exec(), osplookup_exec(), ospnext_exec(), play_mailbox_owner(), playback_exec(), pqm_exec(), privacy_exec(), rqm_exec(), sendimage_exec(), sendtext_exec(), sendurl_exec(), system_exec_helper(), transfer_exec(), upqm_exec(), valid_exit(), vm_box_exists(), vm_exec(), and wait_for_answer().
06381 { 06382 return __ast_goto_if_exists(chan, context, exten, priority, 0); 06383 }
void ast_hint_state_changed | ( | const char * | device, | |
char * | cid_num, | |||
char * | cid_name | |||
) |
Definition at line 2025 of file pbx.c.
References ast_extension_state2(), ast_get_extension_app(), AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, AST_MAX_EXTENSION, ast_state_cb::callback, ast_hint::callbacks, ast_state_cb::data, ast_exten::exten, ast_hint::exten, ast_hint::laststate, ast_state_cb::next, ast_exten::parent, parse(), statecbs, and strsep().
Referenced by do_state_change().
02026 { 02027 struct ast_hint *hint; 02028 02029 AST_LIST_LOCK(&hints); 02030 02031 AST_LIST_TRAVERSE(&hints, hint, list) { 02032 struct ast_state_cb *cblist; 02033 char buf[AST_MAX_EXTENSION]; 02034 char *parse = buf; 02035 char *cur; 02036 int state; 02037 02038 ast_copy_string(buf, ast_get_extension_app(hint->exten), sizeof(buf)); 02039 while ( (cur = strsep(&parse, "&")) ) { 02040 if (!strcasecmp(cur, device)) 02041 break; 02042 } 02043 if (!cur) 02044 continue; 02045 02046 /* Get device state for this hint */ 02047 state = ast_extension_state2(hint->exten); 02048 02049 if ((state == -1) || (state == hint->laststate)) 02050 continue; 02051 02052 /* Device state changed since last check - notify the watchers */ 02053 02054 /* For general callbacks */ 02055 for (cblist = statecbs; cblist; cblist = cblist->next) 02056 cblist->callback(hint->exten->parent->name, hint->exten->exten, state, cblist->data, cid_num, cid_name); 02057 02058 /* For extension callbacks */ 02059 for (cblist = hint->callbacks; cblist; cblist = cblist->next) 02060 cblist->callback(hint->exten->parent->name, hint->exten->exten, state, cblist->data, cid_num, cid_name); 02061 02062 hint->laststate = state; /* record we saw the change */ 02063 } 02064 02065 AST_LIST_UNLOCK(&hints); 02066 }
int ast_ignore_pattern | ( | const char * | context, | |
const char * | pattern | |||
) |
Checks to see if a number should be ignored.
context | context to search within | |
pattern | to check whether it should be ignored or not |
0 | if the pattern should not be ignored | |
non-zero | if the pattern should be ignored |
Definition at line 4541 of file pbx.c.
References ast_context_find(), ast_extension_match(), ast_context::ignorepats, ast_ignorepat::next, and ast_ignorepat::pattern.
Referenced by ast_app_dtget(), disa_exec(), dp_lookup(), dundi_lookup_local(), handle_enbloc_call_message(), handle_soft_key_event_message(), handle_stimulus_message(), mgcp_ss(), skinny_ss(), and ss_thread().
04542 { 04543 struct ast_context *con = ast_context_find(context); 04544 if (con) { 04545 struct ast_ignorepat *pat; 04546 for (pat = con->ignorepats; pat; pat = pat->next) { 04547 if (ast_extension_match(pat->pattern, pattern)) 04548 return 1; 04549 } 04550 } 04551 04552 return 0; 04553 }
int ast_lock_context | ( | struct ast_context * | con | ) |
Locks a given context.
con | context to lock |
0 | on success | |
-1 | on failure |
Definition at line 6186 of file pbx.c.
References ast_mutex_lock(), and ast_context::lock.
Referenced by _macro_exec(), complete_context_dont_include_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), dundi_precache_full(), find_matching_endwhile(), handle_save_dialplan(), lookup_c_ip(), lookup_ci(), and show_dialplan_helper().
06187 { 06188 return ast_mutex_lock(&con->lock); 06189 }
int ast_lock_contexts | ( | void | ) |
Locks the context list.
0 | on success | |
-1 | on error |
Definition at line 6163 of file pbx.c.
References ast_rwlock_wrlock().
Referenced by find_matching_endwhile().
06164 { 06165 return ast_rwlock_wrlock(&conlock); 06166 }
int ast_matchmore_extension | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
const char * | callerid | |||
) |
Looks to see if adding anything to this extension might match something. (exists ^ canmatch).
c | not really important XXX | |
context | context to serach within | |
exten | extension to check | |
priority | priority of extension path | |
callerid | callerid of extension being searched for |
Definition at line 2310 of file pbx.c.
References E_MATCHMORE, and pbx_extension_helper().
Referenced by ast_app_dtget(), collect_digits(), disa_exec(), dp_lookup(), dundi_lookup_local(), handle_stimulus_message(), loopback_matchmore(), mgcp_ss(), skinny_ss(), and ss_thread().
02311 { 02312 return pbx_extension_helper(c, NULL, context, exten, priority, NULL, callerid, E_MATCHMORE); 02313 }
void ast_merge_contexts_and_delete | ( | struct ast_context ** | extcontexts, | |
const char * | registrar | |||
) |
Merge the temporary contexts into a global contexts list and delete from the global list the ones that are being added.
extcontexts | pointer to the ast_context structure pointer | |
registrar | of the context; if it's set the routine will delete all contexts that belong to that registrar; if NULL only the contexts that are specified in extcontexts |
Definition at line 3942 of file pbx.c.
References __ast_context_destroy(), ast_calloc, AST_EXTENSION_REMOVED, AST_LIST_HEAD_INIT_VALUE, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_REMOVE_HEAD, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), ast_unlock_contexts(), ast_wrlock_contexts(), ast_state_cb::callback, ast_hint::callbacks, context, contexts, ast_state_cb::data, E_MATCH, ast_exten::exten, ast_hint::exten, exten, free, ast_hint::laststate, LOG_DEBUG, LOG_WARNING, ast_state_cb::next, ast_context::next, option_debug, ast_exten::parent, pbx_find_extension(), PRIORITY_HINT, ast_context::registrar, and pbx_find_info::stacklen.
Referenced by pbx_load_module().
03943 { 03944 struct ast_context *tmp, *lasttmp = NULL; 03945 struct store_hints store = AST_LIST_HEAD_INIT_VALUE; 03946 struct store_hint *this; 03947 struct ast_hint *hint; 03948 struct ast_exten *exten; 03949 int length; 03950 struct ast_state_cb *thiscb, *prevcb; 03951 03952 /* it is very important that this function hold the hint list lock _and_ the conlock 03953 during its operation; not only do we need to ensure that the list of contexts 03954 and extensions does not change, but also that no hint callbacks (watchers) are 03955 added or removed during the merge/delete process 03956 03957 in addition, the locks _must_ be taken in this order, because there are already 03958 other code paths that use this order 03959 */ 03960 ast_wrlock_contexts(); 03961 AST_LIST_LOCK(&hints); 03962 03963 /* preserve all watchers for hints associated with this registrar */ 03964 AST_LIST_TRAVERSE(&hints, hint, list) { 03965 if (hint->callbacks && !strcmp(registrar, hint->exten->parent->registrar)) { 03966 length = strlen(hint->exten->exten) + strlen(hint->exten->parent->name) + 2 + sizeof(*this); 03967 if (!(this = ast_calloc(1, length))) 03968 continue; 03969 this->callbacks = hint->callbacks; 03970 hint->callbacks = NULL; 03971 this->laststate = hint->laststate; 03972 this->context = this->data; 03973 strcpy(this->data, hint->exten->parent->name); 03974 this->exten = this->data + strlen(this->context) + 1; 03975 strcpy(this->exten, hint->exten->exten); 03976 AST_LIST_INSERT_HEAD(&store, this, list); 03977 } 03978 } 03979 03980 tmp = *extcontexts; 03981 if (registrar) { 03982 /* XXX remove previous contexts from same registrar */ 03983 if (option_debug) 03984 ast_log(LOG_DEBUG, "must remove any reg %s\n", registrar); 03985 __ast_context_destroy(NULL,registrar); 03986 while (tmp) { 03987 lasttmp = tmp; 03988 tmp = tmp->next; 03989 } 03990 } else { 03991 /* XXX remove contexts with the same name */ 03992 while (tmp) { 03993 ast_log(LOG_WARNING, "must remove %s reg %s\n", tmp->name, tmp->registrar); 03994 __ast_context_destroy(tmp,tmp->registrar); 03995 lasttmp = tmp; 03996 tmp = tmp->next; 03997 } 03998 } 03999 if (lasttmp) { 04000 lasttmp->next = contexts; 04001 contexts = *extcontexts; 04002 *extcontexts = NULL; 04003 } else 04004 ast_log(LOG_WARNING, "Requested contexts didn't get merged\n"); 04005 04006 /* restore the watchers for hints that can be found; notify those that 04007 cannot be restored 04008 */ 04009 while ((this = AST_LIST_REMOVE_HEAD(&store, list))) { 04010 struct pbx_find_info q = { .stacklen = 0 }; 04011 exten = pbx_find_extension(NULL, NULL, &q, this->context, this->exten, PRIORITY_HINT, NULL, "", E_MATCH); 04012 /* Find the hint in the list of hints */ 04013 AST_LIST_TRAVERSE(&hints, hint, list) { 04014 if (hint->exten == exten) 04015 break; 04016 } 04017 if (!exten || !hint) { 04018 /* this hint has been removed, notify the watchers */ 04019 prevcb = NULL; 04020 thiscb = this->callbacks; 04021 while (thiscb) { 04022 prevcb = thiscb; 04023 thiscb = thiscb->next; 04024 prevcb->callback(this->context, this->exten, AST_EXTENSION_REMOVED, prevcb->data, NULL, NULL); 04025 free(prevcb); 04026 } 04027 } else { 04028 thiscb = this->callbacks; 04029 while (thiscb->next) 04030 thiscb = thiscb->next; 04031 thiscb->next = hint->callbacks; 04032 hint->callbacks = this->callbacks; 04033 hint->laststate = this->laststate; 04034 } 04035 free(this); 04036 } 04037 04038 AST_LIST_UNLOCK(&hints); 04039 ast_unlock_contexts(); 04040 04041 return; 04042 }
int ast_parseable_goto | ( | struct ast_channel * | chan, | |
const char * | goto_string | |||
) |
This function will handle locking the channel as needed.
Definition at line 6390 of file pbx.c.
References ast_cdr_update(), ast_explicit_goto(), ast_findlabel_extension(), ast_log(), ast_strdupa, ast_strlen_zero(), ast_channel::cid, ast_callerid::cid_num, ast_channel::context, ast_channel::exten, exten, LOG_WARNING, ast_channel::priority, and strsep().
Referenced by _while_exec(), check_goto_on_transfer(), gosub_exec(), ivr_dispatch(), pbx_builtin_goto(), random_exec(), return_exec(), and while_continue_exec().
06391 { 06392 char *exten, *pri, *context; 06393 char *stringp; 06394 int ipri; 06395 int mode = 0; 06396 06397 if (ast_strlen_zero(goto_string)) { 06398 ast_log(LOG_WARNING, "Goto requires an argument (optional context|optional extension|priority)\n"); 06399 return -1; 06400 } 06401 stringp = ast_strdupa(goto_string); 06402 context = strsep(&stringp, "|"); /* guaranteed non-null */ 06403 exten = strsep(&stringp, "|"); 06404 pri = strsep(&stringp, "|"); 06405 if (!exten) { /* Only a priority in this one */ 06406 pri = context; 06407 exten = NULL; 06408 context = NULL; 06409 } else if (!pri) { /* Only an extension and priority in this one */ 06410 pri = exten; 06411 exten = context; 06412 context = NULL; 06413 } 06414 if (*pri == '+') { 06415 mode = 1; 06416 pri++; 06417 } else if (*pri == '-') { 06418 mode = -1; 06419 pri++; 06420 } 06421 if (sscanf(pri, "%d", &ipri) != 1) { 06422 if ((ipri = ast_findlabel_extension(chan, context ? context : chan->context, exten ? exten : chan->exten, 06423 pri, chan->cid.cid_num)) < 1) { 06424 ast_log(LOG_WARNING, "Priority '%s' must be a number > 0, or valid label\n", pri); 06425 return -1; 06426 } else 06427 mode = 0; 06428 } 06429 /* At this point we have a priority and maybe an extension and a context */ 06430 06431 if (mode) 06432 ipri = chan->priority + (ipri * mode); 06433 06434 ast_explicit_goto(chan, context, exten, ipri); 06435 ast_cdr_update(chan); 06436 return 0; 06437 06438 }
int ast_pbx_outgoing_app | ( | const char * | type, | |
int | format, | |||
void * | data, | |||
int | timeout, | |||
const char * | app, | |||
const char * | appdata, | |||
int * | reason, | |||
int | sync, | |||
const char * | cid_num, | |||
const char * | cid_name, | |||
struct ast_variable * | vars, | |||
const char * | account, | |||
struct ast_channel ** | locked_channel | |||
) |
Synchronously or asynchronously make an outbound call and send it to a particular application with given extension
Definition at line 5306 of file pbx.c.
References ast_pbx_outgoing_app_uniqueid().
Referenced by attempt_thread(), and orig_app().
05307 { 05308 return ast_pbx_outgoing_app_uniqueid(type, format, data, timeout, app, appdata, reason, sync, 0, cid_num, cid_name, vars, account, locked_channel, NULL); 05309 }
int ast_pbx_outgoing_app_uniqueid | ( | const char * | type, | |
int | format, | |||
void * | data, | |||
int | timeout, | |||
const char * | app, | |||
const char * | appdata, | |||
int * | reason, | |||
int | sync, | |||
int | callingpres, | |||
const char * | cid_num, | |||
const char * | cid_name, | |||
struct ast_variable * | vars, | |||
const char * | account, | |||
struct ast_channel ** | locked_channel, | |||
char * | uniqueid | |||
) |
Synchronously or asynchronously make an outbound call and send it to a particular application with given extension (extended version with callinpres and uniqueid)
Definition at line 5165 of file pbx.c.
References __ast_request_and_dial_uniqueid(), ast_channel::_state, outgoing_helper::account, async_stat::app, app_tmp::app, async_stat::appdata, ast_calloc, ast_cdr_alloc(), ast_cdr_disposition(), ast_cdr_failed(), ast_cdr_init(), ast_cdr_setaccount(), ast_cdr_start(), ast_channel_lock, ast_channel_unlock, ast_hangup(), ast_log(), ast_pbx_outgoing_cdr_failed(), ast_pbx_run_app(), ast_pthread_create, ast_set_variables(), AST_STATE_UP, ast_strlen_zero(), ast_variables_destroy(), ast_verbose(), async_wait(), ast_channel::cdr, async_stat::chan, app_tmp::chan, app_tmp::data, errno, free, ast_channel::hangupcause, LOG_WARNING, option_verbose, async_stat::p, ast_channel::pbx, app_tmp::t, async_stat::timeout, outgoing_helper::vars, and VERBOSE_PREFIX_4.
Referenced by action_originate(), ast_pbx_outgoing_app(), and fast_originate().
05166 { 05167 struct ast_channel *chan; 05168 struct app_tmp *tmp; 05169 int res = -1, cdr_res = -1; 05170 struct outgoing_helper oh; 05171 pthread_attr_t attr; 05172 05173 memset(&oh, 0, sizeof(oh)); 05174 oh.vars = vars; 05175 oh.account = account; 05176 05177 if (locked_channel) 05178 *locked_channel = NULL; 05179 if (ast_strlen_zero(app)) { 05180 res = -1; 05181 goto outgoing_app_cleanup; 05182 } 05183 if (sync) { 05184 chan = __ast_request_and_dial_uniqueid(type, format, data, timeout, reason, callingpres, cid_num, cid_name, &oh, uniqueid); 05185 if (chan) { 05186 if (!chan->cdr) { /* check if the channel already has a cdr record, if not give it one */ 05187 chan->cdr = ast_cdr_alloc(); /* allocate a cdr for the channel */ 05188 if(!chan->cdr) { 05189 /* allocation of the cdr failed */ 05190 free(chan->pbx); 05191 res = -1; 05192 goto outgoing_app_cleanup; 05193 } 05194 /* allocation of the cdr was successful */ 05195 ast_cdr_init(chan->cdr, chan); /* initilize our channel's cdr */ 05196 ast_cdr_start(chan->cdr); 05197 } 05198 ast_set_variables(chan, vars); 05199 if (account) 05200 ast_cdr_setaccount(chan, account); 05201 if (chan->_state == AST_STATE_UP) { 05202 res = 0; 05203 if (option_verbose > 3) 05204 ast_verbose(VERBOSE_PREFIX_4 "Channel %s was answered.\n", chan->name); 05205 tmp = ast_calloc(1, sizeof(*tmp)); 05206 if (!tmp) 05207 res = -1; 05208 else { 05209 ast_copy_string(tmp->app, app, sizeof(tmp->app)); 05210 if (appdata) 05211 ast_copy_string(tmp->data, appdata, sizeof(tmp->data)); 05212 tmp->chan = chan; 05213 if (sync > 1) { 05214 if (locked_channel) 05215 ast_channel_unlock(chan); 05216 ast_pbx_run_app(tmp); 05217 } else { 05218 pthread_attr_init(&attr); 05219 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 05220 if (locked_channel) 05221 ast_channel_lock(chan); 05222 if (ast_pthread_create(&tmp->t, &attr, ast_pbx_run_app, tmp)) { 05223 ast_log(LOG_WARNING, "Unable to spawn execute thread on %s: %s\n", chan->name, strerror(errno)); 05224 free(tmp); 05225 if (locked_channel) 05226 ast_channel_unlock(chan); 05227 ast_hangup(chan); 05228 res = -1; 05229 } else { 05230 if (locked_channel) 05231 *locked_channel = chan; 05232 } 05233 pthread_attr_destroy(&attr); 05234 } 05235 } 05236 } else { 05237 if (option_verbose > 3) 05238 ast_verbose(VERBOSE_PREFIX_4 "Channel %s was never answered.\n", chan->name); 05239 if (chan->cdr) { /* update the cdr */ 05240 /* here we update the status of the call, which sould be busy. 05241 * if that fails then we set the status to failed */ 05242 if (ast_cdr_disposition(chan->cdr, chan->hangupcause)) 05243 ast_cdr_failed(chan->cdr); 05244 } 05245 ast_hangup(chan); 05246 } 05247 } 05248 05249 if (res < 0) { /* the call failed for some reason */ 05250 if (*reason == 0) { /* if the call failed (not busy or no answer) 05251 * update the cdr with the failed message */ 05252 cdr_res = ast_pbx_outgoing_cdr_failed(); 05253 if (cdr_res != 0) { 05254 res = cdr_res; 05255 goto outgoing_app_cleanup; 05256 } 05257 } 05258 } 05259 05260 } else { 05261 struct async_stat *as; 05262 if (!(as = ast_calloc(1, sizeof(*as)))) { 05263 res = -1; 05264 goto outgoing_app_cleanup; 05265 } 05266 chan = __ast_request_and_dial_uniqueid(type, format, data, timeout, reason, callingpres, cid_num, cid_name, &oh, uniqueid); 05267 if (!chan) { 05268 free(as); 05269 res = -1; 05270 goto outgoing_app_cleanup; 05271 } 05272 as->chan = chan; 05273 ast_copy_string(as->app, app, sizeof(as->app)); 05274 if (appdata) 05275 ast_copy_string(as->appdata, appdata, sizeof(as->appdata)); 05276 as->timeout = timeout; 05277 ast_set_variables(chan, vars); 05278 if (account) 05279 ast_cdr_setaccount(chan, account); 05280 /* Start a new thread, and get something handling this channel. */ 05281 pthread_attr_init(&attr); 05282 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 05283 if (locked_channel) 05284 ast_channel_lock(chan); 05285 if (ast_pthread_create(&as->p, &attr, async_wait, as)) { 05286 ast_log(LOG_WARNING, "Failed to start async wait\n"); 05287 free(as); 05288 if (locked_channel) 05289 ast_channel_unlock(chan); 05290 ast_hangup(chan); 05291 res = -1; 05292 pthread_attr_destroy(&attr); 05293 goto outgoing_app_cleanup; 05294 } else { 05295 if (locked_channel) 05296 *locked_channel = chan; 05297 } 05298 pthread_attr_destroy(&attr); 05299 res = 0; 05300 } 05301 outgoing_app_cleanup: 05302 ast_variables_destroy(vars); 05303 return res; 05304 }
int ast_pbx_outgoing_exten | ( | const char * | type, | |
int | format, | |||
void * | data, | |||
int | timeout, | |||
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
int * | reason, | |||
int | sync, | |||
const char * | cid_num, | |||
const char * | cid_name, | |||
struct ast_variable * | vars, | |||
const char * | account, | |||
struct ast_channel ** | locked_channel | |||
) |
Synchronously or asynchronously make an outbound call and send it to a particular extension
Definition at line 5137 of file pbx.c.
References ast_pbx_outgoing_exten_uniqueid().
Referenced by attempt_thread(), and orig_exten().
05138 { 05139 return ast_pbx_outgoing_exten_uniqueid(type, format, data, timeout, context, exten, priority, reason, sync, 0, cid_num, cid_name, vars, account, channel, NULL); 05140 }
int ast_pbx_outgoing_exten_uniqueid | ( | const char * | type, | |
int | format, | |||
void * | data, | |||
int | timeout, | |||
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
int * | reason, | |||
int | sync, | |||
int | callingpres, | |||
const char * | cid_num, | |||
const char * | cid_name, | |||
struct ast_variable * | vars, | |||
const char * | account, | |||
struct ast_channel ** | locked_channel, | |||
char * | uniqueid | |||
) |
Synchronously or asynchronously make an outbound call and send it to a particular extension (extended version with callinpres and uniqueid)
Definition at line 4995 of file pbx.c.
References __ast_request_and_dial_uniqueid(), ast_channel::_state, ast_calloc, ast_cdr_disposition(), ast_cdr_failed(), ast_cdr_setaccount(), ast_channel_alloc(), ast_channel_lock, ast_channel_unlock, ast_exists_extension(), ast_hangup(), ast_log(), ast_pbx_outgoing_cdr_failed(), ast_pbx_run(), ast_pbx_start(), ast_pthread_create, ast_request_and_dial_uniqueid(), ast_set_variables(), AST_STATE_DOWN, AST_STATE_UP, ast_strlen_zero(), ast_variables_destroy(), ast_verbose(), async_wait(), ast_channel::cdr, async_stat::chan, async_stat::context, ast_channel::context, free, ast_channel::hangupcause, LOAD_OH, LOG_ERROR, LOG_WARNING, option_verbose, async_stat::p, pbx_builtin_setvar_helper(), set_ext_pri(), async_stat::timeout, and VERBOSE_PREFIX_4.
Referenced by action_originate(), ast_pbx_outgoing_exten(), and fast_originate().
04996 { 04997 struct ast_channel *chan; 04998 struct async_stat *as; 04999 int res = -1, cdr_res = -1; 05000 struct outgoing_helper oh; 05001 pthread_attr_t attr; 05002 05003 if (sync) { 05004 LOAD_OH(oh); 05005 chan = __ast_request_and_dial_uniqueid(type, format, data, timeout, reason, callingpres, cid_num, cid_name, &oh, uniqueid); 05006 if (channel) { 05007 *channel = chan; 05008 if (chan) 05009 ast_channel_lock(chan); 05010 } 05011 if (chan) { 05012 if (chan->_state == AST_STATE_UP) { 05013 res = 0; 05014 if (option_verbose > 3) 05015 ast_verbose(VERBOSE_PREFIX_4 "Channel %s was answered.\n", chan->name); 05016 05017 if (sync > 1) { 05018 if (channel) 05019 ast_channel_unlock(chan); 05020 if (ast_pbx_run(chan)) { 05021 ast_log(LOG_ERROR, "Unable to run PBX on %s\n", chan->name); 05022 if (channel) 05023 *channel = NULL; 05024 ast_hangup(chan); 05025 chan = NULL; 05026 res = -1; 05027 } 05028 } else { 05029 if (ast_pbx_start(chan)) { 05030 ast_log(LOG_ERROR, "Unable to start PBX on %s\n", chan->name); 05031 if (channel) { 05032 *channel = NULL; 05033 ast_channel_unlock(chan); 05034 } 05035 ast_hangup(chan); 05036 res = -1; 05037 } 05038 chan = NULL; 05039 } 05040 } else { 05041 if (option_verbose > 3) 05042 ast_verbose(VERBOSE_PREFIX_4 "Channel %s was never answered.\n", chan->name); 05043 05044 if (chan->cdr) { /* update the cdr */ 05045 /* here we update the status of the call, which sould be busy. 05046 * if that fails then we set the status to failed */ 05047 if (ast_cdr_disposition(chan->cdr, chan->hangupcause)) 05048 ast_cdr_failed(chan->cdr); 05049 } 05050 05051 if (channel) { 05052 *channel = NULL; 05053 ast_channel_unlock(chan); 05054 } 05055 ast_hangup(chan); 05056 chan = NULL; 05057 } 05058 } 05059 05060 if (res < 0) { /* the call failed for some reason */ 05061 if (*reason == 0) { /* if the call failed (not busy or no answer) 05062 * update the cdr with the failed message */ 05063 cdr_res = ast_pbx_outgoing_cdr_failed(); 05064 if (cdr_res != 0) { 05065 res = cdr_res; 05066 goto outgoing_exten_cleanup; 05067 } 05068 } 05069 05070 /* create a fake channel and execute the "failed" extension (if it exists) within the requested context */ 05071 /* check if "failed" exists */ 05072 if (ast_exists_extension(chan, context, "failed", 1, NULL)) { 05073 chan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "OutgoingSpoolFailed"); 05074 if (chan) { 05075 char failed_reason[4] = ""; 05076 if (!ast_strlen_zero(context)) 05077 ast_copy_string(chan->context, context, sizeof(chan->context)); 05078 set_ext_pri(chan, "failed", 1); 05079 ast_set_variables(chan, vars); 05080 snprintf(failed_reason, sizeof(failed_reason), "%d", *reason); 05081 pbx_builtin_setvar_helper(chan, "REASON", failed_reason); 05082 if (account) 05083 ast_cdr_setaccount(chan, account); 05084 if (ast_pbx_run(chan)) { 05085 ast_log(LOG_ERROR, "Unable to run PBX on %s\n", chan->name); 05086 ast_hangup(chan); 05087 } 05088 chan = NULL; 05089 } 05090 } 05091 } 05092 } else { 05093 if (!(as = ast_calloc(1, sizeof(*as)))) { 05094 res = -1; 05095 goto outgoing_exten_cleanup; 05096 } 05097 chan = ast_request_and_dial_uniqueid(type, format, data, timeout, reason, callingpres, cid_num, cid_name, uniqueid); 05098 if (channel) { 05099 *channel = chan; 05100 if (chan) 05101 ast_channel_lock(chan); 05102 } 05103 if (!chan) { 05104 free(as); 05105 res = -1; 05106 goto outgoing_exten_cleanup; 05107 } 05108 as->chan = chan; 05109 ast_copy_string(as->context, context, sizeof(as->context)); 05110 set_ext_pri(as->chan, exten, priority); 05111 as->timeout = timeout; 05112 ast_set_variables(chan, vars); 05113 if (account) 05114 ast_cdr_setaccount(chan, account); 05115 pthread_attr_init(&attr); 05116 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 05117 if (ast_pthread_create(&as->p, &attr, async_wait, as)) { 05118 ast_log(LOG_WARNING, "Failed to start async wait\n"); 05119 free(as); 05120 if (channel) { 05121 *channel = NULL; 05122 ast_channel_unlock(chan); 05123 } 05124 ast_hangup(chan); 05125 res = -1; 05126 pthread_attr_destroy(&attr); 05127 goto outgoing_exten_cleanup; 05128 } 05129 pthread_attr_destroy(&attr); 05130 res = 0; 05131 } 05132 outgoing_exten_cleanup: 05133 ast_variables_destroy(vars); 05134 return res; 05135 }
enum ast_pbx_result ast_pbx_run | ( | struct ast_channel * | c | ) |
Execute the PBX in the current thread.
c | channel to run the pbx on |
Definition at line 2670 of file pbx.c.
References __ast_pbx_run(), AST_PBX_CALL_LIMIT, AST_PBX_SUCCESS, decrease_call_count(), and increase_call_count().
Referenced by ast_pbx_outgoing_exten_uniqueid(), async_wait(), mgcp_ss(), skinny_newcall(), and ss_thread().
02671 { 02672 enum ast_pbx_result res = AST_PBX_SUCCESS; 02673 02674 if (increase_call_count(c)) 02675 return AST_PBX_CALL_LIMIT; 02676 02677 res = __ast_pbx_run(c); 02678 decrease_call_count(); 02679 02680 return res; 02681 }
enum ast_pbx_result ast_pbx_start | ( | struct ast_channel * | c | ) |
Create a new thread and start the PBX.
c | channel to start the pbx on |
Definition at line 2644 of file pbx.c.
References ast_log(), AST_PBX_CALL_LIMIT, AST_PBX_FAILED, AST_PBX_SUCCESS, ast_pthread_create, increase_call_count(), LOG_WARNING, pbx_thread(), and t.
Referenced by __oh323_new(), alsa_new(), ast_async_goto(), ast_bridge_call_thread(), ast_iax2_new(), ast_pbx_outgoing_exten_uniqueid(), bridge_exec(), check_goto_on_transfer(), do_parking_thread(), gtalk_new(), gtalk_newcall(), handle_request_invite(), local_call(), mgcp_new(), nbs_new(), oss_new(), pbx_start_chan(), phone_new(), rpt_call(), sip_new(), skinny_new(), and zt_new().
02645 { 02646 pthread_t t; 02647 pthread_attr_t attr; 02648 02649 if (!c) { 02650 ast_log(LOG_WARNING, "Asked to start thread on NULL channel?\n"); 02651 return AST_PBX_FAILED; 02652 } 02653 02654 if (increase_call_count(c)) 02655 return AST_PBX_CALL_LIMIT; 02656 02657 /* Start a new thread, and get something handling this channel. */ 02658 pthread_attr_init(&attr); 02659 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 02660 if (ast_pthread_create(&t, &attr, pbx_thread, c)) { 02661 ast_log(LOG_WARNING, "Failed to create new channel thread\n"); 02662 pthread_attr_destroy(&attr); 02663 return AST_PBX_FAILED; 02664 } 02665 pthread_attr_destroy(&attr); 02666 02667 return AST_PBX_SUCCESS; 02668 }
int ast_rdlock_contexts | ( | void | ) |
Definition at line 6168 of file pbx.c.
References ast_rwlock_rdlock().
Referenced by __ast_context_create(), _macro_exec(), ast_context_find(), ast_context_lockmacro(), ast_context_unlockmacro(), ast_hint_extension(), complete_context_add_extension(), complete_context_add_extension_deprecated(), complete_context_add_ignorepat(), complete_context_add_ignorepat_deprecated(), complete_context_add_include(), complete_context_add_include_deprecated(), complete_context_dont_include_deprecated(), complete_context_remove_extension(), complete_context_remove_extension_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), complete_show_dialplan_context(), dundi_precache_full(), find_context_locked(), handle_save_dialplan(), pbx_extension_helper(), and show_dialplan_helper().
06169 { 06170 return ast_rwlock_rdlock(&conlock); 06171 }
int ast_register_application | ( | const char * | app, | |
int(*)(struct ast_channel *, void *) | execute, | |||
const char * | synopsis, | |||
const char * | description | |||
) |
Register an application.
app | Short name of the application | |
execute | a function callback to execute the application. It should return non-zero if the channel needs to be hung up. | |
synopsis | a short description (one line synopsis) of the application | |
description | long description with all of the details about the use of the application |
0 | success | |
-1 | failure. |
Definition at line 2972 of file pbx.c.
References ast_calloc, AST_LIST_INSERT_BEFORE_CURRENT, AST_LIST_INSERT_TAIL, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, ast_log(), ast_verbose(), COLOR_BRCYAN, ast_app::description, ast_app::execute, LOG_WARNING, option_verbose, ast_app::synopsis, term_color(), and VERBOSE_PREFIX_2.
Referenced by load_module(), and load_pbx().
02973 { 02974 struct ast_app *tmp, *cur = NULL; 02975 char tmps[80]; 02976 int length; 02977 02978 AST_LIST_LOCK(&apps); 02979 AST_LIST_TRAVERSE(&apps, tmp, list) { 02980 if (!strcasecmp(app, tmp->name)) { 02981 ast_log(LOG_WARNING, "Already have an application '%s'\n", app); 02982 AST_LIST_UNLOCK(&apps); 02983 return -1; 02984 } 02985 } 02986 02987 length = sizeof(*tmp) + strlen(app) + 1; 02988 02989 if (!(tmp = ast_calloc(1, length))) { 02990 AST_LIST_UNLOCK(&apps); 02991 return -1; 02992 } 02993 02994 strcpy(tmp->name, app); 02995 tmp->execute = execute; 02996 tmp->synopsis = synopsis; 02997 tmp->description = description; 02998 02999 /* Store in alphabetical order */ 03000 AST_LIST_TRAVERSE_SAFE_BEGIN(&apps, cur, list) { 03001 if (strcasecmp(tmp->name, cur->name) < 0) { 03002 AST_LIST_INSERT_BEFORE_CURRENT(&apps, tmp, list); 03003 break; 03004 } 03005 } 03006 AST_LIST_TRAVERSE_SAFE_END 03007 if (!cur) 03008 AST_LIST_INSERT_TAIL(&apps, tmp, list); 03009 03010 if (option_verbose > 1) 03011 ast_verbose( VERBOSE_PREFIX_2 "Registered application '%s'\n", term_color(tmps, tmp->name, COLOR_BRCYAN, 0, sizeof(tmps))); 03012 03013 AST_LIST_UNLOCK(&apps); 03014 03015 return 0; 03016 }
int ast_register_switch | ( | struct ast_switch * | sw | ) |
Register an alternative dialplan switch.
sw | switch to register |
Definition at line 3022 of file pbx.c.
References AST_LIST_INSERT_TAIL, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), LOG_WARNING, and ast_switch::name.
Referenced by load_module().
03023 { 03024 struct ast_switch *tmp; 03025 03026 AST_LIST_LOCK(&switches); 03027 AST_LIST_TRAVERSE(&switches, tmp, list) { 03028 if (!strcasecmp(tmp->name, sw->name)) { 03029 AST_LIST_UNLOCK(&switches); 03030 ast_log(LOG_WARNING, "Switch '%s' already found\n", sw->name); 03031 return -1; 03032 } 03033 } 03034 AST_LIST_INSERT_TAIL(&switches, sw, list); 03035 AST_LIST_UNLOCK(&switches); 03036 03037 return 0; 03038 }
int ast_spawn_extension | ( | struct ast_channel * | c, | |
const char * | context, | |||
const char * | exten, | |||
int | priority, | |||
const char * | callerid | |||
) |
Launch a new extension (i.e. new stack).
c | not important | |
context | which context to generate the extension within | |
exten | new extension to add | |
priority | priority of new extension | |
callerid | callerid of extension |
0 | on success | |
-1 | on failure. |
Definition at line 2315 of file pbx.c.
References E_SPAWN, and pbx_extension_helper().
Referenced by __ast_pbx_run(), _macro_exec(), and loopback_exec().
02316 { 02317 return pbx_extension_helper(c, NULL, context, exten, priority, NULL, callerid, E_SPAWN); 02318 }
int ast_unlock_context | ( | struct ast_context * | con | ) |
Unlocks | the given context |
con | context to unlock |
0 | on success | |
-1 | on failure |
Definition at line 6191 of file pbx.c.
References ast_mutex_unlock(), and ast_context::lock.
Referenced by _macro_exec(), complete_context_dont_include_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), dundi_precache_full(), find_matching_endwhile(), handle_save_dialplan(), lookup_c_ip(), lookup_ci(), and show_dialplan_helper().
06192 { 06193 return ast_mutex_unlock(&con->lock); 06194 }
int ast_unlock_contexts | ( | void | ) |
Unlocks contexts.
0 | on success | |
-1 | on failure |
Definition at line 6178 of file pbx.c.
References ast_rwlock_unlock().
Referenced by __ast_context_create(), _macro_exec(), ast_add_extension(), ast_context_add_ignorepat(), ast_context_add_include(), ast_context_add_switch(), ast_context_destroy(), ast_context_find(), ast_context_lockmacro(), ast_context_remove_extension(), ast_context_remove_ignorepat(), ast_context_remove_include(), ast_context_remove_switch(), ast_context_unlockmacro(), ast_hint_extension(), ast_merge_contexts_and_delete(), complete_context_add_extension(), complete_context_add_extension_deprecated(), complete_context_add_ignorepat(), complete_context_add_ignorepat_deprecated(), complete_context_add_include(), complete_context_add_include_deprecated(), complete_context_dont_include_deprecated(), complete_context_remove_extension(), complete_context_remove_extension_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), complete_show_dialplan_context(), dundi_precache_full(), find_context_locked(), find_matching_endwhile(), handle_save_dialplan(), pbx_extension_helper(), and show_dialplan_helper().
06179 { 06180 return ast_rwlock_unlock(&conlock); 06181 }
int ast_unregister_application | ( | const char * | app | ) |
Unregister an application.
app | name of the application (does not have to be the same string as the one that was registered) |
0 | success | |
-1 | failure |
Definition at line 3853 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, ast_verbose(), free, option_verbose, and VERBOSE_PREFIX_2.
Referenced by __unload_module(), and unload_module().
03854 { 03855 struct ast_app *tmp; 03856 03857 AST_LIST_LOCK(&apps); 03858 AST_LIST_TRAVERSE_SAFE_BEGIN(&apps, tmp, list) { 03859 if (!strcasecmp(app, tmp->name)) { 03860 AST_LIST_REMOVE_CURRENT(&apps, list); 03861 if (option_verbose > 1) 03862 ast_verbose( VERBOSE_PREFIX_2 "Unregistered application '%s'\n", tmp->name); 03863 free(tmp); 03864 break; 03865 } 03866 } 03867 AST_LIST_TRAVERSE_SAFE_END 03868 AST_LIST_UNLOCK(&apps); 03869 03870 return tmp ? 0 : -1; 03871 }
void ast_unregister_switch | ( | struct ast_switch * | sw | ) |
Unregister an alternative switch.
sw | switch to unregister |
Definition at line 3040 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_REMOVE, and AST_LIST_UNLOCK.
Referenced by __unload_module(), and unload_module().
03041 { 03042 AST_LIST_LOCK(&switches); 03043 AST_LIST_REMOVE(&switches, sw, list); 03044 AST_LIST_UNLOCK(&switches); 03045 }
struct ast_exten* ast_walk_context_extensions | ( | struct ast_context * | con, | |
struct ast_exten * | priority | |||
) | [read] |
Definition at line 6300 of file pbx.c.
References ast_exten::next, and ast_context::root.
Referenced by complete_context_remove_extension(), complete_context_remove_extension_deprecated(), dundi_precache_full(), find_matching_priority(), handle_save_dialplan(), pbx_find_extension(), and show_dialplan_helper().
06302 { 06303 if (!exten) 06304 return con ? con->root : NULL; 06305 else 06306 return exten->next; 06307 }
struct ast_ignorepat* ast_walk_context_ignorepats | ( | struct ast_context * | con, | |
struct ast_ignorepat * | ip | |||
) | [read] |
Definition at line 6333 of file pbx.c.
References ast_context::ignorepats, and ast_ignorepat::next.
Referenced by complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), handle_save_dialplan(), lookup_c_ip(), and show_dialplan_helper().
06335 { 06336 if (!ip) 06337 return con ? con->ignorepats : NULL; 06338 else 06339 return ip->next; 06340 }
struct ast_include* ast_walk_context_includes | ( | struct ast_context * | con, | |
struct ast_include * | inc | |||
) | [read] |
Definition at line 6324 of file pbx.c.
References ast_context::includes, and ast_include::next.
Referenced by ast_context_verify_includes(), complete_context_dont_include_deprecated(), complete_context_remove_include(), find_matching_priority(), handle_save_dialplan(), lookup_ci(), and show_dialplan_helper().
06326 { 06327 if (!inc) 06328 return con ? con->includes : NULL; 06329 else 06330 return inc->next; 06331 }
struct ast_sw* ast_walk_context_switches | ( | struct ast_context * | con, | |
struct ast_sw * | sw | |||
) | [read] |
Definition at line 6309 of file pbx.c.
References AST_LIST_FIRST, and AST_LIST_NEXT.
Referenced by handle_save_dialplan(), and show_dialplan_helper().
06311 { 06312 if (!sw) 06313 return con ? AST_LIST_FIRST(&con->alts) : NULL; 06314 else 06315 return AST_LIST_NEXT(sw, list); 06316 }
struct ast_context* ast_walk_contexts | ( | struct ast_context * | con | ) | [read] |
Definition at line 6295 of file pbx.c.
References contexts, and ast_context::next.
Referenced by _macro_exec(), ast_context_find(), ast_context_lockmacro(), ast_context_unlockmacro(), complete_context_add_extension(), complete_context_add_extension_deprecated(), complete_context_add_ignorepat(), complete_context_add_ignorepat_deprecated(), complete_context_add_include(), complete_context_add_include_deprecated(), complete_context_dont_include_deprecated(), complete_context_remove_extension(), complete_context_remove_extension_deprecated(), complete_context_remove_ignorepat(), complete_context_remove_ignorepat_deprecated(), complete_context_remove_include(), complete_show_dialplan_context(), dundi_precache_full(), find_context_locked(), find_matching_endwhile(), find_matching_priority(), handle_save_dialplan(), pbx_find_extension(), pbx_load_module(), and show_dialplan_helper().
struct ast_exten* ast_walk_extension_priorities | ( | struct ast_exten * | exten, | |
struct ast_exten * | priority | |||
) | [read] |
Definition at line 6318 of file pbx.c.
References ast_exten::peer.
Referenced by complete_context_remove_extension(), complete_context_remove_extension_deprecated(), find_matching_priority(), handle_save_dialplan(), pbx_find_extension(), and show_dialplan_helper().
06320 { 06321 return priority ? priority->peer : exten; 06322 }
int ast_wrlock_contexts | ( | void | ) |
Definition at line 6173 of file pbx.c.
References ast_rwlock_wrlock().
Referenced by __ast_context_create(), ast_context_destroy(), ast_merge_contexts_and_delete(), and complete_context_dont_include_deprecated().
06174 { 06175 return ast_rwlock_wrlock(&conlock); 06176 }
void pbx_builtin_clear_globals | ( | void | ) |
Definition at line 6019 of file pbx.c.
References AST_LIST_REMOVE_HEAD, ast_mutex_lock(), ast_mutex_unlock(), ast_var_delete(), and globals.
Referenced by handle_reload_extensions(), and reload().
06020 { 06021 struct ast_var_t *vardata; 06022 06023 ast_mutex_lock(&globalslock); 06024 while ((vardata = AST_LIST_REMOVE_HEAD(&globals, entries))) 06025 ast_var_delete(vardata); 06026 ast_mutex_unlock(&globalslock); 06027 }
const char* pbx_builtin_getvar_helper | ( | struct ast_channel * | chan, | |
const char * | name | |||
) |
Definition at line 5796 of file pbx.c.
References ast_channel_lock, ast_channel_unlock, AST_LIST_TRAVERSE, ast_mutex_lock(), ast_mutex_unlock(), ast_var_name(), ast_var_value(), globals, and ast_channel::varshead.
Referenced by __ast_pbx_run(), __login_exec(), _macro_exec(), _while_exec(), agent_hangup(), agent_read(), agentmonitoroutgoing_exec(), ast_bridge_call(), ast_channel_bridge(), ast_feature_interpret(), ast_monitor_stop(), builtin_automonitor(), check_goto_on_transfer(), common_exec(), conf_exec(), conf_run(), dundi_exec(), dundi_helper(), get_also_info(), get_index(), get_refer_info(), global_read(), iax2_exec(), import_ch(), leave_voicemail(), local_hangup(), misdn_answer(), misdn_hangup(), morsecode_exec(), notify_new_message(), oh323_call(), oh323_hangup(), park_call_full(), pickup_by_mark(), queue_exec(), real_ctx(), retrydial_exec(), return_exec(), ring_entry(), run_agi(), set_config_flags(), sip_addheader(), sla_trunk_exec(), speech_background(), try_calling(), try_suggested_sip_codec(), wait_for_answer(), zt_call(), and zt_hangup().
05797 { 05798 struct ast_var_t *variables; 05799 const char *ret = NULL; 05800 int i; 05801 struct varshead *places[2] = { NULL, &globals }; 05802 05803 if (!name) 05804 return NULL; 05805 05806 if (chan) { 05807 ast_channel_lock(chan); 05808 places[0] = &chan->varshead; 05809 } 05810 05811 for (i = 0; i < 2; i++) { 05812 if (!places[i]) 05813 continue; 05814 if (places[i] == &globals) 05815 ast_mutex_lock(&globalslock); 05816 AST_LIST_TRAVERSE(places[i], variables, entries) { 05817 if (!strcmp(name, ast_var_name(variables))) { 05818 ret = ast_var_value(variables); 05819 break; 05820 } 05821 } 05822 if (places[i] == &globals) 05823 ast_mutex_unlock(&globalslock); 05824 if (ret) 05825 break; 05826 } 05827 05828 if (chan) 05829 ast_channel_unlock(chan); 05830 05831 return ret; 05832 }
void pbx_builtin_pushvar_helper | ( | struct ast_channel * | chan, | |
const char * | name, | |||
const char * | value | |||
) |
Definition at line 5834 of file pbx.c.
References ast_channel_lock, ast_channel_unlock, ast_func_write(), AST_LIST_INSERT_HEAD, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_strdupa, ast_var_assign(), ast_verbose(), globals, LOG_WARNING, option_verbose, ast_channel::varshead, and VERBOSE_PREFIX_2.
Referenced by acf_odbc_read(), acf_odbc_write(), and gosub_exec().
05835 { 05836 struct ast_var_t *newvariable; 05837 struct varshead *headp; 05838 05839 if (name[strlen(name)-1] == ')') { 05840 char *function = ast_strdupa(name); 05841 05842 ast_log(LOG_WARNING, "Cannot push a value onto a function\n"); 05843 ast_func_write(chan, function, value); 05844 return; 05845 } 05846 05847 if (chan) { 05848 ast_channel_lock(chan); 05849 headp = &chan->varshead; 05850 } else { 05851 ast_mutex_lock(&globalslock); 05852 headp = &globals; 05853 } 05854 05855 if (value) { 05856 if ((option_verbose > 1) && (headp == &globals)) 05857 ast_verbose(VERBOSE_PREFIX_2 "Setting global variable '%s' to '%s'\n", name, value); 05858 newvariable = ast_var_assign(name, value); 05859 AST_LIST_INSERT_HEAD(headp, newvariable, entries); 05860 } 05861 05862 if (chan) 05863 ast_channel_unlock(chan); 05864 else 05865 ast_mutex_unlock(&globalslock); 05866 }
int pbx_builtin_serialize_variables | ( | struct ast_channel * | chan, | |
char * | buf, | |||
size_t | size | |||
) |
Definition at line 5765 of file pbx.c.
References ast_build_string(), ast_channel_lock, ast_channel_unlock, AST_LIST_TRAVERSE, ast_log(), ast_var_name(), ast_var_value(), LOG_ERROR, total, var, and ast_channel::varshead.
Referenced by dumpchan_exec(), handle_showchan(), handle_showchan_deprecated(), and vars2manager().
05766 { 05767 struct ast_var_t *variables; 05768 const char *var, *val; 05769 int total = 0; 05770 05771 if (!chan) 05772 return 0; 05773 05774 memset(buf, 0, size); 05775 05776 ast_channel_lock(chan); 05777 05778 AST_LIST_TRAVERSE(&chan->varshead, variables, entries) { 05779 if ((var=ast_var_name(variables)) && (val=ast_var_value(variables)) 05780 /* && !ast_strlen_zero(var) && !ast_strlen_zero(val) */ 05781 ) { 05782 if (ast_build_string(&buf, &size, "%s=%s\n", var, val)) { 05783 ast_log(LOG_ERROR, "Data Buffer Size Exceeded!\n"); 05784 break; 05785 } else 05786 total++; 05787 } else 05788 break; 05789 } 05790 05791 ast_channel_unlock(chan); 05792 05793 return total; 05794 }
int pbx_builtin_setvar | ( | struct ast_channel * | chan, | |
void * | data | |||
) |
void pbx_builtin_setvar_helper | ( | struct ast_channel * | chan, | |
const char * | name, | |||
const char * | value | |||
) |
Definition at line 5868 of file pbx.c.
References ast_channel_lock, ast_channel_unlock, ast_func_write(), AST_LIST_INSERT_HEAD, AST_LIST_REMOVE, AST_LIST_TRAVERSE, ast_mutex_lock(), ast_mutex_unlock(), ast_strdupa, ast_var_assign(), ast_var_delete(), ast_var_name(), ast_verbose(), globals, option_verbose, ast_channel::varshead, and VERBOSE_PREFIX_2.
Referenced by __ast_pbx_run(), __login_exec(), __oh323_new(), _macro_exec(), _while_exec(), acf_odbc_read(), acf_odbc_write(), action_setvar(), agi_exec_full(), aji_status_exec(), app_exec(), aqm_exec(), array(), ast_bridge_call(), ast_channel_bridge(), ast_feature_request_and_dial(), ast_iax2_new(), ast_monitor_start(), ast_pbx_outgoing_exten_uniqueid(), ast_set_variables(), background_detect_exec(), bridge_exec(), builtin_automonitor(), builtin_blindtransfer(), cb_events(), chanavail_exec(), conf_run(), controlplayback_exec(), count_exec(), disa_exec(), do_waiting(), export_aoc_vars(), export_ch(), function_db_delete(), function_db_exists(), function_db_read(), global_write(), handle_request_bye(), handle_request_refer(), handle_set_global(), handle_set_global_deprecated(), handle_setvariable(), hasvoicemail_exec(), isAnsweringMachine(), leave_voicemail(), local_hangup(), lookupblacklist_exec(), misdn_call(), mixmonitor_exec(), ospauth_exec(), ospfinished_exec(), osplookup_exec(), ospnext_exec(), park_exec(), parse_moved_contact(), pbx_builtin_importvar(), pbx_builtin_setglobalvar(), pbx_builtin_setvar(), pbx_load_config(), play_message_datetime(), playback_exec(), pop_exec(), pqm_exec(), prep_email_sub_vars(), privacy_exec(), process_ast_dsp(), read_exec(), readfile_exec(), realtime_exec(), realtime_update_exec(), record_exec(), return_exec(), rqm_exec(), sendimage_exec(), sendtext_exec(), sendurl_exec(), set(), set_agentbycallerid(), set_queue_result(), sip_addheader(), sip_hangup(), sip_new(), sla_calc_trunk_timeouts(), sla_station_exec(), sla_trunk_exec(), socket_process(), speech_create(), ss_thread(), start_monitor_exec(), system_exec_helper(), transfer_exec(), try_calling(), tryexec_exec(), upqm_exec(), vm_box_exists(), vm_exec(), vmauthenticate(), zt_handle_dtmfup(), and zt_new().
05869 { 05870 struct ast_var_t *newvariable; 05871 struct varshead *headp; 05872 const char *nametail = name; 05873 05874 if (name[strlen(name)-1] == ')') { 05875 char *function = ast_strdupa(name); 05876 05877 ast_func_write(chan, function, value); 05878 return; 05879 } 05880 05881 if (chan) { 05882 ast_channel_lock(chan); 05883 headp = &chan->varshead; 05884 } else { 05885 ast_mutex_lock(&globalslock); 05886 headp = &globals; 05887 } 05888 05889 /* For comparison purposes, we have to strip leading underscores */ 05890 if (*nametail == '_') { 05891 nametail++; 05892 if (*nametail == '_') 05893 nametail++; 05894 } 05895 05896 AST_LIST_TRAVERSE (headp, newvariable, entries) { 05897 if (strcasecmp(ast_var_name(newvariable), nametail) == 0) { 05898 /* there is already such a variable, delete it */ 05899 AST_LIST_REMOVE(headp, newvariable, entries); 05900 ast_var_delete(newvariable); 05901 break; 05902 } 05903 } 05904 05905 if (value) { 05906 if ((option_verbose > 1) && (headp == &globals)) 05907 ast_verbose(VERBOSE_PREFIX_2 "Setting global variable '%s' to '%s'\n", name, value); 05908 newvariable = ast_var_assign(name, value); 05909 AST_LIST_INSERT_HEAD(headp, newvariable, entries); 05910 } 05911 05912 if (chan) 05913 ast_channel_unlock(chan); 05914 else 05915 ast_mutex_unlock(&globalslock); 05916 }
int pbx_checkcondition | ( | const char * | condition | ) |
Evaluate a condition.
0 | if the condition is NULL or of zero length | |
int | If the string is an integer, the integer representation of the integer is returned | |
1 | Any other non-empty string |
Definition at line 6029 of file pbx.c.
References ast_strlen_zero().
Referenced by _macro_exec(), _while_exec(), acf_if(), execif_exec(), gosubif_exec(), macroif_exec(), and pbx_builtin_gotoif().
06030 { 06031 if (ast_strlen_zero(condition)) /* NULL or empty strings are false */ 06032 return 0; 06033 else if (*condition >= '0' && *condition <= '9') /* Numbers are evaluated for truth */ 06034 return atoi(condition); 06035 else /* Strings are true */ 06036 return 1; 06037 }
int pbx_exec | ( | struct ast_channel * | c, | |
struct ast_app * | app, | |||
void * | data | |||
) |
Execute an application.
c | channel to execute on | |
app | which app to execute | |
data | the data passed into the app |
c | Channel | |
app | Application | |
data | Data for execution |
Definition at line 515 of file pbx.c.
References ast_channel::appl, ast_cdr_setapp(), ast_check_hangup(), ast_channel::cdr, ast_channel::data, ast_app::execute, and S_OR.
Referenced by answer_exec_run(), ast_bridge_call(), ast_pbx_run_app(), async_wait(), builtin_automonitor(), conf_run(), dundi_exec(), exec_exec(), execif_exec(), feature_exec_app(), forward_message(), handle_exec(), iax2_exec(), milliwatt_exec(), page_exec(), pbx_builtin_execiftime(), pbx_extension_helper(), realtime_exec(), try_calling(), and tryexec_exec().
00518 { 00519 int res; 00520 00521 const char *saved_c_appl; 00522 const char *saved_c_data; 00523 00524 if (c->cdr && !ast_check_hangup(c)) 00525 ast_cdr_setapp(c->cdr, app->name, data); 00526 00527 /* save channel values */ 00528 saved_c_appl= c->appl; 00529 saved_c_data= c->data; 00530 00531 c->appl = app->name; 00532 c->data = data; 00533 /* XXX remember what to to when we have linked apps to modules */ 00534 if (app->module) { 00535 /* XXX LOCAL_USER_ADD(app->module) */ 00536 } 00537 res = app->execute(c, S_OR(data, "")); 00538 if (app->module) { 00539 /* XXX LOCAL_USER_REMOVE(app->module) */ 00540 } 00541 /* restore channel values */ 00542 c->appl = saved_c_appl; 00543 c->data = saved_c_data; 00544 return res; 00545 }
struct ast_app* pbx_findapp | ( | const char * | app | ) | [read] |
Look up an application.
app | name of the app |
Definition at line 553 of file pbx.c.
References AST_LIST_LOCK, AST_LIST_TRAVERSE, and AST_LIST_UNLOCK.
Referenced by answer_exec_run(), ast_bridge_call(), ast_pbx_run_app(), async_wait(), builtin_automonitor(), conf_run(), dundi_exec(), exec_exec(), execif_exec(), feature_exec_app(), forward_message(), handle_exec(), iax2_exec(), milliwatt_exec(), page_exec(), pbx_builtin_execiftime(), pbx_extension_helper(), realtime_exec(), try_calling(), and tryexec_exec().
00554 { 00555 struct ast_app *tmp; 00556 00557 AST_LIST_LOCK(&apps); 00558 AST_LIST_TRAVERSE(&apps, tmp, list) { 00559 if (!strcasecmp(tmp->name, app)) 00560 break; 00561 } 00562 AST_LIST_UNLOCK(&apps); 00563 00564 return tmp; 00565 }
void pbx_retrieve_variable | ( | struct ast_channel * | c, | |
const char * | var, | |||
char ** | ret, | |||
char * | workspace, | |||
int | workspacelen, | |||
struct varshead * | headp | |||
) |
pbx_retrieve_variable: Support for Asterisk built-in variables ---
Definition at line 1151 of file pbx.c.
References ast_channel_lock, ast_channel_unlock, ast_config_AST_SYSTEM_NAME, ast_get_hint(), AST_LIST_TRAVERSE, ast_mutex_lock(), ast_mutex_unlock(), ast_strdupa, ast_var_name(), ast_var_value(), ast_channel::cid, ast_callerid::cid_ani2, ast_callerid::cid_pres, ast_callerid::cid_tns, ast_callerid::cid_ton, ast_channel::context, ast_channel::exten, globals, ast_channel::hangupcause, offset, parse_variable_name(), ast_channel::priority, s, substring(), and ast_channel::varshead.
Referenced by action_getvar(), handle_getvariable(), and pbx_substitute_variables_helper_full().
01152 { 01153 const char not_found = '\0'; 01154 char *tmpvar; 01155 const char *s; /* the result */ 01156 int offset, length; 01157 int i, need_substring; 01158 struct varshead *places[2] = { headp, &globals }; /* list of places where we may look */ 01159 01160 if (c) { 01161 ast_channel_lock(c); 01162 places[0] = &c->varshead; 01163 } 01164 /* 01165 * Make a copy of var because parse_variable_name() modifies the string. 01166 * Then if called directly, we might need to run substring() on the result; 01167 * remember this for later in 'need_substring', 'offset' and 'length' 01168 */ 01169 tmpvar = ast_strdupa(var); /* parse_variable_name modifies the string */ 01170 need_substring = parse_variable_name(tmpvar, &offset, &length, &i /* ignored */); 01171 01172 /* 01173 * Look first into predefined variables, then into variable lists. 01174 * Variable 's' points to the result, according to the following rules: 01175 * s == ¬_found (set at the beginning) means that we did not find a 01176 * matching variable and need to look into more places. 01177 * If s != ¬_found, s is a valid result string as follows: 01178 * s = NULL if the variable does not have a value; 01179 * you typically do this when looking for an unset predefined variable. 01180 * s = workspace if the result has been assembled there; 01181 * typically done when the result is built e.g. with an snprintf(), 01182 * so we don't need to do an additional copy. 01183 * s != workspace in case we have a string, that needs to be copied 01184 * (the ast_copy_string is done once for all at the end). 01185 * Typically done when the result is already available in some string. 01186 */ 01187 s = ¬_found; /* default value */ 01188 if (c) { /* This group requires a valid channel */ 01189 /* Names with common parts are looked up a piece at a time using strncmp. */ 01190 if (!strncmp(var, "CALL", 4)) { 01191 if (!strncmp(var + 4, "ING", 3)) { 01192 if (!strcmp(var + 7, "PRES")) { /* CALLINGPRES */ 01193 snprintf(workspace, workspacelen, "%d", c->cid.cid_pres); 01194 s = workspace; 01195 } else if (!strcmp(var + 7, "ANI2")) { /* CALLINGANI2 */ 01196 snprintf(workspace, workspacelen, "%d", c->cid.cid_ani2); 01197 s = workspace; 01198 } else if (!strcmp(var + 7, "TON")) { /* CALLINGTON */ 01199 snprintf(workspace, workspacelen, "%d", c->cid.cid_ton); 01200 s = workspace; 01201 } else if (!strcmp(var + 7, "TNS")) { /* CALLINGTNS */ 01202 snprintf(workspace, workspacelen, "%d", c->cid.cid_tns); 01203 s = workspace; 01204 } 01205 } 01206 } else if (!strcmp(var, "HINT")) { 01207 s = ast_get_hint(workspace, workspacelen, NULL, 0, c, c->context, c->exten) ? workspace : NULL; 01208 } else if (!strcmp(var, "HINTNAME")) { 01209 s = ast_get_hint(NULL, 0, workspace, workspacelen, c, c->context, c->exten) ? workspace : NULL; 01210 } else if (!strcmp(var, "EXTEN")) { 01211 s = c->exten; 01212 } else if (!strcmp(var, "CONTEXT")) { 01213 s = c->context; 01214 } else if (!strcmp(var, "PRIORITY")) { 01215 snprintf(workspace, workspacelen, "%d", c->priority); 01216 s = workspace; 01217 } else if (!strcmp(var, "CHANNEL")) { 01218 s = c->name; 01219 } else if (!strcmp(var, "UNIQUEID")) { 01220 s = c->uniqueid; 01221 } else if (!strcmp(var, "HANGUPCAUSE")) { 01222 snprintf(workspace, workspacelen, "%d", c->hangupcause); 01223 s = workspace; 01224 } 01225 } 01226 if (s == ¬_found) { /* look for more */ 01227 if (!strcmp(var, "EPOCH")) { 01228 snprintf(workspace, workspacelen, "%u",(int)time(NULL)); 01229 s = workspace; 01230 } else if (!strcmp(var, "SYSTEMNAME")) { 01231 s = ast_config_AST_SYSTEM_NAME; 01232 } 01233 } 01234 /* if not found, look into chanvars or global vars */ 01235 for (i = 0; s == ¬_found && i < (sizeof(places) / sizeof(places[0])); i++) { 01236 struct ast_var_t *variables; 01237 if (!places[i]) 01238 continue; 01239 if (places[i] == &globals) 01240 ast_mutex_lock(&globalslock); 01241 AST_LIST_TRAVERSE(places[i], variables, entries) { 01242 if (strcasecmp(ast_var_name(variables), var)==0) { 01243 s = ast_var_value(variables); 01244 break; 01245 } 01246 } 01247 if (places[i] == &globals) 01248 ast_mutex_unlock(&globalslock); 01249 } 01250 if (s == ¬_found || s == NULL) 01251 *ret = NULL; 01252 else { 01253 if (s != workspace) 01254 ast_copy_string(workspace, s, workspacelen); 01255 *ret = workspace; 01256 if (need_substring) 01257 *ret = substring(*ret, offset, length, workspace, workspacelen); 01258 } 01259 01260 if (c) 01261 ast_channel_unlock(c); 01262 }
int pbx_set_autofallthrough | ( | int | newval | ) |
Set "autofallthrough" flag, if newval is <0, does not acutally set. If set to 1, sets to auto fall through. If newval set to 0, sets to no auto fall through (reads extension instead). Returns previous value.
Definition at line 2688 of file pbx.c.
References autofallthrough.
Referenced by pbx_load_module().
02689 { 02690 int oldval = autofallthrough; 02691 autofallthrough = newval; 02692 return oldval; 02693 }
void pbx_substitute_variables_helper | ( | struct ast_channel * | c, | |
const char * | cp1, | |||
char * | cp2, | |||
int | count | |||
) |
Definition at line 1767 of file pbx.c.
References pbx_substitute_variables_helper_full(), and ast_channel::varshead.
Referenced by _macro_exec(), acf_odbc_read(), acf_odbc_write(), add_extensions(), custom_log(), cut_internal(), exec_exec(), function_eval(), function_fieldqty(), handle_getvariablefull(), launch_monitor_thread(), make_email_file(), pbx_builtin_importvar(), pbx_find_extension(), pbx_load_config(), pbx_substitute_variables(), realtime_exec(), rpt_do_lstats(), rpt_exec(), sendpage(), try_calling(), and tryexec_exec().
01768 { 01769 pbx_substitute_variables_helper_full(c, (c) ? &c->varshead : NULL, cp1, cp2, count); 01770 }
void pbx_substitute_variables_varshead | ( | struct varshead * | headp, | |
const char * | cp1, | |||
char * | cp2, | |||
int | count | |||
) |
Definition at line 1772 of file pbx.c.
References pbx_substitute_variables_helper_full().
Referenced by ast_add_extension2(), do_say(), dundi_lookup_local(), and loopback_subst().
01773 { 01774 pbx_substitute_variables_helper_full(NULL, headp, cp1, cp2, count); 01775 }