1 // Copyright 2014 The Chromium Authors 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 "crypto/scoped_test_nss_db.h" 6 7 #include <cert.h> 8 9 #include "base/logging.h" 10 #include "base/threading/thread_restrictions.h" 11 #include "crypto/nss_util.h" 12 #include "crypto/nss_util_internal.h" 13 14 namespace crypto { 15 ScopedTestNSSDB()16ScopedTestNSSDB::ScopedTestNSSDB() { 17 EnsureNSSInit(); 18 // NSS is allowed to do IO on the current thread since dispatching 19 // to a dedicated thread would still have the affect of blocking 20 // the current thread, due to NSS's internal locking requirements 21 base::ScopedAllowBlockingForTesting allow_blocking; 22 23 if (!temp_dir_.CreateUniqueTempDir()) 24 return; 25 26 const char kTestDescription[] = "Test DB"; 27 slot_ = OpenSoftwareNSSDB(temp_dir_.GetPath(), kTestDescription); 28 } 29 ~ScopedTestNSSDB()30ScopedTestNSSDB::~ScopedTestNSSDB() { 31 // Remove trust from any certs in the test DB before closing it. Otherwise NSS 32 // may cache verification results even after the test DB is gone. 33 RemoveTrustFromAllCerts(); 34 35 // NSS is allowed to do IO on the current thread since dispatching 36 // to a dedicated thread would still have the affect of blocking 37 // the current thread, due to NSS's internal locking requirements 38 base::ScopedAllowBlockingForTesting allow_blocking; 39 40 if (slot_) { 41 SECStatus status = CloseSoftwareNSSDB(slot_.get()); 42 if (status != SECSuccess) 43 PLOG(ERROR) << "CloseSoftwareNSSDB failed: " << PORT_GetError(); 44 } 45 46 if (!temp_dir_.Delete()) 47 LOG(ERROR) << "Could not delete temporary directory."; 48 } 49 RemoveTrustFromAllCerts()50void ScopedTestNSSDB::RemoveTrustFromAllCerts() { 51 if (!slot_) 52 return; 53 54 ScopedCERTCertList cert_list(PK11_ListCertsInSlot(slot_.get())); 55 if (!cert_list) 56 return; 57 58 for (CERTCertListNode* node = CERT_LIST_HEAD(cert_list); 59 !CERT_LIST_END(node, cert_list); node = CERT_LIST_NEXT(node)) { 60 CERTCertTrust trust = {0}; 61 if (CERT_ChangeCertTrust(CERT_GetDefaultCertDB(), node->cert, &trust) != 62 SECSuccess) { 63 LOG(ERROR) << "CERT_ChangeCertTrust failed: " << PORT_GetError(); 64 } 65 } 66 } 67 68 } // namespace crypto 69