Fri Aug 24 02:24:13 2007

Asterisk developer's documentation


channel.h File Reference

General Asterisk PBX channel definitions. More...

#include "asterisk/abstract_jb.h"
#include <unistd.h>
#include <sys/poll.h>
#include "asterisk/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/options.h"
#include "asterisk/strings.h"
#include "asterisk/compiler.h"

Include dependency graph for channel.h:

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

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_datastore
 Structure for a channel data store. More...
struct  ast_datastore_info
 Structure for a data store type. More...
struct  ast_generator
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_NAME   80
#define AST_GENERATOR_FD   (AST_MAX_FDS-4)
#define AST_MAX_CONTEXT   80
#define AST_MAX_EXTENSION   80
#define AST_MAX_FDS   8
#define AST_TIMING_FD   (AST_MAX_FDS-2)
#define CHECK_BLOCKING(c)
#define CRASH   do { } while(0)
#define DEBUGCHAN_FLAG   0x80000000
#define FRAMECOUNT_INC(x)   ( ((x) & DEBUGCHAN_FLAG) | (((x)+1) & ~DEBUGCHAN_FLAG) )
#define LOAD_OH(oh)
#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_WHISPER = (1 << 11), AST_FLAG_IN_DTMF = (1 << 12),
  AST_FLAG_EMULATE_DTMF = (1 << 13), AST_FLAG_END_DTMF_ONLY = (1 << 14)
}
 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_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  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

ast_channel__ast_request_and_dial (const char *type, int format, void *data, int timeout, int *reason, const char *cidnum, const char *cidname, struct outgoing_helper *oh)
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 ringing call.
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.
ast_channelast_bridged_channel (struct ast_channel *chan)
 Find bridged channel.
int ast_call (struct ast_channel *chan, char *addr, int timeout)
 Make a call.
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.
ast_channelast_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 *name_fmt,...)
 Create a channel structure.
static int ast_channel_best_codec (struct ast_channel *channel)
 Pick the best codec from channel nativeformats.
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_datastore_add (struct ast_channel *chan, struct ast_datastore *datastore)
 Add a datastore to a channel.
ast_datastoreast_channel_datastore_alloc (const struct ast_datastore_info *info, char *uid)
 Create a channel datastore structure.
ast_datastoreast_channel_datastore_find (struct ast_channel *chan, const struct ast_datastore_info *info, char *uid)
 Find a datastore on a channel.
int ast_channel_datastore_free (struct ast_datastore *datastore)
 Free a channel datastore structure.
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.
static void ast_channel_formats_reset (struct ast_channel *channel)
void ast_channel_free (struct ast_channel *)
 Free a channel structure.
static const char * ast_channel_getformatname (struct ast_channel *chan)
static char * ast_channel_getformatname_multiple (char *buf, size_t size, struct ast_channel *chan)
 Get the names of a set of formats.
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.
ast_frameast_channel_queryoption (struct ast_channel *channel, int option, void *data, int *datalen, int block)
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)
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.
ast_silence_generatorast_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.
ast_channelast_channel_walk_locked (const struct ast_channel *prev)
 Browse channels in use Browse the channels currently in use.
int ast_channel_whisper_feed (struct ast_channel *chan, struct ast_frame *f)
 Feed an audio frame into the whisper buffer on a channel.
int ast_channel_whisper_start (struct ast_channel *chan)
 Begin 'whispering' onto a channel.
void ast_channel_whisper_stop (struct ast_channel *chan)
 Stop 'whispering' onto a channel.
ast_variableast_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 wacked 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 max, int *start)
 Helper function for migrating select to poll.
ast_channelast_get_channel_by_exten_locked (const char *exten, const char *context)
 Get channel by exten (and optionally context) and lock it.
ast_channelast_get_channel_by_name_locked (const char *chan)
 Get channel by name (locks channel).
ast_channelast_get_channel_by_name_prefix_locked (const char *name, const int namelen)
 Get channel by name prefix (locks channel).
ast_channel_techast_get_channel_tech (const char *name)
 Get a channel technology structure by name.
ast_group_t ast_get_group (const char *s)
static int ast_get_read_format (struct ast_channel *chan)
 Gets read format from channel chan.
static int ast_get_write_format (struct ast_channel *chan)
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.
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 an outgoing frame.
int ast_queue_hangup (struct ast_channel *chan)
 Queue a hangup frame.
ast_frameast_read (struct ast_channel *chan)
 Reads a frame.
ast_frameast_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.
ast_channelast_request (const char *type, int format, void *data, int *status)
 Requests a channel.
ast_channelast_request_and_dial (const char *type, int format, void *data, int timeout, int *reason, const char *cidnum, const char *cidname)
 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.
static struct ast_channelast_request_inherit (struct ast_channel *chan, const char *type, void *data, int *status)
 call ast_request with format/type of parent channel
int ast_safe_sleep (struct ast_channel *chan, int ms)
 Wait for a specied 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 specied amount of time, looking for hangups and a condition argument.
char * ast_safe_string_alloc (const char *fmt,...)
 printf the string into a correctly sized mallocd buffer, and return the buffer
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)
 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 Write text to a display on a channel.
static void ast_set_best_format (struct ast_channel *channel)
 Set best format, identical to read/write.
void ast_set_callerid (struct ast_channel *chan, const char *cidnum, const char *cidname, const char *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 compoent 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, int samples, int(*func)(void *data), void *data)
int ast_shutting_down (void)
 Returns non-zero if Asterisk is being shut down.
int ast_softhangup (struct ast_channel *chan, int cause)
 Softly hangup up a channel.
int ast_softhangup_nolock (struct ast_channel *chan, int cause)
 Softly hangup up a channel (no channel lock).
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.
ast_channelast_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.
ast_channelast_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.
ast_channelast_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.
ast_channelast_walk_channel_by_name_prefix_locked (const struct ast_channel *chan, const char *name, const int namelen)
 Get channel by name 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_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.


Detailed Description

General Asterisk PBX channel definitions.

See also:

Definition in file channel.h.


Define Documentation

#define AST_AGENT_FD   (AST_MAX_FDS-3)

used by agents for pass through

Definition at line 136 of file channel.h.

Referenced by agent_read().

#define AST_ALERT_FD   (AST_MAX_FDS-1)

used for alertpipe

Definition at line 134 of file channel.h.

Referenced by restore_channel().

#define AST_BRIDGE_DTMF_CHANNEL_0   (1 << 0)

Report DTMF on channel 0.

Definition at line 1009 of file channel.h.

Referenced by ast_generic_bridge(), ast_rtp_bridge(), bridge_native_loop(), bridge_p2p_loop(), iax2_bridge(), misdn_bridge(), set_config_flags(), and zt_bridge().

#define AST_BRIDGE_DTMF_CHANNEL_1   (1 << 1)

Report DTMF on channel 1.

Definition at line 1011 of file channel.h.

Referenced by ast_generic_bridge(), ast_rtp_bridge(), bridge_native_loop(), bridge_p2p_loop(), iax2_bridge(), misdn_bridge(), set_config_flags(), and zt_bridge().

#define AST_BRIDGE_IGNORE_SIGS   (1 << 4)

Ignore all signal frames except NULL.

Definition at line 1017 of file channel.h.

Referenced by bridge_native_loop(), and bridge_p2p_loop().

#define AST_BRIDGE_REC_CHANNEL_0   (1 << 2)

Return all voice frames on channel 0.

Definition at line 1013 of file channel.h.

#define AST_BRIDGE_REC_CHANNEL_1   (1 << 3)

Return all voice frames on channel 1.

Definition at line 1015 of file channel.h.

#define AST_CHANNEL_NAME   80

Max length of an ast_channel name

Definition at line 110 of file channel.h.

Referenced by ast_channel_free(), ast_parse_device_state(), create_jb(), fast_originate(), page_exec(), and softhangup_exec().

#define AST_GENERATOR_FD   (AST_MAX_FDS-4)

used by generator

Definition at line 137 of file channel.h.

Referenced by __ast_read(), and ast_deactivate_generator().

#define AST_MAX_CONTEXT   80

Max length of a context

Definition at line 109 of file channel.h.

Referenced by _macro_exec(), cleanup_stale_contexts(), conf_run(), gosub_exec(), reload_config(), and try_calling().

#define AST_MAX_EXTENSION   80

Max length of an extension

Definition at line 108 of file channel.h.

Referenced by add_extensions(), advanced_options(), ast_device_state_changed(), ast_extension_state2(), ast_hint_state_changed(), ast_ivr_menu_run_internal(), begin_dial(), conf_run(), destroy_station(), disa_exec(), do_parking_thread(), dundi_lookup_local(), forward_message(), function_enum(), get_destination(), gosub_exec(), load_config(), log_exec(), mgcp_ss(), park_add_hints(), phone_check_exception(), realtime_switch_common(), show_dialplan_helper(), skinny_answer(), skinny_indicate(), skinny_ss(), speech_background(), ss_thread(), transmit_state_notify(), try_calling(), vm_authenticate(), vmauthenticate(), and wait_for_answer().

#define AST_MAX_FDS   8

Definition at line 129 of file channel.h.

Referenced by ast_channel_alloc(), ast_waitfor_nandfds(), do_parking_thread(), and update_features().

#define AST_TIMING_FD   (AST_MAX_FDS-2)

used for timingfd

Definition at line 135 of file channel.h.

Referenced by __ast_read(), agent_read(), and restore_channel().

#define CHECK_BLOCKING (  ) 

Definition at line 1420 of file channel.h.

Referenced by ast_sendtext(), ast_waitfor_nandfds(), ast_write(), phone_read(), and zt_read().

#define CRASH   do { } while(0)

Definition at line 1417 of file channel.h.

Referenced by agent_new(), ast_hangup(), ast_queue_frame(), ast_rtcp_read(), ast_rtp_read(), ast_sched_del(), ast_udptl_read(), create_jb(), and jb_get_and_deliver().

#define DEBUGCHAN_FLAG   0x80000000

Todo:
Add explanation here

Definition at line 281 of file channel.h.

Referenced by __ast_read(), ast_write(), handle_core_set_debug_channel(), handle_debugchan_deprecated(), handle_nodebugchan_deprecated(), handle_showchan(), handle_showchan_deprecated(), and serialize_showchan().

#define FRAMECOUNT_INC (  )     ( ((x) & DEBUGCHAN_FLAG) | (((x)+1) & ~DEBUGCHAN_FLAG) )

Definition at line 282 of file channel.h.

Referenced by __ast_read(), and ast_write().

#define LOAD_OH ( oh   ) 

Definition at line 518 of file channel.h.

Referenced by ast_pbx_outgoing_exten().

#define MAX_LANGUAGE   20

Max length of the language setting

Definition at line 111 of file channel.h.

#define MAX_MUSICCLASS   80

Max length of the music class setting

Definition at line 112 of file channel.h.


Typedef Documentation

typedef unsigned long long ast_group_t

Definition at line 146 of file channel.h.


Enumeration Type Documentation

anonymous enum

ast_channel_tech Properties

Enumerator:
AST_CHAN_TP_WANTSJITTER  Channels have this property if they can accept input with jitter; i.e. most VoIP channels.
AST_CHAN_TP_CREATESJITTER  Channels have this property if they can create jitter; i.e. most VoIP channels.

Definition at line 445 of file channel.h.

00445      {
00446    /*! \brief Channels have this property if they can accept input with jitter; 
00447     *         i.e. most VoIP channels */
00448    AST_CHAN_TP_WANTSJITTER = (1 << 0),
00449    /*! \brief Channels have this property if they can create jitter; 
00450     *         i.e. most VoIP channels */
00451    AST_CHAN_TP_CREATESJITTER = (1 << 1),
00452 };

anonymous enum

ast_channel flags

Enumerator:
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_WHISPER  This channel is being whispered on
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.

Definition at line 455 of file channel.h.

00455      {
00456    /*! Queue incoming dtmf, to be released when this flag is turned off */
00457    AST_FLAG_DEFER_DTMF =    (1 << 1),
00458    /*! write should be interrupt generator */
00459    AST_FLAG_WRITE_INT =     (1 << 2),
00460    /*! a thread is blocking on this channel */
00461    AST_FLAG_BLOCKING =      (1 << 3),
00462    /*! This is a zombie channel */
00463    AST_FLAG_ZOMBIE =        (1 << 4),
00464    /*! There is an exception pending */
00465    AST_FLAG_EXCEPTION =     (1 << 5),
00466    /*! Listening to moh XXX anthm promises me this will disappear XXX */
00467    AST_FLAG_MOH =           (1 << 6),
00468    /*! This channel is spying on another channel */
00469    AST_FLAG_SPYING =        (1 << 7),
00470    /*! This channel is in a native bridge */
00471    AST_FLAG_NBRIDGE =       (1 << 8),
00472    /*! the channel is in an auto-incrementing dialplan processor,
00473     *  so when ->priority is set, it will get incremented before
00474     *  finding the next priority to run */
00475    AST_FLAG_IN_AUTOLOOP =   (1 << 9),
00476    /*! This is an outgoing call */
00477    AST_FLAG_OUTGOING =      (1 << 10),
00478    /*! This channel is being whispered on */
00479    AST_FLAG_WHISPER =       (1 << 11),
00480    /*! A DTMF_BEGIN frame has been read from this channel, but not yet an END */
00481    AST_FLAG_IN_DTMF =       (1 << 12),
00482    /*! A DTMF_END was received when not IN_DTMF, so the length of the digit is 
00483     *  currently being emulated */
00484    AST_FLAG_EMULATE_DTMF =  (1 << 13),
00485    /*! This is set to tell the channel not to generate DTMF begin frames, and
00486     *  to instead only generate END frames. */
00487    AST_FLAG_END_DTMF_ONLY = (1 << 14),
00488 };

anonymous enum

ast_bridge_config flags

Enumerator:
AST_FEATURE_PLAY_WARNING 
AST_FEATURE_REDIRECT 
AST_FEATURE_DISCONNECT 
AST_FEATURE_ATXFER 
AST_FEATURE_AUTOMON 
AST_FEATURE_PARKCALL 

Definition at line 491 of file channel.h.

00491      {
00492    AST_FEATURE_PLAY_WARNING = (1 << 0),
00493    AST_FEATURE_REDIRECT =     (1 << 1),
00494    AST_FEATURE_DISCONNECT =   (1 << 2),
00495    AST_FEATURE_ATXFER =       (1 << 3),
00496    AST_FEATURE_AUTOMON =      (1 << 4),
00497    AST_FEATURE_PARKCALL =     (1 << 5),
00498 };

anonymous enum

Enumerator:
AST_CDR_TRANSFER 
AST_CDR_FORWARD 
AST_CDR_CALLWAIT 
AST_CDR_CONFERENCE 

Definition at line 540 of file channel.h.

00540      {
00541    AST_CDR_TRANSFER =   (1 << 0),
00542    AST_CDR_FORWARD =    (1 << 1),
00543    AST_CDR_CALLWAIT =   (1 << 2),
00544    AST_CDR_CONFERENCE = (1 << 3),
00545 };

anonymous enum

Enumerator:
AST_SOFTHANGUP_DEV  Soft hangup by device
AST_SOFTHANGUP_ASYNCGOTO  Soft hangup for async goto
AST_SOFTHANGUP_SHUTDOWN 
AST_SOFTHANGUP_TIMEOUT 
AST_SOFTHANGUP_APPUNLOAD 
AST_SOFTHANGUP_EXPLICIT 
AST_SOFTHANGUP_UNBRIDGE 

Definition at line 547 of file channel.h.

00547      {
00548    /*! Soft hangup by device */
00549    AST_SOFTHANGUP_DEV =       (1 << 0),
00550    /*! Soft hangup for async goto */
00551    AST_SOFTHANGUP_ASYNCGOTO = (1 << 1),
00552    AST_SOFTHANGUP_SHUTDOWN =  (1 << 2),
00553    AST_SOFTHANGUP_TIMEOUT =   (1 << 3),
00554    AST_SOFTHANGUP_APPUNLOAD = (1 << 4),
00555    AST_SOFTHANGUP_EXPLICIT =  (1 << 5),
00556    AST_SOFTHANGUP_UNBRIDGE =  (1 << 6),
00557 };

enum ast_bridge_result

Enumerator:
AST_BRIDGE_COMPLETE 
AST_BRIDGE_FAILED 
AST_BRIDGE_FAILED_NOWARN 
AST_BRIDGE_RETRY 

Definition at line 139 of file channel.h.

00139                        {
00140    AST_BRIDGE_COMPLETE = 0,
00141    AST_BRIDGE_FAILED = -1,
00142    AST_BRIDGE_FAILED_NOWARN = -2,
00143    AST_BRIDGE_RETRY = -3,
00144 };

enum ast_channel_adsicpe

Enumerator:
AST_ADSI_UNKNOWN 
AST_ADSI_AVAILABLE 
AST_ADSI_UNAVAILABLE 
AST_ADSI_OFFHOOKONLY 

Definition at line 284 of file channel.h.

enum ast_channel_state

ast_channel states

Note:
Bits 0-15 of state are reserved for the state (up/down) of the line Bits 16-32 of state are reserved for flags
Enumerator:
AST_STATE_DOWN  Channel is down and available
AST_STATE_RESERVED  Channel is down, but reserved
AST_STATE_OFFHOOK  Channel is off hook
AST_STATE_DIALING  Digits (or equivalent) have been dialed
AST_STATE_RING  Line is ringing
AST_STATE_RINGING  Remote end is ringing
AST_STATE_UP  Line is up
AST_STATE_BUSY  Line is busy
AST_STATE_DIALING_OFFHOOK  Digits (or equivalent) have been dialed while offhook
AST_STATE_PRERING  Channel has detected an incoming call and is waiting for ring
AST_STATE_MUTE  Do not transmit voice data

Definition at line 297 of file channel.h.

00297                        {
00298    /*! Channel is down and available */
00299    AST_STATE_DOWN,
00300    /*! Channel is down, but reserved */
00301    AST_STATE_RESERVED,
00302    /*! Channel is off hook */
00303    AST_STATE_OFFHOOK,
00304    /*! Digits (or equivalent) have been dialed */
00305    AST_STATE_DIALING,
00306    /*! Line is ringing */
00307    AST_STATE_RING,
00308    /*! Remote end is ringing */
00309    AST_STATE_RINGING,
00310    /*! Line is up */
00311    AST_STATE_UP,
00312    /*! Line is busy */
00313    AST_STATE_BUSY,
00314    /*! Digits (or equivalent) have been dialed while offhook */
00315    AST_STATE_DIALING_OFFHOOK,
00316    /*! Channel has detected an incoming call and is waiting for ring */
00317    AST_STATE_PRERING,
00318 
00319    /*! Do not transmit voice data */
00320    AST_STATE_MUTE = (1 << 16),
00321 };

enum channelreloadreason

Channel reload reasons for manager events at load or reload of configuration.

Enumerator:
CHANNEL_MODULE_LOAD 
CHANNEL_MODULE_RELOAD 
CHANNEL_CLI_RELOAD 
CHANNEL_MANAGER_RELOAD 

Definition at line 561 of file channel.h.


Function Documentation

struct ast_channel* __ast_request_and_dial ( const char *  type,
int  format,
void *  data,
int  timeout,
int *  reason,
const char *  cidnum,
const char *  cidname,
struct outgoing_helper oh 
)

Definition at line 3059 of file channel.c.

References ast_channel::_state, outgoing_helper::account, ast_call(), AST_CAUSE_BUSY, AST_CAUSE_CONGESTION, ast_cdr_alloc(), ast_cdr_disposition(), ast_cdr_end(), ast_cdr_failed(), ast_cdr_init(), ast_cdr_setaccount(), ast_cdr_setapp(), ast_cdr_start(), ast_cdr_update(), 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_UNHOLD, AST_CONTROL_VIDUPDATE, AST_FRAME_CONTROL, ast_frfree(), ast_hangup(), ast_log(), ast_read(), ast_request(), ast_set_callerid(), 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_channel::hangupcause, LOG_NOTICE, outgoing_helper::parent_channel, ast_channel::priority, outgoing_helper::priority, and outgoing_helper::vars.

Referenced by ast_pbx_outgoing_app(), ast_pbx_outgoing_exten(), ast_request_and_dial(), and parkandannounce_exec().

03060 {
03061    int dummy_outstate;
03062    int cause = 0;
03063    struct ast_channel *chan;
03064    int res = 0;
03065    
03066    if (outstate)
03067       *outstate = 0;
03068    else
03069       outstate = &dummy_outstate;   /* make outstate always a valid pointer */
03070 
03071    chan = ast_request(type, format, data, &cause);
03072    if (!chan) {
03073       ast_log(LOG_NOTICE, "Unable to request channel %s/%s\n", type, (char *)data);
03074       /* compute error and return */
03075       if (cause == AST_CAUSE_BUSY)
03076          *outstate = AST_CONTROL_BUSY;
03077       else if (cause == AST_CAUSE_CONGESTION)
03078          *outstate = AST_CONTROL_CONGESTION;
03079       return NULL;
03080    }
03081 
03082    if (oh) {
03083       if (oh->vars)  
03084          ast_set_variables(chan, oh->vars);
03085       /* XXX why is this necessary, for the parent_channel perhaps ? */
03086       if (!ast_strlen_zero(oh->cid_num) && !ast_strlen_zero(oh->cid_name))
03087          ast_set_callerid(chan, oh->cid_num, oh->cid_name, oh->cid_num);
03088       if (oh->parent_channel)
03089          ast_channel_inherit_variables(oh->parent_channel, chan);
03090       if (oh->account)
03091          ast_cdr_setaccount(chan, oh->account); 
03092    }
03093    ast_set_callerid(chan, cid_num, cid_name, cid_num);
03094 
03095    
03096 
03097    if (!chan->cdr) { /* up till now, this insertion hasn't been done. Therefore,
03098             to keep from throwing off the basic order of the universe,
03099             we will try to keep this cdr from getting posted. */
03100       chan->cdr = ast_cdr_alloc();
03101       ast_cdr_init(chan->cdr, chan);
03102       ast_cdr_start(chan->cdr);
03103    }
03104    if (ast_call(chan, data, 0)) {   /* ast_call failed... */
03105       ast_log(LOG_NOTICE, "Unable to call channel %s/%s\n", type, (char *)data);
03106    } else {
03107       res = 1; /* mark success in case chan->_state is already AST_STATE_UP */
03108       while (timeout && chan->_state != AST_STATE_UP) {
03109          struct ast_frame *f;
03110          res = ast_waitfor(chan, timeout);
03111          if (res <= 0) /* error, timeout, or done */
03112             break;
03113          if (timeout > -1)
03114             timeout = res;
03115          f = ast_read(chan);
03116          if (!f) {
03117             *outstate = AST_CONTROL_HANGUP;
03118             res = 0;
03119             break;
03120          }
03121          if (f->frametype == AST_FRAME_CONTROL) {
03122             switch (f->subclass) {
03123             case AST_CONTROL_RINGING:  /* record but keep going */
03124                *outstate = f->subclass;
03125                break;
03126 
03127             case AST_CONTROL_BUSY:
03128             case AST_CONTROL_CONGESTION:
03129             case AST_CONTROL_ANSWER:
03130                *outstate = f->subclass;
03131                timeout = 0;      /* trick to force exit from the while() */
03132                break;
03133 
03134             /* Ignore these */
03135             case AST_CONTROL_PROGRESS:
03136             case AST_CONTROL_PROCEEDING:
03137             case AST_CONTROL_HOLD:
03138             case AST_CONTROL_UNHOLD:
03139             case AST_CONTROL_VIDUPDATE:
03140             case -1:       /* Ignore -- just stopping indications */
03141                break;
03142 
03143             default:
03144                ast_log(LOG_NOTICE, "Don't know what to do with control frame %d\n", f->subclass);
03145             }
03146          }
03147          ast_frfree(f);
03148       }
03149    }
03150 
03151    /* Final fixups */
03152    if (oh) {
03153       if (!ast_strlen_zero(oh->context))
03154          ast_copy_string(chan->context, oh->context, sizeof(chan->context));
03155       if (!ast_strlen_zero(oh->exten))
03156          ast_copy_string(chan->exten, oh->exten, sizeof(chan->exten));
03157       if (oh->priority) 
03158          chan->priority = oh->priority;
03159    }
03160    if (chan->_state == AST_STATE_UP)
03161       *outstate = AST_CONTROL_ANSWER;
03162 
03163    if (res <= 0) {
03164       if (!chan->cdr && (chan->cdr = ast_cdr_alloc()))
03165          ast_cdr_init(chan->cdr, chan);
03166       if (chan->cdr) {
03167          char tmp[256];
03168          snprintf(tmp, sizeof(tmp), "%s/%s", type, (char *)data);
03169          ast_cdr_setapp(chan->cdr,"Dial",tmp);
03170          ast_cdr_update(chan);
03171          ast_cdr_start(chan->cdr);
03172          ast_cdr_end(chan->cdr);
03173          /* If the cause wasn't handled properly */
03174          if (ast_cdr_disposition(chan->cdr,chan->hangupcause))
03175             ast_cdr_failed(chan->cdr);
03176       }
03177       ast_hangup(chan);
03178       chan = NULL;
03179    }
03180    return chan;
03181 }

