| Index: chrome/browser/download/download_history.cc | 
| diff --git a/chrome/browser/download/download_history.cc b/chrome/browser/download/download_history.cc | 
| index 115541a4d24742ed52fa9ed9683f915109b60175..f1b6388f3366209510e6f11a35f44eeab1649750 100644 | 
| --- a/chrome/browser/download/download_history.cc | 
| +++ b/chrome/browser/download/download_history.cc | 
| @@ -4,22 +4,29 @@ | 
|  | 
| #include "chrome/browser/download/download_history.h" | 
|  | 
| +#include "base/bind.h" | 
| #include "base/logging.h" | 
| +#include "chrome/browser/download/download_item.h" | 
| +#include "chrome/browser/download/download_manager.h" | 
| +#include "chrome/browser/download/download_prefs.h" | 
| #include "chrome/browser/history/download_history_info.h" | 
| #include "chrome/browser/history/history_marshaling.h" | 
| -#include "chrome/browser/download/download_item.h" | 
| #include "chrome/browser/profiles/profile.h" | 
|  | 
| -// Our download table ID starts at 1, so we use 0 to represent a download that | 
| -// has started, but has not yet had its data persisted in the table. We use fake | 
| -// database handles in incognito mode starting at -1 and progressively getting | 
| -// more negative. | 
| -// static | 
| -const int DownloadHistory::kUninitializedHandle = 0; | 
| +namespace { | 
| +int GetNextIdThunk(Profile* profile) { | 
| +  DCHECK(profile != NULL); | 
| +  DCHECK(profile->GetDownloadManager() != NULL); | 
| +  DCHECK(profile->GetDownloadManager()->download_prefs() != NULL); | 
| +  if ((profile == NULL) || | 
| +      (profile->GetDownloadManager() == NULL) || | 
| +      (profile->GetDownloadManager()->download_prefs() == NULL)) return -1; | 
| +  return profile->GetDownloadManager()->download_prefs()->GetNextId(); | 
| +} | 
| +}  // anonymous namespace | 
|  | 
| DownloadHistory::DownloadHistory(Profile* profile) | 
| -    : profile_(profile), | 
| -      next_fake_db_handle_(kUninitializedHandle - 1) { | 
| +    : profile_(profile) { | 
| DCHECK(profile); | 
| } | 
|  | 
| @@ -40,7 +47,9 @@ void DownloadHistory::Load(HistoryService::DownloadQueryCallback* callback) { | 
| delete callback; | 
| return; | 
| } | 
| -  hs->QueryDownloads(&history_consumer_, callback); | 
| +  hs->QueryDownloads(&history_consumer_, | 
| +                     base::Bind(&GetNextIdThunk, profile_), | 
| +                     callback); | 
|  | 
| // This is the initial load, so do a cleanup of corrupt in-progress entries. | 
| hs->CleanUpInProgressEntries(); | 
| @@ -70,64 +79,52 @@ void DownloadHistory::AddEntry( | 
| DownloadItem* download_item, | 
| HistoryService::DownloadCreateCallback* callback) { | 
| DCHECK(download_item); | 
| -  // Do not store the download in the history database for a few special cases: | 
| -  // - incognito mode (that is the point of this mode) | 
| -  // - extensions (users don't think of extension installation as 'downloading') | 
| -  // - temporary download, like in drag-and-drop | 
| -  // - history service is not available (e.g. in tests) | 
| -  // We have to make sure that these handles don't collide with normal db | 
| -  // handles, so we use a negative value. Eventually, they could overlap, but | 
| -  // you'd have to do enough downloading that your ISP would likely stab you in | 
| -  // the neck first. YMMV. | 
| HistoryService* hs = profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); | 
| -  if (download_item->is_otr() || download_item->is_extension_install() || | 
| -      download_item->is_temporary() || !hs) { | 
| -    callback->RunWithParams( | 
| -        history::DownloadCreateRequest::TupleType(download_item->id(), | 
| -                                                  GetNextFakeDbHandle())); | 
| +  if (download_item->is_otr() || | 
| +      download_item->is_extension_install() || | 
| +      download_item->is_temporary() || | 
| +      (hs == NULL)) { | 
| +    callback->Run(download_item->id()); | 
| delete callback; | 
| return; | 
| } | 
|  | 
| -  int32 id = download_item->id(); | 
| DownloadHistoryInfo history_info = download_item->GetHistoryInfo(); | 
| -  hs->CreateDownload(id, history_info, &history_consumer_, callback); | 
| +  hs->CreateDownload(download_item->id(), | 
| +                     history_info, | 
| +                     &history_consumer_, | 
| +                     callback); | 
| } | 
|  | 
| void DownloadHistory::UpdateEntry(DownloadItem* download_item) { | 
| // Don't store info in the database if the download was initiated while in | 
| // incognito mode or if it hasn't been initialized in our database table. | 
| -  if (download_item->db_handle() <= kUninitializedHandle) | 
| -    return; | 
| - | 
| HistoryService* hs = profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); | 
| -  if (!hs) | 
| -    return; | 
| - | 
| +  if ((download_item == NULL) || | 
| +      (hs == NULL) || | 
| +      !download_item->IsInHistory()) return; | 
| hs->UpdateDownload(download_item->received_bytes(), | 
| download_item->state(), | 
| -                     download_item->db_handle()); | 
| +                     download_item->id()); | 
| } | 
|  | 
| void DownloadHistory::UpdateDownloadPath(DownloadItem* download_item, | 
| const FilePath& new_path) { | 
| // No update necessary if the download was initiated while in incognito mode. | 
| -  if (download_item->db_handle() <= kUninitializedHandle) | 
| -    return; | 
| - | 
| HistoryService* hs = profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); | 
| -  if (hs) | 
| -    hs->UpdateDownloadPath(new_path, download_item->db_handle()); | 
| +  if ((hs == NULL) || | 
| +      (download_item == NULL) || | 
| +      !download_item->IsInHistory()) return; | 
| +  hs->UpdateDownloadPath(new_path, download_item->id()); | 
| } | 
|  | 
| void DownloadHistory::RemoveEntry(DownloadItem* download_item) { | 
| // No update necessary if the download was initiated while in incognito mode. | 
| -  if (download_item->db_handle() <= kUninitializedHandle) | 
| -    return; | 
| - | 
| HistoryService* hs = profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); | 
| -  if (hs) | 
| -    hs->RemoveDownload(download_item->db_handle()); | 
| +  if ((hs == NULL) || | 
| +      (download_item == NULL) || | 
| +      !download_item->IsInHistory()) return; | 
| +  hs->RemoveDownload(download_item->id()); | 
| } | 
|  | 
| void DownloadHistory::RemoveEntriesBetween(const base::Time remove_begin, | 
| @@ -137,10 +134,6 @@ void DownloadHistory::RemoveEntriesBetween(const base::Time remove_begin, | 
| hs->RemoveDownloadsBetween(remove_begin, remove_end); | 
| } | 
|  | 
| -int64 DownloadHistory::GetNextFakeDbHandle() { | 
| -  return next_fake_db_handle_--; | 
| -} | 
| - | 
| void DownloadHistory::OnGotVisitCountToHost(HistoryService::Handle handle, | 
| bool found_visits, | 
| int count, | 
|  |