add gst_caps_copy_nth as a more general replacement for copy_1.

Original commit message from CVS:
* docs/design/part-TODO.txt:
* gst/elements/gstfakesink.c: (gst_fakesink_event),
(gst_fakesink_chain):
* gst/elements/gstfakesink.h:
* gst/elements/gstfakesrc.c: (gst_fakesrc_loop),
(gst_fakesrc_activate):
* gst/elements/gstfilesrc.c: (gst_filesrc_getrange),
(gst_filesrc_open_file), (gst_filesrc_loop),
(gst_filesrc_activate), (gst_filesrc_change_state),
(filesrc_find_peek), (gst_filesrc_type_find):
* gst/gstcaps.c: (gst_caps_copy_nth):
* gst/gstcaps.h:
* gst/gstelement.c: (gst_element_add_pad),
(gst_element_remove_pad), (iterate_pad),
(gst_element_get_state_func), (gst_element_commit_state),
(gst_element_set_state), (gst_element_pads_activate),
(gst_element_change_state), (gst_element_dispose):
* gst/gstutils.c: (gst_element_finish_preroll):
* gst/gstutils.h:
* tools/gst-launch.c: (check_intr):
add gst_caps_copy_nth as a more general replacement for
copy_1.
Slightly change the finish_preroll helper function to
include pad flush/active.
Small cleanups in fakesrc.
Add STREAM_LOCK in filesrc.
This commit is contained in:
Wim Taymans 2005-02-16 15:18:18 +00:00
parent 2af759f2b5
commit dc44130c0e
16 changed files with 125 additions and 38 deletions

View file

@ -1,3 +1,32 @@
2005-02-16 Wim Taymans <wim@fluendo.com>
* docs/design/part-TODO.txt:
* gst/elements/gstfakesink.c: (gst_fakesink_event),
(gst_fakesink_chain):
* gst/elements/gstfakesink.h:
* gst/elements/gstfakesrc.c: (gst_fakesrc_loop),
(gst_fakesrc_activate):
* gst/elements/gstfilesrc.c: (gst_filesrc_getrange),
(gst_filesrc_open_file), (gst_filesrc_loop),
(gst_filesrc_activate), (gst_filesrc_change_state),
(filesrc_find_peek), (gst_filesrc_type_find):
* gst/gstcaps.c: (gst_caps_copy_nth):
* gst/gstcaps.h:
* gst/gstelement.c: (gst_element_add_pad),
(gst_element_remove_pad), (iterate_pad),
(gst_element_get_state_func), (gst_element_commit_state),
(gst_element_set_state), (gst_element_pads_activate),
(gst_element_change_state), (gst_element_dispose):
* gst/gstutils.c: (gst_element_finish_preroll):
* gst/gstutils.h:
* tools/gst-launch.c: (check_intr):
add gst_caps_copy_nth as a more general replacement for
copy_1.
Slightly change the finish_preroll helper function to
include pad flush/active.
Small cleanups in fakesrc.
Add STREAM_LOCK in filesrc.
2005-02-11 Thomas Vander Stichele <thomas at apestaart dot org>
* docs/gst/Makefile.am:

View file

@ -10,3 +10,7 @@
- only emit EOS in PLAYING.
- implement state change order on get<->loop-get<->loop elements.
- unlinking pads in the PAUSED state needs to make sure the stream thread is not
executing code. Can this be done with a flush to unlock all downstream chain
functions?

View file

