d83be6da31c68133c80177bf8e8ca6daa22812a3
[asterisk/asterisk.git] / channels / chan_local.c
1 /*
2  * Asterisk -- An open source telephony toolkit.
3  *
4  * Copyright (C) 1999 - 2005, 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  * \author Mark Spencer <markster@digium.com>
22  *
23  * \brief Local Proxy Channel
24  * 
25  * \ingroup channel_drivers
26  */
27
28 #include "asterisk.h"
29
30 ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
31
32 #include <fcntl.h>
33 #include <sys/signal.h>
34
35 #include "asterisk/lock.h"
36 #include "asterisk/channel.h"
37 #include "asterisk/config.h"
38 #include "asterisk/module.h"
39 #include "asterisk/pbx.h"
40 #include "asterisk/sched.h"
41 #include "asterisk/io.h"
42 #include "asterisk/rtp.h"
43 #include "asterisk/acl.h"
44 #include "asterisk/callerid.h"
45 #include "asterisk/file.h"
46 #include "asterisk/cli.h"
47 #include "asterisk/app.h"
48 #include "asterisk/musiconhold.h"
49 #include "asterisk/manager.h"
50 #include "asterisk/stringfields.h"
51 #include "asterisk/devicestate.h"
52
53 static const char tdesc[] = "Local Proxy Channel Driver";
54
55 #define IS_OUTBOUND(a,b) (a == b->chan ? 1 : 0)
56
57 static struct ast_jb_conf g_jb_conf = {
58         .flags = 0,
59         .max_size = -1,
60         .resync_threshold = -1,
61         .impl = "",
62 };
63
64 static struct ast_channel *local_request(const char *type, int format, void *data, int *cause);
65 static int local_digit_begin(struct ast_channel *ast, char digit);
66 static int local_digit_end(struct ast_channel *ast, char digit, unsigned int duration);
67 static int local_call(struct ast_channel *ast, char *dest, int timeout);
68 static int local_hangup(struct ast_channel *ast);
69 static int local_answer(struct ast_channel *ast);
70 static struct ast_frame *local_read(struct ast_channel *ast);
71 static int local_write(struct ast_channel *ast, struct ast_frame *f);
72 static int local_indicate(struct ast_channel *ast, int condition, const void *data, size_t datalen);
73 static int local_fixup(struct ast_channel *oldchan, struct ast_channel *newchan);
74 static int local_sendhtml(struct ast_channel *ast, int subclass, const char *data, int datalen);
75 static int local_sendtext(struct ast_channel *ast, const char *text);
76 static int local_devicestate(void *data);
77 static struct ast_channel *local_bridgedchannel(struct ast_channel *chan, struct ast_channel *bridge);
78
79 /* PBX interface structure for channel registration */
80 static const struct ast_channel_tech local_tech = {
81         .type = "Local",
82         .description = tdesc,
83         .capabilities = -1,
84         .requester = local_request,
85         .send_digit_begin = local_digit_begin,
86         .send_digit_end = local_digit_end,
87         .call = local_call,
88         .hangup = local_hangup,
89         .answer = local_answer,
90         .read = local_read,
91         .write = local_write,
92         .write_video = local_write,
93         .exception = local_read,
94         .indicate = local_indicate,
95         .fixup = local_fixup,
96         .send_html = local_sendhtml,
97         .send_text = local_sendtext,
98         .devicestate = local_devicestate,
99         .bridged_channel = local_bridgedchannel,
100 };
101
102 struct local_pvt {
103         ast_mutex_t lock;                       /* Channel private lock */
104         unsigned int flags;                     /* Private flags */
105         char context[AST_MAX_CONTEXT];          /* Context to call */
106         char exten[AST_MAX_EXTENSION];          /* Extension to call */
107         int reqformat;                          /* Requested format */
108         struct ast_jb_conf jb_conf;             /*!< jitterbuffer configuration for this local channel */
109         struct ast_channel *owner;              /* Master Channel */
110         struct ast_channel *chan;               /* Outbound channel */
111         struct ast_module_user *u_owner;        /*! reference to keep the module loaded while in use */
112         struct ast_module_user *u_chan;         /*! reference to keep the module loaded while in use */
113         AST_LIST_ENTRY(local_pvt) list;         /* Next entity */
114 };
115
116 #define LOCAL_GLARE_DETECT    (1 << 0) /*!< Detect glare on hangup */
117 #define LOCAL_CANCEL_QUEUE    (1 << 1) /*!< Cancel queue */
118 #define LOCAL_ALREADY_MASQED  (1 << 2) /*!< Already masqueraded */
119 #define LOCAL_LAUNCHED_PBX    (1 << 3) /*!< PBX was launched */
120 #define LOCAL_NO_OPTIMIZATION (1 << 4) /*!< Do not optimize using masquerading */
121 #define LOCAL_BRIDGE          (1 << 5) /*!< Report back the "true" channel as being bridged to */
122
123 static AST_LIST_HEAD_STATIC(locals, local_pvt);
124
125 /*! \brief Adds devicestate to local channels */
126 static int local_devicestate(void *data)
127 {
128         char *exten = ast_strdupa(data);
129         char *context = NULL, *opts = NULL;
130         int res;
131         struct local_pvt *lp;
132
133         if (!(context = strchr(exten, '@'))) {
134                 ast_log(LOG_WARNING, "Someone used Local/%s somewhere without a @context. This is bad.\n", exten);
135                 return AST_DEVICE_INVALID;      
136         }
137
138         *context++ = '\0';
139
140         /* Strip options if they exist */
141         if ((opts = strchr(context, '/')))
142                 *opts = '\0';
143
144         ast_debug(3, "Checking if extension %s@%s exists (devicestate)\n", exten, context);
145
146         res = ast_exists_extension(NULL, context, exten, 1, NULL);
147         if (!res)               
148                 return AST_DEVICE_INVALID;
149         
150         res = AST_DEVICE_NOT_INUSE;
151         AST_LIST_LOCK(&locals);
152         AST_LIST_TRAVERSE(&locals, lp, list) {
153                 if (!strcmp(exten, lp->exten) && !strcmp(context, lp->context) && lp->owner) {
154                         res = AST_DEVICE_INUSE;
155                         break;
156                 }
157         }
158         AST_LIST_UNLOCK(&locals);
159
160         return res;
161 }
162
163 /*!
164  * \note Assumes the pvt is no longer in the pvts list
165  */
166 static struct local_pvt *local_pvt_destroy(struct local_pvt *pvt)
167 {
168         ast_mutex_destroy(&pvt->lock);
169         ast_free(pvt);
170         return NULL;
171 }
172
173 /*! \brief Return the bridged channel of a Local channel */
174 static struct ast_channel *local_bridgedchannel(struct ast_channel *chan, struct ast_channel *bridge)
175 {
176         struct local_pvt *p = bridge->tech_pvt;
177         struct ast_channel *bridged = bridge;
178
179         ast_mutex_lock(&p->lock);
180
181         if (ast_test_flag(p, LOCAL_BRIDGE)) {
182                 /* Find the opposite channel */
183                 bridged = (bridge == p->owner ? p->chan : p->owner);
184                 
185                 /* Now see if the opposite channel is bridged to anything */
186                 if (!bridged) {
187                         bridged = bridge;
188                 } else if (bridged->_bridge) {
189                         bridged = bridged->_bridge;
190                 }
191         }
192
193         ast_mutex_unlock(&p->lock);
194
195         return bridged;
196 }
197
198 static int local_queue_frame(struct local_pvt *p, int isoutbound, struct ast_frame *f, 
199         struct ast_channel *us, int us_locked)
200 {
201         struct ast_channel *other = NULL;
202
203         /* Recalculate outbound channel */
204         other = isoutbound ? p->owner : p->chan;
205
206         /* do not queue frame if generator is on both local channels */
207         if (us && us->generator && other->generator)
208                 return 0;
209
210         /* Set glare detection */
211         ast_set_flag(p, LOCAL_GLARE_DETECT);
212         if (ast_test_flag(p, LOCAL_CANCEL_QUEUE)) {
213                 /* We had a glare on the hangup.  Forget all this business,
214                 return and destroy p.  */
215                 ast_mutex_unlock(&p->lock);
216                 p = local_pvt_destroy(p);
217                 return -1;
218         }
219         if (!other) {
220                 ast_clear_flag(p, LOCAL_GLARE_DETECT);
221                 return 0;
222         }
223
224         /* Ensure that we have both channels locked */
225         while (other && ast_channel_trylock(other)) {
226                 ast_mutex_unlock(&p->lock);
227                 if (us && us_locked) {
228                         do {
229                                 CHANNEL_DEADLOCK_AVOIDANCE(us);
230                         } while (ast_mutex_trylock(&p->lock));
231                 } else {
232                         usleep(1);
233                         ast_mutex_lock(&p->lock);
234                 }
235                 other = isoutbound ? p->owner : p->chan;
236         }
237
238         if (other) {
239                 ast_queue_frame(other, f);
240                 ast_channel_unlock(other);
241         }
242
243         ast_clear_flag(p, LOCAL_GLARE_DETECT);
244
245         return 0;
246 }
247
248 static int local_answer(struct ast_channel *ast)
249 {
250         struct local_pvt *p = ast->tech_pvt;
251         int isoutbound;
252         int res = -1;
253
254         if (!p)
255                 return -1;
256
257         ast_mutex_lock(&p->lock);
258         isoutbound = IS_OUTBOUND(ast, p);
259         if (isoutbound) {
260                 /* Pass along answer since somebody answered us */
261                 struct ast_frame answer = { AST_FRAME_CONTROL, AST_CONTROL_ANSWER };
262                 res = local_queue_frame(p, isoutbound, &answer, ast, 1);
263         } else
264                 ast_log(LOG_WARNING, "Huh?  Local is being asked to answer?\n");
265         if (!res)
266                 ast_mutex_unlock(&p->lock);
267         return res;
268 }
269
270 static void check_bridge(struct local_pvt *p, int isoutbound)
271 {
272         struct ast_channel_monitor *tmp;
273         if (ast_test_flag(p, LOCAL_ALREADY_MASQED) || ast_test_flag(p, LOCAL_NO_OPTIMIZATION) || !p->chan || !p->owner || (p->chan->_bridge != ast_bridged_channel(p->chan)))
274                 return;
275
276         /* only do the masquerade if we are being called on the outbound channel,
277            if it has been bridged to another channel and if there are no pending
278            frames on the owner channel (because they would be transferred to the
279            outbound channel during the masquerade)
280         */
281         if (isoutbound && p->chan->_bridge /* Not ast_bridged_channel!  Only go one step! */ && AST_LIST_EMPTY(&p->owner->readq)) {
282                 /* Masquerade bridged channel into owner */
283                 /* Lock everything we need, one by one, and give up if
284                    we can't get everything.  Remember, we'll get another
285                    chance in just a little bit */
286                 if (!ast_channel_trylock(p->chan->_bridge)) {
287                         if (!ast_check_hangup(p->chan->_bridge)) {
288                                 if (!ast_channel_trylock(p->owner)) {
289                                         if (!ast_check_hangup(p->owner)) {
290                                                 if(p->owner->monitor && !p->chan->_bridge->monitor) {
291                                                         /* If a local channel is being monitored, we don't want a masquerade
292                                                          * to cause the monitor to go away. Since the masquerade swaps the monitors,
293                                                          * pre-swapping the monitors before the masquerade will ensure that the monitor
294                                                          * ends up where it is expected.
295                                                          */
296                                                         tmp = p->owner->monitor;
297                                                         p->owner->monitor = p->chan->_bridge->monitor;
298                                                         p->chan->_bridge->monitor = tmp;
299                                                 }
300                                                 ast_channel_masquerade(p->owner, p->chan->_bridge);
301                                                 ast_set_flag(p, LOCAL_ALREADY_MASQED);
302                                         }
303                                         ast_channel_unlock(p->owner);
304                                 }
305                                 ast_channel_unlock(p->chan->_bridge);
306                         }
307                 }
308         /* We only allow masquerading in one 'direction'... it's important to preserve the state
309            (group variables, etc.) that live on p->chan->_bridge (and were put there by the dialplan)
310            when the local channels go away.
311         */
312 #if 0
313         } else if (!isoutbound && p->owner && p->owner->_bridge && p->chan && AST_LIST_EMPTY(&p->chan->readq)) {
314                 /* Masquerade bridged channel into chan */
315                 if (!ast_mutex_trylock(&(p->owner->_bridge)->lock)) {
316                         if (!ast_check_hangup(p->owner->_bridge)) {
317                                 if (!ast_mutex_trylock(&p->chan->lock)) {
318                                         if (!ast_check_hangup(p->chan)) {
319                                                 ast_channel_masquerade(p->chan, p->owner->_bridge);
320                                                 ast_set_flag(p, LOCAL_ALREADY_MASQED);
321                                         }
322                                         ast_mutex_unlock(&p->chan->lock);
323                                 }
324                         }
325                         ast_mutex_unlock(&(p->owner->_bridge)->lock);
326                 }
327 #endif
328         }
329 }
330
331 static struct ast_frame  *local_read(struct ast_channel *ast)
332 {
333         return &ast_null_frame;
334 }
335
336 static int local_write(struct ast_channel *ast, struct ast_frame *f)
337 {
338         struct local_pvt *p = ast->tech_pvt;
339         int res = -1;
340         int isoutbound;
341
342         if (!p)
343                 return -1;
344
345         /* Just queue for delivery to the other side */
346         ast_mutex_lock(&p->lock);
347         isoutbound = IS_OUTBOUND(ast, p);
348         if (f && (f->frametype == AST_FRAME_VOICE || f->frametype == AST_FRAME_VIDEO))
349                 check_bridge(p, isoutbound);
350         if (!ast_test_flag(p, LOCAL_ALREADY_MASQED))
351                 res = local_queue_frame(p, isoutbound, f, ast, 1);
352         else {
353                 ast_debug(1, "Not posting to queue since already masked on '%s'\n", ast->name);
354                 res = 0;
355         }
356         if (!res)
357                 ast_mutex_unlock(&p->lock);
358         return res;
359 }
360
361 static int local_fixup(struct ast_channel *oldchan, struct ast_channel *newchan)
362 {
363         struct local_pvt *p = newchan->tech_pvt;
364
365         if (!p)
366                 return -1;
367
368         ast_mutex_lock(&p->lock);
369
370         if ((p->owner != oldchan) && (p->chan != oldchan)) {
371                 ast_log(LOG_WARNING, "Old channel wasn't %p but was %p/%p\n", oldchan, p->owner, p->chan);
372                 ast_mutex_unlock(&p->lock);
373                 return -1;
374         }
375         if (p->owner == oldchan)
376                 p->owner = newchan;
377         else
378                 p->chan = newchan;
379         ast_mutex_unlock(&p->lock);
380         return 0;
381 }
382
383 static int local_indicate(struct ast_channel *ast, int condition, const void *data, size_t datalen)
384 {
385         struct local_pvt *p = ast->tech_pvt;
386         int res = 0;
387         struct ast_frame f = { AST_FRAME_CONTROL, };
388         int isoutbound;
389
390         if (!p)
391                 return -1;
392
393         /* If this is an MOH hold or unhold, do it on the Local channel versus real channel */
394         if (condition == AST_CONTROL_HOLD) {
395                 ast_moh_start(ast, data, NULL);
396         } else if (condition == AST_CONTROL_UNHOLD) {
397                 ast_moh_stop(ast);
398         } else {
399                 /* Queue up a frame representing the indication as a control frame */
400                 ast_mutex_lock(&p->lock);
401                 isoutbound = IS_OUTBOUND(ast, p);
402                 f.subclass = condition;
403                 f.data.ptr = (void*)data;
404                 f.datalen = datalen;
405                 if (!(res = local_queue_frame(p, isoutbound, &f, ast, 1)))
406                         ast_mutex_unlock(&p->lock);
407         }
408
409         return res;
410 }
411
412 static int local_digit_begin(struct ast_channel *ast, char digit)
413 {
414         struct local_pvt *p = ast->tech_pvt;
415         int res = -1;
416         struct ast_frame f = { AST_FRAME_DTMF_BEGIN, };
417         int isoutbound;
418
419         if (!p)
420                 return -1;
421
422         ast_mutex_lock(&p->lock);
423         isoutbound = IS_OUTBOUND(ast, p);
424         f.subclass = digit;
425         if (!(res = local_queue_frame(p, isoutbound, &f, ast, 0)))
426                 ast_mutex_unlock(&p->lock);
427
428         return res;
429 }
430
431 static int local_digit_end(struct ast_channel *ast, char digit, unsigned int duration)
432 {
433         struct local_pvt *p = ast->tech_pvt;
434         int res = -1;
435         struct ast_frame f = { AST_FRAME_DTMF_END, };
436         int isoutbound;
437
438         if (!p)
439                 return -1;
440
441         ast_mutex_lock(&p->lock);
442         isoutbound = IS_OUTBOUND(ast, p);
443         f.subclass = digit;
444         f.len = duration;
445         if (!(res = local_queue_frame(p, isoutbound, &f, ast, 0)))
446                 ast_mutex_unlock(&p->lock);
447
448         return res;
449 }
450
451 static int local_sendtext(struct ast_channel *ast, const char *text)
452 {
453         struct local_pvt *p = ast->tech_pvt;
454         int res = -1;
455         struct ast_frame f = { AST_FRAME_TEXT, };
456         int isoutbound;
457
458         if (!p)
459                 return -1;
460
461         ast_mutex_lock(&p->lock);
462         isoutbound = IS_OUTBOUND(ast, p);
463         f.data.ptr = (char *) text;
464         f.datalen = strlen(text) + 1;
465         if (!(res = local_queue_frame(p, isoutbound, &f, ast, 0)))
466                 ast_mutex_unlock(&p->lock);
467         return res;
468 }
469
470 static int local_sendhtml(struct ast_channel *ast, int subclass, const char *data, int datalen)
471 {
472         struct local_pvt *p = ast->tech_pvt;
473         int res = -1;
474         struct ast_frame f = { AST_FRAME_HTML, };
475         int isoutbound;
476
477         if (!p)
478                 return -1;
479         
480         ast_mutex_lock(&p->lock);
481         isoutbound = IS_OUTBOUND(ast, p);
482         f.subclass = subclass;
483         f.data.ptr = (char *)data;
484         f.datalen = datalen;
485         if (!(res = local_queue_frame(p, isoutbound, &f, ast, 0)))
486                 ast_mutex_unlock(&p->lock);
487         return res;
488 }
489
490 /*! \brief Initiate new call, part of PBX interface 
491  *      dest is the dial string */
492 static int local_call(struct ast_channel *ast, char *dest, int timeout)
493 {
494         struct local_pvt *p = ast->tech_pvt;
495         int res;
496         struct ast_var_t *varptr = NULL, *new;
497         size_t len, namelen;
498
499         if (!p)
500                 return -1;
501         
502         ast_mutex_lock(&p->lock);
503
504         /*
505          * Note that cid_num and cid_name aren't passed in the ast_channel_alloc
506          * call, so it's done here instead.
507          */
508         p->chan->cid.cid_dnid = ast_strdup(p->owner->cid.cid_dnid);
509         p->chan->cid.cid_num = ast_strdup(p->owner->cid.cid_num);
510         p->chan->cid.cid_name = ast_strdup(p->owner->cid.cid_name);
511         p->chan->cid.cid_rdnis = ast_strdup(p->owner->cid.cid_rdnis);
512         p->chan->cid.cid_ani = ast_strdup(p->owner->cid.cid_ani);
513         p->chan->cid.cid_pres = p->owner->cid.cid_pres;
514         p->chan->cid.cid_ani2 = p->owner->cid.cid_ani2;
515         p->chan->cid.cid_ton = p->owner->cid.cid_ton;
516         p->chan->cid.cid_tns = p->owner->cid.cid_tns;
517         ast_string_field_set(p->chan, language, p->owner->language);
518         ast_string_field_set(p->chan, accountcode, p->owner->accountcode);
519         ast_cdr_update(p->chan);
520         p->chan->cdrflags = p->owner->cdrflags;
521
522         if (!ast_exists_extension(NULL, p->chan->context, p->chan->exten, 1, p->owner->cid.cid_num)) {
523                 ast_log(LOG_NOTICE, "No such extension/context %s@%s while calling Local channel\n", p->chan->exten, p->chan->context);
524                 ast_mutex_unlock(&p->lock);
525                 return -1;
526         }
527
528         /* copy the channel variables from the incoming channel to the outgoing channel */
529         /* Note that due to certain assumptions, they MUST be in the same order */
530         AST_LIST_TRAVERSE(&p->owner->varshead, varptr, entries) {
531                 namelen = strlen(varptr->name);
532                 len = sizeof(struct ast_var_t) + namelen + strlen(varptr->value) + 2;
533                 if ((new = ast_calloc(1, len))) {
534                         memcpy(new, varptr, len);
535                         new->value = &(new->name[0]) + namelen + 1;
536                         AST_LIST_INSERT_TAIL(&p->chan->varshead, new, entries);
537                 }
538         }
539         ast_channel_datastore_inherit(p->owner, p->chan);
540
541         /* Start switch on sub channel */
542         if (!(res = ast_pbx_start(p->chan)))
543                 ast_set_flag(p, LOCAL_LAUNCHED_PBX);
544
545         ast_mutex_unlock(&p->lock);
546         return res;
547 }
548
549 /*! \brief Hangup a call through the local proxy channel */
550 static int local_hangup(struct ast_channel *ast)
551 {
552         struct local_pvt *p = ast->tech_pvt;
553         int isoutbound;
554         struct ast_frame f = { AST_FRAME_CONTROL, AST_CONTROL_HANGUP, .data.uint32 = ast->hangupcause };
555         struct ast_channel *ochan = NULL;
556         int glaredetect = 0, res = 0;
557
558         if (!p)
559                 return -1;
560
561         ast_mutex_lock(&p->lock);
562
563         if (p->chan && ast_test_flag(ast, AST_FLAG_ANSWERED_ELSEWHERE)) 
564                 ast_set_flag(p->chan, AST_FLAG_ANSWERED_ELSEWHERE);
565         isoutbound = IS_OUTBOUND(ast, p);
566         if (isoutbound) {
567                 const char *status = pbx_builtin_getvar_helper(p->chan, "DIALSTATUS");
568                 if ((status) && (p->owner)) {
569                         /* Deadlock avoidance */
570                         while (p->owner && ast_channel_trylock(p->owner)) {
571                                 ast_mutex_unlock(&p->lock);
572                                 if (ast) {
573                                         ast_channel_unlock(ast);
574                                 }
575                                 usleep(1);
576                                 if (ast) {
577                                         ast_channel_lock(ast);
578                                 }
579                                 ast_mutex_lock(&p->lock);
580                         }
581                         if (p->owner) {
582                                 pbx_builtin_setvar_helper(p->owner, "CHANLOCALSTATUS", status);
583                                 ast_channel_unlock(p->owner);
584                         }
585                 }
586                 p->chan = NULL;
587                 ast_clear_flag(p, LOCAL_LAUNCHED_PBX);
588                 ast_module_user_remove(p->u_chan);
589         } else {
590                 p->owner = NULL;
591                 ast_module_user_remove(p->u_owner);
592                 while (p->chan && ast_channel_trylock(p->chan)) {
593                         DEADLOCK_AVOIDANCE(&p->lock);
594                 }
595                 if (p->chan) {
596                         ast_queue_hangup(p->chan);
597                         ast_channel_unlock(p->chan);
598                 }
599         }
600         
601         ast->tech_pvt = NULL;
602         
603         if (!p->owner && !p->chan) {
604                 /* Okay, done with the private part now, too. */
605                 glaredetect = ast_test_flag(p, LOCAL_GLARE_DETECT);
606                 /* If we have a queue holding, don't actually destroy p yet, but
607                    let local_queue do it. */
608                 if (glaredetect)
609                         ast_set_flag(p, LOCAL_CANCEL_QUEUE);
610                 ast_mutex_unlock(&p->lock);
611                 /* Remove from list */
612                 AST_LIST_LOCK(&locals);
613                 AST_LIST_REMOVE(&locals, p, list);
614                 AST_LIST_UNLOCK(&locals);
615                 /* Grab / release lock just in case */
616                 ast_mutex_lock(&p->lock);
617                 ast_mutex_unlock(&p->lock);
618                 /* And destroy */
619                 if (!glaredetect) {
620                         p = local_pvt_destroy(p);
621                 }
622                 return 0;
623         }
624         if (p->chan && !ast_test_flag(p, LOCAL_LAUNCHED_PBX))
625                 /* Need to actually hangup since there is no PBX */
626                 ochan = p->chan;
627         else
628                 res = local_queue_frame(p, isoutbound, &f, NULL, 1);
629         if (!res)
630                 ast_mutex_unlock(&p->lock);
631         if (ochan)
632                 ast_hangup(ochan);
633         return 0;
634 }
635
636 /*! \brief Create a call structure */
637 static struct local_pvt *local_alloc(const char *data, int format)
638 {
639         struct local_pvt *tmp = NULL;
640         char *c = NULL, *opts = NULL;
641
642         if (!(tmp = ast_calloc(1, sizeof(*tmp))))
643                 return NULL;
644
645         /* Initialize private structure information */
646         ast_mutex_init(&tmp->lock);
647         ast_copy_string(tmp->exten, data, sizeof(tmp->exten));
648
649         memcpy(&tmp->jb_conf, &g_jb_conf, sizeof(tmp->jb_conf));
650
651         /* Look for options */
652         if ((opts = strchr(tmp->exten, '/'))) {
653                 *opts++ = '\0';
654                 if (strchr(opts, 'n'))
655                         ast_set_flag(tmp, LOCAL_NO_OPTIMIZATION);
656                 if (strchr(opts, 'j')) {
657                         if (ast_test_flag(tmp, LOCAL_NO_OPTIMIZATION))
658                                 ast_set_flag(&tmp->jb_conf, AST_JB_ENABLED);
659                         else {
660                                 ast_log(LOG_ERROR, "You must use the 'n' option for chan_local "
661                                         "to use the 'j' option to enable the jitterbuffer\n");
662                         }
663                 }
664                 if (strchr(opts, 'b')) {
665                         ast_set_flag(tmp, LOCAL_BRIDGE);
666                 }
667         }
668
669         /* Look for a context */
670         if ((c = strchr(tmp->exten, '@')))
671                 *c++ = '\0';
672
673         ast_copy_string(tmp->context, c ? c : "default", sizeof(tmp->context));
674
675         tmp->reqformat = format;
676
677 #if 0
678         /* We can't do this check here, because we don't know the CallerID yet, and
679          * the CallerID could potentially affect what step is actually taken (or
680          * even if that step exists). */
681         if (!ast_exists_extension(NULL, tmp->context, tmp->exten, 1, NULL)) {
682                 ast_log(LOG_NOTICE, "No such extension/context %s@%s creating local channel\n", tmp->exten, tmp->context);
683                 tmp = local_pvt_destroy(tmp);
684         } else {
685 #endif
686                 /* Add to list */
687                 AST_LIST_LOCK(&locals);
688                 AST_LIST_INSERT_HEAD(&locals, tmp, list);
689                 AST_LIST_UNLOCK(&locals);
690 #if 0
691         }
692 #endif
693         
694         return tmp;
695 }
696
697 /*! \brief Start new local channel */
698 static struct ast_channel *local_new(struct local_pvt *p, int state)
699 {
700         struct ast_channel *tmp = NULL, *tmp2 = NULL;
701         int randnum = ast_random() & 0xffff, fmt = 0;
702         const char *t;
703         int ama;
704
705         /* Allocate two new Asterisk channels */
706         /* safe accountcode */
707         if (p->owner && p->owner->accountcode)
708                 t = p->owner->accountcode;
709         else
710                 t = "";
711
712         if (p->owner)
713                 ama = p->owner->amaflags;
714         else
715                 ama = 0;
716         if (!(tmp = ast_channel_alloc(1, state, 0, 0, t, p->exten, p->context, ama, "Local/%s@%s-%04x;1", p->exten, p->context, randnum)) 
717                         || !(tmp2 = ast_channel_alloc(1, AST_STATE_RING, 0, 0, t, p->exten, p->context, ama, "Local/%s@%s-%04x;2", p->exten, p->context, randnum))) {
718                 if (tmp)
719                         ast_channel_free(tmp);
720                 if (tmp2)
721                         ast_channel_free(tmp2);
722                 ast_log(LOG_WARNING, "Unable to allocate channel structure(s)\n");
723                 return NULL;
724         } 
725
726         tmp2->tech = tmp->tech = &local_tech;
727
728         tmp->nativeformats = p->reqformat;
729         tmp2->nativeformats = p->reqformat;
730
731         /* Determine our read/write format and set it on each channel */
732         fmt = ast_best_codec(p->reqformat);
733         tmp->writeformat = fmt;
734         tmp2->writeformat = fmt;
735         tmp->rawwriteformat = fmt;
736         tmp2->rawwriteformat = fmt;
737         tmp->readformat = fmt;
738         tmp2->readformat = fmt;
739         tmp->rawreadformat = fmt;
740         tmp2->rawreadformat = fmt;
741
742         tmp->tech_pvt = p;
743         tmp2->tech_pvt = p;
744
745         p->owner = tmp;
746         p->chan = tmp2;
747         p->u_owner = ast_module_user_add(p->owner);
748         p->u_chan = ast_module_user_add(p->chan);
749
750         ast_copy_string(tmp->context, p->context, sizeof(tmp->context));
751         ast_copy_string(tmp2->context, p->context, sizeof(tmp2->context));
752         ast_copy_string(tmp2->exten, p->exten, sizeof(tmp->exten));
753         tmp->priority = 1;
754         tmp2->priority = 1;
755
756         ast_jb_configure(tmp, &p->jb_conf);
757
758         return tmp;
759 }
760
761 /*! \brief Part of PBX interface */
762 static struct ast_channel *local_request(const char *type, int format, void *data, int *cause)
763 {
764         struct local_pvt *p = NULL;
765         struct ast_channel *chan = NULL;
766
767         /* Allocate a new private structure and then Asterisk channel */
768         if ((p = local_alloc(data, format))) {
769                 if (!(chan = local_new(p, AST_STATE_DOWN))) {
770                         AST_LIST_LOCK(&locals);
771                         AST_LIST_REMOVE(&locals, p, list);
772                         AST_LIST_UNLOCK(&locals);
773                         p = local_pvt_destroy(p);
774                 }
775         }
776
777         return chan;
778 }
779
780 /*! \brief CLI command "local show channels" */
781 static char *locals_show(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
782 {
783         struct local_pvt *p = NULL;
784
785         switch (cmd) {
786         case CLI_INIT:
787                 e->command = "local show channels";
788                 e->usage =
789                         "Usage: local show channels\n"
790                         "       Provides summary information on active local proxy channels.\n";
791                 return NULL;
792         case CLI_GENERATE:
793                 return NULL;
794         }
795
796         if (a->argc != 3)
797                 return CLI_SHOWUSAGE;
798
799         AST_LIST_LOCK(&locals);
800         if (!AST_LIST_EMPTY(&locals)) {
801                 AST_LIST_TRAVERSE(&locals, p, list) {
802                         ast_mutex_lock(&p->lock);
803                         ast_cli(a->fd, "%s -- %s@%s\n", p->owner ? p->owner->name : "<unowned>", p->exten, p->context);
804                         ast_mutex_unlock(&p->lock);
805                 }
806         } else
807                 ast_cli(a->fd, "No local channels in use\n");
808         AST_LIST_UNLOCK(&locals);
809
810         return CLI_SUCCESS;
811 }
812
813 static struct ast_cli_entry cli_local[] = {
814         AST_CLI_DEFINE(locals_show, "List status of local channels"),
815 };
816
817 /*! \brief Load module into PBX, register channel */
818 static int load_module(void)
819 {
820         /* Make sure we can register our channel type */
821         if (ast_channel_register(&local_tech)) {
822                 ast_log(LOG_ERROR, "Unable to register channel class 'Local'\n");
823                 return AST_MODULE_LOAD_FAILURE;
824         }
825         ast_cli_register_multiple(cli_local, sizeof(cli_local) / sizeof(struct ast_cli_entry));
826         return AST_MODULE_LOAD_SUCCESS;
827 }
828
829 /*! \brief Unload the local proxy channel from Asterisk */
830 static int unload_module(void)
831 {
832         struct local_pvt *p = NULL;
833
834         /* First, take us out of the channel loop */
835         ast_cli_unregister_multiple(cli_local, sizeof(cli_local) / sizeof(struct ast_cli_entry));
836         ast_channel_unregister(&local_tech);
837         if (!AST_LIST_LOCK(&locals)) {
838                 /* Hangup all interfaces if they have an owner */
839                 AST_LIST_TRAVERSE(&locals, p, list) {
840                         if (p->owner)
841                                 ast_softhangup(p->owner, AST_SOFTHANGUP_APPUNLOAD);
842                 }
843                 AST_LIST_UNLOCK(&locals);
844         } else {
845                 ast_log(LOG_WARNING, "Unable to lock the monitor\n");
846                 return -1;
847         }               
848         return 0;
849 }
850
851 AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "Local Proxy Channel (Note: used internally by other modules)");