Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1017)

Unified Diff: content/browser/loader/temporary_file_manager.cc

Issue 82273002: Fix various issues in RedirectToFileResourceHandler. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Comment Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: content/browser/loader/temporary_file_manager.cc
diff --git a/content/browser/loader/temporary_file_manager.cc b/content/browser/loader/temporary_file_manager.cc
new file mode 100644
index 0000000000000000000000000000000000000000..f32508a56a4db93826f90546826a270fa3b87496
--- /dev/null
+++ b/content/browser/loader/temporary_file_manager.cc
@@ -0,0 +1,113 @@
+// Copyright 2013 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.
+
+#include "content/browser/loader/temporary_file_manager.h"
+
+#include "base/files/file_util_proxy.h"
+#include "content/browser/child_process_security_policy_impl.h"
+#include "content/public/browser/browser_thread.h"
+#include "net/base/file_stream.h"
+#include "webkit/common/blob/shareable_file_reference.h"
+
+using webkit_blob::ShareableFileReference;
+
+namespace content {
+
+namespace {
+
+void RemoveDownloadFileFromChildSecurityPolicy(int child_id,
+ const base::FilePath& path) {
+ ChildProcessSecurityPolicyImpl::GetInstance()->RevokeAllPermissionsForFile(
+ child_id, path);
+}
+
+} // namespace
+
+TemporaryFileManager::TemporaryFileManager() : weak_factory_(this) {
+}
+
+TemporaryFileManager::~TemporaryFileManager() {
+}
+
+void TemporaryFileManager::UnregisterDownloadedTempFile(
+ int child_id, int request_id) {
+ registered_temp_files_[child_id].erase(request_id);
+
+ // Note that we don't remove the security bits here. This will be done
+ // when all file refs are deleted (see RegisterDownloadedTempFile).
+}
+
+void TemporaryFileManager::UnregisterFilesForChild(int child_id) {
+ registered_temp_files_.erase(child_id);
+}
+
+void TemporaryFileManager::CreateTemporary(
+ int child_id,
+ int request_id,
+ base::WeakPtr<RedirectToFileResourceHandler> handler) {
darin (slow to review) 2013/12/06 17:56:07 It would be nice from a unit-testing point of view
davidben 2013/12/19 22:21:01 Done.
+ base::FileUtilProxy::CreateTemporary(
+ BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE).get(),
+ base::PLATFORM_FILE_ASYNC,
+ base::Bind(&TemporaryFileManager::DidCreateTemporaryFile,
+ weak_factory_.GetWeakPtr(),
+ child_id, request_id, handler));
+}
+
+void TemporaryFileManager::DidCreateTemporaryFile(
+ int child_id,
+ int request_id,
+ base::WeakPtr<RedirectToFileResourceHandler> handler,
+ base::PlatformFileError error_code,
+ base::PassPlatformFile file_handle,
+ const base::FilePath& file_path) {
+ if (error_code != base::PLATFORM_FILE_OK) {
+ if (handler) {
+ handler->DidCreateTemporaryFile(
+ error_code, scoped_ptr<net::FileStream>(), NULL);
+ }
+ return;
+ }
+
+ // Cancelled or not, create the deletable_file so the temporary is cleaned up.
+ scoped_refptr<ShareableFileReference> deletable_file =
+ ShareableFileReference::GetOrCreate(
+ file_path,
+ ShareableFileReference::DELETE_ON_FINAL_RELEASE,
+ BrowserThread::GetMessageLoopProxyForThread(
+ BrowserThread::FILE).get());
+
+ // Check if the handler has since been destroyed. If so, skip the rest.
+ if (!handler)
+ return;
+
+ scoped_ptr<net::FileStream> file_stream(new net::FileStream(
+ file_handle.ReleaseValue(),
+ base::PLATFORM_FILE_WRITE | base::PLATFORM_FILE_ASYNC,
+ NULL));
+
+ RegisterDownloadedTempFile(child_id, request_id, deletable_file.get());
+ handler->DidCreateTemporaryFile(
+ error_code, file_stream.Pass(), deletable_file);
+}
+
+void TemporaryFileManager::RegisterDownloadedTempFile(
+ int child_id, int request_id, ShareableFileReference* reference) {
+ registered_temp_files_[child_id][request_id] = reference;
+ ChildProcessSecurityPolicyImpl::GetInstance()->GrantReadFile(
+ child_id, reference->path());
+
+ // When the temp file is deleted, revoke permissions that the renderer has
+ // to that file. This covers an edge case where the file is deleted and then
+ // the same name is re-used for some other purpose, we don't want the old
+ // renderer to still have access to it.
+ //
+ // This is delayed until the file is deleted because the renderer can take a
+ // blob reference to the temp file that outlives the url loaded that it was
+ // loaded with to keep the file (and permissions) alive.
+ reference->AddFinalReleaseCallback(
+ base::Bind(&RemoveDownloadFileFromChildSecurityPolicy,
+ child_id));
+}
+
+} // namespace content

Powered by Google App Engine
This is Rietveld 408576698