@ -330,8 +330,7 @@ gst_fakesink_event (GstPad * pad, GstEvent * event)
switch (GST_EVENT_TYPE (event)) {
case GST_EVENT_EOS:
{
gst_element_finish_preroll (GST_ELEMENT (fakesink),
GST_STREAM_GET_LOCK (pad));
gst_element_finish_preroll (GST_ELEMENT (fakesink), pad);
gst_element_post_message (GST_ELEMENT (fakesink),
gst_message_new_eos (GST_OBJECT (fakesink)));
break;
@ -367,9 +366,7 @@ gst_fakesink_chain (GstPad * pad, GstBuffer * buffer)
/* grab streaming lock to synchronize with event method */
GST_STREAM_LOCK (pad);
result =
gst_element_finish_preroll (GST_ELEMENT (fakesink),
GST_STREAM_GET_LOCK (pad));
result = gst_element_finish_preroll (GST_ELEMENT (fakesink), pad);
if (result != GST_FLOW_OK)
goto exit;

View file

@ -56,6 +56,8 @@ typedef struct _GstFakeSinkClass GstFakeSinkClass;
struct _GstFakeSink {
GstElement element;
GstPad *sinkpad;
gboolean silent;
gboolean dump;
gboolean sync;

View file

@ -777,6 +777,7 @@ gst_fakesrc_loop (GstPad * pad)
GstFakeSrc *src;
GstBuffer *buf;
GstClockTime time;
GstFlowReturn ret;
src = GST_FAKESRC (GST_OBJECT_PARENT (pad));
@ -791,15 +792,13 @@ gst_fakesrc_loop (GstPad * pad)
//gst_pad_push_event (pad, gst_event_new (GST_EVENT_SEGMENT_DONE));
} else {
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
}
}
if (src->rt_num_buffers == 0) {
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
} else {
if (src->rt_num_buffers > 0)
src->rt_num_buffers--;
@ -808,8 +807,7 @@ gst_fakesrc_loop (GstPad * pad)
if (src->eos) {
GST_INFO ("fakesrc is setting eos on pad");
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
}
buf = gst_fakesrc_create_buffer (src);
@ -848,10 +846,18 @@ gst_fakesrc_loop (GstPad * pad)
src->bytes_sent += GST_BUFFER_SIZE (buf);
gst_pad_push (pad, buf);
ret = gst_pad_push (pad, buf);
if (ret != GST_FLOW_OK) {
goto pause;
}
done:
GST_STREAM_UNLOCK (pad);
return;
pause:
gst_task_pause (src->task);
GST_STREAM_UNLOCK (pad);
return;
}
static gboolean

View file

@ -907,15 +907,19 @@ gst_filesrc_loop (GstPad * pad)
filesrc = GST_FILESRC (GST_PAD_PARENT (pad));
GST_STREAM_LOCK (pad);
result = gst_filesrc_get (pad, &buffer);
if (result != GST_FLOW_OK) {
gst_task_pause (GST_RPAD_TASK (pad));
return;
goto done;
}
result = gst_pad_push (pad, buffer);
if (result != GST_FLOW_OK) {
gst_task_pause (GST_RPAD_TASK (pad));
}
done:
GST_STREAM_UNLOCK (pad);
}
@ -978,9 +982,9 @@ gst_filesrc_change_state (GstElement * element)
return GST_STATE_FAILURE;
}
src->need_discont = 2;
break;
case GST_STATE_PAUSED_TO_PLAYING:
gst_task_start (GST_RPAD_TASK (src->srcpad));
break;
}
@ -988,6 +992,7 @@ gst_filesrc_change_state (GstElement * element)
switch (GST_STATE_TRANSITION (element)) {
case GST_STATE_PLAYING_TO_PAUSED:
gst_task_start (GST_RPAD_TASK (src->srcpad));
break;
case GST_STATE_PAUSED_TO_READY:
if (GST_FLAG_IS_SET (element, GST_FILESRC_OPEN))

View file

@ -530,6 +530,35 @@ gst_caps_get_structure (const GstCaps * caps, int index)
return g_ptr_array_index (caps->structs, index);
}
/**
* gst_caps_copy_nth:
* @caps: the @GstCaps to copy
* @nth: the nth structure to copy
*
* Creates a new @GstCaps and appends a copy of the nth structure
* contained in @caps.
*
* Returns: the new @GstCaps
*/
GstCaps *
gst_caps_copy_nth (const GstCaps * caps, gint nth)
{
GstCaps *newcaps;
GstStructure *structure;
g_return_val_if_fail (GST_IS_CAPS (caps), NULL);
newcaps = gst_caps_new_empty ();
newcaps->flags = caps->flags;
if (caps->structs->len > nth) {
structure = gst_caps_get_structure (caps, nth);
gst_caps_append_structure (newcaps, gst_structure_copy (structure));
}
return newcaps;
}
/**
* gst_caps_set_simple:
* @caps: the @GstCaps to set

View file

@ -106,6 +106,7 @@ void gst_caps_append_structure (GstCaps
int gst_caps_get_size (const GstCaps *caps);
GstStructure * gst_caps_get_structure (const GstCaps *caps,
int index);
GstCaps * gst_caps_copy_nth (const GstCaps * caps, gint nth);
void gst_caps_set_simple (GstCaps *caps,
char *field, ...);
void gst_caps_set_simple_valist (GstCaps *caps,

View file

@ -1731,6 +1731,7 @@ gst_element_commit_state (GstElement * element)
GST_STATE (element) = pending;
GST_STATE_PENDING (element) = GST_STATE_VOID_PENDING;
GST_STATE_ERROR (element) = FALSE;
g_signal_emit (G_OBJECT (element), gst_element_signals[STATE_CHANGE],
0, old_state, pending);

View file

@ -388,7 +388,7 @@ gst_element_abort_preroll (GstElement * element)
/* call with stream lock held */
GstFlowReturn
gst_element_finish_preroll (GstElement * element, GMutex * streamlock)
gst_element_finish_preroll (GstElement * element, GstPad * pad)
{
GstFlowReturn result = GST_FLOW_OK;
@ -403,19 +403,20 @@ gst_element_finish_preroll (GstElement * element, GMutex * streamlock)
GST_CAT_DEBUG (GST_CAT_STATES,
"element %s wants to finish preroll", GST_ELEMENT_NAME (element));
/* FIXME, release streaming lock? */
if (streamlock)
g_mutex_unlock (streamlock);
/* here we wait for the next state change */
while (GST_STATE (element) == GST_STATE_PAUSED) {
if (GST_RPAD_IS_FLUSHING (pad) || !GST_RPAD_IS_ACTIVE (pad)) {
GST_CAT_DEBUG (GST_CAT_STATES, "pad is flushing");
result = GST_FLOW_UNEXPECTED;
goto done;
}
GST_CAT_DEBUG (GST_CAT_STATES, "waiting for next state change");
GST_STATE_WAIT (element);
GST_CAT_DEBUG (GST_CAT_STATES, " got state change");
}
if (streamlock)
g_mutex_lock (streamlock);
/* check if we got playing */
if (GST_STATE (element) != GST_STATE_PLAYING) {
/* not playing, we can't accept the buffer */
@ -423,6 +424,7 @@ gst_element_finish_preroll (GstElement * element, GMutex * streamlock)
}
GST_CAT_DEBUG (GST_CAT_STATES, "done preroll");
}
done:
GST_STATE_UNLOCK (element);
return result;

