summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authordarin@chromium.org <darin@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-02-09 22:41:20 +0000
committerdarin@chromium.org <darin@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-02-09 22:41:20 +0000
commit3dbb80bca45a4fdf674250ed833842a71de41838 (patch)
tree46a087293623a29e8bb2a2b8e1567be6ac177c02
parent76477871b30938124add005d5df27c0ffb544ee4 (diff)
downloadchromium_src-3dbb80bca45a4fdf674250ed833842a71de41838.zip
chromium_src-3dbb80bca45a4fdf674250ed833842a71de41838.tar.gz
chromium_src-3dbb80bca45a4fdf674250ed833842a71de41838.tar.bz2
Trigger the blocked cookie notification UI.
This change involves two significant bits: 1- Add URLRequest::Delegate methods to report a blocked attempt to set a cookie or get cookies, respectively. 2- Generalize the mechanisms we use to proxy notifications to the RenderViewHost from the IO thread. See render_view_host_notification_task.h. Finally, these are used together in ResourceDispatcherHost. Note: Additional work is required to notify when JS attempts to set a cookie fail. R=brettw,eroman BUG=34573 TEST=Configure the browser to block cookies, and then visit a site that tries to set a cookie (e.g., cnn.com). You should see a cookie icon appear in the location bar. If you click that it should report that cookies were blocked. Review URL: http://codereview.chromium.org/600009 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@38527 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--base/task.h2
-rw-r--r--chrome/browser/renderer_host/cross_site_resource_handler.cc76
-rw-r--r--chrome/browser/renderer_host/render_view_host.cc10
-rw-r--r--chrome/browser/renderer_host/render_view_host.h5
-rw-r--r--chrome/browser/renderer_host/render_view_host_delegate.h10
-rw-r--r--chrome/browser/renderer_host/render_view_host_notification_task.h237
-rw-r--r--chrome/browser/renderer_host/resource_dispatcher_host.cc159
-rw-r--r--chrome/browser/renderer_host/resource_dispatcher_host.h1
-rw-r--r--chrome/browser/renderer_host/resource_request_details.h2
-rw-r--r--chrome/browser/tab_contents/tab_contents.cc14
-rw-r--r--chrome/browser/tab_contents/tab_contents.h5
-rw-r--r--net/url_request/url_request.h8
-rw-r--r--net/url_request/url_request_http_job.cc25
-rw-r--r--net/url_request/url_request_unittest.cc129
-rw-r--r--net/url_request/url_request_unittest.h28
15 files changed, 494 insertions, 217 deletions
diff --git a/base/task.h b/base/task.h
index d71df20..cbb8c99 100644
--- a/base/task.h
+++ b/base/task.h
@@ -649,7 +649,7 @@ typename Callback5<Arg1, Arg2, Arg3, Arg4, Arg5>::Type* NewCallback(
template <class T, class Method, class Params>
class UnboundMethod {
public:
- UnboundMethod(Method m, Params p) : m_(m), p_(p) {
+ UnboundMethod(Method m, const Params& p) : m_(m), p_(p) {
COMPILE_ASSERT((MethodUsesScopedRefptrCorrectly<Method, Params>::value),
badunboundmethodparams);
}
diff --git a/chrome/browser/renderer_host/cross_site_resource_handler.cc b/chrome/browser/renderer_host/cross_site_resource_handler.cc
index e178cf1..876547e 100644
--- a/chrome/browser/renderer_host/cross_site_resource_handler.cc
+++ b/chrome/browser/renderer_host/cross_site_resource_handler.cc
@@ -11,66 +11,11 @@
#include "chrome/browser/renderer_host/global_request_id.h"
#include "chrome/browser/renderer_host/render_view_host.h"
#include "chrome/browser/renderer_host/render_view_host_delegate.h"
+#include "chrome/browser/renderer_host/render_view_host_notification_task.h"
#include "chrome/browser/renderer_host/resource_dispatcher_host.h"
#include "chrome/browser/renderer_host/resource_dispatcher_host_request_info.h"
#include "net/base/io_buffer.h"
-namespace {
-
-// Task to notify the TabContents that a cross-site response has begun, so that
-// TabContents can tell the old page to run its onunload handler.
-class CrossSiteNotifyTask : public Task {
- public:
- CrossSiteNotifyTask(int render_process_host_id,
- int render_view_id,
- int request_id)
- : render_process_host_id_(render_process_host_id),
- render_view_id_(render_view_id),
- request_id_(request_id) {}
-
- void Run() {
- RenderViewHost* view =
- RenderViewHost::FromID(render_process_host_id_, render_view_id_);
- if (view) {
- view->OnCrossSiteResponse(render_process_host_id_, request_id_);
- } else {
- // The view couldn't be found.
- // TODO(creis): Should notify the IO thread to proceed anyway, using
- // ResourceDispatcherHost::OnClosePageACK.
- }
- }
-
- private:
- int render_process_host_id_;
- int render_view_id_;
- int request_id_;
-};
-
-class CancelPendingRenderViewTask : public Task {
- public:
- CancelPendingRenderViewTask(int render_process_host_id,
- int render_view_id)
- : render_process_host_id_(render_process_host_id),
- render_view_id_(render_view_id) {}
-
- void Run() {
- RenderViewHost* view =
- RenderViewHost::FromID(render_process_host_id_, render_view_id_);
- if (view) {
- RenderViewHostDelegate::RendererManagement* management_delegate =
- view->delegate()->GetRendererManagementDelegate();
- if (management_delegate)
- management_delegate->OnCrossSiteNavigationCanceled();
- }
- }
-
- private:
- int render_process_host_id_;
- int render_view_id_;
-};
-
-} // namespace
-
CrossSiteResourceHandler::CrossSiteResourceHandler(
ResourceHandler* handler,
int render_process_host_id,
@@ -162,10 +107,10 @@ bool CrossSiteResourceHandler::OnResponseCompleted(
// Here the request was canceled, which happens when selecting "take me
// back" from an interstitial. Nothing to do but cancel the pending
// render view host.
- ChromeThread::PostTask(
- ChromeThread::UI, FROM_HERE,
- new CancelPendingRenderViewTask(
- render_process_host_id_, render_view_id_));
+ CallRenderViewHostRendererManagementDelegate(
+ render_process_host_id_, render_view_id_,
+ &RenderViewHostDelegate::RendererManagement::
+ OnCrossSiteNavigationCanceled);
return next_handler_->OnResponseCompleted(request_id, status,
security_info);
} else {
@@ -265,8 +210,11 @@ void CrossSiteResourceHandler::StartCrossSiteTransition(
// Tell the tab responsible for this request that a cross-site response is
// starting, so that it can tell its old renderer to run its onunload
// handler now. We will wait to hear the corresponding ClosePage_ACK.
- ChromeThread::PostTask(
- ChromeThread::UI, FROM_HERE,
- new CrossSiteNotifyTask(
- render_process_host_id_, render_view_id_, request_id));
+ CallRenderViewHostRendererManagementDelegate(
+ render_process_host_id_, render_view_id_,
+ &RenderViewHostDelegate::RendererManagement::OnCrossSiteResponse,
+ render_process_host_id_, request_id);
+
+ // TODO(creis): If the above call should fail, then we need to notify the IO
+ // thread to proceed anyway, using ResourceDispatcherHost::OnClosePageACK.
}
diff --git a/chrome/browser/renderer_host/render_view_host.cc b/chrome/browser/renderer_host/render_view_host.cc
index 89a2093..e235f50 100644
--- a/chrome/browser/renderer_host/render_view_host.cc
+++ b/chrome/browser/renderer_host/render_view_host.cc
@@ -356,16 +356,6 @@ int RenderViewHost::GetPendingRequestId() {
return pending_request_id_;
}
-void RenderViewHost::OnCrossSiteResponse(int new_render_process_host_id,
- int new_request_id) {
- RenderViewHostDelegate::RendererManagement* management_delegate =
- delegate_->GetRendererManagementDelegate();
- if (management_delegate) {
- management_delegate->OnCrossSiteResponse(new_render_process_host_id,
- new_request_id);
- }
-}
-
void RenderViewHost::Stop() {
Send(new ViewMsg_Stop(routing_id()));
}
diff --git a/chrome/browser/renderer_host/render_view_host.h b/chrome/browser/renderer_host/render_view_host.h
index 74e0e77..0ce1372 100644
--- a/chrome/browser/renderer_host/render_view_host.h
+++ b/chrome/browser/renderer_host/render_view_host.h
@@ -182,11 +182,6 @@ class RenderViewHost : public RenderWidgetHost {
// hangs, in which case we need to swap to the pending RenderViewHost.
int GetPendingRequestId();
- // Called by ResourceDispatcherHost when a response for a pending cross-site
- // request is received. The ResourceDispatcherHost will pause the response
- // until the onunload handler of the previous renderer is run.
- void OnCrossSiteResponse(int new_render_process_host_id, int new_request_id);
-
// Stops the current load.
void Stop();
diff --git a/chrome/browser/renderer_host/render_view_host_delegate.h b/chrome/browser/renderer_host/render_view_host_delegate.h
index e782f4b..020537e 100644
--- a/chrome/browser/renderer_host/render_view_host_delegate.h
+++ b/chrome/browser/renderer_host/render_view_host_delegate.h
@@ -26,6 +26,7 @@ class Profile;
struct RendererPreferences;
class RenderProcessHost;
class RenderViewHost;
+class ResourceRedirectDetails;
class ResourceRequestDetails;
class SkBitmap;
class TabContents;
@@ -247,10 +248,8 @@ class RenderViewHostDelegate {
// DidStartProvisionalLoadForFrame above because this is called for every
// resource (images, automatically loaded subframes, etc.) and provisional
// loads are only for user-initiated navigations.
- //
- // The pointer ownership is NOT transferred.
virtual void DidStartReceivingResourceResponse(
- ResourceRequestDetails* details) = 0;
+ const ResourceRequestDetails& details) = 0;
// Sent when a provisional load is redirected.
virtual void DidRedirectProvisionalLoad(int32 page_id,
@@ -262,9 +261,8 @@ class RenderViewHostDelegate {
// DidRedirectProvisionalLoad above because this is called for every
// resource (images, automatically loaded subframes, etc.) and provisional
// loads are only for user-initiated navigations.
- //
- // The pointer ownership is NOT transferred.
- virtual void DidRedirectResource(ResourceRequestDetails* details) = 0;
+ virtual void DidRedirectResource(
+ const ResourceRedirectDetails& details) = 0;
// The RenderView loaded a resource from an in-memory cache.
// |security_info| contains the security info if this resource was
diff --git a/chrome/browser/renderer_host/render_view_host_notification_task.h b/chrome/browser/renderer_host/render_view_host_notification_task.h
new file mode 100644
index 0000000..3093802
--- /dev/null
+++ b/chrome/browser/renderer_host/render_view_host_notification_task.h
@@ -0,0 +1,237 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file defines utility functions for sending notifications (calling
+// methods that return void and do not have out params) to the RenderViewHost
+// or one of its delegate interfaces. The notifications are dispatched
+// asynchronously, and only if the specified RenderViewHost still exists.
+
+#ifndef CHROME_BROWSER_RENDERER_HOST_RENDER_VIEW_HOST_NOTIFICATION_TASK_H_
+#define CHROME_BROWSER_RENDERER_HOST_RENDER_VIEW_HOST_NOTIFICATION_TASK_H_
+
+#include "base/task.h"
+#include "chrome/browser/chrome_thread.h"
+#include "chrome/browser/renderer_host/render_view_host.h"
+#include "chrome/browser/renderer_host/render_view_host_delegate.h"
+
+// ----------------------------------------------------------------------------
+
+namespace internal {
+
+// The simplest Mapper, used when proxying calls to a RenderViewHost.
+class RenderViewHostIdentityMapper {
+ public:
+ typedef RenderViewHost MappedType;
+ static MappedType* Map(RenderViewHost* rvh) { return rvh; }
+};
+
+template <typename Method, typename Params,
+ typename Mapper = RenderViewHostIdentityMapper>
+class RenderViewHostNotificationTask : public Task {
+ public:
+ RenderViewHostNotificationTask(int render_process_id,
+ int render_view_id,
+ Method method,
+ const Params& params)
+ : render_process_id_(render_process_id),
+ render_view_id_(render_view_id),
+ unbound_method_(method, params) {
+ }
+
+ virtual void Run() {
+ RenderViewHost* rvh = RenderViewHost::FromID(render_process_id_,
+ render_view_id_);
+ typename Mapper::MappedType* obj = Mapper::Map(rvh);
+ if (obj)
+ unbound_method_.Run(obj);
+ }
+
+ private:
+ int render_process_id_;
+ int render_view_id_;
+ UnboundMethod<typename Mapper::MappedType, Method, Params> unbound_method_;
+
+ DISALLOW_COPY_AND_ASSIGN(RenderViewHostNotificationTask);
+};
+
+// For proxying calls to RenderViewHost
+
+template <typename Method, typename Params>
+inline void CallRenderViewHostHelper(int render_process_id, int render_view_id,
+ Method method, const Params& params) {
+ ChromeThread::PostTask(
+ ChromeThread::UI, FROM_HERE,
+ new RenderViewHostNotificationTask<Method, Params>(render_process_id,
+ render_view_id,
+ method,
+ params));
+}
+
+// For proxying calls to RenderViewHostDelegate::Resource
+
+class RenderViewHostToResourceDelegate {
+ public:
+ typedef RenderViewHostDelegate::Resource MappedType;
+ static MappedType* Map(RenderViewHost* rvh) {
+ return rvh ? rvh->delegate()->GetResourceDelegate() : NULL;
+ }
+};
+
+template <typename Method, typename Params>
+inline void CallRenderViewHostResourceDelegateHelper(int render_process_id,
+ int render_view_id,
+ Method method,
+ const Params& params) {
+
+ ChromeThread::PostTask(
+ ChromeThread::UI, FROM_HERE,
+ new RenderViewHostNotificationTask<
+ Method, Params, RenderViewHostToResourceDelegate>(render_process_id,
+ render_view_id,
+ method,
+ params));
+}
+
+// For proxying calls to RenderViewHostDelegate::RendererManagement
+
+class RenderViewHostToRendererManagementDelegate {
+ public:
+ typedef RenderViewHostDelegate::RendererManagement MappedType;
+ static MappedType* Map(RenderViewHost* rvh) {
+ return rvh ? rvh->delegate()->GetRendererManagementDelegate() : NULL;
+ }
+};
+
+template <typename Method, typename Params>
+inline void CallRenderViewHostRendererManagementDelegateHelper(
+ int render_process_id,
+ int render_view_id,
+ Method method,
+ const Params& params) {
+ ChromeThread::PostTask(
+ ChromeThread::UI, FROM_HERE,
+ new RenderViewHostNotificationTask<
+ Method, Params, RenderViewHostToRendererManagementDelegate>(
+ render_process_id,
+ render_view_id,
+ method,
+ params));
+}
+
+} // namespace internal
+
+// ----------------------------------------------------------------------------
+// Proxy calls to the specified RenderViewHost.
+
+template <typename Method>
+inline void CallRenderViewHost(int render_process_id,
+ int render_view_id,
+ Method method) {
+ internal::CallRenderViewHostHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple());
+}
+
+template <typename Method, typename A>
+inline void CallRenderViewHost(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a) {
+ internal::CallRenderViewHostHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a));
+}
+
+template <typename Method, typename A, typename B>
+inline void CallRenderViewHost(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a,
+ const B& b) {
+ internal::CallRenderViewHostHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a, b));
+}
+
+// ----------------------------------------------------------------------------
+// Proxy calls to the specified RenderViewHost's Resource delegate.
+
+template <typename Method>
+inline void CallRenderViewHostResourceDelegate(int render_process_id,
+ int render_view_id,
+ Method method) {
+ internal::CallRenderViewHostResourceDelegateHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple());
+}
+
+template <typename Method, typename A>
+inline void CallRenderViewHostResourceDelegate(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a) {
+ internal::CallRenderViewHostResourceDelegateHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a));
+}
+
+template <typename Method, typename A, typename B>
+inline void CallRenderViewHostResourceDelegate(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a,
+ const B& b) {
+ internal::CallRenderViewHostResourceDelegateHelper(render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a, b));
+}
+
+// ----------------------------------------------------------------------------
+// Proxy calls to the specified RenderViewHost's RendererManagement delegate.
+
+template <typename Method>
+inline void CallRenderViewHostRendererManagementDelegate(int render_process_id,
+ int render_view_id,
+ Method method) {
+ internal::CallRenderViewHostRendererManagementDelegateHelper(
+ render_process_id,
+ render_view_id,
+ method,
+ MakeTuple());
+}
+
+template <typename Method, typename A>
+inline void CallRenderViewHostRendererManagementDelegate(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a) {
+ internal::CallRenderViewHostRendererManagementDelegateHelper(
+ render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a));
+}
+
+template <typename Method, typename A, typename B>
+inline void CallRenderViewHostRendererManagementDelegate(int render_process_id,
+ int render_view_id,
+ Method method,
+ const A& a,
+ const B& b) {
+ internal::CallRenderViewHostRendererManagementDelegateHelper(
+ render_process_id,
+ render_view_id,
+ method,
+ MakeTuple(a, b));
+}
+
+// ----------------------------------------------------------------------------
+
+#endif // CHROME_BROWSER_RENDERER_HOST_RENDER_VIEW_HOST_NOTIFICATION_TASK_H_
diff --git a/chrome/browser/renderer_host/resource_dispatcher_host.cc b/chrome/browser/renderer_host/resource_dispatcher_host.cc
index 2907d7f..971888c 100644
--- a/chrome/browser/renderer_host/resource_dispatcher_host.cc
+++ b/chrome/browser/renderer_host/resource_dispatcher_host.cc
@@ -38,6 +38,7 @@
#include "chrome/browser/renderer_host/global_request_id.h"
#include "chrome/browser/renderer_host/render_view_host.h"
#include "chrome/browser/renderer_host/render_view_host_delegate.h"
+#include "chrome/browser/renderer_host/render_view_host_notification_task.h"
#include "chrome/browser/renderer_host/resource_dispatcher_host_request_info.h"
#include "chrome/browser/renderer_host/resource_queue.h"
#include "chrome/browser/renderer_host/resource_request_details.h"
@@ -108,89 +109,6 @@ const int kMaxPendingDataMessages = 20;
// This bound is 25MB, which allows for around 6000 outstanding requests.
const int kMaxOutstandingRequestsCostPerProcess = 26214400;
-// Calls ClosePageIgnoringUnloadEvents on the UI thread for the given
-// RenderView.
-//
-// If there are more functions we need to call on RVH, we should generalize this
-// like the "Delegate" notification task below.
-class RVHCloseNotificationTask : public Task {
- public:
- RVHCloseNotificationTask(int render_process_host_id,
- int render_view_host_id)
- : render_process_host_id_(render_process_host_id),
- render_view_host_id_(render_view_host_id) {
- }
-
- virtual void Run() {
- RenderViewHost* rvh = RenderViewHost::FromID(render_process_host_id_,
- render_view_host_id_);
- if (rvh)
- rvh->ClosePageIgnoringUnloadEvents();
- }
-
- private:
- int render_process_host_id_;
- int render_view_host_id_;
-
- DISALLOW_COPY_AND_ASSIGN(RVHCloseNotificationTask);
-};
-
-// A RVHDelegateNotificationTask proxies a resource dispatcher notification
-// from the IO thread to the RenderViewHostDelegate on the UI thread. It should
-// be constructed on the IO thread and run in the UI thread.
-class RVHDelegateNotificationTask : public Task {
- public:
- typedef void (RenderViewHostDelegate::Resource::* ResourceFunction)
- (ResourceRequestDetails*);
-
- // Supply the originating URLRequest, a function on RenderViewHostDelegate
- // to call, and the details to use as the parameter to the given function.
- //
- // This object will take ownership of the details pointer, which must be
- // allocated on the heap.
- RVHDelegateNotificationTask(
- URLRequest* request,
- ResourceFunction function,
- ResourceRequestDetails* details)
- : render_process_host_id_(-1),
- render_view_host_id_(-1),
- function_(function),
- details_(details) {
- if (!ResourceDispatcherHost::RenderViewForRequest(request,
- &render_process_host_id_,
- &render_view_host_id_)) {
- // Issue a warning here - this can happen during normal operation (for
- // example, if a worker exits while a network operation is pending), but
- // it should be fairly rare.
- DLOG(WARNING) << "Trying to deliver a message to a RenderViewHost" <<
- " that has already exited or has never existed.";
- }
- }
-
- virtual void Run() {
- RenderViewHost* rvh = RenderViewHost::FromID(render_process_host_id_,
- render_view_host_id_);
- if (rvh) {
- RenderViewHostDelegate::Resource* resource_delegate =
- rvh->delegate()->GetResourceDelegate();
- if (resource_delegate)
- (resource_delegate->*function_)(details_.get());
- }
- }
-
- private:
- int render_process_host_id_;
- int render_view_host_id_;
-
- // The function to call on RenderViewHostDelegate::Resource on the UI thread.
- ResourceFunction function_;
-
- // The details for the notification.
- scoped_ptr<ResourceRequestDetails> details_;
-
- DISALLOW_COPY_AND_ASSIGN(RVHDelegateNotificationTask);
-};
-
// Consults the RendererSecurity policy to determine whether the
// ResourceDispatcherHost should service this request. A request might be
// disallowed if the renderer is not authorized to retrieve the request URL or
@@ -635,10 +553,9 @@ void ResourceDispatcherHost::OnClosePageACK(
// This is a tab close, so just forward the message to close it.
DCHECK(params.new_render_process_host_id == -1);
DCHECK(params.new_request_id == -1);
- ChromeThread::PostTask(
- ChromeThread::UI, FROM_HERE,
- new RVHCloseNotificationTask(params.closing_process_id,
- params.closing_route_id));
+ CallRenderViewHost(params.closing_process_id,
+ params.closing_route_id,
+ &RenderViewHost::ClosePageIgnoringUnloadEvents);
}
}
@@ -1057,6 +974,19 @@ void ResourceDispatcherHost::OnSSLCertificateError(
SSLManager::OnSSLCertificateError(this, request, cert_error, cert);
}
+void ResourceDispatcherHost::OnSetCookieBlocked(URLRequest* request) {
+ RESOURCE_LOG("OnSetCookieBlocked: " << request->url().spec());
+
+ int render_process_id, render_view_id;
+ if (!RenderViewForRequest(request, &render_process_id, &render_view_id))
+ return;
+
+ CallRenderViewHostResourceDelegate(
+ render_process_id, render_view_id,
+ &RenderViewHostDelegate::Resource::OnContentBlocked,
+ CONTENT_SETTINGS_TYPE_COOKIES);
+}
+
void ResourceDispatcherHost::OnResponseStarted(URLRequest* request) {
RESOURCE_LOG("OnResponseStarted: " << request->url().spec());
ResourceDispatcherHostRequestInfo* info = InfoForRequest(request);
@@ -1448,20 +1378,20 @@ bool ResourceDispatcherHost::RenderViewForRequest(const URLRequest* request,
// If the request is from the worker process, find a tab that owns the worker.
if (info->process_type() == ChildProcessInfo::WORKER_PROCESS) {
- const WorkerProcessHost::WorkerInstance* worker_instance =
- WorkerService::GetInstance()->FindWorkerInstance(info->child_id());
- if (!worker_instance) {
- *render_process_host_id = -1;
- *render_view_host_id = -1;
- return false;
- }
- DCHECK(!worker_instance->worker_document_set()->IsEmpty());
- const WorkerDocumentSet::DocumentInfoSet& parents =
- worker_instance->worker_document_set()->documents();
- // Need to display some related UI for this network request - pick an
- // arbitrary parent to do so.
- *render_process_host_id = parents.begin()->renderer_id();
- *render_view_host_id = parents.begin()->render_view_route_id();
+ const WorkerProcessHost::WorkerInstance* worker_instance =
+ WorkerService::GetInstance()->FindWorkerInstance(info->child_id());
+ if (!worker_instance) {
+ *render_process_host_id = -1;
+ *render_view_host_id = -1;
+ return false;
+ }
+ DCHECK(!worker_instance->worker_document_set()->IsEmpty());
+ const WorkerDocumentSet::DocumentInfoSet& parents =
+ worker_instance->worker_document_set()->documents();
+ // Need to display some related UI for this network request - pick an
+ // arbitrary parent to do so.
+ *render_process_host_id = parents.begin()->renderer_id();
+ *render_view_host_id = parents.begin()->render_view_route_id();
} else {
*render_process_host_id = info->child_id();
*render_view_host_id = info->route_id();
@@ -1511,13 +1441,15 @@ void ResourceDispatcherHost::NotifyResponseStarted(URLRequest* request,
// Notify the observers on the IO thread.
FOR_EACH_OBSERVER(Observer, observer_list_, OnRequestStarted(this, request));
+ int render_process_id, render_view_id;
+ if (!RenderViewForRequest(request, &render_process_id, &render_view_id))
+ return;
+
// Notify the observers on the UI thread.
- ChromeThread::PostTask(
- ChromeThread::UI, FROM_HERE,
- new RVHDelegateNotificationTask(
- request,
- &RenderViewHostDelegate::Resource::DidStartReceivingResourceResponse,
- new ResourceRequestDetails(request, GetCertID(request, child_id))));
+ CallRenderViewHostResourceDelegate(
+ render_process_id, render_view_id,
+ &RenderViewHostDelegate::Resource::DidStartReceivingResourceResponse,
+ ResourceRequestDetails(request, GetCertID(request, child_id)));
}
void ResourceDispatcherHost::NotifyResponseCompleted(URLRequest* request,
@@ -1534,14 +1466,15 @@ void ResourceDispatcherHost::NotifyReceivedRedirect(URLRequest* request,
FOR_EACH_OBSERVER(Observer, observer_list_,
OnReceivedRedirect(this, request, new_url));
- int cert_id = GetCertID(request, child_id);
+ int render_process_id, render_view_id;
+ if (!RenderViewForRequest(request, &render_process_id, &render_view_id))
+ return;
// Notify the observers on the UI thread.
- ChromeThread::PostTask(
- ChromeThread::UI, FROM_HERE,
- new RVHDelegateNotificationTask(
- request, &RenderViewHostDelegate::Resource::DidRedirectResource,
- new ResourceRedirectDetails(request, cert_id, new_url)));
+ CallRenderViewHostResourceDelegate(
+ render_process_id, render_view_id,
+ &RenderViewHostDelegate::Resource::DidRedirectResource,
+ ResourceRedirectDetails(request, GetCertID(request, child_id), new_url));
}
namespace {
diff --git a/chrome/browser/renderer_host/resource_dispatcher_host.h b/chrome/browser/renderer_host/resource_dispatcher_host.h
index eff192d..4e10dae 100644
--- a/chrome/browser/renderer_host/resource_dispatcher_host.h
+++ b/chrome/browser/renderer_host/resource_dispatcher_host.h
@@ -206,6 +206,7 @@ class ResourceDispatcherHost : public URLRequest::Delegate {
virtual void OnSSLCertificateError(URLRequest* request,
int cert_error,
net::X509Certificate* cert);
+ virtual void OnSetCookieBlocked(URLRequest* request);
virtual void OnResponseStarted(URLRequest* request);
virtual void OnReadCompleted(URLRequest* request, int bytes_read);
void OnResponseCompleted(URLRequest* request);
diff --git a/chrome/browser/renderer_host/resource_request_details.h b/chrome/browser/renderer_host/resource_request_details.h
index ad0df97d..600decd 100644
--- a/chrome/browser/renderer_host/resource_request_details.h
+++ b/chrome/browser/renderer_host/resource_request_details.h
@@ -92,8 +92,6 @@ class ResourceRequestDetails {
int ssl_cert_status_;
ResourceType::Type resource_type_;
FilterPolicy::Type filter_policy_;
-
- DISALLOW_COPY_AND_ASSIGN(ResourceRequestDetails);
};
// Details about a redirection of a resource request.
diff --git a/chrome/browser/tab_contents/tab_contents.cc b/chrome/browser/tab_contents/tab_contents.cc
index f3b986d..9c334dc 100644
--- a/chrome/browser/tab_contents/tab_contents.cc
+++ b/chrome/browser/tab_contents/tab_contents.cc
@@ -580,10 +580,11 @@ bool TabContents::IsContentBlocked(ContentSettingsType content_type) const {
if (content_type == CONTENT_SETTINGS_TYPE_IMAGES ||
content_type == CONTENT_SETTINGS_TYPE_JAVASCRIPT ||
- content_type == CONTENT_SETTINGS_TYPE_PLUGINS)
+ content_type == CONTENT_SETTINGS_TYPE_PLUGINS ||
+ content_type == CONTENT_SETTINGS_TYPE_COOKIES)
return content_blocked_[content_type];
- // TODO(pkasting): Return a meaningful values for cookies.
+ NOTREACHED();
return false;
}
@@ -1893,18 +1894,19 @@ void TabContents::DidStartProvisionalLoadForFrame(
}
void TabContents::DidStartReceivingResourceResponse(
- ResourceRequestDetails* details) {
+ const ResourceRequestDetails& details) {
NotificationService::current()->Notify(
NotificationType::RESOURCE_RESPONSE_STARTED,
Source<NavigationController>(&controller()),
- Details<ResourceRequestDetails>(details));
+ Details<const ResourceRequestDetails>(&details));
}
-void TabContents::DidRedirectResource(ResourceRequestDetails* details) {
+void TabContents::DidRedirectResource(
+ const ResourceRedirectDetails& details) {
NotificationService::current()->Notify(
NotificationType::RESOURCE_RECEIVED_REDIRECT,
Source<NavigationController>(&controller()),
- Details<ResourceRequestDetails>(details));
+ Details<const ResourceRequestDetails>(&details));
}
void TabContents::DidLoadResourceFromMemoryCache(
diff --git a/chrome/browser/tab_contents/tab_contents.h b/chrome/browser/tab_contents/tab_contents.h
index eabbb71e..b66504c 100644
--- a/chrome/browser/tab_contents/tab_contents.h
+++ b/chrome/browser/tab_contents/tab_contents.h
@@ -814,11 +814,12 @@ class TabContents : public PageNavigator,
bool is_main_frame,
const GURL& url);
virtual void DidStartReceivingResourceResponse(
- ResourceRequestDetails* details);
+ const ResourceRequestDetails& details);
virtual void DidRedirectProvisionalLoad(int32 page_id,
const GURL& source_url,
const GURL& target_url);
- virtual void DidRedirectResource(ResourceRequestDetails* details);
+ virtual void DidRedirectResource(
+ const ResourceRedirectDetails& details);
virtual void DidLoadResourceFromMemoryCache(
const GURL& url,
const std::string& frame_origin,
diff --git a/net/url_request/url_request.h b/net/url_request/url_request.h
index e586e28..b420cf8 100644
--- a/net/url_request/url_request.h
+++ b/net/url_request/url_request.h
@@ -187,6 +187,14 @@ class URLRequest {
request->Cancel();
}
+ // Called when unable to get cookies due to policy.
+ virtual void OnGetCookiesBlocked(URLRequest* request) {
+ }
+
+ // Called when unable to set a cookie due to policy.
+ virtual void OnSetCookieBlocked(URLRequest* request) {
+ }
+
// After calling Start(), the delegate will receive an OnResponseStarted
// callback when the request has completed. If an error occurred, the
// request->status() will be set. On success, all redirects have been
diff --git a/net/url_request/url_request_http_job.cc b/net/url_request/url_request_http_job.cc
index 05fd0f2..ef17774 100644
--- a/net/url_request/url_request_http_job.cc
+++ b/net/url_request/url_request_http_job.cc
@@ -432,7 +432,9 @@ bool URLRequestHttpJob::ReadRawData(net::IOBuffer* buf, int buf_size,
void URLRequestHttpJob::OnCanGetCookiesCompleted(int policy) {
// If the request was destroyed, then there is no more work to do.
if (request_ && request_->delegate()) {
- if (request_->context()->cookie_store() && policy == net::OK) {
+ if (policy != net::OK) {
+ request_->delegate()->OnGetCookiesBlocked(request_);
+ } else if (request_->context()->cookie_store()) {
net::CookieOptions options;
options.set_include_httponly();
std::string cookies =
@@ -442,7 +444,12 @@ void URLRequestHttpJob::OnCanGetCookiesCompleted(int policy) {
!cookies.empty())
request_info_.extra_headers += "Cookie: " + cookies + "\r\n";
}
- StartTransaction();
+ // We may have been canceled within OnGetCookiesBlocked.
+ if (GetStatus().is_success()) {
+ StartTransaction();
+ } else {
+ NotifyCanceled();
+ }
}
Release(); // Balance AddRef taken in AddCookieHeaderAndStart
}
@@ -450,9 +457,10 @@ void URLRequestHttpJob::OnCanGetCookiesCompleted(int policy) {
void URLRequestHttpJob::OnCanSetCookieCompleted(int policy) {
// If the request was destroyed, then there is no more work to do.
if (request_ && request_->delegate()) {
- if (request_->context()->cookie_store() &&
- (policy == net::OK ||
- policy == net::OK_FOR_SESSION_ONLY)) {
+ if (policy != net::OK &&
+ policy != net::OK_FOR_SESSION_ONLY) {
+ request_->delegate()->OnSetCookieBlocked(request_);
+ } else if (request_->context()->cookie_store()) {
// OK to save the current response cookie now.
net::CookieOptions options;
options.set_include_httponly();
@@ -463,7 +471,12 @@ void URLRequestHttpJob::OnCanSetCookieCompleted(int policy) {
options);
}
response_cookies_save_index_++;
- SaveNextCookie();
+ // We may have been canceled within OnSetCookieBlocked.
+ if (GetStatus().is_success()) {
+ SaveNextCookie();
+ } else {
+ NotifyCanceled();
+ }
}
Release(); // Balance AddRef taken in SaveNextCookie
}
diff --git a/net/url_request/url_request_unittest.cc b/net/url_request/url_request_unittest.cc
index d25ab08..16f4b3f 100644
--- a/net/url_request/url_request_unittest.cc
+++ b/net/url_request/url_request_unittest.cc
@@ -1241,6 +1241,8 @@ TEST_F(URLRequestTest, DoNotSendCookies) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie is set.
@@ -1253,6 +1255,8 @@ TEST_F(URLRequestTest, DoNotSendCookies) {
EXPECT_TRUE(d.data_received().find("CookieToNotSend=1")
!= std::string::npos);
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie isn't sent when LOAD_DO_NOT_SEND_COOKIES is set.
@@ -1266,6 +1270,8 @@ TEST_F(URLRequestTest, DoNotSendCookies) {
EXPECT_TRUE(d.data_received().find("Cookie: CookieToNotSend=1")
== std::string::npos);
+ EXPECT_EQ(1, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
@@ -1283,6 +1289,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Try to set-up another cookie and update the previous cookie.
@@ -1295,6 +1304,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies) {
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(2, d.blocked_set_cookie_count());
}
// Verify the cookies weren't saved or updated.
@@ -1309,6 +1321,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies) {
== std::string::npos);
EXPECT_TRUE(d.data_received().find("CookieToNotUpdate=2")
!= std::string::npos);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
@@ -1325,6 +1340,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie is set.
@@ -1337,6 +1355,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy) {
EXPECT_TRUE(d.data_received().find("CookieToNotSend=1")
!= std::string::npos);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie isn't sent.
@@ -1354,6 +1375,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy) {
== std::string::npos);
context->set_cookie_policy(NULL);
+
+ EXPECT_EQ(1, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
@@ -1371,6 +1395,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Try to set-up another cookie and update the previous cookie.
@@ -1387,6 +1414,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy) {
MessageLoop::current()->Run();
context->set_cookie_policy(NULL);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(2, d.blocked_set_cookie_count());
}
@@ -1402,6 +1432,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy) {
== std::string::npos);
EXPECT_TRUE(d.data_received().find("CookieToNotUpdate=2")
!= std::string::npos);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
@@ -1418,6 +1451,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy_Async) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie is set.
@@ -1430,6 +1466,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy_Async) {
EXPECT_TRUE(d.data_received().find("CookieToNotSend=1")
!= std::string::npos);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Verify that the cookie isn't sent.
@@ -1448,6 +1487,9 @@ TEST_F(URLRequestTest, DoNotSendCookies_ViaPolicy_Async) {
== std::string::npos);
context->set_cookie_policy(NULL);
+
+ EXPECT_EQ(1, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
@@ -1465,6 +1507,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy_Async) {
req.set_context(context);
req.Start();
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Try to set-up another cookie and update the previous cookie.
@@ -1482,6 +1527,9 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy_Async) {
MessageLoop::current()->Run();
context->set_cookie_policy(NULL);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(2, d.blocked_set_cookie_count());
}
// Verify the cookies weren't saved or updated.
@@ -1496,10 +1544,13 @@ TEST_F(URLRequestTest, DoNotSaveCookies_ViaPolicy_Async) {
== std::string::npos);
EXPECT_TRUE(d.data_received().find("CookieToNotUpdate=2")
!= std::string::npos);
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
}
-TEST_F(URLRequestTest, CancelTest_DuringCookiePolicy) {
+TEST_F(URLRequestTest, CancelTest_During_CookiePolicy) {
scoped_refptr<HTTPTestServer> server =
HTTPTestServer::CreateServer(L"", NULL);
ASSERT_TRUE(NULL != server.get());
@@ -1516,7 +1567,78 @@ TEST_F(URLRequestTest, CancelTest_DuringCookiePolicy) {
req.set_context(context);
req.Start(); // Triggers an asynchronous cookie policy check.
- // But, now we cancel the request. This should not cause a crash.
+ // But, now we cancel the request by letting it go out of scope. This
+ // should not cause a crash.
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
+ }
+
+ context->set_cookie_policy(NULL);
+
+ // Let the cookie policy complete. Make sure it handles the destruction of
+ // the URLRequest properly.
+ MessageLoop::current()->RunAllPending();
+}
+
+TEST_F(URLRequestTest, CancelTest_During_OnGetCookiesBlocked) {
+ scoped_refptr<HTTPTestServer> server =
+ HTTPTestServer::CreateServer(L"", NULL);
+ ASSERT_TRUE(NULL != server.get());
+ scoped_refptr<URLRequestTestContext> context = new URLRequestTestContext();
+
+ TestCookiePolicy cookie_policy(TestCookiePolicy::NO_GET_COOKIES);
+ context->set_cookie_policy(&cookie_policy);
+
+ // Set up a cookie.
+ {
+ TestDelegate d;
+ d.set_cancel_in_get_cookies_blocked(true);
+ URLRequest req(server->TestServerPage("set-cookie?A=1&B=2&C=3"),
+ &d);
+ req.set_context(context);
+ req.Start(); // Triggers an asynchronous cookie policy check.
+
+ MessageLoop::current()->Run();
+
+ EXPECT_EQ(URLRequestStatus::CANCELED, req.status().status());
+
+ EXPECT_EQ(1, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
+ }
+
+ context->set_cookie_policy(NULL);
+}
+
+TEST_F(URLRequestTest, CancelTest_During_OnSetCookieBlocked) {
+ scoped_refptr<HTTPTestServer> server =
+ HTTPTestServer::CreateServer(L"", NULL);
+ ASSERT_TRUE(NULL != server.get());
+ scoped_refptr<URLRequestTestContext> context = new URLRequestTestContext();
+
+ TestCookiePolicy cookie_policy(TestCookiePolicy::NO_SET_COOKIE);
+ context->set_cookie_policy(&cookie_policy);
+
+ // Set up a cookie.
+ {
+ TestDelegate d;
+ d.set_cancel_in_set_cookie_blocked(true);
+ URLRequest req(server->TestServerPage("set-cookie?A=1&B=2&C=3"),
+ &d);
+ req.set_context(context);
+ req.Start(); // Triggers an asynchronous cookie policy check.
+
+ MessageLoop::current()->Run();
+
+ EXPECT_EQ(URLRequestStatus::CANCELED, req.status().status());
+
+ // Even though the response will contain 3 set-cookie headers, we expect
+ // only one to be blocked as that first one will cause OnSetCookieBlocked
+ // to be called, which will cancel the request. Once canceled, it should
+ // not attempt to set further cookies.
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(1, d.blocked_set_cookie_count());
}
context->set_cookie_policy(NULL);
@@ -1540,6 +1662,9 @@ TEST_F(URLRequestTest, CookiePolicy_ForceSession) {
req.Start(); // Triggers an asynchronous cookie policy check.
MessageLoop::current()->Run();
+
+ EXPECT_EQ(0, d.blocked_get_cookies_count());
+ EXPECT_EQ(0, d.blocked_set_cookie_count());
}
// Now, check the cookie store.
diff --git a/net/url_request/url_request_unittest.h b/net/url_request/url_request_unittest.h
index 3f50335..16116d9 100644
--- a/net/url_request/url_request_unittest.h
+++ b/net/url_request/url_request_unittest.h
@@ -192,12 +192,16 @@ class TestDelegate : public URLRequest::Delegate {
cancel_in_rs_(false),
cancel_in_rd_(false),
cancel_in_rd_pending_(false),
+ cancel_in_getcookiesblocked_(false),
+ cancel_in_setcookieblocked_(false),
quit_on_complete_(true),
quit_on_redirect_(false),
allow_certificate_errors_(false),
response_started_count_(0),
received_bytes_count_(0),
received_redirect_count_(0),
+ blocked_get_cookies_count_(0),
+ blocked_set_cookie_count_(0),
received_data_before_response_(false),
request_failed_(false),
have_certificate_errors_(false),
@@ -300,12 +304,30 @@ class TestDelegate : public URLRequest::Delegate {
request->Cancel();
}
+ virtual void OnGetCookiesBlocked(URLRequest* request) {
+ blocked_get_cookies_count_++;
+ if (cancel_in_getcookiesblocked_)
+ request->Cancel();
+ }
+
+ virtual void OnSetCookieBlocked(URLRequest* request) {
+ blocked_set_cookie_count_++;
+ if (cancel_in_setcookieblocked_)
+ request->Cancel();
+ }
+
void set_cancel_in_received_redirect(bool val) { cancel_in_rr_ = val; }
void set_cancel_in_response_started(bool val) { cancel_in_rs_ = val; }
void set_cancel_in_received_data(bool val) { cancel_in_rd_ = val; }
void set_cancel_in_received_data_pending(bool val) {
cancel_in_rd_pending_ = val;
}
+ void set_cancel_in_get_cookies_blocked(bool val) {
+ cancel_in_getcookiesblocked_ = val;
+ }
+ void set_cancel_in_set_cookie_blocked(bool val) {
+ cancel_in_setcookieblocked_ = val;
+ }
void set_quit_on_complete(bool val) { quit_on_complete_ = val; }
void set_quit_on_redirect(bool val) { quit_on_redirect_ = val; }
void set_allow_certificate_errors(bool val) {
@@ -319,6 +341,8 @@ class TestDelegate : public URLRequest::Delegate {
int bytes_received() const { return static_cast<int>(data_received_.size()); }
int response_started_count() const { return response_started_count_; }
int received_redirect_count() const { return received_redirect_count_; }
+ int blocked_get_cookies_count() const { return blocked_get_cookies_count_; }
+ int blocked_set_cookie_count() const { return blocked_set_cookie_count_; }
bool received_data_before_response() const {
return received_data_before_response_;
}
@@ -332,6 +356,8 @@ class TestDelegate : public URLRequest::Delegate {
bool cancel_in_rs_;
bool cancel_in_rd_;
bool cancel_in_rd_pending_;
+ bool cancel_in_getcookiesblocked_;
+ bool cancel_in_setcookieblocked_;
bool quit_on_complete_;
bool quit_on_redirect_;
bool allow_certificate_errors_;
@@ -343,6 +369,8 @@ class TestDelegate : public URLRequest::Delegate {
int response_started_count_;
int received_bytes_count_;
int received_redirect_count_;
+ int blocked_get_cookies_count_;
+ int blocked_set_cookie_count_;
bool received_data_before_response_;
bool request_failed_;
bool have_certificate_errors_;