X-Git-Url: https://git.saurik.com/apple/security.git/blobdiff_plain/5c19dc3ae3bd8e40a9c028b0deddd50ff337692c..02b2aca600d4a0fe6fb259262bd6808ef889acde:/OSX/libsecurity_keychain/lib/Trust.cpp diff --git a/OSX/libsecurity_keychain/lib/Trust.cpp b/OSX/libsecurity_keychain/lib/Trust.cpp index c1514284..ae9d4ee3 100644 --- a/OSX/libsecurity_keychain/lib/Trust.cpp +++ b/OSX/libsecurity_keychain/lib/Trust.cpp @@ -35,6 +35,7 @@ #include "TrustAdditions.h" #include "TrustKeychains.h" #include +#include using namespace Security; @@ -65,29 +66,6 @@ ModuleNexus Trust::gStore; #pragma mark -- TrustKeychains -- -static const CSSM_DL_DB_HANDLE nullCSSMDLDBHandle = {0,}; -// -// TrustKeychains maintains a global reference to standard system keychains, -// to avoid having them be opened anew for each Trust instance. -// -class TrustKeychains -{ -public: - TrustKeychains(); - ~TrustKeychains() {} - CSSM_DL_DB_HANDLE rootStoreHandle() { return mRootStoreHandle; } - CSSM_DL_DB_HANDLE systemKcHandle() { return mSystem ? mSystem->database()->handle() : nullCSSMDLDBHandle; } - Keychain &systemKc() { return mSystem; } - Keychain &rootStore() { return *mRootStore; } - -private: - DL* mRootStoreDL; - Db* mRootStoreDb; - Keychain* mRootStore; - CSSM_DL_DB_HANDLE mRootStoreHandle; - Keychain mSystem; -}; - // // Singleton maintaining open references to standard system keychains, // to avoid having them be opened anew every time SecTrust is used. @@ -102,19 +80,35 @@ TrustKeychains::TrustKeychains() : mRootStoreHandle(nullCSSMDLDBHandle), mSystem(globals().storageManager.make(ADMIN_CERT_STORE_PATH, false)) { - if (GetServerMode()) // in server mode? Don't make a keychain for the root store + if (GetServerMode()) // in server mode? Don't go through StorageManager to make a keychain { - mRootStoreDL = new DL(gGuidAppleFileDL), - mRootStoreDb = new Db(*mRootStoreDL, SYSTEM_ROOT_STORE_PATH), - (*mRootStoreDb)->activate(); - mRootStoreHandle = (*mRootStoreDb)->handle(); + mRootStoreDL = new DL(gGuidAppleFileDL); + mRootStoreDb = new Db(*mRootStoreDL, SYSTEM_ROOT_STORE_PATH); + mRootStore = new Keychain(*mRootStoreDb); } else { + mRootStoreDL = NULL; + mRootStoreDb = NULL; mRootStore = new Keychain(globals().storageManager.make(SYSTEM_ROOT_STORE_PATH, false)); - (*mRootStore)->database()->activate(); - mRootStoreHandle = (*mRootStore)->database()->handle(); } + (*mRootStore)->database()->activate(); + mRootStoreHandle = (*mRootStore)->database()->handle(); +} + +TrustKeychains::~TrustKeychains() { + if(mRootStoreDL) { + delete mRootStoreDL; + mRootStoreDL = NULL; + } + if(mRootStoreDb) { + delete mRootStoreDb; + mRootStoreDb = NULL; + } + if(mRootStore) { + delete mRootStore; + mRootStore = NULL; + } } RecursiveMutex& SecTrustKeychainsGetMutex() @@ -244,11 +238,11 @@ void Trust::evaluate(bool disableEV) } CFArrayRef filteredCerts = NULL; if (isEVCandidate) { - secdebug("evTrust", "Trust::evaluate() certificate is EV candidate"); + secinfo("evTrust", "Trust::evaluate() certificate is EV candidate"); filteredCerts = potentialEVChainWithCertificates(mCerts); mCerts = filteredCerts; } else { - secdebug("evTrust", "Trust::evaluate() performing standard evaluation"); + secinfo("evTrust", "Trust::evaluate() performing standard evaluation"); if (mCerts) { filteredCerts = CFArrayCreateMutableCopy(NULL, 0, mCerts); } @@ -268,7 +262,7 @@ void Trust::evaluate(bool disableEV) if (mAllowedAnchors) { - secdebug("trusteval", "Trust::evaluate: anchors: %ld", CFArrayGetCount(mAllowedAnchors)); + secinfo("trusteval", "Trust::evaluate: anchors: %ld", CFArrayGetCount(mAllowedAnchors)); #if !defined(NDEBUG) CFArrayApplyFunction(mAllowedAnchors, CFRangeMake(0, CFArrayGetCount(mAllowedAnchors)), showCertSKID, NULL); #endif @@ -349,7 +343,7 @@ void Trust::evaluate(bool disableEV) allPolicies = convertRevocationPolicy(numRevocationAdded, context.allocator); if (allPolicies) { // caller has explicitly set the revocation policy they want to use - secdebug("evTrust", "Trust::evaluate() using explicit revocation policy (%d)", + secinfo("evTrust", "Trust::evaluate() using explicit revocation policy (%d)", numRevocationAdded); if (numRevocationAdded == 0) isEVCandidate = false; @@ -358,13 +352,13 @@ void Trust::evaluate(bool disableEV) // caller explicitly provided empty anchors and no keychain list, // and did not explicitly specify the revocation policy; // override global revocation check setting for this evaluation - secdebug("evTrust", "Trust::evaluate() has empty anchors and no keychains"); + secinfo("evTrust", "Trust::evaluate() has empty anchors and no keychains"); allPolicies = NULL; // use only mPolicies isEVCandidate = false; } else if (isEVCandidate || requirePerCert) { // force revocation checking for this evaluation - secdebug("evTrust", "Trust::evaluate() forcing OCSP/CRL revocation check"); + secinfo("evTrust", "Trust::evaluate() forcing OCSP/CRL revocation check"); allPolicies = forceRevocationPolicies(true, requirePerCert, numRevocationAdded, context.allocator, requirePerCert); } @@ -375,7 +369,7 @@ void Trust::evaluate(bool disableEV) } if (allPolicies == NULL) { // use mPolicies; no revocation checking will be performed - secdebug("evTrust", "Trust::evaluate() will not perform revocation check"); + secinfo("evTrust", "Trust::evaluate() will not perform revocation check"); CFIndex numPolicies = CFArrayGetCount(mPolicies); CFAllocatorRef allocator = CFGetAllocator(mPolicies); allPolicies = CFArrayCreateMutableCopy(allocator, numPolicies, mPolicies); @@ -396,14 +390,14 @@ void Trust::evaluate(bool disableEV) // no anchor certificates were provided; // built-in anchors will be trusted unless explicitly disabled. mUsingTrustSettings = (mAnchorPolicy < useAnchorsOnly); - secdebug("userTrust", "Trust::evaluate() %s", + secinfo("userTrust", "Trust::evaluate() %s", (mUsingTrustSettings) ? "using UserTrust" : "has no trusted anchors!"); } else { // anchor certificates were provided; // built-in anchors will NOT also be trusted unless explicitly enabled. mUsingTrustSettings = (mAnchorPolicy == useAnchorsAndBuiltIns); - secdebug("userTrust", "Trust::evaluate() using %s %s anchors", + secinfo("userTrust", "Trust::evaluate() using %s %s anchors", (mUsingTrustSettings) ? "UserTrust AND" : "only", (isEVCandidate) ? "EV" : "caller"); context.anchors(roots, roots); @@ -486,7 +480,7 @@ void Trust::evaluate(bool disableEV) mTpReturn = errSecSuccess; } catch (CommonError &err) { mTpReturn = err.osStatus(); - secdebug("trusteval", "certGroupVerify exception: %d", (int)mTpReturn); + secinfo("trusteval", "certGroupVerify exception: %d", (int)mTpReturn); } mResult = diagnoseOutcome(); @@ -501,11 +495,11 @@ void Trust::evaluate(bool disableEV) mTpResult[2].as(), anchors); } else { // unexpected evidence information. Can't use it - secdebug("trusteval", "unexpected evidence ignored"); + secinfo("trusteval", "unexpected evidence ignored"); } /* do post-processing for the evaluated certificate chain */ - CFArrayRef fullChain = makeCFArray(convert, mCertChain); + CFArrayRef fullChain = makeCFArrayFrom(convert, mCertChain); CFDictionaryRef etResult = extendedTrustResults(fullChain, mResult, mTpReturn, isEVCandidate); mExtendedResult = etResult; // assignment to CFRef type is an implicit retain if (etResult) { @@ -644,7 +638,7 @@ void Trust::evaluateUserTrust(const CertGroup &chain, if (info.recordId()) { Keychain keychain = keychainByDLDb(info.DlDbHandle); DbUniqueRecord uniqueId(keychain->database()->newDbUniqueRecord()); - secdebug("trusteval", "evidence %lu from keychain \"%s\"", (unsigned long)n, keychain->name()); + secinfo("trusteval", "evidence %lu from keychain \"%s\"", (unsigned long)n, keychain->name()); *static_cast(uniqueId) = info.UniqueRecord; uniqueId->activate(); // transfers ownership Item ii = keychain->item(CSSM_DL_DB_RECORD_X509_CERTIFICATE, uniqueId); @@ -654,20 +648,20 @@ void Trust::evaluateUserTrust(const CertGroup &chain, } mCertChain[n] = cert; } else if (info.status(CSSM_CERT_STATUS_IS_IN_INPUT_CERTS)) { - secdebug("trusteval", "evidence %lu from input cert %lu", (unsigned long)n, (unsigned long)info.index()); + secinfo("trusteval", "evidence %lu from input cert %lu", (unsigned long)n, (unsigned long)info.index()); assert(info.index() < uint32(CFArrayGetCount(mCerts))); SecCertificateRef cert = SecCertificateRef(CFArrayGetValueAtIndex(mCerts, info.index())); mCertChain[n] = Certificate::required(cert); } else if (info.status(CSSM_CERT_STATUS_IS_IN_ANCHORS)) { - secdebug("trusteval", "evidence %lu from anchor cert %lu", (unsigned long)n, (unsigned long)info.index()); + secinfo("trusteval", "evidence %lu from anchor cert %lu", (unsigned long)n, (unsigned long)info.index()); assert(info.index() < uint32(CFArrayGetCount(anchors))); SecCertificateRef cert = SecCertificateRef(CFArrayGetValueAtIndex(anchors, info.index())); mCertChain[n] = Certificate::required(cert); } else { // unknown source; make a new Certificate for it - secdebug("trusteval", "evidence %lu from unknown source", (unsigned long)n); + secinfo("trusteval", "evidence %lu from unknown source", (unsigned long)n); mCertChain[n] = new Certificate(chain.blobCerts()[n], CSSM_CERT_X_509v3, CSSM_CERT_ENCODING_BER); @@ -686,7 +680,7 @@ void Trust::evaluateUserTrust(const CertGroup &chain, continue; } mResult = store.find(mCertChain[mResultIndex], policy, searchLibs()); - secdebug("trusteval", "trustResult=%d from cert %d", (int)mResult, (int)mResultIndex); + secinfo("trusteval", "trustResult=%d from cert %d", (int)mResult, (int)mResultIndex); } } @@ -719,12 +713,12 @@ void Trust::releaseTPEvidence(TPVerifyResult &result, Allocator &allocator) allocator.free(evidence[n].StatusCodes); allocator.free(result[2].data()); // array of (flat) info structs } else { - secdebug("trusteval", "unrecognized Apple TP evidence format"); + secinfo("trusteval", "unrecognized Apple TP evidence format"); // drop it -- better leak than kill } } else { // unknown format -- blindly assume flat blobs - secdebug("trusteval", "destroying unknown TP evidence format"); + secinfo("trusteval", "destroying unknown TP evidence format"); for (uint32 n = 0; n < result.count(); n++) { allocator.free(result[n].data()); @@ -745,6 +739,7 @@ void Trust::clearResults() if (mResult != kSecTrustResultInvalid) { releaseTPEvidence(mTpResult, mTP.allocator()); mResult = kSecTrustResultInvalid; + mExtendedResult = NULL; } } @@ -758,7 +753,7 @@ void Trust::buildEvidence(CFArrayRef &certChain, TPEvidenceInfo * &statusChain) if (mResult == kSecTrustResultInvalid) MacOSError::throwMe(errSecTrustNotAvailable); certChain = mEvidenceReturned = - makeCFArray(convert, mCertChain); + makeCFArrayFrom(convert, mCertChain); if(mTpResult.count() >= 3) { statusChain = mTpResult[2].as(); }