[GStreamer] GstCaps and GstPad RefPtr implementation
authorphiln@webkit.org <philn@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 11 Nov 2011 16:35:13 +0000 (16:35 +0000)
committerphiln@webkit.org <philn@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 11 Nov 2011 16:35:13 +0000 (16:35 +0000)
https://bugs.webkit.org/show_bug.cgi?id=72023

Reviewed by Martin Robinson.

Smart pointer implementations for GstCaps and GstPad and them
in the media player code.

* platform/graphics/gstreamer/GRefPtrGStreamer.cpp:
(WTF::GstPad):
(WTF::GstCaps):
* platform/graphics/gstreamer/GRefPtrGStreamer.h:
* platform/graphics/gstreamer/GStreamerGWorld.cpp:
(WebCore::GStreamerGWorld::enterFullscreen):
(WebCore::GStreamerGWorld::exitFullscreen):
* platform/graphics/gstreamer/MediaPlayerPrivateGStreamer.cpp:
(WebCore::MediaPlayerPrivateGStreamer::naturalSize):
(WebCore::MediaPlayerPrivateGStreamer::totalBytes):
(WebCore::MediaPlayerPrivateGStreamer::createGSTPlayBin):
* platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp:
(webkit_web_src_init):
(StreamingClient::didReceiveResponse):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@99977 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebCore/ChangeLog
Source/WebCore/platform/graphics/gstreamer/GRefPtrGStreamer.cpp
Source/WebCore/platform/graphics/gstreamer/GRefPtrGStreamer.h
Source/WebCore/platform/graphics/gstreamer/GStreamerGWorld.cpp
Source/WebCore/platform/graphics/gstreamer/MediaPlayerPrivateGStreamer.cpp
Source/WebCore/platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp

index adc217a..a9499cd 100644 (file)
@@ -1,3 +1,28 @@
+2011-11-10  Philippe Normand  <pnormand@igalia.com>
+
+        [GStreamer] GstCaps and GstPad RefPtr implementation
+        https://bugs.webkit.org/show_bug.cgi?id=72023
+
+        Reviewed by Martin Robinson.
+
+        Smart pointer implementations for GstCaps and GstPad and them
+        in the media player code.
+
+        * platform/graphics/gstreamer/GRefPtrGStreamer.cpp:
+        (WTF::GstPad):
+        (WTF::GstCaps):
+        * platform/graphics/gstreamer/GRefPtrGStreamer.h:
+        * platform/graphics/gstreamer/GStreamerGWorld.cpp:
+        (WebCore::GStreamerGWorld::enterFullscreen):
+        (WebCore::GStreamerGWorld::exitFullscreen):
+        * platform/graphics/gstreamer/MediaPlayerPrivateGStreamer.cpp:
+        (WebCore::MediaPlayerPrivateGStreamer::naturalSize):
+        (WebCore::MediaPlayerPrivateGStreamer::totalBytes):
+        (WebCore::MediaPlayerPrivateGStreamer::createGSTPlayBin):
+        * platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp:
+        (webkit_web_src_init):
+        (StreamingClient::didReceiveResponse):
+
 2011-11-11  Sheriff Bot  <webkit.review.bot@gmail.com>
 
         Unreviewed, rolling out r99964.
index 91b65d8..196ea48 100644 (file)
@@ -28,7 +28,7 @@ namespace WTF {
 template <> GstElement* refGPtr<GstElement>(GstElement* ptr)
 {
     if (ptr)
-        gst_object_ref(ptr);
+        gst_object_ref_sink(ptr);
     return ptr;
 }
 
@@ -38,5 +38,31 @@ template <> void derefGPtr<GstElement>(GstElement* ptr)
         gst_object_unref(ptr);
 }
 
