2 * Copyright (c) 2007-2009,2013-2014 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@
25 #include <TargetConditionals.h>
26 #include <CoreFoundation/CoreFoundation.h>
27 #include <Foundation/Foundation.h>
28 #include <Security/Security.h>
29 #include <Security/SecRandom.h>
30 #include <CommonCrypto/CommonDigest.h>
31 #include <Security/SecKeyPriv.h>
32 #include <Security/SecItem.h>
33 #include <Security/SecCertificatePriv.h>
35 #include <corecrypto/ccsha1.h>
36 #include <corecrypto/ccsha2.h>
38 #include "keychain_regressions.h"
39 #include "utilities/SecCFRelease.h"
40 #include "utilities/array_size.h"
43 static void testdigestandsignalg(SecKeyRef privKey, SecKeyRef pubKey, const SecAsn1AlgId *algId) {
44 uint8_t dataToDigest[256];
45 size_t dataToDigestLen = sizeof(dataToDigest);
46 size_t sigLen = SecKeyGetSize(privKey, kSecKeySignatureSize);
50 oid.length = algId->algorithm.Length;
51 oid.data = algId->algorithm.Data;
53 /* Get the oid in decimal for display purposes. */
54 CFStringRef oidStr = SecDERItemCopyOIDDecimalRepresentation(kCFAllocatorDefault, &oid);
56 CFStringGetCString(oidStr, oidBuf, sizeof(oidBuf), kCFStringEncodingUTF8);
63 ok_status(status = SecKeyDigestAndSign(privKey, algId, dataToDigest, dataToDigestLen,
64 sig, &sigLen), "digest and sign %s with %ld bit RSA key", oidBuf, sigLen * 8);
66 skip("SecKeyDigestAndSign failed", 3, status == errSecSuccess);
68 /* Verify the signature we just made. */
69 ok_status(SecKeyDigestAndVerify(pubKey, algId, dataToDigest, dataToDigestLen,
70 sig, sigLen), "digest and verify");
71 /* Invalidate the signature. */
73 is_status(SecKeyDigestAndVerify(pubKey, algId, dataToDigest, dataToDigestLen,
74 sig, sigLen), errSSLCrypto, "digest and verify bad sig");
76 dataToDigest[0] ^= 0xff;
77 is_status(SecKeyDigestAndVerify(pubKey, algId, dataToDigest, dataToDigestLen,
78 sig, sigLen), errSSLCrypto, "digest and verify bad digest");
82 static void testdigestandsign(SecKeyRef privKey, SecKeyRef pubKey) {
83 static const SecAsn1Oid *oids[] = {
85 &CSSMOID_SHA224WithRSA,
86 &CSSMOID_SHA256WithRSA,
87 &CSSMOID_SHA384WithRSA,
88 &CSSMOID_SHA512WithRSA,
90 &CSSMOID_SHA1WithRSA_OIW,
91 &CSSMOID_SHA1WithDSA, // BSAFE
92 &CSSMOID_SHA1WithDSA_CMS, // X509/CMS
93 &CSSMOID_SHA1WithDSA_JDK, // JDK 1.1
99 SecAsn1AlgId algId = {};
100 for (ix = 0; ix < sizeof(oids) / sizeof(*oids); ++ix) {
102 algId.algorithm = *oids[ix];
104 algId.algorithm.Length = 0;
105 algId.algorithm.Data = NULL;
108 testdigestandsignalg(privKey, pubKey, &algId);
114 static void dump_bytes(uint8_t* bytes, size_t amount)
117 printf("0x%02x ", *bytes);
125 #if !TARGET_OS_IPHONE
126 #define kEncryptDecryptTestCount 0
128 #define kEncryptDecryptTestCount 6
129 static void test_encrypt_decrypt(SecKeyRef pubKey, SecKeyRef privKey, uint32_t padding, size_t keySizeInBytes)
132 size_t max_len = keySizeInBytes;
134 case kSecPaddingNone: max_len = keySizeInBytes; break;
135 case kSecPaddingOAEP: max_len = keySizeInBytes - 2 - 2 * CC_SHA1_DIGEST_LENGTH; break;
136 case kSecPaddingPKCS1: max_len = keySizeInBytes - 11; break;
137 default: skip("what is the max_len for this padding?", 5, false);
140 uint8_t secret[max_len + 1], encrypted_secret[keySizeInBytes], decrypted_secret[keySizeInBytes];
141 uint8_t *secret_ptr = secret;
142 size_t secret_len = max_len;
143 size_t encrypted_secret_len = sizeof(encrypted_secret);
144 size_t decrypted_secret_len = sizeof(decrypted_secret);
145 memset(decrypted_secret, 0xff, decrypted_secret_len);
146 ok_status(SecRandomCopyBytes(kSecRandomDefault, sizeof(secret), secret),"rng");
148 // zero pad, no accidental second zero byte
149 if (padding == kSecPaddingNone) {
154 is_status(SecKeyEncrypt(pubKey, padding,
155 secret, sizeof(secret),
156 encrypted_secret, &encrypted_secret_len), errSecParam, "encrypt secret (overflow)");
157 ok_status(SecKeyEncrypt(pubKey, padding,
159 encrypted_secret, &encrypted_secret_len), "encrypt secret");
161 ok_status(SecKeyDecrypt(privKey, padding,
162 encrypted_secret, encrypted_secret_len,
163 decrypted_secret, &decrypted_secret_len), "decrypt secret");
165 // zero padding is removed on decode
166 if (padding == kSecPaddingNone) {
171 ok(decrypted_secret_len == secret_len, "correct length");
172 ok_status(memcmp(secret_ptr, decrypted_secret, secret_len), "verify secret");
177 #define kKeyGenTestCount (12 + (3*kEncryptDecryptTestCount))
178 static void testkeygen(size_t keySizeInBits) {
179 SecKeyRef pubKey = NULL, privKey = NULL;
180 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
183 kzib = CFNumberCreate(NULL, kCFNumberSInt64Type, &keySizeInBits);
184 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
185 CFDictionaryAddValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
186 CFDictionaryAddValue(kgp, kSecAttrKeySizeInBits, kzib);
189 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
190 "Generate %ld bit (%ld byte) RSA keypair", keySizeInBits,
196 skip("keygen failed", 8, status == errSecSuccess);
197 ok(pubKey, "pubkey returned");
198 ok(privKey, "privKey returned");
199 is(SecKeyGetBlockSize(pubKey) * 8, (size_t) keySizeInBits, "public key size is ok");
200 is(SecKeyGetBlockSize(privKey) * 8, (size_t) keySizeInBits, "private key size is ok");
202 /* Sign something. */
203 uint8_t something[keySizeInBytes];
204 size_t something_len = keySizeInBytes - 11;
205 ok_status(SecRandomCopyBytes(kSecRandomDefault, sizeof(something), something), "rng");
206 uint8_t sig[keySizeInBytes];
207 size_t sigLen = sizeof(sig);
209 /* TODO: This is returning another error on OS X */
210 is_status(SecKeyRawSign(privKey, kSecPaddingPKCS1,
211 something, something_len + 1, sig, &sigLen),
212 errSecParam, "sign overflow");
214 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1,
215 something, something_len, sig, &sigLen), "sign something");
216 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1,
217 something, something_len, sig, sigLen), "verify sig on something");
219 // Torture test ASN.1 encoder by setting high bit to 1.
220 uint8_t digest[CC_SHA512_DIGEST_LENGTH] = {
221 0x80, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
222 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
223 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
224 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
225 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
226 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
227 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
228 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
231 /* Thoses tests are making sure that MD2 and MD5 are NOT supported,
232 but they still are on OS X */
234 //CC_MD2(something, sizeof(something), digest);
235 ok_status(!SecKeyRawSign(privKey, kSecPaddingPKCS1MD2,
236 digest, CC_MD2_DIGEST_LENGTH, sig, &sigLen),
237 "don't sign md2 digest"); //FAIL
238 ok_status(!SecKeyRawVerify(pubKey, kSecPaddingPKCS1MD2,
239 digest, CC_MD2_DIGEST_LENGTH, sig, sigLen),
240 "verify sig on md2 digest fails"); //FAIL
242 //CC_MD5(something, sizeof(something), digest);
243 sigLen = sizeof(sig);
244 ok_status(!SecKeyRawSign(privKey, kSecPaddingPKCS1MD5,
245 digest, CC_MD5_DIGEST_LENGTH, sig, &sigLen),
246 "don't sign md5 digest"); //FAIL
247 ok_status(!SecKeyRawVerify(pubKey, kSecPaddingPKCS1MD5,
248 digest, CC_MD5_DIGEST_LENGTH, sig, sigLen),
249 "verify sig on md5 digest fails"); //FAIL
252 //CCDigest(kCCDigestSHA1, something, sizeof(something), digest);
253 sigLen = sizeof(sig);
254 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1SHA1,
255 digest, CC_SHA1_DIGEST_LENGTH, sig, &sigLen),
257 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1SHA1,
258 digest, CC_SHA1_DIGEST_LENGTH, sig, sigLen),
259 "verify sig on sha1 digest");
262 /* The assumptions in these tests are just wrong on OS X */
263 uint8_t signature[keySizeInBytes], *ptr = signature;
264 size_t signature_len = sizeof(signature);
265 ok_status(SecKeyEncrypt(pubKey, kSecPaddingNone, sig, sigLen, signature, &signature_len), "inspect signature");
266 is(signature_len, keySizeInBytes - 1, "got signature"); // FAIL for 2056
267 while(*ptr && ((size_t)(ptr - signature) < signature_len)) ptr++;
268 is(signature + signature_len - ptr, 16 /* length(\0 || OID_SHA1) */ + CC_SHA1_DIGEST_LENGTH, "successful decode");
272 /* Those are not supported on OS X */
273 /* PKCS1 padding is 00 01 PAD * 8 or more 00 data.
274 data is SEQ { SEQ { OID NULL } BIT STRING 00 DIGEST }
275 So min data + pad overhead is 11 + 9 + oidlen
276 oidlen = 11 for the sha2 family of oids, so we have 29 bytes; or
277 232 bits of minimum overhead. */
278 const size_t pkcs1Overhead = 232;
279 if (keySizeInBits > 224 + pkcs1Overhead) {
280 //CC_SHA224(something, sizeof(something), digest);
281 sigLen = sizeof(sig);
282 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1SHA224,
283 digest, CC_SHA224_DIGEST_LENGTH, sig, &sigLen),
284 "sign sha224 digest");
285 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1SHA224,
286 digest, CC_SHA224_DIGEST_LENGTH, sig, sigLen),
287 "verify sig on sha224 digest");
290 if (keySizeInBits > 256 + pkcs1Overhead) {
291 //CC_SHA256(something, sizeof(something), digest);
292 sigLen = sizeof(sig);
293 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1SHA256,
294 digest, CC_SHA256_DIGEST_LENGTH, sig, &sigLen),
295 "sign sha256 digest");
296 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1SHA256,
297 digest, CC_SHA256_DIGEST_LENGTH, sig, sigLen),
298 "verify sig on sha256 digest");
301 if (keySizeInBits > 384 + pkcs1Overhead) {
302 //CC_SHA384(something, sizeof(something), digest);
303 sigLen = sizeof(sig);
304 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1SHA384,
305 digest, CC_SHA384_DIGEST_LENGTH, sig, &sigLen),
306 "sign sha384 digest");
307 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1SHA384,
308 digest, CC_SHA384_DIGEST_LENGTH, sig, sigLen),
309 "verify sig on sha384 digest");
312 if (keySizeInBits > 512 + pkcs1Overhead) {
313 //CC_SHA512(something, sizeof(something), digest);
314 sigLen = sizeof(sig);
315 ok_status(SecKeyRawSign(privKey, kSecPaddingPKCS1SHA512,
316 digest, CC_SHA512_DIGEST_LENGTH, sig, &sigLen),
317 "sign sha512 digest");
318 ok_status(SecKeyRawVerify(pubKey, kSecPaddingPKCS1SHA512,
319 digest, CC_SHA512_DIGEST_LENGTH, sig, sigLen),
320 "verify sig on sha512 digest");
323 test_encrypt_decrypt(pubKey, privKey, kSecPaddingNone, keySizeInBytes);
324 test_encrypt_decrypt(pubKey, privKey, kSecPaddingPKCS1, keySizeInBytes);
325 test_encrypt_decrypt(pubKey, privKey, kSecPaddingOAEP, keySizeInBytes);
327 testdigestandsign(privKey, pubKey);
330 const void *privkeys[] = {
333 const void *privvalues[] = {
336 CFDictionaryRef privitem = CFDictionaryCreate(NULL, privkeys, privvalues,
337 sizeof(privkeys) / sizeof(*privkeys), NULL, NULL);
339 /* OS X: keys are always added to the keychain when generated */
340 ok_status(SecItemAdd(privitem, NULL), "add private key"); //FAIL
342 ok_status(SecItemDelete(privitem), "delete private key");
343 CFReleaseNull(privitem);
345 const void *pubkeys[] = {
348 const void *pubvalues[] = {
351 CFDictionaryRef pubitem = CFDictionaryCreate(NULL, pubkeys, pubvalues,
352 sizeof(pubkeys) / sizeof(*pubkeys), NULL, NULL);
354 /* OS X: keys are always added to the keychain when generated */
355 ok_status(SecItemAdd(pubitem, NULL), "add public key"); //FAIL
357 ok_status(SecItemDelete(pubitem), "delete public key");
358 CFReleaseNull(pubitem);
361 CFReleaseNull(pubKey);
362 CFReleaseNull(privKey);
366 #define kKeyGen2TestCount 11
367 static void testkeygen2(size_t keySizeInBits) {
368 SecKeyRef pubKey = NULL, privKey = NULL;
369 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
372 CFUUIDRef ourUUID = CFUUIDCreate(kCFAllocatorDefault);
373 CFStringRef uuidString = CFUUIDCreateString(kCFAllocatorDefault, ourUUID);
374 CFMutableStringRef publicName = CFStringCreateMutableCopy(kCFAllocatorDefault, 0, uuidString);
375 CFMutableStringRef privateName = CFStringCreateMutableCopy(kCFAllocatorDefault, 0, uuidString);
377 CFReleaseNull(ourUUID);
378 CFReleaseNull(uuidString);
380 CFStringAppend(publicName, CFSTR("-Public-40"));
381 CFStringAppend(privateName, CFSTR("-Private-40"));
382 CFMutableDictionaryRef pubd = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
383 CFMutableDictionaryRef privd = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
385 CFDictionaryAddValue(pubd, kSecAttrLabel, publicName);
386 CFDictionaryAddValue(privd, kSecAttrLabel, privateName);
388 kzib = CFNumberCreate(NULL, kCFNumberSInt64Type, &keySizeInBits);
389 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
390 CFDictionaryAddValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
391 CFDictionaryAddValue(kgp, kSecAttrKeySizeInBits, kzib);
392 CFDictionaryAddValue(kgp, kSecAttrIsPermanent, kCFBooleanTrue);
393 CFDictionaryAddValue(kgp, kSecPublicKeyAttrs, pubd);
394 CFDictionaryAddValue(kgp, kSecPrivateKeyAttrs, privd);
397 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
398 "Generate %ld bit (%ld byte) persistent RSA keypair",
399 keySizeInBits, keySizeInBytes);
404 skip("keygen failed", 8, status == errSecSuccess);
405 ok(pubKey, "pubkey returned");
406 ok(privKey, "privKey returned");
407 is(SecKeyGetBlockSize(pubKey) * 8, (size_t) keySizeInBits, "public key size is ok");
408 is(SecKeyGetBlockSize(privKey) * 8, (size_t) keySizeInBits, "private key size is ok");
410 SecKeyRef pubKey2, privKey2;
411 CFDictionaryAddValue(pubd, kSecClass, kSecClassKey);
412 CFDictionaryAddValue(pubd, kSecReturnRef, kCFBooleanTrue);
413 CFDictionaryAddValue(privd, kSecClass, kSecClassKey);
414 CFDictionaryAddValue(privd, kSecReturnRef, kCFBooleanTrue);
415 CFDictionaryAddValue(privd, kSecAttrCanSign, kCFBooleanTrue);
416 ok_status(SecItemCopyMatching(pubd, (CFTypeRef *)&pubKey2),
417 "retrieve pub key by label");
418 ok_status(SecItemCopyMatching(privd, (CFTypeRef *)&privKey2),
419 "retrieve priv key by label and kSecAttrCanSign");
421 /* Sign something. */
422 uint8_t something[50] = {0x80, 0xbe, 0xef, 0xba, 0xd0, };
423 uint8_t sig[keySizeInBytes];
424 size_t sigLen = keySizeInBytes;
425 ok_status(SecKeyRawSign(privKey2, kSecPaddingPKCS1,
426 something, sizeof(something), sig, &sigLen), "sign something");
427 ok_status(SecKeyRawVerify(pubKey2, kSecPaddingPKCS1,
428 something, sizeof(something), sig, sigLen), "verify sig on something");
431 /* SecKeyEncrypt does not return errSecParam on OS X in that case */
432 sigLen = keySizeInBytes;
433 is_status(SecKeyEncrypt(pubKey2, kSecPaddingPKCS1SHA1,
434 something, sizeof(something), sig, &sigLen), errSecParam,
435 "encrypt something with invalid padding");
439 CFReleaseNull(pubKey2);
440 CFReleaseNull(privKey2);
442 /* delete from keychain - note: do it before releasing publicName and privateName
443 because pubd and privd have no retain/release callbacks */
444 ok_status(SecItemDelete(pubd), "delete generated pub key");
445 ok_status(SecItemDelete(privd), "delete generated priv key");
449 CFReleaseNull(pubKey);
450 CFReleaseNull(privKey);
452 CFReleaseNull(publicName);
453 CFReleaseNull(privateName);
460 #if !TARGET_OS_IPHONE
461 // Only exists currently in MacOSX
462 typedef struct KDFVector_t {
469 int expected_failure;
472 static KDFVector kdfv[] = {
473 // Test Case PBKDF2 - HMACSHA1 http://tools.ietf.org/html/draft-josefsson-pbkdf2-test-vectors-00
474 { "password", "salt", 1, 1, 160, "0c60c80f961f0e71f3a9b524af6012062fe037a6", 0 },
475 { "password", "salt", 2, 1, 160, "ea6c014dc72d6f8ccd1ed92ace1d41f0d8de8957", 0 },
476 { "password", "salt", 4096, 1, 160, "4b007901b765489abead49d926f721d065a429c1", 0 },
477 { "password", "salt", 1, 0, 160, NULL, -1} // This crashed
480 static size_t kdfvLen = sizeof(kdfv) / sizeof(KDFVector);
482 static int testSecKDF(CFStringRef password, CFDataRef salt, CFNumberRef rounds, CFStringRef alg, CFNumberRef dklen, CFDataRef expected, int expected_failure) {
483 CFMutableDictionaryRef parameters = CFDictionaryCreateMutable(kCFAllocatorDefault, 4, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
486 CFDictionaryAddValue(parameters, kSecAttrSalt, salt);
487 CFDictionaryAddValue(parameters, kSecAttrKeySizeInBits, dklen);
488 CFDictionaryAddValue(parameters, kSecAttrPRF, alg);
489 CFDictionaryAddValue(parameters, kSecAttrRounds, rounds);
491 SecKeyRef derivedKey = SecKeyDeriveFromPassword(password, parameters, NULL);
492 if(derivedKey == NULL && expected_failure) {
493 ok(1, "Correctly failed to produce a key");
495 } else if(derivedKey == NULL) {
496 ok(0, "Could not generate a key when we should have");
499 ok(1, "Made a new key");
501 // NEEDS Fix -- ok(status = expectedEqualsComputed(expected, derivedKey), "Derived key is as expected");
503 if(parameters) CFRelease(parameters);
504 if(derivedKey) CFRelease(derivedKey);
508 static CFDataRef CFDataCreateFromHexBytes(char *s) {
510 size_t len = strlen(s);
511 if(len%2) return NULL;
514 for(size_t i=0; i<len; i++) {
515 buf[i] = s[i*2] * 16 + s[i*2+1];
517 CFDataRef retval = CFDataCreate(NULL, buf, len);
523 PBKDF2Test(KDFVector *kdfvec)
525 CFDataRef expectedBytes = CFDataCreateFromHexBytes(kdfvec->expectedstr);
526 CFStringRef password = CFStringCreateWithCString(NULL, kdfvec->password, kCFStringEncodingUTF8);
527 CFDataRef salt = CFDataCreate(NULL, (const UInt8 *)kdfvec->salt, strlen(kdfvec->salt));
528 CFNumberRef rounds = CFNumberCreate(NULL, kCFNumberIntType, &kdfvec->rounds);
529 CFNumberRef dklen = CFNumberCreate(NULL, kCFNumberIntType, &kdfvec->dklen);
532 ok(testSecKDF(password, salt, rounds, kSecAttrPRFHmacAlgSHA1, dklen, expectedBytes, kdfvec->expected_failure), "Test SecKeyDeriveFromPassword PBKDF2");
534 CFReleaseNull(expectedBytes);
535 CFReleaseNull(password);
537 CFReleaseNull(rounds);
538 CFReleaseNull(dklen);
544 static void testkeyderivation() {
545 for(size_t testcase = 0; testcase < kdfvLen; testcase++) {
546 // diag("Test %lu\n", testcase + 1);
547 ok(PBKDF2Test(&kdfv[testcase]), "Successful full test of KDF Vector");
552 static size_t kdfvLen = 0; // no kdf functions in Sec for iphone
553 #endif /* !TARGET_OS_IPHONE */
555 static void delete_key(SecKeyRef *key) {
556 CFMutableDictionaryRef query = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
557 &kCFTypeDictionaryValueCallBacks);
558 CFDictionarySetValue(query, kSecValueRef, *key);
559 SecItemDelete(query);
560 CFReleaseNull(query);
564 static const int kTestSupportedCount = 3 + (4 * 12) + 2 + (4 * 10) + 2;
565 static void testsupportedalgos(size_t keySizeInBits)
567 SecKeyRef pubKey = NULL, privKey = NULL;
568 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
571 int32_t iKeySizeInBits = (int32_t) keySizeInBits;
572 kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &iKeySizeInBits);
573 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
574 CFDictionaryAddValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
575 CFDictionaryAddValue(kgp, kSecAttrKeySizeInBits, kzib);
578 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
579 "Generate %ld bit (%ld byte) persistent RSA keypair",
580 keySizeInBits, keySizeInBytes);
584 is(SecKeyGetBlockSize(pubKey) * 8, (size_t) keySizeInBits, "public key size is ok");
585 is(SecKeyGetBlockSize(privKey) * 8, (size_t) keySizeInBits, "private key size is ok");
587 const SecKeyAlgorithm sign[] = {
588 kSecKeyAlgorithmRSASignatureRaw,
589 kSecKeyAlgorithmRSASignatureDigestPKCS1v15Raw,
590 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1,
591 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA1,
592 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA224,
593 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA224,
594 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA256,
595 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256,
596 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA384,
597 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA384,
598 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA512,
599 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA512,
602 for (size_t i = 0; i < array_size(sign); i++) {
603 SecKeyAlgorithm algorithm = CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("%@"), sign[i]);
604 ok(SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeSign, algorithm),
605 "privKey supports sign algorithm %@", algorithm);
606 ok(SecKeyIsAlgorithmSupported(pubKey, kSecKeyOperationTypeVerify, algorithm),
607 "pubKey supports verify algorithm %@", algorithm);
608 // Since private key supports RSA decryption, our verify adapters happily accepts it.
609 ok(SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeVerify, algorithm),
610 "privKey supports verify algorithm %@", algorithm);
611 ok(!SecKeyIsAlgorithmSupported(pubKey, kSecKeyOperationTypeSign, algorithm),
612 "pubKey doesn't support sign algorithm %@", algorithm);
613 CFReleaseNull(algorithm);
615 ok(!SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeSign, kSecKeyAlgorithmECDSASignatureDigestX962),
616 "RSA privKey does not support ECDSA algorithm");
617 ok(!SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeVerify, kSecKeyAlgorithmECDSASignatureDigestX962),
618 "RSA pubKey does not support ECDSA algorithm");
620 const SecKeyAlgorithm crypt[] = {
621 kSecKeyAlgorithmRSAEncryptionRaw,
622 kSecKeyAlgorithmRSAEncryptionPKCS1,
623 kSecKeyAlgorithmRSAEncryptionOAEPSHA1,
624 kSecKeyAlgorithmRSAEncryptionOAEPSHA224,
625 kSecKeyAlgorithmRSAEncryptionOAEPSHA256,
626 kSecKeyAlgorithmRSAEncryptionOAEPSHA384,
627 kSecKeyAlgorithmRSAEncryptionOAEPSHA1AESGCM,
628 kSecKeyAlgorithmRSAEncryptionOAEPSHA224AESGCM,
629 kSecKeyAlgorithmRSAEncryptionOAEPSHA256AESGCM,
630 kSecKeyAlgorithmRSAEncryptionOAEPSHA384AESGCM,
631 // kSecKeyAlgorithmRSAEncryptionOAEPSHA512,
633 for (size_t i = 0; i < array_size(crypt); i++) {
634 SecKeyAlgorithm algorithm = CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("%@"), crypt[i]);
635 ok(SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeDecrypt, algorithm),
636 "privKey supports decrypt algorithm %@", algorithm);
637 ok(SecKeyIsAlgorithmSupported(pubKey, kSecKeyOperationTypeEncrypt, algorithm),
638 "pubKey supports encrypt algorithm %@", algorithm);
639 ok(!SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeEncrypt, algorithm),
640 "privKey doesn't supports encrypt algorithm %@", algorithm);
641 ok(!SecKeyIsAlgorithmSupported(pubKey, kSecKeyOperationTypeDecrypt, algorithm),
642 "pubKey doesn't support decrypt algorithm %@", algorithm);
643 CFReleaseNull(algorithm);
645 ok(!SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeDecrypt, kSecKeyAlgorithmRSAEncryptionOAEPSHA512),
646 "privKey doesn't support decrypt algorithm %@", kSecKeyAlgorithmRSAEncryptionOAEPSHA512);
647 ok(!SecKeyIsAlgorithmSupported(privKey, kSecKeyOperationTypeDecrypt, kSecKeyAlgorithmRSAEncryptionOAEPSHA512AESGCM),
648 "privKey doesn't support decrypt algorithm %@", kSecKeyAlgorithmRSAEncryptionOAEPSHA512AESGCM);
652 delete_key(&privKey);
656 #define kTestSupportedCount 15
657 static void testsupportedalgos(size_t keySizeInBits)
659 SecKeyRef pubKey = NULL, privKey = NULL;
660 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
663 int32_t iKeySizeInBits = (int32_t) keySizeInBits;
664 kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &iKeySizeInBits);
665 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
666 CFDictionaryAddValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
667 CFDictionaryAddValue(kgp, kSecAttrKeySizeInBits, kzib);
668 CFDictionaryAddValue(kgp, kSecAttrLabel, CFSTR("sectests:testsupportedalgos"));
671 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
672 "Generate %ld bit (%ld byte) persistent RSA keypair",
673 keySizeInBits, keySizeInBytes);
677 is(SecKeyGetBlockSize(pubKey) * 8, (size_t) keySizeInBits, "public key size is ok");
678 is(SecKeyGetBlockSize(privKey) * 8, (size_t) keySizeInBits, "private key size is ok");
680 CFSetRef keySet, expectedSet;
682 CFIndex value = kSecKeyAlgorithmECDSASignatureDigestX962;
683 CFNumberRef ECDSAX962 = CFNumberCreate(NULL, kCFNumberCFIndexType, &value);
684 value = kSecKeyAlgorithmRSAEncryptionRaw;
685 CFNumberRef RSARaw = CFNumberCreate(NULL, kCFNumberCFIndexType, &value);
688 keySet = SecKeyCopySupportedAlgorithms(privKey, kSecKeyOperationTypeSign);
689 const SecKeyAlgorithm sign[] = {
690 kSecKeyAlgorithmRSASignatureRaw,
691 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1,
692 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA1,
693 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA224,
694 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA224,
695 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA256,
696 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256,
697 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA384,
698 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA384,
699 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA512,
700 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA512,
702 expectedSet = createAlgorithmSet(sign, array_size(sign));
703 ok(CFSetIsSubset(expectedSet, keySet), "privkey contains expecting algos for signing");
704 ok(!CFSetContainsValue(keySet, ECDSAX962));
705 CFReleaseNull(keySet);
706 CFReleaseNull(expectedSet);
708 keySet = SecKeyCopySupportedAlgorithms(privKey, kSecKeyOperationTypeVerify);
709 expectedSet = createAlgorithmSet(sign, array_size(sign));
710 ok(CFSetIsSubset(expectedSet, keySet), "privkey contains expecting algos for verification");
711 ok(!CFSetContainsValue(keySet, ECDSAX962));
712 CFReleaseNull(keySet);
713 CFReleaseNull(expectedSet);
715 keySet = SecKeyCopySupportedAlgorithms(privKey, kSecKeyOperationTypeDecrypt);
716 const SecKeyAlgorithm decrypt[] = {
717 kSecKeyAlgorithmRSAEncryptionRaw,
718 kSecKeyAlgorithmRSAEncryptionPKCS1,
719 kSecKeyAlgorithmRSAEncryptionOAEPSHA1,
720 kSecKeyAlgorithmRSAEncryptionOAEPSHA224,
721 kSecKeyAlgorithmRSAEncryptionOAEPSHA256,
722 kSecKeyAlgorithmRSAEncryptionOAEPSHA384,
723 kSecKeyAlgorithmRSAEncryptionOAEPSHA512,
725 expectedSet = createAlgorithmSet(decrypt, array_size(decrypt));
726 ok(CFSetIsSubset(expectedSet, keySet), "privkey contains expecting algos for decryption");
727 CFReleaseNull(keySet);
728 CFReleaseNull(expectedSet);
730 keySet = SecKeyCopySupportedAlgorithms(privKey, kSecKeyOperationTypeEncrypt);
731 expectedSet = CFSetCreate(NULL, NULL, 0, &kCFTypeSetCallBacks);
732 is(CFSetGetCount(keySet), 0, "privkey contains no algos for encryption");
733 CFReleaseNull(keySet);
734 CFReleaseNull(expectedSet);
738 keySet = SecKeyCopySupportedAlgorithms(pubKey, kSecKeyOperationTypeVerify);
739 const SecKeyAlgorithm verify[] = {
740 kSecKeyAlgorithmRSASignatureRaw,
741 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1,
742 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA224,
743 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA256,
744 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA384,
745 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA512,
746 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA1,
747 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA224,
748 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256,
749 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA384,
750 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA512,
752 expectedSet = createAlgorithmSet(verify, array_size(verify));
753 ok(CFSetIsSubset(expectedSet, keySet), "pubkey contains expecting algos for verification");
754 ok(!CFSetContainsValue(keySet, ECDSAX962),
755 "pubkey does not contain ECDSA algorithms for verification");
756 ok(!CFSetContainsValue(keySet, RSARaw),
757 "pubkey does not contain encryption-specific algorithm for verification");
758 CFReleaseNull(keySet);
759 CFReleaseNull(expectedSet);
761 keySet = SecKeyCopySupportedAlgorithms(pubKey, kSecKeyOperationTypeSign);
762 expectedSet = CFSetCreate(NULL, NULL, 0, &kCFTypeSetCallBacks);
763 is(CFSetGetCount(keySet), 0, "pubkey contains no algos for signing");
764 CFReleaseNull(keySet);
765 CFReleaseNull(expectedSet);
767 const SecKeyAlgorithm crypt[] = {
768 kSecKeyAlgorithmRSAEncryptionRaw,
769 kSecKeyAlgorithmRSAEncryptionPKCS1,
770 kSecKeyAlgorithmRSAEncryptionOAEPSHA1,
771 kSecKeyAlgorithmRSAEncryptionOAEPSHA224,
772 kSecKeyAlgorithmRSAEncryptionOAEPSHA256,
773 kSecKeyAlgorithmRSAEncryptionOAEPSHA384,
774 kSecKeyAlgorithmRSAEncryptionOAEPSHA512,
776 expectedSet = createAlgorithmSet(crypt, array_size(crypt));
777 keySet = SecKeyCopySupportedAlgorithms(pubKey, kSecKeyOperationTypeDecrypt);
779 ok(CFSetIsSubset(expectedSet, keySet), "pubkey contains expecting algos for decryption");
781 ok(CFSetGetCount(keySet) == 0, "pubkey cannot decrypt");
783 CFReleaseNull(keySet);
784 CFReleaseNull(expectedSet);
786 keySet = SecKeyCopySupportedAlgorithms(pubKey, kSecKeyOperationTypeEncrypt);
787 expectedSet = createAlgorithmSet(crypt, array_size(crypt));
788 ok(CFSetIsSubset(expectedSet, keySet), "pubkey contains expecting algos for encryption");
789 CFReleaseNull(keySet);
790 CFReleaseNull(expectedSet);
794 CFReleaseNull(RSARaw);
795 CFReleaseNull(ECDSAX962);
797 delete_key(&privKey);
801 #if !TARGET_OS_IPHONE
802 static inline bool CFEqualSafe(CFTypeRef left, CFTypeRef right)
804 if (left == NULL || right == NULL)
805 return left == right;
807 return CFEqual(left, right);
811 #define kCreateWithDataTestCount 13
812 static void testcreatewithdata(unsigned long keySizeInBits)
814 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
815 int32_t keysz32 = (int32_t)keySizeInBits;
817 CFNumberRef kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &keysz32);
818 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
819 &kCFTypeDictionaryValueCallBacks);
820 CFDictionarySetValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
821 CFDictionarySetValue(kgp, kSecAttrKeySizeInBits, kzib);
822 CFDictionarySetValue(kgp, kSecAttrIsPermanent, kCFBooleanFalse);
823 CFDictionarySetValue(kgp, kSecAttrLabel, CFSTR("sectests:createwithdata"));
825 SecKeyRef pubKey = NULL, privKey = NULL;
827 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
828 "Generate %ld bit (%ld byte) RSA keypair (status = %d)",
829 keySizeInBits, keySizeInBytes, (int)status);
832 CFMutableDictionaryRef kcwd = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
833 &kCFTypeDictionaryValueCallBacks);;
834 CFDictionarySetValue(kcwd, kSecAttrKeyType, kSecAttrKeyTypeRSA);
835 CFDictionarySetValue(kcwd, kSecAttrKeySizeInBits, kzib);
836 CFDictionarySetValue(kcwd, kSecAttrIsPermanent, kCFBooleanFalse);
839 CFErrorRef error = NULL;
840 CFDataRef privExternalData = NULL, pubExternalData = NULL;
841 SecKeyRef dataKey = NULL;
844 privExternalData = SecKeyCopyExternalRepresentation(privKey, &error);
845 ok(privExternalData && CFGetTypeID(privExternalData) == CFDataGetTypeID(),
846 "priv key SecKeyCopyExternalRepresentation failed");
847 CFReleaseNull(error);
850 skip("invalid priv key external data", 4, privExternalData);
852 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPrivate);
853 dataKey = SecKeyCreateWithData(privExternalData, kcwd, &error);
854 ok(dataKey, "priv key SecKeyCreateWithData failed");
855 CFReleaseNull(error);
857 CFDataRef external = SecKeyCopyExternalRepresentation(dataKey, NULL);
858 eq_cf(privExternalData, external, "priv keys differ");
859 CFReleaseNull(external);
860 CFReleaseNull(dataKey);
862 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPublic);
863 dataKey = SecKeyCreateWithData(privExternalData, kcwd, &error);
864 ok(!dataKey, "priv key SecKeyCreateWithData succeeded with invalid kSecAttrKeyClass");
865 CFReleaseNull(error);
866 CFReleaseNull(dataKey);
868 CFMutableDataRef modifiedExternalData = CFDataCreateMutableCopy(kCFAllocatorDefault, 0, privExternalData);
869 *CFDataGetMutableBytePtr(modifiedExternalData) ^= 0xff;
871 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPrivate);
872 dataKey = SecKeyCreateWithData(modifiedExternalData, kcwd, &error);
873 ok(!dataKey, "priv key SecKeyCreateWithData succeeded with invalid external data");
874 CFReleaseNull(error);
875 CFReleaseNull(dataKey);
877 CFReleaseNull(modifiedExternalData);
882 pubExternalData = SecKeyCopyExternalRepresentation(pubKey, &error);
883 ok(pubExternalData && CFGetTypeID(pubExternalData) == CFDataGetTypeID(),
884 "pub key SecKeyCopyExternalRepresentation failed");
885 CFReleaseNull(error);
888 skip("invalid pub key external data", 4, pubExternalData);
890 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPublic);
891 dataKey = SecKeyCreateWithData(pubExternalData, kcwd, &error);
892 ok(dataKey, "pub key SecKeyCreateWithData failed");
893 CFReleaseNull(error);
895 CFDataRef external = SecKeyCopyExternalRepresentation(dataKey, NULL);
896 eq_cf(pubExternalData, external, "pub keys differ");
897 CFReleaseNull(external);
898 CFReleaseNull(dataKey);
900 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPrivate);
901 dataKey = SecKeyCreateWithData(pubExternalData, kcwd, &error);
902 ok(!dataKey, "pub key SecKeyCreateWithData succeeded with invalid kSecAttrKeyClass");
903 CFReleaseNull(error);
904 CFReleaseNull(dataKey);
906 CFMutableDataRef modifiedExternalData = CFDataCreateMutableCopy(kCFAllocatorDefault, 0, pubExternalData);
907 *CFDataGetMutableBytePtr(modifiedExternalData) ^= 0xff;
909 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPublic);
910 dataKey = SecKeyCreateWithData(modifiedExternalData, kcwd, &error);
911 ok(!dataKey, "pub key SecKeyCreateWithData succeeded with invalid external data");
912 CFReleaseNull(error);
913 CFReleaseNull(dataKey);
915 CFReleaseNull(modifiedExternalData);
920 skip("invalid pub key external data", 1, pubExternalData);
922 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPrivate);
923 dataKey = SecKeyCreateWithData(pubExternalData, kcwd, &error);
924 ok(!dataKey, "priv key SecKeyCreateWithData succeeded with public external data");
925 CFReleaseNull(error);
926 CFReleaseNull(dataKey);
928 CFReleaseNull(pubExternalData);
932 skip("invalid priv key external data", 1, privExternalData);
934 CFDictionarySetValue(kcwd, kSecAttrKeyClass, kSecAttrKeyClassPublic);
935 dataKey = SecKeyCreateWithData(privExternalData, kcwd, &error);
936 ok(!dataKey, "pub key SecKeyCreateWithData succeeded with private external data");
937 CFReleaseNull(error);
938 CFReleaseNull(dataKey);
940 CFReleaseNull(privExternalData);
945 delete_key(&privKey);
948 #define kCopyAttributesTestCount 20
949 static void testcopyattributes(unsigned long keySizeInBits, bool extractable)
951 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
952 int32_t keysz32 = (int32_t)keySizeInBits;
954 CFNumberRef kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &keysz32);
955 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
956 &kCFTypeDictionaryValueCallBacks);
957 CFDictionarySetValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
958 CFDictionarySetValue(kgp, kSecAttrKeySizeInBits, kzib);
959 CFDictionarySetValue(kgp, kSecAttrIsExtractable, extractable ? kCFBooleanTrue : kCFBooleanFalse);
960 CFDictionarySetValue(kgp, kSecAttrLabel, CFSTR("sectests:copyattributes"));
961 SecKeyRef pubKey = NULL, privKey = NULL;
963 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
964 "Generate %ld bit (%ld byte) RSA keypair (status = %d)",
965 keySizeInBits, keySizeInBytes, (int)status);
968 CFDictionaryRef attributes;
969 CFTypeRef attrValue = NULL, privAppLabel = NULL, pubAppLabel = NULL;
972 attributes = SecKeyCopyAttributes(privKey);
973 ok(attributes && CFGetTypeID(attributes) == CFDictionaryGetTypeID(),
974 "priv key SecKeyCopyAttributes failed");
977 skip("invalid attributes", 8, attributes);
979 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanEncrypt);
980 eq_cf(attrValue, kCFBooleanFalse, "invalid priv key kSecAttrCanEncrypt");
982 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanDecrypt);
983 eq_cf(attrValue, kCFBooleanTrue, "invalid priv key kSecAttrCanDecrypt");
985 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanDerive);
986 eq_cf(attrValue, kCFBooleanTrue, "invalid priv key kSecAttrCanDerive");
988 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanSign);
989 eq_cf(attrValue, kCFBooleanTrue, "invalid priv key kSecAttrCanSign");
991 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanVerify);
992 eq_cf(attrValue, kCFBooleanFalse, "invalid priv key kSecAttrCanVerify");
994 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeyClass);
995 eq_cf(attrValue, kSecAttrKeyClassPrivate, "priv key invalid kSecAttrKeyClass");
997 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeyType);
998 eq_cf(attrValue, kSecAttrKeyTypeRSA, "invalid priv key kSecAttrKeyType");
1000 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeySizeInBits);
1001 eq_cf(attrValue, kzib, "invalid priv key kSecAttrKeySizeInBits");
1003 privAppLabel = CFDictionaryGetValue(attributes, kSecAttrApplicationLabel);
1004 CFRetainSafe(privAppLabel);
1006 CFReleaseNull(attributes);
1011 attributes = SecKeyCopyAttributes(pubKey);
1012 ok(attributes && CFGetTypeID(attributes) == CFDictionaryGetTypeID(),
1013 "pub key SecKeyCopyAttributes failed");
1016 skip("invalid attributes", 8, attributes);
1018 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanEncrypt);
1019 eq_cf(attrValue, kCFBooleanTrue, "pub key invalid kSecAttrCanEncrypt");
1021 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanDecrypt);
1022 eq_cf(attrValue, kCFBooleanFalse, "pub key invalid kSecAttrCanDecrypt");
1024 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanDerive);
1025 eq_cf(attrValue, kCFBooleanTrue, "pub key invalid kSecAttrCanDerive");
1027 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanSign);
1028 eq_cf(attrValue, kCFBooleanFalse, "pub key invalid kSecAttrCanSign");
1030 attrValue = CFDictionaryGetValue(attributes, kSecAttrCanVerify);
1031 eq_cf(attrValue, kCFBooleanTrue, "pub key invalid kSecAttrCanVerify");
1033 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeyClass);
1034 eq_cf(attrValue, kSecAttrKeyClassPublic, "pub key invalid kSecAttrKeyClass");
1036 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeyType);
1037 eq_cf(attrValue, kSecAttrKeyTypeRSA, "pub key invalid kSecAttrKeyType");
1039 attrValue = CFDictionaryGetValue(attributes, kSecAttrKeySizeInBits);
1040 eq_cf(attrValue, kzib, "pub key invalid kSecAttrKeySizeInBits");
1042 pubAppLabel = CFDictionaryGetValue(attributes, kSecAttrApplicationLabel);
1043 CFRetainSafe(pubAppLabel);
1045 CFReleaseNull(attributes);
1049 eq_cf(privAppLabel, pubAppLabel, "priv key and pub key kSecAttrApplicationLabel differ");
1051 CFReleaseNull(privAppLabel);
1052 CFReleaseNull(pubAppLabel);
1053 CFReleaseNull(kzib);
1054 delete_key(&pubKey);
1055 delete_key(&privKey);
1058 #define kCopyPublicKeyTestCount 5
1059 static void testcopypublickey(unsigned long keySizeInBits, bool extractable, bool permanent) {
1060 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
1061 int32_t keysz32 = (int32_t)keySizeInBits;
1063 CFNumberRef kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &keysz32);
1064 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
1065 &kCFTypeDictionaryValueCallBacks);
1066 CFDictionarySetValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
1067 CFDictionarySetValue(kgp, kSecAttrKeySizeInBits, kzib);
1068 CFDictionarySetValue(kgp, kSecAttrIsPermanent, permanent ? kCFBooleanTrue : kCFBooleanFalse);
1069 CFDictionarySetValue(kgp, kSecAttrIsExtractable, extractable ? kCFBooleanTrue : kCFBooleanFalse);
1070 CFDictionarySetValue(kgp, kSecAttrLabel, CFSTR("sectests:copypublickey"));
1071 SecKeyRef pubKey = NULL, privKey = NULL;
1074 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
1075 "Generate %ld bit (%ld byte) RSA keypair (status = %d)",
1076 keySizeInBits, keySizeInBytes, (int)status);
1078 NSError *error = nil;
1079 privKey = SecKeyCreateRandomKey(kgp, (void *)&error);
1080 pubKey = SecKeyCopyPublicKey(privKey);
1081 ok(privKey != NULL && pubKey != NULL, "Generate %ld bit (%ld byte) RSA keypair (error %@)",
1082 keySizeInBits, keySizeInBytes, error);
1085 CFReleaseNull(kzib);
1087 CFDataRef pubKeyData = SecKeyCopyExternalRepresentation(pubKey, NULL);
1089 SecKeyRef pubKeyCopy = NULL;
1092 pubKeyCopy = SecKeyCopyPublicKey(privKey);
1093 ok(pubKeyCopy, "priv key SecKeyCopyPublicKey failed");
1094 CFDataRef pubKeyCopyData = SecKeyCopyExternalRepresentation(pubKeyCopy, NULL);
1095 eq_cf(pubKeyCopyData, pubKeyData, "pub key from priv key SecKeyCopyPublicKey and pub key differ");
1096 CFReleaseNull(pubKeyCopy);
1097 CFReleaseNull(pubKeyCopyData);
1101 pubKeyCopy = SecKeyCopyPublicKey(pubKey);
1102 ok(pubKeyCopy, "pub key SecKeyCopyPublicKey failed");
1103 CFDataRef pubKeyCopyData = SecKeyCopyExternalRepresentation(pubKeyCopy, NULL);
1104 eq_cf(pubKeyCopyData, pubKeyData, "pub key from pub key SecKeyCopyPublicKey and pub key differ");
1105 CFReleaseNull(pubKeyCopy);
1106 CFReleaseNull(pubKeyCopyData);
1109 CFReleaseNull(pubKeyData);
1111 delete_key(&pubKey);
1112 delete_key(&privKey);
1114 CFReleaseSafe(pubKey);
1115 CFReleaseSafe(privKey);
1119 static const char *kCertWithPubK = "\
1120 MIIELjCCAxagAwIBAgIJALJlcYRBqZlZMA0GCSqGSIb3DQEBBQUAMIGUMQswCQYDVQQGEwJVUzELMAkG\
1121 A1UECBMCQ0ExEjAQBgNVBAcTCUN1cGVydGlubzETMBEGA1UEChMKQXBwbGUgSW5jLjEPMA0GA1UECxMG\
1122 Q29yZU9TMRwwGgYDVQQDExNBcHBsZSBUZXN0IENBMSBDZXJ0MSAwHgYJKoZIhvcNAQkBFhF2a3V6ZWxh\
1123 QGFwcGxlLmNvbTAeFw0xNTA0MjkwODMyMDBaFw0yNTA0MjYwODMyMDBaMIGPMQswCQYDVQQGEwJVUzEL\
1124 MAkGA1UECBMCQ0ExEjAQBgNVBAcTCUN1cGVydGlubzETMBEGA1UEChMKQXBwbGUgSW5jLjEQMA4GA1UE\
1125 CxMHQ29yZSBPUzEWMBQGA1UEAxMNRmlsaXAgU3Rva2xhczEgMB4GCSqGSIb3DQEJARYRc3Rva2xhc0Bh\
1126 cHBsZS5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDZcPMvjpu7i/2SkNDCrSC4Wa8m\
1127 j3r6Lgn0crL4AgU+g3apptyy1eFf4RpNRJTGJ9ZMApbRZ0b7wX87Dq6UlCJUI9RJPOy+/TW0FM6mUVaF\
1128 VSY+P+KMdRYGIOMLVI+LR6lRTf8MWbxZ238cqAIVnLHaE9HrXjyIrgX2IufJjt69WhwsJZuan7jmeXJS\
1129 0AnESB31wS5NOn0tFDtzNAAQmoP8N8q6ZNC85tPVWBM61YLNjwSYl74y14QfX401P2pQRvwxTortRImk\
1130 xjN4DBprG23e59UW2IBxYsqUA61jhA0yVy8gxYpCGa4bEBslhrnkAoSv+Zlyk7u2GyO13AC1dfRxAgMB\
1131 AAGjgYUwgYIwPwYDVR0RBDgwNqAhBgorBgEEAYI3FAIDoBMMEXN0b2tsYXNAYXBwbGUuY29tgRFzdG9r\
1132 bGFzQGFwcGxlLmNvbTA/BgNVHREEODA2oCEGCisGAQQBgjcUAgOgEwwRc3Rva2xhc0BhcHBsZS5jb22B\
1133 EXN0b2tsYXNAYXBwbGUuY29tMA0GCSqGSIb3DQEBBQUAA4IBAQB87bZdl4XEDFA7UdPouhR3dKRl6evS\
1134 MfC9/0jVcdB+P1mNJ/vIZdOZMY0asieOXhsI91nEcHUjbBCnu18mu2jR6SGiJsS/zr6enkpQMcztulMU\
1135 kcjuSjT1hEzRv0LvEgWPOK+VpVqk6N0ZhybBQYVH2ECf7OU48CkFQFg9eLv6VaSK9+FqcBWpq8fXyOa7\
1136 bL58bO5A3URHcmMWibv9/j+lpVeQBxt1UUwqBZT7DSLPw3QCj/zXfAGEu3izvEYaWwsQDhItwQJ6g6pp\
1137 DLO741C7K8eKgvGs8ptna4RSosQda9bdnhZwT+g0UcorsVTUo+sR9+LW7INJ1zovRCL7NXit";
1139 static const char *kPubK = "\
1140 MIIBCgKCAQEA2XDzL46bu4v9kpDQwq0guFmvJo96+i4J9HKy+AIFPoN2qabcstXhX+EaTUSUxifWTAKW\
1141 0WdG+8F/Ow6ulJQiVCPUSTzsvv01tBTOplFWhVUmPj/ijHUWBiDjC1SPi0epUU3/DFm8Wdt/HKgCFZyx\
1142 2hPR6148iK4F9iLnyY7evVocLCWbmp+45nlyUtAJxEgd9cEuTTp9LRQ7czQAEJqD/DfKumTQvObT1VgT\
1143 OtWCzY8EmJe+MteEH1+NNT9qUEb8MU6K7USJpMYzeAwaaxtt3ufVFtiAcWLKlAOtY4QNMlcvIMWKQhmu\
1144 GxAbJYa55AKEr/mZcpO7thsjtdwAtXX0cQIDAQAB";
1146 static const int kTestCountCopyPubKFromCert = 2;
1147 static void testcopypubkfromcert() {
1148 NSData *certData = [[NSData alloc] initWithBase64EncodedString:[NSString stringWithUTF8String:kCertWithPubK]
1149 options:NSDataBase64DecodingIgnoreUnknownCharacters];
1150 NSData *pubKData = [[NSData alloc] initWithBase64EncodedString:[NSString stringWithUTF8String:kPubK]
1151 options:NSDataBase64DecodingIgnoreUnknownCharacters];
1152 SecCertificateRef cert = SecCertificateCreateWithData(kCFAllocatorDefault, (CFDataRef)certData);
1153 SecKeyRef pubKey = NULL;
1154 ok_status(SecCertificateCopyPublicKey(cert, &pubKey), "export public key from certificate");
1155 NSData *pubKeyData = (__bridge_transfer NSData *)SecKeyCopyExternalRepresentation(pubKey, NULL);
1156 eq_cf( (__bridge CFTypeRef) pubKeyData, (__bridge CFTypeRef) pubKData, "public key exports itself into expected data");
1157 CFReleaseNull(pubKey);
1158 CFReleaseNull(cert);
1161 static inline CFDataRef CFDataCreateWithHash(CFAllocatorRef allocator, const struct ccdigest_info *di, const uint8_t *buffer, const uint8_t length) {
1162 CFMutableDataRef result = CFDataCreateMutable(allocator, di->output_size);
1163 CFDataSetLength(result, di->output_size);
1165 ccdigest(di, length, buffer, CFDataGetMutableBytePtr(result));
1170 #define kSignAndVerifyTestCount 130
1171 static void testsignverify(unsigned long keySizeInBits)
1173 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
1174 int32_t keysz32 = (int32_t)keySizeInBits;
1176 CFNumberRef kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &keysz32);
1177 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
1178 &kCFTypeDictionaryValueCallBacks);
1179 CFDictionarySetValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
1180 CFDictionarySetValue(kgp, kSecAttrKeySizeInBits, kzib);
1181 CFDictionarySetValue(kgp, kSecAttrIsPermanent, kCFBooleanFalse);
1182 CFDictionarySetValue(kgp, kSecAttrLabel, CFSTR("sectests:signverify"));
1183 SecKeyRef pubKey = NULL, privKey = NULL, pubKeyIOS = NULL, privKeyIOS = NULL;
1185 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
1186 "Generate %ld bit (%ld byte) RSA keypair (status = %d)",
1187 keySizeInBits, keySizeInBytes, (int)status);
1189 CFReleaseNull(kzib);
1191 CFDataRef privKeyData = SecKeyCopyExternalRepresentation(privKey, NULL);
1192 CFDictionaryRef privKeyAttrs = SecKeyCopyAttributes(privKey);
1193 privKeyIOS = SecKeyCreateWithData(privKeyData, privKeyAttrs, NULL);
1194 CFReleaseNull(privKeyData);
1195 CFReleaseNull(privKeyAttrs);
1196 ok(privKeyIOS, "create IOS version of the private key");
1198 CFDataRef pubKeyData = SecKeyCopyExternalRepresentation(pubKey, NULL);
1199 CFDictionaryRef pubKeyAttrs = SecKeyCopyAttributes(pubKey);
1200 pubKeyIOS = SecKeyCreateWithData(pubKeyData, pubKeyAttrs, NULL);
1201 CFReleaseNull(pubKeyData);
1202 CFReleaseNull(pubKeyAttrs);
1203 ok(pubKeyIOS, "create IOS version of the public key");
1205 SecKeyAlgorithm algorithms[] = {
1206 kSecKeyAlgorithmRSASignatureRaw,
1207 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1,
1208 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA224,
1209 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA256,
1210 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA384,
1211 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA512,
1212 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA1,
1213 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA224,
1214 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256,
1215 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA384,
1216 kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA512,
1219 CFDataRef testData = CFStringCreateExternalRepresentation(kCFAllocatorDefault, CFSTR("test"), kCFStringEncodingUTF8, 0);
1220 ok(testData, "creating test data failed");
1223 skip("invalid test data", 71, testData);
1225 CFErrorRef error = NULL;
1227 for (uint32_t ix = 0; ix < array_size(algorithms); ++ix) {
1228 SecKeyAlgorithm algorithm = algorithms[ix];
1229 SecKeyAlgorithm incompatibleAlgorithm = (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureRaw)) ?
1230 kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1 : kSecKeyAlgorithmRSASignatureRaw;
1232 CFDataRef dataToSign = NULL;
1233 if (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA1)) {
1234 dataToSign = CFDataCreateWithHash(kCFAllocatorDefault, ccsha1_di(),
1235 CFDataGetBytePtr(testData), CFDataGetLength(testData));
1236 ok(dataToSign, "creating digest failed for algorithm %@", algorithm);
1238 else if (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA224)) {
1239 dataToSign = CFDataCreateWithHash(kCFAllocatorDefault, ccsha224_di(),
1240 CFDataGetBytePtr(testData), CFDataGetLength(testData));
1241 ok(dataToSign, "creating digest failed for algorithm %@", algorithm);
1243 else if (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA256)) {
1244 dataToSign = CFDataCreateWithHash(kCFAllocatorDefault, ccsha256_di(),
1245 CFDataGetBytePtr(testData), CFDataGetLength(testData));
1246 ok(dataToSign, "creating digest failed for algorithm %@", algorithm);
1248 else if (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA384)) {
1249 dataToSign = CFDataCreateWithHash(kCFAllocatorDefault, ccsha384_di(),
1250 CFDataGetBytePtr(testData), CFDataGetLength(testData));
1251 ok(dataToSign, "creating digest failed for algorithm %@", algorithm);
1253 else if (CFEqual(algorithm, kSecKeyAlgorithmRSASignatureDigestPKCS1v15SHA512)) {
1254 dataToSign = CFDataCreateWithHash(kCFAllocatorDefault, ccsha512_di(),
1255 CFDataGetBytePtr(testData), CFDataGetLength(testData));
1256 ok(dataToSign, "creating digest failed for algorithm %@", algorithm);
1259 CFRetainAssign(dataToSign, testData);
1261 CFReleaseNull(error);
1264 skip("invalid data to sign", 7, dataToSign);
1266 CFDataRef signature = SecKeyCreateSignature(pubKey, algorithm, dataToSign, &error);
1267 ok(!signature, "SecKeyCopySignature succeeded with pub key for algorithm %@", algorithm);
1268 CFReleaseNull(error);
1269 CFReleaseNull(signature);
1271 signature = SecKeyCreateSignature(privKey, algorithm, dataToSign, &error);
1272 ok(signature, "SecKeyCopySignature failed for algorithm %@", algorithm);
1273 CFReleaseNull(error);
1275 CFDataRef iosSignature = SecKeyCreateSignature(privKeyIOS, algorithm, dataToSign, &error);
1276 ok(iosSignature, "SecKeyCopySignature(ios) failed for algorithm %@", algorithm);
1277 CFReleaseNull(error);
1280 skip("invalid signature", 4, signature);
1282 ok(!SecKeyVerifySignature(privKey, algorithm, dataToSign, signature, &error),
1283 "SecKeyVerifySignature succeeded with priv key for algorithm %@", algorithm);
1284 CFReleaseNull(error);
1286 ok(!SecKeyVerifySignature(pubKey, incompatibleAlgorithm, dataToSign, signature, &error),
1287 "SecKeyVerifySignature succeeded with wrong algorithm for algorithm %@", algorithm);
1288 CFReleaseNull(error);
1290 ok(SecKeyVerifySignature(pubKey, algorithm, dataToSign, signature, &error),
1291 "SecKeyVerifySignature(osx) failed osx-signature for algorithm %@", algorithm);
1292 CFReleaseNull(error);
1294 ok(SecKeyVerifySignature(pubKeyIOS, algorithm, dataToSign, signature, &error),
1295 "SecKeyVerifySignature(ios) failed for osx-signature for algorithm %@", algorithm);
1297 ok(SecKeyVerifySignature(pubKey, algorithm, dataToSign, iosSignature, &error),
1298 "SecKeyVerifySignature(osx) failed for ios-signature for algorithm %@", algorithm);
1299 CFReleaseNull(error);
1301 ok(SecKeyVerifySignature(pubKeyIOS, algorithm, dataToSign, iosSignature, &error),
1302 "SecKeyVerifySignature(ios) failed for ios-signature for algorithm %@", algorithm);
1304 CFMutableDataRef modifiedSignature = CFDataCreateMutableCopy(kCFAllocatorDefault, 0, signature);
1305 *CFDataGetMutableBytePtr(modifiedSignature) ^= 0xff;
1307 ok(!SecKeyVerifySignature(pubKey, algorithm, dataToSign, modifiedSignature, &error),
1308 "SecKeyVerifySignature succeeded with bad signature for algorithm %@", algorithm);
1309 CFReleaseNull(error);
1311 CFMutableDataRef modifiedDataToSign = CFDataCreateMutableCopy(kCFAllocatorDefault, 0, dataToSign);
1312 *CFDataGetMutableBytePtr(modifiedDataToSign) ^= 0xff;
1314 ok(!SecKeyVerifySignature(pubKey, algorithm, modifiedDataToSign, signature, &error),
1315 "SecKeyVerifySignature succeeded with bad data for algorithm %@", algorithm);
1316 CFReleaseNull(error);
1318 CFReleaseNull(modifiedDataToSign);
1319 CFReleaseNull(modifiedSignature);
1320 CFReleaseNull(signature);
1321 CFReleaseNull(iosSignature);
1323 CFReleaseNull(dataToSign);
1326 CFReleaseNull(testData);
1329 delete_key(&pubKey);
1330 delete_key(&privKey);
1331 CFReleaseNull(pubKeyIOS);
1332 CFReleaseNull(privKeyIOS);
1335 #define kNonExtractableTestCount 6
1336 static void testnonextractable(unsigned long keySizeInBits)
1338 size_t keySizeInBytes = (keySizeInBits + 7) / 8;
1339 int32_t keysz32 = (int32_t)keySizeInBits;
1341 CFNumberRef kzib = CFNumberCreate(NULL, kCFNumberSInt32Type, &keysz32);
1342 CFMutableDictionaryRef kgp = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks,
1343 &kCFTypeDictionaryValueCallBacks);
1344 CFDictionarySetValue(kgp, kSecAttrKeyType, kSecAttrKeyTypeRSA);
1345 CFDictionarySetValue(kgp, kSecAttrKeySizeInBits, kzib);
1346 CFDictionarySetValue(kgp, kSecAttrIsPermanent, kCFBooleanTrue);
1347 CFDictionarySetValue(kgp, kSecAttrIsExtractable, kCFBooleanFalse);
1348 CFStringRef label = CFSTR("sectests:nonextractable");
1349 CFDictionarySetValue(kgp, kSecAttrLabel, label);
1350 SecKeyRef pubKey = NULL, privKey = NULL;
1352 ok_status(status = SecKeyGeneratePair(kgp, &pubKey, &privKey),
1353 "Generate %ld bit (%ld byte) RSA keypair (status = %d)",
1354 keySizeInBits, keySizeInBytes, (int)status);
1356 CFReleaseNull(kzib);
1358 // Get attributes, verify that ApplicationLabel is set and equals for both keys.
1359 CFDictionaryRef privAttrs = SecKeyCopyAttributes(privKey);
1360 CFDictionaryRef pubAttrs = SecKeyCopyAttributes(pubKey);
1362 ok(privAttrs, "able to get private key attributes");
1363 ok(pubAttrs, "able to get public key attributes");
1365 CFDataRef privLabel = CFDictionaryGetValue(privAttrs, kSecAttrApplicationLabel);
1366 CFDataRef pubLabel = CFDictionaryGetValue(pubAttrs, kSecAttrApplicationLabel);
1368 ok(privLabel && CFGetTypeID(privLabel) == CFDataGetTypeID() && CFDataGetLength(privLabel) == 20,
1369 "priv appLabel is present and of correct type");
1370 ok(pubLabel && CFGetTypeID(pubLabel) == CFDataGetTypeID() && CFDataGetLength(pubLabel) == 20,
1371 "priv appLabel is present and of correct type");
1372 eq_cf(privLabel, pubLabel, "applabels of pub and priv keys are equal");
1374 CFReleaseNull(pubAttrs);
1375 CFReleaseNull(privAttrs);
1377 delete_key(&pubKey);
1378 delete_key(&privKey);
1381 #define kTestCount ((2 * kKeyGenTestCount) + kKeyGen2TestCount + (int) (kdfvLen*3)) + \
1382 kTestSupportedCount + kCreateWithDataTestCount + (kCopyAttributesTestCount * 2) + (kCopyPublicKeyTestCount * 4) + \
1383 kSignAndVerifyTestCount + kNonExtractableTestCount + \
1384 kTestCountCopyPubKFromCert
1386 static void tests(void)
1388 /* Comment out lines below for testing generating all common key sizes,
1389 disabled now for speed reasons. */
1393 testkeygen(2056); // Stranged sized for edge cases in padding.
1397 testkeygen2(1024); // lots of FAIL!
1399 testsupportedalgos(1024);
1400 testcreatewithdata(1024);
1401 testcopyattributes(1024, true);
1402 testcopyattributes(1024, false);
1403 testcopypublickey(1024, true, true);
1404 testcopypublickey(1024, false, true);
1405 testcopypublickey(1024, true, false);
1406 testcopypublickey(1024, false, false);
1407 testsignverify(1024);
1408 testnonextractable(1024);
1410 #if !TARGET_OS_IPHONE
1411 testkeyderivation();
1414 testcopypubkfromcert();
1417 int kc_40_seckey(int argc, char *const *argv)
1419 plan_tests(kTestCount);