int ast_activate_generator ( struct ast_channel chan,
struct ast_generator gen,
void *  params 
)

Activate a given generator

Definition at line 1856 of file channel.c.

References ast_generator::alloc, ast_channel_lock, ast_channel_unlock, ast_prod(), ast_settimeout(), gen, 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(), local_ast_moh_start(), and milliwatt_exec().

01857 {
01858    int res = 0;
01859 
01860    ast_channel_lock(chan);
01861 
01862    if (chan->generatordata) {
01863       if (chan->generator && chan->generator->release)
01864          chan->generator->release(chan, chan->generatordata);
01865       chan->generatordata = NULL;
01866    }
01867 
01868    ast_prod(chan);
01869    if (gen->alloc && !(chan->generatordata = gen->alloc(chan, params))) {
01870       res = -1;
01871    }
01872    
01873    if (!res) {
01874       ast_settimeout(chan, 160, generator_force, chan);
01875       chan->generator = gen;
01876    }
01877 
01878    ast_channel_unlock(chan);
01879 
01880    return res;
01881 }

int ast_active_channels ( void   ) 

returns number of active/allocated channels

Returns number of active/allocated channels

Definition at line 460 of file channel.c.

References AST_LIST_LOCK, AST_LIST_TRAVERSE, and AST_LIST_UNLOCK.

Referenced by quit_handler().

00461 {
00462    struct ast_channel *c;
00463    int cnt = 0;
00464    AST_LIST_LOCK(&channels);
00465    AST_LIST_TRAVERSE(&channels, c, chan_list)
00466       cnt++;
00467    AST_LIST_UNLOCK(&channels);
00468    return cnt;
00469 }

static int ast_add_fd ( struct pollfd pfd,
int  fd 
) [inline, static]

if fd is a valid descriptor, set *pfd with the descriptor

Returns:
Return 1 (not -1!) if added, 0 otherwise (so we can add the return value to the index into the array)

Definition at line 1339 of file channel.h.

References pollfd::events, pollfd::fd, POLLIN, and POLLPRI.

Referenced by ast_waitfor_nandfds().

01340 {
01341    pfd->fd = fd;
01342    pfd->events = POLLIN | POLLPRI;
01343    return fd >= 0;
01344 }

int ast_answer ( struct ast_channel chan  ) 

Answer a ringing call.

Parameters:
chan channel to answer This function answers a channel and handles all necessary call setup functions.
Returns:
Returns 0 on success, -1 on failure

Definition at line 1789 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_setstate(), AST_STATE_RING, AST_STATE_RINGING, AST_STATE_UP, ast_test_flag, ast_channel::cdr, and ast_channel::tech.

Referenced by __login_exec(), agi_exec_full(), alarmreceiver_exec(), app_exec(), ast_bridge_call(), ast_control_streamfile(), ast_pickup_call(), auth_exec(), background_detect_exec(), builtin_parkcall(), common_exec(), conf_exec(), count_exec(), dictate_exec(), directory_exec(), disa_exec(), features_answer(), handle_answer(), ices_exec(), milliwatt_exec(), mwanalyze_exec(), nv_background_detect_exec(), nv_detectfax_exec(), park_call_exec(), park_exec(), pbx_builtin_answer(), pbx_builtin_background(), pickup_do(), playback_exec(), privacy_exec(), read_exec(), run_station(), rxfax_exec(), sayunixtime_exec(), send_waveform_to_channel(), skel_exec(), sla_handle_dial_state_event(), sla_station_exec(), speech_background(), testclient_exec(), testserver_exec(), txfax_exec(), vm_exec(), vm_execmain(), waitforsilence_exec(), zapateller_exec(), and zapras_exec().

01790 {
01791    int res = 0;
01792    ast_channel_lock(chan);
01793    /* You can't answer an outbound call */
01794    if (ast_test_flag(chan, AST_FLAG_OUTGOING)) {
01795       ast_channel_unlock(chan);
01796       return 0;
01797    }
01798    /* Stop if we're a zombie or need a soft hangup */
01799    if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) {
01800       ast_channel_unlock(chan);
01801       return -1;
01802    }
01803    switch(chan->_state) {
01804    case AST_STATE_RINGING:
01805    case AST_STATE_RING:
01806       if (chan->tech->answer)
01807          res = chan->tech->answer(chan);
01808       ast_setstate(chan, AST_STATE_UP);
01809       ast_cdr_answer(chan->cdr);
01810       break;
01811    case AST_STATE_UP:
01812       ast_cdr_answer(chan->cdr);
01813       break;
01814    default:
01815       break;
01816    }
01817    ast_channel_unlock(chan);
01818    return res;
01819 }

int ast_autoservice_start ( struct ast_channel chan  ) 

Automatically service a channel for us...

Return values:
0 success
-1 failure, or the channel is already being autoserviced

Definition at line 96 of file autoservice.c.

References ast_calloc, 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, asthread, autoservice_run(), asent::chan, free, and LOG_WARNING.

Referenced by _macro_exec(), ast_dtmf_stream(), ast_get_enum(), ast_get_srv(), ast_get_txt(), bridge_playfile(), builtin_atxfer(), builtin_automonitor(), builtin_blindtransfer(), conf_play(), feature_exec_app(), osplookup_exec(), sla_station_exec(), and try_calling().

00097 {
00098    int res = -1;
00099    struct asent *as;
00100    AST_LIST_LOCK(&aslist);
00101 
00102    /* Check if the channel already has autoservice */
00103    AST_LIST_TRAVERSE(&aslist, as, list) {
00104       if (as->chan == chan)
00105          break;
00106    }
00107 
00108    /* If not, start autoservice on channel */
00109    if (!as && (as = ast_calloc(1, sizeof(*as)))) {
00110       as->chan = chan;
00111       AST_LIST_INSERT_HEAD(&aslist, as, list);
00112       res = 0;
00113       if (asthread == AST_PTHREADT_NULL) { /* need start the thread */
00114          if (ast_pthread_create_background(&asthread, NULL, autoservice_run, NULL)) {
00115             ast_log(LOG_WARNING, "Unable to create autoservice thread :(\n");
00116             /* There will only be a single member in the list at this point,
00117                the one we just added. */
00118             AST_LIST_REMOVE(&aslist, as, list);
00119             free(as);
00120             res = -1;
00121          } else
00122             pthread_kill(asthread, SIGURG);
00123       }
00124    }
00125    AST_LIST_UNLOCK(&aslist);
00126    return res;
00127 }

int ast_autoservice_stop ( struct ast_channel chan  ) 

Stop servicing a channel for us...

Return values:
0 success
-1 error, or the channel has been hungup

Definition at line 129 of file autoservice.c.

References ast_channel::_softhangup, AST_FLAG_BLOCKING, AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, AST_PTHREADT_NULL, ast_test_flag, asthread, asent::chan, and free.

Referenced by _macro_exec(), ast_dtmf_stream(), ast_get_srv(), ast_get_txt(), bridge_playfile(), builtin_atxfer(), builtin_automonitor(), conf_play(), feature_exec_app(), finishup(), osplookup_exec(), sla_station_exec(), and try_calling().

00130 {
00131    int res = -1;
00132    struct asent *as;
00133 
00134    AST_LIST_LOCK(&aslist);
00135    AST_LIST_TRAVERSE_SAFE_BEGIN(&aslist, as, list) {  
00136       if (as->chan == chan) {
00137          AST_LIST_REMOVE_CURRENT(&aslist, list);
00138          free(as);
00139          if (!chan->_softhangup)
00140             res = 0;
00141          break;
00142       }
00143    }
00144    AST_LIST_TRAVERSE_SAFE_END
00145 
00146    if (asthread != AST_PTHREADT_NULL) 
00147       pthread_kill(asthread, SIGURG);
00148    AST_LIST_UNLOCK(&aslist);
00149 
00150    /* Wait for it to un-block */
00151    while(ast_test_flag(chan, AST_FLAG_BLOCKING))
00152       usleep(1000);
00153    return res;
00154 }

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 447 of file channel.c.

References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_softhangup(), AST_SOFTHANGUP_SHUTDOWN, and shutting_down.

Referenced by quit_handler().

00448 {
00449    struct ast_channel *c;
00450    shutting_down = 1;
00451    if (hangup) {
00452       AST_LIST_LOCK(&channels);
00453       AST_LIST_TRAVERSE(&channels, c, chan_list)
00454          ast_softhangup(c, AST_SOFTHANGUP_SHUTDOWN);
00455       AST_LIST_UNLOCK(&channels);
00456    }
00457 }

int ast_best_codec ( int  fmts  ) 

Pick the best audio codec.

Pick the best codec

G.722 is better then all codecs in this list

alaw used by all telephone equipment at Russia

Okay, well, signed linear is easy to translate into other stuff! slinear<->alaw recoding very fast

ulaw standart for USA and Japan

Speex is free, but computationally more expensive than GSM

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

G.729a is faster than 723 and slightly less expensive

Down to G.723.1 which is proprietary but at least designed for voice

Ick, LPC10 sounds terrible, but at least we have code for it, if you're tacky enough to use it

Definition at line 672 of file channel.c.

References 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_SPEEX, AST_FORMAT_ULAW, ast_log(), LOG_WARNING, and prefs.

Referenced by __login_exec(), __oh323_new(), agent_call(), ast_channel_best_codec(), ast_codec_choose(), ast_iax2_new(), builtin_atxfer(), echo_exec(), findmeexec(), gtalk_new(), handle_open_receive_channel_ack_message(), iax2_request(), local_new(), mgcp_new(), sip_new(), skinny_new(), socket_process(), and transmit_connect().

00673 {
00674    /* This just our opinion, expressed in code.  We are asked to choose
00675       the best codec to use, given no information */
00676    int x;
00677    static int prefs[] =
00678    {
00679       /*! G.722 is better then all codecs in this list */
00680       AST_FORMAT_G722,
00681       /*! alaw used by all telephone equipment at Russia */
00682       AST_FORMAT_ALAW,
00683       /*! Okay, well, signed linear is easy to translate into other stuff! slinear<->alaw recoding very fast */
00684       AST_FORMAT_SLINEAR,
00685       /*! ulaw standart for USA and Japan */
00686       AST_FORMAT_ULAW,
00687       /*! Speex is free, but computationally more expensive than GSM */
00688       AST_FORMAT_SPEEX,
00689       /*! G.726 is standard ADPCM, in RFC3551 packing order */
00690       AST_FORMAT_G726,
00691       /*! G.726 is standard ADPCM, in AAL2 packing order */
00692       AST_FORMAT_G726_AAL2,
00693       /*! ADPCM has great sound quality and is still pretty easy to translate */
00694       AST_FORMAT_ADPCM,
00695       /*! Okay, we're down to vocoders now, so pick GSM because it's small and easier to
00696           translate and sounds pretty good */
00697       AST_FORMAT_GSM,
00698       /*! iLBC is not too bad */
00699       AST_FORMAT_ILBC,
00700       /*! G.729a is faster than 723 and slightly less expensive */
00701       AST_FORMAT_G729A,
00702       /*! Down to G.723.1 which is proprietary but at least designed for voice */
00703       AST_FORMAT_G723_1,
00704       /*! Ick, LPC10 sounds terrible, but at least we have code for it, if you're tacky enough
00705           to use it */
00706       AST_FORMAT_LPC10,
00707    };
00708 
00709    /* Strip out video */
00710    fmts &= AST_FORMAT_AUDIO_MASK;
00711    
00712    /* Find the first preferred codec in the format given */
00713    for (x=0; x < (sizeof(prefs) / sizeof(prefs[0]) ); x++)
00714       if (fmts & prefs[x])
00715          return prefs[x];
00716    ast_log(LOG_WARNING, "Don't know any of 0x%x formats\n", fmts);
00717    return 0;
00718 }

struct ast_channel* ast_bridged_channel ( struct ast_channel chan  ) 

Find bridged channel.

Parameters:
chan Current channel

Definition at line 3895 of file channel.c.

References ast_channel::_bridge, ast_channel_tech::bridged_channel, and ast_channel::tech.

Referenced by __zt_exception(), agents_show(), agents_show_online(), ast_channel_masquerade(), attempt_transfer(), check_bridge(), common_exec(), console_transfer(), console_transfer_deprecated(), create_jb(), export_aoc_vars(), handle_chanlist(), handle_chanlist_deprecated(), handle_hd_hf(), handle_invite_replaces(), handle_request(), handle_request_bye(), handle_request_info(), handle_request_invite(), handle_request_refer(), handle_response_invite(), handle_showchan(), handle_showchan_deprecated(), local_attended_transfer(), mgcp_hangup(), mgcp_ss(), misdn_transfer_bc(), mixmonitor_thread(), schedule_delivery(), sip_read(), socket_process(), ss_thread(), start_spying(), startmon(), zt_handle_event(), and zt_hangup().

03896 {
03897    struct ast_channel *bridged;
03898    bridged = chan->_bridge;
03899    if (bridged && bridged->tech->bridged_channel)
03900       bridged = bridged->tech->bridged_channel(chan, bridged);
03901    return bridged;
03902 }

int ast_call ( struct ast_channel chan,
char *  addr,
int  timeout 
)

Make a call.

Parameters:
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.
Returns:
Returns -1 on failure, 0 on not enough time (does not automatically stop ringing), and the number of seconds the connect took otherwise.

Definition at line 3238 of file channel.c.

References 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, and ast_channel::tech.

Referenced by __ast_request_and_dial(), agent_call(), ast_feature_request_and_dial(), attempt_reconnect(), begin_dial(), connect_link(), features_call(), findmeexec(), ring_entry(), rpt(), and wait_for_answer().

03239 {
03240    /* Place an outgoing call, but don't wait any longer than timeout ms before returning.
03241       If the remote end does not answer within the timeout, then do NOT hang up, but
03242       return anyway.  */
03243    int res = -1;
03244    /* Stop if we're a zombie or need a soft hangup */
03245    ast_channel_lock(chan);
03246    if (!ast_test_flag(chan, AST_FLAG_ZOMBIE) && !ast_check_hangup(chan)) {
03247       if (chan->tech->call)
03248          res = chan->tech->call(chan, addr, timeout);
03249       ast_set_flag(chan, AST_FLAG_OUTGOING);
03250    }
03251    ast_channel_unlock(chan);
03252    return res;
03253 }

void ast_cancel_shutdown ( void   ) 

Cancel a shutdown in progress.

Cancels an existing shutdown and returns to normal operation

Definition at line 472 of file channel.c.

References shutting_down.

Referenced by handle_abort_halt().

00473 {
00474    shutting_down = 0;
00475 }

const char* ast_cause2str ( int  state  ) 

Gives the string form of a given hangup cause.

Parameters:
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 592 of file channel.c.

References causes, and desc.

Referenced by __transmit_response(), ast_hangup(), findmeexec(), sip_hangup(), and transmit_request_with_auth().

00593 {
00594    int x;
00595 
00596    for (x=0; x < sizeof(causes) / sizeof(causes[0]); x++) {
00597       if (causes[x].cause == cause)
00598          return causes[x].desc;
00599    }
00600 
00601    return "Unknown";
00602 }

void ast_change_name ( struct ast_channel chan,
char *  newname 
)

Change channel name.

Definition at line 3470 of file channel.c.

References ast_string_field_set, EVENT_FLAG_CALL, manager_event(), and name.

03471 {
03472    manager_event(EVENT_FLAG_CALL, "Rename", "Oldname: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", chan->name, newname, chan->uniqueid);
03473    ast_string_field_set(chan, name, newname);
03474 }

struct ast_channel* 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 *  name_fmt,
  ... 
)

Create a channel structure.

Returns:
Returns NULL on failure to allocate.
Note:
New channels are by default set to the "default" context and extension "s"

Definition at line 726 of file channel.c.

References ast_calloc, ast_log(), AST_MAX_FDS, ast_string_field_init, ast_channel::flags, free, HAVE_ZAPTEL, LOG_WARNING, sched_context_create(), sched_context_destroy(), and shutting_down.

Referenced by __oh323_new(), agent_new(), alsa_new(), ast_async_goto(), ast_iax2_new(), ast_masq_park_call(), ast_pbx_outgoing_cdr_failed(), ast_pbx_outgoing_exten(), builtin_atxfer(), check_goto_on_transfer(), features_new(), gtalk_new(), iax_park(), local_new(), make_email_file(), mgcp_new(), misdn_new(), nbs_new(), oss_new(), pbx_substitute_variables_helper_full(), phone_new(), sendpage(), sip_new(), sip_park(), skinny_new(), and zt_new().

00727 {
00728    struct ast_channel *tmp;
00729    int x;
00730    int flags;
00731    struct varshead *headp;
00732    va_list ap1, ap2;
00733 
00734    /* If shutting down, don't allocate any new channels */
00735    if (shutting_down) {
00736       ast_log(LOG_WARNING, "Channel allocation failed: Refusing due to active shutdown\n");
00737       return NULL;
00738    }
00739 
00740    if (!(tmp = ast_calloc(1, sizeof(*tmp))))
00741       return NULL;
00742 
00743    if (!(tmp->sched = sched_context_create())) {
00744       ast_log(LOG_WARNING, "Channel allocation failed: Unable to create schedule context\n");
00745       free(tmp);
00746       return NULL;
00747    }
00748    
00749    if ((ast_string_field_init(tmp, 128))) {
00750       sched_context_destroy(tmp->sched);
00751       free(tmp);
00752       return NULL;
00753    }
00754 
00755    /* Don't bother initializing the last two FD here, because they
00756       will *always* be set just a few lines down (AST_TIMING_FD,
00757       AST_ALERT_FD). */
00758    for (x = 0; x < AST_MAX_FDS - 2; x++)
00759       tmp->fds[x] = -1;
00760 
00761 #ifdef HAVE_ZAPTEL
00762    tmp->timingfd = open("/dev/zap/timer", O_RDWR);
00763    if (tmp->timingfd > -1) {
00764       /* Check if timing interface supports new
00765          ping/pong scheme */
00766       flags = 1;
00767       if (!ioctl(tmp->timingfd, ZT_TIMERPONG, &flags))
00768          needqueue = 0;
00769    }
00770 #else
00771    tmp->timingfd = -1;              
00772 #endif               
00773 
00774    if (needqueue) {
00775       if (pipe(tmp->alertpipe)) {
00776          ast_log(LOG_WARNING, "Channel allocation failed: Can't create alert pipe!\n");
00777          ast_string_field_free_pools(tmp);
00778          free(tmp);
00779          return NULL;
00780       } else {
00781          flags = fcntl(tmp->alertpipe[0], F_GETFL);
00782          fcntl(tmp->alertpipe[0], F_SETFL, flags | O_NONBLOCK);
00783          flags = fcntl(tmp->alertpipe[1], F_GETFL);
00784          fcntl(tmp->alertpipe[1], F_SETFL, flags | O_NONBLOCK);
00785       }
00786    } else   /* Make sure we've got it done right if they don't */
00787       tmp->alertpipe[0] = tmp->alertpipe[1] = -1;
00788 
00789    /* Always watch the alertpipe */
00790    tmp->fds[AST_ALERT_FD] = tmp->alertpipe[0];
00791    /* And timing pipe */
00792    tmp->fds[AST_TIMING_FD] = tmp->timingfd;
00793    ast_string_field_set(tmp, name, "**Unknown**");
00794 
00795    /* Initial state */
00796    tmp->_state = state;
00797 
00798    tmp->streamid = -1;
00799    
00800    tmp->fin = global_fin;
00801    tmp->fout = global_fout;
00802 
00803    if (ast_strlen_zero(ast_config_AST_SYSTEM_NAME)) {
00804       ast_string_field_build(tmp, uniqueid, "%li.%d", (long) time(NULL), 
00805          ast_atomic_fetchadd_int(&uniqueint, 1));
00806    } else {
00807       ast_string_field_build(tmp, uniqueid, "%s-%li.%d", ast_config_AST_SYSTEM_NAME, 
00808          (long) time(NULL), ast_atomic_fetchadd_int(&uniqueint, 1));
00809    }
00810 
00811    tmp->cid.cid_name = ast_strdup(cid_name);
00812    tmp->cid.cid_num = ast_strdup(cid_num);
00813    
00814    if (!ast_strlen_zero(name_fmt)) {
00815       /* Almost every channel is calling this function, and setting the name via the ast_string_field_build() call.
00816        * And they all use slightly different formats for their name string.
00817        * This means, to set the name here, we have to accept variable args, and call the string_field_build from here.
00818        * This means, that the stringfields must have a routine that takes the va_lists directly, and 
00819        * uses them to build the string, instead of forming the va_lists internally from the vararg ... list.
00820        * This new function was written so this can be accomplished.
00821        */
00822       va_start(ap1, name_fmt);
00823       va_start(ap2, name_fmt);
00824       ast_string_field_build_va(tmp, name, name_fmt, ap1, ap2);
00825       va_end(ap1);
00826       va_end(ap2);
00827 
00828       /* and now, since the channel structure is built, and has its name, let's call the
00829        * manager event generator with this Newchannel event. This is the proper and correct
00830        * place to make this call, but you sure do have to pass a lot of data into this func
00831        * to do it here!
00832        */
00833       manager_event(EVENT_FLAG_CALL, "Newchannel",
00834                "Channel: %s\r\n"
00835                "State: %s\r\n"
00836                "CallerIDNum: %s\r\n"
00837                "CallerIDName: %s\r\n"
00838                "Uniqueid: %s\r\n",
00839                tmp->name, ast_state2str(state),
00840                S_OR(cid_num, "<unknown>"),
00841                S_OR(cid_name, "<unknown>"),
00842                tmp->uniqueid);
00843    }
00844 
00845    /* Reminder for the future: under what conditions do we NOT want to track cdrs on channels? */
00846 
00847    /* These 4 variables need to be set up for the cdr_init() to work right */
00848    if (amaflag)
00849       tmp->amaflags = amaflag;
00850    else
00851       tmp->amaflags = ast_default_amaflags;
00852    
00853    if (!ast_strlen_zero(acctcode))
00854       ast_string_field_set(tmp, accountcode, acctcode);
00855    else
00856       ast_string_field_set(tmp, accountcode, ast_default_accountcode);
00857       
00858    if (!ast_strlen_zero(context))
00859       ast_copy_string(tmp->context, context, sizeof(tmp->context));
00860    else
00861       strcpy(tmp->context, "default");
00862 
00863    if (!ast_strlen_zero(exten))
00864       ast_copy_string(tmp->exten, exten, sizeof(tmp->exten));
00865    else
00866       strcpy(tmp->exten, "s");
00867 
00868    tmp->priority = 1;
00869       
00870    tmp->cdr = ast_cdr_alloc();
00871    ast_cdr_init(tmp->cdr, tmp);
00872    ast_cdr_start(tmp->cdr);
00873    
00874    headp = &tmp->varshead;
00875    AST_LIST_HEAD_INIT_NOLOCK(headp);
00876    
00877    ast_mutex_init(&tmp->lock);
00878    
00879    AST_LIST_HEAD_INIT_NOLOCK(&tmp->datastores);
00880    
00881    ast_string_field_set(tmp, language, defaultlanguage);
00882 
00883    tmp->tech = &null_tech;
00884 
00885    AST_LIST_LOCK(&channels);
00886    AST_LIST_INSERT_HEAD(&channels, tmp, chan_list);
00887    AST_LIST_UNLOCK(&channels);
00888 
00889    return tmp;
00890 }

static int ast_channel_best_codec ( struct ast_channel channel  )  [inline, static]

Pick the best codec from channel nativeformats.

Parameters:
channel channel, from that nativeformats used

Definition at line 1106 of file channel.h.

References ast_best_codec(), and ast_channel::nativeformats.

Referenced by ast_set_best_format().

01107 {
01108 #ifndef BUG_4825 
01109    return ast_best_codec(channel->nativeformats);
01110 #else 
01111    return ast_best_codec(channel->nativeformats.audio_bits);
01112 #endif   
01113 }

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