+template <> GstPad* refGPtr<GstPad>(GstPad* ptr)
+{
+    if (ptr)
+        gst_object_ref_sink(GST_OBJECT(ptr));
+    return ptr;
+}
+
+template <> void derefGPtr<GstPad>(GstPad* ptr)
+{
+    if (ptr)
+        gst_object_unref(GST_OBJECT(ptr));
+}
+
+template <> GstCaps* refGPtr<GstCaps>(GstCaps* ptr)
+{
+    if (ptr)
+        gst_caps_ref(ptr);
+    return ptr;
+}
+
+template <> void derefGPtr<GstCaps>(GstCaps* ptr)
+{
+    if (ptr)
+        gst_caps_unref(ptr);
+}
+
 }
 #endif // USE(GSTREAMER)
index fdc6f30..3d43127 100644 (file)
 #include "GRefPtr.h"
 
 typedef struct _GstElement GstElement;
+typedef struct _GstPad GstPad;
+typedef struct _GstCaps GstCaps;
 
 namespace WTF {
 
 template<> GstElement* refGPtr<GstElement>(GstElement* ptr);
 template<> void derefGPtr<GstElement>(GstElement* ptr);
 
+template<> GstPad* refGPtr<GstPad>(GstPad* ptr);
+template<> void derefGPtr<GstPad>(GstPad* ptr);
+
+template<> GstCaps* refGPtr<GstCaps>(GstCaps* ptr);
+template<> void derefGPtr<GstCaps>(GstCaps* ptr);
+
 }
 
 #endif // USE(GSTREAMER)
index 94f6837..4536342 100644 (file)
@@ -92,7 +92,7 @@ bool GStreamerGWorld::enterFullscreen()
     g_object_get(m_pipeline, "video-sink", &sinkPtr, NULL);
     videoSink = adoptGRef(sinkPtr);
 
-    GstElement* tee = gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoTee");
+    GRefPtr<GstElement> tee = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoTee"));
 
     // Add and link a queue, ffmpegcolorspace, videoscale and sink in the bin.
     gst_bin_add_many(GST_BIN(videoSink.get()), platformVideoSink, videoScale, colorspace, queue, NULL);
@@ -103,12 +103,11 @@ bool GStreamerGWorld::enterFullscreen()
     gst_element_link_pads_full(videoScale, "src", platformVideoSink, "sink", GST_PAD_LINK_CHECK_NOTHING);
 
     // Link a new src pad from tee to queue.
-    GstPad* srcPad = gst_element_get_request_pad(tee, "src%d");
-    GstPad* sinkPad = gst_element_get_static_pad(queue, "sink");
-    gst_pad_link(srcPad, sinkPad);
-    gst_object_unref(GST_OBJECT(sinkPad));
+    GRefPtr<GstPad> srcPad = adoptGRef(gst_element_get_request_pad(tee.get(), "src%d"));
+    GRefPtr<GstPad> sinkPad = adoptGRef(gst_element_get_static_pad(queue, "sink"));
+    gst_pad_link(srcPad.get(), sinkPad.get());
 
-    m_dynamicPadName.set(gst_pad_get_name(srcPad));
+    m_dynamicPadName.set(gst_pad_get_name(srcPad.get()));
 
     // Synchronize the new elements with pipeline state. If it's
     // paused limit the state change to pre-rolling.
@@ -121,7 +120,6 @@ bool GStreamerGWorld::enterFullscreen()
     gst_element_set_state(videoScale, state);
     gst_element_set_state(colorspace, state);
     gst_element_set_state(queue, state);
-    gst_object_unref(tee);
 
     // Query the current media segment informations and send them towards
     // the new tee branch downstream.
@@ -131,7 +129,6 @@ bool GStreamerGWorld::enterFullscreen()
 
     if (!queryResult) {
         gst_query_unref(query);
-        gst_object_unref(GST_OBJECT(srcPad));
         return true;
     }
 
@@ -145,10 +142,9 @@ bool GStreamerGWorld::enterFullscreen()
     gst_query_parse_segment(query, &rate, &format, &startValue, &stopValue);
 
     GstEvent* event = gst_event_new_new_segment(FALSE, rate, format, startValue, stopValue, position);
