5 // Created by Richard Murphy on 3/3/15.
9 #include "SOSRingBasic.h"
11 #include <AssertMacros.h>
13 #include <Security/SecureObjectSync/SOSInternal.h>
14 #include <Security/SecureObjectSync/SOSPeerInfoInternal.h>
15 #include <Security/SecureObjectSync/SOSPeerInfoCollections.h>
16 #include <Security/SecureObjectSync/SOSCircle.h>
17 #include <Security/SecFramework.h>
19 #include <Security/SecKey.h>
20 #include <Security/SecKeyPriv.h>
21 #include <CoreFoundation/CoreFoundation.h>
23 #include <utilities/SecCFWrappers.h>
28 #include "SOSRingUtils.h"
29 #include "SOSRingTypes.h"
31 // MARK: Basic Ring Ops
33 static SOSRingRef
SOSRingCreate_Basic(CFStringRef name
, CFStringRef myPeerID
, CFErrorRef
*error
) {
34 SOSRingRef retval
= NULL
;
35 retval
= SOSRingCreate_Internal(name
, 0, error
);
36 if(!retval
) return NULL
;
37 SOSRingSetLastModifier(retval
, myPeerID
);
41 static bool SOSRingResetToEmpty_Basic(SOSRingRef ring
, CFStringRef myPeerID
, CFErrorRef
*error
) {
42 return SOSRingResetToEmpty_Internal(ring
, error
) && SOSRingSetLastModifier(ring
, myPeerID
);
45 static bool SOSRingResetToOffering_Basic(SOSRingRef ring
, SecKeyRef user_privkey
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
46 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
47 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
48 bool retval
= priv
&& myPeerID
&&
49 SOSRingResetToEmpty_Internal(ring
, error
) &&
50 SOSRingAddPeerID(ring
, myPeerID
) &&
51 SOSRingSetLastModifier(ring
, myPeerID
) &&
52 SOSRingGenerationSign_Internal(ring
, priv
, error
);
53 if(user_privkey
) SOSRingConcordanceSign_Internal(ring
, user_privkey
, error
);
58 static SOSRingStatus
SOSRingDeviceIsInRing_Basic(SOSRingRef ring
, CFStringRef peerID
) {
59 if(SOSRingHasPeerID(ring
, peerID
)) return kSOSRingMember
;
60 if(SOSRingHasApplicant(ring
, peerID
)) return kSOSRingApplicant
;
61 if(SOSRingHasRejection(ring
, peerID
)) return kSOSRingReject
;
62 return kSOSRingNotInRing
;
65 static bool SOSRingApply_Basic(SOSRingRef ring
, SecKeyRef user_pubkey
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
67 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
68 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
69 require_action_quiet(SOSRingDeviceIsInRing_Basic(ring
, myPeerID
) == kSOSRingNotInRing
, errOut
, secnotice("ring", "Already associated with ring"));
70 retval
= priv
&& myPeerID
&&
71 SOSRingAddPeerID(ring
, myPeerID
) &&
72 SOSRingSetLastModifier(ring
, myPeerID
) &&
73 SOSRingGenerationSign_Internal(ring
, priv
, error
);
80 static bool SOSRingWithdraw_Basic(SOSRingRef ring
, SecKeyRef user_privkey
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
81 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
82 if(SOSRingHasPeerID(ring
, myPeerID
)) {
83 SOSRingRemovePeerID(ring
, myPeerID
);
84 } else if(SOSRingHasApplicant(ring
, myPeerID
)) {
85 SOSRingRemoveApplicant(ring
, myPeerID
);
86 } else if(SOSRingHasRejection(ring
, myPeerID
)) {
87 SOSRingRemoveRejection(ring
, myPeerID
);
89 SOSCreateError(kSOSErrorPeerNotFound
, CFSTR("Not associated with Ring"), NULL
, error
);
92 SOSRingSetLastModifier(ring
, myPeerID
);
94 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
95 SOSRingGenerationSign_Internal(ring
, priv
, error
);
96 if(user_privkey
) SOSRingConcordanceSign_Internal(ring
, user_privkey
, error
);
101 static bool SOSRingGenerationSign_Basic(SOSRingRef ring
, SecKeyRef user_privkey
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
102 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
103 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
104 bool retval
= priv
&& myPeerID
&&
105 SOSRingSetLastModifier(ring
, myPeerID
) &&
106 SOSRingGenerationSign_Internal(ring
, priv
, error
);
107 if(user_privkey
) SOSRingConcordanceSign_Internal(ring
, user_privkey
, error
);
112 static bool SOSRingConcordanceSign_Basic(SOSRingRef ring
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
113 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
114 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
115 bool retval
= priv
&& myPeerID
&&
116 SOSRingSetLastModifier(ring
, myPeerID
) &&
117 SOSRingConcordanceSign_Internal(ring
, priv
, error
);
122 static bool SOSRingSetPayload_Basic(SOSRingRef ring
, SecKeyRef user_privkey
, CFDataRef payload
, SOSFullPeerInfoRef requestor
, CFErrorRef
*error
) {
123 CFStringRef myPeerID
= SOSPeerInfoGetPeerID(SOSFullPeerInfoGetPeerInfo(requestor
));
124 SecKeyRef priv
= SOSFullPeerInfoCopyDeviceKey(requestor
, error
);
125 bool retval
= priv
&& myPeerID
&&
126 SOSRingSetLastModifier(ring
, myPeerID
) &&
127 SOSRingSetPayload_Internal(ring
, payload
) &&
128 SOSRingGenerationSign_Internal(ring
, priv
, error
);
129 if(user_privkey
) SOSRingConcordanceSign_Internal(ring
, user_privkey
, error
);
134 static CFDataRef
SOSRingGetPayload_Basic(SOSRingRef ring
, CFErrorRef
*error
) {
135 return SOSRingGetPayload_Internal(ring
);
139 ringFuncStruct basic
= {
143 SOSRingResetToEmpty_Basic
,
144 SOSRingResetToOffering_Basic
,
145 SOSRingDeviceIsInRing_Basic
,
147 SOSRingWithdraw_Basic
,
148 SOSRingGenerationSign_Basic
,
149 SOSRingConcordanceSign_Basic
,
150 SOSRingPeerKeyConcordanceTrust
,
153 SOSRingSetPayload_Basic
,
154 SOSRingGetPayload_Basic
,