General Asterisk PBX channel definitions. More...
#include "asterisk/abstract_jb.h"#include "asterisk/poll-compat.h"#include "asterisk/frame.h"#include "asterisk/sched.h"#include "asterisk/chanvars.h"#include "asterisk/config.h"#include "asterisk/lock.h"#include "asterisk/cdr.h"#include "asterisk/utils.h"#include "asterisk/linkedlists.h"#include "asterisk/stringfields.h"#include "asterisk/datastore.h"
Go to the source code of this file.
Data Structures | |
| struct | ast_bridge_config |
| bridge configuration More... | |
| struct | ast_callerid |
| Structure for all kinds of caller ID identifications. More... | |
| struct | ast_channel |
| Main Channel structure associated with a channel. This is the side of it mostly used by the pbx and call management. More... | |
| struct | ast_channel_tech |
| Structure to describe a channel "technology", ie a channel driver See for examples:. More... | |
| struct | ast_generator |
| struct | ast_group_info |
| channel group info More... | |
| struct | outgoing_helper |
Defines | |
| #define | AST_AGENT_FD (AST_MAX_FDS-3) |
| #define | AST_ALERT_FD (AST_MAX_FDS-1) |
| #define | AST_BRIDGE_DTMF_CHANNEL_0 (1 << 0) |
| Report DTMF on channel 0. | |
| #define | AST_BRIDGE_DTMF_CHANNEL_1 (1 << 1) |
| Report DTMF on channel 1. | |
| #define | AST_BRIDGE_IGNORE_SIGS (1 << 4) |
| Ignore all signal frames except NULL. | |
| #define | AST_BRIDGE_REC_CHANNEL_0 (1 << 2) |
| Return all voice frames on channel 0. | |
| #define | AST_BRIDGE_REC_CHANNEL_1 (1 << 3) |
| Return all voice frames on channel 1. | |
| #define | ast_channel_alloc(needqueue, state, cid_num, cid_name, acctcode, exten, context, amaflag,...) |
| #define | AST_CHANNEL_NAME 80 |
| #define | AST_GENERATOR_FD (AST_MAX_FDS-4) |
| #define | AST_MAX_CONTEXT 80 |
| #define | AST_MAX_EXTENSION 80 |
| #define | AST_MAX_FDS 10 |
| #define | AST_TIMING_FD (AST_MAX_FDS-2) |
| #define | CHECK_BLOCKING(c) |
| #define | DATASTORE_INHERIT_FOREVER INT_MAX |
| #define | DEBUGCHAN_FLAG 0x80000000 |
| #define | FRAMECOUNT_INC(x) ( ((x) & DEBUGCHAN_FLAG) | (((x)+1) & ~DEBUGCHAN_FLAG) ) |
| #define | MAX_LANGUAGE 20 |
| #define | MAX_MUSICCLASS 80 |
Typedefs | |
| typedef unsigned long long | ast_group_t |
Enumerations | |
| enum | { AST_CHAN_TP_WANTSJITTER = (1 << 0), AST_CHAN_TP_CREATESJITTER = (1 << 1) } |
ast_channel_tech Properties More... | |
| enum | { AST_FLAG_DEFER_DTMF = (1 << 1), AST_FLAG_WRITE_INT = (1 << 2), AST_FLAG_BLOCKING = (1 << 3), AST_FLAG_ZOMBIE = (1 << 4), AST_FLAG_EXCEPTION = (1 << 5), AST_FLAG_MOH = (1 << 6), AST_FLAG_SPYING = (1 << 7), AST_FLAG_NBRIDGE = (1 << 8), AST_FLAG_IN_AUTOLOOP = (1 << 9), AST_FLAG_OUTGOING = (1 << 10), AST_FLAG_IN_DTMF = (1 << 12), AST_FLAG_EMULATE_DTMF = (1 << 13), AST_FLAG_END_DTMF_ONLY = (1 << 14), AST_FLAG_ANSWERED_ELSEWHERE = (1 << 15), AST_FLAG_MASQ_NOSTREAM = (1 << 16), AST_FLAG_BRIDGE_HANGUP_RUN = (1 << 17), AST_FLAG_BRIDGE_HANGUP_DONT = (1 << 18), AST_FLAG_IN_CHANNEL_LIST = (1 << 19), AST_FLAG_DISABLE_WORKAROUNDS = (1 << 20) } |
ast_channel flags More... | |
| enum | { AST_FEATURE_PLAY_WARNING = (1 << 0), AST_FEATURE_REDIRECT = (1 << 1), AST_FEATURE_DISCONNECT = (1 << 2), AST_FEATURE_ATXFER = (1 << 3), AST_FEATURE_AUTOMON = (1 << 4), AST_FEATURE_PARKCALL = (1 << 5), AST_FEATURE_AUTOMIXMON = (1 << 6), AST_FEATURE_NO_H_EXTEN = (1 << 7), AST_FEATURE_WARNING_ACTIVE = (1 << 8) } |
ast_bridge_config flags More... | |
| enum | { AST_CDR_TRANSFER = (1 << 0), AST_CDR_FORWARD = (1 << 1), AST_CDR_CALLWAIT = (1 << 2), AST_CDR_CONFERENCE = (1 << 3) } |
| enum | { AST_SOFTHANGUP_DEV = (1 << 0), AST_SOFTHANGUP_ASYNCGOTO = (1 << 1), AST_SOFTHANGUP_SHUTDOWN = (1 << 2), AST_SOFTHANGUP_TIMEOUT = (1 << 3), AST_SOFTHANGUP_APPUNLOAD = (1 << 4), AST_SOFTHANGUP_EXPLICIT = (1 << 5), AST_SOFTHANGUP_UNBRIDGE = (1 << 6) } |
| enum | ast_bridge_result { AST_BRIDGE_COMPLETE = 0, AST_BRIDGE_FAILED = -1, AST_BRIDGE_FAILED_NOWARN = -2, AST_BRIDGE_RETRY = -3 } |
| enum | ast_channel_adsicpe { AST_ADSI_UNKNOWN, AST_ADSI_AVAILABLE, AST_ADSI_UNAVAILABLE, AST_ADSI_OFFHOOKONLY } |
| enum | ast_channel_state { AST_STATE_DOWN, AST_STATE_RESERVED, AST_STATE_OFFHOOK, AST_STATE_DIALING, AST_STATE_RING, AST_STATE_RINGING, AST_STATE_UP, AST_STATE_BUSY, AST_STATE_DIALING_OFFHOOK, AST_STATE_PRERING, AST_STATE_MUTE = (1 << 16) } |
ast_channel states More... | |
| enum | ast_t38_state { T38_STATE_UNAVAILABLE, T38_STATE_UNKNOWN, T38_STATE_NEGOTIATING, T38_STATE_REJECTED, T38_STATE_NEGOTIATED } |
Possible T38 states on channels. More... | |
| enum | channelreloadreason { CHANNEL_MODULE_LOAD, CHANNEL_MODULE_RELOAD, CHANNEL_CLI_RELOAD, CHANNEL_MANAGER_RELOAD } |
Channel reload reasons for manager events at load or reload of configuration. More... | |
Functions | |
| int | __ast_answer (struct ast_channel *chan, unsigned int delay, int cdr_answer) |
| Answer a channel, with a selectable delay before returning. | |
| struct ast_channel *attribute_malloc | __ast_channel_alloc (int needqueue, int state, const char *cid_num, const char *cid_name, const char *acctcode, const char *exten, const char *context, const int amaflag, const char *file, int line, const char *function, const char *name_fmt,...) |
| Create a channel structure. | |
| struct ast_channel * | __ast_request_and_dial (const char *type, int format, void *data, int timeout, int *reason, const char *cid_num, const char *cid_name, struct outgoing_helper *oh) |
| Request a channel of a given type, with data as optional information used by the low level module and attempt to place a call on it. | |
| int | ast_activate_generator (struct ast_channel *chan, struct ast_generator *gen, void *params) |
| int | ast_active_channels (void) |
| returns number of active/allocated channels | |
| static int | ast_add_fd (struct pollfd *pfd, int fd) |
| if fd is a valid descriptor, set *pfd with the descriptor | |
| int | ast_answer (struct ast_channel *chan) |
| Answer a channel. | |
| int | ast_autoservice_start (struct ast_channel *chan) |
| Automatically service a channel for us... | |
| int | ast_autoservice_stop (struct ast_channel *chan) |
| Stop servicing a channel for us... | |
| void | ast_begin_shutdown (int hangup) |
| Initiate system shutdown. | |
| int | ast_best_codec (int fmts) |
| Pick the best audio codec. | |
| struct ast_channel * | ast_bridged_channel (struct ast_channel *chan) |
| Find bridged channel. | |
| int | ast_call (struct ast_channel *chan, char *addr, int timeout) |
| Make a call. | |
| struct ast_channel * | ast_call_forward (struct ast_channel *caller, struct ast_channel *orig, int *timeout, int format, struct outgoing_helper *oh, int *outstate) |
| Forwards a call to a new channel specified by the original channel's call_forward str. If possible, the new forwarded channel is created and returned while the original one is terminated. | |
| void | ast_cancel_shutdown (void) |
| Cancel a shutdown in progress. | |
| const char * | ast_cause2str (int state) attribute_pure |
| Gives the string form of a given hangup cause. | |
| void | ast_change_name (struct ast_channel *chan, char *newname) |
| Change channel name. | |
| int | ast_channel_bridge (struct ast_channel *c0, struct ast_channel *c1, struct ast_bridge_config *config, struct ast_frame **fo, struct ast_channel **rc) |
| Bridge two channels together. | |
| int | ast_channel_cmpwhentohangup (struct ast_channel *chan, time_t offset) |
| Compare a offset with the settings of when to hang a channel up. | |
| int | ast_channel_cmpwhentohangup_tv (struct ast_channel *chan, struct timeval offset) |
| Compare a offset with the settings of when to hang a channel up. | |
| int | ast_channel_datastore_add (struct ast_channel *chan, struct ast_datastore *datastore) |
| Add a datastore to a channel. | |
| struct ast_datastore *attribute_malloc | ast_channel_datastore_alloc (const struct ast_datastore_info *info, const char *uid) |
| Create a channel data store object. | |
| struct ast_datastore * | ast_channel_datastore_find (struct ast_channel *chan, const struct ast_datastore_info *info, const char *uid) |
| Find a datastore on a channel. | |
| int | ast_channel_datastore_free (struct ast_datastore *datastore) |
| Free a channel data store object. | |
| int | ast_channel_datastore_inherit (struct ast_channel *from, struct ast_channel *to) |
| Inherit datastores from a parent to a child. | |
| int | ast_channel_datastore_remove (struct ast_channel *chan, struct ast_datastore *datastore) |
| Remove a datastore from a channel. | |
| int | ast_channel_defer_dtmf (struct ast_channel *chan) |
| Set defer DTMF flag on channel. | |
| int | ast_channel_early_bridge (struct ast_channel *c0, struct ast_channel *c1) |
| Bridge two channels together (early). | |
| void | ast_channel_free (struct ast_channel *) |
| Free a channel structure. | |
| static enum ast_t38_state | ast_channel_get_t38_state (struct ast_channel *chan) |
| Retrieves the current T38 state of a channel. | |
| void | ast_channel_inherit_variables (const struct ast_channel *parent, struct ast_channel *child) |
| Inherits channel variable from parent to child channel. | |
| int | ast_channel_make_compatible (struct ast_channel *c0, struct ast_channel *c1) |
| Makes two channel formats compatible. | |
| int | ast_channel_masquerade (struct ast_channel *original, struct ast_channel *clone) |
| Weird function made for call transfers. | |
| int | ast_channel_queryoption (struct ast_channel *channel, int option, void *data, int *datalen, int block) |
| const char * | ast_channel_reason2str (int reason) |
| return an english explanation of the code returned thru __ast_request_and_dial's 'outstate' argument | |
| int | ast_channel_register (const struct ast_channel_tech *tech) |
| Register a channel technology (a new channel driver) Called by a channel module to register the kind of channels it supports. | |
| int | ast_channel_sendhtml (struct ast_channel *channel, int subclass, const char *data, int datalen) |
| int | ast_channel_sendurl (struct ast_channel *channel, const char *url) |
| void | ast_channel_set_fd (struct ast_channel *chan, int which, int fd) |
| int | ast_channel_setoption (struct ast_channel *channel, int option, void *data, int datalen, int block) |
| Sets an option on a channel. | |
| void | ast_channel_setwhentohangup (struct ast_channel *chan, time_t offset) |
| Set when to hang a channel up. | |
| void | ast_channel_setwhentohangup_tv (struct ast_channel *chan, struct timeval offset) |
| Set when to hang a channel up. | |
| struct ast_silence_generator * | ast_channel_start_silence_generator (struct ast_channel *chan) |
| Starts a silence generator on the given channel. | |
| void | ast_channel_stop_silence_generator (struct ast_channel *chan, struct ast_silence_generator *state) |
| Stops a previously-started silence generator on the given channel. | |
| int | ast_channel_supports_html (struct ast_channel *channel) |
| void | ast_channel_undefer_dtmf (struct ast_channel *chan) |
| Unset defer DTMF flag on channel. | |
| void | ast_channel_unregister (const struct ast_channel_tech *tech) |
| Unregister a channel technology. | |
| struct ast_channel * | ast_channel_walk_locked (const struct ast_channel *prev) |
| Browse channels in use Browse the channels currently in use. | |
| struct ast_variable * | ast_channeltype_list (void) |
| return an ast_variable list of channeltypes | |
| int | ast_check_hangup (struct ast_channel *chan) |
| Check to see if a channel is needing hang up. | |
| void | ast_deactivate_generator (struct ast_channel *chan) |
| int | ast_do_masquerade (struct ast_channel *chan) |
| Start masquerading a channel XXX This is a seriously whacked out operation. We're essentially putting the guts of the clone channel into the original channel. Start by killing off the original channel's backend. I'm not sure we're going to keep this function, because while the features are nice, the cost is very high in terms of pure nastiness. XXX. | |
| static int | ast_fdisset (struct pollfd *pfds, int fd, int maximum, int *start) |
| Helper function for migrating select to poll. | |
| struct ast_channel * | ast_get_channel_by_exten_locked (const char *exten, const char *context) |
| Get channel by exten (and optionally context) and lock it. | |
| struct ast_channel * | ast_get_channel_by_name_locked (const char *chan) |
| Get channel by name or uniqueid (locks channel). | |
| struct ast_channel * | ast_get_channel_by_name_prefix_locked (const char *name, const int namelen) |
| Get channel by name or uniqueid prefix (locks channel). | |
| struct ast_channel_tech * | ast_get_channel_tech (const char *name) |
| Get a channel technology structure by name. | |
| ast_group_t | ast_get_group (const char *s) |
| int | ast_hangup (struct ast_channel *chan) |
| Hang up a channel. | |
| int | ast_indicate (struct ast_channel *chan, int condition) |
| Indicates condition of channel. | |
| int | ast_indicate_data (struct ast_channel *chan, int condition, const void *data, size_t datalen) |
| Indicates condition of channel, with payload. | |
| int | ast_internal_timing_enabled (struct ast_channel *chan) |
| Check if the channel can run in internal timing mode. | |
| void | ast_poll_channel_add (struct ast_channel *chan0, struct ast_channel *chan1) |
| void | ast_poll_channel_del (struct ast_channel *chan0, struct ast_channel *chan1) |
| char * | ast_print_group (char *buf, int buflen, ast_group_t group) |
| print call- and pickup groups into buffer | |
| int | ast_prod (struct ast_channel *chan) |
| Send empty audio to prime a channel driver. | |
| int | ast_queue_control (struct ast_channel *chan, enum ast_control_frame_type control) |
| Queue a control frame with payload. | |
| int | ast_queue_control_data (struct ast_channel *chan, enum ast_control_frame_type control, const void *data, size_t datalen) |
| Queue a control frame with payload. | |
| int | ast_queue_frame (struct ast_channel *chan, struct ast_frame *f) |
| Queue one or more frames to a channel's frame queue. | |
| int | ast_queue_frame_head (struct ast_channel *chan, struct ast_frame *f) |
| Queue one or more frames to the head of a channel's frame queue. | |
| int | ast_queue_hangup (struct ast_channel *chan) |
| Queue a hangup frame. | |
| int | ast_queue_hangup_with_cause (struct ast_channel *chan, int cause) |
| Queue a hangup frame with hangupcause set. | |
| int | ast_raw_answer (struct ast_channel *chan, int cdr_answer) |
| Answer a channel. | |
| struct ast_frame * | ast_read (struct ast_channel *chan) |
| Reads a frame. | |
| struct ast_frame * | ast_read_noaudio (struct ast_channel *chan) |
| Reads a frame, returning AST_FRAME_NULL frame if audio. | |
| int | ast_readstring (struct ast_channel *c, char *s, int len, int timeout, int rtimeout, char *enders) |
| int | ast_readstring_full (struct ast_channel *c, char *s, int len, int timeout, int rtimeout, char *enders, int audiofd, int ctrlfd) |
| int | ast_recvchar (struct ast_channel *chan, int timeout) |
| Receives a text character from a channel. | |
| char * | ast_recvtext (struct ast_channel *chan, int timeout) |
| Receives a text string from a channel Read a string of text from a channel. | |
| struct ast_channel * | ast_request (const char *type, int format, void *data, int *status) |
| Requests a channel. | |
| struct ast_channel * | ast_request_and_dial (const char *type, int format, void *data, int timeout, int *reason, const char *cid_num, const char *cid_name) |
| Request a channel of a given type, with data as optional information used by the low level module and attempt to place a call on it. | |
| int | ast_safe_sleep (struct ast_channel *chan, int ms) |
| Wait for a specified amount of time, looking for hangups. | |
| int | ast_safe_sleep_conditional (struct ast_channel *chan, int ms, int(*cond)(void *), void *data) |
| Wait for a specified amount of time, looking for hangups and a condition argument. | |
| static int | ast_select (int nfds, fd_set *rfds, fd_set *wfds, fd_set *efds, struct timeval *tvp) |
| Waits for activity on a group of channels. | |
| int | ast_senddigit (struct ast_channel *chan, char digit, unsigned int duration) |
| Send a DTMF digit to a channel Send a DTMF digit to a channel. | |
| int | ast_senddigit_begin (struct ast_channel *chan, char digit) |
| Send a DTMF digit to a channel Send a DTMF digit to a channel. | |
| int | ast_senddigit_end (struct ast_channel *chan, char digit, unsigned int duration) |
| Send a DTMF digit to a channel. | |
| int | ast_sendtext (struct ast_channel *chan, const char *text) |
| Sends text to a channel. | |
| void | ast_set_callerid (struct ast_channel *chan, const char *cid_num, const char *cid_name, const char *cid_ani) |
| Set caller ID number, name and ANI. | |
| int | ast_set_read_format (struct ast_channel *chan, int format) |
| Sets read format on channel chan Set read format for channel to whichever component of "format" is best. | |
| void | ast_set_variables (struct ast_channel *chan, struct ast_variable *vars) |
| adds a list of channel variables to a channel | |
| int | ast_set_write_format (struct ast_channel *chan, int format) |
| Sets write format on channel chan Set write format for channel to whichever component of "format" is best. | |
| int | ast_setstate (struct ast_channel *chan, enum ast_channel_state) |
| Change the state of a channel. | |
| int | ast_settimeout (struct ast_channel *c, unsigned int rate, int(*func)(const void *data), void *data) |
| Enable or disable timer ticks for a channel. | |
| int | ast_shutting_down (void) |
| Returns non-zero if Asterisk is being shut down. | |
| int | ast_softhangup (struct ast_channel *chan, int reason) |
| Softly hangup up a channel. | |
| int | ast_softhangup_nolock (struct ast_channel *chan, int reason) |
| Softly hangup up a channel (no channel lock). | |
| const char * | ast_state2str (enum ast_channel_state) |
| Gives the string form of a given channel state. | |
| int | ast_str2cause (const char *name) attribute_pure |
| Convert a symbolic hangup cause to number. | |
| int | ast_tonepair (struct ast_channel *chan, int freq1, int freq2, int duration, int vol) |
| int | ast_tonepair_start (struct ast_channel *chan, int freq1, int freq2, int duration, int vol) |
| void | ast_tonepair_stop (struct ast_channel *chan) |
| int | ast_transfer (struct ast_channel *chan, char *dest) |
| Transfer a channel (if supported). Returns -1 on error, 0 if not supported and 1 if supported and requested. | |
| char * | ast_transfercapability2str (int transfercapability) attribute_const |
| Gives the string form of a given transfer capability. | |
| int | ast_waitfor (struct ast_channel *chan, int ms) |
| Wait for input on a channel. | |
| struct ast_channel * | ast_waitfor_n (struct ast_channel **chan, int n, int *ms) |
| Waits for input on a group of channels Wait for input on an array of channels for a given # of milliseconds. | |
| int | ast_waitfor_n_fd (int *fds, int n, int *ms, int *exception) |
| Waits for input on an fd This version works on fd's only. Be careful with it. | |
| struct ast_channel * | ast_waitfor_nandfds (struct ast_channel **chan, int n, int *fds, int nfds, int *exception, int *outfd, int *ms) |
| Waits for activity on a group of channels. | |
| int | ast_waitfordigit (struct ast_channel *c, int ms) |
| Waits for a digit. | |
| int | ast_waitfordigit_full (struct ast_channel *c, int ms, int audiofd, int ctrlfd) |
| Wait for a digit Same as ast_waitfordigit() with audio fd for outputting read audio and ctrlfd to monitor for reading. | |
| struct ast_channel * | ast_walk_channel_by_exten_locked (const struct ast_channel *chan, const char *exten, const char *context) |
| Get next channel by exten (and optionally context) and lock it. | |
| struct ast_channel * | ast_walk_channel_by_name_prefix_locked (const struct ast_channel *chan, const char *name, const int namelen) |
| Get channel by name or uniqueid prefix (locks channel). | |
| int | ast_write (struct ast_channel *chan, struct ast_frame *frame) |
| Write a frame to a channel This function writes the given frame to the indicated channel. | |
| int | ast_write_text (struct ast_channel *chan, struct ast_frame *frame) |
| Write text frame to a channel This function writes the given frame to the indicated channel. | |
| int | ast_write_video (struct ast_channel *chan, struct ast_frame *frame) |
| Write video frame to a channel This function writes the given frame to the indicated channel. | |
| const char * | channelreloadreason2txt (enum channelreloadreason reason) |
| Convert enum channelreloadreason to text string for manager event. | |
Variables | |
| unsigned long | global_fin |
| unsigned long | global_fout |
General Asterisk PBX channel definitions.
Definition in file channel.h.
| #define AST_AGENT_FD (AST_MAX_FDS-3) |
used by agents for pass through
Definition at line 160 of file channel.h.
Referenced by agent_read().
| #define AST_ALERT_FD (AST_MAX_FDS-1) |
used for alertpipe
Definition at line 158 of file channel.h.
Referenced by __ast_channel_alloc_ap().
| #define AST_BRIDGE_DTMF_CHANNEL_0 (1 << 0) |
Report DTMF on channel 0.
Definition at line 1357 of file channel.h.
Referenced by ast_generic_bridge(), ast_rtp_bridge(), bridge_native_loop(), bridge_p2p_loop(), dahdi_bridge(), iax2_bridge(), misdn_bridge(), and set_config_flags().
| #define AST_BRIDGE_DTMF_CHANNEL_1 (1 << 1) |
Report DTMF on channel 1.
Definition at line 1359 of file channel.h.
Referenced by ast_generic_bridge(), ast_rtp_bridge(), bridge_native_loop(), bridge_p2p_loop(), dahdi_bridge(), iax2_bridge(), misdn_bridge(), and set_config_flags().
| #define AST_BRIDGE_IGNORE_SIGS (1 << 4) |
Ignore all signal frames except NULL.
Definition at line 1365 of file channel.h.
Referenced by ast_generic_bridge(), bridge_native_loop(), bridge_p2p_loop(), and iax2_bridge().
| #define AST_BRIDGE_REC_CHANNEL_0 (1 << 2) |
| #define AST_BRIDGE_REC_CHANNEL_1 (1 << 3) |
| #define ast_channel_alloc | ( | needqueue, | |||
| state, | |||||
| cid_num, | |||||
| cid_name, | |||||
| acctcode, | |||||
| exten, | |||||
| context, | |||||
| amaflag, | |||||
| ... | ) |
__ast_channel_alloc(needqueue, state, cid_num, cid_name, acctcode, exten, context, amaflag, \ __FILE__, __LINE__, __FUNCTION__, __VA_ARGS__)
Definition at line 729 of file channel.h.
Referenced by __oh323_new(), acf_odbc_read(), acf_odbc_write(), action_bridge(), action_getvar(), agent_new(), alsa_new(), ast_async_goto(), ast_iax2_new(), ast_pbx_outgoing_cdr_failed(), ast_pbx_outgoing_exten(), bridge_exec(), builtin_atxfer(), check_goto_on_transfer(), console_new(), dahdi_new(), gtalk_new(), iax_park(), jingle_new(), local_new(), make_email_file(), masq_park_call(), mgcp_new(), misdn_new(), nbs_new(), oss_new(), pbx_substitute_variables_helper_full(), phone_new(), rotate_file(), sendmail(), sendpage(), sip_new(), sip_park(), skinny_new(), unistim_new(), and usbradio_new().
| #define AST_CHANNEL_NAME 80 |
Max length of an ast_channel name
Definition at line 136 of file channel.h.
Referenced by ast_channel_free(), ast_do_masquerade(), ast_park_call_full(), ast_parse_device_state(), ast_setstate(), common_exec(), create_jb(), fast_originate(), page_exec(), and softhangup_exec().
| #define AST_GENERATOR_FD (AST_MAX_FDS-4) |
used by generator
Definition at line 161 of file channel.h.
Referenced by __ast_read(), ast_deactivate_generator(), and ast_do_masquerade().
| #define AST_MAX_CONTEXT 80 |
Max length of a context
Definition at line 135 of file channel.h.
Referenced by _macro_exec(), cleanup_stale_contexts(), common_exec(), conf_run(), gtalk_load_config(), handle_gosub(), reload_config(), and try_calling().
| #define AST_MAX_EXTENSION 80 |
Max length of an extension
Definition at line 134 of file channel.h.
Referenced by advanced_options(), ast_bridge_call(), ast_device_state_changed(), ast_devstate_changed(), ast_extension_state2(), ast_ivr_menu_run_internal(), begin_dial_channel(), build_device(), conf_run(), destroy_station(), dial_exec_full(), disa_exec(), do_forward(), dundi_lookup_local(), forward_message(), function_enum(), get_destination(), handle_gosub(), handle_statechange(), load_config(), load_module(), log_exec(), manage_parkinglot(), manager_show_dialplan_helper(), mgcp_ss(), park_add_hints(), park_call_exec(), phone_check_exception(), realtime_switch_common(), search_directory(), show_dialplan_helper(), skinny_extensionstate_cb(), skinny_ss(), sla_build_station(), speech_background(), ss_thread(), transmit_state_notify(), try_calling(), vm_authenticate(), and vmauthenticate().
| #define AST_MAX_FDS 10 |
Definition at line 153 of file channel.h.
Referenced by __ast_channel_alloc_ap(), ast_channel_free(), ast_do_masquerade(), ast_poll_channel_add(), ast_poll_channel_del(), ast_waitfor_nandfds(), and manage_parkinglot().
| #define AST_TIMING_FD (AST_MAX_FDS-2) |
used for timingfd
Definition at line 159 of file channel.h.
Referenced by __ast_channel_alloc_ap(), __ast_read(), agent_read(), and ast_do_masquerade().
| #define CHECK_BLOCKING | ( | c | ) |
Definition at line 1750 of file channel.h.
Referenced by ast_sendtext(), ast_waitfor_nandfds(), ast_write(), dahdi_read(), and phone_read().
| #define DATASTORE_INHERIT_FOREVER INT_MAX |
Definition at line 151 of file channel.h.
Referenced by _macro_exec(), acf_iaxvar_write(), add_features_datastores(), ast_channel_datastore_inherit(), ast_iax2_new(), authenticate_reply(), dial_exec_full(), socket_process(), and try_calling().
| #define DEBUGCHAN_FLAG 0x80000000 |
The high bit of the frame count is used as a debug marker, so increments of the counters must be done with care. Please use c->fin = FRAMECOUNT_INC(c->fin) and the same for c->fout.
Definition at line 334 of file channel.h.
Referenced by __ast_read(), ast_write(), handle_core_set_debug_channel(), handle_showchan(), and serialize_showchan().
| #define FRAMECOUNT_INC | ( | x | ) | ( ((x) & DEBUGCHAN_FLAG) | (((x)+1) & ~DEBUGCHAN_FLAG) ) |
Definition at line 337 of file channel.h.
Referenced by __ast_read(), and ast_write().
| #define MAX_LANGUAGE 20 |
| #define MAX_MUSICCLASS 80 |
| typedef unsigned long long ast_group_t |
| anonymous enum |
ast_channel_tech Properties
Definition at line 510 of file channel.h.
00510 { 00511 /*! \brief Channels have this property if they can accept input with jitter; 00512 * i.e. most VoIP channels */ 00513 AST_CHAN_TP_WANTSJITTER = (1 << 0), 00514 /*! \brief Channels have this property if they can create jitter; 00515 * i.e. most VoIP channels */ 00516 AST_CHAN_TP_CREATESJITTER = (1 << 1), 00517 };
| anonymous enum |
ast_channel flags
| AST_FLAG_DEFER_DTMF |
Queue incoming dtmf, to be released when this flag is turned off |
| AST_FLAG_WRITE_INT |
write should be interrupt generator |
| AST_FLAG_BLOCKING |
a thread is blocking on this channel |
| AST_FLAG_ZOMBIE |
This is a zombie channel |
| AST_FLAG_EXCEPTION |
There is an exception pending |
| AST_FLAG_MOH |
Listening to moh XXX anthm promises me this will disappear XXX |
| AST_FLAG_SPYING |
This channel is spying on another channel |
| AST_FLAG_NBRIDGE |
This channel is in a native bridge |
| AST_FLAG_IN_AUTOLOOP |
the channel is in an auto-incrementing dialplan processor, so when ->priority is set, it will get incremented before finding the next priority to run |
| AST_FLAG_OUTGOING |
This is an outgoing call |
| AST_FLAG_IN_DTMF |
A DTMF_BEGIN frame has been read from this channel, but not yet an END |
| AST_FLAG_EMULATE_DTMF |
A DTMF_END was received when not IN_DTMF, so the length of the digit is currently being emulated |
| AST_FLAG_END_DTMF_ONLY |
This is set to tell the channel not to generate DTMF begin frames, and to instead only generate END frames. |
| AST_FLAG_ANSWERED_ELSEWHERE |
Flag to show channels that this call is hangup due to the fact that the call was indeed anwered, but in another channel |
| AST_FLAG_MASQ_NOSTREAM |
This flag indicates that on a masquerade, an active stream should not be carried over |
| AST_FLAG_BRIDGE_HANGUP_RUN |
This flag indicates that the hangup exten was run when the bridge terminated, a message aimed at preventing a subsequent hangup exten being run at the pbx_run level |
| AST_FLAG_BRIDGE_HANGUP_DONT |
This flag indicates that the hangup exten should NOT be run when the bridge terminates, this will allow the hangup in the pbx loop to be run instead. |
| AST_FLAG_IN_CHANNEL_LIST |
This flag indicates whether the channel is in the channel list or not. |
| AST_FLAG_DISABLE_WORKAROUNDS |
Disable certain workarounds. This reintroduces certain bugs, but allows some non-traditional dialplans (like AGI) to continue to function. |
Definition at line 520 of file channel.h.
00520 { 00521 /*! Queue incoming dtmf, to be released when this flag is turned off */ 00522 AST_FLAG_DEFER_DTMF = (1 << 1), 00523 /*! write should be interrupt generator */ 00524 AST_FLAG_WRITE_INT = (1 << 2), 00525 /*! a thread is blocking on this channel */ 00526 AST_FLAG_BLOCKING = (1 << 3), 00527 /*! This is a zombie channel */ 00528 AST_FLAG_ZOMBIE = (1 << 4), 00529 /*! There is an exception pending */ 00530 AST_FLAG_EXCEPTION = (1 << 5), 00531 /*! Listening to moh XXX anthm promises me this will disappear XXX */ 00532 AST_FLAG_MOH = (1 << 6), 00533 /*! This channel is spying on another channel */ 00534 AST_FLAG_SPYING = (1 << 7), 00535 /*! This channel is in a native bridge */ 00536 AST_FLAG_NBRIDGE = (1 << 8), 00537 /*! the channel is in an auto-incrementing dialplan processor, 00538 * so when ->priority is set, it will get incremented before 00539 * finding the next priority to run */ 00540 AST_FLAG_IN_AUTOLOOP = (1 << 9), 00541 /*! This is an outgoing call */ 00542 AST_FLAG_OUTGOING = (1 << 10), 00543 /*! A DTMF_BEGIN frame has been read from this channel, but not yet an END */ 00544 AST_FLAG_IN_DTMF = (1 << 12), 00545 /*! A DTMF_END was received when not IN_DTMF, so the length of the digit is 00546 * currently being emulated */ 00547 AST_FLAG_EMULATE_DTMF = (1 << 13), 00548 /*! This is set to tell the channel not to generate DTMF begin frames, and 00549 * to instead only generate END frames. */ 00550 AST_FLAG_END_DTMF_ONLY = (1 << 14), 00551 /*! Flag to show channels that this call is hangup due to the fact that the call 00552 was indeed anwered, but in another channel */ 00553 AST_FLAG_ANSWERED_ELSEWHERE = (1 << 15), 00554 /*! This flag indicates that on a masquerade, an active stream should not 00555 * be carried over */ 00556 AST_FLAG_MASQ_NOSTREAM = (1 << 16), 00557 /*! This flag indicates that the hangup exten was run when the bridge terminated, 00558 * a message aimed at preventing a subsequent hangup exten being run at the pbx_run 00559 * level */ 00560 AST_FLAG_BRIDGE_HANGUP_RUN = (1 << 17), 00561 /*! This flag indicates that the hangup exten should NOT be run when the 00562 * bridge terminates, this will allow the hangup in the pbx loop to be run instead. 00563 * */ 00564 AST_FLAG_BRIDGE_HANGUP_DONT = (1 << 18), 00565 /*! This flag indicates whether the channel is in the channel list or not. */ 00566 AST_FLAG_IN_CHANNEL_LIST = (1 << 19), 00567 /*! Disable certain workarounds. This reintroduces certain bugs, but allows 00568 * some non-traditional dialplans (like AGI) to continue to function. 00569 */ 00570 AST_FLAG_DISABLE_WORKAROUNDS = (1 << 20), 00571 };
| anonymous enum |
ast_bridge_config flags
Definition at line 574 of file channel.h.
00574 { 00575 AST_FEATURE_PLAY_WARNING = (1 << 0), 00576 AST_FEATURE_REDIRECT = (1 << 1), 00577 AST_FEATURE_DISCONNECT = (1 << 2), 00578 AST_FEATURE_ATXFER = (1 << 3), 00579 AST_FEATURE_AUTOMON = (1 << 4), 00580 AST_FEATURE_PARKCALL = (1 << 5), 00581 AST_FEATURE_AUTOMIXMON = (1 << 6), 00582 AST_FEATURE_NO_H_EXTEN = (1 << 7), 00583 AST_FEATURE_WARNING_ACTIVE = (1 << 8), 00584 };
| anonymous enum |
Definition at line 623 of file channel.h.
00623 { 00624 AST_CDR_TRANSFER = (1 << 0), 00625 AST_CDR_FORWARD = (1 << 1), 00626 AST_CDR_CALLWAIT = (1 << 2), 00627 AST_CDR_CONFERENCE = (1 << 3), 00628 };
| anonymous enum |
Definition at line 630 of file channel.h.
00630 { 00631 /*! Soft hangup by device */ 00632 AST_SOFTHANGUP_DEV = (1 << 0), 00633 /*! Soft hangup for async goto */ 00634 AST_SOFTHANGUP_ASYNCGOTO = (1 << 1), 00635 AST_SOFTHANGUP_SHUTDOWN = (1 << 2), 00636 AST_SOFTHANGUP_TIMEOUT = (1 << 3), 00637 AST_SOFTHANGUP_APPUNLOAD = (1 << 4), 00638 AST_SOFTHANGUP_EXPLICIT = (1 << 5), 00639 AST_SOFTHANGUP_UNBRIDGE = (1 << 6), 00640 };
| enum ast_bridge_result |
Definition at line 163 of file channel.h.
00163 { 00164 AST_BRIDGE_COMPLETE = 0, 00165 AST_BRIDGE_FAILED = -1, 00166 AST_BRIDGE_FAILED_NOWARN = -2, 00167 AST_BRIDGE_RETRY = -3, 00168 };
| enum ast_channel_adsicpe |
Definition at line 345 of file channel.h.
00345 { 00346 AST_ADSI_UNKNOWN, 00347 AST_ADSI_AVAILABLE, 00348 AST_ADSI_UNAVAILABLE, 00349 AST_ADSI_OFFHOOKONLY, 00350 };
| enum ast_channel_state |
ast_channel states
Definition at line 358 of file channel.h.
00358 { 00359 AST_STATE_DOWN, /*!< Channel is down and available */ 00360 AST_STATE_RESERVED, /*!< Channel is down, but reserved */ 00361 AST_STATE_OFFHOOK, /*!< Channel is off hook */ 00362 AST_STATE_DIALING, /*!< Digits (or equivalent) have been dialed */ 00363 AST_STATE_RING, /*!< Line is ringing */ 00364 AST_STATE_RINGING, /*!< Remote end is ringing */ 00365 AST_STATE_UP, /*!< Line is up */ 00366 AST_STATE_BUSY, /*!< Line is busy */ 00367 AST_STATE_DIALING_OFFHOOK, /*!< Digits (or equivalent) have been dialed while offhook */ 00368 AST_STATE_PRERING, /*!< Channel has detected an incoming call and is waiting for ring */ 00369 00370 AST_STATE_MUTE = (1 << 16), /*!< Do not transmit voice data */ 00371 };
| enum ast_t38_state |
Possible T38 states on channels.
Definition at line 376 of file channel.h.
00376 { 00377 T38_STATE_UNAVAILABLE, /*!< T38 is unavailable on this channel or disabled by configuration */ 00378 T38_STATE_UNKNOWN, /*!< The channel supports T38 but the current status is unknown */ 00379 T38_STATE_NEGOTIATING, /*!< T38 is being negotiated */ 00380 T38_STATE_REJECTED, /*!< Remote side has rejected our offer */ 00381 T38_STATE_NEGOTIATED, /*!< T38 established */ 00382 };
| enum channelreloadreason |
Channel reload reasons for manager events at load or reload of configuration.
Definition at line 644 of file channel.h.
00644 { 00645 CHANNEL_MODULE_LOAD, 00646 CHANNEL_MODULE_RELOAD, 00647 CHANNEL_CLI_RELOAD, 00648 CHANNEL_MANAGER_RELOAD, 00649 };
| int __ast_answer | ( | struct ast_channel * | chan, | |
| unsigned int | delay, | |||
| int | cdr_answer | |||
| ) |
Answer a channel, with a selectable delay before returning.
| chan | channel to answer | |
| delay | maximum amount of time to wait for incoming media | |
| cdr_answer | flag to control whether any associated CDR should be marked as 'answered' |
This function answers a channel and handles all necessary call setup functions.
| 0 | on success | |
| non-zero | on failure |
Definition at line 1823 of file channel.c.
References ast_channel::_state, ast_channel_lock, ast_channel_unlock, AST_CONTROL_HANGUP, ast_debug, AST_FRAME_CNG, AST_FRAME_CONTROL, AST_FRAME_DTMF_BEGIN, AST_FRAME_DTMF_END, AST_FRAME_HTML, AST_FRAME_IAX, AST_FRAME_IMAGE, AST_FRAME_MODEM, AST_FRAME_NULL, AST_FRAME_TEXT, AST_FRAME_VIDEO, AST_FRAME_VOICE, ast_frfree, ast_frisolate(), AST_LIST_HEAD_INIT_NOLOCK, AST_LIST_HEAD_NOLOCK, AST_LIST_INSERT_HEAD, AST_LIST_REMOVE_HEAD, ast_log(), ast_queue_frame_head(), ast_raw_answer(), ast_read(), AST_STATE_RING, AST_STATE_RINGING, ast_waitfor(), errno, frames, ast_frame::frametype, LOG_WARNING, MAX, and ast_frame::subclass.
Referenced by ast_answer(), dial_exec_full(), pbx_builtin_answer(), and pbx_builtin_incomplete().
01824 { 01825 int res = 0; 01826 enum ast_channel_state old_state; 01827 01828 old_state = chan->_state; 01829 if ((res = ast_raw_answer(chan, cdr_answer))) { 01830 return res; 01831 } 01832 01833 switch (old_state) { 01834 case AST_STATE_RINGING: 01835 case AST_STATE_RING: 01836 /* wait for media to start flowing, but don't wait any longer 01837 * than 'delay' or 500 milliseconds, whichever is longer 01838 */ 01839 do { 01840 AST_LIST_HEAD_NOLOCK(, ast_frame) frames; 01841 struct ast_frame *cur, *new; 01842 int ms = MAX(delay, 500); 01843 unsigned int done = 0; 01844 01845 AST_LIST_HEAD_INIT_NOLOCK(&frames); 01846 01847 for (;;) { 01848 ms = ast_waitfor(chan, ms); 01849 if (ms < 0) { 01850 ast_log(LOG_WARNING, "Error condition occurred when polling channel %s for a voice frame: %s\n", chan->name, strerror(errno)); 01851 res = -1; 01852 break; 01853 } 01854 if (ms == 0) { 01855 ast_debug(2, "Didn't receive a media frame from %s within %d ms of answering. Continuing anyway\n", chan->name, MAX(delay, 500)); 01856 break; 01857 } 01858 cur = ast_read(chan); 01859 if (!cur || ((cur->frametype == AST_FRAME_CONTROL) && 01860 (cur->subclass == AST_CONTROL_HANGUP))) { 01861 if (cur) { 01862 ast_frfree(cur); 01863 } 01864 res = -1; 01865 ast_debug(2, "Hangup of channel %s detected in answer routine\n", chan->name); 01866 break; 01867 } 01868 01869 if ((new = ast_frisolate(cur)) != cur) { 01870 ast_frfree(cur); 01871 } 01872 01873 AST_LIST_INSERT_HEAD(&frames, new, frame_list); 01874 01875 /* if a specific delay period was requested, continue 01876 * until that delay has passed. don't stop just because 01877 * incoming media has arrived. 01878 */ 01879 if (delay) { 01880 continue; 01881 } 01882 01883 switch (new->frametype) { 01884 /* all of these frametypes qualify as 'media' */ 01885 case AST_FRAME_VOICE: 01886 case AST_FRAME_VIDEO: 01887 case AST_FRAME_TEXT: 01888 case AST_FRAME_DTMF_BEGIN: 01889 case AST_FRAME_DTMF_END: 01890 case AST_FRAME_IMAGE: 01891 case AST_FRAME_HTML: 01892 case AST_FRAME_MODEM: 01893 done = 1; 01894 break; 01895 case AST_FRAME_CONTROL: 01896 case AST_FRAME_IAX: 01897 case AST_FRAME_NULL: 01898 case AST_FRAME_CNG: 01899 break; 01900 } 01901 01902 if (done) { 01903 break; 01904 } 01905 } 01906 01907 if (res == 0) { 01908 ast_channel_lock(chan); 01909 while ((cur = AST_LIST_REMOVE_HEAD(&frames, frame_list))) { 01910 ast_queue_frame_head(chan, cur); 01911 ast_frfree(cur); 01912 } 01913 ast_channel_unlock(chan); 01914 } 01915 } while (0); 01916 break; 01917 default: 01918 break; 01919 } 01920 01921 return res; 01922 }
| struct ast_channel* attribute_malloc __ast_channel_alloc | ( | int | needqueue, | |
| int | state, | |||
| const char * | cid_num, | |||
| const char * | cid_name, | |||
| const char * | acctcode, | |||
| const char * | exten, | |||
| const char * | context, | |||
| const int | amaflag, | |||
| const char * | file, | |||
| int | line, | |||
| const char * | function, | |||
| const char * | name_fmt, | |||
| ... | ||||
| ) | [read] |
Create a channel structure.
| NULL | failure | |
| non-NULL | successfully allocated channel |
Definition at line 967 of file channel.c.
References __ast_channel_alloc_ap().
00972 { 00973 va_list ap1, ap2; 00974 struct ast_channel *result; 00975 00976 va_start(ap1, name_fmt); 00977 va_start(ap2, name_fmt); 00978 result = __ast_channel_alloc_ap(needqueue, state, cid_num, cid_name, acctcode, exten, context, 00979 amaflag, file, line, function, name_fmt, ap1, ap2); 00980 va_end(ap1); 00981 va_end(ap2); 00982 00983 return result; 00984 }
| struct ast_channel* __ast_request_and_dial | ( | const char * | type, | |
| int | format, | |||
| void * | data, | |||
| int | timeout, | |||
| int * | reason, | |||
| const char * | cid_num, | |||
| const char * | cid_name, | |||
| struct outgoing_helper * | oh | |||
| ) | [read] |
Request a channel of a given type, with data as optional information used by the low level module and attempt to place a call on it.
| type | type of channel to request | |
| format | requested channel format | |
| data | data to pass to the channel requester | |
| timeout | maximum amount of time to wait for an answer | |
| reason | why unsuccessful (if unsuccessful) | |
| cid_num | Caller-ID Number | |
| cid_name | Caller-ID Name (ascii) | |
| oh | Outgoing helper |
Definition at line 3823 of file channel.c.
References ast_channel::_state, outgoing_helper::account, ast_call(), ast_call_forward(), AST_CAUSE_NO_ANSWER, ast_cdr_alloc(), ast_cdr_disposition(), ast_cdr_end(), ast_cdr_failed(), AST_CDR_FLAG_ORIGINATED, ast_cdr_init(), ast_cdr_setaccount(), ast_cdr_setapp(), ast_cdr_start(), ast_cdr_update(), ast_channel_datastore_inherit(), ast_channel_inherit_variables(), AST_CONTROL_ANSWER, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_HANGUP, AST_CONTROL_HOLD, AST_CONTROL_PROCEEDING, AST_CONTROL_PROGRESS, AST_CONTROL_RINGING, AST_CONTROL_SRCUPDATE, AST_CONTROL_UNHOLD, AST_CONTROL_VIDUPDATE, ast_copy_string(), AST_FRAME_CONTROL, ast_frfree, ast_hangup(), ast_log(), ast_read(), ast_request(), ast_set_callerid(), ast_set_flag, ast_set_variables(), AST_STATE_UP, ast_strlen_zero(), ast_waitfor(), ast_channel::cdr, outgoing_helper::cid_name, outgoing_helper::cid_num, ast_channel::context, outgoing_helper::context, ast_channel::exten, outgoing_helper::exten, f, ast_frame::frametype, handle_cause(), ast_channel::hangupcause, LOG_NOTICE, outgoing_helper::parent_channel, ast_channel::priority, outgoing_helper::priority, ast_frame::subclass, and outgoing_helper::vars.
Referenced by ast_pbx_outgoing_app(), ast_pbx_outgoing_exten(), ast_request_and_dial(), and parkandannounce_exec().
03824 { 03825 int dummy_outstate; 03826 int cause = 0; 03827 struct ast_channel *chan; 03828 int res = 0; 03829 int last_subclass = 0; 03830 03831 if (outstate) 03832 *outstate = 0; 03833 else 03834 outstate = &dummy_outstate; /* make outstate always a valid pointer */ 03835 03836 chan = ast_request(type, format, data, &cause); 03837 if (!chan) { 03838 ast_log(LOG_NOTICE, "Unable to request channel %s/%s\n", type, (char *)data); 03839 handle_cause(cause, outstate); 03840 return NULL; 03841 } 03842 03843 if (oh) { 03844 if (oh->vars) 03845 ast_set_variables(chan, oh->vars); 03846 /* XXX why is this necessary, for the parent_channel perhaps ? */ 03847 if (!ast_strlen_zero(oh->cid_num) && !ast_strlen_zero(oh->cid_name)) 03848 ast_set_callerid(chan, oh->cid_num, oh->cid_name, oh->cid_num); 03849 if (oh->parent_channel) { 03850 ast_channel_inherit_variables(oh->parent_channel, chan); 03851 ast_channel_datastore_inherit(oh->parent_channel, chan); 03852 } 03853 if (oh->account) 03854 ast_cdr_setaccount(chan, oh->account); 03855 } 03856 ast_set_callerid(chan, cid_num, cid_name, cid_num); 03857 ast_set_flag(chan->cdr, AST_CDR_FLAG_ORIGINATED); 03858 03859 if (ast_call(chan, data, 0)) { /* ast_call failed... */ 03860 ast_log(LOG_NOTICE, "Unable to call channel %s/%s\n", type, (char *)data); 03861 } else { 03862 res = 1; /* mark success in case chan->_state is already AST_STATE_UP */ 03863 while (timeout && chan->_state != AST_STATE_UP) { 03864 struct ast_frame *f; 03865 res = ast_waitfor(chan, timeout); 03866 if (res == 0) { /* timeout, treat it like ringing */ 03867 *outstate = AST_CONTROL_RINGING; 03868 break; 03869 } 03870 if (res < 0) /* error or done */ 03871 break; 03872 if (timeout > -1) 03873 timeout = res; 03874 if (!ast_strlen_zero(chan->call_forward)) { 03875 if (!(chan = ast_call_forward(NULL, chan, &timeout, format, oh, outstate))) { 03876 return NULL; 03877 } 03878 continue; 03879 } 03880 03881 f = ast_read(chan); 03882 if (!f) { 03883 *outstate = AST_CONTROL_HANGUP; 03884 res = 0; 03885 break; 03886 } 03887 if (f->frametype == AST_FRAME_CONTROL) { 03888 switch (f->subclass) { 03889 case AST_CONTROL_RINGING: /* record but keep going */ 03890 *outstate = f->subclass; 03891 break; 03892 03893 case AST_CONTROL_BUSY: 03894 case AST_CONTROL_CONGESTION: 03895 case AST_CONTROL_ANSWER: 03896 *outstate = f->subclass; 03897 timeout = 0; /* trick to force exit from the while() */ 03898 break; 03899 03900 /* Ignore these */ 03901 case AST_CONTROL_PROGRESS: 03902 case AST_CONTROL_PROCEEDING: 03903 case AST_CONTROL_HOLD: 03904 case AST_CONTROL_UNHOLD: 03905 case AST_CONTROL_VIDUPDATE: 03906 case AST_CONTROL_SRCUPDATE: 03907 case -1: /* Ignore -- just stopping indications */ 03908 break; 03909 03910 default: 03911 ast_log(LOG_NOTICE, "Don't know what to do with control frame %d\n", f->subclass); 03912 } 03913 last_subclass = f->subclass; 03914 } 03915 ast_frfree(f); 03916 } 03917 } 03918 03919 /* Final fixups */ 03920 if (oh) { 03921 if (!ast_strlen_zero(oh->context)) 03922 ast_copy_string(chan->context, oh->context, sizeof(chan->context)); 03923 if (!ast_strlen_zero(oh->exten)) 03924 ast_copy_string(chan->exten, oh->exten, sizeof(chan->exten)); 03925 if (oh->priority) 03926 chan->priority = oh->priority; 03927 } 03928 if (chan->_state == AST_STATE_UP) 03929 *outstate = AST_CONTROL_ANSWER; 03930 03931 if (res <= 0) { 03932 if ( AST_CONTROL_RINGING == last_subclass ) 03933 chan->hangupcause = AST_CAUSE_NO_ANSWER; 03934 if (!chan->cdr && (chan->cdr = ast_cdr_alloc())) 03935 ast_cdr_init(chan->cdr, chan); 03936 if (chan->cdr) { 03937 char tmp[256]; 03938 snprintf(tmp, sizeof(tmp), "%s/%s", type, (char *)data); 03939 ast_cdr_setapp(chan->cdr,"Dial",tmp); 03940 ast_cdr_update(chan); 03941 ast_cdr_start(chan->cdr); 03942 ast_cdr_end(chan->cdr); 03943 /* If the cause wasn't handled properly */ 03944 if (ast_cdr_disposition(chan->cdr,chan->hangupcause)) 03945 ast_cdr_failed(chan->cdr); 03946 } 03947 ast_hangup(chan); 03948 chan = NULL; 03949 } 03950 return chan; 03951 }
| int ast_activate_generator | ( | struct ast_channel * | chan, | |
| struct ast_generator * | gen, | |||
| void * | params | |||
| ) |
Activate a given generator
Definition at line 1974 of file channel.c.
References ast_generator::alloc, ast_channel_lock, ast_channel_unlock, ast_prod(), ast_settimeout(), ast_channel::generator, generator_force(), ast_channel::generatordata, and ast_generator::release.
Referenced by app_exec(), ast_channel_start_silence_generator(), ast_linear_stream(), ast_playtones_start(), ast_tonepair_start(), channel_spy(), eivr_comm(), local_ast_moh_start(), old_milliwatt_exec(), and transmit_audio().
01975 { 01976 int res = 0; 01977 01978 ast_channel_lock(chan); 01979 01980 if (chan->generatordata) { 01981 if (chan->generator && chan->generator->release) 01982 chan->generator->release(chan, chan->generatordata); 01983 chan->generatordata = NULL; 01984 } 01985 01986 ast_prod(chan); 01987 if (gen->alloc && !(chan->generatordata = gen->alloc(chan, params))) { 01988 res = -1; 01989 } 01990 01991 if (!res) { 01992 ast_settimeout(chan, 50, generator_force, chan); 01993 chan->generator = gen; 01994 } 01995 01996 ast_channel_unlock(chan); 01997 01998 return res; 01999 }
| int ast_active_channels | ( | void | ) |
returns number of active/allocated channels
Returns number of active/allocated channels
Definition at line 498 of file channel.c.
References AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, and channels.
Referenced by action_corestatus(), dahdi_restart(), handle_show_settings(), and quit_handler().
00499 { 00500 struct ast_channel *c; 00501 int cnt = 0; 00502 AST_RWLIST_RDLOCK(&channels); 00503 AST_RWLIST_TRAVERSE(&channels, c, chan_list) 00504 cnt++; 00505 AST_RWLIST_UNLOCK(&channels); 00506 return cnt; 00507 }
| static int ast_add_fd | ( | struct pollfd * | pfd, | |
| int | fd | |||
| ) | [inline, static] |
if fd is a valid descriptor, set *pfd with the descriptor
Definition at line 1664 of file channel.h.
Referenced by ast_waitfor_nandfds().
| int ast_answer | ( | struct ast_channel * | chan | ) |
Answer a channel.
| chan | channel to answer |
This function answers a channel and handles all necessary call setup functions.
| 0 | on success | |
| non-zero | on failure |
Definition at line 1924 of file channel.c.
References __ast_answer().
Referenced by action_bridge(), agi_exec_full(), alarmreceiver_exec(), answer_trunk_chan(), app_exec(), ast_control_streamfile(), ast_pickup_call(), auth_exec(), background_detect_exec(), bridge_exec(), builtin_parkcall(), common_exec(), conf_exec(), count_exec(), dahdiras_exec(), dictate_exec(), directory_exec(), disa_exec(), eivr_comm(), handle_answer(), ices_exec(), login_exec(), minivm_accmess_exec(), minivm_greet_exec(), minivm_record_exec(), old_milliwatt_exec(), park_call_exec(), park_exec_full(), pbx_builtin_background(), pickup_do(), playback_exec(), privacy_exec(), read_exec(), readexten_exec(), record_exec(), rpt_exec(), sayunixtime_exec(), send_waveform_to_channel(), setup_privacy_args(), skel_exec(), sla_station_exec(), speech_background(), testclient_exec(), testserver_exec(), transmit(), vm_exec(), vm_execmain(), waitfor_exec(), and zapateller_exec().
01925 { 01926 return __ast_answer(chan, 0, 1); 01927 }
| int ast_autoservice_start | ( | struct ast_channel * | chan | ) |
Automatically service a channel for us...
| 0 | success | |
| -1 | failure, or the channel is already being autoserviced |
Definition at line 192 of file autoservice.c.
References as_cond, ast_calloc, ast_channel_lock, ast_channel_unlock, ast_cond_signal(), AST_FLAG_END_DTMF_ONLY, AST_LIST_EMPTY, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_REMOVE, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), ast_pthread_create_background, AST_PTHREADT_NULL, ast_set_flag, ast_test_flag, asthread, autoservice_run(), asent::chan, free, LOG_WARNING, asent::orig_end_dtmf_flag, and asent::use_count.
Referenced by _macro_exec(), acf_curl_exec(), acf_odbc_read(), acf_odbc_write(), ast_dtmf_stream(), ast_get_enum(), ast_get_srv(), ast_get_txt(), bridge_playfile(), builtin_atxfer(), builtin_automixmonitor(), builtin_blindtransfer(), conf_play(), dial_exec_full(), feature_exec_app(), function_realtime_read(), function_realtime_readdestroy(), function_realtime_store(), function_realtime_write(), lock_read(), lua_autoservice_start(), lua_get_variable_value(), lua_pbx_exec(), lua_set_variable(), lua_set_variable_value(), osplookup_exec(), pbx_find_extension(), play_message_in_bridged_call(), shell_helper(), sla_station_exec(), smdi_msg_retrieve_read(), system_exec_helper(), try_calling(), and trylock_read().
00193 { 00194 int res = 0; 00195 struct asent *as; 00196 00197 AST_LIST_LOCK(&aslist); 00198 AST_LIST_TRAVERSE(&aslist, as, list) { 00199 if (as->chan == chan) { 00200 as->use_count++; 00201 break; 00202 } 00203 } 00204 AST_LIST_UNLOCK(&aslist); 00205 00206 if (as) { 00207 /* Entry exists, autoservice is already handling this channel */ 00208 return 0; 00209 } 00210 00211 if (!(as = ast_calloc(1, sizeof(*as)))) 00212 return -1; 00213 00214 /* New entry created */ 00215 as->chan = chan; 00216 as->use_count = 1; 00217 00218 ast_channel_lock(chan); 00219 as->orig_end_dtmf_flag = ast_test_flag(chan, AST_FLAG_END_DTMF_ONLY) ? 1 : 0; 00220 if (!as->orig_end_dtmf_flag) 00221 ast_set_flag(chan, AST_FLAG_END_DTMF_ONLY); 00222 ast_channel_unlock(chan); 00223 00224 AST_LIST_LOCK(&aslist); 00225 00226 if (AST_LIST_EMPTY(&aslist) && asthread != AST_PTHREADT_NULL) { 00227 ast_cond_signal(&as_cond); 00228 } 00229 00230 AST_LIST_INSERT_HEAD(&aslist, as, list); 00231 00232 if (asthread == AST_PTHREADT_NULL) { /* need start the thread */ 00233 if (ast_pthread_create_background(&asthread, NULL, autoservice_run, NULL)) { 00234 ast_log(LOG_WARNING, "Unable to create autoservice thread :(\n"); 00235 /* There will only be a single member in the list at this point, 00236 the one we just added. */ 00237 AST_LIST_REMOVE(&aslist, as, list); 00238 free(as); 00239 asthread = AST_PTHREADT_NULL; 00240 res = -1; 00241 } else { 00242 pthread_kill(asthread, SIGURG); 00243 } 00244 } 00245 00246 AST_LIST_UNLOCK(&aslist); 00247 00248 return res; 00249 }
| int ast_autoservice_stop | ( | struct ast_channel * | chan | ) |
Stop servicing a channel for us...
| 0 | success | |
| -1 | error, or the channel has been hungup |
Definition at line 251 of file autoservice.c.
References ast_channel::_softhangup, as_chan_list_state, ast_channel_lock, ast_channel_unlock, ast_clear_flag, AST_FLAG_END_DTMF_ONLY, ast_frfree, AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_REMOVE_HEAD, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, AST_PTHREADT_NULL, ast_queue_frame_head(), asthread, asent::chan, f, free, asent::orig_end_dtmf_flag, and asent::use_count.
Referenced by _macro_exec(), acf_curl_exec(), acf_odbc_read(), acf_odbc_write(), array(), ast_dtmf_stream(), ast_get_enum(), ast_get_srv(), ast_get_txt(), ast_hangup(), bridge_playfile(), builtin_atxfer(), builtin_automixmonitor(), conf_play(), dial_exec_full(), feature_exec_app(), finishup(), function_realtime_read(), function_realtime_readdestroy(), function_realtime_store(), function_realtime_write(), lock_read(), lua_autoservice_stop(), lua_get_variable_value(), lua_pbx_exec(), lua_set_variable(), lua_set_variable_value(), osplookup_exec(), pbx_find_extension(), play_message_in_bridged_call(), shell_helper(), sla_station_exec(), smdi_msg_retrieve_read(), system_exec_helper(), try_calling(), and trylock_read().
00252 { 00253 int res = -1; 00254 struct asent *as, *removed = NULL; 00255 struct ast_frame *f; 00256 int chan_list_state; 00257 00258 AST_LIST_LOCK(&aslist); 00259 00260 /* Save the autoservice channel list state. We _must_ verify that the channel 00261 * list has been rebuilt before we return. Because, after we return, the channel 00262 * could get destroyed and we don't want our poor autoservice thread to step on 00263 * it after its gone! */ 00264 chan_list_state = as_chan_list_state; 00265 00266 /* Find the entry, but do not free it because it still can be in the 00267 autoservice thread array */ 00268 AST_LIST_TRAVERSE_SAFE_BEGIN(&aslist, as, list) { 00269 if (as->chan == chan) { 00270 as->use_count--; 00271 if (as->use_count < 1) { 00272 AST_LIST_REMOVE_CURRENT(list); 00273 removed = as; 00274 } 00275 break; 00276 } 00277 } 00278 AST_LIST_TRAVERSE_SAFE_END; 00279 00280 if (removed && asthread != AST_PTHREADT_NULL) { 00281 pthread_kill(asthread, SIGURG); 00282 } 00283 00284 AST_LIST_UNLOCK(&aslist); 00285 00286 if (!removed) { 00287 return 0; 00288 } 00289 00290 /* Wait while autoservice thread rebuilds its list. */ 00291 while (chan_list_state == as_chan_list_state) { 00292 usleep(1000); 00293 } 00294 00295 /* Now autoservice thread should have no references to our entry 00296 and we can safely destroy it */ 00297 00298 if (!chan->_softhangup) { 00299 res = 0; 00300 } 00301 00302 if (!as->orig_end_dtmf_flag) { 00303 ast_clear_flag(chan, AST_FLAG_END_DTMF_ONLY); 00304 } 00305 00306 ast_channel_lock(chan); 00307 while ((f = AST_LIST_REMOVE_HEAD(&as->deferred_frames, frame_list))) { 00308 ast_queue_frame_head(chan, f); 00309 ast_frfree(f); 00310 } 00311 ast_channel_unlock(chan); 00312 00313 free(as); 00314 00315 return res; 00316 }
| void ast_begin_shutdown | ( | int | hangup | ) |
Initiate system shutdown.
Initiate system shutdown -- prevents new channels from being allocated. If "hangup" is non-zero, all existing channels will receive soft hangups
Definition at line 484 of file channel.c.
References AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_softhangup(), AST_SOFTHANGUP_SHUTDOWN, and channels.
Referenced by quit_handler().
00485 { 00486 struct ast_channel *c; 00487 shutting_down = 1; 00488 if (hangup) { 00489 AST_RWLIST_RDLOCK(&channels); 00490 AST_RWLIST_TRAVERSE(&channels, c, chan_list) { 00491 ast_softhangup(c, AST_SOFTHANGUP_SHUTDOWN); 00492 } 00493 AST_RWLIST_UNLOCK(&channels); 00494 } 00495 }
| int ast_best_codec | ( | int | fmts | ) |
Pick the best audio codec.
Pick the best codec
Okay, ulaw is used by all telephony equipment, so start with it
Unless of course, you're a silly European, so then prefer ALAW
G.722 is better then all below, but not as common as the above... so give ulaw and alaw priority
Okay, well, signed linear is easy to translate into other stuff
G.726 is standard ADPCM, in RFC3551 packing order
G.726 is standard ADPCM, in AAL2 packing order
ADPCM has great sound quality and is still pretty easy to translate
Okay, we're down to vocoders now, so pick GSM because it's small and easier to translate and sounds pretty good
iLBC is not too bad
Speex is free, but computationally more expensive than GSM
Ick, LPC10 sounds terrible, but at least we have code for it, if you're tacky enough to use it
G.729a is faster than 723 and slightly less expensive
Down to G.723.1 which is proprietary but at least designed for voice
Definition at line 712 of file channel.c.
References ARRAY_LEN, AST_FORMAT_ADPCM, AST_FORMAT_ALAW, AST_FORMAT_AUDIO_MASK, AST_FORMAT_G722, AST_FORMAT_G723_1, AST_FORMAT_G726, AST_FORMAT_G726_AAL2, AST_FORMAT_G729A, AST_FORMAT_GSM, AST_FORMAT_ILBC, AST_FORMAT_LPC10, AST_FORMAT_SLINEAR, AST_FORMAT_SLINEAR16, AST_FORMAT_SPEEX, AST_FORMAT_ULAW, ast_log(), LOG_WARNING, and prefs.
Referenced by __oh323_new(), agent_call(), ast_codec_choose(), ast_iax2_new(), ast_speech_new(), builtin_atxfer(), echo_exec(), findmeexec(), gtalk_new(), handle_open_receive_channel_ack_message(), iax2_request(), jingle_new(), local_new(), login_exec(), mgcp_new(), sip_new(), skinny_new(), skinny_set_rtp_peer(), socket_process(), start_rtp(), transmit_connect(), and unistim_new().
00713 { 00714 /* This just our opinion, expressed in code. We are asked to choose 00715 the best codec to use, given no information */ 00716 int x; 00717 static const int prefs[] = 00718 { 00719 /*! Okay, ulaw is used by all telephony equipment, so start with it */ 00720 AST_FORMAT_ULAW, 00721 /*! Unless of course, you're a silly European, so then prefer ALAW */ 00722 AST_FORMAT_ALAW, 00723 /*! G.722 is better then all below, but not as common as the above... so give ulaw and alaw priority */ 00724 AST_FORMAT_G722, 00725 /*! Okay, well, signed linear is easy to translate into other stuff */ 00726 AST_FORMAT_SLINEAR16, 00727 AST_FORMAT_SLINEAR, 00728 /*! G.726 is standard ADPCM, in RFC3551 packing order */ 00729 AST_FORMAT_G726, 00730 /*! G.726 is standard ADPCM, in AAL2 packing order */ 00731 AST_FORMAT_G726_AAL2, 00732 /*! ADPCM has great sound quality and is still pretty easy to translate */ 00733 AST_FORMAT_ADPCM, 00734 /*! Okay, we're down to vocoders now, so pick GSM because it's small and easier to 00735 translate and sounds pretty good */ 00736 AST_FORMAT_GSM, 00737 /*! iLBC is not too bad */ 00738 AST_FORMAT_ILBC, 00739 /*! Speex is free, but computationally more expensive than GSM */ 00740 AST_FORMAT_SPEEX, 00741 /*! Ick, LPC10 sounds terrible, but at least we have code for it, if you're tacky enough 00742 to use it */ 00743 AST_FORMAT_LPC10, 00744 /*! G.729a is faster than 723 and slightly less expensive */ 00745 AST_FORMAT_G729A, 00746 /*! Down to G.723.1 which is proprietary but at least designed for voice */ 00747 AST_FORMAT_G723_1, 00748 }; 00749 00750 /* Strip out video */ 00751 fmts &= AST_FORMAT_AUDIO_MASK; 00752 00753 /* Find the first preferred codec in the format given */ 00754 for (x = 0; x < ARRAY_LEN(prefs); x++) { 00755 if (fmts & prefs[x]) 00756 return prefs[x]; 00757 } 00758 00759 ast_log(LOG_WARNING, "Don't know any of 0x%x formats\n", fmts); 00760 00761 return 0; 00762 }
| struct ast_channel* ast_bridged_channel | ( | struct ast_channel * | chan | ) | [read] |
Find bridged channel.
| chan | Current channel |
Definition at line 4705 of file channel.c.
References ast_channel::_bridge, ast_channel_tech::bridged_channel, and ast_channel::tech.
Referenced by __dahdi_exception(), action_agents(), action_coreshowchannels(), agents_show(), agents_show_online(), ast_bridge_call(), ast_channel_masquerade(), ast_park_call_full(), ast_rtp_set_vars(), attempt_transfer(), cb_events(), channel_spy(), check_bridge(), common_exec(), console_transfer(), create_jb(), dahdi_handle_event(), dahdi_hangup(), export_aoc_vars(), get_refer_info(), handle_chanlist(), handle_hd_hf(), handle_invite_replaces(), handle_request(), handle_request_bye(), handle_request_info(), handle_request_refer(), handle_showchan(), handle_soft_key_event_message(), handle_stimulus_message(), key_call(), key_dial_page(), local_attended_transfer(), mgcp_hangup(), mgcp_ss(), misdn_attempt_transfer(), mixmonitor_thread(), schedule_delivery(), sip_hangup(), sip_set_rtp_peer(), skinny_transfer(), socket_process(), ss_thread(), start_spying(), startmon(), TransferCallStep1(), and unistim_hangup().
04706 { 04707 struct ast_channel *bridged; 04708 bridged = chan->_bridge; 04709 if (bridged && bridged->tech->bridged_channel) 04710 bridged = bridged->tech->bridged_channel(chan, bridged); 04711 return bridged; 04712 }
| int ast_call | ( | struct ast_channel * | chan, | |
| char * | addr, | |||
| int | timeout | |||
| ) |
Make a call.
| chan | which channel to make the call on | |
| addr | destination of the call | |
| timeout | time to wait on for connect Place a call, take no longer than timeout ms. |
Definition at line 4014 of file channel.c.
References AST_CDR_FLAG_DIALED, AST_CDR_FLAG_ORIGINATED, ast_channel_lock, ast_channel_unlock, ast_check_hangup(), AST_FLAG_OUTGOING, AST_FLAG_ZOMBIE, ast_set_flag, ast_test_flag, ast_channel_tech::call, ast_channel::cdr, and ast_channel::tech.
Referenced by __ast_request_and_dial(), agent_call(), ast_call_forward(), ast_feature_request_and_dial(), attempt_reconnect(), begin_dial_channel(), connect_link(), dial_exec_full(), do_forward(), do_idle_thread(), findmeexec(), ring_entry(), rpt(), rpt_exec(), and wait_for_answer().
04015 { 04016 /* Place an outgoing call, but don't wait any longer than timeout ms before returning. 04017 If the remote end does not answer within the timeout, then do NOT hang up, but 04018 return anyway. */ 04019 int res = -1; 04020 /* Stop if we're a zombie or need a soft hangup */ 04021 ast_channel_lock(chan); 04022 if (!ast_test_flag(chan, AST_FLAG_ZOMBIE) && !ast_check_hangup(chan)) { 04023 if (chan->cdr) { 04024 ast_set_flag(chan->cdr, AST_CDR_FLAG_DIALED); 04025 ast_set_flag(chan->cdr, AST_CDR_FLAG_ORIGINATED); 04026 } 04027 if (chan->tech->call) 04028 res = chan->tech->call(chan, addr, timeout); 04029 ast_set_flag(chan, AST_FLAG_OUTGOING); 04030 } 04031 ast_channel_unlock(chan); 04032 return res; 04033 }
| struct ast_channel* ast_call_forward | ( | struct ast_channel * | caller, | |
| struct ast_channel * | orig, | |||
| int * | timeout, | |||
| int | format, | |||
| struct outgoing_helper * | oh, | |||
| int * | outstate | |||
| ) | [read] |
Forwards a call to a new channel specified by the original channel's call_forward str. If possible, the new forwarded channel is created and returned while the original one is terminated.
| caller | in channel that requested orig | |
| orig | channel being replaced by the call forward channel | |
| timeout | maximum amount of time to wait for setup of new forward channel | |
| format | requested channel format | |
| oh | outgoing helper used with original channel | |
| outstate | reason why unsuccessful (if uncuccessful) |
Definition at line 3751 of file channel.c.
References outgoing_helper::account, accountcode, ast_call(), AST_CDR_FLAG_ORIGINATED, ast_cdr_setaccount(), ast_channel_datastore_inherit(), ast_channel_inherit_variables(), ast_channel_lock, ast_channel_trylock, ast_channel_unlock, ast_copy_flags, ast_copy_string(), ast_hangup(), ast_log(), ast_request(), ast_set_callerid(), ast_set_variables(), ast_string_field_set, ast_strlen_zero(), ast_channel::cdr, CHANNEL_DEADLOCK_AVOIDANCE, ast_channel::cid, ast_callerid::cid_name, outgoing_helper::cid_name, ast_callerid::cid_num, outgoing_helper::cid_num, ast_channel::context, handle_cause(), LOG_NOTICE, outgoing_helper::parent_channel, pbx_builtin_getvar_helper(), S_OR, type, and outgoing_helper::vars.
Referenced by __ast_request_and_dial(), and ast_feature_request_and_dial().
03752 { 03753 char tmpchan[256]; 03754 struct ast_channel *new = NULL; 03755 char *data, *type; 03756 int cause = 0; 03757 03758 /* gather data and request the new forward channel */ 03759 ast_copy_string(tmpchan, orig->call_forward, sizeof(tmpchan)); 03760 if ((data = strchr(tmpchan, '/'))) { 03761 *data++ = '\0'; 03762 type = tmpchan; 03763 } else { 03764 const char *forward_context; 03765 ast_channel_lock(orig); 03766 forward_context = pbx_builtin_getvar_helper(orig, "FORWARD_CONTEXT"); 03767 snprintf(tmpchan, sizeof(tmpchan), "%s@%s", orig->call_forward, S_OR(forward_context, orig->context)); 03768 ast_channel_unlock(orig); 03769 data = tmpchan; 03770 type = "Local"; 03771 } 03772 if (!(new = ast_request(type, format, data, &cause))) { 03773 ast_log(LOG_NOTICE, "Unable to create channel for call forward to '%s/%s' (cause = %d)\n", type, data, cause); 03774 handle_cause(cause, outstate); 03775 ast_hangup(orig); 03776 return NULL; 03777 } 03778 03779 /* Copy/inherit important information into new channel */ 03780 if (oh) { 03781 if (oh->vars) { 03782 ast_set_variables(new, oh->vars); 03783 } 03784 if (!ast_strlen_zero(oh->cid_num) && !ast_strlen_zero(oh->cid_name)) { 03785 ast_set_callerid(new, oh->cid_num, oh->cid_name, oh->cid_num); 03786 } 03787 if (oh->parent_channel) { 03788 ast_channel_inherit_variables(oh->parent_channel, new); 03789 ast_channel_datastore_inherit(oh->parent_channel, new); 03790 } 03791 if (oh->account) { 03792 ast_cdr_setaccount(new, oh->account); 03793 } 03794 } else if (caller) { /* no outgoing helper so use caller if avaliable */ 03795 ast_channel_inherit_variables(caller, new); 03796 ast_channel_datastore_inherit(caller, new); 03797 } 03798 03799 ast_channel_lock(orig); 03800 while (ast_channel_trylock(new)) { 03801 CHANNEL_DEADLOCK_AVOIDANCE(orig); 03802 } 03803 ast_copy_flags(new->cdr, orig->cdr, AST_CDR_FLAG_ORIGINATED); 03804 ast_string_field_set(new, accountcode, orig->accountcode); 03805 if (!ast_strlen_zero(orig->cid.cid_num) && !ast_strlen_zero(new->cid.cid_name)) { 03806 ast_set_callerid(new, orig->cid.cid_num, orig->cid.cid_name, orig->cid.cid_num); 03807 } 03808 ast_channel_unlock(new); 03809 ast_channel_unlock(orig); 03810 03811 /* call new channel */ 03812 if ((*timeout = ast_call(new, data, 0))) { 03813 ast_log(LOG_NOTICE, "Unable to call forward to channel %s/%s\n", type, (char *)data); 03814 ast_hangup(orig); 03815 ast_hangup(new); 03816 return NULL; 03817 } 03818 ast_hangup(orig); 03819 03820 return new; 03821 }
| void ast_cancel_shutdown | ( | void | ) |
Cancel a shutdown in progress.
Cancels an existing shutdown and returns to normal operation
Definition at line 510 of file channel.c.
Referenced by handle_abort_shutdown().
00511 { 00512 shutting_down = 0; 00513 }
| const char* ast_cause2str | ( | int | state | ) |
Gives the string form of a given hangup cause.
Gives the string form of a given cause code
| state | cause to get the description of Give a name to a cause code Returns the text form of the binary cause code given |
Definition at line 630 of file channel.c.
References ARRAY_LEN, causes, and ast_cause::desc.
Referenced by __transmit_response(), ast_do_masquerade(), ast_hangup(), dial_exec_full(), findmeexec(), sip_hangup(), and transmit_request_with_auth().
| void ast_change_name | ( | struct ast_channel * | chan, | |
| char * | newname | |||
| ) |
Change channel name.
Definition at line 4268 of file channel.c.
References ast_string_field_set, EVENT_FLAG_CALL, manager_event, and name.
Referenced by update_name().
04269 { 04270 manager_event(EVENT_FLAG_CALL, "Rename", "Channel: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", chan->name, newname, chan->uniqueid); 04271 ast_string_field_set(chan, name, newname); 04272 }
| int ast_channel_bridge | ( | struct ast_channel * | c0, | |
| struct ast_channel * | c1, | |||
| struct ast_bridge_config * | config, | |||
| struct ast_frame ** | fo, | |||
| struct ast_channel ** | rc | |||
| ) |
Bridge two channels together.
Bridge two channels together
| c0 | first channel to bridge | |
| c1 | second channel to bridge | |
| config | config for the channels | |
| fo | destination frame(?) | |
| rc | destination channel(?) Bridge two channels (c0 and c1) together. If an important frame occurs, we return that frame in rf (remember, it could be NULL) and which channel (0 or 1) in rc |
Definition at line 5027 of file channel.c.
References ast_channel::_bridge, ast_channel::_softhangup, AST_BRIDGE_COMPLETE, AST_BRIDGE_FAILED, AST_BRIDGE_FAILED_NOWARN, AST_BRIDGE_RETRY, ast_channel_make_compatible(), ast_check_hangup(), ast_check_hangup_locked(), ast_clear_flag, AST_CONTROL_SRCUPDATE, ast_debug, AST_FEATURE_PLAY_WARNING, AST_FEATURE_WARNING_ACTIVE, AST_FLAG_END_DTMF_ONLY, AST_FLAG_NBRIDGE, AST_FLAG_ZOMBIE, ast_generic_bridge(), ast_indicate(), ast_log(), ast_samp2tv(), ast_set_flag, AST_SOFTHANGUP_UNBRIDGE, ast_test_flag, ast_tvadd(), ast_tvdiff_ms(), ast_tvnow(), ast_tvsub(), ast_tvzero(), ast_verb, ast_channel::audiohooks, ast_channel_tech::bridge, bridge_play_sounds(), bridge_playfile(), ast_channel::cid, ast_callerid::cid_num, ast_bridge_config::end_sound, EVENT_FLAG_CALL, ast_bridge_config::feature_timer, ast_bridge_config::features_callee, ast_bridge_config::features_caller, ast_bridge_config::firstpass, ast_bridge_config::flags, ast_channel::generator, LOG_WARNING, manager_bridge_event(), manager_event, ast_channel::masq, ast_channel::masqr, ast_channel::monitor, ast_channel::nativeformats, ast_bridge_config::nexteventts, ast_bridge_config::play_warning, ast_channel::readformat, ast_channel_tech::send_digit_begin, ast_bridge_config::start_sound, ast_bridge_config::start_time, ast_channel::tech, ast_bridge_config::timelimit, update_bridge_vars(), ast_bridge_config::warning_freq, ast_bridge_config::warning_sound, and ast_channel::writeformat.
Referenced by ast_bridge_call().
05029 { 05030 struct ast_channel *who = NULL; 05031 enum ast_bridge_result res = AST_BRIDGE_COMPLETE; 05032 int nativefailed=0; 05033 int firstpass; 05034 int o0nativeformats; 05035 int o1nativeformats; 05036 long time_left_ms=0; 05037 char caller_warning = 0; 05038 char callee_warning = 0; 05039 05040 if (c0->_bridge) { 05041 ast_log(LOG_WARNING, "%s is already in a bridge with %s\n", 05042 c0->name, c0->_bridge->name); 05043 return -1; 05044 } 05045 if (c1->_bridge) { 05046 ast_log(LOG_WARNING, "%s is already in a bridge with %s\n", 05047 c1->name, c1->_bridge->name); 05048 return -1; 05049 } 05050 05051 /* Stop if we're a zombie or need a soft hangup */ 05052 if (ast_test_flag(c0, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c0) || 05053 ast_test_flag(c1, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c1)) 05054 return -1; 05055 05056 *fo = NULL; 05057 firstpass = config->firstpass; 05058 config->firstpass = 0; 05059 05060 if (ast_tvzero(config->start_time)) 05061 config->start_time = ast_tvnow(); 05062 time_left_ms = config->timelimit; 05063 05064 caller_warning = ast_test_flag(&config->features_caller, AST_FEATURE_PLAY_WARNING); 05065 callee_warning = ast_test_flag(&config->features_callee, AST_FEATURE_PLAY_WARNING); 05066 05067 if (config->start_sound && firstpass) { 05068 if (caller_warning) 05069 bridge_playfile(c0, c1, config->start_sound, time_left_ms / 1000); 05070 if (callee_warning) 05071 bridge_playfile(c1, c0, config->start_sound, time_left_ms / 1000); 05072 } 05073 05074 /* Keep track of bridge */ 05075 c0->_bridge = c1; 05076 c1->_bridge = c0; 05077 05078 05079 o0nativeformats = c0->nativeformats; 05080 o1nativeformats = c1->nativeformats; 05081 05082 if (config->feature_timer && !ast_tvzero(config->nexteventts)) { 05083 config->nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->feature_timer, 1000)); 05084 } else if (config->timelimit && firstpass) { 05085 config->nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->timelimit, 1000)); 05086 if (caller_warning || callee_warning) 05087 config->nexteventts = ast_tvsub(config->nexteventts, ast_samp2tv(config->play_warning, 1000)); 05088 } 05089 05090 if (!c0->tech->send_digit_begin) 05091 ast_set_flag(c1, AST_FLAG_END_DTMF_ONLY); 05092 if (!c1->tech->send_digit_begin) 05093 ast_set_flag(c0, AST_FLAG_END_DTMF_ONLY); 05094 manager_bridge_event(1, 1, c0, c1); 05095 05096 /* Before we enter in and bridge these two together tell them both the source of audio has changed */ 05097 ast_indicate(c0, AST_CONTROL_SRCUPDATE); 05098 ast_indicate(c1, AST_CONTROL_SRCUPDATE); 05099 05100 for (/* ever */;;) { 05101 struct timeval now = { 0, }; 05102 int to; 05103 05104 to = -1; 05105 05106 if (!ast_tvzero(config->nexteventts)) { 05107 now = ast_tvnow(); 05108 to = ast_tvdiff_ms(config->nexteventts, now); 05109 if (to <= 0) { 05110 if (!config->timelimit) { 05111 res = AST_BRIDGE_COMPLETE; 05112 break; 05113 } 05114 to = 0; 05115 } 05116 } 05117 05118 if (config->timelimit) { 05119 time_left_ms = config->timelimit - ast_tvdiff_ms(now, config->start_time); 05120 if (time_left_ms < to) 05121 to = time_left_ms; 05122 05123 if (time_left_ms <= 0) { 05124 if (caller_warning && config->end_sound) 05125 bridge_playfile(c0, c1, config->end_sound, 0); 05126 if (callee_warning && config->end_sound) 05127 bridge_playfile(c1, c0, config->end_sound, 0); 05128 *fo = NULL; 05129 if (who) 05130 *rc = who; 05131 res = 0; 05132 break; 05133 } 05134 05135 if (!to) { 05136 if (time_left_ms >= 5000 && config->warning_sound && config->play_warning && ast_test_flag(config, AST_FEATURE_WARNING_ACTIVE)) { 05137 int t = (time_left_ms + 500) / 1000; /* round to nearest second */ 05138 if (caller_warning) 05139 bridge_playfile(c0, c1, config->warning_sound, t); 05140 if (callee_warning) 05141 bridge_playfile(c1, c0, config->warning_sound, t); 05142 } 05143 if (config->warning_freq && (time_left_ms > (config->warning_freq + 5000))) 05144 config->nexteventts = ast_tvadd(config->nexteventts, ast_samp2tv(config->warning_freq, 1000)); 05145 else 05146 config->nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->timelimit, 1000)); 05147 } 05148 ast_clear_flag(config, AST_FEATURE_WARNING_ACTIVE); 05149 } 05150 05151 if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE || c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE) { 05152 if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE) 05153 c0->_softhangup = 0; 05154 if (c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE) 05155 c1->_softhangup = 0; 05156 c0->_bridge = c1; 05157 c1->_bridge = c0; 05158 ast_debug(1, "Unbridge signal received. Ending native bridge.\n"); 05159 continue; 05160 } 05161 05162 /* Stop if we're a zombie or need a soft hangup */ 05163 if (ast_test_flag(c0, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c0) || 05164 ast_test_flag(c1, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c1)) { 05165 *fo = NULL; 05166 if (who) 05167 *rc = who; 05168 res = 0; 05169 ast_debug(1, "Bridge stops because we're zombie or need a soft hangup: c0=%s, c1=%s, flags: %s,%s,%s,%s\n", 05170 c0->name, c1->name, 05171 ast_test_flag(c0, AST_FLAG_ZOMBIE) ? "Yes" : "No", 05172 ast_check_hangup(c0) ? "Yes" : "No", 05173 ast_test_flag(c1, AST_FLAG_ZOMBIE) ? "Yes" : "No", 05174 ast_check_hangup(c1) ? "Yes" : "No"); 05175 break; 05176 } 05177 05178 update_bridge_vars(c0, c1); 05179 05180 bridge_play_sounds(c0, c1); 05181 05182 if (c0->tech->bridge && 05183 (c0->tech->bridge == c1->tech->bridge) && 05184 !nativefailed && !c0->monitor && !c1->monitor && 05185 !c0->audiohooks && !c1->audiohooks && 05186 !c0->masq && !c0->masqr && !c1->masq && !c1->masqr) { 05187 /* Looks like they share a bridge method and nothing else is in the way */ 05188 ast_set_flag(c0, AST_FLAG_NBRIDGE); 05189 ast_set_flag(c1, AST_FLAG_NBRIDGE); 05190 if ((res = c0->tech->bridge(c0, c1, config->flags, fo, rc, to)) == AST_BRIDGE_COMPLETE) { 05191 /* \todo XXX here should check that cid_num is not NULL */ 05192 manager_event(EVENT_FLAG_CALL, "Unlink", 05193 "Channel1: %s\r\n" 05194 "Channel2: %s\r\n" 05195 "Uniqueid1: %s\r\n" 05196 "Uniqueid2: %s\r\n" 05197 "CallerID1: %s\r\n" 05198 "CallerID2: %s\r\n", 05199 c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num); 05200 ast_debug(1, "Returning from native bridge, channels: %s, %s\n", c0->name, c1->name); 05201 05202 ast_clear_flag(c0, AST_FLAG_NBRIDGE); 05203 ast_clear_flag(c1, AST_FLAG_NBRIDGE); 05204 05205 if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE || c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE) 05206 continue; 05207 05208 c0->_bridge = NULL; 05209 c1->_bridge = NULL; 05210 05211 return res; 05212 } else { 05213 ast_clear_flag(c0, AST_FLAG_NBRIDGE); 05214 ast_clear_flag(c1, AST_FLAG_NBRIDGE); 05215 } 05216 switch (res) { 05217 case AST_BRIDGE_RETRY: 05218 if (config->play_warning) { 05219 ast_set_flag(config, AST_FEATURE_WARNING_ACTIVE); 05220 } 05221 continue; 05222 default: 05223 ast_verb(3, "Native bridging %s and %s ended\n", c0->name, c1->name); 05224 /* fallthrough */ 05225 case AST_BRIDGE_FAILED_NOWARN: 05226 nativefailed++; 05227 break; 05228 } 05229 } 05230 05231 if (((c0->writeformat != c1->readformat) || (c0->readformat != c1->writeformat) || 05232 (c0->nativeformats != o0nativeformats) || (c1->nativeformats != o1nativeformats)) && 05233 !(c0->generator || c1->generator)) { 05234 if (ast_channel_make_compatible(c0, c1)) { 05235 ast_log(LOG_WARNING, "Can't make %s and %s compatible\n", c0->name, c1->name); 05236 manager_bridge_event(0, 1, c0, c1); 05237 return AST_BRIDGE_FAILED; 05238 } 05239 o0nativeformats = c0->nativeformats; 05240 o1nativeformats = c1->nativeformats; 05241 } 05242 05243 update_bridge_vars(c0, c1); 05244 05245 res = ast_generic_bridge(c0, c1, config, fo, rc, config->nexteventts); 05246 if (res != AST_BRIDGE_RETRY) { 05247 break; 05248 } else if (config->feature_timer) { 05249 /* feature timer expired but has not been updated, sending to ast_bridge_call to do so */ 05250 break; 05251 } 05252 } 05253 05254 ast_clear_flag(c0, AST_FLAG_END_DTMF_ONLY); 05255 ast_clear_flag(c1, AST_FLAG_END_DTMF_ONLY); 05256 05257 /* Now that we have broken the bridge the source will change yet again */ 05258 ast_indicate(c0, AST_CONTROL_SRCUPDATE); 05259 ast_indicate(c1, AST_CONTROL_SRCUPDATE); 05260 05261 c0->_bridge = NULL; 05262 c1->_bridge = NULL; 05263 05264 /* \todo XXX here should check that cid_num is not NULL */ 05265 manager_event(EVENT_FLAG_CALL, "Unlink", 05266 "Channel1: %s\r\n" 05267 "Channel2: %s\r\n" 05268 "Uniqueid1: %s\r\n" 05269 "Uniqueid2: %s\r\n" 05270 "CallerID1: %s\r\n" 05271 "CallerID2: %s\r\n", 05272 c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num); 05273 ast_debug(1, "Bridge stops bridging channels %s and %s\n", c0->name, c1->name); 05274 05275 return res; 05276 }
| int ast_channel_cmpwhentohangup | ( | struct ast_channel * | chan, | |
| time_t | offset | |||
| ) |
Compare a offset with the settings of when to hang a channel up.
| chan | channel on which to check for hang up | |
| offset | offset in seconds from current time |
Definition at line 551 of file channel.c.
References ast_channel_cmpwhentohangup_tv().
00552 { 00553 struct timeval when = { offset, }; 00554 return ast_channel_cmpwhentohangup_tv(chan, when); 00555 }
| int ast_channel_cmpwhentohangup_tv | ( | struct ast_channel * | chan, | |
| struct timeval | offset | |||
| ) |
Compare a offset with the settings of when to hang a channel up.
| chan | channel on which to check for hangup | |
| offset | offset in seconds and microseconds from current time |
Definition at line 536 of file channel.c.
References ast_tvadd(), ast_tvdiff_ms(), ast_tvnow(), ast_tvzero(), and ast_channel::whentohangup.
Referenced by ast_channel_cmpwhentohangup().
00537 { 00538 struct timeval whentohangup; 00539 00540 if (ast_tvzero(chan->whentohangup)) 00541 return ast_tvzero(offset) ? 0 : -1; 00542 00543 if (ast_tvzero(offset)) 00544 return 1; 00545 00546 whentohangup = ast_tvadd(offset, ast_tvnow()); 00547 00548 return ast_tvdiff_ms(whentohangup, chan->whentohangup); 00549 }
| int ast_channel_datastore_add | ( | struct ast_channel * | chan, | |
| struct ast_datastore * | datastore | |||
| ) |
Add a datastore to a channel.
| 0 | success | |
| non-zero | failure |
Definition at line 1507 of file channel.c.
References AST_LIST_INSERT_HEAD.
Referenced by _macro_exec(), acf_iaxvar_write(), acf_odbc_read(), add_features_datastores(), add_to_agi(), ast_iax2_new(), audiohook_volume_get(), authenticate_reply(), dial_exec_full(), dundi_query_read(), enable_jack_hook(), enum_query_read(), get_lock(), gosub_exec(), lua_get_state(), pbx_builtin_raise_exception(), setup_chanspy_ds(), setup_inheritance_datastore(), setup_mixmonitor_ds(), setup_transfer_datastore(), shared_write(), smdi_msg_retrieve_read(), socket_process(), speech_create(), speex_write(), try_calling(), and volume_write().
01508 { 01509 int res = 0; 01510 01511 AST_LIST_INSERT_HEAD(&chan->datastores, datastore, entry); 01512 01513 return res; 01514 }
| struct ast_datastore* attribute_malloc ast_channel_datastore_alloc | ( | const struct ast_datastore_info * | info, | |
| const char * | uid | |||
| ) | [read] |
Create a channel data store object.
Definition at line 1480 of file channel.c.
References ast_datastore_alloc.
01481 { 01482 return ast_datastore_alloc(info, uid); 01483 }
| struct ast_datastore* ast_channel_datastore_find | ( | struct ast_channel * | chan, | |
| const struct ast_datastore_info * | info, | |||
| const char * | uid | |||
| ) | [read] |
Find a datastore on a channel.
| pointer | to the datastore if found | |
| NULL | if not found |
Definition at line 1521 of file channel.c.
References AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, ast_datastore::info, and ast_datastore::uid.
Referenced by _macro_exec(), acf_exception_read(), acf_fetch(), acf_iaxvar_read(), acf_iaxvar_write(), add_agi_cmd(), add_features_datastores(), add_to_agi(), attended_transfer_occurred(), audiohook_volume_callback(), audiohook_volume_get(), builtin_atxfer(), chanspy_ds_free(), dial_exec_full(), disable_jack_hook(), dundi_result_read(), enable_jack_hook(), enum_result_read(), exec_odbcfinish(), find_speech(), func_inheritance_write(), get_agi_cmd(), get_lock(), gosub_exec(), handle_gosub(), iax2_call(), jack_hook_callback(), local_read(), local_write(), lock_fixup(), lua_get_state(), manage_parkinglot(), park_exec_full(), pbx_builtin_raise_exception(), pop_exec(), queue_transfer_fixup(), return_exec(), shared_read(), shared_write(), smdi_msg_read(), speech_background(), speech_destroy(), speex_callback(), speex_read(), speex_write(), stop_mixmonitor_exec(), try_calling(), unlock_read(), volume_callback(), and volume_write().
01522 { 01523 struct ast_datastore *datastore = NULL; 01524 01525 if (info == NULL) 01526 return NULL; 01527 01528 AST_LIST_TRAVERSE_SAFE_BEGIN(&chan->datastores, datastore, entry) { 01529 if (datastore->info != info) { 01530 continue; 01531 } 01532 01533 if (uid == NULL) { 01534 /* matched by type only */ 01535 break; 01536 } 01537 01538 if ((datastore->uid != NULL) && !strcasecmp(uid, datastore->uid)) { 01539 /* Matched by type AND uid */ 01540 break; 01541 } 01542 } 01543 AST_LIST_TRAVERSE_SAFE_END; 01544 01545 return datastore; 01546 }
| int ast_channel_datastore_free | ( | struct ast_datastore * | datastore | ) |
Free a channel data store object.
Definition at line 1485 of file channel.c.
References ast_datastore_free().
01486 { 01487 return ast_datastore_free(datastore); 01488 }
| int ast_channel_datastore_inherit | ( | struct ast_channel * | from, | |
| struct ast_channel * | to | |||
| ) |
Inherit datastores from a parent to a child.
Definition at line 1490 of file channel.c.
References ast_datastore_alloc, AST_LIST_INSERT_TAIL, AST_LIST_TRAVERSE, ast_datastore::data, DATASTORE_INHERIT_FOREVER, ast_datastore_info::duplicate, ast_datastore::info, ast_datastore::inheritance, and ast_datastore::uid.
Referenced by __ast_request_and_dial(), ast_call_forward(), dial_exec_full(), do_forward(), findmeexec(), local_call(), ring_entry(), and wait_for_answer().
01491 { 01492 struct ast_datastore *datastore = NULL, *datastore2; 01493 01494 AST_LIST_TRAVERSE(&from->datastores, datastore, entry) { 01495 if (datastore->inheritance > 0) { 01496 datastore2 = ast_datastore_alloc(datastore->info, datastore->uid); 01497 if (datastore2) { 01498 datastore2->data = datastore->info->duplicate ? datastore->info->duplicate(datastore->data) : NULL; 01499 datastore2->inheritance = datastore->inheritance == DATASTORE_INHERIT_FOREVER ? DATASTORE_INHERIT_FOREVER : datastore->inheritance - 1; 01500 AST_LIST_INSERT_TAIL(&to->datastores, datastore2, entry); 01501 } 01502 } 01503 } 01504 return 0; 01505 }
| int ast_channel_datastore_remove | ( | struct ast_channel * | chan, | |
| struct ast_datastore * | datastore | |||
| ) |
Remove a datastore from a channel.
| 0 | success | |
| non-zero | failure |
Definition at line 1516 of file channel.c.
References AST_LIST_REMOVE.
Referenced by acf_fetch(), chanspy_ds_free(), dial_exec_full(), disable_jack_hook(), exec_odbcfinish(), lua_get_state(), queue_transfer_fixup(), speech_background(), speech_destroy(), speex_write(), stop_mixmonitor_exec(), and try_calling().
01517 { 01518 return AST_LIST_REMOVE(&chan->datastores, datastore, entry) ? 0 : -1; 01519 }
| int ast_channel_defer_dtmf | ( | struct ast_channel * | chan | ) |
Set defer DTMF flag on channel.
Defers DTMF
Defer DTMF so that you only read things like hangups and audio. Returns non-zero if channel was already DTMF-deferred or 0 if channel is just now being DTMF-deferred
Definition at line 1141 of file channel.c.
References AST_FLAG_DEFER_DTMF, ast_set_flag, and ast_test_flag.
Referenced by __adsi_transmit_messages(), and find_cache().
01142 { 01143 int pre = 0; 01144 01145 if (chan) { 01146 pre = ast_test_flag(chan, AST_FLAG_DEFER_DTMF); 01147 ast_set_flag(chan, AST_FLAG_DEFER_DTMF); 01148 } 01149 return pre; 01150 }
| int ast_channel_early_bridge | ( | struct ast_channel * | c0, | |
| struct ast_channel * | c1 | |||
| ) |
Bridge two channels together (early).
Bridge two channels together (early)
| c0 | first channel to bridge | |
| c1 | second channel to bridge Bridge two channels (c0 and c1) together early. This implies either side may not be answered yet. |
Definition at line 4929 of file channel.c.
References ast_channel_tech::early_bridge, and ast_channel::tech.
Referenced by dial_exec_full(), and wait_for_answer().
04930 { 04931 /* Make sure we can early bridge, if not error out */ 04932 if (!c0->tech->early_bridge || (c1 && (!c1->tech->early_bridge || c0->tech->early_bridge != c1->tech->early_bridge))) 04933 return -1; 04934 04935 return c0->tech->early_bridge(c0, c1); 04936 }
| void ast_channel_free | ( | struct ast_channel * | ) |
Free a channel structure.
Definition at line 1365 of file channel.c.
References ast_channel::alertpipe, ast_app_group_discard(), ast_cdr_discard(), ast_channel_lock, AST_CHANNEL_NAME, ast_channel_unlock, ast_copy_string(), ast_datastore_free(), ast_debug, AST_DEVICE_UNKNOWN, ast_devstate_changed_literal(), AST_FLAG_IN_CHANNEL_LIST, ast_free, ast_frfree, ast_jb_destroy(), AST_LIST_REMOVE_HEAD, ast_log(), AST_MAX_FDS, ast_moh_cleanup(), ast_mutex_destroy(), AST_RWLIST_REMOVE, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_string_field_free_memory, ast_test_flag, ast_timer_close(), ast_translator_free_path(), ast_var_delete(), ast_channel::cdr, channels, ast_channel::cid, f, free, free_cid(), ast_channel::lock_dont_use, LOG_WARNING, ast_channel::monitor, ast_channel::music_state, name, ast_channel::pbx, ast_channel::readtrans, ast_channel::sched, sched_context_destroy(), ast_channel_monitor::stop, ast_channel::tech_pvt, ast_channel::timer, ast_channel::varshead, and ast_channel::writetrans.
Referenced by acf_odbc_read(), acf_odbc_write(), action_getvar(), agent_cleanup(), agent_new(), ast_do_masquerade(), ast_hangup(), ast_iax2_new(), ast_pbx_outgoing_cdr_failed(), gtalk_newcall(), local_new(), make_email_file(), pbx_substitute_variables_helper_full(), rotate_file(), sendmail(), and sendpage().
01366 { 01367 int fd; 01368 #ifdef HAVE_EPOLL 01369 int i; 01370 #endif 01371 struct ast_var_t *vardata; 01372 struct ast_frame *f; 01373 struct varshead *headp; 01374 struct ast_datastore *datastore = NULL; 01375 char name[AST_CHANNEL_NAME], *dashptr; 01376 int inlist; 01377 01378 headp=&chan->varshead; 01379 01380 inlist = ast_test_flag(chan, AST_FLAG_IN_CHANNEL_LIST); 01381 if (inlist) { 01382 AST_RWLIST_WRLOCK(&channels); 01383 if (!AST_RWLIST_REMOVE(&channels, chan, chan_list)) { 01384 ast_debug(1, "Unable to find channel in list to free. Assuming it has already been done.\n"); 01385 } 01386 /* Lock and unlock the channel just to be sure nobody has it locked still 01387 due to a reference retrieved from the channel list. */ 01388 ast_channel_lock(chan); 01389 ast_channel_unlock(chan); 01390 } 01391 01392 /* Get rid of each of the data stores on the channel */ 01393 ast_channel_lock(chan); 01394 while ((datastore = AST_LIST_REMOVE_HEAD(&chan->datastores, entry))) 01395 /* Free the data store */ 01396 ast_datastore_free(datastore); 01397 ast_channel_unlock(chan); 01398 01399 /* Lock and unlock the channel just to be sure nobody has it locked still 01400 due to a reference that was stored in a datastore. (i.e. app_chanspy) */ 01401 ast_channel_lock(chan); 01402 ast_channel_unlock(chan); 01403 01404 if (chan->tech_pvt) { 01405 ast_log(LOG_WARNING, "Channel '%s' may not have been hung up properly\n", chan->name); 01406 ast_free(chan->tech_pvt); 01407 } 01408 01409 if (chan->sched) 01410 sched_context_destroy(chan->sched); 01411 01412 ast_copy_string(name, chan->name, sizeof(name)); 01413 if ((dashptr = strrchr(name, '-'))) { 01414 *dashptr = '\0'; 01415 } 01416 01417 /* Stop monitoring */ 01418 if (chan->monitor) 01419 chan->monitor->stop( chan, 0 ); 01420 01421 /* If there is native format music-on-hold state, free it */ 01422 if (chan->music_state) 01423 ast_moh_cleanup(chan); 01424 01425 /* Free translators */ 01426 if (chan->readtrans) 01427 ast_translator_free_path(chan->readtrans); 01428 if (chan->writetrans) 01429 ast_translator_free_path(chan->writetrans); 01430 if (chan->pbx) 01431 ast_log(LOG_WARNING, "PBX may not have been terminated properly on '%s'\n", chan->name); 01432 free_cid(&chan->cid); 01433 /* Close pipes if appropriate */ 01434 if ((fd = chan->alertpipe[0]) > -1) 01435 close(fd); 01436 if ((fd = chan->alertpipe[1]) > -1) 01437 close(fd); 01438 if (chan->timer) { 01439 ast_timer_close(chan->timer); 01440 } 01441 #ifdef HAVE_EPOLL 01442 for (i = 0; i < AST_MAX_FDS; i++) { 01443 if (chan->epfd_data[i]) 01444 free(chan->epfd_data[i]); 01445 } 01446 close(chan->epfd); 01447 #endif 01448 while ((f = AST_LIST_REMOVE_HEAD(&chan->readq, frame_list))) 01449 ast_frfree(f); 01450 01451 /* loop over the variables list, freeing all data and deleting list items */ 01452 /* no need to lock the list, as the channel is already locked */ 01453 01454 while ((vardata = AST_LIST_REMOVE_HEAD(headp, entries))) 01455 ast_var_delete(vardata); 01456 01457 ast_app_group_discard(chan); 01458 01459 /* Destroy the jitterbuffer */ 01460 ast_jb_destroy(chan); 01461 01462 if (chan->cdr) { 01463 ast_cdr_discard(chan->cdr); 01464 chan->cdr = NULL; 01465 } 01466 01467 ast_mutex_destroy(&chan->lock_dont_use); 01468 01469 ast_string_field_free_memory(chan); 01470 ast_free(chan); 01471 if (inlist) 01472 AST_RWLIST_UNLOCK(&channels); 01473 01474 /* Queue an unknown state, because, while we know that this particular 01475 * instance is dead, we don't know the state of all other possible 01476 * instances. */ 01477 ast_devstate_changed_literal(AST_DEVICE_UNKNOWN, name); 01478 }
| static enum ast_t38_state ast_channel_get_t38_state | ( | struct ast_channel * | chan | ) | [inline, static] |
Retrieves the current T38 state of a channel.
Definition at line 1740 of file channel.h.
References ast_channel_queryoption(), AST_OPTION_T38_STATE, and T38_STATE_UNAVAILABLE.
Referenced by transmit(), transmit_audio(), and transmit_t38().
01741 { 01742 enum ast_t38_state state = T38_STATE_UNAVAILABLE; 01743 int datalen = sizeof(state); 01744 01745 ast_channel_queryoption(chan, AST_OPTION_T38_STATE, &state, &datalen, 0); 01746 01747 return state; 01748 }
| void ast_channel_inherit_variables | ( | const struct ast_channel * | parent, | |
| struct ast_channel * | child | |||
| ) |
Inherits channel variable from parent to child channel.
| parent | Parent channel | |
| child | Child channel |
Scans all channel variables in the parent channel, looking for those that should be copied into the child channel. Variables whose names begin with a single '_' are copied into the child channel with the prefix removed. Variables whose names begin with '__' are copied into the child channel with their names unchanged.
Definition at line 4274 of file channel.c.
References ast_debug, AST_LIST_INSERT_TAIL, AST_LIST_TRAVERSE, ast_var_assign(), ast_var_full_name(), ast_var_name(), ast_var_value(), and ast_channel::varshead.
Referenced by __ast_request_and_dial(), agent_call(), ast_call_forward(), ast_feature_request_and_dial(), begin_dial_channel(), dial_exec_full(), do_forward(), findmeexec(), ring_entry(), and wait_for_answer().
04275 { 04276 struct ast_var_t *current, *newvar; 04277 const char *varname; 04278 04279 AST_LIST_TRAVERSE(&parent->varshead, current, entries) { 04280 int vartype = 0; 04281 04282 varname = ast_var_full_name(current); 04283 if (!varname) 04284 continue; 04285 04286 if (varname[0] == '_') { 04287 vartype = 1; 04288 if (varname[1] == '_') 04289 vartype = 2; 04290 } 04291 04292 switch (vartype) { 04293 case 1: 04294 newvar = ast_var_assign(&varname[1], ast_var_value(current)); 04295 if (newvar) { 04296 AST_LIST_INSERT_TAIL(&child->varshead, newvar, entries); 04297 ast_debug(1, "Copying soft-transferable variable %s.\n", ast_var_name(newvar)); 04298 } 04299 break; 04300 case 2: 04301 newvar = ast_var_assign(varname, ast_var_value(current)); 04302 if (newvar) { 04303 AST_LIST_INSERT_TAIL(&child->varshead, newvar, entries); 04304 ast_debug(1, "Copying hard-transferable variable %s.\n", ast_var_name(newvar)); 04305 } 04306 break; 04307 default: 04308 ast_debug(1, "Not copying variable %s.\n", ast_var_name(current)); 04309 break; 04310 } 04311 } 04312 }
| int ast_channel_make_compatible | ( | struct ast_channel * | c0, | |
| struct ast_channel * | c1 | |||
| ) |
Makes two channel formats compatible.
| c0 | first channel to make compatible | |
| c1 | other channel to make compatible Set two channels to compatible formats -- call before ast_channel_bridge in general . |
Definition at line 4172 of file channel.c.
References ast_channel_make_compatible_helper().
Referenced by action_bridge(), app_exec(), ast_channel_bridge(), bridge_exec(), check_compat(), dial_exec_full(), do_forward(), park_exec_full(), try_calling(), and wait_for_answer().
04173 { 04174 /* Some callers do not check return code, and we must try to set all call legs correctly */ 04175 int rc = 0; 04176 04177 /* Set up translation from the chan to the peer */ 04178 rc = ast_channel_make_compatible_helper(chan, peer); 04179 04180 if (rc < 0) 04181 return rc; 04182 04183 /* Set up translation from the peer to the chan */ 04184 rc = ast_channel_make_compatible_helper(peer, chan); 04185 04186 return rc; 04187 }
| int ast_channel_masquerade | ( | struct ast_channel * | original, | |
| struct ast_channel * | clone | |||
| ) |
Weird function made for call transfers.
| original | channel to make a copy of | |
| clone | copy of the original channel |
This is a very strange and freaky function used primarily for transfer. Suppose that "original" and "clone" are two channels in random situations. This function takes the guts out of "clone" and puts them into the "original" channel, then alerts the channel driver of the change, asking it to fixup any private information (like the p->owner pointer) that is affected by the change. The physical layer of the original channel is hung up.
Definition at line 4189 of file channel.c.
References ast_channel::_bridge, ast_bridged_channel(), ast_channel_lock, ast_channel_trylock, ast_channel_unlock, ast_debug, ast_log(), ast_null_frame, ast_queue_frame(), ast_channel_tech::get_base_channel, LOG_WARNING, ast_channel::masq, ast_channel::masqr, and ast_channel::tech.
Referenced by ast_async_goto(), ast_pickup_call(), attempt_transfer(), builtin_atxfer(), check_availability(), check_bridge(), check_goto_on_transfer(), do_bridge_masquerade(), handle_invite_replaces(), iax_park(), masq_park_call(), misdn_attempt_transfer(), pickup_do(), sip_park(), and skinny_transfer().
04190 { 04191 int res = -1; 04192 struct ast_channel *final_orig, *final_clone, *base; 04193 04194 retrymasq: 04195 final_orig = original; 04196 final_clone = clonechan; 04197 04198 ast_channel_lock(original); 04199 while (ast_channel_trylock(clonechan)) { 04200 ast_channel_unlock(original); 04201 usleep(1); 04202 ast_channel_lock(original); 04203 } 04204 04205 /* each of these channels may be sitting behind a channel proxy (i.e. chan_agent) 04206 and if so, we don't really want to masquerade it, but its proxy */ 04207 if (original->_bridge && (original->_bridge != ast_bridged_channel(original)) && (original->_bridge->_bridge != original)) 04208 final_orig = original->_bridge; 04209 04210 if (clonechan->_bridge && (clonechan->_bridge != ast_bridged_channel(clonechan)) && (clonechan->_bridge->_bridge != clonechan)) 04211 final_clone = clonechan->_bridge; 04212 04213 if (final_clone->tech->get_base_channel && (base = final_clone->tech->get_base_channel(final_clone))) { 04214 final_clone = base; 04215 } 04216 04217 if ((final_orig != original) || (final_clone != clonechan)) { 04218 /* Lots and lots of deadlock avoidance. The main one we're competing with 04219 * is ast_write(), which locks channels recursively, when working with a 04220 * proxy channel. */ 04221 if (ast_channel_trylock(final_orig)) { 04222 ast_channel_unlock(clonechan); 04223 ast_channel_unlock(original); 04224 goto retrymasq; 04225 } 04226 if (ast_channel_trylock(final_clone)) { 04227 ast_channel_unlock(final_orig); 04228 ast_channel_unlock(clonechan); 04229 ast_channel_unlock(original); 04230 goto retrymasq; 04231 } 04232 ast_channel_unlock(clonechan); 04233 ast_channel_unlock(original); 04234 original = final_orig; 04235 clonechan = final_clone; 04236 } 04237 04238 if (original == clonechan) { 04239 ast_log(LOG_WARNING, "Can't masquerade channel '%s' into itself!\n", original->name); 04240 ast_channel_unlock(clonechan); 04241 ast_channel_unlock(original); 04242 return -1; 04243 } 04244 04245 ast_debug(1, "Planning to masquerade channel %s into the structure of %s\n", 04246 clonechan->name, original->name); 04247 if (original->masq) { 04248 ast_log(LOG_WARNING, "%s is already going to masquerade as %s\n", 04249 original->masq->name, original->name); 04250 } else if (clonechan->masqr) { 04251 ast_log(LOG_WARNING, "%s is already going to masquerade as %s\n", 04252 clonechan->name, clonechan->masqr->name); 04253 } else { 04254 original->masq = clonechan; 04255 clonechan->masqr = original; 04256 ast_queue_frame(original, &ast_null_frame); 04257 ast_queue_frame(clonechan, &ast_null_frame); 04258 ast_debug(1, "Done planning to masquerade channel %s into the structure of %s\n", clonechan->name, original->name); 04259 res = 0; 04260 } 04261 04262 ast_channel_unlock(clonechan); 04263 ast_channel_unlock(original); 04264 04265 return res; 04266 }
| int ast_channel_queryoption | ( | struct ast_channel * | channel, | |
| int | option, | |||
| void * | data, | |||
| int * | datalen, | |||
| int | block | |||
| ) |
Checks the value of an option
Query the value of an option Works similarly to setoption except only reads the options.
Definition at line 5292 of file channel.c.
References ast_log(), errno, LOG_ERROR, ast_channel_tech::queryoption, and ast_channel::tech.
Referenced by ast_channel_get_t38_state().
| const char* ast_channel_reason2str | ( | int | reason | ) |
return an english explanation of the code returned thru __ast_request_and_dial's 'outstate' argument
| reason | The integer argument, usually taken from AST_CONTROL_ macros |
Definition at line 3715 of file channel.c.
References AST_CONTROL_ANSWER, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_HANGUP, AST_CONTROL_RING, and AST_CONTROL_RINGING.
Referenced by attempt_thread().
03716 { 03717 switch (reason) /* the following appear to be the only ones actually returned by request_and_dial */ 03718 { 03719 case 0: 03720 return "Call Failure (not BUSY, and not NO_ANSWER, maybe Circuit busy or down?)"; 03721 case AST_CONTROL_HANGUP: 03722 return "Hangup"; 03723 case AST_CONTROL_RING: 03724 return "Local Ring"; 03725 case AST_CONTROL_RINGING: 03726 return "Remote end Ringing"; 03727 case AST_CONTROL_ANSWER: 03728 return "Remote end has Answered"; 03729 case AST_CONTROL_BUSY: 03730 return "Remote end is Busy"; 03731 case AST_CONTROL_CONGESTION: 03732 return "Congestion (circuits busy)"; 03733 default: 03734 return "Unknown Reason!!"; 03735 } 03736 }
| int ast_channel_register | ( | const struct ast_channel_tech * | tech | ) |
Register a channel technology (a new channel driver) Called by a channel module to register the kind of channels it supports.
| tech | Structure defining channel technology or "type" |
Definition at line 558 of file channel.c.
References ast_calloc, ast_debug, AST_LIST_INSERT_HEAD, AST_LIST_TRAVERSE, ast_log(), AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_verb, channels, ast_channel_tech::description, LOG_WARNING, chanlist::tech, and ast_channel_tech::type.
Referenced by load_module(), and unload_module().
00559 { 00560 struct chanlist *chan; 00561 00562 AST_RWLIST_WRLOCK(&channels); 00563 00564 AST_LIST_TRAVERSE(&backends, chan, list) { 00565 if (!strcasecmp(tech->type, chan->tech->type)) { 00566 ast_log(LOG_WARNING, "Already have a handler for type '%s'\n", tech->type); 00567 AST_RWLIST_UNLOCK(&channels); 00568 return -1; 00569 } 00570 } 00571 00572 if (!(chan = ast_calloc(1, sizeof(*chan)))) { 00573 AST_RWLIST_UNLOCK(&channels); 00574 return -1; 00575 } 00576 chan->tech = tech; 00577 AST_LIST_INSERT_HEAD(&backends, chan, list); 00578 00579 ast_debug(1, "Registered handler for '%s' (%s)\n", chan->tech->type, chan->tech->description); 00580 00581 ast_verb(2, "Registered channel type '%s' (%s)\n", chan->tech->type, chan->tech->description); 00582 00583 AST_RWLIST_UNLOCK(&channels); 00584 return 0; 00585 }
| int ast_channel_sendhtml | ( | struct ast_channel * | channel, | |
| int | subclass, | |||
| const char * | data, | |||
| int | datalen | |||
| ) |
Sends HTML on given channel
Send HTML or URL on link. Returns 0 on success or -1 on failure
Definition at line 4118 of file channel.c.
References ast_channel_tech::send_html, and ast_channel::tech.
Referenced by agent_sendhtml(), ast_channel_sendurl(), and wait_for_answer().
| int ast_channel_sendurl | ( | struct ast_channel * | channel, | |
| const char * | url | |||
| ) |
Sends a URL on a given link
Send URL on link. Returns 0 on success or -1 on failure
Definition at line 4125 of file channel.c.
References ast_channel_sendhtml(), and AST_HTML_URL.
Referenced by dial_exec_full(), sendurl_exec(), and try_calling().
04126 { 04127 return ast_channel_sendhtml(chan, AST_HTML_URL, url, strlen(url) + 1); 04128 }
| void ast_channel_set_fd | ( | struct ast_channel * | chan, | |
| int | which, | |||
| int | fd | |||
| ) |
Set the file descriptor on the channel
Definition at line 1549 of file channel.c.
References ast_calloc, ast_epoll_data::chan, ast_channel::fds, free, and ast_epoll_data::which.
Referenced by __ast_channel_alloc_ap(), __oh323_new(), __oh323_rtp_create(), __oh323_update_info(), alsa_new(), ast_deactivate_generator(), ast_do_masquerade(), dahdi_new(), gtalk_new(), jingle_new(), mgcp_new(), misdn_new(), nbs_new(), oss_new(), phone_new(), pri_assign_bearer(), pri_fixup_principle(), setformat(), sip_new(), skinny_new(), start_rtp(), and swap_subs().
01550 { 01551 #ifdef HAVE_EPOLL 01552 struct epoll_event ev; 01553 struct ast_epoll_data *aed = NULL; 01554 01555 if (chan->fds[which] > -1) { 01556 epoll_ctl(chan->epfd, EPOLL_CTL_DEL, chan->fds[which], &ev); 01557 aed = chan->epfd_data[which]; 01558 } 01559 01560 /* If this new fd is valid, add it to the epoll */ 01561 if (fd > -1) { 01562 if (!aed && (!(aed = ast_calloc(1, sizeof(*aed))))) 01563 return; 01564 01565 chan->epfd_data[which] = aed; 01566 aed->chan = chan; 01567 aed->which = which; 01568 01569 ev.events = EPOLLIN | EPOLLPRI | EPOLLERR | EPOLLHUP; 01570 ev.data.ptr = aed; 01571 epoll_ctl(chan->epfd, EPOLL_CTL_ADD, fd, &ev); 01572 } else if (aed) { 01573 /* We don't have to keep around this epoll data structure now */ 01574 free(aed); 01575 chan->epfd_data[which] = NULL; 01576 } 01577 #endif 01578 chan->fds[which] = fd; 01579 return; 01580 }
| int ast_channel_setoption | ( | struct ast_channel * | channel, | |
| int | option, | |||
| void * | data, | |||
| int | datalen, | |||
| int | block | |||
| ) |
Sets an option on a channel.
Sets an option on a channel
| channel | channel to set options on | |
| option | option to change | |
| data | data specific to option | |
| datalen | length of the data | |
| block | blocking or not Set an option on a channel (see frame.h), optionally blocking awaiting the reply Returns 0 on success and -1 on failure |
Definition at line 5279 of file channel.c.
References ast_log(), errno, LOG_ERROR, ast_channel_tech::setoption, and ast_channel::tech.
Referenced by ast_bridge_call(), common_exec(), conf_run(), dahdi_hangup(), dial_exec_full(), func_channel_write(), handle_tddmode(), play_record_review(), reset_volumes(), rpt(), rpt_exec(), set_listen_volume(), set_talk_volume(), try_calling(), and vm_forwardoptions().
| void ast_channel_setwhentohangup | ( | struct ast_channel * | chan, | |
| time_t | offset | |||
| ) |
Set when to hang a channel up.
| chan | channel on which to check for hang up | |
| offset | offset in seconds relative to the current time of when to hang up |
This function sets the absolute time out on a channel (when to hang up).
Definition at line 529 of file channel.c.
References ast_channel_setwhentohangup_tv().
00530 { 00531 struct timeval when = { offset, }; 00532 ast_channel_setwhentohangup_tv(chan, when); 00533 }
| void ast_channel_setwhentohangup_tv | ( | struct ast_channel * | chan, | |
| struct timeval | offset | |||
| ) |
Set when to hang a channel up.
| chan | channel on which to check for hang up | |
| offset | offset in seconds and useconds relative to the current time of when to hang up |
This function sets the absolute time out on a channel (when to hang up).
Definition at line 522 of file channel.c.
References ast_null_frame, ast_queue_frame(), ast_tvadd(), ast_tvnow(), ast_tvzero(), and ast_channel::whentohangup.
Referenced by action_timeout(), ast_channel_setwhentohangup(), handle_autohangup(), and timeout_write().
00523 { 00524 chan->whentohangup = ast_tvzero(offset) ? offset : ast_tvadd(offset, ast_tvnow()); 00525 ast_queue_frame(chan, &ast_null_frame); 00526 return; 00527 }
| struct ast_silence_generator* ast_channel_start_silence_generator | ( | struct ast_channel * | chan | ) | [read] |
Starts a silence generator on the given channel.
| chan | The channel to generate silence on |
This function will cause SLINEAR silence to be generated on the supplied channel until it is disabled; if the channel cannot be put into SLINEAR mode then the function will fail.
The pointer returned by this function must be preserved and passed to ast_channel_stop_silence_generator when you wish to stop the silence generation.
Definition at line 5612 of file channel.c.
References ast_activate_generator(), ast_calloc, ast_debug, AST_FORMAT_SLINEAR, ast_free, ast_log(), ast_set_write_format(), LOG_ERROR, ast_silence_generator::old_write_format, and ast_channel::writeformat.
Referenced by __ast_play_and_record(), ast_dtmf_stream(), ast_safe_sleep_conditional(), channel_spy(), record_exec(), TransferCallStep1(), waitfor_exec(), and waitforring_exec().
05613 { 05614 struct ast_silence_generator *state; 05615 05616 if (!(state = ast_calloc(1, sizeof(*state)))) { 05617 return NULL; 05618 } 05619 05620 state->old_write_format = chan->writeformat; 05621 05622 if (ast_set_write_format(chan, AST_FORMAT_SLINEAR) < 0) { 05623 ast_log(LOG_ERROR, "Could not set write format to SLINEAR\n"); 05624 ast_free(state); 05625 return NULL; 05626 } 05627 05628 ast_activate_generator(chan, &silence_generator, state); 05629 05630 ast_debug(1, "Started silence generator on '%s'\n", chan->name); 05631 05632 return state; 05633 }
| void ast_channel_stop_silence_generator | ( | struct ast_channel * | chan, | |
| struct ast_silence_generator * | state | |||
| ) |
Stops a previously-started silence generator on the given channel.
| chan | The channel to operate on | |
| state | The ast_silence_generator pointer return by a previous call to ast_channel_start_silence_generator. |
This function will stop the operating silence generator and return the channel to its previous write format.
Definition at line 5635 of file channel.c.
References ast_deactivate_generator(), ast_debug, ast_free, ast_log(), ast_set_write_format(), LOG_ERROR, and ast_silence_generator::old_write_format.
Referenced by __ast_play_and_record(), ast_dtmf_stream(), ast_safe_sleep_conditional(), channel_spy(), HandleCallOutgoing(), key_dial_page(), record_exec(), unistim_hangup(), waitfor_exec(), and waitforring_exec().
05636 { 05637 if (!state) 05638 return; 05639 05640 ast_deactivate_generator(chan); 05641 05642 ast_debug(1, "Stopped silence generator on '%s'\n", chan->name); 05643 05644 if (ast_set_write_format(chan, state->old_write_format) < 0) 05645 ast_log(LOG_ERROR, "Could not return write format to its original state\n"); 05646 05647 ast_free(state); 05648 }
| int ast_channel_supports_html | ( | struct ast_channel * | channel | ) |
Checks for HTML support on a channel
Returns 0 if channel does not support HTML or non-zero if it does
Definition at line 4113 of file channel.c.
References ast_channel_tech::send_html, and ast_channel::tech.
Referenced by dial_exec_full(), sendurl_exec(), and try_calling().
| void ast_channel_undefer_dtmf | ( | struct ast_channel * | chan | ) |
Unset defer DTMF flag on channel.
Undo defer. ast_read will return any dtmf characters that were queued
Definition at line 1153 of file channel.c.
References ast_clear_flag, and AST_FLAG_DEFER_DTMF.
Referenced by __adsi_transmit_messages(), find_cache(), and rpt_call().
01154 { 01155 if (chan) 01156 ast_clear_flag(chan, AST_FLAG_DEFER_DTMF); 01157 }
| void ast_channel_unregister | ( | const struct ast_channel_tech * | tech | ) |
Unregister a channel technology.
| tech | Structure defining channel technology or "type" that was previously registered |
Definition at line 588 of file channel.c.
References ast_debug, ast_free, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_verb, channels, chanlist::tech, and ast_channel_tech::type.
Referenced by __unload_module(), load_module(), and unload_module().
00589 { 00590 struct chanlist *chan; 00591 00592 ast_debug(1, "Unregistering channel type '%s'\n", tech->type); 00593 00594 AST_RWLIST_WRLOCK(&channels); 00595 00596 AST_LIST_TRAVERSE_SAFE_BEGIN(&backends, chan, list) { 00597 if (chan->tech == tech) { 00598 AST_LIST_REMOVE_CURRENT(list); 00599 ast_free(chan); 00600 ast_verb(2, "Unregistered channel type '%s'\n", tech->type); 00601 break; 00602 } 00603 } 00604 AST_LIST_TRAVERSE_SAFE_END; 00605 00606 AST_RWLIST_UNLOCK(&channels); 00607 }
| struct ast_channel* ast_channel_walk_locked | ( | const struct ast_channel * | prev | ) | [read] |
Browse channels in use Browse the channels currently in use.
| prev | where you want to start in the channel list |
Definition at line 1267 of file channel.c.
References channel_find_locked().
Referenced by action_coreshowchannels(), action_status(), ast_complete_channels(), ast_pickup_call(), conf_exec(), func_channels_read(), handle_chanlist(), handle_core_set_debug_channel(), next_channel(), pickup_by_exten(), and pickup_by_mark().
01268 { 01269 return channel_find_locked(prev, NULL, 0, NULL, NULL); 01270 }
| struct ast_variable* ast_channeltype_list | ( | void | ) | [read] |
return an ast_variable list of channeltypes
Definition at line 186 of file channel.c.
References AST_LIST_TRAVERSE, ast_variable_new(), ast_channel_tech::description, chanlist::tech, ast_channel_tech::type, and var.
00187 { 00188 struct chanlist *cl; 00189 struct ast_variable *var=NULL, *prev = NULL; 00190 AST_LIST_TRAVERSE(&backends, cl, list) { 00191 if (prev) { 00192 if ((prev->next = ast_variable_new(cl->tech->type, cl->tech->description, ""))) 00193 prev = prev->next; 00194 } else { 00195 var = ast_variable_new(cl->tech->type, cl->tech->description, ""); 00196 prev = var; 00197 } 00198 } 00199 return var; 00200 }
| int ast_check_hangup | ( | struct ast_channel * | chan | ) |
Check to see if a channel is needing hang up.
| chan | channel on which to check for hang up This function determines if the channel is being requested to be hung up. |
Definition at line 462 of file channel.c.
References ast_channel::_softhangup, AST_SOFTHANGUP_TIMEOUT, ast_tvdiff_ms(), ast_tvnow(), ast_tvzero(), and ast_channel::whentohangup.
Referenced by __ast_pbx_run(), __ast_read(), _macro_exec(), action_redirect(), agent_indicate(), agi_exec(), agi_handle_command(), announce_thread(), ast_bridge_call(), ast_bridge_call_thread(), ast_call(), ast_channel_bridge(), ast_check_hangup_locked(), ast_feature_request_and_dial(), ast_indicate_data(), ast_raw_answer(), ast_readstring_full(), ast_recvtext(), ast_rtp_bridge(), ast_sendtext(), ast_transfer(), ast_udptl_bridge(), ast_waitfordigit_full(), ast_write(), autoservice_run(), bridge_exec(), bridge_native_loop(), bridge_p2p_loop(), builtin_atxfer(), channel_spy(), check_bridge(), common_exec(), conf_play(), conf_run(), dahdi_sendtext(), dahdi_setoption(), dial_exec_full(), dundi_lookup_internal(), eagi_exec(), eivr_comm(), findmeexec(), handle_sendimage(), iax2_bridge(), launch_asyncagi(), lua_check_hangup(), ospfinished_exec(), pbx_builtin_incomplete(), pbx_exec(), read_exec(), readexten_exec(), rpt(), rpt_exec(), run_ras(), try_calling(), and wait_for_answer().
00463 { 00464 if (chan->_softhangup) /* yes if soft hangup flag set */ 00465 return 1; 00466 if (ast_tvzero(chan->whentohangup)) /* no if no hangup scheduled */ 00467 return 0; 00468 if (ast_tvdiff_ms(chan->whentohangup, ast_tvnow()) > 0) /* no if hangup time has not come yet. */ 00469 return 0; 00470 chan->_softhangup |= AST_SOFTHANGUP_TIMEOUT; /* record event */ 00471 return 1; 00472 }
| void ast_deactivate_generator | ( | struct ast_channel * | chan | ) |
Deactivate an active generator
Definition at line 1929 of file channel.c.
References ast_channel_lock, ast_channel_set_fd(), ast_channel_unlock, ast_clear_flag, AST_FLAG_WRITE_INT, AST_GENERATOR_FD, ast_settimeout(), ast_channel::generator, ast_channel::generatordata, and ast_generator::release.
Referenced by __ast_read(), app_exec(), ast_channel_stop_silence_generator(), ast_openstream_full(), ast_playtones_stop(), ast_quiet_chan(), ast_read_generator_actions(), ast_tonepair_stop(), ast_write(), cb_events(), channel_spy(), dial_exec_full(), generator_force(), local_ast_moh_stop(), old_milliwatt_exec(), transmit_audio(), and wait_for_answer().
01930 { 01931 ast_channel_lock(chan); 01932 if (chan->generatordata) { 01933 if (chan->generator && chan->generator->release) 01934 chan->generator->release(chan, chan->generatordata); 01935 chan->generatordata = NULL; 01936 chan->generator = NULL; 01937 ast_channel_set_fd(chan, AST_GENERATOR_FD, -1); 01938 ast_clear_flag(chan, AST_FLAG_WRITE_INT); 01939 ast_settimeout(chan, 0, NULL, NULL); 01940 } 01941 ast_channel_unlock(chan); 01942 }
| int ast_do_masquerade | ( | struct ast_channel * | original | ) |
Start masquerading a channel XXX This is a seriously whacked out operation. We're essentially putting the guts of the clone channel into the original channel. Start by killing off the original channel's backend. I'm not sure we're going to keep this function, because while the features are nice, the cost is very high in terms of pure nastiness. XXX.
| chan | Channel to masquerade |
Start masquerading a channel XXX This is a seriously whacked out operation. We're essentially putting the guts of the clone channel into the original channel. Start by killing off the original channel's backend. I'm not sure we're going to keep this function, because while the features are nice, the cost is very high in terms of pure nastiness. XXX.
Definition at line 4365 of file channel.c.
References ast_channel::_softhangup, ast_channel::_state, ast_channel::adsicpe, ast_channel::alertpipe, ast_app_group_update(), ast_cause2str(), ast_channel_free(), ast_channel_lock, AST_CHANNEL_NAME, ast_channel_set_fd(), ast_channel_unlock, ast_copy_string(), ast_debug, AST_FLAG_BLOCKING, AST_FLAG_EXCEPTION, AST_FLAG_OUTGOING, AST_FLAG_ZOMBIE, AST_GENERATOR_FD, ast_indicate(), AST_LIST_APPEND_LIST, AST_LIST_FIRST, AST_LIST_HEAD_NOLOCK, AST_LIST_HEAD_SET_NOLOCK, AST_LIST_INSERT_TAIL, AST_LIST_REMOVE_HEAD, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, ast_log(), AST_MAX_FDS, ast_null_frame, ast_queue_frame(), ast_set_flag, ast_set_read_format(), ast_set_write_format(), AST_SOFTHANGUP_DEV, ast_state2str(), ast_string_field_set, ast_test_flag, AST_TIMING_FD, ast_channel::blocker, ast_channel::cdr, ast_datastore_info::chan_fixup, ast_channel::cid, clone_variables(), ast_datastore::data, errno, EVENT_FLAG_CALL, ast_channel::fdno, ast_channel::fds, ast_channel_tech::fixup, free_translation(), ast_channel_tech::hangup, ast_channel::hangupcause, ast_datastore::info, language, ast_channel::lock_dont_use, LOG_WARNING, manager_event, ast_channel::masq, ast_channel::masqr, ast_channel::monitor, musicclass, name, ast_channel::nativeformats, ast_channel::rawreadformat, ast_channel::rawwriteformat, ast_channel::readformat, report_new_callerid(), ast_channel::tech, ast_channel::tech_pvt, ast_channel::timingfd, ast_channel_tech::type, ast_channel::visible_indication, and ast_channel::writeformat.
Referenced by __ast_read(), ast_async_goto(), ast_hangup(), ast_waitfor_nandfds(), ast_write(), do_bridge_masquerade(), handle_invite_replaces(), iax_park(), sip_park(), and sip_park_thread().
04366 { 04367 int x,i; 04368 int res=0; 04369 int origstate; 04370 struct ast_frame *current; 04371 const struct ast_channel_tech *t; 04372 void *t_pvt; 04373 struct ast_callerid tmpcid; 04374 struct ast_channel *clonechan = original->masq; 04375 struct ast_cdr *cdr; 04376 int rformat = original->readformat; 04377 int wformat = original->writeformat; 04378 char newn[AST_CHANNEL_NAME]; 04379 char orig[AST_CHANNEL_NAME]; 04380 char masqn[AST_CHANNEL_NAME]; 04381 char zombn[AST_CHANNEL_NAME]; 04382 04383 ast_debug(4, "Actually Masquerading %s(%d) into the structure of %s(%d)\n", 04384 clonechan->name, clonechan->_state, original->name, original->_state); 04385 04386 manager_event(EVENT_FLAG_CALL, "Masquerade", "Clone: %s\r\nCloneState: %s\r\nOriginal: %s\r\nOriginalState: %s\r\n", 04387 clonechan->name, ast_state2str(clonechan->_state), original->name, ast_state2str(original->_state)); 04388 04389 /* XXX This operation is a bit odd. We're essentially putting the guts of 04390 * the clone channel into the original channel. Start by killing off the 04391 * original channel's backend. While the features are nice, which is the 04392 * reason we're keeping it, it's still awesomely weird. XXX */ 04393 04394 /* We need the clone's lock, too */ 04395 ast_channel_lock(clonechan); 04396 04397 ast_debug(2, "Got clone lock for masquerade on '%s' at %p\n", clonechan->name, &clonechan->lock_dont_use); 04398 04399 /* Having remembered the original read/write formats, we turn off any translation on either 04400 one */ 04401 free_translation(clonechan); 04402 free_translation(original); 04403 04404 04405 /* Unlink the masquerade */ 04406 original->masq = NULL; 04407 clonechan->masqr = NULL; 04408 04409 /* Save the original name */ 04410 ast_copy_string(orig, original->name, sizeof(orig)); 04411 /* Save the new name */ 04412 ast_copy_string(newn, clonechan->name, sizeof(newn)); 04413 /* Create the masq name */ 04414 snprintf(masqn, sizeof(masqn), "%s<MASQ>", newn); 04415 04416 /* Copy the name from the clone channel */ 04417 ast_string_field_set(original, name, newn); 04418 04419 /* Mangle the name of the clone channel */ 04420 ast_string_field_set(clonechan, name, masqn); 04421 04422 /* Notify any managers of the change, first the masq then the other */ 04423 manager_event(EVENT_FLAG_CALL, "Rename", "Channel: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", newn, masqn, clonechan->uniqueid); 04424 manager_event(EVENT_FLAG_CALL, "Rename", "Channel: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", orig, newn, original->uniqueid); 04425 04426 /* Swap the technologies */ 04427 t = original->tech; 04428 original->tech = clonechan->tech; 04429 clonechan->tech = t; 04430 04431 /* Swap the cdrs */ 04432 cdr = original->cdr; 04433 original->cdr = clonechan->cdr; 04434 clonechan->cdr = cdr; 04435 04436 t_pvt = original->tech_pvt; 04437 original->tech_pvt = clonechan->tech_pvt; 04438 clonechan->tech_pvt = t_pvt; 04439 04440 /* Swap the alertpipes */ 04441 for (i = 0; i < 2; i++) { 04442 x = original->alertpipe[i]; 04443 original->alertpipe[i] = clonechan->alertpipe[i]; 04444 clonechan->alertpipe[i] = x; 04445 } 04446 04447 /* 04448 * Swap the readq's. The end result should be this: 04449 * 04450 * 1) All frames should be on the new (original) channel. 04451 * 2) Any frames that were already on the new channel before this 04452 * masquerade need to be at the end of the readq, after all of the 04453 * frames on the old (clone) channel. 04454 * 3) The alertpipe needs to get poked for every frame that was already 04455 * on the new channel, since we are now using the alert pipe from the 04456 * old (clone) channel. 04457 */ 04458 { 04459 AST_LIST_HEAD_NOLOCK(, ast_frame) tmp_readq; 04460 AST_LIST_HEAD_SET_NOLOCK(&tmp_readq, NULL); 04461 04462 AST_LIST_APPEND_LIST(&tmp_readq, &original->readq, frame_list); 04463 AST_LIST_APPEND_LIST(&original->readq, &clonechan->readq, frame_list); 04464 04465 while ((current = AST_LIST_REMOVE_HEAD(&tmp_readq, frame_list))) { 04466 AST_LIST_INSERT_TAIL(&original->readq, current, frame_list); 04467 if (original->alertpipe[1] > -1) { 04468 int poke = 0; 04469 04470 if (write(original->alertpipe[1], &poke, sizeof(poke)) < 0) { 04471 ast_log(LOG_WARNING, "write() failed: %s\n", strerror(errno)); 04472 } 04473 } 04474 } 04475 } 04476 04477 /* Swap the raw formats */ 04478 x = original->rawreadformat; 04479 original->rawreadformat = clonechan->rawreadformat; 04480 clonechan->rawreadformat = x; 04481 x = original->rawwriteformat; 04482 original->rawwriteformat = clonechan->rawwriteformat; 04483 clonechan->rawwriteformat = x; 04484 04485 clonechan->_softhangup = AST_SOFTHANGUP_DEV; 04486 04487 /* And of course, so does our current state. Note we need not 04488 call ast_setstate since the event manager doesn't really consider 04489 these separate. We do this early so that the clone has the proper 04490 state of the original channel. */ 04491 origstate = original->_state; 04492 original->_state = clonechan->_state; 04493 clonechan->_state = origstate; 04494 04495 if (clonechan->tech->fixup){ 04496 res = clonechan->tech->fixup(original, clonechan); 04497 if (res) 04498 ast_log(LOG_WARNING, "Fixup failed on channel %s, strange things may happen.\n", clonechan->name); 04499 } 04500 04501 /* Start by disconnecting the original's physical side */ 04502 if (clonechan->tech->hangup) 04503 res = clonechan->tech->hangup(clonechan); 04504 if (res) { 04505 ast_log(LOG_WARNING, "Hangup failed! Strange things may happen!\n"); 04506 ast_channel_unlock(clonechan); 04507 return -1; 04508 } 04509 04510 snprintf(zombn, sizeof(zombn), "%s<ZOMBIE>", orig); 04511 /* Mangle the name of the clone channel */ 04512 ast_string_field_set(clonechan, name, zombn); 04513 manager_event(EVENT_FLAG_CALL, "Rename", "Channel: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", masqn, zombn, clonechan->uniqueid); 04514 04515 /* Update the type. */ 04516 t_pvt = original->monitor; 04517 original->monitor = clonechan->monitor; 04518 clonechan->monitor = t_pvt; 04519 04520 /* Keep the same language. */ 04521 ast_string_field_set(original, language, clonechan->language); 04522 /* Copy the FD's other than the generator fd */ 04523 for (x = 0; x < AST_MAX_FDS; x++) { 04524 if (x != AST_GENERATOR_FD) 04525 ast_channel_set_fd(original, x, clonechan->fds[x]); 04526 } 04527 04528 ast_app_group_update(clonechan, original); 04529 04530 /* Move data stores over */ 04531 if (AST_LIST_FIRST(&clonechan->datastores)) { 04532 struct ast_datastore *ds; 04533 /* We use a safe traversal here because some fixup routines actually 04534 * remove the datastore from the list and free them. 04535 */ 04536 AST_LIST_TRAVERSE_SAFE_BEGIN(&clonechan->datastores, ds, entry) { 04537 if (ds->info->chan_fixup) 04538 ds->info->chan_fixup(ds->data, clonechan, original); 04539 } 04540 AST_LIST_TRAVERSE_SAFE_END; 04541 AST_LIST_APPEND_LIST(&original->datastores, &clonechan->datastores, entry); 04542 } 04543 04544 clone_variables(original, clonechan); 04545 /* Presense of ADSI capable CPE follows clone */ 04546 original->adsicpe = clonechan->adsicpe; 04547 /* Bridge remains the same */ 04548 /* CDR fields remain the same */ 04549 /* XXX What about blocking, softhangup, blocker, and lock and blockproc? XXX */ 04550 /* Application and data remain the same */ 04551 /* Clone exception becomes real one, as with fdno */ 04552 ast_set_flag(original, ast_test_flag(clonechan, AST_FLAG_OUTGOING | AST_FLAG_EXCEPTION)); 04553 original->fdno = clonechan->fdno; 04554 /* Schedule context remains the same */ 04555 /* Stream stuff stays the same */ 04556 /* Keep the original state. The fixup code will need to work with it most likely */ 04557 04558 /* Just swap the whole structures, nevermind the allocations, they'll work themselves 04559 out. */ 04560 tmpcid = original->cid; 04561 original->cid = clonechan->cid; 04562 clonechan->cid = tmpcid; 04563 report_new_callerid(original); 04564 04565 /* Restore original timing file descriptor */ 04566 ast_channel_set_fd(original, AST_TIMING_FD, original->timingfd); 04567 04568 /* Our native formats are different now */ 04569 original->nativeformats = clonechan->nativeformats; 04570 04571 /* Context, extension, priority, app data, jump table, remain the same */ 04572 /* pvt switches. pbx stays the same, as does next */ 04573 04574 /* Set the write format */ 04575 ast_set_write_format(original, wformat); 04576 04577 /* Set the read format */ 04578 ast_set_read_format(original, rformat); 04579 04580 /* Copy the music class */ 04581 ast_string_field_set(original, musicclass, clonechan->musicclass); 04582 04583 ast_debug(1, "Putting channel %s in %d/%d formats\n", original->name, wformat, rformat); 04584 04585 /* Okay. Last thing is to let the channel driver know about all this mess, so he 04586 can fix up everything as best as possible */ 04587 if (original->tech->fixup) { 04588 res = original->tech->fixup(clonechan, original); 04589 if (res) { 04590 ast_log(LOG_WARNING, "Channel for type '%s' could not fixup channel %s\n", 04591 original->tech->type, original->name); 04592 ast_channel_unlock(clonechan); 04593 return -1; 04594 } 04595 } else 04596 ast_log(LOG_WARNING, "Channel type '%s' does not have a fixup routine (for %s)! Bad things may happen.\n", 04597 original->tech->type, original->name); 04598 04599 /* 04600 * If an indication is currently playing, maintain it on the channel 04601 * that is taking the place of original 04602 * 04603 * This is needed because the masquerade is swapping out in the internals 04604 * of this channel, and the new channel private data needs to be made 04605 * aware of the current visible indication (RINGING, CONGESTION, etc.) 04606 */ 04607 if (original->visible_indication) { 04608 ast_indicate(original, original->visible_indication); 04609 } 04610 04611 /* Now, at this point, the "clone" channel is totally F'd up. We mark it as 04612 a zombie so nothing tries to touch it. If it's already been marked as a 04613 zombie, then free it now (since it already is considered invalid). */ 04614 if (ast_test_flag(clonechan, AST_FLAG_ZOMBIE)) { 04615 ast_debug(1, "Destroying channel clone '%s'\n", clonechan->name); 04616 ast_channel_unlock(clonechan); 04617 manager_event(EVENT_FLAG_CALL, "Hangup", 04618 "Channel: %s\r\n" 04619 "Uniqueid: %s\r\n" 04620 "Cause: %d\r\n" 04621 "Cause-txt: %s\r\n", 04622 clonechan->name, 04623 clonechan->uniqueid, 04624 clonechan->hangupcause, 04625 ast_cause2str(clonechan->hangupcause) 04626 ); 04627 ast_channel_free(clonechan); 04628 } else { 04629 ast_debug(1, "Released clone lock on '%s'\n", clonechan->name); 04630 ast_set_flag(clonechan, AST_FLAG_ZOMBIE); 04631 ast_queue_frame(clonechan, &ast_null_frame); 04632 ast_channel_unlock(clonechan); 04633 } 04634 04635 /* Signal any blocker */ 04636 if (ast_test_flag(original, AST_FLAG_BLOCKING)) 04637 pthread_kill(original->blocker, SIGURG); 04638 ast_debug(1, "Done Masquerading %s (%d)\n", original->name, original->_state); 04639 return 0; 04640 }
| static int ast_fdisset | ( | struct pollfd * | pfds, | |
| int | fd, | |||
| int | maximum, | |||
| int * | start | |||
| ) | [inline, static] |
Helper function for migrating select to poll.
Definition at line 1672 of file channel.h.
References dummy().
Referenced by do_monitor().
01673 { 01674 int x; 01675 int dummy = 0; 01676 01677 if (fd < 0) 01678 return 0; 01679 if (!start) 01680 start = &dummy; 01681 for (x = *start; x < maximum; x++) 01682 if (pfds[x].fd == fd) { 01683 if (x == *start) 01684 (*start)++; 01685 return pfds[x].revents; 01686 } 01687 return 0; 01688 }
| struct ast_channel* ast_get_channel_by_exten_locked | ( | const char * | exten, | |
| const char * | context | |||
| ) | [read] |
Get channel by exten (and optionally context) and lock it.
Definition at line 1292 of file channel.c.
References channel_find_locked().
01293 { 01294 return channel_find_locked(NULL, NULL, 0, context, exten); 01295 }
| struct ast_channel* ast_get_channel_by_name_locked | ( | const char * | name | ) | [read] |
Get channel by name or uniqueid (locks channel).
Definition at line 1273 of file channel.c.
References channel_find_locked().
Referenced by acf_import(), action_add_agi_cmd(), action_atxfer(), action_getvar(), action_hangup(), action_redirect(), action_sendtext(), action_setvar(), action_status(), action_timeout(), ast_async_goto_by_name(), ast_bridge_call(), ast_park_call_full(), asyncgoto_exec(), change_monitor_action(), do_pause_or_unpause(), get_dahdi_channel_locked(), handle_channelstatus(), handle_cli_agi_add_cmd(), handle_core_set_debug_channel(), handle_getvariablefull(), handle_hangup(), handle_set_chanvar(), handle_show_chanvar(), handle_showchan(), handle_softhangup(), manager_park(), manager_play_dtmf(), pbx_builtin_importvar(), shared_read(), shared_write(), start_monitor_action(), and stop_monitor_action().
01274 { 01275 return channel_find_locked(NULL, name, 0, NULL, NULL); 01276 }
| struct ast_channel* ast_get_channel_by_name_prefix_locked | ( | const char * | name, | |
| const int | namelen | |||
| ) | [read] |
Get channel by name or uniqueid prefix (locks channel).
Definition at line 1279 of file channel.c.
References channel_find_locked().
Referenced by action_bridge(), ast_parse_device_state(), bridge_exec(), common_exec(), handle_cli_mixmonitor(), shared_read(), and shared_write().
01280 { 01281 return channel_find_locked(NULL, name, namelen, NULL, NULL); 01282 }
| struct ast_channel_tech* ast_get_channel_tech | ( | const char * | name | ) | [read] |
Get a channel technology structure by name.
| name | name of technology to find |
Definition at line 610 of file channel.c.
References AST_LIST_TRAVERSE, AST_RWLIST_RDLOCK, AST_RWLIST_UNLOCK, channels, chanlist::tech, and ast_channel_tech::type.
Referenced by _ast_device_state().
00611 { 00612 struct chanlist *chanls; 00613 const struct ast_channel_tech *ret = NULL; 00614 00615 AST_RWLIST_RDLOCK(&channels); 00616 00617 AST_LIST_TRAVERSE(&backends, chanls, list) { 00618 if (!strcasecmp(name, chanls->tech->type)) { 00619 ret = chanls->tech; 00620 break; 00621 } 00622 } 00623 00624 AST_RWLIST_UNLOCK(&channels); 00625 00626 return ret; 00627 }
| ast_group_t ast_get_group | ( | const char * | s | ) |
Definition at line 5457 of file channel.c.
References ast_log(), ast_strdupa, ast_strlen_zero(), LOG_ERROR, LOG_WARNING, and strsep().
Referenced by _parse(), build_device(), build_gateway(), build_peer(), func_channel_write(), process_dahdi(), and read_agent_config().
05458 { 05459 char *piece; 05460 char *c; 05461 int start=0, finish=0, x; 05462 ast_group_t group = 0; 05463 05464 if (ast_strlen_zero(s)) 05465 return 0; 05466 05467 c = ast_strdupa(s); 05468 05469 while ((piece = strsep(&c, ","))) { 05470 if (sscanf(piece, "%30d-%30d", &start, &finish) == 2) { 05471 /* Range */ 05472 } else if (sscanf(piece, "%30d", &start)) { 05473 /* Just one */ 05474 finish = start; 05475 } else { 05476 ast_log(LOG_ERROR, "Syntax error parsing group configuration '%s' at '%s'. Ignoring.\n", s, piece); 05477 continue; 05478 } 05479 for (x = start; x <= finish; x++) { 05480 if ((x > 63) || (x < 0)) { 05481 ast_log(LOG_WARNING, "Ignoring invalid group %d (maximum group is 63)\n", x); 05482 } else 05483 group |= ((ast_group_t) 1 << x); 05484 } 05485 } 05486 return group; 05487 }
| int ast_hangup | ( | struct ast_channel * | chan | ) |
Hang up a channel.
| chan | channel to hang up |
Definition at line 1663 of file channel.c.
References ast_assert, ast_audiohook_detach_list(), ast_autoservice_stop(), ast_cause2str(), ast_cdr_detach(), ast_cdr_end(), AST_CDR_FLAG_BRIDGED, AST_CDR_FLAG_DIALED, AST_CDR_FLAG_POST_DISABLED, AST_CDR_NULL, ast_channel_free(), ast_channel_lock, ast_channel_unlock, ast_clear_flag, ast_closestream(), ast_debug, ast_do_masquerade(), AST_FLAG_BLOCKING, AST_FLAG_IN_CHANNEL_LIST, AST_FLAG_ZOMBIE, ast_log(), AST_RWLIST_REMOVE, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_set_flag, ast_test_flag, ast_channel::audiohooks, ast_channel::blocker, ast_channel::blockproc, ast_channel::cdr, channels, ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, ast_cdr::disposition, EVENT_FLAG_CALL, free_translation(), ast_channel::generator, ast_channel::generatordata, ast_channel_tech::hangup, ast_channel::hangupcause, LOG_ERROR, LOG_WARNING, manager_event, ast_channel::masq, ast_channel::masqr, ast_generator::release, S_OR, ast_channel::sched, sched_context_destroy(), ast_channel::stream, ast_channel::tech, and ast_channel::vstream.
Referenced by __ast_pbx_run(), __ast_request_and_dial(), __oh323_new(), action_bridge(), agent_hangup(), agent_read(), alsa_new(), answer_exec_run(), app_exec(), ast_async_goto(), ast_bridge_call_thread(), ast_call_forward(), ast_dial_destroy(), ast_dial_hangup(), ast_feature_request_and_dial(), ast_iax2_new(), ast_pbx_outgoing_app(), ast_pbx_outgoing_exten(), ast_pbx_run_app(), async_wait(), begin_dial_channel(), bridge_exec(), build_conf(), builtin_atxfer(), chanavail_exec(), check_compat(), check_goto_on_transfer(), clear_caller(), conf_free(), conf_run(), connect_link(), console_new(), dahdi_handle_event(), dahdi_new(), dial_exec_full(), do_forward(), do_hang(), do_idle_thread(), findmeexec(), gtalk_new(), handle_call_forward(), handle_callforward_button(), handle_enbloc_call_message(), handle_frame(), handle_frame_ownerless(), handle_hd_hf(), handle_init_event(), handle_invite_replaces(), handle_offhook_message(), handle_request_invite(), handle_soft_key_event_message(), handle_stimulus_message(), handle_timeout_trip(), handle_transfer_button(), HandleCallOutgoing(), hangup_chan(), hangupcalls(), hanguptree(), iax2_request(), iax_park(), iax_park_thread(), jingle_new(), local_hangup(), manage_parkinglot(), masq_park_call(), mgcp_new(), mgcp_ss(), monitor_dial(), mwi_thread(), nbs_new(), oss_new(), park_exec_full(), parkandannounce_exec(), phone_new(), pri_dchannel(), rpt(), rpt_call(), rpt_exec(), rpt_tele_thread(), sip_new(), sip_park(), sip_park_thread(), skinny_new(), skinny_ss(), ss_thread(), try_calling(), unistim_new(), usbradio_new(), wait_for_answer(), and wait_for_winner().
01664 { 01665 int res = 0; 01666 01667 /* Don't actually hang up a channel that will masquerade as someone else, or 01668 if someone is going to masquerade as us */ 01669 ast_channel_lock(chan); 01670 01671 if (chan->audiohooks) { 01672 ast_audiohook_detach_list(chan->audiohooks); 01673 chan->audiohooks = NULL; 01674 } 01675 01676 ast_autoservice_stop(chan); 01677 01678 if (chan->masq) { 01679 if (ast_do_masquerade(chan)) 01680 ast_log(LOG_WARNING, "Failed to perform masquerade\n"); 01681 } 01682 01683 if (chan->masq) { 01684 ast_log(LOG_WARNING, "%s getting hung up, but someone is trying to masq into us?!?\n", chan->name); 01685 ast_channel_unlock(chan); 01686 return 0; 01687 } 01688 /* If this channel is one which will be masqueraded into something, 01689 mark it as a zombie already, so we know to free it later */ 01690 if (chan->masqr) { 01691 ast_set_flag(chan, AST_FLAG_ZOMBIE); 01692 ast_channel_unlock(chan); 01693 return 0; 01694 } 01695 ast_channel_unlock(chan); 01696 01697 AST_RWLIST_WRLOCK(&channels); 01698 if (!AST_RWLIST_REMOVE(&channels, chan, chan_list)) { 01699 ast_log(LOG_ERROR, "Unable to find channel in list to free. Assuming it has already been done.\n"); 01700 } 01701 ast_clear_flag(chan, AST_FLAG_IN_CHANNEL_LIST); 01702 AST_RWLIST_UNLOCK(&channels); 01703 01704 ast_channel_lock(chan); 01705 free_translation(chan); 01706 /* Close audio stream */ 01707 if (chan->stream) { 01708 ast_closestream(chan->stream); 01709 chan->stream = NULL; 01710 } 01711 /* Close video stream */ 01712 if (chan->vstream) { 01713 ast_closestream(chan->vstream); 01714 chan->vstream = NULL; 01715 } 01716 if (chan->sched) { 01717 sched_context_destroy(chan->sched); 01718 chan->sched = NULL; 01719 } 01720 01721 if (chan->generatordata) /* Clear any tone stuff remaining */ 01722 if (chan->generator && chan->generator->release) 01723 chan->generator->release(chan, chan->generatordata); 01724 chan->generatordata = NULL; 01725 chan->generator = NULL; 01726 if (ast_test_flag(chan, AST_FLAG_BLOCKING)) { 01727 ast_log(LOG_WARNING, "Hard hangup called by thread %ld on %s, while fd " 01728 "is blocked by thread %ld in procedure %s! Expect a failure\n", 01729 (long)pthread_self(), chan->name, (long)chan->blocker, chan->blockproc); 01730 ast_assert(ast_test_flag(chan, AST_FLAG_BLOCKING) == 0); 01731 } 01732 if (!ast_test_flag(chan, AST_FLAG_ZOMBIE)) { 01733 ast_debug(1, "Hanging up channel '%s'\n", chan->name); 01734 if (chan->tech->hangup) 01735 res = chan->tech->hangup(chan); 01736 } else { 01737 ast_debug(1, "Hanging up zombie '%s'\n", chan->name); 01738 } 01739 01740 ast_channel_unlock(chan); 01741 manager_event(EVENT_FLAG_CALL, "Hangup", 01742 "Channel: %s\r\n" 01743 "Uniqueid: %s\r\n" 01744 "CallerIDNum: %s\r\n" 01745 "CallerIDName: %s\r\n" 01746 "Cause: %d\r\n" 01747 "Cause-txt: %s\r\n", 01748 chan->name, 01749 chan->uniqueid, 01750 S_OR(chan->cid.cid_num, "<unknown>"), 01751 S_OR(chan->cid.cid_name, "<unknown>"), 01752 chan->hangupcause, 01753 ast_cause2str(chan->hangupcause) 01754 ); 01755 01756 if (chan->cdr && !ast_test_flag(chan->cdr, AST_CDR_FLAG_BRIDGED) && 01757 !ast_test_flag(chan->cdr, AST_CDR_FLAG_POST_DISABLED) && 01758 (chan->cdr->disposition != AST_CDR_NULL || ast_test_flag(chan->cdr, AST_CDR_FLAG_DIALED))) { 01759 ast_channel_lock(chan); 01760 01761 ast_cdr_end(chan->cdr); 01762 ast_cdr_detach(chan->cdr); 01763 chan->cdr = NULL; 01764 ast_channel_unlock(chan); 01765 } 01766 01767 ast_channel_free(chan); 01768 01769 return res; 01770 }
| int ast_indicate | ( | struct ast_channel * | chan, | |
| int | condition | |||
| ) |
Indicates condition of channel.
| chan | channel to change the indication | |
| condition | which condition to indicate on the channel |
Definition at line 3083 of file channel.c.
References ast_indicate_data().
Referenced by __ast_play_and_record(), agent_new(), alsa_call(), answer_trunk_chan(), ast_bridge_call(), ast_channel_bridge(), ast_do_masquerade(), ast_dtmf_stream(), ast_feature_request_and_dial(), ast_park_call_full(), ast_raw_answer(), attempt_transfer(), builtin_atxfer(), builtin_blindtransfer(), cli_console_answer(), conf_run(), console_call(), dial_exec_full(), disa_exec(), do_forward(), finishup(), function_remote(), handle_callforward_button(), handle_frame(), handle_recordfile(), manage_parkinglot(), mgcp_ss(), monitor_dial(), oss_call(), park_exec_full(), pbx_builtin_busy(), pbx_builtin_congestion(), pbx_builtin_proceeding(), pbx_builtin_progress(), pbx_builtin_ringing(), pbx_builtin_waitexten(), queue_exec(), record_exec(), rpt(), rpt_exec(), say_periodic_announcement(), say_position(), send_waveform_to_channel(), skinny_ss(), sla_handle_hold_event(), sla_station_exec(), sla_trunk_exec(), try_calling(), and wait_for_answer().
03084 { 03085 return ast_indicate_data(chan, condition, NULL, 0); 03086 }
| int ast_indicate_data | ( | struct ast_channel * | chan, | |
| int | condition, | |||
| const void * | data, | |||
| size_t | datalen | |||
| ) |
Indicates condition of channel, with payload.
| chan | channel to change the indication | |
| condition | which condition to indicate on the channel | |
| data | pointer to payload data | |
| datalen | size of payload data |
Definition at line 3123 of file channel.c.
References ast_channel::_state, _XXX_AST_CONTROL_T38, ast_channel_lock, ast_channel_unlock, ast_check_hangup(), AST_CONTROL_ANSWER, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_FLASH, AST_CONTROL_HANGUP, AST_CONTROL_HOLD, AST_CONTROL_OFFHOOK, AST_CONTROL_OPTION, AST_CONTROL_PROCEEDING, AST_CONTROL_PROGRESS, AST_CONTROL_RADIO_KEY, AST_CONTROL_RADIO_UNKEY, AST_CONTROL_RING, AST_CONTROL_RINGING, AST_CONTROL_SRCUPDATE, AST_CONTROL_T38_PARAMETERS, AST_CONTROL_TAKEOFFHOOK, AST_CONTROL_UNHOLD, AST_CONTROL_VIDUPDATE, AST_CONTROL_WINK, ast_debug, AST_FLAG_ZOMBIE, ast_get_indication_tone(), ast_log(), ast_playtones_start(), ast_playtones_stop(), AST_STATE_UP, ast_test_flag, tone_zone_sound::data, ast_channel_tech::indicate, is_visible_indication(), LOG_WARNING, ast_channel::tech, ast_channel::visible_indication, and ast_channel::zone.
Referenced by agent_hangup(), ast_bridge_call(), ast_generic_bridge(), ast_indicate(), ast_park_call_full(), bridge_native_loop(), bridge_p2p_loop(), login_exec(), manage_parkinglot(), pbx_builtin_waitexten(), transmit_audio(), transmit_t38(), and wait_for_answer().
03125 { 03126 /* By using an enum, we'll get compiler warnings for values not handled 03127 * in switch statements. */ 03128 enum ast_control_frame_type condition = _condition; 03129 const struct tone_zone_sound *ts = NULL; 03130 int res = -1; 03131 03132 ast_channel_lock(chan); 03133 03134 /* Don't bother if the channel is about to go away, anyway. */ 03135 if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) { 03136 ast_channel_unlock(chan); 03137 return -1; 03138 } 03139 03140 if (chan->tech->indicate) { 03141 /* See if the channel driver can handle this condition. */ 03142 res = chan->tech->indicate(chan, condition, data, datalen); 03143 } 03144 03145 ast_channel_unlock(chan); 03146 03147 if (!res) { 03148 /* The channel driver successfully handled this indication */ 03149 if (is_visible_indication(condition)) { 03150 chan->visible_indication = condition; 03151 } 03152 return 0; 03153 } 03154 03155 /* The channel driver does not support this indication, let's fake 03156 * it by doing our own tone generation if applicable. */ 03157 03158 /*!\note If we compare the enumeration type, which does not have any 03159 * negative constants, the compiler may optimize this code away. 03160 * Therefore, we must perform an integer comparison here. */ 03161 if (_condition < 0) { 03162 /* Stop any tones that are playing */ 03163 ast_playtones_stop(chan); 03164 return 0; 03165 } 03166 03167 /* Handle conditions that we have tones for. */ 03168 switch (condition) { 03169 case _XXX_AST_CONTROL_T38: 03170 /* deprecated T.38 control frame */ 03171 return -1; 03172 case AST_CONTROL_T38_PARAMETERS: 03173 /* there is no way to provide 'default' behavior for these 03174 * control frames, so we need to return failure, but there 03175 * is also no value in the log message below being emitted 03176 * since failure to handle these frames is not an 'error' 03177 * so just return right now. 03178 */ 03179 return -1; 03180 case AST_CONTROL_RINGING: 03181 ts = ast_get_indication_tone(chan->zone, "ring"); 03182 /* It is common practice for channel drivers to return -1 if trying 03183 * to indicate ringing on a channel which is up. The idea is to let the 03184 * core generate the ringing inband. However, we don't want the 03185 * warning message about not being able to handle the specific indication 03186 * to print nor do we want ast_indicate_data to return an "error" for this 03187 * condition 03188 */ 03189 if (chan->_state == AST_STATE_UP) { 03190 res = 0; 03191 } 03192 break; 03193 case AST_CONTROL_BUSY: 03194 ts = ast_get_indication_tone(chan->zone, "busy"); 03195 break; 03196 case AST_CONTROL_CONGESTION: 03197 ts = ast_get_indication_tone(chan->zone, "congestion"); 03198 break; 03199 case AST_CONTROL_PROGRESS: 03200 case AST_CONTROL_PROCEEDING: 03201 case AST_CONTROL_VIDUPDATE: 03202 case AST_CONTROL_SRCUPDATE: 03203 case AST_CONTROL_RADIO_KEY: 03204 case AST_CONTROL_RADIO_UNKEY: 03205 case AST_CONTROL_OPTION: 03206 case AST_CONTROL_WINK: 03207 case AST_CONTROL_FLASH: 03208 case AST_CONTROL_OFFHOOK: 03209 case AST_CONTROL_TAKEOFFHOOK: 03210 case AST_CONTROL_ANSWER: 03211 case AST_CONTROL_HANGUP: 03212 case AST_CONTROL_RING: 03213 case AST_CONTROL_HOLD: 03214 case AST_CONTROL_UNHOLD: 03215 /* Nothing left to do for these. */ 03216 res = 0; 03217 break; 03218 } 03219 03220 if (ts && ts->data[0]) { 03221 /* We have a tone to play, yay. */ 03222 ast_debug(1, "Driver for channel '%s' does not support indication %d, emulating it\n", chan->name, condition); 03223 ast_playtones_start(chan, 0, ts->data, 1); 03224 res = 0; 03225 chan->visible_indication = condition; 03226 } 03227 03228 if (res) { 03229 /* not handled */ 03230 ast_log(LOG_WARNING, "Unable to handle indication %d for '%s'\n", condition, chan->name); 03231 } 03232 03233 return res; 03234 }
| int ast_internal_timing_enabled | ( | struct ast_channel * | chan | ) |
Check if the channel can run in internal timing mode.
| chan | The channel to check |
This function will return 1 if internal timing is enabled and the timing device is available.
Definition at line 3066 of file channel.c.
References ast_debug, ast_opt_internal_timing, and ast_channel::timingfd.
Referenced by add_sdp(), and ast_read_generator_actions().
03067 { 03068 int ret = ast_opt_internal_timing && chan->timingfd > -1; 03069 ast_debug(5, "Internal timing is %s (option_internal_timing=%d chan->timingfd=%d)\n", ret? "enabled": "disabled", ast_opt_internal_timing, chan->timingfd); 03070 return ret; 03071 }
| void ast_poll_channel_add | ( | struct ast_channel * | chan0, | |
| struct ast_channel * | chan1 | |||
| ) |
Add a channel to an optimized waitfor
Definition at line 1583 of file channel.c.
References AST_MAX_FDS, and ast_channel::fds.
Referenced by ast_feature_request_and_dial(), ast_generic_bridge(), begin_dial_channel(), bridge_native_loop(), bridge_p2p_loop(), and wait_for_answer().
01584 { 01585 #ifdef HAVE_EPOLL 01586 struct epoll_event ev; 01587 int i = 0; 01588 01589 if (chan0->epfd == -1) 01590 return; 01591 01592 /* Iterate through the file descriptors on chan1, adding them to chan0 */ 01593 for (i = 0; i < AST_MAX_FDS; i++) { 01594 if (chan1->fds[i] == -1) 01595 continue; 01596 ev.events = EPOLLIN | EPOLLPRI | EPOLLERR | EPOLLHUP; 01597 ev.data.ptr = chan1->epfd_data[i]; 01598 epoll_ctl(chan0->epfd, EPOLL_CTL_ADD, chan1->fds[i], &ev); 01599 } 01600 01601 #endif 01602 return; 01603 }
| void ast_poll_channel_del | ( | struct ast_channel * | chan0, | |
| struct ast_channel * | chan1 | |||
| ) |
Delete a channel from an optimized waitfor
Definition at line 1606 of file channel.c.
References AST_MAX_FDS, and ast_channel::fds.
Referenced by ast_feature_request_and_dial(), ast_generic_bridge(), bridge_native_loop(), bridge_p2p_loop(), monitor_dial(), and wait_for_answer().
01607 { 01608 #ifdef HAVE_EPOLL 01609 struct epoll_event ev; 01610 int i = 0; 01611 01612 if (chan0->epfd == -1) 01613 return; 01614 01615 for (i = 0; i < AST_MAX_FDS; i++) { 01616 if (chan1->fds[i] == -1) 01617 continue; 01618 epoll_ctl(chan0->epfd, EPOLL_CTL_DEL, chan1->fds[i], &ev); 01619 } 01620 01621 #endif 01622 return; 01623 }
| char* ast_print_group | ( | char * | buf, | |
| int | buflen, | |||
| ast_group_t | group | |||
| ) |
print call- and pickup groups into buffer
Definition at line 5539 of file channel.c.
Referenced by _sip_show_peer(), func_channel_read(), function_sippeer(), handle_skinny_show_line(), misdn_cfg_get_config_string(), print_group(), read_config(), and serialize_showchan().
05540 { 05541 unsigned int i; 05542 int first = 1; 05543 char num[3]; 05544 05545 buf[0] = '\0'; 05546 05547 if (!group) /* Return empty string if no group */ 05548 return buf; 05549 05550 for (i = 0; i <= 63; i++) { /* Max group is 63 */ 05551 if (group & ((ast_group_t) 1 << i)) { 05552 if (!first) { 05553 strncat(buf, ", ", buflen - strlen(buf) - 1); 05554 } else { 05555 first = 0; 05556 } 05557 snprintf(num, sizeof(num), "%u", i); 05558 strncat(buf, num, buflen - strlen(buf) - 1); 05559 } 05560 } 05561 return buf; 05562 }
| int ast_prod | ( | struct ast_channel * | chan | ) |
Send empty audio to prime a channel driver.
Definition at line 3355 of file channel.c.
References ast_channel::_state, ast_debug, AST_FRAME_VOICE, AST_FRIENDLY_OFFSET, ast_log(), AST_STATE_UP, ast_write(), ast_frame::data, LOG_WARNING, ast_frame::ptr, ast_channel::rawwriteformat, ast_frame::src, and ast_frame::subclass.
Referenced by ast_activate_generator().
03356 { 03357 struct ast_frame a = { AST_FRAME_VOICE }; 03358 char nothing[128]; 03359 03360 /* Send an empty audio frame to get things moving */ 03361 if (chan->_state != AST_STATE_UP) { 03362 ast_debug(1, "Prodding channel '%s'\n", chan->name); 03363 a.subclass = chan->rawwriteformat; 03364 a.data.ptr = nothing + AST_FRIENDLY_OFFSET; 03365 a.src = "ast_prod"; 03366 if (ast_write(chan, &a)) 03367 ast_log(LOG_WARNING, "Prodding channel '%s' failed\n", chan->name); 03368 } 03369 return 0; 03370 }
| int ast_queue_control | ( | struct ast_channel * | chan, | |
| enum ast_control_frame_type | control | |||
| ) |
Queue a control frame with payload.
| chan | channel to queue frame onto | |
| control | type of control frame |
| zero | on success | |
| non-zero | on failure |
Definition at line 1118 of file channel.c.
References AST_FRAME_CONTROL, ast_queue_frame(), and ast_frame::subclass.
Referenced by __dahdi_exception(), __oh323_update_info(), ast_pickup_call(), attempt_transfer(), auto_congest(), cb_events(), dahdi_handle_event(), dahdi_hangup(), gtalk_is_answered(), gtalk_ringing_ack(), handle_hd_hf(), handle_offhook_message(), handle_request(), handle_request_bye(), handle_request_info(), handle_request_invite(), handle_request_refer(), handle_response(), handle_response_invite(), handle_response_refer(), handle_soft_key_event_message(), handle_stimulus_message(), HandleCallIncoming(), jingle_is_answered(), jingle_ringing_ack(), mgcp_call(), misdn_attempt_transfer(), nbs_call(), phone_call(), pickup_do(), process_sdp(), receive_digit(), remote_hold(), send_cause2ast(), setup_rtp_connection(), skinny_call(), skinny_transfer(), skinny_unhold(), ss_thread(), unistim_call(), and update_state().
01119 { 01120 struct ast_frame f = { AST_FRAME_CONTROL, }; 01121 01122 f.subclass = control; 01123 01124 return ast_queue_frame(chan, &f); 01125 }
| int ast_queue_control_data | ( | struct ast_channel * | chan, | |
| enum ast_control_frame_type | control, | |||
| const void * | data, | |||
| size_t | datalen | |||
| ) |
Queue a control frame with payload.
| chan | channel to queue frame onto | |
| control | type of control frame | |
| data | pointer to payload data to be included in frame | |
| datalen | number of bytes of payload data |
| 0 | success | |
| non-zero | failure |
The supplied payload data is copied into the frame, so the caller's copy is not modified nor freed, and the resulting frame will retain a copy of the data even if the caller frees their local copy.
Definition at line 1128 of file channel.c.
References AST_FRAME_CONTROL, ast_queue_frame(), ast_frame::data, ast_frame::datalen, ast_frame::ptr, and ast_frame::subclass.
Referenced by change_t38_state(), dahdi_handle_event(), dahdi_hangup(), iax2_queue_control_data(), process_sdp(), and skinny_hold().
01130 { 01131 struct ast_frame f = { AST_FRAME_CONTROL, }; 01132 01133 f.subclass = control; 01134 f.data.ptr = (void *) data; 01135 f.datalen = datalen; 01136 01137 return ast_queue_frame(chan, &f); 01138 }
| int ast_queue_frame | ( | struct ast_channel * | chan, | |
| struct ast_frame * | f | |||
| ) |
Queue one or more frames to a channel's frame queue.
| chan | the channel to queue the frame(s) on | |
| f | the frame(s) to queue. Note that the frame(s) will be duplicated by this function. It is the responsibility of the caller to handle freeing the memory associated with the frame(s) being passed if necessary. |
| 0 | success | |
| non-zero | failure |
Definition at line 1075 of file channel.c.
References __ast_queue_frame().
Referenced by __ast_read(), __oh323_rtp_create(), __oh323_update_info(), action_atxfer(), agent_new(), alsa_call(), ast_channel_masquerade(), ast_channel_setwhentohangup_tv(), ast_do_masquerade(), ast_dsp_process(), ast_queue_control(), ast_queue_control_data(), ast_queue_hangup(), ast_queue_hangup_with_cause(), ast_softhangup_nolock(), cb_events(), cli_console_answer(), cli_console_dial(), cli_console_flash(), cli_console_sendtext(), console_answer(), console_call(), console_dial(), console_do_answer(), console_flash(), console_sendtext(), dahdi_queue_frame(), dictate_exec(), do_immediate_setup(), gtalk_handle_dtmf(), handle_keypad_button_message(), handle_request_info(), handle_request_invite(), handle_response_invite(), iax2_queue_frame(), jingle_handle_dtmf(), local_queue_frame(), mgcp_queue_frame(), oh323_simulate_dtmf_end(), oss_call(), process_sdp(), queue_dtmf_readq(), receive_digit(), receive_message(), rpt_call(), stream_monitor(), unistim_do_senddigit(), unistim_senddigit_end(), usbradio_read(), and wakeup_sub().
01076 { 01077 return __ast_queue_frame(chan, fin, 0, NULL); 01078 }
| int ast_queue_frame_head | ( | struct ast_channel * | chan, | |
| struct ast_frame * | f | |||
| ) |
Queue one or more frames to the head of a channel's frame queue.
| chan | the channel to queue the frame(s) on | |
| f | the frame(s) to queue. Note that the frame(s) will be duplicated by this function. It is the responsibility of the caller to handle freeing the memory associated with the frame(s) being passed if necessary. |
| 0 | success | |
| non-zero | failure |
Definition at line 1080 of file channel.c.
References __ast_queue_frame().
Referenced by __ast_answer(), __ast_read(), and ast_autoservice_stop().
01081 { 01082 return __ast_queue_frame(chan, fin, 1, NULL); 01083 }
| int ast_queue_hangup | ( | struct ast_channel * | chan | ) |
Queue a hangup frame.
Definition at line 1086 of file channel.c.
References ast_channel::_softhangup, ast_channel_trylock, ast_channel_unlock, AST_CONTROL_HANGUP, AST_FRAME_CONTROL, ast_queue_frame(), and AST_SOFTHANGUP_DEV.
Referenced by cleanup_connection(), cli_console_hangup(), close_call(), gtalk_hangup_farend(), gtalk_is_answered(), handle_onhook_message(), handle_request_bye(), handle_request_cancel(), handle_soft_key_event_message(), iax2_destroy(), iax2_queue_hangup(), jingle_hangup_farend(), local_hangup(), and mgcp_queue_hangup().
01087 { 01088 struct ast_frame f = { AST_FRAME_CONTROL, AST_CONTROL_HANGUP }; 01089 /* Yeah, let's not change a lock-critical value without locking */ 01090 if (!ast_channel_trylock(chan)) { 01091 chan->_softhangup |= AST_SOFTHANGUP_DEV; 01092 ast_channel_unlock(chan); 01093 } 01094 return ast_queue_frame(chan, &f); 01095 }
| int ast_queue_hangup_with_cause | ( | struct ast_channel * | chan, | |
| int | cause | |||
| ) |
Queue a hangup frame with hangupcause set.
| [in] | chan | channel to queue frame onto |
| [in] | cause | the hangup cause |
Definition at line 1098 of file channel.c.
References ast_channel::_softhangup, ast_channel_trylock, ast_channel_unlock, AST_CONTROL_HANGUP, AST_FRAME_CONTROL, ast_queue_frame(), AST_SOFTHANGUP_DEV, ast_frame::data, ast_channel::hangupcause, and ast_frame::uint32.
Referenced by __oh323_update_info(), __sip_autodestruct(), close_call(), close_client(), console_hangup(), dahdi_handle_event(), handle_request_bye(), handle_response(), handle_response_invite(), handle_response_notify(), HandleCallOutgoing(), hangup_chan(), hangup_connection(), misdn_answer(), pri_hangup_all(), retrans_pkt(), and TransferCallStep1().
01099 { 01100 struct ast_frame f = { AST_FRAME_CONTROL, AST_CONTROL_HANGUP }; 01101 01102 if (cause >= 0) 01103 f.data.uint32 = cause; 01104 01105 /* Yeah, let's not change a lock-critical value without locking */ 01106 if (!ast_channel_trylock(chan)) { 01107 chan->_softhangup |= AST_SOFTHANGUP_DEV; 01108 if (cause < 0) 01109 f.data.uint32 = chan->hangupcause; 01110 01111 ast_channel_unlock(chan); 01112 } 01113 01114 return ast_queue_frame(chan, &f); 01115 }
| int ast_raw_answer | ( | struct ast_channel * | chan, | |
| int | cdr_answer | |||
| ) |
Answer a channel.
| chan | channel to answer | |
| cdr_answer | flag to control whether any associated CDR should be marked as 'answered' |
This function answers a channel and handles all necessary call setup functions.
| 0 | on success | |
| non-zero | on failure |
Definition at line 1772 of file channel.c.
References ast_channel::_state, ast_channel_tech::answer, ast_cdr_answer(), ast_channel_lock, ast_channel_unlock, ast_check_hangup(), AST_FLAG_OUTGOING, AST_FLAG_ZOMBIE, ast_indicate(), ast_setstate(), AST_STATE_RING, AST_STATE_RINGING, AST_STATE_UP, ast_test_flag, ast_channel::cdr, ast_channel::tech, and ast_channel::visible_indication.
Referenced by __ast_answer(), and ast_bridge_call().
01773 { 01774 int res = 0; 01775 01776 ast_channel_lock(chan); 01777 01778 /* You can't answer an outbound call */ 01779 if (ast_test_flag(chan, AST_FLAG_OUTGOING)) { 01780 ast_channel_unlock(chan); 01781 return 0; 01782 } 01783 01784 /* Stop if we're a zombie or need a soft hangup */ 01785 if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) { 01786 ast_channel_unlock(chan); 01787 return -1; 01788 } 01789 01790 ast_channel_unlock(chan); 01791 01792 switch (chan->_state) { 01793 case AST_STATE_RINGING: 01794 case AST_STATE_RING: 01795 ast_channel_lock(chan); 01796 if (chan->tech->answer) { 01797 res = chan->tech->answer(chan); 01798 } 01799 ast_setstate(chan, AST_STATE_UP); 01800 if (cdr_answer) { 01801 ast_cdr_answer(chan->cdr); 01802 } 01803 ast_channel_unlock(chan); 01804 break; 01805 case AST_STATE_UP: 01806 /* Calling ast_cdr_answer when it it has previously been called 01807 * is essentially a no-op, so it is safe. 01808 */ 01809 if (cdr_answer) { 01810 ast_cdr_answer(chan->cdr); 01811 } 01812 break; 01813 default: 01814 break; 01815 } 01816 01817 ast_indicate(chan, -1); 01818 chan->visible_indication = 0; 01819 01820 return res; 01821 }
| struct ast_frame* ast_read | ( | struct ast_channel * | chan | ) | [read] |
Reads a frame.
| chan | channel to read a frame from |
Definition at line 3073 of file channel.c.
References __ast_read().
Referenced by __adsi_transmit_messages(), __ast_answer(), __ast_play_and_record(), __ast_request_and_dial(), adsi_careful_send(), agent_ack_sleep(), agent_read(), ast_feature_request_and_dial(), ast_generic_bridge(), ast_recvtext(), ast_safe_sleep_conditional(), ast_tonepair(), ast_udptl_bridge(), ast_waitfordigit_full(), async_wait(), autoservice_run(), background_detect_exec(), bridge_native_loop(), bridge_p2p_loop(), builtin_atxfer(), channel_spy(), check_goto_on_transfer(), conf_exec(), conf_flush(), conf_run(), dahdi_bridge(), dial_exec_full(), dictate_exec(), disa_exec(), do_idle_thread(), do_waiting(), echo_exec(), eivr_comm(), find_cache(), handle_recordfile(), handle_speechrecognize(), iax2_bridge(), iax_park_thread(), ices_exec(), isAnsweringMachine(), jack_exec(), launch_asyncagi(), manage_parkinglot(), masq_park_call(), measurenoise(), misdn_bridge(), monitor_dial(), mp3_exec(), NBScat_exec(), receive_dtmf_digits(), record_exec(), recordthread(), rpt(), rpt_exec(), run_agi(), send_tone_burst(), send_waveform_to_channel(), sendurl_exec(), speech_background(), ss_thread(), transmit_audio(), transmit_t38(), wait_for_answer(), wait_for_hangup(), wait_for_winner(), waitforring_exec(), and waitstream_core().
03074 { 03075 return __ast_read(chan, 0); 03076 }
| struct ast_frame* ast_read_noaudio | ( | struct ast_channel * | chan | ) | [read] |
Reads a frame, returning AST_FRAME_NULL frame if audio.
| chan | channel to read a frame from |
Definition at line 3078 of file channel.c.
References __ast_read().
Referenced by conf_run().
03079 { 03080 return __ast_read(chan, 1); 03081 }
| int ast_readstring | ( | struct ast_channel * | c, | |
| char * | s, | |||
| int | len, | |||
| int | timeout, | |||
| int | rtimeout, | |||
| char * | enders | |||
| ) |
Reads multiple digits
| c | channel to read from | |
| s | string to read in to. Must be at least the size of your length | |
| len | how many digits to read (maximum) | |
| timeout | how long to timeout between digits | |
| rtimeout | timeout to wait on the first digit | |
| enders | digits to end the string Read in a digit string "s", max length "len", maximum timeout between digits "timeout" (-1 for none), terminated by anything in "enders". Give them rtimeout for the first digit. Returns 0 on normal return, or 1 on a timeout. In the case of a timeout, any digits that were read before the timeout will still be available in s. RETURNS 2 in full version when ctrlfd is available, NOT 1 |
Definition at line 4060 of file channel.c.
References ast_readstring_full().
Referenced by __adsi_transmit_messages(), _ast_adsi_begin_download(), _ast_adsi_get_cpeinfo(), _ast_adsi_load_session(), ast_app_getdata(), dialout(), do_directory(), forward_message(), privacy_exec(), vm_authenticate(), vm_newuser(), and vm_options().
04061 { 04062 return ast_readstring_full(c, s, len, timeout, ftimeout, enders, -1, -1); 04063 }
| int ast_readstring_full | ( | struct ast_channel * | c, | |
| char * | s, | |||
| int | len, | |||
| int | timeout, | |||
| int | rtimeout, | |||
| char * | enders, | |||
| int | audiofd, | |||
| int | ctrlfd | |||
| ) |
Definition at line 4065 of file channel.c.
References ast_check_hangup(), AST_DIGIT_ANY, AST_FLAG_ZOMBIE, AST_GETDATA_COMPLETE, AST_GETDATA_EMPTY_END_TERMINATED, AST_GETDATA_FAILED, AST_GETDATA_INTERRUPTED, AST_GETDATA_TIMEOUT, ast_stopstream(), ast_test_flag, ast_waitfordigit_full(), ast_waitstream_full(), and ast_channel::stream.
Referenced by ast_app_getdata_full(), and ast_readstring().
04066 { 04067 int pos = 0; /* index in the buffer where we accumulate digits */ 04068 int to = ftimeout; 04069 04070 /* Stop if we're a zombie or need a soft hangup */ 04071 if (ast_test_flag(c, AST_FLAG_ZOMBIE) || ast_check_hangup(c)) 04072 return -1; 04073 if (!len) 04074 return -1; 04075 for (;;) { 04076 int d; 04077 if (c->stream) { 04078 d = ast_waitstream_full(c, AST_DIGIT_ANY, audiofd, ctrlfd); 04079 ast_stopstream(c); 04080 usleep(1000); 04081 if (!d) 04082 d = ast_waitfordigit_full(c, to, audiofd, ctrlfd); 04083 } else { 04084 d = ast_waitfordigit_full(c, to, audiofd, ctrlfd); 04085 } 04086 if (d < 0) 04087 return AST_GETDATA_FAILED; 04088 if (d == 0) { 04089 s[pos] = '\0'; 04090 return AST_GETDATA_TIMEOUT; 04091 } 04092 if (d == 1) { 04093 s[pos] = '\0'; 04094 return AST_GETDATA_INTERRUPTED; 04095 } 04096 if (strchr(enders, d) && (pos == 0)) { 04097 s[pos] = '\0'; 04098 return AST_GETDATA_EMPTY_END_TERMINATED; 04099 } 04100 if (!strchr(enders, d)) { 04101 s[pos++] = d; 04102 } 04103 if (strchr(enders, d) || (pos >= len)) { 04104 s[pos] = '\0'; 04105 return AST_GETDATA_COMPLETE; 04106 } 04107 to = timeout; 04108 } 04109 /* Never reached */ 04110 return 0; 04111 }
| int ast_recvchar | ( | struct ast_channel * | chan, | |
| int | timeout | |||
| ) |
Receives a text character from a channel.
| chan | channel to act upon | |
| timeout | timeout in milliseconds (0 for infinite wait) Read a char of text from a channel Returns 0 on success, -1 on failure |
Definition at line 3236 of file channel.c.
References ast_free, and ast_recvtext().
Referenced by handle_recvchar().
03237 { 03238 int c; 03239 char *buf = ast_recvtext(chan, timeout); 03240 if (buf == NULL) 03241 return -1; /* error or timeout */ 03242 c = *(unsigned char *)buf; 03243 ast_free(buf); 03244 return c; 03245 }
| char* ast_recvtext | ( | struct ast_channel * | chan, | |
| int | timeout | |||
| ) |
Receives a text string from a channel Read a string of text from a channel.
| chan | channel to act upon | |
| timeout | timeout in milliseconds (0 for infinite wait) |
Definition at line 3247 of file channel.c.
References ast_check_hangup(), AST_CONTROL_HANGUP, AST_FRAME_CONTROL, AST_FRAME_TEXT, ast_frfree, ast_read(), ast_strndup, ast_waitfor(), ast_frame::data, ast_frame::datalen, f, ast_frame::frametype, ast_frame::ptr, and ast_frame::subclass.
Referenced by ast_recvchar(), and handle_recvtext().
03248 { 03249 int res, done = 0; 03250 char *buf = NULL; 03251 03252 while (!done) { 03253 struct ast_frame *f; 03254 if (ast_check_hangup(chan)) 03255 break; 03256 res = ast_waitfor(chan, timeout); 03257 if (res <= 0) /* timeout or error */ 03258 break; 03259 timeout = res; /* update timeout */ 03260 f = ast_read(chan); 03261 if (f == NULL) 03262 break; /* no frame */ 03263 if (f->frametype == AST_FRAME_CONTROL && f->subclass == AST_CONTROL_HANGUP) 03264 done = 1; /* force a break */ 03265 else if (f->frametype == AST_FRAME_TEXT) { /* what we want */ 03266 buf = ast_strndup((char *) f->data.ptr, f->datalen); /* dup and break */ 03267 done = 1; 03268 } 03269 ast_frfree(f); 03270 } 03271 return buf; 03272 }
| struct ast_channel* ast_request | ( | const char * | type, | |
| int | format, | |||
| void * | data, | |||
| int * | status | |||
| ) | [read] |
Requests a channel.
| type | type of channel to request | |
| format | requested channel format (codec) | |
| data | data to pass to the channel requester | |
| status | status |
Request a channel of a given type, with data as optional information used by the low level module
| NULL | failure | |
| non-NULL | channel on success |
Definition at line 3958 of file channel.c.
References AST_CAUSE_BEARERCAPABILITY_NOTAVAIL, AST_CAUSE_NOSUCHDRIVER, AST_CAUSE_NOTDEFINED, AST_FORMAT_AUDIO_MASK, AST_FORMAT_TEXT_MASK, AST_FORMAT_VIDEO_MASK, AST_LIST_TRAVERSE, ast_log(), AST_RWLIST_RDLOCK, AST_RWLIST_UNLOCK, ast_translator_best_choice(), ast_channel_tech::capabilities, capabilities, channels, LOG_WARNING, ast_channel_tech::requester, chanlist::tech, and ast_channel_tech::type.
Referenced by __ast_request_and_dial(), agent_request(), ast_call_forward(), ast_feature_request_and_dial(), attempt_reconnect(), begin_dial_channel(), build_conf(), chanavail_exec(), conf_run(), connect_link(), dial_exec_full(), do_forward(), findmeexec(), ring_entry(), rpt(), rpt_call(), rpt_exec(), rpt_tele_thread(), and wait_for_answer().
03959 { 03960 struct chanlist *chan; 03961 struct ast_channel *c; 03962 int capabilities; 03963 int fmt; 03964 int res; 03965 int foo; 03966 int videoformat = format & AST_FORMAT_VIDEO_MASK; 03967 int textformat = format & AST_FORMAT_TEXT_MASK; 03968 03969 if (!cause) 03970 cause = &foo; 03971 *cause = AST_CAUSE_NOTDEFINED; 03972 03973 if (AST_RWLIST_RDLOCK(&channels)) { 03974 ast_log(LOG_WARNING, "Unable to lock channel list\n"); 03975 return NULL; 03976 } 03977 03978 AST_LIST_TRAVERSE(&backends, chan, list) { 03979 if (strcasecmp(type, chan->tech->type)) 03980 continue; 03981 03982 capabilities = chan->tech->capabilities; 03983 fmt = format & AST_FORMAT_AUDIO_MASK; 03984 if (fmt) { 03985 /* We have audio - is it possible to connect the various calls to each other? 03986 (Avoid this check for calls without audio, like text+video calls) 03987 */ 03988 res = ast_translator_best_choice(&fmt, &capabilities); 03989 if (res < 0) { 03990 ast_log(LOG_WARNING, "No translator path exists for channel type %s (native 0x%x) to 0x%x\n", type, chan->tech->capabilities, format); 03991 *cause = AST_CAUSE_BEARERCAPABILITY_NOTAVAIL; 03992 AST_RWLIST_UNLOCK(&channels); 03993 return NULL; 03994 } 03995 } 03996 AST_RWLIST_UNLOCK(&channels); 03997 if (!chan->tech->requester) 03998 return NULL; 03999 04000 if (!(c = chan->tech->requester(type, capabilities | videoformat | textformat, data, cause))) 04001 return NULL; 04002 04003 /* no need to generate a Newchannel event here; it is done in the channel_alloc call */ 04004 return c; 04005 } 04006 04007 ast_log(LOG_WARNING, "No channel type registered for '%s'\n", type); 04008 *cause = AST_CAUSE_NOSUCHDRIVER; 04009 AST_RWLIST_UNLOCK(&channels); 04010 04011 return NULL; 04012 }
| struct ast_channel* ast_request_and_dial | ( | const char * | type, | |
| int | format, | |||
| void * | data, | |||
| int | timeout, | |||
| int * | reason, | |||
| const char * | cid_num, | |||
| const char * | cid_name | |||
| ) | [read] |
Request a channel of a given type, with data as optional information used by the low level module and attempt to place a call on it.
| type | type of channel to request | |
| format | requested channel format | |
| data | data to pass to the channel requester | |
| timeout | maximum amount of time to wait for an answer | |
| reason | why unsuccessful (if unsuccessful) | |
| cid_num | Caller-ID Number | |
| cid_name | Caller-ID Name (ascii) |
Definition at line 3953 of file channel.c.
References __ast_request_and_dial().
Referenced by ast_pbx_outgoing_exten().
03954 { 03955 return __ast_request_and_dial(type, format, data, timeout, outstate, cidnum, cidname, NULL); 03956 }
| int ast_safe_sleep | ( | struct ast_channel * | chan, | |
| int | ms | |||
| ) |
Wait for a specified amount of time, looking for hangups.
| chan | channel to wait for | |
| ms | length of time in milliseconds to sleep Waits for a specified amount of time, servicing the channel as required. |
Definition at line 1344 of file channel.c.
References ast_safe_sleep_conditional().
Referenced by _ast_adsi_transmit_message_full(), alarmreceiver_exec(), ast_dtmf_stream(), ast_senddigit(), builtin_atxfer(), builtin_parkcall(), conf_run(), dictate_exec(), disa_exec(), flash_exec(), function_ilink(), handle_callforward_button(), login_exec(), mgcp_ss(), milliwatt_exec(), misdn_check_l2l1(), old_milliwatt_exec(), park_call_exec(), pbx_builtin_wait(), play_moh_exec(), play_tone_pair(), playtone(), privacy_exec(), receive_ademco_contact_id(), rpt_call(), rpt_exec(), rpt_tele_thread(), send_morse(), send_tone_telemetry(), skinny_ss(), ss_thread(), testclient_exec(), testserver_exec(), try_calling(), wait_for_hangup(), wait_interval(), wait_moh_exec(), waituntil_exec(), and zapateller_exec().
01345 { 01346 return ast_safe_sleep_conditional(chan, ms, NULL, NULL); 01347 }
| int ast_safe_sleep_conditional | ( | struct ast_channel * | chan, | |
| int | ms, | |||
| int(*)(void *) | cond, | |||
| void * | data | |||
| ) |
Wait for a specified amount of time, looking for hangups and a condition argument.
| chan | channel to wait for | |
| ms | length of time in milliseconds to sleep | |
| cond | a function pointer for testing continue condition | |
| data | argument to be passed to the condition test function |
Definition at line 1305 of file channel.c.
References ast_channel_start_silence_generator(), ast_channel_stop_silence_generator(), ast_frfree, ast_opt_transmit_silence, ast_read(), ast_waitfor(), cond, f, and ast_channel::generatordata.
Referenced by ast_safe_sleep(), and login_exec().
01306 { 01307 struct ast_frame *f; 01308 struct ast_silence_generator *silgen = NULL; 01309 int res = 0; 01310 01311 /* If no other generator is present, start silencegen while waiting */ 01312 if (ast_opt_transmit_silence && !chan->generatordata) { 01313 silgen = ast_channel_start_silence_generator(chan); 01314 } 01315 01316 while (ms > 0) { 01317 if (cond && ((*cond)(data) == 0)) { 01318 break; 01319 } 01320 ms = ast_waitfor(chan, ms); 01321 if (ms < 0) { 01322 res = -1; 01323 break; 01324 } 01325 if (ms > 0) { 01326 f = ast_read(chan); 01327 if (!f) { 01328 res = -1; 01329 break; 01330 } 01331 ast_frfree(f); 01332 } 01333 } 01334 01335 /* stop silgen if present */ 01336 if (silgen) { 01337 ast_channel_stop_silence_generator(chan, silgen); 01338 } 01339 01340 return res; 01341 }
| static int ast_select | ( | int | nfds, | |
| fd_set * | rfds, | |||
| fd_set * | wfds, | |||
| fd_set * | efds, | |||
| struct timeval * | tvp | |||
| ) | [inline, static] |
Waits for activity on a group of channels.
| nfds | the maximum number of file descriptors in the sets | |
| rfds | file descriptors to check for read availability | |
| wfds | file descriptors to check for write availability | |
| efds | file descriptors to check for exceptions (OOB data) | |
| tvp | timeout while waiting for events This is the same as a standard select(), except it guarantees the behaviour where the passed struct timeval is updated with how much time was not slept while waiting for the specified events |
Definition at line 1713 of file channel.h.
Referenced by aji_io_recv(), ast_stun_request(), dispatch_thread_handler(), do_monitor(), do_parking_thread(), and hidthread().
01714 { 01715 #ifdef __linux__ 01716 return select(nfds, rfds, wfds, efds, tvp); 01717 #else 01718 if (tvp) { 01719 struct timeval tv, tvstart, tvend, tvlen; 01720 int res; 01721 01722 tv = *tvp; 01723 gettimeofday(&tvstart, NULL); 01724 res = select(nfds, rfds, wfds, efds, tvp); 01725 gettimeofday(&tvend, NULL); 01726 timersub(&tvend, &tvstart, &tvlen); 01727 timersub(&tv, &tvlen, tvp); 01728 if (tvp->tv_sec < 0 || (tvp->tv_sec == 0 && tvp->tv_usec < 0)) { 01729 tvp->tv_sec = 0; 01730 tvp->tv_usec = 0; 01731 } 01732 return res; 01733 } 01734 else 01735 return select(nfds, rfds, wfds, efds, NULL); 01736 #endif 01737 }
| int ast_senddigit | ( | struct ast_channel * | chan, | |
| char | digit, | |||
| unsigned int | duration | |||
| ) |
Send a DTMF digit to a channel Send a DTMF digit to a channel.
| chan | channel to act upon | |
| digit | the DTMF digit to send, encoded in ASCII | |
| duration | the duration of the digit ending in ms |
Definition at line 3345 of file channel.c.
References AST_DEFAULT_EMULATE_DTMF_DURATION, ast_safe_sleep(), ast_senddigit_begin(), ast_senddigit_end(), ast_channel_tech::send_digit_begin, and ast_channel::tech.
Referenced by ast_dtmf_stream(), dial_exec_full(), do_dtmf_phone(), manager_play_dtmf(), and rpt_call().
03346 { 03347 if (chan->tech->send_digit_begin) { 03348 ast_senddigit_begin(chan, digit); 03349 ast_safe_sleep(chan, (duration >= AST_DEFAULT_EMULATE_DTMF_DURATION ? duration : AST_DEFAULT_EMULATE_DTMF_DURATION)); 03350 } 03351 03352 return ast_senddigit_end(chan, digit, (duration >= AST_DEFAULT_EMULATE_DTMF_DURATION ? duration : AST_DEFAULT_EMULATE_DTMF_DURATION)); 03353 }
| int ast_senddigit_begin | ( | struct ast_channel * | chan, | |
| char | digit | |||
| ) |
Send a DTMF digit to a channel Send a DTMF digit to a channel.
| chan | channel to act upon | |
| digit | the DTMF digit to send, encoded in ASCII |
Definition at line 3287 of file channel.c.
References ast_debug, ast_playtones_start(), ast_channel_tech::send_digit_begin, and ast_channel::tech.
Referenced by agent_digit_begin(), ast_senddigit(), and ast_write().
03288 { 03289 /* Device does not support DTMF tones, lets fake 03290 * it by doing our own generation. */ 03291 static const char* dtmf_tones[] = { 03292 "941+1336", /* 0 */ 03293 "697+1209", /* 1 */ 03294 "697+1336", /* 2 */ 03295 "697+1477", /* 3 */ 03296 "770+1209", /* 4 */ 03297 "770+1336", /* 5 */ 03298 "770+1477", /* 6 */ 03299 "852+1209", /* 7 */ 03300 "852+1336", /* 8 */ 03301 "852+1477", /* 9 */ 03302 "697+1633", /* A */ 03303 "770+1633", /* B */ 03304 "852+1633", /* C */ 03305 "941+1633", /* D */ 03306 "941+1209", /* * */ 03307 "941+1477" /* # */ 03308 }; 03309 03310 if (!chan->tech->send_digit_begin) 03311 return 0; 03312 03313 if (!chan->tech->send_digit_begin(chan, digit)) 03314 return 0; 03315 03316 if (digit >= '0' && digit <='9') 03317 ast_playtones_start(chan, 0, dtmf_tones[digit-'0'], 0); 03318 else if (digit >= 'A' && digit <= 'D') 03319 ast_playtones_start(chan, 0, dtmf_tones[digit-'A'+10], 0); 03320 else if (digit == '*') 03321 ast_playtones_start(chan, 0, dtmf_tones[14], 0); 03322 else if (digit == '#') 03323 ast_playtones_start(chan, 0, dtmf_tones[15], 0); 03324 else { 03325 /* not handled */ 03326 ast_debug(1, "Unable to generate DTMF tone '%c' for '%s'\n", digit, chan->name); 03327 } 03328 03329 return 0; 03330 }
| int ast_senddigit_end | ( | struct ast_channel * | chan, | |
| char | digit, | |||
| unsigned int | duration | |||
| ) |
Send a DTMF digit to a channel.
Send a DTMF digit to a channel.
| chan | channel to act upon | |
| digit | the DTMF digit to send, encoded in ASCII | |
| duration | the duration of the digit ending in ms |
Definition at line 3332 of file channel.c.
References ast_playtones_stop(), ast_channel::generator, ast_channel_tech::send_digit_end, and ast_channel::tech.
Referenced by agent_digit_end(), ast_senddigit(), and ast_write().
03333 { 03334 int res = -1; 03335 03336 if (chan->tech->send_digit_end) 03337 res = chan->tech->send_digit_end(chan, digit, duration); 03338 03339 if (res && chan->generator) 03340 ast_playtones_stop(chan); 03341 03342 return 0; 03343 }
| int ast_sendtext | ( | struct ast_channel * | chan, | |
| const char * | text | |||
| ) |
Sends text to a channel.
| chan | channel to act upon | |
| text | string of text to send on the channel |
Write text to a display on a channel
| 0 | on success | |
| -1 | on failure |
Definition at line 3274 of file channel.c.
References ast_check_hangup(), ast_clear_flag, AST_FLAG_BLOCKING, AST_FLAG_ZOMBIE, ast_test_flag, CHECK_BLOCKING, ast_channel_tech::send_text, and ast_channel::tech.
Referenced by action_sendtext(), agent_sendtext(), handle_sendtext(), send_newkey(), and sendtext_exec().
03275 { 03276 int res = 0; 03277 /* Stop if we're a zombie or need a soft hangup */ 03278 if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) 03279 return -1; 03280 CHECK_BLOCKING(chan); 03281 if (chan->tech->send_text) 03282 res = chan->tech->send_text(chan, text); 03283 ast_clear_flag(chan, AST_FLAG_BLOCKING); 03284 return res; 03285 }
| void ast_set_callerid | ( | struct ast_channel * | chan, | |
| const char * | cid_num, | |||
| const char * | cid_name, | |||
| const char * | cid_ani | |||
| ) |
Set caller ID number, name and ANI.
Definition at line 4642 of file channel.c.
References ast_channel_lock, ast_channel_unlock, ast_free, ast_strdup, ast_channel::cid, ast_callerid::cid_ani, ast_callerid::cid_name, ast_callerid::cid_num, and report_new_callerid().
Referenced by __ast_request_and_dial(), agent_call(), ast_call_forward(), ast_feature_request_and_dial(), callerid_write(), dahdi_read(), dial_exec_full(), disa_exec(), do_forward(), findmeexec(), handle_setcallerid(), mgcp_ss(), privacy_exec(), read_config(), rpt_exec(), skinny_newcall(), and ss_thread().
04643 { 04644 ast_channel_lock(chan); 04645 04646 if (cid_num) { 04647 if (chan->cid.cid_num) 04648 ast_free(chan->cid.cid_num); 04649 chan->cid.cid_num = ast_strdup(cid_num); 04650 } 04651 if (cid_name) { 04652 if (chan->cid.cid_name) 04653 ast_free(chan->cid.cid_name); 04654 chan->cid.cid_name = ast_strdup(cid_name); 04655 } 04656 if (cid_ani) { 04657 if (chan->cid.cid_ani) 04658 ast_free(chan->cid.cid_ani); 04659 chan->cid.cid_ani = ast_strdup(cid_ani); 04660 } 04661 04662 report_new_callerid(chan); 04663 04664 ast_channel_unlock(chan); 04665 }
| int ast_set_read_format | ( | struct ast_channel * | chan, | |
| int | format | |||
| ) |
Sets read format on channel chan Set read format for channel to whichever component of "format" is best.
| chan | channel to change | |
| format | format to change to |
Definition at line 3703 of file channel.c.
References ast_channel::rawreadformat, ast_channel::readformat, ast_channel::readtrans, and set_format().
Referenced by __ast_play_and_record(), __oh323_update_info(), _ast_adsi_transmit_message_full(), agent_call(), alarmreceiver_exec(), ast_channel_make_compatible_helper(), ast_do_masquerade(), attempt_reconnect(), background_detect_exec(), build_conf(), conf_run(), connect_link(), dictate_exec(), do_waiting(), eagi_exec(), echo_exec(), gtalk_rtp_read(), handle_recordfile(), handle_speechrecognize(), ices_exec(), isAnsweringMachine(), jack_exec(), jingle_rtp_read(), login_exec(), measurenoise(), mgcp_rtp_read(), oh323_rtp_read(), old_milliwatt_exec(), process_sdp(), record_exec(), rpt(), rpt_exec(), setup_rtp_connection(), sip_rtp_read(), skinny_rtp_read(), socket_process(), speech_background(), transmit_audio(), and unistim_rtp_read().
03704 { 03705 return set_format(chan, fmt, &chan->rawreadformat, &chan->readformat, 03706 &chan->readtrans, 0); 03707 }
| void ast_set_variables | ( | struct ast_channel * | chan, | |
| struct ast_variable * | vars | |||
| ) |
adds a list of channel variables to a channel
| chan | the channel | |
| vars | a linked list of variables |
Variable names can be for a regular channel variable or a dialplan function that has the ability to be written to.
Definition at line 5564 of file channel.c.
References ast_variable::name, ast_variable::next, pbx_builtin_setvar_helper(), and ast_variable::value.
Referenced by __ast_request_and_dial(), ast_call_forward(), ast_pbx_outgoing_app(), and ast_pbx_outgoing_exten().
05565 { 05566 struct ast_variable *cur; 05567 05568 for (cur = vars; cur; cur = cur->next) 05569 pbx_builtin_setvar_helper(chan, cur->name, cur->value); 05570 }
| int ast_set_write_format | ( | struct ast_channel * | chan, | |
| int | format | |||
| ) |
Sets write format on channel chan Set write format for channel to whichever component of "format" is best.
| chan | channel to change | |
| format | new format for writing |
Definition at line 3709 of file channel.c.
References ast_channel::rawwriteformat, set_format(), ast_channel::writeformat, and ast_channel::writetrans.
Referenced by __oh323_update_info(), _ast_adsi_transmit_message_full(), agent_call(), alarmreceiver_exec(), ast_channel_make_compatible_helper(), ast_channel_start_silence_generator(), ast_channel_stop_silence_generator(), ast_do_masquerade(), ast_openstream_full(), ast_stopstream(), attempt_reconnect(), build_conf(), chanspy_exec(), conf_run(), connect_link(), echo_exec(), extenspy_exec(), gtalk_rtp_read(), jack_exec(), jingle_rtp_read(), linear_alloc(), linear_release(), login_exec(), mgcp_rtp_read(), moh_alloc(), moh_files_release(), moh_release(), mp3_exec(), NBScat_exec(), oh323_rtp_read(), old_milliwatt_exec(), playtones_alloc(), playtones_release(), process_sdp(), rpt(), rpt_exec(), send_waveform_to_channel(), setup_rtp_connection(), sip_rtp_read(), skinny_rtp_read(), socket_process(), tonepair_alloc(), tonepair_release(), transmit_audio(), and unistim_rtp_read().
03710 { 03711 return set_format(chan, fmt, &chan->rawwriteformat, &chan->writeformat, 03712 &chan->writetrans, 1); 03713 }
| int ast_setstate | ( | struct ast_channel * | chan, | |
| enum | ast_channel_state | |||
| ) |
Change the state of a channel.
Definition at line 4667 of file channel.c.
References ast_channel::_state, AST_CHANNEL_NAME, ast_copy_string(), AST_DEVICE_UNKNOWN, ast_devstate_changed_literal(), ast_state2str(), ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, EVENT_FLAG_CALL, manager_event, name, and S_OR.
Referenced by __ast_read(), __dahdi_exception(), __oh323_update_info(), agent_call(), alsa_answer(), ast_raw_answer(), cb_events(), check_availability(), console_answer(), dahdi_answer(), dahdi_call(), dahdi_handle_event(), dahdi_indicate(), dahdi_read(), do_bridge_masquerade(), gtalk_call(), gtalk_newcall(), handle_invite_replaces(), handle_offhook_message(), handle_request_invite(), handle_response_invite(), handle_soft_key_event_message(), handle_stimulus_message(), iax2_call(), jingle_call(), jingle_newcall(), local_queue_frame(), mgcp_answer(), mgcp_call(), mgcp_ss(), misdn_call(), misdn_indication(), nbs_call(), nbs_hangup(), oh323_answer(), oss_answer(), pbx_builtin_busy(), pbx_builtin_congestion(), phone_answer(), phone_call(), phone_exception(), phone_hangup(), phone_write(), release_chan(), release_chan_early(), sip_answer(), skinny_answer(), skinny_call(), skinny_newcall(), ss_thread(), unistim_answer(), unistim_call(), unistim_new(), unistim_ss(), update_state(), usbradio_answer(), and usbradio_call().
04668 { 04669 int oldstate = chan->_state; 04670 char name[AST_CHANNEL_NAME], *dashptr; 04671 04672 if (oldstate == state) 04673 return 0; 04674 04675 ast_copy_string(name, chan->name, sizeof(name)); 04676 if ((dashptr = strrchr(name, '-'))) { 04677 *dashptr = '\0'; 04678 } 04679 04680 chan->_state = state; 04681 04682 /* We have to pass AST_DEVICE_UNKNOWN here because it is entirely possible that the channel driver 04683 * for this channel is using the callback method for device state. If we pass in an actual state here 04684 * we override what they are saying the state is and things go amuck. */ 04685 ast_devstate_changed_literal(AST_DEVICE_UNKNOWN, name); 04686 04687 /* setstate used to conditionally report Newchannel; this is no more */ 04688 manager_event(EVENT_FLAG_CALL, 04689 "Newstate", 04690 "Channel: %s\r\n" 04691 "ChannelState: %d\r\n" 04692 "ChannelStateDesc: %s\r\n" 04693 "CallerIDNum: %s\r\n" 04694 "CallerIDName: %s\r\n" 04695 "Uniqueid: %s\r\n", 04696 chan->name, chan->_state, ast_state2str(chan->_state), 04697 S_OR(chan->cid.cid_num, ""), 04698 S_OR(chan->cid.cid_name, ""), 04699 chan->uniqueid); 04700 04701 return 0; 04702 }
| int ast_settimeout | ( | struct ast_channel * | c, | |
| unsigned int | rate, | |||
| int(*)(const void *data) | func, | |||
| void * | data | |||
| ) |
Enable or disable timer ticks for a channel.
| rate | number of timer ticks per second |
If timers are supported, force a scheduled expiration on the timer fd, at which point we call the callback function / data
Call this function with a rate of 0 to turn off the timer ticks
Definition at line 2378 of file channel.c.
References ast_channel_lock, ast_channel_unlock, ast_debug, ast_timer_get_max_rate(), ast_timer_set_rate(), ast_channel::timer, ast_channel::timingdata, ast_channel::timingfd, and ast_channel::timingfunc.
Referenced by ast_activate_generator(), ast_closestream(), ast_deactivate_generator(), ast_read_generator_actions(), ast_readaudio_callback(), and filestream_destructor().
02379 { 02380 int res; 02381 unsigned int real_rate = rate, max_rate; 02382 02383 ast_channel_lock(c); 02384 02385 if (c->timingfd == -1) { 02386 ast_channel_unlock(c); 02387 return -1; 02388 } 02389 02390 if (!func) { 02391 rate = 0; 02392 data = NULL; 02393 } 02394 02395 if (rate && rate > (max_rate = ast_timer_get_max_rate(c->timer))) { 02396 real_rate = max_rate; 02397 } 02398 02399 ast_debug(1, "Scheduling timer at (%u requested / %u actual) timer ticks per second\n", rate, real_rate); 02400 02401 res = ast_timer_set_rate(c->timer, real_rate); 02402 02403 c->timingfunc = func; 02404 c->timingdata = data; 02405 02406 ast_channel_unlock(c); 02407 02408 return res; 02409 }
| int ast_shutting_down | ( | void | ) |
Returns non-zero if Asterisk is being shut down.
Returns non-zero if Asterisk is being shut down
Definition at line 516 of file channel.c.
Referenced by handle_request_options().
00517 { 00518 return shutting_down; 00519 }
| int ast_softhangup | ( | struct ast_channel * | chan, | |
| int | cause | |||
| ) |
Softly hangup up a channel.
| chan | channel to be soft-hung-up | |
| reason | an AST_SOFTHANGUP_* reason code |
Call the protocol layer, but don't destroy the channel structure (use this if you are trying to safely hangup a channel managed by another thread.
Definition at line 1639 of file channel.c.
References ast_channel_lock, ast_channel_unlock, and ast_softhangup_nolock().
Referenced by __ast_module_user_hangup_all(), __ast_pbx_run(), __unload_module(), action_hangup(), agent_hangup(), agent_logoff(), agent_read(), ast_begin_shutdown(), ast_dial_join(), birdbath(), conf_free(), connect_link(), dahdi_handle_event(), flush_telem(), function_ilink(), handle_hangup(), handle_link_data(), handle_softhangup(), login_exec(), manager_park(), read_agent_config(), rpt(), rpt_call(), rpt_do_restart(), rpt_exec(), sla_handle_hold_event(), softhangup_exec(), start_spying(), startmon(), and unload_module().
01640 { 01641 int res; 01642 01643 ast_channel_lock(chan); 01644 res = ast_softhangup_nolock(chan, cause); 01645 ast_channel_unlock(chan); 01646 01647 return res; 01648 }
| int ast_softhangup_nolock | ( | struct ast_channel * | chan, | |
| int | cause | |||
| ) |
Softly hangup up a channel (no channel lock).
| chan | channel to be soft-hung-up | |
| reason | an AST_SOFTHANGUP_* reason code |
Definition at line 1626 of file channel.c.
References ast_channel::_softhangup, ast_debug, AST_FLAG_BLOCKING, ast_null_frame, ast_queue_frame(), ast_test_flag, and ast_channel::blocker.
Referenced by ast_async_goto(), ast_softhangup(), attempt_transfer(), check_rtp_timeout(), dahdi_softhangup_all(), oh323_indicate(), proc_session_timer(), sip_indicate(), and skinny_indicate().
01627 { 01628 ast_debug(1, "Soft-Hanging up channel '%s'\n", chan->name); 01629 /* Inform channel driver that we need to be hung up, if it cares */ 01630 chan->_softhangup |= cause; 01631 ast_queue_frame(chan, &ast_null_frame); 01632 /* Interrupt any poll call or such */ 01633 if (ast_test_flag(chan, AST_FLAG_BLOCKING)) 01634 pthread_kill(chan->blocker, SIGURG); 01635 return 0; 01636 }
| const char* ast_state2str | ( | enum ast_channel_state | state | ) |
Gives the string form of a given channel state.
Gives the string form of a given channel state
| ast_channel_state | state to get the name of Give a name to a state Returns the text form of the binary state given |
Definition at line 657 of file channel.c.
References AST_STATE_BUSY, AST_STATE_DIALING, AST_STATE_DIALING_OFFHOOK, AST_STATE_DOWN, AST_STATE_OFFHOOK, AST_STATE_PRERING, AST_STATE_RESERVED, AST_STATE_RING, AST_STATE_RINGING, AST_STATE_UP, ast_threadstorage_get(), and STATE2STR_BUFSIZE.
Referenced by __ast_channel_alloc_ap(), action_coreshowchannels(), action_status(), agent_hangup(), ast_do_masquerade(), ast_setstate(), attempt_transfer(), func_channel_read(), handle_chanlist(), handle_invite_replaces(), handle_showchan(), local_attended_transfer(), mgcp_new(), serialize_showchan(), and sip_hangup().
00658 { 00659 char *buf; 00660 00661 switch (state) { 00662 case AST_STATE_DOWN: 00663 return "Down"; 00664 case AST_STATE_RESERVED: 00665 return "Rsrvd"; 00666 case AST_STATE_OFFHOOK: 00667 return "OffHook"; 00668 case AST_STATE_DIALING: 00669 return "Dialing"; 00670 case AST_STATE_RING: 00671 return "Ring"; 00672 case AST_STATE_RINGING: 00673 return "Ringing"; 00674 case AST_STATE_UP: 00675 return "Up"; 00676 case AST_STATE_BUSY: 00677 return "Busy"; 00678 case AST_STATE_DIALING_OFFHOOK: 00679 return "Dialing Offhook"; 00680 case AST_STATE_PRERING: 00681 return "Pre-ring"; 00682 default: 00683 if (!(buf = ast_threadstorage_get(&state2str_threadbuf, STATE2STR_BUFSIZE))) 00684 return "Unknown"; 00685 snprintf(buf, STATE2STR_BUFSIZE, "Unknown (%d)", state); 00686 return buf; 00687 } 00688 }
| int ast_str2cause | ( | const char * | name | ) |
| int ast_tonepair | ( | struct ast_channel * | chan, | |
| int | freq1, | |||
| int | freq2, | |||
| int | duration, | |||
| int | vol | |||
| ) |
Play a tone pair for a given amount of time
Definition at line 5439 of file channel.c.
References ast_frfree, ast_read(), ast_tonepair_start(), ast_waitfor(), f, and ast_channel::generatordata.
Referenced by zapateller_exec().
05440 { 05441 int res; 05442 05443 if ((res = ast_tonepair_start(chan, freq1, freq2, duration, vol))) 05444 return res; 05445 05446 /* Give us some wiggle room */ 05447 while (chan->generatordata && ast_waitfor(chan, 100) >= 0) { 05448 struct ast_frame *f = ast_read(chan); 05449 if (f) 05450 ast_frfree(f); 05451 else 05452 return -1; 05453 } 05454 return 0; 05455 }
| int ast_tonepair_start | ( | struct ast_channel * | chan, | |
| int | freq1, | |||
| int | freq2, | |||
| int | duration, | |||
| int | vol | |||
| ) |
Start a tone going
Definition at line 5421 of file channel.c.
References ast_activate_generator(), tonepair_def::duration, tonepair_def::freq1, tonepair_def::freq2, tonepair, and tonepair_def::vol.
Referenced by ast_tonepair(), pbx_builtin_waitexten(), play_dialtone(), play_tone_pair(), rpt_tele_thread(), and sendnoise().
| void ast_tonepair_stop | ( | struct ast_channel * | chan | ) |
Stop a tone from playing
Definition at line 5434 of file channel.c.
References ast_deactivate_generator().
Referenced by sendnoise().
05435 { 05436 ast_deactivate_generator(chan); 05437 }
| int ast_transfer | ( | struct ast_channel * | chan, | |
| char * | dest | |||
| ) |
Transfer a channel (if supported). Returns -1 on error, 0 if not supported and 1 if supported and requested.
| chan | current channel | |
| dest | destination extension for transfer |
Transfer a channel (if supported). Returns -1 on error, 0 if not supported and 1 if supported and requested.
Called by:
Definition at line 4042 of file channel.c.
References ast_channel_lock, ast_channel_unlock, ast_check_hangup(), AST_FLAG_ZOMBIE, ast_test_flag, ast_channel::tech, and ast_channel_tech::transfer.
Referenced by transfer_exec().
04043 { 04044 int res = -1; 04045 04046 /* Stop if we're a zombie or need a soft hangup */ 04047 ast_channel_lock(chan); 04048 if (!ast_test_flag(chan, AST_FLAG_ZOMBIE) && !ast_check_hangup(chan)) { 04049 if (chan->tech->transfer) { 04050 res = chan->tech->transfer(chan, dest); 04051 if (!res) 04052 res = 1; 04053 } else 04054 res = 0; 04055 } 04056 ast_channel_unlock(chan); 04057 return res; 04058 }
| char* ast_transfercapability2str | ( | int | transfercapability | ) | const |
Gives the string form of a given transfer capability.
Gives the string form of a given transfer capability
| transfercapability | transfercapabilty to get the name of Give a name to a transfercapbility See above Returns the text form of the binary transfer capability |
Definition at line 691 of file channel.c.
References AST_TRANS_CAP_3_1K_AUDIO, AST_TRANS_CAP_DIGITAL, AST_TRANS_CAP_DIGITAL_W_TONES, AST_TRANS_CAP_RESTRICTED_DIGITAL, AST_TRANS_CAP_SPEECH, and AST_TRANS_CAP_VIDEO.
Referenced by cb_events(), dahdi_call(), dahdi_new(), misdn_call(), and oh323_call().
00692 { 00693 switch (transfercapability) { 00694 case AST_TRANS_CAP_SPEECH: 00695 return "SPEECH"; 00696 case AST_TRANS_CAP_DIGITAL: 00697 return "DIGITAL"; 00698 case AST_TRANS_CAP_RESTRICTED_DIGITAL: 00699 return "RESTRICTED_DIGITAL"; 00700 case AST_TRANS_CAP_3_1K_AUDIO: 00701 return "3K1AUDIO"; 00702 case AST_TRANS_CAP_DIGITAL_W_TONES: 00703 return "DIGITAL_W_TONES"; 00704 case AST_TRANS_CAP_VIDEO: 00705 return "VIDEO"; 00706 default: 00707 return "UNKNOWN"; 00708 } 00709 }
| int ast_waitfor | ( | struct ast_channel * | chan, | |
| int | ms | |||
| ) |
Wait for input on a channel.
| chan | channel to wait on | |
| ms | length of time to wait on the channel Wait for input on a channel for a given # of milliseconds (<0 for indefinite). |
Definition at line 2362 of file channel.c.
References ast_waitfor_nandfds().
Referenced by __adsi_transmit_messages(), __ast_answer(), __ast_play_and_record(), __ast_request_and_dial(), adsi_careful_send(), agent_ack_sleep(), ast_dtmf_stream(), ast_recvtext(), ast_safe_sleep_conditional(), ast_tonepair(), async_wait(), background_detect_exec(), channel_spy(), conf_exec(), conf_flush(), dictate_exec(), disa_exec(), do_idle_thread(), do_waiting(), echo_exec(), handle_recordfile(), handle_speechrecognize(), ices_exec(), isAnsweringMachine(), jack_exec(), launch_asyncagi(), measurenoise(), mp3_exec(), NBScat_exec(), receive_dtmf_digits(), record_exec(), recordthread(), send_tone_burst(), send_waveform_to_channel(), sendurl_exec(), speech_background(), ss_thread(), transmit_audio(), transmit_t38(), wait_for_hangup(), waitforring_exec(), and waitstream_core().
02363 { 02364 int oldms = ms; /* -1 if no timeout */ 02365 02366 ast_waitfor_nandfds(&c, 1, NULL, 0, NULL, NULL, &ms); 02367 if ((ms < 0) && (oldms < 0)) 02368 ms = 0; 02369 return ms; 02370 }
| struct ast_channel* ast_waitfor_n | ( | struct ast_channel ** | chan, | |
| int | n, | |||
| int * | ms | |||
| ) | [read] |
Waits for input on a group of channels Wait for input on an array of channels for a given # of milliseconds.
| chan | an array of pointers to channels | |
| n | number of channels that are to be waited upon | |
| ms | time "ms" is modified in-place, if applicable |
Definition at line 2357 of file channel.c.
References ast_waitfor_nandfds().
Referenced by ast_feature_request_and_dial(), ast_generic_bridge(), ast_udptl_bridge(), autoservice_run(), bridge_native_loop(), bridge_p2p_loop(), dahdi_bridge(), dial_exec_full(), iax2_bridge(), misdn_bridge(), monitor_dial(), rpt(), rpt_exec(), wait_for_answer(), and wait_for_winner().
02358 { 02359 return ast_waitfor_nandfds(c, n, NULL, 0, NULL, NULL, ms); 02360 }
| int ast_waitfor_n_fd | ( | int * | fds, | |
| int | n, | |||
| int * | ms, | |||
| int * | exception | |||
| ) |
Waits for input on an fd This version works on fd's only. Be careful with it.
Definition at line 2002 of file channel.c.
References ast_waitfor_nandfds().
Referenced by dundi_lookup_internal(), and dundi_precache_internal().
02003 { 02004 int winner = -1; 02005 ast_waitfor_nandfds(NULL, 0, fds, n, exception, &winner, ms); 02006 return winner; 02007 }
| struct ast_channel* ast_waitfor_nandfds | ( | struct ast_channel ** | c, | |
| int | n, | |||
| int * | fds, | |||
| int | nfds, | |||
| int * | exception, | |||
| int * | outfd, | |||
| int * | ms | |||
| ) | [read] |
Waits for activity on a group of channels.
| chan | an array of pointers to channels | |
| n | number of channels that are to be waited upon | |
| fds | an array of fds to wait upon | |
| nfds | the number of fds to wait upon | |
| exception | exception flag | |
| outfd | fd that had activity on it | |
| ms | how long the wait was Big momma function here. Wait for activity on any of the n channels, or any of the nfds file descriptors. |
Definition at line 2014 of file channel.c.
References ast_channel::_softhangup, ast_add_fd(), ast_channel_lock, ast_channel_unlock, ast_clear_flag, ast_do_masquerade(), AST_FLAG_BLOCKING, AST_FLAG_EXCEPTION, ast_log(), AST_MAX_FDS, ast_poll, ast_set_flag, AST_SOFTHANGUP_TIMEOUT, ast_tvcmp(), ast_tvdiff_ms(), ast_tvnow(), ast_tvsub(), ast_tvzero(), CHECK_BLOCKING, errno, ast_channel::fdno, and LOG_WARNING.
Referenced by ast_waitfor(), ast_waitfor_n(), ast_waitfor_n_fd(), ast_waitfordigit_full(), conf_run(), eivr_comm(), find_cache(), run_agi(), and waitstream_core().
02017 { 02018 struct timeval start = { 0 , 0 }; 02019 struct pollfd *pfds = NULL; 02020 int res; 02021 long rms; 02022 int x, y, max; 02023 int sz; 02024 struct timeval now = { 0, 0 }; 02025 struct timeval whentohangup = { 0, 0 }, diff; 02026 struct ast_channel *winner = NULL; 02027 struct fdmap { 02028 int chan; 02029 int fdno; 02030 } *fdmap = NULL; 02031 02032 if ((sz = n * AST_MAX_FDS + nfds)) { 02033 pfds = alloca(sizeof(*pfds) * sz); 02034 fdmap = alloca(sizeof(*fdmap) * sz); 02035 } 02036 02037 if (outfd) 02038 *outfd = -99999; 02039 if (exception) 02040 *exception = 0; 02041 02042 /* Perform any pending masquerades */ 02043 for (x = 0; x < n; x++) { 02044 ast_channel_lock(c[x]); 02045 if (c[x]->masq && ast_do_masquerade(c[x])) { 02046 ast_log(LOG_WARNING, "Masquerade failed\n"); 02047 *ms = -1; 02048 ast_channel_unlock(c[x]); 02049 return NULL; 02050 } 02051 if (!ast_tvzero(c[x]->whentohangup)) { 02052 if (ast_tvzero(whentohangup)) 02053 now = ast_tvnow(); 02054 diff = ast_tvsub(c[x]->whentohangup, now); 02055 if (diff.tv_sec < 0 || ast_tvzero(diff)) { 02056 /* Should already be hungup */ 02057 c[x]->_softhangup |= AST_SOFTHANGUP_TIMEOUT; 02058 ast_channel_unlock(c[x]); 02059 return c[x]; 02060 } 02061 if (ast_tvzero(whentohangup) || ast_tvcmp(diff, whentohangup) < 0) 02062 whentohangup = diff; 02063 } 02064 ast_channel_unlock(c[x]); 02065 } 02066 /* Wait full interval */ 02067 rms = *ms; 02068 if (!ast_tvzero(whentohangup)) { 02069 rms = whentohangup.tv_sec * 1000 + whentohangup.tv_usec / 1000; /* timeout in milliseconds */ 02070 if (*ms >= 0 && *ms < rms) /* original *ms still smaller */ 02071 rms = *ms; 02072 } 02073 /* 02074 * Build the pollfd array, putting the channels' fds first, 02075 * followed by individual fds. Order is important because 02076 * individual fd's must have priority over channel fds. 02077 */ 02078 max = 0; 02079 for (x = 0; x < n; x++) { 02080 for (y = 0; y < AST_MAX_FDS; y++) { 02081 fdmap[max].fdno = y; /* fd y is linked to this pfds */ 02082 fdmap[max].chan = x; /* channel x is linked to this pfds */ 02083 max += ast_add_fd(&pfds[max], c[x]->fds[y]); 02084 } 02085 CHECK_BLOCKING(c[x]); 02086 } 02087 /* Add the individual fds */ 02088 for (x = 0; x < nfds; x++) { 02089 fdmap[max].chan = -1; 02090 max += ast_add_fd(&pfds[max], fds[x]); 02091 } 02092 02093 if (*ms > 0) 02094 start = ast_tvnow(); 02095 02096 if (sizeof(int) == 4) { /* XXX fix timeout > 600000 on linux x86-32 */ 02097 do { 02098 int kbrms = rms; 02099 if (kbrms > 600000) 02100 kbrms = 600000; 02101 res = ast_poll(pfds, max, kbrms); 02102 if (!res) 02103 rms -= kbrms; 02104 } while (!res && (rms > 0)); 02105 } else { 02106 res = ast_poll(pfds, max, rms); 02107 } 02108 for (x = 0; x < n; x++) 02109 ast_clear_flag(c[x], AST_FLAG_BLOCKING); 02110 if (res < 0) { /* Simulate a timeout if we were interrupted */ 02111 if (errno != EINTR) 02112 *ms = -1; 02113 return NULL; 02114 } 02115 if (!ast_tvzero(whentohangup)) { /* if we have a timeout, check who expired */ 02116 now = ast_tvnow(); 02117 for (x = 0; x < n; x++) { 02118 if (!ast_tvzero(c[x]->whentohangup) && ast_tvcmp(c[x]->whentohangup, now) <= 0) { 02119 c[x]->_softhangup |= AST_SOFTHANGUP_TIMEOUT; 02120 if (winner == NULL) 02121 winner = c[x]; 02122 } 02123 } 02124 } 02125 if (res == 0) { /* no fd ready, reset timeout and done */ 02126 *ms = 0; /* XXX use 0 since we may not have an exact timeout. */ 02127 return winner; 02128 } 02129 /* 02130 * Then check if any channel or fd has a pending event. 02131 * Remember to check channels first and fds last, as they 02132 * must have priority on setting 'winner' 02133 */ 02134 for (x = 0; x < max; x++) { 02135 res = pfds[x].revents; 02136 if (res == 0) 02137 continue; 02138 if (fdmap[x].chan >= 0) { /* this is a channel */ 02139 winner = c[fdmap[x].chan]; /* override previous winners */ 02140 if (res & POLLPRI) 02141 ast_set_flag(winner, AST_FLAG_EXCEPTION); 02142 else 02143 ast_clear_flag(winner, AST_FLAG_EXCEPTION); 02144 winner->fdno = fdmap[x].fdno; 02145 } else { /* this is an fd */ 02146 if (outfd) 02147 *outfd = pfds[x].fd; 02148 if (exception) 02149 *exception = (res & POLLPRI) ? -1 : 0; 02150 winner = NULL; 02151 } 02152 } 02153 if (*ms > 0) { 02154 *ms -= ast_tvdiff_ms(ast_tvnow(), start); 02155 if (*ms < 0) 02156 *ms = 0; 02157 } 02158 return winner; 02159 }
| int ast_waitfordigit | ( | struct ast_channel * | c, | |
| int | ms | |||
| ) |
Waits for a digit.
!
| c | channel to wait for a digit on | |
| ms | how many milliseconds to wait |
Definition at line 2373 of file channel.c.
References ast_waitfordigit_full().
Referenced by _ast_adsi_get_cpeid(), _ast_adsi_get_cpeinfo(), _ast_adsi_print(), _ast_adsi_read_encoded_dtmf(), _ast_adsi_transmit_message_full(), _while_exec(), advanced_options(), ast_app_dtget(), ast_control_streamfile(), ast_record_review(), builtin_atxfer(), collect_digits(), common_exec(), cpeid_exec(), dialout(), directory_exec(), forward_message(), get_folder(), ivr_dispatch(), mgcp_ss(), my_getsigstr(), pbx_builtin_waitexten(), play_record_review(), read_exec(), read_newoption(), readexten_exec(), retrydial_exec(), select_item_menu(), select_item_seq(), sendnoise(), ss_thread(), testclient_exec(), testserver_exec(), vm_execmain(), vm_forwardoptions(), vm_instructions_en(), vm_options(), vm_tempgreeting(), wait_a_bit(), and wait_our_turn().
02374 { 02375 return ast_waitfordigit_full(c, ms, -1, -1); 02376 }
| int ast_waitfordigit_full | ( | struct ast_channel * | c, | |
| int | ms, | |||
| int | audiofd, | |||
| int | ctrlfd | |||
| ) |
Wait for a digit Same as ast_waitfordigit() with audio fd for outputting read audio and ctrlfd to monitor for reading.
| c | channel to wait for a digit on | |
| ms | how many milliseconds to wait | |
| audiofd | audio file descriptor to write to if audio frames are received | |
| ctrlfd | control file descriptor to monitor for reading |
Definition at line 2411 of file channel.c.
References ast_check_hangup(), ast_clear_flag, AST_CONTROL_ANSWER, AST_CONTROL_HANGUP, AST_CONTROL_RINGING, AST_CONTROL_SRCUPDATE, AST_FLAG_END_DTMF_ONLY, AST_FLAG_ZOMBIE, AST_FRAME_CONTROL, AST_FRAME_DTMF_BEGIN, AST_FRAME_DTMF_END, AST_FRAME_VOICE, ast_frfree, ast_log(), ast_read(), ast_set_flag, ast_test_flag, ast_waitfor_nandfds(), ast_frame::data, ast_frame::datalen, errno, f, ast_frame::frametype, LOG_WARNING, ast_frame::ptr, and ast_frame::subclass.
Referenced by ast_readstring_full(), ast_waitfordigit(), handle_getoption(), and handle_waitfordigit().
02412 { 02413 /* Stop if we're a zombie or need a soft hangup */ 02414 if (ast_test_flag(c, AST_FLAG_ZOMBIE) || ast_check_hangup(c)) 02415 return -1; 02416 02417 /* Only look for the end of DTMF, don't bother with the beginning and don't emulate things */ 02418 ast_set_flag(c, AST_FLAG_END_DTMF_ONLY); 02419 02420 /* Wait for a digit, no more than ms milliseconds total. */ 02421 02422 while (ms) { 02423 struct ast_channel *rchan; 02424 int outfd=-1; 02425 02426 errno = 0; 02427 rchan = ast_waitfor_nandfds(&c, 1, &cmdfd, (cmdfd > -1) ? 1 : 0, NULL, &outfd, &ms); 02428 02429 if (!rchan && outfd < 0 && ms) { 02430 if (errno == 0 || errno == EINTR) 02431 continue; 02432 ast_log(LOG_WARNING, "Wait failed (%s)\n", strerror(errno)); 02433 ast_clear_flag(c, AST_FLAG_END_DTMF_ONLY); 02434 return -1; 02435 } else if (outfd > -1) { 02436 /* The FD we were watching has something waiting */ 02437 ast_log(LOG_WARNING, "The FD we were waiting for has something waiting. Waitfordigit returning numeric 1\n"); 02438 ast_clear_flag(c, AST_FLAG_END_DTMF_ONLY); 02439 return 1; 02440 } else if (rchan) { 02441 int res; 02442 struct ast_frame *f = ast_read(c); 02443 if (!f) 02444 return -1; 02445 02446 switch (f->frametype) { 02447 case AST_FRAME_DTMF_BEGIN: 02448 break; 02449 case AST_FRAME_DTMF_END: 02450 res = f->subclass; 02451 ast_frfree(f); 02452 ast_clear_flag(c, AST_FLAG_END_DTMF_ONLY); 02453 return res; 02454 case AST_FRAME_CONTROL: 02455 switch (f->subclass) { 02456 case AST_CONTROL_HANGUP: 02457 ast_frfree(f); 02458 ast_clear_flag(c, AST_FLAG_END_DTMF_ONLY); 02459 return -1; 02460 case AST_CONTROL_RINGING: 02461 case AST_CONTROL_ANSWER: 02462 case AST_CONTROL_SRCUPDATE: 02463 /* Unimportant */ 02464 break; 02465 default: 02466 ast_log(LOG_WARNING, "Unexpected control subclass '%d'\n", f->subclass); 02467 break; 02468 } 02469 break; 02470 case AST_FRAME_VOICE: 02471 /* Write audio if appropriate */ 02472 if (audiofd > -1) { 02473 if (write(audiofd, f->data.ptr, f->datalen) < 0) { 02474 ast_log(LOG_WARNING, "write() failed: %s\n", strerror(errno)); 02475 } 02476 } 02477 default: 02478 /* Ignore */ 02479 break; 02480 } 02481 ast_frfree(f); 02482 } 02483 } 02484 02485 ast_clear_flag(c, AST_FLAG_END_DTMF_ONLY); 02486 02487 return 0; /* Time is up */ 02488 }
| struct ast_channel* ast_walk_channel_by_exten_locked | ( | const struct ast_channel * | chan, | |
| const char * | exten, | |||
| const char * | context | |||
| ) | [read] |
Get next channel by exten (and optionally context) and lock it.
Definition at line 1298 of file channel.c.
References channel_find_locked().
Referenced by next_channel().
01300 { 01301 return channel_find_locked(chan, NULL, 0, context, exten); 01302 }
| struct ast_channel* ast_walk_channel_by_name_prefix_locked | ( | const struct ast_channel * | chan, | |
| const char * | name, | |||
| const int | namelen | |||
| ) | [read] |
Get channel by name or uniqueid prefix (locks channel).
Definition at line 1285 of file channel.c.
References channel_find_locked().
Referenced by my_ast_get_channel_by_name_locked(), next_channel(), and softhangup_exec().
01287 { 01288 return channel_find_locked(chan, name, namelen, NULL, NULL); 01289 }
| int ast_write | ( | struct ast_channel * | chan, | |
| struct ast_frame * | frame | |||
| ) |
Write a frame to a channel This function writes the given frame to the indicated channel.
| chan | destination channel of the frame | |
| frame | frame that will be written |
Definition at line 3383 of file channel.c.
References ast_channel::_softhangup, AST_AUDIOHOOK_DIRECTION_WRITE, ast_audiohook_write_list(), ast_channel_lock, ast_channel_trylock, ast_channel_unlock, ast_check_hangup(), ast_clear_flag, AST_CONTROL_UNHOLD, ast_deactivate_generator(), ast_debug, ast_do_masquerade(), AST_FLAG_BLOCKING, AST_FLAG_WRITE_INT, AST_FLAG_ZOMBIE, ast_format_rate(), AST_FORMAT_T140, AST_FRAME_CONTROL, AST_FRAME_DTMF_BEGIN, AST_FRAME_DTMF_END, ast_frame_dump(), AST_FRAME_HTML, AST_FRAME_IAX, AST_FRAME_MODEM, AST_FRAME_NULL, AST_FRAME_TEXT, AST_FRAME_VIDEO, AST_FRAME_VOICE, ast_frfree, ast_frisolate(), AST_LIST_NEXT, ast_log(), AST_MONITOR_RUNNING, ast_seekstream(), ast_senddigit_begin(), ast_senddigit_end(), AST_SOFTHANGUP_DEV, ast_test_flag, ast_translate(), ast_writestream(), ast_channel::audiohooks, calc_monitor_jump(), CHECK_BLOCKING, ast_frame::data, ast_frame::datalen, DEBUGCHAN_FLAG, f, ast_filestream::fmt, ast_format::format, ast_channel::fout, FRAMECOUNT_INC, ast_frame::frametype, ast_channel::generatordata, ast_channel_tech::indicate, ast_channel::insmpl, ast_frame::len, LOG_WARNING, ast_channel::masq, ast_channel::masqr, ast_channel::monitor, chanlist::next, ast_channel::outsmpl, ast_frame::ptr, ast_channel::rawwriteformat, ast_channel_monitor::read_stream, ast_frame::samples, SEEK_FORCECUR, send_dtmf_event(), ast_channel_tech::send_html, ast_channel_tech::send_text, ast_channel_monitor::state, ast_frame::subclass, ast_channel::tech, ast_channel_tech::write, ast_channel_monitor::write_stream, ast_channel_tech::write_text, ast_channel_tech::write_video, and ast_channel::writetrans.
Referenced by adsi_careful_send(), agent_write(), ast_feature_request_and_dial(), ast_generic_bridge(), ast_prod(), ast_readaudio_callback(), ast_readvideo_callback(), ast_udptl_bridge(), ast_write_video(), bridge_native_loop(), bridge_p2p_loop(), conf_queue_dtmf(), conf_run(), dahdi_bridge(), dictate_exec(), echo_exec(), fax_generator_generate(), function_ilink(), gen_generate(), handle_jack_audio(), handle_link_data(), iax2_bridge(), jb_get_and_deliver(), linear_generator(), milliwatt_generate(), misdn_bridge(), moh_files_generator(), moh_generate(), mp3_exec(), NBScat_exec(), playtones_generator(), rpt(), rpt_exec(), send_link_dtmf(), send_link_keyquery(), send_tone_burst(), send_usb_txt(), send_waveform_to_channel(), silence_generator_generate(), sms_generate(), spy_generate(), t38_tx_packet_handler(), tonepair_generator(), and wait_for_answer().
03384 { 03385 int res = -1; 03386 struct ast_frame *f = NULL; 03387 int count = 0; 03388 03389 /*Deadlock avoidance*/ 03390 while(ast_channel_trylock(chan)) { 03391 /*cannot goto done since the channel is not locked*/ 03392 if(count++ > 10) { 03393 ast_debug(1, "Deadlock avoided for write to channel '%s'\n", chan->name); 03394 return 0; 03395 } 03396 usleep(1); 03397 } 03398 /* Stop if we're a zombie or need a soft hangup */ 03399 if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) 03400 goto done; 03401 03402 /* Handle any pending masquerades */ 03403 if (chan->masq && ast_do_masquerade(chan)) { 03404 ast_log(LOG_WARNING, "Failed to perform masquerade\n"); 03405 goto done; 03406 } 03407 if (chan->masqr) { 03408 res = 0; /* XXX explain, why 0 ? */ 03409 goto done; 03410 } 03411 if (chan->generatordata) { 03412 if (ast_test_flag(chan, AST_FLAG_WRITE_INT)) 03413 ast_deactivate_generator(chan); 03414 else { 03415 if (fr->frametype == AST_FRAME_DTMF_END) { 03416 /* There is a generator running while we're in the middle of a digit. 03417 * It's probably inband DTMF, so go ahead and pass it so it can 03418 * stop the generator */ 03419 ast_clear_flag(chan, AST_FLAG_BLOCKING); 03420 ast_channel_unlock(chan); 03421 res = ast_senddigit_end(chan, fr->subclass, fr->len); 03422 ast_channel_lock(chan); 03423 CHECK_BLOCKING(chan); 03424 } else if (fr->frametype == AST_FRAME_CONTROL && fr->subclass == AST_CONTROL_UNHOLD) { 03425 /* This is a side case where Echo is basically being called and the person put themselves on hold and took themselves off hold */ 03426 res = (chan->tech->indicate == NULL) ? 0 : 03427 chan->tech->indicate(chan, fr->subclass, fr->data.ptr, fr->datalen); 03428 } 03429 res = 0; /* XXX explain, why 0 ? */ 03430 goto done; 03431 } 03432 } 03433 /* High bit prints debugging */ 03434 if (chan->fout & DEBUGCHAN_FLAG) 03435 ast_frame_dump(chan->name, fr, ">>"); 03436 CHECK_BLOCKING(chan); 03437 switch (fr->frametype) { 03438 case AST_FRAME_CONTROL: 03439 res = (chan->tech->indicate == NULL) ? 0 : 03440 chan->tech->indicate(chan, fr->subclass, fr->data.ptr, fr->datalen); 03441 break; 03442 case AST_FRAME_DTMF_BEGIN: 03443 if (chan->audiohooks) { 03444 struct ast_frame *old_frame = fr; 03445 fr = ast_audiohook_write_list(chan, chan->audiohooks, AST_AUDIOHOOK_DIRECTION_WRITE, fr); 03446 if (old_frame != fr) 03447 f = fr; 03448 } 03449 send_dtmf_event(chan, "Sent", fr->subclass, "Yes", "No"); 03450 ast_clear_flag(chan, AST_FLAG_BLOCKING); 03451 ast_channel_unlock(chan); 03452 res = ast_senddigit_begin(chan, fr->subclass); 03453 ast_channel_lock(chan); 03454 CHECK_BLOCKING(chan); 03455 break; 03456 case AST_FRAME_DTMF_END: 03457 if (chan->audiohooks) { 03458 struct ast_frame *new_frame = fr; 03459 03460 new_frame = ast_audiohook_write_list(chan, chan->audiohooks, AST_AUDIOHOOK_DIRECTION_WRITE, fr); 03461 if (new_frame != fr) { 03462 ast_frfree(new_frame); 03463 } 03464 } 03465 send_dtmf_event(chan, "Sent", fr->subclass, "No", "Yes"); 03466 ast_clear_flag(chan, AST_FLAG_BLOCKING); 03467 ast_channel_unlock(chan); 03468 res = ast_senddigit_end(chan, fr->subclass, fr->len); 03469 ast_channel_lock(chan); 03470 CHECK_BLOCKING(chan); 03471 break; 03472 case AST_FRAME_TEXT: 03473 if (fr->subclass == AST_FORMAT_T140) { 03474 res = (chan->tech->write_text == NULL) ? 0 : 03475 chan->tech->write_text(chan, fr); 03476 } else { 03477 res = (chan->tech->send_text == NULL) ? 0 : 03478 chan->tech->send_text(chan, (char *) fr->data.ptr); 03479 } 03480 break; 03481 case AST_FRAME_HTML: 03482 res = (chan->tech->send_html == NULL) ? 0 : 03483 chan->tech->send_html(chan, fr->subclass, (char *) fr->data.ptr, fr->datalen); 03484 break; 03485 case AST_FRAME_VIDEO: 03486 /* XXX Handle translation of video codecs one day XXX */ 03487 res = (chan->tech->write_video == NULL) ? 0 : 03488 chan->tech->write_video(chan, fr); 03489 break; 03490 case AST_FRAME_MODEM: 03491 res = (chan->tech->write == NULL) ? 0 : 03492 chan->tech->write(chan, fr); 03493 break; 03494 case AST_FRAME_VOICE: 03495 if (chan->tech->write == NULL) 03496 break; /*! \todo XXX should return 0 maybe ? */ 03497 03498 /* If the frame is in the raw write format, then it's easy... just use the frame - otherwise we will have to translate */ 03499 if (fr->subclass == chan->rawwriteformat) 03500 f = fr; 03501 else 03502 f = (chan->writetrans) ? ast_translate(chan->writetrans, fr, 0) : fr; 03503 03504 if (!f) { 03505 res = 0; 03506 break; 03507 } 03508 03509 if (chan->audiohooks) { 03510 struct ast_frame *prev = NULL, *new_frame, *cur, *dup; 03511 int freeoldlist = 0; 03512 03513 if (f != fr) { 03514 freeoldlist = 1; 03515 } 03516 03517 /* Since ast_audiohook_write may return a new frame, and the cur frame is 03518 * an item in a list of frames, create a new list adding each cur frame back to it 03519 * regardless if the cur frame changes or not. */ 03520 for (cur = f; cur; cur = AST_LIST_NEXT(cur, frame_list)) { 03521 new_frame = ast_audiohook_write_list(chan, chan->audiohooks, AST_AUDIOHOOK_DIRECTION_WRITE, cur); 03522 03523 /* if this frame is different than cur, preserve the end of the list, 03524 * free the old frames, and set cur to be the new frame */ 03525 if (new_frame != cur) { 03526 03527 /* doing an ast_frisolate here seems silly, but we are not guaranteed the new_frame 03528 * isn't part of local storage, meaning if ast_audiohook_write is called multiple 03529 * times it may override the previous frame we got from it unless we dup it */ 03530 if ((dup = ast_frisolate(new_frame))) { 03531 AST_LIST_NEXT(dup, frame_list) = AST_LIST_NEXT(cur, frame_list); 03532 if (freeoldlist) { 03533 AST_LIST_NEXT(cur, frame_list) = NULL; 03534 ast_frfree(cur); 03535 } 03536 cur = dup; 03537 } 03538 } 03539 03540 /* now, regardless if cur is new or not, add it to the new list, 03541 * if the new list has not started, cur will become the first item. */ 03542 if (prev) { 03543 AST_LIST_NEXT(prev, frame_list) = cur; 03544 } else { 03545 f = cur; /* set f to be the beginning of our new list */ 03546 } 03547 prev = cur; 03548 } 03549 } 03550 03551 /* If Monitor is running on this channel, then we have to write frames out there too */ 03552 /* the translator on chan->writetrans may have returned multiple frames 03553 from the single frame we passed in; if so, feed each one of them to the 03554 monitor */ 03555 if (chan->monitor && chan->monitor->write_stream) { 03556 struct ast_frame *cur; 03557 03558 for (cur = f; cur; cur = AST_LIST_NEXT(cur, frame_list)) { 03559 /* XXX must explain this code */ 03560 #ifndef MONITOR_CONSTANT_DELAY 03561 int jump = chan->insmpl - chan->outsmpl - 4 * cur->samples; 03562 if (jump >= 0) { 03563 jump = calc_monitor_jump((chan->insmpl - chan->outsmpl), ast_format_rate(f->subclass), ast_format_rate(chan->monitor->read_stream->fmt->format)); 03564 if (ast_seekstream(chan->monitor->write_stream, jump, SEEK_FORCECUR) == -1) 03565 ast_log(LOG_WARNING, "Failed to perform seek in monitoring write stream, synchronization between the files may be broken\n"); 03566 chan->outsmpl += (chan->insmpl - chan->outsmpl) + cur->samples; 03567 } else { 03568 chan->outsmpl += cur->samples; 03569 } 03570 #else 03571 int jump = calc_monitor_jump((chan->insmpl - chan->outsmpl), ast_format_rate(f->subclass), ast_format_rate(chan->monitor->read_stream->fmt->format)); 03572 if (jump - MONITOR_DELAY >= 0) { 03573 if (ast_seekstream(chan->monitor->write_stream, jump - cur->samples, SEEK_FORCECUR) == -1) 03574 ast_log(LOG_WARNING, "Failed to perform seek in monitoring write stream, synchronization between the files may be broken\n"); 03575 chan->outsmpl += chan->insmpl - chan->outsmpl; 03576 } else { 03577 chan->outsmpl += cur->samples; 03578 } 03579 #endif 03580 if (chan->monitor->state == AST_MONITOR_RUNNING) { 03581 if (ast_writestream(chan->monitor->write_stream, cur) < 0) 03582 ast_log(LOG_WARNING, "Failed to write data to channel monitor write stream\n"); 03583 } 03584 } 03585 } 03586 03587 /* the translator on chan->writetrans may have returned multiple frames 03588 from the single frame we passed in; if so, feed each one of them to the 03589 channel, freeing each one after it has been written */ 03590 if ((f != fr) && AST_LIST_NEXT(f, frame_list)) { 03591 struct ast_frame *cur, *next; 03592 unsigned int skip = 0; 03593 03594 for (cur = f, next = AST_LIST_NEXT(cur, frame_list); 03595 cur; 03596 cur = next, next = cur ? AST_LIST_NEXT(cur, frame_list) : NULL) { 03597 if (!skip) { 03598 if ((res = chan->tech->write(chan, cur)) < 0) { 03599 chan->_softhangup |= AST_SOFTHANGUP_DEV; 03600 skip = 1; 03601 } else if (next) { 03602 /* don't do this for the last frame in the list, 03603 as the code outside the loop will do it once 03604 */ 03605 chan->fout = FRAMECOUNT_INC(chan->fout); 03606 } 03607 } 03608 ast_frfree(cur); 03609 } 03610 03611 /* reset f so the code below doesn't attempt to free it */ 03612 f = NULL; 03613 } else { 03614 res = chan->tech->write(chan, f); 03615 } 03616 break; 03617 case AST_FRAME_NULL: 03618 case AST_FRAME_IAX: 03619 /* Ignore these */ 03620 res = 0; 03621 break; 03622 default: 03623 /* At this point, fr is the incoming frame and f is NULL. Channels do 03624 * not expect to get NULL as a frame pointer and will segfault. Hence, 03625 * we output the original frame passed in. */ 03626 res = chan->tech->write(chan, fr); 03627 break; 03628 } 03629 03630 if (f && f != fr) 03631 ast_frfree(f); 03632 ast_clear_flag(chan, AST_FLAG_BLOCKING); 03633 03634 /* Consider a write failure to force a soft hangup */ 03635 if (res < 0) { 03636 chan->_softhangup |= AST_SOFTHANGUP_DEV; 03637 } else { 03638 chan->fout = FRAMECOUNT_INC(chan->fout); 03639 } 03640 done: 03641 ast_channel_unlock(chan); 03642 return res; 03643 }
| int ast_write_text | ( | struct ast_channel * | chan, | |
| struct ast_frame * | frame | |||
| ) |
Write text frame to a channel This function writes the given frame to the indicated channel.
| chan | destination channel of the frame | |
| frame | frame that will be written |
| int ast_write_video | ( | struct ast_channel * | chan, | |
| struct ast_frame * | frame | |||
| ) |
Write video frame to a channel This function writes the given frame to the indicated channel.
| chan | destination channel of the frame | |
| frame | frame that will be written |
Definition at line 3372 of file channel.c.
References ast_write(), ast_channel::tech, and ast_channel_tech::write_video.
03373 { 03374 int res; 03375 if (!chan->tech->write_video) 03376 return 0; 03377 res = ast_write(chan, fr); 03378 if (!res) 03379 res = 1; 03380 return res; 03381 }
| const char* channelreloadreason2txt | ( | enum channelreloadreason | reason | ) |
Convert enum channelreloadreason to text string for manager event.
| reason | Enum channelreloadreason - reason for reload (manager, cli, start etc) |
\ brief Convert channel reloadreason (ENUM) to text string for manager event
Definition at line 5652 of file channel.c.
References CHANNEL_CLI_RELOAD, CHANNEL_MODULE_LOAD, and CHANNEL_MODULE_RELOAD.
Referenced by reload_config().
05653 { 05654 switch (reason) { 05655 case CHANNEL_MODULE_LOAD: 05656 return "LOAD (Channel module load)"; 05657 05658 case CHANNEL_MODULE_RELOAD: 05659 return "RELOAD (Channel module reload)"; 05660 05661 case CHANNEL_CLI_RELOAD: 05662 return "CLIRELOAD (Channel module reload by CLI command)"; 05663 05664 default: 05665 return "MANAGERRELOAD (Channel module reload by manager)"; 05666 } 05667 };
| unsigned long global_fin |
The current value of the debug flags is stored in the two variables global_fin and global_fout (declared in main/channel.c)
Definition at line 86 of file channel.c.
Referenced by handle_core_set_debug_channel().
| unsigned long global_fout |
Definition at line 86 of file channel.c.
Referenced by handle_core_set_debug_channel().
1.6.1