-    gst_pad_push_event(srcPad, event);
+    gst_pad_push_event(srcPad.get(), event);
 
     gst_query_unref(query);
-    gst_object_unref(GST_OBJECT(srcPad));
     return true;
 }
 
@@ -164,44 +160,35 @@ void GStreamerGWorld::exitFullscreen()
     g_object_get(m_pipeline, "video-sink", &sinkPtr, NULL);
     videoSink = adoptGRef(sinkPtr);
 
-    GstElement* tee = gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoTee");
-    GstElement* platformVideoSink = gst_bin_get_by_name(GST_BIN(videoSink.get()), "platformVideoSink");
-    GstElement* queue = gst_bin_get_by_name(GST_BIN(videoSink.get()), "queue");
-    GstElement* colorspace = gst_bin_get_by_name(GST_BIN(videoSink.get()), "colorspace");
-    GstElement* videoScale = gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoScale");
+    GRefPtr<GstElement> tee = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoTee"));
+    GRefPtr<GstElement> platformVideoSink = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "platformVideoSink"));
+    GRefPtr<GstElement> queue = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "queue"));
+    GRefPtr<GstElement> colorspace = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "colorspace"));
+    GRefPtr<GstElement> videoScale = adoptGRef(gst_bin_get_by_name(GST_BIN(videoSink.get()), "videoScale"));
 
     // Get pads to unlink and remove.
-    GstPad* srcPad = gst_element_get_static_pad(tee, m_dynamicPadName.get());
-    GstPad* sinkPad = gst_element_get_static_pad(queue, "sink");
+    GRefPtr<GstPad> srcPad = adoptGRef(gst_element_get_static_pad(tee.get(), m_dynamicPadName.get()));
+    GRefPtr<GstPad> sinkPad = adoptGRef(gst_element_get_static_pad(queue.get(), "sink"));
 
     // Block data flow towards the pipeline branch to remove. No need
     // for pad blocking if the pipeline is paused.
     GstState state;
     gst_element_get_state(m_pipeline, &state, 0, 0);
-    if (state < GST_STATE_PLAYING || gst_pad_set_blocked(srcPad, true)) {
+    if (state < GST_STATE_PLAYING || gst_pad_set_blocked(srcPad.get(), true)) {
 
         // Unlink and release request pad.
-        gst_pad_unlink(srcPad, sinkPad);
-        gst_element_release_request_pad(tee, srcPad);
+        gst_pad_unlink(srcPad.get(), sinkPad.get());
+        gst_element_release_request_pad(tee.get(), srcPad.get());
 
         // Unlink, remove and cleanup queue, ffmpegcolorspace, videoScale and sink.
-        gst_element_unlink_many(queue, colorspace, videoScale, platformVideoSink, NULL);
-        gst_bin_remove_many(GST_BIN(videoSink.get()), queue, colorspace, videoScale, platformVideoSink, NULL);
-        gst_element_set_state(platformVideoSink, GST_STATE_NULL);
-        gst_element_set_state(videoScale, GST_STATE_NULL);
-        gst_element_set_state(colorspace, GST_STATE_NULL);
-        gst_element_set_state(queue, GST_STATE_NULL);
+        gst_element_unlink_many(queue.get(), colorspace.get(), videoScale.get(), platformVideoSink.get(), NULL);
+        gst_bin_remove_many(GST_BIN(videoSink.get()), queue.get(), colorspace.get(), videoScale.get(), platformVideoSink.get(), NULL);
+        gst_element_set_state(platformVideoSink.get(), GST_STATE_NULL);
+        gst_element_set_state(videoScale.get(), GST_STATE_NULL);
+        gst_element_set_state(colorspace.get(), GST_STATE_NULL);
+        gst_element_set_state(queue.get(), GST_STATE_NULL);
     }
 
-    gst_object_unref(GST_OBJECT(srcPad));
-    gst_object_unref(GST_OBJECT(sinkPad));
-
-    gst_object_unref(queue);
-    gst_object_unref(colorspace);
-    gst_object_unref(videoScale);
-    gst_object_unref(platformVideoSink);
-
-    gst_object_unref(tee);
     m_dynamicPadName.clear();
 }
 
