2  * Copyright (c) 2000-2004,2006-2007,2011-2012 Apple Inc. All Rights Reserved. 
   4  * @APPLE_LICENSE_HEADER_START@ 
   6  * This file contains Original Code and/or Modifications of Original Code 
   7  * as defined in and that are subject to the Apple Public Source License 
   8  * Version 2.0 (the 'License'). You may not use this file except in 
   9  * compliance with the License. Please obtain a copy of the License at 
  10  * http://www.opensource.apple.com/apsl/ and read it before using this 
  13  * The Original Code and all software distributed under the License are 
  14  * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 
  15  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 
  16  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 
  17  * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 
  18  * Please see the License for the specific language governing rights and 
  19  * limitations under the License. 
  21  * @APPLE_LICENSE_HEADER_END@ 
  26 // cssmaclpod - enhanced PodWrappers for ACL-related CSSM data structures 
  28 #include <security_cdsa_utilities/cssmaclpod.h> 
  29 #include <security_cdsa_utilities/cssmwalkers.h> 
  37 // AclAuthorizationSets 
  39 AclAuthorizationSet::AclAuthorizationSet(AclAuthorization auth0
, AclAuthorization auth
, ...) 
  47                 auth 
= va_arg(args
, AclAuthorization
); 
  54 // AclAuthorizationGroups 
  56 AuthorizationGroup::AuthorizationGroup(const AclAuthorizationSet 
&auths
, Allocator 
&alloc
) 
  58         NumberOfAuthTags 
= (uint32
)auths
.size(); 
  59         AuthTags 
= alloc
.alloc
<CSSM_ACL_AUTHORIZATION_TAG
>(NumberOfAuthTags
); 
  60         copy(auths
.begin(), auths
.end(), AuthTags
);     // happens to be sorted 
  63 AuthorizationGroup::AuthorizationGroup(CSSM_ACL_AUTHORIZATION_TAG tag
, Allocator 
&alloc
) 
  65         AuthTags 
= alloc
.alloc
<CSSM_ACL_AUTHORIZATION_TAG
>(1); 
  70 void AuthorizationGroup::destroy(Allocator 
&alloc
) 
  75 bool AuthorizationGroup::contains(CSSM_ACL_AUTHORIZATION_TAG tag
) const 
  77         return find(AuthTags
, &AuthTags
[NumberOfAuthTags
], tag
) != &AuthTags
[NumberOfAuthTags
]; 
  81 AuthorizationGroup::operator AclAuthorizationSet() const 
  83         return AclAuthorizationSet(AuthTags
, &AuthTags
[NumberOfAuthTags
]); 
  86 AclEntryPrototype::AclEntryPrototype(const AclOwnerPrototype 
&proto
) 
  88         memset(this, 0, sizeof(*this)); 
  89         TypedSubject 
= proto
.subject(); Delegate 
= proto
.delegate(); 
  90         //@@@ set authorization to "is owner" pseudo-auth? See cssmacl.h 
  93 void AclEntryPrototype::tag(const char *tagString
) 
  95         if (tagString 
== NULL
) 
  97         else if (strlen(tagString
) > CSSM_MODULE_STRING_SIZE
) 
  98                 CssmError::throwMe(CSSM_ERRCODE_INVALID_ACL_ENTRY_TAG
); 
 100                 strcpy(EntryTag
, tagString
); 
 103 void AclEntryPrototype::tag(const string 
&tagString
) 
 105         if (tagString
.length() > CSSM_MODULE_STRING_SIZE
) 
 106                 CssmError::throwMe(CSSM_ERRCODE_INVALID_ACL_ENTRY_TAG
); 
 108                 memcpy(EntryTag
, tagString
.c_str(), tagString
.length() + 1); 
 112 AclOwnerPrototype 
*AutoAclOwnerPrototype::make() 
 114         if (!mAclOwnerPrototype
) { 
 115                 mAclOwnerPrototype 
= (AclOwnerPrototype
*) mAllocator
->malloc(sizeof(AclOwnerPrototype
)); 
 116         new (mAclOwnerPrototype
) AclOwnerPrototype
; 
 117                 mAclOwnerPrototype
->clearPod(); 
 119         return mAclOwnerPrototype
; 
 122 AutoAclOwnerPrototype::~AutoAclOwnerPrototype() 
 125                 DataWalkers::chunkFree(mAclOwnerPrototype
, *mAllocator
); 
 129 AutoAclOwnerPrototype::allocator(Allocator 
&allocator
) 
 131         mAllocator 
= &allocator
; 
 135 void AutoAclEntryInfoList::size(uint32 newSize
) 
 138         mEntries 
= mAllocator
->alloc
<AclEntryInfo
>(mEntries
, newSize
); 
 139         for (uint32 n 
= mCount
; n 
< newSize
; n
++) 
 140                 mEntries
[n
].clearPod(); 
 145 AclEntryInfo 
&AutoAclEntryInfoList::at(uint32 ix
) 
 148                 size(ix 
+ 1);   // expand vector 
 153 void AutoAclEntryInfoList::clear() 
 157                 DataWalkers::ChunkFreeWalker 
w(*mAllocator
); 
 158                 for (uint32 ix 
= 0; ix 
< mCount
; ix
++) 
 159                         walk(w
, mEntries
[ix
]); 
 160                 mAllocator
->free(mEntries
); 
 166 void AutoAclEntryInfoList::allocator(Allocator 
&allocator
) 
 168         mAllocator 
= &allocator
; 
 172 void AutoAclEntryInfoList::add(const TypedList 
&subj
, const AclAuthorizationSet 
&auths
, const char *tag 
/* = NULL */) 
 174         AclEntryInfo 
&info 
= at(size()); 
 175         info
.proto() = AclEntryPrototype(subj
); 
 176         info
.proto().authorization() = AuthorizationGroup(auths
, allocator()); 
 177         info
.proto().tag(tag
); 
 181 void AutoAclEntryInfoList::addPin(const TypedList 
&subj
, uint32 slot
) 
 184         snprintf(tag
, sizeof(tag
), "PIN%d", slot
); 
 185         add(subj
, CSSM_ACL_AUTHORIZATION_PREAUTH(slot
), tag
); 
 188 void AutoAclEntryInfoList::addPinState(uint32 slot
, uint32 status
) 
 191         snprintf(tag
, sizeof(tag
), "PIN%d?", slot
); 
 192         TypedList 
subj(allocator(), CSSM_WORDID_PIN
, 
 193                 new(allocator()) ListElement(slot
), 
 194                 new(allocator()) ListElement(status
)); 
 195         add(subj
, CSSM_WORDID_PIN
, tag
); 
 198 void AutoAclEntryInfoList::addPinState(uint32 slot
, uint32 status
, uint32 count
) 
 201         snprintf(tag
, sizeof(tag
), "PIN%d?", slot
); 
 202         TypedList 
subj(allocator(), CSSM_WORDID_PIN
, 
 203                 new(allocator()) ListElement(slot
), 
 204                 new(allocator()) ListElement(status
), 
 205                 new(allocator()) ListElement(count
)); 
 206         add(subj
, CSSM_WORDID_PIN
, tag
); 
 209 uint32 
pinFromAclTag(const char *tag
, const char *suffix 
/* = NULL */) 
 213                 snprintf(format
, sizeof(format
), "PIN%%d%s%%n", suffix 
? suffix 
: ""); 
 216                 sscanf(tag
, format
, &pin
, &consumed
); 
 217                 if (consumed 
== strlen(tag
))    // complete and sufficient 
 223 }       // namespace Security