| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/download/download_manager.h" | 5 #include "chrome/browser/download/download_manager.h" |
| 6 | 6 |
| 7 #include "base/bind.h" |
| 7 #include "base/callback.h" | 8 #include "base/callback.h" |
| 8 #include "base/file_util.h" | 9 #include "base/file_util.h" |
| 9 #include "base/i18n/case_conversion.h" | 10 #include "base/i18n/case_conversion.h" |
| 10 #include "base/logging.h" | 11 #include "base/logging.h" |
| 11 #include "base/path_service.h" | 12 #include "base/path_service.h" |
| 12 #include "base/rand_util.h" | 13 #include "base/rand_util.h" |
| 13 #include "base/stl_util.h" | 14 #include "base/stl_util.h" |
| 14 #include "base/stringprintf.h" | 15 #include "base/stringprintf.h" |
| 16 #include "base/synchronization/lock.h" |
| 15 #include "base/sys_string_conversions.h" | 17 #include "base/sys_string_conversions.h" |
| 16 #include "base/task.h" | 18 #include "base/task.h" |
| 17 #include "base/utf_string_conversions.h" | 19 #include "base/utf_string_conversions.h" |
| 18 #include "build/build_config.h" | 20 #include "build/build_config.h" |
| 19 #include "chrome/browser/browser_process.h" | 21 #include "chrome/browser/browser_process.h" |
| 20 #include "chrome/browser/download/download_create_info.h" | 22 #include "chrome/browser/download/download_create_info.h" |
| 21 #include "chrome/browser/download/download_extensions.h" | 23 #include "chrome/browser/download/download_extensions.h" |
| 22 #include "chrome/browser/download/download_file_manager.h" | 24 #include "chrome/browser/download/download_file_manager.h" |
| 23 #include "chrome/browser/download/download_history.h" | 25 #include "chrome/browser/download/download_history.h" |
| 24 #include "chrome/browser/download/download_item.h" | 26 #include "chrome/browser/download/download_item.h" |
| (...skipping 20 matching lines...) Expand all Loading... |
| 45 #include "grit/generated_resources.h" | 47 #include "grit/generated_resources.h" |
| 46 #include "grit/theme_resources.h" | 48 #include "grit/theme_resources.h" |
| 47 #include "net/base/mime_util.h" | 49 #include "net/base/mime_util.h" |
| 48 #include "net/base/net_util.h" | 50 #include "net/base/net_util.h" |
| 49 #include "ui/base/l10n/l10n_util.h" | 51 #include "ui/base/l10n/l10n_util.h" |
| 50 #include "ui/base/resource/resource_bundle.h" | 52 #include "ui/base/resource/resource_bundle.h" |
| 51 | 53 |
| 52 DownloadManager::DownloadManager(DownloadManagerDelegate* delegate, | 54 DownloadManager::DownloadManager(DownloadManagerDelegate* delegate, |
| 53 DownloadStatusUpdater* status_updater) | 55 DownloadStatusUpdater* status_updater) |
| 54 : shutdown_needed_(false), | 56 : shutdown_needed_(false), |
| 57 next_id_(0), |
| 55 profile_(NULL), | 58 profile_(NULL), |
| 56 file_manager_(NULL), | 59 file_manager_(NULL), |
| 57 status_updater_(status_updater->AsWeakPtr()), | 60 status_updater_(status_updater->AsWeakPtr()), |
| 58 next_save_page_id_(0), | 61 next_save_page_id_(0), |
| 59 delegate_(delegate) { | 62 delegate_(delegate) { |
| 60 if (status_updater_) | 63 if (status_updater_) |
| 61 status_updater_->AddDelegate(this); | 64 status_updater_->AddDelegate(this); |
| 62 } | 65 } |
| 63 | 66 |
| 64 DownloadManager::~DownloadManager() { | 67 DownloadManager::~DownloadManager() { |
| (...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 211 if (download_item->MatchesQuery(query_lower)) | 214 if (download_item->MatchesQuery(query_lower)) |
| 212 result->push_back(download_item); | 215 result->push_back(download_item); |
| 213 } | 216 } |
| 214 | 217 |
| 215 // If we have a parent profile, let it add its downloads to the results. | 218 // If we have a parent profile, let it add its downloads to the results. |
| 216 Profile* original_profile = profile_->GetOriginalProfile(); | 219 Profile* original_profile = profile_->GetOriginalProfile(); |
| 217 if (original_profile != profile_) | 220 if (original_profile != profile_) |
| 218 original_profile->GetDownloadManager()->SearchDownloads(query, result); | 221 original_profile->GetDownloadManager()->SearchDownloads(query, result); |
| 219 } | 222 } |
| 220 | 223 |
| 224 void DownloadManager::OnHistoryGetNextId(int next_id) { |
| 225 DVLOG(1) << __FUNCTION__ << " " << next_id; |
| 226 base::AutoLock lock(next_id_lock_); |
| 227 // TODO(benjhayden) Delay Profile initialization until here, and set next_id_ |
| 228 // = next_id. The '+=' works for now because these ids are not yet persisted |
| 229 // to the database. GetNextId() can allocate zero or more ids starting from 0, |
| 230 // then this callback can increment next_id_, and the items with lower ids |
| 231 // won't clash with any other items even though there may be items loaded from |
| 232 // the history because items from the history don't have valid ids. |
| 233 next_id_ += next_id; |
| 234 } |
| 235 |
| 236 DownloadId DownloadManager::GetNextId() { |
| 237 // May be called on any thread via the GetNextIdThunk. |
| 238 // TODO(benjhayden) If otr, forward to parent DM. |
| 239 base::AutoLock lock(next_id_lock_); |
| 240 return DownloadId(this, next_id_++); |
| 241 } |
| 242 |
| 243 DownloadManager::GetNextIdThunkType DownloadManager::GetNextIdThunk() { |
| 244 // TODO(benjhayden) If otr, forward to parent DM. |
| 245 return base::Bind(&DownloadManager::GetNextId, this); |
| 246 } |
| 247 |
| 221 // Query the history service for information about all persisted downloads. | 248 // Query the history service for information about all persisted downloads. |
| 222 bool DownloadManager::Init(Profile* profile) { | 249 bool DownloadManager::Init(Profile* profile) { |
| 223 DCHECK(profile); | 250 DCHECK(profile); |
| 224 DCHECK(!shutdown_needed_) << "DownloadManager already initialized."; | 251 DCHECK(!shutdown_needed_) << "DownloadManager already initialized."; |
| 225 shutdown_needed_ = true; | 252 shutdown_needed_ = true; |
| 226 | 253 |
| 227 profile_ = profile; | 254 profile_ = profile; |
| 228 download_history_.reset(new DownloadHistory(profile)); | 255 download_history_.reset(new DownloadHistory(profile)); |
| 256 // DownloadHistory does not guarantee that these callbacks will be run. These |
| 257 // callbacks won't be run if the user has disabled history or history |
| 258 // initialization failed. |
| 259 download_history_->GetNextId(NewCallback( |
| 260 this, &DownloadManager::OnHistoryGetNextId)); |
| 229 download_history_->Load( | 261 download_history_->Load( |
| 230 NewCallback(this, &DownloadManager::OnQueryDownloadEntriesComplete)); | 262 NewCallback(this, &DownloadManager::OnQueryDownloadEntriesComplete)); |
| 231 | 263 |
| 232 download_prefs_.reset(new DownloadPrefs(profile_->GetPrefs())); | 264 download_prefs_.reset(new DownloadPrefs(profile_->GetPrefs())); |
| 233 | 265 |
| 234 // In test mode, there may be no ResourceDispatcherHost. In this case it's | 266 // In test mode, there may be no ResourceDispatcherHost. In this case it's |
| 235 // safe to avoid setting |file_manager_| because we only call a small set of | 267 // safe to avoid setting |file_manager_| because we only call a small set of |
| 236 // functions, none of which need it. | 268 // functions, none of which need it. |
| 237 ResourceDispatcherHost* rdh = g_browser_process->resource_dispatcher_host(); | 269 ResourceDispatcherHost* rdh = g_browser_process->resource_dispatcher_host(); |
| 238 if (rdh) { | 270 if (rdh) { |
| (...skipping 342 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 581 // name after user confirmation will be set from | 613 // name after user confirmation will be set from |
| 582 // DownloadItem::OnDownloadCompleting. | 614 // DownloadItem::OnDownloadCompleting. |
| 583 download_path = | 615 download_path = |
| 584 download_util::GetCrDownloadPath(download->full_path()); | 616 download_util::GetCrDownloadPath(download->full_path()); |
| 585 } | 617 } |
| 586 | 618 |
| 587 BrowserThread::PostTask( | 619 BrowserThread::PostTask( |
| 588 BrowserThread::FILE, FROM_HERE, | 620 BrowserThread::FILE, FROM_HERE, |
| 589 NewRunnableMethod( | 621 NewRunnableMethod( |
| 590 file_manager_, &DownloadFileManager::RenameInProgressDownloadFile, | 622 file_manager_, &DownloadFileManager::RenameInProgressDownloadFile, |
| 591 download->id(), download_path)); | 623 download->global_id(), download_path)); |
| 592 | 624 |
| 593 download->Rename(download_path); | 625 download->Rename(download_path); |
| 594 | 626 |
| 595 download_history_->AddEntry(download, | 627 download_history_->AddEntry(download, |
| 596 NewCallback(this, &DownloadManager::OnCreateDownloadEntryComplete)); | 628 NewCallback(this, &DownloadManager::OnCreateDownloadEntryComplete)); |
| 597 } | 629 } |
| 598 | 630 |
| 599 void DownloadManager::UpdateDownload(int32 download_id, int64 size) { | 631 void DownloadManager::UpdateDownload(int32 download_id, int64 size) { |
| 600 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 632 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 601 DownloadMap::iterator it = active_downloads_.find(download_id); | 633 DownloadMap::iterator it = active_downloads_.find(download_id); |
| (...skipping 183 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 785 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 817 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 786 | 818 |
| 787 DownloadItem* item = GetDownloadItem(download_id); | 819 DownloadItem* item = GetDownloadItem(download_id); |
| 788 if (!item) | 820 if (!item) |
| 789 return; | 821 return; |
| 790 | 822 |
| 791 if (item->safety_state() == DownloadItem::SAFE) { | 823 if (item->safety_state() == DownloadItem::SAFE) { |
| 792 DCHECK_EQ(0, uniquifier) << "We should not uniquify SAFE downloads twice"; | 824 DCHECK_EQ(0, uniquifier) << "We should not uniquify SAFE downloads twice"; |
| 793 } | 825 } |
| 794 | 826 |
| 795 BrowserThread::PostTask( | 827 BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE, NewRunnableMethod( |
| 796 BrowserThread::FILE, FROM_HERE, | 828 file_manager_, |
| 797 NewRunnableMethod( | 829 &DownloadFileManager::CompleteDownload, |
| 798 file_manager_, &DownloadFileManager::CompleteDownload, download_id)); | 830 item->global_id())); |
| 799 | 831 |
| 800 if (uniquifier) | 832 if (uniquifier) |
| 801 item->set_path_uniquifier(uniquifier); | 833 item->set_path_uniquifier(uniquifier); |
| 802 | 834 |
| 803 item->OnDownloadRenamedToFinalName(full_path); | 835 item->OnDownloadRenamedToFinalName(full_path); |
| 804 download_history_->UpdateDownloadPath(item, full_path); | 836 download_history_->UpdateDownloadPath(item, full_path); |
| 805 } | 837 } |
| 806 | 838 |
| 807 void DownloadManager::DownloadCancelled(int32 download_id) { | 839 void DownloadManager::DownloadCancelled(int32 download_id) { |
| 808 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 840 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| (...skipping 15 matching lines...) Expand all Loading... |
| 824 } | 856 } |
| 825 | 857 |
| 826 DownloadCancelledInternal(download_id, download->request_handle()); | 858 DownloadCancelledInternal(download_id, download->request_handle()); |
| 827 } | 859 } |
| 828 | 860 |
| 829 void DownloadManager::DownloadCancelledInternal( | 861 void DownloadManager::DownloadCancelledInternal( |
| 830 int download_id, const DownloadRequestHandle& request_handle) { | 862 int download_id, const DownloadRequestHandle& request_handle) { |
| 831 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 863 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 832 request_handle.CancelRequest(); | 864 request_handle.CancelRequest(); |
| 833 | 865 |
| 834 BrowserThread::PostTask( | 866 BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE, NewRunnableMethod( |
| 835 BrowserThread::FILE, FROM_HERE, | 867 file_manager_, &DownloadFileManager::CancelDownload, |
| 836 NewRunnableMethod( | 868 DownloadId(this, download_id))); |
| 837 file_manager_, &DownloadFileManager::CancelDownload, download_id)); | |
| 838 } | 869 } |
| 839 | 870 |
| 840 void DownloadManager::OnDownloadError(int32 download_id, | 871 void DownloadManager::OnDownloadError(int32 download_id, |
| 841 int64 size, | 872 int64 size, |
| 842 int os_error) { | 873 int os_error) { |
| 843 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 874 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 844 DownloadMap::iterator it = active_downloads_.find(download_id); | 875 DownloadMap::iterator it = active_downloads_.find(download_id); |
| 845 // A cancel at the right time could remove the download from the | 876 // A cancel at the right time could remove the download from the |
| 846 // |active_downloads_| map before we get here. | 877 // |active_downloads_| map before we get here. |
| 847 if (it == active_downloads_.end()) | 878 if (it == active_downloads_.end()) |
| (...skipping 12 matching lines...) Expand all Loading... |
| 860 // | 891 // |
| 861 // Clean up will happen when the history system create callback runs if we | 892 // Clean up will happen when the history system create callback runs if we |
| 862 // don't have a valid db_handle yet. | 893 // don't have a valid db_handle yet. |
| 863 if (download->db_handle() != DownloadHistory::kUninitializedHandle) { | 894 if (download->db_handle() != DownloadHistory::kUninitializedHandle) { |
| 864 in_progress_.erase(download_id); | 895 in_progress_.erase(download_id); |
| 865 active_downloads_.erase(download_id); | 896 active_downloads_.erase(download_id); |
| 866 UpdateAppIcon(); // Reflect removal from in_progress_. | 897 UpdateAppIcon(); // Reflect removal from in_progress_. |
| 867 download_history_->UpdateEntry(download); | 898 download_history_->UpdateEntry(download); |
| 868 } | 899 } |
| 869 | 900 |
| 870 BrowserThread::PostTask( | 901 BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE, NewRunnableMethod( |
| 871 BrowserThread::FILE, FROM_HERE, | 902 file_manager_, |
| 872 NewRunnableMethod( | 903 &DownloadFileManager::CancelDownload, |
| 873 file_manager_, &DownloadFileManager::CancelDownload, download_id)); | 904 download->global_id())); |
| 874 } | 905 } |
| 875 | 906 |
| 876 void DownloadManager::UpdateAppIcon() { | 907 void DownloadManager::UpdateAppIcon() { |
| 877 if (status_updater_) | 908 if (status_updater_) |
| 878 status_updater_->Update(); | 909 status_updater_->Update(); |
| 879 } | 910 } |
| 880 | 911 |
| 881 int DownloadManager::RemoveDownloadItems( | 912 int DownloadManager::RemoveDownloadItems( |
| 882 const DownloadVector& pending_deletes) { | 913 const DownloadVector& pending_deletes) { |
| 883 if (pending_deletes.empty()) | 914 if (pending_deletes.empty()) |
| (...skipping 482 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1366 Source<DownloadManager>(this), | 1397 Source<DownloadManager>(this), |
| 1367 Details<DownloadItem>(download)); | 1398 Details<DownloadItem>(download)); |
| 1368 } | 1399 } |
| 1369 } | 1400 } |
| 1370 | 1401 |
| 1371 int32 DownloadManager::GetNextSavePageId() { | 1402 int32 DownloadManager::GetNextSavePageId() { |
| 1372 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 1403 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 1373 return next_save_page_id_++; | 1404 return next_save_page_id_++; |
| 1374 } | 1405 } |
| 1375 | 1406 |
| OLD | NEW |