index 6e49bd2..e28b67b 100644 (file)
@@ -481,12 +481,12 @@ IntSize MediaPlayerPrivateGStreamer::naturalSize() const
     if (!hasVideo())
         return IntSize();
 
-    GstPad* pad = gst_element_get_static_pad(m_webkitVideoSink, "sink");
+    GRefPtr<GstPad> pad = adoptGRef(gst_element_get_static_pad(m_webkitVideoSink, "sink"));
     if (!pad)
         return IntSize();
 
     guint64 width = 0, height = 0;
-    GstCaps* caps = GST_PAD_CAPS(pad);
+    GstCaps* caps = GST_PAD_CAPS(pad.get());
     int pixelAspectRatioNumerator, pixelAspectRatioDenominator;
     int displayWidth, displayHeight, displayAspectRatioGCD;
     int originalWidth = 0, originalHeight = 0;
@@ -496,17 +496,13 @@ IntSize MediaPlayerPrivateGStreamer::naturalSize() const
     // TODO: handle possible transformation matrix. See
     // https://bugzilla.gnome.org/show_bug.cgi?id=596326
 
-    // Get the video PAR and original size.
+    // Get the video PAR and original size, if this fails the
+    // video-sink has likely not yet negotiated its caps.
     if (!GST_IS_CAPS(caps) || !gst_caps_is_fixed(caps)
         || !gst_video_format_parse_caps(caps, 0, &originalWidth, &originalHeight)
         || !gst_video_parse_caps_pixel_aspect_ratio(caps, &pixelAspectRatioNumerator,
-                                                    &pixelAspectRatioDenominator)) {
-        gst_object_unref(GST_OBJECT(pad));
-        // The video-sink has likely not yet negotiated its caps.
+                                                    &pixelAspectRatioDenominator))
         return IntSize();
-    }
-
-    gst_object_unref(GST_OBJECT(pad));
 
     LOG_VERBOSE(Media, "Original video size: %dx%d", originalWidth, originalHeight);
     LOG_VERBOSE(Media, "Pixel aspect ratio: %d/%d", pixelAspectRatioNumerator, pixelAspectRatioDenominator);
