e8f717b3f16aee9e8675484a9b2b8ee6ef4e0d75
[asterisk/asterisk.git] / apps / app_jack.c
1 /*
2  * Asterisk -- An open source telephony toolkit.
3  *
4  * Copyright (C) 2007 - 2008, Russell Bryant
5  *
6  * Russell Bryant <russell@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 /*!
20  * \file
21  * \brief Jack Application
22  *
23  * \author Russell Bryant <russell@digium.com>
24  *
25  * This is an application to connect an Asterisk channel to an input
26  * and output jack port so that the audio can be processed through
27  * another application, or to play audio from another application.
28  *
29  * \extref http://www.jackaudio.org/
30  *
31  * \note To install libresample, check it out of the following repository:
32  * <code>$ svn co http://svn.digium.com/svn/thirdparty/libresample/trunk</code>
33  *
34  * \ingroup applications
35  */
36
37 /*** MODULEINFO
38         <depend>jack</depend>
39         <depend>resample</depend>
40  ***/
41
42 #include "asterisk.h"
43
44 ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
45
46 #include <limits.h>
47
48 #include <jack/jack.h>
49 #include <jack/ringbuffer.h>
50
51 #include <libresample.h>
52
53 #include "asterisk/module.h"
54 #include "asterisk/channel.h"
55 #include "asterisk/strings.h"
56 #include "asterisk/lock.h"
57 #include "asterisk/app.h"
58 #include "asterisk/pbx.h"
59 #include "asterisk/audiohook.h"
60
61 #define RESAMPLE_QUALITY 1
62
63 #define RINGBUFFER_SIZE 16384
64
65 /*! \brief Common options between the Jack() app and JACK_HOOK() function */
66 #define COMMON_OPTIONS \
67 "    s(<name>) - Connect to the specified jack server name.\n" \
68 "    i(<name>) - Connect the output port that gets created to the specified\n" \
69 "                jack input port.\n" \
70 "    o(<name>) - Connect the input port that gets created to the specified\n" \
71 "                jack output port.\n" \
72 "    n         - Do not automatically start the JACK server if it is not already\n" \
73 "                running.\n" \
74 "    c(<name>) - By default, Asterisk will use the channel name for the jack client\n" \
75 "                name.  Use this option to specify a custom client name.\n"
76 /*** DOCUMENTATION
77         <application name="JACK" language="en_US">
78                 <synopsis>
79                         Jack Audio Connection Kit
80                 </synopsis>
81                 <syntax>
82                         <parameter name="options" required="false">
83                                 <optionlist>
84                                         <option name="s">
85                                                 <argument name="name" required="true">
86                                                         <para>Connect to the specified jack server name</para>
87                                                 </argument>
88                                         </option>
89                                         <option name="i">
90                                                 <argument name="name" required="true">
91                                                         <para>Connect the output port that gets created to the specified jack input port</para>
92                                                 </argument>
93                                         </option>
94                                         <option name="o">
95                                                 <argument name="name" required="true">
96                                                         <para>Connect the input port that gets created to the specified jack output port</para>
97                                                 </argument>
98                                         </option>
99                                         <option name="c">
100                                                 <argument name="name" required="true">
101                                                         <para>By default, Asterisk will use the channel name for the jack client name.</para>
102                                                         <para>Use this option to specify a custom client name.</para>
103                                                 </argument>
104                                         </option>
105                                 </optionlist>
106                         </parameter>
107                 </syntax>
108                 <description>
109                         <para>When executing this application, two jack ports will be created;
110                         one input and one output. Other applications can be hooked up to
111                         these ports to access audio coming from, or being send to the channel.</para>
112                 </description>
113         </application>
114  ***/
115
116 static const char jack_app[] = "JACK";
117
118 struct jack_data {
119         AST_DECLARE_STRING_FIELDS(
120                 AST_STRING_FIELD(server_name);
121                 AST_STRING_FIELD(client_name);
122                 AST_STRING_FIELD(connect_input_port);
123                 AST_STRING_FIELD(connect_output_port);
124         );
125         jack_client_t *client;
126         jack_port_t *input_port;
127         jack_port_t *output_port;
128         jack_ringbuffer_t *input_rb;
129         jack_ringbuffer_t *output_rb;
130         void *output_resampler;
131         double output_resample_factor;
132         void *input_resampler;
133         double input_resample_factor;
134         unsigned int stop:1;
135         unsigned int has_audiohook:1;
136         unsigned int no_start_server:1;
137         /*! Only used with JACK_HOOK */
138         struct ast_audiohook audiohook;
139 };
140
141 static const struct {
142         jack_status_t status;
143         const char *str;
144 } jack_status_table[] = {
145         { JackFailure,        "Failure" },
146         { JackInvalidOption,  "Invalid Option" },
147         { JackNameNotUnique,  "Name Not Unique" },
148         { JackServerStarted,  "Server Started" },
149         { JackServerFailed,   "Server Failed" },
150         { JackServerError,    "Server Error" },
151         { JackNoSuchClient,   "No Such Client" },
152         { JackLoadFailure,    "Load Failure" },
153         { JackInitFailure,    "Init Failure" },
154         { JackShmFailure,     "Shared Memory Access Failure" },
155         { JackVersionError,   "Version Mismatch" },
156 };
157
158 static const char *jack_status_to_str(jack_status_t status)
159 {
160         int i;
161
162         for (i = 0; i < ARRAY_LEN(jack_status_table); i++) {
163                 if (jack_status_table[i].status == status)
164                         return jack_status_table[i].str;
165         }
166
167         return "Unknown Error";
168 }
169
170 static void log_jack_status(const char *prefix, jack_status_t status)
171 {
172         struct ast_str *str = ast_str_alloca(512);
173         int i, first = 0;
174
175         for (i = 0; i < (sizeof(status) * 8); i++) {
176                 if (!(status & (1 << i)))
177                         continue;
178
179                 if (!first) {
180                         ast_str_set(&str, 0, "%s", jack_status_to_str((1 << i)));
181                         first = 1;
182                 } else
183                         ast_str_append(&str, 0, ", %s", jack_status_to_str((1 << i)));
184         }
185
186         ast_log(LOG_NOTICE, "%s: %s\n", prefix, ast_str_buffer(str));
187 }
188
189 static int alloc_resampler(struct jack_data *jack_data, int input)
190 {
191         double from_srate, to_srate, jack_srate;
192         void **resampler;
193         double *resample_factor;
194
195         if (input && jack_data->input_resampler)
196                 return 0;
197
198         if (!input && jack_data->output_resampler)
199                 return 0;
200
201         jack_srate = jack_get_sample_rate(jack_data->client);
202
203         /* XXX Hard coded 8 kHz */
204
205         to_srate = input ? 8000.0 : jack_srate;
206         from_srate = input ? jack_srate : 8000.0;
207
208         resample_factor = input ? &jack_data->input_resample_factor :
209                 &jack_data->output_resample_factor;
210
211         if (from_srate == to_srate) {
212                 /* Awesome!  The jack sample rate is the same as ours.
213                  * Resampling isn't needed. */
214                 *resample_factor = 1.0;
215                 return 0;
216         }
217
218         *resample_factor = to_srate / from_srate;
219
220         resampler = input ? &jack_data->input_resampler :
221                 &jack_data->output_resampler;
222
223         if (!(*resampler = resample_open(RESAMPLE_QUALITY,
224                 *resample_factor, *resample_factor))) {
225                 ast_log(LOG_ERROR, "Failed to open %s resampler\n",
226                         input ? "input" : "output");
227                 return -1;
228         }
229
230         return 0;
231 }
232
233 /*!
234  * \brief Handle jack input port
235  *
236  * Read nframes number of samples from the input buffer, resample it
237  * if necessary, and write it into the appropriate ringbuffer.
238  */
239 static void handle_input(void *buf, jack_nframes_t nframes,
240         struct jack_data *jack_data)
241 {
242         short s_buf[nframes];
243         float *in_buf = buf;
244         size_t res;
245         int i;
246         size_t write_len = sizeof(s_buf);
247
248         if (jack_data->input_resampler) {
249                 int total_in_buf_used = 0;
250                 int total_out_buf_used = 0;
251                 float f_buf[nframes + 1];
252
253                 memset(f_buf, 0, sizeof(f_buf));
254
255                 while (total_in_buf_used < nframes) {
256                         int in_buf_used;
257                         int out_buf_used;
258
259                         out_buf_used = resample_process(jack_data->input_resampler,
260                                 jack_data->input_resample_factor,
261                                 &in_buf[total_in_buf_used], nframes - total_in_buf_used,
262                                 0, &in_buf_used,
263                                 &f_buf[total_out_buf_used], ARRAY_LEN(f_buf) - total_out_buf_used);
264
265                         if (out_buf_used < 0)
266                                 break;
267
268                         total_out_buf_used += out_buf_used;
269                         total_in_buf_used += in_buf_used;
270
271                         if (total_out_buf_used == ARRAY_LEN(f_buf)) {
272                                 ast_log(LOG_ERROR, "Output buffer filled ... need to increase its size, "
273                                         "nframes '%d', total_out_buf_used '%d'\n", nframes, total_out_buf_used);
274                                 break;
275                         }
276                 }
277
278                 for (i = 0; i < total_out_buf_used; i++)
279                         s_buf[i] = f_buf[i] * (SHRT_MAX / 1.0);
280
281                 write_len = total_out_buf_used * sizeof(int16_t);
282         } else {
283                 /* No resampling needed */
284
285                 for (i = 0; i < nframes; i++)
286                         s_buf[i] = in_buf[i] * (SHRT_MAX / 1.0);
287         }
288
289         res = jack_ringbuffer_write(jack_data->input_rb, (const char *) s_buf, write_len);
290         if (res != write_len) {
291                 ast_debug(2, "Tried to write %d bytes to the ringbuffer, but only wrote %d\n",
292                         (int) sizeof(s_buf), (int) res);
293         }
294 }
295
296 /*!
297  * \brief Handle jack output port
298  *
299  * Read nframes number of samples from the ringbuffer and write it out to the
300  * output port buffer.
301  */
302 static void handle_output(void *buf, jack_nframes_t nframes,
303         struct jack_data *jack_data)
304 {
305         size_t res, len;
306
307         len = nframes * sizeof(float);
308
309         res = jack_ringbuffer_read(jack_data->output_rb, buf, len);
310
311         if (len != res) {
312                 ast_debug(2, "Wanted %d bytes to send to the output port, "
313                         "but only got %d\n", (int) len, (int) res);
314         }
315 }
316
317 static int jack_process(jack_nframes_t nframes, void *arg)
318 {
319         struct jack_data *jack_data = arg;
320         void *input_port_buf, *output_port_buf;
321
322         if (!jack_data->input_resample_factor)
323                 alloc_resampler(jack_data, 1);
324
325         input_port_buf = jack_port_get_buffer(jack_data->input_port, nframes);
326         handle_input(input_port_buf, nframes, jack_data);
327
328         output_port_buf = jack_port_get_buffer(jack_data->output_port, nframes);
329         handle_output(output_port_buf, nframes, jack_data);
330
331         return 0;
332 }
333
334 static void jack_shutdown(void *arg)
335 {
336         struct jack_data *jack_data = arg;
337
338         jack_data->stop = 1;
339 }
340
341 static struct jack_data *destroy_jack_data(struct jack_data *jack_data)
342 {
343         if (jack_data->input_port) {
344                 jack_port_unregister(jack_data->client, jack_data->input_port);
345                 jack_data->input_port = NULL;
346         }
347
348         if (jack_data->output_port) {
349                 jack_port_unregister(jack_data->client, jack_data->output_port);
350                 jack_data->output_port = NULL;
351         }
352
353         if (jack_data->client) {
354                 jack_client_close(jack_data->client);
355                 jack_data->client = NULL;
356         }
357
358         if (jack_data->input_rb) {
359                 jack_ringbuffer_free(jack_data->input_rb);
360                 jack_data->input_rb = NULL;
361         }
362
363         if (jack_data->output_rb) {
364                 jack_ringbuffer_free(jack_data->output_rb);
365                 jack_data->output_rb = NULL;
366         }
367
368         if (jack_data->output_resampler) {
369                 resample_close(jack_data->output_resampler);
370                 jack_data->output_resampler = NULL;
371         }
372
373         if (jack_data->input_resampler) {
374                 resample_close(jack_data->input_resampler);
375                 jack_data->input_resampler = NULL;
376         }
377
378         if (jack_data->has_audiohook)
379                 ast_audiohook_destroy(&jack_data->audiohook);
380
381         ast_string_field_free_memory(jack_data);
382
383         ast_free(jack_data);
384
385         return NULL;
386 }
387
388 static int init_jack_data(struct ast_channel *chan, struct jack_data *jack_data)
389 {
390         const char *client_name;
391         jack_status_t status = 0;
392         jack_options_t jack_options = JackNullOption;
393
394         if (!ast_strlen_zero(jack_data->client_name)) {
395                 client_name = jack_data->client_name;
396         } else {
397                 ast_channel_lock(chan);
398                 client_name = ast_strdupa(chan->name);
399                 ast_channel_unlock(chan);
400         }
401
402         if (!(jack_data->output_rb = jack_ringbuffer_create(RINGBUFFER_SIZE)))
403                 return -1;
404
405         if (!(jack_data->input_rb = jack_ringbuffer_create(RINGBUFFER_SIZE)))
406                 return -1;
407
408         if (jack_data->no_start_server)
409                 jack_options |= JackNoStartServer;
410
411         if (!ast_strlen_zero(jack_data->server_name)) {
412                 jack_options |= JackServerName;
413                 jack_data->client = jack_client_open(client_name, jack_options, &status,
414                         jack_data->server_name);
415         } else {
416                 jack_data->client = jack_client_open(client_name, jack_options, &status);
417         }
418
419         if (status)
420                 log_jack_status("Client Open Status", status);
421
422         if (!jack_data->client)
423                 return -1;
424
425         jack_data->input_port = jack_port_register(jack_data->client, "input",
426                 JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput | JackPortIsTerminal, 0);
427         if (!jack_data->input_port) {
428                 ast_log(LOG_ERROR, "Failed to create input port for jack port\n");
429                 return -1;
430         }
431
432         jack_data->output_port = jack_port_register(jack_data->client, "output",
433                 JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput | JackPortIsTerminal, 0);
434         if (!jack_data->output_port) {
435                 ast_log(LOG_ERROR, "Failed to create output port for jack port\n");
436                 return -1;
437         }
438
439         if (jack_set_process_callback(jack_data->client, jack_process, jack_data)) {
440                 ast_log(LOG_ERROR, "Failed to register process callback with jack client\n");
441                 return -1;
442         }
443
444         jack_on_shutdown(jack_data->client, jack_shutdown, jack_data);
445
446         if (jack_activate(jack_data->client)) {
447                 ast_log(LOG_ERROR, "Unable to activate jack client\n");
448                 return -1;
449         }
450
451         while (!ast_strlen_zero(jack_data->connect_input_port)) {
452                 const char **ports;
453                 int i;
454
455                 ports = jack_get_ports(jack_data->client, jack_data->connect_input_port,
456                         NULL, JackPortIsInput);
457
458                 if (!ports) {
459                         ast_log(LOG_ERROR, "No input port matching '%s' was found\n",
460                                 jack_data->connect_input_port);
461                         break;
462                 }
463
464                 for (i = 0; ports[i]; i++) {
465                         ast_debug(1, "Found port '%s' that matched specified input port '%s'\n",
466                                 ports[i], jack_data->connect_input_port);
467                 }
468
469                 if (jack_connect(jack_data->client, jack_port_name(jack_data->output_port), ports[0])) {
470                         ast_log(LOG_ERROR, "Failed to connect '%s' to '%s'\n", ports[0],
471                                 jack_port_name(jack_data->output_port));
472                 } else {
473                         ast_debug(1, "Connected '%s' to '%s'\n", ports[0],
474                                 jack_port_name(jack_data->output_port));
475                 }
476
477                 free((void *) ports);
478
479                 break;
480         }
481
482         while (!ast_strlen_zero(jack_data->connect_output_port)) {
483                 const char **ports;
484                 int i;
485
486                 ports = jack_get_ports(jack_data->client, jack_data->connect_output_port,
487                         NULL, JackPortIsOutput);
488
489                 if (!ports) {
490                         ast_log(LOG_ERROR, "No output port matching '%s' was found\n",
491                                 jack_data->connect_output_port);
492                         break;
493                 }
494
495                 for (i = 0; ports[i]; i++) {
496                         ast_debug(1, "Found port '%s' that matched specified output port '%s'\n",
497                                 ports[i], jack_data->connect_output_port);
498                 }
499
500                 if (jack_connect(jack_data->client, ports[0], jack_port_name(jack_data->input_port))) {
501                         ast_log(LOG_ERROR, "Failed to connect '%s' to '%s'\n", ports[0],
502                                 jack_port_name(jack_data->input_port));
503                 } else {
504                         ast_debug(1, "Connected '%s' to '%s'\n", ports[0],
505                                 jack_port_name(jack_data->input_port));
506                 }
507
508                 free((void *) ports);
509
510                 break;
511         }
512
513         return 0;
514 }
515
516 static int queue_voice_frame(struct jack_data *jack_data, struct ast_frame *f)
517 {
518         float f_buf[f->samples * 8];
519         size_t f_buf_used = 0;
520         int i;
521         int16_t *s_buf = f->data.ptr;
522         size_t res;
523
524         memset(f_buf, 0, sizeof(f_buf));
525
526         if (!jack_data->output_resample_factor)
527                 alloc_resampler(jack_data, 0);
528
529         if (jack_data->output_resampler) {
530                 float in_buf[f->samples];
531                 int total_in_buf_used = 0;
532                 int total_out_buf_used = 0;
533
534                 memset(in_buf, 0, sizeof(in_buf));
535
536                 for (i = 0; i < f->samples; i++)
537                         in_buf[i] = s_buf[i] * (1.0 / SHRT_MAX);
538
539                 while (total_in_buf_used < ARRAY_LEN(in_buf)) {
540                         int in_buf_used;
541                         int out_buf_used;
542
543                         out_buf_used = resample_process(jack_data->output_resampler,
544                                 jack_data->output_resample_factor,
545                                 &in_buf[total_in_buf_used], ARRAY_LEN(in_buf) - total_in_buf_used,
546                                 0, &in_buf_used,
547                                 &f_buf[total_out_buf_used], ARRAY_LEN(f_buf) - total_out_buf_used);
548
549                         if (out_buf_used < 0)
550                                 break;
551
552                         total_out_buf_used += out_buf_used;
553                         total_in_buf_used += in_buf_used;
554
555                         if (total_out_buf_used == ARRAY_LEN(f_buf)) {
556                                 ast_log(LOG_ERROR, "Output buffer filled ... need to increase its size\n");
557                                 break;
558                         }
559                 }
560
561                 f_buf_used = total_out_buf_used;
562                 if (f_buf_used > ARRAY_LEN(f_buf))
563                         f_buf_used = ARRAY_LEN(f_buf);
564         } else {
565                 /* No resampling needed */
566
567                 for (i = 0; i < f->samples; i++)
568                         f_buf[i] = s_buf[i] * (1.0 / SHRT_MAX);
569
570                 f_buf_used = f->samples;
571         }
572
573         res = jack_ringbuffer_write(jack_data->output_rb, (const char *) f_buf, f_buf_used * sizeof(float));
574         if (res != (f_buf_used * sizeof(float))) {
575                 ast_debug(2, "Tried to write %d bytes to the ringbuffer, but only wrote %d\n",
576                         (int) (f_buf_used * sizeof(float)), (int) res);
577         }
578
579         return 0;
580 }
581
582 /*!
583  * \brief handle jack audio
584  *
585  * \param[in]  chan The Asterisk channel to write the frames to if no output frame
586  *             is provided.
587  * \param[in]  jack_data This is the jack_data struct that contains the input
588  *             ringbuffer that audio will be read from.
589  * \param[out] out_frame If this argument is non-NULL, then assuming there is
590  *             enough data avilable in the ringbuffer, the audio in this frame
591  *             will get replaced with audio from the input buffer.  If there is
592  *             not enough data available to read at this time, then the frame
593  *             data gets zeroed out.
594  *
595  * Read data from the input ringbuffer, which is the properly resampled audio
596  * that was read from the jack input port.  Write it to the channel in 20 ms frames,
597  * or fill up an output frame instead if one is provided.
598  *
599  * \return Nothing.
600  */
601 static void handle_jack_audio(struct ast_channel *chan, struct jack_data *jack_data,
602         struct ast_frame *out_frame)
603 {
604         short buf[160];
605         struct ast_frame f = {
606                 .frametype = AST_FRAME_VOICE,
607                 .subclass.codec = AST_FORMAT_SLINEAR,
608                 .src = "JACK",
609                 .data.ptr = buf,
610                 .datalen = sizeof(buf),
611                 .samples = ARRAY_LEN(buf),
612         };
613
614         for (;;) {
615                 size_t res, read_len;
616                 char *read_buf;
617
618                 read_len = out_frame ? out_frame->datalen : sizeof(buf);
619                 read_buf = out_frame ? out_frame->data.ptr : buf;
620
621                 res = jack_ringbuffer_read_space(jack_data->input_rb);
622
623                 if (res < read_len) {
624                         /* Not enough data ready for another frame, move on ... */
625                         if (out_frame) {
626                                 ast_debug(1, "Sending an empty frame for the JACK_HOOK\n");
627                                 memset(out_frame->data.ptr, 0, out_frame->datalen);
628                         }
629                         break;
630                 }
631
632                 res = jack_ringbuffer_read(jack_data->input_rb, (char *) read_buf, read_len);
633
634                 if (res < read_len) {
635                         ast_log(LOG_ERROR, "Error reading from ringbuffer, even though it said there was enough data\n");
636                         break;
637                 }
638
639                 if (out_frame) {
640                         /* If an output frame was provided, then we just want to fill up the
641                          * buffer in that frame and return. */
642                         break;
643                 }
644
645                 ast_write(chan, &f);
646         }
647 }
648
649 enum {
650         OPT_SERVER_NAME =    (1 << 0),
651         OPT_INPUT_PORT =     (1 << 1),
652         OPT_OUTPUT_PORT =    (1 << 2),
653         OPT_NOSTART_SERVER = (1 << 3),
654         OPT_CLIENT_NAME =    (1 << 4),
655 };
656
657 enum {
658         OPT_ARG_SERVER_NAME,
659         OPT_ARG_INPUT_PORT,
660         OPT_ARG_OUTPUT_PORT,
661         OPT_ARG_CLIENT_NAME,
662
663         /* Must be the last element */
664         OPT_ARG_ARRAY_SIZE,
665 };
666
667 AST_APP_OPTIONS(jack_exec_options, BEGIN_OPTIONS
668         AST_APP_OPTION_ARG('s', OPT_SERVER_NAME, OPT_ARG_SERVER_NAME),
669         AST_APP_OPTION_ARG('i', OPT_INPUT_PORT, OPT_ARG_INPUT_PORT),
670         AST_APP_OPTION_ARG('o', OPT_OUTPUT_PORT, OPT_ARG_OUTPUT_PORT),
671         AST_APP_OPTION('n', OPT_NOSTART_SERVER),
672         AST_APP_OPTION_ARG('c', OPT_CLIENT_NAME, OPT_ARG_CLIENT_NAME),
673 END_OPTIONS );
674
675 static struct jack_data *jack_data_alloc(void)
676 {
677         struct jack_data *jack_data;
678
679         if (!(jack_data = ast_calloc(1, sizeof(*jack_data))))
680                 return NULL;
681
682         if (ast_string_field_init(jack_data, 32)) {
683                 ast_free(jack_data);
684                 return NULL;
685         }
686
687         return jack_data;
688 }
689
690 /*!
691  * \note This must be done before calling init_jack_data().
692  */
693 static int handle_options(struct jack_data *jack_data, const char *__options_str)
694 {
695         struct ast_flags options = { 0, };
696         char *option_args[OPT_ARG_ARRAY_SIZE];
697         char *options_str;
698
699         options_str = ast_strdupa(__options_str);
700
701         ast_app_parse_options(jack_exec_options, &options, option_args, options_str);
702
703         if (ast_test_flag(&options, OPT_SERVER_NAME)) {
704                 if (!ast_strlen_zero(option_args[OPT_ARG_SERVER_NAME]))
705                         ast_string_field_set(jack_data, server_name, option_args[OPT_ARG_SERVER_NAME]);
706                 else {
707                         ast_log(LOG_ERROR, "A server name must be provided with the s() option\n");
708                         return -1;
709                 }
710         }
711
712         if (ast_test_flag(&options, OPT_CLIENT_NAME)) {
713                 if (!ast_strlen_zero(option_args[OPT_ARG_CLIENT_NAME]))
714                         ast_string_field_set(jack_data, client_name, option_args[OPT_ARG_CLIENT_NAME]);
715                 else {
716                         ast_log(LOG_ERROR, "A client name must be provided with the c() option\n");
717                         return -1;
718                 }
719         }
720
721         if (ast_test_flag(&options, OPT_INPUT_PORT)) {
722                 if (!ast_strlen_zero(option_args[OPT_ARG_INPUT_PORT]))
723                         ast_string_field_set(jack_data, connect_input_port, option_args[OPT_ARG_INPUT_PORT]);
724                 else {
725                         ast_log(LOG_ERROR, "A name must be provided with the i() option\n");
726                         return -1;
727                 }
728         }
729
730         if (ast_test_flag(&options, OPT_OUTPUT_PORT)) {
731                 if (!ast_strlen_zero(option_args[OPT_ARG_OUTPUT_PORT]))
732                         ast_string_field_set(jack_data, connect_output_port, option_args[OPT_ARG_OUTPUT_PORT]);
733                 else {
734                         ast_log(LOG_ERROR, "A name must be provided with the o() option\n");
735                         return -1;
736                 }
737         }
738
739         jack_data->no_start_server = ast_test_flag(&options, OPT_NOSTART_SERVER) ? 1 : 0;
740
741         return 0;
742 }
743
744 static int jack_exec(struct ast_channel *chan, const char *data)
745 {
746         struct jack_data *jack_data;
747
748         if (!(jack_data = jack_data_alloc()))
749                 return -1;
750
751         if (!ast_strlen_zero(data) && handle_options(jack_data, data)) {
752                 destroy_jack_data(jack_data);
753                 return -1;
754         }
755
756         if (init_jack_data(chan, jack_data)) {
757                 destroy_jack_data(jack_data);
758                 return -1;
759         }
760
761         if (ast_set_read_format(chan, AST_FORMAT_SLINEAR)) {
762                 destroy_jack_data(jack_data);
763                 return -1;
764         }
765
766         if (ast_set_write_format(chan, AST_FORMAT_SLINEAR)) {
767                 destroy_jack_data(jack_data);
768                 return -1;
769         }
770
771         while (!jack_data->stop) {
772                 struct ast_frame *f;
773
774                 ast_waitfor(chan, -1);
775
776                 f = ast_read(chan);
777                 if (!f) {
778                         jack_data->stop = 1;
779                         continue;
780                 }
781
782                 switch (f->frametype) {
783                 case AST_FRAME_CONTROL:
784                         if (f->subclass.integer == AST_CONTROL_HANGUP)
785                                 jack_data->stop = 1;
786                         break;
787                 case AST_FRAME_VOICE:
788                         queue_voice_frame(jack_data, f);
789                 default:
790                         break;
791                 }
792
793                 ast_frfree(f);
794
795                 handle_jack_audio(chan, jack_data, NULL);
796         }
797
798         jack_data = destroy_jack_data(jack_data);
799
800         return 0;
801 }
802
803 static void jack_hook_ds_destroy(void *data)
804 {
805         struct jack_data *jack_data = data;
806
807         destroy_jack_data(jack_data);
808 }
809
810 static const struct ast_datastore_info jack_hook_ds_info = {
811         .type = "JACK_HOOK",
812         .destroy = jack_hook_ds_destroy,
813 };
814
815 static int jack_hook_callback(struct ast_audiohook *audiohook, struct ast_channel *chan,
816         struct ast_frame *frame, enum ast_audiohook_direction direction)
817 {
818         struct ast_datastore *datastore;
819         struct jack_data *jack_data;
820
821         if (audiohook->status == AST_AUDIOHOOK_STATUS_DONE)
822                 return 0;
823
824         if (direction != AST_AUDIOHOOK_DIRECTION_READ)
825                 return 0;
826
827         if (frame->frametype != AST_FRAME_VOICE)
828                 return 0;
829
830         if (frame->subclass.codec != AST_FORMAT_SLINEAR) {
831                 ast_log(LOG_WARNING, "Expected frame in SLINEAR for the audiohook, but got format %s\n",
832                         ast_getformatname(frame->subclass.codec));
833                 return 0;
834         }
835
836         ast_channel_lock(chan);
837
838         if (!(datastore = ast_channel_datastore_find(chan, &jack_hook_ds_info, NULL))) {
839                 ast_log(LOG_ERROR, "JACK_HOOK datastore not found for '%s'\n", chan->name);
840                 ast_channel_unlock(chan);
841                 return -1;
842         }
843
844         jack_data = datastore->data;
845
846         queue_voice_frame(jack_data, frame);
847
848         handle_jack_audio(chan, jack_data, frame);
849
850         ast_channel_unlock(chan);
851
852         return 0;
853 }
854
855 static int enable_jack_hook(struct ast_channel *chan, char *data)
856 {
857         struct ast_datastore *datastore;
858         struct jack_data *jack_data = NULL;
859         AST_DECLARE_APP_ARGS(args,
860                 AST_APP_ARG(mode);
861                 AST_APP_ARG(options);
862         );
863
864         AST_STANDARD_APP_ARGS(args, data);
865
866         ast_channel_lock(chan);
867
868         if ((datastore = ast_channel_datastore_find(chan, &jack_hook_ds_info, NULL))) {
869                 ast_log(LOG_ERROR, "JACK_HOOK already enabled for '%s'\n", chan->name);
870                 goto return_error;
871         }
872
873         if (ast_strlen_zero(args.mode) || strcasecmp(args.mode, "manipulate")) {
874                 ast_log(LOG_ERROR, "'%s' is not a supported mode.  Only manipulate is supported.\n",
875                         S_OR(args.mode, "<none>"));
876                 goto return_error;
877         }
878
879         if (!(jack_data = jack_data_alloc()))
880                 goto return_error;
881
882         if (!ast_strlen_zero(args.options) && handle_options(jack_data, args.options))
883                 goto return_error;
884
885         if (init_jack_data(chan, jack_data))
886                 goto return_error;
887
888         if (!(datastore = ast_datastore_alloc(&jack_hook_ds_info, NULL)))
889                 goto return_error;
890
891         jack_data->has_audiohook = 1;
892         ast_audiohook_init(&jack_data->audiohook, AST_AUDIOHOOK_TYPE_MANIPULATE, "JACK_HOOK");
893         jack_data->audiohook.manipulate_callback = jack_hook_callback;
894
895         datastore->data = jack_data;
896
897         if (ast_audiohook_attach(chan, &jack_data->audiohook))
898                 goto return_error;
899
900         if (ast_channel_datastore_add(chan, datastore))
901                 goto return_error;
902
903         ast_channel_unlock(chan);
904
905         return 0;
906
907 return_error:
908         ast_channel_unlock(chan);
909
910         if (jack_data)
911                 destroy_jack_data(jack_data);
912
913         return -1;
914 }
915
916 static int disable_jack_hook(struct ast_channel *chan)
917 {
918         struct ast_datastore *datastore;
919         struct jack_data *jack_data;
920
921         ast_channel_lock(chan);
922
923         if (!(datastore = ast_channel_datastore_find(chan, &jack_hook_ds_info, NULL))) {
924                 ast_channel_unlock(chan);
925                 ast_log(LOG_WARNING, "No JACK_HOOK found to disable\n");
926                 return -1;
927         }
928
929         ast_channel_datastore_remove(chan, datastore);
930
931         jack_data = datastore->data;
932         ast_audiohook_detach(&jack_data->audiohook);
933
934         /* Keep the channel locked while we destroy the datastore, so that we can
935          * ensure that all of the jack stuff is stopped just in case another frame
936          * tries to come through the audiohook callback. */
937         ast_datastore_free(datastore);
938
939         ast_channel_unlock(chan);
940
941         return 0;
942 }
943
944 static int jack_hook_write(struct ast_channel *chan, const char *cmd, char *data,
945         const char *value)
946 {
947         int res;
948
949         if (!strcasecmp(value, "on"))
950                 res = enable_jack_hook(chan, data);
951         else if (!strcasecmp(value, "off"))
952                 res = disable_jack_hook(chan);
953         else {
954                 ast_log(LOG_ERROR, "'%s' is not a valid value for JACK_HOOK()\n", value);
955                 res = -1;
956         }
957
958         return res;
959 }
960
961 static struct ast_custom_function jack_hook_function = {
962         .name = "JACK_HOOK",
963         .synopsis = "Enable a jack hook on a channel",
964         .syntax = "JACK_HOOK(<mode>,[options])",
965         .desc =
966         "   The JACK_HOOK allows turning on or off jack connectivity to this channel.\n"
967         "When the JACK_HOOK is turned on, jack ports will get created that allow\n"
968         "access to the audio stream for this channel.  The mode specifies which mode\n"
969         "this hook should run in.  A mode must be specified when turning the JACK_HOOK.\n"
970         "on.  However, all arguments are optional when turning it off.\n"
971         "\n"
972         "   Valid modes are:\n"
973 #if 0
974         /* XXX TODO */
975         "    spy -        Create a read-only audio hook.  Only an output jack port will\n"
976         "                 get created.\n"
977         "    whisper -    Create a write-only audio hook.  Only an input jack port will\n"
978         "                 get created.\n"
979 #endif
980         "    manipulate - Create a read/write audio hook.  Both an input and an output\n"
981         "                 jack port will get created.  Audio from the channel will be\n"
982         "                 sent out the output port and will be replaced by the audio\n"
983         "                 coming in on the input port as it gets passed on.\n"
984         "\n"
985         "   Valid options are:\n"
986         COMMON_OPTIONS
987         "\n"
988         " Examples:\n"
989         "   To turn on the JACK_HOOK,\n"
990         "     Set(JACK_HOOK(manipulate,i(pure_data_0:input0)o(pure_data_0:output0))=on)\n"
991         "   To turn off the JACK_HOOK,\n"
992         "     Set(JACK_HOOK()=off)\n"
993         "",
994         .write = jack_hook_write,
995 };
996
997 static int unload_module(void)
998 {
999         int res;
1000
1001         res = ast_unregister_application(jack_app);
1002         res |= ast_custom_function_unregister(&jack_hook_function);
1003
1004         return res;
1005 }
1006
1007 static int load_module(void)
1008 {
1009         if (ast_register_application_xml(jack_app, jack_exec)) {
1010                 return AST_MODULE_LOAD_DECLINE;
1011         }
1012
1013         if (ast_custom_function_register(&jack_hook_function)) {
1014                 ast_unregister_application(jack_app);
1015                 return AST_MODULE_LOAD_DECLINE;
1016         }
1017
1018         return AST_MODULE_LOAD_SUCCESS;
1019 }
1020
1021 AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "JACK Interface");