Title: [260629] releases/WebKitGTK/webkit-2.28
Revision
260629
Author
[email protected]
Date
2020-04-24 02:20:41 -0700 (Fri, 24 Apr 2020)

Log Message

Merge r260506 - [GStreamer][MSE] Youtube 'live stream'/H264 URLs fail to play, VP8/9 URLs play OK
https://bugs.webkit.org/show_bug.cgi?id=209119

Reviewed by Xabier Rodriguez-Calvar.

Source/WebCore:

The fix consists of removing the initial avoiding of seeking and just
issuing the proper segment instead of seeking (seeks in GStreamer can't
be done before prerolling anyway). Appsrc doesn't make easy to emit our
own custom segment, so what I did was to use a segment fixer probe to
modify the original [0, infinity] segment issued by appsrc and use
a [startTime, stopTime] with proper values depending on the seek target
and rate.

Covered by existing tests.

* platform/graphics/gstreamer/mse/MediaPlayerPrivateGStreamerMSE.cpp:
(WebCore::checkShouldDelaySeek): Don't hold seeks on startup, when changing from READY to PAUSED.
(WebCore::MediaPlayerPrivateGStreamerMSE::doSeek): Refactored seek delay condition. Also, don't do a regular
gst_element_seek() for initial seeks, just proceed with a special case in that situation.
* platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.cpp:
(initialSeekSegmentFixerProbe): Probe that fixes the segment.
(webKitMediaSrcPrepareInitialSeek): Behave much like a regular seek, but also compute the right GstSegment, install
the segment fixer probe and setReadyForMoreSamples() on the SourceBufferPrivates.
* platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.h:

LayoutTests:

Unskipped media/media-source/media-source-seek-redundant-append.html,
which passes now.

* platform/gtk/TestExpectations:
* platform/wpe/TestExpectations:

Modified Paths

Diff

