sdb.c (81575B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 /* 5 * This file implements PKCS 11 on top of our existing security modules 6 * 7 * For more information about PKCS 11 See PKCS 11 Token Inteface Standard. 8 * This implementation has two slots: 9 * slot 1 is our generic crypto support. It does not require login. 10 * It supports Public Key ops, and all they bulk ciphers and hashes. 11 * It can also support Private Key ops for imported Private keys. It does 12 * not have any token storage. 13 * slot 2 is our private key support. It requires a login before use. It 14 * can store Private Keys and Certs as token objects. Currently only private 15 * keys and their associated Certificates are saved on the token. 16 * 17 * In this implementation, session objects are only visible to the session 18 * that created or generated them. 19 */ 20 21 #include "sdb.h" 22 #include "pkcs11t.h" 23 #include "seccomon.h" 24 #include <sqlite3.h> 25 #include "prthread.h" 26 #include "prio.h" 27 #include <stdio.h> 28 #include "secport.h" 29 #include "prmon.h" 30 #include "prenv.h" 31 #include "prprf.h" 32 #include "prsystem.h" /* for PR_GetDirectorySeparator() */ 33 #include <sys/stat.h> 34 #if defined(_WIN32) 35 #include <io.h> 36 #include <windows.h> 37 #elif defined(XP_UNIX) 38 #include <unistd.h> 39 #endif 40 #if defined(LINUX) && !defined(ANDROID) 41 #include <linux/magic.h> 42 #include <sys/vfs.h> 43 #endif 44 #include "utilpars.h" 45 46 #ifdef SQLITE_UNSAFE_THREADS 47 #include "prlock.h" 48 /* 49 * SQLite can be compiled to be thread safe or not. 50 * turn on SQLITE_UNSAFE_THREADS if the OS does not support 51 * a thread safe version of sqlite. 52 */ 53 static PRLock *sqlite_lock = NULL; 54 55 #define LOCK_SQLITE() PR_Lock(sqlite_lock); 56 #define UNLOCK_SQLITE() PR_Unlock(sqlite_lock); 57 #else 58 #define LOCK_SQLITE() 59 #define UNLOCK_SQLITE() 60 #endif 61 62 typedef enum { 63 SDB_CERT = 1, 64 SDB_KEY = 2 65 } sdbDataType; 66 67 /* 68 * defines controlling how long we wait to acquire locks. 69 * 70 * SDB_SQLITE_BUSY_TIMEOUT specifies how long (in milliseconds) 71 * sqlite will wait on lock. If that timeout expires, sqlite will 72 * return SQLITE_BUSY. 73 * SDB_BUSY_RETRY_TIME specifies how many seconds the sdb_ code waits 74 * after receiving a busy before retrying. 75 * SDB_MAX_BUSY_RETRIES specifies how many times the sdb_ will retry on 76 * a busy condition. 77 * 78 * SDB_SQLITE_BUSY_TIMEOUT affects all opertions, both manual 79 * (prepare/step/reset/finalize) and automatic (sqlite3_exec()). 80 * SDB_BUSY_RETRY_TIME and SDB_MAX_BUSY_RETRIES only affect manual operations 81 * 82 * total wait time for automatic operations: 83 * 1 second (SDB_SQLITE_BUSY_TIMEOUT/1000). 84 * total wait time for manual operations: 85 * (1 second + SDB_BUSY_RETRY_TIME) * 30 = 30 seconds. 86 * (SDB_SQLITE_BUSY_TIMEOUT/1000 + SDB_BUSY_RETRY_TIME)*SDB_MAX_BUSY_RETRIES 87 */ 88 #define SDB_SQLITE_BUSY_TIMEOUT 1000 /* milliseconds */ 89 #define SDB_BUSY_RETRY_TIME 5 /* 'ticks', varies by platforms */ 90 #define SDB_MAX_BUSY_RETRIES 30 91 92 /* 93 * known attributes 94 */ 95 // clang-format off 96 const CK_ATTRIBUTE_TYPE sftkdb_known_attributes[] = { 97 CKA_CLASS, CKA_TOKEN, CKA_PRIVATE, CKA_LABEL, CKA_UNIQUE_ID, 98 CKA_APPLICATION, CKA_VALUE, CKA_OBJECT_ID, CKA_CERTIFICATE_TYPE, CKA_ISSUER, 99 CKA_SERIAL_NUMBER, CKA_AC_ISSUER, CKA_OWNER, CKA_ATTR_TYPES, CKA_TRUSTED, 100 CKA_CERTIFICATE_CATEGORY, CKA_JAVA_MIDP_SECURITY_DOMAIN, CKA_URL, 101 CKA_HASH_OF_SUBJECT_PUBLIC_KEY, CKA_HASH_OF_ISSUER_PUBLIC_KEY, 102 CKA_NAME_HASH_ALGORITHM, CKA_CHECK_VALUE, CKA_KEY_TYPE, CKA_SUBJECT, 103 CKA_ID, CKA_SENSITIVE, CKA_ENCRYPT, CKA_DECRYPT, CKA_WRAP, CKA_UNWRAP, 104 CKA_SIGN, CKA_SIGN_RECOVER, CKA_VERIFY, CKA_VERIFY_RECOVER, CKA_DERIVE, 105 CKA_START_DATE, CKA_END_DATE, CKA_MODULUS, CKA_MODULUS_BITS, 106 CKA_PUBLIC_EXPONENT, CKA_PRIVATE_EXPONENT, CKA_PRIME_1, CKA_PRIME_2, 107 CKA_EXPONENT_1, CKA_EXPONENT_2, CKA_COEFFICIENT, CKA_PUBLIC_KEY_INFO, 108 CKA_PRIME, CKA_SUBPRIME, CKA_BASE, CKA_PRIME_BITS, CKA_SUB_PRIME_BITS, 109 CKA_VALUE_BITS, CKA_VALUE_LEN, CKA_EXTRACTABLE, CKA_LOCAL, 110 CKA_NEVER_EXTRACTABLE, CKA_ALWAYS_SENSITIVE, CKA_KEY_GEN_MECHANISM, 111 CKA_MODIFIABLE, CKA_COPYABLE, CKA_DESTROYABLE, CKA_EC_PARAMS, CKA_EC_POINT, 112 CKA_SECONDARY_AUTH, CKA_AUTH_PIN_FLAGS, CKA_ALWAYS_AUTHENTICATE, 113 CKA_WRAP_WITH_TRUSTED, CKA_WRAP_TEMPLATE, CKA_UNWRAP_TEMPLATE, 114 CKA_DERIVE_TEMPLATE, CKA_OTP_FORMAT, CKA_OTP_LENGTH, CKA_OTP_TIME_INTERVAL, 115 CKA_OTP_USER_FRIENDLY_MODE, CKA_OTP_CHALLENGE_REQUIREMENT, 116 CKA_OTP_TIME_REQUIREMENT, CKA_OTP_COUNTER_REQUIREMENT, 117 CKA_OTP_PIN_REQUIREMENT, CKA_OTP_COUNTER, CKA_OTP_TIME, 118 CKA_OTP_USER_IDENTIFIER, CKA_OTP_SERVICE_IDENTIFIER, CKA_OTP_SERVICE_LOGO, 119 CKA_OTP_SERVICE_LOGO_TYPE, CKA_GOSTR3410_PARAMS, CKA_GOSTR3411_PARAMS, 120 CKA_GOST28147_PARAMS, CKA_HW_FEATURE_TYPE, CKA_RESET_ON_INIT, 121 CKA_HAS_RESET, CKA_PIXEL_X, CKA_PIXEL_Y, CKA_RESOLUTION, CKA_CHAR_ROWS, 122 CKA_CHAR_COLUMNS, CKA_COLOR, CKA_BITS_PER_PIXEL, CKA_CHAR_SETS, 123 CKA_ENCODING_METHODS, CKA_MIME_TYPES, CKA_MECHANISM_TYPE, 124 CKA_REQUIRED_CMS_ATTRIBUTES, CKA_DEFAULT_CMS_ATTRIBUTES, 125 CKA_SUPPORTED_CMS_ATTRIBUTES, CKA_PROFILE_ID, CKA_X2RATCHET_BAG, 126 CKA_X2RATCHET_BAGSIZE, CKA_X2RATCHET_BOBS1STMSG, CKA_X2RATCHET_CKR, 127 CKA_X2RATCHET_CKS, CKA_X2RATCHET_DHP, CKA_X2RATCHET_DHR, 128 CKA_X2RATCHET_DHS, CKA_X2RATCHET_HKR, CKA_X2RATCHET_HKS, 129 CKA_X2RATCHET_ISALICE, CKA_X2RATCHET_NHKR, CKA_X2RATCHET_NHKS, 130 CKA_X2RATCHET_NR, CKA_X2RATCHET_NS, CKA_X2RATCHET_PNS, CKA_X2RATCHET_RK, 131 CKA_HSS_LEVELS, CKA_HSS_LMS_TYPE, CKA_HSS_LMOTS_TYPE, CKA_HSS_LMS_TYPES, 132 CKA_HSS_LMOTS_TYPES, CKA_HSS_KEYS_REMAINING, CKA_PARAMETER_SET, 133 CKA_OBJECT_VALIDATION_FLAGS, CKA_VALIDATION_TYPE, CKA_VALIDATION_VERSION, 134 CKA_VALIDATION_LEVEL, CKA_VALIDATION_MODULE_ID, CKA_VALIDATION_FLAG, 135 CKA_VALIDATION_AUTHORITY_TYPE, CKA_VALIDATION_COUNTRY, 136 CKA_VALIDATION_CERTIFICATE_IDENTIFIER, CKA_VALIDATION_CERTIFICATE_URI, 137 CKA_VALIDATION_PROFILE, CKA_VALIDATION_VENDOR_URI, CKA_ENCAPSULATE_TEMPLATE, 138 CKA_DECAPSULATE_TEMPLATE, CKA_PKCS_TRUST_SERVER_AUTH, 139 CKA_PKCS_TRUST_CLIENT_AUTH, CKA_PKCS_TRUST_CODE_SIGNING, 140 CKA_PKCS_TRUST_EMAIL_PROTECTION, CKA_TRUST_IPSEC_IKE, 141 CKA_PKCS_TRUST_TIME_STAMPING, CKA_PKCS_TRUST_OCSP_SIGNING, CKA_ENCAPSULATE, 142 CKA_DECAPSULATE, CKA_HASH_OF_CERTIFICATE, CKA_PUBLIC_CRC64_VALUE, CKA_SEED, 143 CKA_NSS_TRUST, CKA_NSS_URL, CKA_NSS_EMAIL, CKA_NSS_SMIME_INFO, 144 CKA_NSS_SMIME_TIMESTAMP, CKA_NSS_PKCS8_SALT, CKA_NSS_PASSWORD_CHECK, 145 CKA_NSS_EXPIRES, CKA_NSS_KRL, CKA_NSS_PQG_COUNTER, CKA_NSS_PQG_SEED, 146 CKA_NSS_PQG_H, CKA_NSS_PQG_SEED_BITS, CKA_NSS_MODULE_SPEC, 147 CKA_NSS_OVERRIDE_EXTENSIONS, CKA_NSS_SERVER_DISTRUST_AFTER, 148 CKA_NSS_EMAIL_DISTRUST_AFTER, CKA_NSS_TRUST_DIGITAL_SIGNATURE, 149 CKA_NSS_TRUST_NON_REPUDIATION, CKA_NSS_TRUST_KEY_ENCIPHERMENT, 150 CKA_NSS_TRUST_DATA_ENCIPHERMENT, CKA_NSS_TRUST_KEY_AGREEMENT, 151 CKA_NSS_TRUST_KEY_CERT_SIGN, CKA_NSS_TRUST_CRL_SIGN, 152 CKA_NSS_TRUST_SERVER_AUTH, CKA_NSS_TRUST_CLIENT_AUTH, 153 CKA_NSS_TRUST_CODE_SIGNING, CKA_NSS_TRUST_EMAIL_PROTECTION, 154 CKA_NSS_TRUST_IPSEC_END_SYSTEM, CKA_NSS_TRUST_IPSEC_TUNNEL, 155 CKA_NSS_TRUST_IPSEC_USER, CKA_NSS_TRUST_TIME_STAMPING, 156 CKA_NSS_TRUST_STEP_UP_APPROVED, CKA_NSS_CERT_SHA1_HASH, 157 CKA_NSS_CERT_MD5_HASH, CKA_NSS_DB, 158 }; 159 // clang-format on 160 161 const size_t sftkdb_known_attributes_size = PR_ARRAY_SIZE(sftkdb_known_attributes); 162 163 /* 164 * Note on use of sqlReadDB: Only one thread at a time may have an actual 165 * operation going on given sqlite3 * database. An operation is defined as 166 * the time from a sqlite3_prepare() until the sqlite3_finalize(). 167 * Multiple sqlite3 * databases can be open and have simultaneous operations 168 * going. We use the sqlXactDB for all write operations. This database 169 * is only opened when we first create a transaction and closed when the 170 * transaction is complete. sqlReadDB is open when we first opened the database 171 * and is used for all read operation. It's use is protected by a monitor. This 172 * is because an operation can span the use of FindObjectsInit() through the 173 * call to FindObjectsFinal(). In the intermediate time it is possible to call 174 * other operations like NSC_GetAttributeValue */ 175 176 struct SDBPrivateStr { 177 char *sqlDBName; /* invariant, path to this database */ 178 sqlite3 *sqlXactDB; /* access protected by dbMon, use protected 179 * by the transaction. Current transaction db*/ 180 PRThread *sqlXactThread; /* protected by dbMon, 181 * current transaction thread */ 182 sqlite3 *sqlReadDB; /* use protected by dbMon, value invariant */ 183 PRIntervalTime lastUpdateTime; /* last time the cache was updated */ 184 PRIntervalTime updateInterval; /* how long the cache can go before it 185 * must be updated again */ 186 sdbDataType type; /* invariant, database type */ 187 char *table; /* invariant, SQL table which contains the db */ 188 char *cacheTable; /* invariant, SQL table cache of db */ 189 PRMonitor *dbMon; /* invariant, monitor to protect 190 * sqlXact* fields, and use of the sqlReadDB */ 191 CK_ATTRIBUTE_TYPE *schemaAttrs; /* Attribute columns that exist in the table. */ 192 unsigned int numSchemaAttrs; 193 }; 194 195 typedef struct SDBPrivateStr SDBPrivate; 196 197 /* Magic for an explicit NULL. NOTE: ideally this should be 198 * out of band data. Since it's not completely out of band, pick 199 * a value that has no meaning to any existing PKCS #11 attributes. 200 * This value is 1) not a valid string (imbedded '\0'). 2) not a U_LONG 201 * or a normal key (too short). 3) not a bool (too long). 4) not an RSA 202 * public exponent (too many bits). 203 */ 204 const unsigned char SQLITE_EXPLICIT_NULL[] = { 0xa5, 0x0, 0x5a }; 205 #define SQLITE_EXPLICIT_NULL_LEN 3 206 207 /* 208 * determine when we've completed our tasks 209 */ 210 static int 211 sdb_done(int err, int *count) 212 { 213 /* allow as many rows as the database wants to give */ 214 if (err == SQLITE_ROW) { 215 *count = 0; 216 return 0; 217 } 218 if (err != SQLITE_BUSY) { 219 return 1; 220 } 221 /* err == SQLITE_BUSY, Dont' retry forever in this case */ 222 if (++(*count) >= SDB_MAX_BUSY_RETRIES) { 223 return 1; 224 } 225 return 0; 226 } 227 228 #if defined(_WIN32) 229 /* 230 * NSPR functions and narrow CRT functions do not handle UTF-8 file paths that 231 * sqlite3 expects. 232 */ 233 234 static int 235 sdb_chmod(const char *filename, int pmode) 236 { 237 int result; 238 239 if (!filename) { 240 return -1; 241 } 242 243 wchar_t *filenameWide = _NSSUTIL_UTF8ToWide(filename); 244 if (!filenameWide) { 245 return -1; 246 } 247 result = _wchmod(filenameWide, pmode); 248 PORT_Free(filenameWide); 249 250 return result; 251 } 252 #else 253 #define sdb_chmod(filename, pmode) chmod((filename), (pmode)) 254 #endif 255 256 /* 257 * find out where sqlite stores the temp tables. We do this by replicating 258 * the logic from sqlite. 259 */ 260 #if defined(_WIN32) 261 static char * 262 sdb_getFallbackTempDir(void) 263 { 264 /* sqlite uses sqlite3_temp_directory if it is not NULL. We don't have 265 * access to sqlite3_temp_directory because it is not exported from 266 * sqlite3.dll. Assume sqlite3_win32_set_directory isn't called and 267 * sqlite3_temp_directory is NULL. 268 */ 269 char path[MAX_PATH]; 270 DWORD rv; 271 size_t len; 272 273 rv = GetTempPathA(MAX_PATH, path); 274 if (rv > MAX_PATH || rv == 0) 275 return NULL; 276 len = strlen(path); 277 if (len == 0) 278 return NULL; 279 /* The returned string ends with a backslash, for example, "C:\TEMP\". */ 280 if (path[len - 1] == '\\') 281 path[len - 1] = '\0'; 282 return PORT_Strdup(path); 283 } 284 #elif defined(XP_UNIX) 285 static char * 286 sdb_getFallbackTempDir(void) 287 { 288 const char *azDirs[] = { 289 NULL, 290 NULL, 291 "/var/tmp", 292 "/usr/tmp", 293 "/tmp", 294 NULL /* List terminator */ 295 }; 296 unsigned int i; 297 struct stat buf; 298 const char *zDir = NULL; 299 300 azDirs[0] = sqlite3_temp_directory; 301 azDirs[1] = PR_GetEnvSecure("TMPDIR"); 302 303 for (i = 0; i < PR_ARRAY_SIZE(azDirs); i++) { 304 zDir = azDirs[i]; 305 if (zDir == NULL) 306 continue; 307 if (stat(zDir, &buf)) 308 continue; 309 if (!S_ISDIR(buf.st_mode)) 310 continue; 311 if (access(zDir, 07)) 312 continue; 313 break; 314 } 315 316 if (zDir == NULL) 317 return NULL; 318 return PORT_Strdup(zDir); 319 } 320 #else 321 #error "sdb_getFallbackTempDir not implemented" 322 #endif 323 324 #ifndef SQLITE_FCNTL_TEMPFILENAME 325 /* SQLITE_FCNTL_TEMPFILENAME was added in SQLite 3.7.15 */ 326 #define SQLITE_FCNTL_TEMPFILENAME 16 327 #endif 328 329 static char * 330 sdb_getTempDir(sqlite3 *sqlDB) 331 { 332 int sqlrv; 333 char *result = NULL; 334 char *tempName = NULL; 335 char *foundSeparator = NULL; 336 337 /* Obtain temporary filename in sqlite's directory for temporary tables */ 338 sqlrv = sqlite3_file_control(sqlDB, 0, SQLITE_FCNTL_TEMPFILENAME, 339 (void *)&tempName); 340 if (sqlrv == SQLITE_NOTFOUND) { 341 /* SQLITE_FCNTL_TEMPFILENAME not implemented because we are using 342 * an older SQLite. */ 343 return sdb_getFallbackTempDir(); 344 } 345 if (sqlrv != SQLITE_OK) { 346 return NULL; 347 } 348 349 /* We'll extract the temporary directory from tempName */ 350 foundSeparator = PORT_Strrchr(tempName, PR_GetDirectorySeparator()); 351 if (foundSeparator) { 352 /* We shorten the temp filename string to contain only 353 * the directory name (including the trailing separator). 354 * We know the byte after the foundSeparator position is 355 * safe to use, in the shortest scenario it contains the 356 * end-of-string byte. 357 * By keeping the separator at the found position, it will 358 * even work if tempDir consists of the separator, only. 359 * (In this case the toplevel directory will be used for 360 * access speed testing). */ 361 ++foundSeparator; 362 *foundSeparator = 0; 363 364 /* Now we copy the directory name for our caller */ 365 result = PORT_Strdup(tempName); 366 } 367 368 sqlite3_free(tempName); 369 return result; 370 } 371 372 /* 373 * Map SQL_LITE errors to PKCS #11 errors as best we can. 374 */ 375 static CK_RV 376 sdb_mapSQLError(sdbDataType type, int sqlerr) 377 { 378 switch (sqlerr) { 379 /* good matches */ 380 case SQLITE_OK: 381 case SQLITE_DONE: 382 return CKR_OK; 383 case SQLITE_NOMEM: 384 return CKR_HOST_MEMORY; 385 case SQLITE_READONLY: 386 return CKR_TOKEN_WRITE_PROTECTED; 387 /* close matches */ 388 case SQLITE_AUTH: 389 case SQLITE_PERM: 390 /*return CKR_USER_NOT_LOGGED_IN; */ 391 case SQLITE_CANTOPEN: 392 case SQLITE_NOTFOUND: 393 /* NSS distiguishes between failure to open the cert and the key db */ 394 return type == SDB_CERT ? CKR_NSS_CERTDB_FAILED : CKR_NSS_KEYDB_FAILED; 395 case SQLITE_IOERR: 396 return CKR_DEVICE_ERROR; 397 default: 398 break; 399 } 400 return CKR_GENERAL_ERROR; 401 } 402 403 /* 404 * build up database name from a directory, prefix, name, version and flags. 405 */ 406 static char * 407 sdb_BuildFileName(const char *directory, 408 const char *prefix, const char *type, 409 int version) 410 { 411 char *dbname = NULL; 412 /* build the full dbname */ 413 dbname = sqlite3_mprintf("%s%c%s%s%d.db", directory, 414 (int)(unsigned char)PR_GetDirectorySeparator(), 415 prefix, type, version); 416 return dbname; 417 } 418 419 /* 420 * find out how expensive the access system call is for non-existant files 421 * in the given directory. Return the number of operations done in 33 ms. 422 */ 423 static PRUint32 424 sdb_measureAccess(const char *directory) 425 { 426 PRUint32 i; 427 PRIntervalTime time; 428 PRIntervalTime delta; 429 PRIntervalTime duration = PR_MillisecondsToInterval(33); 430 const char *doesntExistName = "_dOeSnotExist_.db"; 431 char *temp, *tempStartOfFilename; 432 size_t maxTempLen, maxFileNameLen, directoryLength, tmpdirLength = 0; 433 #ifdef SDB_MEASURE_USE_TEMP_DIR 434 /* 435 * on some OS's and Filesystems, creating a bunch of files and deleting 436 * them messes up the systems's caching, but if we create the files in 437 * a temp directory which we later delete, then the cache gets cleared 438 * up. This code uses several OS dependent calls, and it's not clear 439 * that temp directory use won't mess up other filesystems and OS caching, 440 * so if you need this for your OS, you can turn on the 441 * 'SDB_MEASURE_USE_TEMP_DIR' define in coreconf 442 */ 443 const char template[] = "dbTemp.XXXXXX"; 444 tmpdirLength = sizeof(template); 445 #endif 446 /* no directory, just return one */ 447 if (directory == NULL) { 448 return 1; 449 } 450 451 /* our calculation assumes time is a 4 bytes == 32 bit integer */ 452 PORT_Assert(sizeof(time) == 4); 453 454 directoryLength = strlen(directory); 455 456 maxTempLen = directoryLength + 1 /* dirname + / */ 457 + tmpdirLength /* tmpdirname includes / */ 458 + strlen(doesntExistName) /* filename base */ 459 + 11 /* max chars for 32 bit int plus potential sign */ 460 + 1; /* zero terminator */ 461 462 temp = PORT_ZAlloc(maxTempLen); 463 if (!temp) { 464 return 1; 465 } 466 467 /* We'll copy directory into temp just once, then ensure it ends 468 * with the directory separator. */ 469 470 strcpy(temp, directory); 471 if (directory[directoryLength - 1] != PR_GetDirectorySeparator()) { 472 temp[directoryLength++] = PR_GetDirectorySeparator(); 473 } 474 475 #ifdef SDB_MEASURE_USE_TEMP_DIR 476 /* add the template for a temporary subdir, and create it */ 477 strcat(temp, template); 478 if (!mkdtemp(temp)) { 479 PORT_Free(temp); 480 return 1; 481 } 482 /* and terminate that tmp subdir with a / */ 483 strcat(temp, "/"); 484 #endif 485 486 /* Remember the position after the last separator, and calculate the 487 * number of remaining bytes. */ 488 tempStartOfFilename = temp + directoryLength + tmpdirLength; 489 maxFileNameLen = maxTempLen - directoryLength; 490 491 /* measure number of Access operations that can be done in 33 milliseconds 492 * (1/30'th of a second), or 10000 operations, which ever comes first. 493 */ 494 time = PR_IntervalNow(); 495 for (i = 0; i < 10000u; i++) { 496 PRIntervalTime next; 497 498 /* We'll use the variable part first in the filename string, just in 499 * case it's longer than assumed, so if anything gets cut off, it 500 * will be cut off from the constant part. 501 * This code assumes the directory name at the beginning of 502 * temp remains unchanged during our loop. */ 503 PR_snprintf(tempStartOfFilename, maxFileNameLen, 504 ".%lu%s", (PRUint32)(time + i), doesntExistName); 505 PR_Access(temp, PR_ACCESS_EXISTS); 506 next = PR_IntervalNow(); 507 delta = next - time; 508 if (delta >= duration) 509 break; 510 } 511 512 #ifdef SDB_MEASURE_USE_TEMP_DIR 513 /* turn temp back into our tmpdir path by removing doesntExistName, and 514 * remove the tmp dir */ 515 *tempStartOfFilename = '\0'; 516 (void)rmdir(temp); 517 #endif 518 PORT_Free(temp); 519 520 /* always return 1 or greater */ 521 return i ? i : 1u; 522 } 523 524 /* 525 * some file sytems are very slow to run sqlite3 on, particularly if the 526 * access count is pretty high. On these filesystems is faster to create 527 * a temporary database on the local filesystem and access that. This 528 * code uses a temporary table to create that cache. Temp tables are 529 * automatically cleared when the database handle it was created on 530 * Is freed. 531 */ 532 static const char DROP_CACHE_CMD[] = "DROP TABLE %s"; 533 static const char CREATE_CACHE_CMD[] = 534 "CREATE TEMPORARY TABLE %s AS SELECT * FROM %s"; 535 static const char CREATE_ISSUER_INDEX_CMD[] = 536 "CREATE INDEX issuer ON %s (a81)"; 537 static const char CREATE_SUBJECT_INDEX_CMD[] = 538 "CREATE INDEX subject ON %s (a101)"; 539 static const char CREATE_LABEL_INDEX_CMD[] = "CREATE INDEX label ON %s (a3)"; 540 static const char CREATE_ID_INDEX_CMD[] = "CREATE INDEX ckaid ON %s (a102)"; 541 542 static CK_RV 543 sdb_buildCache(sqlite3 *sqlDB, sdbDataType type, 544 const char *cacheTable, const char *table) 545 { 546 char *newStr; 547 int sqlerr = SQLITE_OK; 548 549 newStr = sqlite3_mprintf(CREATE_CACHE_CMD, cacheTable, table); 550 if (newStr == NULL) { 551 return CKR_HOST_MEMORY; 552 } 553 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 554 sqlite3_free(newStr); 555 if (sqlerr != SQLITE_OK) { 556 return sdb_mapSQLError(type, sqlerr); 557 } 558 /* failure to create the indexes is not an issue */ 559 newStr = sqlite3_mprintf(CREATE_ISSUER_INDEX_CMD, cacheTable); 560 if (newStr == NULL) { 561 return CKR_OK; 562 } 563 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 564 sqlite3_free(newStr); 565 newStr = sqlite3_mprintf(CREATE_SUBJECT_INDEX_CMD, cacheTable); 566 if (newStr == NULL) { 567 return CKR_OK; 568 } 569 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 570 sqlite3_free(newStr); 571 newStr = sqlite3_mprintf(CREATE_LABEL_INDEX_CMD, cacheTable); 572 if (newStr == NULL) { 573 return CKR_OK; 574 } 575 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 576 sqlite3_free(newStr); 577 newStr = sqlite3_mprintf(CREATE_ID_INDEX_CMD, cacheTable); 578 if (newStr == NULL) { 579 return CKR_OK; 580 } 581 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 582 sqlite3_free(newStr); 583 return CKR_OK; 584 } 585 586 /* 587 * update the cache and the data records describing it. 588 * The cache is updated by dropping the temp database and recreating it. 589 */ 590 static CK_RV 591 sdb_updateCache(SDBPrivate *sdb_p) 592 { 593 int sqlerr = SQLITE_OK; 594 CK_RV error = CKR_OK; 595 char *newStr; 596 597 /* drop the old table */ 598 newStr = sqlite3_mprintf(DROP_CACHE_CMD, sdb_p->cacheTable); 599 if (newStr == NULL) { 600 return CKR_HOST_MEMORY; 601 } 602 sqlerr = sqlite3_exec(sdb_p->sqlReadDB, newStr, NULL, 0, NULL); 603 sqlite3_free(newStr); 604 if ((sqlerr != SQLITE_OK) && (sqlerr != SQLITE_ERROR)) { 605 /* something went wrong with the drop, don't try to refresh... 606 * NOTE: SQLITE_ERROR is returned if the table doesn't exist. In 607 * that case, we just continue on and try to reload it */ 608 return sdb_mapSQLError(sdb_p->type, sqlerr); 609 } 610 611 /* set up the new table */ 612 error = sdb_buildCache(sdb_p->sqlReadDB, sdb_p->type, 613 sdb_p->cacheTable, sdb_p->table); 614 if (error == CKR_OK) { 615 /* we have a new cache! */ 616 sdb_p->lastUpdateTime = PR_IntervalNow(); 617 } 618 return error; 619 } 620 621 /* 622 * The sharing of sqlite3 handles across threads is tricky. Older versions 623 * couldn't at all, but newer ones can under strict conditions. Basically 624 * no 2 threads can use the same handle while another thread has an open 625 * stmt running. Once the sqlite3_stmt is finalized, another thread can then 626 * use the database handle. 627 * 628 * We use monitors to protect against trying to use a database before 629 * it's sqlite3_stmt is finalized. This is preferable to the opening and 630 * closing the database each operation because there is significant overhead 631 * in the open and close. Also continually opening and closing the database 632 * defeats the cache code as the cache table is lost on close (thus 633 * requiring us to have to reinitialize the cache every operation). 634 * 635 * An execption to the shared handle is transations. All writes happen 636 * through a transaction. When we are in a transaction, we must use the 637 * same database pointer for that entire transation. In this case we save 638 * the transaction database and use it for all accesses on the transaction 639 * thread. Other threads use the common database. 640 * 641 * There can only be once active transaction on the database at a time. 642 * 643 * sdb_openDBLocal() provides us with a valid database handle for whatever 644 * state we are in (reading or in a transaction), and acquires any locks 645 * appropriate to that state. It also decides when it's time to refresh 646 * the cache before we start an operation. Any database handle returned 647 * just eventually be closed with sdb_closeDBLocal(). 648 * 649 * The table returned either points to the database's physical table, or 650 * to the cached shadow. Tranactions always return the physical table 651 * and read operations return either the physical table or the cache 652 * depending on whether or not the cache exists. 653 */ 654 static CK_RV 655 sdb_openDBLocal(SDBPrivate *sdb_p, sqlite3 **sqlDB, const char **table) 656 { 657 *sqlDB = NULL; 658 659 PR_EnterMonitor(sdb_p->dbMon); 660 661 if (table) { 662 *table = sdb_p->table; 663 } 664 665 /* We're in a transaction, use the transaction DB */ 666 if ((sdb_p->sqlXactDB) && (sdb_p->sqlXactThread == PR_GetCurrentThread())) { 667 *sqlDB = sdb_p->sqlXactDB; 668 /* only one thread can get here, safe to unlock */ 669 PR_ExitMonitor(sdb_p->dbMon); 670 return CKR_OK; 671 } 672 673 /* 674 * if we are just reading from the table, we may have the table 675 * cached in a temporary table (especially if it's on a shared FS). 676 * In that case we want to see updates to the table, the the granularity 677 * is on order of human scale, not computer scale. 678 */ 679 if (table && sdb_p->cacheTable) { 680 PRIntervalTime now = PR_IntervalNow(); 681 if ((now - sdb_p->lastUpdateTime) > sdb_p->updateInterval) { 682 sdb_updateCache(sdb_p); 683 } 684 *table = sdb_p->cacheTable; 685 } 686 687 *sqlDB = sdb_p->sqlReadDB; 688 689 /* leave holding the lock. only one thread can actually use a given 690 * database connection at once */ 691 692 return CKR_OK; 693 } 694 695 /* closing the local database currenly means unlocking the monitor */ 696 static CK_RV 697 sdb_closeDBLocal(SDBPrivate *sdb_p, sqlite3 *sqlDB) 698 { 699 if (sdb_p->sqlXactDB != sqlDB) { 700 /* if we weren't in a transaction, we got a lock */ 701 PR_ExitMonitor(sdb_p->dbMon); 702 } 703 return CKR_OK; 704 } 705 706 /* 707 * wrapper to sqlite3_open which also sets the busy_timeout 708 */ 709 static int 710 sdb_openDB(const char *name, sqlite3 **sqlDB, int flags) 711 { 712 int sqlerr; 713 int openFlags; 714 715 *sqlDB = NULL; 716 717 if (flags & SDB_RDONLY) { 718 openFlags = SQLITE_OPEN_READONLY; 719 } else { 720 openFlags = SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE; 721 /* sqlite 3.34 seem to incorrectly open readwrite. 722 * when the file is readonly. Explicitly reject that issue here */ 723 if ((_NSSUTIL_Access(name, PR_ACCESS_EXISTS) == PR_SUCCESS) && (_NSSUTIL_Access(name, PR_ACCESS_WRITE_OK) != PR_SUCCESS)) { 724 return SQLITE_READONLY; 725 } 726 } 727 728 /* Requires SQLite 3.5.0 or newer. */ 729 sqlerr = sqlite3_open_v2(name, sqlDB, openFlags, NULL); 730 if (sqlerr != SQLITE_OK) { 731 return sqlerr; 732 } 733 734 sqlerr = sqlite3_busy_timeout(*sqlDB, SDB_SQLITE_BUSY_TIMEOUT); 735 if (sqlerr != SQLITE_OK) { 736 sqlite3_close(*sqlDB); 737 *sqlDB = NULL; 738 return sqlerr; 739 } 740 return SQLITE_OK; 741 } 742 743 /* Sigh, if we created a new table since we opened the database, 744 * the database handle will not see the new table, we need to close this 745 * database and reopen it. Caller must be in a transaction or holding 746 * the dbMon. sqlDB is changed on success. */ 747 static int 748 sdb_reopenDBLocal(SDBPrivate *sdb_p, sqlite3 **sqlDB) 749 { 750 sqlite3 *newDB; 751 int sqlerr; 752 753 /* open a new database */ 754 sqlerr = sdb_openDB(sdb_p->sqlDBName, &newDB, SDB_RDONLY); 755 if (sqlerr != SQLITE_OK) { 756 return sqlerr; 757 } 758 759 /* if we are in a transaction, we may not be holding the monitor. 760 * grab it before we update the transaction database. This is 761 * safe since are using monitors. */ 762 PR_EnterMonitor(sdb_p->dbMon); 763 /* update our view of the database */ 764 if (sdb_p->sqlReadDB == *sqlDB) { 765 sdb_p->sqlReadDB = newDB; 766 } else if (sdb_p->sqlXactDB == *sqlDB) { 767 sdb_p->sqlXactDB = newDB; 768 } 769 PR_ExitMonitor(sdb_p->dbMon); 770 771 /* close the old one */ 772 sqlite3_close(*sqlDB); 773 774 *sqlDB = newDB; 775 return SQLITE_OK; 776 } 777 778 struct SDBFindStr { 779 sqlite3 *sqlDB; 780 sqlite3_stmt *findstmt; 781 }; 782 783 static const char FIND_OBJECTS_CMD[] = "SELECT ALL id FROM %s WHERE %s;"; 784 static const char FIND_OBJECTS_ALL_CMD[] = "SELECT ALL id FROM %s;"; 785 CK_RV 786 sdb_FindObjectsInit(SDB *sdb, const CK_ATTRIBUTE *template, CK_ULONG count, 787 SDBFind **find) 788 { 789 SDBPrivate *sdb_p = sdb->private; 790 sqlite3 *sqlDB = NULL; 791 const char *table; 792 char *newStr, *findStr = NULL; 793 sqlite3_stmt *findstmt = NULL; 794 char *join = ""; 795 int sqlerr = SQLITE_OK; 796 CK_RV error = CKR_OK; 797 unsigned int i; 798 799 LOCK_SQLITE() 800 *find = NULL; 801 error = sdb_openDBLocal(sdb_p, &sqlDB, &table); 802 if (error != CKR_OK) { 803 goto loser; 804 } 805 806 findStr = sqlite3_mprintf(""); 807 for (i = 0; findStr && i < count; i++) { 808 newStr = sqlite3_mprintf("%s%sa%x=$DATA%d", findStr, join, 809 template[i].type, i); 810 join = " AND "; 811 sqlite3_free(findStr); 812 findStr = newStr; 813 } 814 815 if (findStr == NULL) { 816 error = CKR_HOST_MEMORY; 817 goto loser; 818 } 819 820 if (count == 0) { 821 newStr = sqlite3_mprintf(FIND_OBJECTS_ALL_CMD, table); 822 } else { 823 newStr = sqlite3_mprintf(FIND_OBJECTS_CMD, table, findStr); 824 } 825 sqlite3_free(findStr); 826 if (newStr == NULL) { 827 error = CKR_HOST_MEMORY; 828 goto loser; 829 } 830 sqlerr = sqlite3_prepare_v2(sqlDB, newStr, -1, &findstmt, NULL); 831 sqlite3_free(newStr); 832 for (i = 0; sqlerr == SQLITE_OK && i < count; i++) { 833 const void *blobData = template[i].pValue; 834 unsigned int blobSize = template[i].ulValueLen; 835 if (blobSize == 0) { 836 blobSize = SQLITE_EXPLICIT_NULL_LEN; 837 blobData = SQLITE_EXPLICIT_NULL; 838 } 839 sqlerr = sqlite3_bind_blob(findstmt, i + 1, blobData, blobSize, 840 SQLITE_TRANSIENT); 841 } 842 if (sqlerr == SQLITE_OK) { 843 *find = PORT_New(SDBFind); 844 if (*find == NULL) { 845 error = CKR_HOST_MEMORY; 846 goto loser; 847 } 848 (*find)->findstmt = findstmt; 849 (*find)->sqlDB = sqlDB; 850 UNLOCK_SQLITE() 851 return CKR_OK; 852 } 853 error = sdb_mapSQLError(sdb_p->type, sqlerr); 854 855 loser: 856 if (findstmt) { 857 sqlite3_reset(findstmt); 858 sqlite3_finalize(findstmt); 859 } 860 if (sqlDB) { 861 sdb_closeDBLocal(sdb_p, sqlDB); 862 } 863 UNLOCK_SQLITE() 864 return error; 865 } 866 867 CK_RV 868 sdb_FindObjects(SDB *sdb, SDBFind *sdbFind, CK_OBJECT_HANDLE *object, 869 CK_ULONG arraySize, CK_ULONG *count) 870 { 871 SDBPrivate *sdb_p = sdb->private; 872 sqlite3_stmt *stmt = sdbFind->findstmt; 873 int sqlerr = SQLITE_OK; 874 int retry = 0; 875 876 *count = 0; 877 878 if (arraySize == 0) { 879 return CKR_OK; 880 } 881 LOCK_SQLITE() 882 883 do { 884 sqlerr = sqlite3_step(stmt); 885 if (sqlerr == SQLITE_BUSY) { 886 PR_Sleep(SDB_BUSY_RETRY_TIME); 887 } 888 if (sqlerr == SQLITE_ROW) { 889 /* only care about the id */ 890 *object++ = sqlite3_column_int(stmt, 0); 891 arraySize--; 892 (*count)++; 893 } 894 } while (!sdb_done(sqlerr, &retry) && (arraySize > 0)); 895 896 /* we only have some of the objects, there is probably more, 897 * set the sqlerr to an OK value so we return CKR_OK */ 898 if (sqlerr == SQLITE_ROW && arraySize == 0) { 899 sqlerr = SQLITE_DONE; 900 } 901 UNLOCK_SQLITE() 902 903 return sdb_mapSQLError(sdb_p->type, sqlerr); 904 } 905 906 CK_RV 907 sdb_FindObjectsFinal(SDB *sdb, SDBFind *sdbFind) 908 { 909 SDBPrivate *sdb_p = sdb->private; 910 sqlite3_stmt *stmt = sdbFind->findstmt; 911 sqlite3 *sqlDB = sdbFind->sqlDB; 912 int sqlerr = SQLITE_OK; 913 914 LOCK_SQLITE() 915 if (stmt) { 916 sqlite3_reset(stmt); 917 sqlerr = sqlite3_finalize(stmt); 918 } 919 if (sqlDB) { 920 sdb_closeDBLocal(sdb_p, sqlDB); 921 } 922 PORT_Free(sdbFind); 923 924 UNLOCK_SQLITE() 925 return sdb_mapSQLError(sdb_p->type, sqlerr); 926 } 927 928 static CK_RV 929 sdb_GetValidAttributeValueNoLock(SDB *sdb, CK_OBJECT_HANDLE object_id, 930 CK_ATTRIBUTE *template, CK_ULONG count) 931 { 932 SDBPrivate *sdb_p = sdb->private; 933 sqlite3 *sqlDB = NULL; 934 sqlite3_stmt *stmt = NULL; 935 const char *table = NULL; 936 int sqlerr = SQLITE_OK; 937 CK_RV error = CKR_OK; 938 int found = 0; 939 int retry = 0; 940 unsigned int i; 941 942 if (count == 0) { 943 error = CKR_OBJECT_HANDLE_INVALID; 944 goto loser; 945 } 946 947 /* open a new db if necessary */ 948 error = sdb_openDBLocal(sdb_p, &sqlDB, &table); 949 if (error != CKR_OK) { 950 goto loser; 951 } 952 953 char *columns = NULL; 954 for (i = 0; i < count; i++) { 955 char *newColumns; 956 if (columns) { 957 newColumns = sqlite3_mprintf("%s, a%x", columns, template[i].type); 958 sqlite3_free(columns); 959 columns = NULL; 960 } else { 961 newColumns = sqlite3_mprintf("a%x", template[i].type); 962 } 963 if (!newColumns) { 964 error = CKR_HOST_MEMORY; 965 goto loser; 966 } 967 columns = newColumns; 968 } 969 970 PORT_Assert(columns); 971 972 char *statement = sqlite3_mprintf("SELECT DISTINCT %s FROM %s where id=$ID LIMIT 1;", 973 columns, table); 974 sqlite3_free(columns); 975 columns = NULL; 976 if (!statement) { 977 error = CKR_HOST_MEMORY; 978 goto loser; 979 } 980 981 sqlerr = sqlite3_prepare_v2(sqlDB, statement, -1, &stmt, NULL); 982 sqlite3_free(statement); 983 statement = NULL; 984 if (sqlerr != SQLITE_OK) { 985 goto loser; 986 } 987 988 // NB: indices in sqlite3_bind_int are 1-indexed 989 sqlerr = sqlite3_bind_int(stmt, 1, object_id); 990 if (sqlerr != SQLITE_OK) { 991 goto loser; 992 } 993 994 do { 995 sqlerr = sqlite3_step(stmt); 996 if (sqlerr == SQLITE_BUSY) { 997 PR_Sleep(SDB_BUSY_RETRY_TIME); 998 } 999 if (sqlerr == SQLITE_ROW) { 1000 PORT_Assert(!found); 1001 for (i = 0; i < count; i++) { 1002 unsigned int blobSize; 1003 const char *blobData; 1004 1005 // NB: indices in sqlite_column_{bytes,blob} are 0-indexed 1006 blobSize = sqlite3_column_bytes(stmt, i); 1007 blobData = sqlite3_column_blob(stmt, i); 1008 if (blobData == NULL) { 1009 /* PKCS 11 requires that get attributes process all the 1010 * attributes in the template, marking the attributes with 1011 * issues with -1. Mark the error but continue */ 1012 template[i].ulValueLen = -1; 1013 error = CKR_ATTRIBUTE_TYPE_INVALID; 1014 continue; 1015 } 1016 /* If the blob equals our explicit NULL value, then the 1017 * attribute is a NULL. */ 1018 if ((blobSize == SQLITE_EXPLICIT_NULL_LEN) && 1019 (PORT_Memcmp(blobData, SQLITE_EXPLICIT_NULL, 1020 SQLITE_EXPLICIT_NULL_LEN) == 0)) { 1021 blobSize = 0; 1022 } 1023 if (template[i].pValue) { 1024 if (template[i].ulValueLen < blobSize) { 1025 /* like CKR_ATTRIBUTE_TYPE_INVALID, continue processing */ 1026 template[i].ulValueLen = -1; 1027 error = CKR_BUFFER_TOO_SMALL; 1028 continue; 1029 } 1030 PORT_Memcpy(template[i].pValue, blobData, blobSize); 1031 } 1032 template[i].ulValueLen = blobSize; 1033 } 1034 found = 1; 1035 } 1036 } while (!sdb_done(sqlerr, &retry)); 1037 1038 sqlite3_reset(stmt); 1039 sqlite3_finalize(stmt); 1040 stmt = NULL; 1041 1042 loser: 1043 /* fix up the error if necessary */ 1044 if (error == CKR_OK) { 1045 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1046 if (!found && error == CKR_OK) { 1047 error = CKR_OBJECT_HANDLE_INVALID; 1048 } 1049 } 1050 1051 if (stmt) { 1052 sqlite3_reset(stmt); 1053 sqlite3_finalize(stmt); 1054 } 1055 1056 /* if we had to open a new database, free it now */ 1057 if (sqlDB) { 1058 sdb_closeDBLocal(sdb_p, sqlDB); 1059 } 1060 return error; 1061 } 1062 1063 /* NOTE: requires sdb_p->schemaAttrs to be sorted asc. */ 1064 inline static PRBool 1065 sdb_attributeExists(SDB *sdb, CK_ATTRIBUTE_TYPE attr) 1066 { 1067 SDBPrivate *sdb_p = sdb->private; 1068 int first = 0; 1069 int last = (int)sdb_p->numSchemaAttrs - 1; 1070 while (last >= first) { 1071 int mid = first + (last - first) / 2; 1072 if (sdb_p->schemaAttrs[mid] == attr) { 1073 return PR_TRUE; 1074 } 1075 if (attr > sdb_p->schemaAttrs[mid]) { 1076 first = mid + 1; 1077 } else { 1078 last = mid - 1; 1079 } 1080 } 1081 1082 return PR_FALSE; 1083 } 1084 1085 CK_RV 1086 sdb_GetAttributeValue(SDB *sdb, CK_OBJECT_HANDLE object_id, 1087 CK_ATTRIBUTE *template, CK_ULONG count) 1088 { 1089 CK_RV crv = CKR_OK; 1090 unsigned int tmplIdx; 1091 unsigned int resIdx = 0; 1092 unsigned int validCount = 0; 1093 unsigned int i; 1094 1095 if (count == 0) { 1096 return crv; 1097 } 1098 1099 CK_ATTRIBUTE *validTemplate; 1100 PRBool invalidExists = PR_FALSE; 1101 for (tmplIdx = 0; tmplIdx < count; tmplIdx++) { 1102 if (!sdb_attributeExists(sdb, template[tmplIdx].type)) { 1103 template[tmplIdx].ulValueLen = -1; 1104 crv = CKR_ATTRIBUTE_TYPE_INVALID; 1105 invalidExists = PR_TRUE; 1106 break; 1107 } 1108 } 1109 1110 if (!invalidExists) { 1111 validTemplate = template; 1112 validCount = count; 1113 } else { 1114 /* Create a new template containing only the valid subset of 1115 * input |template|, and query with that. */ 1116 validCount = tmplIdx; 1117 validTemplate = malloc(sizeof(CK_ATTRIBUTE) * count); 1118 if (!validTemplate) { 1119 return CKR_HOST_MEMORY; 1120 } 1121 /* Copy in what we already know is valid. */ 1122 for (i = 0; i < validCount; i++) { 1123 validTemplate[i] = template[i]; 1124 } 1125 1126 /* tmplIdx was left at the index of the first invalid 1127 * attribute, which has been handled. We only need to 1128 * deal with the remainder. */ 1129 tmplIdx++; 1130 for (; tmplIdx < count; tmplIdx++) { 1131 if (sdb_attributeExists(sdb, template[tmplIdx].type)) { 1132 validTemplate[validCount++] = template[tmplIdx]; 1133 } else { 1134 template[tmplIdx].ulValueLen = -1; 1135 } 1136 } 1137 } 1138 1139 if (validCount) { 1140 LOCK_SQLITE() 1141 CK_RV crv2 = sdb_GetValidAttributeValueNoLock(sdb, object_id, validTemplate, validCount); 1142 UNLOCK_SQLITE() 1143 1144 /* If an invalid attribute was removed above, let 1145 * the caller know. Any other error from the actual 1146 * query should propogate. */ 1147 crv = (crv2 == CKR_OK) ? crv : crv2; 1148 } 1149 1150 if (invalidExists) { 1151 /* Copy out valid lengths. */ 1152 tmplIdx = 0; 1153 for (resIdx = 0; resIdx < validCount; resIdx++) { 1154 for (; tmplIdx < count; tmplIdx++) { 1155 if (template[tmplIdx].type != validTemplate[resIdx].type) { 1156 continue; 1157 } 1158 template[tmplIdx].ulValueLen = validTemplate[resIdx].ulValueLen; 1159 tmplIdx++; 1160 break; 1161 } 1162 } 1163 free(validTemplate); 1164 } 1165 1166 return crv; 1167 } 1168 1169 static const char SET_ATTRIBUTE_CMD[] = "UPDATE %s SET %s WHERE id=$ID;"; 1170 CK_RV 1171 sdb_SetAttributeValue(SDB *sdb, CK_OBJECT_HANDLE object_id, 1172 const CK_ATTRIBUTE *template, CK_ULONG count) 1173 { 1174 SDBPrivate *sdb_p = sdb->private; 1175 sqlite3 *sqlDB = NULL; 1176 sqlite3_stmt *stmt = NULL; 1177 char *setStr = NULL; 1178 char *newStr = NULL; 1179 int sqlerr = SQLITE_OK; 1180 int retry = 0; 1181 CK_RV error = CKR_OK; 1182 unsigned int i; 1183 1184 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1185 return CKR_TOKEN_WRITE_PROTECTED; 1186 } 1187 1188 if (count == 0) { 1189 return CKR_OK; 1190 } 1191 1192 LOCK_SQLITE() 1193 setStr = sqlite3_mprintf(""); 1194 for (i = 0; setStr && i < count; i++) { 1195 if (i == 0) { 1196 sqlite3_free(setStr); 1197 setStr = sqlite3_mprintf("a%x=$VALUE%d", 1198 template[i].type, i); 1199 continue; 1200 } 1201 newStr = sqlite3_mprintf("%s,a%x=$VALUE%d", setStr, 1202 template[i].type, i); 1203 sqlite3_free(setStr); 1204 setStr = newStr; 1205 } 1206 newStr = NULL; 1207 1208 if (setStr == NULL) { 1209 return CKR_HOST_MEMORY; 1210 } 1211 newStr = sqlite3_mprintf(SET_ATTRIBUTE_CMD, sdb_p->table, setStr); 1212 sqlite3_free(setStr); 1213 if (newStr == NULL) { 1214 UNLOCK_SQLITE() 1215 return CKR_HOST_MEMORY; 1216 } 1217 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1218 if (error != CKR_OK) { 1219 goto loser; 1220 } 1221 sqlerr = sqlite3_prepare_v2(sqlDB, newStr, -1, &stmt, NULL); 1222 if (sqlerr != SQLITE_OK) 1223 goto loser; 1224 for (i = 0; i < count; i++) { 1225 if (template[i].ulValueLen != 0) { 1226 sqlerr = sqlite3_bind_blob(stmt, i + 1, template[i].pValue, 1227 template[i].ulValueLen, SQLITE_STATIC); 1228 } else { 1229 sqlerr = sqlite3_bind_blob(stmt, i + 1, SQLITE_EXPLICIT_NULL, 1230 SQLITE_EXPLICIT_NULL_LEN, SQLITE_STATIC); 1231 } 1232 if (sqlerr != SQLITE_OK) 1233 goto loser; 1234 } 1235 sqlerr = sqlite3_bind_int(stmt, i + 1, object_id); 1236 if (sqlerr != SQLITE_OK) 1237 goto loser; 1238 1239 do { 1240 sqlerr = sqlite3_step(stmt); 1241 if (sqlerr == SQLITE_BUSY) { 1242 PR_Sleep(SDB_BUSY_RETRY_TIME); 1243 } 1244 } while (!sdb_done(sqlerr, &retry)); 1245 1246 loser: 1247 if (newStr) { 1248 sqlite3_free(newStr); 1249 } 1250 if (error == CKR_OK) { 1251 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1252 } 1253 1254 if (stmt) { 1255 sqlite3_reset(stmt); 1256 sqlite3_finalize(stmt); 1257 } 1258 1259 if (sqlDB) { 1260 sdb_closeDBLocal(sdb_p, sqlDB); 1261 } 1262 1263 UNLOCK_SQLITE() 1264 return error; 1265 } 1266 1267 /* 1268 * check to see if a candidate object handle already exists. 1269 */ 1270 static PRBool 1271 sdb_objectExists(SDB *sdb, CK_OBJECT_HANDLE candidate) 1272 { 1273 CK_RV crv; 1274 CK_ATTRIBUTE template = { CKA_LABEL, NULL, 0 }; 1275 1276 crv = sdb_GetValidAttributeValueNoLock(sdb, candidate, &template, 1); 1277 if (crv == CKR_OBJECT_HANDLE_INVALID) { 1278 return PR_FALSE; 1279 } 1280 return PR_TRUE; 1281 } 1282 1283 /* 1284 * if we're here, we are in a transaction, so it's safe 1285 * to examine the current state of the database 1286 */ 1287 static CK_OBJECT_HANDLE 1288 sdb_getObjectId(SDB *sdb) 1289 { 1290 CK_OBJECT_HANDLE candidate; 1291 static CK_OBJECT_HANDLE next_obj = CK_INVALID_HANDLE; 1292 int count; 1293 /* 1294 * get an initial object handle to use 1295 */ 1296 if (next_obj == CK_INVALID_HANDLE) { 1297 PRTime time; 1298 time = PR_Now(); 1299 1300 next_obj = (CK_OBJECT_HANDLE)(time & 0x3fffffffL); 1301 } 1302 candidate = next_obj++; 1303 /* detect that we've looped through all the handles... */ 1304 for (count = 0; count < 0x40000000; count++, candidate = next_obj++) { 1305 /* mask off excess bits */ 1306 candidate &= 0x3fffffff; 1307 /* if we hit zero, go to the next entry */ 1308 if (candidate == CK_INVALID_HANDLE) { 1309 continue; 1310 } 1311 /* make sure we aren't already using */ 1312 if (!sdb_objectExists(sdb, candidate)) { 1313 /* this one is free */ 1314 return candidate; 1315 } 1316 } 1317 1318 /* no handle is free, fail */ 1319 return CK_INVALID_HANDLE; 1320 } 1321 1322 CK_RV 1323 sdb_GetNewObjectID(SDB *sdb, CK_OBJECT_HANDLE *object) 1324 { 1325 CK_OBJECT_HANDLE id; 1326 1327 id = sdb_getObjectId(sdb); 1328 if (id == CK_INVALID_HANDLE) { 1329 return CKR_DEVICE_MEMORY; /* basically we ran out of resources */ 1330 } 1331 *object = id; 1332 return CKR_OK; 1333 } 1334 1335 static const char CREATE_CMD[] = "INSERT INTO %s (id%s) VALUES($ID%s);"; 1336 CK_RV 1337 sdb_CreateObject(SDB *sdb, CK_OBJECT_HANDLE *object_id, 1338 const CK_ATTRIBUTE *template, CK_ULONG count) 1339 { 1340 SDBPrivate *sdb_p = sdb->private; 1341 sqlite3 *sqlDB = NULL; 1342 sqlite3_stmt *stmt = NULL; 1343 char *columnStr = NULL; 1344 char *valueStr = NULL; 1345 char *newStr = NULL; 1346 int sqlerr = SQLITE_OK; 1347 CK_RV error = CKR_OK; 1348 CK_OBJECT_HANDLE this_object = CK_INVALID_HANDLE; 1349 int retry = 0; 1350 unsigned int i; 1351 1352 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1353 return CKR_TOKEN_WRITE_PROTECTED; 1354 } 1355 1356 LOCK_SQLITE() 1357 if ((*object_id != CK_INVALID_HANDLE) && 1358 !sdb_objectExists(sdb, *object_id)) { 1359 this_object = *object_id; 1360 } else { 1361 this_object = sdb_getObjectId(sdb); 1362 } 1363 if (this_object == CK_INVALID_HANDLE) { 1364 UNLOCK_SQLITE(); 1365 return CKR_HOST_MEMORY; 1366 } 1367 columnStr = sqlite3_mprintf(""); 1368 valueStr = sqlite3_mprintf(""); 1369 *object_id = this_object; 1370 for (i = 0; columnStr && valueStr && i < count; i++) { 1371 newStr = sqlite3_mprintf("%s,a%x", columnStr, template[i].type); 1372 sqlite3_free(columnStr); 1373 columnStr = newStr; 1374 newStr = sqlite3_mprintf("%s,$VALUE%d", valueStr, i); 1375 sqlite3_free(valueStr); 1376 valueStr = newStr; 1377 } 1378 newStr = NULL; 1379 if ((columnStr == NULL) || (valueStr == NULL)) { 1380 if (columnStr) { 1381 sqlite3_free(columnStr); 1382 } 1383 if (valueStr) { 1384 sqlite3_free(valueStr); 1385 } 1386 UNLOCK_SQLITE() 1387 return CKR_HOST_MEMORY; 1388 } 1389 newStr = sqlite3_mprintf(CREATE_CMD, sdb_p->table, columnStr, valueStr); 1390 sqlite3_free(columnStr); 1391 sqlite3_free(valueStr); 1392 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1393 if (error != CKR_OK) { 1394 goto loser; 1395 } 1396 sqlerr = sqlite3_prepare_v2(sqlDB, newStr, -1, &stmt, NULL); 1397 if (sqlerr != SQLITE_OK) 1398 goto loser; 1399 sqlerr = sqlite3_bind_int(stmt, 1, *object_id); 1400 if (sqlerr != SQLITE_OK) 1401 goto loser; 1402 for (i = 0; i < count; i++) { 1403 if (template[i].ulValueLen) { 1404 sqlerr = sqlite3_bind_blob(stmt, i + 2, template[i].pValue, 1405 template[i].ulValueLen, SQLITE_STATIC); 1406 } else { 1407 sqlerr = sqlite3_bind_blob(stmt, i + 2, SQLITE_EXPLICIT_NULL, 1408 SQLITE_EXPLICIT_NULL_LEN, SQLITE_STATIC); 1409 } 1410 if (sqlerr != SQLITE_OK) 1411 goto loser; 1412 } 1413 1414 do { 1415 sqlerr = sqlite3_step(stmt); 1416 if (sqlerr == SQLITE_BUSY) { 1417 PR_Sleep(SDB_BUSY_RETRY_TIME); 1418 } 1419 } while (!sdb_done(sqlerr, &retry)); 1420 1421 loser: 1422 if (newStr) { 1423 sqlite3_free(newStr); 1424 } 1425 if (error == CKR_OK) { 1426 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1427 } 1428 1429 if (stmt) { 1430 sqlite3_reset(stmt); 1431 sqlite3_finalize(stmt); 1432 } 1433 1434 if (sqlDB) { 1435 sdb_closeDBLocal(sdb_p, sqlDB); 1436 } 1437 UNLOCK_SQLITE() 1438 1439 return error; 1440 } 1441 1442 /* 1443 * Generic destroy that can destroy metadata or objects 1444 */ 1445 static const char DESTROY_CMD[] = "DELETE FROM %s WHERE (id=$ID);"; 1446 CK_RV 1447 sdb_destroyAnyObject(SDB *sdb, const char *table, 1448 CK_OBJECT_HANDLE object_id, const char *string_id) 1449 { 1450 SDBPrivate *sdb_p = sdb->private; 1451 sqlite3 *sqlDB = NULL; 1452 sqlite3_stmt *stmt = NULL; 1453 char *newStr = NULL; 1454 int sqlerr = SQLITE_OK; 1455 CK_RV error = CKR_OK; 1456 int retry = 0; 1457 1458 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1459 return CKR_TOKEN_WRITE_PROTECTED; 1460 } 1461 1462 LOCK_SQLITE() 1463 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1464 if (error != CKR_OK) { 1465 goto loser; 1466 } 1467 newStr = sqlite3_mprintf(DESTROY_CMD, table); 1468 if (newStr == NULL) { 1469 error = CKR_HOST_MEMORY; 1470 goto loser; 1471 } 1472 sqlerr = sqlite3_prepare_v2(sqlDB, newStr, -1, &stmt, NULL); 1473 sqlite3_free(newStr); 1474 if (sqlerr != SQLITE_OK) 1475 goto loser; 1476 if (string_id == NULL) { 1477 sqlerr = sqlite3_bind_int(stmt, 1, object_id); 1478 } else { 1479 sqlerr = sqlite3_bind_text(stmt, 1, string_id, 1480 PORT_Strlen(string_id), SQLITE_STATIC); 1481 } 1482 if (sqlerr != SQLITE_OK) 1483 goto loser; 1484 1485 do { 1486 sqlerr = sqlite3_step(stmt); 1487 if (sqlerr == SQLITE_BUSY) { 1488 PR_Sleep(SDB_BUSY_RETRY_TIME); 1489 } 1490 } while (!sdb_done(sqlerr, &retry)); 1491 1492 loser: 1493 if (error == CKR_OK) { 1494 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1495 } 1496 1497 if (stmt) { 1498 sqlite3_reset(stmt); 1499 sqlite3_finalize(stmt); 1500 } 1501 1502 if (sqlDB) { 1503 sdb_closeDBLocal(sdb_p, sqlDB); 1504 } 1505 1506 UNLOCK_SQLITE() 1507 return error; 1508 } 1509 1510 CK_RV 1511 sdb_DestroyObject(SDB *sdb, CK_OBJECT_HANDLE object_id) 1512 { 1513 SDBPrivate *sdb_p = sdb->private; 1514 return sdb_destroyAnyObject(sdb, sdb_p->table, object_id, NULL); 1515 } 1516 1517 CK_RV 1518 sdb_DestroyMetaData(SDB *sdb, const char *id) 1519 { 1520 return sdb_destroyAnyObject(sdb, "metaData", 0, id); 1521 } 1522 1523 static const char BEGIN_CMD[] = "BEGIN IMMEDIATE TRANSACTION;"; 1524 1525 /* 1526 * start a transaction. 1527 * 1528 * We need to open a new database, then store that new database into 1529 * the private data structure. We open the database first, then use locks 1530 * to protect storing the data to prevent deadlocks. 1531 */ 1532 CK_RV 1533 sdb_Begin(SDB *sdb) 1534 { 1535 SDBPrivate *sdb_p = sdb->private; 1536 sqlite3 *sqlDB = NULL; 1537 sqlite3_stmt *stmt = NULL; 1538 int sqlerr = SQLITE_OK; 1539 CK_RV error = CKR_OK; 1540 int retry = 0; 1541 1542 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1543 return CKR_TOKEN_WRITE_PROTECTED; 1544 } 1545 1546 LOCK_SQLITE() 1547 1548 /* get a new version that we will use for the entire transaction */ 1549 sqlerr = sdb_openDB(sdb_p->sqlDBName, &sqlDB, SDB_RDWR); 1550 if (sqlerr != SQLITE_OK) { 1551 goto loser; 1552 } 1553 1554 sqlerr = sqlite3_prepare_v2(sqlDB, BEGIN_CMD, -1, &stmt, NULL); 1555 1556 do { 1557 sqlerr = sqlite3_step(stmt); 1558 if (sqlerr == SQLITE_BUSY) { 1559 PR_Sleep(SDB_BUSY_RETRY_TIME); 1560 } 1561 /* don't retry BEGIN transaction*/ 1562 retry = 0; 1563 } while (!sdb_done(sqlerr, &retry)); 1564 1565 if (stmt) { 1566 sqlite3_reset(stmt); 1567 sqlite3_finalize(stmt); 1568 } 1569 1570 loser: 1571 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1572 1573 /* we are starting a new transaction, 1574 * and if we succeeded, then save this database for the rest of 1575 * our transaction */ 1576 if (error == CKR_OK) { 1577 /* we hold a 'BEGIN TRANSACTION' and a sdb_p->lock. At this point 1578 * sdb_p->sqlXactDB MUST be null */ 1579 PR_EnterMonitor(sdb_p->dbMon); 1580 PORT_Assert(sdb_p->sqlXactDB == NULL); 1581 sdb_p->sqlXactDB = sqlDB; 1582 sdb_p->sqlXactThread = PR_GetCurrentThread(); 1583 PR_ExitMonitor(sdb_p->dbMon); 1584 } else { 1585 /* we failed to start our transaction, 1586 * free any databases we opened. */ 1587 if (sqlDB) { 1588 sqlite3_close(sqlDB); 1589 } 1590 } 1591 1592 UNLOCK_SQLITE() 1593 return error; 1594 } 1595 1596 /* 1597 * Complete a transaction. Basically undo everything we did in begin. 1598 * There are 2 flavors Abort and Commit. Basically the only differerence between 1599 * these 2 are what the database will show. (no change in to former, change in 1600 * the latter). 1601 */ 1602 static CK_RV 1603 sdb_complete(SDB *sdb, const char *cmd) 1604 { 1605 SDBPrivate *sdb_p = sdb->private; 1606 sqlite3 *sqlDB = NULL; 1607 sqlite3_stmt *stmt = NULL; 1608 int sqlerr = SQLITE_OK; 1609 CK_RV error = CKR_OK; 1610 int retry = 0; 1611 1612 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1613 return CKR_TOKEN_WRITE_PROTECTED; 1614 } 1615 1616 /* We must have a transation database, or we shouldn't have arrived here */ 1617 PR_EnterMonitor(sdb_p->dbMon); 1618 PORT_Assert(sdb_p->sqlXactDB); 1619 if (sdb_p->sqlXactDB == NULL) { 1620 PR_ExitMonitor(sdb_p->dbMon); 1621 return CKR_GENERAL_ERROR; /* shouldn't happen */ 1622 } 1623 PORT_Assert(sdb_p->sqlXactThread == PR_GetCurrentThread()); 1624 if (sdb_p->sqlXactThread != PR_GetCurrentThread()) { 1625 PR_ExitMonitor(sdb_p->dbMon); 1626 return CKR_GENERAL_ERROR; /* shouldn't happen */ 1627 } 1628 sqlDB = sdb_p->sqlXactDB; 1629 sdb_p->sqlXactDB = NULL; /* no one else can get to this DB, 1630 * safe to unlock */ 1631 sdb_p->sqlXactThread = NULL; 1632 PR_ExitMonitor(sdb_p->dbMon); 1633 1634 sqlerr = sqlite3_prepare_v2(sqlDB, cmd, -1, &stmt, NULL); 1635 1636 do { 1637 sqlerr = sqlite3_step(stmt); 1638 if (sqlerr == SQLITE_BUSY) { 1639 PR_Sleep(SDB_BUSY_RETRY_TIME); 1640 } 1641 } while (!sdb_done(sqlerr, &retry)); 1642 1643 /* Pending BEGIN TRANSACTIONS Can move forward at this point. */ 1644 1645 if (stmt) { 1646 sqlite3_reset(stmt); 1647 sqlite3_finalize(stmt); 1648 } 1649 1650 /* we we have a cached DB image, update it as well */ 1651 if (sdb_p->cacheTable) { 1652 PR_EnterMonitor(sdb_p->dbMon); 1653 sdb_updateCache(sdb_p); 1654 PR_ExitMonitor(sdb_p->dbMon); 1655 } 1656 1657 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1658 1659 /* We just finished a transaction. 1660 * Free the database, and remove it from the list */ 1661 sqlite3_close(sqlDB); 1662 1663 return error; 1664 } 1665 1666 static const char COMMIT_CMD[] = "COMMIT TRANSACTION;"; 1667 CK_RV 1668 sdb_Commit(SDB *sdb) 1669 { 1670 CK_RV crv; 1671 LOCK_SQLITE() 1672 crv = sdb_complete(sdb, COMMIT_CMD); 1673 UNLOCK_SQLITE() 1674 return crv; 1675 } 1676 1677 static const char ROLLBACK_CMD[] = "ROLLBACK TRANSACTION;"; 1678 CK_RV 1679 sdb_Abort(SDB *sdb) 1680 { 1681 CK_RV crv; 1682 LOCK_SQLITE() 1683 crv = sdb_complete(sdb, ROLLBACK_CMD); 1684 UNLOCK_SQLITE() 1685 return crv; 1686 } 1687 1688 static int tableExists(sqlite3 *sqlDB, const char *tableName); 1689 1690 static const char GET_PW_CMD[] = "SELECT ALL * FROM metaData WHERE id=$ID;"; 1691 CK_RV 1692 sdb_GetMetaData(SDB *sdb, const char *id, SECItem *item1, SECItem *item2) 1693 { 1694 SDBPrivate *sdb_p = sdb->private; 1695 sqlite3 *sqlDB = NULL; 1696 sqlite3_stmt *stmt = NULL; 1697 int sqlerr = SQLITE_OK; 1698 CK_RV error = CKR_OK; 1699 int found = 0; 1700 int retry = 0; 1701 1702 LOCK_SQLITE() 1703 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1704 if (error != CKR_OK) { 1705 goto loser; 1706 } 1707 1708 /* handle 'test' versions of the sqlite db */ 1709 sqlerr = sqlite3_prepare_v2(sqlDB, GET_PW_CMD, -1, &stmt, NULL); 1710 /* Sigh, if we created a new table since we opened the database, 1711 * the database handle will not see the new table, we need to close this 1712 * database and reopen it. This is safe because we are holding the lock 1713 * still. */ 1714 if (sqlerr == SQLITE_SCHEMA) { 1715 sqlerr = sdb_reopenDBLocal(sdb_p, &sqlDB); 1716 if (sqlerr != SQLITE_OK) { 1717 goto loser; 1718 } 1719 sqlerr = sqlite3_prepare_v2(sqlDB, GET_PW_CMD, -1, &stmt, NULL); 1720 } 1721 if (sqlerr != SQLITE_OK) 1722 goto loser; 1723 sqlerr = sqlite3_bind_text(stmt, 1, id, PORT_Strlen(id), SQLITE_STATIC); 1724 do { 1725 sqlerr = sqlite3_step(stmt); 1726 if (sqlerr == SQLITE_BUSY) { 1727 PR_Sleep(SDB_BUSY_RETRY_TIME); 1728 } 1729 if (sqlerr == SQLITE_ROW) { 1730 const char *blobData; 1731 unsigned int len = item1->len; 1732 item1->len = sqlite3_column_bytes(stmt, 1); 1733 if (item1->len > len) { 1734 error = CKR_BUFFER_TOO_SMALL; 1735 continue; 1736 } 1737 blobData = sqlite3_column_blob(stmt, 1); 1738 PORT_Memcpy(item1->data, blobData, item1->len); 1739 if (item2) { 1740 len = item2->len; 1741 item2->len = sqlite3_column_bytes(stmt, 2); 1742 if (item2->len > len) { 1743 error = CKR_BUFFER_TOO_SMALL; 1744 continue; 1745 } 1746 blobData = sqlite3_column_blob(stmt, 2); 1747 PORT_Memcpy(item2->data, blobData, item2->len); 1748 } 1749 found = 1; 1750 } 1751 } while (!sdb_done(sqlerr, &retry)); 1752 1753 loser: 1754 /* fix up the error if necessary */ 1755 if (error == CKR_OK) { 1756 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1757 if (!found && error == CKR_OK) { 1758 error = CKR_OBJECT_HANDLE_INVALID; 1759 } 1760 } 1761 1762 if (stmt) { 1763 sqlite3_reset(stmt); 1764 sqlite3_finalize(stmt); 1765 } 1766 1767 if (sqlDB) { 1768 sdb_closeDBLocal(sdb_p, sqlDB); 1769 } 1770 UNLOCK_SQLITE() 1771 1772 return error; 1773 } 1774 1775 static const char PW_CREATE_TABLE_CMD[] = 1776 "CREATE TABLE metaData (id PRIMARY KEY UNIQUE ON CONFLICT REPLACE, item1, item2);"; 1777 static const char PW_CREATE_CMD[] = 1778 "INSERT INTO metaData (id,item1,item2) VALUES($ID,$ITEM1,$ITEM2);"; 1779 static const char MD_CREATE_CMD[] = 1780 "INSERT INTO metaData (id,item1) VALUES($ID,$ITEM1);"; 1781 1782 CK_RV 1783 sdb_PutMetaData(SDB *sdb, const char *id, const SECItem *item1, 1784 const SECItem *item2) 1785 { 1786 SDBPrivate *sdb_p = sdb->private; 1787 sqlite3 *sqlDB = sdb_p->sqlXactDB; 1788 sqlite3_stmt *stmt = NULL; 1789 int sqlerr = SQLITE_OK; 1790 CK_RV error = CKR_OK; 1791 int retry = 0; 1792 const char *cmd = PW_CREATE_CMD; 1793 1794 if ((sdb->sdb_flags & SDB_RDONLY) != 0) { 1795 return CKR_TOKEN_WRITE_PROTECTED; 1796 } 1797 1798 LOCK_SQLITE() 1799 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1800 if (error != CKR_OK) { 1801 goto loser; 1802 } 1803 1804 if (!tableExists(sqlDB, "metaData")) { 1805 sqlerr = sqlite3_exec(sqlDB, PW_CREATE_TABLE_CMD, NULL, 0, NULL); 1806 if (sqlerr != SQLITE_OK) 1807 goto loser; 1808 } 1809 if (item2 == NULL) { 1810 cmd = MD_CREATE_CMD; 1811 } 1812 sqlerr = sqlite3_prepare_v2(sqlDB, cmd, -1, &stmt, NULL); 1813 if (sqlerr != SQLITE_OK) 1814 goto loser; 1815 sqlerr = sqlite3_bind_text(stmt, 1, id, PORT_Strlen(id), SQLITE_STATIC); 1816 if (sqlerr != SQLITE_OK) 1817 goto loser; 1818 sqlerr = sqlite3_bind_blob(stmt, 2, item1->data, item1->len, SQLITE_STATIC); 1819 if (sqlerr != SQLITE_OK) 1820 goto loser; 1821 if (item2) { 1822 sqlerr = sqlite3_bind_blob(stmt, 3, item2->data, 1823 item2->len, SQLITE_STATIC); 1824 if (sqlerr != SQLITE_OK) 1825 goto loser; 1826 } 1827 1828 do { 1829 sqlerr = sqlite3_step(stmt); 1830 if (sqlerr == SQLITE_BUSY) { 1831 PR_Sleep(SDB_BUSY_RETRY_TIME); 1832 } 1833 } while (!sdb_done(sqlerr, &retry)); 1834 1835 loser: 1836 /* fix up the error if necessary */ 1837 if (error == CKR_OK) { 1838 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1839 } 1840 1841 if (stmt) { 1842 sqlite3_reset(stmt); 1843 sqlite3_finalize(stmt); 1844 } 1845 1846 if (sqlDB) { 1847 sdb_closeDBLocal(sdb_p, sqlDB); 1848 } 1849 UNLOCK_SQLITE() 1850 1851 return error; 1852 } 1853 1854 static const char RESET_CMD[] = "DELETE FROM %s;"; 1855 CK_RV 1856 sdb_Reset(SDB *sdb) 1857 { 1858 SDBPrivate *sdb_p = sdb->private; 1859 sqlite3 *sqlDB = NULL; 1860 char *newStr; 1861 int sqlerr = SQLITE_OK; 1862 CK_RV error = CKR_OK; 1863 1864 /* only Key databases can be reset */ 1865 if (sdb_p->type != SDB_KEY) { 1866 return CKR_OBJECT_HANDLE_INVALID; 1867 } 1868 1869 LOCK_SQLITE() 1870 error = sdb_openDBLocal(sdb_p, &sqlDB, NULL); 1871 if (error != CKR_OK) { 1872 goto loser; 1873 } 1874 1875 if (tableExists(sqlDB, sdb_p->table)) { 1876 /* delete the contents of the key table */ 1877 newStr = sqlite3_mprintf(RESET_CMD, sdb_p->table); 1878 if (newStr == NULL) { 1879 error = CKR_HOST_MEMORY; 1880 goto loser; 1881 } 1882 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 1883 sqlite3_free(newStr); 1884 1885 if (sqlerr != SQLITE_OK) 1886 goto loser; 1887 } 1888 1889 /* delete the password entry table */ 1890 sqlerr = sqlite3_exec(sqlDB, "DROP TABLE IF EXISTS metaData;", 1891 NULL, 0, NULL); 1892 1893 loser: 1894 /* fix up the error if necessary */ 1895 if (error == CKR_OK) { 1896 error = sdb_mapSQLError(sdb_p->type, sqlerr); 1897 } 1898 1899 if (sqlDB) { 1900 sdb_closeDBLocal(sdb_p, sqlDB); 1901 } 1902 1903 UNLOCK_SQLITE() 1904 return error; 1905 } 1906 1907 CK_RV 1908 sdb_Close(SDB *sdb) 1909 { 1910 SDBPrivate *sdb_p = sdb->private; 1911 int sqlerr = SQLITE_OK; 1912 sdbDataType type = sdb_p->type; 1913 1914 sqlerr = sqlite3_close(sdb_p->sqlReadDB); 1915 PORT_Free(sdb_p->sqlDBName); 1916 if (sdb_p->cacheTable) { 1917 sqlite3_free(sdb_p->cacheTable); 1918 } 1919 if (sdb_p->dbMon) { 1920 PR_DestroyMonitor(sdb_p->dbMon); 1921 } 1922 free(sdb_p->schemaAttrs); 1923 free(sdb_p); 1924 free(sdb); 1925 return sdb_mapSQLError(type, sqlerr); 1926 } 1927 1928 /* 1929 * functions to support open 1930 */ 1931 1932 static const char CHECK_TABLE_CMD[] = "SELECT ALL * FROM %s LIMIT 0;"; 1933 1934 /* return 1 if sqlDB contains table 'tableName */ 1935 static int 1936 tableExists(sqlite3 *sqlDB, const char *tableName) 1937 { 1938 char *cmd = sqlite3_mprintf(CHECK_TABLE_CMD, tableName); 1939 int sqlerr = SQLITE_OK; 1940 1941 if (cmd == NULL) { 1942 return 0; 1943 } 1944 1945 sqlerr = sqlite3_exec(sqlDB, cmd, NULL, 0, 0); 1946 sqlite3_free(cmd); 1947 1948 return (sqlerr == SQLITE_OK) ? 1 : 0; 1949 } 1950 1951 void 1952 sdb_SetForkState(PRBool forked) 1953 { 1954 /* XXXright now this is a no-op. The global fork state in the softokn3 1955 * shared library is already taken care of at the PKCS#11 level. 1956 * If and when we add fork state to the sqlite shared library and extern 1957 * interface, we will need to set it and reset it from here */ 1958 } 1959 1960 static int 1961 sdb_attributeComparator(const void *a, const void *b) 1962 { 1963 if (*(CK_ATTRIBUTE_TYPE *)a < *(CK_ATTRIBUTE_TYPE *)b) { 1964 return -1; 1965 } 1966 if (*(CK_ATTRIBUTE_TYPE *)a > *(CK_ATTRIBUTE_TYPE *)b) { 1967 return 1; 1968 } 1969 return 0; 1970 } 1971 1972 static const char ADD_COLUMN_CMD[] = "ALTER TABLE %s ADD COLUMN %s"; 1973 static CK_RV 1974 sdb_add_column(sqlite3 *sqlDB, const char *table, sdbDataType type, 1975 const char *typeString) 1976 { 1977 char *newStr = sqlite3_mprintf(ADD_COLUMN_CMD, table, typeString); 1978 int sqlerr; 1979 1980 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 1981 sqlite3_free(newStr); 1982 if (sqlerr != SQLITE_OK) { 1983 return sdb_mapSQLError(type, sqlerr); 1984 } 1985 return CKR_OK; 1986 } 1987 1988 static const char COLUMN_QUERY_CMD[] = 1989 "SELECT * FROM %s"; 1990 /* 1991 * if our current database does not have all the attributes in the columns, 1992 * we need to add those columns or attempts to add objects with those 1993 * attributes will fail. We only need this on R/W databases because we only 1994 * add objects to R/W databases. 1995 */ 1996 static CK_RV 1997 sdb_update_column(sqlite3 *sqlDB, const char *table, sdbDataType type) 1998 { 1999 char *newStr = sqlite3_mprintf(COLUMN_QUERY_CMD, table); 2000 sqlite3_stmt *stmt; 2001 int columnCount; 2002 int sqlerr; 2003 CK_RV error; 2004 2005 if (!newStr) { 2006 return CKR_HOST_MEMORY; 2007 } 2008 2009 sqlerr = sqlite3_prepare_v2(sqlDB, newStr, -1, &stmt, NULL); 2010 sqlite3_free(newStr); 2011 if (sqlerr != SQLITE_OK) { 2012 return sdb_mapSQLError(type, sqlerr); 2013 } 2014 2015 columnCount = sqlite3_column_count(stmt); 2016 /* columns include the first column, which is id, which is not 2017 * and attribute. check to make sure we have at least as many attributes 2018 * as there are id in out list. This assumes we never add some 2019 * attributes in some NSS version and not others, which is generally 2020 * true. */ 2021 if (columnCount >= sftkdb_known_attributes_size + 1) { 2022 sqlite3_finalize(stmt); 2023 return CKR_OK; 2024 } 2025 /* we have more attributes than in the database, so we know things 2026 * are missing, find what was missing */ 2027 for (size_t i = 0; i < sftkdb_known_attributes_size; i++) { 2028 char *typeString = sqlite3_mprintf("a%lx", sftkdb_known_attributes[i]); 2029 PRBool found = PR_FALSE; 2030 /* this one index is important, we skip the first column (id), since 2031 * it will never match, starting at zero isn't a bug, 2032 * just inefficient */ 2033 for (int j = 1; j < columnCount; j++) { 2034 const char *columnName = sqlite3_column_name(stmt, j); 2035 if (columnName == NULL) { 2036 sqlite3_free(typeString); 2037 sqlite3_finalize(stmt); 2038 /* if we couldnt' get the colmun name, it's only because 2039 * we couldn't get the memory */ 2040 return CKR_HOST_MEMORY; 2041 } 2042 if (PORT_Strcmp(typeString, columnName) == 0) { 2043 /* we found this one, no need to add it */ 2044 found = PR_TRUE; 2045 break; 2046 } 2047 } 2048 if (found) { 2049 sqlite3_free(typeString); 2050 continue; 2051 } 2052 /* we didn't find the attribute, so now add it */ 2053 error = sdb_add_column(sqlDB, table, type, typeString); 2054 if (error != CKR_OK) { 2055 sqlite3_free(typeString); 2056 sqlite3_finalize(stmt); 2057 return error; 2058 } 2059 sqlite3_free(typeString); 2060 } 2061 sqlite3_finalize(stmt); 2062 return CKR_OK; 2063 } 2064 2065 /* 2066 * initialize a single database 2067 */ 2068 static const char INIT_CMD[] = 2069 "CREATE TABLE %s (id PRIMARY KEY UNIQUE ON CONFLICT ABORT%s)"; 2070 2071 CK_RV 2072 sdb_init(char *dbname, char *table, sdbDataType type, int *inUpdate, 2073 int *newInit, int inFlags, PRUint32 accessOps, SDB **pSdb) 2074 { 2075 char *initStr = NULL; 2076 char *newStr; 2077 char *queryStr = NULL; 2078 int inTransaction = 0; 2079 SDB *sdb = NULL; 2080 SDBPrivate *sdb_p = NULL; 2081 sqlite3 *sqlDB = NULL; 2082 int sqlerr = SQLITE_OK; 2083 CK_RV error = CKR_OK; 2084 char *cacheTable = NULL; 2085 PRIntervalTime now = 0; 2086 char *env; 2087 PRBool enableCache = PR_FALSE; 2088 PRBool checkFSType = PR_FALSE; 2089 PRBool measureSpeed = PR_FALSE; 2090 PRBool create; 2091 int flags = inFlags & 0x7; 2092 2093 *pSdb = NULL; 2094 *inUpdate = 0; 2095 2096 /* sqlite3 doesn't have a flag to specify that we want to 2097 * open the database read only. If the db doesn't exist, 2098 * sqlite3 will always create it. 2099 */ 2100 LOCK_SQLITE(); 2101 create = (_NSSUTIL_Access(dbname, PR_ACCESS_EXISTS) != PR_SUCCESS); 2102 if ((flags == SDB_RDONLY) && create) { 2103 error = sdb_mapSQLError(type, SQLITE_CANTOPEN); 2104 goto loser; 2105 } 2106 sqlerr = sdb_openDB(dbname, &sqlDB, flags); 2107 if (sqlerr != SQLITE_OK) { 2108 error = sdb_mapSQLError(type, sqlerr); 2109 goto loser; 2110 } 2111 2112 /* 2113 * SQL created the file, but it doesn't set appropriate modes for 2114 * a database. 2115 * 2116 * NO NSPR call for chmod? :( 2117 */ 2118 if (create && sdb_chmod(dbname, 0600) != 0) { 2119 error = sdb_mapSQLError(type, SQLITE_CANTOPEN); 2120 goto loser; 2121 } 2122 2123 if (flags != SDB_RDONLY) { 2124 sqlerr = sqlite3_exec(sqlDB, BEGIN_CMD, NULL, 0, NULL); 2125 if (sqlerr != SQLITE_OK) { 2126 error = sdb_mapSQLError(type, sqlerr); 2127 goto loser; 2128 } 2129 inTransaction = 1; 2130 } 2131 if (!tableExists(sqlDB, table)) { 2132 *newInit = 1; 2133 if (flags != SDB_CREATE) { 2134 error = sdb_mapSQLError(type, SQLITE_CANTOPEN); 2135 goto loser; 2136 } 2137 initStr = sqlite3_mprintf(""); 2138 for (size_t i = 0; initStr && i < sftkdb_known_attributes_size; i++) { 2139 newStr = sqlite3_mprintf("%s, a%lx", initStr, 2140 sftkdb_known_attributes[i]); 2141 sqlite3_free(initStr); 2142 initStr = newStr; 2143 } 2144 if (initStr == NULL) { 2145 error = CKR_HOST_MEMORY; 2146 goto loser; 2147 } 2148 2149 newStr = sqlite3_mprintf(INIT_CMD, table, initStr); 2150 sqlite3_free(initStr); 2151 if (newStr == NULL) { 2152 error = CKR_HOST_MEMORY; 2153 goto loser; 2154 } 2155 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 2156 sqlite3_free(newStr); 2157 if (sqlerr != SQLITE_OK) { 2158 error = sdb_mapSQLError(type, sqlerr); 2159 goto loser; 2160 } 2161 2162 newStr = sqlite3_mprintf(CREATE_ISSUER_INDEX_CMD, table); 2163 if (newStr == NULL) { 2164 error = CKR_HOST_MEMORY; 2165 goto loser; 2166 } 2167 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 2168 sqlite3_free(newStr); 2169 if (sqlerr != SQLITE_OK) { 2170 error = sdb_mapSQLError(type, sqlerr); 2171 goto loser; 2172 } 2173 2174 newStr = sqlite3_mprintf(CREATE_SUBJECT_INDEX_CMD, table); 2175 if (newStr == NULL) { 2176 error = CKR_HOST_MEMORY; 2177 goto loser; 2178 } 2179 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 2180 sqlite3_free(newStr); 2181 if (sqlerr != SQLITE_OK) { 2182 error = sdb_mapSQLError(type, sqlerr); 2183 goto loser; 2184 } 2185 2186 newStr = sqlite3_mprintf(CREATE_LABEL_INDEX_CMD, table); 2187 if (newStr == NULL) { 2188 error = CKR_HOST_MEMORY; 2189 goto loser; 2190 } 2191 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 2192 sqlite3_free(newStr); 2193 if (sqlerr != SQLITE_OK) { 2194 error = sdb_mapSQLError(type, sqlerr); 2195 goto loser; 2196 } 2197 2198 newStr = sqlite3_mprintf(CREATE_ID_INDEX_CMD, table); 2199 if (newStr == NULL) { 2200 error = CKR_HOST_MEMORY; 2201 goto loser; 2202 } 2203 sqlerr = sqlite3_exec(sqlDB, newStr, NULL, 0, NULL); 2204 sqlite3_free(newStr); 2205 if (sqlerr != SQLITE_OK) { 2206 error = sdb_mapSQLError(type, sqlerr); 2207 goto loser; 2208 } 2209 } else if (flags != SDB_RDONLY) { 2210 /* check to see if we need to update the scheme, only need to 2211 * do this if we open r/w, since that's the only case where 2212 * it's a problem if the attribute colmumn are missing */ 2213 error = sdb_update_column(sqlDB, table, type); 2214 if (error != CKR_OK) { 2215 goto loser; 2216 } 2217 } 2218 2219 /* 2220 * detect the case where we have created the database, but have 2221 * not yet updated it. 2222 * 2223 * We only check the Key database because only the key database has 2224 * a metaData table. The metaData table is created when a password 2225 * is set, or in the case of update, when a password is supplied. 2226 * If no key database exists, then the update would have happened immediately 2227 * on noticing that the cert database didn't exist (see newInit set above). 2228 */ 2229 if (type == SDB_KEY && !tableExists(sqlDB, "metaData")) { 2230 *newInit = 1; 2231 } 2232 2233 /* access to network filesystems are significantly slower than local ones 2234 * for database operations. In those cases we need to create a cached copy 2235 * of the database in a temporary location on the local disk. SQLITE 2236 * already provides a way to create a temporary table and initialize it, 2237 * so we use it for the cache (see sdb_buildCache for how it's done).*/ 2238 2239 /* 2240 * we decide whether or not to use the cache based on the following input. 2241 * 2242 * NSS_SDB_USE_CACHE environment variable is set to anything other than 2243 * "yes" or "no" (for instance, "auto"): NSS will measure the performance 2244 * of access to the temp database versus the access to the user's 2245 * passed-in database location. If the temp database location is 2246 * "significantly" faster we will use the cache. 2247 * 2248 * NSS_SDB_USE_CACHE environment variable is nonexistent or set to "no": 2249 * cache will not be used. 2250 * 2251 * NSS_SDB_USE_CACHE environment variable is set to "yes": cache will 2252 * always be used. 2253 * 2254 * It is expected that most applications will not need this feature, and 2255 * thus it is disabled by default. 2256 */ 2257 2258 env = PR_GetEnvSecure("NSS_SDB_USE_CACHE"); 2259 2260 /* Variables enableCache, checkFSType, measureSpeed are PR_FALSE by default, 2261 * which is the expected behavior for NSS_SDB_USE_CACHE="no". 2262 * We don't need to check for "no" here. */ 2263 if (!env) { 2264 /* By default, with no variable set, we avoid expensive measuring for 2265 * most FS types. We start with inexpensive FS type checking, and 2266 * might perform measuring for some types. */ 2267 checkFSType = PR_TRUE; 2268 } else if (PORT_Strcasecmp(env, "yes") == 0) { 2269 enableCache = PR_TRUE; 2270 } else if (PORT_Strcasecmp(env, "no") != 0) { /* not "no" => "auto" */ 2271 measureSpeed = PR_TRUE; 2272 } 2273 2274 if (checkFSType) { 2275 #if defined(LINUX) && !defined(ANDROID) 2276 struct statfs statfs_s; 2277 if (statfs(dbname, &statfs_s) == 0) { 2278 switch (statfs_s.f_type) { 2279 case SMB_SUPER_MAGIC: 2280 case 0xff534d42: /* CIFS_MAGIC_NUMBER */ 2281 case NFS_SUPER_MAGIC: 2282 /* We assume these are slow. */ 2283 enableCache = PR_TRUE; 2284 break; 2285 case CODA_SUPER_MAGIC: 2286 case 0x65735546: /* FUSE_SUPER_MAGIC */ 2287 case NCP_SUPER_MAGIC: 2288 /* It's uncertain if this FS is fast or slow. 2289 * It seems reasonable to perform slow measuring for users 2290 * with questionable FS speed. */ 2291 measureSpeed = PR_TRUE; 2292 break; 2293 case AFS_SUPER_MAGIC: /* Already implements caching. */ 2294 default: 2295 break; 2296 } 2297 } 2298 #endif 2299 } 2300 2301 if (measureSpeed) { 2302 char *tempDir = NULL; 2303 PRUint32 tempOps = 0; 2304 /* 2305 * Use PR_Access to determine how expensive it 2306 * is to check for the existance of a local file compared to the same 2307 * check in the temp directory. If the temp directory is faster, cache 2308 * the database there. */ 2309 tempDir = sdb_getTempDir(sqlDB); 2310 if (tempDir) { 2311 tempOps = sdb_measureAccess(tempDir); 2312 PORT_Free(tempDir); 2313 2314 /* There is a cost to continually copying the database. 2315 * Account for that cost with the arbitrary factor of 10 */ 2316 enableCache = (PRBool)(tempOps > accessOps * 10); 2317 } 2318 } 2319 2320 if (enableCache) { 2321 /* try to set the temp store to memory.*/ 2322 sqlite3_exec(sqlDB, "PRAGMA temp_store=MEMORY", NULL, 0, NULL); 2323 /* Failure to set the temp store to memory is not fatal, 2324 * ignore the error */ 2325 2326 cacheTable = sqlite3_mprintf("%sCache", table); 2327 if (cacheTable == NULL) { 2328 error = CKR_HOST_MEMORY; 2329 goto loser; 2330 } 2331 /* build the cache table */ 2332 error = sdb_buildCache(sqlDB, type, cacheTable, table); 2333 if (error != CKR_OK) { 2334 goto loser; 2335 } 2336 /* initialize the last cache build time */ 2337 now = PR_IntervalNow(); 2338 } 2339 2340 sdb = (SDB *)malloc(sizeof(SDB)); 2341 if (!sdb) { 2342 error = CKR_HOST_MEMORY; 2343 goto loser; 2344 } 2345 sdb_p = (SDBPrivate *)malloc(sizeof(SDBPrivate)); 2346 if (!sdb_p) { 2347 error = CKR_HOST_MEMORY; 2348 goto loser; 2349 } 2350 2351 /* Cache the attributes that are held in the table, so we can later check 2352 * that queried attributes actually exist. We don't assume the schema 2353 * to be exactly |sftkdb_known_attributes|, as it may change over time. */ 2354 sdb_p->schemaAttrs = NULL; 2355 if (!PORT_Strcmp("nssPublic", table) || 2356 !PORT_Strcmp("nssPrivate", table)) { 2357 sqlite3_stmt *stmt = NULL; 2358 int retry = 0; 2359 unsigned int backedAttrs = 0; 2360 2361 /* Can't bind parameters to a PRAGMA. */ 2362 queryStr = sqlite3_mprintf("PRAGMA table_info(%s);", table); 2363 if (queryStr == NULL) { 2364 error = CKR_HOST_MEMORY; 2365 goto loser; 2366 } 2367 sqlerr = sqlite3_prepare_v2(sqlDB, queryStr, -1, &stmt, NULL); 2368 sqlite3_free(queryStr); 2369 queryStr = NULL; 2370 if (sqlerr != SQLITE_OK) { 2371 goto loser; 2372 } 2373 unsigned int schemaAttrsCapacity = sftkdb_known_attributes_size; 2374 sdb_p->schemaAttrs = malloc(schemaAttrsCapacity * sizeof(CK_ATTRIBUTE_TYPE)); 2375 if (!sdb_p->schemaAttrs) { 2376 error = CKR_HOST_MEMORY; 2377 goto loser; 2378 } 2379 do { 2380 sqlerr = sqlite3_step(stmt); 2381 if (sqlerr == SQLITE_BUSY) { 2382 PR_Sleep(SDB_BUSY_RETRY_TIME); 2383 } 2384 if (sqlerr == SQLITE_ROW) { 2385 if (backedAttrs == schemaAttrsCapacity) { 2386 schemaAttrsCapacity += sftkdb_known_attributes_size; 2387 sdb_p->schemaAttrs = realloc(sdb_p->schemaAttrs, 2388 schemaAttrsCapacity * sizeof(CK_ATTRIBUTE_TYPE)); 2389 if (!sdb_p->schemaAttrs) { 2390 error = CKR_HOST_MEMORY; 2391 goto loser; 2392 } 2393 } 2394 /* Record the ULONG attribute value. */ 2395 char *val = (char *)sqlite3_column_text(stmt, 1); 2396 if (val && val[0] == 'a') { 2397 CK_ATTRIBUTE_TYPE attr = strtoul(&val[1], NULL, 16); 2398 sdb_p->schemaAttrs[backedAttrs++] = attr; 2399 } 2400 } 2401 } while (!sdb_done(sqlerr, &retry)); 2402 2403 if (sqlerr != SQLITE_DONE) { 2404 goto loser; 2405 } 2406 sqlerr = sqlite3_reset(stmt); 2407 if (sqlerr != SQLITE_OK) { 2408 goto loser; 2409 } 2410 sqlerr = sqlite3_finalize(stmt); 2411 if (sqlerr != SQLITE_OK) { 2412 goto loser; 2413 } 2414 2415 sdb_p->numSchemaAttrs = backedAttrs; 2416 2417 /* Sort these once so we can shortcut invalid attribute searches. */ 2418 qsort(sdb_p->schemaAttrs, sdb_p->numSchemaAttrs, 2419 sizeof(CK_ATTRIBUTE_TYPE), sdb_attributeComparator); 2420 } 2421 2422 /* invariant fields */ 2423 sdb_p->sqlDBName = PORT_Strdup(dbname); 2424 sdb_p->type = type; 2425 sdb_p->table = table; 2426 sdb_p->cacheTable = cacheTable; 2427 sdb_p->lastUpdateTime = now; 2428 /* set the cache delay time. This is how long we will wait before we 2429 * decide the existing cache is stale. Currently set to 10 sec */ 2430 sdb_p->updateInterval = PR_SecondsToInterval(10); 2431 sdb_p->dbMon = PR_NewMonitor(); 2432 /* these fields are protected by the lock */ 2433 sdb_p->sqlXactDB = NULL; 2434 sdb_p->sqlXactThread = NULL; 2435 sdb->private = sdb_p; 2436 sdb->version = 1; 2437 sdb->sdb_flags = inFlags | SDB_HAS_META; 2438 sdb->app_private = NULL; 2439 sdb->sdb_FindObjectsInit = sdb_FindObjectsInit; 2440 sdb->sdb_FindObjects = sdb_FindObjects; 2441 sdb->sdb_FindObjectsFinal = sdb_FindObjectsFinal; 2442 sdb->sdb_GetAttributeValue = sdb_GetAttributeValue; 2443 sdb->sdb_SetAttributeValue = sdb_SetAttributeValue; 2444 sdb->sdb_CreateObject = sdb_CreateObject; 2445 sdb->sdb_DestroyObject = sdb_DestroyObject; 2446 sdb->sdb_GetMetaData = sdb_GetMetaData; 2447 sdb->sdb_PutMetaData = sdb_PutMetaData; 2448 sdb->sdb_DestroyMetaData = sdb_DestroyMetaData; 2449 sdb->sdb_Begin = sdb_Begin; 2450 sdb->sdb_Commit = sdb_Commit; 2451 sdb->sdb_Abort = sdb_Abort; 2452 sdb->sdb_Reset = sdb_Reset; 2453 sdb->sdb_Close = sdb_Close; 2454 sdb->sdb_SetForkState = sdb_SetForkState; 2455 sdb->sdb_GetNewObjectID = sdb_GetNewObjectID; 2456 2457 if (inTransaction) { 2458 sqlerr = sqlite3_exec(sqlDB, COMMIT_CMD, NULL, 0, NULL); 2459 if (sqlerr != SQLITE_OK) { 2460 error = sdb_mapSQLError(sdb_p->type, sqlerr); 2461 goto loser; 2462 } 2463 inTransaction = 0; 2464 } 2465 2466 sdb_p->sqlReadDB = sqlDB; 2467 2468 *pSdb = sdb; 2469 UNLOCK_SQLITE(); 2470 return CKR_OK; 2471 2472 loser: 2473 /* lots of stuff to do */ 2474 if (inTransaction) { 2475 sqlite3_exec(sqlDB, ROLLBACK_CMD, NULL, 0, NULL); 2476 } 2477 if (sdb) { 2478 free(sdb); 2479 } 2480 if (sdb_p) { 2481 if (sdb_p->schemaAttrs) { 2482 free(sdb_p->schemaAttrs); 2483 } 2484 free(sdb_p); 2485 } 2486 if (sqlDB) { 2487 sqlite3_close(sqlDB); 2488 } 2489 UNLOCK_SQLITE(); 2490 return error; 2491 } 2492 2493 /* sdbopen */ 2494 CK_RV 2495 s_open(const char *directory, const char *certPrefix, const char *keyPrefix, 2496 int cert_version, int key_version, int flags, 2497 SDB **certdb, SDB **keydb, int *newInit) 2498 { 2499 char *cert = sdb_BuildFileName(directory, certPrefix, 2500 "cert", cert_version); 2501 char *key = sdb_BuildFileName(directory, keyPrefix, 2502 "key", key_version); 2503 CK_RV error = CKR_OK; 2504 int inUpdate; 2505 PRUint32 accessOps; 2506 2507 if (certdb) 2508 *certdb = NULL; 2509 if (keydb) 2510 *keydb = NULL; 2511 *newInit = 0; 2512 2513 #ifdef SQLITE_UNSAFE_THREADS 2514 if (sqlite_lock == NULL) { 2515 sqlite_lock = PR_NewLock(); 2516 if (sqlite_lock == NULL) { 2517 error = CKR_HOST_MEMORY; 2518 goto loser; 2519 } 2520 } 2521 #endif 2522 2523 /* how long does it take to test for a non-existant file in our working 2524 * directory? Allows us to test if we may be on a network file system */ 2525 accessOps = 1; 2526 { 2527 char *env; 2528 env = PR_GetEnvSecure("NSS_SDB_USE_CACHE"); 2529 /* If the environment variable is undefined or set to yes or no, 2530 * sdb_init() will ignore the value of accessOps, and we can skip the 2531 * measuring.*/ 2532 if (env && PORT_Strcasecmp(env, "no") != 0 && 2533 PORT_Strcasecmp(env, "yes") != 0) { 2534 accessOps = sdb_measureAccess(directory); 2535 } 2536 } 2537 2538 /* 2539 * open the cert data base 2540 */ 2541 if (certdb) { 2542 /* initialize Certificate database */ 2543 error = sdb_init(cert, "nssPublic", SDB_CERT, &inUpdate, 2544 newInit, flags, accessOps, certdb); 2545 if (error != CKR_OK) { 2546 goto loser; 2547 } 2548 } 2549 2550 /* 2551 * open the key data base: 2552 * NOTE:if we want to implement a single database, we open 2553 * the same database file as the certificate here. 2554 * 2555 * cert an key db's have different tables, so they will not 2556 * conflict. 2557 */ 2558 if (keydb) { 2559 /* initialize the Key database */ 2560 error = sdb_init(key, "nssPrivate", SDB_KEY, &inUpdate, 2561 newInit, flags, accessOps, keydb); 2562 if (error != CKR_OK) { 2563 goto loser; 2564 } 2565 } 2566 2567 loser: 2568 if (cert) { 2569 sqlite3_free(cert); 2570 } 2571 if (key) { 2572 sqlite3_free(key); 2573 } 2574 2575 if (error != CKR_OK) { 2576 /* currently redundant, but could be necessary if more code is added 2577 * just before loser */ 2578 if (keydb && *keydb) { 2579 sdb_Close(*keydb); 2580 } 2581 if (certdb && *certdb) { 2582 sdb_Close(*certdb); 2583 } 2584 } 2585 2586 return error; 2587 } 2588 2589 CK_RV 2590 s_shutdown() 2591 { 2592 #ifdef SQLITE_UNSAFE_THREADS 2593 if (sqlite_lock) { 2594 PR_DestroyLock(sqlite_lock); 2595 sqlite_lock = NULL; 2596 } 2597 #endif 2598 return CKR_OK; 2599 }