2 * Copyright (c) 2016 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 "si-95-cms-basic.h"
25 #include "Security_regressions.h"
27 #include <AssertMacros.h>
29 #include <utilities/SecCFRelease.h>
31 #include <Security/SecBase.h>
32 #include <Security/SecImportExport.h>
34 #include <Security/SecIdentity.h>
35 #include <Security/SecPolicy.h>
36 #include <Security/SecItem.h>
38 #include <Security/SecCmsMessage.h>
39 #include <Security/SecCmsSignedData.h>
40 #include <Security/SecCmsContentInfo.h>
41 #include <Security/SecCmsSignerInfo.h>
42 #include <Security/SecCmsEncoder.h>
43 #include <Security/SecCmsDecoder.h>
44 #include <Security/SecCmsEnvelopedData.h>
45 #include <Security/SecCmsRecipientInfo.h>
46 #include <Security/SecAsn1Types.h>
48 #include <security_asn1/secerr.h>
49 #include <security_asn1/seccomon.h>
51 /* These tests are essentially the same as cms_01_basic in the OS X
52 * libsecurity_cms_regressions. They are not unified into a single
53 * test because libsecurity_smime diverges so much between the platforms
54 * that unifying the tests makes every third line a TARGET macro.
57 #define kNumberSetupTests 8
58 static CFDataRef
setup_keychain(const uint8_t *p12
, size_t p12_len
, SecIdentityRef
*identity
, SecCertificateRef
*cert
) {
59 CFDictionaryRef p12Options
= NULL
, item_dict
= NULL
, query_dict
= NULL
;
60 CFArrayRef p12Items
= NULL
;
61 CFStringRef p12Password
= NULL
;
62 CFDataRef p12Data
= NULL
, identityPersistentRef
= NULL
;
63 CFTypeRef keychainItems
= NULL
;
66 ok(p12Password
= CFStringCreateWithCString(NULL
, "password", kCFStringEncodingASCII
),
67 "Create p12 password");
68 require_action(p12Options
= CFDictionaryCreate(NULL
, (const void **)&kSecImportExportPassphrase
,
69 (const void **)&p12Password
, 1,
70 &kCFTypeDictionaryKeyCallBacks
,
71 &kCFTypeDictionaryValueCallBacks
),
72 errOut
, fail("Create p12 options dictionary"));
73 require_action(p12Data
= CFDataCreate(NULL
, p12
, p12_len
), errOut
,
74 fail("Create p12 data"));
75 ok_status(SecPKCS12Import(p12Data
, p12Options
, &p12Items
),
76 "import test identity");
77 ok(item_dict
= CFArrayGetValueAtIndex(p12Items
, 0),
79 ok(*identity
= (SecIdentityRef
)CFRetainSafe(CFDictionaryGetValue(item_dict
, kSecImportItemIdentity
)),
80 "Get identity from results");
82 /* add identity to keychain because libsecurity_smime needs it there */
83 const void *keys
[] = { kSecValueRef
, kSecReturnPersistentRef
};
84 const void *values
[] = { *identity
, kCFBooleanTrue
};
85 require_action(query_dict
= CFDictionaryCreate(NULL
, keys
, values
, 2,
86 &kCFTypeDictionaryKeyCallBacks
,
87 &kCFTypeDictionaryValueCallBacks
),
88 errOut
, fail("Create SecItem query dictionary"));
89 ok_status(SecItemAdd(query_dict
, &keychainItems
),
90 "Add identity to keychain");
91 is(CFGetTypeID(keychainItems
), CFDataGetTypeID(),
92 "Verify SecItem result type");
93 ok(identityPersistentRef
= (CFDataRef
)CFRetainSafe(keychainItems
),
94 "Get persistent reference to identity");
96 /* get the certificate */
97 require_action(identity
&& *identity
, errOut
, fail("get identity failed"));
98 ok_status(SecIdentityCopyCertificate(*identity
, cert
),
102 CFReleaseNull(p12Password
);
103 CFReleaseNull(p12Options
);
104 CFReleaseNull(p12Data
);
105 CFReleaseNull(p12Items
);
106 CFReleaseNull(query_dict
);
107 CFReleaseNull(keychainItems
);
108 return identityPersistentRef
;
111 #define kNumberCleanupTests 1
112 static void cleanup_keychain(CFDataRef identityPersistenRef
, SecIdentityRef identity
, SecCertificateRef cert
) {
113 CFDictionaryRef query
= NULL
;
114 require_action(query
= CFDictionaryCreate(NULL
, (const void**)&kSecValuePersistentRef
,
115 (const void**)&identityPersistenRef
, 1,
116 &kCFTypeDictionaryKeyCallBacks
,
117 &kCFTypeDictionaryValueCallBacks
),
118 errOut
, fail("Create SecItem dictionary"));
119 ok_status(SecItemDelete(query
),
120 "Delete identity from keychain");
123 CFReleaseNull(query
);
125 CFReleaseNull(identity
);
128 static OSStatus
sign_please(SecIdentityRef identity
, SECOidTag digestAlgTag
, bool withAttrs
, uint8_t *expected_output
, size_t expected_len
) {
129 OSStatus status
= SECFailure
;
130 SecCmsMessageRef cmsg
= NULL
;
131 SecCmsSignedDataRef sigd
= NULL
;
132 SecCmsContentInfoRef cinfo
= NULL
;
133 SecCmsSignerInfoRef signerInfo
= NULL
;
134 SecCmsEncoderRef encoder
= NULL
;
135 CFMutableDataRef outCms
= NULL
;
136 uint8_t string_to_sign
[] = "This message is signed. Ain't it pretty?";
138 /* setup the message */
139 require_action_string(cmsg
= SecCmsMessageCreate(), out
,
140 status
= errSecAllocate
, "Failed to create message");
141 require_action_string(sigd
= SecCmsSignedDataCreate(cmsg
), out
,
142 status
= errSecAllocate
, "Failed to create signed data");
143 require_action_string(cinfo
= SecCmsMessageGetContentInfo(cmsg
), out
,
144 status
= errSecParam
, "Failed to get cms content info");
145 require_noerr_string(status
= SecCmsContentInfoSetContentSignedData(cinfo
, sigd
), out
,
146 "Failed to set signed data into content info");
147 require_action_string(cinfo
= SecCmsSignedDataGetContentInfo(sigd
), out
,
148 status
= errSecParam
, "Failed to get content info from signed data");
149 require_noerr_string(status
= SecCmsContentInfoSetContentData(cinfo
, NULL
, false), out
,
150 "Failed to set signed data content info");
151 require_action_string(signerInfo
= SecCmsSignerInfoCreate(sigd
, identity
, digestAlgTag
), out
,
152 status
= errSecAllocate
, "Failed to create signer info");
153 require_noerr_string(status
= SecCmsSignerInfoIncludeCerts(signerInfo
, SecCmsCMCertOnly
,
154 certUsageEmailSigner
), out
,
155 "Failed to put certs in signer info");
158 require_noerr_string(status
= SecCmsSignerInfoAddSigningTime(signerInfo
, 480000000.0), out
,
159 "Couldn't add an attribute");
163 require_action_string(outCms
= CFDataCreateMutable(NULL
, 0), out
,
164 status
= errSecAllocate
, "Failed to create cms data");
165 require_noerr_string(status
= SecCmsEncoderCreate(cmsg
, NULL
, NULL
, outCms
, NULL
, NULL
,
166 NULL
, NULL
, &encoder
), out
,
167 "Failed to create encoder");
168 require_noerr_string(status
= SecCmsEncoderUpdate(encoder
, string_to_sign
, sizeof(string_to_sign
)), out
,
169 "Failed to add data ");
170 status
= SecCmsEncoderFinish(encoder
);
171 encoder
= NULL
; // SecCmsEncoderFinish always frees the encoder but doesn't NULL it.
172 require_noerr_quiet(status
, out
);
174 /* verify the output matches expected results */
175 if (expected_output
) {
176 require_action_string((CFIndex
)expected_len
== CFDataGetLength(outCms
), out
,
177 status
= -1, "Output size differs from expected");
178 require_noerr_action_string(memcmp(expected_output
, CFDataGetBytePtr(outCms
), expected_len
), out
,
179 status
= -1, "Output differs from expected");
184 SecCmsEncoderDestroy(encoder
);
187 SecCmsMessageDestroy(cmsg
);
189 CFReleaseNull(outCms
);
194 static OSStatus
verify_please(SecKeychainRef keychain
, uint8_t *data_to_verify
, size_t length
) {
195 OSStatus status
= SECFailure
;
196 SecCmsDecoderRef decoder
= NULL
;
197 SecCmsMessageRef cmsg
= NULL
;
198 SecCmsContentInfoRef cinfo
= NULL
;
199 SecCmsSignedDataRef sigd
= NULL
;
200 SecPolicyRef policy
= NULL
;
201 SecTrustRef trust
= NULL
;
203 if (!data_to_verify
) {
204 return errSecSuccess
; // reasons...
207 require_noerr_string(status
= SecCmsDecoderCreate(NULL
, NULL
, NULL
, NULL
,
208 NULL
, NULL
, &decoder
), out
,
209 "Failed to create decoder");
210 require_noerr_string(status
= SecCmsDecoderUpdate(decoder
, data_to_verify
, length
), out
,
211 "Failed to add data ");
212 status
= SecCmsDecoderFinish(decoder
, &cmsg
);
213 decoder
= NULL
; // SecCmsDecoderFinish always frees the decoder
214 require_noerr_quiet(status
, out
);
216 require_action_string(cinfo
= SecCmsMessageContentLevel(cmsg
, 0), out
,
217 status
= errSecDecode
, "Failed to get content info");
218 require_action_string(SEC_OID_PKCS7_SIGNED_DATA
== SecCmsContentInfoGetContentTypeTag(cinfo
), out
,
219 status
= errSecDecode
, "Content type was pkcs7 signed data");
220 require_action_string(sigd
= (SecCmsSignedDataRef
)SecCmsContentInfoGetContent(cinfo
), out
,
221 status
= errSecDecode
, "Failed to get signed data");
222 require_action_string(policy
= SecPolicyCreateBasicX509(), out
,
223 status
= errSecAllocate
, "Failed to create basic policy");
224 status
= SecCmsSignedDataVerifySignerInfo(sigd
, 0, keychain
, policy
, &trust
);
228 SecCmsDecoderDestroy(decoder
);
231 SecCmsMessageDestroy(cmsg
);
233 CFReleaseNull(policy
);
234 CFReleaseNull(trust
);
238 static uint8_t *invalidate_signature(uint8_t *cms_data
, size_t length
) {
239 if (!cms_data
|| !length
|| (length
< 10)) {
242 uint8_t *invalid_cms
= NULL
;
244 invalid_cms
= malloc(length
);
246 memcpy(invalid_cms
, cms_data
, length
);
247 /* This modifies the signature part of the test cms binaries */
248 invalid_cms
[length
- 10] = 0x00;
254 static OSStatus
invalidate_and_verify(SecKeychainRef kc
, uint8_t *cms_data
, size_t length
) {
255 OSStatus status
= SECFailure
;
256 uint8_t *invalid_cms_data
= NULL
;
259 return SECFailure
; // reasons...
262 require_action_string(invalid_cms_data
= invalidate_signature(cms_data
, length
), out
,
263 status
= errSecAllocate
, "Unable to allocate buffer for invalid cms data");
264 status
= verify_please(kc
, invalid_cms_data
, length
);
267 if (invalid_cms_data
) {
268 free(invalid_cms_data
);
273 /* forward declaration */
274 static OSStatus
decrypt_please(const uint8_t *data_to_decrypt
, size_t length
);
276 static OSStatus
encrypt_please(SecCertificateRef recipient
, SECOidTag encAlg
, int keysize
) {
277 OSStatus status
= SECFailure
;
278 SecCmsMessageRef cmsg
= NULL
;
279 SecCmsEnvelopedDataRef envd
= NULL
;
280 SecCmsContentInfoRef cinfo
= NULL
;
281 SecCmsRecipientInfoRef rinfo
= NULL
;
282 SecCmsEncoderRef encoder
= NULL
;
283 CFMutableDataRef outCms
= NULL
;
285 const uint8_t data_to_encrypt
[] = "This data is encrypted. Is cool, no?";
287 /* set up the message */
288 require_action_string(cmsg
= SecCmsMessageCreate(), out
,
289 status
= errSecAllocate
, "Failed to create message");
290 require_action_string(envd
= SecCmsEnvelopedDataCreate(cmsg
, encAlg
, keysize
), out
,
291 status
= errSecAllocate
, "Failed to create enveloped data");
292 require_action_string(cinfo
= SecCmsMessageGetContentInfo(cmsg
), out
,
293 status
= errSecParam
, "Failed to get content info from cms message");
294 require_noerr_string(status
= SecCmsContentInfoSetContentEnvelopedData(cinfo
, envd
), out
,
295 "Failed to set enveloped data in cms message");
296 require_action_string(cinfo
= SecCmsEnvelopedDataGetContentInfo(envd
), out
,
297 status
= errSecParam
, "Failed to get content info from enveloped data");
298 require_noerr_string(status
= SecCmsContentInfoSetContentData(cinfo
, NULL
, false), out
,
299 "Failed to set data type in envelope");
300 require_action_string(rinfo
= SecCmsRecipientInfoCreate(envd
, recipient
), out
,
301 status
= errSecAllocate
, "Failed to create recipient info");
303 /* encode the message */
304 require_action_string(outCms
= CFDataCreateMutable(NULL
, 0), out
,
305 status
= errSecAllocate
, "Failed to create cms data");
306 require_noerr_string(status
= SecCmsEncoderCreate(cmsg
, NULL
, NULL
, outCms
, NULL
, NULL
,
307 NULL
, NULL
, &encoder
), out
,
308 "Failed to create encoder");
309 require_noerr_string(status
= SecCmsEncoderUpdate(encoder
, data_to_encrypt
, sizeof(data_to_encrypt
)), out
,
310 "Failed to update encoder with data");
311 status
= SecCmsEncoderFinish(encoder
);
312 encoder
= NULL
; // SecCmsEncoderFinish always frees the encoder but doesn't NULL it.
313 require_noerr_quiet(status
, out
);
315 require_noerr_string(status
= decrypt_please(CFDataGetBytePtr(outCms
), CFDataGetLength(outCms
)), out
,
316 "Failed to decrypt the data we just encrypted");
320 SecCmsEncoderDestroy(encoder
);
323 SecCmsMessageDestroy(cmsg
);
325 CFReleaseNull(outCms
);
329 static OSStatus
decrypt_please(const uint8_t *data_to_decrypt
, size_t length
) {
330 OSStatus status
= SECFailure
;
331 SecCmsDecoderRef decoder
= NULL
;
332 SecCmsMessageRef cmsg
= NULL
;
333 const SecAsn1Item
*content
= NULL
;
334 const uint8_t encrypted_string
[] = "This data is encrypted. Is cool, no?";
336 require_noerr_string(status
= SecCmsDecoderCreate(NULL
, NULL
, NULL
, NULL
, NULL
,
337 NULL
, &decoder
), out
,
338 "Failed to create decoder");
339 require_noerr_string(status
= SecCmsDecoderUpdate(decoder
, data_to_decrypt
, length
), out
,
340 "Failed to add data ");
341 status
= SecCmsDecoderFinish(decoder
, &cmsg
);
342 decoder
= NULL
; // SecCmsDecoderFinish always frees the decoder
343 require_noerr_quiet(status
, out
);
344 require_action_string(content
= SecCmsMessageGetContent(cmsg
), out
,
345 status
= errSecDecode
, "Unable to get message contents");
347 /* verify the output matches expected results */
348 require_action_string(sizeof(encrypted_string
) == content
->Length
, out
,
349 status
= -1, "Output size differs from expected");
350 require_noerr_action_string(memcmp(encrypted_string
, content
->Data
, content
->Length
), out
,
351 status
= -1, "Output differs from expected");
355 SecCmsMessageDestroy(cmsg
);
360 /* Signing with attributes goes through a different code path than signing without,
361 * so we need to test both. */
362 #define kNumberSignTests 10
363 static void sign_tests(SecIdentityRef identity
, bool isRSA
) {
366 is(sign_please(identity
, SEC_OID_MD5
, false, NULL
, 0),
367 SEC_ERROR_INVALID_ALGORITHM
, "Signed with MD5. Not cool.");
368 is(sign_please(identity
, SEC_OID_SHA1
, false, (isRSA
) ? rsa_sha1
: NULL
,
369 (isRSA
) ? sizeof(rsa_sha1
) : 0),
370 errSecSuccess
, "Signed with SHA-1");
371 is(sign_please(identity
, SEC_OID_SHA256
, false, (isRSA
) ? new_sig_alg_rsa_sha256
: NULL
,
372 (isRSA
) ? sizeof(rsa_sha256
) : 0),
373 errSecSuccess
, "Signed with SHA-256");
374 is(sign_please(identity
, SEC_OID_SHA384
, false, NULL
, 0), errSecSuccess
, "Signed with SHA-384");
375 is(sign_please(identity
, SEC_OID_SHA512
, false, NULL
, 0), errSecSuccess
, "Signed with SHA-512");
377 /* with attributes */
378 is(sign_please(identity
, SEC_OID_MD5
, true, NULL
, 0),
379 SEC_ERROR_INVALID_ALGORITHM
, "Signed with MD5 and attributes. Not cool.");
380 is(sign_please(identity
, SEC_OID_SHA1
, true, (isRSA
) ? rsa_sha1_attr
: NULL
,
381 (isRSA
) ? sizeof(rsa_sha1_attr
) : 0),
382 errSecSuccess
, "Signed with SHA-1 and attributes");
383 is(sign_please(identity
, SEC_OID_SHA256
, true, (isRSA
) ? rsa_sha256_attr
: NULL
,
384 (isRSA
) ? sizeof(rsa_sha256_attr
) : 0),
385 errSecSuccess
, "Signed with SHA-256 and attributes");
386 is(sign_please(identity
, SEC_OID_SHA384
, true, NULL
, 0),
387 errSecSuccess
, "Signed with SHA-384 and attributes");
388 is(sign_please(identity
, SEC_OID_SHA512
, true, NULL
, 0),
389 errSecSuccess
, "Signed with SHA-512 and attributes");
392 /* Verifying with attributes goes through a different code path than verifying without,
393 * so we need to test both. */
394 #define kNumberVerifyTests 13
395 static void verify_tests(SecKeychainRef kc
, bool isRsa
) {
397 is(verify_please(kc
, (isRsa
) ? rsa_md5
: ec_md5
,
398 (isRsa
) ? sizeof(rsa_md5
) : sizeof(ec_md5
)),
399 (isRsa
) ? errSecSuccess
: SECFailure
, "Verify MD5, no attributes");
400 is(verify_please(kc
, (isRsa
) ? rsa_sha1
: ec_sha1
,
401 (isRsa
) ? sizeof(rsa_sha1
) : sizeof(ec_sha1
)),
402 errSecSuccess
, "Verify SHA1, no attributes");
403 is(verify_please(kc
, (isRsa
) ? rsa_sha256
: ec_sha256
,
404 (isRsa
) ? sizeof(rsa_sha256
) : sizeof(ec_sha256
)),
405 errSecSuccess
, "Verify SHA256, no attributes");
407 /* with attributes */
408 is(verify_please(kc
, (isRsa
) ? rsa_md5_attr
: NULL
,
409 (isRsa
) ? sizeof(rsa_md5_attr
) : 0),
410 errSecSuccess
, "Verify MD5, with attributes");
411 is(verify_please(kc
, (isRsa
) ? rsa_sha1_attr
: ec_sha1_attr
,
412 (isRsa
) ? sizeof(rsa_sha1_attr
) : sizeof(ec_sha1_attr
)),
413 errSecSuccess
, "Verify SHA1, with attributes");
414 is(verify_please(kc
, (isRsa
) ? rsa_sha256_attr
: ec_sha256_attr
,
415 (isRsa
) ? sizeof(rsa_sha256_attr
) : sizeof(ec_sha256_attr
)),
416 errSecSuccess
, "Verify SHA256, with attributes");
418 /***** Once more, with validation errors *****/
421 is(verify_please(kc
, (isRsa
) ? rsa_sinfo_unknown_digest
: ec_sinfo_unknown_digest
,
422 (isRsa
) ? sizeof(rsa_sinfo_unknown_digest
) : sizeof(ec_sinfo_unknown_digest
)),
423 errSecInvalidDigestAlgorithm
, "Verify unknown digest OID in signer info");
424 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_md5
: ec_md5
,
425 (isRsa
) ? sizeof(rsa_md5
) : sizeof(ec_md5
)),
426 SECFailure
, "Verify invalid MD5, no attributes");
427 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_sha1
: ec_sha1
,
428 (isRsa
) ? sizeof(rsa_sha1
) : sizeof(ec_sha1
)),
429 SECFailure
, "Verify invalid SHA1, no attributes");
430 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_sha256
: ec_sha256
,
431 (isRsa
) ? sizeof(rsa_sha256
) : sizeof(ec_sha256
)),
432 SECFailure
, "Verify invalid SHA256, no attributes");
434 /* with attributes */
435 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_md5_attr
: NULL
,
436 (isRsa
) ? sizeof(rsa_md5_attr
) : 0),
437 SECFailure
, "Verify invalid MD5, with attributes");
438 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_sha1_attr
: ec_sha1_attr
,
439 (isRsa
) ? sizeof(rsa_sha1_attr
) : sizeof(ec_sha1_attr
)),
440 SECFailure
, "Verify invalid SHA1, with attributes");
441 is(invalidate_and_verify(kc
, (isRsa
) ? rsa_sha256_attr
: ec_sha256_attr
,
442 (isRsa
) ? sizeof(rsa_sha256_attr
) : sizeof(ec_sha256_attr
)),
443 SECFailure
, "Verify invalid SHA256, with attributes");
446 #define kNumberEncryptTests 5
447 static void encrypt_tests(SecCertificateRef certificate
) {
448 is(encrypt_please(certificate
, SEC_OID_DES_EDE3_CBC
, 192),
449 errSecSuccess
, "Encrypt with 3DES");
450 is(encrypt_please(certificate
, SEC_OID_RC2_CBC
, 128),
451 errSecDecode
, "Encrypt with 128-bit RC2");
452 is(encrypt_please(certificate
, SEC_OID_AES_128_CBC
, 128),
453 errSecSuccess
, "Encrypt with 128-bit AES");
454 is(encrypt_please(certificate
, SEC_OID_AES_192_CBC
, 192),
455 errSecSuccess
, "Encrypt with 192-bit AES");
456 is(encrypt_please(certificate
, SEC_OID_AES_256_CBC
, 256),
457 errSecSuccess
, "Encrypt with 256-bit AES");
460 #define kNumberDecryptTests 5
461 static void decrypt_tests(bool isRsa
) {
462 is(decrypt_please((isRsa
) ? rsa_3DES
: ec_3DES
,
463 (isRsa
) ? sizeof(rsa_3DES
) : sizeof(ec_3DES
)),
464 errSecSuccess
, "Decrypt 3DES");
465 is(decrypt_please((isRsa
) ? rsa_RC2
: ec_RC2
,
466 (isRsa
) ? sizeof(rsa_RC2
) : sizeof(ec_RC2
)),
467 errSecDecode
, "Decrypt 128-bit RC2");
468 is(decrypt_please((isRsa
) ? rsa_AES_128
: ec_AES_128
,
469 (isRsa
) ? sizeof(rsa_AES_128
) : sizeof(ec_AES_128
)),
470 errSecSuccess
, "Decrypt 128-bit AES");
471 is(decrypt_please((isRsa
) ? rsa_AES_192
: ec_AES_192
,
472 (isRsa
) ? sizeof(rsa_AES_192
) : sizeof(ec_AES_192
)),
473 errSecSuccess
, "Decrypt 192-bit AES");
474 is(decrypt_please((isRsa
) ? rsa_AES_256
: ec_AES_256
,
475 (isRsa
) ? sizeof(rsa_AES_256
) : sizeof(ec_AES_256
)),
476 errSecSuccess
, "Decrypt 256-bit AES");
479 int si_95_cms_basic(int argc
, char *const *argv
)
481 plan_tests(2*(kNumberSetupTests
+ kNumberSignTests
+ kNumberVerifyTests
+
482 kNumberEncryptTests
+ kNumberDecryptTests
+ kNumberCleanupTests
));
484 SecIdentityRef identity
= NULL
;
485 SecCertificateRef certificate
= NULL
;
486 CFDataRef persistentRef
= NULL
;
488 /* SecKeychainRef's aren't a thing on iOS. But the SecCms SPI takes one as
489 * an argument. It gets ignored down in the bowels of libsecurity_smime, so
490 * it's safe to just pass NULL. */
491 SecKeychainRef kc
= NULL
;
494 persistentRef
= setup_keychain(_rsa_identity
, sizeof(_rsa_identity
), &identity
, &certificate
);
495 sign_tests(identity
, true);
496 verify_tests(kc
, true);
497 encrypt_tests(certificate
);
499 cleanup_keychain(persistentRef
, identity
, certificate
);
502 persistentRef
= setup_keychain(_ec_identity
, sizeof(_ec_identity
), &identity
, &certificate
);
503 sign_tests(identity
, false);
504 verify_tests(kc
, false);
505 encrypt_tests(certificate
);
506 decrypt_tests(false);
507 cleanup_keychain(persistentRef
, identity
, certificate
);