]>
Commit | Line | Data |
---|---|---|
d8f41ccd A |
1 | #include <Security/SecKeychain.h> |
2 | #include <Security/SecKeychainItem.h> | |
3 | #include <stdlib.h> | |
4 | #include <unistd.h> | |
5 | ||
6 | #include "testmore.h" | |
7 | #include "testenv.h" | |
8 | #include "testleaks.h" | |
9 | ||
10 | void tests(int dont_skip) | |
11 | { | |
12 | SecKeychainRef source, dest; | |
13 | ok_status(SecKeychainCreate("source", 4, "test", FALSE, NULL, &source), | |
14 | "create source keychain"); | |
15 | ok_status(SecKeychainCreate("dest", 4, "test", FALSE, NULL, &dest), | |
16 | "create dest keychain"); | |
17 | SecKeychainItemRef original = NULL; | |
18 | ok_status(SecKeychainAddInternetPassword(source, | |
19 | 19, "members.spamcop.net", | |
20 | 0, NULL, | |
21 | 5, "smith", | |
22 | 0, NULL, | |
23 | 80, kSecProtocolTypeHTTP, | |
24 | kSecAuthenticationTypeDefault, | |
25 | 4, "test", &original), "add internet password"); | |
26 | SecKeychainAttribute origAttrs[] = | |
27 | { | |
28 | { kSecCreationDateItemAttr }, | |
29 | { kSecModDateItemAttr } | |
30 | }; | |
31 | SecKeychainAttributeList origAttrList = | |
32 | { | |
33 | sizeof(origAttrs) / sizeof(*origAttrs), | |
34 | origAttrs | |
35 | }; | |
36 | ok_status(SecKeychainItemCopyContent(original, NULL, &origAttrList, | |
37 | NULL, NULL), "SecKeychainItemCopyContent"); | |
38 | ||
39 | /* Must sleep 1 second to trigger mod date bug. */ | |
40 | sleep(1); | |
41 | SecKeychainItemRef copy; | |
42 | ok_status(SecKeychainItemCreateCopy(original, dest, NULL, ©), | |
43 | "copy item"); | |
44 | ||
45 | SecKeychainAttribute copyAttrs[] = | |
46 | { | |
47 | { kSecCreationDateItemAttr }, | |
48 | { kSecModDateItemAttr } | |
49 | }; | |
50 | SecKeychainAttributeList copyAttrList = | |
51 | { | |
52 | sizeof(copyAttrs) / sizeof(*copyAttrs), | |
53 | copyAttrs | |
54 | }; | |
55 | ok_status(SecKeychainItemCopyContent(copy, NULL, ©AttrList, | |
56 | NULL, NULL), "SecKeychainItemCopyContent"); | |
57 | ||
58 | is(origAttrs[0].length, 16, "creation date length 16"); | |
59 | is(origAttrs[1].length, 16, "mod date length 16"); | |
60 | is(origAttrs[0].length, copyAttrs[0].length, "creation date length same"); | |
61 | is(origAttrs[1].length, copyAttrs[1].length, "mod date length same"); | |
62 | ||
63 | TODO: { | |
64 | todo("<rdar://problem/3731664> Moving/copying a keychain item " | |
65 | "between keychains erroneously updates dates"); | |
66 | ||
67 | diag("original creation: %.*s copy creation: %.*s", | |
68 | (int)origAttrs[0].length, (const char *)origAttrs[0].data, | |
69 | (int)copyAttrs[0].length, (const char *)copyAttrs[0].data); | |
70 | ok(!memcmp(origAttrs[0].data, copyAttrs[0].data, origAttrs[0].length), | |
71 | "creation date same"); | |
72 | ||
73 | diag("original mod: %.*s copy mod: %.*s", | |
74 | (int)origAttrs[1].length, (const char *)origAttrs[1].data, | |
75 | (int)copyAttrs[1].length, (const char *)copyAttrs[1].data); | |
76 | ok(!memcmp(origAttrs[1].data, copyAttrs[1].data, origAttrs[1].length), | |
77 | "mod date same"); | |
78 | } | |
79 | ||
80 | ok_status(SecKeychainItemFreeContent(&origAttrList, NULL), | |
81 | "SecKeychainItemCopyContent"); | |
82 | ok_status(SecKeychainItemFreeContent(©AttrList, NULL), | |
83 | "SecKeychainItemCopyContent"); | |
84 | ||
85 | is(CFGetRetainCount(original), 1, "original retaincount is 1"); | |
86 | CFRelease(original); | |
87 | is(CFGetRetainCount(copy), 1, "copy retaincount is 1"); | |
88 | CFRelease(copy); | |
89 | is(CFGetRetainCount(source), 1, "source retaincount is 1"); | |
90 | ok_status(SecKeychainDelete(source), "delete keychain source"); | |
91 | CFRelease(source); | |
92 | ok_status(SecKeychainDelete(dest), "delete keychain dest"); | |
93 | is(CFGetRetainCount(dest), 1, "dest retaincount is 1"); | |
94 | CFRelease(dest); | |
95 | ||
96 | ok(tests_end(1), "cleanup"); | |
97 | } | |
98 | ||
99 | int main(int argc, char *const *argv) | |
100 | { | |
101 | int dont_skip = argc > 1 && !strcmp(argv[1], "-s"); | |
102 | ||
103 | plan_tests(22); | |
104 | ||
105 | if (!tests_begin(argc, argv)) | |
106 | BAIL_OUT("tests_begin failed"); | |
107 | ||
108 | tests(dont_skip); | |
109 | ok_leaks("no leaks"); | |
110 | ||
111 | return 0; | |
112 | } |