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., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
21 * SECTION:gstringbuffer
22 * @short_description: Base class for audio ringbuffer implementations
23 * @see_also: #GstBaseAudioSink, #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 "gstringbuffer.h"
46 GST_DEBUG_CATEGORY_STATIC (gst_ring_buffer_debug);
47 #define GST_CAT_DEFAULT gst_ring_buffer_debug
49 static void gst_ring_buffer_dispose (GObject * object);
50 static void gst_ring_buffer_finalize (GObject * object);
52 static gboolean gst_ring_buffer_pause_unlocked (GstRingBuffer * buf);
53 static void default_clear_all (GstRingBuffer * buf);
54 static guint default_commit (GstRingBuffer * buf, guint64 * sample,
55 guchar * data, gint in_samples, gint out_samples, gint * accum);
57 /* ringbuffer abstract base class */
58 G_DEFINE_ABSTRACT_TYPE (GstRingBuffer, gst_ring_buffer, GST_TYPE_OBJECT);
61 gst_ring_buffer_class_init (GstRingBufferClass * klass)
63 GObjectClass *gobject_class;
64 GstRingBufferClass *gstringbuffer_class;
66 gobject_class = (GObjectClass *) klass;
67 gstringbuffer_class = (GstRingBufferClass *) klass;
69 GST_DEBUG_CATEGORY_INIT (gst_ring_buffer_debug, "ringbuffer", 0,
72 gobject_class->dispose = gst_ring_buffer_dispose;
73 gobject_class->finalize = gst_ring_buffer_finalize;
75 gstringbuffer_class->clear_all = GST_DEBUG_FUNCPTR (default_clear_all);
76 gstringbuffer_class->commit = GST_DEBUG_FUNCPTR (default_commit);
80 gst_ring_buffer_init (GstRingBuffer * ringbuffer)
82 ringbuffer->open = FALSE;
83 ringbuffer->acquired = FALSE;
84 ringbuffer->state = GST_RING_BUFFER_STATE_STOPPED;
85 ringbuffer->cond = g_cond_new ();
86 ringbuffer->waiting = 0;
87 ringbuffer->empty_seg = NULL;
88 ringbuffer->abidata.ABI.flushing = TRUE;
92 gst_ring_buffer_dispose (GObject * object)
94 GstRingBuffer *ringbuffer = GST_RING_BUFFER (object);
96 gst_caps_replace (&ringbuffer->spec.caps, NULL);
98 G_OBJECT_CLASS (gst_ring_buffer_parent_class)->dispose (G_OBJECT
103 gst_ring_buffer_finalize (GObject * object)
105 GstRingBuffer *ringbuffer = GST_RING_BUFFER (object);
107 g_cond_free (ringbuffer->cond);
108 g_free (ringbuffer->empty_seg);
110 G_OBJECT_CLASS (gst_ring_buffer_parent_class)->finalize (G_OBJECT
116 const GstBufferFormat format;
117 const guint8 silence[4];
120 static const FormatDef linear_defs[4 * 2 * 2] = {
121 {GST_S8, {0x00, 0x00, 0x00, 0x00}},
122 {GST_S8, {0x00, 0x00, 0x00, 0x00}},
123 {GST_U8, {0x80, 0x80, 0x80, 0x80}},
124 {GST_U8, {0x80, 0x80, 0x80, 0x80}},
125 {GST_S16_LE, {0x00, 0x00, 0x00, 0x00}},
126 {GST_S16_BE, {0x00, 0x00, 0x00, 0x00}},
127 {GST_U16_LE, {0x00, 0x80, 0x00, 0x80}},
128 {GST_U16_BE, {0x80, 0x00, 0x80, 0x00}},
129 {GST_S24_LE, {0x00, 0x00, 0x00, 0x00}},
130 {GST_S24_BE, {0x00, 0x00, 0x00, 0x00}},
131 {GST_U24_LE, {0x00, 0x00, 0x80, 0x00}},
132 {GST_U24_BE, {0x80, 0x00, 0x00, 0x00}},
133 {GST_S32_LE, {0x00, 0x00, 0x00, 0x00}},
134 {GST_S32_BE, {0x00, 0x00, 0x00, 0x00}},
135 {GST_U32_LE, {0x00, 0x00, 0x00, 0x80}},
136 {GST_U32_BE, {0x80, 0x00, 0x00, 0x00}}
139 static const FormatDef linear24_defs[3 * 2 * 2] = {
140 {GST_S24_3LE, {0x00, 0x00, 0x00, 0x00}},
141 {GST_S24_3BE, {0x00, 0x00, 0x00, 0x00}},
142 {GST_U24_3LE, {0x00, 0x00, 0x80, 0x00}},
143 {GST_U24_3BE, {0x80, 0x00, 0x00, 0x00}},
144 {GST_S20_3LE, {0x00, 0x00, 0x00, 0x00}},
145 {GST_S20_3BE, {0x00, 0x00, 0x00, 0x00}},
146 {GST_U20_3LE, {0x00, 0x00, 0x08, 0x00}},
147 {GST_U20_3BE, {0x08, 0x00, 0x00, 0x00}},
148 {GST_S18_3LE, {0x00, 0x00, 0x00, 0x00}},
149 {GST_S18_3BE, {0x00, 0x00, 0x00, 0x00}},
150 {GST_U18_3LE, {0x00, 0x00, 0x02, 0x00}},
151 {GST_U18_3BE, {0x02, 0x00, 0x00, 0x00}}
154 static const FormatDef *
155 build_linear_format (int depth, int width, int unsignd, int big_endian)
157 const FormatDef *formats;
162 formats = &linear24_defs[0];
165 formats = &linear24_defs[4];
168 formats = &linear24_defs[8];
176 formats = &linear_defs[0];
179 formats = &linear_defs[4];
182 formats = &linear_defs[8];
185 formats = &linear_defs[12];
199 #ifndef GST_DISABLE_GST_DEBUG
200 static const gchar *format_type_names[] = {
214 static const gchar *format_names[] = {
259 * gst_ring_buffer_debug_spec_caps:
260 * @spec: the spec to debug
262 * Print debug info about the parsed caps in @spec to the debug log.
265 gst_ring_buffer_debug_spec_caps (GstRingBufferSpec * spec)
269 GST_DEBUG ("spec caps: %p %" GST_PTR_FORMAT, spec->caps, spec->caps);
270 GST_DEBUG ("parsed caps: type: %d, '%s'", spec->type,
271 format_type_names[spec->type]);
272 GST_DEBUG ("parsed caps: format: %d, '%s'", spec->format,
273 format_names[spec->format]);
274 GST_DEBUG ("parsed caps: width: %d", spec->width);
275 GST_DEBUG ("parsed caps: depth: %d", spec->depth);
276 GST_DEBUG ("parsed caps: sign: %d", spec->sign);
277 GST_DEBUG ("parsed caps: bigend: %d", spec->bigend);
278 GST_DEBUG ("parsed caps: rate: %d", spec->rate);
279 GST_DEBUG ("parsed caps: channels: %d", spec->channels);
280 GST_DEBUG ("parsed caps: sample bytes: %d", spec->bytes_per_sample);
281 bytes = (spec->width >> 3) * spec->channels;
282 for (i = 0; i < bytes; i++) {
283 GST_DEBUG ("silence byte %d: %02x", i, spec->silence_sample[i]);
288 * gst_ring_buffer_debug_spec_buff:
289 * @spec: the spec to debug
291 * Print debug info about the buffer sized in @spec to the debug log.
294 gst_ring_buffer_debug_spec_buff (GstRingBufferSpec * spec)
296 GST_DEBUG ("acquire ringbuffer: buffer time: %" G_GINT64_FORMAT " usec",
298 GST_DEBUG ("acquire ringbuffer: latency time: %" G_GINT64_FORMAT " usec",
300 GST_DEBUG ("acquire ringbuffer: total segments: %d", spec->segtotal);
301 GST_DEBUG ("acquire ringbuffer: latency segments: %d", spec->seglatency);
302 GST_DEBUG ("acquire ringbuffer: segment size: %d bytes = %d samples",
303 spec->segsize, spec->segsize / spec->bytes_per_sample);
304 GST_DEBUG ("acquire ringbuffer: buffer size: %d bytes = %d samples",
305 spec->segsize * spec->segtotal,
306 spec->segsize * spec->segtotal / spec->bytes_per_sample);
310 * gst_ring_buffer_parse_caps:
314 * Parse @caps into @spec.
316 * Returns: TRUE if the caps could be parsed.
319 gst_ring_buffer_parse_caps (GstRingBufferSpec * spec, GstCaps * caps)
321 const gchar *mimetype;
322 GstStructure *structure;
325 structure = gst_caps_get_structure (caps, 0);
327 /* we have to differentiate between int and float formats */
328 mimetype = gst_structure_get_name (structure);
330 if (!strncmp (mimetype, "audio/x-raw-int", 15)) {
332 const FormatDef *def;
335 spec->type = GST_BUFTYPE_LINEAR;
337 /* extract the needed information from the cap */
338 if (!(gst_structure_get_int (structure, "rate", &spec->rate) &&
339 gst_structure_get_int (structure, "channels", &spec->channels) &&
340 gst_structure_get_int (structure, "width", &spec->width) &&
341 gst_structure_get_int (structure, "depth", &spec->depth) &&
342 gst_structure_get_boolean (structure, "signed", &spec->sign)))
345 /* extract endianness if needed */
346 if (spec->width > 8) {
347 if (!gst_structure_get_int (structure, "endianness", &endianness))
350 endianness = G_BYTE_ORDER;
353 spec->bigend = endianness == G_LITTLE_ENDIAN ? FALSE : TRUE;
355 def = build_linear_format (spec->depth, spec->width, spec->sign ? 0 : 1,
356 spec->bigend ? 1 : 0);
361 spec->format = def->format;
363 bytes = spec->width >> 3;
365 for (i = 0; i < spec->channels; i++) {
366 for (j = 0; j < bytes; j++) {
367 spec->silence_sample[i * bytes + j] = def->silence[j];
370 } else if (!strncmp (mimetype, "audio/x-raw-float", 17)) {
372 spec->type = GST_BUFTYPE_FLOAT;
374 /* extract the needed information from the cap */
375 if (!(gst_structure_get_int (structure, "rate", &spec->rate) &&
376 gst_structure_get_int (structure, "channels", &spec->channels) &&
377 gst_structure_get_int (structure, "width", &spec->width)))
380 /* match layout to format wrt to endianness */
381 switch (spec->width) {
384 G_BYTE_ORDER == G_LITTLE_ENDIAN ? GST_FLOAT32_LE : GST_FLOAT32_BE;
388 G_BYTE_ORDER == G_LITTLE_ENDIAN ? GST_FLOAT64_LE : GST_FLOAT64_BE;
393 /* float silence is all zeros.. */
394 memset (spec->silence_sample, 0, 32);
395 } else if (!strncmp (mimetype, "audio/x-alaw", 12)) {
396 /* extract the needed information from the cap */
397 if (!(gst_structure_get_int (structure, "rate", &spec->rate) &&
398 gst_structure_get_int (structure, "channels", &spec->channels)))
401 spec->type = GST_BUFTYPE_A_LAW;
402 spec->format = GST_A_LAW;
405 for (i = 0; i < spec->channels; i++)
406 spec->silence_sample[i] = 0xd5;
407 } else if (!strncmp (mimetype, "audio/x-mulaw", 13)) {
408 /* extract the needed information from the cap */
409 if (!(gst_structure_get_int (structure, "rate", &spec->rate) &&
410 gst_structure_get_int (structure, "channels", &spec->channels)))
413 spec->type = GST_BUFTYPE_MU_LAW;
414 spec->format = GST_MU_LAW;
417 for (i = 0; i < spec->channels; i++)
418 spec->silence_sample[i] = 0xff;
419 } else if (!strncmp (mimetype, "audio/x-iec958", 14)) {
420 /* extract the needed information from the cap */
421 if (!(gst_structure_get_int (structure, "rate", &spec->rate)))
424 spec->type = GST_BUFTYPE_IEC958;
425 spec->format = GST_IEC958;
429 } else if (!strncmp (mimetype, "audio/x-ac3", 11)) {
430 /* extract the needed information from the cap */
431 if (!(gst_structure_get_int (structure, "rate", &spec->rate)))
434 spec->type = GST_BUFTYPE_AC3;
435 spec->format = GST_AC3;
443 spec->bytes_per_sample = (spec->width >> 3) * spec->channels;
445 gst_caps_replace (&spec->caps, caps);
447 g_return_val_if_fail (spec->latency_time != 0, FALSE);
449 /* calculate suggested segsize and segtotal. segsize should be one unit
450 * of 'latency_time' samples, scaling for the fact that latency_time is
451 * currently stored in microseconds (FIXME: in 0.11) */
452 spec->segsize = gst_util_uint64_scale (spec->rate * spec->bytes_per_sample,
453 spec->latency_time, GST_SECOND / GST_USECOND);
454 /* Round to an integer number of samples */
455 spec->segsize -= spec->segsize % spec->bytes_per_sample;
457 spec->segtotal = spec->buffer_time / spec->latency_time;
458 /* leave the latency undefined now, implementations can change it but if it's
459 * not changed, we assume the same value as segtotal */
460 spec->seglatency = -1;
462 gst_ring_buffer_debug_spec_caps (spec);
463 gst_ring_buffer_debug_spec_buff (spec);
470 GST_DEBUG ("could not parse caps");
476 * gst_ring_buffer_convert:
477 * @buf: the #GstRingBuffer
478 * @src_fmt: the source format
479 * @src_val: the source value
480 * @dest_fmt: the destination format
481 * @dest_val: a location to store the converted value
483 * Convert @src_val in @src_fmt to the equivalent value in @dest_fmt. The result
484 * will be put in @dest_val.
486 * Returns: TRUE if the conversion succeeded.
491 gst_ring_buffer_convert (GstRingBuffer * buf,
492 GstFormat src_fmt, gint64 src_val, GstFormat dest_fmt, gint64 * dest_val)
497 GST_DEBUG ("converting value %" G_GINT64_FORMAT " from %s (%d) to %s (%d)",
498 src_val, gst_format_get_name (src_fmt), src_fmt,
499 gst_format_get_name (dest_fmt), dest_fmt);
501 if (src_fmt == dest_fmt || src_val == -1) {
506 /* get important info */
507 GST_OBJECT_LOCK (buf);
508 bps = buf->spec.bytes_per_sample;
509 rate = buf->spec.rate;
510 GST_OBJECT_UNLOCK (buf);
512 if (bps == 0 || rate == 0) {
513 GST_DEBUG ("no rate or bps configured");
519 case GST_FORMAT_BYTES:
521 case GST_FORMAT_TIME:
522 *dest_val = gst_util_uint64_scale_int (src_val / bps, GST_SECOND,
525 case GST_FORMAT_DEFAULT:
526 *dest_val = src_val / bps;
533 case GST_FORMAT_DEFAULT:
535 case GST_FORMAT_TIME:
536 *dest_val = gst_util_uint64_scale_int (src_val, GST_SECOND, rate);
538 case GST_FORMAT_BYTES:
539 *dest_val = src_val * bps;
546 case GST_FORMAT_TIME:
548 case GST_FORMAT_DEFAULT:
549 *dest_val = gst_util_uint64_scale_int (src_val, rate, GST_SECOND);
551 case GST_FORMAT_BYTES:
552 *dest_val = gst_util_uint64_scale_int (src_val, rate, GST_SECOND);
565 GST_DEBUG ("ret=%d result %" G_GINT64_FORMAT, res, *dest_val);
571 * gst_ring_buffer_set_callback:
572 * @buf: the #GstRingBuffer to set the callback on
573 * @cb: the callback to set
574 * @user_data: user data passed to the callback
576 * Sets the given callback function on the buffer. This function
577 * will be called every time a segment has been written to a device.
582 gst_ring_buffer_set_callback (GstRingBuffer * buf, GstRingBufferCallback cb,
585 g_return_if_fail (GST_IS_RING_BUFFER (buf));
587 GST_OBJECT_LOCK (buf);
589 buf->cb_data = user_data;
590 GST_OBJECT_UNLOCK (buf);
595 * gst_ring_buffer_open_device:
596 * @buf: the #GstRingBuffer
598 * Open the audio device associated with the ring buffer. Does not perform any
599 * setup on the device. You must open the device before acquiring the ring
602 * Returns: TRUE if the device could be opened, FALSE on error.
607 gst_ring_buffer_open_device (GstRingBuffer * buf)
610 GstRingBufferClass *rclass;
612 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
614 GST_DEBUG_OBJECT (buf, "opening device");
616 GST_OBJECT_LOCK (buf);
617 if (G_UNLIKELY (buf->open))
622 /* if this fails, something is wrong in this file */
623 g_assert (!buf->acquired);
625 rclass = GST_RING_BUFFER_GET_CLASS (buf);
626 if (G_LIKELY (rclass->open_device))
627 res = rclass->open_device (buf);
629 if (G_UNLIKELY (!res))
632 GST_DEBUG_OBJECT (buf, "opened device");
635 GST_OBJECT_UNLOCK (buf);
642 GST_DEBUG_OBJECT (buf, "Device for ring buffer already open");
643 g_warning ("Device for ring buffer %p already open, fix your code", buf);
650 GST_DEBUG_OBJECT (buf, "failed opening device");
656 * gst_ring_buffer_close_device:
657 * @buf: the #GstRingBuffer
659 * Close the audio device associated with the ring buffer. The ring buffer
660 * should already have been released via gst_ring_buffer_release().
662 * Returns: TRUE if the device could be closed, FALSE on error.
667 gst_ring_buffer_close_device (GstRingBuffer * buf)
670 GstRingBufferClass *rclass;
672 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
674 GST_DEBUG_OBJECT (buf, "closing device");
676 GST_OBJECT_LOCK (buf);
677 if (G_UNLIKELY (!buf->open))
680 if (G_UNLIKELY (buf->acquired))
685 rclass = GST_RING_BUFFER_GET_CLASS (buf);
686 if (G_LIKELY (rclass->close_device))
687 res = rclass->close_device (buf);
689 if (G_UNLIKELY (!res))
692 GST_DEBUG_OBJECT (buf, "closed device");
695 GST_OBJECT_UNLOCK (buf);
702 GST_DEBUG_OBJECT (buf, "Device for ring buffer already closed");
703 g_warning ("Device for ring buffer %p already closed, fix your code", buf);
709 GST_DEBUG_OBJECT (buf, "Resources for ring buffer still acquired");
710 g_critical ("Resources for ring buffer %p still acquired", buf);
717 GST_DEBUG_OBJECT (buf, "error closing device");
723 * gst_ring_buffer_device_is_open:
724 * @buf: the #GstRingBuffer
726 * Checks the status of the device associated with the ring buffer.
728 * Returns: TRUE if the device was open, FALSE if it was closed.
733 gst_ring_buffer_device_is_open (GstRingBuffer * buf)
737 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
739 GST_OBJECT_LOCK (buf);
741 GST_OBJECT_UNLOCK (buf);
747 * gst_ring_buffer_acquire:
748 * @buf: the #GstRingBuffer to acquire
749 * @spec: the specs of the buffer
751 * Allocate the resources for the ringbuffer. This function fills
752 * in the data pointer of the ring buffer with a valid #GstBuffer
753 * to which samples can be written.
755 * Returns: TRUE if the device could be acquired, FALSE on error.
760 gst_ring_buffer_acquire (GstRingBuffer * buf, GstRingBufferSpec * spec)
762 gboolean res = FALSE;
763 GstRingBufferClass *rclass;
767 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
769 GST_DEBUG_OBJECT (buf, "acquiring device %p", buf);
771 GST_OBJECT_LOCK (buf);
772 if (G_UNLIKELY (!buf->open))
775 if (G_UNLIKELY (buf->acquired))
778 buf->acquired = TRUE;
780 rclass = GST_RING_BUFFER_GET_CLASS (buf);
781 if (G_LIKELY (rclass->acquire))
782 res = rclass->acquire (buf, spec);
784 if (G_UNLIKELY (!res))
787 if (G_UNLIKELY ((bps = buf->spec.bytes_per_sample) == 0))
790 /* if the seglatency was overwritten with something else than -1, use it, else
791 * assume segtotal as the latency */
792 if (buf->spec.seglatency == -1)
793 buf->spec.seglatency = buf->spec.segtotal;
795 segsize = buf->spec.segsize;
797 buf->samples_per_seg = segsize / bps;
799 /* create an empty segment */
800 g_free (buf->empty_seg);
801 buf->empty_seg = g_malloc (segsize);
803 /* FIXME, we only have 32 silence samples, which might not be enough to
804 * represent silence in all channels */
806 for (i = 0, j = 0; i < segsize; i++) {
807 buf->empty_seg[i] = buf->spec.silence_sample[j];
810 GST_DEBUG_OBJECT (buf, "acquired device");
813 GST_OBJECT_UNLOCK (buf);
820 GST_DEBUG_OBJECT (buf, "device not opened");
821 g_critical ("Device for %p not opened", buf);
828 GST_DEBUG_OBJECT (buf, "device was acquired");
833 buf->acquired = FALSE;
834 GST_DEBUG_OBJECT (buf, "failed to acquire device");
840 ("invalid bytes_per_sample from acquire ringbuffer %p, fix the element",
842 buf->acquired = FALSE;
849 * gst_ring_buffer_release:
850 * @buf: the #GstRingBuffer to release
852 * Free the resources of the ringbuffer.
854 * Returns: TRUE if the device could be released, FALSE on error.
859 gst_ring_buffer_release (GstRingBuffer * buf)
861 gboolean res = FALSE;
862 GstRingBufferClass *rclass;
864 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
866 GST_DEBUG_OBJECT (buf, "releasing device");
868 gst_ring_buffer_stop (buf);
870 GST_OBJECT_LOCK (buf);
871 if (G_UNLIKELY (!buf->acquired))
874 buf->acquired = FALSE;
876 /* if this fails, something is wrong in this file */
877 g_assert (buf->open == TRUE);
879 rclass = GST_RING_BUFFER_GET_CLASS (buf);
880 if (G_LIKELY (rclass->release))
881 res = rclass->release (buf);
883 /* signal any waiters */
884 GST_DEBUG_OBJECT (buf, "signal waiter");
885 GST_RING_BUFFER_SIGNAL (buf);
887 if (G_UNLIKELY (!res))
890 g_free (buf->empty_seg);
891 buf->empty_seg = NULL;
892 GST_DEBUG_OBJECT (buf, "released device");
895 GST_OBJECT_UNLOCK (buf);
903 GST_DEBUG_OBJECT (buf, "device was released");
908 buf->acquired = TRUE;
909 GST_DEBUG_OBJECT (buf, "failed to release device");
915 * gst_ring_buffer_is_acquired:
916 * @buf: the #GstRingBuffer to check
918 * Check if the ringbuffer is acquired and ready to use.
920 * Returns: TRUE if the ringbuffer is acquired, FALSE on error.
925 gst_ring_buffer_is_acquired (GstRingBuffer * buf)
929 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
931 GST_OBJECT_LOCK (buf);
933 GST_OBJECT_UNLOCK (buf);
939 * gst_ring_buffer_activate:
940 * @buf: the #GstRingBuffer to activate
941 * @active: the new mode
943 * Activate @buf to start or stop pulling data.
947 * Returns: TRUE if the device could be activated in the requested mode,
953 gst_ring_buffer_activate (GstRingBuffer * buf, gboolean active)
955 gboolean res = FALSE;
956 GstRingBufferClass *rclass;
958 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
960 GST_DEBUG_OBJECT (buf, "activate device");
962 GST_OBJECT_LOCK (buf);
963 if (G_UNLIKELY (active && !buf->acquired))
966 if (G_UNLIKELY (buf->abidata.ABI.active == active))
969 rclass = GST_RING_BUFFER_GET_CLASS (buf);
970 /* if there is no activate function we assume it was started/released
971 * in the acquire method */
972 if (G_LIKELY (rclass->activate))
973 res = rclass->activate (buf, active);
977 if (G_UNLIKELY (!res))
978 goto activate_failed;
980 buf->abidata.ABI.active = active;
983 GST_OBJECT_UNLOCK (buf);
990 GST_DEBUG_OBJECT (buf, "device not acquired");
991 g_critical ("Device for %p not acquired", buf);
998 GST_DEBUG_OBJECT (buf, "device was active in mode %d", active);
1003 GST_DEBUG_OBJECT (buf, "failed to activate device");
1009 * gst_ring_buffer_is_active:
1010 * @buf: the #GstRingBuffer
1012 * Check if @buf is activated.
1016 * Returns: TRUE if the device is active.
1021 gst_ring_buffer_is_active (GstRingBuffer * buf)
1025 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
1027 GST_OBJECT_LOCK (buf);
1028 res = buf->abidata.ABI.active;
1029 GST_OBJECT_UNLOCK (buf);
1036 * gst_ring_buffer_set_flushing:
1037 * @buf: the #GstRingBuffer to flush
1038 * @flushing: the new mode
1040 * Set the ringbuffer to flushing mode or normal mode.
1045 gst_ring_buffer_set_flushing (GstRingBuffer * buf, gboolean flushing)
1047 g_return_if_fail (GST_IS_RING_BUFFER (buf));
1049 GST_OBJECT_LOCK (buf);
1050 buf->abidata.ABI.flushing = flushing;
1053 gst_ring_buffer_pause_unlocked (buf);
1055 gst_ring_buffer_clear_all (buf);
1057 GST_OBJECT_UNLOCK (buf);
1061 * gst_ring_buffer_start:
1062 * @buf: the #GstRingBuffer to start
1064 * Start processing samples from the ringbuffer.
1066 * Returns: TRUE if the device could be started, FALSE on error.
1071 gst_ring_buffer_start (GstRingBuffer * buf)
1073 gboolean res = FALSE;
1074 GstRingBufferClass *rclass;
1075 gboolean resume = FALSE;
1077 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
1079 GST_DEBUG_OBJECT (buf, "starting ringbuffer");
1081 GST_OBJECT_LOCK (buf);
1082 if (G_UNLIKELY (buf->abidata.ABI.flushing))
1085 if (G_UNLIKELY (!buf->acquired))
1088 if (G_UNLIKELY (g_atomic_int_get (&buf->abidata.ABI.may_start) == FALSE))
1091 /* if stopped, set to started */
1092 res = g_atomic_int_compare_and_exchange (&buf->state,
1093 GST_RING_BUFFER_STATE_STOPPED, GST_RING_BUFFER_STATE_STARTED);
1096 GST_DEBUG_OBJECT (buf, "was not stopped, try paused");
1097 /* was not stopped, try from paused */
1098 res = g_atomic_int_compare_and_exchange (&buf->state,
1099 GST_RING_BUFFER_STATE_PAUSED, GST_RING_BUFFER_STATE_STARTED);
1101 /* was not paused either, must be started then */
1103 GST_DEBUG_OBJECT (buf, "was not paused, must have been started");
1107 GST_DEBUG_OBJECT (buf, "resuming");
1110 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1112 if (G_LIKELY (rclass->resume))
1113 res = rclass->resume (buf);
1115 if (G_LIKELY (rclass->start))
1116 res = rclass->start (buf);
1119 if (G_UNLIKELY (!res)) {
1120 buf->state = GST_RING_BUFFER_STATE_PAUSED;
1121 GST_DEBUG_OBJECT (buf, "failed to start");
1123 GST_DEBUG_OBJECT (buf, "started");
1127 GST_OBJECT_UNLOCK (buf);
1133 GST_DEBUG_OBJECT (buf, "we are flushing");
1134 GST_OBJECT_UNLOCK (buf);
1139 GST_DEBUG_OBJECT (buf, "we are not acquired");
1140 GST_OBJECT_UNLOCK (buf);
1145 GST_DEBUG_OBJECT (buf, "we may not start");
1146 GST_OBJECT_UNLOCK (buf);
1152 gst_ring_buffer_pause_unlocked (GstRingBuffer * buf)
1154 gboolean res = FALSE;
1155 GstRingBufferClass *rclass;
1157 GST_DEBUG_OBJECT (buf, "pausing ringbuffer");
1159 /* if started, set to paused */
1160 res = g_atomic_int_compare_and_exchange (&buf->state,
1161 GST_RING_BUFFER_STATE_STARTED, GST_RING_BUFFER_STATE_PAUSED);
1166 /* signal any waiters */
1167 GST_DEBUG_OBJECT (buf, "signal waiter");
1168 GST_RING_BUFFER_SIGNAL (buf);
1170 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1171 if (G_LIKELY (rclass->pause))
1172 res = rclass->pause (buf);
1174 if (G_UNLIKELY (!res)) {
1175 buf->state = GST_RING_BUFFER_STATE_STARTED;
1176 GST_DEBUG_OBJECT (buf, "failed to pause");
1178 GST_DEBUG_OBJECT (buf, "paused");
1185 /* was not started */
1186 GST_DEBUG_OBJECT (buf, "was not started");
1192 * gst_ring_buffer_pause:
1193 * @buf: the #GstRingBuffer to pause
1195 * Pause processing samples from the ringbuffer.
1197 * Returns: TRUE if the device could be paused, FALSE on error.
1202 gst_ring_buffer_pause (GstRingBuffer * buf)
1204 gboolean res = FALSE;
1206 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
1208 GST_OBJECT_LOCK (buf);
1209 if (G_UNLIKELY (buf->abidata.ABI.flushing))
1212 if (G_UNLIKELY (!buf->acquired))
1215 res = gst_ring_buffer_pause_unlocked (buf);
1216 GST_OBJECT_UNLOCK (buf);
1223 GST_DEBUG_OBJECT (buf, "we are flushing");
1224 GST_OBJECT_UNLOCK (buf);
1229 GST_DEBUG_OBJECT (buf, "not acquired");
1230 GST_OBJECT_UNLOCK (buf);
1236 * gst_ring_buffer_stop:
1237 * @buf: the #GstRingBuffer to stop
1239 * Stop processing samples from the ringbuffer.
1241 * Returns: TRUE if the device could be stopped, FALSE on error.
1246 gst_ring_buffer_stop (GstRingBuffer * buf)
1248 gboolean res = FALSE;
1249 GstRingBufferClass *rclass;
1251 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
1253 GST_DEBUG_OBJECT (buf, "stopping");
1255 GST_OBJECT_LOCK (buf);
1257 /* if started, set to stopped */
1258 res = g_atomic_int_compare_and_exchange (&buf->state,
1259 GST_RING_BUFFER_STATE_STARTED, GST_RING_BUFFER_STATE_STOPPED);
1262 GST_DEBUG_OBJECT (buf, "was not started, try paused");
1263 /* was not started, try from paused */
1264 res = g_atomic_int_compare_and_exchange (&buf->state,
1265 GST_RING_BUFFER_STATE_PAUSED, GST_RING_BUFFER_STATE_STOPPED);
1267 /* was not paused either, must have been stopped then */
1269 GST_DEBUG_OBJECT (buf, "was not paused, must have been stopped");
1274 /* signal any waiters */
1275 GST_DEBUG_OBJECT (buf, "signal waiter");
1276 GST_RING_BUFFER_SIGNAL (buf);
1278 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1279 if (G_LIKELY (rclass->stop))
1280 res = rclass->stop (buf);
1282 if (G_UNLIKELY (!res)) {
1283 buf->state = GST_RING_BUFFER_STATE_STARTED;
1284 GST_DEBUG_OBJECT (buf, "failed to stop");
1286 GST_DEBUG_OBJECT (buf, "stopped");
1289 GST_OBJECT_UNLOCK (buf);
1295 * gst_ring_buffer_delay:
1296 * @buf: the #GstRingBuffer to query
1298 * Get the number of samples queued in the audio device. This is
1299 * usually less than the segment size but can be bigger when the
1300 * implementation uses another internal buffer between the audio
1303 * For playback ringbuffers this is the amount of samples transfered from the
1304 * ringbuffer to the device but still not played.
1306 * For capture ringbuffers this is the amount of samples in the device that are
1307 * not yet transfered to the ringbuffer.
1309 * Returns: The number of samples queued in the audio device.
1314 gst_ring_buffer_delay (GstRingBuffer * buf)
1316 GstRingBufferClass *rclass;
1319 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), 0);
1321 /* buffer must be acquired */
1322 if (G_UNLIKELY (!gst_ring_buffer_is_acquired (buf)))
1325 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1326 if (G_LIKELY (rclass->delay))
1327 res = rclass->delay (buf);
1335 GST_DEBUG_OBJECT (buf, "not acquired");
1341 * gst_ring_buffer_samples_done:
1342 * @buf: the #GstRingBuffer to query
1344 * Get the number of samples that were processed by the ringbuffer
1345 * since it was last started. This does not include the number of samples not
1346 * yet processed (see gst_ring_buffer_delay()).
1348 * Returns: The number of samples processed by the ringbuffer.
1353 gst_ring_buffer_samples_done (GstRingBuffer * buf)
1358 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), 0);
1360 /* get the amount of segments we processed */
1361 segdone = g_atomic_int_get (&buf->segdone);
1363 /* convert to samples */
1364 samples = ((guint64) segdone) * buf->samples_per_seg;
1370 * gst_ring_buffer_set_sample:
1371 * @buf: the #GstRingBuffer to use
1372 * @sample: the sample number to set
1374 * Make sure that the next sample written to the device is
1375 * accounted for as being the @sample sample written to the
1376 * device. This value will be used in reporting the current
1377 * sample position of the ringbuffer.
1379 * This function will also clear the buffer with silence.
1384 gst_ring_buffer_set_sample (GstRingBuffer * buf, guint64 sample)
1386 g_return_if_fail (GST_IS_RING_BUFFER (buf));
1391 if (G_UNLIKELY (buf->samples_per_seg == 0))
1394 /* FIXME, we assume the ringbuffer can restart at a random
1395 * position, round down to the beginning and keep track of
1396 * offset when calculating the processed samples. */
1397 buf->segbase = buf->segdone - sample / buf->samples_per_seg;
1399 gst_ring_buffer_clear_all (buf);
1401 GST_DEBUG_OBJECT (buf, "set sample to %" G_GUINT64_FORMAT ", segbase %d",
1402 sample, buf->segbase);
1406 default_clear_all (GstRingBuffer * buf)
1410 /* not fatal, we just are not negotiated yet */
1411 if (G_UNLIKELY (buf->spec.segtotal <= 0))
1414 GST_DEBUG_OBJECT (buf, "clear all segments");
1416 for (i = 0; i < buf->spec.segtotal; i++) {
1417 gst_ring_buffer_clear (buf, i);
1422 * gst_ring_buffer_clear_all:
1423 * @buf: the #GstRingBuffer to clear
1425 * Fill the ringbuffer with silence.
1430 gst_ring_buffer_clear_all (GstRingBuffer * buf)
1432 GstRingBufferClass *rclass;
1434 g_return_if_fail (GST_IS_RING_BUFFER (buf));
1436 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1438 if (G_LIKELY (rclass->clear_all))
1439 rclass->clear_all (buf);
1444 wait_segment (GstRingBuffer * buf)
1447 gboolean wait = TRUE;
1449 /* buffer must be started now or we deadlock since nobody is reading */
1450 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1451 GST_RING_BUFFER_STATE_STARTED)) {
1452 /* see if we are allowed to start it */
1453 if (G_UNLIKELY (g_atomic_int_get (&buf->abidata.ABI.may_start) == FALSE))
1456 GST_DEBUG_OBJECT (buf, "start!");
1457 segments = g_atomic_int_get (&buf->segdone);
1458 gst_ring_buffer_start (buf);
1460 /* After starting, the writer may have wrote segments already and then we
1461 * don't need to wait anymore */
1462 if (G_LIKELY (g_atomic_int_get (&buf->segdone) != segments))
1466 /* take lock first, then update our waiting flag */
1467 GST_OBJECT_LOCK (buf);
1468 if (G_UNLIKELY (buf->abidata.ABI.flushing))
1471 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1472 GST_RING_BUFFER_STATE_STARTED))
1475 if (G_LIKELY (wait)) {
1476 if (g_atomic_int_compare_and_exchange (&buf->waiting, 0, 1)) {
1477 GST_DEBUG_OBJECT (buf, "waiting..");
1478 GST_RING_BUFFER_WAIT (buf);
1480 if (G_UNLIKELY (buf->abidata.ABI.flushing))
1483 if (G_UNLIKELY (g_atomic_int_get (&buf->state) !=
1484 GST_RING_BUFFER_STATE_STARTED))
1488 GST_OBJECT_UNLOCK (buf);
1495 g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0);
1496 GST_DEBUG_OBJECT (buf, "stopped processing");
1497 GST_OBJECT_UNLOCK (buf);
1502 g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0);
1503 GST_DEBUG_OBJECT (buf, "flushing");
1504 GST_OBJECT_UNLOCK (buf);
1509 GST_DEBUG_OBJECT (buf, "not allowed to start");
1514 #define FWD_SAMPLES(s,se,d,de) \
1516 /* no rate conversion */ \
1517 guint towrite = MIN (se + bps - s, de - d); \
1520 memcpy (d, s, towrite); \
1521 in_samples -= towrite / bps; \
1522 out_samples -= towrite / bps; \
1524 GST_DEBUG ("copy %u bytes", towrite); \
1527 /* in_samples >= out_samples, rate > 1.0 */
1528 #define FWD_UP_SAMPLES(s,se,d,de) \
1530 guint8 *sb = s, *db = d; \
1531 while (s <= se && d < de) { \
1533 memcpy (d, s, bps); \
1536 if ((*accum << 1) >= inr) { \
1541 in_samples -= (s - sb)/bps; \
1542 out_samples -= (d - db)/bps; \
1543 GST_DEBUG ("fwd_up end %d/%d",*accum,*toprocess); \
1546 /* out_samples > in_samples, for rates smaller than 1.0 */
1547 #define FWD_DOWN_SAMPLES(s,se,d,de) \
1549 guint8 *sb = s, *db = d; \
1550 while (s <= se && d < de) { \
1552 memcpy (d, s, bps); \
1555 if ((*accum << 1) >= outr) { \
1560 in_samples -= (s - sb)/bps; \
1561 out_samples -= (d - db)/bps; \
1562 GST_DEBUG ("fwd_down end %d/%d",*accum,*toprocess); \
1565 #define REV_UP_SAMPLES(s,se,d,de) \
1567 guint8 *sb = se, *db = d; \
1568 while (s <= se && d < de) { \
1570 memcpy (d, se, bps); \
1573 while (d < de && (*accum << 1) >= inr) { \
1578 in_samples -= (sb - se)/bps; \
1579 out_samples -= (d - db)/bps; \
1580 GST_DEBUG ("rev_up end %d/%d",*accum,*toprocess); \
1583 #define REV_DOWN_SAMPLES(s,se,d,de) \
1585 guint8 *sb = se, *db = d; \
1586 while (s <= se && d < de) { \
1588 memcpy (d, se, bps); \
1591 while (s <= se && (*accum << 1) >= outr) { \
1596 in_samples -= (sb - se)/bps; \
1597 out_samples -= (d - db)/bps; \
1598 GST_DEBUG ("rev_down end %d/%d",*accum,*toprocess); \
1602 default_commit (GstRingBuffer * buf, guint64 * sample,
1603 guchar * data, gint in_samples, gint out_samples, gint * accum)
1606 gint segsize, segtotal, bps, sps;
1607 guint8 *dest, *data_end;
1608 gint writeseg, sampleoff;
1613 g_return_val_if_fail (buf->data != NULL, -1);
1614 g_return_val_if_fail (data != NULL, -1);
1616 dest = GST_BUFFER_DATA (buf->data);
1617 segsize = buf->spec.segsize;
1618 segtotal = buf->spec.segtotal;
1619 bps = buf->spec.bytes_per_sample;
1620 sps = buf->samples_per_seg;
1622 reverse = out_samples < 0;
1623 out_samples = ABS (out_samples);
1625 if (in_samples >= out_samples)
1626 toprocess = &in_samples;
1628 toprocess = &out_samples;
1630 inr = in_samples - 1;
1631 outr = out_samples - 1;
1633 /* data_end points to the last sample we have to write, not past it. This is
1634 * needed to properly handle reverse playback: it points to the last sample. */
1635 data_end = data + (bps * inr);
1637 /* figure out the segment and the offset inside the segment where
1638 * the first sample should be written. */
1639 writeseg = *sample / sps;
1640 sampleoff = (*sample % sps) * bps;
1642 /* write out all samples */
1643 while (*toprocess > 0) {
1652 /* get the currently processed segment */
1653 segdone = g_atomic_int_get (&buf->segdone) - buf->segbase;
1655 /* see how far away it is from the write segment */
1656 diff = writeseg - segdone;
1659 ("pointer at %d, write to %d-%d, diff %d, segtotal %d, segsize %d, base %d",
1660 segdone, writeseg, sampleoff, diff, segtotal, segsize, buf->segbase);
1662 /* segment too far ahead, writer too slow, we need to drop, hopefully UNLIKELY */
1663 if (G_UNLIKELY (diff < 0)) {
1664 /* we need to drop one segment at a time, pretend we wrote a
1670 /* write segment is within writable range, we can break the loop and
1671 * start writing the data. */
1672 if (diff < segtotal) {
1677 /* else we need to wait for the segment to become writable. */
1678 if (!wait_segment (buf))
1682 /* we can write now */
1683 ws = writeseg % segtotal;
1684 avail = MIN (segsize - sampleoff, bps * out_samples);
1686 d = dest + (ws * segsize) + sampleoff;
1688 *sample += avail / bps;
1690 GST_DEBUG_OBJECT (buf, "write @%p seg %d, sps %d, off %d, avail %d",
1691 dest + ws * segsize, ws, sps, sampleoff, avail);
1693 if (G_LIKELY (inr == outr && !reverse)) {
1694 /* no rate conversion, simply copy samples */
1695 FWD_SAMPLES (data, data_end, d, d_end);
1696 } else if (!reverse) {
1698 /* forward speed up */
1699 FWD_UP_SAMPLES (data, data_end, d, d_end);
1701 /* forward slow down */
1702 FWD_DOWN_SAMPLES (data, data_end, d, d_end);
1705 /* reverse speed up */
1706 REV_UP_SAMPLES (data, data_end, d, d_end);
1708 /* reverse slow down */
1709 REV_DOWN_SAMPLES (data, data_end, d, d_end);
1712 /* for the next iteration we write to the next segment at the beginning. */
1716 /* we consumed all samples here */
1717 data = data_end + bps;
1720 return inr - ((data_end - data) / bps);
1725 GST_DEBUG_OBJECT (buf, "stopped processing");
1731 * gst_ring_buffer_commit_full:
1732 * @buf: the #GstRingBuffer to commit
1733 * @sample: the sample position of the data
1734 * @data: the data to commit
1735 * @in_samples: the number of samples in the data to commit
1736 * @out_samples: the number of samples to write to the ringbuffer
1737 * @accum: accumulator for rate conversion.
1739 * Commit @in_samples samples pointed to by @data to the ringbuffer @buf.
1741 * @in_samples and @out_samples define the rate conversion to perform on the the
1742 * samples in @data. For negative rates, @out_samples must be negative and
1743 * @in_samples positive.
1745 * When @out_samples is positive, the first sample will be written at position @sample
1746 * in the ringbuffer. When @out_samples is negative, the last sample will be written to
1747 * @sample in reverse order.
1749 * @out_samples does not need to be a multiple of the segment size of the ringbuffer
1750 * although it is recommended for optimal performance.
1752 * @accum will hold a temporary accumulator used in rate conversion and should be
1753 * set to 0 when this function is first called. In case the commit operation is
1754 * interrupted, one can resume the processing by passing the previously returned
1755 * @accum value back to this function.
1759 * Returns: The number of samples written to the ringbuffer or -1 on error. The
1760 * number of samples written can be less than @out_samples when @buf was interrupted
1761 * with a flush or stop.
1766 gst_ring_buffer_commit_full (GstRingBuffer * buf, guint64 * sample,
1767 guchar * data, gint in_samples, gint out_samples, gint * accum)
1769 GstRingBufferClass *rclass;
1772 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), -1);
1774 if (G_UNLIKELY (in_samples == 0 || out_samples == 0))
1777 rclass = GST_RING_BUFFER_GET_CLASS (buf);
1779 if (G_LIKELY (rclass->commit))
1780 res = rclass->commit (buf, sample, data, in_samples, out_samples, accum);
1786 * gst_ring_buffer_commit:
1787 * @buf: the #GstRingBuffer to commit
1788 * @sample: the sample position of the data
1789 * @data: the data to commit
1790 * @len: the number of samples in the data to commit
1792 * Same as gst_ring_buffer_commit_full() but with a in_samples and out_samples
1793 * equal to @len, ignoring accum.
1795 * Returns: The number of samples written to the ringbuffer or -1 on
1801 gst_ring_buffer_commit (GstRingBuffer * buf, guint64 sample, guchar * data,
1805 guint64 samplep = sample;
1807 res = gst_ring_buffer_commit_full (buf, &samplep, data, len, len, NULL);
1813 * gst_ring_buffer_read:
1814 * @buf: the #GstRingBuffer to read from
1815 * @sample: the sample position of the data
1816 * @data: where the data should be read
1817 * @len: the number of samples in data to read
1819 * Read @len samples from the ringbuffer into the memory pointed
1821 * The first sample should be read from position @sample in
1824 * @len should not be a multiple of the segment size of the ringbuffer
1825 * although it is recommended.
1827 * Returns: The number of samples read from the ringbuffer or -1 on
1833 gst_ring_buffer_read (GstRingBuffer * buf, guint64 sample, guchar * data,
1837 gint segsize, segtotal, bps, sps;
1841 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), -1);
1842 g_return_val_if_fail (buf->data != NULL, -1);
1843 g_return_val_if_fail (data != NULL, -1);
1845 dest = GST_BUFFER_DATA (buf->data);
1846 segsize = buf->spec.segsize;
1847 segtotal = buf->spec.segtotal;
1848 bps = buf->spec.bytes_per_sample;
1849 sps = buf->samples_per_seg;
1852 /* read enough samples */
1853 while (to_read > 0) {
1855 gint readseg, sampleoff;
1857 /* figure out the segment and the offset inside the segment where
1858 * the sample should be read from. */
1859 readseg = sample / sps;
1860 sampleoff = (sample % sps);
1865 /* get the currently processed segment */
1866 segdone = g_atomic_int_get (&buf->segdone) - buf->segbase;
1868 /* see how far away it is from the read segment, normally segdone (where
1869 * the hardware is writing) is bigger than readseg (where software is
1871 diff = segdone - readseg;
1874 ("pointer at %d, sample %" G_GUINT64_FORMAT
1875 ", read from %d-%d, to_read %d, diff %d, segtotal %d, segsize %d",
1876 segdone, sample, readseg, sampleoff, to_read, diff, segtotal,
1879 /* segment too far ahead, reader too slow */
1880 if (G_UNLIKELY (diff >= segtotal)) {
1881 /* pretend we read an empty segment. */
1882 sampleslen = MIN (sps, to_read);
1883 memcpy (data, buf->empty_seg, sampleslen * bps);
1887 /* read segment is within readable range, we can break the loop and
1888 * start reading the data. */
1892 /* else we need to wait for the segment to become readable. */
1893 if (!wait_segment (buf))
1897 /* we can read now */
1898 readseg = readseg % segtotal;
1899 sampleslen = MIN (sps - sampleoff, to_read);
1901 GST_DEBUG_OBJECT (buf, "read @%p seg %d, off %d, sampleslen %d",
1902 dest + readseg * segsize, readseg, sampleoff, sampleslen);
1904 memcpy (data, dest + (readseg * segsize) + (sampleoff * bps),
1905 (sampleslen * bps));
1908 to_read -= sampleslen;
1909 sample += sampleslen;
1910 data += sampleslen * bps;
1913 return len - to_read;
1918 GST_DEBUG_OBJECT (buf, "stopped processing");
1919 return len - to_read;
1924 * gst_ring_buffer_prepare_read:
1925 * @buf: the #GstRingBuffer to read from
1926 * @segment: the segment to read
1927 * @readptr: the pointer to the memory where samples can be read
1928 * @len: the number of bytes to read
1930 * Returns a pointer to memory where the data from segment @segment
1931 * can be found. This function is mostly used by subclasses.
1933 * Returns: FALSE if the buffer is not started.
1938 gst_ring_buffer_prepare_read (GstRingBuffer * buf, gint * segment,
1939 guint8 ** readptr, gint * len)
1944 g_return_val_if_fail (GST_IS_RING_BUFFER (buf), FALSE);
1946 if (buf->callback == NULL) {
1947 /* push mode, fail when nothing is started */
1948 if (g_atomic_int_get (&buf->state) != GST_RING_BUFFER_STATE_STARTED)
1952 g_return_val_if_fail (buf->data != NULL, FALSE);
1953 g_return_val_if_fail (segment != NULL, FALSE);
1954 g_return_val_if_fail (readptr != NULL, FALSE);
1955 g_return_val_if_fail (len != NULL, FALSE);
1957 data = GST_BUFFER_DATA (buf->data);
1959 /* get the position of the pointer */
1960 segdone = g_atomic_int_get (&buf->segdone);
1962 *segment = segdone % buf->spec.segtotal;
1963 *len = buf->spec.segsize;
1964 *readptr = data + *segment * *len;
1966 GST_LOG ("prepare read from segment %d (real %d) @%p",
1967 *segment, segdone, *readptr);
1969 /* callback to fill the memory with data, for pull based
1972 buf->callback (buf, *readptr, *len, buf->cb_data);
1978 * gst_ring_buffer_advance:
1979 * @buf: the #GstRingBuffer to advance
1980 * @advance: the number of segments written
1982 * Subclasses should call this function to notify the fact that
1983 * @advance segments are now processed by the device.
1988 gst_ring_buffer_advance (GstRingBuffer * buf, guint advance)
1990 g_return_if_fail (GST_IS_RING_BUFFER (buf));
1992 /* update counter */
1993 g_atomic_int_add (&buf->segdone, advance);
1995 /* the lock is already taken when the waiting flag is set,
1996 * we grab the lock as well to make sure the waiter is actually
1997 * waiting for the signal */
1998 if (g_atomic_int_compare_and_exchange (&buf->waiting, 1, 0)) {
1999 GST_OBJECT_LOCK (buf);
2000 GST_DEBUG_OBJECT (buf, "signal waiter");
2001 GST_RING_BUFFER_SIGNAL (buf);
2002 GST_OBJECT_UNLOCK (buf);
2007 * gst_ring_buffer_clear:
2008 * @buf: the #GstRingBuffer to clear
2009 * @segment: the segment to clear
2011 * Clear the given segment of the buffer with silence samples.
2012 * This function is used by subclasses.
2017 gst_ring_buffer_clear (GstRingBuffer * buf, gint segment)
2021 g_return_if_fail (GST_IS_RING_BUFFER (buf));
2023 /* no data means it's already cleared */
2024 if (G_UNLIKELY (buf->data == NULL))
2027 /* no empty_seg means it's not opened */
2028 if (G_UNLIKELY (buf->empty_seg == NULL))
2031 segment %= buf->spec.segtotal;
2033 data = GST_BUFFER_DATA (buf->data);
2034 data += segment * buf->spec.segsize;
2036 GST_LOG ("clear segment %d @%p", segment, data);
2038 memcpy (data, buf->empty_seg, buf->spec.segsize);
2042 * gst_ring_buffer_may_start:
2043 * @buf: the #GstRingBuffer
2044 * @allowed: the new value
2046 * Tell the ringbuffer that it is allowed to start playback when
2047 * the ringbuffer is filled with samples.
2054 gst_ring_buffer_may_start (GstRingBuffer * buf, gboolean allowed)
2056 g_return_if_fail (GST_IS_RING_BUFFER (buf));
2058 GST_LOG_OBJECT (buf, "may start: %d", allowed);
2059 g_atomic_int_set (&buf->abidata.ABI.may_start, allowed);