Changeset 151021 in webkit


Ignore:
Timestamp:
May 31, 2013 9:17:47 AM (11 years ago)
Author:
commit-queue@webkit.org
Message:

Make sure gstreamer source element is thread-safe
https://bugs.webkit.org/show_bug.cgi?id=115352

Patch by Andre Moreira Magalhaes <Andre Moreira Magalhaes> on 2013-05-31
Reviewed by Philippe Normand.

GStreamer source element may be created by any gstreamer element on any thread by calling
gst_element_make_from_uri with the URIs handled by the source element.
This patch makes sure the gstreamer source element is thread-safe to avoid issues with it
being created outside the main thread.

  • platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp:

(_WebKitWebSrcPrivate):
(webkit_web_src_init):
(webKitWebSrcFinalize):
(webKitWebSrcSetProperty):
(webKitWebSrcGetProperty):
(webKitWebSrcStop):
(webKitWebSrcStart):
(webKitWebSrcChangeState):
(webKitWebSrcQueryWithParent):
(webKitWebSrcGetUri):
(webKitWebSrcSetUri):
(webKitWebSrcNeedDataMainCb):
(webKitWebSrcEnoughDataMainCb):
(webKitWebSrcSeekMainCb):
(webKitWebSrcSeekDataCb):
(webKitWebSrcSetMediaPlayer):
(StreamingClient::StreamingClient):
(StreamingClient::~StreamingClient):
(StreamingClient::didReceiveResponse):
(StreamingClient::didReceiveData):
(StreamingClient::didFinishLoading):
(StreamingClient::wasBlocked):
(StreamingClient::cannotShowURL):

