diff options
author | Iain Merrick <husky@google.com> | 2010-10-28 10:39:47 +0100 |
---|---|---|
committer | Iain Merrick <husky@google.com> | 2010-10-28 13:48:51 +0100 |
commit | d4a869207d9c64cff5a8ac08cd9cddf473360504 (patch) | |
tree | cdc08af537c0f364c1ff290e70754eb3c7faaabb /WebKit/android/WebCoreSupport | |
parent | bf3f67c4fcfd68df256e5c001c67969997a63e28 (diff) | |
download | external_webkit-d4a869207d9c64cff5a8ac08cd9cddf473360504.zip external_webkit-d4a869207d9c64cff5a8ac08cd9cddf473360504.tar.gz external_webkit-d4a869207d9c64cff5a8ac08cd9cddf473360504.tar.bz2 |
Use Tasks for WebRequest -> WebUrlLoaderClient callbacks.
We were using some hand-rolled boilerplate for inter-thread communication,
with all data packed into the same LoaderData struct. This CL uses the
Chromium utility function NewRunnableMethod to pack up the parameters, so
the callback methods don't have to be static and can have different
parameters. Also using smart pointers wherever possible.
Testing: manually verified that both synchronous and asynchronous requests
work correctly with no leaks. Will also do stress-testing to check for
race conditions.
Change-Id: I934a2ee795138f8eee43803a94bb7494ee73031d
Diffstat (limited to 'WebKit/android/WebCoreSupport')
-rw-r--r-- | WebKit/android/WebCoreSupport/WebRequest.cpp | 78 | ||||
-rw-r--r-- | WebKit/android/WebCoreSupport/WebRequest.h | 4 | ||||
-rw-r--r-- | WebKit/android/WebCoreSupport/WebUrlLoader.h | 3 | ||||
-rw-r--r-- | WebKit/android/WebCoreSupport/WebUrlLoaderClient.cpp | 140 | ||||
-rw-r--r-- | WebKit/android/WebCoreSupport/WebUrlLoaderClient.h | 65 |
5 files changed, 106 insertions, 184 deletions
diff --git a/WebKit/android/WebCoreSupport/WebRequest.cpp b/WebKit/android/WebCoreSupport/WebRequest.cpp index ec6dce1..cefd541 100644 --- a/WebKit/android/WebCoreSupport/WebRequest.cpp +++ b/WebKit/android/WebCoreSupport/WebRequest.cpp @@ -103,17 +103,21 @@ void WebRequest::finish(bool success) { ASSERT(m_loadState < Finished, "called finish on an already finished WebRequest (%d)", m_loadState); + // Make sure WebUrlLoaderClient doesn't delete us in the middle of this method. + scoped_refptr<WebRequest> guard(this); + m_loadState = Finished; if (success) { - LoaderData* loaderData = new LoaderData(m_urlLoader); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didFinishLoading, loaderData); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didFinishLoading)); } else { - WebResponse webResponse(m_request.get()); - LoaderData* loaderData = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didFail, loaderData); + OwnPtr<WebResponse> webResponse(new WebResponse(m_request.get())); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didFail, webResponse.release())); } m_networkBuffer = 0; m_request = 0; + m_urlLoader = 0; } void WebRequest::AppendBytesToUpload(WTF::Vector<char>* data) @@ -170,9 +174,9 @@ void WebRequest::handleAndroidURL() JNIEnv* env = JSC::Bindings::getJNIEnv(); if (m_inputStream == 0) { m_loadState = Finished; - WebResponse webResponse(m_url, "", 0, "", 0); - LoaderData* loaderData = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didFail, loaderData); + OwnPtr<WebResponse> webResponse(new WebResponse(m_url, "", 0, "", 0)); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didFail, webResponse.release())); return; } @@ -180,9 +184,9 @@ void WebRequest::handleAndroidURL() FilePath path(m_url); std::string mimeType(""); net::GetMimeTypeFromFile(path, &mimeType); - WebResponse webResponse(m_url, mimeType, 0, "", 200); - LoaderData* loaderResponse = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveResponse, loaderResponse); + OwnPtr<WebResponse> webResponse(new WebResponse(m_url, mimeType, 0, "", 200)); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveResponse, webResponse.release())); int size = 0; jclass bridgeClass = env->FindClass("android/webkit/BrowserFrame"); @@ -196,14 +200,12 @@ void WebRequest::handleAndroidURL() // data is deleted in WebUrlLoaderClient::didReceiveAndroidFileData // data is sent to the webcore thread - std::vector<char>* data = new std::vector<char>(); - data->reserve(size); + OwnPtr<std::vector<char> > data(new std::vector<char>(size)); env->GetByteArrayRegion(jb, 0, size, (jbyte*)&data->front()); m_loadState = GotData; - // Passes ownership of data - LoaderData* loaderData = new LoaderData(m_urlLoader, data, size); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveAndroidFileData, loaderData); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveAndroidFileData, data.release())); } while (true); env->DeleteLocalRef(jb); @@ -214,7 +216,7 @@ void WebRequest::handleAndroidURL() void WebRequest::handleDataURL(GURL url) { - OwnPtr<std::string*> data(new std::string); + OwnPtr<std::string> data(new std::string); std::string mimeType; std::string charset; @@ -222,14 +224,14 @@ void WebRequest::handleDataURL(GURL url) // PopulateURLResponse from chrome implementation // weburlloader_impl.cc m_loadState = Response; - WebResponse webResponse(url.spec(), mimeType, data->size(), charset, 200); - LoaderData* loaderResponse = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveResponse, loaderResponse); + OwnPtr<WebResponse> webResponse(new WebResponse(url.spec(), mimeType, data->size(), charset, 200)); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveResponse, webResponse.release())); if (!data->empty()) { m_loadState = GotData; - LoaderData* loaderData = new LoaderData(m_urlLoader, data.leakPtr()); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveDataUrl, loaderData); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveDataUrl, data.release())); } } else { // handle the failed case @@ -274,10 +276,10 @@ void WebRequest::OnReceivedRedirect(URLRequest* newRequest, const GURL& newUrl, ASSERT(m_loadState < Response, "Redirect after receiving response"); if (newRequest && newRequest->status().is_success()) { - WebResponse webResponse(newRequest); - webResponse.setUrl(newUrl.spec()); - LoaderData* ld = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::willSendRequest, ld); + OwnPtr<WebResponse> webResponse(new WebResponse(newRequest)); + webResponse->setUrl(newUrl.spec()); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::willSendRequest, webResponse.release())); } else { // why would this happen? And what to do? } @@ -297,9 +299,9 @@ void WebRequest::OnAuthRequired(URLRequest* request, net::AuthChallengeInfo* aut { ASSERT(m_loadState == Started, "OnAuthRequired called on a WebRequest not in STARTED state (state=%d)", m_loadState); - LoaderData* ld = new LoaderData(m_urlLoader); - ld->authChallengeInfo = authInfo; - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::authRequired, ld); + scoped_refptr<net::AuthChallengeInfo> authInfoPtr(authInfo); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::authRequired, authInfoPtr)); } // After calling Start(), the delegate will receive an OnResponseStarted @@ -314,9 +316,9 @@ void WebRequest::OnResponseStarted(URLRequest* request) m_loadState = Response; if (request && request->status().is_success()) { - WebResponse webResponse(request); - LoaderData* loaderData = new LoaderData(m_urlLoader, webResponse); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveResponse, loaderData); + OwnPtr<WebResponse> webResponse(new WebResponse(request)); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveResponse, webResponse.release())); // Start reading the response startReading(); @@ -367,10 +369,8 @@ void WebRequest::startReading() m_loadState = GotData; // Read ok, forward buffer to webcore - m_networkBuffer->AddRef(); - LoaderData* loaderData = new LoaderData(m_urlLoader, m_networkBuffer.get(), bytesRead); - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveData, loaderData); - // m_networkBuffer->Release() on main thread + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveData, m_networkBuffer, bytesRead)); m_networkBuffer = 0; } else if (m_request && m_request->status().is_io_pending()) { // got io_pending, so break and wait for read @@ -408,10 +408,8 @@ void WebRequest::OnReadCompleted(URLRequest* request, int bytesRead) if (request->status().is_success()) { m_loadState = GotData; - m_networkBuffer->AddRef(); - LoaderData* loaderData = new LoaderData(m_urlLoader, m_networkBuffer.get(), bytesRead); - // m_networkBuffer->Release() on main thread - m_urlLoader->maybeCallOnMainThread(WebUrlLoaderClient::didReceiveData, loaderData); + m_urlLoader->maybeCallOnMainThread(NewRunnableMethod( + m_urlLoader.get(), &WebUrlLoaderClient::didReceiveData, m_networkBuffer, bytesRead)); m_networkBuffer = 0; // Get the rest of the data diff --git a/WebKit/android/WebCoreSupport/WebRequest.h b/WebKit/android/WebCoreSupport/WebRequest.h index e52425a..b96126b 100644 --- a/WebKit/android/WebCoreSupport/WebRequest.h +++ b/WebKit/android/WebCoreSupport/WebRequest.h @@ -87,9 +87,7 @@ private: void handleAndroidURL(); void finish(bool success); - // Not owned - WebUrlLoaderClient* m_urlLoader; - + scoped_refptr<WebUrlLoaderClient> m_urlLoader; OwnPtr<URLRequest> m_request; scoped_refptr<net::IOBuffer> m_networkBuffer; int m_inputStream; diff --git a/WebKit/android/WebCoreSupport/WebUrlLoader.h b/WebKit/android/WebCoreSupport/WebUrlLoader.h index 7106ede..2e76c14 100644 --- a/WebKit/android/WebCoreSupport/WebUrlLoader.h +++ b/WebKit/android/WebCoreSupport/WebUrlLoader.h @@ -26,6 +26,7 @@ #ifndef WebUrlLoader_h #define WebUrlLoader_h +#include "ChromiumIncludes.h" #include "ResourceLoaderAndroid.h" using namespace WebCore; @@ -47,7 +48,7 @@ private: WebUrlLoader(WebFrame*, WebCore::ResourceHandle*, const WebCore::ResourceRequest&); static PassRefPtr<WebUrlLoader> create(WebFrame*, WebCore::ResourceHandle*, const WebCore::ResourceRequest&); - OwnPtr<WebUrlLoaderClient> m_loaderClient; + scoped_refptr<WebUrlLoaderClient> m_loaderClient; }; } // namespace android diff --git a/WebKit/android/WebCoreSupport/WebUrlLoaderClient.cpp b/WebKit/android/WebCoreSupport/WebUrlLoaderClient.cpp index 87a76a4..e6c06af 100644 --- a/WebKit/android/WebCoreSupport/WebUrlLoaderClient.cpp +++ b/WebKit/android/WebCoreSupport/WebUrlLoaderClient.cpp @@ -37,12 +37,6 @@ namespace android { -LoaderData::~LoaderData() -{ - if (buffer) - buffer->Release(); -} - base::Thread* WebUrlLoaderClient::ioThread() { static base::Thread* networkThread = 0; @@ -77,9 +71,6 @@ ConditionVariable* WebUrlLoaderClient::syncCondition() { WebUrlLoaderClient::~WebUrlLoaderClient() { - base::Thread* thread = ioThread(); - if (thread) - thread->message_loop()->ReleaseSoon(FROM_HERE, m_request); } bool WebUrlLoaderClient::isActive() const @@ -103,12 +94,10 @@ WebUrlLoaderClient::WebUrlLoaderClient(WebFrame* webFrame, WebCore::ResourceHand if (webResourceRequest.isAndroidUrl()) { int inputStream = webFrame->inputStreamForAndroidResource(webResourceRequest.url().c_str(), webResourceRequest.androidFileType()); m_request = new WebRequest(this, webResourceRequest, inputStream); - m_request->AddRef(); // Matched by ReleaseSoon in destructor return; } m_request = new WebRequest(this, webResourceRequest); - m_request->AddRef(); // Matched by ReleaseSoon in destructor // Set uploads before start is called on the request if (resourceRequest.httpBody() && !(webResourceRequest.method() == "GET" || webResourceRequest.method() == "HEAD")) { @@ -124,7 +113,7 @@ WebUrlLoaderClient::WebUrlLoaderClient(WebFrame* webFrame, WebCore::ResourceHand base::Thread* thread = ioThread(); if (thread) { Vector<char>* data = new Vector<char>(element.m_data); - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::AppendBytesToUpload, data)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::AppendBytesToUpload, data)); } } break; @@ -156,16 +145,14 @@ bool WebUrlLoaderClient::start(bool sync, bool isPrivateBrowsing) m_sync = sync; if (m_sync) { AutoLock autoLock(*syncLock()); - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::start, isPrivateBrowsing)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::start, isPrivateBrowsing)); // Run callbacks until the queue is exhausted and m_finished is true. while(!m_finished) { while (!m_queue.empty()) { - Callback& callback = m_queue.front(); - CallbackFunction* function = callback.a; - void* context = callback.b; - (*function)(context); + OwnPtr<Task> task(m_queue.front()); m_queue.pop_front(); + task->Run(); } if (m_queue.empty() && !m_finished) { syncCondition()->Wait(); @@ -177,7 +164,7 @@ bool WebUrlLoaderClient::start(bool sync, bool isPrivateBrowsing) m_resourceHandle = 0; } else { // Asynchronous start. - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::start, isPrivateBrowsing)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::start, isPrivateBrowsing)); } return true; } @@ -193,7 +180,7 @@ void WebUrlLoaderClient::cancel() base::Thread* thread = ioThread(); if (thread) - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::cancel)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::cancel)); } void WebUrlLoaderClient::setAuth(const std::string& username, const std::string& password) @@ -204,7 +191,7 @@ void WebUrlLoaderClient::setAuth(const std::string& username, const std::string& } string16 username16 = ASCIIToUTF16(username); string16 password16 = ASCIIToUTF16(password); - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::setAuth, username16, password16)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::setAuth, username16, password16)); } void WebUrlLoaderClient::cancelAuth() @@ -213,7 +200,7 @@ void WebUrlLoaderClient::cancelAuth() if (!thread) { return; } - thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request, &WebRequest::cancelAuth)); + thread->message_loop()->PostTask(FROM_HERE, NewRunnableMethod(m_request.get(), &WebRequest::cancelAuth)); } void WebUrlLoaderClient::finish() @@ -224,133 +211,106 @@ void WebUrlLoaderClient::finish() // We only release the reference here if start() was called asynchronously! m_resourceHandle = 0; } + m_request = 0; +} + +namespace { +// Trampoline to wrap a Chromium Task* in a WebKit-style static function + void*. +static void RunTask(void* v) { + OwnPtr<Task> task(static_cast<Task*>(v)); + task->Run(); +} } // This is called from the IO thread, and dispatches the callback to the main thread. -void WebUrlLoaderClient::maybeCallOnMainThread(CallbackFunction* function, void* context) +void WebUrlLoaderClient::maybeCallOnMainThread(Task* task) { if (m_sync) { AutoLock autoLock(*syncLock()); if (m_queue.empty()) { syncCondition()->Broadcast(); } - m_queue.push_back(Callback(function, context)); + m_queue.push_back(task); } else { // Let WebKit handle it. - callOnMainThread(function, context); + callOnMainThread(RunTask, task); } } // Response methods -// static - on main thread -void WebUrlLoaderClient::didReceiveResponse(void* data) +void WebUrlLoaderClient::didReceiveResponse(PassOwnPtr<WebResponse> webResponse) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - const WebUrlLoaderClient* loader = loaderData->loader; - WebResponse webResponse = loaderData->webResponse; - - if (!loader->isActive()) + if (!isActive()) return; - loader->m_resourceHandle->client()->didReceiveResponse(loader->m_resourceHandle.get(), webResponse.createResourceResponse()); + m_resourceHandle->client()->didReceiveResponse(m_resourceHandle.get(), webResponse->createResourceResponse()); } -// static - on main thread -void WebUrlLoaderClient::didReceiveData(void* data) +void WebUrlLoaderClient::didReceiveData(scoped_refptr<net::IOBuffer> buf, int size) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - const WebUrlLoaderClient* loader = loaderData->loader; - net::IOBuffer* buf = loaderData->buffer; - - if (!loader->isActive()) + if (!isActive()) return; // didReceiveData will take a copy of the data - if (loader->m_resourceHandle && loader->m_resourceHandle->client()) - loader->m_resourceHandle->client()->didReceiveData(loader->m_resourceHandle.get(), buf->data(), loaderData->size, loaderData->size); + if (m_resourceHandle && m_resourceHandle->client()) + m_resourceHandle->client()->didReceiveData(m_resourceHandle.get(), buf->data(), size, size); } -// static - on main thread // For data url's -void WebUrlLoaderClient::didReceiveDataUrl(void* data) +void WebUrlLoaderClient::didReceiveDataUrl(PassOwnPtr<std::string> str) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - const WebUrlLoaderClient* loader = loaderData->loader; - - if (!loader->isActive()) + if (!isActive()) return; - std::string* str = loaderData->string.get(); // didReceiveData will take a copy of the data - loader->m_resourceHandle->client()->didReceiveData(loader->m_resourceHandle.get(), str->data(), str->size(), str->size()); + m_resourceHandle->client()->didReceiveData(m_resourceHandle.get(), str->data(), str->size(), str->size()); } -// static - on main thread // For special android files -void WebUrlLoaderClient::didReceiveAndroidFileData(void* data) +void WebUrlLoaderClient::didReceiveAndroidFileData(PassOwnPtr<std::vector<char> > vector) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - const WebUrlLoaderClient* loader = loaderData->loader; - - if (!loader->isActive()) + if (!isActive()) return; // didReceiveData will take a copy of the data - loader->m_resourceHandle->client()->didReceiveData(loader->m_resourceHandle.get(), &(loaderData->vector->front()), loaderData->size, loaderData->size); + m_resourceHandle->client()->didReceiveData(m_resourceHandle.get(), vector->begin(), vector->size(), vector->size()); } -// static - on main thread -void WebUrlLoaderClient::didFail(void* data) +void WebUrlLoaderClient::didFail(PassOwnPtr<WebResponse> webResponse) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - WebUrlLoaderClient* loader = loaderData->loader; - - if (loader->isActive()) - loader->m_resourceHandle->client()->didFail(loader->m_resourceHandle.get(), loaderData->webResponse.createResourceError()); + if (isActive()) + m_resourceHandle->client()->didFail(m_resourceHandle.get(), webResponse->createResourceError()); // Always finish a request, if not it will leak - loader->finish(); + finish(); } -// static - on main thread -void WebUrlLoaderClient::willSendRequest(void* data) +void WebUrlLoaderClient::willSendRequest(PassOwnPtr<WebResponse> webResponse) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - const WebUrlLoaderClient* loader = loaderData->loader; - - if (!loader->isActive()) + if (!isActive()) return; - WebResponse webResponse = loaderData->webResponse; - OwnPtr<WebCore::ResourceRequest> resourceRequest(new WebCore::ResourceRequest(webResponse.url())); - loader->m_resourceHandle->client()->willSendRequest(loader->m_resourceHandle.get(), *resourceRequest, webResponse.createResourceResponse()); + OwnPtr<WebCore::ResourceRequest> resourceRequest(new WebCore::ResourceRequest(webResponse->url())); + m_resourceHandle->client()->willSendRequest(m_resourceHandle.get(), *resourceRequest, webResponse->createResourceResponse()); } -// static - on main thread -void WebUrlLoaderClient::didFinishLoading(void* data) +void WebUrlLoaderClient::didFinishLoading() { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - WebUrlLoaderClient* loader = loaderData->loader; - - if (loader->isActive()) - loader->m_resourceHandle->client()->didFinishLoading(loader->m_resourceHandle.get(), 0); + if (isActive()) + m_resourceHandle->client()->didFinishLoading(m_resourceHandle.get(), 0); // Always finish a request, if not it will leak - loader->finish(); + finish(); } -// static - on main thread -void WebUrlLoaderClient::authRequired(void* data) +void WebUrlLoaderClient::authRequired(scoped_refptr<net::AuthChallengeInfo> authChallengeInfo) { - OwnPtr<LoaderData> loaderData(static_cast<LoaderData*>(data)); - WebUrlLoaderClient* loader = loaderData->loader; - - if (!loader->isActive()) { + if (!isActive()) { return; } - std::string host = base::SysWideToUTF8(loaderData->authChallengeInfo->host_and_port); - std::string realm = base::SysWideToUTF8(loaderData->authChallengeInfo->realm); + std::string host = base::SysWideToUTF8(authChallengeInfo->host_and_port); + std::string realm = base::SysWideToUTF8(authChallengeInfo->realm); // TODO: Not clear whose responsibility it is to cache credentials. There's nothing // in AuthChallengeInfo that seems suitable, so for safety we'll tell the UI *not* @@ -358,7 +318,7 @@ void WebUrlLoaderClient::authRequired(void* data) // the first call, then "false" for a second call if the credentials are rejected). bool useCachedCredentials = false; - loader->m_webFrame->didReceiveAuthenticationChallenge(loader, host, realm, useCachedCredentials); + m_webFrame->didReceiveAuthenticationChallenge(this, host, realm, useCachedCredentials); } } // namespace android diff --git a/WebKit/android/WebCoreSupport/WebUrlLoaderClient.h b/WebKit/android/WebCoreSupport/WebUrlLoaderClient.h index b568c91..d038489 100644 --- a/WebKit/android/WebCoreSupport/WebUrlLoaderClient.h +++ b/WebKit/android/WebCoreSupport/WebUrlLoaderClient.h @@ -60,10 +60,9 @@ class WebRequest; // - Implement sync requests // - Implement downloadFile // - Implement pauseLoad -class WebUrlLoaderClient { +class WebUrlLoaderClient : public base::RefCountedThreadSafe<WebUrlLoaderClient> { public: WebUrlLoaderClient(WebFrame*, WebCore::ResourceHandle*, const WebCore::ResourceRequest&); - ~WebUrlLoaderClient(); // Called from WebCore, will be forwarded to the IO thread bool start(bool sync, bool isPrivateBrowsing); @@ -77,22 +76,25 @@ public: // This is called from the IO thread, and dispatches the callback to the main thread. // (For asynchronous calls, we just delegate to WebKit's callOnMainThread.) - void maybeCallOnMainThread(CallbackFunction*, void* context); + void maybeCallOnMainThread(Task* task); // Called by WebRequest (using maybeCallOnMainThread), should be forwarded to WebCore. - static void didReceiveResponse(void*); - static void didReceiveData(void*); - static void didReceiveDataUrl(void*); - static void didReceiveAndroidFileData(void*); - static void didFinishLoading(void*); - static void didFail(void*); - static void willSendRequest(void*); - static void authRequired(void*); + void didReceiveResponse(PassOwnPtr<WebResponse>); + void didReceiveData(scoped_refptr<net::IOBuffer>, int size); + void didReceiveDataUrl(PassOwnPtr<std::string>); + void didReceiveAndroidFileData(PassOwnPtr<std::vector<char> >); + void didFinishLoading(); + void didFail(PassOwnPtr<WebResponse>); + void willSendRequest(PassOwnPtr<WebResponse>); + void authRequired(scoped_refptr<net::AuthChallengeInfo>); // Handle to the chrome IO thread static base::Thread* ioThread(); private: + friend class base::RefCountedThreadSafe<WebUrlLoaderClient>; + virtual ~WebUrlLoaderClient(); + void finish(); WebFrame* m_webFrame; @@ -101,8 +103,7 @@ private: bool m_sync; volatile bool m_finished; - // Not an OwnPtr since it should be deleted on another thread - WebRequest* m_request; + scoped_refptr<WebRequest> m_request; // Check if a request is active bool isActive() const; @@ -112,44 +113,8 @@ private: static Lock* syncLock(); static ConditionVariable* syncCondition(); - typedef Tuple2<CallbackFunction*, void*> Callback; - typedef std::deque<Callback> CallbackQueue; - // Queue of callbacks to be executed by the main thread. Must only be accessed inside mutex. - CallbackQueue m_queue; -}; - -// A struct to send more than one thing in a void*, needed for maybeCallOnMainThread -struct LoaderData { - net::IOBuffer* buffer; - WebUrlLoaderClient* loader; - WebResponse webResponse; - const int size; - OwnPtr<std::string*> string; - OwnPtr<std::vector<char> > vector; - scoped_refptr<net::AuthChallengeInfo> authChallengeInfo; - - LoaderData(WebUrlLoaderClient* l) : buffer(0), loader(l), size(0) - { - } - - LoaderData(WebUrlLoaderClient* l, std::string* s) : buffer(0), loader(l), size(0), string(s) - { - } - - LoaderData(WebUrlLoaderClient* l, WebResponse r) : buffer(0), loader(l), webResponse(r), size(0) - { - } - - LoaderData(WebUrlLoaderClient* l, net::IOBuffer* b, const int s) : buffer(b), loader(l), size(s) - { - } - - LoaderData(WebUrlLoaderClient* l, std::vector<char>* data, const int s) : buffer(0), loader(l), size(s), vector(data) - { - } - - ~LoaderData(); + std::deque<Task*> m_queue; }; } // namespace android |