Parameters:
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 4084 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_FEATURE_PLAY_WARNING, AST_FEATURE_REDIRECT, AST_FLAG_END_DTMF_ONLY, AST_FLAG_NBRIDGE, AST_FLAG_ZOMBIE, ast_generic_bridge(), ast_log(), ast_set_flag, AST_SOFTHANGUP_UNBRIDGE, ast_strlen_zero(), ast_test_flag, ast_tvadd(), ast_tvsub(), ast_verbose(), ast_channel_tech::bridge, bridge_playfile(), ast_channel::cid, ast_callerid::cid_num, config, EVENT_FLAG_CALL, ast_channel::generator, LOG_DEBUG, LOG_WARNING, manager_event(), ast_channel::monitor, ast_channel::nativeformats, option_verbose, pbx_builtin_getvar_helper(), pbx_builtin_setvar_helper(), ast_channel::readformat, ast_channel_tech::send_digit_begin, ast_channel::spies, t, ast_channel::tech, VERBOSE_PREFIX_3, and ast_channel::writeformat.

Referenced by ast_bridge_call().

04086 {
04087    struct ast_channel *who = NULL;
04088    enum ast_bridge_result res = AST_BRIDGE_COMPLETE;
04089    int nativefailed=0;
04090    int firstpass;
04091    int o0nativeformats;
04092    int o1nativeformats;
04093    long time_left_ms=0;
04094    struct timeval nexteventts = { 0, };
04095    char caller_warning = 0;
04096    char callee_warning = 0;
04097 
04098    if (c0->_bridge) {
04099       ast_log(LOG_WARNING, "%s is already in a bridge with %s\n",
04100          c0->name, c0->_bridge->name);
04101       return -1;
04102    }
04103    if (c1->_bridge) {
04104       ast_log(LOG_WARNING, "%s is already in a bridge with %s\n",
04105          c1->name, c1->_bridge->name);
04106       return -1;
04107    }
04108    
04109    /* Stop if we're a zombie or need a soft hangup */
04110    if (ast_test_flag(c0, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c0) ||
04111        ast_test_flag(c1, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c1))
04112       return -1;
04113 
04114    *fo = NULL;
04115    firstpass = config->firstpass;
04116    config->firstpass = 0;
04117 
04118    if (ast_tvzero(config->start_time))
04119       config->start_time = ast_tvnow();
04120    time_left_ms = config->timelimit;
04121 
04122    caller_warning = ast_test_flag(&config->features_caller, AST_FEATURE_PLAY_WARNING);
04123    callee_warning = ast_test_flag(&config->features_callee, AST_FEATURE_PLAY_WARNING);
04124 
04125    if (config->start_sound && firstpass) {
04126       if (caller_warning)
04127          bridge_playfile(c0, c1, config->start_sound, time_left_ms / 1000);
04128       if (callee_warning)
04129          bridge_playfile(c1, c0, config->start_sound, time_left_ms / 1000);
04130    }
04131 
04132    /* Keep track of bridge */
04133    c0->_bridge = c1;
04134    c1->_bridge = c0;
04135 
04136    /* \todo  XXX here should check that cid_num is not NULL */
04137    manager_event(EVENT_FLAG_CALL, "Link",
04138             "Channel1: %s\r\n"
04139             "Channel2: %s\r\n"
04140             "Uniqueid1: %s\r\n"
04141             "Uniqueid2: %s\r\n"
04142             "CallerID1: %s\r\n"
04143             "CallerID2: %s\r\n",
04144             c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num);
04145 
04146    o0nativeformats = c0->nativeformats;
04147    o1nativeformats = c1->nativeformats;
04148 
04149    if (config->feature_timer) {
04150       nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->feature_timer, 1000));
04151    } else if (config->timelimit) {
04152       nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->timelimit, 1000));
04153       if (caller_warning || callee_warning)
04154          nexteventts = ast_tvsub(nexteventts, ast_samp2tv(config->play_warning, 1000));
04155    }
04156 
04157    if (!c0->tech->send_digit_begin)
04158       ast_set_flag(c1, AST_FLAG_END_DTMF_ONLY);
04159    if (!c1->tech->send_digit_begin)
04160       ast_set_flag(c0, AST_FLAG_END_DTMF_ONLY);
04161 
04162    for (/* ever */;;) {
04163       struct timeval now = { 0, };
04164       int to;
04165 
04166       to = -1;
04167 
04168       if (!ast_tvzero(nexteventts)) {
04169          now = ast_tvnow();
04170          to = ast_tvdiff_ms(nexteventts, now);
04171          if (to <= 0) {
04172             if (!config->timelimit) {
04173                res = AST_BRIDGE_COMPLETE;
04174                break;
04175             }
04176             to = 0;
04177          }
04178       }
04179 
04180       if (config->timelimit) {
04181          time_left_ms = config->timelimit - ast_tvdiff_ms(now, config->start_time);
04182          if (time_left_ms < to)
04183             to = time_left_ms;
04184 
04185          if (time_left_ms <= 0) {
04186             if (caller_warning && config->end_sound)
04187                bridge_playfile(c0, c1, config->end_sound, 0);
04188             if (callee_warning && config->end_sound)
04189                bridge_playfile(c1, c0, config->end_sound, 0);
04190             *fo = NULL;
04191             if (who)
04192                *rc = who;
04193             res = 0;
04194             break;
04195          }
04196          
04197          if (!to) {
04198             if (time_left_ms >= 5000 && config->warning_sound && config->play_warning) {
04199                int t = (time_left_ms + 500) / 1000; /* round to nearest second */
04200                if (caller_warning)
04201                   bridge_playfile(c0, c1, config->warning_sound, t);
04202                if (callee_warning)
04203                   bridge_playfile(c1, c0, config->warning_sound, t);
04204             }
04205             if (config->warning_freq && (time_left_ms > (config->warning_freq + 5000)))
04206                nexteventts = ast_tvadd(nexteventts, ast_samp2tv(config->warning_freq, 1000));
04207             else
04208                nexteventts = ast_tvadd(config->start_time, ast_samp2tv(config->timelimit, 1000));
04209          }
04210       }
04211 
04212       if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE || c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE) {
04213          if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE)
04214             c0->_softhangup = 0;
04215          if (c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE)
04216             c1->_softhangup = 0;
04217          c0->_bridge = c1;
04218          c1->_bridge = c0;
04219          if (option_debug)
04220             ast_log(LOG_DEBUG, "Unbridge signal received. Ending native bridge.\n");
04221          continue;
04222       }
04223       
04224       /* Stop if we're a zombie or need a soft hangup */
04225       if (ast_test_flag(c0, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c0) ||
04226           ast_test_flag(c1, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c1)) {
04227          *fo = NULL;
04228          if (who)
04229             *rc = who;
04230          res = 0;
04231          if (option_debug)
04232             ast_log(LOG_DEBUG, "Bridge stops because we're zombie or need a soft hangup: c0=%s, c1=%s, flags: %s,%s,%s,%s\n",
04233                c0->name, c1->name,
04234                ast_test_flag(c0, AST_FLAG_ZOMBIE) ? "Yes" : "No",
04235                ast_check_hangup(c0) ? "Yes" : "No",
04236                ast_test_flag(c1, AST_FLAG_ZOMBIE) ? "Yes" : "No",
04237                ast_check_hangup(c1) ? "Yes" : "No");
04238          break;
04239       }
04240       
04241       /* See if the BRIDGEPEER variable needs to be updated */
04242       if (!ast_strlen_zero(pbx_builtin_getvar_helper(c0, "BRIDGEPEER")))
04243          pbx_builtin_setvar_helper(c0, "BRIDGEPEER", c1->name);
04244       if (!ast_strlen_zero(pbx_builtin_getvar_helper(c1, "BRIDGEPEER")))
04245          pbx_builtin_setvar_helper(c1, "BRIDGEPEER", c0->name);
04246       
04247       if (c0->tech->bridge &&
04248           (config->timelimit == 0) &&
04249           (c0->tech->bridge == c1->tech->bridge) &&
04250           !nativefailed && !c0->monitor && !c1->monitor &&
04251           !c0->spies && !c1->spies && !ast_test_flag(&(config->features_callee),AST_FEATURE_REDIRECT) &&
04252           !ast_test_flag(&(config->features_caller),AST_FEATURE_REDIRECT) ) {
04253          /* Looks like they share a bridge method and nothing else is in the way */
04254          ast_set_flag(c0, AST_FLAG_NBRIDGE);
04255          ast_set_flag(c1, AST_FLAG_NBRIDGE);
04256          if ((res = c0->tech->bridge(c0, c1, config->flags, fo, rc, to)) == AST_BRIDGE_COMPLETE) {
04257             /* \todo  XXX here should check that cid_num is not NULL */
04258             manager_event(EVENT_FLAG_CALL, "Unlink",
04259                      "Channel1: %s\r\n"
04260                      "Channel2: %s\r\n"
04261                      "Uniqueid1: %s\r\n"
04262                      "Uniqueid2: %s\r\n"
04263                      "CallerID1: %s\r\n"
04264                      "CallerID2: %s\r\n",
04265                      c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num);
04266             if (option_debug)
04267                ast_log(LOG_DEBUG, "Returning from native bridge, channels: %s, %s\n", c0->name, c1->name);
04268 
04269             ast_clear_flag(c0, AST_FLAG_NBRIDGE);
04270             ast_clear_flag(c1, AST_FLAG_NBRIDGE);
04271 
04272             if (c0->_softhangup == AST_SOFTHANGUP_UNBRIDGE || c1->_softhangup == AST_SOFTHANGUP_UNBRIDGE)
04273                continue;
04274 
04275             c0->_bridge = NULL;
04276             c1->_bridge = NULL;
04277 
04278             return res;
04279          } else {
04280             ast_clear_flag(c0, AST_FLAG_NBRIDGE);
04281             ast_clear_flag(c1, AST_FLAG_NBRIDGE);
04282          }
04283          switch (res) {
04284          case AST_BRIDGE_RETRY:
04285             continue;
04286          default:
04287             if (option_verbose > 2)
04288                ast_verbose(VERBOSE_PREFIX_3 "Native bridging %s and %s ended\n",
04289                       c0->name, c1->name);
04290             /* fallthrough */
04291          case AST_BRIDGE_FAILED_NOWARN:
04292             nativefailed++;
04293             break;
04294          }
04295       }
04296    
04297       if (((c0->writeformat != c1->readformat) || (c0->readformat != c1->writeformat) ||
04298           (c0->nativeformats != o0nativeformats) || (c1->nativeformats != o1nativeformats)) &&
04299           !(c0->generator || c1->generator)) {
04300          if (ast_channel_make_compatible(c0, c1)) {
04301             ast_log(LOG_WARNING, "Can't make %s and %s compatible\n", c0->name, c1->name);
04302             /* \todo  XXX here should check that cid_num is not NULL */
04303                                 manager_event(EVENT_FLAG_CALL, "Unlink",
04304                      "Channel1: %s\r\n"
04305                      "Channel2: %s\r\n"
04306                      "Uniqueid1: %s\r\n"
04307                      "Uniqueid2: %s\r\n"
04308                      "CallerID1: %s\r\n"
04309                      "CallerID2: %s\r\n",
04310                      c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num);
04311             return AST_BRIDGE_FAILED;
04312          }
04313          o0nativeformats = c0->nativeformats;
04314          o1nativeformats = c1->nativeformats;
04315       }
04316       res = ast_generic_bridge(c0, c1, config, fo, rc, nexteventts);
04317       if (res != AST_BRIDGE_RETRY)
04318          break;
04319    }
04320 
04321    ast_clear_flag(c0, AST_FLAG_END_DTMF_ONLY);
04322    ast_clear_flag(c1, AST_FLAG_END_DTMF_ONLY);
04323 
04324    c0->_bridge = NULL;
04325    c1->_bridge = NULL;
04326 
04327    /* \todo  XXX here should check that cid_num is not NULL */
04328    manager_event(EVENT_FLAG_CALL, "Unlink",
04329             "Channel1: %s\r\n"
04330             "Channel2: %s\r\n"
04331             "Uniqueid1: %s\r\n"
04332             "Uniqueid2: %s\r\n"
04333             "CallerID1: %s\r\n"
04334             "CallerID2: %s\r\n",
04335             c0->name, c1->name, c0->uniqueid, c1->uniqueid, c0->cid.cid_num, c1->cid.cid_num);
04336    if (option_debug)
04337       ast_log(LOG_DEBUG, "Bridge stops bridging channels %s and %s\n", c0->name, c1->name);
04338 
04339    return res;
04340 }

int ast_channel_cmpwhentohangup ( struct ast_channel chan,
time_t  offset 
)

Compare a offset with the settings of when to hang a channel up.

Parameters:
chan channel on which to check for hang up
offset offset in seconds from current time
Returns:
1, 0, or -1 This function compares a offset from current time with the absolute time out on a channel (when to hang up). If the absolute time out on a channel is earlier than current time plus the offset, it returns 1, if the two time values are equal, it return 0, otherwise, it retturn -1.

Definition at line 492 of file channel.c.

References ast_channel::whentohangup.

00493 {
00494    time_t whentohangup;
00495 
00496    if (chan->whentohangup == 0) {
00497       return (offset == 0) ? 0 : -1;
00498    } else {
00499       if (offset == 0)  /* XXX why is this special ? */
00500          return (1);
00501       else {
00502          whentohangup = offset + time (NULL);
00503          if (chan->whentohangup < whentohangup)
00504             return (1);
00505          else if (chan->whentohangup == whentohangup)
00506             return (0);
00507          else
00508             return (-1);
00509       }
00510    }
00511 }

int ast_channel_datastore_add ( struct ast_channel chan,
struct ast_datastore datastore 
)

Add a datastore to a channel.

Definition at line 1317 of file channel.c.

References AST_LIST_INSERT_HEAD.

Referenced by speech_create().

01318 {
01319    int res = 0;
01320 
01321    AST_LIST_INSERT_HEAD(&chan->datastores, datastore, entry);
01322 
01323    return res;
01324 }

struct ast_datastore* ast_channel_datastore_alloc ( const struct ast_datastore_info info,
char *  uid 
)

Create a channel datastore structure.

Definition at line 1273 of file channel.c.

References ast_calloc, ast_strdup, and ast_datastore::info.

Referenced by speech_create().

01274 {
01275    struct ast_datastore *datastore = NULL;
01276 
01277    /* Make sure we at least have type so we can identify this */
01278    if (info == NULL) {
01279       return NULL;
01280    }
01281 
01282    /* Allocate memory for datastore and clear it */
01283    datastore = ast_calloc(1, sizeof(*datastore));
01284    if (datastore == NULL) {
01285       return NULL;
01286    }
01287 
01288    datastore->info = info;
01289 
01290    datastore->uid = ast_strdup(uid);
01291 
01292    return datastore;
01293 }

struct ast_datastore* ast_channel_datastore_find ( struct ast_channel chan,
const struct ast_datastore_info info,
char *  uid 
)

Find a datastore on a channel.

Definition at line 1344 of file channel.c.

References AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, ast_datastore::info, and ast_datastore::uid.

Referenced by find_speech(), speech_background(), and speech_destroy().

01345 {
01346    struct ast_datastore *datastore = NULL;
01347    
01348    if (info == NULL)
01349       return NULL;
01350 
01351    AST_LIST_TRAVERSE_SAFE_BEGIN(&chan->datastores, datastore, entry) {
01352       if (datastore->info == info) {
01353          if (uid != NULL && datastore->uid != NULL) {
01354             if (!strcasecmp(uid, datastore->uid)) {
01355                /* Matched by type AND uid */
01356                break;
01357             }
01358          } else {
01359             /* Matched by type at least */
01360             break;
01361          }
01362       }
01363    }
01364    AST_LIST_TRAVERSE_SAFE_END
01365 
01366    return datastore;
01367 }

int ast_channel_datastore_free ( struct ast_datastore datastore  ) 

Free a channel datastore structure.

Definition at line 1295 of file channel.c.

References ast_datastore::data, ast_datastore_info::destroy, free, ast_datastore::info, and ast_datastore::uid.

Referenced by ast_channel_free().

01296 {
01297    int res = 0;
01298 
01299    /* Using the destroy function (if present) destroy the data */
01300    if (datastore->info->destroy != NULL && datastore->data != NULL) {
01301       datastore->info->destroy(datastore->data);
01302       datastore->data = NULL;
01303    }
01304 
01305    /* Free allocated UID memory */
01306    if (datastore->uid != NULL) {
01307       free(datastore->uid);
01308       datastore->uid = NULL;
01309    }
01310 
01311    /* Finally free memory used by ourselves */
01312    free(datastore);
01313 
01314    return res;
01315 }

int ast_channel_datastore_remove ( struct ast_channel chan,
struct ast_datastore datastore 
)

Remove a datastore from a channel.

Definition at line 1326 of file channel.c.

References AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, and AST_LIST_TRAVERSE_SAFE_END.

Referenced by speech_background(), and speech_destroy().

01327 {
01328    struct ast_datastore *datastore2 = NULL;
01329    int res = -1;
01330 
01331    /* Find our position and remove ourselves */
01332    AST_LIST_TRAVERSE_SAFE_BEGIN(&chan->datastores, datastore2, entry) {
01333       if (datastore2 == datastore) {
01334          AST_LIST_REMOVE_CURRENT(&chan->datastores, entry);
01335          res = 0;
01336          break;
01337       }
01338    }
01339    AST_LIST_TRAVERSE_SAFE_END
01340 
01341    return res;
01342 }

int ast_channel_defer_dtmf ( struct ast_channel chan  ) 

Set defer DTMF flag on channel.

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 984 of file channel.c.

References AST_FLAG_DEFER_DTMF, ast_set_flag, and ast_test_flag.

Referenced by __adsi_transmit_messages(), and find_cache().

00985 {
00986    int pre = 0;
00987 
00988    if (chan) {
00989       pre = ast_test_flag(chan, AST_FLAG_DEFER_DTMF);
00990       ast_set_flag(chan, AST_FLAG_DEFER_DTMF);
00991    }
00992    return pre;
00993 }

static void ast_channel_formats_reset ( struct ast_channel channel  )  [inline, static]

Definition at line 1137 of file channel.h.

References ast_get_read_format(), ast_get_write_format(), ast_log(), ast_set_read_format(), ast_set_write_format(), LOG_DEBUG, and option_debug.

01138 {
01139    int r, w;
01140    r = ast_get_read_format(channel);
01141    w = ast_get_write_format(channel);
01142 
01143    if (option_debug)
01144       ast_log(LOG_DEBUG, "Resetting read to %d and write to %d on channel %s\n", r, w, channel->name);
01145    if (r)
01146       ast_set_read_format(channel, r);
01147    if (w)
01148       ast_set_write_format(channel, w);
01149 }

void ast_channel_free ( struct ast_channel  ) 

Free a channel structure.

Definition at line 1188 of file channel.c.

References ast_channel::alertpipe, ast_app_group_discard(), ast_channel_datastore_free(), ast_channel_lock, AST_CHANNEL_NAME, ast_channel_unlock, ast_channel_whisper_stop(), ast_device_state_changed_literal(), ast_frfree(), ast_jb_destroy(), AST_LIST_HEAD_INIT_NOLOCK, AST_LIST_LOCK, AST_LIST_REMOVE, AST_LIST_REMOVE_HEAD, AST_LIST_UNLOCK, ast_log(), ast_moh_cleanup(), ast_mutex_destroy(), ast_string_field_free_pools, ast_translator_free_path(), ast_var_delete(), ast_channel::cid, f, free, free_cid(), ast_channel::lock, LOG_ERROR, 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::timingfd, ast_channel::varshead, ast_channel::whisper, and ast_channel::writetrans.

Referenced by agent_cleanup(), agent_new(), ast_hangup(), ast_pbx_outgoing_cdr_failed(), local_new(), make_email_file(), pbx_substitute_variables_helper_full(), and sendpage().

01189 {
01190    int fd;
01191    struct ast_var_t *vardata;
01192    struct ast_frame *f;
01193    struct varshead *headp;
01194    struct ast_datastore *datastore = NULL;
01195    char name[AST_CHANNEL_NAME];
01196    
01197    headp=&chan->varshead;
01198    
01199    AST_LIST_LOCK(&channels);
01200    if (!AST_LIST_REMOVE(&channels, chan, chan_list)) {
01201       AST_LIST_UNLOCK(&channels);
01202       ast_log(LOG_ERROR, "Unable to find channel in list to free. Assuming it has already been done.\n");
01203    }
01204    /* Lock and unlock the channel just to be sure nobody
01205       has it locked still */
01206    ast_channel_lock(chan);
01207    ast_channel_unlock(chan);
01208    if (chan->tech_pvt) {
01209       ast_log(LOG_WARNING, "Channel '%s' may not have been hung up properly\n", chan->name);
01210       free(chan->tech_pvt);
01211    }
01212 
01213    if (chan->sched)
01214       sched_context_destroy(chan->sched);
01215 
01216    ast_copy_string(name, chan->name, sizeof(name));
01217 
01218    /* Stop monitoring */
01219    if (chan->monitor)
01220       chan->monitor->stop( chan, 0 );
01221 
01222    /* If there is native format music-on-hold state, free it */
01223    if (chan->music_state)
01224       ast_moh_cleanup(chan);
01225 
01226    /* if someone is whispering on the channel, stop them */
01227    if (chan->whisper)
01228       ast_channel_whisper_stop(chan);
01229 
01230    /* Free translators */
01231    if (chan->readtrans)
01232       ast_translator_free_path(chan->readtrans);
01233    if (chan->writetrans)
01234       ast_translator_free_path(chan->writetrans);
01235    if (chan->pbx)
01236       ast_log(LOG_WARNING, "PBX may not have been terminated properly on '%s'\n", chan->name);
01237    free_cid(&chan->cid);
01238    ast_mutex_destroy(&chan->lock);
01239    /* Close pipes if appropriate */
01240    if ((fd = chan->alertpipe[0]) > -1)
01241       close(fd);
01242    if ((fd = chan->alertpipe[1]) > -1)
01243       close(fd);
01244    if ((fd = chan->timingfd) > -1)
01245       close(fd);
01246    while ((f = AST_LIST_REMOVE_HEAD(&chan->readq, frame_list)))
01247       ast_frfree(f);
01248    
01249    /* Get rid of each of the data stores on the channel */
01250    while ((datastore = AST_LIST_REMOVE_HEAD(&chan->datastores, entry)))
01251       /* Free the data store */
01252       ast_channel_datastore_free(datastore);
01253    AST_LIST_HEAD_INIT_NOLOCK(&chan->datastores);
01254 
01255    /* loop over the variables list, freeing all data and deleting list items */
01256    /* no need to lock the list, as the channel is already locked */
01257    
01258    while ((vardata = AST_LIST_REMOVE_HEAD(headp, entries)))
01259       ast_var_delete(vardata);
01260 
01261    ast_app_group_discard(chan);
01262 
01263    /* Destroy the jitterbuffer */
01264    ast_jb_destroy(chan);
01265 
01266    ast_string_field_free_pools(chan);
01267    free(chan);
01268    AST_LIST_UNLOCK(&channels);
01269 
01270    ast_device_state_changed_literal(name);
01271 }

static const char* ast_channel_getformatname ( struct ast_channel chan  )  [inline, static]

Definition at line 1128 of file channel.h.

References ast_getformatname(), and ast_channel::nativeformats.

01129 {
01130 #ifndef BUG_4825 
01131    return chan ? ast_getformatname(chan->nativeformats) : "undefined";
01132 #else 
01133    return chan ? ast_getformatname(chan->nativeformats.audio_bits) : "undefined";
01134 #endif   
01135 }

static char* ast_channel_getformatname_multiple ( char *  buf,
size_t  size,
struct ast_channel chan 
) [inline, static]

Get the names of a set of formats.

Parameters:
buf a buffer for the output string
size size of buf (bytes)
channel the channel Prints a list of readable codec names corresponding to "format". ex: for format=AST_FORMAT_GSM|AST_FORMAT_SPEEX|AST_FORMAT_ILBC it will return "0x602 (GSM|SPEEX|ILBC)"
Returns:
The return value is buf.

Definition at line 1122 of file channel.h.

References ast_getformatname_multiple(), and ast_channel::nativeformats.

01123 {
01124    return ast_getformatname_multiple(buf, size, chan->nativeformats);
01125 }

void ast_channel_inherit_variables ( const struct ast_channel parent,
struct ast_channel child 
)

Inherits channel variable from parent to child channel.

Parameters:
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 3476 of file channel.c.

References AST_LIST_INSERT_TAIL, AST_LIST_TRAVERSE, ast_log(), ast_var_assign(), ast_var_full_name(), ast_var_name(), ast_var_value(), LOG_DEBUG, option_debug, and ast_channel::varshead.