Location:
trunk/Source/WebCore
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r151016 r151021  
     12013-05-31  Andre Moreira Magalhaes   <andre.magalhaes@collabora.co.uk>
     2
     3        Make sure gstreamer source element is thread-safe
     4        https://bugs.webkit.org/show_bug.cgi?id=115352
     5
     6        Reviewed by Philippe Normand.
     7
     8        GStreamer source element may be created by any gstreamer element on any thread by calling
     9        gst_element_make_from_uri with the URIs handled by the source element.
     10        This patch makes sure the gstreamer source element is thread-safe to avoid issues with it
     11        being created outside the main thread.
     12
     13        * platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp:
     14        (_WebKitWebSrcPrivate):
     15        (webkit_web_src_init):
     16        (webKitWebSrcFinalize):
     17        (webKitWebSrcSetProperty):
     18        (webKitWebSrcGetProperty):
     19        (webKitWebSrcStop):
     20        (webKitWebSrcStart):
     21        (webKitWebSrcChangeState):
     22        (webKitWebSrcQueryWithParent):
     23        (webKitWebSrcGetUri):
     24        (webKitWebSrcSetUri):
     25        (webKitWebSrcNeedDataMainCb):
     26        (webKitWebSrcEnoughDataMainCb):
     27        (webKitWebSrcSeekMainCb):
     28        (webKitWebSrcSeekDataCb):
     29        (webKitWebSrcSetMediaPlayer):
     30        (StreamingClient::StreamingClient):
     31        (StreamingClient::~StreamingClient):
     32        (StreamingClient::didReceiveResponse):
     33        (StreamingClient::didReceiveData):
     34        (StreamingClient::didFinishLoading):
     35        (StreamingClient::wasBlocked):
     36        (StreamingClient::cannotShowURL):
     37
    1382013-05-31  Sergio Villar Senin  <svillar@igalia.com>
    239
  • trunk/Source/WebCore/platform/graphics/gstreamer/WebKitWebSourceGStreamer.cpp

    r149383 r151021  
    4343#include <wtf/text/CString.h>
    4444
     45/* Premisses:
     46 * - webkitsrc may be created from any thread inside gstreamer
     47 * - client holds reference to src, so that src is never deleted while client exists
     48 * - if the src exists, appsrc also exists
     49 * - client is created on start
     50 * - client is deleted on stop after cancelling resource handle
     51 * - client callbacks are always invoked from main thread
     52 * - resource handle methods must always be called from main thread
     53 */
     54
    4555using namespace WebCore;
    4656
     
    8595    guint64 requestedOffset;
    8696
     97    guint startID;
     98    guint stopID;
    8799    guint needDataID;
    88100    guint enoughDataID;
     
    136148static void webKitWebSrcEnoughDataCb(GstAppSrc*, gpointer userData);
    137149static gboolean webKitWebSrcSeekDataCb(GstAppSrc*, guint64 offset, gpointer userData);
    138 
    139 static void webKitWebSrcStop(WebKitWebSrc*, bool);
    140150
    141151static GstAppSrcCallbacks appsrcCallbacks = {
     
    230240    src->priv = priv;
    231241
    232     priv->client = new StreamingClient(src);
    233 
    234242    priv->appsrc = GST_APP_SRC(gst_element_factory_make("appsrc", 0));
    235243    if (!priv->appsrc) {
     
    280288        g_object_set(priv->appsrc, "min-percent", 20, NULL);
    281289
    282     webKitWebSrcStop(src, false);
     290    gst_app_src_set_caps(priv->appsrc, 0);
     291    gst_app_src_set_size(priv->appsrc, -1);
    283292}
    284293
     
    303312    WebKitWebSrcPrivate* priv = src->priv;
    304313
    305     delete priv->client;
    306 
    307314    g_free(priv->uri);
    308315
     
    317324    switch (propID) {
    318325    case PROP_IRADIO_MODE:
     326        GST_OBJECT_LOCK(src);
    319327        priv->iradioMode = g_value_get_boolean(value);
     328        GST_OBJECT_UNLOCK(src);
    320329        break;
    321330    case PROP_LOCATION:
     
    337346    WebKitWebSrcPrivate* priv = src->priv;
    338347
     348    GST_OBJECT_LOCK(src);
    339349    switch (propID) {
    340350    case PROP_IRADIO_MODE:
     
    360370        break;
    361371    }
    362 }
    363 
    364 
    365 static void webKitWebSrcStop(WebKitWebSrc* src, bool seeking)
    366 {
    367     WebKitWebSrcPrivate* priv = src->priv;
     372    GST_OBJECT_UNLOCK(src);
     373}
     374
     375// must be called on main thread and with object unlocked
     376static gboolean webKitWebSrcStop(WebKitWebSrc* src)
     377{
     378    WebKitWebSrcPrivate* priv = src->priv;
     379    gboolean seeking;
     380
     381    GST_OBJECT_LOCK(src);
     382
     383    seeking = priv->seekID;
     384
     385    if (priv->startID) {
     386        g_source_remove(priv->startID);
     387        priv->startID = 0;
     388    }
    368389
    369390    if (priv->resourceHandle) {
     
    373394    priv->resourceHandle = 0;
    374395
     396    if (priv->client) {
     397        delete priv->client;
     398        priv->client = 0;
     399    }
     400
    375401    if (priv->frame && !seeking)
    376402        priv->frame.clear();
     
    385411    }
    386412
    387     GST_OBJECT_LOCK(src);
    388413    if (priv->needDataID)
    389414        g_source_remove(priv->needDataID);
     
    399424
    400425    priv->paused = FALSE;
    401     GST_OBJECT_UNLOCK(src);
    402426
    403427    g_free(priv->iradioName);
     
    412436    g_free(priv->iradioTitle);
    413437    priv->iradioTitle = 0;
     438
     439    priv->offset = 0;
     440    priv->seekable = FALSE;
     441
     442    if (!seeking) {
     443        priv->size = 0;
     444        priv->requestedOffset = 0;
     445    }
     446
     447    priv->stopID = 0;
     448    GST_OBJECT_UNLOCK(src);
    414449
    415450    if (priv->appsrc) {
     
    419454    }
    420455
    421     priv->offset = 0;
    422     priv->seekable = FALSE;
    423 
    424     if (!seeking) {
    425         priv->size = 0;
    426         priv->requestedOffset = 0;
    427     }
    428 
    429456    GST_DEBUG_OBJECT(src, "Stopped request");
    430 }
    431 
    432 static bool webKitWebSrcStart(WebKitWebSrc* src)
    433 {
    434     WebKitWebSrcPrivate* priv = src->priv;
    435 
     457
     458    return FALSE;
     459}
     460
     461// must be called on main thread and with object unlocked
     462static gboolean webKitWebSrcStart(WebKitWebSrc* src)
     463{
     464    WebKitWebSrcPrivate* priv = src->priv;
     465
     466    GST_OBJECT_LOCK(src);
    436467    if (!priv->uri) {
    437468        GST_ERROR_OBJECT(src, "No URI provided");
    438         return false;
    439     }
    440    
     469        GST_OBJECT_UNLOCK(src);
     470        webKitWebSrcStop(src);
     471        return FALSE;
     472    }
     473
    441474    KURL url = KURL(KURL(), priv->uri);
    442475
     
    473506    request.setHTTPHeaderField("transferMode.dlna", "Streaming");
    474507
     508    priv->client = new StreamingClient(src);
    475509    priv->resourceHandle = ResourceHandle::create(context, request, priv->client, false, false);
    476510    if (!priv->resourceHandle) {
    477511        GST_ERROR_OBJECT(src, "Failed to create ResourceHandle");
    478         return false;
    479     }
    480 
    481     GST_DEBUG_OBJECT(src, "Started request");
    482 
    483     return true;
     512        GST_OBJECT_UNLOCK(src);
     513        webKitWebSrcStop(src);
     514    } else {
     515        GST_OBJECT_UNLOCK(src);
     516        GST_DEBUG_OBJECT(src, "Started request");
     517    }
     518    return FALSE;
    484519}
    485520
     
    512547    case GST_STATE_CHANGE_READY_TO_PAUSED:
    513548        GST_DEBUG_OBJECT(src, "READY->PAUSED");
    514         if (!webKitWebSrcStart(src))
    515             ret = GST_STATE_CHANGE_FAILURE;
     549        GST_OBJECT_LOCK(src);
     550        priv->startID = g_timeout_add_full(G_PRIORITY_DEFAULT, 0, (GSourceFunc) webKitWebSrcStart, gst_object_ref(src), (GDestroyNotify) gst_object_unref);
     551        GST_OBJECT_UNLOCK(src);
    516552        break;
    517553    case GST_STATE_CHANGE_PAUSED_TO_READY:
    518554        GST_DEBUG_OBJECT(src, "PAUSED->READY");
    519         webKitWebSrcStop(src, false);
     555        GST_OBJECT_LOCK(src);
     556        priv->stopID = g_timeout_add_full(G_PRIORITY_DEFAULT, 0, (GSourceFunc) webKitWebSrcStop, gst_object_ref(src), (GDestroyNotify) gst_object_unref);
     557        GST_OBJECT_UNLOCK(src);
    520558        break;
    521559    default:
     
    528566static gboolean webKitWebSrcQueryWithParent(GstPad* pad, GstObject* parent, GstQuery* query)
    529567{
    530     WebKitWebSrc* webkitSrc = WEBKIT_WEB_SRC(GST_ELEMENT(parent));
     568    WebKitWebSrc* src = WEBKIT_WEB_SRC(GST_ELEMENT(parent));
    531569    gboolean result = FALSE;
    532570
     
    537575        gst_query_parse_duration(query, &format, NULL);
    538576
    539         GST_DEBUG_OBJECT(webkitSrc, "duration query in format %s", gst_format_get_name(format));
    540         if ((format == GST_FORMAT_BYTES) && (webkitSrc->priv->size > 0)) {
    541             gst_query_set_duration(query, format, webkitSrc->priv->size);
     577        GST_DEBUG_OBJECT(src, "duration query in format %s", gst_format_get_name(format));
     578        GST_OBJECT_LOCK(src);
     579        if ((format == GST_FORMAT_BYTES) && (src->priv->size > 0)) {
     580            gst_query_set_duration(query, format, src->priv->size);
    542581            result = TRUE;
    543582        }
     583        GST_OBJECT_UNLOCK(src);
    544584        break;
    545585    }
    546586    case GST_QUERY_URI: {
    547         gst_query_set_uri(query, webkitSrc->priv->uri);
     587        GST_OBJECT_LOCK(src);
     588        gst_query_set_uri(query, src->priv->uri);
     589        GST_OBJECT_UNLOCK(src);
    548590        result = TRUE;
    549591        break;
     
    586628static gchar* webKitWebSrcGetUri(GstURIHandler* handler)
    587629{
    588     return g_strdup(WEBKIT_WEB_SRC(handler)->priv->uri);
     630    WebKitWebSrc* src = WEBKIT_WEB_SRC(handler);
     631    gchar* ret;
     632
     633    GST_OBJECT_LOCK(src);
     634    ret = g_strdup(src->priv->uri);
     635    GST_OBJECT_UNLOCK(src);
     636    return ret;
    589637}
    590638
     
    599647    }
    600648
     649    GST_OBJECT_LOCK(src);
    601650    g_free(priv->uri);
    602651    priv->uri = 0;
    603652
    604     if (!uri)
     653    if (!uri) {
     654        GST_OBJECT_UNLOCK(src);
    605655        return TRUE;
     656    }
    606657
    607658    KURL url(KURL(), uri);
    608659
    609660    if (!url.isValid() || !url.protocolIsInHTTPFamily()) {
     661        GST_OBJECT_UNLOCK(src);
    610662        g_set_error(error, GST_URI_ERROR, GST_URI_ERROR_BAD_URI, "Invalid URI '%s'", uri);
    611663        return FALSE;
     
    613665
    614666    priv->uri = g_strdup(url.string().utf8().data());
     667    GST_OBJECT_UNLOCK(src);
    615668    return TRUE;
    616669}
     
    630683static const gchar* webKitWebSrcGetUri(GstURIHandler* handler)
    631684{
    632     return g_strdup(WEBKIT_WEB_SRC(handler)->priv->uri);
     685    WebKitWebSrc* src = WEBKIT_WEB_SRC(handler);
     686    gchar* ret;
     687
     688    GST_OBJECT_LOCK(src);
     689    ret = g_strdup(src->priv->uri);
     690    GST_OBJECT_UNLOCK(src);
     691    return ret;
    633692}
    634693
     
    643702    }
    644703
     704    GST_OBJECT_LOCK(src);
    645705    g_free(priv->uri);
    646706    priv->uri = 0;
    647707
    648     if (!uri)
     708    if (!uri) {
     709        GST_OBJECT_UNLOCK(src);
    649710        return TRUE;
     711    }
    650712
    651713    KURL url(KURL(), uri);
    652714
    653715    if (!url.isValid() || !url.protocolIsInHTTPFamily()) {
     716        GST_OBJECT_UNLOCK(src);
    654717        GST_ERROR_OBJECT(src, "Invalid URI '%s'", uri);
    655718        return FALSE;
     
    657720
    658721    priv->uri = g_strdup(url.string().utf8().data());
     722    GST_OBJECT_UNLOCK(src);
    659723    return TRUE;
    660724}
     
    677741    WebKitWebSrcPrivate* priv = src->priv;
    678742
    679     priv->resourceHandle->setDefersLoading(false);
    680 
    681     GST_OBJECT_LOCK(src);
     743    GST_OBJECT_LOCK(src);
     744    // already stopped
     745    if (!priv->needDataID) {
     746        GST_OBJECT_UNLOCK(src);
     747        return FALSE;
     748    }
     749
    682750    priv->paused = FALSE;
    683751    priv->needDataID = 0;
    684752    GST_OBJECT_UNLOCK(src);
     753
     754    if (priv->resourceHandle)
     755        priv->resourceHandle->setDefersLoading(false);
    685756    return FALSE;
    686757}
     
    707778    WebKitWebSrcPrivate* priv = src->priv;
    708779
    709     priv->resourceHandle->setDefersLoading(true);
    710 
    711     GST_OBJECT_LOCK(src);
     780    GST_OBJECT_LOCK(src);
     781    // already stopped
     782    if (!priv->enoughDataID) {
     783        GST_OBJECT_UNLOCK(src);
     784        return FALSE;
     785    }
     786
    712787    priv->paused = TRUE;
    713788    priv->enoughDataID = 0;
    714789    GST_OBJECT_UNLOCK(src);
    715790
     791    if (priv->resourceHandle)
     792        priv->resourceHandle->setDefersLoading(true);
    716793    return FALSE;
    717794}
     
    736813static gboolean webKitWebSrcSeekMainCb(WebKitWebSrc* src)
    737814{
    738     webKitWebSrcStop(src, true);
     815    webKitWebSrcStop(src);
    739816    webKitWebSrcStart(src);
    740817
     
    748825
    749826    GST_DEBUG_OBJECT(src, "Seeking to offset: %" G_GUINT64_FORMAT, offset);
    750     if (offset == priv->offset && priv->requestedOffset == priv->offset)
     827    GST_OBJECT_LOCK(src);
     828    if (offset == priv->offset && priv->requestedOffset == priv->offset) {
     829        GST_OBJECT_UNLOCK(src);
    751830        return TRUE;
    752 
    753     if (!priv->seekable)
     831    }
     832
     833    if (!priv->seekable) {
     834        GST_OBJECT_UNLOCK(src);
    754835        return FALSE;
    755     if (offset > priv->size)
     836    }
     837    if (offset > priv->size) {
     838        GST_OBJECT_UNLOCK(src);
    756839        return FALSE;
     840    }
    757841
    758842    GST_DEBUG_OBJECT(src, "Doing range-request seek");
    759843    priv->requestedOffset = offset;
    760844
    761     GST_OBJECT_LOCK(src);
    762845    if (priv->seekID)
    763846        g_source_remove(priv->seekID);
    764847    priv->seekID = g_timeout_add_full(G_PRIORITY_DEFAULT, 0, (GSourceFunc) webKitWebSrcSeekMainCb, gst_object_ref(src), (GDestroyNotify) gst_object_unref);
    765848    GST_OBJECT_UNLOCK(src);
    766    
     849
    767850    return TRUE;
    768851}
     
    781864}
    782865
    783 StreamingClient::StreamingClient(WebKitWebSrc* src) : m_src(src)
     866StreamingClient::StreamingClient(WebKitWebSrc* src)
     867    : m_src(static_cast<WebKitWebSrc*>(gst_object_ref(src)))
    784868{
    785869
     
    788872StreamingClient::~StreamingClient()
    789873{
    790 
     874    gst_object_unref(m_src);
    791875}
    792876
     
    795879}
    796880
    797 void StreamingClient::didReceiveResponse(ResourceHandle*, const ResourceResponse& response)
     881void StreamingClient::didReceiveResponse(ResourceHandle *handle, const ResourceResponse& response)
    798882{
    799883    WebKitWebSrcPrivate* priv = m_src->priv;
     
    801885    GST_DEBUG_OBJECT(m_src, "Received response: %d", response.httpStatusCode());
    802886
     887    GST_OBJECT_LOCK(m_src);
     888
    803889    // If we seeked we need 206 == PARTIAL_CONTENT
    804     if (priv->requestedOffset && response.httpStatusCode() != 206) {
     890    if (handle != priv->resourceHandle || (priv->requestedOffset && response.httpStatusCode() != 206)) {
     891        GST_OBJECT_UNLOCK(m_src);
    805892        GST_ELEMENT_ERROR(m_src, RESOURCE, READ, (0), (0));
    806893        gst_app_src_end_of_stream(priv->appsrc);
    807         webKitWebSrcStop(m_src, false);
     894        webKitWebSrcStop(m_src);
    808895        return;
    809896    }
    810897
    811898    long long length = response.expectedContentLength();
    812     if (length > 0) {
     899    if (length > 0)
    813900        length += priv->requestedOffset;
    814         gst_app_src_set_size(priv->appsrc, length);
    815 
    816 #ifndef GST_API_VERSION_1
    817         if (!priv->haveAppSrc27) {
    818             gst_segment_set_duration(&GST_BASE_SRC(priv->appsrc)->segment, GST_FORMAT_BYTES, length);
    819             gst_element_post_message(GST_ELEMENT(priv->appsrc),
    820                                      gst_message_new_duration(GST_OBJECT(priv->appsrc),
    821                                                               GST_FORMAT_BYTES, length));
    822         }
    823 #endif
    824     }
    825901
    826902    priv->size = length >= 0 ? length : 0;
    827903    priv->seekable = length > 0 && g_ascii_strcasecmp("none", response.httpHeaderField("Accept-Ranges").utf8().data());
    828 
    829     // icecast stuff
    830     String value = response.httpHeaderField("icy-metaint");
    831     if (!value.isEmpty()) {
    832         gchar* endptr = 0;
    833         gint64 icyMetaInt = g_ascii_strtoll(value.utf8().data(), &endptr, 10);
    834            
    835         if (endptr && *endptr == '\0' && icyMetaInt > 0) {
    836             GRefPtr<GstCaps> caps = adoptGRef(gst_caps_new_simple("application/x-icy", "metadata-interval", G_TYPE_INT, (gint) icyMetaInt, NULL));
    837 
    838             gst_app_src_set_caps(priv->appsrc, caps.get());
    839         }
    840     }
    841904
    842905#ifdef GST_API_VERSION_1
     
    845908    GstTagList* tags = gst_tag_list_new();
    846909#endif
    847     value = response.httpHeaderField("icy-name");
     910    String value = response.httpHeaderField("icy-name");
    848911    if (!value.isEmpty()) {
    849912        g_free(priv->iradioName);
     
    874937    }
    875938
     939    GST_OBJECT_UNLOCK(m_src);
     940
     941    // notify size/duration
     942    if (length > 0) {
     943        gst_app_src_set_size(priv->appsrc, length);
     944
     945#ifndef GST_API_VERSION_1
     946        if (!priv->haveAppSrc27) {
     947            gst_segment_set_duration(&GST_BASE_SRC(priv->appsrc)->segment, GST_FORMAT_BYTES, length);
     948            gst_element_post_message(GST_ELEMENT(priv->appsrc),
     949                gst_message_new_duration(GST_OBJECT(priv->appsrc),
     950                    GST_FORMAT_BYTES, length));
     951        }
     952#endif
     953    } else
     954        gst_app_src_set_size(priv->appsrc, -1);
     955
     956    // icecast stuff
     957    value = response.httpHeaderField("icy-metaint");
     958    if (!value.isEmpty()) {
     959        gchar* endptr = 0;
     960        gint64 icyMetaInt = g_ascii_strtoll(value.utf8().data(), &endptr, 10);
     961
     962        if (endptr && *endptr == '\0' && icyMetaInt > 0) {
     963            GRefPtr<GstCaps> caps = adoptGRef(gst_caps_new_simple("application/x-icy", "metadata-interval", G_TYPE_INT, (gint) icyMetaInt, NULL));
     964
     965            gst_app_src_set_caps(priv->appsrc, caps.get());
     966        }
     967    } else
     968        gst_app_src_set_caps(priv->appsrc, 0);
     969
     970    // notify tags
    876971    if (gst_tag_list_is_empty(tags))
    877972#ifdef GST_API_VERSION_1
     
    881976#endif
    882977    else
    883         notifyGstTagsOnPad(GST_ELEMENT(m_src), m_src->priv->srcpad, tags);
     978        notifyGstTagsOnPad(GST_ELEMENT(m_src), priv->srcpad, tags);
    884979}
    885980
     
    887982{
    888983    WebKitWebSrcPrivate* priv = m_src->priv;
     984
     985    GST_OBJECT_LOCK(m_src);
    889986
    890987    GST_LOG_OBJECT(m_src, "Have %d bytes of data", priv->buffer ? getGstBufferSize(priv->buffer.get()) : length);
     
    898995
    899996    if (priv->seekID || handle != priv->resourceHandle) {
     997        GST_OBJECT_UNLOCK(m_src);
    900998        GST_DEBUG_OBJECT(m_src, "Seek in progress, ignoring data");
    901999        priv->buffer.clear();
     
    9161014    GST_BUFFER_OFFSET_END(priv->buffer.get()) = priv->offset;
    9171015
     1016    GST_OBJECT_UNLOCK(m_src);
     1017
    9181018    GstFlowReturn ret = gst_app_src_push_buffer(priv->appsrc, priv->buffer.leakRef());
    9191019#ifdef GST_API_VERSION_1
     
    9491049    GST_DEBUG_OBJECT(m_src, "Have EOS");
    9501050
    951     if (!priv->seekID)
     1051    GST_OBJECT_LOCK(m_src);
     1052    if (!priv->seekID) {
     1053        GST_OBJECT_UNLOCK(m_src);
    9521054        gst_app_src_end_of_stream(m_src->priv->appsrc);
     1055    } else
     1056        GST_OBJECT_UNLOCK(m_src);
    9531057}
    9541058
     
    9621066void StreamingClient::wasBlocked(ResourceHandle*)
    9631067{
     1068    GOwnPtr<gchar> uri;
     1069
    9641070    GST_ERROR_OBJECT(m_src, "Request was blocked");
    965     GST_ELEMENT_ERROR(m_src, RESOURCE, OPEN_READ, ("Access to \"%s\" was blocked", m_src->priv->uri), (0));
     1071
     1072    GST_OBJECT_LOCK(m_src);
     1073    uri.set(g_strdup(m_src->priv->uri));
     1074    GST_OBJECT_UNLOCK(m_src);
     1075
     1076    GST_ELEMENT_ERROR(m_src, RESOURCE, OPEN_READ, ("Access to \"%s\" was blocked", uri.get()), (0));
    9661077}
    9671078
    9681079void StreamingClient::cannotShowURL(ResourceHandle*)
    9691080{
     1081    GOwnPtr<gchar> uri;
     1082
    9701083    GST_ERROR_OBJECT(m_src, "Cannot show URL");
    971     GST_ELEMENT_ERROR(m_src, RESOURCE, OPEN_READ, ("Can't show \"%s\"", m_src->priv->uri), (0));
     1084
     1085    GST_OBJECT_LOCK(m_src);
     1086    uri.set(g_strdup(m_src->priv->uri));
     1087    GST_OBJECT_UNLOCK(m_src);
     1088
     1089    GST_ELEMENT_ERROR(m_src, RESOURCE, OPEN_READ, ("Can't show \"%s\"", uri.get()), (0));
    9721090}
    9731091
Note: See TracChangeset for help on using the changeset viewer.