Movatterモバイル変換


[0]ホーム

URL:


Google Git
Sign in
chromium /chromium /src /refs/heads/main /. /sql /sqlite_result_code.cc
blob: 242f06d861a1041de1a99c0426c6aad911ecfb9f [file] [log] [blame]
Avi Drissman69b874f2022-09-15 19:11:14[diff] [blame]1// Copyright 2022 The Chromium Authors
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include"sql/sqlite_result_code.h"
6
Peter Kasting3f01b692025-01-27 19:50:47[diff] [blame]7#include<algorithm>
Takuto Ikuta2eb61342024-05-10 09:05:35[diff] [blame]8#include<cstddef>
Peter Boström6baf5232024-06-05 23:40:05[diff] [blame]9#include<ostream>// Needed to compile CHECK() with operator <<.
Daniel Chenga565e82b2024-07-04 14:09:17[diff] [blame]10#include<ranges>
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]11#include<set>
Will Harrisb60653cc2023-06-13 22:32:23[diff] [blame]12#include<string>
Md Hasibul Hasan52ffeca62024-03-26 18:23:18[diff] [blame]13#include<string_view>
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]14
Peter Boström6baf5232024-06-05 23:40:05[diff] [blame]15#include"base/check.h"
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]16#include"base/check_op.h"
Takuto Ikuta2eb61342024-05-10 09:05:35[diff] [blame]17#include"base/dcheck_is_on.h"
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]18#include"base/logging.h"
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]19#include"base/metrics/histogram_functions.h"
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]20#include"sql/sqlite_result_code_values.h"
21#include"third_party/sqlite/sqlite3.h"
22
23namespace sql{
24
25namespace{
26
27// The highly packed representation minimizes binary size and memory usage.
28structSqliteResultCodeMappingEntry{
29unsigned result_code:16;
30unsigned logged_code:8;
31
32// The remaining bits will be used to encode the result values of helpers that
33// indicate corruption handling.
34};
35
36constexprSqliteResultCodeMappingEntry kResultCodeMapping[]={
37// Entries are ordered by SQLite result code value. This should match the
38// ordering in https://www.sqlite.org/rescode.html.
39
40{SQLITE_OK,static_cast<int>(SqliteLoggedResultCode::kNoError)},
41{SQLITE_ERROR,static_cast<int>(SqliteLoggedResultCode::kGeneric)},
42{SQLITE_INTERNAL,static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
43{SQLITE_PERM,static_cast<int>(SqliteLoggedResultCode::kPermission)},
44{SQLITE_ABORT,static_cast<int>(SqliteLoggedResultCode::kAbort)},
45{SQLITE_BUSY,static_cast<int>(SqliteLoggedResultCode::kBusy)},
46
47// Chrome features shouldn't execute conflicting statements concurrently.
48{SQLITE_LOCKED,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
49
50// Chrome should crash on OOM.
51{SQLITE_NOMEM,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
52
53{SQLITE_READONLY,static_cast<int>(SqliteLoggedResultCode::kReadOnly)},
54
55// Chrome doesn't use sqlite3_interrupt().
56{SQLITE_INTERRUPT,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
57
58{SQLITE_IOERR,static_cast<int>(SqliteLoggedResultCode::kIo)},
59{SQLITE_CORRUPT,static_cast<int>(SqliteLoggedResultCode::kCorrupt)},
60
61// Chrome only passes a few known-good opcodes to sqlite3_file_control().
62{SQLITE_NOTFOUND,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
63
64{SQLITE_FULL,static_cast<int>(SqliteLoggedResultCode::kFullDisk)},
65{SQLITE_CANTOPEN,static_cast<int>(SqliteLoggedResultCode::kCantOpen)},
66{SQLITE_PROTOCOL,
67static_cast<int>(SqliteLoggedResultCode::kLockingProtocol)},
68{SQLITE_EMPTY,static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
69{SQLITE_SCHEMA,static_cast<int>(SqliteLoggedResultCode::kSchemaChanged)},
70{SQLITE_TOOBIG,static_cast<int>(SqliteLoggedResultCode::kTooBig)},
71{SQLITE_CONSTRAINT,static_cast<int>(SqliteLoggedResultCode::kConstraint)},
72{SQLITE_MISMATCH,static_cast<int>(SqliteLoggedResultCode::kTypeMismatch)},
73
74// Chrome should not misuse SQLite's API.
75{SQLITE_MISUSE,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
76
77{SQLITE_NOLFS,
78static_cast<int>(SqliteLoggedResultCode::kNoLargeFileSupport)},
79
80// Chrome does not set an authorizer callback.
81{SQLITE_AUTH,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
82
83{SQLITE_FORMAT,static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
84
85// Chrome should not use invalid column indexes in sqlite3_{bind,column}*().
86{SQLITE_RANGE,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
87
88{SQLITE_NOTADB,static_cast<int>(SqliteLoggedResultCode::kNotADatabase)},
89{SQLITE_NOTICE,static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
90{SQLITE_WARNING,static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
91{SQLITE_ROW,static_cast<int>(SqliteLoggedResultCode::kNoError)},
92{SQLITE_DONE,static_cast<int>(SqliteLoggedResultCode::kNoError)},
93{SQLITE_OK_LOAD_PERMANENTLY,
94static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
95
96// Chrome should not use collating sequence names in SQL statements.
97{SQLITE_ERROR_MISSING_COLLSEQ,
98static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
99
100{SQLITE_BUSY_RECOVERY,
101static_cast<int>(SqliteLoggedResultCode::kBusyRecovery)},
102
103// Chrome does not use a shared page cache.
104{SQLITE_LOCKED_SHAREDCACHE,
105static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
106
107{SQLITE_READONLY_RECOVERY,
108static_cast<int>(SqliteLoggedResultCode::kReadOnlyRecovery)},
109{SQLITE_IOERR_READ,static_cast<int>(SqliteLoggedResultCode::kIoRead)},
110
111// Chrome does not use a virtual table that signals corruption. We only use
112// a
113// virtual table code for recovery. That code does not use this error.
114{SQLITE_CORRUPT_VTAB,
115static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
116
117{SQLITE_CANTOPEN_NOTEMPDIR,
118static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
119{SQLITE_CONSTRAINT_CHECK,
120static_cast<int>(SqliteLoggedResultCode::kConstraintCheck)},
121
122// Chrome does not set an authorizer callback.
123{SQLITE_AUTH_USER,static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
124
125{SQLITE_NOTICE_RECOVER_WAL,
126static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
127{SQLITE_WARNING_AUTOINDEX,
128static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
129{SQLITE_ERROR_RETRY,
130static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
131{SQLITE_ABORT_ROLLBACK,
132static_cast<int>(SqliteLoggedResultCode::kAbortRollback)},
133{SQLITE_BUSY_SNAPSHOT,
134static_cast<int>(SqliteLoggedResultCode::kBusySnapshot)},
135
136// Chrome does not use a virtual table that signals conflicts. We only use a
137// virtual table code for recovery. That code does not use this error.
138{SQLITE_LOCKED_VTAB,
139static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
140
141{SQLITE_READONLY_CANTLOCK,
142static_cast<int>(SqliteLoggedResultCode::kReadOnlyCantLock)},
143{SQLITE_IOERR_SHORT_READ,
144static_cast<int>(SqliteLoggedResultCode::kIoShortRead)},
145{SQLITE_CORRUPT_SEQUENCE,
146static_cast<int>(SqliteLoggedResultCode::kCorruptSequence)},
147{SQLITE_CANTOPEN_ISDIR,
148static_cast<int>(SqliteLoggedResultCode::kCantOpenIsDir)},
149
150// Chrome does not use commit hook callbacks.
151{SQLITE_CONSTRAINT_COMMITHOOK,
152static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
153
154{SQLITE_NOTICE_RECOVER_ROLLBACK,
155static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
156
157// Chrome does not use sqlite3_snapshot_open().
158{SQLITE_ERROR_SNAPSHOT,
159static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
160#ifdef SQLITE_ENABLE_SNAPSHOT
161#error"This code assumes that Chrome does not use sqlite3_snapshot_open()"
162#endif
163
164// Chrome does not use blocking Posix advisory file lock requests.
165{SQLITE_BUSY_TIMEOUT,
166static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
167#ifdef SQLITE_ENABLE_SETLK_TIMEOUT
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]168#error \
169"This code assumes thatChrome does not use blockingPosix advisory \
Ivan Murashov3c7a0d52022-10-27 21:21:47[diff] [blame]170file lock requests"
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]171#endif
172
173{SQLITE_READONLY_ROLLBACK,
174static_cast<int>(SqliteLoggedResultCode::kReadOnlyRollback)},
175{SQLITE_IOERR_WRITE,static_cast<int>(SqliteLoggedResultCode::kIoWrite)},
176{SQLITE_CORRUPT_INDEX,
177static_cast<int>(SqliteLoggedResultCode::kCorruptIndex)},
178
179// Chrome should always pass full paths to SQLite.
180{SQLITE_CANTOPEN_FULLPATH,
181static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
182
183{SQLITE_CONSTRAINT_FOREIGNKEY,
184static_cast<int>(SqliteLoggedResultCode::kConstraintForeignKey)},
185{SQLITE_READONLY_DBMOVED,
186static_cast<int>(SqliteLoggedResultCode::kReadOnlyDbMoved)},
187{SQLITE_IOERR_FSYNC,static_cast<int>(SqliteLoggedResultCode::kIoFsync)},
188
189// Chrome does not support Cygwin and does not use its VFS.
190{SQLITE_CANTOPEN_CONVPATH,
191static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
192
193// Chrome does not use extension functions.
194{SQLITE_CONSTRAINT_FUNCTION,
195static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
196
197{SQLITE_READONLY_CANTINIT,
198static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
199{SQLITE_IOERR_DIR_FSYNC,
200static_cast<int>(SqliteLoggedResultCode::kIoDirFsync)},
201{SQLITE_CANTOPEN_DIRTYWAL,
202static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
203{SQLITE_CONSTRAINT_NOTNULL,
204static_cast<int>(SqliteLoggedResultCode::kConstraintNotNull)},
205{SQLITE_READONLY_DIRECTORY,
206static_cast<int>(SqliteLoggedResultCode::kReadOnlyDirectory)},
207{SQLITE_IOERR_TRUNCATE,
208static_cast<int>(SqliteLoggedResultCode::kIoTruncate)},
209
210// Chrome does not use the SQLITE_OPEN_NOFOLLOW flag.
211{SQLITE_CANTOPEN_SYMLINK,
212static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
213
214{SQLITE_CONSTRAINT_PRIMARYKEY,
215static_cast<int>(SqliteLoggedResultCode::kConstraintPrimaryKey)},
216{SQLITE_IOERR_FSTAT,static_cast<int>(SqliteLoggedResultCode::kIoFstat)},
217
218// Chrome unconditionally disables database triggers via
219// sqlite3_db_config(SQLITE_DBCONFIG_ENABLE_TRIGGER).
220{SQLITE_CONSTRAINT_TRIGGER,
221static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
222
223{SQLITE_IOERR_UNLOCK,static_cast<int>(SqliteLoggedResultCode::kIoUnlock)},
224{SQLITE_CONSTRAINT_UNIQUE,
225static_cast<int>(SqliteLoggedResultCode::kConstraintUnique)},
226{SQLITE_IOERR_RDLOCK,
227static_cast<int>(SqliteLoggedResultCode::kIoReadLock)},
228
229// Chrome does not use a virtual table that signals constraints. We only use
230// a virtual table code for recovery. That code does not use this error.
231{SQLITE_CONSTRAINT_VTAB,
232static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
233
234{SQLITE_IOERR_DELETE,static_cast<int>(SqliteLoggedResultCode::kIoDelete)},
235{SQLITE_CONSTRAINT_ROWID,
236static_cast<int>(SqliteLoggedResultCode::kConstraintRowId)},
237{SQLITE_IOERR_BLOCKED,
238static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
239
240// Chrome unconditionally disables database triggers via
241// sqlite3_db_config(SQLITE_DBCONFIG_ENABLE_TRIGGER).
242{SQLITE_CONSTRAINT_PINNED,
243static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
244
245// The SQLite docus claim that this error code is "normally" converted to
246// SQLITE_NOMEM. This doesn't seem 100% categorical, so we're flagging this
247// as "unused in Chrome" per the same rationale as SQLITE_NOMEM.
248{SQLITE_IOERR_NOMEM,
249static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
250
251{SQLITE_CONSTRAINT_DATATYPE,
252static_cast<int>(SqliteLoggedResultCode::kConstraintDataType)},
253{SQLITE_IOERR_ACCESS,static_cast<int>(SqliteLoggedResultCode::kIoAccess)},
254{SQLITE_IOERR_CHECKRESERVEDLOCK,
255static_cast<int>(SqliteLoggedResultCode::kIoCheckReservedLock)},
256{SQLITE_IOERR_LOCK,static_cast<int>(SqliteLoggedResultCode::kIoLock)},
257{SQLITE_IOERR_CLOSE,static_cast<int>(SqliteLoggedResultCode::kIoClose)},
258{SQLITE_IOERR_DIR_CLOSE,
259static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
260
261// Chrome will only allow enabling WAL on databases with exclusive locking.
262{SQLITE_IOERR_SHMOPEN,
263static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
264
265// Chrome will only allow enabling WAL on databases with exclusive locking.
266{SQLITE_IOERR_SHMSIZE,
267static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
268
269{SQLITE_IOERR_SHMLOCK,
270static_cast<int>(SqliteLoggedResultCode::kUnusedSqlite)},
271
272// Chrome will only allow enabling WAL on databases with exclusive locking.
273{SQLITE_IOERR_SHMMAP,
274static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
275
276{SQLITE_IOERR_SEEK,static_cast<int>(SqliteLoggedResultCode::kIoSeek)},
277{SQLITE_IOERR_DELETE_NOENT,
278static_cast<int>(SqliteLoggedResultCode::kIoDeleteNoEntry)},
279{SQLITE_IOERR_MMAP,
280static_cast<int>(SqliteLoggedResultCode::kIoMemoryMapping)},
281{SQLITE_IOERR_GETTEMPPATH,
282static_cast<int>(SqliteLoggedResultCode::kIoGetTemporaryPath)},
283
284// Chrome does not support Cygwin and does not use its VFS.
285{SQLITE_IOERR_CONVPATH,
286static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
287
288// Chrome does not use SQLite extensions.
289{SQLITE_IOERR_VNODE,
290static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
291
292// Chrome does not use SQLite extensions.
293{SQLITE_IOERR_AUTH,
294static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
295
296{SQLITE_IOERR_BEGIN_ATOMIC,
297static_cast<int>(SqliteLoggedResultCode::kIoBeginAtomic)},
298{SQLITE_IOERR_COMMIT_ATOMIC,
299static_cast<int>(SqliteLoggedResultCode::kIoCommitAtomic)},
300{SQLITE_IOERR_ROLLBACK_ATOMIC,
301static_cast<int>(SqliteLoggedResultCode::kIoRollbackAtomic)},
302
303// Chrome does not use the checksum VFS shim.
304{SQLITE_IOERR_DATA,
305static_cast<int>(SqliteLoggedResultCode::kUnusedChrome)},
306
307{SQLITE_IOERR_CORRUPTFS,
308static_cast<int>(SqliteLoggedResultCode::kIoCorruptFileSystem)},
309};
310
Peter Boström7bf135552025-03-11 10:15:00[diff] [blame]311// Number of #defines in https://www.sqlite.org/c3ref/c_abort.html
312//
313// This number is also stated at
314// https://www.sqlite.org/rescode.html#primary_result_code_list
315staticconstexprint kPrimaryResultCodes=31;
316
317// Number of #defines in https://www.sqlite.org/c3ref/c_abort_rollback.html
318//
319// This number is also stated at
320// https://www.sqlite.org/rescode.html#extended_result_code_list
321staticconstexprint kExtendedResultCodes=74;
322
323static_assert(std::size(kResultCodeMapping)==
324size_t{kPrimaryResultCodes+ kExtendedResultCodes},
325"Mapping table has incorrect number of entries");
326
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]327// Looks up a `sqlite_result_code` in the mapping tables.
328//
329// Returns an entry in kResultCodeMapping or kUnknownResultCodeMappingEntry.
Peter Boström6baf5232024-06-05 23:40:05[diff] [blame]330// CHECKs if the `sqlite_result_code` is not in the mapping table.
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]331SqliteResultCodeMappingEntryFindResultCode(int sqlite_result_code){
Peter Kasting3f01b692025-01-27 19:50:47[diff] [blame]332constauto* mapping_it= std::ranges::find_if(
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]333 kResultCodeMapping,
334[&sqlite_result_code](SqliteResultCodeMappingEntry rhs){
335return sqlite_result_code== rhs.result_code;
336});
337
Daniel Chenga565e82b2024-07-04 14:09:17[diff] [blame]338 CHECK(mapping_it!= std::ranges::end(kResultCodeMapping))
Peter Boström6baf5232024-06-05 23:40:05[diff] [blame]339<<"Unsupported SQLite result code: "<< sqlite_result_code;
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]340return*mapping_it;
341}
342
343}// namespace
344
345#if DCHECK_IS_ON()
346
347SqliteResultCodeToSqliteResultCode(int sqlite_result_code){
348SqliteLoggedResultCode logged_code=static_cast<SqliteLoggedResultCode>(
349FindResultCode(sqlite_result_code).logged_code);
350
351 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedSqlite)
352<<"SQLite reported code marked for internal use: "<< sqlite_result_code;
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]353 DVLOG_IF(1, logged_code==SqliteLoggedResultCode::kUnusedChrome)
354<<"SQLite reported code that should never show up in Chrome unless a "
355"sql database has been corrupted: "
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]356<< sqlite_result_code;
357
358returnstatic_cast<SqliteResultCode>(sqlite_result_code);
359}
360
361SqliteErrorCodeToSqliteErrorCode(SqliteResultCode sqlite_error_code){
362SqliteLoggedResultCode logged_code=static_cast<SqliteLoggedResultCode>(
363FindResultCode(static_cast<int>(sqlite_error_code)).logged_code);
364
365 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedSqlite)
366<<"SQLite reported code marked for internal use: "<< sqlite_error_code;
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]367 DVLOG_IF(1, logged_code==SqliteLoggedResultCode::kUnusedChrome)
368<<"SQLite reported code that should never show up in Chrome unless a "
369"sql database has been corrupted: "
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]370<< sqlite_error_code;
371 DCHECK_NE(logged_code,SqliteLoggedResultCode::kNoError)
372<< __func__
373<<" called with non-error result code: "<< sqlite_error_code;
374
375returnstatic_cast<SqliteErrorCode>(sqlite_error_code);
376}
377
378#endif// DCHECK_IS_ON()
379
Victor Costanf176d242022-03-22 05:31:22[diff] [blame]380boolIsSqliteSuccessCode(SqliteResultCode sqlite_result_code){
381// https://www.sqlite.org/rescode.html lists the result codes that are not
382// errors.
383bool is_success=(sqlite_result_code==SqliteResultCode::kOk)||
384(sqlite_result_code==SqliteResultCode::kRow)||
385(sqlite_result_code==SqliteResultCode::kDone);
386
387#if DCHECK_IS_ON()
388SqliteLoggedResultCode logged_code=static_cast<SqliteLoggedResultCode>(
389FindResultCode(static_cast<int>(sqlite_result_code)).logged_code);
390
391 DCHECK_EQ(is_success, logged_code==SqliteLoggedResultCode::kNoError)
392<< __func__<<" logic disagrees with the code mapping for "
393<< sqlite_result_code;
394
395 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedSqlite)
396<<"SQLite reported code marked for internal use: "<< sqlite_result_code;
397 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedChrome)
398<<"SQLite reported code that should never show up in Chrome: "
399<< sqlite_result_code;
400#endif// DCHECK_IS_ON()
401
402return is_success;
403}
404
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]405SqliteLoggedResultCodeToSqliteLoggedResultCode(int sqlite_result_code){
406SqliteLoggedResultCode logged_code=static_cast<SqliteLoggedResultCode>(
407FindResultCode(sqlite_result_code).logged_code);
408
409 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedSqlite)
410<<"SQLite reported code marked for internal use: "<< sqlite_result_code;
411 DCHECK_NE(logged_code,SqliteLoggedResultCode::kUnusedChrome)
412<<"SQLite reported code that should never show up in Chrome: "
413<< sqlite_result_code;
414return logged_code;
415}
416
Will Harrisb60653cc2023-06-13 22:32:23[diff] [blame]417voidUmaHistogramSqliteResult(const std::string& histogram_name,
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]418int sqlite_result_code){
419auto logged_code=ToSqliteLoggedResultCode(sqlite_result_code);
420 base::UmaHistogramEnumeration(histogram_name, logged_code);
421}
422
423std::ostream&operator<<(std::ostream& os,
424SqliteResultCode sqlite_result_code){
425return os<<static_cast<int>(sqlite_result_code);
426}
427
428std::ostream&operator<<(std::ostream& os,SqliteErrorCode sqlite_error_code){
429return os<<static_cast<SqliteResultCode>(sqlite_error_code);
430}
431
432voidCheckSqliteLoggedResultCodeForTesting(){
433// Ensure that error codes are alphabetical.
Peter Kasting3f01b692025-01-27 19:50:47[diff] [blame]434constauto* unordered_it= std::ranges::adjacent_find(
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]435 kResultCodeMapping,
436[](SqliteResultCodeMappingEntry lhs,SqliteResultCodeMappingEntry rhs){
437return lhs.result_code>= rhs.result_code;
438});
Daniel Chenga565e82b2024-07-04 14:09:17[diff] [blame]439 DCHECK_EQ(unordered_it, std::ranges::end(kResultCodeMapping))
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]440<<"Mapping ordering broken at {"<< unordered_it->result_code<<", "
441<<static_cast<int>(unordered_it->logged_code)<<"}";
442
443 std::set<int> sqlite_result_codes;
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]444for(auto& mapping_entry: kResultCodeMapping){
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]445 sqlite_result_codes.insert(mapping_entry.result_code);
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]446}
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]447
448// SQLite doesn't have special messages for extended errors.
449// At the time of this writing, sqlite3_errstr() has a string table for
450// primary result codes, and uses it for extended error codes as well.
451//
452// So, we can only use sqlite3_errstr() to check for holes in the primary
453// message table.
454for(int result_code=0; result_code<=256;++result_code){
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]455if(sqlite_result_codes.count(result_code)!=0){
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]456continue;
Nathan Memmott4aff5042024-06-12 19:27:51[diff] [blame]457}
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]458
459constchar* error_message= sqlite3_errstr(result_code);
460
Md Hasibul Hasan52ffeca62024-03-26 18:23:18[diff] [blame]461staticconstexpr std::string_view kUnknownErrorMessage("unknown error");
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]462 DCHECK_EQ(kUnknownErrorMessage.compare(error_message),0)
463<<"Unmapped SQLite result code: "<< result_code
464<<" SQLite message: "<< error_message;
465}
Victor Costanab7a2452022-03-21 23:06:08[diff] [blame]466}
467
468}// namespace sql

[8]ページ先頭

©2009-2025 Movatter.jp