Referenced by __ast_request_and_dial(), agent_call(), ast_feature_request_and_dial(), begin_dial(), findmeexec(), ring_entry(), and wait_for_answer().

03477 {
03478    struct ast_var_t *current, *newvar;
03479    const char *varname;
03480 
03481    AST_LIST_TRAVERSE(&parent->varshead, current, entries) {
03482       int vartype = 0;
03483 
03484       varname = ast_var_full_name(current);
03485       if (!varname)
03486          continue;
03487 
03488       if (varname[0] == '_') {
03489          vartype = 1;
03490          if (varname[1] == '_')
03491             vartype = 2;
03492       }
03493 
03494       switch (vartype) {
03495       case 1:
03496          newvar = ast_var_assign(&varname[1], ast_var_value(current));
03497          if (newvar) {
03498             AST_LIST_INSERT_TAIL(&child->varshead, newvar, entries);
03499             if (option_debug)
03500                ast_log(LOG_DEBUG, "Copying soft-transferable variable %s.\n", ast_var_name(newvar));
03501          }
03502          break;
03503       case 2:
03504          newvar = ast_var_assign(ast_var_full_name(current), ast_var_value(current));
03505          if (newvar) {
03506             AST_LIST_INSERT_TAIL(&child->varshead, newvar, entries);
03507             if (option_debug)
03508                ast_log(LOG_DEBUG, "Copying hard-transferable variable %s.\n", ast_var_name(newvar));
03509          }
03510          break;
03511       default:
03512          if (option_debug)
03513             ast_log(LOG_DEBUG, "Not copying variable %s.\n", ast_var_name(current));
03514          break;
03515       }
03516    }
03517 }

int ast_channel_make_compatible ( struct ast_channel c0,
struct ast_channel c1 
)

Makes two channel formats compatible.

Parameters:
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 .
Returns:
Returns 0 on success and -1 if it could not be done

Definition at line 3345 of file channel.c.

References AST_FORMAT_SLINEAR, ast_log(), ast_opt_transcode_via_slin, ast_set_read_format(), ast_set_write_format(), ast_translate_path_steps(), ast_translator_best_choice(), LOG_WARNING, ast_channel::nativeformats, ast_channel::readformat, and ast_channel::writeformat.

Referenced by app_exec(), ast_channel_bridge(), check_compat(), park_exec(), try_calling(), and wait_for_answer().

03346 {
03347    int src;
03348    int dst;
03349 
03350    if (chan->readformat == peer->writeformat && chan->writeformat == peer->readformat) {
03351       /* Already compatible!  Moving on ... */
03352       return 0;
03353    }
03354 
03355    /* Set up translation from the chan to the peer */
03356    src = chan->nativeformats;
03357    dst = peer->nativeformats;
03358    if (ast_translator_best_choice(&dst, &src) < 0) {
03359       ast_log(LOG_WARNING, "No path to translate from %s(%d) to %s(%d)\n", chan->name, src, peer->name, dst);
03360       return -1;
03361    }
03362 
03363    /* if the best path is not 'pass through', then
03364       transcoding is needed; if desired, force transcode path
03365       to use SLINEAR between channels, but only if there is
03366       no direct conversion available */
03367    if ((src != dst) && ast_opt_transcode_via_slin &&
03368        (ast_translate_path_steps(dst, src) != 1))
03369       dst = AST_FORMAT_SLINEAR;
03370    if (ast_set_read_format(chan, dst) < 0) {
03371       ast_log(LOG_WARNING, "Unable to set read format on channel %s to %d\n", chan->name, dst);
03372       return -1;
03373    }
03374    if (ast_set_write_format(peer, dst) < 0) {
03375       ast_log(LOG_WARNING, "Unable to set write format on channel %s to %d\n", peer->name, dst);
03376       return -1;
03377    }
03378 
03379    /* Set up translation from the peer to the chan */
03380    src = peer->nativeformats;
03381    dst = chan->nativeformats;
03382    if (ast_translator_best_choice(&dst, &src) < 0) {
03383       ast_log(LOG_WARNING, "No path to translate from %s(%d) to %s(%d)\n", peer->name, src, chan->name, dst);
03384       return -1;
03385    }
03386 
03387    /* if the best path is not 'pass through', then
03388       transcoding is needed; if desired, force transcode path
03389       to use SLINEAR between channels, but only if there is
03390       no direct conversion available */
03391    if ((src != dst) && ast_opt_transcode_via_slin &&
03392        (ast_translate_path_steps(dst, src) != 1))
03393       dst = AST_FORMAT_SLINEAR;
03394    if (ast_set_read_format(peer, dst) < 0) {
03395       ast_log(LOG_WARNING, "Unable to set read format on channel %s to %d\n", peer->name, dst);
03396       return -1;
03397    }
03398    if (ast_set_write_format(chan, dst) < 0) {
03399       ast_log(LOG_WARNING, "Unable to set write format on channel %s to %d\n", chan->name, dst);
03400       return -1;
03401    }
03402    return 0;
03403 }

int ast_channel_masquerade ( struct ast_channel original,
struct ast_channel clone 
)

Weird function made for call transfers.

Parameters:
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 3405 of file channel.c.

References ast_channel::_bridge, ast_bridged_channel(), ast_channel_lock, ast_channel_trylock, ast_channel_unlock, ast_log(), ast_null_frame, ast_queue_frame(), LOG_DEBUG, LOG_WARNING, ast_channel::masq, ast_channel::masqr, and option_debug.

Referenced by ast_async_goto(), ast_masq_park_call(), ast_pickup_call(), attempt_transfer(), builtin_atxfer(), check_availability(), check_bridge(), check_goto_on_transfer(), handle_invite_replaces(), iax_park(), misdn_transfer_bc(), pickup_do(), and sip_park().

03406 {
03407    int res = -1;
03408    struct ast_channel *final_orig = original, *final_clone = clone;
03409 
03410    ast_channel_lock(original);
03411    while (ast_channel_trylock(clone)) {
03412       ast_channel_unlock(original);
03413       usleep(1);
03414       ast_channel_lock(original);
03415    }
03416 
03417    /* each of these channels may be sitting behind a channel proxy (i.e. chan_agent)
03418       and if so, we don't really want to masquerade it, but its proxy */
03419    if (original->_bridge && (original->_bridge != ast_bridged_channel(original)) && (original->_bridge->_bridge != original))
03420       final_orig = original->_bridge;
03421 
03422    if (clone->_bridge && (clone->_bridge != ast_bridged_channel(clone)) && (clone->_bridge->_bridge != clone))
03423       final_clone = clone->_bridge;
03424 
03425    if ((final_orig != original) || (final_clone != clone)) {
03426       ast_channel_lock(final_orig);
03427       while (ast_channel_trylock(final_clone)) {
03428          ast_channel_unlock(final_orig);
03429          usleep(1);
03430          ast_channel_lock(final_orig);
03431       }
03432       ast_channel_unlock(clone);
03433       ast_channel_unlock(original);
03434       original = final_orig;
03435       clone = final_clone;
03436    }
03437 
03438    if (original == clone) {
03439       ast_log(LOG_WARNING, "Can't masquerade channel '%s' into itself!\n", original->name);
03440       ast_channel_unlock(clone);
03441       ast_channel_unlock(original);
03442       return -1;
03443    }
03444 
03445    if (option_debug)
03446       ast_log(LOG_DEBUG, "Planning to masquerade channel %s into the structure of %s\n",
03447          clone->name, original->name);
03448    if (original->masq) {
03449       ast_log(LOG_WARNING, "%s is already going to masquerade as %s\n",
03450          original->masq->name, original->name);
03451    } else if (clone->masqr) {
03452       ast_log(LOG_WARNING, "%s is already going to masquerade as %s\n",
03453          clone->name, clone->masqr->name);
03454    } else {
03455       original->masq = clone;
03456       clone->masqr = original;
03457       ast_queue_frame(original, &ast_null_frame);
03458       ast_queue_frame(clone, &ast_null_frame);
03459       if (option_debug)
03460          ast_log(LOG_DEBUG, "Done planning to masquerade channel %s into the structure of %s\n", clone->name, original->name);
03461       res = 0;
03462    }
03463 
03464    ast_channel_unlock(clone);
03465    ast_channel_unlock(original);
03466 
03467    return res;
03468 }

struct ast_frame* ast_channel_queryoption ( struct ast_channel channel,
int  option,
void *  data,
int *  datalen,
int  block 
)

Query the value of an option, optionally blocking until a reply is received Works similarly to setoption except only reads the options.

char* ast_channel_reason2str ( int  reason  ) 

return an english explanation of the code returned thru __ast_request_and_dial's 'outstate' argument

Parameters:
reason The integer argument, usually taken from AST_CONTROL_ macros
Returns:
char pointer explaining the code

Definition at line 3036 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().

03037 {
03038    switch (reason) /* the following appear to be the only ones actually returned by request_and_dial */
03039    {
03040    case 0:
03041       return "Call Failure (not BUSY, and not NO_ANSWER, maybe Circuit busy or down?)";
03042    case AST_CONTROL_HANGUP:
03043       return "Hangup";
03044    case AST_CONTROL_RING:
03045       return "Local Ring";
03046    case AST_CONTROL_RINGING:
03047       return "Remote end Ringing";
03048    case AST_CONTROL_ANSWER:
03049       return "Remote end has Answered";
03050    case AST_CONTROL_BUSY:
03051       return "Remote end is Busy";
03052    case AST_CONTROL_CONGESTION:
03053       return "Congestion (circuits busy)";
03054    default:
03055       return "Unknown Reason!!";
03056    }
03057 }

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.

Parameters:
tech Structure defining channel technology or "type"
Returns:
Returns 0 on success, -1 on failure.

Definition at line 514 of file channel.c.

References ast_calloc, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), ast_verbose(), LOG_DEBUG, LOG_WARNING, option_debug, option_verbose, chanlist::tech, ast_channel_tech::type, and VERBOSE_PREFIX_2.

Referenced by load_module(), and unload_module().

00515 {
00516    struct chanlist *chan;
00517 
00518    AST_LIST_LOCK(&channels);
00519 
00520    AST_LIST_TRAVERSE(&backends, chan, list) {
00521       if (!strcasecmp(tech->type, chan->tech->type)) {
00522          ast_log(LOG_WARNING, "Already have a handler for type '%s'\n", tech->type);
00523          AST_LIST_UNLOCK(&channels);
00524          return -1;
00525       }
00526    }
00527    
00528    if (!(chan = ast_calloc(1, sizeof(*chan)))) {
00529       AST_LIST_UNLOCK(&channels);
00530       return -1;
00531    }
00532    chan->tech = tech;
00533    AST_LIST_INSERT_HEAD(&backends, chan, list);
00534 
00535    if (option_debug)
00536       ast_log(LOG_DEBUG, "Registered handler for '%s' (%s)\n", chan->tech->type, chan->tech->description);
00537 
00538    if (option_verbose > 1)
00539       ast_verbose(VERBOSE_PREFIX_2 "Registered channel type '%s' (%s)\n", chan->tech->type,
00540              chan->tech->description);
00541 
00542    AST_LIST_UNLOCK(&channels);
00543    return 0;
00544 }

int ast_channel_sendhtml ( struct ast_channel channel,
int  subclass,
const char *  data,
int  datalen 
)

Send HTML or URL on link. Returns 0 on success or -1 on failure

Definition at line 3333 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().

03334 {
03335    if (chan->tech->send_html)
03336       return chan->tech->send_html(chan, subclass, data, datalen);
03337    return -1;
03338 }

int ast_channel_sendurl ( struct ast_channel channel,
const char *  url 
)

Send URL on link. Returns 0 on success or -1 on failure

Definition at line 3340 of file channel.c.

References ast_channel_sendhtml(), and AST_HTML_URL.

Referenced by sendurl_exec(), and try_calling().

03341 {
03342    return ast_channel_sendhtml(chan, AST_HTML_URL, url, strlen(url) + 1);
03343 }

int ast_channel_setoption ( struct ast_channel channel,
int  option,
void *  data,
int  datalen,
int  block 
)

Sets an option on a channel.

Parameters:
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 4343 of file channel.c.

References ast_log(), LOG_ERROR, ast_channel_tech::setoption, and ast_channel::tech.

Referenced by ast_bridge_call(), common_exec(), conf_run(), func_channel_write(), handle_tddmode(), play_record_review(), reset_volumes(), rpt(), set_listen_volume(), set_talk_volume(), set_volume(), try_calling(), vm_forwardoptions(), and zt_hangup().

04344 {
04345    int res;
04346 
04347    if (chan->tech->setoption) {
04348       res = chan->tech->setoption(chan, option, data, datalen);
04349       if (res < 0)
04350          return res;
04351    } else {
04352       errno = ENOSYS;
04353       return -1;
04354    }
04355    if (block) {
04356       /* XXX Implement blocking -- just wait for our option frame reply, discarding
04357          intermediate packets. XXX */
04358       ast_log(LOG_ERROR, "XXX Blocking not implemented yet XXX\n");
04359       return -1;
04360    }
04361    return 0;
04362 }

void ast_channel_setwhentohangup ( struct ast_channel chan,
time_t  offset 
)

Set when to hang a channel up.

Parameters:
chan channel on which to check for hang up
offset offset in seconds from current time of when to hang up This function sets the absolute time out on a channel (when to hang up).

Definition at line 484 of file channel.c.

References ast_null_frame, ast_queue_frame(), and ast_channel::whentohangup.

Referenced by action_timeout(), and timeout_write().

00485 {
00486    chan->whentohangup = offset ? time(NULL) + offset : 0;
00487    ast_queue_frame(chan, &ast_null_frame);
00488    return;
00489 }

struct ast_silence_generator* ast_channel_start_silence_generator ( struct ast_channel chan  ) 

Starts a silence generator on the given channel.

Parameters:
chan The channel to generate silence on
Returns:
An ast_silence_generator pointer, or NULL if an error occurs
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 4791 of file channel.c.

References ast_activate_generator(), ast_calloc, AST_FORMAT_SLINEAR, ast_log(), ast_set_write_format(), free, LOG_DEBUG, LOG_ERROR, ast_silence_generator::old_write_format, silence_generator, and ast_channel::writeformat.

Referenced by __ast_play_and_record(), and channel_spy().

04792 {
04793    struct ast_silence_generator *state;
04794 
04795    if (!(state = ast_calloc(1, sizeof(*state)))) {
04796       return NULL;
04797    }
04798 
04799    state->old_write_format = chan->writeformat;
04800 
04801    if (ast_set_write_format(chan, AST_FORMAT_SLINEAR) < 0) {
04802       ast_log(LOG_ERROR, "Could not set write format to SLINEAR\n");
04803       free(state);
04804       return NULL;
04805    }
04806 
04807    ast_activate_generator(chan, &silence_generator, state);
04808 
04809    if (option_debug)
04810       ast_log(LOG_DEBUG, "Started silence generator on '%s'\n", chan->name);
04811 
04812    return state;
04813 }

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.

Parameters:
chan The channel to operate on
state The ast_silence_generator pointer return by a previous call to ast_channel_start_silence_generator.
Returns:
nothing
This function will stop the operating silence generator and return the channel to its previous write format.

Definition at line 4815 of file channel.c.

References ast_deactivate_generator(), ast_log(), ast_set_write_format(), free, LOG_DEBUG, LOG_ERROR, and ast_silence_generator::old_write_format.

Referenced by __ast_play_and_record(), and channel_spy().

04816 {
04817    if (!state)
04818       return;
04819 
04820    ast_deactivate_generator(chan);
04821 
04822    if (option_debug)
04823       ast_log(LOG_DEBUG, "Stopped silence generator on '%s'\n", chan->name);
04824 
04825    if (ast_set_write_format(chan, state->old_write_format) < 0)
04826       ast_log(LOG_ERROR, "Could not return write format to its original state\n");
04827 
04828    free(state);
04829 }

int ast_channel_supports_html ( struct ast_channel channel  ) 

Returns 0 if channel does not support HTML or non-zero if it does

Definition at line 3328 of file channel.c.

References ast_channel_tech::send_html, and ast_channel::tech.

Referenced by sendurl_exec(), and try_calling().

03329 {
03330    return (chan->tech->send_html) ? 1 : 0;
03331 }

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 996 of file channel.c.

References ast_clear_flag, and AST_FLAG_DEFER_DTMF.

Referenced by __adsi_transmit_messages(), find_cache(), and rpt_call().

00997 {
00998    if (chan)
00999       ast_clear_flag(chan, AST_FLAG_DEFER_DTMF);
01000 }

void ast_channel_unregister ( const struct ast_channel_tech tech  ) 

Unregister a channel technology.

Parameters:
tech Structure defining channel technology or "type" that was previously registered
Returns:
No return value.

Definition at line 546 of file channel.c.

References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, ast_log(), ast_verbose(), free, LOG_DEBUG, option_debug, option_verbose, chanlist::tech, ast_channel_tech::type, and VERBOSE_PREFIX_2.

Referenced by __unload_module(), and unload_module().

00547 {
00548    struct chanlist *chan;
00549 
00550    if (option_debug)
00551       ast_log(LOG_DEBUG, "Unregistering channel type '%s'\n", tech->type);
00552 
00553    AST_LIST_LOCK(&channels);
00554 
00555    AST_LIST_TRAVERSE_SAFE_BEGIN(&backends, chan, list) {
00556       if (chan->tech == tech) {
00557          AST_LIST_REMOVE_CURRENT(&backends, list);
00558          free(chan);
00559          if (option_verbose > 1)
00560             ast_verbose(VERBOSE_PREFIX_2 "Unregistered channel type '%s'\n", tech->type);
00561          break;   
00562       }
00563    }
00564    AST_LIST_TRAVERSE_SAFE_END
00565 
00566    AST_LIST_UNLOCK(&channels);
00567 }

struct ast_channel* ast_channel_walk_locked ( const struct ast_channel prev  ) 

Browse channels in use Browse the channels currently in use.

Parameters:
prev where you want to start in the channel list
Returns:
Returns the next channel in the list, NULL on end. If it returns a channel, that channel *has been locked*!

Definition at line 1109 of file channel.c.

References channel_find_locked().

Referenced by action_status(), ast_complete_channels(), ast_pickup_call(), complete_ch_helper(), conf_exec(), handle_chanlist(), handle_chanlist_deprecated(), handle_core_set_debug_channel(), handle_debugchan_deprecated(), handle_nodebugchan_deprecated(), next_channel(), pickup_by_exten(), pickup_by_mark(), and softhangup_exec().

01110 {
01111    return channel_find_locked(prev, NULL, 0, NULL, NULL);
01112 }

int ast_channel_whisper_feed ( struct ast_channel chan,
struct ast_frame f 
)

Feed an audio frame into the whisper buffer on a channel.

Parameters:
chan The channel to whisper onto
f The frame to to whisper onto chan
Returns:
0 for success, non-zero for failure

Definition at line 5029 of file channel.c.

References ast_mutex_lock(), ast_mutex_unlock(), ast_slinfactory_feed(), f, ast_channel_whisper_buffer::lock, ast_channel_whisper_buffer::sf, and ast_channel::whisper.

Referenced by channel_spy().

05030 {
05031    if (!chan->whisper)
05032       return -1;
05033 
05034    ast_mutex_lock(&chan->whisper->lock);
05035    ast_slinfactory_feed(&chan->whisper->sf, f);
05036    ast_mutex_unlock(&chan->whisper->lock);
05037 
05038    return 0;
05039 }

int ast_channel_whisper_start ( struct ast_channel chan  ) 

Begin 'whispering' onto a channel.

Parameters:
chan The channel to whisper onto
Returns:
0 for success, non-zero for failure
This function will add a whisper buffer onto a channel and set a flag causing writes to the channel to reduce the volume level of the written audio samples, and then to mix in audio from the whisper buffer if it is available.

Note:
Note: This function performs no locking; you must hold the channel's lock before calling this function.

Definition at line 5014 of file channel.c.

References ast_calloc, AST_FLAG_WHISPER, ast_mutex_init(), ast_set_flag, ast_slinfactory_init(), ast_channel_whisper_buffer::lock, ast_channel_whisper_buffer::sf, and ast_channel::whisper.

Referenced by channel_spy().

05015 {
05016    if (chan->whisper)
05017       return -1;
05018 
05019    if (!(chan->whisper = ast_calloc(1, sizeof(*chan->whisper))))
05020       return -1;
05021 
05022    ast_mutex_init(&chan->whisper->lock);
05023    ast_slinfactory_init(&chan->whisper->sf);
05024    ast_set_flag(chan, AST_FLAG_WHISPER);
05025 
05026    return 0;
05027 }

void ast_channel_whisper_stop ( struct ast_channel chan  ) 

Stop 'whispering' onto a channel.

Parameters:
chan The channel to whisper onto
Returns:
0 for success, non-zero for failure
Note: This function performs no locking; you must hold the channel's lock before calling this function.

Definition at line 5041 of file channel.c.

References ast_clear_flag, AST_FLAG_WHISPER, AST_FORMAT_SLINEAR, ast_mutex_destroy(), ast_set_write_format(), ast_slinfactory_destroy(), ast_translator_free_path(), free, ast_channel_whisper_buffer::original_format, ast_channel_whisper_buffer::path, ast_channel::whisper, and ast_channel::writeformat.

Referenced by ast_channel_free(), and channel_spy().

05042 {
05043    if (!chan->whisper)
05044       return;
05045 
05046    ast_clear_flag(chan, AST_FLAG_WHISPER);
05047    if (chan->whisper->path)
05048       ast_translator_free_path(chan->whisper->path);
05049    if (chan->whisper->original_format && chan->writeformat == AST_FORMAT_SLINEAR)
05050       ast_set_write_format(chan, chan->whisper->original_format);
05051    ast_slinfactory_destroy(&chan->whisper->sf);
05052    ast_mutex_destroy(&chan->whisper->lock);
05053    free(chan->whisper);
05054    chan->whisper = NULL;
05055 }

struct ast_variable* ast_channeltype_list ( void   ) 

return an ast_variable list of channeltypes

Definition at line 180 of file channel.c.

References AST_LIST_TRAVERSE, ast_variable_new(), ast_channel_tech::description, chanlist::tech, ast_channel_tech::type, and var.

00181 {
00182    struct chanlist *cl;
00183    struct ast_variable *var=NULL, *prev = NULL;
00184    AST_LIST_TRAVERSE(&backends, cl, list) {
00185       if (prev)  {
00186          if ((prev->next = ast_variable_new(cl->tech->type, cl->tech->description)))
00187             prev = prev->next;
00188       } else {
00189          var = ast_variable_new(cl->tech->type, cl->tech->description);
00190          prev = var;
00191       }
00192    }
00193    return var;
00194 }

int ast_check_hangup ( struct ast_channel chan  ) 

Check to see if a channel is needing hang up.

Parameters:
chan channel on which to check for hang up This function determines if the channel is being requested to be hung up.
Returns:
Returns 0 if not, or 1 if hang up is requested (including time-out).

Definition at line 402 of file channel.c.

References ast_channel::_softhangup, AST_SOFTHANGUP_TIMEOUT, ast_channel::tech_pvt, and ast_channel::whentohangup.

Referenced by __ast_read(), action_redirect(), app_exec(), ast_answer(), ast_call(), ast_channel_bridge(), ast_check_hangup_locked(), ast_feature_request_and_dial(), ast_indicate_data(), ast_readstring_full(), ast_recvtext(), ast_sendtext(), ast_transfer(), ast_udptl_bridge(), ast_waitfordigit_full(), ast_write(), bridge_native_loop(), bridge_p2p_loop(), builtin_atxfer(), channel_spy(), common_exec(), conf_run(), deadagi_exec(), handle_sendimage(), pbx_exec(), rpt(), wait_for_answer(), zt_sendtext(), and zt_setoption().

00403 {
00404    if (chan->_softhangup)     /* yes if soft hangup flag set */
00405       return 1;
00406    if (!chan->tech_pvt)    /* yes if no technology private data */
00407       return 1;
00408    if (!chan->whentohangup)   /* no if no hangup scheduled */
00409       return 0;
00410    if (chan->whentohangup > time(NULL))   /* no if hangup time has not come yet. */
00411       return 0;
00412    chan->_softhangup |= AST_SOFTHANGUP_TIMEOUT; /* record event */
00413    return 1;
00414 }

void ast_deactivate_generator ( struct ast_channel chan  ) 

Deactive an active generator

Definition at line 1821 of file channel.c.

References ast_channel_lock, ast_channel_unlock, ast_clear_flag, AST_FLAG_WRITE_INT, AST_GENERATOR_FD, ast_settimeout(), ast_channel::fds, 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(), channel_spy(), generator_force(), local_ast_moh_stop(), milliwatt_exec(), and wait_for_answer().

