jackaudiosink: Don't call g_alloca() in process_cb
[platform/upstream/gstreamer.git] / ext / jack / gstjackaudiosink.c
1 /* GStreamer
2  * Copyright (C) 2006 Wim Taymans <wim@fluendo.com>
3  *
4  * gstjackaudiosink.c: jack audio sink implementation
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Library General Public
8  * License as published by the Free Software Foundation; either
9  * version 2 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Library General Public License for more details.
15  *
16  * You should have received a copy of the GNU Library General Public
17  * License along with this library; if not, write to the
18  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19  * Boston, MA 02111-1307, USA.
20  */
21
22 /**
23  * SECTION:element-jackaudiosink
24  * @see_also: #GstBaseAudioSink, #GstRingBuffer
25  *
26  * A Sink that outputs data to Jack ports.
27  * 
28  * It will create N Jack ports named out_&lt;name&gt;_&lt;num&gt; where 
29  * &lt;name&gt; is the element name and &lt;num&gt; is starting from 1.
30  * Each port corresponds to a gstreamer channel.
31  * 
32  * The samplerate as exposed on the caps is always the same as the samplerate of
33  * the jack server.
34  * 
35  * When the #GstJackAudioSink:connect property is set to auto, this element
36  * will try to connect each output port to a random physical jack input pin. In
37  * this mode, the sink will expose the number of physical channels on its pad
38  * caps.
39  * 
40  * When the #GstJackAudioSink:connect property is set to none, the element will
41  * accept any number of input channels and will create (but not connect) an
42  * output port for each channel.
43  * 
44  * The element will generate an error when the Jack server is shut down when it
45  * was PAUSED or PLAYING. This element does not support dynamic rate and buffer
46  * size changes at runtime.
47  * 
48  * <refsect2>
49  * <title>Example launch line</title>
50  * |[
51  * gst-launch audiotestsrc ! jackaudiosink
52  * ]| Play a sine wave to using jack.
53  * </refsect2>
54  *
55  * Last reviewed on 2006-11-30 (0.10.4)
56  */
57
58 #ifdef HAVE_CONFIG_H
59 #include "config.h"
60 #endif
61
62 #include <gst/gst-i18n-plugin.h>
63 #include <stdlib.h>
64 #include <string.h>
65
66 #include "gstjackaudiosink.h"
67 #include "gstjackringbuffer.h"
68
69 GST_DEBUG_CATEGORY_STATIC (gst_jack_audio_sink_debug);
70 #define GST_CAT_DEFAULT gst_jack_audio_sink_debug
71
72 static gboolean
73 gst_jack_audio_sink_allocate_channels (GstJackAudioSink * sink, gint channels)
74 {
75   jack_client_t *client;
76
77   client = gst_jack_audio_client_get_client (sink->client);
78
79   /* remove ports we don't need */
80   while (sink->port_count > channels) {
81     jack_port_unregister (client, sink->ports[--sink->port_count]);
82   }
83
84   /* alloc enough output ports */
85   sink->ports = g_realloc (sink->ports, sizeof (jack_port_t *) * channels);
86   sink->buffers = g_realloc (sink->buffers, sizeof (sample_t *) * channels);
87
88   /* create an output port for each channel */
89   while (sink->port_count < channels) {
90     gchar *name;
91
92     /* port names start from 1 and are local to the element */
93     name =
94         g_strdup_printf ("out_%s_%d", GST_ELEMENT_NAME (sink),
95         sink->port_count + 1);
96     sink->ports[sink->port_count] =
97         jack_port_register (client, name, JACK_DEFAULT_AUDIO_TYPE,
98         JackPortIsOutput, 0);
99     if (sink->ports[sink->port_count] == NULL)
100       return FALSE;
101
102     sink->port_count++;
103
104     g_free (name);
105   }
106   return TRUE;
107 }
108
109 static void
110 gst_jack_audio_sink_free_channels (GstJackAudioSink * sink)
111 {
112   gint res, i = 0;
113   jack_client_t *client;
114
115   client = gst_jack_audio_client_get_client (sink->client);
116
117   /* get rid of all ports */
118   while (sink->port_count) {
119     GST_LOG_OBJECT (sink, "unregister port %d", i);
120     if ((res = jack_port_unregister (client, sink->ports[i++]))) {
121       GST_DEBUG_OBJECT (sink, "unregister of port failed (%d)", res);
122     }
123     sink->port_count--;
124   }
125   g_free (sink->ports);
126   sink->ports = NULL;
127   g_free (sink->buffers);
128   sink->buffers = NULL;
129 }
130
131 /* ringbuffer abstract base class */
132 static GType
133 gst_jack_ring_buffer_get_type (void)
134 {
135   static volatile gsize ringbuffer_type = 0;
136
137   if (g_once_init_enter (&ringbuffer_type)) {
138     static const GTypeInfo ringbuffer_info = {
139       sizeof (GstJackRingBufferClass),
140       NULL,
141       NULL,
142       (GClassInitFunc) gst_jack_ring_buffer_class_init,
143       NULL,
144       NULL,
145       sizeof (GstJackRingBuffer),
146       0,
147       (GInstanceInitFunc) gst_jack_ring_buffer_init,
148       NULL
149     };
150     GType tmp = g_type_register_static (GST_TYPE_RING_BUFFER,
151         "GstJackAudioSinkRingBuffer", &ringbuffer_info, 0);
152     g_once_init_leave (&ringbuffer_type, tmp);
153   }
154
155   return (GType) ringbuffer_type;
156 }
157
158 static void
159 gst_jack_ring_buffer_class_init (GstJackRingBufferClass * klass)
160 {
161   GstRingBufferClass *gstringbuffer_class;
162
163   gstringbuffer_class = (GstRingBufferClass *) klass;
164
165   ring_parent_class = g_type_class_peek_parent (klass);
166
167   gstringbuffer_class->open_device =
168       GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_open_device);
169   gstringbuffer_class->close_device =
170       GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_close_device);
171   gstringbuffer_class->acquire =
172       GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_acquire);
173   gstringbuffer_class->release =
174       GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_release);
175   gstringbuffer_class->start = GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_start);
176   gstringbuffer_class->pause = GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_pause);
177   gstringbuffer_class->resume = GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_start);
178   gstringbuffer_class->stop = GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_stop);
179
180   gstringbuffer_class->delay = GST_DEBUG_FUNCPTR (gst_jack_ring_buffer_delay);
181 }
182
183 /* this is the callback of jack. This should RT-safe.
184  */
185 static int
186 jack_process_cb (jack_nframes_t nframes, void *arg)
187 {
188   GstJackAudioSink *sink;
189   GstRingBuffer *buf;
190   gint readseg, len;
191   guint8 *readptr;
192   gint i, j, flen, channels;
193   sample_t *data;
194
195   buf = GST_RING_BUFFER_CAST (arg);
196   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
197
198   channels = buf->spec.channels;
199
200   /* get target buffers */
201   for (i = 0; i < channels; i++) {
202     sink->buffers[i] =
203         (sample_t *) jack_port_get_buffer (sink->ports[i], nframes);
204   }
205
206   if (gst_ring_buffer_prepare_read (buf, &readseg, &readptr, &len)) {
207     flen = len / channels;
208
209     /* the number of samples must be exactly the segment size */
210     if (nframes * sizeof (sample_t) != flen)
211       goto wrong_size;
212
213     GST_DEBUG_OBJECT (sink, "copy %d frames: %p, %d bytes, %d channels",
214         nframes, readptr, flen, channels);
215     data = (sample_t *) readptr;
216
217     /* the samples in the ringbuffer have the channels interleaved, we need to
218      * deinterleave into the jack target buffers */
219     for (i = 0; i < nframes; i++) {
220       for (j = 0; j < channels; j++) {
221         sink->buffers[j][i] = *data++;
222       }
223     }
224
225     /* clear written samples in the ringbuffer */
226     gst_ring_buffer_clear (buf, readseg);
227
228     /* we wrote one segment */
229     gst_ring_buffer_advance (buf, 1);
230   } else {
231     GST_DEBUG_OBJECT (sink, "write %d frames silence", nframes);
232     /* We are not allowed to read from the ringbuffer, write silence to all
233      * jack output buffers */
234     for (i = 0; i < channels; i++) {
235       memset (sink->buffers[i], 0, nframes * sizeof (sample_t));
236     }
237   }
238   return 0;
239
240   /* ERRORS */
241 wrong_size:
242   {
243     GST_ERROR_OBJECT (sink, "nbytes (%d) != flen (%d)",
244         (gint) (nframes * sizeof (sample_t)), flen);
245     return 1;
246   }
247 }
248
249 /* we error out */
250 static int
251 jack_sample_rate_cb (jack_nframes_t nframes, void *arg)
252 {
253   GstJackAudioSink *sink;
254   GstJackRingBuffer *abuf;
255
256   abuf = GST_JACK_RING_BUFFER_CAST (arg);
257   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (arg));
258
259   if (abuf->sample_rate != -1 && abuf->sample_rate != nframes)
260     goto not_supported;
261
262   return 0;
263
264   /* ERRORS */
265 not_supported:
266   {
267     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS,
268         (NULL), ("Jack changed the sample rate, which is not supported"));
269     return 1;
270   }
271 }
272
273 /* we error out */
274 static int
275 jack_buffer_size_cb (jack_nframes_t nframes, void *arg)
276 {
277   GstJackAudioSink *sink;
278   GstJackRingBuffer *abuf;
279
280   abuf = GST_JACK_RING_BUFFER_CAST (arg);
281   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (arg));
282
283   if (abuf->buffer_size != -1 && abuf->buffer_size != nframes)
284     goto not_supported;
285
286   return 0;
287
288   /* ERRORS */
289 not_supported:
290   {
291     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS,
292         (NULL), ("Jack changed the buffer size, which is not supported"));
293     return 1;
294   }
295 }
296
297 static void
298 jack_shutdown_cb (void *arg)
299 {
300   GstJackAudioSink *sink;
301
302   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (arg));
303
304   GST_DEBUG_OBJECT (sink, "shutdown");
305
306   GST_ELEMENT_ERROR (sink, RESOURCE, NOT_FOUND,
307       (NULL), ("Jack server shutdown"));
308 }
309
310 static void
311 gst_jack_ring_buffer_init (GstJackRingBuffer * buf,
312     GstJackRingBufferClass * g_class)
313 {
314   buf->channels = -1;
315   buf->buffer_size = -1;
316   buf->sample_rate = -1;
317 }
318
319 /* the _open_device method should make a connection with the server
320  */
321 static gboolean
322 gst_jack_ring_buffer_open_device (GstRingBuffer * buf)
323 {
324   GstJackAudioSink *sink;
325   jack_status_t status = 0;
326   const gchar *name;
327
328   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
329
330   GST_DEBUG_OBJECT (sink, "open");
331
332   name = g_get_application_name ();
333   if (!name)
334     name = "GStreamer";
335
336   sink->client = gst_jack_audio_client_new (name, sink->server,
337       sink->jclient,
338       GST_JACK_CLIENT_SINK,
339       jack_shutdown_cb,
340       jack_process_cb, jack_buffer_size_cb, jack_sample_rate_cb, buf, &status);
341   if (sink->client == NULL)
342     goto could_not_open;
343
344   GST_DEBUG_OBJECT (sink, "opened");
345
346   return TRUE;
347
348   /* ERRORS */
349 could_not_open:
350   {
351     if (status & JackServerFailed) {
352       GST_ELEMENT_ERROR (sink, RESOURCE, NOT_FOUND,
353           (_("Jack server not found")),
354           ("Cannot connect to the Jack server (status %d)", status));
355     } else {
356       GST_ELEMENT_ERROR (sink, RESOURCE, OPEN_WRITE,
357           (NULL), ("Jack client open error (status %d)", status));
358     }
359     return FALSE;
360   }
361 }
362
363 /* close the connection with the server
364  */
365 static gboolean
366 gst_jack_ring_buffer_close_device (GstRingBuffer * buf)
367 {
368   GstJackAudioSink *sink;
369
370   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
371
372   GST_DEBUG_OBJECT (sink, "close");
373
374   gst_jack_audio_sink_free_channels (sink);
375   gst_jack_audio_client_free (sink->client);
376   sink->client = NULL;
377
378   return TRUE;
379 }
380
381 /* allocate a buffer and setup resources to process the audio samples of
382  * the format as specified in @spec.
383  *
384  * We allocate N jack ports, one for each channel. If we are asked to
385  * automatically make a connection with physical ports, we connect as many
386  * ports as there are physical ports, leaving leftover ports unconnected.
387  *
388  * It is assumed that samplerate and number of channels are acceptable since our
389  * getcaps method will always provide correct values. If unacceptable caps are
390  * received for some reason, we fail here.
391  */
392 static gboolean
393 gst_jack_ring_buffer_acquire (GstRingBuffer * buf, GstRingBufferSpec * spec)
394 {
395   GstJackAudioSink *sink;
396   GstJackRingBuffer *abuf;
397   const char **ports;
398   gint sample_rate, buffer_size;
399   gint i, channels, res;
400   jack_client_t *client;
401
402   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
403   abuf = GST_JACK_RING_BUFFER_CAST (buf);
404
405   GST_DEBUG_OBJECT (sink, "acquire");
406
407   client = gst_jack_audio_client_get_client (sink->client);
408
409   /* sample rate must be that of the server */
410   sample_rate = jack_get_sample_rate (client);
411   if (sample_rate != spec->rate)
412     goto wrong_samplerate;
413
414   channels = spec->channels;
415
416   if (!gst_jack_audio_sink_allocate_channels (sink, channels))
417     goto out_of_ports;
418
419   buffer_size = jack_get_buffer_size (client);
420
421   /* the segment size in bytes, this is large enough to hold a buffer of 32bit floats
422    * for all channels  */
423   spec->segsize = buffer_size * sizeof (gfloat) * channels;
424   spec->latency_time = gst_util_uint64_scale (spec->segsize,
425       (GST_SECOND / GST_USECOND), spec->rate * spec->bytes_per_sample);
426   /* segtotal based on buffer-time latency */
427   spec->segtotal = spec->buffer_time / spec->latency_time;
428   if (spec->segtotal < 2) {
429     spec->segtotal = 2;
430     spec->buffer_time = spec->latency_time * spec->segtotal;
431   }
432
433   GST_DEBUG_OBJECT (sink, "buffer time: %" G_GINT64_FORMAT " usec",
434       spec->buffer_time);
435   GST_DEBUG_OBJECT (sink, "latency time: %" G_GINT64_FORMAT " usec",
436       spec->latency_time);
437   GST_DEBUG_OBJECT (sink, "buffer_size %d, segsize %d, segtotal %d",
438       buffer_size, spec->segsize, spec->segtotal);
439
440   /* allocate the ringbuffer memory now */
441   buf->data = gst_buffer_new_and_alloc (spec->segtotal * spec->segsize);
442   memset (GST_BUFFER_DATA (buf->data), 0, GST_BUFFER_SIZE (buf->data));
443
444   if ((res = gst_jack_audio_client_set_active (sink->client, TRUE)))
445     goto could_not_activate;
446
447   /* if we need to automatically connect the ports, do so now. We must do this
448    * after activating the client. */
449   if (sink->connect == GST_JACK_CONNECT_AUTO
450       || sink->connect == GST_JACK_CONNECT_AUTO_FORCED) {
451     /* find all the physical input ports. A physical input port is a port
452      * associated with a hardware device. Someone needs connect to a physical
453      * port in order to hear something. */
454     ports = jack_get_ports (client, NULL, NULL,
455         JackPortIsPhysical | JackPortIsInput);
456     if (ports == NULL) {
457       /* no ports? fine then we don't do anything except for posting a warning
458        * message. */
459       GST_ELEMENT_WARNING (sink, RESOURCE, NOT_FOUND, (NULL),
460           ("No physical input ports found, leaving ports unconnected"));
461       goto done;
462     }
463
464     for (i = 0; i < channels; i++) {
465       /* stop when all input ports are exhausted */
466       if (ports[i] == NULL) {
467         /* post a warning that we could not connect all ports */
468         GST_ELEMENT_WARNING (sink, RESOURCE, NOT_FOUND, (NULL),
469             ("No more physical ports, leaving some ports unconnected"));
470         break;
471       }
472       GST_DEBUG_OBJECT (sink, "try connecting to %s",
473           jack_port_name (sink->ports[i]));
474       /* connect the port to a physical port */
475       res = jack_connect (client, jack_port_name (sink->ports[i]), ports[i]);
476       if (res != 0 && res != EEXIST)
477         goto cannot_connect;
478     }
479     free (ports);
480   }
481 done:
482
483   abuf->sample_rate = sample_rate;
484   abuf->buffer_size = buffer_size;
485   abuf->channels = spec->channels;
486
487   return TRUE;
488
489   /* ERRORS */
490 wrong_samplerate:
491   {
492     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS, (NULL),
493         ("Wrong samplerate, server is running at %d and we received %d",
494             sample_rate, spec->rate));
495     return FALSE;
496   }
497 out_of_ports:
498   {
499     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS, (NULL),
500         ("Cannot allocate more Jack ports"));
501     return FALSE;
502   }
503 could_not_activate:
504   {
505     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS, (NULL),
506         ("Could not activate client (%d:%s)", res, g_strerror (res)));
507     return FALSE;
508   }
509 cannot_connect:
510   {
511     GST_ELEMENT_ERROR (sink, RESOURCE, SETTINGS, (NULL),
512         ("Could not connect output ports to physical ports (%d:%s)",
513             res, g_strerror (res)));
514     free (ports);
515     return FALSE;
516   }
517 }
518
519 /* function is called with LOCK */
520 static gboolean
521 gst_jack_ring_buffer_release (GstRingBuffer * buf)
522 {
523   GstJackAudioSink *sink;
524   GstJackRingBuffer *abuf;
525   gint res;
526
527   abuf = GST_JACK_RING_BUFFER_CAST (buf);
528   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
529
530   GST_DEBUG_OBJECT (sink, "release");
531
532   if ((res = gst_jack_audio_client_set_active (sink->client, FALSE))) {
533     /* we only warn, this means the server is probably shut down and the client
534      * is gone anyway. */
535     GST_ELEMENT_WARNING (sink, RESOURCE, CLOSE, (NULL),
536         ("Could not deactivate Jack client (%d)", res));
537   }
538
539   abuf->channels = -1;
540   abuf->buffer_size = -1;
541   abuf->sample_rate = -1;
542
543   /* free the buffer */
544   gst_buffer_unref (buf->data);
545   buf->data = NULL;
546
547   return TRUE;
548 }
549
550 static gboolean
551 gst_jack_ring_buffer_start (GstRingBuffer * buf)
552 {
553   GstJackAudioSink *sink;
554
555   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
556
557   GST_DEBUG_OBJECT (sink, "start");
558
559   return TRUE;
560 }
561
562 static gboolean
563 gst_jack_ring_buffer_pause (GstRingBuffer * buf)
564 {
565   GstJackAudioSink *sink;
566
567   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
568
569   GST_DEBUG_OBJECT (sink, "pause");
570
571   return TRUE;
572 }
573
574 static gboolean
575 gst_jack_ring_buffer_stop (GstRingBuffer * buf)
576 {
577   GstJackAudioSink *sink;
578
579   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
580
581   GST_DEBUG_OBJECT (sink, "stop");
582
583   return TRUE;
584 }
585
586 #if defined (HAVE_JACK_0_120_1) || defined(HAVE_JACK_1_9_7)
587 static guint
588 gst_jack_ring_buffer_delay (GstRingBuffer * buf)
589 {
590   GstJackAudioSink *sink;
591   guint i, res = 0;
592   jack_latency_range_t range;
593
594   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
595
596   for (i = 0; i < sink->port_count; i++) {
597     jack_port_get_latency_range (sink->ports[i], JackPlaybackLatency, &range);
598     if (range.max > res)
599       res = range.max;
600   }
601
602   GST_LOG_OBJECT (sink, "delay %u", res);
603
604   return res;
605 }
606 #else /* !(defined (HAVE_JACK_0_120_1) || defined(HAVE_JACK_1_9_7)) */
607 static guint
608 gst_jack_ring_buffer_delay (GstRingBuffer * buf)
609 {
610   GstJackAudioSink *sink;
611   guint i, res = 0;
612   guint latency;
613   jack_client_t *client;
614
615   sink = GST_JACK_AUDIO_SINK (GST_OBJECT_PARENT (buf));
616   client = gst_jack_audio_client_get_client (sink->client);
617
618   for (i = 0; i < sink->port_count; i++) {
619     latency = jack_port_get_total_latency (client, sink->ports[i]);
620     if (latency > res)
621       res = latency;
622   }
623
624   GST_LOG_OBJECT (sink, "delay %u", res);
625
626   return res;
627 }
628 #endif
629
630 static GstStaticPadTemplate jackaudiosink_sink_factory =
631 GST_STATIC_PAD_TEMPLATE ("sink",
632     GST_PAD_SINK,
633     GST_PAD_ALWAYS,
634     GST_STATIC_CAPS ("audio/x-raw-float, "
635         "endianness = (int) BYTE_ORDER, "
636         "width = (int) 32, "
637         "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, MAX ]")
638     );
639
640 /* AudioSink signals and args */
641 enum
642 {
643   /* FILL ME */
644   SIGNAL_LAST
645 };
646
647 #define DEFAULT_PROP_CONNECT    GST_JACK_CONNECT_AUTO
648 #define DEFAULT_PROP_SERVER     NULL
649
650 enum
651 {
652   PROP_0,
653   PROP_CONNECT,
654   PROP_SERVER,
655   PROP_CLIENT,
656   PROP_LAST
657 };
658
659 #define _do_init(bla) \
660     GST_DEBUG_CATEGORY_INIT (gst_jack_audio_sink_debug, "jacksink", 0, "jacksink element");
661
662 GST_BOILERPLATE_FULL (GstJackAudioSink, gst_jack_audio_sink, GstBaseAudioSink,
663     GST_TYPE_BASE_AUDIO_SINK, _do_init);
664
665 static void gst_jack_audio_sink_dispose (GObject * object);
666 static void gst_jack_audio_sink_set_property (GObject * object, guint prop_id,
667     const GValue * value, GParamSpec * pspec);
668 static void gst_jack_audio_sink_get_property (GObject * object, guint prop_id,
669     GValue * value, GParamSpec * pspec);
670
671 static GstCaps *gst_jack_audio_sink_getcaps (GstBaseSink * bsink);
672 static GstRingBuffer *gst_jack_audio_sink_create_ringbuffer (GstBaseAudioSink *
673     sink);
674
675 static void
676 gst_jack_audio_sink_base_init (gpointer g_class)
677 {
678   GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
679
680   gst_element_class_set_details_simple (element_class, "Audio Sink (Jack)",
681       "Sink/Audio", "Output audio to a JACK server",
682       "Wim Taymans <wim.taymans@gmail.com>");
683
684   gst_element_class_add_pad_template (element_class,
685       gst_static_pad_template_get (&jackaudiosink_sink_factory));
686 }
687
688 static void
689 gst_jack_audio_sink_class_init (GstJackAudioSinkClass * klass)
690 {
691   GObjectClass *gobject_class;
692   GstBaseSinkClass *gstbasesink_class;
693   GstBaseAudioSinkClass *gstbaseaudiosink_class;
694
695   gobject_class = (GObjectClass *) klass;
696   gstbasesink_class = (GstBaseSinkClass *) klass;
697   gstbaseaudiosink_class = (GstBaseAudioSinkClass *) klass;
698
699   gobject_class->dispose = gst_jack_audio_sink_dispose;
700   gobject_class->get_property = gst_jack_audio_sink_get_property;
701   gobject_class->set_property = gst_jack_audio_sink_set_property;
702
703   g_object_class_install_property (gobject_class, PROP_CONNECT,
704       g_param_spec_enum ("connect", "Connect",
705           "Specify how the output ports will be connected",
706           GST_TYPE_JACK_CONNECT, DEFAULT_PROP_CONNECT,
707           G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
708
709   g_object_class_install_property (gobject_class, PROP_SERVER,
710       g_param_spec_string ("server", "Server",
711           "The Jack server to connect to (NULL = default)",
712           DEFAULT_PROP_SERVER, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
713
714   g_object_class_install_property (gobject_class, PROP_CLIENT,
715       g_param_spec_boxed ("client", "JackClient", "Handle for jack client",
716           GST_TYPE_JACK_CLIENT,
717           GST_PARAM_MUTABLE_READY | G_PARAM_READWRITE |
718           G_PARAM_STATIC_STRINGS));
719
720   gstbasesink_class->get_caps = GST_DEBUG_FUNCPTR (gst_jack_audio_sink_getcaps);
721
722   gstbaseaudiosink_class->create_ringbuffer =
723       GST_DEBUG_FUNCPTR (gst_jack_audio_sink_create_ringbuffer);
724
725   /* ref class from a thread-safe context to work around missing bit of
726    * thread-safety in GObject */
727   g_type_class_ref (GST_TYPE_JACK_RING_BUFFER);
728
729   gst_jack_audio_client_init ();
730 }
731
732 static void
733 gst_jack_audio_sink_init (GstJackAudioSink * sink,
734     GstJackAudioSinkClass * g_class)
735 {
736   sink->connect = DEFAULT_PROP_CONNECT;
737   sink->server = g_strdup (DEFAULT_PROP_SERVER);
738   sink->jclient = NULL;
739   sink->ports = NULL;
740   sink->port_count = 0;
741   sink->buffers = NULL;
742 }
743
744 static void
745 gst_jack_audio_sink_dispose (GObject * object)
746 {
747   GstJackAudioSink *sink = GST_JACK_AUDIO_SINK (object);
748
749   gst_caps_replace (&sink->caps, NULL);
750   G_OBJECT_CLASS (parent_class)->dispose (object);
751 }
752
753 static void
754 gst_jack_audio_sink_set_property (GObject * object, guint prop_id,
755     const GValue * value, GParamSpec * pspec)
756 {
757   GstJackAudioSink *sink;
758
759   sink = GST_JACK_AUDIO_SINK (object);
760
761   switch (prop_id) {
762     case PROP_CONNECT:
763       sink->connect = g_value_get_enum (value);
764       break;
765     case PROP_SERVER:
766       g_free (sink->server);
767       sink->server = g_value_dup_string (value);
768       break;
769     case PROP_CLIENT:
770       if (GST_STATE (sink) == GST_STATE_NULL ||
771           GST_STATE (sink) == GST_STATE_READY) {
772         sink->jclient = g_value_get_boxed (value);
773       }
774       break;
775     default:
776       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
777       break;
778   }
779 }
780
781 static void
782 gst_jack_audio_sink_get_property (GObject * object, guint prop_id,
783     GValue * value, GParamSpec * pspec)
784 {
785   GstJackAudioSink *sink;
786
787   sink = GST_JACK_AUDIO_SINK (object);
788
789   switch (prop_id) {
790     case PROP_CONNECT:
791       g_value_set_enum (value, sink->connect);
792       break;
793     case PROP_SERVER:
794       g_value_set_string (value, sink->server);
795       break;
796     case PROP_CLIENT:
797       g_value_set_boxed (value, sink->jclient);
798       break;
799     default:
800       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
801       break;
802   }
803 }
804
805 static GstCaps *
806 gst_jack_audio_sink_getcaps (GstBaseSink * bsink)
807 {
808   GstJackAudioSink *sink = GST_JACK_AUDIO_SINK (bsink);
809   const char **ports;
810   gint min, max;
811   gint rate;
812   jack_client_t *client;
813
814   if (sink->client == NULL)
815     goto no_client;
816
817   client = gst_jack_audio_client_get_client (sink->client);
818
819   if (sink->connect == GST_JACK_CONNECT_AUTO) {
820     /* get a port count, this is the number of channels we can automatically
821      * connect. */
822     ports = jack_get_ports (client, NULL, NULL,
823         JackPortIsPhysical | JackPortIsInput);
824     max = 0;
825     if (ports != NULL) {
826       for (; ports[max]; max++);
827       free (ports);
828     } else
829       max = 0;
830   } else {
831     /* we allow any number of pads, something else is going to connect the
832      * pads. */
833     max = G_MAXINT;
834   }
835   min = MIN (1, max);
836
837   rate = jack_get_sample_rate (client);
838
839   GST_DEBUG_OBJECT (sink, "got %d-%d ports, samplerate: %d", min, max, rate);
840
841   if (!sink->caps) {
842     sink->caps = gst_caps_new_simple ("audio/x-raw-float",
843         "endianness", G_TYPE_INT, G_BYTE_ORDER,
844         "width", G_TYPE_INT, 32,
845         "rate", G_TYPE_INT, rate,
846         "channels", GST_TYPE_INT_RANGE, min, max, NULL);
847   }
848   GST_INFO_OBJECT (sink, "returning caps %" GST_PTR_FORMAT, sink->caps);
849
850   return gst_caps_ref (sink->caps);
851
852   /* ERRORS */
853 no_client:
854   {
855     GST_DEBUG_OBJECT (sink, "device not open, using template caps");
856     /* base class will get template caps for us when we return NULL */
857     return NULL;
858   }
859 }
860
861 static GstRingBuffer *
862 gst_jack_audio_sink_create_ringbuffer (GstBaseAudioSink * sink)
863 {
864   GstRingBuffer *buffer;
865
866   buffer = g_object_new (GST_TYPE_JACK_RING_BUFFER, NULL);
867   GST_DEBUG_OBJECT (sink, "created ringbuffer @%p", buffer);
868
869   return buffer;
870 }