@@ -939,12 +935,11 @@ unsigned MediaPlayerPrivateGStreamer::totalBytes() const
 
         switch (gst_iterator_next(iter, &data)) {
         case GST_ITERATOR_OK: {
-            GstPad* pad = GST_PAD_CAST(data);
+            GRefPtr<GstPad> pad = adoptGRef(GST_PAD_CAST(data));
             gint64 padLength = 0;
-            if (gst_pad_query_duration(pad, &fmt, &padLength)
+            if (gst_pad_query_duration(pad.get(), &fmt, &padLength)
                 && padLength > length)
                 length = padLength;
-            gst_object_unref(pad);
             break;
         }
         case GST_ITERATOR_RESYNC:
@@ -1708,11 +1703,9 @@ void MediaPlayerPrivateGStreamer::createGSTPlayBin()
     gst_bin_add_many(GST_BIN(m_videoSinkBin), videoTee, queue, NULL);
 
     // Link a new src pad from tee to queue1.
-    GstPad* srcPad = gst_element_get_request_pad(videoTee, "src%d");
-    GstPad* sinkPad = gst_element_get_static_pad(queue, "sink");
-    gst_pad_link(srcPad, sinkPad);
-    gst_object_unref(GST_OBJECT(srcPad));
-    gst_object_unref(GST_OBJECT(sinkPad));
+    GRefPtr<GstPad> srcPad = adoptGRef(gst_element_get_request_pad(videoTee, "src%d"));
+    GRefPtr<GstPad> sinkPad = adoptGRef(gst_element_get_static_pad(queue, "sink"));
+    gst_pad_link(srcPad.get(), sinkPad.get());
 
     GstElement* actualVideoSink = 0;
     m_fpsSink = gst_element_factory_make("fpsdisplaysink", "sink");
@@ -1750,19 +1743,15 @@ void MediaPlayerPrivateGStreamer::createGSTPlayBin()
     gst_element_link_pads_full(queue, "src", actualVideoSink, "sink", GST_PAD_LINK_CHECK_NOTHING);
 
     // Add a ghostpad to the bin so it can proxy to tee.
-    GstPad* pad = gst_element_get_static_pad(videoTee, "sink");
-    gst_element_add_pad(m_videoSinkBin, gst_ghost_pad_new("sink", pad));
-    gst_object_unref(GST_OBJECT(pad));
+    GRefPtr<GstPad> pad = adoptGRef(gst_element_get_static_pad(videoTee, "sink"));
+    gst_element_add_pad(m_videoSinkBin, gst_ghost_pad_new("sink", pad.get()));
 
     // Set the bin as video sink of playbin.
     g_object_set(m_playBin, "video-sink", m_videoSinkBin, NULL);
 
-
-    pad = gst_element_get_static_pad(m_webkitVideoSink, "sink");
-    if (pad) {
-        g_signal_connect(pad, "notify::caps", G_CALLBACK(mediaPlayerPrivateVideoSinkCapsChangedCallback), this);
-        gst_object_unref(GST_OBJECT(pad));
-    }
+    pad = adoptGRef(gst_element_get_static_pad(m_webkitVideoSink, "sink"));
+    if (pad)
+        g_signal_connect(pad.get(), "notify::caps", G_CALLBACK(mediaPlayerPrivateVideoSinkCapsChangedCallback), this);
 
 }
 
index e7ad8ab..32f587c 100644 (file)
@@ -213,7 +213,6 @@ static void webkit_web_src_class_init(WebKitWebSrcClass* klass)
 static void webkit_web_src_init(WebKitWebSrc* src)
 {
     GstPadTemplate* padTemplate = gst_static_pad_template_get(&srcTemplate);
-    GstPad* targetpad;
     WebKitWebSrcPrivate* priv = WEBKIT_WEB_SRC_GET_PRIVATE(src);
 
     src->priv = priv;
@@ -232,9 +231,8 @@ static void webkit_web_src_init(WebKitWebSrc* src)
     gst_bin_add(GST_BIN(src), GST_ELEMENT(priv->appsrc));
 
 
-    targetpad = gst_element_get_static_pad(GST_ELEMENT(priv->appsrc), "src");
-    priv->srcpad = gst_ghost_pad_new_from_template("src", targetpad, padTemplate);
-    gst_object_unref(targetpad);
+    GRefPtr<GstPad> targetPad = adoptGRef(gst_element_get_static_pad(GST_ELEMENT(priv->appsrc), "src"));
+    priv->srcpad = gst_ghost_pad_new_from_template("src", targetPad.get(), padTemplate);
 
     gst_element_add_pad(GST_ELEMENT(src), priv->srcpad);
     gst_pad_set_query_function(priv->srcpad, webKitWebSrcQuery);
@@ -732,10 +730,9 @@ void StreamingClient::didReceiveResponse(ResourceHandle*, const ResourceResponse
         gint64 icyMetaInt = g_ascii_strtoll(value.utf8().data(), &endptr, 10);
             
         if (endptr && *endptr == '\0' && icyMetaInt > 0) {
-            GstCaps* caps = gst_caps_new_simple("application/x-icy", "metadata-interval", G_TYPE_INT, (gint) icyMetaInt, NULL);
+            GRefPtr<GstCaps> caps = adoptGRef(gst_caps_new_simple("application/x-icy", "metadata-interval", G_TYPE_INT, (gint) icyMetaInt, NULL));
 
-            gst_app_src_set_caps(priv->appsrc, caps);
-            gst_caps_unref(caps);
+            gst_app_src_set_caps(priv->appsrc, caps.get());
         }
     }