01822 {
01823    ast_channel_lock(chan);
01824    if (chan->generatordata) {
01825       if (chan->generator && chan->generator->release)
01826          chan->generator->release(chan, chan->generatordata);
01827       chan->generatordata = NULL;
01828       chan->generator = NULL;
01829       chan->fds[AST_GENERATOR_FD] = -1;
01830       ast_clear_flag(chan, AST_FLAG_WRITE_INT);
01831       ast_settimeout(chan, 0, NULL, NULL);
01832    }
01833    ast_channel_unlock(chan);
01834 }

int ast_do_masquerade ( struct ast_channel original  ) 

Start masquerading a channel XXX This is a seriously wacked 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.

Note:
Assumes channel will be locked when called

Definition at line 3551 of file channel.c.

References ast_channel::_state, ast_channel::alertpipe, ast_channel_lock, AST_LIST_FIRST, AST_LIST_HEAD_SET_NOLOCK, AST_LIST_TRAVERSE, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_string_field_set, ast_channel::cdr, ast_channel_spy::chan, EVENT_FLAG_CALL, free_translation(), ast_channel_spy::lock, ast_channel::lock, LOG_DEBUG, manager_event(), ast_channel::masq, ast_channel::masqr, name, option_debug, ast_channel::rawreadformat, ast_channel::rawwriteformat, ast_channel::readformat, ast_channel::spies, t, ast_channel::tech, ast_channel::tech_pvt, and ast_channel::writeformat.

Referenced by __ast_read(), ast_async_goto(), ast_hangup(), ast_waitfor_nandfds(), ast_write(), iax_park(), sip_park(), and sip_park_thread().

03552 {
03553    int x,i;
03554    int res=0;
03555    int origstate;
03556    struct ast_frame *cur;
03557    const struct ast_channel_tech *t;
03558    void *t_pvt;
03559    struct ast_callerid tmpcid;
03560    struct ast_channel *clone = original->masq;
03561    struct ast_channel_spy_list *spy_list = NULL;
03562    struct ast_channel_spy *spy = NULL;
03563    struct ast_cdr *cdr;
03564    int rformat = original->readformat;
03565    int wformat = original->writeformat;
03566    char newn[100];
03567    char orig[100];
03568    char masqn[100];
03569    char zombn[100];
03570 
03571    if (option_debug > 3)
03572       ast_log(LOG_DEBUG, "Actually Masquerading %s(%d) into the structure of %s(%d)\n",
03573          clone->name, clone->_state, original->name, original->_state);
03574 
03575    /* XXX This is a seriously wacked out operation.  We're essentially putting the guts of
03576       the clone channel into the original channel.  Start by killing off the original
03577       channel's backend.   I'm not sure we're going to keep this function, because
03578       while the features are nice, the cost is very high in terms of pure nastiness. XXX */
03579 
03580    /* We need the clone's lock, too */
03581    ast_channel_lock(clone);
03582 
03583    if (option_debug > 1)
03584       ast_log(LOG_DEBUG, "Got clone lock for masquerade on '%s' at %p\n", clone->name, &clone->lock);
03585 
03586    /* Having remembered the original read/write formats, we turn off any translation on either
03587       one */
03588    free_translation(clone);
03589    free_translation(original);
03590 
03591 
03592    /* Unlink the masquerade */
03593    original->masq = NULL;
03594    clone->masqr = NULL;
03595    
03596    /* Save the original name */
03597    ast_copy_string(orig, original->name, sizeof(orig));
03598    /* Save the new name */
03599    ast_copy_string(newn, clone->name, sizeof(newn));
03600    /* Create the masq name */
03601    snprintf(masqn, sizeof(masqn), "%s<MASQ>", newn);
03602       
03603    /* Copy the name from the clone channel */
03604    ast_string_field_set(original, name, newn);
03605 
03606    /* Mangle the name of the clone channel */
03607    ast_string_field_set(clone, name, masqn);
03608    
03609    /* Notify any managers of the change, first the masq then the other */
03610    manager_event(EVENT_FLAG_CALL, "Rename", "Oldname: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", newn, masqn, clone->uniqueid);
03611    manager_event(EVENT_FLAG_CALL, "Rename", "Oldname: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", orig, newn, original->uniqueid);
03612 
03613    /* Swap the technologies */   
03614    t = original->tech;
03615    original->tech = clone->tech;
03616    clone->tech = t;
03617 
03618    /* Swap the cdrs */
03619    cdr = original->cdr;
03620    original->cdr = clone->cdr;
03621    clone->cdr = cdr;
03622 
03623    t_pvt = original->tech_pvt;
03624    original->tech_pvt = clone->tech_pvt;
03625    clone->tech_pvt = t_pvt;
03626 
03627    /* Swap the readq's */
03628    cur = AST_LIST_FIRST(&original->readq);
03629    AST_LIST_HEAD_SET_NOLOCK(&original->readq, AST_LIST_FIRST(&clone->readq));
03630    AST_LIST_HEAD_SET_NOLOCK(&clone->readq, cur);
03631 
03632    /* Swap the alertpipes */
03633    for (i = 0; i < 2; i++) {
03634       x = original->alertpipe[i];
03635       original->alertpipe[i] = clone->alertpipe[i];
03636       clone->alertpipe[i] = x;
03637    }
03638 
03639    /* Swap the raw formats */
03640    x = original->rawreadformat;
03641    original->rawreadformat = clone->rawreadformat;
03642    clone->rawreadformat = x;
03643    x = original->rawwriteformat;
03644    original->rawwriteformat = clone->rawwriteformat;
03645    clone->rawwriteformat = x;
03646 
03647    /* Swap the spies */
03648    spy_list = original->spies;
03649    original->spies = clone->spies;
03650    clone->spies = spy_list;
03651 
03652    /* Update channel on respective spy lists if present */
03653    if (original->spies) {
03654       AST_LIST_TRAVERSE(&original->spies->list, spy, list) {
03655          ast_mutex_lock(&spy->lock);
03656          spy->chan = original;
03657          ast_mutex_unlock(&spy->lock);
03658       }
03659    }
03660    if (clone->spies) {
03661       AST_LIST_TRAVERSE(&clone->spies->list, spy, list) {
03662          ast_mutex_lock(&spy->lock);
03663          spy->chan = clone;
03664          ast_mutex_unlock(&spy->lock);
03665       }
03666    }
03667 
03668    /* Save any pending frames on both sides.  Start by counting
03669     * how many we're going to need... */
03670    x = 0;
03671    if (original->alertpipe[1] > -1) {
03672       AST_LIST_TRAVERSE(&clone->readq, cur, frame_list)
03673          x++;
03674    }
03675 
03676    /* If we had any, prepend them to the ones already in the queue, and 
03677     * load up the alertpipe */
03678    if (AST_LIST_FIRST(&clone->readq)) {
03679       AST_LIST_INSERT_TAIL(&clone->readq, AST_LIST_FIRST(&original->readq), frame_list);
03680       AST_LIST_HEAD_SET_NOLOCK(&original->readq, AST_LIST_FIRST(&clone->readq));
03681       AST_LIST_HEAD_SET_NOLOCK(&clone->readq, NULL);
03682       for (i = 0; i < x; i++)
03683          write(original->alertpipe[1], &x, sizeof(x));
03684    }
03685    
03686    clone->_softhangup = AST_SOFTHANGUP_DEV;
03687 
03688 
03689    /* And of course, so does our current state.  Note we need not
03690       call ast_setstate since the event manager doesn't really consider
03691       these separate.  We do this early so that the clone has the proper
03692       state of the original channel. */
03693    origstate = original->_state;
03694    original->_state = clone->_state;
03695    clone->_state = origstate;
03696 
03697    if (clone->tech->fixup){
03698       res = clone->tech->fixup(original, clone);
03699       if (res)
03700          ast_log(LOG_WARNING, "Fixup failed on channel %s, strange things may happen.\n", clone->name);
03701    }
03702 
03703    /* Start by disconnecting the original's physical side */
03704    if (clone->tech->hangup)
03705       res = clone->tech->hangup(clone);
03706    if (res) {
03707       ast_log(LOG_WARNING, "Hangup failed!  Strange things may happen!\n");
03708       ast_channel_unlock(clone);
03709       return -1;
03710    }
03711    
03712    snprintf(zombn, sizeof(zombn), "%s<ZOMBIE>", orig);
03713    /* Mangle the name of the clone channel */
03714    ast_string_field_set(clone, name, zombn);
03715    manager_event(EVENT_FLAG_CALL, "Rename", "Oldname: %s\r\nNewname: %s\r\nUniqueid: %s\r\n", masqn, zombn, clone->uniqueid);
03716 
03717    /* Update the type. */
03718    t_pvt = original->monitor;
03719    original->monitor = clone->monitor;
03720    clone->monitor = t_pvt;
03721    
03722    /* Keep the same language.  */
03723    ast_string_field_set(original, language, clone->language);
03724    /* Copy the FD's other than the generator fd */
03725    for (x = 0; x < AST_MAX_FDS; x++) {
03726       if (x != AST_GENERATOR_FD)
03727          original->fds[x] = clone->fds[x];
03728    }
03729 
03730    ast_app_group_update(clone, original);
03731 
03732    /* move any whisperer over */
03733    ast_channel_whisper_stop(original);
03734    if (ast_test_flag(clone, AST_FLAG_WHISPER)) {
03735       original->whisper = clone->whisper;
03736       ast_set_flag(original, AST_FLAG_WHISPER);
03737       clone->whisper = NULL;
03738       ast_clear_flag(clone, AST_FLAG_WHISPER);
03739    }
03740 
03741    /* Move data stores over */
03742    if (AST_LIST_FIRST(&clone->datastores))
03743                 AST_LIST_INSERT_TAIL(&original->datastores, AST_LIST_FIRST(&clone->datastores), entry);
03744    AST_LIST_HEAD_INIT_NOLOCK(&clone->datastores);
03745 
03746    clone_variables(original, clone);
03747    /* Presense of ADSI capable CPE follows clone */
03748    original->adsicpe = clone->adsicpe;
03749    /* Bridge remains the same */
03750    /* CDR fields remain the same */
03751    /* XXX What about blocking, softhangup, blocker, and lock and blockproc? XXX */
03752    /* Application and data remain the same */
03753    /* Clone exception  becomes real one, as with fdno */
03754    ast_copy_flags(original, clone, AST_FLAG_EXCEPTION);
03755    original->fdno = clone->fdno;
03756    /* Schedule context remains the same */
03757    /* Stream stuff stays the same */
03758    /* Keep the original state.  The fixup code will need to work with it most likely */
03759 
03760    /* Just swap the whole structures, nevermind the allocations, they'll work themselves
03761       out. */
03762    tmpcid = original->cid;
03763    original->cid = clone->cid;
03764    clone->cid = tmpcid;
03765    
03766    /* Restore original timing file descriptor */
03767    original->fds[AST_TIMING_FD] = original->timingfd;
03768    
03769    /* Our native formats are different now */
03770    original->nativeformats = clone->nativeformats;
03771    
03772    /* Context, extension, priority, app data, jump table,  remain the same */
03773    /* pvt switches.  pbx stays the same, as does next */
03774    
03775    /* Set the write format */
03776    ast_set_write_format(original, wformat);
03777 
03778    /* Set the read format */
03779    ast_set_read_format(original, rformat);
03780 
03781    /* Copy the music class */
03782    ast_string_field_set(original, musicclass, clone->musicclass);
03783 
03784    if (option_debug)
03785       ast_log(LOG_DEBUG, "Putting channel %s in %d/%d formats\n", original->name, wformat, rformat);
03786 
03787    /* Okay.  Last thing is to let the channel driver know about all this mess, so he
03788       can fix up everything as best as possible */
03789    if (original->tech->fixup) {
03790       res = original->tech->fixup(clone, original);
03791       if (res) {
03792          ast_log(LOG_WARNING, "Channel for type '%s' could not fixup channel %s\n",
03793             original->tech->type, original->name);
03794          ast_channel_unlock(clone);
03795          return -1;
03796       }
03797    } else
03798       ast_log(LOG_WARNING, "Channel type '%s' does not have a fixup routine (for %s)!  Bad things may happen.\n",
03799          original->tech->type, original->name);
03800    
03801    /* Now, at this point, the "clone" channel is totally F'd up.  We mark it as
03802       a zombie so nothing tries to touch it.  If it's already been marked as a
03803       zombie, then free it now (since it already is considered invalid). */
03804    if (ast_test_flag(clone, AST_FLAG_ZOMBIE)) {
03805       if (option_debug)
03806          ast_log(LOG_DEBUG, "Destroying channel clone '%s'\n", clone->name);
03807       ast_channel_unlock(clone);
03808       manager_event(EVENT_FLAG_CALL, "Hangup",
03809          "Channel: %s\r\n"
03810          "Uniqueid: %s\r\n"
03811          "Cause: %d\r\n"
03812          "Cause-txt: %s\r\n",
03813          clone->name,
03814          clone->uniqueid,
03815          clone->hangupcause,
03816          ast_cause2str(clone->hangupcause)
03817          );
03818       ast_channel_free(clone);
03819    } else {
03820       if (option_debug)
03821          ast_log(LOG_DEBUG, "Released clone lock on '%s'\n", clone->name);
03822       ast_set_flag(clone, AST_FLAG_ZOMBIE);
03823       ast_queue_frame(clone, &ast_null_frame);
03824       ast_channel_unlock(clone);
03825    }
03826    
03827    /* Signal any blocker */
03828    if (ast_test_flag(original, AST_FLAG_BLOCKING))
03829       pthread_kill(original->blocker, SIGURG);
03830    if (option_debug)
03831       ast_log(LOG_DEBUG, "Done Masquerading %s (%d)\n", original->name, original->_state);
03832    return 0;
03833 }

static int ast_fdisset ( struct pollfd pfds,
int  fd,
int  max,
int *  start 
) [inline, static]

Helper function for migrating select to poll.

Definition at line 1347 of file channel.h.

References pollfd::revents.

01348 {
01349    int x;
01350    int dummy=0;
01351 
01352    if (fd < 0)
01353       return 0;
01354    if (!start)
01355       start = &dummy;
01356    for (x = *start; x<max; x++)
01357       if (pfds[x].fd == fd) {
01358          if (x == *start)
01359             (*start)++;
01360          return pfds[x].revents;
01361       }
01362    return 0;
01363 }

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.

Definition at line 1134 of file channel.c.

References channel_find_locked().

01135 {
01136    return channel_find_locked(NULL, NULL, 0, context, exten);
01137 }

struct ast_channel* ast_get_channel_by_name_locked ( const char *  chan  ) 

Get channel by name (locks channel).

Definition at line 1115 of file channel.c.

References channel_find_locked().

Referenced by action_getvar(), action_hangup(), action_redirect(), action_setcdruserfield(), action_setvar(), action_status(), action_timeout(), ast_async_goto_by_name(), asyncgoto_exec(), change_monitor_action(), do_pause_or_unpause(), get_zap_channel_locked(), handle_channelstatus(), handle_core_set_debug_channel(), handle_debugchan_deprecated(), handle_getvariablefull(), handle_hangup(), handle_nodebugchan_deprecated(), handle_showchan(), handle_showchan_deprecated(), handle_softhangup(), manager_park(), manager_play_dtmf(), pbx_builtin_importvar(), start_monitor_action(), and stop_monitor_action().

01116 {
01117    return channel_find_locked(NULL, name, 0, NULL, NULL);
01118 }

struct ast_channel* ast_get_channel_by_name_prefix_locked ( const char *  name,
const int  namelen 
)

Get channel by name prefix (locks channel).

Definition at line 1121 of file channel.c.

References channel_find_locked().

Referenced by ast_parse_device_state(), common_exec(), and mixmonitor_cli().

01122 {
01123    return channel_find_locked(NULL, name, namelen, NULL, NULL);
01124 }

struct ast_channel_tech* ast_get_channel_tech ( const char *  name  ) 

Get a channel technology structure by name.

Parameters:
name name of technology to find
Returns:
a pointer to the structure, or NULL if no matching technology found

Definition at line 569 of file channel.c.

References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), LOG_WARNING, chanlist::tech, and ast_channel_tech::type.

Referenced by ast_device_state().

00570 {
00571    struct chanlist *chanls;
00572    const struct ast_channel_tech *ret = NULL;
00573 
00574    if (AST_LIST_LOCK(&channels)) {
00575       ast_log(LOG_WARNING, "Unable to lock channel tech list\n");
00576       return NULL;
00577    }
00578 
00579    AST_LIST_TRAVERSE(&backends, chanls, list) {
00580       if (!strcasecmp(name, chanls->tech->type)) {
00581          ret = chanls->tech;
00582          break;
00583       }
00584    }
00585 
00586    AST_LIST_UNLOCK(&channels);
00587    
00588    return ret;
00589 }

ast_group_t ast_get_group ( const char *  s  ) 

Definition at line 4516 of file channel.c.

References ast_log(), ast_strdupa, group, LOG_ERROR, LOG_WARNING, and strsep().

Referenced by _parse(), build_device(), build_gateway(), build_peer(), func_channel_write(), process_zap(), and read_agent_config().

04517 {
04518    char *piece;
04519    char *c;
04520    int start=0, finish=0, x;
04521    ast_group_t group = 0;
04522 
04523    c = ast_strdupa(s);
04524    
04525    while ((piece = strsep(&c, ","))) {
04526       if (sscanf(piece, "%d-%d", &start, &finish) == 2) {
04527          /* Range */
04528       } else if (sscanf(piece, "%d", &start)) {
04529          /* Just one */
04530          finish = start;
04531       } else {
04532          ast_log(LOG_ERROR, "Syntax error parsing group configuration '%s' at '%s'. Ignoring.\n", s, piece);
04533          continue;
04534       }
04535       for (x = start; x <= finish; x++) {
04536          if ((x > 63) || (x < 0)) {
04537             ast_log(LOG_WARNING, "Ignoring invalid group %d (maximum group is 63)\n", x);
04538          } else
04539             group |= ((ast_group_t) 1 << x);
04540       }
04541    }
04542    return group;
04543 }

static int ast_get_read_format ( struct ast_channel chan  )  [inline, static]

Gets read format from channel chan.

Parameters:
chan channel to get info Get read format for channel Returns read format

Definition at line 880 of file channel.h.

References ast_channel::readformat.

Referenced by ast_channel_formats_reset().

00881 {
00882     return chan->readformat;
00883 }

static int ast_get_write_format ( struct ast_channel chan  )  [inline, static]

Parameters:
chan channel to get info Get write format for channel Returns write format

Definition at line 891 of file channel.h.

References ast_channel::writeformat.

Referenced by ast_channel_formats_reset().

00892 {
00893     return chan->writeformat;
00894 }

int ast_hangup ( struct ast_channel chan  ) 

Hang up a channel.

Note:
This function performs a hard hangup on a channel. Unlike the soft-hangup, this function performs all stream stopping, etc, on the channel that needs to end. chan is no longer valid after this call.
Parameters:
chan channel to hang up
Returns:
Returns 0 on success, -1 on failure.

Definition at line 1701 of file channel.c.

References ast_cause2str(), ast_cdr_detach(), ast_cdr_end(), ast_channel_free(), ast_channel_lock, ast_channel_unlock, ast_closestream(), ast_do_masquerade(), AST_FLAG_BLOCKING, AST_FLAG_ZOMBIE, ast_log(), ast_set_flag, ast_test_flag, ast_channel::blocker, ast_channel::blockproc, ast_channel::cdr, CRASH, detach_spies(), EVENT_FLAG_CALL, free_translation(), ast_channel::generator, ast_channel::generatordata, ast_channel_tech::hangup, ast_channel::hangupcause, LOG_DEBUG, LOG_WARNING, manager_event(), ast_channel::masq, ast_channel::masqr, option_debug, ast_generator::release, ast_channel::sched, sched_context_destroy(), ast_channel::stream, ast_channel::tech, and ast_channel::vstream.

Referenced by __ast_request_and_dial(), __oh323_new(), agent_hangup(), agent_read(), alsa_new(), app_exec(), ast_async_goto(), ast_bridge_call_thread(), 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(), build_conf(), builtin_atxfer(), chanavail_exec(), check_compat(), check_goto_on_transfer(), clear_caller(), conf_free(), conf_run(), connect_link(), do_hang(), do_parking_thread(), features_hangup(), findmeexec(), gtalk_new(), 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(), hangup_chan(), hangupcalls(), hanguptree(), iax2_request(), iax_park(), iax_park_thread(), local_attended_transfer(), local_hangup(), mgcp_new(), mgcp_ss(), monitor_dial(), nbs_new(), oss_new(), park_exec(), parkandannounce_exec(), phone_new(), rpt(), rpt_call(), rpt_tele_thread(), sip_new(), sip_park(), sip_park_thread(), skinny_new(), skinny_ss(), ss_thread(), try_calling(), wait_for_answer(), wait_for_winner(), zt_handle_event(), and zt_new().

01702 {
01703    int res = 0;
01704    struct ast_cdr *cdr = NULL;
01705 
01706    /* Don't actually hang up a channel that will masquerade as someone else, or
01707       if someone is going to masquerade as us */
01708    ast_channel_lock(chan);
01709 
01710    detach_spies(chan);     /* get rid of spies */
01711 
01712    if (chan->masq) {
01713       if (ast_do_masquerade(chan))
01714          ast_log(LOG_WARNING, "Failed to perform masquerade\n");
01715    }
01716 
01717    if (chan->masq) {
01718       ast_log(LOG_WARNING, "%s getting hung up, but someone is trying to masq into us?!?\n", chan->name);
01719       ast_channel_unlock(chan);
01720       return 0;
01721    }
01722    /* If this channel is one which will be masqueraded into something,
01723       mark it as a zombie already, so we know to free it later */
01724    if (chan->masqr) {
01725       ast_set_flag(chan, AST_FLAG_ZOMBIE);
01726       ast_channel_unlock(chan);
01727       return 0;
01728    }
01729    free_translation(chan);
01730    /* Close audio stream */
01731    if (chan->stream) {
01732       ast_closestream(chan->stream);
01733       chan->stream = NULL;
01734    }
01735    /* Close video stream */
01736    if (chan->vstream) {
01737       ast_closestream(chan->vstream);
01738       chan->vstream = NULL;
01739    }
01740    if (chan->sched) {
01741       sched_context_destroy(chan->sched);
01742       chan->sched = NULL;
01743    }
01744    
01745    if (chan->generatordata)   /* Clear any tone stuff remaining */
01746       chan->generator->release(chan, chan->generatordata);
01747    chan->generatordata = NULL;
01748    chan->generator = NULL;
01749    if (chan->cdr) {     /* End the CDR if it hasn't already */
01750       ast_cdr_end(chan->cdr);
01751       cdr = chan->cdr;
01752       chan->cdr = NULL;
01753    }
01754    if (ast_test_flag(chan, AST_FLAG_BLOCKING)) {
01755       ast_log(LOG_WARNING, "Hard hangup called by thread %ld on %s, while fd "
01756                "is blocked by thread %ld in procedure %s!  Expect a failure\n",
01757                (long)pthread_self(), chan->name, (long)chan->blocker, chan->blockproc);
01758       CRASH;
01759    }
01760    if (!ast_test_flag(chan, AST_FLAG_ZOMBIE)) {
01761       if (option_debug)
01762          ast_log(LOG_DEBUG, "Hanging up channel '%s'\n", chan->name);
01763       if (chan->tech->hangup)
01764          res = chan->tech->hangup(chan);
01765    } else {
01766       if (option_debug)
01767          ast_log(LOG_DEBUG, "Hanging up zombie '%s'\n", chan->name);
01768    }
01769          
01770    ast_channel_unlock(chan);
01771    manager_event(EVENT_FLAG_CALL, "Hangup",
01772          "Channel: %s\r\n"
01773          "Uniqueid: %s\r\n"
01774          "Cause: %d\r\n"
01775          "Cause-txt: %s\r\n",
01776          chan->name,
01777          chan->uniqueid,
01778          chan->hangupcause,
01779          ast_cause2str(chan->hangupcause)
01780          );
01781    ast_channel_free(chan);
01782 
01783    if (cdr)
01784       ast_cdr_detach(cdr);
01785 
01786    return res;
01787 }

int ast_indicate ( struct ast_channel chan,
int  condition 
)

Indicates condition of channel.

Note:
Indicate a condition such as AST_CONTROL_BUSY, AST_CONTROL_RINGING, or AST_CONTROL_CONGESTION on a channel
Parameters:
chan channel to change the indication
condition which condition to indicate on the channel
Returns:
Returns 0 on success, -1 on failure

Definition at line 2556 of file channel.c.

References ast_indicate_data().

