I found this reference: http://www.mozilla.org/projects/xpcom/Proxies.html

I'll check and test it.


Maciste wrote:

Hello Kevin,

I think you're right. It's a "thread safety" problem. In COM we have to use proxies to send (with data marshalling) events to objects on others threads, so I think XPCOM have something like COM. For now, I have only a glue:

nsIProxyObjectManager

  Anyone know nsIProxyObjectManager and how to use it?


Kevin Strong wrote:

Those look like the EXACT same errors I am getting in my own component! In
mine, nsIDOMHTMLInputElement::Click and nsIWebNavigation::LoadURI are
crashing in the same way. I have spent days debugging and searching for
answers, and I am pretty much 99.9% certain that the reason for these errors
is that none of the XPCOM components are thread-safe (and that fact that
both of us are getting similar crashes from XPCOM components called from
worker threads proves this is a serious issue).
So, basically the only solution I know of to this is to not call the
functions that are crashing in your thread. I know it sucks, but that is
what you will have to do. I recommend finding some way to call all the
non-thread safe methods of your components (i.e. the ones crashing when you call them from your worker thread) in the main thread. A possible solution I looked into was having my worker thread use the nsIObserverService to tell
the main component to do what it needs to do, however,
nsIObserverService::NotifyObservers is also not thread safe (and crashed in
the same way)! I'm not to sure if there are any other workarounds, at the
moment the best option I see is a dirty hack using a timer that checks a
global variable to see when the worker threads needs something to be done, however in my eyes this is a less than ideal solution. Anyone else have any
ideas?

-----Original Message-----
From: [EMAIL PROTECTED]
[mailto:[EMAIL PROTECTED] On Behalf Of Maciste
Sent: Thursday, August 25, 2005 11:08 AM
To: [email protected]
Subject: nsIChannel::Open access violation

Hi,

     I'm getting an "access violation" erro calling nsIChannel::Open:

First-chance exception at 0x00455eb7 in firefox.exe: 0xC0000005: Access violation reading location 0x00000000. Unhandled exception at 0x00455eb7 in firefox.exe: 0xC0000005: Access violation reading location 0x00000000.

     Details:

1) It's C++ component, called from javascript
2) When called, the component starts a background task using PR_CreateThread passing its reference ("this" pointer)
3) The thread uses the received reference to call a component's method
4) This method uses nsIChannel::Open to download some data. At this moment I receive an "access violation".

     Obs:

1) I get the same error with nsIChannel::AsyncOpen
2) If I call nsIChannel::Open on the same thread, there is no problem.

     Is there any restrictions on using nsIChannel::AsyncOpen/OPen
on differents threads ? Is there any workaround ?

Thanks,

Maciste


PS.: Callstack and code snipet:

=================================================
firefox.exe!00455eb7() firefox.exe!00455e78() firefox.exe!004438eb() firefox.exe!004ab26f() xpcom.dll!6030d246() firefox.exe!004536bc() firefox.exe!0047db77() firefox.exe!004823e0() firefox.exe!00478f53() firefox.exe!0049801e() > XPComRssReader.dll!CRssHttp::Get(std::basic_string<char,std::char_traits<cha r>,std::allocator<char> > sUrl={...}, std::basic_string<char,std::char_traits<char>,std::allocator<char> > & sData={...}) Line 304 + 0x3b C++ XPComRssReader.dll!CFeeder::LoadFromUrl(std::basic_string<char,std::char_tra its<char>,std::allocator<char> > sUrl={...}, std::basic_string<char,std::char_traits<char>,std::allocator<char> > sCookie={...}) Line 375 + 0x28 C++
      XPComRssReader.dll!CFeeder::Refresh()  Line 458 + 0x50    C++
XPComRssReader.dll!CRssReader::Refresh(int nBatch=5) Line 987 + 0x8
C++
XPComRssReader.dll!CRssReaderWrapper::WorkThread(void * param=0x027d5df8) Line 972 C++ nspr4.dll!60144c21() ntdll.dll!7c96e0d4() nspr4.dll!60146d4b() msvcrt.dll!77c3a3b0() ntdll.dll!7c96e0d4() kernel32.dll!7c80b50b() ntdll.dll!7c96e0d4() kernel32.dll!7c8399f3() ================================================

    nsCOMPtr<nsIServiceManager> servMan;
    nsCOMPtr<nsIComponentManager> compMan;
    nsCOMPtr<nsIIOService> ioService;

    nsCOMPtr<nsIInputStream> inputStream;
    nsCOMPtr<nsIChannel> channel;
    nsCOMPtr<nsIHttpChannel> http_channel;
    nsEmbedCString sRequestMethod("GET");
    nsCOMPtr<nsIURI> ext_uri;
    nsEmbedCString uri_str(sUrl.c_str());
    nsEmbedCString asScheme;
    string    sScheme;

    nsCOMPtr<nsIStreamListener> streamListener;
    nsCOMPtr<nsIXMLHttpRequest> xmlRequest;
    nsEmbedString asData;
    nsEmbedCString ascData;

    nsresult rv = NS_GetServiceManager(getter_AddRefs(servMan));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }

rv = NS_GetComponentManager(getter_AddRefs(compMan));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }


rv = servMan->GetServiceByContractID("@mozilla.org/network/io-service;1", NS_GET_IID(nsIIOService), getter_AddRefs(ioService));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }

    rv = ioService->NewURI(uri_str, nsnull,  nsnull,
getter_AddRefs(ext_uri));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }

    PRBool bIsHttp, bIsHttps;
    rv = ext_uri->SchemeIs("http", &bIsHttp);
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }
    rv = ext_uri->SchemeIs("https", &bIsHttps);
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }

    if(!bIsHttp && !bIsHttps)
    {
        lRet = ERR_INVALID_PROTOCOL;
        goto final;
    }

    rv = ioService->NewChannelFromURI(ext_uri, getter_AddRefs(channel));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }

    http_channel = do_QueryInterface(channel);

    http_channel->SetRedirectionLimit(0);
http_channel->SetRequestMethod(sRequestMethod);


//HERE, ACCESS VIOLATION
rv = channel->Open(getter_AddRefs(inputStream));//AsyncOpen(static_cast< nsIStreamListener* >(this), static_cast< nsISupports* >(this));
    if (NS_FAILED(rv))
    {
        lRet = ERR_CONNECTION_FAILED;
        goto final;
    }





_______________________________________________
Mozilla-xpcom mailing list
[email protected]
http://mail.mozilla.org/listinfo/mozilla-xpcom


_______________________________________________
Mozilla-xpcom mailing list
[email protected]
http://mail.mozilla.org/listinfo/mozilla-xpcom

Reply via email to