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

Side by Side Diff: components/history/core/browser/download_database.cc

Issue 1548113002: Switch to standard integer types in components/, part 2 of 4. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: gn Created 4 years, 12 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
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 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 "components/history/core/browser/download_database.h" 5 #include "components/history/core/browser/download_database.h"
6 6
7 #include <limits> 7 #include <limits>
8 #include <string> 8 #include <string>
9 #include <vector> 9 #include <vector>
10 10
(...skipping 212 matching lines...) Expand 10 before | Expand all | Expand 10 after
223 return EnsureColumnExists("end_time", "INTEGER NOT NULL DEFAULT 0") && 223 return EnsureColumnExists("end_time", "INTEGER NOT NULL DEFAULT 0") &&
224 EnsureColumnExists("opened", "INTEGER NOT NULL DEFAULT 0"); 224 EnsureColumnExists("opened", "INTEGER NOT NULL DEFAULT 0");
225 } else { 225 } else {
226 // If the "downloads" table doesn't exist, the downloads_url_chain 226 // If the "downloads" table doesn't exist, the downloads_url_chain
227 // table better not. 227 // table better not.
228 return (!GetDB().DoesTableExist("downloads_url_chain") && 228 return (!GetDB().DoesTableExist("downloads_url_chain") &&
229 GetDB().Execute(kSchema) && GetDB().Execute(kUrlChainSchema)); 229 GetDB().Execute(kSchema) && GetDB().Execute(kUrlChainSchema));
230 } 230 }
231 } 231 }
232 232
233 uint32 DownloadDatabase::GetNextDownloadId() { 233 uint32_t DownloadDatabase::GetNextDownloadId() {
234 sql::Statement select_max_id(GetDB().GetUniqueStatement( 234 sql::Statement select_max_id(GetDB().GetUniqueStatement(
235 "SELECT max(id) FROM downloads")); 235 "SELECT max(id) FROM downloads"));
236 bool result = select_max_id.Step(); 236 bool result = select_max_id.Step();
237 DCHECK(result); 237 DCHECK(result);
238 // If there are zero records in the downloads table, then max(id) will 238 // If there are zero records in the downloads table, then max(id) will
239 // return 0 = kInvalidDownloadId, so GetNextDownloadId() will set 239 // return 0 = kInvalidDownloadId, so GetNextDownloadId() will set
240 // *id = kInvalidDownloadId + 1. 240 // *id = kInvalidDownloadId + 1.
241 // 241 //
242 // If there is at least one record but all of the |id|s are 242 // If there is at least one record but all of the |id|s are
243 // <= kInvalidDownloadId, then max(id) will return <= kInvalidDownloadId, 243 // <= kInvalidDownloadId, then max(id) will return <= kInvalidDownloadId,
244 // so GetNextDownloadId() should return kInvalidDownloadId + 1. 244 // so GetNextDownloadId() should return kInvalidDownloadId + 1.
245 // 245 //
246 // Note that any records with |id <= kInvalidDownloadId| will be dropped in 246 // Note that any records with |id <= kInvalidDownloadId| will be dropped in
247 // QueryDownloads(). 247 // QueryDownloads().
248 // 248 //
249 // SQLITE doesn't have unsigned integers. 249 // SQLITE doesn't have unsigned integers.
250 return 1 + static_cast<uint32>(std::max( 250 return 1 + static_cast<uint32_t>(
251 static_cast<int64>(kInvalidDownloadId), 251 std::max(static_cast<int64_t>(kInvalidDownloadId),
252 select_max_id.ColumnInt64(0))); 252 select_max_id.ColumnInt64(0)));
253 } 253 }
254 254
255 bool DownloadDatabase::DropDownloadTable() { 255 bool DownloadDatabase::DropDownloadTable() {
256 return GetDB().Execute("DROP TABLE downloads"); 256 return GetDB().Execute("DROP TABLE downloads");
257 } 257 }
258 258
259 void DownloadDatabase::QueryDownloads(std::vector<DownloadRow>* results) { 259 void DownloadDatabase::QueryDownloads(std::vector<DownloadRow>* results) {
260 EnsureInProgressEntriesCleanedUp(); 260 EnsureInProgressEntriesCleanedUp();
261 261
262 results->clear(); 262 results->clear();
263 std::set<uint32> ids; 263 std::set<uint32_t> ids;
264 264
265 std::map<uint32, DownloadRow*> info_map; 265 std::map<uint32_t, DownloadRow*> info_map;
266 266
267 sql::Statement statement_main(GetDB().GetCachedStatement(SQL_FROM_HERE, 267 sql::Statement statement_main(GetDB().GetCachedStatement(SQL_FROM_HERE,
268 "SELECT id, current_path, target_path, " 268 "SELECT id, current_path, target_path, "
269 "mime_type, original_mime_type, " 269 "mime_type, original_mime_type, "
270 "start_time, received_bytes, " 270 "start_time, received_bytes, "
271 "total_bytes, state, danger_type, interrupt_reason, end_time, opened, " 271 "total_bytes, state, danger_type, interrupt_reason, end_time, opened, "
272 "referrer, by_ext_id, by_ext_name, etag, last_modified " 272 "referrer, by_ext_id, by_ext_name, etag, last_modified "
273 "FROM downloads ORDER BY start_time")); 273 "FROM downloads ORDER BY start_time"));
274 274
275 while (statement_main.Step()) { 275 while (statement_main.Step()) {
276 scoped_ptr<DownloadRow> info(new DownloadRow()); 276 scoped_ptr<DownloadRow> info(new DownloadRow());
277 int column = 0; 277 int column = 0;
278 278
279 // SQLITE does not have unsigned integers, so explicitly handle negative 279 // SQLITE does not have unsigned integers, so explicitly handle negative
280 // |id|s instead of casting them to very large uint32s, which would break 280 // |id|s instead of casting them to very large uint32s, which would break
281 // the max(id) logic in GetNextDownloadId(). 281 // the max(id) logic in GetNextDownloadId().
282 int64 signed_id = statement_main.ColumnInt64(column++); 282 int64_t signed_id = statement_main.ColumnInt64(column++);
283 info->id = IntToDownloadId(signed_id); 283 info->id = IntToDownloadId(signed_id);
284 info->current_path = ColumnFilePath(statement_main, column++); 284 info->current_path = ColumnFilePath(statement_main, column++);
285 info->target_path = ColumnFilePath(statement_main, column++); 285 info->target_path = ColumnFilePath(statement_main, column++);
286 info->mime_type = statement_main.ColumnString(column++); 286 info->mime_type = statement_main.ColumnString(column++);
287 info->original_mime_type = statement_main.ColumnString(column++); 287 info->original_mime_type = statement_main.ColumnString(column++);
288 info->start_time = 288 info->start_time =
289 base::Time::FromInternalValue(statement_main.ColumnInt64(column++)); 289 base::Time::FromInternalValue(statement_main.ColumnInt64(column++));
290 info->received_bytes = statement_main.ColumnInt64(column++); 290 info->received_bytes = statement_main.ColumnInt64(column++);
291 info->total_bytes = statement_main.ColumnInt64(column++); 291 info->total_bytes = statement_main.ColumnInt64(column++);
292 int state = statement_main.ColumnInt(column++); 292 int state = statement_main.ColumnInt(column++);
293 info->state = IntToDownloadState(state); 293 info->state = IntToDownloadState(state);
294 if (info->state == DownloadState::INVALID) 294 if (info->state == DownloadState::INVALID)
295 UMA_HISTOGRAM_COUNTS("Download.DatabaseInvalidState", state); 295 UMA_HISTOGRAM_COUNTS("Download.DatabaseInvalidState", state);
296 info->danger_type = 296 info->danger_type =
297 IntToDownloadDangerType(statement_main.ColumnInt(column++)); 297 IntToDownloadDangerType(statement_main.ColumnInt(column++));
298 info->interrupt_reason = 298 info->interrupt_reason =
299 IntToDownloadInterruptReason(statement_main.ColumnInt(column++)); 299 IntToDownloadInterruptReason(statement_main.ColumnInt(column++));
300 info->end_time = 300 info->end_time =
301 base::Time::FromInternalValue(statement_main.ColumnInt64(column++)); 301 base::Time::FromInternalValue(statement_main.ColumnInt64(column++));
302 info->opened = statement_main.ColumnInt(column++) != 0; 302 info->opened = statement_main.ColumnInt(column++) != 0;
303 info->referrer_url = GURL(statement_main.ColumnString(column++)); 303 info->referrer_url = GURL(statement_main.ColumnString(column++));
304 info->by_ext_id = statement_main.ColumnString(column++); 304 info->by_ext_id = statement_main.ColumnString(column++);
305 info->by_ext_name = statement_main.ColumnString(column++); 305 info->by_ext_name = statement_main.ColumnString(column++);
306 info->etag = statement_main.ColumnString(column++); 306 info->etag = statement_main.ColumnString(column++);
307 info->last_modified = statement_main.ColumnString(column++); 307 info->last_modified = statement_main.ColumnString(column++);
308 308
309 // If the record is corrupted, note that and drop it. 309 // If the record is corrupted, note that and drop it.
310 // http://crbug.com/251269 310 // http://crbug.com/251269
311 DroppedReason dropped_reason = DROPPED_REASON_MAX; 311 DroppedReason dropped_reason = DROPPED_REASON_MAX;
312 if (signed_id <= static_cast<int64>(kInvalidDownloadId)) { 312 if (signed_id <= static_cast<int64_t>(kInvalidDownloadId)) {
313 // SQLITE doesn't have unsigned integers. 313 // SQLITE doesn't have unsigned integers.
314 dropped_reason = DROPPED_REASON_BAD_ID; 314 dropped_reason = DROPPED_REASON_BAD_ID;
315 } else if (!ids.insert(info->id).second) { 315 } else if (!ids.insert(info->id).second) {
316 dropped_reason = DROPPED_REASON_DUPLICATE_ID; 316 dropped_reason = DROPPED_REASON_DUPLICATE_ID;
317 NOTREACHED() << info->id; 317 NOTREACHED() << info->id;
318 } else if (info->state == DownloadState::INVALID) { 318 } else if (info->state == DownloadState::INVALID) {
319 dropped_reason = DROPPED_REASON_BAD_STATE; 319 dropped_reason = DROPPED_REASON_BAD_STATE;
320 } else if (info->danger_type == DownloadDangerType::INVALID) { 320 } else if (info->danger_type == DownloadDangerType::INVALID) {
321 dropped_reason = DROPPED_REASON_BAD_DANGER_TYPE; 321 dropped_reason = DROPPED_REASON_BAD_DANGER_TYPE;
322 } 322 }
323 if (dropped_reason != DROPPED_REASON_MAX) { 323 if (dropped_reason != DROPPED_REASON_MAX) {
324 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseRecordDropped", 324 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseRecordDropped",
325 dropped_reason, 325 dropped_reason,
326 DROPPED_REASON_MAX + 1); 326 DROPPED_REASON_MAX + 1);
327 } else { 327 } else {
328 DCHECK(!ContainsKey(info_map, info->id)); 328 DCHECK(!ContainsKey(info_map, info->id));
329 uint32 id = info->id; 329 uint32_t id = info->id;
330 info_map[id] = info.release(); 330 info_map[id] = info.release();
331 } 331 }
332 } 332 }
333 333
334 sql::Statement statement_chain(GetDB().GetCachedStatement( 334 sql::Statement statement_chain(GetDB().GetCachedStatement(
335 SQL_FROM_HERE, 335 SQL_FROM_HERE,
336 "SELECT id, chain_index, url FROM downloads_url_chains " 336 "SELECT id, chain_index, url FROM downloads_url_chains "
337 "ORDER BY id, chain_index")); 337 "ORDER BY id, chain_index"));
338 338
339 while (statement_chain.Step()) { 339 while (statement_chain.Step()) {
340 int column = 0; 340 int column = 0;
341 // See the comment above about SQLITE lacking unsigned integers. 341 // See the comment above about SQLITE lacking unsigned integers.
342 int64 signed_id = statement_chain.ColumnInt64(column++); 342 int64_t signed_id = statement_chain.ColumnInt64(column++);
343 int chain_index = statement_chain.ColumnInt(column++); 343 int chain_index = statement_chain.ColumnInt(column++);
344 344
345 if (signed_id <= static_cast<int64>(kInvalidDownloadId)) 345 if (signed_id <= static_cast<int64_t>(kInvalidDownloadId))
346 continue; 346 continue;
347 uint32 id = IntToDownloadId(signed_id); 347 uint32_t id = IntToDownloadId(signed_id);
348 348
349 // Note that these DCHECKs may trip as a result of corrupted databases. 349 // Note that these DCHECKs may trip as a result of corrupted databases.
350 // We have them because in debug builds the chances are higher there's 350 // We have them because in debug builds the chances are higher there's
351 // an actual bug than that the database is corrupt, but we handle the 351 // an actual bug than that the database is corrupt, but we handle the
352 // DB corruption case in production code. 352 // DB corruption case in production code.
353 353
354 // Confirm the id has already been seen--if it hasn't, discard the 354 // Confirm the id has already been seen--if it hasn't, discard the
355 // record. 355 // record.
356 DCHECK(ContainsKey(info_map, id)); 356 DCHECK(ContainsKey(info_map, id));
357 if (!ContainsKey(info_map, id)) 357 if (!ContainsKey(info_map, id))
358 continue; 358 continue;
359 359
360 // Confirm all previous URLs in the chain have already been seen; 360 // Confirm all previous URLs in the chain have already been seen;
361 // if not, fill in with null or discard record. 361 // if not, fill in with null or discard record.
362 int current_chain_size = static_cast<int>(info_map[id]->url_chain.size()); 362 int current_chain_size = static_cast<int>(info_map[id]->url_chain.size());
363 std::vector<GURL>* url_chain(&info_map[id]->url_chain); 363 std::vector<GURL>* url_chain(&info_map[id]->url_chain);
364 DCHECK_EQ(chain_index, current_chain_size); 364 DCHECK_EQ(chain_index, current_chain_size);
365 while (current_chain_size < chain_index) { 365 while (current_chain_size < chain_index) {
366 url_chain->push_back(GURL()); 366 url_chain->push_back(GURL());
367 current_chain_size++; 367 current_chain_size++;
368 } 368 }
369 if (current_chain_size > chain_index) 369 if (current_chain_size > chain_index)
370 continue; 370 continue;
371 371
372 // Save the record. 372 // Save the record.
373 url_chain->push_back(GURL(statement_chain.ColumnString(2))); 373 url_chain->push_back(GURL(statement_chain.ColumnString(2)));
374 } 374 }
375 375
376 for (std::map<uint32, DownloadRow*>::iterator 376 for (std::map<uint32_t, DownloadRow*>::iterator it = info_map.begin();
377 it = info_map.begin(); it != info_map.end(); ++it) { 377 it != info_map.end(); ++it) {
378 DownloadRow* row = it->second; 378 DownloadRow* row = it->second;
379 bool empty_url_chain = row->url_chain.empty(); 379 bool empty_url_chain = row->url_chain.empty();
380 UMA_HISTOGRAM_BOOLEAN("Download.DatabaseEmptyUrlChain", empty_url_chain); 380 UMA_HISTOGRAM_BOOLEAN("Download.DatabaseEmptyUrlChain", empty_url_chain);
381 if (empty_url_chain) { 381 if (empty_url_chain) {
382 RemoveDownload(row->id); 382 RemoveDownload(row->id);
383 } else { 383 } else {
384 // Copy the contents of the stored info. 384 // Copy the contents of the stored info.
385 results->push_back(*row); 385 results->push_back(*row);
386 } 386 }
387 delete row; 387 delete row;
(...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after
534 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseURLChainInsertError", 534 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseURLChainInsertError",
535 GetDB().GetErrorCode() & 0xff, 50); 535 GetDB().GetErrorCode() & 0xff, 50);
536 RemoveDownload(info.id); 536 RemoveDownload(info.id);
537 return false; 537 return false;
538 } 538 }
539 statement_insert_chain.Reset(true); 539 statement_insert_chain.Reset(true);
540 } 540 }
541 return true; 541 return true;
542 } 542 }
543 543
544 void DownloadDatabase::RemoveDownload(uint32 id) { 544 void DownloadDatabase::RemoveDownload(uint32_t id) {
545 EnsureInProgressEntriesCleanedUp(); 545 EnsureInProgressEntriesCleanedUp();
546 546
547 sql::Statement downloads_statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 547 sql::Statement downloads_statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
548 "DELETE FROM downloads WHERE id=?")); 548 "DELETE FROM downloads WHERE id=?"));
549 downloads_statement.BindInt(0, id); 549 downloads_statement.BindInt(0, id);
550 if (!downloads_statement.Run()) { 550 if (!downloads_statement.Run()) {
551 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseMainDeleteError", 551 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseMainDeleteError",
552 GetDB().GetErrorCode() & 0xff, 50); 552 GetDB().GetErrorCode() & 0xff, 50);
553 return; 553 return;
554 } 554 }
555 RemoveDownloadURLs(id); 555 RemoveDownloadURLs(id);
556 } 556 }
557 557
558 void DownloadDatabase::RemoveDownloadURLs(uint32 id) { 558 void DownloadDatabase::RemoveDownloadURLs(uint32_t id) {
559 sql::Statement urlchain_statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 559 sql::Statement urlchain_statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
560 "DELETE FROM downloads_url_chains WHERE id=?")); 560 "DELETE FROM downloads_url_chains WHERE id=?"));
561 urlchain_statement.BindInt(0, id); 561 urlchain_statement.BindInt(0, id);
562 if (!urlchain_statement.Run()) { 562 if (!urlchain_statement.Run()) {
563 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseURLChainDeleteError", 563 UMA_HISTOGRAM_ENUMERATION("Download.DatabaseURLChainDeleteError",
564 GetDB().GetErrorCode() & 0xff, 50); 564 GetDB().GetErrorCode() & 0xff, 50);
565 } 565 }
566 } 566 }
567 567
568 size_t DownloadDatabase::CountDownloads() { 568 size_t DownloadDatabase::CountDownloads() {
569 EnsureInProgressEntriesCleanedUp(); 569 EnsureInProgressEntriesCleanedUp();
570 570
571 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 571 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
572 "SELECT count(*) from downloads")); 572 "SELECT count(*) from downloads"));
573 statement.Step(); 573 statement.Step();
574 return statement.ColumnInt(0); 574 return statement.ColumnInt(0);
575 } 575 }
576 576
577 } // namespace history 577 } // namespace history
OLDNEW
« no previous file with comments | « components/history/core/browser/download_database.h ('k') | components/history/core/browser/download_row.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698