Referenced by __ast_play_and_record(), agent_new(), ast_bridge_call(), ast_dtmf_stream(), ast_feature_request_and_dial(), attempt_transfer(), builtin_atxfer(), builtin_blindtransfer(), conf_run(), disa_exec(), do_parking_thread(), features_indicate(), finishup(), function_remote(), handle_frame(), handle_recordfile(), mgcp_ss(), monitor_dial(), park_exec(), pbx_builtin_busy(), pbx_builtin_congestion(), pbx_builtin_progress(), pbx_builtin_ringing(), pbx_builtin_waitexten(), queue_exec(), rpt(), send_waveform_to_channel(), skinny_ss(), sla_handle_hold_event(), sla_station_exec(), sla_trunk_exec(), and wait_for_answer().

02557 {
02558    return ast_indicate_data(chan, condition, NULL, 0);
02559 }

int ast_indicate_data ( struct ast_channel chan,
int  condition,
const void *  data,
size_t  datalen 
)

Indicates condition of channel, with payload.

Note:
Indicate a condition such as AST_CONTROL_HOLD with payload being music on hold class
Parameters:
chan channel to change the indication
condition which condition to indicate on the channel
data pointer to payload data
datalen size of payload data
Returns:
Returns 0 on success, -1 on failure

Definition at line 2561 of file channel.c.

References ast_channel_lock, ast_channel_unlock, ast_check_hangup(), AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_HOLD, AST_CONTROL_PROCEEDING, AST_CONTROL_PROGRESS, AST_CONTROL_RINGING, AST_CONTROL_UNHOLD, AST_CONTROL_VIDUPDATE, AST_FLAG_ZOMBIE, ast_get_indication_tone(), ast_log(), ast_playtones_start(), ast_playtones_stop(), ast_test_flag, tone_zone_sound::data, ast_channel_tech::indicate, LOG_DEBUG, LOG_WARNING, option_debug, ast_channel::tech, and ast_channel::zone.

Referenced by __login_exec(), agent_hangup(), ast_bridge_call(), ast_indicate(), ast_park_call(), bridge_native_loop(), bridge_p2p_loop(), do_parking_thread(), pbx_builtin_waitexten(), and wait_for_answer().

02562 {
02563    int res = -1;
02564 
02565    ast_channel_lock(chan);
02566    /* Stop if we're a zombie or need a soft hangup */
02567    if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan)) {
02568       ast_channel_unlock(chan);
02569       return -1;
02570    }
02571    if (chan->tech->indicate)
02572       res = chan->tech->indicate(chan, condition, data, datalen);
02573    ast_channel_unlock(chan);
02574    if (!chan->tech->indicate || res) {
02575       /*
02576        * Device does not support (that) indication, lets fake
02577        * it by doing our own tone generation. (PM2002)
02578        */
02579       if (condition < 0)
02580          ast_playtones_stop(chan);
02581       else {
02582          const struct tone_zone_sound *ts = NULL;
02583          switch (condition) {
02584          case AST_CONTROL_RINGING:
02585             ts = ast_get_indication_tone(chan->zone, "ring");
02586             break;
02587          case AST_CONTROL_BUSY:
02588             ts = ast_get_indication_tone(chan->zone, "busy");
02589             break;
02590          case AST_CONTROL_CONGESTION:
02591             ts = ast_get_indication_tone(chan->zone, "congestion");
02592             break;
02593          }
02594          if (ts && ts->data[0]) {
02595             if (option_debug)
02596                ast_log(LOG_DEBUG, "Driver for channel '%s' does not support indication %d, emulating it\n", chan->name, condition);
02597             ast_playtones_start(chan,0,ts->data, 1);
02598             res = 0;
02599          } else if (condition == AST_CONTROL_PROGRESS) {
02600             /* ast_playtones_stop(chan); */
02601          } else if (condition == AST_CONTROL_PROCEEDING) {
02602             /* Do nothing, really */
02603          } else if (condition == AST_CONTROL_HOLD) {
02604             /* Do nothing.... */
02605          } else if (condition == AST_CONTROL_UNHOLD) {
02606             /* Do nothing.... */
02607          } else if (condition == AST_CONTROL_VIDUPDATE) {
02608             /* Do nothing.... */
02609          } else {
02610             /* not handled */
02611             ast_log(LOG_WARNING, "Unable to handle indication %d for '%s'\n", condition, chan->name);
02612             res = -1;
02613          }
02614       }
02615    }
02616    return res;
02617 }

int ast_internal_timing_enabled ( struct ast_channel chan  ) 

Check if the channel can run in internal timing mode.

Parameters:
chan The channel to check
Returns:
boolean
This function will return 1 if internal timing is enabled and the timing device is available.

Definition at line 2538 of file channel.c.

References ast_log(), ast_opt_internal_timing, LOG_DEBUG, option_debug, and ast_channel::timingfd.

Referenced by add_sdp(), and ast_read_generator_actions().

02539 {
02540    int ret = ast_opt_internal_timing && chan->timingfd > -1;
02541    if (option_debug > 4)
02542       ast_log(LOG_DEBUG, "Internal timing is %s (option_internal_timing=%d chan->timingfd=%d)\n", ret? "enabled": "disabled", ast_opt_internal_timing, chan->timingfd);
02543    return ret;
02544 }

char* ast_print_group ( char *  buf,
int  buflen,
ast_group_t  group 
)

print call- and pickup groups into buffer

Definition at line 4598 of file channel.c.

Referenced by _sip_show_peer(), func_channel_read(), misdn_cfg_get_config_string(), print_group(), read_config(), and serialize_showchan().

04599 {
04600    unsigned int i;
04601    int first=1;
04602    char num[3];
04603 
04604    buf[0] = '\0';
04605    
04606    if (!group) /* Return empty string if no group */
04607       return buf;
04608 
04609    for (i = 0; i <= 63; i++) {   /* Max group is 63 */
04610       if (group & ((ast_group_t) 1 << i)) {
04611             if (!first) {
04612             strncat(buf, ", ", buflen);
04613          } else {
04614             first=0;
04615          }
04616          snprintf(num, sizeof(num), "%u", i);
04617          strncat(buf, num, buflen);
04618       }
04619    }
04620    return buf;
04621 }

int ast_prod ( struct ast_channel chan  ) 

Send empty audio to prime a channel driver.

Definition at line 2739 of file channel.c.

References ast_channel::_state, AST_FRAME_VOICE, AST_FRIENDLY_OFFSET, ast_log(), AST_STATE_UP, ast_write(), ast_frame::data, LOG_DEBUG, LOG_WARNING, option_debug, ast_channel::rawwriteformat, ast_frame::src, and ast_frame::subclass.

Referenced by ast_activate_generator().

02740 {
02741    struct ast_frame a = { AST_FRAME_VOICE };
02742    char nothing[128];
02743 
02744    /* Send an empty audio frame to get things moving */
02745    if (chan->_state != AST_STATE_UP) {
02746       if (option_debug)
02747          ast_log(LOG_DEBUG, "Prodding channel '%s'\n", chan->name);
02748       a.subclass = chan->rawwriteformat;
02749       a.data = nothing + AST_FRIENDLY_OFFSET;
02750       a.src = "ast_prod";
02751       if (ast_write(chan, &a))
02752          ast_log(LOG_WARNING, "Prodding channel '%s' failed\n", chan->name);
02753    }
02754    return 0;
02755 }

int ast_queue_control ( struct ast_channel chan,
enum ast_control_frame_type  control 
)

Queue a control frame with payload.

Parameters:
chan channel to queue frame onto
control type of control frame
Returns:
zero on success, non-zero on failure

Definition at line 961 of file channel.c.

References AST_FRAME_CONTROL, ast_queue_frame(), and f.

Referenced by __oh323_update_info(), __zt_exception(), ast_pickup_call(), attempt_transfer(), auto_congest(), gtalk_is_answered(), gtalk_ringing_ack(), handle_hd_hf(), handle_offhook_message(), handle_request(), handle_request_bye(), handle_request_info(), handle_request_refer(), handle_response(), handle_response_invite(), handle_response_refer(), handle_soft_key_event_message(), handle_stimulus_message(), mgcp_call(), nbs_call(), phone_call(), pickup_do(), process_sdp(), receive_digit(), send_cause2ast(), setup_rtp_connection(), skinny_call(), skinny_unhold(), ss_thread(), update_state(), zt_handle_event(), and zt_hangup().

00962 {
00963    struct ast_frame f = { AST_FRAME_CONTROL, };
00964 
00965    f.subclass = control;
00966 
00967    return ast_queue_frame(chan, &f);
00968 }

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.

Parameters:
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
Returns:
zero on success, non-zero on 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.

Note:
This method should be treated as a 'network transport'; in other words, your frames may be transferred across an IAX2 channel to another system, which may be a different endianness than yours. Because of this, you should ensure that either your frames will never be expected to work across systems, or that you always put your payload data into 'network byte order' before calling this function.

Definition at line 971 of file channel.c.

References AST_FRAME_CONTROL, ast_queue_frame(), and f.

Referenced by iax2_queue_control_data(), process_sdp(), skinny_hold(), zt_handle_event(), and zt_hangup().

00973 {
00974    struct ast_frame f = { AST_FRAME_CONTROL, };
00975 
00976    f.subclass = control;
00977    f.data = (void *) data;
00978    f.datalen = datalen;
00979 
00980    return ast_queue_frame(chan, &f);
00981 }

int ast_queue_frame ( struct ast_channel chan,
struct ast_frame f 
)

Queue an outgoing frame.

Definition at line 893 of file channel.c.

References ast_channel::alertpipe, ast_channel_lock, ast_channel_unlock, AST_CONTROL_HANGUP, AST_FLAG_BLOCKING, AST_FRAME_CONTROL, AST_FRAME_VOICE, ast_frdup(), ast_frfree(), AST_LIST_INSERT_TAIL, AST_LIST_LAST, AST_LIST_TRAVERSE, ast_log(), ast_test_flag, ast_channel::blocker, CRASH, f, ast_frame::frametype, LOG_DEBUG, LOG_WARNING, option_debug, ast_frame::subclass, and ast_channel::timingfd.

Referenced by __oh323_rtp_create(), __oh323_update_info(), agent_new(), alsa_call(), ast_channel_masquerade(), ast_channel_setwhentohangup(), ast_dsp_process(), ast_queue_control(), ast_queue_control_data(), ast_queue_hangup(), ast_softhangup_nolock(), cb_events(), console_answer(), console_answer_deprecated(), console_dial(), console_dial_deprecated(), console_flash(), console_flash_deprecated(), console_sendtext(), console_sendtext_deprecated(), dictate_exec(), do_immediate_setup(), gtalk_handle_dtmf(), handle_keypad_button_message(), handle_request_info(), handle_request_invite(), handle_response_invite(), iax2_queue_frame(), local_queue_frame(), mgcp_queue_frame(), oh323_simulate_dtmf_end(), oss_call(), process_sdp(), receive_digit(), receive_message(), rpt_call(), wakeup_sub(), and zap_queue_frame().

00894 {
00895    struct ast_frame *f;
00896    struct ast_frame *cur;
00897    int blah = 1;
00898    int qlen = 0;
00899 
00900    /* Build us a copy and free the original one */
00901    if (!(f = ast_frdup(fin))) {
00902       ast_log(LOG_WARNING, "Unable to duplicate frame\n");
00903       return -1;
00904    }
00905    ast_channel_lock(chan);
00906 
00907    /* See if the last frame on the queue is a hangup, if so don't queue anything */
00908    if ((cur = AST_LIST_LAST(&chan->readq)) && (cur->frametype == AST_FRAME_CONTROL) && (cur->subclass == AST_CONTROL_HANGUP)) {
00909       ast_frfree(f);
00910       ast_channel_unlock(chan);
00911       return 0;
00912    }
00913 
00914    /* Count how many frames exist on the queue */
00915    AST_LIST_TRAVERSE(&chan->readq, cur, frame_list) {
00916       qlen++;
00917    }
00918 
00919    /* Allow up to 96 voice frames outstanding, and up to 128 total frames */
00920    if (((fin->frametype == AST_FRAME_VOICE) && (qlen > 96)) || (qlen  > 128)) {
00921       if (fin->frametype != AST_FRAME_VOICE) {
00922          ast_log(LOG_WARNING, "Exceptionally long queue length queuing to %s\n", chan->name);
00923          CRASH;
00924       } else {
00925          if (option_debug)
00926             ast_log(LOG_DEBUG, "Dropping voice to exceptionally long queue on %s\n", chan->name);
00927          ast_frfree(f);
00928          ast_channel_unlock(chan);
00929          return 0;
00930       }
00931    }
00932    AST_LIST_INSERT_TAIL(&chan->readq, f, frame_list);
00933    if (chan->alertpipe[1] > -1) {
00934       if (write(chan->alertpipe[1], &blah, sizeof(blah)) != sizeof(blah))
00935          ast_log(LOG_WARNING, "Unable to write to alert pipe on %s, frametype/subclass %d/%d (qlen = %d): %s!\n",
00936             chan->name, f->frametype, f->subclass, qlen, strerror(errno));
00937 #ifdef HAVE_ZAPTEL
00938    } else if (chan->timingfd > -1) {
00939       ioctl(chan->timingfd, ZT_TIMERPING, &blah);
00940 #endif            
00941    } else if (ast_test_flag(chan, AST_FLAG_BLOCKING)) {
00942       pthread_kill(chan->blocker, SIGURG);
00943    }
00944    ast_channel_unlock(chan);
00945    return 0;
00946 }

int ast_queue_hangup ( struct ast_channel chan  ) 

Queue a hangup frame.

Definition at line 949 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, and f.

Referenced by __oh323_update_info(), __sip_autodestruct(), cleanup_connection(), console_hangup(), console_hangup_deprecated(), gtalk_hangup_farend(), handle_onhook_message(), handle_request_bye(), handle_request_cancel(), handle_response(), handle_response_invite(), handle_soft_key_event_message(), hangup_chan(), hangup_connection(), iax2_destroy(), iax2_queue_hangup(), mgcp_queue_hangup(), misdn_answer(), retrans_pkt(), and zt_handle_event().

00950 {
00951    struct ast_frame f = { AST_FRAME_CONTROL, AST_CONTROL_HANGUP };
00952    /* Yeah, let's not change a lock-critical value without locking */
00953    if (!ast_channel_trylock(chan)) {
00954       chan->_softhangup |= AST_SOFTHANGUP_DEV;
00955       ast_channel_unlock(chan);
00956    }
00957    return ast_queue_frame(chan, &f);
00958 }

struct ast_frame* ast_read ( struct ast_channel chan  ) 

Reads a frame.

Parameters:
chan channel to read a frame from
Returns:
Returns a frame, or NULL on error. If it returns NULL, you best just stop reading frames and assume the channel has been disconnected.

Definition at line 2546 of file channel.c.

References __ast_read().

Referenced by __adsi_transmit_messages(), __ast_play_and_record(), __ast_request_and_dial(), adsi_careful_send(), agent_ack_sleep(), agent_read(), app_exec(), ast_feature_request_and_dial(), ast_masq_park_call(), 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(), dictate_exec(), disa_exec(), do_parking_thread(), do_waiting(), echo_exec(), features_read(), find_cache(), handle_invite_replaces(), handle_recordfile(), iax_park_thread(), ices_exec(), isAnsweringMachine(), measurenoise(), misdn_bridge(), monitor_dial(), mp3_exec(), mwanalyze_exec(), NBScat_exec(), nv_background_detect_exec(), nv_detectfax_exec(), receive_dtmf_digits(), recordthread(), rpt(), run_agi(), rxfax_exec(), send_tone_burst(), send_waveform_to_channel(), sendurl_exec(), speech_background(), ss_thread(), txfax_exec(), wait_for_answer(), wait_for_hangup(), wait_for_winner(), waitforring_exec(), waitstream_core(), and zt_bridge().

02547 {
02548    return __ast_read(chan, 0);
02549 }

struct ast_frame* ast_read_noaudio ( struct ast_channel chan  ) 

Reads a frame, returning AST_FRAME_NULL frame if audio.

Parameters:
chan channel to read a frame from
Returns:
Returns a frame, or NULL on error. If it returns NULL, you best just stop reading frames and assume the channel has been disconnected.
Note:
Audio is replaced with AST_FRAME_NULL to avoid transcode when the resulting audio is not necessary.

Definition at line 2551 of file channel.c.

References __ast_read().

Referenced by conf_run().

02552 {
02553    return __ast_read(chan, 1);
02554 }

int ast_readstring ( struct ast_channel c,
char *  s,
int  len,
int  timeout,
int  rtimeout,
char *  enders 
)

Reads multiple digits

Parameters:
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 3280 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().

03281 {
03282    return ast_readstring_full(c, s, len, timeout, ftimeout, enders, -1, -1);
03283 }

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 3285 of file channel.c.

References ast_check_hangup(), AST_DIGIT_ANY, AST_FLAG_ZOMBIE, ast_stopstream(), ast_test_flag, ast_waitfordigit_full(), ast_waitstream_full(), and ast_channel::stream.

Referenced by ast_app_getdata_full(), and ast_readstring().

03286 {
03287    int pos = 0;   /* index in the buffer where we accumulate digits */
03288    int to = ftimeout;
03289 
03290    /* Stop if we're a zombie or need a soft hangup */
03291    if (ast_test_flag(c, AST_FLAG_ZOMBIE) || ast_check_hangup(c))
03292       return -1;
03293    if (!len)
03294       return -1;
03295    for (;;) {
03296       int d;
03297       if (c->stream) {
03298          d = ast_waitstream_full(c, AST_DIGIT_ANY, audiofd, ctrlfd);
03299          ast_stopstream(c);
03300          usleep(1000);
03301          if (!d)
03302             d = ast_waitfordigit_full(c, to, audiofd, ctrlfd);
03303       } else {
03304          d = ast_waitfordigit_full(c, to, audiofd, ctrlfd);
03305       }
03306       if (d < 0)
03307          return -1;
03308       if (d == 0) {
03309          s[pos]='\0';
03310          return 1;
03311       }
03312       if (d == 1) {
03313          s[pos]='\0';
03314          return 2;
03315       }
03316       if (!strchr(enders, d))
03317          s[pos++] = d;
03318       if (strchr(enders, d) || (pos >= len)) {
03319          s[pos]='\0';
03320          return 0;
03321       }
03322       to = timeout;
03323    }
03324    /* Never reached */
03325    return 0;
03326 }

int ast_recvchar ( struct ast_channel chan,
int  timeout 
)

Receives a text character from a channel.

Parameters:
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 2619 of file channel.c.

References ast_recvtext(), and free.

Referenced by handle_recvchar().

02620 {
02621    int c;
02622    char *buf = ast_recvtext(chan, timeout);
02623    if (buf == NULL)
02624       return -1;  /* error or timeout */
02625    c = *(unsigned char *)buf;
02626    free(buf);
02627    return c;
02628 }

char* ast_recvtext ( struct ast_channel chan,
int  timeout 
)

Receives a text string from a channel Read a string of text from a channel.

Parameters:
chan channel to act upon
timeout timeout in milliseconds (0 for infinite wait)
Returns:
the received text, or NULL to signify failure.

Definition at line 2630 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(), and f.

Referenced by ast_recvchar(), and handle_recvtext().

02631 {
02632    int res, done = 0;
02633    char *buf = NULL;
02634    
02635    while (!done) {
02636       struct ast_frame *f;
02637       if (ast_check_hangup(chan))
02638          break;
02639       res = ast_waitfor(chan, timeout);
02640       if (res <= 0) /* timeout or error */
02641          break;
02642       timeout = res; /* update timeout */
02643       f = ast_read(chan);
02644       if (f == NULL)
02645          break; /* no frame */
02646       if (f->frametype == AST_FRAME_CONTROL && f->subclass == AST_CONTROL_HANGUP)
02647          done = 1;   /* force a break */
02648       else if (f->frametype == AST_FRAME_TEXT) {      /* what we want */
02649          buf = ast_strndup((char *) f->data, f->datalen);   /* dup and break */
02650          done = 1;
02651       }
02652       ast_frfree(f);
02653    }
02654    return buf;
02655 }

struct ast_channel* ast_request ( const char *  type,
int  format,
void *  data,
int *  status 
)

Requests a channel.

Parameters:
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
Returns:
Returns an ast_channel on success, NULL on failure.

Definition at line 3188 of file channel.c.

References AST_CAUSE_BEARERCAPABILITY_NOTAVAIL, AST_CAUSE_NOSUCHDRIVER, AST_CAUSE_NOTDEFINED, AST_FORMAT_AUDIO_MASK, AST_FORMAT_VIDEO_MASK, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_log(), ast_translator_best_choice(), ast_channel_tech::capabilities, capabilities, fmt, LOG_WARNING, ast_channel_tech::requester, chanlist::tech, and ast_channel_tech::type.

Referenced by __ast_request_and_dial(), agent_request(), ast_feature_request_and_dial(), ast_request_inherit(), attempt_reconnect(), begin_dial(), build_conf(), chanavail_exec(), conf_run(), connect_link(), features_alloc(), findmeexec(), ring_entry(), rpt(), rpt_call(), rpt_tele_thread(), and wait_for_answer().

03189 {
03190    struct chanlist *chan;
03191    struct ast_channel *c;
03192    int capabilities;
03193    int fmt;
03194    int res;
03195    int foo;
03196    int videoformat = format & AST_FORMAT_VIDEO_MASK;
03197 
03198    if (!cause)
03199       cause = &foo;
03200    *cause = AST_CAUSE_NOTDEFINED;
03201 
03202    if (AST_LIST_LOCK(&channels)) {
03203       ast_log(LOG_WARNING, "Unable to lock channel list\n");
03204       return NULL;
03205    }
03206 
03207    AST_LIST_TRAVERSE(&backends, chan, list) {
03208       if (strcasecmp(type, chan->tech->type))
03209          continue;
03210 
03211       capabilities = chan->tech->capabilities;
03212       fmt = format & AST_FORMAT_AUDIO_MASK;
03213       res = ast_translator_best_choice(&fmt, &capabilities);
03214       if (res < 0) {
03215          ast_log(LOG_WARNING, "No translator path exists for channel type %s (native %d) to %d\n", type, chan->tech->capabilities, format);
03216          *cause = AST_CAUSE_BEARERCAPABILITY_NOTAVAIL;
03217          AST_LIST_UNLOCK(&channels);
03218          return NULL;
03219       }
03220       AST_LIST_UNLOCK(&channels);
03221       if (!chan->tech->requester)
03222          return NULL;
03223       
03224       if (!(c = chan->tech->requester(type, capabilities | videoformat, data, cause)))
03225          return NULL;
03226 
03227       /* no need to generate a Newchannel event here; it is done in the channel_alloc call */
03228       return c;
03229    }
03230 
03231    ast_log(LOG_WARNING, "No channel type registered for '%s'\n", type);
03232    *cause = AST_CAUSE_NOSUCHDRIVER;
03233    AST_LIST_UNLOCK(&channels);
03234 
03235    return NULL;
03236 }

struct ast_channel* ast_request_and_dial ( const char *  type,
int  format,
void *  data,
int  timeout,
int *  reason,
const char *  cidnum,
const char *  cidname 
)

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.

Parameters:
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 unsuceessful)
cidnum Caller-ID Number
cidname Caller-ID Name
Returns:
Returns an ast_channel on success or no answer, NULL on failure. Check the value of chan->_state to know if the call was answered or not.

Definition at line 3183 of file channel.c.

References __ast_request_and_dial().

Referenced by ast_pbx_outgoing_exten().

03184 {
03185    return __ast_request_and_dial(type, format, data, timeout, outstate, cidnum, cidname, NULL);
03186 }

static struct ast_channel* ast_request_inherit ( struct ast_channel chan,
const char *  type,
void *  data,
int *  status 
) [inline, static]

call ast_request with format/type of parent channel

Definition at line 650 of file channel.h.

References ast_request(), ast_channel::nativeformats, S_OR, ast_channel::tech, and ast_channel_tech::type.

00651 {
00652    return ast_request(S_OR(type, chan->tech->type), chan->nativeformats, data, status);
00653 }

int ast_safe_sleep ( struct ast_channel chan,
int  ms 
)

Wait for a specied amount of time, looking for hangups.

Parameters:
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.
Returns:
returns -1 on hangup, otherwise 0.

Definition at line 1168 of file channel.c.

References ast_safe_sleep_conditional().

