Clean up ResourceHandler API.

1. Move URLRequest member to ResourceHandler base class and add convenience functions for subclasses.
2. Make OnWillRead take a scoped_refptr to avoid leaking the buffer.

(Attempt 2, after being reverted for possibly unrelated crashes.)

BUG=295239
TEST=No behavior change.
TBR=darin

Review URL: https://codereview.chromium.org/26420005

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@228741 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/content/browser/loader/buffered_resource_handler.cc b/content/browser/loader/buffered_resource_handler.cc
index beb32280..0d7ad70 100644
--- a/content/browser/loader/buffered_resource_handler.cc
+++ b/content/browser/loader/buffered_resource_handler.cc
@@ -80,10 +80,9 @@
     scoped_ptr<ResourceHandler> next_handler,
     ResourceDispatcherHostImpl* host,
     net::URLRequest* request)
-    : LayeredResourceHandler(next_handler.Pass()),
+    : LayeredResourceHandler(request, next_handler.Pass()),
       state_(STATE_STARTING),
       host_(host),
-      request_(request),
       read_buffer_size_(0),
       bytes_read_(0),
       must_download_(false),
@@ -147,8 +146,10 @@
 
 // We'll let the original event handler provide a buffer, and reuse it for
 // subsequent reads until we're done buffering.