View file

@ -230,7 +230,7 @@ void gst_object_default_error (GstObject * source,
/* element functions */
GstFlowReturn gst_element_abort_preroll (GstElement *element);
GstFlowReturn gst_element_finish_preroll (GstElement *element, GMutex *streamlock);
GstFlowReturn gst_element_finish_preroll (GstElement *element, GstPad *pad);
GstPad* gst_element_get_compatible_pad (GstElement *element, GstPad *pad);
GstPad* gst_element_get_compatible_pad_filtered (GstElement *element, GstPad *pad,

View file

@ -330,8 +330,7 @@ gst_fakesink_event (GstPad * pad, GstEvent * event)
switch (GST_EVENT_TYPE (event)) {
case GST_EVENT_EOS:
{
gst_element_finish_preroll (GST_ELEMENT (fakesink),
GST_STREAM_GET_LOCK (pad));
gst_element_finish_preroll (GST_ELEMENT (fakesink), pad);
gst_element_post_message (GST_ELEMENT (fakesink),
gst_message_new_eos (GST_OBJECT (fakesink)));
break;
@ -367,9 +366,7 @@ gst_fakesink_chain (GstPad * pad, GstBuffer * buffer)
/* grab streaming lock to synchronize with event method */
GST_STREAM_LOCK (pad);
result =
gst_element_finish_preroll (GST_ELEMENT (fakesink),
GST_STREAM_GET_LOCK (pad));
result = gst_element_finish_preroll (GST_ELEMENT (fakesink), pad);
if (result != GST_FLOW_OK)
goto exit;

View file

@ -56,6 +56,8 @@ typedef struct _GstFakeSinkClass GstFakeSinkClass;
struct _GstFakeSink {
GstElement element;
GstPad *sinkpad;
gboolean silent;
gboolean dump;
gboolean sync;

View file

@ -777,6 +777,7 @@ gst_fakesrc_loop (GstPad * pad)
GstFakeSrc *src;
GstBuffer *buf;
GstClockTime time;
GstFlowReturn ret;
src = GST_FAKESRC (GST_OBJECT_PARENT (pad));
@ -791,15 +792,13 @@ gst_fakesrc_loop (GstPad * pad)
//gst_pad_push_event (pad, gst_event_new (GST_EVENT_SEGMENT_DONE));
} else {
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
}
}
if (src->rt_num_buffers == 0) {
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
} else {
if (src->rt_num_buffers > 0)
src->rt_num_buffers--;
@ -808,8 +807,7 @@ gst_fakesrc_loop (GstPad * pad)
if (src->eos) {
GST_INFO ("fakesrc is setting eos on pad");
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
gst_task_pause (src->task);
goto done;
goto pause;
}
buf = gst_fakesrc_create_buffer (src);
@ -848,10 +846,18 @@ gst_fakesrc_loop (GstPad * pad)
src->bytes_sent += GST_BUFFER_SIZE (buf);
gst_pad_push (pad, buf);
ret = gst_pad_push (pad, buf);
if (ret != GST_FLOW_OK) {
goto pause;
}
done:
GST_STREAM_UNLOCK (pad);
return;
pause:
gst_task_pause (src->task);
GST_STREAM_UNLOCK (pad);
return;
}
static gboolean

View file

@ -907,15 +907,19 @@ gst_filesrc_loop (GstPad * pad)
filesrc = GST_FILESRC (GST_PAD_PARENT (pad));
GST_STREAM_LOCK (pad);
result = gst_filesrc_get (pad, &buffer);
if (result != GST_FLOW_OK) {
gst_task_pause (GST_RPAD_TASK (pad));
return;
goto done;
}
result = gst_pad_push (pad, buffer);
if (result != GST_FLOW_OK) {
gst_task_pause (GST_RPAD_TASK (pad));
}
done:
GST_STREAM_UNLOCK (pad);
}
@ -978,9 +982,9 @@ gst_filesrc_change_state (GstElement * element)
return GST_STATE_FAILURE;
}
src->need_discont = 2;
break;
case GST_STATE_PAUSED_TO_PLAYING:
gst_task_start (GST_RPAD_TASK (src->srcpad));
break;
}
@ -988,6 +992,7 @@ gst_filesrc_change_state (GstElement * element)
switch (GST_STATE_TRANSITION (element)) {
case GST_STATE_PLAYING_TO_PAUSED:
gst_task_start (GST_RPAD_TASK (src->srcpad));
break;
case GST_STATE_PAUSED_TO_READY:
if (GST_FLAG_IS_SET (element, GST_FILESRC_OPEN))

View file

@ -279,6 +279,7 @@ check_intr (user_data)
} else {
g_print ("Pausing pipeline.\n");
gst_element_set_state (pipeline, GST_STATE_PAUSED);
g_print ("Paused pipeline.\n");
g_main_loop_quit (loop);
return FALSE;
}