]> git.saurik.com Git - apple/security.git/blobdiff - OSX/sec/SOSCircle/SecureObjectSync/SOSRingUtils.c
Security-59306.11.20.tar.gz
[apple/security.git] / OSX / sec / SOSCircle / SecureObjectSync / SOSRingUtils.c
diff --git a/OSX/sec/SOSCircle/SecureObjectSync/SOSRingUtils.c b/OSX/sec/SOSCircle/SecureObjectSync/SOSRingUtils.c
deleted file mode 100644 (file)
index a83f8c4..0000000
+++ /dev/null
@@ -1,826 +0,0 @@
-/*
- * Copyright (c) 2015 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@
- */
-
-
-/*
- * SOSRingUtils.c - Functions for building rings
- */
-
-#include <AssertMacros.h>
-
-#include <Security/SecureObjectSync/SOSInternal.h>
-#include <Security/SecureObjectSync/SOSPeer.h>
-#include <Security/SecureObjectSync/SOSPeerInfoInternal.h>
-#include <Security/SecureObjectSync/SOSPeerInfoCollections.h>
-#include <Security/SecureObjectSync/SOSCircle.h>
-#include <Security/SecFramework.h>
-
-#include <Security/SecKey.h>
-#include <Security/SecKeyPriv.h>
-#include <CoreFoundation/CoreFoundation.h>
-
-#include <utilities/SecCFWrappers.h>
-
-//#include "ckdUtilities.h"
-
-#include <corecrypto/ccder.h>
-#include <corecrypto/ccdigest.h>
-#include <corecrypto/ccsha2.h>
-
-
-#include <utilities/der_plist.h>
-#include <utilities/der_plist_internal.h>
-#include <corecrypto/ccder.h>
-#include <utilities/der_date.h>
-
-#include <stdlib.h>
-#include <assert.h>
-
-#include "SOSRing.h"
-#include "SOSRingUtils.h"
-
-CFGiblisWithCompareFor(SOSRing);
-
-/* unSignedInformation Dictionary Keys */
-CFStringRef sApplicantsKey              = CFSTR("Applicants");
-CFStringRef sRejectionsKey              = CFSTR("Rejections");
-CFStringRef sLastPeerToModifyKey        = CFSTR("LastModifier");
-
-/* signedInformation Dictionary Keys */
-CFStringRef sPeerIDsKey                 = CFSTR("PeerIDs");
-CFStringRef sPayloadKey                 = CFSTR("Payload");
-CFStringRef sBackupViewSetKey           = CFSTR("BackupViews");
-CFStringRef sGenerationKey              = CFSTR("Generation");
-CFStringRef sNameKey                    = CFSTR("RingName");
-CFStringRef sTypeKey                    = CFSTR("RingType");
-CFStringRef sIdentifierKey              = CFSTR("Identifier");
-CFStringRef sRingVersionKey              = CFSTR("RingVersion");
-
-#define RINGVERSION 1
-
-SOSRingRef SOSRingAllocate(void) {
-    return (SOSRingRef) CFTypeAllocate(SOSRing, struct __OpaqueSOSRing, ALLOCATOR);
-}
-
-__unused static bool addValueToDict(CFMutableDictionaryRef thedict, CFStringRef key, CFTypeRef value) {
-    if(!value) return false;
-    CFDictionaryAddValue(thedict, key, value);
-    return true;
-}
-
-static bool setValueInDict(CFMutableDictionaryRef thedict, CFStringRef key, CFTypeRef value) {
-    if(!value) return false;
-    CFDictionarySetValue(thedict, key, value);
-    return true;
-}
-
-static CFMutableSetRef CFSetCreateMutableForSOSPeerIDs(void) {
-    return CFSetCreateMutable(ALLOCATOR, 0, &kCFTypeSetCallBacks);
-}
-
-
-static inline
-SOSRingRef SOSRingConvertAndAssertStable(CFTypeRef ringAsType) {
-    if (CFGetTypeID(ringAsType) != SOSRingGetTypeID())
-        return NULL;
-
-    SOSRingRef ring = (SOSRingRef) ringAsType;
-
-    SOSRingAssertStable(ring);
-
-    return ring;
-}
-
-// MARK: Ring Name
-
-CFStringRef SOSRingGetName(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->signedInformation);
-    return asString(CFDictionaryGetValue(ring->signedInformation, sNameKey), NULL);
-}
-
-const char *SOSRingGetNameC(SOSRingRef ring) {
-    CFStringRef name = asString(SOSRingGetName(ring), NULL);
-    if (!name)
-        return strdup("");
-    return CFStringToCString(name);
-}
-
-static inline bool SOSRingSetName(SOSRingRef ring, CFStringRef name) {
-    assert(ring);
-    assert(ring->signedInformation);
-    return setValueInDict(ring->signedInformation, sNameKey, name);
-}
-
-// MARK: Ring Type
-
-static bool SOSRingCheckType(SOSRingType type, CFErrorRef *error) {
-    if(type < kSOSRingTypeCount) return true;
-    SOSCreateError(kSOSErrorUnexpectedType, CFSTR("Bad Ring Type Specification"), (error != NULL) ? *error : NULL, error);
-    return false;
-}
-
-uint32_t SOSRingGetType(SOSRingRef ring) {
-    uint32_t retval = kSOSRingTypeError; // Error return
-    SOSRingAssertStable(ring);
-    if(!ring->signedInformation) return retval;
-    CFNumberRef ringtype = (CFNumberRef) CFDictionaryGetValue(ring->signedInformation, sTypeKey);
-    CFNumberGetValue(ringtype, kCFNumberSInt32Type, &retval);
-    return retval;
-}
-
-static inline bool SOSRingSetType(SOSRingRef ring, uint32_t ringtype) {
-    bool retval = false;
-    CFNumberRef cfrtype = NULL;
-    SOSRingAssertStable(ring);
-    require_action_quiet(SOSRingCheckType(ringtype, NULL), errOut, secnotice("ring", "Bad ring type specification"));
-    cfrtype = CFNumberCreate(ALLOCATOR, kCFNumberSInt32Type, &ringtype);
-    retval = setValueInDict(ring->signedInformation, sTypeKey, cfrtype);
-errOut:
-    CFReleaseNull(cfrtype);
-    return retval;
-}
-
-// MARK: Version
-
-uint32_t SOSRingGetVersion(SOSRingRef ring) {
-    uint32_t version = 0;
-    assert(ring);
-    assert(ring->signedInformation);
-    CFNumberRef cfversion = CFDictionaryGetValue(ring->signedInformation, sRingVersionKey);
-    require_action_quiet(cfversion, errOut, secnotice("ring", "Could not create version number"));
-    CFNumberGetValue(cfversion, kCFNumberSInt32Type, &version);
-errOut:
-    return version;
-}
-
-static inline bool SOSRingSetVersion(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->signedInformation);
-    int32_t thisversion = RINGVERSION;
-    CFNumberRef version = CFNumberCreate(ALLOCATOR, kCFNumberSInt32Type, &thisversion);
-    require_action_quiet(version, errOut, secnotice("ring", "Could not create version number"));
-    CFDictionarySetValue(ring->signedInformation, sRingVersionKey, version);
-    CFReleaseNull(version);
-    return true;
-errOut:
-    return false;
-}
-
-// MARK: Identifier
-
-CFStringRef SOSRingGetIdentifier(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->signedInformation);
-    return CFDictionaryGetValue(ring->signedInformation, sIdentifierKey);
-}
-
-static inline bool SOSRingSetIdentifier(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->signedInformation);
-    bool retval = false;
-    CFStringRef identifier = NULL;
-    CFUUIDRef uuid = CFUUIDCreate(ALLOCATOR);
-    require_action_quiet(uuid, errOut, secnotice("ring", "Could not create ring identifier"));
-    identifier = CFUUIDCreateString(ALLOCATOR, uuid);
-    CFDictionarySetValue(ring->signedInformation, sIdentifierKey, identifier);
-    retval = true;
-errOut:
-    CFReleaseNull(uuid);
-    CFReleaseNull(identifier);
-    return retval;
-}
-
-// MARK: Ring Identity
-
-bool SOSRingIsSame(SOSRingRef ring1, SOSRingRef ring2) {
-    CFStringRef name1 = SOSRingGetName(ring1);
-    CFStringRef name2 = SOSRingGetName(ring2);
-    require_action_quiet(name1 && name2, errOut, secnotice("ring", "Cannot get both names to consider rings the same"));
-    if(CFEqualSafe(name1, name2) != true) return false;
-
-    uint32_t type1 = SOSRingGetType(ring1);
-    uint32_t type2 = SOSRingGetVersion(ring2);
-    require_action_quiet(type1 && type2, errOut, secnotice("ring", "Cannot get both types to consider rings the same"));
-    if(type1 != type2) return false;
-
-    CFStringRef identifier1 = SOSRingGetIdentifier(ring1);
-    CFStringRef identifier2 = SOSRingGetIdentifier(ring2);
-    require_action_quiet(identifier1 && identifier2, errOut, secnotice("ring", "Cannot get both identifiers to consider rings the same"));
-    if(CFEqualSafe(identifier1, identifier2) != true) return false;
-
-    return true;
-errOut:
-    return false;
-
-}
-
-static Boolean SOSRingCompare(CFTypeRef lhs, CFTypeRef rhs) {
-    if (CFGetTypeID(lhs) != SOSRingGetTypeID()
-        || CFGetTypeID(rhs) != SOSRingGetTypeID())
-        return false;
-
-    SOSRingRef left = SOSRingConvertAndAssertStable(lhs);
-    SOSRingRef right = SOSRingConvertAndAssertStable(rhs);
-
-    return NULL != left && NULL != right
-    && CFEqualSafe(left->unSignedInformation, right->unSignedInformation)
-    && CFEqualSafe(left->signedInformation, right->signedInformation)
-    && CFEqualSafe(left->data, right->data)
-    && CFEqualSafe(left->signatures, right->signatures);
-}
-
-
-// MARK: Ring Generation Count
-
-SOSGenCountRef SOSRingGetGeneration(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->signedInformation);
-    return CFDictionaryGetValue(ring->signedInformation, sGenerationKey);
-}
-
-static inline bool SOSRingSetGeneration(SOSRingRef ring, SOSGenCountRef gen) {
-    assert(ring);
-    assert(ring->signedInformation);
-    return setValueInDict(ring->signedInformation, sGenerationKey, gen);
-}
-
-void SOSRingGenerationIncrement(SOSRingRef ring) {
-    SOSGenCountRef gen = SOSRingGetGeneration(ring);
-    SOSGenCountRef newgen = SOSGenerationIncrementAndCreate(gen);
-    SOSRingSetGeneration(ring, newgen);
-    CFReleaseNull(newgen);
-}
-
-bool SOSRingIsOlderGeneration(SOSRingRef olderRing, SOSRingRef newerRing) {
-    SOSGenCountRef old = SOSRingGetGeneration(olderRing);
-    SOSGenCountRef new = SOSRingGetGeneration(newerRing);
-    return SOSGenerationIsOlder(old, new);
-}
-
-void SOSRingGenerationCreateWithBaseline(SOSRingRef newring, SOSRingRef baseline) {
-    if(!newring) return;
-    SOSGenCountRef gen = SOSGenerationCreateWithBaseline(SOSRingGetGeneration(baseline));
-    SOSRingSetGeneration(newring, gen);
-    CFReleaseNull(gen);
-}
-
-// MARK: Last Modifier
-CFStringRef SOSRingGetLastModifier(SOSRingRef ring) {
-    assert(ring);
-    assert(ring->unSignedInformation);
-    return CFDictionaryGetValue(ring->unSignedInformation, sLastPeerToModifyKey);
-}
-
-bool SOSRingSetLastModifier(SOSRingRef ring, CFStringRef peerID) {
-    assert(ring);
-    assert(ring->unSignedInformation);
-    return setValueInDict(ring->unSignedInformation, sLastPeerToModifyKey, peerID);
-}
-
-
-// MARK: Ring Applicants
-
-CFMutableSetRef SOSRingGetApplicants(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (CFMutableSetRef) CFDictionaryGetValue(ring->unSignedInformation, sApplicantsKey);
-}
-
-bool SOSRingSetApplicants(SOSRingRef ring, CFMutableSetRef applicants) {
-    SOSRingAssertStable(ring);
-    return setValueInDict(ring->unSignedInformation, sApplicantsKey, applicants);
-}
-
-int SOSRingCountApplicants(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (int)CFSetGetCount(SOSRingGetApplicants(ring));
-}
-
-bool SOSRingHasApplicant(SOSRingRef ring, CFStringRef peerID) {
-    SOSRingAssertStable(ring);
-    return CFSetContainsValue(SOSRingGetApplicants(ring), peerID);
-}
-
-CFMutableSetRef SOSRingCopyApplicants(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    CFSetRef applicants = SOSRingGetApplicants(ring);
-    return CFSetCreateMutableCopy(ALLOCATOR, 0, applicants);
-}
-
-bool SOSRingAddApplicant(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef applicants = SOSRingGetApplicants(ring);
-    CFSetAddValue(applicants, peerid);
-    return true;
-}
-
-bool SOSRingRemoveApplicant(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef applicants = SOSRingGetApplicants(ring);
-    CFSetRemoveValue(applicants, peerid);
-    return true;
-}
-
-// MARK: Ring Rejections
-
-static inline CFMutableSetRef SOSRingGetRejections(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (CFMutableSetRef) CFDictionaryGetValue(ring->unSignedInformation, sRejectionsKey);
-}
-
-static inline bool SOSRingSetRejections(SOSRingRef ring, CFMutableSetRef rejections) {
-    SOSRingAssertStable(ring);
-    return setValueInDict(ring->unSignedInformation, sRejectionsKey, rejections);
-}
-
-int SOSRingCountRejections(SOSRingRef ring) {
-    CFSetRef rejects = SOSRingGetRejections(ring);
-    return (int)CFSetGetCount(rejects);
-}
-
-bool SOSRingHasRejection(SOSRingRef ring, CFStringRef peerID) {
-    SOSRingAssertStable(ring);
-    return CFSetContainsValue(SOSRingGetRejections(ring), peerID);
-}
-
-CFMutableSetRef SOSRingCopyRejections(SOSRingRef ring) {
-    CFSetRef rejects = SOSRingGetRejections(ring);
-    return CFSetCreateMutableCopy(ALLOCATOR, 0, rejects);
-}
-
-
-bool SOSRingAddRejection(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef rejects = SOSRingGetRejections(ring);
-    CFSetAddValue(rejects, peerid);
-    return true;
-}
-
-bool SOSRingRemoveRejection(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef rejects = SOSRingGetRejections(ring);
-    CFSetRemoveValue(rejects, peerid);
-    return true;
-}
-
-// MARK: Ring Payload
-
-CFDataRef SOSRingGetPayload_Internal(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (CFDataRef) CFDictionaryGetValue(ring->signedInformation, sPayloadKey);
-}
-
-bool SOSRingSetPayload_Internal(SOSRingRef ring, CFDataRef payload) {
-    SOSRingAssertStable(ring);
-    return setValueInDict(ring->signedInformation, sPayloadKey, payload);
-}
-
-// MARK: Ring Backup Viewset
-
-
-CFSetRef SOSRingGetBackupViewset_Internal(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return asSet(CFDictionaryGetValue(ring->signedInformation, sBackupViewSetKey), NULL);
-}
-
-bool SOSRingSetBackupViewset_Internal(SOSRingRef ring, CFSetRef viewSet) {
-    SOSRingAssertStable(ring);
-    return setValueInDict(ring->signedInformation, sBackupViewSetKey, viewSet);
-}
-
-
-
-// MARK: Ring PeerIDs
-
-static inline CFMutableSetRef SOSRingGetPeerIDs(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (CFMutableSetRef) asSet(CFDictionaryGetValue(ring->signedInformation, sPeerIDsKey), NULL);
-}
-
-bool SOSRingSetPeerIDs(SOSRingRef ring, CFMutableSetRef peers) {
-    SOSRingAssertStable(ring);
-    return setValueInDict(ring->signedInformation, sPeerIDsKey, peers);
-}
-
-int SOSRingCountPeerIDs(SOSRingRef ring) {
-    CFSetRef peerIDs = SOSRingGetPeerIDs(ring);
-    return (int)CFSetGetCount(peerIDs);
-}
-
-
-bool SOSRingHasPeerID(SOSRingRef ring, CFStringRef peerID) {
-    SOSRingAssertStable(ring);
-    return CFSetContainsValue(SOSRingGetPeerIDs(ring), peerID);
-}
-
-CFMutableSetRef SOSRingCopyPeerIDs(SOSRingRef ring) {
-    CFSetRef peerIDs = SOSRingGetPeerIDs(ring);
-    return CFSetCreateMutableCopy(ALLOCATOR, 0, peerIDs);
-}
-
-void SOSRingAddAll(SOSRingRef ring, CFSetRef peerInfosOrIDs) {
-    CFSetForEach(peerInfosOrIDs, ^(const void *value) {
-        CFStringRef peerID = value;
-
-        if (isSOSPeerInfo(value))
-            peerID = SOSPeerInfoGetPeerID((SOSPeerInfoRef)value);
-
-        if (isString(peerID))
-            SOSRingAddPeerID(ring, peerID);
-    });
-}
-
-bool SOSRingAddPeerID(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef peerIDs = SOSRingGetPeerIDs(ring);
-    CFSetAddValue(peerIDs, peerid);
-    return true;
-}
-
-bool SOSRingRemovePeerID(SOSRingRef ring, CFStringRef peerid) {
-    CFMutableSetRef peerIDs = SOSRingGetPeerIDs(ring);
-    CFSetRemoveValue(peerIDs, peerid);
-    return true;
-}
-
-void SOSRingForEachPeerID(SOSRingRef ring, void (^action)(CFStringRef peerID)) {
-    SOSRingAssertStable(ring);
-    CFMutableSetRef peerIDs = SOSRingGetPeerIDs(ring);
-    if(!peerIDs) return;
-    CFSetForEach(peerIDs, ^(const void*value) {
-        CFStringRef peerID = (CFStringRef) value;
-            action(peerID);
-    });
-}
-
-// MARK: SOSRing Ops
-
-SOSRingRef SOSRingCreate_Internal(CFStringRef name, SOSRingType type, CFErrorRef *error) {
-    SOSRingRef r = SOSRingAllocate();
-    SOSGenCountRef gen = SOSGenerationCreate();
-
-    require_action_quiet(name, errout0,
-        SOSCreateError(kSOSErrorNoCircleName, CFSTR("No ring name"), NULL, error));
-    require_action_quiet(SOSRingCheckType(type, error), errout0,
-        SOSCreateError(kSOSErrorUnexpectedType, CFSTR("Unknown ring type"), NULL, error));
-    require_action_quiet((r->unSignedInformation = CFDictionaryCreateMutableForCFTypes(ALLOCATOR)), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate unsigned information area"), NULL, error));
-    require_action_quiet((r->signedInformation = CFDictionaryCreateMutableForCFTypes(ALLOCATOR)), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate signed information area"), NULL, error));
-    require_action_quiet((r->signatures = CFDictionaryCreateMutableForCFTypes(ALLOCATOR)), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate signature area"), NULL, error));
-    require_action_quiet((r->data = CFDictionaryCreateMutableForCFTypes(ALLOCATOR)), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate data area"), NULL, error));
-
-    require_action_quiet(SOSRingSetName(r, name), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate ring name area"), NULL, error));
-    require_action_quiet(SOSRingSetType(r, type), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate ring type"), NULL, error));
-    require_action_quiet(SOSRingSetVersion(r), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate ring version"), NULL, error));
-    require_action_quiet(SOSRingSetIdentifier(r), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate ring identifier"), NULL, error));
-    
-    CFMutableSetRef peerIDs = CFSetCreateMutableForSOSPeerIDs();
-    require_action_quiet(SOSRingSetApplicants(r, peerIDs), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate applicant area"), NULL, error));
-    CFReleaseNull(peerIDs);
-    
-    CFMutableSetRef rejectedIDs = CFSetCreateMutableForSOSPeerIDs();
-    require_action_quiet(SOSRingSetRejections(r, rejectedIDs), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate rejection area"), NULL, error));
-    CFReleaseNull(rejectedIDs);
-    
-    require_action_quiet(SOSRingSetGeneration(r, gen), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate generation count"), NULL, error));
-    
-    peerIDs = CFSetCreateMutableForSOSPeerIDs();
-    require_action_quiet(SOSRingSetPeerIDs(r, peerIDs), errout,
-        SOSCreateError(kSOSErrorAllocationFailure, CFSTR("Failed to allocate PeerID"), NULL, error));
-    CFReleaseNull(gen);
-    CFReleaseNull(peerIDs);
-    
-    return r;
-errout:
-    CFReleaseNull(r->unSignedInformation);
-    CFReleaseNull(r->signedInformation);
-    CFReleaseNull(r->signatures);
-    CFReleaseNull(r->data);
-errout0:
-    CFReleaseNull(gen);
-    CFReleaseNull(r);
-    return NULL;
-}
-
-
-static void SOSRingDestroy(CFTypeRef aObj) {
-    SOSRingRef c = (SOSRingRef) aObj;
-
-    CFReleaseNull(c->unSignedInformation);
-    CFReleaseNull(c->signedInformation);
-    CFReleaseNull(c->data);
-    CFReleaseNull(c->signatures);
-}
-
-
-SOSRingRef SOSRingCopyRing(SOSRingRef original, CFErrorRef *error) {
-    SOSRingRef r = CFTypeAllocate(SOSRing, struct __OpaqueSOSRing, ALLOCATOR);
-
-    assert(original);
-    r->unSignedInformation = CFDictionaryCreateMutableCopy(ALLOCATOR, 0, original->unSignedInformation);
-    r->signedInformation = CFDictionaryCreateMutableCopy(ALLOCATOR, 0, original->signedInformation);
-    r->signatures = CFDictionaryCreateMutableCopy(ALLOCATOR, 0, original->signatures);
-    r->data = CFDictionaryCreateMutableCopy(ALLOCATOR, 0, original->data);
-
-    return r;
-}
-
-bool SOSRingIsEmpty_Internal(SOSRingRef ring) {
-    return CFSetGetCount(SOSRingGetPeerIDs(ring)) == 0;
-}
-
-bool SOSRingIsOffering_Internal(SOSRingRef ring) {
-    return SOSRingCountPeers(ring) == 1;
-}
-
-bool SOSRingResetToEmpty_Internal(SOSRingRef ring, CFErrorRef *error) {
-    SOSGenCountRef gen = NULL;
-    CFSetRemoveAllValues(SOSRingGetApplicants(ring));
-    CFSetRemoveAllValues(SOSRingGetRejections(ring));
-    CFSetRemoveAllValues(SOSRingGetPeerIDs(ring));
-    CFDictionaryRemoveAllValues(ring->signatures);
-    SOSRingSetGeneration(ring, gen = SOSGenerationCreate());
-    CFReleaseNull(gen);
-    return true;
-}
-
-// MARK: PeerIDs in Ring
-
-int SOSRingCountPeers(SOSRingRef ring) {
-    SOSRingAssertStable(ring);
-    return (int) CFSetGetCount(SOSRingGetPeerIDs(ring));
-}
-
-
-bool SOSRingHasPeerWithID(SOSRingRef ring, CFStringRef peerid, CFErrorRef *error) {
-    SOSRingAssertStable(ring);
-    return CFSetContainsValue(SOSRingGetPeerIDs(ring), peerid);
-}
-
-// MARK: Ring Signatures
-
-
-static inline CFDictionaryRef SOSRingGetSignatures(SOSRingRef ring) {
-    return ring->signatures;
-}
-
-static inline CFDataRef SOSRingGetSignatureForPeerID(SOSRingRef ring, CFStringRef peerID) {
-    if(!ring || !peerID) return NULL;
-    CFDataRef result = NULL;
-    CFTypeRef value = (CFDataRef)CFDictionaryGetValue(SOSRingGetSignatures(ring), peerID);
-    if (isData(value)) result = (CFDataRef) value;
-    return result;
-}
-
-static CFDataRef SOSRingCreateHash(const struct ccdigest_info *di, SOSRingRef ring, CFErrorRef *error) {
-    uint8_t hash_result[di->output_size];
-
-    size_t dersize = der_sizeof_plist(ring->signedInformation, error);
-    if(dersize == 0) {
-        return false;
-    }
-    uint8_t *der = malloc(dersize);
-    if (der == NULL) {
-        return false;
-    }
-    if (der_encode_plist(ring->signedInformation, error, der, der+dersize) == NULL) {
-        free(der);
-        return false;
-    }
-
-    ccdigest(di, dersize, der, hash_result);
-    free(der);
-    return CFDataCreate(NULL, hash_result, di->output_size);
-}
-
-static bool SOSRingSetSignature(SOSRingRef ring, SecKeyRef privKey, CFDataRef signature, CFErrorRef *error) {
-    bool result = false;
-    SecKeyRef pubkey = SecKeyCreatePublicFromPrivate(privKey);
-    CFStringRef pubKeyID = SOSCopyIDOfKey(pubkey, error);
-    require_quiet(pubKeyID, fail);
-    CFDictionarySetValue(ring->signatures, pubKeyID, signature);
-    result = true;
-fail:
-    CFReleaseSafe(pubkey);
-    CFReleaseSafe(pubKeyID);
-    return result;
-}
-
-static bool SOSRingRemoveSignatures(SOSRingRef ring, CFErrorRef *error) {
-    CFDictionaryRemoveAllValues(ring->signatures);
-    return true;
-}
-
-static CFDataRef SOSCopySignedHash(SecKeyRef privKey, CFDataRef hash, CFErrorRef *error) {
-    size_t siglen = SecKeyGetSize(privKey, kSecKeySignatureSize)+16;
-    uint8_t sig[siglen];
-    OSStatus stat =  SecKeyRawSign(privKey, kSecPaddingNone, CFDataGetBytePtr(hash), CFDataGetLength(hash), sig, &siglen);
-    if(stat) {
-        return NULL;
-    }
-    return CFDataCreate(NULL, sig, siglen);
-}
-
-static bool SOSRingSign(SOSRingRef ring, SecKeyRef privKey, CFErrorRef *error) {
-    if (!ring || !privKey) {
-        SOSCreateError(kSOSErrorBadSignature, CFSTR("SOSRingSign Lacking ring or private key"),
-            (error != NULL) ? *error : NULL, error);
-        return false;
-    }
-    const struct ccdigest_info *di = ccsha256_di();
-    CFDataRef hash = SOSRingCreateHash(di, ring, error);
-    CFDataRef signature = SOSCopySignedHash(privKey, hash, error);
-    SOSRingSetSignature(ring, privKey, signature, error);
-    CFRelease(signature);
-    CFReleaseNull(hash);
-    return true;
-}
-
-bool SOSRingVerifySignatureExists(SOSRingRef ring, SecKeyRef pubKey, CFErrorRef *error) {
-    CFStringRef pubKeyID = SOSCopyIDOfKey(pubKey, error);
-    CFDataRef signature = SOSRingGetSignatureForPeerID(ring, pubKeyID);
-    CFReleaseNull(pubKeyID);
-    return NULL != signature;
-}
-
-bool SOSRingVerify(SOSRingRef ring, SecKeyRef pubKey, CFErrorRef *error) {
-    CFStringRef pubKeyID = SOSCopyIDOfKey(pubKey, error);
-    CFDataRef signature = SOSRingGetSignatureForPeerID(ring, pubKeyID);
-    CFReleaseNull(pubKeyID);
-    if(!signature) return false;
-    CFDataRef hash = SOSRingCreateHash(ccsha256_di(), ring, error);
-    bool success = SecKeyRawVerify(pubKey, kSecPaddingNone, CFDataGetBytePtr(hash), CFDataGetLength(hash),
-                           CFDataGetBytePtr(signature), CFDataGetLength(signature)) == errSecSuccess;
-    CFReleaseNull(hash);
-    return success;
-}
-
-bool SOSRingVerifyPeerSigned(SOSRingRef ring, SOSPeerInfoRef peer, CFErrorRef *error) {
-    bool result = false;
-    SecKeyRef pubkey = SOSPeerInfoCopyPubKey(peer, error);
-    require_quiet(pubkey, fail);
-
-    result = SOSRingVerify(ring, pubkey, error);
-
-fail:
-    CFReleaseSafe(pubkey);
-    return result;
-}
-
-static bool SOSRingEnsureRingConsistency(SOSRingRef ring, CFErrorRef *error) {
-    secnotice("Development", "SOSRingEnsureRingConsistency requires ring membership and generation count consistency check", NULL);
-    return true;
-}
-
-bool SOSRingGenerationSign_Internal(SOSRingRef ring, SecKeyRef privKey, CFErrorRef *error) {
-    if(!privKey || !ring) return false;
-    bool retval = false;
-    SOSRingGenerationIncrement(ring);
-    require_quiet(SOSRingEnsureRingConsistency(ring, error), fail);
-    require_quiet(SOSRingRemoveSignatures(ring, error), fail);
-    require_quiet(SOSRingSign(ring, privKey, error), fail);
-    retval = true;
-fail:
-    return retval;
-}
-
-// MARK: Concordance
-
-bool SOSRingConcordanceSign_Internal(SOSRingRef ring, SecKeyRef privKey, CFErrorRef *error) {
-    if(!privKey || !ring) return false;
-    bool retval = false;
-    require_quiet(SOSRingSign(ring, privKey, error), fail);
-    retval = true;
-fail:
-    return retval;
-}
-
-
-
-// MARK: Debugging
-
-static inline void CFSetForEachPeerID(CFSetRef set, void (^operation)(CFStringRef peerID)) {
-    CFSetForEach(set, ^(const void *value) {
-        CFStringRef peerID = (CFStringRef) value;
-        operation(peerID);
-    });
-}
-
-static CFStringRef CreateCommaSeparatedPeerIDs(CFSetRef peers) {
-    CFMutableStringRef result = CFStringCreateMutable(kCFAllocatorDefault, 0);
-
-    __block bool addSeparator = false;
-
-    CFSetForEachPeerID(peers, ^(CFStringRef peerID) {
-        if (addSeparator) {
-            CFStringAppendCString(result, ", ", kCFStringEncodingUTF8);
-        }
-        CFStringAppend(result, peerID);
-
-        addSeparator = true;
-    });
-
-    return result;
-}
-
-CFDictionaryRef SOSRingCopyPeerIDList(SOSRingRef ring) {
-    CFStringRef peerIDS = CreateCommaSeparatedPeerIDs(SOSRingGetPeerIDs(ring));
-    CFStringRef applicantIDs = CreateCommaSeparatedPeerIDs(SOSRingGetApplicants(ring));
-    CFStringRef rejectIDs = CreateCommaSeparatedPeerIDs(SOSRingGetRejections(ring));
-    CFDictionaryRef list = CFDictionaryCreateForCFTypes(ALLOCATOR,
-                                        CFSTR("MEMBER"), peerIDS,
-                                        CFSTR("APPLICANTS"), applicantIDs,
-                                        CFSTR("REJECTS"), rejectIDs,
-                                        NULL);
-    
-    CFReleaseNull(peerIDS);
-    CFReleaseNull(applicantIDs);
-    CFReleaseNull(rejectIDs);
-    return list;
-}
-
- CFStringRef SOSRingCopySignerList(SOSRingRef ring) {
-    __block bool addSeparator = false;
-   CFMutableStringRef signers = CFStringCreateMutable(ALLOCATOR, 0);
-    CFDictionaryForEach(ring->signatures, ^(const void *key, const void *value) {
-        CFStringRef peerID = (CFStringRef) key;
-        if (addSeparator)
-            CFStringAppendCString(signers, ", ", kCFStringEncodingUTF8);
-        CFStringAppend(signers, peerID);
-        addSeparator = true;
-    });
-    return signers;
-}
-
-static CFStringRef SOSRingCopyFormatDescription(CFTypeRef aObj, CFDictionaryRef formatOpts) {
-    SOSRingRef ring = (SOSRingRef) aObj;
-
-    SOSRingAssertStable(ring);
-
-    CFDictionaryRef peers = SOSRingCopyPeerIDList(ring);
-    CFStringRef signers = SOSRingCopySignerList(ring);
-
-    CFDataRef payload = SOSRingGetPayload(ring, NULL);
-
-    CFStringRef gcString = SOSGenerationCountCopyDescription(SOSRingGetGeneration(ring));
-
-    CFMutableStringRef description = CFStringCreateMutable(kCFAllocatorDefault, 0);
-
-    CFStringAppendFormat(description, formatOpts, CFSTR("<SOSRing@%p: '%@', Version %u, "), ring, SOSRingGetName(ring), SOSRingGetVersion(ring));
-    CFStringAppendFormat(description, formatOpts, CFSTR("UUID: %@, "), SOSRingGetIdentifier(ring));
-    SOSGenerationCountWithDescription(SOSRingGetGeneration(ring), ^(CFStringRef gcString) {
-        CFStringAppendFormat(description, formatOpts, CFSTR("Gen: %@, "), gcString);
-    });
-    CFStringAppendFormat(description, formatOpts, CFSTR("Mod: %@, "), SOSRingGetLastModifier(ring));
-    
-    CFStringAppendFormat(description, formatOpts, CFSTR("D: %ld "), payload ? CFDataGetLength(payload) : 0);
-
-    SOSBackupSliceKeyBagRef payloadAsBSKB = SOSRingCopyBackupSliceKeyBag(ring, NULL);
-
-    if (payloadAsBSKB) {
-        CFStringAppendFormat(description, formatOpts, CFSTR("%@ "), payloadAsBSKB);
-    }
-
-    CFReleaseSafe(payloadAsBSKB);
-
-    CFStringAppendFormat(description, formatOpts, CFSTR("P: [%@], "), CFDictionaryGetValue(peers, CFSTR("MEMBER")));
-    CFStringAppendFormat(description, formatOpts, CFSTR("A: [%@], "), CFDictionaryGetValue(peers, CFSTR("APPLICANTS")));
-    CFStringAppendFormat(description, formatOpts, CFSTR("R: [%@], "), CFDictionaryGetValue(peers, CFSTR("REJECTS")));
-    CFStringAppendFormat(description, formatOpts, CFSTR("S: [%@]>"), signers);
-
-    CFReleaseNull(gcString);
-    CFReleaseNull(peers);
-    CFReleaseNull(signers);
-    CFReleaseNull(peers);
-    
-    return description;
-}
-
-#define SIGLEN 128
-
-