-bool BufferedResourceHandler::OnWillRead(int request_id, net::IOBuffer** buf,
-                                         int* buf_size, int min_size) {
+bool BufferedResourceHandler::OnWillRead(int request_id,
+                                         scoped_refptr<net::IOBuffer>* buf,
+                                         int* buf_size,
+                                         int min_size) {
   if (state_ == STATE_STREAMING)
     return next_handler_->OnWillRead(request_id, buf, buf_size, min_size);
 
@@ -240,8 +241,7 @@
 
   state_ = STATE_REPLAYING;
 
-  int request_id = ResourceRequestInfo::ForRequest(request_)->GetRequestID();
-  if (!next_handler_->OnResponseStarted(request_id, response_.get(), defer))
+  if (!next_handler_->OnResponseStarted(GetRequestID(), response_.get(), defer))
     return false;
 
   if (!read_buffer_.get()) {
@@ -259,13 +259,13 @@
   const std::string& mime_type = response_->head.mime_type;
 
   std::string content_type_options;
-  request_->GetResponseHeaderByName("x-content-type-options",
-                                    &content_type_options);
+  request()->GetResponseHeaderByName("x-content-type-options",
+                                     &content_type_options);
 
   bool sniffing_blocked =
       LowerCaseEqualsASCII(content_type_options, "nosniff");
   bool we_would_like_to_sniff =
-      net::ShouldSniffMimeType(request_->url(), mime_type);
+      net::ShouldSniffMimeType(request()->url(), mime_type);
 
   RecordSnifferMetrics(sniffing_blocked, we_would_like_to_sniff, mime_type);
 
@@ -273,7 +273,7 @@
     // We're going to look at the data before deciding what the content type
     // is.  That means we need to delay sending the ResponseStarted message
     // over the IPC channel.
-    VLOG(1) << "To buffer: " << request_->url().spec();
+    VLOG(1) << "To buffer: " << request()->url().spec();
     return true;
   }
 
@@ -287,7 +287,7 @@
 
   std::string new_type;
   bool made_final_decision =
-      net::SniffMimeType(read_buffer_->data(), bytes_read_, request_->url(),
+      net::SniffMimeType(read_buffer_->data(), bytes_read_, request()->url(),
                          type_hint, &new_type);
 
   // SniffMimeType() returns false if there is not enough data to determine
@@ -301,13 +301,13 @@
 bool BufferedResourceHandler::SelectNextHandler(bool* defer) {
   DCHECK(!response_->head.mime_type.empty());
 
-  ResourceRequestInfoImpl* info = ResourceRequestInfoImpl::ForRequest(request_);
+  ResourceRequestInfoImpl* info = GetRequestInfo();
   const std::string& mime_type = response_->head.mime_type;
 
   if (net::IsSupportedCertificateMimeType(mime_type)) {
     // Install certificate file.
     scoped_ptr<ResourceHandler> handler(
-        new CertificateResourceHandler(request_));
+        new CertificateResourceHandler(request()));
     return UseAlternateNextHandler(handler.Pass());
   }
 
@@ -320,7 +320,7 @@
       return true;
 
     scoped_ptr<ResourceHandler> handler(
-        host_->MaybeInterceptAsStream(request_, response_.get()));
+        host_->MaybeInterceptAsStream(request(), response_.get()));
     if (handler)
       return UseAlternateNextHandler(handler.Pass());
 
@@ -344,7 +344,7 @@
   info->set_is_download(true);
   scoped_ptr<ResourceHandler> handler(
       host_->CreateResourceHandlerForDownload(
-          request_,
+          request(),
           true,  // is_content_initiated
           must_download,
           content::DownloadItem::kInvalidId,
@@ -362,11 +362,11 @@
     // own error page instead of triggering a download.
     // TODO(abarth): We should abstract the response_code test, but this kind
     //               of check is scattered throughout our codebase.
-    request_->CancelWithError(net::ERR_FILE_NOT_FOUND);
+    request()->CancelWithError(net::ERR_FILE_NOT_FOUND);
     return false;
   }
 
-  int request_id = ResourceRequestInfo::ForRequest(request_)->GetRequestID();
+  int request_id = GetRequestID();
 
   // Inform the original ResourceHandler that this will be handled entirely by
   // the new ResourceHandler.
@@ -389,8 +389,8 @@
 bool BufferedResourceHandler::ReplayReadCompleted(bool* defer) {
   DCHECK(read_buffer_.get());
 
-  int request_id = ResourceRequestInfo::ForRequest(request_)->GetRequestID();
-  bool result = next_handler_->OnReadCompleted(request_id, bytes_read_, defer);
+  bool result = next_handler_->OnReadCompleted(GetRequestID(), bytes_read_,
+                                               defer);
 
   read_buffer_ = NULL;
   read_buffer_size_ = 0;
@@ -418,13 +418,13 @@
   must_download_is_set_ = true;
 
   std::string disposition;
-  request_->GetResponseHeaderByName("content-disposition", &disposition);
+  request()->GetResponseHeaderByName("content-disposition", &disposition);
   if (!disposition.empty() &&
       net::HttpContentDisposition(disposition, std::string()).is_attachment()) {
     must_download_ = true;
   } else if (host_->delegate() &&
              host_->delegate()->ShouldForceDownloadResource(
-                 request_->url(), response_->head.mime_type)) {
+                 request()->url(), response_->head.mime_type)) {
     must_download_ = true;
   } else {
     must_download_ = false;
@@ -434,13 +434,13 @@
 }
 
 bool BufferedResourceHandler::HasSupportingPlugin(bool* stale) {
-  ResourceRequestInfoImpl* info = ResourceRequestInfoImpl::ForRequest(request_);
+  ResourceRequestInfoImpl* info = GetRequestInfo();
 
   bool allow_wildcard = false;
   WebPluginInfo plugin;
   return PluginServiceImpl::GetInstance()->GetPluginInfo(
       info->GetChildID(), info->GetRouteID(), info->GetContext(),
-      request_->url(), GURL(), response_->head.mime_type, allow_wildcard,
+      request()->url(), GURL(), response_->head.mime_type, allow_wildcard,
       stale, &plugin, NULL);
 }
 
@@ -448,7 +448,7 @@
   if (!bytes_read_)
     return true;
 
-  net::IOBuffer* buf = NULL;
+  scoped_refptr<net::IOBuffer> buf;
   int buf_len = 0;
   if (!next_handler_->OnWillRead(request_id, &buf, &buf_len, bytes_read_))
     return false;