Modified: releases/WebKitGTK/webkit-2.28/LayoutTests/ChangeLog (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/LayoutTests/ChangeLog	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/LayoutTests/ChangeLog	2020-04-24 09:20:41 UTC (rev 260629)
@@ -1,3 +1,16 @@
+2020-04-22  Enrique Ocaña González  <[email protected]>
+
+        [GStreamer][MSE] Youtube 'live stream'/H264 URLs fail to play, VP8/9 URLs play OK
+        https://bugs.webkit.org/show_bug.cgi?id=209119
+
+        Reviewed by Xabier Rodriguez-Calvar.
+
+        Unskipped media/media-source/media-source-seek-redundant-append.html,
+        which passes now.
+
+        * platform/gtk/TestExpectations:
+        * platform/wpe/TestExpectations:
+
 2020-03-18  Eugene But  <[email protected]>
 
         Test for ReplaceSelectionCommand::InsertedNodes::willRemoveNodePreservingChildren crash fix

Modified: releases/WebKitGTK/webkit-2.28/LayoutTests/platform/gtk/TestExpectations (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/LayoutTests/platform/gtk/TestExpectations	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/LayoutTests/platform/gtk/TestExpectations	2020-04-24 09:20:41 UTC (rev 260629)
@@ -2760,8 +2760,6 @@
 webkit.org/b/202736 storage/indexeddb/modern/handle-user-delete.html [ Timeout ]
 webkit.org/b/202736 storage/indexeddb/modern/new-database-after-user-delete.html [ Timeout ]
 
-webkit.org/b/206873 media/media-source/media-source-seek-redundant-append.html [ Timeout ]
-
 webkit.org/b/206876 http/tests/security/storage-blocking-strengthened-private-browsing-plugin.html [ Timeout ]
 
 #////////////////////////////////////////////////////////////////////////////////////////

Modified: releases/WebKitGTK/webkit-2.28/LayoutTests/platform/wpe/TestExpectations (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/LayoutTests/platform/wpe/TestExpectations	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/LayoutTests/platform/wpe/TestExpectations	2020-04-24 09:20:41 UTC (rev 260629)
@@ -1338,8 +1338,6 @@
 
 webkit.org/b/201268 accessibility/insert-newline.html [ Timeout ]
 
-webkit.org/b/206873 media/media-source/media-source-seek-redundant-append.html [ Timeout ]
-
 #////////////////////////////////////////////////////////////////////////////////////////
 # 9. TESTS FAILING
 #////////////////////////////////////////////////////////////////////////////////////////

Modified: releases/WebKitGTK/webkit-2.28/Source/WebCore/ChangeLog (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/Source/WebCore/ChangeLog	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/Source/WebCore/ChangeLog	2020-04-24 09:20:41 UTC (rev 260629)
@@ -1,3 +1,30 @@
+2020-04-22  Enrique Ocaña González  <[email protected]>
+
+        [GStreamer][MSE] Youtube 'live stream'/H264 URLs fail to play, VP8/9 URLs play OK
+        https://bugs.webkit.org/show_bug.cgi?id=209119
+
+        Reviewed by Xabier Rodriguez-Calvar.
+
+        The fix consists of removing the initial avoiding of seeking and just
+        issuing the proper segment instead of seeking (seeks in GStreamer can't
+        be done before prerolling anyway). Appsrc doesn't make easy to emit our
+        own custom segment, so what I did was to use a segment fixer probe to
+        modify the original [0, infinity] segment issued by appsrc and use
+        a [startTime, stopTime] with proper values depending on the seek target
+        and rate.
+
+        Covered by existing tests.
+
+        * platform/graphics/gstreamer/mse/MediaPlayerPrivateGStreamerMSE.cpp:
+        (WebCore::checkShouldDelaySeek): Don't hold seeks on startup, when changing from READY to PAUSED.
+        (WebCore::MediaPlayerPrivateGStreamerMSE::doSeek): Refactored seek delay condition. Also, don't do a regular
+        gst_element_seek() for initial seeks, just proceed with a special case in that situation.
+        * platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.cpp:
+        (initialSeekSegmentFixerProbe): Probe that fixes the segment.
+        (webKitMediaSrcPrepareInitialSeek): Behave much like a regular seek, but also compute the right GstSegment, install
+        the segment fixer probe and setReadyForMoreSamples() on the SourceBufferPrivates.
+        * platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.h:
+
 2020-03-25  Ting-Wei Lan  <[email protected]>
 
         [GTK] Add user agent quirk for auth.mayohr.com

Modified: releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/MediaPlayerPrivateGStreamerMSE.cpp (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/MediaPlayerPrivateGStreamerMSE.cpp	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/MediaPlayerPrivateGStreamerMSE.cpp	2020-04-24 09:20:41 UTC (rev 260629)
@@ -241,6 +241,17 @@
     }
 }
 
+static bool checkShouldDelaySeek(GstStateChangeReturn getStateResult, GstState currentState, GstState newState)
+{
+    if (getStateResult != GST_STATE_CHANGE_ASYNC)
+        return false;
+    if (GST_STATE_TRANSITION(currentState, newState) == GST_STATE_CHANGE_PLAYING_TO_PAUSED)
+        return false;
+    if (currentState == GST_STATE_READY && newState >= GST_STATE_PAUSED)
+        return false;
+    return true;
+}
+
 bool MediaPlayerPrivateGStreamerMSE::doSeek(const MediaTime& position, float rate, GstSeekFlags seekType)
 {
     // FIXME: Make a copy here because in some cases below it is modified. This
@@ -259,13 +270,11 @@
         m_isSeeking = false;
         return false;
     }
-    if ((getStateResult == GST_STATE_CHANGE_ASYNC
-        && !(state == GST_STATE_PLAYING && newState == GST_STATE_PAUSED))
-        || state < GST_STATE_PAUSED
-        || m_isEndReached
-        || !m_gstSeekCompleted) {
+
+    bool shouldDelaySeek = checkShouldDelaySeek(getStateResult, state, newState);
+    if (shouldDelaySeek || m_isEndReached || !m_gstSeekCompleted) {
         CString reason = "Unknown reason";
-        if (getStateResult == GST_STATE_CHANGE_ASYNC) {
+        if (shouldDelaySeek) {
             reason = makeString("In async change ",
                 gst_element_state_get_name(state), " --> ",
                 gst_element_state_get_name(newState)).utf8();
@@ -347,20 +356,26 @@
 
     GST_DEBUG_OBJECT(pipeline(), "Actual seek to %s, end time:  %s, rate: %f", toString(startTime).utf8().data(), toString(endTime).utf8().data(), rate);
 
-    // This will call notifySeekNeedsData() after some time to tell that the pipeline is ready for sample enqueuing.
-    webKitMediaSrcPrepareSeek(WEBKIT_MEDIA_SRC(m_source.get()), seekTime);
+    m_gstSeekCompleted = false;
+    if (state < GST_STATE_PAUSED) {
+        // Special case of initial seek. We set the right segment instead of a seek.
+        webKitMediaSrcPrepareInitialSeek(WEBKIT_MEDIA_SRC(m_source.get()), rate, startTime, endTime);
+        notifySeekNeedsDataForTime(seekTime);
+        GST_DEBUG("Initial seek succeeded, returning true");
+    } else {
+        // This will call notifySeekNeedsData() after some time to tell that the pipeline is ready for sample enqueuing.
+        webKitMediaSrcPrepareSeek(WEBKIT_MEDIA_SRC(m_source.get()), seekTime);
 
-    m_gstSeekCompleted = false;
-    if (!gst_element_seek(m_pipeline.get(), rate, GST_FORMAT_TIME, seekType, GST_SEEK_TYPE_SET, toGstClockTime(startTime), GST_SEEK_TYPE_SET, toGstClockTime(endTime))) {
-        webKitMediaSrcSetReadyForSamples(WEBKIT_MEDIA_SRC(m_source.get()), true);
-        m_isSeeking = false;
-        m_gstSeekCompleted = true;
-        GST_DEBUG_OBJECT(pipeline(), "doSeek(): gst_element_seek() failed, returning false");
-        return false;
+        if (!gst_element_seek(m_pipeline.get(), rate, GST_FORMAT_TIME, seekType, GST_SEEK_TYPE_SET, toGstClockTime(startTime), GST_SEEK_TYPE_SET, toGstClockTime(endTime))) {
+            webKitMediaSrcSetReadyForSamples(WEBKIT_MEDIA_SRC(m_source.get()), true);
+            m_isSeeking = false;
+            m_gstSeekCompleted = true;
+            GST_DEBUG("gst_element_seek() failed, returning false");
+            return false;
+        }
+        // The samples will be enqueued in notifySeekNeedsData().
+        GST_DEBUG("gst_element_seek() succeeded, returning true");
     }
-
-    // The samples will be enqueued in notifySeekNeedsData().
-    GST_DEBUG_OBJECT(pipeline(), "doSeek(): gst_element_seek() succeeded, returning true");
     return true;
 }
 

Modified: releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.cpp (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.cpp	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.cpp	2020-04-24 09:20:41 UTC (rev 260629)
@@ -729,6 +729,55 @@
     GST_OBJECT_UNLOCK(source);
 }
 
+GstPadProbeReturn initialSeekSegmentFixerProbe(GstPad *pad, GstPadProbeInfo *info, gpointer userData)
+{
+    GstEvent* event = GST_PAD_PROBE_INFO_EVENT(info);
+    if (GST_EVENT_TYPE(event) == GST_EVENT_SEGMENT) {
+        const GstSegment* originalSegment = nullptr;
+        const GstSegment* fixedSegment = static_cast<GstSegment*>(userData);
+        gst_event_parse_segment(event, &originalSegment);
+        GST_DEBUG("Segment at %s: %" GST_SEGMENT_FORMAT ", replaced by %" GST_SEGMENT_FORMAT, GST_ELEMENT_NAME(GST_PAD_PARENT(pad)), originalSegment, fixedSegment);
+        gst_event_replace(reinterpret_cast<GstEvent**>(&info->data), gst_event_new_segment(fixedSegment));
+        return GST_PAD_PROBE_REMOVE;
+    }
+    return GST_PAD_PROBE_OK;
+}
+
+void webKitMediaSrcPrepareInitialSeek(WebKitMediaSrc* source, double rate, const MediaTime& startTime, const MediaTime& endTime)
+{
+    GST_OBJECT_LOCK(source);
+    MediaTime seekTime = (rate >= 0) ? startTime : endTime;
+    source->priv->seekTime = seekTime;
+    source->priv->appsrcSeekDataCount = 0;
+    source->priv->appsrcNeedDataCount = 0;
+
+    for (Stream* stream : source->priv->streams) {
+        stream->appsrcNeedDataFlag = false;
+        // Don't allow samples away from the seekTime to be enqueued.
+        stream->lastEnqueuedTime = seekTime;
+    }
+
+    // The pending action will be performed in enabledAppsrcSeekData().
+    source->priv->appsrcSeekDataNextAction = MediaSourceSeekToTime;
+
+    GUniquePtr<GstSegment> segment(gst_segment_new());
+    segment->format = GST_FORMAT_TIME;
+    gst_segment_do_seek(segment.get(), rate, GST_FORMAT_TIME,
+        static_cast<GstSeekFlags>(GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_ACCURATE),
+        GST_SEEK_TYPE_SET, WebCore::toGstUnsigned64Time(startTime),
+        GST_SEEK_TYPE_SET, WebCore::toGstUnsigned64Time(endTime), nullptr);
+
+    for (Stream* stream : source->priv->streams) {
+        // This probe will fix the segment autogenerated by appsrc.
+        GRefPtr<GstPad> pad = adoptGRef(gst_element_get_static_pad(stream->appsrc, "src"));
+        gst_pad_add_probe(pad.get(), GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM,
+            initialSeekSegmentFixerProbe, gst_segment_copy(segment.get()), reinterpret_cast<GDestroyNotify>(gst_segment_free));
+        stream->sourceBuffer->setReadyForMoreSamples(true);
+    }
+
+    GST_OBJECT_UNLOCK(source);
+}
+
 namespace WTF {
 template <> GRefPtr<WebKitMediaSrc> adoptGRef(WebKitMediaSrc* ptr)
 {

Modified: releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.h (260628 => 260629)


--- releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.h	2020-04-24 09:20:34 UTC (rev 260628)
+++ releases/WebKitGTK/webkit-2.28/Source/WebCore/platform/graphics/gstreamer/mse/WebKitMediaSourceGStreamer.h	2020-04-24 09:20:41 UTC (rev 260629)
@@ -73,6 +73,7 @@
 void webKitMediaSrcSetMediaPlayerPrivate(WebKitMediaSrc*, WebCore::MediaPlayerPrivateGStreamerMSE*);
 
 void webKitMediaSrcPrepareSeek(WebKitMediaSrc*, const MediaTime&);
+void webKitMediaSrcPrepareInitialSeek(WebKitMediaSrc*, double rate, const MediaTime& startTime, const MediaTime& endTime);
 void webKitMediaSrcSetReadyForSamples(WebKitMediaSrc*, bool);
 
 G_END_DECLS
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to