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

Side by Side Diff: content/browser/download/download_file_manager.cc

Issue 10912173: Replace the DownloadFileManager with direct ownership of DownloadFileImpl (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Incorporated comments and sync'd to r158560 Created 8 years, 2 months 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 unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "content/browser/download/download_file_manager.h"
6
7 #include <set>
8 #include <string>
9
10 #include "base/bind.h"
11 #include "base/file_util.h"
12 #include "base/logging.h"
13 #include "base/stl_util.h"
14 #include "base/utf_string_conversions.h"
15 #include "content/browser/download/base_file.h"
16 #include "content/browser/download/download_create_info.h"
17 #include "content/browser/download/download_file_impl.h"
18 #include "content/browser/download/download_interrupt_reasons_impl.h"
19 #include "content/browser/download/download_request_handle.h"
20 #include "content/browser/download/download_stats.h"
21 #include "content/browser/power_save_blocker.h"
22 #include "content/browser/web_contents/web_contents_impl.h"
23 #include "content/public/browser/browser_thread.h"
24 #include "content/public/browser/download_manager.h"
25 #include "content/public/browser/download_manager_delegate.h"
26 #include "googleurl/src/gurl.h"
27 #include "net/base/io_buffer.h"
28
29 using content::BrowserThread;
30 using content::DownloadFile;
31 using content::DownloadId;
32 using content::DownloadManager;
33
34 DownloadFileManager::DownloadFileManager(content::DownloadFileFactory* factory)
35 : download_file_factory_(factory) {
36 if (download_file_factory_ == NULL)
37 download_file_factory_.reset(new content::DownloadFileFactory);
38 }
39
40 DownloadFileManager::~DownloadFileManager() {
41 DCHECK(downloads_.empty());
42 }
43
44 void DownloadFileManager::Shutdown() {
45 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
46 BrowserThread::PostTask(
47 BrowserThread::FILE, FROM_HERE,
48 base::Bind(&DownloadFileManager::OnShutdown, this));
49 }
50
51 void DownloadFileManager::OnShutdown() {
52 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
53 STLDeleteValues(&downloads_);
54 }
55
56 void DownloadFileManager::CreateDownloadFile(
57 scoped_ptr<DownloadCreateInfo> info,
58 scoped_ptr<content::ByteStreamReader> stream,
59 scoped_refptr<DownloadManager> download_manager, bool get_hash,
60 const net::BoundNetLog& bound_net_log,
61 const CreateDownloadFileCallback& callback) {
62 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
63 DCHECK(info.get());
64 VLOG(20) << __FUNCTION__ << "()" << " info = " << info->DebugString();
65
66 scoped_ptr<DownloadFile> download_file(download_file_factory_->CreateFile(
67 info.get(), stream.Pass(), download_manager, get_hash, bound_net_log));
68
69 content::DownloadInterruptReason interrupt_reason(
70 download_file->Initialize());
71 if (interrupt_reason == content::DOWNLOAD_INTERRUPT_REASON_NONE) {
72 DCHECK(GetDownloadFile(info->download_id) == NULL);
73 downloads_[info->download_id] = download_file.release();
74 }
75
76 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
77 base::Bind(callback, interrupt_reason));
78 }
79
80 DownloadFile* DownloadFileManager::GetDownloadFile(
81 DownloadId global_id) {
82 DownloadFileMap::iterator it = downloads_.find(global_id);
83 return it == downloads_.end() ? NULL : it->second;
84 }
85
86 // This method will be sent via a user action, or shutdown on the UI thread, and
87 // run on the download thread. Since this message has been sent from the UI
88 // thread, the download may have already completed and won't exist in our map.
89 void DownloadFileManager::CancelDownload(DownloadId global_id) {
90 VLOG(20) << __FUNCTION__ << "()" << " id = " << global_id;
91 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
92 DownloadFileMap::iterator it = downloads_.find(global_id);
93 if (it == downloads_.end())
94 return;
95
96 DownloadFile* download_file = it->second;
97 VLOG(20) << __FUNCTION__ << "()"
98 << " download_file = " << download_file->DebugString();
99 download_file->Cancel();
100
101 EraseDownload(global_id);
102 }
103
104 void DownloadFileManager::CompleteDownload(
105 DownloadId global_id, const base::Closure& callback) {
106 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
107
108 if (!ContainsKey(downloads_, global_id))
109 return;
110
111 DownloadFile* download_file = downloads_[global_id];
112
113 VLOG(20) << " " << __FUNCTION__ << "()"
114 << " id = " << global_id
115 << " download_file = " << download_file->DebugString();
116
117 download_file->Detach(callback);
118
119 EraseDownload(global_id);
120 }
121
122 void DownloadFileManager::OnDownloadManagerShutdown(DownloadManager* manager) {
123 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
124 DCHECK(manager);
125
126 std::set<DownloadFile*> to_remove;
127
128 for (DownloadFileMap::iterator i = downloads_.begin();
129 i != downloads_.end(); ++i) {
130 DownloadFile* download_file = i->second;
131 if (download_file->GetDownloadManager() == manager) {
132 download_file->CancelDownloadRequest();
133 to_remove.insert(download_file);
134 }
135 }
136
137 for (std::set<DownloadFile*>::iterator i = to_remove.begin();
138 i != to_remove.end(); ++i) {
139 downloads_.erase((*i)->GlobalId());
140 delete *i;
141 }
142 }
143
144 // Actions from the UI thread and run on the download thread
145
146 void DownloadFileManager::RenameDownloadFile(
147 DownloadId global_id,
148 const FilePath& full_path,
149 bool overwrite_existing_file,
150 const RenameCompletionCallback& callback) {
151 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
152 DownloadFile* download_file = GetDownloadFile(global_id);
153 if (!download_file) {
154 BrowserThread::PostTask(
155 BrowserThread::UI, FROM_HERE,
156 base::Bind(callback, content::DOWNLOAD_INTERRUPT_REASON_FILE_FAILED,
157 FilePath()));
158 return;
159 }
160
161 download_file->Rename(full_path, overwrite_existing_file, callback);
162 }
163
164 int DownloadFileManager::NumberOfActiveDownloads() const {
165 return downloads_.size();
166 }
167
168 void DownloadFileManager::EraseDownload(DownloadId global_id) {
169 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
170
171 if (!ContainsKey(downloads_, global_id))
172 return;
173
174 DownloadFile* download_file = downloads_[global_id];
175
176 VLOG(20) << " " << __FUNCTION__ << "()"
177 << " id = " << global_id
178 << " download_file = " << download_file->DebugString();
179
180 downloads_.erase(global_id);
181
182 delete download_file;
183 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698