Chromium Code Reviews| OLD | NEW |
|---|---|
| 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 174 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 185 return EnsureColumnExists("etag", "VARCHAR NOT NULL DEFAULT \"\"") && | 185 return EnsureColumnExists("etag", "VARCHAR NOT NULL DEFAULT \"\"") && |
| 186 EnsureColumnExists("last_modified", "VARCHAR NOT NULL DEFAULT \"\""); | 186 EnsureColumnExists("last_modified", "VARCHAR NOT NULL DEFAULT \"\""); |
| 187 } | 187 } |
| 188 | 188 |
| 189 bool DownloadDatabase::MigrateHashHttpMethodAndGenerateGuids() { | 189 bool DownloadDatabase::MigrateHashHttpMethodAndGenerateGuids() { |
| 190 if (!EnsureColumnExists("guid", "VARCHAR NOT NULL DEFAULT ''") || | 190 if (!EnsureColumnExists("guid", "VARCHAR NOT NULL DEFAULT ''") || |
| 191 !EnsureColumnExists("hash", "BLOB NOT NULL DEFAULT X''") || | 191 !EnsureColumnExists("hash", "BLOB NOT NULL DEFAULT X''") || |
| 192 !EnsureColumnExists("http_method", "VARCHAR NOT NULL DEFAULT ''")) | 192 !EnsureColumnExists("http_method", "VARCHAR NOT NULL DEFAULT ''")) |
| 193 return false; | 193 return false; |
| 194 | 194 |
| 195 // Generate GUIDs for each download. The GUID is generated thusly: | 195 // Generate GUIDs for each download. GUIDs based on random data should conform |
| 196 // with RFC 4122 section 4.4. Given the following field layout (based on RFC | |
| 197 // 4122): | |
| 196 // | 198 // |
| 197 // XXXXXXXX-RRRR-RRRR-RRRR-RRRRRRRRRRRR | 199 // 0 1 2 3 |
| 200 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | |
| 201 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
| 202 // | time_low | | |
| 203 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
| 204 // | time_mid | time_hi_and_version | | |
| 205 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
| 206 // |clk_seq_hi_res | clk_seq_low | node (0-1) | | |
| 207 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
| 208 // | node (2-5) | | |
| 209 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
| 210 // | |
| 211 // * Bits 4-7 of time_hi_and_version should be set to 0b0100 == 4 | |
| 212 // * Bits 6-7 of clk_seq_hi_res should be set to 0b10 | |
| 213 // * All other bits should be random or pseudorandom. | |
| 214 // | |
| 215 // We are going to take the liberty of setting time_low to the 32-bit download | |
| 216 // ID. That will guarantee that no two randomly generated GUIDs will collide | |
| 217 // even if the 90 bits of entropy doesn't save us. | |
| 218 // | |
| 219 // Translated to the canonical string representation, the GUID is generated | |
| 220 // thusly: | |
| 221 // | |
| 222 // XXXXXXXX-RRRR-4RRR-yRRR-RRRRRRRRRRRR | |
|
sky
2016/04/08 21:59:32
The old code may not have generated the 4 and y, r
asanka
2016/04/11 17:32:59
None at all. I'd have added migration code if it d
| |
| 198 // \__ __/ \___________ ____________/ | 223 // \__ __/ \___________ ____________/ |
| 199 // \/ \/ | 224 // \/ \/ |
| 200 // | Random hex digits | 225 // | R = random hex digit. |
| 226 // | y = one of {'8','9','A','B'} selected randomly. | |
| 227 // | 4 = the character '4'. | |
| 201 // | | 228 // | |
| 202 // Hex representation of 32-bit download ID. | 229 // Hex representation of 32-bit download ID. |
| 203 // | 230 // |
| 204 // The 96 random bits provide entropy while the 32-bits from the download ID | |
| 205 // ensure that the generated identifiers will at least be unique amongst the | |
| 206 // download rows in the unlikely event there's a collision in the 96 entropy | |
| 207 // bits. | |
| 208 // | |
| 209 // This GUID generation scheme is only used for migrated download rows and | 231 // This GUID generation scheme is only used for migrated download rows and |
| 210 // assumes that the likelihood of a collision with a GUID generated via | 232 // assumes that the likelihood of a collision with a GUID generated via |
| 211 // base::GenerateGUID() will be vanishingly small. | 233 // base::GenerateGUID() will be vanishingly small. |
| 212 const char kMigrateGuidsQuery[] = | 234 const char kMigrateGuidsQuery[] = |
| 213 "UPDATE downloads SET guid = printf" | 235 "UPDATE downloads SET guid = printf" |
| 214 "(\"%08X-%s-%s-%s-%s\", id, hex(randomblob(2)), hex(randomblob(2))," | 236 "(\"%08X-%s-4%s-%01X%s-%s\"," |
| 215 " hex(randomblob(2)), hex(randomblob(6)))"; | 237 " id," |
| 238 " hex(randomblob(2))," | |
| 239 " substr(hex(randomblob(2)),2)," | |
| 240 " (8 | (random() & 3))," | |
| 241 " substr(hex(randomblob(2)),2)," | |
| 242 " hex(randomblob(6)))"; | |
| 216 return GetDB().Execute(kMigrateGuidsQuery); | 243 return GetDB().Execute(kMigrateGuidsQuery); |
| 217 } | 244 } |
| 218 | 245 |
| 219 bool DownloadDatabase::InitDownloadTable() { | 246 bool DownloadDatabase::InitDownloadTable() { |
| 220 const char kSchema[] = | 247 const char kSchema[] = |
| 221 "CREATE TABLE downloads (" | 248 "CREATE TABLE downloads (" |
| 222 "id INTEGER PRIMARY KEY," // Primary key. | 249 "id INTEGER PRIMARY KEY," // Primary key. |
| 223 "guid VARCHAR NOT NULL," // GUID. | 250 "guid VARCHAR NOT NULL," // GUID. |
| 224 "current_path LONGVARCHAR NOT NULL," // Current disk location | 251 "current_path LONGVARCHAR NOT NULL," // Current disk location |
| 225 "target_path LONGVARCHAR NOT NULL," // Final disk location | 252 "target_path LONGVARCHAR NOT NULL," // Final disk location |
| (...skipping 388 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 614 size_t DownloadDatabase::CountDownloads() { | 641 size_t DownloadDatabase::CountDownloads() { |
| 615 EnsureInProgressEntriesCleanedUp(); | 642 EnsureInProgressEntriesCleanedUp(); |
| 616 | 643 |
| 617 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, | 644 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, |
| 618 "SELECT count(*) from downloads")); | 645 "SELECT count(*) from downloads")); |
| 619 statement.Step(); | 646 statement.Step(); |
| 620 return statement.ColumnInt(0); | 647 return statement.ColumnInt(0); |
| 621 } | 648 } |
| 622 | 649 |
| 623 } // namespace history | 650 } // namespace history |
| OLD | NEW |