Referenced by __login_exec(), alarmreceiver_exec(), ast_adsi_transmit_message_full(), ast_dtmf_stream(), ast_senddigit(), builtin_parkcall(), dictate_exec(), flash_exec(), function_ilink(), mgcp_ss(), milliwatt_exec(), moh0_exec(), moh1_exec(), park_call_exec(), pbx_builtin_answer(), pbx_builtin_wait(), 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(), test1_client(), test1_server(), testclient_exec(), testserver_exec(), try_calling(), wait_for_hangup(), wait_interval(), and zapateller_exec().

01169 {
01170    return ast_safe_sleep_conditional(chan, ms, NULL, NULL);
01171 }

int ast_safe_sleep_conditional ( struct ast_channel chan,
int  ms,
int(*)(void *)  cond,
void *  data 
)

Wait for a specied amount of time, looking for hangups and a condition argument.

Parameters:
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
Returns:
returns -1 on hangup, otherwise 0. Waits for a specified amount of time, servicing the channel as required. If cond returns 0, this function returns.

Definition at line 1147 of file channel.c.

References ast_frfree(), ast_read(), ast_waitfor(), and f.

Referenced by __login_exec(), and ast_safe_sleep().

01148 {
01149    struct ast_frame *f;
01150 
01151    while (ms > 0) {
01152       if (cond && ((*cond)(data) == 0))
01153          return 0;
01154       ms = ast_waitfor(chan, ms);
01155       if (ms < 0)
01156          return -1;
01157       if (ms > 0) {
01158          f = ast_read(chan);
01159          if (!f)
01160             return -1;
01161          ast_frfree(f);
01162       }
01163    }
01164    return 0;
01165 }

char* ast_safe_string_alloc ( const char *  fmt,
  ... 
)

printf the string into a correctly sized mallocd buffer, and return the buffer

return a mallocd string with the result of sprintf of the fmt and following args

Definition at line 426 of file channel.c.

References ast_malloc, and len.

Referenced by features_new(), and zt_new().

00427 {
00428    char *b2, buf[1];
00429    int len;
00430    va_list args;
00431 
00432    va_start(args, fmt);
00433    len = vsnprintf(buf, 1, fmt, args);
00434    va_end(args);
00435 
00436    if (!(b2 = ast_malloc(len + 1)))
00437       return NULL;
00438 
00439    va_start(args, fmt);
00440    vsnprintf(b2, len + 1,  fmt, args);
00441    va_end(args);
00442 
00443    return b2;
00444 }

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.

Parameters:
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 1388 of file channel.h.

Referenced by do_monitor(), do_parking_thread(), and sound_thread().

01389 {
01390 #ifdef __linux__
01391    return select(nfds, rfds, wfds, efds, tvp);
01392 #else
01393    if (tvp) {
01394       struct timeval tv, tvstart, tvend, tvlen;
01395       int res;
01396 
01397       tv = *tvp;
01398       gettimeofday(&tvstart, NULL);
01399       res = select(nfds, rfds, wfds, efds, tvp);
01400       gettimeofday(&tvend, NULL);
01401       timersub(&tvend, &tvstart, &tvlen);
01402       timersub(&tv, &tvlen, tvp);
01403       if (tvp->tv_sec < 0 || (tvp->tv_sec == 0 && tvp->tv_usec < 0)) {
01404          tvp->tv_sec = 0;
01405          tvp->tv_usec = 0;
01406       }
01407       return res;
01408    }
01409    else
01410       return select(nfds, rfds, wfds, efds, NULL);
01411 #endif
01412 }

int ast_senddigit ( struct ast_channel chan,
char  digit 
)

Send a DTMF digit to a channel Send a DTMF digit to a channel.

Parameters:
chan channel to act upon
digit the DTMF digit to send, encoded in ASCII
Returns:
Returns 0 on success, -1 on failure

Definition at line 2729 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(), do_dtmf_phone(), manager_play_dtmf(), and rpt_call().

02730 {
02731    if (chan->tech->send_digit_begin) {
02732       ast_senddigit_begin(chan, digit);
02733       ast_safe_sleep(chan, AST_DEFAULT_EMULATE_DTMF_DURATION);
02734    }
02735    
02736    return ast_senddigit_end(chan, digit, AST_DEFAULT_EMULATE_DTMF_DURATION);
02737 }

int ast_senddigit_begin ( struct ast_channel chan,
char  digit 
)

Send a DTMF digit to a channel Send a DTMF digit to a channel.

Parameters:
chan channel to act upon
digit the DTMF digit to send, encoded in ASCII
Returns:
Returns 0 on success, -1 on failure

Definition at line 2670 of file channel.c.

References ast_log(), ast_playtones_start(), LOG_DEBUG, option_debug, ast_channel_tech::send_digit_begin, and ast_channel::tech.

Referenced by agent_digit_begin(), ast_senddigit(), ast_write(), and features_digit_begin().

02671 {
02672    /* Device does not support DTMF tones, lets fake
02673     * it by doing our own generation. */
02674    static const char* dtmf_tones[] = {
02675       "941+1336", /* 0 */
02676       "697+1209", /* 1 */
02677       "697+1336", /* 2 */
02678       "697+1477", /* 3 */
02679       "770+1209", /* 4 */
02680       "770+1336", /* 5 */
02681       "770+1477", /* 6 */
02682       "852+1209", /* 7 */
02683       "852+1336", /* 8 */
02684       "852+1477", /* 9 */
02685       "697+1633", /* A */
02686       "770+1633", /* B */
02687       "852+1633", /* C */
02688       "941+1633", /* D */
02689       "941+1209", /* * */
02690       "941+1477"  /* # */
02691    };
02692 
02693    if (!chan->tech->send_digit_begin)
02694       return 0;
02695 
02696    if (!chan->tech->send_digit_begin(chan, digit))
02697       return 0;
02698 
02699    if (digit >= '0' && digit <='9')
02700       ast_playtones_start(chan, 0, dtmf_tones[digit-'0'], 0);
02701    else if (digit >= 'A' && digit <= 'D')
02702       ast_playtones_start(chan, 0, dtmf_tones[digit-'A'+10], 0);
02703    else if (digit == '*')
02704       ast_playtones_start(chan, 0, dtmf_tones[14], 0);
02705    else if (digit == '#')
02706       ast_playtones_start(chan, 0, dtmf_tones[15], 0);
02707    else {
02708       /* not handled */
02709       if (option_debug)
02710          ast_log(LOG_DEBUG, "Unable to generate DTMF tone '%c' for '%s'\n", digit, chan->name);
02711    }
02712 
02713    return 0;
02714 }

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.

Parameters:
chan channel to act upon
digit the DTMF digit to send, encoded in ASCII
Returns:
Returns 0 on success, -1 on failure

Definition at line 2716 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(), ast_write(), and features_digit_end().

02717 {
02718    int res = -1;
02719 
02720    if (chan->tech->send_digit_end)
02721       res = chan->tech->send_digit_end(chan, digit, duration);
02722 
02723    if (res && chan->generator)
02724       ast_playtones_stop(chan);
02725    
02726    return 0;
02727 }

int ast_sendtext ( struct ast_channel chan,
const char *  text 
)

Sends text to a channel Write text to a display on a channel.

Parameters:
chan channel to act upon
text string of text to send on the channel
Returns:
Returns 0 on success, -1 on failure

Definition at line 2657 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 agent_sendtext(), handle_sendtext(), and sendtext_exec().

02658 {
02659    int res = 0;
02660    /* Stop if we're a zombie or need a soft hangup */
02661    if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan))
02662       return -1;
02663    CHECK_BLOCKING(chan);
02664    if (chan->tech->send_text)
02665       res = chan->tech->send_text(chan, text);
02666    ast_clear_flag(chan, AST_FLAG_BLOCKING);
02667    return res;
02668 }

static void ast_set_best_format ( struct ast_channel channel  )  [inline, static]

Set best format, identical to read/write.

Parameters:
channel channel, from that nativeformats used and formats set

Definition at line 1155 of file channel.h.

References ast_channel_best_codec(), ast_set_read_format(), and ast_set_write_format().

01156 {
01157     int format = ast_channel_best_codec(channel);
01158     ast_set_read_format(channel, format);
01159     ast_set_write_format(channel, format);
01160 }

void ast_set_callerid ( struct ast_channel chan,
const char *  cidnum,
const char *  cidname,
const char *  ani 
)

Definition at line 3835 of file channel.c.

References ast_cdr_setcid(), ast_describe_caller_presentation(), ast_strdup, ast_channel::cdr, ast_channel::cid, ast_callerid::cid_ani, ast_callerid::cid_name, ast_callerid::cid_num, ast_callerid::cid_pres, EVENT_FLAG_CALL, free, manager_event(), and S_OR.

Referenced by __ast_request_and_dial(), agent_call(), ast_feature_request_and_dial(), callerid_write(), disa_exec(), findmeexec(), handle_setcallerid(), lookupcidname_exec(), mgcp_ss(), privacy_exec(), read_config(), setcallerid_exec(), skinny_newcall(), ss_thread(), wait_for_answer(), and zt_read().

03836 {
03837    if (callerid) {
03838       if (chan->cid.cid_num)
03839          free(chan->cid.cid_num);
03840       chan->cid.cid_num = ast_strdup(callerid);
03841    }
03842    if (calleridname) {
03843       if (chan->cid.cid_name)
03844          free(chan->cid.cid_name);
03845       chan->cid.cid_name = ast_strdup(calleridname);
03846    }
03847    if (ani) {
03848       if (chan->cid.cid_ani)
03849          free(chan->cid.cid_ani);
03850       chan->cid.cid_ani = ast_strdup(ani);
03851    }
03852    if (chan->cdr)
03853       ast_cdr_setcid(chan->cdr, chan);
03854    manager_event(EVENT_FLAG_CALL, "Newcallerid",
03855             "Channel: %s\r\n"
03856             "CallerID: %s\r\n"
03857             "CallerIDName: %s\r\n"
03858             "Uniqueid: %s\r\n"
03859             "CID-CallingPres: %d (%s)\r\n",
03860             chan->name,
03861             S_OR(chan->cid.cid_num, "<Unknown>"),
03862             S_OR(chan->cid.cid_name, "<Unknown>"),
03863             chan->uniqueid,
03864             chan->cid.cid_pres,
03865             ast_describe_caller_presentation(chan->cid.cid_pres)
03866             );
03867 }

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.

Parameters:
chan channel to change
format format to change to
Returns:
Returns 0 on success, -1 on failure

Definition at line 3024 of file channel.c.

References ast_channel::rawreadformat, ast_channel::readformat, ast_channel::readtrans, and set_format().

Referenced by __ast_play_and_record(), __login_exec(), __oh323_update_info(), agent_call(), alarmreceiver_exec(), ast_adsi_transmit_message_full(), ast_channel_formats_reset(), ast_channel_make_compatible(), ast_set_best_format(), attempt_reconnect(), background_detect_exec(), build_conf(), conf_run(), connect_link(), dictate_exec(), disa_exec(), do_waiting(), eagi_exec(), echo_exec(), gtalk_rtp_read(), handle_recordfile(), ices_exec(), isAnsweringMachine(), measurenoise(), mgcp_rtp_read(), milliwatt_exec(), mwanalyze_exec(), nv_background_detect_exec(), nv_detectfax_exec(), oh323_rtp_read(), process_sdp(), rpt(), rxfax_exec(), setup_rtp_connection(), sip_rtp_read(), skinny_rtp_read(), socket_process(), speech_background(), txfax_exec(), and update_features().

03025 {
03026    return set_format(chan, fmt, &chan->rawreadformat, &chan->readformat,
03027            &chan->readtrans, 0);
03028 }

void ast_set_variables ( struct ast_channel chan,
struct ast_variable vars 
)

adds a list of channel variables to a channel

Parameters:
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 4623 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_pbx_outgoing_app(), and ast_pbx_outgoing_exten().

04624 {
04625    struct ast_variable *cur;
04626 
04627    for (cur = vars; cur; cur = cur->next)
04628       pbx_builtin_setvar_helper(chan, cur->name, cur->value);  
04629 }

int ast_set_write_format ( struct ast_channel chan,
int  format 
)

Sets write format on channel chan Set write format for channel to whichever compoent of "format" is best.

Parameters:
chan channel to change
format new format for writing
Returns:
Returns 0 on success, -1 on failure

Definition at line 3030 of file channel.c.

References ast_channel::rawwriteformat, set_format(), ast_channel::writeformat, and ast_channel::writetrans.

Referenced by __login_exec(), __oh323_update_info(), agent_call(), alarmreceiver_exec(), ast_adsi_transmit_message_full(), ast_channel_formats_reset(), ast_channel_make_compatible(), ast_channel_start_silence_generator(), ast_channel_stop_silence_generator(), ast_channel_whisper_stop(), ast_openstream_full(), ast_set_best_format(), ast_stopstream(), ast_write(), attempt_reconnect(), build_conf(), channel_spy(), chanspy_exec(), conf_run(), connect_link(), disa_exec(), echo_exec(), extenspy_exec(), gtalk_rtp_read(), linear_alloc(), linear_release(), mgcp_rtp_read(), milliwatt_exec(), moh_alloc(), moh_files_release(), moh_release(), mp3_exec(), mwanalyze_exec(), NBScat_exec(), oh323_rtp_read(), playtones_alloc(), playtones_release(), process_sdp(), rpt(), rxfax_exec(), send_waveform_to_channel(), setup_rtp_connection(), sip_rtp_read(), skinny_rtp_read(), socket_process(), tonepair_alloc(), tonepair_release(), txfax_exec(), and update_features().

03031 {
03032    return set_format(chan, fmt, &chan->rawwriteformat, &chan->writeformat,
03033            &chan->writetrans, 1);
03034 }

int ast_setstate ( struct ast_channel chan,
enum  ast_channel_state 
)

Change the state of a channel.

Definition at line 3869 of file channel.c.

References ast_channel::_state, ast_device_state_changed_literal(), ast_state2str(), ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, EVENT_FLAG_CALL, manager_event(), and S_OR.

Referenced by __ast_read(), __oh323_update_info(), __zt_exception(), agent_call(), alsa_answer(), ast_answer(), cb_events(), check_availability(), 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(), 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(), sip_answer(), skinny_answer(), skinny_call(), skinny_newcall(), ss_thread(), update_state(), zt_answer(), zt_call(), zt_handle_event(), zt_indicate(), and zt_read().

03870 {
03871    int oldstate = chan->_state;
03872 
03873    if (oldstate == state)
03874       return 0;
03875 
03876    chan->_state = state;
03877    ast_device_state_changed_literal(chan->name);
03878    /* setstate used to conditionally report Newchannel; this is no more */
03879    manager_event(EVENT_FLAG_CALL,
03880             "Newstate",
03881             "Channel: %s\r\n"
03882             "State: %s\r\n"
03883             "CallerID: %s\r\n"
03884             "CallerIDName: %s\r\n"
03885             "Uniqueid: %s\r\n",
03886             chan->name, ast_state2str(chan->_state),
03887             S_OR(chan->cid.cid_num, "<unknown>"),
03888             S_OR(chan->cid.cid_name, "<unknown>"),
03889             chan->uniqueid);
03890 
03891    return 0;
03892 }

int ast_settimeout ( struct ast_channel c,
int  samples,
int(*)(void *data)  func,
void *  data 
)

Definition at line 2060 of file channel.c.

References ast_log(), LOG_DEBUG, option_debug, ast_channel::timingdata, ast_channel::timingfd, and ast_channel::timingfunc.

Referenced by ast_activate_generator(), ast_closestream(), ast_deactivate_generator(), ast_read_generator_actions(), and ast_readaudio_callback().

02061 {
02062    int res = -1;
02063 #ifdef HAVE_ZAPTEL
02064    if (c->timingfd > -1) {
02065       if (!func) {
02066          samples = 0;
02067          data = 0;
02068       }
02069       if (option_debug)
02070          ast_log(LOG_DEBUG, "Scheduling timer at %d sample intervals\n", samples);
02071       res = ioctl(c->timingfd, ZT_TIMERCONFIG, &samples);
02072       c->timingfunc = func;
02073       c->timingdata = data;
02074    }
02075 #endif   
02076    return res;
02077 }

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 478 of file channel.c.

References shutting_down.

00479 {
00480    return shutting_down;
00481 }

int ast_softhangup ( struct ast_channel chan,
int  cause 
)

Softly hangup up a channel.

Parameters:
chan channel to be soft-hung-up 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.
cause Ast hangupcause for hangup
Returns:
Returns 0 regardless

Definition at line 1556 of file channel.c.

References ast_channel_lock, ast_channel_unlock, ast_softhangup_nolock(), and ast_channel_spy::chan.

Referenced by __ast_module_user_hangup_all(), __login_exec(), __unload_module(), action_hangup(), agent_hangup(), agent_logoff(), ast_begin_shutdown(), connect_link(), function_ilink(), handle_hangup(), handle_link_data(), handle_softhangup(), manager_park(), read_agent_config(), rpt(), rpt_call(), rpt_do_restart(), sla_handle_hold_event(), softhangup_exec(), start_spying(), startmon(), unload_module(), and zt_handle_event().

01557 {
01558    int res;
01559    ast_channel_lock(chan);
01560    res = ast_softhangup_nolock(chan, cause);
01561    ast_channel_unlock(chan);
01562    return res;
01563 }

int ast_softhangup_nolock ( struct ast_channel chan,
int  cause 
)

Softly hangup up a channel (no channel lock).

Parameters:
chan channel to be soft-hung-up
cause Ast hangupcause for hangup (see cause.h)

Definition at line 1542 of file channel.c.

References ast_channel::_softhangup, AST_FLAG_BLOCKING, ast_log(), ast_null_frame, ast_queue_frame(), ast_test_flag, ast_channel::blocker, ast_channel_spy::chan, LOG_DEBUG, and option_debug.

Referenced by ast_async_goto(), ast_softhangup(), attempt_transfer(), do_monitor(), oh323_indicate(), sip_indicate(), and skinny_indicate().

01543 {
01544    if (option_debug)
01545       ast_log(LOG_DEBUG, "Soft-Hanging up channel '%s'\n", chan->name);
01546    /* Inform channel driver that we need to be hung up, if it cares */
01547    chan->_softhangup |= cause;
01548    ast_queue_frame(chan, &ast_null_frame);
01549    /* Interrupt any poll call or such */
01550    if (ast_test_flag(chan, AST_FLAG_BLOCKING))
01551       pthread_kill(chan->blocker, SIGURG);
01552    return 0;
01553 }

char* ast_state2str ( enum  ast_channel_state  ) 

Gives the string form of a given channel state.

Parameters:
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 617 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, and STATE2STR_BUFSIZE.

Referenced by action_status(), agent_hangup(), ast_setstate(), attempt_transfer(), func_channel_read(), handle_chanlist(), handle_chanlist_deprecated(), handle_invite_replaces(), handle_showchan(), handle_showchan_deprecated(), local_attended_transfer(), mgcp_new(), serialize_showchan(), and sip_hangup().

00618 {
00619    char *buf;
00620 
00621    switch(state) {
00622    case AST_STATE_DOWN:
00623       return "Down";
00624    case AST_STATE_RESERVED:
00625       return "Rsrvd";
00626    case AST_STATE_OFFHOOK:
00627       return "OffHook";
00628    case AST_STATE_DIALING:
00629       return "Dialing";
00630    case AST_STATE_RING:
00631       return "Ring";
00632    case AST_STATE_RINGING:
00633       return "Ringing";
00634    case AST_STATE_UP:
00635       return "Up";
00636    case AST_STATE_BUSY:
00637       return "Busy";
00638    case AST_STATE_DIALING_OFFHOOK:
00639       return "Dialing Offhook";
00640    case AST_STATE_PRERING:
00641       return "Pre-ring";
00642    default:
00643       if (!(buf = ast_threadstorage_get(&state2str_threadbuf, STATE2STR_BUFSIZE)))
00644          return "Unknown";
00645       snprintf(buf, STATE2STR_BUFSIZE, "Unknown (%d)", state);
00646       return buf;
00647    }
00648 }

int ast_str2cause ( const char *  name  ) 

Convert a symbolic hangup cause to number.

Parameters:
name string form of the cause Returns the cause code

Definition at line 605 of file channel.c.

References causes.

Referenced by pbx_builtin_hangup().

00606 {
00607    int x;
00608 
00609    for (x = 0; x < sizeof(causes) / sizeof(causes[0]); x++)
00610       if (strncasecmp(causes[x].name, name, strlen(causes[x].name)) == 0)
00611          return causes[x].cause;
00612 
00613    return -1;
00614 }

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 4498 of file channel.c.

References ast_frfree(), ast_read(), ast_tonepair_start(), ast_waitfor(), f, and ast_channel::generatordata.

Referenced by zapateller_exec().

04499 {
04500    int res;
04501 
04502    if ((res = ast_tonepair_start(chan, freq1, freq2, duration, vol)))
04503       return res;
04504 
04505    /* Give us some wiggle room */
04506    while (chan->generatordata && ast_waitfor(chan, 100) >= 0) {
04507       struct ast_frame *f = ast_read(chan);
04508       if (f)
04509          ast_frfree(f);
04510       else
04511          return -1;
04512    }
04513    return 0;
04514 }

int ast_tonepair_start ( struct ast_channel chan,
int  freq1,
int  freq2,
int  duration,
int  vol 
)

Start a tone going

Definition at line 4480 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(), play_dialtone(), play_tone_pair(), rpt_tele_thread(), and sendnoise().

04481 {
04482    struct tonepair_def d = { 0, };
04483 
04484    d.freq1 = freq1;
04485    d.freq2 = freq2;
04486    d.duration = duration;
04487    d.vol = (vol < 1) ? 8192 : vol; /* force invalid to 8192 */
04488    if (ast_activate_generator(chan, &tonepair, &d))
04489       return -1;
04490    return 0;
04491 }

void ast_tonepair_stop ( struct ast_channel chan  ) 

Stop a tone from playing

Definition at line 4493 of file channel.c.

References ast_deactivate_generator().

Referenced by sendnoise().

04494 {
04495    ast_deactivate_generator(chan);
04496 }

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.

Called by:

Definition at line 3262 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().

03263 {
03264    int res = -1;
03265 
03266    /* Stop if we're a zombie or need a soft hangup */
03267    ast_channel_lock(chan);
03268    if (!ast_test_flag(chan, AST_FLAG_ZOMBIE) && !ast_check_hangup(chan)) {
03269       if (chan->tech->transfer) {
03270          res = chan->tech->transfer(chan, dest);
03271          if (!res)
03272             res = 1;
03273       } else
03274          res = 0;
03275    }
03276    ast_channel_unlock(chan);
03277    return res;
03278 }

char* ast_transfercapability2str ( int  transfercapability  )  const

Gives the string form of a given transfer capability.

Parameters:
transfercapability transfercapabilty to get the name of Give a name to a transfercapbility See above Returns the text form of the binary transfer capbility

Definition at line 651 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(), misdn_call(), oh323_call(), zt_call(), and zt_new().

00652 {
00653    switch(transfercapability) {
00654    case AST_TRANS_CAP_SPEECH:
00655       return "SPEECH";
00656    case AST_TRANS_CAP_DIGITAL:
00657       return "DIGITAL";
00658    case AST_TRANS_CAP_RESTRICTED_DIGITAL:
00659       return "RESTRICTED_DIGITAL";
00660    case AST_TRANS_CAP_3_1K_AUDIO:
00661       return "3K1AUDIO";
00662    case AST_TRANS_CAP_DIGITAL_W_TONES:
00663       return "DIGITAL_W_TONES";
00664    case AST_TRANS_CAP_VIDEO:
00665       return "VIDEO";
00666    default:
00667       return "UNKNOWN";
00668    }
00669 }

int ast_waitfor ( struct ast_channel chan,
int  ms 
)

Wait for input on a channel.

Parameters:
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).
Returns:
Returns < 0 on failure, 0 if nothing ever arrived, and the # of ms remaining otherwise

Definition at line 2044 of file channel.c.

References ast_waitfor_nandfds().

Referenced by __adsi_transmit_messages(), __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_waiting(), echo_exec(), handle_recordfile(), ices_exec(), isAnsweringMachine(), measurenoise(), mp3_exec(), mwanalyze_exec(), NBScat_exec(), nv_background_detect_exec(), nv_detectfax_exec(), receive_dtmf_digits(), recordthread(), rxfax_exec(), send_tone_burst(), send_waveform_to_channel(), sendurl_exec(), speech_background(), ss_thread(), txfax_exec(), wait_for_hangup(), waitforring_exec(), and waitstream_core().

02045 {
02046    int oldms = ms;   /* -1 if no timeout */
02047 
02048    ast_waitfor_nandfds(&c, 1, NULL, 0, NULL, NULL, &ms);
02049    if ((ms < 0) && (oldms < 0))
02050       ms = 0;
02051    return ms;
02052 }

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.

