AGI/Manager: Prevent multiple NewExten events during AGI application changes
[asterisk/asterisk.git] / main / manager_channels.c
1 /*
2  * Asterisk -- An open source telephony toolkit.
3  *
4  * Copyright (C) 2013, Digium, Inc.
5  *
6  * David M. Lee, II <dlee@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 The Asterisk Management Interface - AMI (channel event handling)
22  *
23  * \author David M. Lee, II <dlee@digium.com>
24  *
25  * AMI generated many per-channel and global-channel events by converting Stasis
26  * messages to AMI events. It makes sense to simply put them into a single file.
27  */
28
29 #include "asterisk.h"
30
31 ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
32
33 #include "asterisk/callerid.h"
34 #include "asterisk/channel.h"
35 #include "asterisk/manager.h"
36 #include "asterisk/stasis_message_router.h"
37 #include "asterisk/pbx.h"
38 #include "asterisk/stasis_channels.h"
39
40 /*** DOCUMENTATION
41         <managerEvent language="en_US" name="Newchannel">
42                 <managerEventInstance class="EVENT_FLAG_CALL">
43                         <synopsis>Raised when a new channel is created.</synopsis>
44                         <syntax>
45                                 <channel_snapshot/>
46                         </syntax>
47                 </managerEventInstance>
48         </managerEvent>
49         <managerEvent language="en_US" name="Newstate">
50                 <managerEventInstance class="EVENT_FLAG_CALL">
51                         <synopsis>Raised when a channel's state changes.</synopsis>
52                         <syntax>
53                                 <channel_snapshot/>
54                         </syntax>
55                 </managerEventInstance>
56         </managerEvent>
57         <managerEvent language="en_US" name="Hangup">
58                 <managerEventInstance class="EVENT_FLAG_CALL">
59                         <synopsis>Raised when a channel is hung up.</synopsis>
60                         <syntax>
61                                 <channel_snapshot/>
62                                 <parameter name="Cause">
63                                         <para>A numeric cause code for why the channel was hung up.</para>
64                                 </parameter>
65                                 <parameter name="Cause-txt">
66                                         <para>A description of why the channel was hung up.</para>
67                                 </parameter>
68                         </syntax>
69                 </managerEventInstance>
70         </managerEvent>
71         <managerEvent language="en_US" name="HangupRequest">
72                 <managerEventInstance class="EVENT_FLAG_CALL">
73                         <synopsis>Raised when a hangup is requested.</synopsis>
74                         <syntax>
75                                 <channel_snapshot/>
76                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='Hangup']/managerEventInstance/syntax/parameter[@name='Cause'])" />
77                         </syntax>
78                 </managerEventInstance>
79         </managerEvent>
80         <managerEvent language="en_US" name="SoftHangupRequest">
81                 <managerEventInstance class="EVENT_FLAG_CALL">
82                         <synopsis>Raised when a soft hangup is requested with a specific cause code.</synopsis>
83                         <syntax>
84                                 <channel_snapshot/>
85                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='Hangup']/managerEventInstance/syntax/parameter[@name='Cause'])" />
86                         </syntax>
87                 </managerEventInstance>
88         </managerEvent>
89         <managerEvent language="en_US" name="NewExten">
90                 <managerEventInstance class="EVENT_FLAG_DIALPLAN">
91                         <synopsis>Raised when a channel enters a new context, extension, priority.</synopsis>
92                         <syntax>
93                                 <channel_snapshot/>
94                                 <parameter name="Extension">
95                                         <para>Deprecated in 12, but kept for
96                                         backward compatability. Please use
97                                         'Exten' instead.</para>
98                                 </parameter>
99                                 <parameter name="Application">
100                                         <para>The application about to be executed.</para>
101                                 </parameter>
102                                 <parameter name="AppData">
103                                         <para>The data to be passed to the application.</para>
104                                 </parameter>
105                         </syntax>
106                 </managerEventInstance>
107         </managerEvent>
108         <managerEvent language="en_US" name="NewCallerid">
109                 <managerEventInstance class="EVENT_FLAG_CALL">
110                         <synopsis>Raised when a channel receives new Caller ID information.</synopsis>
111                         <syntax>
112                                 <channel_snapshot/>
113                                 <parameter name="CID-CallingPres">
114                                         <para>A description of the Caller ID presentation.</para>
115                                 </parameter>
116                         </syntax>
117                 </managerEventInstance>
118         </managerEvent>
119         <managerEvent language="en_US" name="NewAccountCode">
120                 <managerEventInstance class="EVENT_FLAG_CALL">
121                         <synopsis>Raised when a Channel's AccountCode is changed.</synopsis>
122                         <syntax>
123                                 <channel_snapshot/>
124                                 <parameter name="OldAccountCode">
125                                         <para>The channel's previous account code</para>
126                                 </parameter>
127                         </syntax>
128                 </managerEventInstance>
129         </managerEvent>
130         <managerEvent language="en_US" name="DialBegin">
131                 <managerEventInstance class="EVENT_FLAG_CALL">
132                         <synopsis>Raised when a dial action has started.</synopsis>
133                         <syntax>
134                                 <channel_snapshot/>
135                                 <channel_snapshot prefix="Dest"/>
136                                 <parameter name="DialString">
137                                         <para>The non-technology specific device being dialed.</para>
138                                 </parameter>
139                         </syntax>
140                         <see-also>
141                                 <ref type="application">Dial</ref>
142                         </see-also>
143                 </managerEventInstance>
144         </managerEvent>
145         <managerEvent language="en_US" name="DialEnd">
146                 <managerEventInstance class="EVENT_FLAG_CALL">
147                         <synopsis>Raised when a dial action has completed.</synopsis>
148                         <syntax>
149                                 <channel_snapshot/>
150                                 <channel_snapshot prefix="Dest"/>
151                                 <parameter name="DialStatus">
152                                         <para>The result of the dial operation.</para>
153                                         <enumlist>
154                                                 <enum name="ABORT">
155                                                         <para>The call was aborted.</para>
156                                                 </enum>
157                                                 <enum name="ANSWER">
158                                                         <para>The caller answered.</para>
159                                                 </enum>
160                                                 <enum name="BUSY">
161                                                         <para>The caller was busy.</para>
162                                                 </enum>
163                                                 <enum name="CANCEL">
164                                                         <para>The caller cancelled the call.</para>
165                                                 </enum>
166                                                 <enum name="CHANUNAVAIL">
167                                                         <para>The requested channel is unavailable.</para>
168                                                 </enum>
169                                                 <enum name="CONGESTION">
170                                                         <para>The called party is congested.</para>
171                                                 </enum>
172                                                 <enum name="CONTINUE">
173                                                         <para>The dial completed, but the caller elected
174                                                         to continue in the dialplan.</para>
175                                                 </enum>
176                                                 <enum name="GOTO">
177                                                         <para>The dial completed, but the caller jumped to
178                                                         a dialplan location.</para>
179                                                         <para>If known, the location the caller is jumping
180                                                         to will be appended to the result following a
181                                                         ":".</para>
182                                                 </enum>
183                                                 <enum name="NOANSWER">
184                                                         <para>The called party failed to answer.</para>
185                                                 </enum>
186                                         </enumlist>
187                                 </parameter>
188                         </syntax>
189                         <see-also>
190                                 <ref type="application">Dial</ref>
191                         </see-also>
192                 </managerEventInstance>
193         </managerEvent>
194         <managerEvent language="en_US" name="Hold">
195                 <managerEventInstance class="EVENT_FLAG_CALL">
196                         <synopsis>Raised when a channel goes on hold.</synopsis>
197                         <syntax>
198                                 <channel_snapshot/>
199                                 <parameter name="MusicClass">
200                                         <para>The suggested MusicClass, if provided.</para>
201                                 </parameter>
202                         </syntax>
203                 </managerEventInstance>
204         </managerEvent>
205         <managerEvent language="en_US" name="Unhold">
206                 <managerEventInstance class="EVENT_FLAG_CALL">
207                         <synopsis>Raised when a channel goes off hold.</synopsis>
208                         <syntax>
209                                 <channel_snapshot/>
210                         </syntax>
211                 </managerEventInstance>
212         </managerEvent>
213         <managerEvent language="en_US" name="ChanSpyStart">
214                 <managerEventInstance class="EVENT_FLAG_CALL">
215                         <synopsis>Raised when one channel begins spying on another channel.</synopsis>
216                         <syntax>
217                                 <channel_snapshot prefix="Spyer"/>
218                                 <channel_snapshot prefix="Spyee"/>
219                         </syntax>
220                         <see-also>
221                                 <ref type="application">ChanSpyStop</ref>
222                         </see-also>
223                 </managerEventInstance>
224         </managerEvent>
225         <managerEvent language="en_US" name="ChanSpyStop">
226                 <managerEventInstance class="EVENT_FLAG_CALL">
227                         <synopsis>Raised when a channel has stopped spying.</synopsis>
228                         <syntax>
229                                 <channel_snapshot prefix="Spyer"/>
230                                 <channel_snapshot prefix="Spyee"/>
231                         </syntax>
232                         <see-also>
233                                 <ref type="application">ChanSpyStart</ref>
234                         </see-also>
235                 </managerEventInstance>
236         </managerEvent>
237         <managerEvent language="en_US" name="HangupHandlerRun">
238                 <managerEventInstance class="EVENT_FLAG_DIALPLAN">
239                         <synopsis>Raised when a hangup handler is about to be called.</synopsis>
240                         <syntax>
241                                 <channel_snapshot/>
242                                 <parameter name="Handler">
243                                         <para>Hangup handler parameter string passed to the Gosub application.</para>
244                                 </parameter>
245                         </syntax>
246                 </managerEventInstance>
247         </managerEvent>
248         <managerEvent language="en_US" name="HangupHandlerPop">
249                 <managerEventInstance class="EVENT_FLAG_DIALPLAN">
250                         <synopsis>
251                                 Raised when a hangup handler is removed from the handler stack
252                                 by the CHANNEL() function.
253                         </synopsis>
254                         <syntax>
255                                 <channel_snapshot/>
256                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='HangupHandlerRun']/managerEventInstance/syntax/parameter)" />
257                         </syntax>
258                         <see-also>
259                                 <ref type="managerEvent">HangupHandlerPush</ref>
260                                 <ref type="function">CHANNEL</ref>
261                         </see-also>
262                 </managerEventInstance>
263         </managerEvent>
264         <managerEvent language="en_US" name="HangupHandlerPush">
265                 <managerEventInstance class="EVENT_FLAG_DIALPLAN">
266                         <synopsis>
267                                 Raised when a hangup handler is added to the handler stack by
268                                 the CHANNEL() function.
269                         </synopsis>
270                         <syntax>
271                                 <channel_snapshot/>
272                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='HangupHandlerRun']/managerEventInstance/syntax/parameter)" />
273                         </syntax>
274                         <see-also>
275                                 <ref type="managerEvent">HangupHandlerPop</ref>
276                                 <ref type="function">CHANNEL</ref>
277                         </see-also>
278                 </managerEventInstance>
279         </managerEvent>
280         <managerEvent language="en_US" name="FAXStatus">
281                 <managerEventInstance class="EVENT_FLAG_CALL">
282                         <synopsis>
283                                 Raised periodically during a fax transmission.
284                         </synopsis>
285                         <syntax>
286                                 <channel_snapshot/>
287                                 <parameter name="Operation">
288                                         <enumlist>
289                                                 <enum name="gateway"/>
290                                                 <enum name="receive"/>
291                                                 <enum name="send"/>
292                                         </enumlist>
293                                 </parameter>
294                                 <parameter name="Status">
295                                         <para>A text message describing the current status of the fax</para>
296                                 </parameter>
297                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='ReceiveFAX']/managerEventInstance/syntax/parameter[@name='LocalStationID'])" />
298                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='ReceiveFAX']/managerEventInstance/syntax/parameter[@name='FileName'])" />
299                         </syntax>
300                 </managerEventInstance>
301         </managerEvent>
302         <managerEvent language="en_US" name="ReceiveFAX">
303                 <managerEventInstance class="EVENT_FLAG_CALL">
304                         <synopsis>
305                                 Raised when a receive fax operation has completed.
306                         </synopsis>
307                         <syntax>
308                                 <channel_snapshot/>
309                                 <parameter name="LocalStationID">
310                                         <para>The value of the <variable>LOCALSTATIONID</variable> channel variable</para>
311                                 </parameter>
312                                 <parameter name="RemoteStationID">
313                                         <para>The value of the <variable>REMOTESTATIONID</variable> channel variable</para>
314                                 </parameter>
315                                 <parameter name="PagesTransferred">
316                                         <para>The number of pages that have been transferred</para>
317                                 </parameter>
318                                 <parameter name="Resolution">
319                                         <para>The negotiated resolution</para>
320                                 </parameter>
321                                 <parameter name="TransferRate">
322                                         <para>The negotiated transfer rate</para>
323                                 </parameter>
324                                 <parameter name="FileName" multiple="yes">
325                                         <para>The files being affected by the fax operation</para>
326                                 </parameter>
327                         </syntax>
328                 </managerEventInstance>
329         </managerEvent>
330         <managerEvent language="en_US" name="SendFAX">
331                 <managerEventInstance class="EVENT_FLAG_CALL">
332                         <synopsis>
333                                 Raised when a send fax operation has completed.
334                         </synopsis>
335                         <syntax>
336                                 <channel_snapshot/>
337                                 <xi:include xpointer="xpointer(/docs/managerEvent[@name='ReceiveFAX']/managerEventInstance/syntax/parameter)" />
338                         </syntax>
339                 </managerEventInstance>
340         </managerEvent>
341         <managerEvent language="en_US" name="MusicOnHoldStart">
342                 <managerEventInstance class="EVENT_FLAG_CALL">
343                         <synopsis>Raised when music on hold has started on a channel.</synopsis>
344                         <syntax>
345                                 <channel_snapshot/>
346                                 <parameter name="Class">
347                                         <para>The class of music being played on the channel</para>
348                                 </parameter>
349                         </syntax>
350                         <see-also>
351                                 <ref type="managerEvent">MusicOnHoldStop</ref>
352                                 <ref type="application">MusicOnHold</ref>
353                         </see-also>
354                 </managerEventInstance>
355         </managerEvent>
356         <managerEvent language="en_US" name="MusicOnHoldStop">
357                 <managerEventInstance class="EVENT_FLAG_CALL">
358                         <synopsis>Raised when music on hold has stopped on a channel.</synopsis>
359                         <syntax>
360                                 <channel_snapshot/>
361                         </syntax>
362                         <see-also>
363                                 <ref type="managerEvent">MusicOnHoldStart</ref>
364                                 <ref type="application">StopMusicOnHold</ref>
365                         </see-also>
366                 </managerEventInstance>
367         </managerEvent>
368         <managerEvent language="en_US" name="MonitorStart">
369                 <managerEventInstance class="EVENT_FLAG_CALL">
370                         <synopsis>Raised when monitoring has started on a channel.</synopsis>
371                         <syntax>
372                                 <channel_snapshot/>
373                         </syntax>
374                         <see-also>
375                                 <ref type="managerEvent">MonitorStop</ref>
376                                 <ref type="application">Monitor</ref>
377                                 <ref type="manager">Monitor</ref>
378                         </see-also>
379                 </managerEventInstance>
380         </managerEvent>
381         <managerEvent language="en_US" name="MonitorStop">
382                 <managerEventInstance class="EVENT_FLAG_CALL">
383                 <synopsis>Raised when monitoring has stopped on a channel.</synopsis>
384                 <syntax>
385                         <channel_snapshot/>
386                 </syntax>
387                 <see-also>
388                         <ref type="managerEvent">MonitorStart</ref>
389                         <ref type="application">StopMonitor</ref>
390                         <ref type="manager">StopMonitor</ref>
391                 </see-also>
392                 </managerEventInstance>
393         </managerEvent>
394 ***/
395
396 /*! \brief The \ref stasis subscription returned by the forwarding of the channel topic
397  * to the manager topic
398  */
399 static struct stasis_forward *topic_forwarder;
400
401 struct ast_str *ast_manager_build_channel_state_string_prefix(
402                 const struct ast_channel_snapshot *snapshot,
403                 const char *prefix)
404 {
405         struct ast_str *out = ast_str_create(1024);
406         int res = 0;
407
408         if (!out) {
409                 return NULL;
410         }
411
412         if (snapshot->tech_properties & AST_CHAN_TP_INTERNAL) {
413                 ast_free(out);
414                 return NULL;
415         }
416
417         res = ast_str_set(&out, 0,
418                 "%sChannel: %s\r\n"
419                 "%sChannelState: %d\r\n"
420                 "%sChannelStateDesc: %s\r\n"
421                 "%sCallerIDNum: %s\r\n"
422                 "%sCallerIDName: %s\r\n"
423                 "%sConnectedLineNum: %s\r\n"
424                 "%sConnectedLineName: %s\r\n"
425                 "%sAccountCode: %s\r\n"
426                 "%sContext: %s\r\n"
427                 "%sExten: %s\r\n"
428                 "%sPriority: %d\r\n"
429                 "%sUniqueid: %s\r\n",
430                 prefix, snapshot->name,
431                 prefix, snapshot->state,
432                 prefix, ast_state2str(snapshot->state),
433                 prefix, S_OR(snapshot->caller_number, "<unknown>"),
434                 prefix, S_OR(snapshot->caller_name, "<unknown>"),
435                 prefix, S_OR(snapshot->connected_number, "<unknown>"),
436                 prefix, S_OR(snapshot->connected_name, "<unknown>"),
437                 prefix, snapshot->accountcode,
438                 prefix, snapshot->context,
439                 prefix, snapshot->exten,
440                 prefix, snapshot->priority,
441                 prefix, snapshot->uniqueid);
442
443         if (!res) {
444                 ast_free(out);
445                 return NULL;
446         }
447
448         if (snapshot->manager_vars) {
449                 struct ast_var_t *var;
450                 AST_LIST_TRAVERSE(snapshot->manager_vars, var, entries) {
451                         ast_str_append(&out, 0, "%sChanVariable: %s=%s\r\n",
452                                        prefix,
453                                        var->name, var->value);
454                 }
455         }
456
457         return out;
458 }
459
460 struct ast_str *ast_manager_build_channel_state_string(
461                 const struct ast_channel_snapshot *snapshot)
462 {
463         return ast_manager_build_channel_state_string_prefix(snapshot, "");
464 }
465
466 /*! \brief Typedef for callbacks that get called on channel snapshot updates */
467 typedef struct ast_manager_event_blob *(*channel_snapshot_monitor)(
468         struct ast_channel_snapshot *old_snapshot,
469         struct ast_channel_snapshot *new_snapshot);
470
471 /*! \brief Handle channel state changes */
472 static struct ast_manager_event_blob *channel_state_change(
473         struct ast_channel_snapshot *old_snapshot,
474         struct ast_channel_snapshot *new_snapshot)
475 {
476         int is_hungup, was_hungup;
477
478         if (!new_snapshot) {
479                 /* Ignore cache clearing events; we'll see the hangup first */
480                 return NULL;
481         }
482
483         /* The Newchannel, Newstate and Hangup events are closely related, in
484          * in that they are mutually exclusive, basically different flavors
485          * of a new channel state event.
486          */
487
488         if (!old_snapshot) {
489                 return ast_manager_event_blob_create(
490                         EVENT_FLAG_CALL, "Newchannel", NO_EXTRA_FIELDS);
491         }
492
493         was_hungup = ast_test_flag(&old_snapshot->flags, AST_FLAG_DEAD) ? 1 : 0;
494         is_hungup = ast_test_flag(&new_snapshot->flags, AST_FLAG_DEAD) ? 1 : 0;
495
496         if (!was_hungup && is_hungup) {
497                 return ast_manager_event_blob_create(
498                         EVENT_FLAG_CALL, "Hangup",
499                         "Cause: %d\r\n"
500                         "Cause-txt: %s\r\n",
501                         new_snapshot->hangupcause,
502                         ast_cause2str(new_snapshot->hangupcause));
503         }
504
505         if (old_snapshot->state != new_snapshot->state) {
506                 return ast_manager_event_blob_create(
507                         EVENT_FLAG_CALL, "Newstate", NO_EXTRA_FIELDS);
508         }
509
510         /* No event */
511         return NULL;
512 }
513
514 static struct ast_manager_event_blob *channel_newexten(
515         struct ast_channel_snapshot *old_snapshot,
516         struct ast_channel_snapshot *new_snapshot)
517 {
518         /* No Newexten event on cache clear */
519         if (!new_snapshot) {
520                 return NULL;
521         }
522
523         /* Empty application is not valid for a Newexten event */
524         if (ast_strlen_zero(new_snapshot->appl)) {
525                 return NULL;
526         }
527
528         /* Ignore any updates if we're hungup */
529         if (ast_test_flag(&new_snapshot->flags, AST_FLAG_DEAD)) {
530                 return NULL;
531         }
532
533         /* Ignore updates if the CEP is unchanged */
534         if (old_snapshot && ast_channel_snapshot_cep_equal(old_snapshot, new_snapshot)) {
535                 return NULL;
536         }
537
538         /* DEPRECATED: Extension field deprecated in 12; remove in 14 */
539         return ast_manager_event_blob_create(
540                 EVENT_FLAG_CALL, "Newexten",
541                 "Extension: %s\r\n"
542                 "Application: %s\r\n"
543                 "AppData: %s\r\n",
544                 new_snapshot->exten,
545                 new_snapshot->appl,
546                 new_snapshot->data);
547 }
548
549 static struct ast_manager_event_blob *channel_new_callerid(
550         struct ast_channel_snapshot *old_snapshot,
551         struct ast_channel_snapshot *new_snapshot)
552 {
553         /* No NewCallerid event on cache clear or first event */
554         if (!old_snapshot || !new_snapshot) {
555                 return NULL;
556         }
557
558         if (ast_channel_snapshot_caller_id_equal(old_snapshot, new_snapshot)) {
559                 return NULL;
560         }
561
562         return ast_manager_event_blob_create(
563                 EVENT_FLAG_CALL, "NewCallerid",
564                 "CID-CallingPres: %d (%s)\r\n",
565                 new_snapshot->caller_pres,
566                 ast_describe_caller_presentation(new_snapshot->caller_pres));
567 }
568
569 static struct ast_manager_event_blob *channel_new_accountcode(
570         struct ast_channel_snapshot *old_snapshot,
571         struct ast_channel_snapshot *new_snapshot)
572 {
573         if (!old_snapshot || !new_snapshot) {
574                 return NULL;
575         }
576
577         if (!strcmp(old_snapshot->accountcode, new_snapshot->accountcode)) {
578                 return NULL;
579         }
580
581         return ast_manager_event_blob_create(
582                 EVENT_FLAG_CALL, "NewAccountCode",
583                 "OldAccountCode: %s\r\n", old_snapshot->accountcode);
584 }
585
586 channel_snapshot_monitor channel_monitors[] = {
587         channel_state_change,
588         channel_newexten,
589         channel_new_callerid,
590         channel_new_accountcode
591 };
592
593 static void channel_snapshot_update(void *data, struct stasis_subscription *sub,
594                                     struct stasis_message *message)
595 {
596         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
597         struct stasis_cache_update *update;
598         struct ast_channel_snapshot *old_snapshot;
599         struct ast_channel_snapshot *new_snapshot;
600         size_t i;
601
602         update = stasis_message_data(message);
603
604         ast_assert(ast_channel_snapshot_type() == update->type);
605
606         old_snapshot = stasis_message_data(update->old_snapshot);
607         new_snapshot = stasis_message_data(update->new_snapshot);
608
609         for (i = 0; i < ARRAY_LEN(channel_monitors); ++i) {
610                 RAII_VAR(struct ast_manager_event_blob *, ev, NULL, ao2_cleanup);
611                 ev = channel_monitors[i](old_snapshot, new_snapshot);
612
613                 if (!ev) {
614                         continue;
615                 }
616
617                 /* If we haven't already, build the channel event string */
618                 if (!channel_event_string) {
619                         channel_event_string =
620                                 ast_manager_build_channel_state_string(new_snapshot);
621                         if (!channel_event_string) {
622                                 return;
623                         }
624                 }
625
626                 manager_event(ev->event_flags, ev->manager_event, "%s%s",
627                         ast_str_buffer(channel_event_string),
628                         ev->extra_fields);
629         }
630 }
631
632 static int userevent_exclusion_cb(const char *key)
633 {
634         if (!strcmp("type", key)) {
635                 return 1;
636         }
637         if (!strcmp("eventname", key)) {
638                 return 1;
639         }
640         return 0;
641 }
642
643 static void channel_user_event_cb(void *data, struct stasis_subscription *sub,
644         struct stasis_message *message)
645 {
646         struct ast_channel_blob *obj = stasis_message_data(message);
647         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
648         RAII_VAR(struct ast_str *, body, NULL, ast_free);
649         const char *eventname;
650
651         eventname = ast_json_string_get(ast_json_object_get(obj->blob, "eventname"));
652         body = ast_manager_str_from_json_object(obj->blob, userevent_exclusion_cb);
653         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
654
655         if (!channel_event_string || !body) {
656                 return;
657         }
658
659         /*** DOCUMENTATION
660                 <managerEventInstance>
661                         <synopsis>A user defined event raised from the dialplan.</synopsis>
662                         <syntax>
663                                 <channel_snapshot/>
664                                 <parameter name="UserEvent">
665                                         <para>The event name, as specified in the dialplan.</para>
666                                 </parameter>
667                         </syntax>
668                         <see-also>
669                                 <ref type="application">UserEvent</ref>
670                         </see-also>
671                 </managerEventInstance>
672         ***/
673         manager_event(EVENT_FLAG_USER, "UserEvent",
674                       "%s"
675                       "UserEvent: %s\r\n"
676                       "%s",
677                       ast_str_buffer(channel_event_string), eventname, ast_str_buffer(body));
678 }
679
680 static void publish_basic_channel_event(const char *event, int class, struct ast_channel_snapshot *snapshot)
681 {
682         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
683
684         channel_event_string = ast_manager_build_channel_state_string(snapshot);
685         if (!channel_event_string) {
686                 return;
687         }
688
689         manager_event(class, event,
690                 "%s",
691                 ast_str_buffer(channel_event_string));
692 }
693
694 static void channel_hangup_request_cb(void *data,
695         struct stasis_subscription *sub,
696         struct stasis_message *message)
697 {
698         struct ast_channel_blob *obj = stasis_message_data(message);
699         RAII_VAR(struct ast_str *, extra, NULL, ast_free);
700         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
701         struct ast_json *cause;
702         int is_soft;
703         char *manager_event = "HangupRequest";
704
705         extra = ast_str_create(20);
706         if (!extra) {
707                 return;
708         }
709
710         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
711
712         if (!channel_event_string) {
713                 return;
714         }
715
716         cause = ast_json_object_get(obj->blob, "cause");
717         if (cause) {
718                 ast_str_append(&extra, 0,
719                                "Cause: %jd\r\n",
720                                ast_json_integer_get(cause));
721         }
722
723         is_soft = ast_json_is_true(ast_json_object_get(obj->blob, "soft"));
724         if (is_soft) {
725                 manager_event = "SoftHangupRequest";
726         }
727
728         manager_event(EVENT_FLAG_CALL, manager_event,
729                       "%s%s",
730                       ast_str_buffer(channel_event_string),
731                       ast_str_buffer(extra));
732 }
733
734 static void channel_chanspy_stop_cb(void *data, struct stasis_subscription *sub,
735                 struct stasis_message *message)
736 {
737         RAII_VAR(struct ast_str *, spyer_channel_string, NULL, ast_free);
738         struct ast_channel_snapshot *spyer;
739         struct ast_multi_channel_blob *payload = stasis_message_data(message);
740
741         spyer = ast_multi_channel_blob_get_channel(payload, "spyer_channel");
742         if (!spyer) {
743                 ast_log(AST_LOG_WARNING, "Received ChanSpy Start event with no spyer channel!\n");
744                 return;
745         }
746
747         spyer_channel_string = ast_manager_build_channel_state_string_prefix(spyer, "Spyer");
748         if (!spyer_channel_string) {
749                 return;
750         }
751
752         manager_event(EVENT_FLAG_CALL, "ChanSpyStop",
753                       "%s",
754                       ast_str_buffer(spyer_channel_string));
755 }
756
757 static void channel_chanspy_start_cb(void *data, struct stasis_subscription *sub,
758                 struct stasis_message *message)
759 {
760         RAII_VAR(struct ast_str *, spyer_channel_string, NULL, ast_free);
761         RAII_VAR(struct ast_str *, spyee_channel_string, NULL, ast_free);
762         struct ast_channel_snapshot *spyer;
763         struct ast_channel_snapshot *spyee;
764         struct ast_multi_channel_blob *payload = stasis_message_data(message);
765
766         spyer = ast_multi_channel_blob_get_channel(payload, "spyer_channel");
767         if (!spyer) {
768                 ast_log(AST_LOG_WARNING, "Received ChanSpy Start event with no spyer channel!\n");
769                 return;
770         }
771         spyee = ast_multi_channel_blob_get_channel(payload, "spyee_channel");
772         if (!spyee) {
773                 ast_log(AST_LOG_WARNING, "Received ChanSpy Start event with no spyee channel!\n");
774                 return;
775         }
776
777         spyer_channel_string = ast_manager_build_channel_state_string_prefix(spyer, "Spyer");
778         if (!spyer_channel_string) {
779                 return;
780         }
781         spyee_channel_string = ast_manager_build_channel_state_string_prefix(spyee, "Spyee");
782         if (!spyee_channel_string) {
783                 return;
784         }
785
786         manager_event(EVENT_FLAG_CALL, "ChanSpyStart",
787                       "%s%s",
788                       ast_str_buffer(spyer_channel_string),
789                       ast_str_buffer(spyee_channel_string));
790 }
791
792 static void channel_dtmf_begin_cb(void *data, struct stasis_subscription *sub,
793         struct stasis_message *message)
794 {
795         struct ast_channel_blob *obj = stasis_message_data(message);
796         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
797         const char *digit =
798                 ast_json_string_get(ast_json_object_get(obj->blob, "digit"));
799         const char *direction =
800                 ast_json_string_get(ast_json_object_get(obj->blob, "direction"));
801
802         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
803
804         if (!channel_event_string) {
805                 return;
806         }
807
808         /*** DOCUMENTATION
809                 <managerEventInstance>
810                         <synopsis>Raised when a DTMF digit has started on a channel.</synopsis>
811                                 <syntax>
812                                         <channel_snapshot/>
813                                         <parameter name="Digit">
814                                                 <para>DTMF digit received or transmitted (0-9, A-E, # or *</para>
815                                         </parameter>
816                                         <parameter name="Direction">
817                                                 <enumlist>
818                                                         <enum name="Received"/>
819                                                         <enum name="Sent"/>
820                                                 </enumlist>
821                                         </parameter>
822                                 </syntax>
823                 </managerEventInstance>
824         ***/
825         manager_event(EVENT_FLAG_DTMF, "DTMFBegin",
826                 "%s"
827                 "Digit: %s\r\n"
828                 "Direction: %s\r\n",
829                 ast_str_buffer(channel_event_string),
830                 digit, direction);
831 }
832
833 static void channel_dtmf_end_cb(void *data, struct stasis_subscription *sub,
834         struct stasis_message *message)
835 {
836         struct ast_channel_blob *obj = stasis_message_data(message);
837         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
838         const char *digit =
839                 ast_json_string_get(ast_json_object_get(obj->blob, "digit"));
840         const char *direction =
841                 ast_json_string_get(ast_json_object_get(obj->blob, "direction"));
842         long duration_ms =
843                 ast_json_integer_get(ast_json_object_get(obj->blob, "duration_ms"));
844
845         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
846
847         if (!channel_event_string) {
848                 return;
849         }
850
851         /*** DOCUMENTATION
852                 <managerEventInstance>
853                         <synopsis>Raised when a DTMF digit has ended on a channel.</synopsis>
854                                 <syntax>
855                                         <channel_snapshot/>
856                                         <parameter name="Digit">
857                                                 <para>DTMF digit received or transmitted (0-9, A-E, # or *</para>
858                                         </parameter>
859                                         <parameter name="DurationMs">
860                                                 <para>Duration (in milliseconds) DTMF was sent/received</para>
861                                         </parameter>
862                                         <parameter name="Direction">
863                                                 <enumlist>
864                                                         <enum name="Received"/>
865                                                         <enum name="Sent"/>
866                                                 </enumlist>
867                                         </parameter>
868                                 </syntax>
869                 </managerEventInstance>
870         ***/
871         manager_event(EVENT_FLAG_DTMF, "DTMFEnd",
872                 "%s"
873                 "Digit: %s\r\n"
874                 "DurationMs: %ld\r\n"
875                 "Direction: %s\r\n",
876                 ast_str_buffer(channel_event_string),
877                 digit, duration_ms, direction);
878 }
879
880 static void channel_hangup_handler_cb(void *data, struct stasis_subscription *sub,
881                 struct stasis_message *message)
882 {
883         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
884         struct ast_channel_blob *payload = stasis_message_data(message);
885         const char *action = ast_json_string_get(ast_json_object_get(payload->blob, "type"));
886         const char *handler = ast_json_string_get(ast_json_object_get(payload->blob, "handler"));
887         const char *event;
888
889         channel_event_string = ast_manager_build_channel_state_string(payload->snapshot);
890
891         if (!channel_event_string) {
892                 return;
893         }
894
895         if (!strcmp(action, "type")) {
896                 event = "HangupHandlerRun";
897         } else if (!strcmp(action, "type")) {
898                 event = "HangupHandlerPop";
899         } else if (!strcmp(action, "type")) {
900                 event = "HangupHandlerPush";
901         } else {
902                 return;
903         }
904         manager_event(EVENT_FLAG_DIALPLAN, event,
905                 "%s"
906                 "Handler: %s\r\n",
907                 ast_str_buffer(channel_event_string),
908                 handler);
909 }
910
911 static void channel_fax_cb(void *data, struct stasis_subscription *sub,
912                 struct stasis_message *message)
913 {
914         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
915         RAII_VAR(struct ast_str *, event_buffer, ast_str_create(256), ast_free);
916         struct ast_channel_blob *payload = stasis_message_data(message);
917         const char *type = ast_json_string_get(ast_json_object_get(payload->blob, "type"));
918         struct ast_json *operation = ast_json_object_get(payload->blob, "operation");
919         struct ast_json *status = ast_json_object_get(payload->blob, "status");
920         struct ast_json *local_station_id = ast_json_object_get(payload->blob, "local_station_id");
921         struct ast_json *remote_station_id = ast_json_object_get(payload->blob, "remote_station_id");
922         struct ast_json *fax_pages = ast_json_object_get(payload->blob, "fax_pages");
923         struct ast_json *fax_resolution = ast_json_object_get(payload->blob, "fax_resolution");
924         struct ast_json *fax_bitrate = ast_json_object_get(payload->blob, "fax_bitrate");
925         struct ast_json *filenames = ast_json_object_get(payload->blob, "filenames");
926         const char *event;
927         size_t array_len;
928         size_t i;
929
930         if (!event_buffer) {
931                 return;
932         }
933
934         channel_event_string = ast_manager_build_channel_state_string(payload->snapshot);
935         if (!channel_event_string) {
936                 return;
937         }
938
939         if (!strcmp(type, "status")) {
940                 event = "FAXStatus";
941         } else if (!strcmp(type, "receive")) {
942                 event = "ReceiveFAX";
943         } else if (!strcmp(type, "send")) {
944                 event = "SendFAX";
945         } else {
946                 return;
947         }
948
949         if (operation) {
950                 ast_str_append(&event_buffer, 0, "Operation: %s\r\n", ast_json_string_get(operation));
951         }
952         if (status) {
953                 ast_str_append(&event_buffer, 0, "Status: %s\r\n", ast_json_string_get(status));
954         }
955         if (local_station_id) {
956                 ast_str_append(&event_buffer, 0, "LocalStationID: %s\r\n", ast_json_string_get(local_station_id));
957         }
958         if (remote_station_id) {
959                 ast_str_append(&event_buffer, 0, "RemoteStationID: %s\r\n", ast_json_string_get(remote_station_id));
960         }
961         if (fax_pages) {
962                 ast_str_append(&event_buffer, 0, "PagesTransferred: %s\r\n", ast_json_string_get(fax_pages));
963         }
964         if (fax_resolution) {
965                 ast_str_append(&event_buffer, 0, "Resolution: %s\r\n", ast_json_string_get(fax_resolution));
966         }
967         if (fax_bitrate) {
968                 ast_str_append(&event_buffer, 0, "TransferRate: %s\r\n", ast_json_string_get(fax_bitrate));
969         }
970         if (filenames) {
971                 array_len = ast_json_array_size(filenames);
972                 for (i = 0; i < array_len; i++) {
973                         ast_str_append(&event_buffer, 0, "FileName: %s\r\n", ast_json_string_get(ast_json_array_get(filenames, i)));
974                 }
975         }
976
977         manager_event(EVENT_FLAG_CALL, event,
978                 "%s"
979                 "%s",
980                 ast_str_buffer(channel_event_string),
981                 ast_str_buffer(event_buffer));
982 }
983
984 static void channel_moh_start_cb(void *data, struct stasis_subscription *sub,
985                 struct stasis_message *message)
986 {
987         struct ast_channel_blob *payload = stasis_message_data(message);
988         struct ast_json *blob = payload->blob;
989         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
990
991         channel_event_string = ast_manager_build_channel_state_string(payload->snapshot);
992         if (!channel_event_string) {
993                 return;
994         }
995
996         manager_event(EVENT_FLAG_CALL, "MusicOnHoldStart",
997                 "%s"
998                 "Class: %s\r\n",
999                 ast_str_buffer(channel_event_string),
1000                 ast_json_string_get(ast_json_object_get(blob, "class")));
1001
1002 }
1003
1004 static void channel_moh_stop_cb(void *data, struct stasis_subscription *sub,
1005                 struct stasis_message *message)
1006 {
1007         struct ast_channel_blob *payload = stasis_message_data(message);
1008
1009         publish_basic_channel_event("MusicOnHoldStop", EVENT_FLAG_CALL, payload->snapshot);
1010 }
1011
1012 static void channel_monitor_start_cb(void *data, struct stasis_subscription *sub,
1013                 struct stasis_message *message)
1014 {
1015         struct ast_channel_blob *payload = stasis_message_data(message);
1016
1017         publish_basic_channel_event("MonitorStart", EVENT_FLAG_CALL, payload->snapshot);
1018 }
1019
1020 static void channel_monitor_stop_cb(void *data, struct stasis_subscription *sub,
1021                 struct stasis_message *message)
1022 {
1023         struct ast_channel_blob *payload = stasis_message_data(message);
1024
1025         publish_basic_channel_event("MonitorStop", EVENT_FLAG_CALL, payload->snapshot);
1026 }
1027
1028 /*!
1029  * \brief Callback processing messages for channel dialing
1030  */
1031 static void channel_dial_cb(void *data, struct stasis_subscription *sub,
1032         struct stasis_message *message)
1033 {
1034         struct ast_multi_channel_blob *obj = stasis_message_data(message);
1035         const char *dialstatus;
1036         const char *dialstring;
1037         struct ast_channel_snapshot *caller;
1038         struct ast_channel_snapshot *peer;
1039         RAII_VAR(struct ast_str *, caller_event_string, NULL, ast_free);
1040         RAII_VAR(struct ast_str *, peer_event_string, NULL, ast_free);
1041
1042         caller = ast_multi_channel_blob_get_channel(obj, "caller");
1043         peer = ast_multi_channel_blob_get_channel(obj, "peer");
1044
1045         /* Peer is required - otherwise, who are we dialing? */
1046         ast_assert(peer != NULL);
1047         peer_event_string = ast_manager_build_channel_state_string_prefix(peer, "Dest");
1048         if (!peer_event_string) {
1049                 return;
1050         }
1051
1052         if (caller && !(caller_event_string = ast_manager_build_channel_state_string(caller))) {
1053                 return;
1054         }
1055
1056         dialstatus = ast_json_string_get(ast_json_object_get(ast_multi_channel_blob_get_json(obj), "dialstatus"));
1057         dialstring = ast_json_string_get(ast_json_object_get(ast_multi_channel_blob_get_json(obj), "dialstring"));
1058         if (ast_strlen_zero(dialstatus)) {
1059                 manager_event(EVENT_FLAG_CALL, "DialBegin",
1060                                 "%s"
1061                                 "%s"
1062                                 "DialString: %s\r\n",
1063                                 caller_event_string ? ast_str_buffer(caller_event_string) : "",
1064                                 ast_str_buffer(peer_event_string),
1065                                 S_OR(dialstring, "unknown"));
1066         } else {
1067                 manager_event(EVENT_FLAG_CALL, "DialEnd",
1068                                 "%s"
1069                                 "%s"
1070                                 "DialStatus: %s\r\n",
1071                                 caller_event_string ? ast_str_buffer(caller_event_string) : "",
1072                                 ast_str_buffer(peer_event_string),
1073                                 S_OR(dialstatus, "unknown"));
1074         }
1075
1076 }
1077
1078 static void channel_hold_cb(void *data, struct stasis_subscription *sub,
1079         struct stasis_message *message)
1080 {
1081         struct ast_channel_blob *obj = stasis_message_data(message);
1082         const char *musicclass;
1083         RAII_VAR(struct ast_str *, musicclass_string, NULL, ast_free);
1084         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
1085
1086         if (!(musicclass_string = ast_str_create(32))) {
1087                 return;
1088         }
1089
1090         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
1091         if (!channel_event_string) {
1092                 return;
1093         }
1094
1095         if (obj->blob) {
1096                 musicclass = ast_json_string_get(ast_json_object_get(obj->blob, "musicclass"));
1097
1098                 if (!ast_strlen_zero(musicclass)) {
1099                         ast_str_set(&musicclass_string, 0, "MusicClass: %s\r\n", musicclass);
1100                 }
1101         }
1102
1103         manager_event(EVENT_FLAG_CALL, "Hold",
1104                 "%s"
1105                 "%s",
1106                 ast_str_buffer(channel_event_string),
1107                 ast_str_buffer(musicclass_string));
1108 }
1109
1110 static void channel_unhold_cb(void *data, struct stasis_subscription *sub,
1111         struct stasis_message *message)
1112 {
1113         struct ast_channel_blob *obj = stasis_message_data(message);
1114         RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free);
1115
1116         channel_event_string = ast_manager_build_channel_state_string(obj->snapshot);
1117         if (!channel_event_string) {
1118                 return;
1119         }
1120
1121         manager_event(EVENT_FLAG_CALL, "Unhold",
1122                 "%s",
1123                 ast_str_buffer(channel_event_string));
1124 }
1125
1126 static void manager_channels_shutdown(void)
1127 {
1128         stasis_forward_cancel(topic_forwarder);
1129         topic_forwarder = NULL;
1130 }
1131
1132 int manager_channels_init(void)
1133 {
1134         int ret = 0;
1135         struct stasis_topic *manager_topic;
1136         struct stasis_topic *channel_topic;
1137         struct stasis_message_router *message_router;
1138
1139         manager_topic = ast_manager_get_topic();
1140         if (!manager_topic) {
1141                 return -1;
1142         }
1143         message_router = ast_manager_get_message_router();
1144         if (!message_router) {
1145                 return -1;
1146         }
1147         channel_topic = ast_channel_topic_all_cached();
1148         if (!channel_topic) {
1149                 return -1;
1150         }
1151
1152         topic_forwarder = stasis_forward_all(channel_topic, manager_topic);
1153         if (!topic_forwarder) {
1154                 return -1;
1155         }
1156
1157         ast_register_atexit(manager_channels_shutdown);
1158
1159         ret |= stasis_message_router_add_cache_update(message_router,
1160                 ast_channel_snapshot_type(), channel_snapshot_update, NULL);
1161
1162         ret |= stasis_message_router_add(message_router,
1163                 ast_channel_user_event_type(), channel_user_event_cb, NULL);
1164
1165         ret |= stasis_message_router_add(message_router,
1166                 ast_channel_dtmf_begin_type(), channel_dtmf_begin_cb, NULL);
1167
1168         ret |= stasis_message_router_add(message_router,
1169                 ast_channel_dtmf_end_type(), channel_dtmf_end_cb, NULL);
1170
1171         ret |= stasis_message_router_add(message_router,
1172                 ast_channel_hangup_request_type(), channel_hangup_request_cb,
1173                 NULL);
1174
1175         ret |= stasis_message_router_add(message_router,
1176                 ast_channel_dial_type(), channel_dial_cb, NULL);
1177
1178         ret |= stasis_message_router_add(message_router,
1179                 ast_channel_hold_type(), channel_hold_cb, NULL);
1180
1181         ret |= stasis_message_router_add(message_router,
1182                 ast_channel_unhold_type(), channel_unhold_cb, NULL);
1183
1184         ret |= stasis_message_router_add(message_router,
1185                 ast_channel_fax_type(), channel_fax_cb, NULL);
1186
1187         ret |= stasis_message_router_add(message_router,
1188                 ast_channel_chanspy_start_type(), channel_chanspy_start_cb,
1189                 NULL);
1190
1191         ret |= stasis_message_router_add(message_router,
1192                 ast_channel_chanspy_stop_type(), channel_chanspy_stop_cb, NULL);
1193
1194         ret |= stasis_message_router_add(message_router,
1195                 ast_channel_hangup_handler_type(), channel_hangup_handler_cb,
1196                 NULL);
1197
1198         ret |= stasis_message_router_add(message_router,
1199                 ast_channel_moh_start_type(), channel_moh_start_cb, NULL);
1200
1201         ret |= stasis_message_router_add(message_router,
1202                 ast_channel_moh_stop_type(), channel_moh_stop_cb, NULL);
1203
1204         ret |= stasis_message_router_add(message_router,
1205                 ast_channel_monitor_start_type(), channel_monitor_start_cb,
1206                 NULL);
1207
1208         ret |= stasis_message_router_add(message_router,
1209                 ast_channel_monitor_stop_type(), channel_monitor_stop_cb, NULL);
1210
1211         /* If somehow we failed to add any routes, just shut down the whole
1212          * thing and fail it.
1213          */
1214         if (ret) {
1215                 manager_channels_shutdown();
1216                 return -1;
1217         }
1218
1219         return 0;
1220 }
1221