GNOME Bugzilla – Bug 475784
rtspsrc has race condition between loop_interleaved() and _pause()
Last modified: 2007-10-22 16:45:51 UTC
There is a possibility that following happens in rtspsrc element (in TCP mode): 1. In gst_rtspsrc_loop_interleaved() the function gst_rtspsrc_connection_receive() has just returned with data message. 2. State change PLAYING_TO_PAUSED happens --> gst_rtsp_connection_flush(TRUE) is called to interrupt reading from RTSP connection, but there is no pending read -> this does nothing 3. gst_rtspsrc_pause() is called --> It gets the CONN_LOCK since no-one is holding it at that moment --> this calls gst_rtsp_connection_flush(FALSE) -> interrupt message is removed from internal message passing pipeline 4. _loop_interleaved() pushes the buffer and exits 5. _loop_interleaved() is called again, since the GstTask is not paused. It does have no idea that playback has been paused. To put the GstTask properly to paused, there should be a check about this before calling gst_rtspsrc_connection_receive().
Created attachment 95334 [details] [review] Detect pause before entering _receive() function Here is one way to fix this. We can check if element has already changed to PAUSED state and leave the _loop_interleaved().
going to take a closer look at this soon..
I had to move the unlock after the _receive() call because if the paused call happens between the check and the _receive() the same problem occurs. Patch by: Tommi Myöhänen <ext-tommi dot myohanen at nokia dot com> * gst/rtsp/gstrtspsrc.c: (gst_rtspsrc_loop_interleaved): Fix race when pausing a RTSP stream in interleaved. Fixes #475784.