static GstStateChangeReturn gst_audio_ringbuffer_change_state (GstElement * element, GstStateChange transition) { GstAudioRingbuffer *ringbuffer; GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; ringbuffer = GST_AUDIO_RINGBUFFER (element); switch (transition) { case GST_STATE_CHANGE_NULL_TO_READY: if (ringbuffer->buffer == NULL) { ringbuffer->buffer = gst_int_ring_buffer_new (); gst_object_set_parent (GST_OBJECT (ringbuffer->buffer), GST_OBJECT (ringbuffer)); gst_ring_buffer_open_device (ringbuffer->buffer); } break; case GST_STATE_CHANGE_READY_TO_PAUSED: ringbuffer->next_sample = -1; ringbuffer->last_align = -1; gst_ring_buffer_set_flushing (ringbuffer->buffer, FALSE); gst_ring_buffer_may_start (ringbuffer->buffer, TRUE); break; case GST_STATE_CHANGE_PAUSED_TO_READY: GST_OBJECT_LOCK (ringbuffer); ringbuffer->flushing = TRUE; ringbuffer->waiting = FALSE; g_cond_broadcast (ringbuffer->cond); GST_OBJECT_UNLOCK (ringbuffer); gst_ring_buffer_set_flushing (ringbuffer->buffer, TRUE); gst_ring_buffer_may_start (ringbuffer->buffer, FALSE); break; default: break; } ret = GST_ELEMENT_CLASS (elem_parent_class)->change_state (element, transition); switch (transition) { case GST_STATE_CHANGE_PAUSED_TO_READY: gst_ring_buffer_activate (ringbuffer->buffer, FALSE); gst_ring_buffer_release (ringbuffer->buffer); break; case GST_STATE_CHANGE_READY_TO_NULL: if (ringbuffer->buffer != NULL) { gst_ring_buffer_close_device (ringbuffer->buffer); gst_object_unparent (GST_OBJECT (ringbuffer->buffer)); ringbuffer->buffer = NULL; } break; default: break; } return ret; }
static GstStateChangeReturn gst_base_audio_src_change_state (GstElement * element, GstStateChange transition) { GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; GstBaseAudioSrc *src = GST_BASE_AUDIO_SRC (element); switch (transition) { case GST_STATE_CHANGE_NULL_TO_READY: GST_DEBUG_OBJECT (src, "NULL->READY"); GST_OBJECT_LOCK (src); if (src->ringbuffer == NULL) { gst_audio_clock_reset (GST_AUDIO_CLOCK (src->clock), 0); src->ringbuffer = gst_base_audio_src_create_ringbuffer (src); } GST_OBJECT_UNLOCK (src); if (!gst_ring_buffer_open_device (src->ringbuffer)) goto open_failed; break; case GST_STATE_CHANGE_READY_TO_PAUSED: GST_DEBUG_OBJECT (src, "READY->PAUSED"); src->next_sample = -1; gst_ring_buffer_set_flushing (src->ringbuffer, FALSE); gst_ring_buffer_may_start (src->ringbuffer, FALSE); break; case GST_STATE_CHANGE_PAUSED_TO_PLAYING: GST_DEBUG_OBJECT (src, "PAUSED->PLAYING"); gst_ring_buffer_may_start (src->ringbuffer, TRUE); break; case GST_STATE_CHANGE_PLAYING_TO_PAUSED: GST_DEBUG_OBJECT (src, "PLAYING->PAUSED"); gst_ring_buffer_may_start (src->ringbuffer, FALSE); gst_ring_buffer_pause (src->ringbuffer); break; case GST_STATE_CHANGE_PAUSED_TO_READY: GST_DEBUG_OBJECT (src, "PAUSED->READY"); gst_ring_buffer_set_flushing (src->ringbuffer, TRUE); break; default: break; } ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition); switch (transition) { case GST_STATE_CHANGE_PAUSED_TO_READY: GST_DEBUG_OBJECT (src, "PAUSED->READY"); gst_ring_buffer_release (src->ringbuffer); break; case GST_STATE_CHANGE_READY_TO_NULL: GST_DEBUG_OBJECT (src, "READY->NULL"); gst_ring_buffer_close_device (src->ringbuffer); GST_OBJECT_LOCK (src); gst_object_unparent (GST_OBJECT_CAST (src->ringbuffer)); src->ringbuffer = NULL; GST_OBJECT_UNLOCK (src); break; default: break; } return ret; /* ERRORS */ open_failed: { /* subclass must post a meaningfull error message */ GST_DEBUG_OBJECT (src, "open failed"); return GST_STATE_CHANGE_FAILURE; } }
static GstStateChangeReturn gst_base_audio_src_change_state (GstElement * element, GstStateChange transition) { GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; GstBaseAudioSrc *src = GST_BASE_AUDIO_SRC (element); switch (transition) { case GST_STATE_CHANGE_NULL_TO_READY: GST_DEBUG_OBJECT (src, "NULL->READY"); GST_OBJECT_LOCK (src); if (src->ringbuffer == NULL) { gst_audio_clock_reset (GST_AUDIO_CLOCK (src->clock), 0); src->ringbuffer = gst_base_audio_src_create_ringbuffer (src); } GST_OBJECT_UNLOCK (src); if (!gst_ring_buffer_open_device (src->ringbuffer)) goto open_failed; break; case GST_STATE_CHANGE_READY_TO_PAUSED: GST_DEBUG_OBJECT (src, "READY->PAUSED"); src->next_sample = -1; gst_ring_buffer_set_flushing (src->ringbuffer, FALSE); gst_ring_buffer_may_start (src->ringbuffer, FALSE); /* Only post clock-provide messages if this is the clock that * we've created. If the subclass has overriden it the subclass * should post this messages whenever necessary */ if (src->clock && GST_IS_AUDIO_CLOCK (src->clock) && GST_AUDIO_CLOCK_CAST (src->clock)->func == (GstAudioClockGetTimeFunc) gst_base_audio_src_get_time) gst_element_post_message (element, gst_message_new_clock_provide (GST_OBJECT_CAST (element), src->clock, TRUE)); break; case GST_STATE_CHANGE_PAUSED_TO_PLAYING: GST_DEBUG_OBJECT (src, "PAUSED->PLAYING"); gst_ring_buffer_may_start (src->ringbuffer, TRUE); break; case GST_STATE_CHANGE_PLAYING_TO_PAUSED: GST_DEBUG_OBJECT (src, "PLAYING->PAUSED"); gst_ring_buffer_may_start (src->ringbuffer, FALSE); gst_ring_buffer_pause (src->ringbuffer); break; case GST_STATE_CHANGE_PAUSED_TO_READY: GST_DEBUG_OBJECT (src, "PAUSED->READY"); /* Only post clock-lost messages if this is the clock that * we've created. If the subclass has overriden it the subclass * should post this messages whenever necessary */ if (src->clock && GST_IS_AUDIO_CLOCK (src->clock) && GST_AUDIO_CLOCK_CAST (src->clock)->func == (GstAudioClockGetTimeFunc) gst_base_audio_src_get_time) gst_element_post_message (element, gst_message_new_clock_lost (GST_OBJECT_CAST (element), src->clock)); gst_ring_buffer_set_flushing (src->ringbuffer, TRUE); break; default: break; } ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition); switch (transition) { case GST_STATE_CHANGE_PAUSED_TO_READY: GST_DEBUG_OBJECT (src, "PAUSED->READY"); gst_ring_buffer_release (src->ringbuffer); break; case GST_STATE_CHANGE_READY_TO_NULL: GST_DEBUG_OBJECT (src, "READY->NULL"); gst_ring_buffer_close_device (src->ringbuffer); GST_OBJECT_LOCK (src); gst_object_unparent (GST_OBJECT_CAST (src->ringbuffer)); src->ringbuffer = NULL; GST_OBJECT_UNLOCK (src); break; default: break; } return ret; /* ERRORS */ open_failed: { /* subclass must post a meaningfull error message */ GST_DEBUG_OBJECT (src, "open failed"); return GST_STATE_CHANGE_FAILURE; } }