2 * Copyright (C) 2005 Wim Taymans <wim@fluendo.com>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
21 * SECTION:gstaudioringbuffer
22 * @short_description: Base class for audio ringbuffer implementations
23 * @see_also: #GstAudioBaseSink, #GstAudioSink
27 * This object is the base class for audio ringbuffers used by the base
28 * audio source and sink classes.
31 * The ringbuffer abstracts a circular buffer of data. One reader and
32 * one writer can operate on the data from different threads in a lockfree
33 * manner. The base class is sufficiently flexible to be used as an
34 * abstraction for DMA based ringbuffers as well as a pure software
39 * Last reviewed on 2006-02-02 (0.10.4)
44 #include <gst/audio/audio.h>
45 #include "gstaudioringbuffer.h"
47 GST_DEBUG_CATEGORY_STATIC (gst_audio_ring_buffer_debug);
48 #define GST_CAT_DEFAULT gst_audio_ring_buffer_debug
50 static void gst_audio_ring_buffer_dispose (GObject * object);
51 static void gst_audio_ring_buffer_finalize (GObject * object);
53 static gboolean gst_audio_ring_buffer_pause_unlocked (GstAudioRingBuffer * buf);
54 static void default_clear_all (GstAudioRingBuffer * buf);
55 static guint default_commit (GstAudioRingBuffer * buf, guint64 * sample,
56 guint8 * data, gint in_samples, gint out_samples, gint * accum);
58 /* ringbuffer abstract base class */
59 G_DEFINE_ABSTRACT_TYPE (GstAudioRingBuffer, gst_audio_ring_buffer,
63 gst_audio_ring_buffer_class_init (GstAudioRingBufferClass * klass)
65 GObjectClass *gobject_class;
66 GstAudioRingBufferClass *gstaudioringbuffer_class;
68 gobject_class = (GObjectClass *) klass;
69 gstaudioringbuffer_class = (GstAudioRingBufferClass *) klass;
71 GST_DEBUG_CATEGORY_INIT (gst_audio_ring_buffer_debug, "ringbuffer", 0,
74 gobject_class->dispose = gst_audio_ring_buffer_dispose;
75 gobject_class->finalize = gst_audio_ring_buffer_finalize;
77 gstaudioringbuffer_class->clear_all = GST_DEBUG_FUNCPTR (default_clear_all);
78 gstaudioringbuffer_class->commit = GST_DEBUG_FUNCPTR (default_commit);
82 gst_audio_ring_buffer_init (GstAudioRingBuffer * ringbuffer)
84 ringbuffer->open = FALSE;
85 ringbuffer->acquired = FALSE;
86 ringbuffer->state = GST_AUDIO_RING_BUFFER_STATE_STOPPED;
87 g_cond_init (&ringbuffer->cond);
88 ringbuffer->waiting = 0;
89 ringbuffer->empty_seg = NULL;
90 ringbuffer->flushing = TRUE;
94 gst_audio_ring_buffer_dispose (GObject * object)
96 GstAudioRingBuffer *ringbuffer = GST_AUDIO_RING_BUFFER (object);
98 gst_caps_replace (&ringbuffer->spec.caps, NULL);
100 G_OBJECT_CLASS (gst_audio_ring_buffer_parent_class)->dispose (G_OBJECT
105 gst_audio_ring_buffer_finalize (GObject * object)
107 GstAudioRingBuffer *ringbuffer = GST_AUDIO_RING_BUFFER (object);
109 g_cond_clear (&ringbuffer->cond);
110 g_free (ringbuffer->empty_seg);
112 G_OBJECT_CLASS (gst_audio_ring_buffer_parent_class)->finalize (G_OBJECT
116 #ifndef GST_DISABLE_GST_DEBUG
117 static const gchar *format_type_names[] = {
134 * gst_audio_ring_buffer_debug_spec_caps:
135 * @spec: the spec to debug
137 * Print debug info about the parsed caps in @spec to the debug log.
140 gst_audio_ring_buffer_debug_spec_caps (GstAudioRingBufferSpec * spec)
146 GST_DEBUG ("spec caps: %p %" GST_PTR_FORMAT, spec->caps, spec->caps);
147 GST_DEBUG ("parsed caps: type: %d, '%s'", spec->type,
148 format_type_names[spec->type]);
150 GST_DEBUG ("parsed caps: width: %d", spec->width);
151 GST_DEBUG ("parsed caps: sign: %d", spec->sign);
152 GST_DEBUG ("parsed caps: bigend: %d", spec->bigend);
153 GST_DEBUG ("parsed caps: rate: %d", spec->rate);
154 GST_DEBUG ("parsed caps: channels: %d", spec->channels);
155 GST_DEBUG ("parsed caps: sample bytes: %d", spec->bytes_per_sample);
156 bytes = (spec->width >> 3) * spec->channels;
157 for (i = 0; i < bytes; i++) {
158 GST_DEBUG ("silence byte %d: %02x", i, spec->silence_sample[i]);
164 * gst_audio_ring_buffer_debug_spec_buff:
165 * @spec: the spec to debug
167 * Print debug info about the buffer sized in @spec to the debug log.
170 gst_audio_ring_buffer_debug_spec_buff (GstAudioRingBufferSpec * spec)
172 gint bpf = GST_AUDIO_INFO_BPF (&spec->info);
174 GST_DEBUG ("acquire ringbuffer: buffer time: %" G_GINT64_FORMAT " usec",
176 GST_DEBUG ("acquire ringbuffer: latency time: %" G_GINT64_FORMAT " usec",
178 GST_DEBUG ("acquire ringbuffer: total segments: %d", spec->segtotal);
179 GST_DEBUG ("acquire ringbuffer: latency segments: %d", spec->seglatency);
180 GST_DEBUG ("acquire ringbuffer: segment size: %d bytes = %d samples",
181 spec->segsize, (bpf != 0) ? (spec->segsize / bpf) : -1);
182 GST_DEBUG ("acquire ringbuffer: buffer size: %d bytes = %d samples",
183 spec->segsize * spec->segtotal,
184 (bpf != 0) ? (spec->segsize * spec->segtotal / bpf) : -1);
188 * gst_audio_ring_buffer_parse_caps:
192 * Parse @caps into @spec.
194 * Returns: TRUE if the caps could be parsed.
197 gst_audio_ring_buffer_parse_caps (GstAudioRingBufferSpec * spec, GstCaps * caps)
199 const gchar *mimetype;
200 GstStructure *structure;
204 structure = gst_caps_get_structure (caps, 0);
205 gst_audio_info_init (&info);
207 /* we have to differentiate between int and float formats */
208 mimetype = gst_structure_get_name (structure);
210 if (g_str_equal (mimetype, "audio/x-raw")) {
211 if (!gst_audio_info_from_caps (&info, caps))
214 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_RAW;
215 } else if (g_str_equal (mimetype, "audio/x-alaw")) {
216 /* extract the needed information from the cap */
217 if (!(gst_structure_get_int (structure, "rate", &info.rate) &&
218 gst_structure_get_int (structure, "channels", &info.channels)))
221 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_A_LAW;
222 info.bpf = info.channels;
223 } else if (g_str_equal (mimetype, "audio/x-mulaw")) {
224 /* extract the needed information from the cap */
225 if (!(gst_structure_get_int (structure, "rate", &info.rate) &&
226 gst_structure_get_int (structure, "channels", &info.channels)))
229 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MU_LAW;
230 info.bpf = info.channels;
231 } else if (g_str_equal (mimetype, "audio/x-iec958")) {
232 /* extract the needed information from the cap */
233 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
236 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_IEC958;
238 } else if (g_str_equal (mimetype, "audio/x-ac3")) {
239 /* extract the needed information from the cap */
240 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
243 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_AC3;
245 } else if (g_str_equal (mimetype, "audio/x-eac3")) {
246 /* extract the needed information from the cap */
247 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
250 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_EAC3;
252 } else if (g_str_equal (mimetype, "audio/x-dts")) {
253 /* extract the needed information from the cap */
254 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
257 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_DTS;
259 } else if (g_str_equal (mimetype, "audio/mpeg") &&
260 gst_structure_get_int (structure, "mpegaudioversion", &i) &&
261 (i == 1 || i == 2)) {
262 /* Now we know this is MPEG-1 or MPEG-2 (non AAC) */
263 /* extract the needed information from the cap */
264 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
267 spec->type = GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MPEG;
269 } else if (g_str_equal (mimetype, "audio/mpeg") &&
270 gst_structure_get_int (structure, "mpegversion", &i) &&
271 (i == 2 || i == 4) &&
272 !g_strcmp0 (gst_structure_get_string (structure, "stream-format"),
274 /* MPEG-2 AAC or MPEG-4 AAC */
275 if (!(gst_structure_get_int (structure, "rate", &info.rate)))
277 spec->type = (i == 2) ? GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MPEG2_AAC :
278 GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MPEG4_AAC;
284 gst_caps_replace (&spec->caps, caps);
286 g_return_val_if_fail (spec->latency_time != 0, FALSE);
288 /* calculate suggested segsize and segtotal. segsize should be one unit
289 * of 'latency_time' samples, scaling for the fact that latency_time is
290 * currently stored in microseconds (FIXME: in 0.11) */
291 spec->segsize = gst_util_uint64_scale (info.rate * info.bpf,
292 spec->latency_time, GST_SECOND / GST_USECOND);
293 /* Round to an integer number of samples */
294 spec->segsize -= spec->segsize % info.bpf;
296 spec->segtotal = spec->buffer_time / spec->latency_time;
297 /* leave the latency undefined now, implementations can change it but if it's
298 * not changed, we assume the same value as segtotal */
299 spec->seglatency = -1;
303 gst_audio_ring_buffer_debug_spec_caps (spec);
304 gst_audio_ring_buffer_debug_spec_buff (spec);
311 GST_DEBUG ("could not parse caps");
317 * gst_audio_ring_buffer_convert:
318 * @buf: the #GstAudioRingBuffer
319 * @src_fmt: the source format
320 * @src_val: the source value
321 * @dest_fmt: the destination format
322 * @dest_val: a location to store the converted value
324 * Convert @src_val in @src_fmt to the equivalent value in @dest_fmt. The result
325 * will be put in @dest_val.
327 * Returns: TRUE if the conversion succeeded.
330 gst_audio_ring_buffer_convert (GstAudioRingBuffer * buf,
331 GstFormat src_fmt, gint64 src_val, GstFormat dest_fmt, gint64 * dest_val)
335 GST_OBJECT_LOCK (buf);
337 gst_audio_info_convert (&buf->spec.info, src_fmt, src_val, dest_fmt,
339 GST_OBJECT_UNLOCK (buf);
345 * gst_audio_ring_buffer_set_callback:
346 * @buf: the #GstAudioRingBuffer to set the callback on
347 * @cb: (scope async): the callback to set
348 * @user_data: user data passed to the callback
350 * Sets the given callback function on the buffer. This function
351 * will be called every time a segment has been written to a device.
356 gst_audio_ring_buffer_set_callback (GstAudioRingBuffer * buf,
357 GstAudioRingBufferCallback cb, gpointer user_data)
359 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
361 GST_OBJECT_LOCK (buf);
363 buf->cb_data = user_data;
364 GST_OBJECT_UNLOCK (buf);
369 * gst_audio_ring_buffer_open_device:
370 * @buf: the #GstAudioRingBuffer
372 * Open the audio device associated with the ring buffer. Does not perform any
373 * setup on the device. You must open the device before acquiring the ring
376 * Returns: TRUE if the device could be opened, FALSE on error.
381 gst_audio_ring_buffer_open_device (GstAudioRingBuffer * buf)
384 GstAudioRingBufferClass *rclass;
386 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
388 GST_DEBUG_OBJECT (buf, "opening device");
390 GST_OBJECT_LOCK (buf);
391 if (G_UNLIKELY (buf->open))
396 /* if this fails, something is wrong in this file */
397 g_assert (!buf->acquired);
399 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
400 if (G_LIKELY (rclass->open_device))
401 res = rclass->open_device (buf);
403 if (G_UNLIKELY (!res))
406 GST_DEBUG_OBJECT (buf, "opened device");
409 GST_OBJECT_UNLOCK (buf);
416 GST_DEBUG_OBJECT (buf, "Device for ring buffer already open");
417 g_warning ("Device for ring buffer %p already open, fix your code", buf);
424 GST_DEBUG_OBJECT (buf, "failed opening device");
430 * gst_audio_ring_buffer_close_device:
431 * @buf: the #GstAudioRingBuffer
433 * Close the audio device associated with the ring buffer. The ring buffer
434 * should already have been released via gst_audio_ring_buffer_release().
436 * Returns: TRUE if the device could be closed, FALSE on error.
441 gst_audio_ring_buffer_close_device (GstAudioRingBuffer * buf)
444 GstAudioRingBufferClass *rclass;
446 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
448 GST_DEBUG_OBJECT (buf, "closing device");
450 GST_OBJECT_LOCK (buf);
451 if (G_UNLIKELY (!buf->open))
454 if (G_UNLIKELY (buf->acquired))
459 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
460 if (G_LIKELY (rclass->close_device))
461 res = rclass->close_device (buf);
463 if (G_UNLIKELY (!res))
466 GST_DEBUG_OBJECT (buf, "closed device");
469 GST_OBJECT_UNLOCK (buf);
476 GST_DEBUG_OBJECT (buf, "Device for ring buffer already closed");
477 g_warning ("Device for ring buffer %p already closed, fix your code", buf);
483 GST_DEBUG_OBJECT (buf, "Resources for ring buffer still acquired");
484 g_critical ("Resources for ring buffer %p still acquired", buf);
491 GST_DEBUG_OBJECT (buf, "error closing device");
497 * gst_audio_ring_buffer_device_is_open:
498 * @buf: the #GstAudioRingBuffer
500 * Checks the status of the device associated with the ring buffer.
502 * Returns: TRUE if the device was open, FALSE if it was closed.
507 gst_audio_ring_buffer_device_is_open (GstAudioRingBuffer * buf)
511 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
513 GST_OBJECT_LOCK (buf);
515 GST_OBJECT_UNLOCK (buf);
521 * gst_audio_ring_buffer_acquire:
522 * @buf: the #GstAudioRingBuffer to acquire
523 * @spec: the specs of the buffer
525 * Allocate the resources for the ringbuffer. This function fills
526 * in the data pointer of the ring buffer with a valid #GstBuffer
527 * to which samples can be written.
529 * Returns: TRUE if the device could be acquired, FALSE on error.
534 gst_audio_ring_buffer_acquire (GstAudioRingBuffer * buf,
535 GstAudioRingBufferSpec * spec)
537 gboolean res = FALSE;
538 GstAudioRingBufferClass *rclass;
539 gint segsize, bpf, i;
541 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
543 GST_DEBUG_OBJECT (buf, "acquiring device %p", buf);
545 GST_OBJECT_LOCK (buf);
546 if (G_UNLIKELY (!buf->open))
549 if (G_UNLIKELY (buf->acquired))
552 buf->acquired = TRUE;
553 buf->need_reorder = FALSE;
555 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
556 if (G_LIKELY (rclass->acquire))
557 res = rclass->acquire (buf, spec);
559 /* Only reorder for raw audio */
560 buf->need_reorder = (buf->need_reorder
561 && buf->spec.type == GST_AUDIO_RING_BUFFER_FORMAT_TYPE_RAW);
563 if (G_UNLIKELY (!res))
566 GST_INFO_OBJECT (buf, "Allocating an array for %d timestamps",
568 buf->timestamps = g_slice_alloc0 (sizeof (GstClockTime) * spec->segtotal);
569 /* initialize array with invalid timestamps */
570 for (i = 0; i < spec->segtotal; i++) {
571 buf->timestamps[i] = GST_CLOCK_TIME_NONE;
574 if (G_UNLIKELY ((bpf = buf->spec.info.bpf) == 0))
577 /* if the seglatency was overwritten with something else than -1, use it, else
578 * assume segtotal as the latency */
579 if (buf->spec.seglatency == -1)
580 buf->spec.seglatency = buf->spec.segtotal;
582 segsize = buf->spec.segsize;
584 buf->samples_per_seg = segsize / bpf;
586 /* create an empty segment */
587 g_free (buf->empty_seg);
588 buf->empty_seg = g_malloc (segsize);
590 if (buf->spec.type == GST_AUDIO_RING_BUFFER_FORMAT_TYPE_RAW) {
591 gst_audio_format_fill_silence (buf->spec.info.finfo, buf->empty_seg,
594 /* FIXME, non-raw formats get 0 as the empty sample */
595 memset (buf->empty_seg, 0, segsize);
597 GST_DEBUG_OBJECT (buf, "acquired device");
600 GST_OBJECT_UNLOCK (buf);
607 GST_DEBUG_OBJECT (buf, "device not opened");
608 g_critical ("Device for %p not opened", buf);
615 GST_DEBUG_OBJECT (buf, "device was acquired");
620 buf->acquired = FALSE;
621 GST_DEBUG_OBJECT (buf, "failed to acquire device");
627 ("invalid bytes_per_frame from acquire ringbuffer %p, fix the element",
629 buf->acquired = FALSE;
636 * gst_audio_ring_buffer_release:
637 * @buf: the #GstAudioRingBuffer to release
639 * Free the resources of the ringbuffer.
641 * Returns: TRUE if the device could be released, FALSE on error.
646 gst_audio_ring_buffer_release (GstAudioRingBuffer * buf)
648 gboolean res = FALSE;
649 GstAudioRingBufferClass *rclass;
651 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
653 GST_DEBUG_OBJECT (buf, "releasing device");
655 gst_audio_ring_buffer_stop (buf);
657 GST_OBJECT_LOCK (buf);
659 if (G_LIKELY (buf->timestamps)) {
660 GST_INFO_OBJECT (buf, "Freeing timestamp buffer, %d entries",
662 g_slice_free1 (sizeof (GstClockTime) * buf->spec.segtotal, buf->timestamps);
663 buf->timestamps = NULL;
666 if (G_UNLIKELY (!buf->acquired))
669 buf->acquired = FALSE;
671 /* if this fails, something is wrong in this file */
672 g_assert (buf->open == TRUE);
674 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
675 if (G_LIKELY (rclass->release))
676 res = rclass->release (buf);
678 /* signal any waiters */
679 GST_DEBUG_OBJECT (buf, "signal waiter");
680 GST_AUDIO_RING_BUFFER_SIGNAL (buf);
682 if (G_UNLIKELY (!res))
685 g_free (buf->empty_seg);
686 buf->empty_seg = NULL;
687 gst_caps_replace (&buf->spec.caps, NULL);
688 gst_audio_info_init (&buf->spec.info);
689 GST_DEBUG_OBJECT (buf, "released device");
692 GST_OBJECT_UNLOCK (buf);
700 GST_DEBUG_OBJECT (buf, "device was released");
705 buf->acquired = TRUE;
706 GST_DEBUG_OBJECT (buf, "failed to release device");
712 * gst_audio_ring_buffer_is_acquired:
713 * @buf: the #GstAudioRingBuffer to check
715 * Check if the ringbuffer is acquired and ready to use.
717 * Returns: TRUE if the ringbuffer is acquired, FALSE on error.
722 gst_audio_ring_buffer_is_acquired (GstAudioRingBuffer * buf)
726 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
728 GST_OBJECT_LOCK (buf);
730 GST_OBJECT_UNLOCK (buf);
736 * gst_audio_ring_buffer_activate:
737 * @buf: the #GstAudioRingBuffer to activate
738 * @active: the new mode
740 * Activate @buf to start or stop pulling data.
744 * Returns: TRUE if the device could be activated in the requested mode,
748 gst_audio_ring_buffer_activate (GstAudioRingBuffer * buf, gboolean active)
750 gboolean res = FALSE;
751 GstAudioRingBufferClass *rclass;
753 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
755 GST_DEBUG_OBJECT (buf, "activate device");
757 GST_OBJECT_LOCK (buf);
758 if (G_UNLIKELY (active && !buf->acquired))
761 if (G_UNLIKELY (buf->active == active))
764 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
765 /* if there is no activate function we assume it was started/released
766 * in the acquire method */
767 if (G_LIKELY (rclass->activate))
768 res = rclass->activate (buf, active);
772 if (G_UNLIKELY (!res))
773 goto activate_failed;
775 buf->active = active;
778 GST_OBJECT_UNLOCK (buf);
785 GST_DEBUG_OBJECT (buf, "device not acquired");
786 g_critical ("Device for %p not acquired", buf);
793 GST_DEBUG_OBJECT (buf, "device was active in mode %d", active);
798 GST_DEBUG_OBJECT (buf, "failed to activate device");
804 * gst_audio_ring_buffer_is_active:
805 * @buf: the #GstAudioRingBuffer
807 * Check if @buf is activated.
811 * Returns: TRUE if the device is active.
814 gst_audio_ring_buffer_is_active (GstAudioRingBuffer * buf)
818 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
820 GST_OBJECT_LOCK (buf);
822 GST_OBJECT_UNLOCK (buf);
829 * gst_audio_ring_buffer_set_flushing:
830 * @buf: the #GstAudioRingBuffer to flush
831 * @flushing: the new mode
833 * Set the ringbuffer to flushing mode or normal mode.
838 gst_audio_ring_buffer_set_flushing (GstAudioRingBuffer * buf, gboolean flushing)
840 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
842 GST_OBJECT_LOCK (buf);
843 buf->flushing = flushing;
846 gst_audio_ring_buffer_pause_unlocked (buf);
848 gst_audio_ring_buffer_clear_all (buf);
850 GST_OBJECT_UNLOCK (buf);
854 * gst_audio_ring_buffer_is_flushing:
855 * @buf: the #GstAudioRingBuffer
857 * Check if @buf is flushing.
861 * Returns: TRUE if the device is flushing.
864 gst_audio_ring_buffer_is_flushing (GstAudioRingBuffer * buf)
868 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), TRUE);
870 GST_OBJECT_LOCK (buf);
872 GST_OBJECT_UNLOCK (buf);
878 * gst_audio_ring_buffer_start:
879 * @buf: the #GstAudioRingBuffer to start
881 * Start processing samples from the ringbuffer.
883 * Returns: TRUE if the device could be started, FALSE on error.
888 gst_audio_ring_buffer_start (GstAudioRingBuffer * buf)
890 gboolean res = FALSE;
891 GstAudioRingBufferClass *rclass;
892 gboolean resume = FALSE;
894 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
896 GST_DEBUG_OBJECT (buf, "starting ringbuffer");
898 GST_OBJECT_LOCK (buf);
899 if (G_UNLIKELY (buf->flushing))
902 if (G_UNLIKELY (!buf->acquired))
905 if (G_UNLIKELY (g_atomic_int_get (&buf->may_start) == FALSE))
908 /* if stopped, set to started */
909 res = g_atomic_int_compare_and_exchange (&buf->state,
910 GST_AUDIO_RING_BUFFER_STATE_STOPPED, GST_AUDIO_RING_BUFFER_STATE_STARTED);
913 GST_DEBUG_OBJECT (buf, "was not stopped, try paused");
914 /* was not stopped, try from paused */
915 res = g_atomic_int_compare_and_exchange (&buf->state,
916 GST_AUDIO_RING_BUFFER_STATE_PAUSED,
917 GST_AUDIO_RING_BUFFER_STATE_STARTED);
919 /* was not paused either, must be started then */
921 GST_DEBUG_OBJECT (buf, "was not paused, must have been started");
925 GST_DEBUG_OBJECT (buf, "resuming");
928 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
930 if (G_LIKELY (rclass->resume))
931 res = rclass->resume (buf);
933 if (G_LIKELY (rclass->start))
934 res = rclass->start (buf);
937 if (G_UNLIKELY (!res)) {
938 buf->state = GST_AUDIO_RING_BUFFER_STATE_PAUSED;
939 GST_DEBUG_OBJECT (buf, "failed to start");
941 GST_DEBUG_OBJECT (buf, "started");
945 GST_OBJECT_UNLOCK (buf);
951 GST_DEBUG_OBJECT (buf, "we are flushing");
952 GST_OBJECT_UNLOCK (buf);
957 GST_DEBUG_OBJECT (buf, "we are not acquired");
958 GST_OBJECT_UNLOCK (buf);
963 GST_DEBUG_OBJECT (buf, "we may not start");
964 GST_OBJECT_UNLOCK (buf);
970 gst_audio_ring_buffer_pause_unlocked (GstAudioRingBuffer * buf)
972 gboolean res = FALSE;
973 GstAudioRingBufferClass *rclass;
975 GST_DEBUG_OBJECT (buf, "pausing ringbuffer");
977 /* if started, set to paused */
978 res = g_atomic_int_compare_and_exchange (&buf->state,
979 GST_AUDIO_RING_BUFFER_STATE_STARTED, GST_AUDIO_RING_BUFFER_STATE_PAUSED);
984 /* signal any waiters */
985 GST_DEBUG_OBJECT (buf, "signal waiter");
986 GST_AUDIO_RING_BUFFER_SIGNAL (buf);
988 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
989 if (G_LIKELY (rclass->pause))
990 res = rclass->pause (buf);
992 if (G_UNLIKELY (!res)) {
993 buf->state = GST_AUDIO_RING_BUFFER_STATE_STARTED;
994 GST_DEBUG_OBJECT (buf, "failed to pause");
996 GST_DEBUG_OBJECT (buf, "paused");
1003 /* was not started */
1004 GST_DEBUG_OBJECT (buf, "was not started");
1010 * gst_audio_ring_buffer_pause:
1011 * @buf: the #GstAudioRingBuffer to pause
1013 * Pause processing samples from the ringbuffer.
1015 * Returns: TRUE if the device could be paused, FALSE on error.
1020 gst_audio_ring_buffer_pause (GstAudioRingBuffer * buf)
1022 gboolean res = FALSE;
1024 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
1026 GST_OBJECT_LOCK (buf);
1027 if (G_UNLIKELY (buf->flushing))
1030 if (G_UNLIKELY (!buf->acquired))
1033 res = gst_audio_ring_buffer_pause_unlocked (buf);
1034 GST_OBJECT_UNLOCK (buf);
1041 GST_DEBUG_OBJECT (buf, "we are flushing");
1042 GST_OBJECT_UNLOCK (buf);
1047 GST_DEBUG_OBJECT (buf, "not acquired");
1048 GST_OBJECT_UNLOCK (buf);
1054 * gst_audio_ring_buffer_stop:
1055 * @buf: the #GstAudioRingBuffer to stop
1057 * Stop processing samples from the ringbuffer.
1059 * Returns: TRUE if the device could be stopped, FALSE on error.
1064 gst_audio_ring_buffer_stop (GstAudioRingBuffer * buf)
1066 gboolean res = FALSE;
1067 GstAudioRingBufferClass *rclass;
1069 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
1071 GST_DEBUG_OBJECT (buf, "stopping");
1073 GST_OBJECT_LOCK (buf);
1075 /* if started, set to stopped */
1076 res = g_atomic_int_compare_and_exchange (&buf->state,
1077 GST_AUDIO_RING_BUFFER_STATE_STARTED, GST_AUDIO_RING_BUFFER_STATE_STOPPED);
1080 GST_DEBUG_OBJECT (buf, "was not started, try paused");
1081 /* was not started, try from paused */
1082 res = g_atomic_int_compare_and_exchange (&buf->state,
1083 GST_AUDIO_RING_BUFFER_STATE_PAUSED,
1084 GST_AUDIO_RING_BUFFER_STATE_STOPPED);
1086 /* was not paused either, must have been stopped then */
1088 GST_DEBUG_OBJECT (buf, "was not paused, must have been stopped");
1093 /* signal any waiters */
1094 GST_DEBUG_OBJECT (buf, "signal waiter");
1095 GST_AUDIO_RING_BUFFER_SIGNAL (buf);
1097 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
1098 if (G_LIKELY (rclass->stop))
1099 res = rclass->stop (buf);
1101 if (G_UNLIKELY (!res)) {
1102 buf->state = GST_AUDIO_RING_BUFFER_STATE_STARTED;
1103 GST_DEBUG_OBJECT (buf, "failed to stop");
1105 GST_DEBUG_OBJECT (buf, "stopped");
1108 GST_OBJECT_UNLOCK (buf);
1114 * gst_audio_ring_buffer_delay:
1115 * @buf: the #GstAudioRingBuffer to query
1117 * Get the number of samples queued in the audio device. This is
1118 * usually less than the segment size but can be bigger when the
1119 * implementation uses another internal buffer between the audio
1122 * For playback ringbuffers this is the amount of samples transfered from the
1123 * ringbuffer to the device but still not played.
1125 * For capture ringbuffers this is the amount of samples in the device that are
1126 * not yet transfered to the ringbuffer.
1128 * Returns: The number of samples queued in the audio device.
1133 gst_audio_ring_buffer_delay (GstAudioRingBuffer * buf)
1135 GstAudioRingBufferClass *rclass;
1138 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), 0);
1140 /* buffer must be acquired */
1141 if (G_UNLIKELY (!gst_audio_ring_buffer_is_acquired (buf)))
1144 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
1145 if (G_LIKELY (rclass->delay))
1146 res = rclass->delay (buf);
1154 GST_DEBUG_OBJECT (buf, "not acquired");
1160 * gst_audio_ring_buffer_samples_done:
1161 * @buf: the #GstAudioRingBuffer to query
1163 * Get the number of samples that were processed by the ringbuffer
1164 * since it was last started. This does not include the number of samples not
1165 * yet processed (see gst_audio_ring_buffer_delay()).
1167 * Returns: The number of samples processed by the ringbuffer.
1172 gst_audio_ring_buffer_samples_done (GstAudioRingBuffer * buf)
1177 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), 0);
1179 /* get the amount of segments we processed */
1180 segdone = g_atomic_int_get (&buf->segdone);
1182 /* convert to samples */
1183 samples = ((guint64) segdone) * buf->samples_per_seg;
1189 * gst_audio_ring_buffer_set_sample:
1190 * @buf: the #GstAudioRingBuffer to use
1191 * @sample: the sample number to set
1193 * Make sure that the next sample written to the device is
1194 * accounted for as being the @sample sample written to the
1195 * device. This value will be used in reporting the current
1196 * sample position of the ringbuffer.
1198 * This function will also clear the buffer with silence.
1203 gst_audio_ring_buffer_set_sample (GstAudioRingBuffer * buf, guint64 sample)
1205 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1210 if (G_UNLIKELY (buf->samples_per_seg == 0))
1213 /* FIXME, we assume the ringbuffer can restart at a random
1214 * position, round down to the beginning and keep track of
1215 * offset when calculating the processed samples. */
1216 buf->segbase = buf->segdone - sample / buf->samples_per_seg;
1218 gst_audio_ring_buffer_clear_all (buf);
1220 GST_DEBUG_OBJECT (buf, "set sample to %" G_GUINT64_FORMAT ", segbase %d",
1221 sample, buf->segbase);
1225 default_clear_all (GstAudioRingBuffer * buf)
1229 /* not fatal, we just are not negotiated yet */
1230 if (G_UNLIKELY (buf->spec.segtotal <= 0))
1233 GST_DEBUG_OBJECT (buf, "clear all segments");
1235 for (i = 0; i < buf->spec.segtotal; i++) {
1236 gst_audio_ring_buffer_clear (buf, i);
1241 * gst_audio_ring_buffer_clear_all:
1242 * @buf: the #GstAudioRingBuffer to clear
1244 * Fill the ringbuffer with silence.
1249 gst_audio_ring_buffer_clear_all (GstAudioRingBuffer * buf)
1251 GstAudioRingBufferClass *rclass;
1253 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1255 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
1257 if (G_LIKELY (rclass->clear_all))
1258 rclass->clear_all (buf);
1263 wait_segment (GstAudioRingBuffer * buf)
1266 gboolean wait = TRUE;
1268 /* buffer must be started now or we deadlock since nobody is reading */
1269 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1270 GST_AUDIO_RING_BUFFER_STATE_STARTED)) {
1271 /* see if we are allowed to start it */
1272 if (G_UNLIKELY (g_atomic_int_get (&buf->may_start) == FALSE))
1275 GST_DEBUG_OBJECT (buf, "start!");
1276 segments = g_atomic_int_get (&buf->segdone);
1277 gst_audio_ring_buffer_start (buf);
1279 /* After starting, the writer may have wrote segments already and then we
1280 * don't need to wait anymore */
1281 if (G_LIKELY (g_atomic_int_get (&buf->segdone) != segments))
1285 /* take lock first, then update our waiting flag */
1286 GST_OBJECT_LOCK (buf);
1287 if (G_UNLIKELY (buf->flushing))
1290 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1291 GST_AUDIO_RING_BUFFER_STATE_STARTED))
1294 if (G_LIKELY (wait)) {
1295 if (g_atomic_int_compare_and_exchange (&buf->waiting, 0, 1)) {
1296 GST_DEBUG_OBJECT (buf, "waiting..");
1297 GST_AUDIO_RING_BUFFER_WAIT (buf);
1299 if (G_UNLIKELY (buf->flushing))
1302 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1303 GST_AUDIO_RING_BUFFER_STATE_STARTED))
1307 GST_OBJECT_UNLOCK (buf);
1314 g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0);
1315 GST_DEBUG_OBJECT (buf, "stopped processing");
1316 GST_OBJECT_UNLOCK (buf);
1321 g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0);
1322 GST_DEBUG_OBJECT (buf, "flushing");
1323 GST_OBJECT_UNLOCK (buf);
1328 GST_DEBUG_OBJECT (buf, "not allowed to start");
1335 #define REORDER_SAMPLE(d, s, l) \
1338 for (i = 0; i < channels; i++) { \
1339 memcpy (d + reorder_map[i] * bps, s + i * bps, bps); \
1343 #define REORDER_SAMPLES(d, s, len) \
1345 gint i, len_ = len / bpf; \
1346 guint8 *d_ = d, *s_ = s; \
1347 for (i = 0; i < len_; i++) { \
1348 REORDER_SAMPLE(d_, s_, bpf); \
1354 #define FWD_SAMPLES(s,se,d,de,F) \
1356 /* no rate conversion */ \
1357 guint towrite = MIN (se + bpf - s, de - d); \
1360 F (d, s, towrite); \
1361 in_samples -= towrite / bpf; \
1362 out_samples -= towrite / bpf; \
1364 GST_DEBUG ("copy %u bytes", towrite); \
1367 /* in_samples >= out_samples, rate > 1.0 */
1368 #define FWD_UP_SAMPLES(s,se,d,de,F) \
1370 guint8 *sb = s, *db = d; \
1371 while (s <= se && d < de) { \
1376 if ((*accum << 1) >= inr) { \
1381 in_samples -= (s - sb)/bpf; \
1382 out_samples -= (d - db)/bpf; \
1383 GST_DEBUG ("fwd_up end %d/%d",*accum,*toprocess); \
1386 /* out_samples > in_samples, for rates smaller than 1.0 */
1387 #define FWD_DOWN_SAMPLES(s,se,d,de,F) \
1389 guint8 *sb = s, *db = d; \
1390 while (s <= se && d < de) { \
1395 if ((*accum << 1) >= outr) { \
1400 in_samples -= (s - sb)/bpf; \
1401 out_samples -= (d - db)/bpf; \
1402 GST_DEBUG ("fwd_down end %d/%d",*accum,*toprocess); \
1405 #define REV_UP_SAMPLES(s,se,d,de,F) \
1407 guint8 *sb = se, *db = d; \
1408 while (s <= se && d < de) { \
1413 while (d < de && (*accum << 1) >= inr) { \
1418 in_samples -= (sb - se)/bpf; \
1419 out_samples -= (d - db)/bpf; \
1420 GST_DEBUG ("rev_up end %d/%d",*accum,*toprocess); \
1423 #define REV_DOWN_SAMPLES(s,se,d,de,F) \
1425 guint8 *sb = se, *db = d; \
1426 while (s <= se && d < de) { \
1431 while (s <= se && (*accum << 1) >= outr) { \
1436 in_samples -= (sb - se)/bpf; \
1437 out_samples -= (d - db)/bpf; \
1438 GST_DEBUG ("rev_down end %d/%d",*accum,*toprocess); \
1442 default_commit (GstAudioRingBuffer * buf, guint64 * sample,
1443 guint8 * data, gint in_samples, gint out_samples, gint * accum)
1446 gint segsize, segtotal, channels, bps, bpf, sps;
1447 guint8 *dest, *data_end;
1448 gint writeseg, sampleoff;
1452 gboolean need_reorder;
1454 g_return_val_if_fail (buf->memory != NULL, -1);
1455 g_return_val_if_fail (data != NULL, -1);
1457 need_reorder = buf->need_reorder;
1459 channels = buf->spec.info.channels;
1461 segsize = buf->spec.segsize;
1462 segtotal = buf->spec.segtotal;
1463 bpf = buf->spec.info.bpf;
1464 bps = bpf / channels;
1465 sps = buf->samples_per_seg;
1467 reverse = out_samples < 0;
1468 out_samples = ABS (out_samples);
1470 if (in_samples >= out_samples)
1471 toprocess = &in_samples;
1473 toprocess = &out_samples;
1475 inr = in_samples - 1;
1476 outr = out_samples - 1;
1478 /* data_end points to the last sample we have to write, not past it. This is
1479 * needed to properly handle reverse playback: it points to the last sample. */
1480 data_end = data + (bpf * inr);
1482 /* figure out the segment and the offset inside the segment where
1483 * the first sample should be written. */
1484 writeseg = *sample / sps;
1485 sampleoff = (*sample % sps) * bpf;
1487 GST_DEBUG_OBJECT (buf, "write %d : %d", in_samples, out_samples);
1489 /* write out all samples */
1490 while (*toprocess > 0) {
1499 /* get the currently processed segment */
1500 segdone = g_atomic_int_get (&buf->segdone) - buf->segbase;
1502 /* see how far away it is from the write segment */
1503 diff = writeseg - segdone;
1505 GST_DEBUG_OBJECT (buf,
1506 "pointer at %d, write to %d-%d, diff %d, segtotal %d, segsize %d, base %d",
1507 segdone, writeseg, sampleoff, diff, segtotal, segsize, buf->segbase);
1509 /* segment too far ahead, writer too slow, we need to drop, hopefully UNLIKELY */
1510 if (G_UNLIKELY (diff < 0)) {
1511 /* we need to drop one segment at a time, pretend we wrote a segment. */
1516 /* write segment is within writable range, we can break the loop and
1517 * start writing the data. */
1518 if (diff < segtotal) {
1523 /* else we need to wait for the segment to become writable. */
1524 if (!wait_segment (buf))
1528 /* we can write now */
1529 ws = writeseg % segtotal;
1530 avail = MIN (segsize - sampleoff, bpf * out_samples);
1532 d = dest + (ws * segsize) + sampleoff;
1534 *sample += avail / bpf;
1536 GST_DEBUG_OBJECT (buf, "write @%p seg %d, sps %d, off %d, avail %d",
1537 dest + ws * segsize, ws, sps, sampleoff, avail);
1540 gint *reorder_map = buf->channel_reorder_map;
1542 if (G_LIKELY (inr == outr && !reverse)) {
1543 /* no rate conversion, simply copy samples */
1544 FWD_SAMPLES (data, data_end, d, d_end, REORDER_SAMPLES);
1545 } else if (!reverse) {
1547 /* forward speed up */
1548 FWD_UP_SAMPLES (data, data_end, d, d_end, REORDER_SAMPLE);
1550 /* forward slow down */
1551 FWD_DOWN_SAMPLES (data, data_end, d, d_end, REORDER_SAMPLE);
1554 /* reverse speed up */
1555 REV_UP_SAMPLES (data, data_end, d, d_end, REORDER_SAMPLE);
1557 /* reverse slow down */
1558 REV_DOWN_SAMPLES (data, data_end, d, d_end, REORDER_SAMPLE);
1561 if (G_LIKELY (inr == outr && !reverse)) {
1562 /* no rate conversion, simply copy samples */
1563 FWD_SAMPLES (data, data_end, d, d_end, memcpy);
1564 } else if (!reverse) {
1566 /* forward speed up */
1567 FWD_UP_SAMPLES (data, data_end, d, d_end, memcpy);
1569 /* forward slow down */
1570 FWD_DOWN_SAMPLES (data, data_end, d, d_end, memcpy);
1573 /* reverse speed up */
1574 REV_UP_SAMPLES (data, data_end, d, d_end, memcpy);
1576 /* reverse slow down */
1577 REV_DOWN_SAMPLES (data, data_end, d, d_end, memcpy);
1581 /* for the next iteration we write to the next segment at the beginning. */
1585 /* we consumed all samples here */
1586 data = data_end + bpf;
1589 return inr - ((data_end - data) / bpf);
1594 GST_DEBUG_OBJECT (buf, "stopped processing");
1600 * gst_audio_ring_buffer_commit:
1601 * @buf: the #GstAudioRingBuffer to commit
1602 * @sample: the sample position of the data
1603 * @data: the data to commit
1604 * @in_samples: the number of samples in the data to commit
1605 * @out_samples: the number of samples to write to the ringbuffer
1606 * @accum: accumulator for rate conversion.
1608 * Commit @in_samples samples pointed to by @data to the ringbuffer @buf.
1610 * @in_samples and @out_samples define the rate conversion to perform on the
1611 * samples in @data. For negative rates, @out_samples must be negative and
1612 * @in_samples positive.
1614 * When @out_samples is positive, the first sample will be written at position @sample
1615 * in the ringbuffer. When @out_samples is negative, the last sample will be written to
1616 * @sample in reverse order.
1618 * @out_samples does not need to be a multiple of the segment size of the ringbuffer
1619 * although it is recommended for optimal performance.
1621 * @accum will hold a temporary accumulator used in rate conversion and should be
1622 * set to 0 when this function is first called. In case the commit operation is
1623 * interrupted, one can resume the processing by passing the previously returned
1624 * @accum value back to this function.
1628 * Returns: The number of samples written to the ringbuffer or -1 on error. The
1629 * number of samples written can be less than @out_samples when @buf was interrupted
1630 * with a flush or stop.
1633 gst_audio_ring_buffer_commit (GstAudioRingBuffer * buf, guint64 * sample,
1634 guint8 * data, gint in_samples, gint out_samples, gint * accum)
1636 GstAudioRingBufferClass *rclass;
1639 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), -1);
1641 if (G_UNLIKELY (in_samples == 0 || out_samples == 0))
1644 rclass = GST_AUDIO_RING_BUFFER_GET_CLASS (buf);
1646 if (G_LIKELY (rclass->commit))
1647 res = rclass->commit (buf, sample, data, in_samples, out_samples, accum);
1653 * gst_audio_ring_buffer_read:
1654 * @buf: the #GstAudioRingBuffer to read from
1655 * @sample: the sample position of the data
1656 * @data: where the data should be read
1657 * @len: the number of samples in data to read
1658 * @timestamp: where the timestamp is returned
1660 * Read @len samples from the ringbuffer into the memory pointed
1662 * The first sample should be read from position @sample in
1665 * @len should not be a multiple of the segment size of the ringbuffer
1666 * although it is recommended.
1668 * @timestamp will return the timestamp associated with the data returned.
1670 * Returns: The number of samples read from the ringbuffer or -1 on
1676 gst_audio_ring_buffer_read (GstAudioRingBuffer * buf, guint64 sample,
1677 guint8 * data, guint len, GstClockTime * timestamp)
1680 gint segsize, segtotal, channels, bps, bpf, sps, readseg = 0;
1683 gboolean need_reorder;
1685 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), -1);
1686 g_return_val_if_fail (buf->memory != NULL, -1);
1687 g_return_val_if_fail (data != NULL, -1);
1689 need_reorder = buf->need_reorder;
1691 segsize = buf->spec.segsize;
1692 segtotal = buf->spec.segtotal;
1693 channels = buf->spec.info.channels;
1694 bpf = buf->spec.info.bpf;
1695 bps = bpf / channels;
1696 sps = buf->samples_per_seg;
1699 /* read enough samples */
1700 while (to_read > 0) {
1704 /* figure out the segment and the offset inside the segment where
1705 * the sample should be read from. */
1706 readseg = sample / sps;
1707 sampleoff = (sample % sps);
1712 /* get the currently processed segment */
1713 segdone = g_atomic_int_get (&buf->segdone) - buf->segbase;
1715 /* see how far away it is from the read segment, normally segdone (where
1716 * the hardware is writing) is bigger than readseg (where software is
1718 diff = segdone - readseg;
1721 ("pointer at %d, sample %" G_GUINT64_FORMAT
1722 ", read from %d-%d, to_read %d, diff %d, segtotal %d, segsize %d",
1723 segdone, sample, readseg, sampleoff, to_read, diff, segtotal,
1726 /* segment too far ahead, reader too slow */
1727 if (G_UNLIKELY (diff >= segtotal)) {
1728 /* pretend we read an empty segment. */
1729 sampleslen = MIN (sps, to_read);
1730 memcpy (data, buf->empty_seg, sampleslen * bpf);
1734 /* read segment is within readable range, we can break the loop and
1735 * start reading the data. */
1739 /* else we need to wait for the segment to become readable. */
1740 if (!wait_segment (buf))
1744 /* we can read now */
1745 readseg = readseg % segtotal;
1746 sampleslen = MIN (sps - sampleoff, to_read);
1748 GST_DEBUG_OBJECT (buf, "read @%p seg %d, off %d, sampleslen %d",
1749 dest + readseg * segsize, readseg, sampleoff, sampleslen);
1752 guint8 *ptr = dest + (readseg * segsize) + (sampleoff * bpf);
1754 gint *reorder_map = buf->channel_reorder_map;
1756 /* Reorder from device order to GStreamer order */
1757 for (i = 0; i < sampleslen; i++) {
1758 for (j = 0; j < channels; j++) {
1759 memcpy (data + reorder_map[j] * bps, ptr + j * bps, bps);
1764 memcpy (data, dest + (readseg * segsize) + (sampleoff * bpf),
1765 (sampleslen * bpf));
1769 to_read -= sampleslen;
1770 sample += sampleslen;
1771 data += sampleslen * bpf;
1774 if (buf->timestamps && timestamp) {
1775 *timestamp = buf->timestamps[readseg % segtotal];
1776 GST_INFO_OBJECT (buf, "Retrieved timestamp %" GST_TIME_FORMAT
1777 " @ %d", GST_TIME_ARGS (*timestamp), readseg % segtotal);
1780 return len - to_read;
1785 GST_DEBUG_OBJECT (buf, "stopped processing");
1786 return len - to_read;
1791 * gst_audio_ring_buffer_prepare_read:
1792 * @buf: the #GstAudioRingBuffer to read from
1793 * @segment: the segment to read
1794 * @readptr: the pointer to the memory where samples can be read
1795 * @len: the number of bytes to read
1797 * Returns a pointer to memory where the data from segment @segment
1798 * can be found. This function is mostly used by subclasses.
1800 * Returns: FALSE if the buffer is not started.
1805 gst_audio_ring_buffer_prepare_read (GstAudioRingBuffer * buf, gint * segment,
1806 guint8 ** readptr, gint * len)
1811 g_return_val_if_fail (GST_IS_AUDIO_RING_BUFFER (buf), FALSE);
1813 if (buf->callback == NULL) {
1814 /* push mode, fail when nothing is started */
1815 if (g_atomic_int_get (&buf->state) != GST_AUDIO_RING_BUFFER_STATE_STARTED)
1819 g_return_val_if_fail (buf->memory != NULL, FALSE);
1820 g_return_val_if_fail (segment != NULL, FALSE);
1821 g_return_val_if_fail (readptr != NULL, FALSE);
1822 g_return_val_if_fail (len != NULL, FALSE);
1826 /* get the position of the pointer */
1827 segdone = g_atomic_int_get (&buf->segdone);
1829 *segment = segdone % buf->spec.segtotal;
1830 *len = buf->spec.segsize;
1831 *readptr = data + *segment * *len;
1833 GST_LOG ("prepare read from segment %d (real %d) @%p",
1834 *segment, segdone, *readptr);
1836 /* callback to fill the memory with data, for pull based
1839 buf->callback (buf, *readptr, *len, buf->cb_data);
1845 * gst_audio_ring_buffer_advance:
1846 * @buf: the #GstAudioRingBuffer to advance
1847 * @advance: the number of segments written
1849 * Subclasses should call this function to notify the fact that
1850 * @advance segments are now processed by the device.
1855 gst_audio_ring_buffer_advance (GstAudioRingBuffer * buf, guint advance)
1857 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1859 /* update counter */
1860 g_atomic_int_add (&buf->segdone, advance);
1862 /* the lock is already taken when the waiting flag is set,
1863 * we grab the lock as well to make sure the waiter is actually
1864 * waiting for the signal */
1865 if (g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0)) {
1866 GST_OBJECT_LOCK (buf);
1867 GST_DEBUG_OBJECT (buf, "signal waiter");
1868 GST_AUDIO_RING_BUFFER_SIGNAL (buf);
1869 GST_OBJECT_UNLOCK (buf);
1874 * gst_audio_ring_buffer_clear:
1875 * @buf: the #GstAudioRingBuffer to clear
1876 * @segment: the segment to clear
1878 * Clear the given segment of the buffer with silence samples.
1879 * This function is used by subclasses.
1884 gst_audio_ring_buffer_clear (GstAudioRingBuffer * buf, gint segment)
1888 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1890 /* no data means it's already cleared */
1891 if (G_UNLIKELY (buf->memory == NULL))
1894 /* no empty_seg means it's not opened */
1895 if (G_UNLIKELY (buf->empty_seg == NULL))
1898 segment %= buf->spec.segtotal;
1901 data += segment * buf->spec.segsize;
1903 GST_LOG ("clear segment %d @%p", segment, data);
1905 memcpy (data, buf->empty_seg, buf->spec.segsize);
1909 * gst_audio_ring_buffer_may_start:
1910 * @buf: the #GstAudioRingBuffer
1911 * @allowed: the new value
1913 * Tell the ringbuffer that it is allowed to start playback when
1914 * the ringbuffer is filled with samples.
1919 gst_audio_ring_buffer_may_start (GstAudioRingBuffer * buf, gboolean allowed)
1921 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1923 GST_LOG_OBJECT (buf, "may start: %d", allowed);
1924 g_atomic_int_set (&buf->may_start, allowed);
1928 * gst_audio_ring_buffer_set_channel_positions:
1929 * @buf: the #GstAudioRingBuffer
1930 * @position: the device channel positions
1932 * Tell the ringbuffer about the device's channel positions. This must
1933 * be called in when the ringbuffer is acquired.
1936 gst_audio_ring_buffer_set_channel_positions (GstAudioRingBuffer * buf,
1937 const GstAudioChannelPosition * position)
1939 const GstAudioChannelPosition *to;
1943 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1944 g_return_if_fail (buf->acquired);
1946 channels = buf->spec.info.channels;
1947 to = buf->spec.info.position;
1949 buf->need_reorder = FALSE;
1950 if (memcmp (position, to, channels * sizeof (to[0])) == 0)
1953 if (!gst_audio_get_channel_reorder_map (channels, position, to,
1954 buf->channel_reorder_map))
1955 g_return_if_reached ();
1957 for (i = 0; i < channels; i++) {
1958 if (buf->channel_reorder_map[i] != i) {
1959 buf->need_reorder = TRUE;
1966 * gst_ring_buffer_set_timestamp:
1967 * @buf: the #GstRingBuffer
1968 * @readseg: the current data segment
1969 * @timestamp: The new timestamp of the buffer.
1971 * Set a new timestamp on the buffer.
1976 gst_audio_ring_buffer_set_timestamp (GstAudioRingBuffer * buf, gint readseg,
1977 GstClockTime timestamp)
1979 g_return_if_fail (GST_IS_AUDIO_RING_BUFFER (buf));
1981 GST_INFO_OBJECT (buf, "Storing timestamp %" GST_TIME_FORMAT
1982 " @ %d", GST_TIME_ARGS (timestamp), readseg);
1983 if (buf->timestamps) {
1984 buf->timestamps[readseg] = timestamp;
1986 GST_ERROR_OBJECT (buf, "Could not store timestamp, no timestamps buffer");