87551f72f3ace1501a42b56d1bfa756a24cd644a
[asterisk/asterisk.git] / main / channel_internal_api.c
1 /*
2  * Asterisk -- An open source telephony toolkit.
3  *
4  * Copyright (C) 2012, Digium, Inc.
5  *
6  * Mark Spencer <markster@digium.com>
7  *
8  * See http://www.asterisk.org for more information about
9  * the Asterisk project. Please do not directly contact
10  * any of the maintainers of this project for assistance;
11  * the project provides a web site, mailing lists and IRC
12  * channels for your use.
13  *
14  * This program is free software, distributed under the terms of
15  * the GNU General Public License Version 2. See the LICENSE file
16  * at the top of the source tree.
17  */
18
19 /*! \file
20  *
21  * \brief Channel Accessor API
22  *
23  * This file is intended to be the only file that ever accesses the
24  * internals of an ast_channel. All other files should use the
25  * accessor functions defined here.
26  *
27  * \author Terry Wilson
28  */
29
30 /*** MODULEINFO
31         <support_level>core</support_level>
32  ***/
33
34 #include "asterisk.h"
35
36 ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
37
38 #include <unistd.h>
39 #include <fcntl.h>
40
41 #include "asterisk/channel.h"
42 #include "asterisk/channel_internal.h"
43 #include "asterisk/data.h"
44 #include "asterisk/endpoints.h"
45 #include "asterisk/indications.h"
46 #include "asterisk/stasis_channels.h"
47 #include "asterisk/stasis_endpoints.h"
48 #include "asterisk/stringfields.h"
49 #include "asterisk/test.h"
50
51 /*!
52  * \brief Main Channel structure associated with a channel.
53  *
54  * \note When adding fields to this structure, it is important to add the field
55  *       'in position' with like-aligned fields, so as to keep the compiler from
56  *       having to add padding to align fields. The structure's fields are sorted
57  *       in this order: pointers, structures, long, int/enum, short, char. This
58  *       is especially important on 64-bit architectures, where mixing 4-byte
59  *       and 8-byte fields causes 4 bytes of padding to be added before many
60  *       8-byte fields.
61  */
62 struct ast_channel {
63         const struct ast_channel_tech *tech;            /*!< Technology (point to channel driver) */
64         void *tech_pvt;                                 /*!< Private data used by the technology driver */
65         void *music_state;                              /*!< Music State*/
66         void *generatordata;                            /*!< Current generator data if there is any */
67         struct ast_generator *generator;                /*!< Current active data generator */
68 /* BUGBUG bridged_channel must be eliminated from ast_channel */
69         struct ast_channel * bridged_channel;                   /*!< Who are we bridged to, if we're bridged.
70                                                          *   Who is proxying for us, if we are proxied (i.e. chan_agent).
71                                                          *   Do not access directly, use ast_bridged_channel(chan) */
72         struct ast_channel *masq;                       /*!< Channel that will masquerade as us */
73         struct ast_channel *masqr;                      /*!< Who we are masquerading as */
74         const char *blockproc;                          /*!< Procedure causing blocking */
75         const char *appl;                               /*!< Current application */
76         const char *data;                               /*!< Data passed to current application */
77         struct ast_sched_context *sched;                /*!< Schedule context */
78         struct ast_filestream *stream;                  /*!< Stream itself. */
79         struct ast_filestream *vstream;                 /*!< Video Stream itself. */
80         ast_timing_func_t timingfunc;
81         void *timingdata;
82         struct ast_pbx *pbx;                            /*!< PBX private structure for this channel */
83         struct ast_trans_pvt *writetrans;               /*!< Write translation path */
84         struct ast_trans_pvt *readtrans;                /*!< Read translation path */
85         struct ast_audiohook_list *audiohooks;
86         struct ast_framehook_list *framehooks;
87         struct ast_cdr *cdr;                            /*!< Call Detail Record */
88         struct ast_tone_zone *zone;                     /*!< Tone zone as set in indications.conf or
89                                                          *   in the CHANNEL dialplan function */
90         struct ast_channel_monitor *monitor;            /*!< Channel monitoring */
91         struct ast_callid *callid;                      /*!< Bound call identifier pointer */
92 #ifdef HAVE_EPOLL
93         struct ast_epoll_data *epfd_data[AST_MAX_FDS];
94 #endif
95         struct ao2_container *dialed_causes;            /*!< Contains tech-specific and Asterisk cause data from dialed channels */
96
97         AST_DECLARE_STRING_FIELDS(
98                 AST_STRING_FIELD(name);         /*!< ASCII unique channel name */
99                 AST_STRING_FIELD(language);     /*!< Language requested for voice prompts */
100                 AST_STRING_FIELD(musicclass);   /*!< Default music class */
101                 AST_STRING_FIELD(accountcode);  /*!< Account code for billing */
102                 AST_STRING_FIELD(peeraccount);  /*!< Peer account code for billing */
103                 AST_STRING_FIELD(userfield);    /*!< Userfield for CEL billing */
104                 AST_STRING_FIELD(call_forward); /*!< Where to forward to if asked to dial on this interface */
105                 AST_STRING_FIELD(uniqueid);     /*!< Unique Channel Identifier */
106                 AST_STRING_FIELD(linkedid);     /*!< Linked Channel Identifier -- gets propagated by linkage */
107                 AST_STRING_FIELD(parkinglot);   /*! Default parking lot, if empty, default parking lot  */
108                 AST_STRING_FIELD(hangupsource); /*! Who is responsible for hanging up this channel */
109                 AST_STRING_FIELD(dialcontext);  /*!< Dial: Extension context that we were called from */
110         );
111
112         struct timeval whentohangup; /*!< Non-zero, set to actual time when channel is to be hung up */
113         pthread_t blocker;           /*!< If anyone is blocking, this is them */
114
115         /*!
116          * \brief Dialed/Called information.
117          * \note Set on incoming channels to indicate the originally dialed party.
118          * \note Dialed Number Identifier (DNID)
119          */
120         struct ast_party_dialed dialed;
121
122         /*!
123          * \brief Channel Caller ID information.
124          * \note The caller id information is the caller id of this
125          * channel when it is used to initiate a call.
126          */
127         struct ast_party_caller caller;
128
129         /*!
130          * \brief Channel Connected Line ID information.
131          * \note The connected line information identifies the channel
132          * connected/bridged to this channel.
133          */
134         struct ast_party_connected_line connected;
135
136         /*! \brief Redirecting/Diversion information */
137         struct ast_party_redirecting redirecting;
138
139         struct ast_frame dtmff;                         /*!< DTMF frame */
140         struct varshead varshead;                       /*!< A linked list for channel variables. See \ref AstChanVar */
141         ast_group_t callgroup;                          /*!< Call group for call pickups */
142         ast_group_t pickupgroup;                        /*!< Pickup group - which calls groups can be picked up? */
143         struct ast_namedgroups *named_callgroups;       /*!< Named call group for call pickups */
144         struct ast_namedgroups *named_pickupgroups;     /*!< Named pickup group - which call groups can be picked up? */
145         struct timeval creationtime;                    /*!< The time of channel creation */
146         struct ast_readq_list readq;
147         struct ast_jb jb;                               /*!< The jitterbuffer state */
148         struct timeval dtmf_tv;                         /*!< The time that an in process digit began, or the last digit ended */
149         struct ast_hangup_handler_list hangup_handlers;/*!< Hangup handlers on the channel. */
150         struct ast_datastore_list datastores; /*!< Data stores on the channel */
151         struct ast_autochan_list autochans; /*!< Autochans on the channel */
152         unsigned long insmpl;                           /*!< Track the read/written samples for monitor use */
153         unsigned long outsmpl;                          /*!< Track the read/written samples for monitor use */
154
155         int fds[AST_MAX_FDS];                           /*!< File descriptors for channel -- Drivers will poll on
156                                                          *   these file descriptors, so at least one must be non -1.
157                                                          *   See \arg \ref AstFileDesc */
158         int softhangup;                         /*!< Whether or not we have been hung up...  Do not set this value
159                                                          *   directly, use ast_softhangup() */
160         int fdno;                                       /*!< Which fd had an event detected on */
161         int streamid;                                   /*!< For streaming playback, the schedule ID */
162         int vstreamid;                                  /*!< For streaming video playback, the schedule ID */
163         struct ast_format oldwriteformat;  /*!< Original writer format */
164         int timingfd;                                   /*!< Timing fd */
165         enum ast_channel_state state;                   /*!< State of line -- Don't write directly, use ast_setstate() */
166         int rings;                                      /*!< Number of rings so far */
167         int priority;                                   /*!< Dialplan: Current extension priority */
168         int macropriority;                              /*!< Macro: Current non-macro priority. See app_macro.c */
169         int amaflags;                                   /*!< Set BEFORE PBX is started to determine AMA flags */
170         enum ast_channel_adsicpe adsicpe;               /*!< Whether or not ADSI is detected on CPE */
171         unsigned int fin;                               /*!< Frames in counters. The high bit is a debug mask, so
172                                                          *   the counter is only in the remaining bits */
173         unsigned int fout;                              /*!< Frames out counters. The high bit is a debug mask, so
174                                                          *   the counter is only in the remaining bits */
175         int hangupcause;                                /*!< Why is the channel hanged up. See causes.h */
176         unsigned int finalized:1;       /*!< Whether or not the channel has been successfully allocated */
177         struct ast_flags flags;                         /*!< channel flags of AST_FLAG_ type */
178         int alertpipe[2];
179         struct ast_format_cap *nativeformats;         /*!< Kinds of data this channel can natively handle */
180         struct ast_format readformat;            /*!< Requested read format (after translation) */
181         struct ast_format writeformat;           /*!< Requested write format (after translation) */
182         struct ast_format rawreadformat;         /*!< Raw read format (before translation) */
183         struct ast_format rawwriteformat;        /*!< Raw write format (before translation) */
184         unsigned int emulate_dtmf_duration;             /*!< Number of ms left to emulate DTMF for */
185 #ifdef HAVE_EPOLL
186         int epfd;
187 #endif
188         int visible_indication;                         /*!< Indication currently playing on the channel */
189
190         unsigned short transfercapability;              /*!< ISDN Transfer Capability - AST_FLAG_DIGITAL is not enough */
191
192 /* BUGBUG the bridge pointer must change to an ast_channel_bridge pointer because it will never change while the channel is in the bridging system whereas the bridge could change. */
193         struct ast_bridge *bridge;                      /*!< Bridge this channel is participating in */
194         struct ast_bridge_channel *bridge_channel;/*!< The bridge_channel this channel is linked with. */
195         struct ast_timer *timer;                        /*!< timer object that provided timingfd */
196
197         char context[AST_MAX_CONTEXT];                  /*!< Dialplan: Current extension context */
198         char exten[AST_MAX_EXTENSION];                  /*!< Dialplan: Current extension number */
199         char macrocontext[AST_MAX_CONTEXT];             /*!< Macro: Current non-macro context. See app_macro.c */
200         char macroexten[AST_MAX_EXTENSION];             /*!< Macro: Current non-macro extension. See app_macro.c */
201         char dtmf_digit_to_emulate;                     /*!< Digit being emulated */
202         char sending_dtmf_digit;                        /*!< Digit this channel is currently sending out. (zero if not sending) */
203         struct timeval sending_dtmf_tv;         /*!< The time this channel started sending the current digit. (Invalid if sending_dtmf_digit is zero.) */
204         struct stasis_topic *topic;                     /*!< Topic for all channel's events */
205         struct stasis_subscription *forwarder;          /*!< Subscription for event forwarding to all topic */
206         struct stasis_subscription *endpoint_forward;   /*!< Subscription for event forwarding to endpoint's topic */
207 };
208
209 /* AST_DATA definitions, which will probably have to be re-thought since the channel will be opaque */
210
211 #if 0   /* XXX AstData: ast_callerid no longer exists. (Equivalent code not readily apparent.) */
212 #define DATA_EXPORT_CALLERID(MEMBER)                            \
213         MEMBER(ast_callerid, cid_dnid, AST_DATA_STRING)         \
214         MEMBER(ast_callerid, cid_num, AST_DATA_STRING)          \
215         MEMBER(ast_callerid, cid_name, AST_DATA_STRING)         \
216         MEMBER(ast_callerid, cid_ani, AST_DATA_STRING)          \
217         MEMBER(ast_callerid, cid_pres, AST_DATA_INTEGER)        \
218         MEMBER(ast_callerid, cid_ani2, AST_DATA_INTEGER)        \
219         MEMBER(ast_callerid, cid_tag, AST_DATA_STRING)
220
221 AST_DATA_STRUCTURE(ast_callerid, DATA_EXPORT_CALLERID);
222 #endif
223
224 #define DATA_EXPORT_CHANNEL(MEMBER)                                             \
225         MEMBER(ast_channel, blockproc, AST_DATA_STRING)                         \
226         MEMBER(ast_channel, appl, AST_DATA_STRING)                              \
227         MEMBER(ast_channel, data, AST_DATA_STRING)                              \
228         MEMBER(ast_channel, name, AST_DATA_STRING) \
229         MEMBER(ast_channel, language, AST_DATA_STRING)                          \
230         MEMBER(ast_channel, musicclass, AST_DATA_STRING)                        \
231         MEMBER(ast_channel, accountcode, AST_DATA_STRING)                       \
232         MEMBER(ast_channel, peeraccount, AST_DATA_STRING)                       \
233         MEMBER(ast_channel, userfield, AST_DATA_STRING)                         \
234         MEMBER(ast_channel, call_forward, AST_DATA_STRING)                      \
235         MEMBER(ast_channel, uniqueid, AST_DATA_STRING)                          \
236         MEMBER(ast_channel, linkedid, AST_DATA_STRING)                          \
237         MEMBER(ast_channel, parkinglot, AST_DATA_STRING)                        \
238         MEMBER(ast_channel, hangupsource, AST_DATA_STRING)                      \
239         MEMBER(ast_channel, dialcontext, AST_DATA_STRING)                       \
240         MEMBER(ast_channel, rings, AST_DATA_INTEGER)                            \
241         MEMBER(ast_channel, priority, AST_DATA_INTEGER)                         \
242         MEMBER(ast_channel, macropriority, AST_DATA_INTEGER)                    \
243         MEMBER(ast_channel, adsicpe, AST_DATA_INTEGER)                          \
244         MEMBER(ast_channel, fin, AST_DATA_UNSIGNED_INTEGER)                     \
245         MEMBER(ast_channel, fout, AST_DATA_UNSIGNED_INTEGER)                    \
246         MEMBER(ast_channel, emulate_dtmf_duration, AST_DATA_UNSIGNED_INTEGER)   \
247         MEMBER(ast_channel, visible_indication, AST_DATA_INTEGER)               \
248         MEMBER(ast_channel, context, AST_DATA_STRING)                           \
249         MEMBER(ast_channel, exten, AST_DATA_STRING)                             \
250         MEMBER(ast_channel, macrocontext, AST_DATA_STRING)                      \
251         MEMBER(ast_channel, macroexten, AST_DATA_STRING)
252
253 AST_DATA_STRUCTURE(ast_channel, DATA_EXPORT_CHANNEL);
254
255 static void channel_data_add_flags(struct ast_data *tree,
256         struct ast_channel *chan)
257 {
258         ast_data_add_bool(tree, "DEFER_DTMF", ast_test_flag(ast_channel_flags(chan), AST_FLAG_DEFER_DTMF));
259         ast_data_add_bool(tree, "WRITE_INT", ast_test_flag(ast_channel_flags(chan), AST_FLAG_WRITE_INT));
260         ast_data_add_bool(tree, "BLOCKING", ast_test_flag(ast_channel_flags(chan), AST_FLAG_BLOCKING));
261         ast_data_add_bool(tree, "ZOMBIE", ast_test_flag(ast_channel_flags(chan), AST_FLAG_ZOMBIE));
262         ast_data_add_bool(tree, "EXCEPTION", ast_test_flag(ast_channel_flags(chan), AST_FLAG_EXCEPTION));
263         ast_data_add_bool(tree, "MOH", ast_test_flag(ast_channel_flags(chan), AST_FLAG_MOH));
264         ast_data_add_bool(tree, "SPYING", ast_test_flag(ast_channel_flags(chan), AST_FLAG_SPYING));
265         ast_data_add_bool(tree, "NBRIDGE", ast_test_flag(ast_channel_flags(chan), AST_FLAG_NBRIDGE));
266         ast_data_add_bool(tree, "IN_AUTOLOOP", ast_test_flag(ast_channel_flags(chan), AST_FLAG_IN_AUTOLOOP));
267         ast_data_add_bool(tree, "OUTGOING", ast_test_flag(ast_channel_flags(chan), AST_FLAG_OUTGOING));
268         ast_data_add_bool(tree, "IN_DTMF", ast_test_flag(ast_channel_flags(chan), AST_FLAG_IN_DTMF));
269         ast_data_add_bool(tree, "EMULATE_DTMF", ast_test_flag(ast_channel_flags(chan), AST_FLAG_EMULATE_DTMF));
270         ast_data_add_bool(tree, "END_DTMF_ONLY", ast_test_flag(ast_channel_flags(chan), AST_FLAG_END_DTMF_ONLY));
271         ast_data_add_bool(tree, "MASQ_NOSTREAM", ast_test_flag(ast_channel_flags(chan), AST_FLAG_MASQ_NOSTREAM));
272         ast_data_add_bool(tree, "BRIDGE_HANGUP_RUN", ast_test_flag(ast_channel_flags(chan), AST_FLAG_BRIDGE_HANGUP_RUN));
273         ast_data_add_bool(tree, "DISABLE_WORKAROUNDS", ast_test_flag(ast_channel_flags(chan), AST_FLAG_DISABLE_WORKAROUNDS));
274         ast_data_add_bool(tree, "DISABLE_DEVSTATE_CACHE", ast_test_flag(ast_channel_flags(chan), AST_FLAG_DISABLE_DEVSTATE_CACHE));
275 }
276
277 int ast_channel_data_add_structure(struct ast_data *tree,
278         struct ast_channel *chan, int add_bridged)
279 {
280         struct ast_channel *bc;
281         struct ast_data *data_bridged;
282         struct ast_data *data_cdr;
283         struct ast_data *data_flags;
284         struct ast_data *data_zones;
285         struct ast_data *enum_node;
286         struct ast_data *data_softhangup;
287 #if 0   /* XXX AstData: ast_callerid no longer exists. (Equivalent code not readily apparent.) */
288         struct ast_data *data_callerid;
289         char value_str[100];
290 #endif
291
292         if (!tree) {
293                 return -1;
294         }
295
296         ast_data_add_structure(ast_channel, tree, chan);
297
298         if (add_bridged) {
299                 bc = ast_bridged_channel(chan);
300                 if (bc) {
301                         data_bridged = ast_data_add_node(tree, "bridged");
302                         if (!data_bridged) {
303                                 return -1;
304                         }
305                         ast_channel_data_add_structure(data_bridged, bc, 0);
306                 }
307         }
308
309         ast_data_add_codec(tree, "oldwriteformat", ast_channel_oldwriteformat(chan));
310         ast_data_add_codec(tree, "readformat", ast_channel_readformat(chan));
311         ast_data_add_codec(tree, "writeformat", ast_channel_writeformat(chan));
312         ast_data_add_codec(tree, "rawreadformat", ast_channel_rawreadformat(chan));
313         ast_data_add_codec(tree, "rawwriteformat", ast_channel_rawwriteformat(chan));
314         ast_data_add_codecs(tree, "nativeformats", ast_channel_nativeformats(chan));
315
316         /* state */
317         enum_node = ast_data_add_node(tree, "state");
318         if (!enum_node) {
319                 return -1;
320         }
321         ast_data_add_str(enum_node, "text", ast_state2str(ast_channel_state(chan)));
322         ast_data_add_int(enum_node, "value", ast_channel_state(chan));
323
324         /* hangupcause */
325         enum_node = ast_data_add_node(tree, "hangupcause");
326         if (!enum_node) {
327                 return -1;
328         }
329         ast_data_add_str(enum_node, "text", ast_cause2str(ast_channel_hangupcause(chan)));
330         ast_data_add_int(enum_node, "value", ast_channel_hangupcause(chan));
331
332         /* amaflags */
333         enum_node = ast_data_add_node(tree, "amaflags");
334         if (!enum_node) {
335                 return -1;
336         }
337         ast_data_add_str(enum_node, "text", ast_cdr_flags2str(ast_channel_amaflags(chan)));
338         ast_data_add_int(enum_node, "value", ast_channel_amaflags(chan));
339
340         /* transfercapability */
341         enum_node = ast_data_add_node(tree, "transfercapability");
342         if (!enum_node) {
343                 return -1;
344         }
345         ast_data_add_str(enum_node, "text", ast_transfercapability2str(ast_channel_transfercapability(chan)));
346         ast_data_add_int(enum_node, "value", ast_channel_transfercapability(chan));
347
348         /* _softphangup */
349         data_softhangup = ast_data_add_node(tree, "softhangup");
350         if (!data_softhangup) {
351                 return -1;
352         }
353         ast_data_add_bool(data_softhangup, "dev", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_DEV);
354         ast_data_add_bool(data_softhangup, "asyncgoto", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_ASYNCGOTO);
355         ast_data_add_bool(data_softhangup, "shutdown", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_SHUTDOWN);
356         ast_data_add_bool(data_softhangup, "timeout", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_TIMEOUT);
357         ast_data_add_bool(data_softhangup, "appunload", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_APPUNLOAD);
358         ast_data_add_bool(data_softhangup, "explicit", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_EXPLICIT);
359         ast_data_add_bool(data_softhangup, "unbridge", ast_channel_softhangup_internal_flag(chan) & AST_SOFTHANGUP_UNBRIDGE);
360
361         /* channel flags */
362         data_flags = ast_data_add_node(tree, "flags");
363         if (!data_flags) {
364                 return -1;
365         }
366         channel_data_add_flags(data_flags, chan);
367
368         ast_data_add_uint(tree, "timetohangup", ast_channel_whentohangup(chan)->tv_sec);
369
370 #if 0   /* XXX AstData: ast_callerid no longer exists. (Equivalent code not readily apparent.) */
371         /* callerid */
372         data_callerid = ast_data_add_node(tree, "callerid");
373         if (!data_callerid) {
374                 return -1;
375         }
376         ast_data_add_structure(ast_callerid, data_callerid, &(chan->cid));
377         /* insert the callerid ton */
378         enum_node = ast_data_add_node(data_callerid, "cid_ton");
379         if (!enum_node) {
380                 return -1;
381         }
382         ast_data_add_int(enum_node, "value", chan->cid.cid_ton);
383         snprintf(value_str, sizeof(value_str), "TON: %s/Plan: %s",
384                 party_number_ton2str(chan->cid.cid_ton),
385                 party_number_plan2str(chan->cid.cid_ton));
386         ast_data_add_str(enum_node, "text", value_str);
387 #endif
388
389         /* tone zone */
390         if (ast_channel_zone(chan)) {
391                 data_zones = ast_data_add_node(tree, "zone");
392                 if (!data_zones) {
393                         return -1;
394                 }
395                 ast_tone_zone_data_add_structure(data_zones, ast_channel_zone(chan));
396         }
397
398         /* insert cdr */
399         data_cdr = ast_data_add_node(tree, "cdr");
400         if (!data_cdr) {
401                 return -1;
402         }
403
404         ast_cdr_data_add_structure(data_cdr, ast_channel_cdr(chan), 1);
405
406         return 0;
407 }
408
409 int ast_channel_data_cmp_structure(const struct ast_data_search *tree,
410         struct ast_channel *chan, const char *structure_name)
411 {
412         return ast_data_search_cmp_structure(tree, ast_channel, chan, structure_name);
413 }
414
415 /* ACCESSORS */
416
417 #define DEFINE_STRINGFIELD_SETTERS_FOR(field, publish)                  \
418 void ast_channel_##field##_set(struct ast_channel *chan, const char *value) \
419 { \
420         ast_string_field_set(chan, field, value); \
421         if (publish) ast_channel_publish_snapshot(chan); \
422 } \
423   \
424 void ast_channel_##field##_build_va(struct ast_channel *chan, const char *fmt, va_list ap) \
425 { \
426         ast_string_field_build_va(chan, field, fmt, ap); \
427         if (publish) ast_channel_publish_snapshot(chan); \
428 } \
429 void ast_channel_##field##_build(struct ast_channel *chan, const char *fmt, ...) \
430 { \
431         va_list ap; \
432         va_start(ap, fmt); \
433         ast_channel_##field##_build_va(chan, fmt, ap); \
434         va_end(ap); \
435         if (publish) ast_channel_publish_snapshot(chan); \
436 }
437
438 DEFINE_STRINGFIELD_SETTERS_FOR(name, 0);
439 DEFINE_STRINGFIELD_SETTERS_FOR(language, 1);
440 DEFINE_STRINGFIELD_SETTERS_FOR(musicclass, 0);
441 DEFINE_STRINGFIELD_SETTERS_FOR(accountcode, 0);
442 DEFINE_STRINGFIELD_SETTERS_FOR(peeraccount, 0);
443 DEFINE_STRINGFIELD_SETTERS_FOR(userfield, 0);
444 DEFINE_STRINGFIELD_SETTERS_FOR(call_forward, 0);
445 DEFINE_STRINGFIELD_SETTERS_FOR(uniqueid, 0);
446 DEFINE_STRINGFIELD_SETTERS_FOR(parkinglot, 0);
447 DEFINE_STRINGFIELD_SETTERS_FOR(hangupsource, 0);
448 DEFINE_STRINGFIELD_SETTERS_FOR(dialcontext, 0);
449
450 #define DEFINE_STRINGFIELD_GETTER_FOR(field) const char *ast_channel_##field(const struct ast_channel *chan) \
451 { \
452         return chan->field; \
453 }
454
455 DEFINE_STRINGFIELD_GETTER_FOR(name);
456 DEFINE_STRINGFIELD_GETTER_FOR(language);
457 DEFINE_STRINGFIELD_GETTER_FOR(musicclass);
458 DEFINE_STRINGFIELD_GETTER_FOR(accountcode);
459 DEFINE_STRINGFIELD_GETTER_FOR(peeraccount);
460 DEFINE_STRINGFIELD_GETTER_FOR(userfield);
461 DEFINE_STRINGFIELD_GETTER_FOR(call_forward);
462 DEFINE_STRINGFIELD_GETTER_FOR(uniqueid);
463 DEFINE_STRINGFIELD_GETTER_FOR(linkedid);
464 DEFINE_STRINGFIELD_GETTER_FOR(parkinglot);
465 DEFINE_STRINGFIELD_GETTER_FOR(hangupsource);
466 DEFINE_STRINGFIELD_GETTER_FOR(dialcontext);
467
468 void ast_channel_linkedid_set(struct ast_channel *chan, const char *value)
469 {
470         ast_assert(!ast_strlen_zero(value));
471         ast_string_field_set(chan, linkedid, value);
472 }
473
474 const char *ast_channel_appl(const struct ast_channel *chan)
475 {
476         return chan->appl;
477 }
478 void ast_channel_appl_set(struct ast_channel *chan, const char *value)
479 {
480         chan->appl = value;
481 }
482 const char *ast_channel_blockproc(const struct ast_channel *chan)
483 {
484         return chan->blockproc;
485 }
486 void ast_channel_blockproc_set(struct ast_channel *chan, const char *value)
487 {
488         chan->blockproc = value;
489 }
490 const char *ast_channel_data(const struct ast_channel *chan)
491 {
492         return chan->data;
493 }
494 void ast_channel_data_set(struct ast_channel *chan, const char *value)
495 {
496         chan->data = value;
497 }
498
499 const char *ast_channel_context(const struct ast_channel *chan)
500 {
501         return chan->context;
502 }
503 void ast_channel_context_set(struct ast_channel *chan, const char *value)
504 {
505         ast_copy_string(chan->context, value, sizeof(chan->context));
506 }
507 const char *ast_channel_exten(const struct ast_channel *chan)
508 {
509         return chan->exten;
510 }
511 void ast_channel_exten_set(struct ast_channel *chan, const char *value)
512 {
513         ast_copy_string(chan->exten, value, sizeof(chan->exten));
514 }
515 const char *ast_channel_macrocontext(const struct ast_channel *chan)
516 {
517         return chan->macrocontext;
518 }
519 void ast_channel_macrocontext_set(struct ast_channel *chan, const char *value)
520 {
521         ast_copy_string(chan->macrocontext, value, sizeof(chan->macrocontext));
522 }
523 const char *ast_channel_macroexten(const struct ast_channel *chan)
524 {
525         return chan->macroexten;
526 }
527 void ast_channel_macroexten_set(struct ast_channel *chan, const char *value)
528 {
529         ast_copy_string(chan->macroexten, value, sizeof(chan->macroexten));
530 }
531
532 char ast_channel_dtmf_digit_to_emulate(const struct ast_channel *chan)
533 {
534         return chan->dtmf_digit_to_emulate;
535 }
536 void ast_channel_dtmf_digit_to_emulate_set(struct ast_channel *chan, char value)
537 {
538         chan->dtmf_digit_to_emulate = value;
539 }
540
541 char ast_channel_sending_dtmf_digit(const struct ast_channel *chan)
542 {
543         return chan->sending_dtmf_digit;
544 }
545 void ast_channel_sending_dtmf_digit_set(struct ast_channel *chan, char value)
546 {
547         chan->sending_dtmf_digit = value;
548 }
549
550 struct timeval ast_channel_sending_dtmf_tv(const struct ast_channel *chan)
551 {
552         return chan->sending_dtmf_tv;
553 }
554 void ast_channel_sending_dtmf_tv_set(struct ast_channel *chan, struct timeval value)
555 {
556         chan->sending_dtmf_tv = value;
557 }
558
559 int ast_channel_amaflags(const struct ast_channel *chan)
560 {
561         return chan->amaflags;
562 }
563 void ast_channel_amaflags_set(struct ast_channel *chan, int value)
564 {
565         chan->amaflags = value;
566 }
567 #ifdef HAVE_EPOLL
568 int ast_channel_epfd(const struct ast_channel *chan)
569 {
570         return chan->epfd;
571 }
572 void ast_channel_epfd_set(struct ast_channel *chan, int value)
573 {
574         chan->epfd = value;
575 }
576 #endif
577 int ast_channel_fdno(const struct ast_channel *chan)
578 {
579         return chan->fdno;
580 }
581 void ast_channel_fdno_set(struct ast_channel *chan, int value)
582 {
583         chan->fdno = value;
584 }
585 int ast_channel_hangupcause(const struct ast_channel *chan)
586 {
587         return chan->hangupcause;
588 }
589 void ast_channel_hangupcause_set(struct ast_channel *chan, int value)
590 {
591         chan->hangupcause = value;
592 }
593 int ast_channel_macropriority(const struct ast_channel *chan)
594 {
595         return chan->macropriority;
596 }
597 void ast_channel_macropriority_set(struct ast_channel *chan, int value)
598 {
599         chan->macropriority = value;
600 }
601 int ast_channel_priority(const struct ast_channel *chan)
602 {
603         return chan->priority;
604 }
605 void ast_channel_priority_set(struct ast_channel *chan, int value)
606 {
607         chan->priority = value;
608 }
609 int ast_channel_rings(const struct ast_channel *chan)
610 {
611         return chan->rings;
612 }
613 void ast_channel_rings_set(struct ast_channel *chan, int value)
614 {
615         chan->rings = value;
616 }
617 int ast_channel_streamid(const struct ast_channel *chan)
618 {
619         return chan->streamid;
620 }
621 void ast_channel_streamid_set(struct ast_channel *chan, int value)
622 {
623         chan->streamid = value;
624 }
625 int ast_channel_timingfd(const struct ast_channel *chan)
626 {
627         return chan->timingfd;
628 }
629 void ast_channel_timingfd_set(struct ast_channel *chan, int value)
630 {
631         chan->timingfd = value;
632 }
633 int ast_channel_visible_indication(const struct ast_channel *chan)
634 {
635         return chan->visible_indication;
636 }
637 void ast_channel_visible_indication_set(struct ast_channel *chan, int value)
638 {
639         chan->visible_indication = value;
640 }
641 int ast_channel_vstreamid(const struct ast_channel *chan)
642 {
643         return chan->vstreamid;
644 }
645 void ast_channel_vstreamid_set(struct ast_channel *chan, int value)
646 {
647         chan->vstreamid = value;
648 }
649 unsigned short ast_channel_transfercapability(const struct ast_channel *chan)
650 {
651         return chan->transfercapability;
652 }
653 void ast_channel_transfercapability_set(struct ast_channel *chan, unsigned short value)
654 {
655         chan->transfercapability = value;
656 }
657 unsigned int ast_channel_emulate_dtmf_duration(const struct ast_channel *chan)
658 {
659         return chan->emulate_dtmf_duration;
660 }
661 void ast_channel_emulate_dtmf_duration_set(struct ast_channel *chan, unsigned int value)
662 {
663         chan->emulate_dtmf_duration = value;
664 }
665 unsigned int ast_channel_fin(const struct ast_channel *chan)
666 {
667         return chan->fin;
668 }
669 void ast_channel_fin_set(struct ast_channel *chan, unsigned int value)
670 {
671         chan->fin = value;
672 }
673 unsigned int ast_channel_fout(const struct ast_channel *chan)
674 {
675         return chan->fout;
676 }
677 void ast_channel_fout_set(struct ast_channel *chan, unsigned int value)
678 {
679         chan->fout = value;
680 }
681 unsigned long ast_channel_insmpl(const struct ast_channel *chan)
682 {
683         return chan->insmpl;
684 }
685 void ast_channel_insmpl_set(struct ast_channel *chan, unsigned long value)
686 {
687         chan->insmpl = value;
688 }
689 unsigned long ast_channel_outsmpl(const struct ast_channel *chan)
690 {
691         return chan->outsmpl;
692 }
693 void ast_channel_outsmpl_set(struct ast_channel *chan, unsigned long value)
694 {
695         chan->outsmpl = value;
696 }
697 void *ast_channel_generatordata(const struct ast_channel *chan)
698 {
699         return chan->generatordata;
700 }
701 void ast_channel_generatordata_set(struct ast_channel *chan, void *value)
702 {
703         chan->generatordata = value;
704 }
705 void *ast_channel_music_state(const struct ast_channel *chan)
706 {
707         return chan->music_state;
708 }
709 void ast_channel_music_state_set(struct ast_channel *chan, void *value)
710 {
711         chan->music_state = value;
712 }
713 void *ast_channel_tech_pvt(const struct ast_channel *chan)
714 {
715         return chan->tech_pvt;
716 }
717 void ast_channel_tech_pvt_set(struct ast_channel *chan, void *value)
718 {
719         chan->tech_pvt = value;
720 }
721 void *ast_channel_timingdata(const struct ast_channel *chan)
722 {
723         return chan->timingdata;
724 }
725 void ast_channel_timingdata_set(struct ast_channel *chan, void *value)
726 {
727         chan->timingdata = value;
728 }
729 struct ast_audiohook_list *ast_channel_audiohooks(const struct ast_channel *chan)
730 {
731         return chan->audiohooks;
732 }
733 void ast_channel_audiohooks_set(struct ast_channel *chan, struct ast_audiohook_list *value)
734 {
735         chan->audiohooks = value;
736 }
737 struct ast_cdr *ast_channel_cdr(const struct ast_channel *chan)
738 {
739         return chan->cdr;
740 }
741 void ast_channel_cdr_set(struct ast_channel *chan, struct ast_cdr *value)
742 {
743         chan->cdr = value;
744 }
745 struct ast_channel *ast_channel_masq(const struct ast_channel *chan)
746 {
747         return chan->masq;
748 }
749 void ast_channel_masq_set(struct ast_channel *chan, struct ast_channel *value)
750 {
751         chan->masq = value;
752 }
753 struct ast_channel *ast_channel_masqr(const struct ast_channel *chan)
754 {
755         return chan->masqr;
756 }
757 void ast_channel_masqr_set(struct ast_channel *chan, struct ast_channel *value)
758 {
759         chan->masqr = value;
760 }
761 struct ast_channel_monitor *ast_channel_monitor(const struct ast_channel *chan)
762 {
763         return chan->monitor;
764 }
765 void ast_channel_monitor_set(struct ast_channel *chan, struct ast_channel_monitor *value)
766 {
767         chan->monitor = value;
768 }
769 struct ast_filestream *ast_channel_stream(const struct ast_channel *chan)
770 {
771         return chan->stream;
772 }
773 void ast_channel_stream_set(struct ast_channel *chan, struct ast_filestream *value)
774 {
775         chan->stream = value;
776 }
777 struct ast_filestream *ast_channel_vstream(const struct ast_channel *chan)
778 {
779         return chan->vstream;
780 }
781 void ast_channel_vstream_set(struct ast_channel *chan, struct ast_filestream *value)
782 {
783         chan->vstream = value;
784 }
785 struct ast_format_cap *ast_channel_nativeformats(const struct ast_channel *chan)
786 {
787         return chan->nativeformats;
788 }
789 void ast_channel_nativeformats_set(struct ast_channel *chan, struct ast_format_cap *value)
790 {
791         chan->nativeformats = value;
792 }
793 struct ast_framehook_list *ast_channel_framehooks(const struct ast_channel *chan)
794 {
795         return chan->framehooks;
796 }
797 void ast_channel_framehooks_set(struct ast_channel *chan, struct ast_framehook_list *value)
798 {
799         chan->framehooks = value;
800 }
801 struct ast_generator *ast_channel_generator(const struct ast_channel *chan)
802 {
803         return chan->generator;
804 }
805 void ast_channel_generator_set(struct ast_channel *chan, struct ast_generator *value)
806 {
807         chan->generator = value;
808 }
809 struct ast_pbx *ast_channel_pbx(const struct ast_channel *chan)
810 {
811         return chan->pbx;
812 }
813 void ast_channel_pbx_set(struct ast_channel *chan, struct ast_pbx *value)
814 {
815         chan->pbx = value;
816 }
817 struct ast_sched_context *ast_channel_sched(const struct ast_channel *chan)
818 {
819         return chan->sched;
820 }
821 void ast_channel_sched_set(struct ast_channel *chan, struct ast_sched_context *value)
822 {
823         chan->sched = value;
824 }
825 struct ast_timer *ast_channel_timer(const struct ast_channel *chan)
826 {
827         return chan->timer;
828 }
829 void ast_channel_timer_set(struct ast_channel *chan, struct ast_timer *value)
830 {
831         chan->timer = value;
832 }
833 struct ast_tone_zone *ast_channel_zone(const struct ast_channel *chan)
834 {
835         return chan->zone;
836 }
837 void ast_channel_zone_set(struct ast_channel *chan, struct ast_tone_zone *value)
838 {
839         chan->zone = value;
840 }
841 struct ast_trans_pvt *ast_channel_readtrans(const struct ast_channel *chan)
842 {
843         return chan->readtrans;
844 }
845 void ast_channel_readtrans_set(struct ast_channel *chan, struct ast_trans_pvt *value)
846 {
847         chan->readtrans = value;
848 }
849 struct ast_trans_pvt *ast_channel_writetrans(const struct ast_channel *chan)
850 {
851         return chan->writetrans;
852 }
853 void ast_channel_writetrans_set(struct ast_channel *chan, struct ast_trans_pvt *value)
854 {
855         chan->writetrans = value;
856 }
857 const struct ast_channel_tech *ast_channel_tech(const struct ast_channel *chan)
858 {
859         return chan->tech;
860 }
861 void ast_channel_tech_set(struct ast_channel *chan, const struct ast_channel_tech *value)
862 {
863         chan->tech = value;
864 }
865 enum ast_channel_adsicpe ast_channel_adsicpe(const struct ast_channel *chan)
866 {
867         return chan->adsicpe;
868 }
869 void ast_channel_adsicpe_set(struct ast_channel *chan, enum ast_channel_adsicpe value)
870 {
871         chan->adsicpe = value;
872 }
873 enum ast_channel_state ast_channel_state(const struct ast_channel *chan)
874 {
875         return chan->state;
876 }
877 struct ast_callid *ast_channel_callid(const struct ast_channel *chan)
878 {
879         if (chan->callid) {
880                 ast_callid_ref(chan->callid);
881                 return chan->callid;
882         }
883         return NULL;
884 }
885 void ast_channel_callid_set(struct ast_channel *chan, struct ast_callid *callid)
886 {
887         char call_identifier_from[AST_CALLID_BUFFER_LENGTH];
888         char call_identifier_to[AST_CALLID_BUFFER_LENGTH];
889         call_identifier_from[0] = '\0';
890         ast_callid_strnprint(call_identifier_to, sizeof(call_identifier_to), callid);
891         if (chan->callid) {
892                 ast_callid_strnprint(call_identifier_from, sizeof(call_identifier_from), chan->callid);
893                 ast_debug(3, "Channel Call ID changing from %s to %s\n", call_identifier_from, call_identifier_to);
894                 /* unbind if already set */
895                 ast_callid_unref(chan->callid);
896         }
897
898         chan->callid = ast_callid_ref(callid);
899
900         ast_test_suite_event_notify("CallIDChange",
901                 "State: CallIDChange\r\n"
902                 "Channel: %s\r\n"
903                 "CallID: %s\r\n"
904                 "PriorCallID: %s",
905                 ast_channel_name(chan),
906                 call_identifier_to,
907                 call_identifier_from);
908
909 }
910 void ast_channel_state_set(struct ast_channel *chan, enum ast_channel_state value)
911 {
912         chan->state = value;
913 }
914 struct ast_format *ast_channel_oldwriteformat(struct ast_channel *chan)
915 {
916         return &chan->oldwriteformat;
917 }
918 struct ast_format *ast_channel_rawreadformat(struct ast_channel *chan)
919 {
920         return &chan->rawreadformat;
921 }
922 struct ast_format *ast_channel_rawwriteformat(struct ast_channel *chan)
923 {
924         return &chan->rawwriteformat;
925 }
926 struct ast_format *ast_channel_readformat(struct ast_channel *chan)
927 {
928         return &chan->readformat;
929 }
930 struct ast_format *ast_channel_writeformat(struct ast_channel *chan)
931 {
932         return &chan->writeformat;
933 }
934 struct ast_hangup_handler_list *ast_channel_hangup_handlers(struct ast_channel *chan)
935 {
936         return &chan->hangup_handlers;
937 }
938 struct ast_datastore_list *ast_channel_datastores(struct ast_channel *chan)
939 {
940         return &chan->datastores;
941 }
942 struct ast_autochan_list *ast_channel_autochans(struct ast_channel *chan)
943 {
944         return &chan->autochans;
945 }
946 struct ast_readq_list *ast_channel_readq(struct ast_channel *chan)
947 {
948         return &chan->readq;
949 }
950 struct ast_frame *ast_channel_dtmff(struct ast_channel *chan)
951 {
952         return &chan->dtmff;
953 }
954 struct ast_jb *ast_channel_jb(struct ast_channel *chan)
955 {
956         return &chan->jb;
957 }
958 struct ast_party_caller *ast_channel_caller(struct ast_channel *chan)
959 {
960         return &chan->caller;
961 }
962 struct ast_party_connected_line *ast_channel_connected(struct ast_channel *chan)
963 {
964         return &chan->connected;
965 }
966 struct ast_party_id ast_channel_connected_effective_id(struct ast_channel *chan)
967 {
968         return ast_party_id_merge(&chan->connected.id, &chan->connected.priv);
969 }
970 struct ast_party_dialed *ast_channel_dialed(struct ast_channel *chan)
971 {
972         return &chan->dialed;
973 }
974 struct ast_party_redirecting *ast_channel_redirecting(struct ast_channel *chan)
975 {
976         return &chan->redirecting;
977 }
978 struct ast_party_id ast_channel_redirecting_effective_orig(struct ast_channel *chan)
979 {
980         return ast_party_id_merge(&chan->redirecting.orig, &chan->redirecting.priv_orig);
981 }
982 struct ast_party_id ast_channel_redirecting_effective_from(struct ast_channel *chan)
983 {
984         return ast_party_id_merge(&chan->redirecting.from, &chan->redirecting.priv_from);
985 }
986 struct ast_party_id ast_channel_redirecting_effective_to(struct ast_channel *chan)
987 {
988         return ast_party_id_merge(&chan->redirecting.to, &chan->redirecting.priv_to);
989 }
990 struct timeval *ast_channel_dtmf_tv(struct ast_channel *chan)
991 {
992         return &chan->dtmf_tv;
993 }
994 struct timeval *ast_channel_whentohangup(struct ast_channel *chan)
995 {
996         return &chan->whentohangup;
997 }
998 struct varshead *ast_channel_varshead(struct ast_channel *chan)
999 {
1000         return &chan->varshead;
1001 }
1002 void ast_channel_dtmff_set(struct ast_channel *chan, struct ast_frame *value)
1003 {
1004         chan->dtmff = *value;
1005 }
1006 void ast_channel_jb_set(struct ast_channel *chan, struct ast_jb *value)
1007 {
1008         chan->jb = *value;
1009 }
1010 void ast_channel_caller_set(struct ast_channel *chan, struct ast_party_caller *value)
1011 {
1012         chan->caller = *value;
1013 }
1014 void ast_channel_connected_set(struct ast_channel *chan, struct ast_party_connected_line *value)
1015 {
1016         chan->connected = *value;
1017 }
1018 void ast_channel_dialed_set(struct ast_channel *chan, struct ast_party_dialed *value)
1019 {
1020         chan->dialed = *value;
1021 }
1022 void ast_channel_redirecting_set(struct ast_channel *chan, struct ast_party_redirecting *value)
1023 {
1024         chan->redirecting = *value;
1025 }
1026 void ast_channel_dtmf_tv_set(struct ast_channel *chan, struct timeval *value)
1027 {
1028         chan->dtmf_tv = *value;
1029 }
1030 void ast_channel_whentohangup_set(struct ast_channel *chan, struct timeval *value)
1031 {
1032         chan->whentohangup = *value;
1033 }
1034 void ast_channel_varshead_set(struct ast_channel *chan, struct varshead *value)
1035 {
1036         chan->varshead = *value;
1037 }
1038 struct timeval ast_channel_creationtime(struct ast_channel *chan)
1039 {
1040         return chan->creationtime;
1041 }
1042 void ast_channel_creationtime_set(struct ast_channel *chan, struct timeval *value)
1043 {
1044         chan->creationtime = *value;
1045 }
1046
1047 /* Evil softhangup accessors */
1048 int ast_channel_softhangup_internal_flag(struct ast_channel *chan)
1049 {
1050         return chan->softhangup;
1051 }
1052 void ast_channel_softhangup_internal_flag_set(struct ast_channel *chan, int value)
1053 {
1054         chan->softhangup = value;
1055 }
1056 void ast_channel_softhangup_internal_flag_add(struct ast_channel *chan, int value)
1057 {
1058         chan->softhangup |= value;
1059 }
1060 void ast_channel_softhangup_internal_flag_clear(struct ast_channel *chan, int value)
1061 {
1062         chan ->softhangup &= ~value;
1063 }
1064
1065 void ast_channel_callid_cleanup(struct ast_channel *chan)
1066 {
1067         if (chan->callid) {
1068                 chan->callid = ast_callid_unref(chan->callid);
1069         }
1070 }
1071
1072 /* Typedef accessors */
1073 ast_group_t ast_channel_callgroup(const struct ast_channel *chan)
1074 {
1075         return chan->callgroup;
1076 }
1077 void ast_channel_callgroup_set(struct ast_channel *chan, ast_group_t value)
1078 {
1079         chan->callgroup = value;
1080 }
1081 ast_group_t ast_channel_pickupgroup(const struct ast_channel *chan)
1082 {
1083         return chan->pickupgroup;
1084 }
1085 void ast_channel_pickupgroup_set(struct ast_channel *chan, ast_group_t value)
1086 {
1087         chan->pickupgroup = value;
1088 }
1089 struct ast_namedgroups *ast_channel_named_callgroups(const struct ast_channel *chan)
1090 {
1091         return chan->named_callgroups;
1092 }
1093 void ast_channel_named_callgroups_set(struct ast_channel *chan, struct ast_namedgroups *value)
1094 {
1095         ast_unref_namedgroups(chan->named_callgroups);
1096         chan->named_callgroups = ast_ref_namedgroups(value);
1097 }
1098 struct ast_namedgroups *ast_channel_named_pickupgroups(const struct ast_channel *chan)
1099 {
1100         return chan->named_pickupgroups;
1101 }
1102 void ast_channel_named_pickupgroups_set(struct ast_channel *chan, struct ast_namedgroups *value)
1103 {
1104         ast_unref_namedgroups(chan->named_pickupgroups);
1105         chan->named_pickupgroups = ast_ref_namedgroups(value);
1106 }
1107
1108 /* Alertpipe functions */
1109 int ast_channel_alert_write(struct ast_channel *chan)
1110 {
1111         char blah = 0x7F;
1112         return ast_channel_alert_writable(chan) && write(chan->alertpipe[1], &blah, sizeof(blah)) != sizeof(blah);
1113 }
1114
1115 ast_alert_status_t ast_channel_internal_alert_read(struct ast_channel *chan)
1116 {
1117         int flags;
1118         char blah;
1119
1120         if (!ast_channel_internal_alert_readable(chan)) {
1121                 return AST_ALERT_NOT_READABLE;
1122         }
1123
1124         flags = fcntl(chan->alertpipe[0], F_GETFL);
1125         /* For some odd reason, the alertpipe occasionally loses nonblocking status,
1126          * which immediately causes a deadlock scenario.  Detect and prevent this. */
1127         if ((flags & O_NONBLOCK) == 0) {
1128                 ast_log(LOG_ERROR, "Alertpipe on channel %s lost O_NONBLOCK?!!\n", ast_channel_name(chan));
1129                 if (fcntl(chan->alertpipe[0], F_SETFL, flags | O_NONBLOCK) < 0) {
1130                         ast_log(LOG_WARNING, "Unable to set alertpipe nonblocking! (%d: %s)\n", errno, strerror(errno));
1131                         return AST_ALERT_READ_FATAL;
1132                 }
1133         }
1134         if (read(chan->alertpipe[0], &blah, sizeof(blah)) < 0) {
1135                 if (errno != EINTR && errno != EAGAIN) {
1136                         ast_log(LOG_WARNING, "read() failed: %s\n", strerror(errno));
1137                         return AST_ALERT_READ_FAIL;
1138                 }
1139         }
1140
1141         return AST_ALERT_READ_SUCCESS;
1142 }
1143
1144 int ast_channel_alert_writable(struct ast_channel *chan)
1145 {
1146         return chan->alertpipe[1] > -1;
1147 }
1148
1149 int ast_channel_internal_alert_readable(struct ast_channel *chan)
1150 {
1151         return chan->alertpipe[0] > -1;
1152 }
1153
1154 void ast_channel_internal_alertpipe_clear(struct ast_channel *chan)
1155 {
1156         chan->alertpipe[0] = chan->alertpipe[1] = -1;
1157 }
1158
1159 void ast_channel_internal_alertpipe_close(struct ast_channel *chan)
1160 {
1161         if (ast_channel_internal_alert_readable(chan)) {
1162                 close(chan->alertpipe[0]);
1163         }
1164         if (ast_channel_alert_writable(chan)) {
1165                 close(chan->alertpipe[1]);
1166         }
1167 }
1168
1169 int ast_channel_internal_alertpipe_init(struct ast_channel *chan)
1170 {
1171         if (pipe(chan->alertpipe)) {
1172                 ast_log(LOG_WARNING, "Channel allocation failed: Can't create alert pipe! Try increasing max file descriptors with ulimit -n\n");
1173                 return -1;
1174         } else {
1175                 int flags = fcntl(chan->alertpipe[0], F_GETFL);
1176                 if (fcntl(chan->alertpipe[0], F_SETFL, flags | O_NONBLOCK) < 0) {
1177                         ast_log(LOG_WARNING, "Channel allocation failed: Unable to set alertpipe nonblocking! (%d: %s)\n", errno, strerror(errno));
1178                         return -1;
1179                 }
1180                 flags = fcntl(chan->alertpipe[1], F_GETFL);
1181                 if (fcntl(chan->alertpipe[1], F_SETFL, flags | O_NONBLOCK) < 0) {
1182                         ast_log(LOG_WARNING, "Channel allocation failed: Unable to set alertpipe nonblocking! (%d: %s)\n", errno, strerror(errno));
1183                         return -1;
1184                 }
1185         }
1186         return 0;
1187 }
1188
1189 int ast_channel_internal_alert_readfd(struct ast_channel *chan)
1190 {
1191         return chan->alertpipe[0];
1192 }
1193
1194 void ast_channel_internal_alertpipe_swap(struct ast_channel *chan1, struct ast_channel *chan2)
1195 {
1196         int i;
1197         for (i = 0; i < ARRAY_LEN(chan1->alertpipe); i++) {
1198                 SWAP(chan1->alertpipe[i], chan2->alertpipe[i]);
1199         }
1200 }
1201
1202 /* file descriptor array accessors */
1203 void ast_channel_internal_fd_set(struct ast_channel *chan, int which, int value)
1204 {
1205         chan->fds[which] = value;
1206 }
1207 void ast_channel_internal_fd_clear(struct ast_channel *chan, int which)
1208 {
1209         ast_channel_internal_fd_set(chan, which, -1);
1210 }
1211 void ast_channel_internal_fd_clear_all(struct ast_channel *chan)
1212 {
1213         int i;
1214         for (i = 0; i < AST_MAX_FDS; i++) {
1215                 ast_channel_internal_fd_clear(chan, i);
1216         }
1217 }
1218 int ast_channel_fd(const struct ast_channel *chan, int which)
1219 {
1220         return chan->fds[which];
1221 }
1222 int ast_channel_fd_isset(const struct ast_channel *chan, int which)
1223 {
1224         return ast_channel_fd(chan, which) > -1;
1225 }
1226
1227 #ifdef HAVE_EPOLL
1228 struct ast_epoll_data *ast_channel_internal_epfd_data(const struct ast_channel *chan, int which)
1229 {
1230         return chan->epfd_data[which];
1231 }
1232 void ast_channel_internal_epfd_data_set(struct ast_channel *chan, int which , struct ast_epoll_data *value)
1233 {
1234         chan->epfd_data[which] = value;
1235 }
1236 #endif
1237
1238 pthread_t ast_channel_blocker(const struct ast_channel *chan)
1239 {
1240         return chan->blocker;
1241 }
1242 void ast_channel_blocker_set(struct ast_channel *chan, pthread_t value)
1243 {
1244         chan->blocker = value;
1245 }
1246
1247 ast_timing_func_t ast_channel_timingfunc(const struct ast_channel *chan)
1248 {
1249         return chan->timingfunc;
1250 }
1251 void ast_channel_timingfunc_set(struct ast_channel *chan, ast_timing_func_t value)
1252 {
1253         chan->timingfunc = value;
1254 }
1255
1256 struct ast_bridge *ast_channel_internal_bridge(const struct ast_channel *chan)
1257 {
1258         return chan->bridge;
1259 }
1260 void ast_channel_internal_bridge_set(struct ast_channel *chan, struct ast_bridge *value)
1261 {
1262         chan->bridge = value;
1263 }
1264
1265 struct ast_bridge_channel *ast_channel_internal_bridge_channel(const struct ast_channel *chan)
1266 {
1267         return chan->bridge_channel;
1268 }
1269 void ast_channel_internal_bridge_channel_set(struct ast_channel *chan, struct ast_bridge_channel *value)
1270 {
1271         chan->bridge_channel = value;
1272 }
1273
1274 struct ast_channel *ast_channel_internal_bridged_channel(const struct ast_channel *chan)
1275 {
1276         return chan->bridged_channel;
1277 }
1278 void ast_channel_internal_bridged_channel_set(struct ast_channel *chan, struct ast_channel *value)
1279 {
1280         chan->bridged_channel = value;
1281 }
1282
1283 struct ast_flags *ast_channel_flags(struct ast_channel *chan)
1284 {
1285         return &chan->flags;
1286 }
1287
1288 static int collect_names_cb(void *obj, void *arg, int flags) {
1289         struct ast_control_pvt_cause_code *cause_code = obj;
1290         struct ast_str **str = arg;
1291
1292         ast_str_append(str, 0, "%s%s", (ast_str_strlen(*str) ? "," : ""), cause_code->chan_name);
1293
1294         return 0;
1295 }
1296
1297 struct ast_str *ast_channel_dialed_causes_channels(const struct ast_channel *chan)
1298 {
1299         struct ast_str *chanlist = ast_str_create(128);
1300
1301         if (!chanlist) {
1302                 return NULL;
1303         }
1304
1305         ao2_callback(chan->dialed_causes, 0, collect_names_cb, &chanlist);
1306
1307         return chanlist;
1308 }
1309
1310 struct ast_control_pvt_cause_code *ast_channel_dialed_causes_find(const struct ast_channel *chan, const char *chan_name)
1311 {
1312         return ao2_find(chan->dialed_causes, chan_name, OBJ_KEY);
1313 }
1314
1315 int ast_channel_dialed_causes_add(const struct ast_channel *chan, const struct ast_control_pvt_cause_code *cause_code, int datalen)
1316 {
1317         struct ast_control_pvt_cause_code *ao2_cause_code;
1318         ao2_find(chan->dialed_causes, cause_code->chan_name, OBJ_KEY | OBJ_UNLINK | OBJ_NODATA);
1319         ao2_cause_code = ao2_alloc(datalen, NULL);
1320
1321         if (ao2_cause_code) {
1322                 memcpy(ao2_cause_code, cause_code, datalen);
1323                 ao2_link(chan->dialed_causes, ao2_cause_code);
1324                 ao2_ref(ao2_cause_code, -1);
1325                 return 0;
1326         } else {
1327                 return -1;
1328         }
1329 }
1330
1331 void ast_channel_dialed_causes_clear(const struct ast_channel *chan)
1332 {
1333         ao2_callback(chan->dialed_causes, OBJ_UNLINK | OBJ_NODATA | OBJ_MULTIPLE, NULL, NULL);
1334 }
1335
1336 /* \brief Hash function for pvt cause code frames */
1337 static int pvt_cause_hash_fn(const void *vpc, const int flags)
1338 {
1339         const struct ast_control_pvt_cause_code *pc = vpc;
1340         return ast_str_hash(ast_tech_to_upper(ast_strdupa(pc->chan_name)));
1341 }
1342
1343 /* \brief Comparison function for pvt cause code frames */
1344 static int pvt_cause_cmp_fn(void *obj, void *vstr, int flags)
1345 {
1346         struct ast_control_pvt_cause_code *pc = obj;
1347         char *str = ast_tech_to_upper(ast_strdupa(vstr));
1348         char *pc_str = ast_tech_to_upper(ast_strdupa(pc->chan_name));
1349         return !strcmp(pc_str, str) ? CMP_MATCH | CMP_STOP : 0;
1350 }
1351
1352 #define DIALED_CAUSES_BUCKETS 37
1353
1354 struct ast_channel *__ast_channel_internal_alloc(void (*destructor)(void *obj), const char *file, int line, const char *function)
1355 {
1356         struct ast_channel *tmp;
1357 #if defined(REF_DEBUG)
1358         tmp = __ao2_alloc_debug(sizeof(*tmp), destructor,
1359                 AO2_ALLOC_OPT_LOCK_MUTEX, "", file, line, function, 1);
1360 #elif defined(__AST_DEBUG_MALLOC)
1361         tmp = __ao2_alloc_debug(sizeof(*tmp), destructor,
1362                 AO2_ALLOC_OPT_LOCK_MUTEX, "", file, line, function, 0);
1363 #else
1364         tmp = ao2_alloc(sizeof(*tmp), destructor);
1365 #endif
1366
1367         if ((ast_string_field_init(tmp, 128))) {
1368                 return ast_channel_unref(tmp);
1369         }
1370
1371         if (!(tmp->dialed_causes = ao2_container_alloc(DIALED_CAUSES_BUCKETS, pvt_cause_hash_fn, pvt_cause_cmp_fn))) {
1372                 return ast_channel_unref(tmp);
1373         }
1374
1375         return tmp;
1376 }
1377
1378 void ast_channel_internal_cleanup(struct ast_channel *chan)
1379 {
1380         if (chan->dialed_causes) {
1381                 ao2_t_ref(chan->dialed_causes, -1,
1382                         "done with dialed causes since the channel is going away");
1383                 chan->dialed_causes = NULL;
1384         }
1385
1386         ast_string_field_free_memory(chan);
1387
1388         chan->forwarder = stasis_unsubscribe(chan->forwarder);
1389         chan->endpoint_forward = stasis_unsubscribe(chan->endpoint_forward);
1390
1391         ao2_cleanup(chan->topic);
1392         chan->topic = NULL;
1393 }
1394
1395 void ast_channel_internal_finalize(struct ast_channel *chan)
1396 {
1397         chan->finalized = 1;
1398 }
1399
1400 int ast_channel_internal_is_finalized(struct ast_channel *chan)
1401 {
1402         return chan->finalized;
1403 }
1404
1405 struct stasis_topic *ast_channel_topic(struct ast_channel *chan)
1406 {
1407         return chan ? chan->topic : ast_channel_topic_all();
1408 }
1409
1410 int ast_endpoint_add_channel(struct ast_endpoint *endpoint,
1411         struct ast_channel *chan)
1412 {
1413         RAII_VAR(struct ast_channel_snapshot *, snapshot, NULL, ao2_cleanup);
1414         RAII_VAR(struct stasis_message *, msg, NULL, ao2_cleanup);
1415
1416         ast_assert(chan != NULL);
1417         ast_assert(endpoint != NULL);
1418
1419         snapshot = ast_channel_snapshot_create(chan);
1420         if (!snapshot) {
1421                 return -1;
1422         }
1423
1424         msg = stasis_message_create(ast_channel_snapshot_type(), snapshot);
1425         if (!msg) {
1426                 return -1;
1427         }
1428
1429         chan->endpoint_forward =
1430                 stasis_forward_all(chan->topic, ast_endpoint_topic(endpoint));
1431
1432         if (chan->endpoint_forward == NULL) {
1433                 return -1;
1434         }
1435
1436         stasis_publish(ast_endpoint_topic(endpoint), msg);
1437
1438         return 0;
1439 }
1440
1441 void ast_channel_internal_setup_topics(struct ast_channel *chan)
1442 {
1443         const char *topic_name = chan->uniqueid;
1444         ast_assert(chan->topic == NULL);
1445         ast_assert(chan->forwarder == NULL);
1446
1447         if (ast_strlen_zero(topic_name)) {
1448                 topic_name = "<dummy-channel>";
1449         }
1450
1451         chan->topic = stasis_topic_create(topic_name);
1452         chan->forwarder = stasis_forward_all(chan->topic, ast_channel_topic_all());
1453
1454         ast_assert(chan->topic != NULL);
1455         ast_assert(chan->forwarder != NULL);
1456 }