| Index: webkit/child/weburlloader_impl.cc | 
| diff --git a/webkit/child/weburlloader_impl.cc b/webkit/child/weburlloader_impl.cc | 
| index 63ce778da190cc1ab6e217469ad82afdef646bb8..c776d7945243966d9728e53bf3515f2c544b06d3 100644 | 
| --- a/webkit/child/weburlloader_impl.cc | 
| +++ b/webkit/child/weburlloader_impl.cc | 
| @@ -31,6 +31,7 @@ | 
| #include "webkit/child/ftp_directory_listing_response_delegate.h" | 
| #include "webkit/child/multipart_response_delegate.h" | 
| #include "webkit/child/resource_loader_bridge.h" | 
| +#include "webkit/child/site_isolation_policy.h" | 
| #include "webkit/child/webkitplatformsupport_impl.h" | 
| #include "webkit/child/weburlrequest_extradata_impl.h" | 
| #include "webkit/child/weburlresponse_extradata_impl.h" | 
| @@ -59,263 +60,264 @@ namespace webkit_glue { | 
|  | 
| namespace { | 
|  | 
| -const char kThrottledErrorDescription[] = | 
| -    "Request throttled. Visit http://dev.chromium.org/throttling for more " | 
| -    "information."; | 
| - | 
| -class HeaderFlattener : public WebHTTPHeaderVisitor { | 
| - public: | 
| -  explicit HeaderFlattener(int load_flags) | 
| -      : load_flags_(load_flags), | 
| -        has_accept_header_(false) { | 
| -  } | 
| - | 
| -  virtual void visitHeader(const WebString& name, const WebString& value) { | 
| -    // TODO(darin): is UTF-8 really correct here?  It is if the strings are | 
| -    // already ASCII (i.e., if they are already escaped properly). | 
| -    const std::string& name_utf8 = name.utf8(); | 
| -    const std::string& value_utf8 = value.utf8(); | 
| - | 
| -    // Skip over referrer headers found in the header map because we already | 
| -    // pulled it out as a separate parameter. | 
| -    if (LowerCaseEqualsASCII(name_utf8, "referer")) | 
| -      return; | 
| - | 
| -    // Skip over "Cache-Control: max-age=0" header if the corresponding | 
| -    // load flag is already specified. FrameLoader sets both the flag and | 
| -    // the extra header -- the extra header is redundant since our network | 
| -    // implementation will add the necessary headers based on load flags. | 
| -    // See http://code.google.com/p/chromium/issues/detail?id=3434. | 
| -    if ((load_flags_ & net::LOAD_VALIDATE_CACHE) && | 
| -        LowerCaseEqualsASCII(name_utf8, "cache-control") && | 
| -        LowerCaseEqualsASCII(value_utf8, "max-age=0")) | 
| -      return; | 
| - | 
| -    if (LowerCaseEqualsASCII(name_utf8, "accept")) | 
| -      has_accept_header_ = true; | 
| - | 
| -    if (!buffer_.empty()) | 
| -      buffer_.append("\r\n"); | 
| -    buffer_.append(name_utf8 + ": " + value_utf8); | 
| -  } | 
| - | 
| -  const std::string& GetBuffer() { | 
| -    // In some cases, WebKit doesn't add an Accept header, but not having the | 
| -    // header confuses some web servers.  See bug 808613. | 
| -    if (!has_accept_header_) { | 
| -      if (!buffer_.empty()) | 
| -        buffer_.append("\r\n"); | 
| -      buffer_.append("Accept: */*"); | 
| -      has_accept_header_ = true; | 
| -    } | 
| -    return buffer_; | 
| -  } | 
| +    const char kThrottledErrorDescription[] = "Request throttled. Visit http://dev.chromium.org/throttling for more " | 
| +                                              "information."; | 
|  | 
| - private: | 
| -  int load_flags_; | 
| -  std::string buffer_; | 
| -  bool has_accept_header_; | 
| -}; | 
| +    class HeaderFlattener : public WebHTTPHeaderVisitor { | 
| +    public: | 
| +        explicit HeaderFlattener(int load_flags) | 
| +            : load_flags_(load_flags) | 
| +            , has_accept_header_(false) | 
| +        { | 
| +        } | 
|  | 
| -// Extracts the information from a data: url. | 
| -bool GetInfoFromDataURL(const GURL& url, | 
| -                        ResourceResponseInfo* info, | 
| -                        std::string* data, | 
| -                        int* error_code) { | 
| -  std::string mime_type; | 
| -  std::string charset; | 
| -  if (net::DataURL::Parse(url, &mime_type, &charset, data)) { | 
| -    *error_code = net::OK; | 
| -    // Assure same time for all time fields of data: URLs. | 
| -    Time now = Time::Now(); | 
| -    info->load_timing.request_start = TimeTicks::Now(); | 
| -    info->load_timing.request_start_time = now; | 
| -    info->request_time = now; | 
| -    info->response_time = now; | 
| -    info->headers = NULL; | 
| -    info->mime_type.swap(mime_type); | 
| -    info->charset.swap(charset); | 
| -    info->security_info.clear(); | 
| -    info->content_length = data->length(); | 
| -    info->encoded_data_length = 0; | 
| - | 
| -    return true; | 
| -  } | 
| - | 
| -  *error_code = net::ERR_INVALID_URL; | 
| -  return false; | 
| -} | 
| +        virtual void visitHeader(const WebString& name, const WebString& value) | 
| +        { | 
| +            // TODO(darin): is UTF-8 really correct here?  It is if the strings are | 
| +            // already ASCII (i.e., if they are already escaped properly). | 
| +            const std::string& name_utf8 = name.utf8(); | 
| +            const std::string& value_utf8 = value.utf8(); | 
| + | 
| +            // Skip over referrer headers found in the header map because we already | 
| +            // pulled it out as a separate parameter. | 
| +            if (LowerCaseEqualsASCII(name_utf8, "referer")) | 
| +                return; | 
| + | 
| +            // Skip over "Cache-Control: max-age=0" header if the corresponding | 
| +            // load flag is already specified. FrameLoader sets both the flag and | 
| +            // the extra header -- the extra header is redundant since our network | 
| +            // implementation will add the necessary headers based on load flags. | 
| +            // See http://code.google.com/p/chromium/issues/detail?id=3434. | 
| +            if ((load_flags_ & net::LOAD_VALIDATE_CACHE) && LowerCaseEqualsASCII(name_utf8, "cache-control") && LowerCaseEqualsASCII(value_utf8, "max-age=0")) | 
| +                return; | 
| + | 
| +            if (LowerCaseEqualsASCII(name_utf8, "accept")) | 
| +                has_accept_header_ = true; | 
| + | 
| +            if (!buffer_.empty()) | 
| +                buffer_.append("\r\n"); | 
| +            buffer_.append(name_utf8 + ": " + value_utf8); | 
| +        } | 
|  | 
| -typedef ResourceDevToolsInfo::HeadersVector HeadersVector; | 
| - | 
| -// Converts timing data from |load_timing| to the format used by WebKit. | 
| -void PopulateURLLoadTiming(const net::LoadTimingInfo& load_timing, | 
| -                           WebURLLoadTiming* url_timing) { | 
| -  DCHECK(!load_timing.request_start.is_null()); | 
| - | 
| -  const TimeTicks kNullTicks; | 
| -  url_timing->initialize(); | 
| -  url_timing->setRequestTime( | 
| -      (load_timing.request_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setProxyStart( | 
| -      (load_timing.proxy_resolve_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setProxyEnd( | 
| -      (load_timing.proxy_resolve_end - kNullTicks).InSecondsF()); | 
| -  url_timing->setDNSStart( | 
| -      (load_timing.connect_timing.dns_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setDNSEnd( | 
| -      (load_timing.connect_timing.dns_end - kNullTicks).InSecondsF()); | 
| -  url_timing->setConnectStart( | 
| -      (load_timing.connect_timing.connect_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setConnectEnd( | 
| -      (load_timing.connect_timing.connect_end - kNullTicks).InSecondsF()); | 
| -  url_timing->setSSLStart( | 
| -      (load_timing.connect_timing.ssl_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setSSLEnd( | 
| -      (load_timing.connect_timing.ssl_end - kNullTicks).InSecondsF()); | 
| -  url_timing->setSendStart( | 
| -      (load_timing.send_start - kNullTicks).InSecondsF()); | 
| -  url_timing->setSendEnd( | 
| -      (load_timing.send_end - kNullTicks).InSecondsF()); | 
| -  url_timing->setReceiveHeadersEnd( | 
| -      (load_timing.receive_headers_end - kNullTicks).InSecondsF()); | 
| -} | 
| +        const std::string& GetBuffer() | 
| +        { | 
| +            // In some cases, WebKit doesn't add an Accept header, but not having the | 
| +            // header confuses some web servers.  See bug 808613. | 
| +            if (!has_accept_header_) { | 
| +                if (!buffer_.empty()) | 
| +                    buffer_.append("\r\n"); | 
| +                buffer_.append("Accept: */*"); | 
| +                has_accept_header_ = true; | 
| +            } | 
| +            return buffer_; | 
| +        } | 
|  | 
| -void PopulateURLResponse( | 
| -    const GURL& url, | 
| -    const ResourceResponseInfo& info, | 
| -    WebURLResponse* response) { | 
| -  response->setURL(url); | 
| -  response->setResponseTime(info.response_time.ToDoubleT()); | 
| -  response->setMIMEType(WebString::fromUTF8(info.mime_type)); | 
| -  response->setTextEncodingName(WebString::fromUTF8(info.charset)); | 
| -  response->setExpectedContentLength(info.content_length); | 
| -  response->setSecurityInfo(info.security_info); | 
| -  response->setAppCacheID(info.appcache_id); | 
| -  response->setAppCacheManifestURL(info.appcache_manifest_url); | 
| -  response->setWasCached(!info.load_timing.request_start_time.is_null() && | 
| -      info.response_time < info.load_timing.request_start_time); | 
| -  response->setRemoteIPAddress( | 
| -      WebString::fromUTF8(info.socket_address.host())); | 
| -  response->setRemotePort(info.socket_address.port()); | 
| -  response->setConnectionID(info.load_timing.socket_log_id); | 
| -  response->setConnectionReused(info.load_timing.socket_reused); | 
| -  response->setDownloadFilePath(info.download_file_path.AsUTF16Unsafe()); | 
| -  WebURLResponseExtraDataImpl* extra_data = | 
| -      new WebURLResponseExtraDataImpl(info.npn_negotiated_protocol); | 
| -  response->setExtraData(extra_data); | 
| -  extra_data->set_was_fetched_via_spdy(info.was_fetched_via_spdy); | 
| -  extra_data->set_was_npn_negotiated(info.was_npn_negotiated); | 
| -  extra_data->set_was_alternate_protocol_available( | 
| -      info.was_alternate_protocol_available); | 
| -  extra_data->set_connection_info(info.connection_info); | 
| -  extra_data->set_was_fetched_via_proxy(info.was_fetched_via_proxy); | 
| - | 
| -  // If there's no received headers end time, don't set load timing.  This is | 
| -  // the case for non-HTTP requests, requests that don't go over the wire, and | 
| -  // certain error cases. | 
| -  if (!info.load_timing.receive_headers_end.is_null()) { | 
| -    WebURLLoadTiming timing; | 
| -    PopulateURLLoadTiming(info.load_timing, &timing); | 
| -    response->setLoadTiming(timing); | 
| -  } | 
| - | 
| -  if (info.devtools_info.get()) { | 
| -    WebHTTPLoadInfo load_info; | 
| - | 
| -    load_info.setHTTPStatusCode(info.devtools_info->http_status_code); | 
| -    load_info.setHTTPStatusText(WebString::fromUTF8( | 
| -        info.devtools_info->http_status_text)); | 
| -    load_info.setEncodedDataLength(info.encoded_data_length); | 
| - | 
| -    load_info.setRequestHeadersText(WebString::fromUTF8( | 
| -        info.devtools_info->request_headers_text)); | 
| -    load_info.setResponseHeadersText(WebString::fromUTF8( | 
| -        info.devtools_info->response_headers_text)); | 
| -    const HeadersVector& request_headers = info.devtools_info->request_headers; | 
| -    for (HeadersVector::const_iterator it = request_headers.begin(); | 
| -         it != request_headers.end(); ++it) { | 
| -      load_info.addRequestHeader(WebString::fromUTF8(it->first), | 
| -          WebString::fromUTF8(it->second)); | 
| +    private: | 
| +        int load_flags_; | 
| +        std::string buffer_; | 
| +        bool has_accept_header_; | 
| +    }; | 
| + | 
| +    // Extracts the information from a data: url. | 
| +    bool GetInfoFromDataURL(const GURL& url, | 
| +                            ResourceResponseInfo* info, | 
| +                            std::string* data, | 
| +                            int* error_code) | 
| +    { | 
| +        std::string mime_type; | 
| +        std::string charset; | 
| +        if (net::DataURL::Parse(url, &mime_type, &charset, data)) { | 
| +            *error_code = net::OK; | 
| +            // Assure same time for all time fields of data: URLs. | 
| +            Time now = Time::Now(); | 
| +            info->load_timing.request_start = TimeTicks::Now(); | 
| +            info->load_timing.request_start_time = now; | 
| +            info->request_time = now; | 
| +            info->response_time = now; | 
| +            info->headers = NULL; | 
| +            info->mime_type.swap(mime_type); | 
| +            info->charset.swap(charset); | 
| +            info->security_info.clear(); | 
| +            info->content_length = data->length(); | 
| +            info->encoded_data_length = 0; | 
| + | 
| +            return true; | 
| +        } | 
| + | 
| +        *error_code = net::ERR_INVALID_URL; | 
| +        return false; | 
| } | 
| -    const HeadersVector& response_headers = | 
| -        info.devtools_info->response_headers; | 
| -    for (HeadersVector::const_iterator it = response_headers.begin(); | 
| -         it != response_headers.end(); ++it) { | 
| -      load_info.addResponseHeader(WebString::fromUTF8(it->first), | 
| -          WebString::fromUTF8(it->second)); | 
| + | 
| +    typedef ResourceDevToolsInfo::HeadersVector HeadersVector; | 
| + | 
| +    // Converts timing data from |load_timing| to the format used by WebKit. | 
| +    void PopulateURLLoadTiming(const net::LoadTimingInfo& load_timing, | 
| +                               WebURLLoadTiming* url_timing) | 
| +    { | 
| +        DCHECK(!load_timing.request_start.is_null()); | 
| + | 
| +        const TimeTicks kNullTicks; | 
| +        url_timing->initialize(); | 
| +        url_timing->setRequestTime( | 
| +            (load_timing.request_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setProxyStart( | 
| +            (load_timing.proxy_resolve_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setProxyEnd( | 
| +            (load_timing.proxy_resolve_end - kNullTicks).InSecondsF()); | 
| +        url_timing->setDNSStart( | 
| +            (load_timing.connect_timing.dns_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setDNSEnd( | 
| +            (load_timing.connect_timing.dns_end - kNullTicks).InSecondsF()); | 
| +        url_timing->setConnectStart( | 
| +            (load_timing.connect_timing.connect_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setConnectEnd( | 
| +            (load_timing.connect_timing.connect_end - kNullTicks).InSecondsF()); | 
| +        url_timing->setSSLStart( | 
| +            (load_timing.connect_timing.ssl_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setSSLEnd( | 
| +            (load_timing.connect_timing.ssl_end - kNullTicks).InSecondsF()); | 
| +        url_timing->setSendStart( | 
| +            (load_timing.send_start - kNullTicks).InSecondsF()); | 
| +        url_timing->setSendEnd( | 
| +            (load_timing.send_end - kNullTicks).InSecondsF()); | 
| +        url_timing->setReceiveHeadersEnd( | 
| +            (load_timing.receive_headers_end - kNullTicks).InSecondsF()); | 
| } | 
| -    response->setHTTPLoadInfo(load_info); | 
| -  } | 
| - | 
| -  const net::HttpResponseHeaders* headers = info.headers.get(); | 
| -  if (!headers) | 
| -    return; | 
| - | 
| -  WebURLResponse::HTTPVersion version = WebURLResponse::Unknown; | 
| -  if (headers->GetHttpVersion() == net::HttpVersion(0, 9)) | 
| -    version = WebURLResponse::HTTP_0_9; | 
| -  else if (headers->GetHttpVersion() == net::HttpVersion(1, 0)) | 
| -    version = WebURLResponse::HTTP_1_0; | 
| -  else if (headers->GetHttpVersion() == net::HttpVersion(1, 1)) | 
| -    version = WebURLResponse::HTTP_1_1; | 
| -  response->setHTTPVersion(version); | 
| -  response->setHTTPStatusCode(headers->response_code()); | 
| -  response->setHTTPStatusText(WebString::fromUTF8(headers->GetStatusText())); | 
| - | 
| -  // TODO(darin): We should leverage HttpResponseHeaders for this, and this | 
| -  // should be using the same code as ResourceDispatcherHost. | 
| -  // TODO(jungshik): Figure out the actual value of the referrer charset and | 
| -  // pass it to GetSuggestedFilename. | 
| -  std::string value; | 
| -  headers->EnumerateHeader(NULL, "content-disposition", &value); | 
| -  response->setSuggestedFileName( | 
| -      net::GetSuggestedFilename(url, | 
| -                                value, | 
| -                                std::string(),  // referrer_charset | 
| -                                std::string(),  // suggested_name | 
| -                                std::string(),  // mime_type | 
| -                                std::string()));  // default_name | 
| - | 
| -  Time time_val; | 
| -  if (headers->GetLastModifiedValue(&time_val)) | 
| -    response->setLastModifiedDate(time_val.ToDoubleT()); | 
| - | 
| -  // Build up the header map. | 
| -  void* iter = NULL; | 
| -  std::string name; | 
| -  while (headers->EnumerateHeaderLines(&iter, &name, &value)) { | 
| -    response->addHTTPHeaderField(WebString::fromUTF8(name), | 
| -                                 WebString::fromUTF8(value)); | 
| -  } | 
| -} | 
|  | 
| -net::RequestPriority ConvertWebKitPriorityToNetPriority( | 
| -    const WebURLRequest::Priority& priority) { | 
| -  switch (priority) { | 
| -    case WebURLRequest::PriorityVeryHigh: | 
| -      return net::HIGHEST; | 
| +    void PopulateURLResponse( | 
| +        const GURL& url, | 
| +        const ResourceResponseInfo& info, | 
| +        WebURLResponse* response) | 
| +    { | 
| +        response->setURL(url); | 
| +        response->setResponseTime(info.response_time.ToDoubleT()); | 
| +        response->setMIMEType(WebString::fromUTF8(info.mime_type)); | 
| +        response->setTextEncodingName(WebString::fromUTF8(info.charset)); | 
| +        response->setExpectedContentLength(info.content_length); | 
| +        response->setSecurityInfo(info.security_info); | 
| +        response->setAppCacheID(info.appcache_id); | 
| +        response->setAppCacheManifestURL(info.appcache_manifest_url); | 
| +        response->setWasCached(!info.load_timing.request_start_time.is_null() && info.response_time < info.load_timing.request_start_time); | 
| +        response->setRemoteIPAddress( | 
| +            WebString::fromUTF8(info.socket_address.host())); | 
| +        response->setRemotePort(info.socket_address.port()); | 
| +        response->setConnectionID(info.load_timing.socket_log_id); | 
| +        response->setConnectionReused(info.load_timing.socket_reused); | 
| +        response->setDownloadFilePath(info.download_file_path.AsUTF16Unsafe()); | 
| +        WebURLResponseExtraDataImpl* extra_data = new WebURLResponseExtraDataImpl(info.npn_negotiated_protocol); | 
| +        response->setExtraData(extra_data); | 
| +        extra_data->set_was_fetched_via_spdy(info.was_fetched_via_spdy); | 
| +        extra_data->set_was_npn_negotiated(info.was_npn_negotiated); | 
| +        extra_data->set_was_alternate_protocol_available( | 
| +            info.was_alternate_protocol_available); | 
| +        extra_data->set_connection_info(info.connection_info); | 
| +        extra_data->set_was_fetched_via_proxy(info.was_fetched_via_proxy); | 
| + | 
| +        // If there's no received headers end time, don't set load timing.  This is | 
| +        // the case for non-HTTP requests, requests that don't go over the wire, and | 
| +        // certain error cases. | 
| +        if (!info.load_timing.receive_headers_end.is_null()) { | 
| +            WebURLLoadTiming timing; | 
| +            PopulateURLLoadTiming(info.load_timing, &timing); | 
| +            response->setLoadTiming(timing); | 
| +        } | 
|  | 
| -    case WebURLRequest::PriorityHigh: | 
| -      return net::MEDIUM; | 
| +        if (info.devtools_info.get()) { | 
| +            WebHTTPLoadInfo load_info; | 
| + | 
| +            load_info.setHTTPStatusCode(info.devtools_info->http_status_code); | 
| +            load_info.setHTTPStatusText(WebString::fromUTF8( | 
| +                info.devtools_info->http_status_text)); | 
| +            load_info.setEncodedDataLength(info.encoded_data_length); | 
| + | 
| +            load_info.setRequestHeadersText(WebString::fromUTF8( | 
| +                info.devtools_info->request_headers_text)); | 
| +            load_info.setResponseHeadersText(WebString::fromUTF8( | 
| +                info.devtools_info->response_headers_text)); | 
| +            const HeadersVector& request_headers = info.devtools_info->request_headers; | 
| +            for (HeadersVector::const_iterator it = request_headers.begin(); | 
| +                 it != request_headers.end(); ++it) { | 
| +                load_info.addRequestHeader(WebString::fromUTF8(it->first), | 
| +                                           WebString::fromUTF8(it->second)); | 
| +            } | 
| +            const HeadersVector& response_headers = info.devtools_info->response_headers; | 
| +            for (HeadersVector::const_iterator it = response_headers.begin(); | 
| +                 it != response_headers.end(); ++it) { | 
| +                load_info.addResponseHeader(WebString::fromUTF8(it->first), | 
| +                                            WebString::fromUTF8(it->second)); | 
| +            } | 
| +            response->setHTTPLoadInfo(load_info); | 
| +        } | 
|  | 
| -    case WebURLRequest::PriorityMedium: | 
| -      return net::LOW; | 
| +        const net::HttpResponseHeaders* headers = info.headers.get(); | 
| +        if (!headers) | 
| +            return; | 
| + | 
| +        WebURLResponse::HTTPVersion version = WebURLResponse::Unknown; | 
| +        if (headers->GetHttpVersion() == net::HttpVersion(0, 9)) | 
| +            version = WebURLResponse::HTTP_0_9; | 
| +        else if (headers->GetHttpVersion() == net::HttpVersion(1, 0)) | 
| +            version = WebURLResponse::HTTP_1_0; | 
| +        else if (headers->GetHttpVersion() == net::HttpVersion(1, 1)) | 
| +            version = WebURLResponse::HTTP_1_1; | 
| +        response->setHTTPVersion(version); | 
| +        response->setHTTPStatusCode(headers->response_code()); | 
| +        response->setHTTPStatusText(WebString::fromUTF8(headers->GetStatusText())); | 
| + | 
| +        // TODO(darin): We should leverage HttpResponseHeaders for this, and this | 
| +        // should be using the same code as ResourceDispatcherHost. | 
| +        // TODO(jungshik): Figure out the actual value of the referrer charset and | 
| +        // pass it to GetSuggestedFilename. | 
| +        std::string value; | 
| +        headers->EnumerateHeader(NULL, "content-disposition", &value); | 
| +        response->setSuggestedFileName( | 
| +            net::GetSuggestedFilename(url, | 
| +                                      value, | 
| +                                      std::string(), // referrer_charset | 
| +                                      std::string(), // suggested_name | 
| +                                      std::string(), // mime_type | 
| +                                      std::string())); // default_name | 
| + | 
| +        Time time_val; | 
| +        if (headers->GetLastModifiedValue(&time_val)) | 
| +            response->setLastModifiedDate(time_val.ToDoubleT()); | 
| + | 
| +        // Build up the header map. | 
| +        void* iter = NULL; | 
| +        std::string name; | 
| +        while (headers->EnumerateHeaderLines(&iter, &name, &value)) { | 
| +            response->addHTTPHeaderField(WebString::fromUTF8(name), | 
| +                                         WebString::fromUTF8(value)); | 
| +        } | 
| +    } | 
|  | 
| -    case WebURLRequest::PriorityLow: | 
| -      return net::LOWEST; | 
| +    net::RequestPriority ConvertWebKitPriorityToNetPriority( | 
| +        const WebURLRequest::Priority& priority) | 
| +    { | 
| +        switch (priority) { | 
| +        case WebURLRequest::PriorityVeryHigh: | 
| +            return net::HIGHEST; | 
|  | 
| -    case WebURLRequest::PriorityVeryLow: | 
| -      return net::IDLE; | 
| +        case WebURLRequest::PriorityHigh: | 
| +            return net::MEDIUM; | 
|  | 
| -    case WebURLRequest::PriorityUnresolved: | 
| -    default: | 
| -      NOTREACHED(); | 
| -      return net::LOW; | 
| -  } | 
| -} | 
| +        case WebURLRequest::PriorityMedium: | 
| +            return net::LOW; | 
| + | 
| +        case WebURLRequest::PriorityLow: | 
| +            return net::LOWEST; | 
| + | 
| +        case WebURLRequest::PriorityVeryLow: | 
| +            return net::IDLE; | 
|  | 
| -}  // namespace | 
| +        case WebURLRequest::PriorityUnresolved: | 
| +        default: | 
| +            NOTREACHED(); | 
| +            return net::LOW; | 
| +        } | 
| +    } | 
| + | 
| +} // namespace | 
|  | 
| // WebURLLoaderImpl::Context -------------------------------------------------- | 
|  | 
| @@ -324,530 +326,571 @@ net::RequestPriority ConvertWebKitPriorityToNetPriority( | 
| // until it receives OnCompletedRequest. | 
| class WebURLLoaderImpl::Context : public base::RefCounted<Context>, | 
| public ResourceLoaderBridge::Peer { | 
| - public: | 
| -  explicit Context(WebURLLoaderImpl* loader); | 
| - | 
| -  WebURLLoaderClient* client() const { return client_; } | 
| -  void set_client(WebURLLoaderClient* client) { client_ = client; } | 
| - | 
| -  void Cancel(); | 
| -  void SetDefersLoading(bool value); | 
| -  void DidChangePriority(WebURLRequest::Priority new_priority); | 
| -  void Start( | 
| -      const WebURLRequest& request, | 
| -      ResourceLoaderBridge::SyncLoadResponse* sync_load_response, | 
| -      WebKitPlatformSupportImpl* platform); | 
| - | 
| -  // ResourceLoaderBridge::Peer methods: | 
| -  virtual void OnUploadProgress(uint64 position, uint64 size) OVERRIDE; | 
| -  virtual bool OnReceivedRedirect( | 
| -      const GURL& new_url, | 
| -      const ResourceResponseInfo& info, | 
| -      bool* has_new_first_party_for_cookies, | 
| -      GURL* new_first_party_for_cookies) OVERRIDE; | 
| -  virtual void OnReceivedResponse(const ResourceResponseInfo& info) OVERRIDE; | 
| -  virtual void OnDownloadedData(int len) OVERRIDE; | 
| -  virtual void OnReceivedData(const char* data, | 
| -                              int data_length, | 
| -                              int encoded_data_length) OVERRIDE; | 
| -  virtual void OnReceivedCachedMetadata(const char* data, int len) OVERRIDE; | 
| -  virtual void OnCompletedRequest( | 
| -      int error_code, | 
| -      bool was_ignored_by_handler, | 
| -      const std::string& security_info, | 
| -      const base::TimeTicks& completion_time) OVERRIDE; | 
| - | 
| - private: | 
| -  friend class base::RefCounted<Context>; | 
| -  virtual ~Context() {} | 
| - | 
| -  // We can optimize the handling of data URLs in most cases. | 
| -  bool CanHandleDataURL(const GURL& url) const; | 
| -  void HandleDataURL(); | 
| - | 
| -  WebURLLoaderImpl* loader_; | 
| -  WebURLRequest request_; | 
| -  WebURLLoaderClient* client_; | 
| -  WebReferrerPolicy referrer_policy_; | 
| -  scoped_ptr<ResourceLoaderBridge> bridge_; | 
| -  scoped_ptr<FtpDirectoryListingResponseDelegate> ftp_listing_delegate_; | 
| -  scoped_ptr<MultipartResponseDelegate> multipart_delegate_; | 
| -  scoped_ptr<ResourceLoaderBridge> completed_bridge_; | 
| +public: | 
| +    explicit Context(WebURLLoaderImpl* loader); | 
| + | 
| +    WebURLLoaderClient* client() const | 
| +    { | 
| +        return client_; | 
| +    } | 
| +    void set_client(WebURLLoaderClient* client) | 
| +    { | 
| +        client_ = client; | 
| +    } | 
| + | 
| +    void Cancel(); | 
| +    void SetDefersLoading(bool value); | 
| +    void DidChangePriority(WebURLRequest::Priority new_priority); | 
| +    void Start( | 
| +        const WebURLRequest& request, | 
| +        ResourceLoaderBridge::SyncLoadResponse* sync_load_response, | 
| +        WebKitPlatformSupportImpl* platform); | 
| + | 
| +    // ResourceLoaderBridge::Peer methods: | 
| +    virtual void OnUploadProgress(uint64 position, uint64 size) OVERRIDE; | 
| +    virtual bool OnReceivedRedirect( | 
| +        const GURL& new_url, | 
| +        const ResourceResponseInfo& info, | 
| +        bool* has_new_first_party_for_cookies, | 
| +        GURL* new_first_party_for_cookies) OVERRIDE; | 
| +    virtual void OnReceivedResponse(const ResourceResponseInfo& info) OVERRIDE; | 
| +    virtual void OnDownloadedData(int len) OVERRIDE; | 
| +    virtual void OnReceivedData(const char* data, | 
| +                                int data_length, | 
| +                                int encoded_data_length) OVERRIDE; | 
| +    virtual void OnReceivedCachedMetadata(const char* data, int len) OVERRIDE; | 
| +    virtual void OnCompletedRequest( | 
| +        int error_code, | 
| +        bool was_ignored_by_handler, | 
| +        const std::string& security_info, | 
| +        const base::TimeTicks& completion_time) OVERRIDE; | 
| + | 
| +private: | 
| +    friend class base::RefCounted<Context>; | 
| +    virtual ~Context() | 
| +    { | 
| +    } | 
| + | 
| +    // We can optimize the handling of data URLs in most cases. | 
| +    bool CanHandleDataURL(const GURL& url) const; | 
| +    void HandleDataURL(); | 
| + | 
| +    WebURLLoaderImpl* loader_; | 
| +    WebURLRequest request_; | 
| +    WebURLLoaderClient* client_; | 
| +    WebReferrerPolicy referrer_policy_; | 
| +    scoped_ptr<ResourceLoaderBridge> bridge_; | 
| +    scoped_ptr<FtpDirectoryListingResponseDelegate> ftp_listing_delegate_; | 
| +    scoped_ptr<MultipartResponseDelegate> multipart_delegate_; | 
| +    scoped_ptr<ResourceLoaderBridge> completed_bridge_; | 
| + | 
| +    // TODO(dsjang): A temporary hack to connect the lastest response | 
| +    // observed by OnReceiveResponse() and the data stream received by OnReceivedData(). | 
| +    WebURL response_url_; | 
| }; | 
|  | 
| WebURLLoaderImpl::Context::Context(WebURLLoaderImpl* loader) | 
| -    : loader_(loader), | 
| -      client_(NULL), | 
| -      referrer_policy_(WebKit::WebReferrerPolicyDefault) { | 
| +    : loader_(loader) | 
| +    , client_(NULL) | 
| +    , referrer_policy_(WebKit::WebReferrerPolicyDefault) | 
| +{ | 
| } | 
|  | 
| -void WebURLLoaderImpl::Context::Cancel() { | 
| -  // The bridge will still send OnCompletedRequest, which will Release() us, so | 
| -  // we don't do that here. | 
| -  if (bridge_) | 
| -    bridge_->Cancel(); | 
| - | 
| -  // Ensure that we do not notify the multipart delegate anymore as it has | 
| -  // its own pointer to the client. | 
| -  if (multipart_delegate_) | 
| -    multipart_delegate_->Cancel(); | 
| - | 
| -  // Do not make any further calls to the client. | 
| -  client_ = NULL; | 
| -  loader_ = NULL; | 
| +void WebURLLoaderImpl::Context::Cancel() | 
| +{ | 
| +    // The bridge will still send OnCompletedRequest, which will Release() us, so | 
| +    // we don't do that here. | 
| +    if (bridge_) | 
| +        bridge_->Cancel(); | 
| + | 
| +    // Ensure that we do not notify the multipart delegate anymore as it has | 
| +    // its own pointer to the client. | 
| +    if (multipart_delegate_) | 
| +        multipart_delegate_->Cancel(); | 
| + | 
| +    // Do not make any further calls to the client. | 
| +    client_ = NULL; | 
| +    loader_ = NULL; | 
| } | 
|  | 
| -void WebURLLoaderImpl::Context::SetDefersLoading(bool value) { | 
| -  if (bridge_) | 
| -    bridge_->SetDefersLoading(value); | 
| +void WebURLLoaderImpl::Context::SetDefersLoading(bool value) | 
| +{ | 
| +    if (bridge_) | 
| +        bridge_->SetDefersLoading(value); | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::DidChangePriority( | 
| -    WebURLRequest::Priority new_priority) { | 
| -  if (bridge_) | 
| -    bridge_->DidChangePriority( | 
| -        ConvertWebKitPriorityToNetPriority(new_priority)); | 
| +    WebURLRequest::Priority new_priority) | 
| +{ | 
| +    if (bridge_) | 
| +        bridge_->DidChangePriority( | 
| +            ConvertWebKitPriorityToNetPriority(new_priority)); | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::Start( | 
| const WebURLRequest& request, | 
| ResourceLoaderBridge::SyncLoadResponse* sync_load_response, | 
| -    WebKitPlatformSupportImpl* platform) { | 
| -  DCHECK(!bridge_.get()); | 
| - | 
| -  request_ = request;  // Save the request. | 
| - | 
| -  GURL url = request.url(); | 
| -  if (url.SchemeIs("data") && CanHandleDataURL(url)) { | 
| -    if (sync_load_response) { | 
| -      // This is a sync load. Do the work now. | 
| -      sync_load_response->url = url; | 
| -      std::string data; | 
| -      GetInfoFromDataURL(sync_load_response->url, sync_load_response, | 
| -                         &sync_load_response->data, | 
| -                         &sync_load_response->error_code); | 
| -    } else { | 
| -      AddRef();  // Balanced in OnCompletedRequest | 
| -      base::MessageLoop::current()->PostTask( | 
| -          FROM_HERE, base::Bind(&Context::HandleDataURL, this)); | 
| +    WebKitPlatformSupportImpl* platform) | 
| +{ | 
| +    DCHECK(!bridge_.get()); | 
| + | 
| +    request_ = request; // Save the request. | 
| + | 
| +    GURL url = request.url(); | 
| +    if (url.SchemeIs("data") && CanHandleDataURL(url)) { | 
| +        if (sync_load_response) { | 
| +            // This is a sync load. Do the work now. | 
| +            sync_load_response->url = url; | 
| +            std::string data; | 
| +            GetInfoFromDataURL(sync_load_response->url, sync_load_response, | 
| +                               &sync_load_response->data, | 
| +                               &sync_load_response->error_code); | 
| +        } else { | 
| +            AddRef(); // Balanced in OnCompletedRequest | 
| +            base::MessageLoop::current()->PostTask( | 
| +                FROM_HERE, base::Bind(&Context::HandleDataURL, this)); | 
| +        } | 
| +        return; | 
| } | 
| -    return; | 
| -  } | 
|  | 
| -  GURL referrer_url( | 
| -      request.httpHeaderField(WebString::fromUTF8("Referer")).utf8()); | 
| -  const std::string& method = request.httpMethod().utf8(); | 
| +    GURL referrer_url( | 
| +        request.httpHeaderField(WebString::fromUTF8("Referer")).utf8()); | 
| +    const std::string& method = request.httpMethod().utf8(); | 
|  | 
| -  int load_flags = net::LOAD_NORMAL; | 
| -  switch (request.cachePolicy()) { | 
| +    int load_flags = net::LOAD_NORMAL; | 
| +    switch (request.cachePolicy()) { | 
| case WebURLRequest::ReloadIgnoringCacheData: | 
| -      // Required by LayoutTests/http/tests/misc/refresh-headers.php | 
| -      load_flags |= net::LOAD_VALIDATE_CACHE; | 
| -      break; | 
| +        // Required by LayoutTests/http/tests/misc/refresh-headers.php | 
| +        load_flags |= net::LOAD_VALIDATE_CACHE; | 
| +        break; | 
| case WebURLRequest::ReturnCacheDataElseLoad: | 
| -      load_flags |= net::LOAD_PREFERRING_CACHE; | 
| -      break; | 
| +        load_flags |= net::LOAD_PREFERRING_CACHE; | 
| +        break; | 
| case WebURLRequest::ReturnCacheDataDontLoad: | 
| -      load_flags |= net::LOAD_ONLY_FROM_CACHE; | 
| -      break; | 
| +        load_flags |= net::LOAD_ONLY_FROM_CACHE; | 
| +        break; | 
| case WebURLRequest::UseProtocolCachePolicy: | 
| -      break; | 
| -  } | 
| - | 
| -  if (request.reportUploadProgress()) | 
| -    load_flags |= net::LOAD_ENABLE_UPLOAD_PROGRESS; | 
| -  if (request.reportLoadTiming()) | 
| -    load_flags |= net::LOAD_ENABLE_LOAD_TIMING; | 
| -  if (request.reportRawHeaders()) | 
| -    load_flags |= net::LOAD_REPORT_RAW_HEADERS; | 
| - | 
| -  if (!request.allowCookies() || !request.allowStoredCredentials()) { | 
| -    load_flags |= net::LOAD_DO_NOT_SAVE_COOKIES; | 
| -    load_flags |= net::LOAD_DO_NOT_SEND_COOKIES; | 
| -  } | 
| - | 
| -  if (!request.allowStoredCredentials()) | 
| -    load_flags |= net::LOAD_DO_NOT_SEND_AUTH_DATA; | 
| - | 
| -  HeaderFlattener flattener(load_flags); | 
| -  request.visitHTTPHeaderFields(&flattener); | 
| - | 
| -  // TODO(brettw) this should take parameter encoding into account when | 
| -  // creating the GURLs. | 
| - | 
| -  ResourceLoaderBridge::RequestInfo request_info; | 
| -  request_info.method = method; | 
| -  request_info.url = url; | 
| -  request_info.first_party_for_cookies = request.firstPartyForCookies(); | 
| -  request_info.referrer = referrer_url; | 
| -  request_info.headers = flattener.GetBuffer(); | 
| -  request_info.load_flags = load_flags; | 
| -  // requestor_pid only needs to be non-zero if the request originates outside | 
| -  // the render process, so we can use requestorProcessID even for requests | 
| -  // from in-process plugins. | 
| -  request_info.requestor_pid = request.requestorProcessID(); | 
| -  request_info.request_type = | 
| -      ResourceType::FromTargetType(request.targetType()); | 
| -  request_info.priority = | 
| -      ConvertWebKitPriorityToNetPriority(request.priority()); | 
| -  request_info.appcache_host_id = request.appCacheHostID(); | 
| -  request_info.routing_id = request.requestorID(); | 
| -  request_info.download_to_file = request.downloadToFile(); | 
| -  request_info.has_user_gesture = request.hasUserGesture(); | 
| -  request_info.extra_data = request.extraData(); | 
| -  if (request.extraData()) { | 
| -    referrer_policy_ = static_cast<WebURLRequestExtraDataImpl*>( | 
| -        request.extraData())->referrer_policy(); | 
| -    request_info.referrer_policy = referrer_policy_; | 
| -  } | 
| -  bridge_.reset(platform->CreateResourceLoader(request_info)); | 
| - | 
| -  if (!request.httpBody().isNull()) { | 
| -    // GET and HEAD requests shouldn't have http bodies. | 
| -    DCHECK(method != "GET" && method != "HEAD"); | 
| -    const WebHTTPBody& httpBody = request.httpBody(); | 
| -    size_t i = 0; | 
| -    WebHTTPBody::Element element; | 
| -    scoped_refptr<ResourceRequestBody> request_body = new ResourceRequestBody; | 
| -    while (httpBody.elementAt(i++, element)) { | 
| -      switch (element.type) { | 
| -        case WebHTTPBody::Element::TypeData: | 
| -          if (!element.data.isEmpty()) { | 
| -            // WebKit sometimes gives up empty data to append. These aren't | 
| -            // necessary so we just optimize those out here. | 
| -            request_body->AppendBytes( | 
| -                element.data.data(), static_cast<int>(element.data.size())); | 
| -          } | 
| -          break; | 
| -        case WebHTTPBody::Element::TypeFile: | 
| -          if (element.fileLength == -1) { | 
| -            request_body->AppendFileRange( | 
| -                base::FilePath::FromUTF16Unsafe(element.filePath), | 
| -                0, kuint64max, base::Time()); | 
| -          } else { | 
| -            request_body->AppendFileRange( | 
| -                base::FilePath::FromUTF16Unsafe(element.filePath), | 
| -                static_cast<uint64>(element.fileStart), | 
| -                static_cast<uint64>(element.fileLength), | 
| -                base::Time::FromDoubleT(element.modificationTime)); | 
| -          } | 
| -          break; | 
| -        case WebHTTPBody::Element::TypeURL: { | 
| -          GURL url = GURL(element.url); | 
| -          DCHECK(url.SchemeIsFileSystem()); | 
| -          request_body->AppendFileSystemFileRange( | 
| -              url, | 
| -              static_cast<uint64>(element.fileStart), | 
| -              static_cast<uint64>(element.fileLength), | 
| -              base::Time::FromDoubleT(element.modificationTime)); | 
| -          break; | 
| +        break; | 
| +    } | 
| + | 
| +    if (request.reportUploadProgress()) | 
| +        load_flags |= net::LOAD_ENABLE_UPLOAD_PROGRESS; | 
| +    if (request.reportLoadTiming()) | 
| +        load_flags |= net::LOAD_ENABLE_LOAD_TIMING; | 
| +    if (request.reportRawHeaders()) | 
| +        load_flags |= net::LOAD_REPORT_RAW_HEADERS; | 
| + | 
| +    if (!request.allowCookies() || !request.allowStoredCredentials()) { | 
| +        load_flags |= net::LOAD_DO_NOT_SAVE_COOKIES; | 
| +        load_flags |= net::LOAD_DO_NOT_SEND_COOKIES; | 
| +    } | 
| + | 
| +    if (!request.allowStoredCredentials()) | 
| +        load_flags |= net::LOAD_DO_NOT_SEND_AUTH_DATA; | 
| + | 
| +    HeaderFlattener flattener(load_flags); | 
| +    request.visitHTTPHeaderFields(&flattener); | 
| + | 
| +    // TODO(brettw) this should take parameter encoding into account when | 
| +    // creating the GURLs. | 
| + | 
| +    ResourceLoaderBridge::RequestInfo request_info; | 
| +    request_info.method = method; | 
| +    request_info.url = url; | 
| +    request_info.first_party_for_cookies = request.firstPartyForCookies(); | 
| +    request_info.referrer = referrer_url; | 
| +    request_info.headers = flattener.GetBuffer(); | 
| +    request_info.load_flags = load_flags; | 
| +    // requestor_pid only needs to be non-zero if the request originates outside | 
| +    // the render process, so we can use requestorProcessID even for requests | 
| +    // from in-process plugins. | 
| +    request_info.requestor_pid = request.requestorProcessID(); | 
| +    request_info.request_type = ResourceType::FromTargetType(request.targetType()); | 
| +    request_info.priority = ConvertWebKitPriorityToNetPriority(request.priority()); | 
| +    request_info.appcache_host_id = request.appCacheHostID(); | 
| +    request_info.routing_id = request.requestorID(); | 
| +    request_info.download_to_file = request.downloadToFile(); | 
| +    request_info.has_user_gesture = request.hasUserGesture(); | 
| +    request_info.extra_data = request.extraData(); | 
| +    if (request.extraData()) { | 
| +        referrer_policy_ = static_cast<WebURLRequestExtraDataImpl*>( | 
| +            request.extraData())->referrer_policy(); | 
| +        request_info.referrer_policy = referrer_policy_; | 
| +    } | 
| +    bridge_.reset(platform->CreateResourceLoader(request_info)); | 
| + | 
| +    if (!request.httpBody().isNull()) { | 
| +        // GET and HEAD requests shouldn't have http bodies. | 
| +        DCHECK(method != "GET" && method != "HEAD"); | 
| +        const WebHTTPBody& httpBody = request.httpBody(); | 
| +        size_t i = 0; | 
| +        WebHTTPBody::Element element; | 
| +        scoped_refptr<ResourceRequestBody> request_body = new ResourceRequestBody; | 
| +        while (httpBody.elementAt(i++, element)) { | 
| +            switch (element.type) { | 
| +            case WebHTTPBody::Element::TypeData: | 
| +                if (!element.data.isEmpty()) { | 
| +                    // WebKit sometimes gives up empty data to append. These aren't | 
| +                    // necessary so we just optimize those out here. | 
| +                    request_body->AppendBytes( | 
| +                        element.data.data(), static_cast<int>(element.data.size())); | 
| +                } | 
| +                break; | 
| +            case WebHTTPBody::Element::TypeFile: | 
| +                if (element.fileLength == -1) { | 
| +                    request_body->AppendFileRange( | 
| +                        base::FilePath::FromUTF16Unsafe(element.filePath), | 
| +                        0, kuint64max, base::Time()); | 
| +                } else { | 
| +                    request_body->AppendFileRange( | 
| +                        base::FilePath::FromUTF16Unsafe(element.filePath), | 
| +                        static_cast<uint64>(element.fileStart), | 
| +                        static_cast<uint64>(element.fileLength), | 
| +                        base::Time::FromDoubleT(element.modificationTime)); | 
| +                } | 
| +                break; | 
| +            case WebHTTPBody::Element::TypeURL: { | 
| +                GURL url = GURL(element.url); | 
| +                DCHECK(url.SchemeIsFileSystem()); | 
| +                request_body->AppendFileSystemFileRange( | 
| +                    url, | 
| +                    static_cast<uint64>(element.fileStart), | 
| +                    static_cast<uint64>(element.fileLength), | 
| +                    base::Time::FromDoubleT(element.modificationTime)); | 
| +                break; | 
| +            } | 
| +            case WebHTTPBody::Element::TypeBlob: | 
| +                request_body->AppendBlob(GURL(element.blobURL)); | 
| +                break; | 
| +            default: | 
| +                NOTREACHED(); | 
| +            } | 
| } | 
| -        case WebHTTPBody::Element::TypeBlob: | 
| -          request_body->AppendBlob(GURL(element.blobURL)); | 
| -          break; | 
| -        default: | 
| -          NOTREACHED(); | 
| -      } | 
| +        request_body->set_identifier(request.httpBody().identifier()); | 
| +        bridge_->SetRequestBody(request_body.get()); | 
| +    } | 
| + | 
| +    if (sync_load_response) { | 
| +        bridge_->SyncLoad(sync_load_response); | 
| +        return; | 
| +    } | 
| + | 
| +    if (bridge_->Start(this)) { | 
| +        AddRef(); // Balanced in OnCompletedRequest | 
| +    } else { | 
| +        bridge_.reset(); | 
| } | 
| -    request_body->set_identifier(request.httpBody().identifier()); | 
| -    bridge_->SetRequestBody(request_body.get()); | 
| -  } | 
| - | 
| -  if (sync_load_response) { | 
| -    bridge_->SyncLoad(sync_load_response); | 
| -    return; | 
| -  } | 
| - | 
| -  if (bridge_->Start(this)) { | 
| -    AddRef();  // Balanced in OnCompletedRequest | 
| -  } else { | 
| -    bridge_.reset(); | 
| -  } | 
| } | 
|  | 
| -void WebURLLoaderImpl::Context::OnUploadProgress(uint64 position, uint64 size) { | 
| -  if (client_) | 
| -    client_->didSendData(loader_, position, size); | 
| +void WebURLLoaderImpl::Context::OnUploadProgress(uint64 position, uint64 size) | 
| +{ | 
| +    if (client_) | 
| +        client_->didSendData(loader_, position, size); | 
| } | 
|  | 
| bool WebURLLoaderImpl::Context::OnReceivedRedirect( | 
| const GURL& new_url, | 
| const ResourceResponseInfo& info, | 
| bool* has_new_first_party_for_cookies, | 
| -    GURL* new_first_party_for_cookies) { | 
| -  if (!client_) | 
| +    GURL* new_first_party_for_cookies) | 
| +{ | 
| +    if (!client_) | 
| +        return false; | 
| + | 
| +    WebURLResponse response; | 
| +    response.initialize(); | 
| +    PopulateURLResponse(request_.url(), info, &response); | 
| + | 
| +    // TODO(darin): We lack sufficient information to construct the actual | 
| +    // request that resulted from the redirect. | 
| +    WebURLRequest new_request(new_url); | 
| +    new_request.setFirstPartyForCookies(request_.firstPartyForCookies()); | 
| +    new_request.setDownloadToFile(request_.downloadToFile()); | 
| + | 
| +    WebString referrer_string = WebString::fromUTF8("Referer"); | 
| +    WebString referrer = WebSecurityPolicy::generateReferrerHeader( | 
| +        referrer_policy_, | 
| +        new_url, | 
| +        request_.httpHeaderField(referrer_string)); | 
| +    if (!referrer.isEmpty()) | 
| +        new_request.setHTTPHeaderField(referrer_string, referrer); | 
| + | 
| +    if (response.httpStatusCode() == 307) | 
| +        new_request.setHTTPMethod(request_.httpMethod()); | 
| + | 
| +    client_->willSendRequest(loader_, new_request, response); | 
| +    request_ = new_request; | 
| +    *has_new_first_party_for_cookies = true; | 
| +    *new_first_party_for_cookies = request_.firstPartyForCookies(); | 
| + | 
| +    // Only follow the redirect if WebKit left the URL unmodified. | 
| +    if (new_url == GURL(new_request.url())) | 
| +        return true; | 
| + | 
| +    // We assume that WebKit only changes the URL to suppress a redirect, and we | 
| +    // assume that it does so by setting it to be invalid. | 
| +    DCHECK(!new_request.url().isValid()); | 
| return false; | 
| - | 
| -  WebURLResponse response; | 
| -  response.initialize(); | 
| -  PopulateURLResponse(request_.url(), info, &response); | 
| - | 
| -  // TODO(darin): We lack sufficient information to construct the actual | 
| -  // request that resulted from the redirect. | 
| -  WebURLRequest new_request(new_url); | 
| -  new_request.setFirstPartyForCookies(request_.firstPartyForCookies()); | 
| -  new_request.setDownloadToFile(request_.downloadToFile()); | 
| - | 
| -  WebString referrer_string = WebString::fromUTF8("Referer"); | 
| -  WebString referrer = WebSecurityPolicy::generateReferrerHeader( | 
| -      referrer_policy_, | 
| -      new_url, | 
| -      request_.httpHeaderField(referrer_string)); | 
| -  if (!referrer.isEmpty()) | 
| -    new_request.setHTTPHeaderField(referrer_string, referrer); | 
| - | 
| -  if (response.httpStatusCode() == 307) | 
| -    new_request.setHTTPMethod(request_.httpMethod()); | 
| - | 
| -  client_->willSendRequest(loader_, new_request, response); | 
| -  request_ = new_request; | 
| -  *has_new_first_party_for_cookies = true; | 
| -  *new_first_party_for_cookies = request_.firstPartyForCookies(); | 
| - | 
| -  // Only follow the redirect if WebKit left the URL unmodified. | 
| -  if (new_url == GURL(new_request.url())) | 
| -    return true; | 
| - | 
| -  // We assume that WebKit only changes the URL to suppress a redirect, and we | 
| -  // assume that it does so by setting it to be invalid. | 
| -  DCHECK(!new_request.url().isValid()); | 
| -  return false; | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::OnReceivedResponse( | 
| -    const ResourceResponseInfo& info) { | 
| -  if (!client_) | 
| -    return; | 
| - | 
| -  WebURLResponse response; | 
| -  response.initialize(); | 
| -  PopulateURLResponse(request_.url(), info, &response); | 
| - | 
| -  bool show_raw_listing = (GURL(request_.url()).query() == "raw"); | 
| - | 
| -  if (info.mime_type == "text/vnd.chromium.ftp-dir") { | 
| -    if (show_raw_listing) { | 
| -      // Set the MIME type to plain text to prevent any active content. | 
| -      response.setMIMEType("text/plain"); | 
| -    } else { | 
| -      // We're going to produce a parsed listing in HTML. | 
| -      response.setMIMEType("text/html"); | 
| +    const ResourceResponseInfo& info) | 
| +{ | 
| +    if (!client_) | 
| +        return; | 
| + | 
| +    WebURLResponse response; | 
| +    response.initialize(); | 
| +    PopulateURLResponse(request_.url(), info, &response); | 
| + | 
| +    bool show_raw_listing = (GURL(request_.url()).query() == "raw"); | 
| + | 
| +    if (info.mime_type == "text/vnd.chromium.ftp-dir") { | 
| +        if (show_raw_listing) { | 
| +            // Set the MIME type to plain text to prevent any active content. | 
| +            response.setMIMEType("text/plain"); | 
| +        } else { | 
| +            // We're going to produce a parsed listing in HTML. | 
| +            response.setMIMEType("text/html"); | 
| +        } | 
| } | 
| -  } | 
| - | 
| -  scoped_refptr<Context> protect(this); | 
| -  client_->didReceiveResponse(loader_, response); | 
| - | 
| -  // We may have been cancelled after didReceiveResponse, which would leave us | 
| -  // without a client and therefore without much need to do further handling. | 
| -  if (!client_) | 
| -    return; | 
| - | 
| -  DCHECK(!ftp_listing_delegate_.get()); | 
| -  DCHECK(!multipart_delegate_.get()); | 
| -  if (info.headers.get() && info.mime_type == "multipart/x-mixed-replace") { | 
| -    std::string content_type; | 
| -    info.headers->EnumerateHeader(NULL, "content-type", &content_type); | 
| - | 
| -    std::string mime_type; | 
| -    std::string charset; | 
| -    bool had_charset = false; | 
| -    std::string boundary; | 
| -    net::HttpUtil::ParseContentType(content_type, &mime_type, &charset, | 
| -                                    &had_charset, &boundary); | 
| -    TrimString(boundary, " \"", &boundary); | 
| - | 
| -    // If there's no boundary, just handle the request normally.  In the gecko | 
| -    // code, nsMultiMixedConv::OnStartRequest throws an exception. | 
| -    if (!boundary.empty()) { | 
| -      multipart_delegate_.reset( | 
| -          new MultipartResponseDelegate(client_, loader_, response, boundary)); | 
| + | 
| +    scoped_refptr<Context> protect(this); | 
| +    client_->didReceiveResponse(loader_, response); | 
| + | 
| +    // We may have been cancelled after didReceiveResponse, which would leave us | 
| +    // without a client and therefore without much need to do further handling. | 
| +    if (!client_) | 
| +        return; | 
| + | 
| +    DCHECK(!ftp_listing_delegate_.get()); | 
| +    DCHECK(!multipart_delegate_.get()); | 
| +    if (info.headers.get() && info.mime_type == "multipart/x-mixed-replace") { | 
| +        std::string content_type; | 
| +        info.headers->EnumerateHeader(NULL, "content-type", &content_type); | 
| + | 
| +        std::string mime_type; | 
| +        std::string charset; | 
| +        bool had_charset = false; | 
| +        std::string boundary; | 
| +        net::HttpUtil::ParseContentType(content_type, &mime_type, &charset, | 
| +                                        &had_charset, &boundary); | 
| +        TrimString(boundary, " \"", &boundary); | 
| + | 
| +        // If there's no boundary, just handle the request normally.  In the gecko | 
| +        // code, nsMultiMixedConv::OnStartRequest throws an exception. | 
| +        if (!boundary.empty()) { | 
| +            multipart_delegate_.reset( | 
| +                new MultipartResponseDelegate(client_, loader_, response, boundary)); | 
| +        } | 
| +    } else if (info.mime_type == "text/vnd.chromium.ftp-dir" && !show_raw_listing) { | 
| +        ftp_listing_delegate_.reset( | 
| +            new FtpDirectoryListingResponseDelegate(client_, loader_, response)); | 
| } | 
| -  } else if (info.mime_type == "text/vnd.chromium.ftp-dir" && | 
| -             !show_raw_listing) { | 
| -    ftp_listing_delegate_.reset( | 
| -        new FtpDirectoryListingResponseDelegate(client_, loader_, response)); | 
| -  } | 
| + | 
| +    response_url_ = response.url(); | 
| } | 
|  | 
| -void WebURLLoaderImpl::Context::OnDownloadedData(int len) { | 
| -  if (client_) | 
| -    client_->didDownloadData(loader_, len); | 
| +void WebURLLoaderImpl::Context::OnDownloadedData(int len) | 
| +{ | 
| +    if (client_) | 
| +        client_->didDownloadData(loader_, len); | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::OnReceivedData(const char* data, | 
| int data_length, | 
| -                                               int encoded_data_length) { | 
| -  if (!client_) | 
| -    return; | 
| - | 
| -  if (ftp_listing_delegate_) { | 
| -    // The FTP listing delegate will make the appropriate calls to | 
| -    // client_->didReceiveData and client_->didReceiveResponse. | 
| -    ftp_listing_delegate_->OnReceivedData(data, data_length); | 
| -  } else if (multipart_delegate_) { | 
| -    // The multipart delegate will make the appropriate calls to | 
| -    // client_->didReceiveData and client_->didReceiveResponse. | 
| -    multipart_delegate_->OnReceivedData(data, data_length, encoded_data_length); | 
| -  } else { | 
| -    client_->didReceiveData(loader_, data, data_length, encoded_data_length); | 
| -  } | 
| +                                               int encoded_data_length) | 
| +{ | 
| +    if (!client_) | 
| +        return; | 
| + | 
| +    if (ftp_listing_delegate_) { | 
| +        // The FTP listing delegate will make the appropriate calls to | 
| +        // client_->didReceiveData and client_->didReceiveResponse. | 
| +        ftp_listing_delegate_->OnReceivedData(data, data_length); | 
| +    } else if (multipart_delegate_) { | 
| +        // The multipart delegate will make the appropriate calls to | 
| +        // client_->didReceiveData and client_->didReceiveResponse. | 
| +        multipart_delegate_->OnReceivedData(data, data_length, encoded_data_length); | 
| +    } else { | 
| +        client_->didReceiveData(loader_, data, data_length, encoded_data_length); | 
| +    } | 
| + | 
| +    // TODO(dsjang): This logging code is just temporary. There has to | 
| +    // be a better way to connect the received data to the response_url | 
| +    // than this. | 
| +    SiteIsolationPolicy::DidReceiveData(data, data_length, response_url_); | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::OnReceivedCachedMetadata( | 
| -    const char* data, int len) { | 
| -  if (client_) | 
| -    client_->didReceiveCachedMetadata(loader_, data, len); | 
| +    const char* data, int len) | 
| +{ | 
| +    if (client_) | 
| +        client_->didReceiveCachedMetadata(loader_, data, len); | 
| } | 
|  | 
| void WebURLLoaderImpl::Context::OnCompletedRequest( | 
| int error_code, | 
| bool was_ignored_by_handler, | 
| const std::string& security_info, | 
| -    const base::TimeTicks& completion_time) { | 
| -  if (ftp_listing_delegate_) { | 
| -    ftp_listing_delegate_->OnCompletedRequest(); | 
| -    ftp_listing_delegate_.reset(NULL); | 
| -  } else if (multipart_delegate_) { | 
| -    multipart_delegate_->OnCompletedRequest(); | 
| -    multipart_delegate_.reset(NULL); | 
| -  } | 
| - | 
| -  // Prevent any further IPC to the browser now that we're complete, but | 
| -  // don't delete it to keep any downloaded temp files alive. | 
| -  DCHECK(!completed_bridge_.get()); | 
| -  completed_bridge_.swap(bridge_); | 
| - | 
| -  if (client_) { | 
| -    if (error_code != net::OK) { | 
| -      client_->didFail(loader_, CreateError(request_.url(), error_code)); | 
| -    } else { | 
| -      client_->didFinishLoading( | 
| -          loader_, (completion_time - TimeTicks()).InSecondsF()); | 
| +    const base::TimeTicks& completion_time) | 
| +{ | 
| +    if (ftp_listing_delegate_) { | 
| +        ftp_listing_delegate_->OnCompletedRequest(); | 
| +        ftp_listing_delegate_.reset(NULL); | 
| +    } else if (multipart_delegate_) { | 
| +        multipart_delegate_->OnCompletedRequest(); | 
| +        multipart_delegate_.reset(NULL); | 
| +    } | 
| + | 
| +    // Prevent any further IPC to the browser now that we're complete, but | 
| +    // don't delete it to keep any downloaded temp files alive. | 
| +    DCHECK(!completed_bridge_.get()); | 
| +    completed_bridge_.swap(bridge_); | 
| + | 
| +    if (client_) { | 
| +        if (error_code != net::OK) { | 
| +            client_->didFail(loader_, CreateError(request_.url(), error_code)); | 
| +        } else { | 
| +            client_->didFinishLoading( | 
| +                loader_, (completion_time - TimeTicks()).InSecondsF()); | 
| +        } | 
| } | 
| -  } | 
|  | 
| -  // We are done with the bridge now, and so we need to release the reference | 
| -  // to ourselves that we took on behalf of the bridge.  This may cause our | 
| -  // destruction. | 
| -  Release(); | 
| +    // TODO(dsjang): This logging code is just temporary. There has to | 
| +    // be a better way to connect the received data to the response_url | 
| +    // than this. | 
| +    SiteIsolationPolicy::DidFinishResourceLoad(response_url_); | 
| + | 
| +    // We are done with the bridge now, and so we need to release the reference | 
| +    // to ourselves that we took on behalf of the bridge.  This may cause our | 
| +    // destruction. | 
| +    Release(); | 
| } | 
|  | 
| -bool WebURLLoaderImpl::Context::CanHandleDataURL(const GURL& url) const { | 
| -  DCHECK(url.SchemeIs("data")); | 
| +bool WebURLLoaderImpl::Context::CanHandleDataURL(const GURL& url) const | 
| +{ | 
| +    DCHECK(url.SchemeIs("data")); | 
|  | 
| -  // Optimize for the case where we can handle a data URL locally.  We must | 
| -  // skip this for data URLs targetted at frames since those could trigger a | 
| -  // download. | 
| -  // | 
| -  // NOTE: We special case MIME types we can render both for performance | 
| -  // reasons as well as to support unit tests, which do not have an underlying | 
| -  // ResourceLoaderBridge implementation. | 
| +// Optimize for the case where we can handle a data URL locally.  We must | 
| +// skip this for data URLs targetted at frames since those could trigger a | 
| +// download. | 
| +// | 
| +// NOTE: We special case MIME types we can render both for performance | 
| +// reasons as well as to support unit tests, which do not have an underlying | 
| +// ResourceLoaderBridge implementation. | 
|  | 
| #if defined(OS_ANDROID) | 
| -  // For compatibility reasons on Android we need to expose top-level data:// | 
| -  // to the browser. | 
| -  if (request_.targetType() == WebURLRequest::TargetIsMainFrame) | 
| -    return false; | 
| +    // For compatibility reasons on Android we need to expose top-level data:// | 
| +    // to the browser. | 
| +    if (request_.targetType() == WebURLRequest::TargetIsMainFrame) | 
| +        return false; | 
| #endif | 
|  | 
| -  if (request_.targetType() != WebURLRequest::TargetIsMainFrame && | 
| -      request_.targetType() != WebURLRequest::TargetIsSubframe) | 
| -    return true; | 
| +    if (request_.targetType() != WebURLRequest::TargetIsMainFrame && request_.targetType() != WebURLRequest::TargetIsSubframe) | 
| +        return true; | 
|  | 
| -  std::string mime_type, unused_charset; | 
| -  if (net::DataURL::Parse(url, &mime_type, &unused_charset, NULL) && | 
| -      net::IsSupportedMimeType(mime_type)) | 
| -    return true; | 
| +    std::string mime_type, unused_charset; | 
| +    if (net::DataURL::Parse(url, &mime_type, &unused_charset, NULL) && net::IsSupportedMimeType(mime_type)) | 
| +        return true; | 
|  | 
| -  return false; | 
| +    return false; | 
| } | 
|  | 
| -void WebURLLoaderImpl::Context::HandleDataURL() { | 
| -  ResourceResponseInfo info; | 
| -  int error_code; | 
| -  std::string data; | 
| +void WebURLLoaderImpl::Context::HandleDataURL() | 
| +{ | 
| +    ResourceResponseInfo info; | 
| +    int error_code; | 
| +    std::string data; | 
|  | 
| -  if (GetInfoFromDataURL(request_.url(), &info, &data, &error_code)) { | 
| -    OnReceivedResponse(info); | 
| -    if (!data.empty()) | 
| -      OnReceivedData(data.data(), data.size(), 0); | 
| -  } | 
| +    if (GetInfoFromDataURL(request_.url(), &info, &data, &error_code)) { | 
| +        OnReceivedResponse(info); | 
| +        if (!data.empty()) | 
| +            OnReceivedData(data.data(), data.size(), 0); | 
| +    } | 
|  | 
| -  OnCompletedRequest(error_code, false, info.security_info, | 
| -                     base::TimeTicks::Now()); | 
| +    OnCompletedRequest(error_code, false, info.security_info, | 
| +                       base::TimeTicks::Now()); | 
| } | 
|  | 
| // WebURLLoaderImpl ----------------------------------------------------------- | 
|  | 
| WebURLLoaderImpl::WebURLLoaderImpl(WebKitPlatformSupportImpl* platform) | 
| -    : context_(new Context(this)), | 
| -      platform_(platform) { | 
| +    : context_(new Context(this)) | 
| +    , platform_(platform) | 
| +{ | 
| } | 
|  | 
| -WebURLLoaderImpl::~WebURLLoaderImpl() { | 
| -  cancel(); | 
| +WebURLLoaderImpl::~WebURLLoaderImpl() | 
| +{ | 
| +    cancel(); | 
| } | 
|  | 
| WebURLError WebURLLoaderImpl::CreateError(const WebURL& unreachable_url, | 
| -                                          int reason) { | 
| -  WebURLError error; | 
| -  error.domain = WebString::fromUTF8(net::kErrorDomain); | 
| -  error.reason = reason; | 
| -  error.unreachableURL = unreachable_url; | 
| -  if (reason == net::ERR_ABORTED) { | 
| -    error.isCancellation = true; | 
| -  } else if (reason == net::ERR_TEMPORARILY_THROTTLED) { | 
| -    error.localizedDescription = WebString::fromUTF8( | 
| -        kThrottledErrorDescription); | 
| -  } | 
| -  return error; | 
| +                                          int reason) | 
| +{ | 
| +    WebURLError error; | 
| +    error.domain = WebString::fromUTF8(net::kErrorDomain); | 
| +    error.reason = reason; | 
| +    error.unreachableURL = unreachable_url; | 
| +    if (reason == net::ERR_ABORTED) { | 
| +        error.isCancellation = true; | 
| +    } else if (reason == net::ERR_TEMPORARILY_THROTTLED) { | 
| +        error.localizedDescription = WebString::fromUTF8( | 
| +            kThrottledErrorDescription); | 
| +    } | 
| +    return error; | 
| } | 
|  | 
| void WebURLLoaderImpl::loadSynchronously(const WebURLRequest& request, | 
| WebURLResponse& response, | 
| WebURLError& error, | 
| -                                         WebData& data) { | 
| -  ResourceLoaderBridge::SyncLoadResponse sync_load_response; | 
| -  context_->Start(request, &sync_load_response, platform_); | 
| +                                         WebData& data) | 
| +{ | 
| +    ResourceLoaderBridge::SyncLoadResponse sync_load_response; | 
| +    context_->Start(request, &sync_load_response, platform_); | 
|  | 
| -  const GURL& final_url = sync_load_response.url; | 
| +    const GURL& final_url = sync_load_response.url; | 
|  | 
| -  // TODO(tc): For file loads, we may want to include a more descriptive | 
| -  // status code or status text. | 
| -  int error_code = sync_load_response.error_code; | 
| -  if (error_code != net::OK) { | 
| -    response.setURL(final_url); | 
| -    error.domain = WebString::fromUTF8(net::kErrorDomain); | 
| -    error.reason = error_code; | 
| -    error.unreachableURL = final_url; | 
| -    return; | 
| -  } | 
| +    // TODO(tc): For file loads, we may want to include a more descriptive | 
| +    // status code or status text. | 
| +    int error_code = sync_load_response.error_code; | 
| +    if (error_code != net::OK) { | 
| +        response.setURL(final_url); | 
| +        error.domain = WebString::fromUTF8(net::kErrorDomain); | 
| +        error.reason = error_code; | 
| +        error.unreachableURL = final_url; | 
| +        return; | 
| +    } | 
|  | 
| -  PopulateURLResponse(final_url, sync_load_response, &response); | 
| +    PopulateURLResponse(final_url, sync_load_response, &response); | 
|  | 
| -  data.assign(sync_load_response.data.data(), | 
| -              sync_load_response.data.size()); | 
| +    data.assign(sync_load_response.data.data(), | 
| +                sync_load_response.data.size()); | 
| } | 
|  | 
| void WebURLLoaderImpl::loadAsynchronously(const WebURLRequest& request, | 
| -                                          WebURLLoaderClient* client) { | 
| -  DCHECK(!context_->client()); | 
| +                                          WebURLLoaderClient* client) | 
| +{ | 
| +    DCHECK(!context_->client()); | 
|  | 
| -  context_->set_client(client); | 
| -  context_->Start(request, NULL, platform_); | 
| +    context_->set_client(client); | 
| +    context_->Start(request, NULL, platform_); | 
| } | 
|  | 
| -void WebURLLoaderImpl::cancel() { | 
| -  context_->Cancel(); | 
| +void WebURLLoaderImpl::cancel() | 
| +{ | 
| +    context_->Cancel(); | 
| } | 
|  | 
| -void WebURLLoaderImpl::setDefersLoading(bool value) { | 
| -  context_->SetDefersLoading(value); | 
| +void WebURLLoaderImpl::setDefersLoading(bool value) | 
| +{ | 
| +    context_->SetDefersLoading(value); | 
| } | 
|  | 
| -void WebURLLoaderImpl::didChangePriority(WebURLRequest::Priority new_priority) { | 
| -  context_->DidChangePriority(new_priority); | 
| +void WebURLLoaderImpl::didChangePriority(WebURLRequest::Priority new_priority) | 
| +{ | 
| +    context_->DidChangePriority(new_priority); | 
| } | 
|  | 
| -}  // namespace webkit_glue | 
| +} // namespace webkit_glue | 
|  |