| 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 "content/browser/download/download_item_impl.h" | 5 #include "content/browser/download/download_item_impl.h" |
| 6 | 6 |
| 7 #include <vector> | 7 #include <vector> |
| 8 | 8 |
| 9 #include "base/basictypes.h" | 9 #include "base/basictypes.h" |
| 10 #include "base/bind.h" | 10 #include "base/bind.h" |
| (...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 160 DownloadItemImpl::DownloadItemImpl(Delegate* delegate, | 160 DownloadItemImpl::DownloadItemImpl(Delegate* delegate, |
| 161 DownloadId download_id, | 161 DownloadId download_id, |
| 162 const DownloadPersistentStoreInfo& info) | 162 const DownloadPersistentStoreInfo& info) |
| 163 : download_id_(download_id), | 163 : download_id_(download_id), |
| 164 full_path_(info.path), | 164 full_path_(info.path), |
| 165 url_chain_(1, info.url), | 165 url_chain_(1, info.url), |
| 166 referrer_url_(info.referrer_url), | 166 referrer_url_(info.referrer_url), |
| 167 total_bytes_(info.total_bytes), | 167 total_bytes_(info.total_bytes), |
| 168 received_bytes_(info.received_bytes), | 168 received_bytes_(info.received_bytes), |
| 169 bytes_per_sec_(0), | 169 bytes_per_sec_(0), |
| 170 last_reason_(DOWNLOAD_INTERRUPT_REASON_NONE), |
| 170 start_tick_(base::TimeTicks()), | 171 start_tick_(base::TimeTicks()), |
| 171 state_(static_cast<DownloadState>(info.state)), | 172 state_(static_cast<DownloadState>(info.state)), |
| 172 start_time_(info.start_time), | 173 start_time_(info.start_time), |
| 173 end_time_(info.end_time), | 174 end_time_(info.end_time), |
| 174 db_handle_(info.db_handle), | 175 db_handle_(info.db_handle), |
| 175 delegate_(delegate), | 176 delegate_(delegate), |
| 176 is_paused_(false), | 177 is_paused_(false), |
| 177 open_when_complete_(false), | 178 open_when_complete_(false), |
| 178 file_externally_removed_(false), | 179 file_externally_removed_(false), |
| 179 safety_state_(SAFE), | 180 safety_state_(SAFE), |
| (...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 360 UMA_HISTOGRAM_ENUMERATION("Download.DangerousDownloadValidated", | 361 UMA_HISTOGRAM_ENUMERATION("Download.DangerousDownloadValidated", |
| 361 GetDangerType(), | 362 GetDangerType(), |
| 362 DownloadStateInfo::DANGEROUS_TYPE_MAX); | 363 DownloadStateInfo::DANGEROUS_TYPE_MAX); |
| 363 | 364 |
| 364 safety_state_ = DANGEROUS_BUT_VALIDATED; | 365 safety_state_ = DANGEROUS_BUT_VALIDATED; |
| 365 UpdateObservers(); | 366 UpdateObservers(); |
| 366 | 367 |
| 367 delegate_->MaybeCompleteDownload(this); | 368 delegate_->MaybeCompleteDownload(this); |
| 368 } | 369 } |
| 369 | 370 |
| 370 void DownloadItemImpl::UpdateSize(int64 bytes_so_far) { | 371 void DownloadItemImpl::ProgressComplete(int64 bytes_so_far, |
| 371 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 372 const std::string& final_hash) { |
| 372 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 373 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 374 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 375 |
| 376 hash_ = final_hash; |
| 377 hash_state_ = ""; |
| 373 | 378 |
| 374 received_bytes_ = bytes_so_far; | 379 received_bytes_ = bytes_so_far; |
| 375 | 380 |
| 376 // If we've received more data than we were expecting (bad server info?), | 381 // If we've received more data than we were expecting (bad server info?), |
| 377 // revert to 'unknown size mode'. | 382 // revert to 'unknown size mode'. |
| 378 if (received_bytes_ > total_bytes_) | 383 if (received_bytes_ > total_bytes_) |
| 379 total_bytes_ = 0; | 384 total_bytes_ = 0; |
| 380 } | 385 } |
| 381 | 386 |
| 387 void DownloadItemImpl::UpdateProgress(int64 bytes_so_far, |
| 388 const std::string& hash_state) { |
| 389 hash_state_ = hash_state; |
| 390 |
| 391 received_bytes_ = bytes_so_far; |
| 392 |
| 393 // If we've received more data than we were expecting (bad server info?), |
| 394 // revert to 'unknown size mode'. |
| 395 if (received_bytes_ > total_bytes_) |
| 396 total_bytes_ = 0; |
| 397 } |
| 398 |
| 382 // Updates from the download thread may have been posted while this download | 399 // Updates from the download thread may have been posted while this download |
| 383 // was being cancelled in the UI thread, so we'll accept them unless we're | 400 // was being cancelled in the UI thread, so we'll accept them unless we're |
| 384 // complete. | 401 // complete. |
| 385 void DownloadItemImpl::UpdateProgress(int64 bytes_so_far, int64 bytes_per_sec) { | 402 void DownloadItemImpl::UpdateProgress(int64 bytes_so_far, |
| 403 int64 bytes_per_sec, |
| 404 const std::string& hash_state) { |
| 386 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 405 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 387 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 406 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 388 | 407 |
| 389 if (!IsInProgress()) { | 408 if (!IsInProgress()) { |
| 390 NOTREACHED(); | 409 NOTREACHED(); |
| 391 return; | 410 return; |
| 392 } | 411 } |
| 393 bytes_per_sec_ = bytes_per_sec; | 412 bytes_per_sec_ = bytes_per_sec; |
| 394 UpdateSize(bytes_so_far); | 413 UpdateProgress(bytes_so_far, hash_state); |
| 395 UpdateObservers(); | 414 UpdateObservers(); |
| 396 } | 415 } |
| 397 | 416 |
| 398 // Triggered by a user action. | 417 // Triggered by a user action. |
| 399 void DownloadItemImpl::Cancel(bool user_cancel) { | 418 void DownloadItemImpl::Cancel(bool user_cancel) { |
| 400 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 419 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 401 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 420 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 402 | 421 |
| 403 last_reason_ = user_cancel ? | 422 last_reason_ = user_cancel ? |
| 404 DOWNLOAD_INTERRUPT_REASON_USER_CANCELED : | 423 DOWNLOAD_INTERRUPT_REASON_USER_CANCELED : |
| (...skipping 27 matching lines...) Expand all Loading... |
| 432 Completed(); | 451 Completed(); |
| 433 } | 452 } |
| 434 | 453 |
| 435 void DownloadItemImpl::OnAllDataSaved( | 454 void DownloadItemImpl::OnAllDataSaved( |
| 436 int64 size, const std::string& final_hash) { | 455 int64 size, const std::string& final_hash) { |
| 437 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 456 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 438 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 457 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 439 | 458 |
| 440 DCHECK(!all_data_saved_); | 459 DCHECK(!all_data_saved_); |
| 441 all_data_saved_ = true; | 460 all_data_saved_ = true; |
| 442 UpdateSize(size); | 461 ProgressComplete(size, final_hash); |
| 443 hash_ = final_hash; | |
| 444 } | 462 } |
| 445 | 463 |
| 446 void DownloadItemImpl::OnDownloadedFileRemoved() { | 464 void DownloadItemImpl::OnDownloadedFileRemoved() { |
| 447 file_externally_removed_ = true; | 465 file_externally_removed_ = true; |
| 448 UpdateObservers(); | 466 UpdateObservers(); |
| 449 } | 467 } |
| 450 | 468 |
| 451 void DownloadItemImpl::MaybeCompleteDownload() { | 469 void DownloadItemImpl::MaybeCompleteDownload() { |
| 452 // TODO(rdsmith): Move logic for this function here. | 470 // TODO(rdsmith): Move logic for this function here. |
| 453 delegate_->MaybeCompleteDownload(this); | 471 delegate_->MaybeCompleteDownload(this); |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 499 } | 517 } |
| 500 | 518 |
| 501 void DownloadItemImpl::UpdateTarget() { | 519 void DownloadItemImpl::UpdateTarget() { |
| 502 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 520 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 503 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 521 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 504 | 522 |
| 505 if (state_info_.target_name.value().empty()) | 523 if (state_info_.target_name.value().empty()) |
| 506 state_info_.target_name = full_path_.BaseName(); | 524 state_info_.target_name = full_path_.BaseName(); |
| 507 } | 525 } |
| 508 | 526 |
| 509 void DownloadItemImpl::Interrupted(int64 size, InterruptReason reason) { | 527 void DownloadItemImpl::Interrupted(int64 size, |
| 528 const std::string& hash_state, |
| 529 InterruptReason reason) { |
| 510 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 530 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 511 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 531 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 512 | 532 |
| 513 if (!IsInProgress()) | 533 if (!IsInProgress()) |
| 514 return; | 534 return; |
| 515 | 535 |
| 516 last_reason_ = reason; | 536 last_reason_ = reason; |
| 517 UpdateSize(size); | 537 UpdateProgress(size, hash_state); |
| 518 download_stats::RecordDownloadInterrupted(reason, | 538 download_stats::RecordDownloadInterrupted(reason, |
| 519 received_bytes_, | 539 received_bytes_, |
| 520 total_bytes_); | 540 total_bytes_); |
| 521 TransitionTo(INTERRUPTED); | 541 TransitionTo(INTERRUPTED); |
| 522 } | 542 } |
| 523 | 543 |
| 524 void DownloadItemImpl::Delete(DeleteReason reason) { | 544 void DownloadItemImpl::Delete(DeleteReason reason) { |
| 525 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 545 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 526 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 546 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 527 | 547 |
| (...skipping 259 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 787 BrowserThread::FILE, FROM_HERE, | 807 BrowserThread::FILE, FROM_HERE, |
| 788 base::Bind(&DownloadFileManager::CancelDownload, | 808 base::Bind(&DownloadFileManager::CancelDownload, |
| 789 file_manager, download_id_)); | 809 file_manager, download_id_)); |
| 790 } | 810 } |
| 791 | 811 |
| 792 void DownloadItemImpl::Init(bool active) { | 812 void DownloadItemImpl::Init(bool active) { |
| 793 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. | 813 // TODO(rdsmith): Change to DCHECK after http://crbug.com/85408 resolved. |
| 794 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 814 CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 795 | 815 |
| 796 UpdateTarget(); | 816 UpdateTarget(); |
| 797 if (active) { | 817 if (active) |
| 798 download_stats::RecordDownloadCount(download_stats::START_COUNT); | 818 download_stats::RecordDownloadCount(download_stats::START_COUNT); |
| 799 } | |
| 800 VLOG(20) << __FUNCTION__ << "() " << DebugString(true); | 819 VLOG(20) << __FUNCTION__ << "() " << DebugString(true); |
| 801 } | 820 } |
| 802 | 821 |
| 803 // TODO(ahendrickson) -- Move |INTERRUPTED| from |IsCancelled()| to | 822 // TODO(ahendrickson) -- Move |INTERRUPTED| from |IsCancelled()| to |
| 804 // |IsPartialDownload()|, when resuming interrupted downloads is implemented. | 823 // |IsPartialDownload()|, when resuming interrupted downloads is implemented. |
| 805 bool DownloadItemImpl::IsPartialDownload() const { | 824 bool DownloadItemImpl::IsPartialDownload() const { |
| 806 return (state_ == IN_PROGRESS); | 825 return (state_ == IN_PROGRESS); |
| 807 } | 826 } |
| 808 | 827 |
| 809 bool DownloadItemImpl::IsInProgress() const { | 828 bool DownloadItemImpl::IsInProgress() const { |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 850 } | 869 } |
| 851 | 870 |
| 852 if (verbose) { | 871 if (verbose) { |
| 853 description += base::StringPrintf( | 872 description += base::StringPrintf( |
| 854 " db_handle = %" PRId64 | 873 " db_handle = %" PRId64 |
| 855 " total_bytes = %" PRId64 | 874 " total_bytes = %" PRId64 |
| 856 " received_bytes = %" PRId64 | 875 " received_bytes = %" PRId64 |
| 857 " is_paused = %c" | 876 " is_paused = %c" |
| 858 " is_otr = %c" | 877 " is_otr = %c" |
| 859 " safety_state = %s" | 878 " safety_state = %s" |
| 879 " last_modified = '%s'" |
| 880 " etag = '%s'" |
| 860 " url_chain = \n\t\"%s\"\n\t" | 881 " url_chain = \n\t\"%s\"\n\t" |
| 861 " target_name = \"%" PRFilePath "\"" | 882 " target_name = \"%" PRFilePath "\"" |
| 862 " full_path = \"%" PRFilePath "\"", | 883 " full_path = \"%" PRFilePath "\"", |
| 863 GetDbHandle(), | 884 GetDbHandle(), |
| 864 GetTotalBytes(), | 885 GetTotalBytes(), |
| 865 GetReceivedBytes(), | 886 GetReceivedBytes(), |
| 866 IsPaused() ? 'T' : 'F', | 887 IsPaused() ? 'T' : 'F', |
| 867 IsOtr() ? 'T' : 'F', | 888 IsOtr() ? 'T' : 'F', |
| 868 DebugSafetyStateString(GetSafetyState()), | 889 DebugSafetyStateString(GetSafetyState()), |
| 890 GetLastModifiedTime().c_str(), |
| 891 GetETag().c_str(), |
| 869 url_list.c_str(), | 892 url_list.c_str(), |
| 870 state_info_.target_name.value().c_str(), | 893 state_info_.target_name.value().c_str(), |
| 871 GetFullPath().value().c_str()); | 894 GetFullPath().value().c_str()); |
| 872 } else { | 895 } else { |
| 873 description += base::StringPrintf(" url = \"%s\"", url_list.c_str()); | 896 description += base::StringPrintf(" url = \"%s\"", url_list.c_str()); |
| 874 } | 897 } |
| 875 | 898 |
| 876 description += " }"; | 899 description += " }"; |
| 877 | 900 |
| 878 return description; | 901 return description; |
| (...skipping 29 matching lines...) Expand all Loading... |
| 908 } | 931 } |
| 909 std::string DownloadItemImpl::GetRemoteAddress() const { | 932 std::string DownloadItemImpl::GetRemoteAddress() const { |
| 910 return remote_address_; | 933 return remote_address_; |
| 911 } | 934 } |
| 912 int64 DownloadItemImpl::GetTotalBytes() const { return total_bytes_; } | 935 int64 DownloadItemImpl::GetTotalBytes() const { return total_bytes_; } |
| 913 void DownloadItemImpl::SetTotalBytes(int64 total_bytes) { | 936 void DownloadItemImpl::SetTotalBytes(int64 total_bytes) { |
| 914 total_bytes_ = total_bytes; | 937 total_bytes_ = total_bytes; |
| 915 } | 938 } |
| 916 const std::string& DownloadItemImpl::GetHash() const { return hash_; } | 939 const std::string& DownloadItemImpl::GetHash() const { return hash_; } |
| 917 int64 DownloadItemImpl::GetReceivedBytes() const { return received_bytes_; } | 940 int64 DownloadItemImpl::GetReceivedBytes() const { return received_bytes_; } |
| 941 const std::string& DownloadItemImpl::GetHashState() const { |
| 942 return hash_state_; |
| 943 } |
| 918 int32 DownloadItemImpl::GetId() const { return download_id_.local(); } | 944 int32 DownloadItemImpl::GetId() const { return download_id_.local(); } |
| 919 DownloadId DownloadItemImpl::GetGlobalId() const { return download_id_; } | 945 DownloadId DownloadItemImpl::GetGlobalId() const { return download_id_; } |
| 920 base::Time DownloadItemImpl::GetStartTime() const { return start_time_; } | 946 base::Time DownloadItemImpl::GetStartTime() const { return start_time_; } |
| 921 base::Time DownloadItemImpl::GetEndTime() const { return end_time_; } | 947 base::Time DownloadItemImpl::GetEndTime() const { return end_time_; } |
| 922 void DownloadItemImpl::SetDbHandle(int64 handle) { db_handle_ = handle; } | 948 void DownloadItemImpl::SetDbHandle(int64 handle) { db_handle_ = handle; } |
| 923 int64 DownloadItemImpl::GetDbHandle() const { return db_handle_; } | 949 int64 DownloadItemImpl::GetDbHandle() const { return db_handle_; } |
| 924 bool DownloadItemImpl::IsPaused() const { return is_paused_; } | 950 bool DownloadItemImpl::IsPaused() const { return is_paused_; } |
| 925 bool DownloadItemImpl::GetOpenWhenComplete() const { | 951 bool DownloadItemImpl::GetOpenWhenComplete() const { |
| 926 return open_when_complete_; | 952 return open_when_complete_; |
| 927 } | 953 } |
| (...skipping 13 matching lines...) Expand all Loading... |
| 941 } | 967 } |
| 942 bool DownloadItemImpl::PromptUserForSaveLocation() const { | 968 bool DownloadItemImpl::PromptUserForSaveLocation() const { |
| 943 return state_info_.prompt_user_for_save_location; | 969 return state_info_.prompt_user_for_save_location; |
| 944 } | 970 } |
| 945 const FilePath& DownloadItemImpl::GetSuggestedPath() const { | 971 const FilePath& DownloadItemImpl::GetSuggestedPath() const { |
| 946 return state_info_.suggested_path; | 972 return state_info_.suggested_path; |
| 947 } | 973 } |
| 948 bool DownloadItemImpl::IsTemporary() const { return is_temporary_; } | 974 bool DownloadItemImpl::IsTemporary() const { return is_temporary_; } |
| 949 void DownloadItemImpl::SetOpened(bool opened) { opened_ = opened; } | 975 void DownloadItemImpl::SetOpened(bool opened) { opened_ = opened; } |
| 950 bool DownloadItemImpl::GetOpened() const { return opened_; } | 976 bool DownloadItemImpl::GetOpened() const { return opened_; } |
| 977 const std::string& DownloadItemImpl::GetLastModifiedTime() const { |
| 978 return last_modified_time_; |
| 979 } |
| 980 const std::string& DownloadItemImpl::GetETag() const { return etag_; } |
| 951 InterruptReason DownloadItemImpl::GetLastReason() const { | 981 InterruptReason DownloadItemImpl::GetLastReason() const { |
| 952 return last_reason_; | 982 return last_reason_; |
| 953 } | 983 } |
| 954 DownloadStateInfo DownloadItemImpl::GetStateInfo() const { return state_info_; } | 984 DownloadStateInfo DownloadItemImpl::GetStateInfo() const { return state_info_; } |
| 955 bool DownloadItemImpl::NeedsRename() const { | 985 bool DownloadItemImpl::NeedsRename() const { |
| 956 return state_info_.target_name != full_path_.BaseName(); | 986 return state_info_.target_name != full_path_.BaseName(); |
| 957 } | 987 } |
| 958 void DownloadItemImpl::MockDownloadOpenForTesting() { open_enabled_ = false; } | 988 void DownloadItemImpl::MockDownloadOpenForTesting() { open_enabled_ = false; } |
| 959 | 989 |
| 960 DownloadItem::ExternalData* | 990 DownloadItem::ExternalData* |
| 961 DownloadItemImpl::GetExternalData(const void* key) { | 991 DownloadItemImpl::GetExternalData(const void* key) { |
| 962 if (!ContainsKey(external_data_map_, key)) | 992 if (!ContainsKey(external_data_map_, key)) |
| 963 return NULL; | 993 return NULL; |
| 964 return external_data_map_[key]; | 994 return external_data_map_[key]; |
| 965 } | 995 } |
| 966 | 996 |
| 967 void DownloadItemImpl::SetExternalData( | 997 void DownloadItemImpl::SetExternalData( |
| 968 const void* key, DownloadItem::ExternalData* data) { | 998 const void* key, DownloadItem::ExternalData* data) { |
| 969 std::map<const void*, ExternalData*>::iterator it = | 999 std::map<const void*, ExternalData*>::iterator it = |
| 970 external_data_map_.find(key); | 1000 external_data_map_.find(key); |
| 971 | 1001 |
| 972 if (it == external_data_map_.end()) { | 1002 if (it == external_data_map_.end()) { |
| 973 external_data_map_[key] = data; | 1003 external_data_map_[key] = data; |
| 974 } else if (it->second != data) { | 1004 } else if (it->second != data) { |
| 975 delete it->second; | 1005 delete it->second; |
| 976 it->second = data; | 1006 it->second = data; |
| 977 } | 1007 } |
| 978 } | 1008 } |
| OLD | NEW |