Returns:
Return channel with activity, or NULL if none has activity.
Parameters:
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 2039 of file channel.c.

References ast_waitfor_nandfds().

Referenced by ast_feature_request_and_dial(), ast_udptl_bridge(), autoservice_run(), bridge_native_loop(), bridge_p2p_loop(), misdn_bridge(), monitor_dial(), rpt(), wait_for_answer(), wait_for_winner(), and zt_bridge().

02040 {
02041    return ast_waitfor_nandfds(c, n, NULL, 0, NULL, NULL, ms);
02042 }

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 1884 of file channel.c.

References ast_waitfor_nandfds().

Referenced by dundi_lookup_internal(), and dundi_precache_internal().

01885 {
01886    int winner = -1;
01887    ast_waitfor_nandfds(NULL, 0, fds, n, exception, &winner, ms);
01888    return winner;
01889 }

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.

Parameters:
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.
Returns:
Returns the channel with activity, or NULL on error or if an FD came first. If the FD came first, it will be returned in outfd, otherwise, outfd will be -1

Definition at line 1892 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_set_flag, AST_SOFTHANGUP_TIMEOUT, CHECK_BLOCKING, LOG_WARNING, poll(), POLLPRI, and ast_channel::whentohangup.

Referenced by app_exec(), ast_waitfor(), ast_waitfor_n(), ast_waitfor_n_fd(), ast_waitfordigit_full(), conf_run(), find_cache(), run_agi(), and waitstream_core().

01894 {
01895    struct timeval start = { 0 , 0 };
01896    struct pollfd *pfds;
01897    int res;
01898    long rms;
01899    int x, y, max;
01900    int sz;
01901    time_t now = 0;
01902    long whentohangup = 0, diff;
01903    struct ast_channel *winner = NULL;
01904    struct fdmap {
01905       int chan;
01906       int fdno;
01907    } *fdmap;
01908 
01909    sz = n * AST_MAX_FDS + nfds;
01910    pfds = alloca(sizeof(*pfds) * sz);
01911    fdmap = alloca(sizeof(*fdmap) * sz);
01912 
01913    if (outfd)
01914       *outfd = -99999;
01915    if (exception)
01916       *exception = 0;
01917    
01918    /* Perform any pending masquerades */
01919    for (x=0; x < n; x++) {
01920       ast_channel_lock(c[x]);
01921       if (c[x]->masq) {
01922          if (ast_do_masquerade(c[x])) {
01923             ast_log(LOG_WARNING, "Masquerade failed\n");
01924             *ms = -1;
01925             ast_channel_unlock(c[x]);
01926             return NULL;
01927          }
01928       }
01929       if (c[x]->whentohangup) {
01930          if (!whentohangup)
01931             time(&now);
01932          diff = c[x]->whentohangup - now;
01933          if (diff < 1) {
01934             /* Should already be hungup */
01935             c[x]->_softhangup |= AST_SOFTHANGUP_TIMEOUT;
01936             ast_channel_unlock(c[x]);
01937             return c[x];
01938          }
01939          if (!whentohangup || (diff < whentohangup))
01940             whentohangup = diff;
01941       }
01942       ast_channel_unlock(c[x]);
01943    }
01944    /* Wait full interval */
01945    rms = *ms;
01946    if (whentohangup) {
01947       rms = whentohangup * 1000;              /* timeout in milliseconds */
01948       if (*ms >= 0 && *ms < rms)    /* original *ms still smaller */
01949          rms =  *ms;
01950    }
01951    /*
01952     * Build the pollfd array, putting the channels' fds first,
01953     * followed by individual fds. Order is important because
01954     * individual fd's must have priority over channel fds.
01955     */
01956    max = 0;
01957    for (x=0; x<n; x++) {
01958       for (y=0; y<AST_MAX_FDS; y++) {
01959          fdmap[max].fdno = y;  /* fd y is linked to this pfds */
01960          fdmap[max].chan = x;  /* channel x is linked to this pfds */
01961          max += ast_add_fd(&pfds[max], c[x]->fds[y]);
01962       }
01963       CHECK_BLOCKING(c[x]);
01964    }
01965    /* Add the individual fds */
01966    for (x=0; x<nfds; x++) {
01967       fdmap[max].chan = -1;
01968       max += ast_add_fd(&pfds[max], fds[x]);
01969    }
01970 
01971    if (*ms > 0)
01972       start = ast_tvnow();
01973    
01974    if (sizeof(int) == 4) { /* XXX fix timeout > 600000 on linux x86-32 */
01975       do {
01976          int kbrms = rms;
01977          if (kbrms > 600000)
01978             kbrms = 600000;
01979          res = poll(pfds, max, kbrms);
01980          if (!res)
01981             rms -= kbrms;
01982       } while (!res && (rms > 0));
01983    } else {
01984       res = poll(pfds, max, rms);
01985    }
01986    for (x=0; x<n; x++)
01987       ast_clear_flag(c[x], AST_FLAG_BLOCKING);
01988    if (res < 0) { /* Simulate a timeout if we were interrupted */
01989       if (errno != EINTR)
01990          *ms = -1;
01991       return NULL;
01992    }
01993    if (whentohangup) {   /* if we have a timeout, check who expired */
01994       time(&now);
01995       for (x=0; x<n; x++) {
01996          if (c[x]->whentohangup && now >= c[x]->whentohangup) {
01997             c[x]->_softhangup |= AST_SOFTHANGUP_TIMEOUT;
01998             if (winner == NULL)
01999                winner = c[x];
02000          }
02001       }
02002    }
02003    if (res == 0) { /* no fd ready, reset timeout and done */
02004       *ms = 0; /* XXX use 0 since we may not have an exact timeout. */
02005       return winner;
02006    }
02007    /*
02008     * Then check if any channel or fd has a pending event.
02009     * Remember to check channels first and fds last, as they
02010     * must have priority on setting 'winner'
02011     */
02012    for (x = 0; x < max; x++) {
02013       res = pfds[x].revents;
02014       if (res == 0)
02015          continue;
02016       if (fdmap[x].chan >= 0) {  /* this is a channel */
02017          winner = c[fdmap[x].chan]; /* override previous winners */
02018          if (res & POLLPRI)
02019             ast_set_flag(winner, AST_FLAG_EXCEPTION);
02020          else
02021             ast_clear_flag(winner, AST_FLAG_EXCEPTION);
02022          winner->fdno = fdmap[x].fdno;
02023       } else {       /* this is an fd */
02024          if (outfd)
02025             *outfd = pfds[x].fd;
02026          if (exception)
02027             *exception = (res & POLLPRI) ? -1 : 0;
02028          winner = NULL;
02029       }
02030    }
02031    if (*ms > 0) {
02032       *ms -= ast_tvdiff_ms(ast_tvnow(), start);
02033       if (*ms < 0)
02034          *ms = 0;
02035    }
02036    return winner;
02037 }

int ast_waitfordigit ( struct ast_channel c,
int  ms 
)

Waits for a digit.

!

Parameters:
c channel to wait for a digit on
ms how many milliseconds to wait
Returns:
Returns <0 on error, 0 on no entry, and the digit on success.

Definition at line 2055 of file channel.c.

References ast_waitfordigit_full().

Referenced by _while_exec(), advanced_options(), ast_adsi_get_cpeid(), ast_adsi_get_cpeinfo(), ast_adsi_print(), ast_adsi_read_encoded_dtmf(), ast_adsi_transmit_message_full(), 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_mailbox_owner(), play_record_review(), read_exec(), read_newoption(), retrydial_exec(), sendnoise(), ss_thread(), test1_client(), test1_server(), vm_execmain(), vm_forwardoptions(), vm_instructions(), vm_options(), vm_tempgreeting(), wait_a_bit(), and wait_our_turn().

02056 {
02057    return ast_waitfordigit_full(c, ms, -1, -1);
02058 }

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.

Parameters:
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
Returns:
Returns 1 if ctrlfd becomes available

Definition at line 2079 of file channel.c.

References ast_check_hangup(), AST_CONTROL_ANSWER, AST_CONTROL_HANGUP, AST_CONTROL_RINGING, AST_FLAG_ZOMBIE, AST_FRAME_CONTROL, AST_FRAME_DTMF_BEGIN, AST_FRAME_DTMF_END, AST_FRAME_VOICE, ast_frfree(), ast_log(), ast_read(), ast_test_flag, ast_waitfor_nandfds(), f, and LOG_WARNING.

Referenced by ast_readstring_full(), ast_waitfordigit(), handle_getoption(), and handle_waitfordigit().

02080 {
02081    int begin_digit = 0;
02082 
02083    /* Stop if we're a zombie or need a soft hangup */
02084    if (ast_test_flag(c, AST_FLAG_ZOMBIE) || ast_check_hangup(c))
02085       return -1;
02086    /* Wait for a digit, no more than ms milliseconds total. */
02087    while (ms) {
02088       struct ast_channel *rchan;
02089       int outfd;
02090 
02091       errno = 0;
02092       rchan = ast_waitfor_nandfds(&c, 1, &cmdfd, (cmdfd > -1) ? 1 : 0, NULL, &outfd, &ms);
02093       if (!rchan && outfd < 0 && ms) {
02094          if (errno == 0 || errno == EINTR)
02095             continue;
02096          ast_log(LOG_WARNING, "Wait failed (%s)\n", strerror(errno));
02097          return -1;
02098       } else if (outfd > -1) {
02099          /* The FD we were watching has something waiting */
02100          return 1;
02101       } else if (rchan) {
02102          int res;
02103          struct ast_frame *f = ast_read(c);
02104          if (!f)
02105             return -1;
02106 
02107          switch(f->frametype) {
02108          case AST_FRAME_DTMF_BEGIN:
02109             begin_digit = f->subclass;
02110             break;
02111          case AST_FRAME_DTMF_END:
02112             if (begin_digit != f->subclass)
02113                break;
02114             res = f->subclass;
02115             ast_frfree(f);
02116             return res;
02117          case AST_FRAME_CONTROL:
02118             switch(f->subclass) {
02119             case AST_CONTROL_HANGUP:
02120                ast_frfree(f);
02121                return -1;
02122             case AST_CONTROL_RINGING:
02123             case AST_CONTROL_ANSWER:
02124                /* Unimportant */
02125                break;
02126             default:
02127                ast_log(LOG_WARNING, "Unexpected control subclass '%d'\n", f->subclass);
02128                break;
02129             }
02130             break;
02131          case AST_FRAME_VOICE:
02132             /* Write audio if appropriate */
02133             if (audiofd > -1)
02134                write(audiofd, f->data, f->datalen);
02135          default:
02136             /* Ignore */
02137             break;
02138          }
02139          ast_frfree(f);
02140       }
02141    }
02142    return 0; /* Time is up */
02143 }

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.

Definition at line 1140 of file channel.c.

References channel_find_locked().

Referenced by next_channel().

01142 {
01143    return channel_find_locked(chan, NULL, 0, context, exten);
01144 }

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 prefix (locks channel).

Definition at line 1127 of file channel.c.

References channel_find_locked().

Referenced by next_channel().

01129 {
01130    return channel_find_locked(chan, name, namelen, NULL, NULL);
01131 }

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.

Parameters:
chan destination channel of the frame
frame frame that will be written
Returns:
It returns 0 on success, -1 on failure.

Todo:
XXX should return 0 maybe ?

Definition at line 2768 of file channel.c.

References ast_channel::_softhangup, ast_channel_lock, ast_channel_unlock, ast_check_hangup(), ast_clear_flag, AST_CONTROL_UNHOLD, ast_deactivate_generator(), ast_do_masquerade(), AST_FLAG_BLOCKING, AST_FLAG_WHISPER, AST_FLAG_WRITE_INT, AST_FLAG_ZOMBIE, AST_FORMAT_SLINEAR, ast_frame_adjust_volume(), 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_slinear_sum(), AST_FRAME_TEXT, AST_FRAME_VIDEO, AST_FRAME_VOICE, ast_frfree(), ast_log(), AST_MONITOR_RUNNING, ast_mutex_lock(), ast_mutex_unlock(), ast_seekstream(), ast_senddigit_begin(), ast_senddigit_end(), ast_set_write_format(), ast_slinfactory_available(), ast_slinfactory_read(), AST_SOFTHANGUP_DEV, ast_test_flag, ast_translate(), ast_translator_build_path(), ast_translator_free_path(), ast_writestream(), CHECK_BLOCKING, ast_frame::data, ast_frame::datalen, DEBUGCHAN_FLAG, f, ast_channel::fout, FRAMECOUNT_INC, ast_frame::frametype, ast_channel::generatordata, ast_channel_tech::indicate, ast_channel::insmpl, ast_frame::len, ast_channel_whisper_buffer::lock, LOG_WARNING, ast_channel::masq, ast_channel::masqr, ast_channel::monitor, MONITOR_DELAY, ast_channel_whisper_buffer::original_format, ast_channel::outsmpl, ast_channel_whisper_buffer::path, queue_frame_to_spies(), ast_channel::rawwriteformat, SEEK_FORCECUR, ast_channel_tech::send_html, ast_channel_tech::send_text, ast_channel_whisper_buffer::sf, ast_channel::spies, SPY_WRITE, ast_channel_monitor::state, ast_frame::subclass, ast_channel::tech, ast_channel::whisper, ast_channel_tech::write, ast_channel_monitor::write_stream, ast_channel_tech::write_video, ast_channel::writeformat, and ast_channel::writetrans.

Referenced by adsi_careful_send(), agent_write(), 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(), dictate_exec(), echo_exec(), features_write(), function_ilink(), gen_generate(), handle_link_data(), jb_get_and_deliver(), linear_generator(), milliwatt_generate(), misdn_bridge(), moh_files_generator(), moh_generate(), mp3_exec(), mwanalyze_exec(), NBScat_exec(), rpt(), rxfax_exec(), send_link_dtmf(), send_tone_burst(), send_waveform_to_channel(), silence_generator_generate(), spy_generate(), txfax_exec(), wait_for_answer(), and zt_bridge().

02769 {
02770    int res = -1;
02771    struct ast_frame *f = NULL;
02772 
02773    /* Stop if we're a zombie or need a soft hangup */
02774    ast_channel_lock(chan);
02775    if (ast_test_flag(chan, AST_FLAG_ZOMBIE) || ast_check_hangup(chan))
02776       goto done;
02777 
02778    /* Handle any pending masquerades */
02779    if (chan->masq && ast_do_masquerade(chan)) {
02780       ast_log(LOG_WARNING, "Failed to perform masquerade\n");
02781       goto done;
02782    }
02783    if (chan->masqr) {
02784       res = 0; /* XXX explain, why 0 ? */
02785       goto done;
02786    }
02787    if (chan->generatordata) {
02788       if (ast_test_flag(chan, AST_FLAG_WRITE_INT))
02789          ast_deactivate_generator(chan);
02790       else {
02791          if (fr->frametype == AST_FRAME_DTMF_END) {
02792             /* There is a generator running while we're in the middle of a digit.
02793              * It's probably inband DTMF, so go ahead and pass it so it can
02794              * stop the generator */
02795             ast_clear_flag(chan, AST_FLAG_BLOCKING);
02796             ast_channel_unlock(chan);
02797             res = ast_senddigit_end(chan, fr->subclass, fr->len);
02798             ast_channel_lock(chan);
02799             CHECK_BLOCKING(chan);
02800          } else if (fr->frametype == AST_FRAME_CONTROL && fr->subclass == AST_CONTROL_UNHOLD) {
02801             /* This is a side case where Echo is basically being called and the person put themselves on hold and took themselves off hold */
02802             res = (chan->tech->indicate == NULL) ? 0 :
02803                chan->tech->indicate(chan, fr->subclass, fr->data, fr->datalen);
02804          }
02805          res = 0; /* XXX explain, why 0 ? */
02806          goto done;
02807       }
02808    }
02809    /* High bit prints debugging */
02810    if (chan->fout & DEBUGCHAN_FLAG)
02811       ast_frame_dump(chan->name, fr, ">>");
02812    CHECK_BLOCKING(chan);
02813    switch(fr->frametype) {
02814    case AST_FRAME_CONTROL:
02815       res = (chan->tech->indicate == NULL) ? 0 :
02816          chan->tech->indicate(chan, fr->subclass, fr->data, fr->datalen);
02817       break;
02818    case AST_FRAME_DTMF_BEGIN:
02819       ast_clear_flag(chan, AST_FLAG_BLOCKING);
02820       ast_channel_unlock(chan);
02821       res = ast_senddigit_begin(chan, fr->subclass);
02822       ast_channel_lock(chan);
02823       CHECK_BLOCKING(chan);
02824       break;
02825    case AST_FRAME_DTMF_END:
02826       ast_clear_flag(chan, AST_FLAG_BLOCKING);
02827       ast_channel_unlock(chan);
02828       res = ast_senddigit_end(chan, fr->subclass, fr->len);
02829       ast_channel_lock(chan);
02830       CHECK_BLOCKING(chan);
02831       break;
02832    case AST_FRAME_TEXT:
02833       res = (chan->tech->send_text == NULL) ? 0 :
02834          chan->tech->send_text(chan, (char *) fr->data);
02835       break;
02836    case AST_FRAME_HTML:
02837       res = (chan->tech->send_html == NULL) ? 0 :
02838          chan->tech->send_html(chan, fr->subclass, (char *) fr->data, fr->datalen);
02839       break;
02840    case AST_FRAME_VIDEO:
02841       /* XXX Handle translation of video codecs one day XXX */
02842       res = (chan->tech->write_video == NULL) ? 0 :
02843          chan->tech->write_video(chan, fr);
02844       break;
02845    case AST_FRAME_MODEM:
02846       res = (chan->tech->write == NULL) ? 0 :
02847          chan->tech->write(chan, fr);
02848       break;
02849    case AST_FRAME_VOICE:
02850       if (chan->tech->write == NULL)
02851          break;   /*! \todo XXX should return 0 maybe ? */
02852 
02853       /* If someone is whispering on this channel then we must ensure that we are always getting signed linear frames */
02854       if (ast_test_flag(chan, AST_FLAG_WHISPER)) {
02855          if (fr->subclass == AST_FORMAT_SLINEAR)
02856             f = fr;
02857          else {
02858             ast_mutex_lock(&chan->whisper->lock);
02859             if (chan->writeformat != AST_FORMAT_SLINEAR) {
02860                /* Rebuild the translation path and set our write format back to signed linear */
02861                chan->whisper->original_format = chan->writeformat;
02862                ast_set_write_format(chan, AST_FORMAT_SLINEAR);
02863                if (chan->whisper->path)
02864                   ast_translator_free_path(chan->whisper->path);
02865                chan->whisper->path = ast_translator_build_path(AST_FORMAT_SLINEAR, chan->whisper->original_format);
02866             }
02867             /* Translate frame using the above translation path */
02868             f = (chan->whisper->path) ? ast_translate(chan->whisper->path, fr, 0) : fr;
02869             ast_mutex_unlock(&chan->whisper->lock);
02870          }
02871       } else {
02872          /* If the frame is in the raw write format, then it's easy... just use the frame - otherwise we will have to translate */
02873          if (fr->subclass == chan->rawwriteformat)
02874             f = fr;
02875          else
02876             f = (chan->writetrans) ? ast_translate(chan->writetrans, fr, 0) : fr;
02877       }
02878 
02879       /* If we have no frame of audio, then we have to bail out */
02880       if (f == NULL) {
02881          res = 0;
02882          break;
02883       }
02884 
02885       /* If spies are on the channel then queue the frame out to them */
02886       if (chan->spies)
02887          queue_frame_to_spies(chan, f, SPY_WRITE);
02888 
02889       /* If Monitor is running on this channel, then we have to write frames out there too */
02890       if (chan->monitor && chan->monitor->write_stream) {
02891          /* XXX must explain this code */
02892 #ifndef MONITOR_CONSTANT_DELAY
02893          int jump = chan->insmpl - chan->outsmpl - 4 * f->samples;
02894          if (jump >= 0) {
02895             jump = chan->insmpl - chan->outsmpl;
02896             if (ast_seekstream(chan->monitor->write_stream, jump, SEEK_FORCECUR) == -1)
02897                ast_log(LOG_WARNING, "Failed to perform seek in monitoring write stream, synchronization between the files may be broken\n");
02898             chan->outsmpl += jump + f->samples;
02899          } else
02900             chan->outsmpl += f->samples;
02901 #else
02902          int jump = chan->insmpl - chan->outsmpl;
02903          if (jump - MONITOR_DELAY >= 0) {
02904             if (ast_seekstream(chan->monitor->write_stream, jump - f->samples, SEEK_FORCECUR) == -1)
02905                ast_log(LOG_WARNING, "Failed to perform seek in monitoring write stream, synchronization between the files may be broken\n");
02906             chan->outsmpl += jump;
02907          } else
02908             chan->outsmpl += f->samples;
02909 #endif
02910          if (chan->monitor->state == AST_MONITOR_RUNNING) {
02911             if (ast_writestream(chan->monitor->write_stream, f) < 0)
02912                ast_log(LOG_WARNING, "Failed to write data to channel monitor write stream\n");
02913          }
02914       }
02915 
02916       /* Finally the good part! Write this out to the channel */
02917       if (ast_test_flag(chan, AST_FLAG_WHISPER)) {
02918          /* frame is assumed to be in SLINEAR, since that is
02919             required for whisper mode */
02920          ast_frame_adjust_volume(f, -2);
02921          if (ast_slinfactory_available(&chan->whisper->sf) >= f->samples) {
02922             short buf[f->samples];
02923             struct ast_frame whisper = {
02924                .frametype = AST_FRAME_VOICE,
02925                .subclass = AST_FORMAT_SLINEAR,
02926                .data = buf,
02927                .datalen = sizeof(buf),
02928                .samples = f->samples,
02929             };
02930             
02931             ast_mutex_lock(&chan->whisper->lock);
02932             if (ast_slinfactory_read(&chan->whisper->sf, buf, f->samples))
02933                ast_frame_slinear_sum(f, &whisper);
02934             ast_mutex_unlock(&chan->whisper->lock);
02935          }
02936          /* and now put it through the regular translator */
02937          f = (chan->writetrans) ? ast_translate(chan->writetrans, f, 0) : f;
02938       }
02939       if (f)
02940          res = chan->tech->write(chan, f);
02941       else
02942          res = 0;
02943       break;
02944    case AST_FRAME_NULL:
02945    case AST_FRAME_IAX:
02946       /* Ignore these */
02947       res = 0;
02948       break;
02949    default:
02950       /* At this point, fr is the incoming frame and f is NULL.  Channels do
02951        * not expect to get NULL as a frame pointer and will segfault.  Hence,
02952        * we output the original frame passed in. */
02953       res = chan->tech->write(chan, fr);
02954       break;
02955    }
02956 
02957    if (f && f != fr)
02958       ast_frfree(f);
02959    ast_clear_flag(chan, AST_FLAG_BLOCKING);
02960    /* Consider a write failure to force a soft hangup */
02961    if (res < 0)
02962       chan->_softhangup |= AST_SOFTHANGUP_DEV;
02963    else {
02964       chan->fout = FRAMECOUNT_INC(chan->fout);
02965    }
02966 done:
02967    ast_channel_unlock(chan);
02968    return res;
02969 }

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.

Parameters:
chan destination channel of the frame
frame frame that will be written
Returns:
It returns 1 on success, 0 if not implemented, and -1 on failure.

Definition at line 2757 of file channel.c.

References ast_write(), ast_channel::tech, and ast_channel_tech::write_video.

02758 {
02759    int res;
02760    if (!chan->tech->write_video)
02761       return 0;
02762    res = ast_write(chan, fr);
02763    if (!res)
02764       res = 1;
02765    return res;
02766 }

const char* channelreloadreason2txt ( enum channelreloadreason  reason  ) 

Convert enum channelreloadreason to text string for manager event.

\ brief Convert channel reloadreason (ENUM) to text string for manager event

Definition at line 4833 of file channel.c.

References CHANNEL_CLI_RELOAD, CHANNEL_MODULE_LOAD, and CHANNEL_MODULE_RELOAD.

04834 {
04835    switch (reason) {
04836    case CHANNEL_MODULE_LOAD:
04837       return "LOAD (Channel module load)";
04838 
04839    case CHANNEL_MODULE_RELOAD:
04840       return "RELOAD (Channel module reload)";
04841 
04842    case CHANNEL_CLI_RELOAD:
04843       return "CLIRELOAD (Channel module reload by CLI command)";
04844 
04845    default:
04846       return "MANAGERRELOAD (Channel module reload by manager)";
04847    }
04848 };


Generated on Fri Aug 24 02:24:25 2007 for Asterisk - the Open Source PBX by  doxygen 1.5.1