2 * Copyright (c) 2015 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@
24 #include "kc-helpers.h"
25 #include "utilities/SecCFRelease.h"
27 #ifndef kc_item_helpers_h
28 #define kc_item_helpers_h
32 #pragma clang diagnostic push
33 #pragma clang diagnostic ignored "-Wunused-variable"
34 #pragma clang diagnostic ignored "-Wunused-function"
36 static CFMutableDictionaryRef
makeBaseDictionary(CFStringRef itemclass
) {
37 CFMutableDictionaryRef query
= CFDictionaryCreateMutable(NULL
, 0, &kCFTypeDictionaryKeyCallBacks
, &kCFTypeDictionaryValueCallBacks
);
38 CFDictionaryAddValue(query
, kSecReturnRef
, kCFBooleanTrue
);
39 CFDictionarySetValue(query
, kSecClass
, itemclass
);
44 static CFMutableDictionaryRef
convertToQuery(CFMutableDictionaryRef query
, SecKeychainRef kc
) {
45 CFMutableArrayRef searchList
= (CFMutableArrayRef
) CFArrayCreateMutable(kCFAllocatorDefault
, 1, &kCFTypeArrayCallBacks
);
46 CFArrayAppendValue((CFMutableArrayRef
)searchList
, kc
);
47 CFDictionarySetValue(query
, kSecMatchSearchList
, searchList
);
49 CFDictionarySetValue(query
, kSecMatchLimit
, kSecMatchLimitAll
);
54 static CFMutableDictionaryRef
addLabel(CFMutableDictionaryRef query
, CFStringRef label
) {
55 CFDictionarySetValue(query
, kSecAttrLabel
, label
);
59 static CFMutableDictionaryRef
createBaseItemDictionary(CFStringRef itemclass
, CFStringRef service
) {
60 CFMutableDictionaryRef query
= makeBaseDictionary(itemclass
);
62 if(CFEqual(itemclass
, kSecClassInternetPassword
)) {
63 CFDictionarySetValue(query
, kSecAttrServer
, service
== NULL
? CFSTR("test_service") : service
);
64 CFDictionarySetValue(query
, kSecAttrAuthenticationType
, CFSTR("dflt")); // Default, I guess?
66 // Generic passwords have services
67 CFDictionarySetValue(query
, kSecAttrService
, service
== NULL
? CFSTR("test_service") : service
);
72 static CFMutableDictionaryRef
createQueryItemDictionaryWithService(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef service
) {
73 return convertToQuery(createBaseItemDictionary(itemclass
, service
), kc
);
75 static CFMutableDictionaryRef
createQueryItemDictionary(SecKeychainRef kc
, CFStringRef itemclass
) {
76 return createQueryItemDictionaryWithService(kc
, itemclass
, NULL
);
79 static CFMutableDictionaryRef
makeBaseQueryDictionary(SecKeychainRef kc
, CFStringRef itemclass
) {
80 return convertToQuery(makeBaseDictionary(itemclass
), kc
);
83 static CFMutableDictionaryRef
createQueryCustomItemDictionaryWithService(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
, CFStringRef service
) {
84 CFMutableDictionaryRef query
= createQueryItemDictionaryWithService(kc
, itemclass
, service
);
85 CFDictionarySetValue(query
, kSecAttrLabel
, label
);
88 static CFMutableDictionaryRef
createQueryCustomItemDictionary(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
) {
89 return createQueryCustomItemDictionaryWithService(kc
, itemclass
, label
, NULL
);
92 static CFMutableDictionaryRef
createAddCustomItemDictionaryWithService(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
, CFStringRef account
, CFStringRef service
) {
93 CFMutableDictionaryRef query
= createBaseItemDictionary(itemclass
, service
);
95 CFDictionaryAddValue(query
, kSecUseKeychain
, kc
);
96 CFDictionarySetValue(query
, kSecAttrAccount
, account
);
97 CFDictionarySetValue(query
, kSecAttrComment
, CFSTR("a comment"));
98 CFDictionarySetValue(query
, kSecAttrLabel
, label
);
99 CFDataRef data
= CFDataCreate(NULL
, (void*)"data", 4);
100 CFDictionarySetValue(query
, kSecValueData
, data
);
104 static CFMutableDictionaryRef
createAddCustomItemDictionary(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
, CFStringRef account
) {
105 return createAddCustomItemDictionaryWithService(kc
, itemclass
, label
, account
, NULL
);
108 static CFMutableDictionaryRef
createAddItemDictionary(SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
) {
109 return createAddCustomItemDictionary(kc
, itemclass
, label
, CFSTR("test_account"));
112 static SecKeychainItemRef
createCustomItem(const char* name
, SecKeychainRef kc
, CFDictionaryRef CF_CONSUMED addDictionary
) {
113 CFTypeRef result
= NULL
;
114 ok_status(SecItemAdd(addDictionary
, &result
), "%s: SecItemAdd", name
);
115 ok(result
!= NULL
, "%s: SecItemAdd returned a result", name
);
117 SecKeychainItemRef item
= (SecKeychainItemRef
) result
;
118 ok(item
!= NULL
, "%s: Couldn't convert into SecKeychainItemRef", name
);
122 #define createCustomItemTests 3
124 static SecKeychainItemRef
makeItem(const char* name
, SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
) {
125 CFMutableDictionaryRef query
= createAddItemDictionary(kc
, itemclass
, label
);
127 SecKeychainItemRef item
= createCustomItem(name
, kc
, query
);
129 CFReleaseNull(query
);
132 #define makeItemTests createCustomItemTests
134 static void makeCustomDuplicateItem(const char* name
, SecKeychainRef kc
, CFStringRef itemclass
, CFStringRef label
) {
135 CFMutableDictionaryRef query
= createAddItemDictionary(kc
, itemclass
, label
);
137 CFTypeRef result
= NULL
;
138 is(SecItemAdd(query
, &result
), errSecDuplicateItem
, "%s: SecItemAdd (duplicate)", name
);
140 CFReleaseNull(query
);
142 #define makeCustomDuplicateItemTests 1
144 static void makeDuplicateItem(const char* name
, SecKeychainRef kc
, CFStringRef itemclass
) {
145 return makeCustomDuplicateItem(name
, kc
, itemclass
, CFSTR("test_label"));
147 #define makeDuplicateItemTests makeCustomDuplicateItemTests
150 #pragma clang diagnostic pop
153 #endif /* TARGET_OS_MAC */
155 #endif /* kc_item_helpers_h */