]> git.saurik.com Git - apple/security.git/blobdiff - Security/libsecurity_apple_x509_tp/lib/tpOcspCache.cpp
Security-57336.1.9.tar.gz
[apple/security.git] / Security / libsecurity_apple_x509_tp / lib / tpOcspCache.cpp
diff --git a/Security/libsecurity_apple_x509_tp/lib/tpOcspCache.cpp b/Security/libsecurity_apple_x509_tp/lib/tpOcspCache.cpp
deleted file mode 100644 (file)
index 5ac0ef4..0000000
+++ /dev/null
@@ -1,319 +0,0 @@
-/*
- * Copyright (c) 2004,2011,2014 Apple Inc. All Rights Reserved.
- * 
- * @APPLE_LICENSE_HEADER_START@
- * 
- * This file contains Original Code and/or Modifications of Original Code
- * as defined in and that are subject to the Apple Public Source License
- * Version 2.0 (the 'License'). You may not use this file except in
- * compliance with the License. Please obtain a copy of the License at
- * http://www.opensource.apple.com/apsl/ and read it before using this
- * file.
- * 
- * The Original Code and all software distributed under the License are
- * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
- * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
- * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
- * Please see the License for the specific language governing rights and
- * limitations under the License.
- * 
- * @APPLE_LICENSE_HEADER_END@
- */
-
-/*
- * tpOcspCache.cpp - local OCSP response cache.
- */
-#include "tpOcspCache.h"
-#include "tpdebugging.h"
-#include "certGroupUtils.h"
-#include <security_utilities/globalizer.h>
-#include <security_utilities/threading.h>
-#include <security_ocspd/ocspdUtils.h>
-#include <assert.h>
-
-/*
- * Set this flag nonzero to turn off this cache module. Generally used to debug
- * the ocspd disk cache.
- */
-#ifndef        NDEBUG
-#define TP_OCSP_CACHE_DISABLE  0
-#else
-/* cache always enabled in production build */
-#define TP_OCSP_CACHE_DISABLE  0
-#endif
-#pragma mark ---- single cache entry ----
-
-/* 
- * One cache entry, just a parsed OCSPResponse plus an optional URI and a 
- * "latest" nextUpdate time. An entry is stale when its nextUpdate time has 
- * come and gone. 
- */
-class OcspCacheEntry : public OCSPResponse
-{
-public:
-       OcspCacheEntry(
-               const CSSM_DATA derEncoded,
-               const CSSM_DATA *localResponder);               // optional
-       ~OcspCacheEntry();
-       
-       /* a trusting environment, this module...all public */
-       CSSM_DATA               mLocalResponder;                        // we new[]
-};
-
-OcspCacheEntry::OcspCacheEntry(
-       const CSSM_DATA derEncoded,
-       const CSSM_DATA *localResponder)                        // optional
-       : OCSPResponse(derEncoded, TP_OCSP_CACHE_TTL)
-{
-       if(localResponder) {
-               mLocalResponder.Data = new uint8[localResponder->Length];
-               mLocalResponder.Length = localResponder->Length;
-               memmove(mLocalResponder.Data, localResponder->Data, localResponder->Length);
-       }
-       else {
-               mLocalResponder.Data = NULL;
-               mLocalResponder.Length = 0;
-       }
-}
-
-OcspCacheEntry::~OcspCacheEntry()
-{
-       delete[] mLocalResponder.Data;
-}
-
-#pragma mark ---- global cache object ----
-
-/*
- * The cache object; ModuleNexus provides each task with at most of of these.
- * All ops which affect the contents of the cache hold the (essentially) global
- * mCacheLock.
- */
-class OcspCache
-{
-public:
-       OcspCache();
-       ~OcspCache();
-
-       /* The methods corresponding to this module's public interface */
-       OCSPSingleResponse *lookup(
-               OCSPClientCertID        &certID,
-               const CSSM_DATA         *localResponderURI);    // optional 
-       void addResponse(
-               const CSSM_DATA         &ocspResp,                              // we'll decode it
-               const CSSM_DATA         *localResponderURI);    // optional 
-       void flush(
-               OCSPClientCertID        &certID);
-
-private:
-       void removeEntry(unsigned dex);
-       void scanForStale();
-       OCSPSingleResponse *lookupPriv(
-               OCSPClientCertID        &certID,
-               const CSSM_DATA         *localResponderURI,             // optional 
-               unsigned                        &rtnDex);                               // RETURNED on success
-
-       Mutex                   mCacheLock;
-       
-       /*
-        * NOTE: I am aware that most folks would just use an array<> here, but
-        * gdb is so lame that it doesn't even let one examine the contents
-        * of an array<> (or just about anything else in the STL). I prefer
-        * debuggability over saving a few lines of trivial code.
-        */
-       OcspCacheEntry  **mEntries;                     // just an array of pointers
-       unsigned                mNumEntries;            // valid entries in mEntries
-       unsigned                mSizeofEntries;         // mallocd space in mEntries
-};
-
-OcspCache::OcspCache()
-       : mEntries(NULL), mNumEntries(0), mSizeofEntries(0)
-{
-
-}
-
-/* As of Tiger I believe that this code never runs */
-OcspCache::~OcspCache()
-{
-       for(unsigned dex=0; dex<mNumEntries; dex++) {
-               delete mEntries[dex];
-       }
-       if(mEntries) {
-               free(mEntries);
-       }
-}
-
-/* 
- * Private routine, remove entry 'n' from cache.
- * -- caller must hold mCacheLock
- * -- if caller is traversing mEntries, they must start over because we
- *    manipulate it.
- */
-void OcspCache::removeEntry(
-       unsigned dex)
-{
-       assert(dex <= (mNumEntries - 1));
-       
-       /* removed requested element and compact remaining array */
-       delete mEntries[dex];
-       for(unsigned i=dex; i<(mNumEntries - 1); i++) {
-               mEntries[i] = mEntries[i+1];
-       }
-       mNumEntries--;
-}
-
-/* 
- * Private routine to scan cache, deleting stale entries.
- * Caller must hold mCacheLock, and not be traversing mEntries.
- */
-void OcspCache::scanForStale()
-{
-       CFAbsoluteTime now = CFAbsoluteTimeGetCurrent();
-       bool foundOne;
-       do {
-               /* restart every time we delete a stale entry */
-               foundOne = false;
-               for(unsigned dex=0; dex<mNumEntries; dex++) {
-                       OcspCacheEntry *entry = mEntries[dex];
-                       if(entry->expireTime() < now) {
-                               tpOcspCacheDebug("OcspCache::scanForStale: deleting stale entry %p",
-                                       entry);
-                               removeEntry(dex);
-                               foundOne = true;
-                               break;
-                       }
-               }
-       } while(foundOne);
-}
-
-/* 
- * Private lookup routine. Caller holds mCacheLock. We return both an
- * OCSPSingleResponse and the index into mEntries at which we found it. 
- */
- OCSPSingleResponse *OcspCache::lookupPriv(
-       OCSPClientCertID        &certID,
-       const CSSM_DATA         *localResponderURI,             // optional 
-       unsigned                        &rtnDex)                                // RETURNED on success
-{
-       OCSPSingleResponse *resp = NULL;
-       for(unsigned dex=0; dex<mNumEntries; dex++) {
-               OcspCacheEntry *entry = mEntries[dex];
-               if(localResponderURI) {
-                       /* if caller specifies, it must match */
-                       if(entry->mLocalResponder.Data == NULL) {
-                               /* came from somewhere else, skip it */
-                               tpOcspCacheDebug("OcspCache::lookup: uri mismatch (1) on entry %p",
-                                       entry);
-                               continue;
-                       }
-                       if(!tpCompareCssmData(localResponderURI, &entry->mLocalResponder)) {
-                               tpOcspCacheDebug("OcspCache::lookup: uri mismatch (2) on entry %p",
-                                       entry);
-                               continue;
-                       }
-               }
-               resp = entry->singleResponseFor(certID);
-               if(resp) {
-                       tpOcspCacheDebug("OcspCache::lookupPriv: cache HIT on entry %p", entry);
-                       rtnDex=dex;
-                       return resp;
-               }
-       }
-       tpOcspCacheDebug("OcspCache::lookupPriv: cache MISS");
-       return NULL;
-}
-
-OCSPSingleResponse *OcspCache::lookup(
-       OCSPClientCertID        &certID,
-       const CSSM_DATA         *localResponderURI)             // optional 
-{
-       StLock<Mutex> _(mCacheLock);
-       
-       /* take care of stale entries right away */
-       scanForStale();
-       
-       unsigned rtnDex;
-       return lookupPriv(certID, localResponderURI, rtnDex);
-}
-
-void OcspCache::addResponse(
-       const CSSM_DATA         &ocspResp,                              // we'll decode it
-       const CSSM_DATA         *localResponderURI)             // optional 
-{
-       StLock<Mutex> _(mCacheLock);
-
-       OcspCacheEntry *entry = new OcspCacheEntry(ocspResp, localResponderURI);
-       if(mNumEntries == mSizeofEntries) {
-               if(mSizeofEntries == 0) {
-                       /* appending to empty array */
-                       mSizeofEntries = 1;
-               }
-               else {
-                       mSizeofEntries *= 2;
-               }
-               mEntries = (OcspCacheEntry **)realloc(mEntries, 
-                       mSizeofEntries * sizeof(OcspCacheEntry *));
-       }
-       mEntries[mNumEntries++] = entry;
-       tpOcspCacheDebug("OcspCache::addResponse: add entry %p", entry);
-}
-
-void OcspCache::flush(
-       OCSPClientCertID        &certID)
-{
-       StLock<Mutex> _(mCacheLock);
-       
-       /* take care of all stale entries */
-       scanForStale();
-       
-       unsigned rtnDex;
-       OCSPSingleResponse *resp;
-       do {
-               /* execute as until we find no more entries matching */
-               resp = lookupPriv(certID, NULL, rtnDex);
-               if(resp) {
-                       assert((rtnDex >= 0) && (rtnDex < mNumEntries));
-                       tpOcspCacheDebug("OcspCache::flush: deleting entry %p", mEntries[rtnDex]);
-                       removeEntry(rtnDex);
-               }
-       } while(resp != NULL);
-}
-
-
-static ModuleNexus<OcspCache> tpOcspCache;
-
-#pragma mark ---- Public API ----
-/*
- * Lookup locally cached response. Caller must free the returned OCSPSingleResponse.
- */
-OCSPSingleResponse *tpOcspCacheLookup(
-       OCSPClientCertID        &certID,
-       const CSSM_DATA         *localResponderURI)                     // optional 
-{
-       return tpOcspCache().lookup(certID, localResponderURI);
-}
-
-/* 
- * Add a fully verified OCSP response to cache. 
- */
-void tpOcspCacheAdd(
-       const CSSM_DATA         &ocspResp,                              // we'll decode it, not keep a ref
-       const CSSM_DATA         *localResponderURI)             // optional 
-{
-       #if     TP_OCSP_CACHE_DISABLE
-       return;
-       #endif
-       tpOcspCache().addResponse(ocspResp, localResponderURI);
-}
-
-/*
- * Delete any entry associated with specified certID from cache.
- */
-void tpOcspCacheFlush(
-       OCSPClientCertID        &certID)
-{
-       tpOcspCache().flush(certID);
-}
-