blob: 7da74565460821b8a7cdb4fc4dd4e395ab0ea7e0 [file] [log] [blame]
Gilles Peskinee59236f2018-01-27 23:32:46 +01001/* BEGIN_HEADER */
itayzafrir3e02b3b2018-06-12 17:06:52 +03002#include <stdint.h>
mohammad160327010052018-07-03 13:16:15 +03003
4#if defined(MBEDTLS_PSA_CRYPTO_SPM)
5#include "spm/psa_defs.h"
6#endif
7
Gilles Peskinedd2f95b2018-08-11 01:22:42 +02008#include "mbedtls/asn1.h"
Gilles Peskine0b352bc2018-06-28 00:16:11 +02009#include "mbedtls/asn1write.h"
Gilles Peskinedd2f95b2018-08-11 01:22:42 +020010#include "mbedtls/oid.h"
11
Gilles Peskinee59236f2018-01-27 23:32:46 +010012#include "psa/crypto.h"
itayzafrir3e02b3b2018-06-12 17:06:52 +030013
Jaeden Amerof24c7f82018-06-27 17:20:43 +010014/** An invalid export length that will never be set by psa_export_key(). */
15static const size_t INVALID_EXPORT_LENGTH = ~0U;
16
Gilles Peskinef426e0f2019-02-25 17:42:03 +010017/* A hash algorithm that is known to be supported.
18 *
19 * This is used in some smoke tests.
20 */
21#if defined(MBEDTLS_MD2_C)
22#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_MD2
23#elif defined(MBEDTLS_MD4_C)
24#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_MD4
25#elif defined(MBEDTLS_MD5_C)
26#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_MD5
27/* MBEDTLS_RIPEMD160_C omitted. This is necessary for the sake of
28 * exercise_signature_key() because Mbed TLS doesn't support RIPEMD160
29 * in RSA PKCS#1v1.5 signatures. A RIPEMD160-only configuration would be
30 * implausible anyway. */
31#elif defined(MBEDTLS_SHA1_C)
32#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_SHA_1
33#elif defined(MBEDTLS_SHA256_C)
34#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_SHA_256
35#elif defined(MBEDTLS_SHA512_C)
36#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_SHA_384
37#elif defined(MBEDTLS_SHA3_C)
38#define KNOWN_SUPPORTED_HASH_ALG PSA_ALG_SHA3_256
39#else
40#undef KNOWN_SUPPORTED_HASH_ALG
41#endif
42
43/* A block cipher that is known to be supported.
44 *
45 * For simplicity's sake, stick to block ciphers with 16-byte blocks.
46 */
47#if defined(MBEDTLS_AES_C)
48#define KNOWN_SUPPORTED_BLOCK_CIPHER PSA_KEY_TYPE_AES
49#elif defined(MBEDTLS_ARIA_C)
50#define KNOWN_SUPPORTED_BLOCK_CIPHER PSA_KEY_TYPE_ARIA
51#elif defined(MBEDTLS_CAMELLIA_C)
52#define KNOWN_SUPPORTED_BLOCK_CIPHER PSA_KEY_TYPE_CAMELLIA
53#undef KNOWN_SUPPORTED_BLOCK_CIPHER
54#endif
55
56/* A MAC mode that is known to be supported.
57 *
58 * It must either be HMAC with #KNOWN_SUPPORTED_HASH_ALG or
59 * a block cipher-based MAC with #KNOWN_SUPPORTED_BLOCK_CIPHER.
60 *
61 * This is used in some smoke tests.
62 */
63#if defined(KNOWN_SUPPORTED_HASH_ALG)
64#define KNOWN_SUPPORTED_MAC_ALG ( PSA_ALG_HMAC( KNOWN_SUPPORTED_HASH_ALG ) )
65#define KNOWN_SUPPORTED_MAC_KEY_TYPE PSA_KEY_TYPE_HMAC
66#elif defined(KNOWN_SUPPORTED_BLOCK_CIPHER) && defined(MBEDTLS_CMAC_C)
67#define KNOWN_SUPPORTED_MAC_ALG PSA_ALG_CMAC
68#define KNOWN_SUPPORTED_MAC_KEY_TYPE KNOWN_SUPPORTED_BLOCK_CIPHER
69#else
70#undef KNOWN_SUPPORTED_MAC_ALG
71#undef KNOWN_SUPPORTED_MAC_KEY_TYPE
72#endif
73
74/* A cipher algorithm and key type that are known to be supported.
75 *
76 * This is used in some smoke tests.
77 */
78#if defined(KNOWN_SUPPORTED_BLOCK_CIPHER) && defined(MBEDTLS_CIPHER_MODE_CTR)
79#define KNOWN_SUPPORTED_BLOCK_CIPHER_ALG PSA_ALG_CTR
80#elif defined(KNOWN_SUPPORTED_BLOCK_CIPHER) && defined(MBEDTLS_CIPHER_MODE_CBC)
81#define KNOWN_SUPPORTED_BLOCK_CIPHER_ALG PSA_ALG_CBC_NO_PADDING
82#elif defined(KNOWN_SUPPORTED_BLOCK_CIPHER) && defined(MBEDTLS_CIPHER_MODE_CFB)
83#define KNOWN_SUPPORTED_BLOCK_CIPHER_ALG PSA_ALG_CFB
84#elif defined(KNOWN_SUPPORTED_BLOCK_CIPHER) && defined(MBEDTLS_CIPHER_MODE_OFB)
85#define KNOWN_SUPPORTED_BLOCK_CIPHER_ALG PSA_ALG_OFB
86#else
87#undef KNOWN_SUPPORTED_BLOCK_CIPHER_ALG
88#endif
89#if defined(KNOWN_SUPPORTED_BLOCK_CIPHER_ALG)
90#define KNOWN_SUPPORTED_CIPHER_ALG KNOWN_SUPPORTED_BLOCK_CIPHER_ALG
91#define KNOWN_SUPPORTED_CIPHER_KEY_TYPE KNOWN_SUPPORTED_BLOCK_CIPHER
92#elif defined(MBEDTLS_RC4_C)
93#define KNOWN_SUPPORTED_CIPHER_ALG PSA_ALG_RC4
94#define KNOWN_SUPPORTED_CIPHER_KEY_TYPE PSA_KEY_TYPE_RC4
95#else
96#undef KNOWN_SUPPORTED_CIPHER_ALG
97#undef KNOWN_SUPPORTED_CIPHER_KEY_TYPE
98#endif
99
Gilles Peskinea7aa4422018-08-14 15:17:54 +0200100/** Test if a buffer contains a constant byte value.
101 *
102 * `mem_is_char(buffer, c, size)` is true after `memset(buffer, c, size)`.
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200103 *
104 * \param buffer Pointer to the beginning of the buffer.
Gilles Peskinea7aa4422018-08-14 15:17:54 +0200105 * \param c Expected value of every byte.
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200106 * \param size Size of the buffer in bytes.
107 *
Gilles Peskine3f669c32018-06-21 09:21:51 +0200108 * \return 1 if the buffer is all-bits-zero.
109 * \return 0 if there is at least one nonzero byte.
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200110 */
Gilles Peskinea7aa4422018-08-14 15:17:54 +0200111static int mem_is_char( void *buffer, unsigned char c, size_t size )
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200112{
113 size_t i;
114 for( i = 0; i < size; i++ )
115 {
Gilles Peskinea7aa4422018-08-14 15:17:54 +0200116 if( ( (unsigned char *) buffer )[i] != c )
Gilles Peskine3f669c32018-06-21 09:21:51 +0200117 return( 0 );
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200118 }
Gilles Peskine3f669c32018-06-21 09:21:51 +0200119 return( 1 );
Gilles Peskinee66ca3b2018-06-20 00:11:45 +0200120}
Gilles Peskine818ca122018-06-20 18:16:48 +0200121
Gilles Peskine0b352bc2018-06-28 00:16:11 +0200122/* Write the ASN.1 INTEGER with the value 2^(bits-1)+x backwards from *p. */
123static int asn1_write_10x( unsigned char **p,
124 unsigned char *start,
125 size_t bits,
126 unsigned char x )
127{
128 int ret;
129 int len = bits / 8 + 1;
Gilles Peskine480416a2018-06-28 19:04:07 +0200130 if( bits == 0 )
131 return( MBEDTLS_ERR_ASN1_INVALID_DATA );
132 if( bits <= 8 && x >= 1 << ( bits - 1 ) )
Gilles Peskine0b352bc2018-06-28 00:16:11 +0200133 return( MBEDTLS_ERR_ASN1_INVALID_DATA );
Moran Pekercb088e72018-07-17 17:36:59 +0300134 if( *p < start || *p - start < (ptrdiff_t) len )
Gilles Peskine0b352bc2018-06-28 00:16:11 +0200135 return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL );
136 *p -= len;
137 ( *p )[len-1] = x;
138 if( bits % 8 == 0 )
139 ( *p )[1] |= 1;
140 else
141 ( *p )[0] |= 1 << ( bits % 8 );
142 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( p, start, len ) );
143 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( p, start,
144 MBEDTLS_ASN1_INTEGER ) );
145 return( len );
146}
147
148static int construct_fake_rsa_key( unsigned char *buffer,
149 size_t buffer_size,
150 unsigned char **p,
151 size_t bits,
152 int keypair )
153{
154 size_t half_bits = ( bits + 1 ) / 2;
155 int ret;
156 int len = 0;
157 /* Construct something that looks like a DER encoding of
158 * as defined by PKCS#1 v2.2 (RFC 8017) section A.1.2:
159 * RSAPrivateKey ::= SEQUENCE {
160 * version Version,
161 * modulus INTEGER, -- n
162 * publicExponent INTEGER, -- e
163 * privateExponent INTEGER, -- d
164 * prime1 INTEGER, -- p
165 * prime2 INTEGER, -- q
166 * exponent1 INTEGER, -- d mod (p-1)
167 * exponent2 INTEGER, -- d mod (q-1)
168 * coefficient INTEGER, -- (inverse of q) mod p
169 * otherPrimeInfos OtherPrimeInfos OPTIONAL
170 * }
171 * Or, for a public key, the same structure with only
172 * version, modulus and publicExponent.
173 */
174 *p = buffer + buffer_size;
175 if( keypair )
176 {
177 MBEDTLS_ASN1_CHK_ADD( len, /* pq */
178 asn1_write_10x( p, buffer, half_bits, 1 ) );
179 MBEDTLS_ASN1_CHK_ADD( len, /* dq */
180 asn1_write_10x( p, buffer, half_bits, 1 ) );
181 MBEDTLS_ASN1_CHK_ADD( len, /* dp */
182 asn1_write_10x( p, buffer, half_bits, 1 ) );
183 MBEDTLS_ASN1_CHK_ADD( len, /* q */
184 asn1_write_10x( p, buffer, half_bits, 1 ) );
185 MBEDTLS_ASN1_CHK_ADD( len, /* p != q to pass mbedtls sanity checks */
186 asn1_write_10x( p, buffer, half_bits, 3 ) );
187 MBEDTLS_ASN1_CHK_ADD( len, /* d */
188 asn1_write_10x( p, buffer, bits, 1 ) );
189 }
190 MBEDTLS_ASN1_CHK_ADD( len, /* e = 65537 */
191 asn1_write_10x( p, buffer, 17, 1 ) );
192 MBEDTLS_ASN1_CHK_ADD( len, /* n */
193 asn1_write_10x( p, buffer, bits, 1 ) );
194 if( keypair )
195 MBEDTLS_ASN1_CHK_ADD( len, /* version = 0 */
196 mbedtls_asn1_write_int( p, buffer, 0 ) );
197 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( p, buffer, len ) );
198 {
199 const unsigned char tag =
200 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE;
201 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( p, buffer, tag ) );
202 }
203 return( len );
204}
205
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100206int exercise_mac_setup( psa_key_type_t key_type,
207 const unsigned char *key_bytes,
208 size_t key_length,
209 psa_algorithm_t alg,
210 psa_mac_operation_t *operation,
211 psa_status_t *status )
212{
213 psa_key_handle_t handle = 0;
214 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
215
216 PSA_ASSERT( psa_allocate_key( &handle ) );
217 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
218 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
219 PSA_ASSERT( psa_import_key( handle, key_type, key_bytes, key_length ) );
220
221 *status = psa_mac_sign_setup( operation, handle, alg );
222 if( *status == PSA_SUCCESS )
223 {
224 PSA_ASSERT( psa_mac_abort( operation ) );
225 }
226
227 psa_destroy_key( handle );
228 return( 1 );
229
230exit:
231 psa_destroy_key( handle );
232 return( 0 );
233}
234
235int exercise_cipher_setup( psa_key_type_t key_type,
236 const unsigned char *key_bytes,
237 size_t key_length,
238 psa_algorithm_t alg,
239 psa_cipher_operation_t *operation,
240 psa_status_t *status )
241{
242 psa_key_handle_t handle = 0;
243 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
244
245 PSA_ASSERT( psa_allocate_key( &handle ) );
246 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
247 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
248 PSA_ASSERT( psa_import_key( handle, key_type, key_bytes, key_length ) );
249
250 *status = psa_cipher_encrypt_setup( operation, handle, alg );
251 if( *status == PSA_SUCCESS )
252 {
253 PSA_ASSERT( psa_cipher_abort( operation ) );
254 }
255
256 psa_destroy_key( handle );
257 return( 1 );
258
259exit:
260 psa_destroy_key( handle );
261 return( 0 );
262}
263
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100264static int exercise_mac_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200265 psa_key_usage_t usage,
266 psa_algorithm_t alg )
267{
Jaeden Amero769ce272019-01-04 11:48:03 +0000268 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskine818ca122018-06-20 18:16:48 +0200269 const unsigned char input[] = "foo";
Gilles Peskine69c12672018-06-28 00:07:19 +0200270 unsigned char mac[PSA_MAC_MAX_SIZE] = {0};
Gilles Peskine818ca122018-06-20 18:16:48 +0200271 size_t mac_length = sizeof( mac );
272
273 if( usage & PSA_KEY_USAGE_SIGN )
274 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100275 PSA_ASSERT( psa_mac_sign_setup( &operation,
276 handle, alg ) );
277 PSA_ASSERT( psa_mac_update( &operation,
278 input, sizeof( input ) ) );
279 PSA_ASSERT( psa_mac_sign_finish( &operation,
280 mac, sizeof( mac ),
281 &mac_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200282 }
283
284 if( usage & PSA_KEY_USAGE_VERIFY )
285 {
286 psa_status_t verify_status =
287 ( usage & PSA_KEY_USAGE_SIGN ?
288 PSA_SUCCESS :
289 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine8817f612018-12-18 00:18:46 +0100290 PSA_ASSERT( psa_mac_verify_setup( &operation,
291 handle, alg ) );
292 PSA_ASSERT( psa_mac_update( &operation,
293 input, sizeof( input ) ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100294 TEST_EQUAL( psa_mac_verify_finish( &operation, mac, mac_length ),
295 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200296 }
297
298 return( 1 );
299
300exit:
301 psa_mac_abort( &operation );
302 return( 0 );
303}
304
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100305static int exercise_cipher_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200306 psa_key_usage_t usage,
307 psa_algorithm_t alg )
308{
Jaeden Amero5bae2272019-01-04 11:48:27 +0000309 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine818ca122018-06-20 18:16:48 +0200310 unsigned char iv[16] = {0};
311 size_t iv_length = sizeof( iv );
312 const unsigned char plaintext[16] = "Hello, world...";
313 unsigned char ciphertext[32] = "(wabblewebblewibblewobblewubble)";
314 size_t ciphertext_length = sizeof( ciphertext );
315 unsigned char decrypted[sizeof( ciphertext )];
316 size_t part_length;
317
318 if( usage & PSA_KEY_USAGE_ENCRYPT )
319 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100320 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
321 handle, alg ) );
322 PSA_ASSERT( psa_cipher_generate_iv( &operation,
323 iv, sizeof( iv ),
324 &iv_length ) );
325 PSA_ASSERT( psa_cipher_update( &operation,
326 plaintext, sizeof( plaintext ),
327 ciphertext, sizeof( ciphertext ),
328 &ciphertext_length ) );
329 PSA_ASSERT( psa_cipher_finish( &operation,
330 ciphertext + ciphertext_length,
331 sizeof( ciphertext ) - ciphertext_length,
332 &part_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200333 ciphertext_length += part_length;
334 }
335
336 if( usage & PSA_KEY_USAGE_DECRYPT )
337 {
338 psa_status_t status;
Mohammad AboMokhadb9b232018-06-28 01:52:54 -0700339 psa_key_type_t type = PSA_KEY_TYPE_NONE;
Gilles Peskine818ca122018-06-20 18:16:48 +0200340 if( ! ( usage & PSA_KEY_USAGE_ENCRYPT ) )
341 {
Gilles Peskine818ca122018-06-20 18:16:48 +0200342 size_t bits;
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100343 TEST_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200344 iv_length = PSA_BLOCK_CIPHER_BLOCK_SIZE( type );
345 }
Gilles Peskine8817f612018-12-18 00:18:46 +0100346 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
347 handle, alg ) );
348 PSA_ASSERT( psa_cipher_set_iv( &operation,
349 iv, iv_length ) );
350 PSA_ASSERT( psa_cipher_update( &operation,
351 ciphertext, ciphertext_length,
352 decrypted, sizeof( decrypted ),
353 &part_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200354 status = psa_cipher_finish( &operation,
355 decrypted + part_length,
356 sizeof( decrypted ) - part_length,
357 &part_length );
358 /* For a stream cipher, all inputs are valid. For a block cipher,
359 * if the input is some aribtrary data rather than an actual
360 ciphertext, a padding error is likely. */
Mohammad AboMokh65fa0b82018-06-28 02:14:00 -0700361 if( ( usage & PSA_KEY_USAGE_ENCRYPT ) ||
Mohammad AboMokhadb9b232018-06-28 01:52:54 -0700362 PSA_BLOCK_CIPHER_BLOCK_SIZE( type ) == 1 )
Gilles Peskine8817f612018-12-18 00:18:46 +0100363 PSA_ASSERT( status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200364 else
365 TEST_ASSERT( status == PSA_SUCCESS ||
366 status == PSA_ERROR_INVALID_PADDING );
367 }
368
369 return( 1 );
370
371exit:
372 psa_cipher_abort( &operation );
373 return( 0 );
374}
375
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100376static int exercise_aead_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200377 psa_key_usage_t usage,
378 psa_algorithm_t alg )
379{
380 unsigned char nonce[16] = {0};
381 size_t nonce_length = sizeof( nonce );
382 unsigned char plaintext[16] = "Hello, world...";
383 unsigned char ciphertext[48] = "(wabblewebblewibblewobblewubble)";
384 size_t ciphertext_length = sizeof( ciphertext );
385 size_t plaintext_length = sizeof( ciphertext );
386
387 if( usage & PSA_KEY_USAGE_ENCRYPT )
388 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100389 PSA_ASSERT( psa_aead_encrypt( handle, alg,
390 nonce, nonce_length,
391 NULL, 0,
392 plaintext, sizeof( plaintext ),
393 ciphertext, sizeof( ciphertext ),
394 &ciphertext_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200395 }
396
397 if( usage & PSA_KEY_USAGE_DECRYPT )
398 {
399 psa_status_t verify_status =
400 ( usage & PSA_KEY_USAGE_ENCRYPT ?
401 PSA_SUCCESS :
402 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100403 TEST_EQUAL( psa_aead_decrypt( handle, alg,
404 nonce, nonce_length,
405 NULL, 0,
406 ciphertext, ciphertext_length,
407 plaintext, sizeof( plaintext ),
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100408 &plaintext_length ),
409 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200410 }
411
412 return( 1 );
413
414exit:
415 return( 0 );
416}
417
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100418static int exercise_signature_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200419 psa_key_usage_t usage,
420 psa_algorithm_t alg )
421{
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200422 unsigned char payload[PSA_HASH_MAX_SIZE] = {1};
423 size_t payload_length = 16;
Gilles Peskine69c12672018-06-28 00:07:19 +0200424 unsigned char signature[PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE] = {0};
Gilles Peskine818ca122018-06-20 18:16:48 +0200425 size_t signature_length = sizeof( signature );
Gilles Peskine57ab7212019-01-28 13:03:09 +0100426 psa_algorithm_t hash_alg = PSA_ALG_SIGN_GET_HASH( alg );
427
428 /* If the policy allows signing with any hash, just pick one. */
429 if( PSA_ALG_IS_HASH_AND_SIGN( alg ) && hash_alg == PSA_ALG_ANY_HASH )
430 {
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100431#if defined(KNOWN_SUPPORTED_HASH_ALG)
432 hash_alg = KNOWN_SUPPORTED_HASH_ALG;
433 alg ^= PSA_ALG_ANY_HASH ^ hash_alg;
Gilles Peskine57ab7212019-01-28 13:03:09 +0100434#else
435 test_fail( "No hash algorithm for hash-and-sign testing", __LINE__, __FILE__ );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100436 return( 1 );
Gilles Peskine57ab7212019-01-28 13:03:09 +0100437#endif
Gilles Peskine57ab7212019-01-28 13:03:09 +0100438 }
Gilles Peskine818ca122018-06-20 18:16:48 +0200439
440 if( usage & PSA_KEY_USAGE_SIGN )
441 {
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200442 /* Some algorithms require the payload to have the size of
443 * the hash encoded in the algorithm. Use this input size
444 * even for algorithms that allow other input sizes. */
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200445 if( hash_alg != 0 )
446 payload_length = PSA_HASH_SIZE( hash_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +0100447 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
448 payload, payload_length,
449 signature, sizeof( signature ),
450 &signature_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200451 }
452
453 if( usage & PSA_KEY_USAGE_VERIFY )
454 {
455 psa_status_t verify_status =
456 ( usage & PSA_KEY_USAGE_SIGN ?
457 PSA_SUCCESS :
458 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100459 TEST_EQUAL( psa_asymmetric_verify( handle, alg,
460 payload, payload_length,
461 signature, signature_length ),
462 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200463 }
464
465 return( 1 );
466
467exit:
468 return( 0 );
469}
470
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100471static int exercise_asymmetric_encryption_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200472 psa_key_usage_t usage,
473 psa_algorithm_t alg )
474{
475 unsigned char plaintext[256] = "Hello, world...";
476 unsigned char ciphertext[256] = "(wabblewebblewibblewobblewubble)";
477 size_t ciphertext_length = sizeof( ciphertext );
478 size_t plaintext_length = 16;
479
480 if( usage & PSA_KEY_USAGE_ENCRYPT )
481 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100482 PSA_ASSERT( psa_asymmetric_encrypt( handle, alg,
483 plaintext, plaintext_length,
484 NULL, 0,
485 ciphertext, sizeof( ciphertext ),
486 &ciphertext_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200487 }
488
489 if( usage & PSA_KEY_USAGE_DECRYPT )
490 {
491 psa_status_t status =
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100492 psa_asymmetric_decrypt( handle, alg,
Gilles Peskine818ca122018-06-20 18:16:48 +0200493 ciphertext, ciphertext_length,
494 NULL, 0,
495 plaintext, sizeof( plaintext ),
496 &plaintext_length );
497 TEST_ASSERT( status == PSA_SUCCESS ||
498 ( ( usage & PSA_KEY_USAGE_ENCRYPT ) == 0 &&
499 ( status == PSA_ERROR_INVALID_ARGUMENT ||
500 status == PSA_ERROR_INVALID_PADDING ) ) );
501 }
502
503 return( 1 );
504
505exit:
506 return( 0 );
507}
Gilles Peskine02b75072018-07-01 22:31:34 +0200508
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100509static int exercise_key_derivation_key( psa_key_handle_t handle,
Gilles Peskineea0fb492018-07-12 17:17:20 +0200510 psa_key_usage_t usage,
511 psa_algorithm_t alg )
512{
513 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
514 unsigned char label[16] = "This is a label.";
515 size_t label_length = sizeof( label );
516 unsigned char seed[16] = "abcdefghijklmnop";
517 size_t seed_length = sizeof( seed );
518 unsigned char output[1];
519
520 if( usage & PSA_KEY_USAGE_DERIVE )
521 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100522 PSA_ASSERT( psa_key_derivation( &generator,
523 handle, alg,
524 label, label_length,
525 seed, seed_length,
526 sizeof( output ) ) );
527 PSA_ASSERT( psa_generator_read( &generator,
528 output,
529 sizeof( output ) ) );
530 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +0200531 }
532
533 return( 1 );
534
535exit:
536 return( 0 );
537}
538
Gilles Peskinec7998b72018-11-07 18:45:02 +0100539/* We need two keys to exercise key agreement. Exercise the
540 * private key against its own public key. */
541static psa_status_t key_agreement_with_self( psa_crypto_generator_t *generator,
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100542 psa_key_handle_t handle,
Gilles Peskinec7998b72018-11-07 18:45:02 +0100543 psa_algorithm_t alg )
544{
545 psa_key_type_t private_key_type;
546 psa_key_type_t public_key_type;
547 size_t key_bits;
548 uint8_t *public_key = NULL;
549 size_t public_key_length;
David Saadab4ecc272019-02-14 13:48:10 +0200550 /* Return GENERIC_ERROR if something other than the final call to
Gilles Peskinec7998b72018-11-07 18:45:02 +0100551 * psa_key_agreement fails. This isn't fully satisfactory, but it's
552 * good enough: callers will report it as a failed test anyway. */
David Saadab4ecc272019-02-14 13:48:10 +0200553 psa_status_t status = PSA_ERROR_GENERIC_ERROR;
Gilles Peskinec7998b72018-11-07 18:45:02 +0100554
Gilles Peskine8817f612018-12-18 00:18:46 +0100555 PSA_ASSERT( psa_get_key_information( handle,
556 &private_key_type,
557 &key_bits ) );
Gilles Peskinec7998b72018-11-07 18:45:02 +0100558 public_key_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( private_key_type );
559 public_key_length = PSA_KEY_EXPORT_MAX_SIZE( public_key_type, key_bits );
560 ASSERT_ALLOC( public_key, public_key_length );
Gilles Peskine8817f612018-12-18 00:18:46 +0100561 PSA_ASSERT( psa_export_public_key( handle,
562 public_key, public_key_length,
563 &public_key_length ) );
Gilles Peskinec7998b72018-11-07 18:45:02 +0100564
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100565 status = psa_key_agreement( generator, handle,
Gilles Peskinec7998b72018-11-07 18:45:02 +0100566 public_key, public_key_length,
567 alg );
568exit:
569 mbedtls_free( public_key );
570 return( status );
571}
572
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100573static int exercise_key_agreement_key( psa_key_handle_t handle,
Gilles Peskine01d718c2018-09-18 12:01:02 +0200574 psa_key_usage_t usage,
575 psa_algorithm_t alg )
576{
577 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Gilles Peskine01d718c2018-09-18 12:01:02 +0200578 unsigned char output[1];
579 int ok = 0;
580
581 if( usage & PSA_KEY_USAGE_DERIVE )
582 {
583 /* We need two keys to exercise key agreement. Exercise the
584 * private key against its own public key. */
Gilles Peskine8817f612018-12-18 00:18:46 +0100585 PSA_ASSERT( key_agreement_with_self( &generator, handle, alg ) );
586 PSA_ASSERT( psa_generator_read( &generator,
587 output,
588 sizeof( output ) ) );
589 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +0200590 }
591 ok = 1;
592
593exit:
Gilles Peskine01d718c2018-09-18 12:01:02 +0200594 return( ok );
595}
596
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200597static int is_oid_of_key_type( psa_key_type_t type,
598 const uint8_t *oid, size_t oid_length )
599{
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200600 const uint8_t *expected_oid = NULL;
601 size_t expected_oid_length = 0;
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200602#if defined(MBEDTLS_RSA_C)
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200603 if( PSA_KEY_TYPE_IS_RSA( type ) )
604 {
605 expected_oid = (uint8_t *) MBEDTLS_OID_PKCS1_RSA;
606 expected_oid_length = sizeof( MBEDTLS_OID_PKCS1_RSA ) - 1;
607 }
608 else
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200609#endif /* MBEDTLS_RSA_C */
610#if defined(MBEDTLS_ECP_C)
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200611 if( PSA_KEY_TYPE_IS_ECC( type ) )
612 {
613 expected_oid = (uint8_t *) MBEDTLS_OID_EC_ALG_UNRESTRICTED;
614 expected_oid_length = sizeof( MBEDTLS_OID_EC_ALG_UNRESTRICTED ) - 1;
615 }
616 else
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200617#endif /* MBEDTLS_ECP_C */
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200618 {
619 char message[40];
620 mbedtls_snprintf( message, sizeof( message ),
621 "OID not known for key type=0x%08lx",
622 (unsigned long) type );
623 test_fail( message, __LINE__, __FILE__ );
624 return( 0 );
625 }
626
Gilles Peskinebd7dea92018-09-27 13:57:19 +0200627 ASSERT_COMPARE( expected_oid, expected_oid_length, oid, oid_length );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200628 return( 1 );
629
630exit:
631 return( 0 );
632}
633
634static int asn1_skip_integer( unsigned char **p, const unsigned char *end,
635 size_t min_bits, size_t max_bits,
636 int must_be_odd )
637{
638 size_t len;
639 size_t actual_bits;
640 unsigned char msb;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100641 TEST_EQUAL( mbedtls_asn1_get_tag( p, end, &len,
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100642 MBEDTLS_ASN1_INTEGER ),
643 0 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200644 /* Tolerate a slight departure from DER encoding:
645 * - 0 may be represented by an empty string or a 1-byte string.
646 * - The sign bit may be used as a value bit. */
647 if( ( len == 1 && ( *p )[0] == 0 ) ||
648 ( len > 1 && ( *p )[0] == 0 && ( ( *p )[1] & 0x80 ) != 0 ) )
649 {
650 ++( *p );
651 --len;
652 }
653 if( min_bits == 0 && len == 0 )
654 return( 1 );
655 msb = ( *p )[0];
656 TEST_ASSERT( msb != 0 );
657 actual_bits = 8 * ( len - 1 );
658 while( msb != 0 )
659 {
660 msb >>= 1;
661 ++actual_bits;
662 }
663 TEST_ASSERT( actual_bits >= min_bits );
664 TEST_ASSERT( actual_bits <= max_bits );
665 if( must_be_odd )
666 TEST_ASSERT( ( ( *p )[len-1] & 1 ) != 0 );
667 *p += len;
668 return( 1 );
669exit:
670 return( 0 );
671}
672
673static int asn1_get_implicit_tag( unsigned char **p, const unsigned char *end,
674 size_t *len,
675 unsigned char n, unsigned char tag )
676{
677 int ret;
678 ret = mbedtls_asn1_get_tag( p, end, len,
679 MBEDTLS_ASN1_CONTEXT_SPECIFIC |
680 MBEDTLS_ASN1_CONSTRUCTED | ( n ) );
681 if( ret != 0 )
682 return( ret );
683 end = *p + *len;
684 ret = mbedtls_asn1_get_tag( p, end, len, tag );
685 if( ret != 0 )
686 return( ret );
687 if( *p + *len != end )
688 return( MBEDTLS_ERR_ASN1_LENGTH_MISMATCH );
689 return( 0 );
690}
691
692static int exported_key_sanity_check( psa_key_type_t type, size_t bits,
693 uint8_t *exported, size_t exported_length )
694{
695 if( PSA_KEY_TYPE_IS_UNSTRUCTURED( type ) )
Gilles Peskinefe11b722018-12-18 00:24:04 +0100696 TEST_EQUAL( exported_length, ( bits + 7 ) / 8 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200697 else
698 TEST_ASSERT( exported_length <= PSA_KEY_EXPORT_MAX_SIZE( type, bits ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200699
700#if defined(MBEDTLS_DES_C)
701 if( type == PSA_KEY_TYPE_DES )
702 {
703 /* Check the parity bits. */
704 unsigned i;
705 for( i = 0; i < bits / 8; i++ )
706 {
707 unsigned bit_count = 0;
708 unsigned m;
709 for( m = 1; m <= 0x100; m <<= 1 )
710 {
711 if( exported[i] & m )
712 ++bit_count;
713 }
714 TEST_ASSERT( bit_count % 2 != 0 );
715 }
716 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200717 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200718#endif
719
720#if defined(MBEDTLS_RSA_C) && defined(MBEDTLS_PK_PARSE_C)
721 if( type == PSA_KEY_TYPE_RSA_KEYPAIR )
722 {
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200723 uint8_t *p = exported;
724 uint8_t *end = exported + exported_length;
725 size_t len;
726 /* RSAPrivateKey ::= SEQUENCE {
Gilles Peskinedea46cf2018-08-21 16:12:54 +0200727 * version INTEGER, -- must be 0
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200728 * modulus INTEGER, -- n
729 * publicExponent INTEGER, -- e
730 * privateExponent INTEGER, -- d
731 * prime1 INTEGER, -- p
732 * prime2 INTEGER, -- q
733 * exponent1 INTEGER, -- d mod (p-1)
734 * exponent2 INTEGER, -- d mod (q-1)
735 * coefficient INTEGER, -- (inverse of q) mod p
736 * }
737 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100738 TEST_EQUAL( mbedtls_asn1_get_tag( &p, end, &len,
739 MBEDTLS_ASN1_SEQUENCE |
740 MBEDTLS_ASN1_CONSTRUCTED ), 0 );
741 TEST_EQUAL( p + len, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200742 if( ! asn1_skip_integer( &p, end, 0, 0, 0 ) )
743 goto exit;
744 if( ! asn1_skip_integer( &p, end, bits, bits, 1 ) )
745 goto exit;
746 if( ! asn1_skip_integer( &p, end, 2, bits, 1 ) )
747 goto exit;
748 /* Require d to be at least half the size of n. */
749 if( ! asn1_skip_integer( &p, end, bits / 2, bits, 1 ) )
750 goto exit;
751 /* Require p and q to be at most half the size of n, rounded up. */
752 if( ! asn1_skip_integer( &p, end, bits / 2, bits / 2 + 1, 1 ) )
753 goto exit;
754 if( ! asn1_skip_integer( &p, end, bits / 2, bits / 2 + 1, 1 ) )
755 goto exit;
756 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
757 goto exit;
758 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
759 goto exit;
760 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
761 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100762 TEST_EQUAL( p, end );
Gilles Peskine0f915f12018-12-17 23:35:42 +0100763 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200764 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200765#endif /* MBEDTLS_RSA_C */
766
767#if defined(MBEDTLS_ECP_C)
768 if( PSA_KEY_TYPE_IS_ECC_KEYPAIR( type ) )
769 {
Gilles Peskine5b802a32018-10-29 19:21:41 +0100770 /* Just the secret value */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100771 TEST_EQUAL( exported_length, PSA_BITS_TO_BYTES( bits ) );
Gilles Peskine5b802a32018-10-29 19:21:41 +0100772 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200773 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200774#endif /* MBEDTLS_ECP_C */
775
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200776 if( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) )
777 {
778 uint8_t *p = exported;
779 uint8_t *end = exported + exported_length;
780 size_t len;
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200781#if defined(MBEDTLS_RSA_C)
782 if( type == PSA_KEY_TYPE_RSA_PUBLIC_KEY )
783 {
784 /* RSAPublicKey ::= SEQUENCE {
785 * modulus INTEGER, -- n
786 * publicExponent INTEGER } -- e
787 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100788 TEST_EQUAL( mbedtls_asn1_get_tag( &p, end, &len,
789 MBEDTLS_ASN1_SEQUENCE |
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100790 MBEDTLS_ASN1_CONSTRUCTED ),
791 0 );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100792 TEST_EQUAL( p + len, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200793 if( ! asn1_skip_integer( &p, end, bits, bits, 1 ) )
794 goto exit;
795 if( ! asn1_skip_integer( &p, end, 2, bits, 1 ) )
796 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100797 TEST_EQUAL( p, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200798 }
799 else
800#endif /* MBEDTLS_RSA_C */
801#if defined(MBEDTLS_ECP_C)
802 if( PSA_KEY_TYPE_IS_ECC_PUBLIC_KEY( type ) )
803 {
Jaeden Ameroccdce902019-01-10 11:42:27 +0000804 /* The representation of an ECC public key is:
805 * - The byte 0x04;
806 * - `x_P` as a `ceiling(m/8)`-byte string, big-endian;
807 * - `y_P` as a `ceiling(m/8)`-byte string, big-endian;
808 * - where m is the bit size associated with the curve.
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200809 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100810 TEST_EQUAL( p + 1 + 2 * PSA_BITS_TO_BYTES( bits ), end );
811 TEST_EQUAL( p[0], 4 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200812 }
813 else
814#endif /* MBEDTLS_ECP_C */
815 {
Jaeden Amero594a3302018-10-26 17:07:22 +0100816 char message[47];
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200817 mbedtls_snprintf( message, sizeof( message ),
818 "No sanity check for public key type=0x%08lx",
819 (unsigned long) type );
820 test_fail( message, __LINE__, __FILE__ );
821 return( 0 );
822 }
823 }
824 else
825
826 {
827 /* No sanity checks for other types */
828 }
829
830 return( 1 );
Gilles Peskined14664a2018-08-10 19:07:32 +0200831
832exit:
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200833 return( 0 );
Gilles Peskined14664a2018-08-10 19:07:32 +0200834}
835
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100836static int exercise_export_key( psa_key_handle_t handle,
Gilles Peskined14664a2018-08-10 19:07:32 +0200837 psa_key_usage_t usage )
838{
839 psa_key_type_t type;
840 size_t bits;
841 uint8_t *exported = NULL;
842 size_t exported_size = 0;
843 size_t exported_length = 0;
844 int ok = 0;
845
Gilles Peskine8817f612018-12-18 00:18:46 +0100846 PSA_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskineacec7b6f2018-09-13 20:34:11 +0200847
848 if( ( usage & PSA_KEY_USAGE_EXPORT ) == 0 &&
849 ! PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) )
Gilles Peskined14664a2018-08-10 19:07:32 +0200850 {
Gilles Peskinefe11b722018-12-18 00:24:04 +0100851 TEST_EQUAL( psa_export_key( handle, NULL, 0, &exported_length ),
852 PSA_ERROR_NOT_PERMITTED );
Gilles Peskined14664a2018-08-10 19:07:32 +0200853 return( 1 );
854 }
855
Gilles Peskined14664a2018-08-10 19:07:32 +0200856 exported_size = PSA_KEY_EXPORT_MAX_SIZE( type, bits );
Gilles Peskine8cebbba2018-09-27 13:54:18 +0200857 ASSERT_ALLOC( exported, exported_size );
Gilles Peskined14664a2018-08-10 19:07:32 +0200858
Gilles Peskine8817f612018-12-18 00:18:46 +0100859 PSA_ASSERT( psa_export_key( handle,
860 exported, exported_size,
861 &exported_length ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200862 ok = exported_key_sanity_check( type, bits, exported, exported_length );
863
864exit:
865 mbedtls_free( exported );
866 return( ok );
867}
868
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100869static int exercise_export_public_key( psa_key_handle_t handle )
Gilles Peskined14664a2018-08-10 19:07:32 +0200870{
871 psa_key_type_t type;
872 psa_key_type_t public_type;
873 size_t bits;
874 uint8_t *exported = NULL;
875 size_t exported_size = 0;
876 size_t exported_length = 0;
877 int ok = 0;
878
Gilles Peskine8817f612018-12-18 00:18:46 +0100879 PSA_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200880 if( ! PSA_KEY_TYPE_IS_ASYMMETRIC( type ) )
881 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100882 TEST_EQUAL( psa_export_public_key( handle, NULL, 0, &exported_length ),
Gilles Peskinefe11b722018-12-18 00:24:04 +0100883 PSA_ERROR_INVALID_ARGUMENT );
Gilles Peskined14664a2018-08-10 19:07:32 +0200884 return( 1 );
885 }
886
887 public_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( type );
888 exported_size = PSA_KEY_EXPORT_MAX_SIZE( public_type, bits );
Gilles Peskine8cebbba2018-09-27 13:54:18 +0200889 ASSERT_ALLOC( exported, exported_size );
Gilles Peskined14664a2018-08-10 19:07:32 +0200890
Gilles Peskine8817f612018-12-18 00:18:46 +0100891 PSA_ASSERT( psa_export_public_key( handle,
892 exported, exported_size,
893 &exported_length ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200894 ok = exported_key_sanity_check( public_type, bits,
895 exported, exported_length );
896
897exit:
898 mbedtls_free( exported );
899 return( ok );
900}
901
Gilles Peskinec9516fb2019-02-05 20:32:06 +0100902/** Do smoke tests on a key.
903 *
904 * Perform one of each operation indicated by \p alg (decrypt/encrypt,
905 * sign/verify, or derivation) that is permitted according to \p usage.
906 * \p usage and \p alg should correspond to the expected policy on the
907 * key.
908 *
909 * Export the key if permitted by \p usage, and check that the output
910 * looks sensible. If \p usage forbids export, check that
911 * \p psa_export_key correctly rejects the attempt. If the key is
912 * asymmetric, also check \p psa_export_public_key.
913 *
914 * If the key fails the tests, this function calls the test framework's
915 * `test_fail` function and returns false. Otherwise this function returns
916 * true. Therefore it should be used as follows:
917 * ```
918 * if( ! exercise_key( ... ) ) goto exit;
919 * ```
920 *
921 * \param handle The key to exercise. It should be capable of performing
922 * \p alg.
923 * \param usage The usage flags to assume.
924 * \param alg The algorithm to exercise.
925 *
926 * \retval 0 The key failed the smoke tests.
927 * \retval 1 The key passed the smoke tests.
928 */
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100929static int exercise_key( psa_key_handle_t handle,
Gilles Peskine02b75072018-07-01 22:31:34 +0200930 psa_key_usage_t usage,
931 psa_algorithm_t alg )
932{
933 int ok;
934 if( alg == 0 )
935 ok = 1; /* If no algorihm, do nothing (used for raw data "keys"). */
936 else if( PSA_ALG_IS_MAC( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100937 ok = exercise_mac_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +0200938 else if( PSA_ALG_IS_CIPHER( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100939 ok = exercise_cipher_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +0200940 else if( PSA_ALG_IS_AEAD( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100941 ok = exercise_aead_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +0200942 else if( PSA_ALG_IS_SIGN( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100943 ok = exercise_signature_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +0200944 else if( PSA_ALG_IS_ASYMMETRIC_ENCRYPTION( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100945 ok = exercise_asymmetric_encryption_key( handle, usage, alg );
Gilles Peskineea0fb492018-07-12 17:17:20 +0200946 else if( PSA_ALG_IS_KEY_DERIVATION( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100947 ok = exercise_key_derivation_key( handle, usage, alg );
Gilles Peskine01d718c2018-09-18 12:01:02 +0200948 else if( PSA_ALG_IS_KEY_AGREEMENT( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100949 ok = exercise_key_agreement_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +0200950 else
951 {
952 char message[40];
953 mbedtls_snprintf( message, sizeof( message ),
954 "No code to exercise alg=0x%08lx",
955 (unsigned long) alg );
956 test_fail( message, __LINE__, __FILE__ );
957 ok = 0;
958 }
Gilles Peskined14664a2018-08-10 19:07:32 +0200959
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100960 ok = ok && exercise_export_key( handle, usage );
961 ok = ok && exercise_export_public_key( handle );
Gilles Peskined14664a2018-08-10 19:07:32 +0200962
Gilles Peskine02b75072018-07-01 22:31:34 +0200963 return( ok );
964}
965
Gilles Peskine10df3412018-10-25 22:35:43 +0200966static psa_key_usage_t usage_to_exercise( psa_key_type_t type,
967 psa_algorithm_t alg )
968{
969 if( PSA_ALG_IS_MAC( alg ) || PSA_ALG_IS_SIGN( alg ) )
970 {
971 return( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) ?
972 PSA_KEY_USAGE_VERIFY :
973 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY );
974 }
975 else if( PSA_ALG_IS_CIPHER( alg ) || PSA_ALG_IS_AEAD( alg ) ||
976 PSA_ALG_IS_ASYMMETRIC_ENCRYPTION( alg ) )
977 {
978 return( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) ?
979 PSA_KEY_USAGE_ENCRYPT :
980 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT );
981 }
982 else if( PSA_ALG_IS_KEY_DERIVATION( alg ) ||
983 PSA_ALG_IS_KEY_AGREEMENT( alg ) )
984 {
985 return( PSA_KEY_USAGE_DERIVE );
986 }
987 else
988 {
989 return( 0 );
990 }
991
992}
Darryl Green0c6575a2018-11-07 16:05:30 +0000993
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100994/* An overapproximation of the amount of storage needed for a key of the
995 * given type and with the given content. The API doesn't make it easy
996 * to find a good value for the size. The current implementation doesn't
997 * care about the value anyway. */
998#define KEY_BITS_FROM_DATA( type, data ) \
999 ( data )->len
1000
Darryl Green0c6575a2018-11-07 16:05:30 +00001001typedef enum {
1002 IMPORT_KEY = 0,
1003 GENERATE_KEY = 1,
1004 DERIVE_KEY = 2
1005} generate_method;
1006
Gilles Peskinee59236f2018-01-27 23:32:46 +01001007/* END_HEADER */
1008
1009/* BEGIN_DEPENDENCIES
1010 * depends_on:MBEDTLS_PSA_CRYPTO_C
1011 * END_DEPENDENCIES
1012 */
1013
1014/* BEGIN_CASE */
Gilles Peskinee1f2d7d2018-08-21 14:54:54 +02001015void static_checks( )
1016{
1017 size_t max_truncated_mac_size =
1018 PSA_ALG_MAC_TRUNCATION_MASK >> PSA_MAC_TRUNCATION_OFFSET;
1019
1020 /* Check that the length for a truncated MAC always fits in the algorithm
1021 * encoding. The shifted mask is the maximum truncated value. The
1022 * untruncated algorithm may be one byte larger. */
1023 TEST_ASSERT( PSA_MAC_MAX_SIZE <= 1 + max_truncated_mac_size );
1024}
1025/* END_CASE */
1026
1027/* BEGIN_CASE */
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001028void import( data_t *data, int type, int expected_status_arg )
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001029{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001030 psa_key_handle_t handle = 0;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001031 psa_status_t expected_status = expected_status_arg;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001032 psa_status_t status;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001033
Gilles Peskine8817f612018-12-18 00:18:46 +01001034 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001035
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001036 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001037 status = psa_import_key( handle, type, data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001038 TEST_EQUAL( status, expected_status );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001039 if( status == PSA_SUCCESS )
Gilles Peskine8817f612018-12-18 00:18:46 +01001040 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001041
1042exit:
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001043 mbedtls_psa_crypto_free( );
1044}
1045/* END_CASE */
1046
1047/* BEGIN_CASE */
Gilles Peskinea4261682018-12-03 11:34:01 +01001048void import_twice( int alg_arg, int usage_arg,
1049 int type1_arg, data_t *data1,
1050 int expected_import1_status_arg,
1051 int type2_arg, data_t *data2,
1052 int expected_import2_status_arg )
1053{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001054 psa_key_handle_t handle = 0;
Gilles Peskinea4261682018-12-03 11:34:01 +01001055 psa_algorithm_t alg = alg_arg;
1056 psa_key_usage_t usage = usage_arg;
1057 psa_key_type_t type1 = type1_arg;
1058 psa_status_t expected_import1_status = expected_import1_status_arg;
1059 psa_key_type_t type2 = type2_arg;
1060 psa_status_t expected_import2_status = expected_import2_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00001061 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea4261682018-12-03 11:34:01 +01001062 psa_status_t status;
1063
Gilles Peskine8817f612018-12-18 00:18:46 +01001064 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001065
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001066 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001067 psa_key_policy_set_usage( &policy, usage, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001068 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001069
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001070 status = psa_import_key( handle, type1, data1->x, data1->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001071 TEST_EQUAL( status, expected_import1_status );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001072 status = psa_import_key( handle, type2, data2->x, data2->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001073 TEST_EQUAL( status, expected_import2_status );
Gilles Peskinea4261682018-12-03 11:34:01 +01001074
1075 if( expected_import1_status == PSA_SUCCESS ||
1076 expected_import2_status == PSA_SUCCESS )
1077 {
Gilles Peskinec9516fb2019-02-05 20:32:06 +01001078 if( ! exercise_key( handle, usage, alg ) )
1079 goto exit;
Gilles Peskinea4261682018-12-03 11:34:01 +01001080 }
1081
1082exit:
1083 mbedtls_psa_crypto_free( );
1084}
1085/* END_CASE */
1086
1087/* BEGIN_CASE */
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001088void import_rsa_made_up( int bits_arg, int keypair, int expected_status_arg )
1089{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001090 psa_key_handle_t handle = 0;
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001091 size_t bits = bits_arg;
1092 psa_status_t expected_status = expected_status_arg;
1093 psa_status_t status;
1094 psa_key_type_t type =
1095 keypair ? PSA_KEY_TYPE_RSA_KEYPAIR : PSA_KEY_TYPE_RSA_PUBLIC_KEY;
1096 size_t buffer_size = /* Slight overapproximations */
1097 keypair ? bits * 9 / 16 + 80 : bits / 8 + 20;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001098 unsigned char *buffer = NULL;
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001099 unsigned char *p;
1100 int ret;
1101 size_t length;
1102
Gilles Peskine8817f612018-12-18 00:18:46 +01001103 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001104 ASSERT_ALLOC( buffer, buffer_size );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001105
1106 TEST_ASSERT( ( ret = construct_fake_rsa_key( buffer, buffer_size, &p,
1107 bits, keypair ) ) >= 0 );
1108 length = ret;
1109
1110 /* Try importing the key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001111 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001112 status = psa_import_key( handle, type, p, length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001113 TEST_EQUAL( status, expected_status );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001114 if( status == PSA_SUCCESS )
Gilles Peskine8817f612018-12-18 00:18:46 +01001115 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001116
1117exit:
1118 mbedtls_free( buffer );
1119 mbedtls_psa_crypto_free( );
1120}
1121/* END_CASE */
1122
1123/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03001124void import_export( data_t *data,
Moran Pekera964a8f2018-06-04 18:42:36 +03001125 int type_arg,
1126 int alg_arg,
1127 int usage_arg,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001128 int expected_bits,
1129 int export_size_delta,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001130 int expected_export_status_arg,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001131 int canonical_input )
1132{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001133 psa_key_handle_t handle = 0;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001134 psa_key_type_t type = type_arg;
Gilles Peskine4abf7412018-06-18 16:35:34 +02001135 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001136 psa_status_t expected_export_status = expected_export_status_arg;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001137 psa_status_t status;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001138 unsigned char *exported = NULL;
1139 unsigned char *reexported = NULL;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001140 size_t export_size;
Jaeden Amerof24c7f82018-06-27 17:20:43 +01001141 size_t exported_length = INVALID_EXPORT_LENGTH;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001142 size_t reexported_length;
1143 psa_key_type_t got_type;
1144 size_t got_bits;
Jaeden Amero70261c52019-01-04 11:47:20 +00001145 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001146
Moran Pekercb088e72018-07-17 17:36:59 +03001147 export_size = (ptrdiff_t) data->len + export_size_delta;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001148 ASSERT_ALLOC( exported, export_size );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001149 if( ! canonical_input )
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001150 ASSERT_ALLOC( reexported, export_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01001151 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001152
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001153 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02001154 psa_key_policy_set_usage( &policy, usage_arg, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001155 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001156
Gilles Peskinef812dcf2018-12-18 00:33:25 +01001157 TEST_EQUAL( psa_get_key_information( handle, NULL, NULL ),
David Saadab4ecc272019-02-14 13:48:10 +02001158 PSA_ERROR_DOES_NOT_EXIST );
mohammad1603a97cb8c2018-03-28 03:46:26 -07001159
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001160 /* Import the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001161 PSA_ASSERT( psa_import_key( handle, type,
1162 data->x, data->len ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001163
1164 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01001165 PSA_ASSERT( psa_get_key_information( handle,
1166 &got_type,
1167 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001168 TEST_EQUAL( got_type, type );
1169 TEST_EQUAL( got_bits, (size_t) expected_bits );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001170
1171 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001172 status = psa_export_key( handle,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001173 exported, export_size,
1174 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001175 TEST_EQUAL( status, expected_export_status );
Jaeden Amerof24c7f82018-06-27 17:20:43 +01001176
1177 /* The exported length must be set by psa_export_key() to a value between 0
1178 * and export_size. On errors, the exported length must be 0. */
1179 TEST_ASSERT( exported_length != INVALID_EXPORT_LENGTH );
1180 TEST_ASSERT( status == PSA_SUCCESS || exported_length == 0 );
1181 TEST_ASSERT( exported_length <= export_size );
1182
Gilles Peskinea7aa4422018-08-14 15:17:54 +02001183 TEST_ASSERT( mem_is_char( exported + exported_length, 0,
Gilles Peskine3f669c32018-06-21 09:21:51 +02001184 export_size - exported_length ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001185 if( status != PSA_SUCCESS )
Gilles Peskinee66ca3b2018-06-20 00:11:45 +02001186 {
Gilles Peskinefe11b722018-12-18 00:24:04 +01001187 TEST_EQUAL( exported_length, 0 );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001188 goto destroy;
Gilles Peskinee66ca3b2018-06-20 00:11:45 +02001189 }
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001190
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001191 if( ! exercise_export_key( handle, usage_arg ) )
Gilles Peskine8f609232018-08-11 01:24:55 +02001192 goto exit;
1193
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001194 if( canonical_input )
Gilles Peskinebd7dea92018-09-27 13:57:19 +02001195 ASSERT_COMPARE( data->x, data->len, exported, exported_length );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001196 else
1197 {
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001198 psa_key_handle_t handle2;
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001199 PSA_ASSERT( psa_allocate_key( &handle2 ) );
Gilles Peskine8817f612018-12-18 00:18:46 +01001200 PSA_ASSERT( psa_set_key_policy( handle2, &policy ) );
mohammad1603a97cb8c2018-03-28 03:46:26 -07001201
Gilles Peskine8817f612018-12-18 00:18:46 +01001202 PSA_ASSERT( psa_import_key( handle2, type,
1203 exported,
1204 exported_length ) );
1205 PSA_ASSERT( psa_export_key( handle2,
1206 reexported,
1207 export_size,
1208 &reexported_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02001209 ASSERT_COMPARE( exported, exported_length,
1210 reexported, reexported_length );
Gilles Peskine8817f612018-12-18 00:18:46 +01001211 PSA_ASSERT( psa_close_key( handle2 ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001212 }
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001213 TEST_ASSERT( exported_length <= PSA_KEY_EXPORT_MAX_SIZE( type, got_bits ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001214
1215destroy:
1216 /* Destroy the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001217 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01001218 TEST_EQUAL( psa_get_key_information( handle, NULL, NULL ),
1219 PSA_ERROR_INVALID_HANDLE );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001220
1221exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03001222 mbedtls_free( exported );
1223 mbedtls_free( reexported );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001224 mbedtls_psa_crypto_free( );
1225}
1226/* END_CASE */
Gilles Peskine20035e32018-02-03 22:44:14 +01001227
Moran Pekerf709f4a2018-06-06 17:26:04 +03001228/* BEGIN_CASE */
Moran Peker28a38e62018-11-07 16:18:24 +02001229void import_key_nonempty_slot( )
1230{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001231 psa_key_handle_t handle = 0;
Moran Peker28a38e62018-11-07 16:18:24 +02001232 psa_key_type_t type = PSA_KEY_TYPE_RAW_DATA;
1233 psa_status_t status;
1234 const uint8_t data[] = { 0x1, 0x2, 0x3, 0x4, 0x5 };
Gilles Peskine8817f612018-12-18 00:18:46 +01001235 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001236
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001237 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001238
Moran Peker28a38e62018-11-07 16:18:24 +02001239 /* Import the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001240 PSA_ASSERT( psa_import_key( handle, type,
1241 data, sizeof( data ) ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001242
1243 /* Import the key again */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001244 status = psa_import_key( handle, type, data, sizeof( data ) );
David Saadab4ecc272019-02-14 13:48:10 +02001245 TEST_EQUAL( status, PSA_ERROR_ALREADY_EXISTS );
Moran Peker28a38e62018-11-07 16:18:24 +02001246
1247exit:
1248 mbedtls_psa_crypto_free( );
1249}
1250/* END_CASE */
1251
1252/* BEGIN_CASE */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001253void export_invalid_handle( int handle, int expected_export_status_arg )
Moran Peker28a38e62018-11-07 16:18:24 +02001254{
1255 psa_status_t status;
1256 unsigned char *exported = NULL;
1257 size_t export_size = 0;
1258 size_t exported_length = INVALID_EXPORT_LENGTH;
1259 psa_status_t expected_export_status = expected_export_status_arg;
1260
Gilles Peskine8817f612018-12-18 00:18:46 +01001261 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001262
1263 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001264 status = psa_export_key( (psa_key_handle_t) handle,
Moran Peker28a38e62018-11-07 16:18:24 +02001265 exported, export_size,
1266 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001267 TEST_EQUAL( status, expected_export_status );
Moran Peker28a38e62018-11-07 16:18:24 +02001268
1269exit:
1270 mbedtls_psa_crypto_free( );
1271}
1272/* END_CASE */
1273
1274/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001275void export_with_no_key_activity( )
1276{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001277 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001278 psa_algorithm_t alg = PSA_ALG_CTR;
1279 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001280 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Peker34550092018-11-07 16:19:34 +02001281 unsigned char *exported = NULL;
1282 size_t export_size = 0;
1283 size_t exported_length = INVALID_EXPORT_LENGTH;
1284
Gilles Peskine8817f612018-12-18 00:18:46 +01001285 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001286
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001287 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001288 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001289 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Peker34550092018-11-07 16:19:34 +02001290
1291 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001292 status = psa_export_key( handle,
Moran Peker34550092018-11-07 16:19:34 +02001293 exported, export_size,
1294 &exported_length );
David Saadab4ecc272019-02-14 13:48:10 +02001295 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Peker34550092018-11-07 16:19:34 +02001296
1297exit:
1298 mbedtls_psa_crypto_free( );
1299}
1300/* END_CASE */
1301
1302/* BEGIN_CASE */
Moran Pekerce500072018-11-07 16:20:07 +02001303void cipher_with_no_key_activity( )
1304{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001305 psa_key_handle_t handle = 0;
Moran Pekerce500072018-11-07 16:20:07 +02001306 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001307 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001308 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Moran Pekerce500072018-11-07 16:20:07 +02001309 int exercise_alg = PSA_ALG_CTR;
1310
Gilles Peskine8817f612018-12-18 00:18:46 +01001311 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerce500072018-11-07 16:20:07 +02001312
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001313 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekerce500072018-11-07 16:20:07 +02001314 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, exercise_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001315 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekerce500072018-11-07 16:20:07 +02001316
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001317 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
David Saadab4ecc272019-02-14 13:48:10 +02001318 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Pekerce500072018-11-07 16:20:07 +02001319
1320exit:
1321 psa_cipher_abort( &operation );
1322 mbedtls_psa_crypto_free( );
1323}
1324/* END_CASE */
1325
1326/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001327void export_after_import_failure( data_t *data, int type_arg,
1328 int expected_import_status_arg )
1329{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001330 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001331 psa_key_type_t type = type_arg;
1332 psa_status_t status;
1333 unsigned char *exported = NULL;
1334 size_t export_size = 0;
1335 psa_status_t expected_import_status = expected_import_status_arg;
1336 size_t exported_length = INVALID_EXPORT_LENGTH;
1337
Gilles Peskine8817f612018-12-18 00:18:46 +01001338 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001339
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001340 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001341
Moran Peker34550092018-11-07 16:19:34 +02001342 /* Import the key - expect failure */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001343 status = psa_import_key( handle, type,
Gilles Peskine0f915f12018-12-17 23:35:42 +01001344 data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001345 TEST_EQUAL( status, expected_import_status );
Moran Peker34550092018-11-07 16:19:34 +02001346
1347 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001348 status = psa_export_key( handle,
Moran Peker34550092018-11-07 16:19:34 +02001349 exported, export_size,
1350 &exported_length );
David Saadab4ecc272019-02-14 13:48:10 +02001351 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Peker34550092018-11-07 16:19:34 +02001352
1353exit:
1354 mbedtls_psa_crypto_free( );
1355}
1356/* END_CASE */
1357
1358/* BEGIN_CASE */
Moran Pekerce500072018-11-07 16:20:07 +02001359void cipher_after_import_failure( data_t *data, int type_arg,
1360 int expected_import_status_arg )
1361{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001362 psa_key_handle_t handle = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001363 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Moran Pekerce500072018-11-07 16:20:07 +02001364 psa_key_type_t type = type_arg;
1365 psa_status_t status;
1366 psa_status_t expected_import_status = expected_import_status_arg;
1367 int exercise_alg = PSA_ALG_CTR;
1368
Gilles Peskine8817f612018-12-18 00:18:46 +01001369 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerce500072018-11-07 16:20:07 +02001370
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001371 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001372
Moran Pekerce500072018-11-07 16:20:07 +02001373 /* Import the key - expect failure */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001374 status = psa_import_key( handle, type,
Gilles Peskine0f915f12018-12-17 23:35:42 +01001375 data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001376 TEST_EQUAL( status, expected_import_status );
Moran Pekerce500072018-11-07 16:20:07 +02001377
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001378 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
David Saadab4ecc272019-02-14 13:48:10 +02001379 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Pekerce500072018-11-07 16:20:07 +02001380
1381exit:
1382 psa_cipher_abort( &operation );
1383 mbedtls_psa_crypto_free( );
1384}
1385/* END_CASE */
1386
1387/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001388void export_after_destroy_key( data_t *data, int type_arg )
1389{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001390 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001391 psa_key_type_t type = type_arg;
1392 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001393 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Peker34550092018-11-07 16:19:34 +02001394 psa_algorithm_t alg = PSA_ALG_CTR;
1395 unsigned char *exported = NULL;
1396 size_t export_size = 0;
1397 size_t exported_length = INVALID_EXPORT_LENGTH;
1398
Gilles Peskine8817f612018-12-18 00:18:46 +01001399 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001400
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001401 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001402 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001403 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Peker34550092018-11-07 16:19:34 +02001404 export_size = (ptrdiff_t) data->len;
1405 ASSERT_ALLOC( exported, export_size );
1406
1407 /* Import the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001408 PSA_ASSERT( psa_import_key( handle, type,
1409 data->x, data->len ) );
Moran Peker34550092018-11-07 16:19:34 +02001410
Gilles Peskine8817f612018-12-18 00:18:46 +01001411 PSA_ASSERT( psa_export_key( handle, exported, export_size,
1412 &exported_length ) );
Moran Peker34550092018-11-07 16:19:34 +02001413
1414 /* Destroy the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001415 PSA_ASSERT( psa_destroy_key( handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001416
1417 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001418 status = psa_export_key( handle, exported, export_size,
Moran Peker34550092018-11-07 16:19:34 +02001419 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001420 TEST_EQUAL( status, PSA_ERROR_INVALID_HANDLE );
Moran Peker34550092018-11-07 16:19:34 +02001421
1422exit:
1423 mbedtls_free( exported );
1424 mbedtls_psa_crypto_free( );
1425}
1426/* END_CASE */
1427
1428/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03001429void import_export_public_key( data_t *data,
Gilles Peskine2d277862018-06-18 15:41:12 +02001430 int type_arg,
1431 int alg_arg,
Gilles Peskine49c25912018-10-29 15:15:31 +01001432 int export_size_delta,
1433 int expected_export_status_arg,
1434 data_t *expected_public_key )
Moran Pekerf709f4a2018-06-06 17:26:04 +03001435{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001436 psa_key_handle_t handle = 0;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001437 psa_key_type_t type = type_arg;
Gilles Peskine4abf7412018-06-18 16:35:34 +02001438 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001439 psa_status_t expected_export_status = expected_export_status_arg;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001440 psa_status_t status;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001441 unsigned char *exported = NULL;
Gilles Peskine49c25912018-10-29 15:15:31 +01001442 size_t export_size = expected_public_key->len + export_size_delta;
Jaeden Amero2a671e92018-06-27 17:47:40 +01001443 size_t exported_length = INVALID_EXPORT_LENGTH;
Jaeden Amero70261c52019-01-04 11:47:20 +00001444 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001445
Gilles Peskine8817f612018-12-18 00:18:46 +01001446 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001447
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001448 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02001449 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001450 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001451
1452 /* Import the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001453 PSA_ASSERT( psa_import_key( handle, type,
1454 data->x, data->len ) );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001455
Gilles Peskine49c25912018-10-29 15:15:31 +01001456 /* Export the public key */
1457 ASSERT_ALLOC( exported, export_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001458 status = psa_export_public_key( handle,
Gilles Peskine2d277862018-06-18 15:41:12 +02001459 exported, export_size,
1460 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001461 TEST_EQUAL( status, expected_export_status );
Gilles Peskine49c25912018-10-29 15:15:31 +01001462 if( status == PSA_SUCCESS )
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001463 {
1464 psa_key_type_t public_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( type );
1465 size_t bits;
Gilles Peskine8817f612018-12-18 00:18:46 +01001466 PSA_ASSERT( psa_get_key_information( handle, NULL, &bits ) );
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001467 TEST_ASSERT( expected_public_key->len <=
1468 PSA_KEY_EXPORT_MAX_SIZE( public_type, bits ) );
Gilles Peskine49c25912018-10-29 15:15:31 +01001469 ASSERT_COMPARE( expected_public_key->x, expected_public_key->len,
1470 exported, exported_length );
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001471 }
Moran Pekerf709f4a2018-06-06 17:26:04 +03001472
1473exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03001474 mbedtls_free( exported );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001475 psa_destroy_key( handle );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001476 mbedtls_psa_crypto_free( );
1477}
1478/* END_CASE */
1479
Gilles Peskine20035e32018-02-03 22:44:14 +01001480/* BEGIN_CASE */
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001481void import_and_exercise_key( data_t *data,
1482 int type_arg,
1483 int bits_arg,
1484 int alg_arg )
1485{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001486 psa_key_handle_t handle = 0;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001487 psa_key_type_t type = type_arg;
1488 size_t bits = bits_arg;
1489 psa_algorithm_t alg = alg_arg;
Gilles Peskine10df3412018-10-25 22:35:43 +02001490 psa_key_usage_t usage = usage_to_exercise( type, alg );
Jaeden Amero70261c52019-01-04 11:47:20 +00001491 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001492 psa_key_type_t got_type;
1493 size_t got_bits;
1494 psa_status_t status;
1495
Gilles Peskine8817f612018-12-18 00:18:46 +01001496 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001497
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001498 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001499 psa_key_policy_set_usage( &policy, usage, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001500 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001501
1502 /* Import the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001503 status = psa_import_key( handle, type, data->x, data->len );
Gilles Peskine8817f612018-12-18 00:18:46 +01001504 PSA_ASSERT( status );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001505
1506 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01001507 PSA_ASSERT( psa_get_key_information( handle,
1508 &got_type,
1509 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001510 TEST_EQUAL( got_type, type );
1511 TEST_EQUAL( got_bits, bits );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001512
1513 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001514 if( ! exercise_key( handle, usage, alg ) )
Gilles Peskine02b75072018-07-01 22:31:34 +02001515 goto exit;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001516
1517exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001518 psa_destroy_key( handle );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001519 mbedtls_psa_crypto_free( );
1520}
1521/* END_CASE */
1522
1523/* BEGIN_CASE */
Gilles Peskined5b33222018-06-18 22:20:03 +02001524void key_policy( int usage_arg, int alg_arg )
1525{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001526 psa_key_handle_t handle = 0;
Gilles Peskined5b33222018-06-18 22:20:03 +02001527 psa_algorithm_t alg = alg_arg;
1528 psa_key_usage_t usage = usage_arg;
1529 psa_key_type_t key_type = PSA_KEY_TYPE_AES;
1530 unsigned char key[32] = {0};
Jaeden Amero70261c52019-01-04 11:47:20 +00001531 psa_key_policy_t policy_set = PSA_KEY_POLICY_INIT;
1532 psa_key_policy_t policy_get = PSA_KEY_POLICY_INIT;
Gilles Peskined5b33222018-06-18 22:20:03 +02001533
1534 memset( key, 0x2a, sizeof( key ) );
1535
Gilles Peskine8817f612018-12-18 00:18:46 +01001536 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001537
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001538 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001539 psa_key_policy_set_usage( &policy_set, usage, alg );
1540
Gilles Peskinefe11b722018-12-18 00:24:04 +01001541 TEST_EQUAL( psa_key_policy_get_usage( &policy_set ), usage );
1542 TEST_EQUAL( psa_key_policy_get_algorithm( &policy_set ), alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001543 PSA_ASSERT( psa_set_key_policy( handle, &policy_set ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001544
Gilles Peskine8817f612018-12-18 00:18:46 +01001545 PSA_ASSERT( psa_import_key( handle, key_type,
1546 key, sizeof( key ) ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001547
Gilles Peskine8817f612018-12-18 00:18:46 +01001548 PSA_ASSERT( psa_get_key_policy( handle, &policy_get ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001549
Gilles Peskinefe11b722018-12-18 00:24:04 +01001550 TEST_EQUAL( policy_get.usage, policy_set.usage );
1551 TEST_EQUAL( policy_get.alg, policy_set.alg );
Gilles Peskined5b33222018-06-18 22:20:03 +02001552
1553exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001554 psa_destroy_key( handle );
Gilles Peskined5b33222018-06-18 22:20:03 +02001555 mbedtls_psa_crypto_free( );
1556}
1557/* END_CASE */
1558
1559/* BEGIN_CASE */
Jaeden Amero70261c52019-01-04 11:47:20 +00001560void key_policy_init( )
1561{
1562 /* Test each valid way of initializing the object, except for `= {0}`, as
1563 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
1564 * though it's OK by the C standard. We could test for this, but we'd need
1565 * to supress the Clang warning for the test. */
1566 psa_key_policy_t func = psa_key_policy_init( );
1567 psa_key_policy_t init = PSA_KEY_POLICY_INIT;
1568 psa_key_policy_t zero;
1569
1570 memset( &zero, 0, sizeof( zero ) );
1571
Jaeden Amero5229bbb2019-02-07 16:33:37 +00001572 /* A default key policy should not permit any usage. */
1573 TEST_EQUAL( psa_key_policy_get_usage( &func ), 0 );
1574 TEST_EQUAL( psa_key_policy_get_usage( &init ), 0 );
1575 TEST_EQUAL( psa_key_policy_get_usage( &zero ), 0 );
1576
1577 /* A default key policy should not permit any algorithm. */
1578 TEST_EQUAL( psa_key_policy_get_algorithm( &func ), 0 );
1579 TEST_EQUAL( psa_key_policy_get_algorithm( &init ), 0 );
1580 TEST_EQUAL( psa_key_policy_get_algorithm( &zero ), 0 );
Jaeden Amero70261c52019-01-04 11:47:20 +00001581}
1582/* END_CASE */
1583
1584/* BEGIN_CASE */
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001585void mac_key_policy( int policy_usage,
1586 int policy_alg,
1587 int key_type,
1588 data_t *key_data,
1589 int exercise_alg )
Gilles Peskined5b33222018-06-18 22:20:03 +02001590{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001591 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001592 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero769ce272019-01-04 11:48:03 +00001593 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001594 psa_status_t status;
1595 unsigned char mac[PSA_MAC_MAX_SIZE];
Gilles Peskined5b33222018-06-18 22:20:03 +02001596
Gilles Peskine8817f612018-12-18 00:18:46 +01001597 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001598
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001599 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001600 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001601 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001602
Gilles Peskine8817f612018-12-18 00:18:46 +01001603 PSA_ASSERT( psa_import_key( handle, key_type,
1604 key_data->x, key_data->len ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001605
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001606 status = psa_mac_sign_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001607 if( policy_alg == exercise_alg &&
1608 ( policy_usage & PSA_KEY_USAGE_SIGN ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001609 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001610 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001611 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001612 psa_mac_abort( &operation );
Gilles Peskined5b33222018-06-18 22:20:03 +02001613
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001614 memset( mac, 0, sizeof( mac ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001615 status = psa_mac_verify_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001616 if( policy_alg == exercise_alg &&
1617 ( policy_usage & PSA_KEY_USAGE_VERIFY ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001618 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001619 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001620 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001621
1622exit:
1623 psa_mac_abort( &operation );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001624 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001625 mbedtls_psa_crypto_free( );
1626}
1627/* END_CASE */
1628
1629/* BEGIN_CASE */
1630void cipher_key_policy( int policy_usage,
1631 int policy_alg,
1632 int key_type,
1633 data_t *key_data,
1634 int exercise_alg )
1635{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001636 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001637 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001638 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001639 psa_status_t status;
1640
Gilles Peskine8817f612018-12-18 00:18:46 +01001641 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001642
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001643 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001644 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001645 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001646
Gilles Peskine8817f612018-12-18 00:18:46 +01001647 PSA_ASSERT( psa_import_key( handle, key_type,
1648 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001649
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001650 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001651 if( policy_alg == exercise_alg &&
1652 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001653 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001654 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001655 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001656 psa_cipher_abort( &operation );
1657
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001658 status = psa_cipher_decrypt_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001659 if( policy_alg == exercise_alg &&
1660 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001661 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001662 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001663 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001664
1665exit:
1666 psa_cipher_abort( &operation );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001667 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001668 mbedtls_psa_crypto_free( );
1669}
1670/* END_CASE */
1671
1672/* BEGIN_CASE */
1673void aead_key_policy( int policy_usage,
1674 int policy_alg,
1675 int key_type,
1676 data_t *key_data,
1677 int nonce_length_arg,
1678 int tag_length_arg,
1679 int exercise_alg )
1680{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001681 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001682 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001683 psa_status_t status;
1684 unsigned char nonce[16] = {0};
1685 size_t nonce_length = nonce_length_arg;
1686 unsigned char tag[16];
1687 size_t tag_length = tag_length_arg;
1688 size_t output_length;
1689
1690 TEST_ASSERT( nonce_length <= sizeof( nonce ) );
1691 TEST_ASSERT( tag_length <= sizeof( tag ) );
1692
Gilles Peskine8817f612018-12-18 00:18:46 +01001693 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001694
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001695 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001696 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001697 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001698
Gilles Peskine8817f612018-12-18 00:18:46 +01001699 PSA_ASSERT( psa_import_key( handle, key_type,
1700 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001701
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001702 status = psa_aead_encrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001703 nonce, nonce_length,
1704 NULL, 0,
1705 NULL, 0,
1706 tag, tag_length,
1707 &output_length );
1708 if( policy_alg == exercise_alg &&
1709 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001710 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001711 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001712 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001713
1714 memset( tag, 0, sizeof( tag ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001715 status = psa_aead_decrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001716 nonce, nonce_length,
1717 NULL, 0,
1718 tag, tag_length,
1719 NULL, 0,
1720 &output_length );
1721 if( policy_alg == exercise_alg &&
1722 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001723 TEST_EQUAL( status, PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001724 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001725 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001726
1727exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001728 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001729 mbedtls_psa_crypto_free( );
1730}
1731/* END_CASE */
1732
1733/* BEGIN_CASE */
1734void asymmetric_encryption_key_policy( int policy_usage,
1735 int policy_alg,
1736 int key_type,
1737 data_t *key_data,
1738 int exercise_alg )
1739{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001740 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001741 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001742 psa_status_t status;
1743 size_t key_bits;
1744 size_t buffer_length;
1745 unsigned char *buffer = NULL;
1746 size_t output_length;
1747
Gilles Peskine8817f612018-12-18 00:18:46 +01001748 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001749
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001750 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001751 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001752 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001753
Gilles Peskine8817f612018-12-18 00:18:46 +01001754 PSA_ASSERT( psa_import_key( handle, key_type,
1755 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001756
Gilles Peskine8817f612018-12-18 00:18:46 +01001757 PSA_ASSERT( psa_get_key_information( handle,
1758 NULL,
1759 &key_bits ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001760 buffer_length = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits,
1761 exercise_alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001762 ASSERT_ALLOC( buffer, buffer_length );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001763
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001764 status = psa_asymmetric_encrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001765 NULL, 0,
1766 NULL, 0,
1767 buffer, buffer_length,
1768 &output_length );
1769 if( policy_alg == exercise_alg &&
1770 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001771 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001772 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001773 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001774
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02001775 if( buffer_length != 0 )
1776 memset( buffer, 0, buffer_length );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001777 status = psa_asymmetric_decrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001778 buffer, buffer_length,
1779 NULL, 0,
1780 buffer, buffer_length,
1781 &output_length );
1782 if( policy_alg == exercise_alg &&
1783 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001784 TEST_EQUAL( status, PSA_ERROR_INVALID_PADDING );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001785 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001786 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001787
1788exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001789 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001790 mbedtls_psa_crypto_free( );
1791 mbedtls_free( buffer );
1792}
1793/* END_CASE */
1794
1795/* BEGIN_CASE */
1796void asymmetric_signature_key_policy( int policy_usage,
1797 int policy_alg,
1798 int key_type,
1799 data_t *key_data,
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001800 int exercise_alg,
1801 int payload_length_arg )
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001802{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001803 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001804 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001805 psa_status_t status;
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001806 unsigned char payload[PSA_HASH_MAX_SIZE] = {1};
1807 /* If `payload_length_arg > 0`, `exercise_alg` is supposed to be
1808 * compatible with the policy and `payload_length_arg` is supposed to be
1809 * a valid input length to sign. If `payload_length_arg <= 0`,
1810 * `exercise_alg` is supposed to be forbidden by the policy. */
1811 int compatible_alg = payload_length_arg > 0;
1812 size_t payload_length = compatible_alg ? payload_length_arg : 0;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001813 unsigned char signature[PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE] = {0};
1814 size_t signature_length;
1815
Gilles Peskine8817f612018-12-18 00:18:46 +01001816 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001817
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001818 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001819 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001820 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001821
Gilles Peskine8817f612018-12-18 00:18:46 +01001822 PSA_ASSERT( psa_import_key( handle, key_type,
1823 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001824
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001825 status = psa_asymmetric_sign( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001826 payload, payload_length,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001827 signature, sizeof( signature ),
1828 &signature_length );
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001829 if( compatible_alg && ( policy_usage & PSA_KEY_USAGE_SIGN ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001830 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001831 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001832 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001833
1834 memset( signature, 0, sizeof( signature ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001835 status = psa_asymmetric_verify( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001836 payload, payload_length,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001837 signature, sizeof( signature ) );
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001838 if( compatible_alg && ( policy_usage & PSA_KEY_USAGE_VERIFY ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001839 TEST_EQUAL( status, PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001840 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001841 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskined5b33222018-06-18 22:20:03 +02001842
1843exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001844 psa_destroy_key( handle );
Gilles Peskined5b33222018-06-18 22:20:03 +02001845 mbedtls_psa_crypto_free( );
1846}
1847/* END_CASE */
1848
1849/* BEGIN_CASE */
Gilles Peskineea0fb492018-07-12 17:17:20 +02001850void derive_key_policy( int policy_usage,
1851 int policy_alg,
1852 int key_type,
1853 data_t *key_data,
1854 int exercise_alg )
1855{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001856 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001857 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskineea0fb492018-07-12 17:17:20 +02001858 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
1859 psa_status_t status;
1860
Gilles Peskine8817f612018-12-18 00:18:46 +01001861 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001862
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001863 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001864 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001865 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001866
Gilles Peskine8817f612018-12-18 00:18:46 +01001867 PSA_ASSERT( psa_import_key( handle, key_type,
1868 key_data->x, key_data->len ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001869
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001870 status = psa_key_derivation( &generator, handle,
Gilles Peskineea0fb492018-07-12 17:17:20 +02001871 exercise_alg,
1872 NULL, 0,
1873 NULL, 0,
1874 1 );
1875 if( policy_alg == exercise_alg &&
1876 ( policy_usage & PSA_KEY_USAGE_DERIVE ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001877 PSA_ASSERT( status );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001878 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001879 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001880
1881exit:
1882 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001883 psa_destroy_key( handle );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001884 mbedtls_psa_crypto_free( );
1885}
1886/* END_CASE */
1887
1888/* BEGIN_CASE */
Gilles Peskine01d718c2018-09-18 12:01:02 +02001889void agreement_key_policy( int policy_usage,
1890 int policy_alg,
1891 int key_type_arg,
1892 data_t *key_data,
1893 int exercise_alg )
1894{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001895 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001896 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine01d718c2018-09-18 12:01:02 +02001897 psa_key_type_t key_type = key_type_arg;
Gilles Peskine01d718c2018-09-18 12:01:02 +02001898 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
1899 psa_status_t status;
1900
Gilles Peskine8817f612018-12-18 00:18:46 +01001901 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001902
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001903 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001904 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001905 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001906
Gilles Peskine8817f612018-12-18 00:18:46 +01001907 PSA_ASSERT( psa_import_key( handle, key_type,
1908 key_data->x, key_data->len ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001909
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001910 status = key_agreement_with_self( &generator, handle, exercise_alg );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001911
Gilles Peskine01d718c2018-09-18 12:01:02 +02001912 if( policy_alg == exercise_alg &&
1913 ( policy_usage & PSA_KEY_USAGE_DERIVE ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001914 PSA_ASSERT( status );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001915 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001916 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001917
1918exit:
1919 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001920 psa_destroy_key( handle );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001921 mbedtls_psa_crypto_free( );
1922}
1923/* END_CASE */
1924
1925/* BEGIN_CASE */
Gilles Peskine57ab7212019-01-28 13:03:09 +01001926void copy_key_policy( int source_usage_arg, int source_alg_arg,
1927 int type_arg, data_t *material,
1928 int target_usage_arg, int target_alg_arg,
1929 int constraint_usage_arg, int constraint_alg_arg,
1930 int expected_usage_arg, int expected_alg_arg )
1931{
1932 psa_key_usage_t source_usage = source_usage_arg;
1933 psa_algorithm_t source_alg = source_alg_arg;
1934 psa_key_handle_t source_handle = 0;
1935 psa_key_policy_t source_policy = PSA_KEY_POLICY_INIT;
1936 psa_key_type_t source_type = type_arg;
1937 size_t source_bits;
1938 psa_key_usage_t target_usage = target_usage_arg;
1939 psa_algorithm_t target_alg = target_alg_arg;
1940 psa_key_handle_t target_handle = 0;
1941 psa_key_policy_t target_policy = PSA_KEY_POLICY_INIT;
1942 psa_key_type_t target_type;
1943 size_t target_bits;
1944 psa_key_usage_t constraint_usage = constraint_usage_arg;
1945 psa_algorithm_t constraint_alg = constraint_alg_arg;
1946 psa_key_policy_t constraint = PSA_KEY_POLICY_INIT;
1947 psa_key_policy_t *p_constraint = NULL;
1948 psa_key_usage_t expected_usage = expected_usage_arg;
1949 psa_algorithm_t expected_alg = expected_alg_arg;
1950 uint8_t *export_buffer = NULL;
1951
1952 if( constraint_usage_arg != -1 )
1953 {
1954 p_constraint = &constraint;
1955 psa_key_policy_set_usage( p_constraint,
1956 constraint_usage, constraint_alg );
1957 }
1958
1959 PSA_ASSERT( psa_crypto_init( ) );
1960
1961 /* Populate the source slot. */
1962 PSA_ASSERT( psa_allocate_key( &source_handle ) );
1963 psa_key_policy_set_usage( &source_policy, source_usage, source_alg );
1964 PSA_ASSERT( psa_set_key_policy( source_handle, &source_policy ) );
1965 PSA_ASSERT( psa_import_key( source_handle, source_type,
1966 material->x, material->len ) );
1967 PSA_ASSERT( psa_get_key_information( source_handle, NULL, &source_bits ) );
1968
1969 /* Prepare the target slot. */
1970 PSA_ASSERT( psa_allocate_key( &target_handle ) );
1971 psa_key_policy_set_usage( &target_policy, target_usage, target_alg );
1972 PSA_ASSERT( psa_set_key_policy( target_handle, &target_policy ) );
1973 target_policy = psa_key_policy_init();
1974
1975 /* Copy the key. */
1976 PSA_ASSERT( psa_copy_key( source_handle, target_handle, p_constraint ) );
1977
1978 /* Destroy the source to ensure that this doesn't affect the target. */
1979 PSA_ASSERT( psa_destroy_key( source_handle ) );
1980
1981 /* Test that the target slot has the expected content and policy. */
1982 PSA_ASSERT( psa_get_key_information( target_handle,
1983 &target_type, &target_bits ) );
1984 TEST_EQUAL( source_type, target_type );
1985 TEST_EQUAL( source_bits, target_bits );
1986 PSA_ASSERT( psa_get_key_policy( target_handle, &target_policy ) );
1987 TEST_EQUAL( expected_usage, psa_key_policy_get_usage( &target_policy ) );
1988 TEST_EQUAL( expected_alg, psa_key_policy_get_algorithm( &target_policy ) );
1989 if( expected_usage & PSA_KEY_USAGE_EXPORT )
1990 {
1991 size_t length;
1992 ASSERT_ALLOC( export_buffer, material->len );
1993 PSA_ASSERT( psa_export_key( target_handle, export_buffer,
1994 material->len, &length ) );
1995 ASSERT_COMPARE( material->x, material->len,
1996 export_buffer, length );
1997 }
1998 if( ! exercise_key( target_handle, expected_usage, expected_alg ) )
1999 goto exit;
2000
2001 PSA_ASSERT( psa_close_key( target_handle ) );
2002
2003exit:
2004 mbedtls_psa_crypto_free( );
2005 mbedtls_free( export_buffer );
2006}
2007/* END_CASE */
2008
2009/* BEGIN_CASE */
2010void copy_fail( int source_usage_arg, int source_alg_arg,
2011 int type_arg, data_t *material,
2012 int target_usage_arg, int target_alg_arg,
2013 int constraint_usage_arg, int constraint_alg_arg,
2014 int expected_status_arg )
2015{
2016 /* Test copy failure into an empty slot. There is a test for copy failure
2017 * into an occupied slot in
2018 * test_suite_psa_crypto_slot_management.function. */
2019
2020 psa_key_usage_t source_usage = source_usage_arg;
2021 psa_algorithm_t source_alg = source_alg_arg;
2022 psa_key_handle_t source_handle = 0;
2023 psa_key_policy_t source_policy = PSA_KEY_POLICY_INIT;
2024 psa_key_type_t source_type = type_arg;
2025 size_t source_bits;
2026 psa_key_usage_t target_usage = target_usage_arg;
2027 psa_algorithm_t target_alg = target_alg_arg;
2028 psa_key_handle_t target_handle = 0;
2029 psa_key_policy_t target_policy = PSA_KEY_POLICY_INIT;
2030 psa_key_type_t target_type;
2031 size_t target_bits;
2032 psa_key_usage_t constraint_usage = constraint_usage_arg;
2033 psa_algorithm_t constraint_alg = constraint_alg_arg;
2034 psa_key_policy_t constraint = PSA_KEY_POLICY_INIT;
2035 psa_key_policy_t *p_constraint = NULL;
2036 psa_status_t expected_status = expected_status_arg;
2037
2038 if( constraint_usage_arg != -1 )
2039 {
2040 p_constraint = &constraint;
2041 psa_key_policy_set_usage( p_constraint,
2042 constraint_usage, constraint_alg );
2043 }
2044
2045 PSA_ASSERT( psa_crypto_init( ) );
2046
2047 /* Populate the source slot. */
2048 PSA_ASSERT( psa_allocate_key( &source_handle ) );
2049 psa_key_policy_set_usage( &source_policy, source_usage, source_alg );
2050 PSA_ASSERT( psa_set_key_policy( source_handle, &source_policy ) );
2051 PSA_ASSERT( psa_import_key( source_handle, source_type,
2052 material->x, material->len ) );
2053 PSA_ASSERT( psa_get_key_information( source_handle, NULL, &source_bits ) );
2054
2055 /* Prepare the target slot. */
2056 PSA_ASSERT( psa_allocate_key( &target_handle ) );
2057 psa_key_policy_set_usage( &target_policy, target_usage, target_alg );
2058 PSA_ASSERT( psa_set_key_policy( target_handle, &target_policy ) );
2059 target_policy = psa_key_policy_init();
2060
2061 /* Copy the key. */
2062 TEST_EQUAL( psa_copy_key( source_handle, target_handle, p_constraint ),
2063 expected_status );
2064
2065 /* Test that the target slot is unaffected. */
2066 TEST_EQUAL( psa_get_key_information( target_handle,
2067 &target_type, &target_bits ),
David Saadab4ecc272019-02-14 13:48:10 +02002068 PSA_ERROR_DOES_NOT_EXIST );
Gilles Peskine57ab7212019-01-28 13:03:09 +01002069 PSA_ASSERT( psa_get_key_policy( target_handle, &target_policy ) );
2070 TEST_EQUAL( target_usage, psa_key_policy_get_usage( &target_policy ) );
2071 TEST_EQUAL( target_alg, psa_key_policy_get_algorithm( &target_policy ) );
2072
2073exit:
2074 mbedtls_psa_crypto_free( );
2075}
2076/* END_CASE */
2077
2078/* BEGIN_CASE */
Jaeden Amero6a25b412019-01-04 11:47:44 +00002079void hash_operation_init( )
2080{
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002081 const uint8_t input[1] = { 0 };
Jaeden Amero6a25b412019-01-04 11:47:44 +00002082 /* Test each valid way of initializing the object, except for `= {0}`, as
2083 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2084 * though it's OK by the C standard. We could test for this, but we'd need
2085 * to supress the Clang warning for the test. */
2086 psa_hash_operation_t func = psa_hash_operation_init( );
2087 psa_hash_operation_t init = PSA_HASH_OPERATION_INIT;
2088 psa_hash_operation_t zero;
2089
2090 memset( &zero, 0, sizeof( zero ) );
2091
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002092 /* A freshly-initialized hash operation should not be usable. */
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002093 TEST_EQUAL( psa_hash_update( &func, input, sizeof( input ) ),
2094 PSA_ERROR_BAD_STATE );
2095 TEST_EQUAL( psa_hash_update( &init, input, sizeof( input ) ),
2096 PSA_ERROR_BAD_STATE );
2097 TEST_EQUAL( psa_hash_update( &zero, input, sizeof( input ) ),
2098 PSA_ERROR_BAD_STATE );
2099
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002100 /* A default hash operation should be abortable without error. */
2101 PSA_ASSERT( psa_hash_abort( &func ) );
2102 PSA_ASSERT( psa_hash_abort( &init ) );
2103 PSA_ASSERT( psa_hash_abort( &zero ) );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002104}
2105/* END_CASE */
2106
2107/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002108void hash_setup( int alg_arg,
2109 int expected_status_arg )
2110{
2111 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002112 psa_status_t expected_status = expected_status_arg;
Jaeden Amero6a25b412019-01-04 11:47:44 +00002113 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002114 psa_status_t status;
2115
Gilles Peskine8817f612018-12-18 00:18:46 +01002116 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002117
Gilles Peskineda8191d1c2018-07-08 19:46:38 +02002118 status = psa_hash_setup( &operation, alg );
Gilles Peskinefe11b722018-12-18 00:24:04 +01002119 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002120
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002121 if( status == PSA_SUCCESS )
2122 PSA_ASSERT( psa_hash_abort( &operation ) );
2123 /* Now the operation object should be reusable. */
2124#if defined(KNOWN_SUPPORTED_HASH_ALG)
2125 PSA_ASSERT( psa_hash_setup( &operation, KNOWN_SUPPORTED_HASH_ALG ) );
2126 PSA_ASSERT( psa_hash_abort( &operation ) );
2127#endif
2128
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002129exit:
2130 mbedtls_psa_crypto_free( );
2131}
2132/* END_CASE */
2133
2134/* BEGIN_CASE */
itayzafrirf86548d2018-11-01 10:44:32 +02002135void hash_bad_order( )
2136{
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002137 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrirf86548d2018-11-01 10:44:32 +02002138 unsigned char input[] = "";
2139 /* SHA-256 hash of an empty string */
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002140 const unsigned char valid_hash[] = {
itayzafrirf86548d2018-11-01 10:44:32 +02002141 0xe3, 0xb0, 0xc4, 0x42, 0x98, 0xfc, 0x1c, 0x14, 0x9a, 0xfb, 0xf4, 0xc8,
2142 0x99, 0x6f, 0xb9, 0x24, 0x27, 0xae, 0x41, 0xe4, 0x64, 0x9b, 0x93, 0x4c,
2143 0xa4, 0x95, 0x99, 0x1b, 0x78, 0x52, 0xb8, 0x55 };
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002144 unsigned char hash[sizeof(valid_hash)] = { 0 };
itayzafrirf86548d2018-11-01 10:44:32 +02002145 size_t hash_len;
Jaeden Amero6a25b412019-01-04 11:47:44 +00002146 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrirf86548d2018-11-01 10:44:32 +02002147
Gilles Peskine8817f612018-12-18 00:18:46 +01002148 PSA_ASSERT( psa_crypto_init( ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002149
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002150 /* Call setup twice in a row. */
2151 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2152 TEST_EQUAL( psa_hash_setup( &operation, alg ),
2153 PSA_ERROR_BAD_STATE );
2154 PSA_ASSERT( psa_hash_abort( &operation ) );
2155
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002156 /* Call update without calling setup beforehand. */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002157 TEST_EQUAL( psa_hash_update( &operation, input, sizeof( input ) ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002158 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002159 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002160
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002161 /* Call update after finish. */
2162 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2163 PSA_ASSERT( psa_hash_finish( &operation,
2164 hash, sizeof( hash ), &hash_len ) );
2165 TEST_EQUAL( psa_hash_update( &operation, input, sizeof( input ) ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002166 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002167 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002168
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002169 /* Call verify without calling setup beforehand. */
2170 TEST_EQUAL( psa_hash_verify( &operation,
2171 valid_hash, sizeof( valid_hash ) ),
2172 PSA_ERROR_BAD_STATE );
2173 PSA_ASSERT( psa_hash_abort( &operation ) );
2174
2175 /* Call verify after finish. */
2176 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2177 PSA_ASSERT( psa_hash_finish( &operation,
2178 hash, sizeof( hash ), &hash_len ) );
2179 TEST_EQUAL( psa_hash_verify( &operation,
2180 valid_hash, sizeof( valid_hash ) ),
2181 PSA_ERROR_BAD_STATE );
2182 PSA_ASSERT( psa_hash_abort( &operation ) );
2183
2184 /* Call verify twice in a row. */
2185 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2186 PSA_ASSERT( psa_hash_verify( &operation,
2187 valid_hash, sizeof( valid_hash ) ) );
2188 TEST_EQUAL( psa_hash_verify( &operation,
2189 valid_hash, sizeof( valid_hash ) ),
2190 PSA_ERROR_BAD_STATE );
2191 PSA_ASSERT( psa_hash_abort( &operation ) );
2192
2193 /* Call finish without calling setup beforehand. */
Gilles Peskinefe11b722018-12-18 00:24:04 +01002194 TEST_EQUAL( psa_hash_finish( &operation,
2195 hash, sizeof( hash ), &hash_len ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002196 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002197 PSA_ASSERT( psa_hash_abort( &operation ) );
2198
2199 /* Call finish twice in a row. */
2200 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2201 PSA_ASSERT( psa_hash_finish( &operation,
2202 hash, sizeof( hash ), &hash_len ) );
2203 TEST_EQUAL( psa_hash_finish( &operation,
2204 hash, sizeof( hash ), &hash_len ),
2205 PSA_ERROR_BAD_STATE );
2206 PSA_ASSERT( psa_hash_abort( &operation ) );
2207
2208 /* Call finish after calling verify. */
2209 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2210 PSA_ASSERT( psa_hash_verify( &operation,
2211 valid_hash, sizeof( valid_hash ) ) );
2212 TEST_EQUAL( psa_hash_finish( &operation,
2213 hash, sizeof( hash ), &hash_len ),
2214 PSA_ERROR_BAD_STATE );
2215 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002216
2217exit:
2218 mbedtls_psa_crypto_free( );
2219}
2220/* END_CASE */
2221
itayzafrir27e69452018-11-01 14:26:34 +02002222/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2223void hash_verify_bad_args( )
itayzafrirec93d302018-10-18 18:01:10 +03002224{
2225 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrir27e69452018-11-01 14:26:34 +02002226 /* SHA-256 hash of an empty string with 2 extra bytes (0xaa and 0xbb)
2227 * appended to it */
2228 unsigned char hash[] = {
2229 0xe3, 0xb0, 0xc4, 0x42, 0x98, 0xfc, 0x1c, 0x14, 0x9a, 0xfb, 0xf4, 0xc8,
2230 0x99, 0x6f, 0xb9, 0x24, 0x27, 0xae, 0x41, 0xe4, 0x64, 0x9b, 0x93, 0x4c,
2231 0xa4, 0x95, 0x99, 0x1b, 0x78, 0x52, 0xb8, 0x55, 0xaa, 0xbb };
itayzafrirec93d302018-10-18 18:01:10 +03002232 size_t expected_size = PSA_HASH_SIZE( alg );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002233 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrirec93d302018-10-18 18:01:10 +03002234
Gilles Peskine8817f612018-12-18 00:18:46 +01002235 PSA_ASSERT( psa_crypto_init( ) );
itayzafrirec93d302018-10-18 18:01:10 +03002236
itayzafrir27e69452018-11-01 14:26:34 +02002237 /* psa_hash_verify with a smaller hash than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002238 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002239 TEST_EQUAL( psa_hash_verify( &operation, hash, expected_size - 1 ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002240 PSA_ERROR_INVALID_SIGNATURE );
itayzafrirec93d302018-10-18 18:01:10 +03002241
itayzafrir27e69452018-11-01 14:26:34 +02002242 /* psa_hash_verify with a non-matching hash */
Gilles Peskine8817f612018-12-18 00:18:46 +01002243 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002244 TEST_EQUAL( psa_hash_verify( &operation, hash + 1, expected_size ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002245 PSA_ERROR_INVALID_SIGNATURE );
itayzafrirec93d302018-10-18 18:01:10 +03002246
itayzafrir27e69452018-11-01 14:26:34 +02002247 /* psa_hash_verify with a hash longer than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002248 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002249 TEST_EQUAL( psa_hash_verify( &operation, hash, sizeof( hash ) ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002250 PSA_ERROR_INVALID_SIGNATURE );
itayzafrir4271df92018-10-24 18:16:19 +03002251
itayzafrirec93d302018-10-18 18:01:10 +03002252exit:
2253 mbedtls_psa_crypto_free( );
2254}
2255/* END_CASE */
2256
itayzafrirb2dd5ed2018-11-01 11:58:59 +02002257/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2258void hash_finish_bad_args( )
itayzafrir58028322018-10-25 10:22:01 +03002259{
2260 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrirb2dd5ed2018-11-01 11:58:59 +02002261 unsigned char hash[PSA_HASH_MAX_SIZE];
itayzafrir58028322018-10-25 10:22:01 +03002262 size_t expected_size = PSA_HASH_SIZE( alg );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002263 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrir58028322018-10-25 10:22:01 +03002264 size_t hash_len;
2265
Gilles Peskine8817f612018-12-18 00:18:46 +01002266 PSA_ASSERT( psa_crypto_init( ) );
itayzafrir58028322018-10-25 10:22:01 +03002267
itayzafrir58028322018-10-25 10:22:01 +03002268 /* psa_hash_finish with a smaller hash buffer than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002269 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01002270 TEST_EQUAL( psa_hash_finish( &operation,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002271 hash, expected_size - 1, &hash_len ),
2272 PSA_ERROR_BUFFER_TOO_SMALL );
itayzafrir58028322018-10-25 10:22:01 +03002273
2274exit:
2275 mbedtls_psa_crypto_free( );
2276}
2277/* END_CASE */
2278
Gilles Peskineebb2c3e2019-01-19 12:03:41 +01002279/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2280void hash_clone_source_state( )
2281{
2282 psa_algorithm_t alg = PSA_ALG_SHA_256;
2283 unsigned char hash[PSA_HASH_MAX_SIZE];
2284 psa_hash_operation_t op_source = PSA_HASH_OPERATION_INIT;
2285 psa_hash_operation_t op_init = PSA_HASH_OPERATION_INIT;
2286 psa_hash_operation_t op_setup = PSA_HASH_OPERATION_INIT;
2287 psa_hash_operation_t op_finished = PSA_HASH_OPERATION_INIT;
2288 psa_hash_operation_t op_aborted = PSA_HASH_OPERATION_INIT;
2289 size_t hash_len;
2290
2291 PSA_ASSERT( psa_crypto_init( ) );
2292 PSA_ASSERT( psa_hash_setup( &op_source, alg ) );
2293
2294 PSA_ASSERT( psa_hash_setup( &op_setup, alg ) );
2295 PSA_ASSERT( psa_hash_setup( &op_finished, alg ) );
2296 PSA_ASSERT( psa_hash_finish( &op_finished,
2297 hash, sizeof( hash ), &hash_len ) );
2298 PSA_ASSERT( psa_hash_setup( &op_aborted, alg ) );
2299 PSA_ASSERT( psa_hash_abort( &op_aborted ) );
2300
2301 TEST_EQUAL( psa_hash_clone( &op_source, &op_setup ),
2302 PSA_ERROR_BAD_STATE );
2303
2304 PSA_ASSERT( psa_hash_clone( &op_source, &op_init ) );
2305 PSA_ASSERT( psa_hash_finish( &op_init,
2306 hash, sizeof( hash ), &hash_len ) );
2307 PSA_ASSERT( psa_hash_clone( &op_source, &op_finished ) );
2308 PSA_ASSERT( psa_hash_finish( &op_finished,
2309 hash, sizeof( hash ), &hash_len ) );
2310 PSA_ASSERT( psa_hash_clone( &op_source, &op_aborted ) );
2311 PSA_ASSERT( psa_hash_finish( &op_aborted,
2312 hash, sizeof( hash ), &hash_len ) );
2313
2314exit:
2315 psa_hash_abort( &op_source );
2316 psa_hash_abort( &op_init );
2317 psa_hash_abort( &op_setup );
2318 psa_hash_abort( &op_finished );
2319 psa_hash_abort( &op_aborted );
2320 mbedtls_psa_crypto_free( );
2321}
2322/* END_CASE */
2323
2324/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2325void hash_clone_target_state( )
2326{
2327 psa_algorithm_t alg = PSA_ALG_SHA_256;
2328 unsigned char hash[PSA_HASH_MAX_SIZE];
2329 psa_hash_operation_t op_init = PSA_HASH_OPERATION_INIT;
2330 psa_hash_operation_t op_setup = PSA_HASH_OPERATION_INIT;
2331 psa_hash_operation_t op_finished = PSA_HASH_OPERATION_INIT;
2332 psa_hash_operation_t op_aborted = PSA_HASH_OPERATION_INIT;
2333 psa_hash_operation_t op_target = PSA_HASH_OPERATION_INIT;
2334 size_t hash_len;
2335
2336 PSA_ASSERT( psa_crypto_init( ) );
2337
2338 PSA_ASSERT( psa_hash_setup( &op_setup, alg ) );
2339 PSA_ASSERT( psa_hash_setup( &op_finished, alg ) );
2340 PSA_ASSERT( psa_hash_finish( &op_finished,
2341 hash, sizeof( hash ), &hash_len ) );
2342 PSA_ASSERT( psa_hash_setup( &op_aborted, alg ) );
2343 PSA_ASSERT( psa_hash_abort( &op_aborted ) );
2344
2345 PSA_ASSERT( psa_hash_clone( &op_setup, &op_target ) );
2346 PSA_ASSERT( psa_hash_finish( &op_target,
2347 hash, sizeof( hash ), &hash_len ) );
2348
2349 TEST_EQUAL( psa_hash_clone( &op_init, &op_target ), PSA_ERROR_BAD_STATE );
2350 TEST_EQUAL( psa_hash_clone( &op_finished, &op_target ),
2351 PSA_ERROR_BAD_STATE );
2352 TEST_EQUAL( psa_hash_clone( &op_aborted, &op_target ),
2353 PSA_ERROR_BAD_STATE );
2354
2355exit:
2356 psa_hash_abort( &op_target );
2357 psa_hash_abort( &op_init );
2358 psa_hash_abort( &op_setup );
2359 psa_hash_abort( &op_finished );
2360 psa_hash_abort( &op_aborted );
2361 mbedtls_psa_crypto_free( );
2362}
2363/* END_CASE */
2364
itayzafrir58028322018-10-25 10:22:01 +03002365/* BEGIN_CASE */
Jaeden Amero769ce272019-01-04 11:48:03 +00002366void mac_operation_init( )
2367{
Jaeden Amero252ef282019-02-15 14:05:35 +00002368 const uint8_t input[1] = { 0 };
2369
Jaeden Amero769ce272019-01-04 11:48:03 +00002370 /* Test each valid way of initializing the object, except for `= {0}`, as
2371 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2372 * though it's OK by the C standard. We could test for this, but we'd need
2373 * to supress the Clang warning for the test. */
2374 psa_mac_operation_t func = psa_mac_operation_init( );
2375 psa_mac_operation_t init = PSA_MAC_OPERATION_INIT;
2376 psa_mac_operation_t zero;
2377
2378 memset( &zero, 0, sizeof( zero ) );
2379
Jaeden Amero252ef282019-02-15 14:05:35 +00002380 /* A freshly-initialized MAC operation should not be usable. */
2381 TEST_EQUAL( psa_mac_update( &func,
2382 input, sizeof( input ) ),
2383 PSA_ERROR_BAD_STATE );
2384 TEST_EQUAL( psa_mac_update( &init,
2385 input, sizeof( input ) ),
2386 PSA_ERROR_BAD_STATE );
2387 TEST_EQUAL( psa_mac_update( &zero,
2388 input, sizeof( input ) ),
2389 PSA_ERROR_BAD_STATE );
2390
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002391 /* A default MAC operation should be abortable without error. */
2392 PSA_ASSERT( psa_mac_abort( &func ) );
2393 PSA_ASSERT( psa_mac_abort( &init ) );
2394 PSA_ASSERT( psa_mac_abort( &zero ) );
Jaeden Amero769ce272019-01-04 11:48:03 +00002395}
2396/* END_CASE */
2397
2398/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002399void mac_setup( int key_type_arg,
2400 data_t *key,
2401 int alg_arg,
2402 int expected_status_arg )
2403{
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002404 psa_key_type_t key_type = key_type_arg;
2405 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002406 psa_status_t expected_status = expected_status_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002407 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002408 psa_status_t status = PSA_ERROR_GENERIC_ERROR;
2409#if defined(KNOWN_SUPPORTED_MAC_ALG)
2410 const uint8_t smoke_test_key_data[16] = "kkkkkkkkkkkkkkkk";
2411#endif
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002412
Gilles Peskine8817f612018-12-18 00:18:46 +01002413 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002414
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002415 if( ! exercise_mac_setup( key_type, key->x, key->len, alg,
2416 &operation, &status ) )
2417 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01002418 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002419
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002420 /* The operation object should be reusable. */
2421#if defined(KNOWN_SUPPORTED_MAC_ALG)
2422 if( ! exercise_mac_setup( KNOWN_SUPPORTED_MAC_KEY_TYPE,
2423 smoke_test_key_data,
2424 sizeof( smoke_test_key_data ),
2425 KNOWN_SUPPORTED_MAC_ALG,
2426 &operation, &status ) )
2427 goto exit;
2428 TEST_EQUAL( status, PSA_SUCCESS );
2429#endif
2430
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002431exit:
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002432 mbedtls_psa_crypto_free( );
2433}
2434/* END_CASE */
2435
2436/* BEGIN_CASE */
Jaeden Amero252ef282019-02-15 14:05:35 +00002437void mac_bad_order( )
2438{
2439 psa_key_handle_t handle = 0;
2440 psa_key_type_t key_type = PSA_KEY_TYPE_HMAC;
2441 psa_algorithm_t alg = PSA_ALG_HMAC(PSA_ALG_SHA_256);
2442 const uint8_t key[] = {
2443 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2444 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2445 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa };
2446 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
2447 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
2448 uint8_t sign_mac[PSA_MAC_MAX_SIZE + 10] = { 0 };
2449 size_t sign_mac_length = 0;
2450 const uint8_t input[] = { 0xbb, 0xbb, 0xbb, 0xbb };
2451 const uint8_t verify_mac[] = {
2452 0x74, 0x65, 0x93, 0x8c, 0xeb, 0x1d, 0xb3, 0x76, 0x5a, 0x38, 0xe7, 0xdd,
2453 0x85, 0xc5, 0xad, 0x4f, 0x07, 0xe7, 0xd5, 0xb2, 0x64, 0xf0, 0x1a, 0x1a,
2454 0x2c, 0xf9, 0x18, 0xca, 0x59, 0x7e, 0x5d, 0xf6 };
2455
2456 PSA_ASSERT( psa_crypto_init( ) );
2457 PSA_ASSERT( psa_allocate_key( &handle ) );
2458 psa_key_policy_set_usage( &policy,
2459 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY,
2460 alg );
2461 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
2462
2463 PSA_ASSERT( psa_import_key( handle, key_type,
2464 key, sizeof(key) ) );
2465
2466 /* Call update without calling setup beforehand. */
2467 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2468 PSA_ERROR_BAD_STATE );
2469 PSA_ASSERT( psa_mac_abort( &operation ) );
2470
2471 /* Call sign finish without calling setup beforehand. */
2472 TEST_EQUAL( psa_mac_sign_finish( &operation, sign_mac, sizeof( sign_mac ),
2473 &sign_mac_length),
2474 PSA_ERROR_BAD_STATE );
2475 PSA_ASSERT( psa_mac_abort( &operation ) );
2476
2477 /* Call verify finish without calling setup beforehand. */
2478 TEST_EQUAL( psa_mac_verify_finish( &operation,
2479 verify_mac, sizeof( verify_mac ) ),
2480 PSA_ERROR_BAD_STATE );
2481 PSA_ASSERT( psa_mac_abort( &operation ) );
2482
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002483 /* Call setup twice in a row. */
2484 PSA_ASSERT( psa_mac_sign_setup( &operation,
2485 handle, alg ) );
2486 TEST_EQUAL( psa_mac_sign_setup( &operation,
2487 handle, alg ),
2488 PSA_ERROR_BAD_STATE );
2489 PSA_ASSERT( psa_mac_abort( &operation ) );
2490
Jaeden Amero252ef282019-02-15 14:05:35 +00002491 /* Call update after sign finish. */
2492 PSA_ASSERT( psa_mac_sign_setup( &operation,
2493 handle, alg ) );
2494 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2495 PSA_ASSERT( psa_mac_sign_finish( &operation,
2496 sign_mac, sizeof( sign_mac ),
2497 &sign_mac_length ) );
2498 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2499 PSA_ERROR_BAD_STATE );
2500 PSA_ASSERT( psa_mac_abort( &operation ) );
2501
2502 /* Call update after verify finish. */
2503 PSA_ASSERT( psa_mac_verify_setup( &operation,
2504 handle, alg ) );
2505 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2506 PSA_ASSERT( psa_mac_verify_finish( &operation,
2507 verify_mac, sizeof( verify_mac ) ) );
2508 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2509 PSA_ERROR_BAD_STATE );
2510 PSA_ASSERT( psa_mac_abort( &operation ) );
2511
2512 /* Call sign finish twice in a row. */
2513 PSA_ASSERT( psa_mac_sign_setup( &operation,
2514 handle, alg ) );
2515 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2516 PSA_ASSERT( psa_mac_sign_finish( &operation,
2517 sign_mac, sizeof( sign_mac ),
2518 &sign_mac_length ) );
2519 TEST_EQUAL( psa_mac_sign_finish( &operation,
2520 sign_mac, sizeof( sign_mac ),
2521 &sign_mac_length ),
2522 PSA_ERROR_BAD_STATE );
2523 PSA_ASSERT( psa_mac_abort( &operation ) );
2524
2525 /* Call verify finish twice in a row. */
2526 PSA_ASSERT( psa_mac_verify_setup( &operation,
2527 handle, alg ) );
2528 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2529 PSA_ASSERT( psa_mac_verify_finish( &operation,
2530 verify_mac, sizeof( verify_mac ) ) );
2531 TEST_EQUAL( psa_mac_verify_finish( &operation,
2532 verify_mac, sizeof( verify_mac ) ),
2533 PSA_ERROR_BAD_STATE );
2534 PSA_ASSERT( psa_mac_abort( &operation ) );
2535
2536 /* Setup sign but try verify. */
2537 PSA_ASSERT( psa_mac_sign_setup( &operation,
2538 handle, alg ) );
2539 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2540 TEST_EQUAL( psa_mac_verify_finish( &operation,
2541 verify_mac, sizeof( verify_mac ) ),
2542 PSA_ERROR_BAD_STATE );
2543 PSA_ASSERT( psa_mac_abort( &operation ) );
2544
2545 /* Setup verify but try sign. */
2546 PSA_ASSERT( psa_mac_verify_setup( &operation,
2547 handle, alg ) );
2548 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2549 TEST_EQUAL( psa_mac_sign_finish( &operation,
2550 sign_mac, sizeof( sign_mac ),
2551 &sign_mac_length ),
2552 PSA_ERROR_BAD_STATE );
2553 PSA_ASSERT( psa_mac_abort( &operation ) );
2554
2555exit:
2556 mbedtls_psa_crypto_free( );
2557}
2558/* END_CASE */
2559
2560/* BEGIN_CASE */
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002561void mac_sign( int key_type_arg,
2562 data_t *key,
2563 int alg_arg,
2564 data_t *input,
2565 data_t *expected_mac )
2566{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002567 psa_key_handle_t handle = 0;
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002568 psa_key_type_t key_type = key_type_arg;
2569 psa_algorithm_t alg = alg_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002570 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002571 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002572 /* Leave a little extra room in the output buffer. At the end of the
2573 * test, we'll check that the implementation didn't overwrite onto
2574 * this extra room. */
2575 uint8_t actual_mac[PSA_MAC_MAX_SIZE + 10];
2576 size_t mac_buffer_size =
2577 PSA_MAC_FINAL_SIZE( key_type, PSA_BYTES_TO_BITS( key->len ), alg );
2578 size_t mac_length = 0;
2579
2580 memset( actual_mac, '+', sizeof( actual_mac ) );
2581 TEST_ASSERT( mac_buffer_size <= PSA_MAC_MAX_SIZE );
2582 TEST_ASSERT( expected_mac->len <= mac_buffer_size );
2583
Gilles Peskine8817f612018-12-18 00:18:46 +01002584 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002585
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002586 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002587 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002588 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002589
Gilles Peskine8817f612018-12-18 00:18:46 +01002590 PSA_ASSERT( psa_import_key( handle, key_type,
2591 key->x, key->len ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002592
2593 /* Calculate the MAC. */
Gilles Peskine8817f612018-12-18 00:18:46 +01002594 PSA_ASSERT( psa_mac_sign_setup( &operation,
2595 handle, alg ) );
2596 PSA_ASSERT( psa_mac_update( &operation,
2597 input->x, input->len ) );
2598 PSA_ASSERT( psa_mac_sign_finish( &operation,
2599 actual_mac, mac_buffer_size,
2600 &mac_length ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002601
2602 /* Compare with the expected value. */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01002603 ASSERT_COMPARE( expected_mac->x, expected_mac->len,
2604 actual_mac, mac_length );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002605
2606 /* Verify that the end of the buffer is untouched. */
2607 TEST_ASSERT( mem_is_char( actual_mac + mac_length, '+',
2608 sizeof( actual_mac ) - mac_length ) );
2609
2610exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002611 psa_destroy_key( handle );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002612 mbedtls_psa_crypto_free( );
2613}
2614/* END_CASE */
2615
2616/* BEGIN_CASE */
Gilles Peskinec0ec9722018-06-18 17:03:37 +02002617void mac_verify( int key_type_arg,
2618 data_t *key,
2619 int alg_arg,
2620 data_t *input,
2621 data_t *expected_mac )
Gilles Peskine8c9def32018-02-08 10:02:12 +01002622{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002623 psa_key_handle_t handle = 0;
Gilles Peskine8c9def32018-02-08 10:02:12 +01002624 psa_key_type_t key_type = key_type_arg;
2625 psa_algorithm_t alg = alg_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002626 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002627 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine8c9def32018-02-08 10:02:12 +01002628
Gilles Peskine69c12672018-06-28 00:07:19 +02002629 TEST_ASSERT( expected_mac->len <= PSA_MAC_MAX_SIZE );
2630
Gilles Peskine8817f612018-12-18 00:18:46 +01002631 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002632
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002633 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02002634 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002635 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad16036df908f2018-04-02 08:34:15 -07002636
Gilles Peskine8817f612018-12-18 00:18:46 +01002637 PSA_ASSERT( psa_import_key( handle, key_type,
2638 key->x, key->len ) );
Gilles Peskinec0ec9722018-06-18 17:03:37 +02002639
Gilles Peskine8817f612018-12-18 00:18:46 +01002640 PSA_ASSERT( psa_mac_verify_setup( &operation,
2641 handle, alg ) );
2642 PSA_ASSERT( psa_destroy_key( handle ) );
2643 PSA_ASSERT( psa_mac_update( &operation,
2644 input->x, input->len ) );
2645 PSA_ASSERT( psa_mac_verify_finish( &operation,
2646 expected_mac->x,
2647 expected_mac->len ) );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002648
2649exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002650 psa_destroy_key( handle );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002651 mbedtls_psa_crypto_free( );
2652}
2653/* END_CASE */
2654
2655/* BEGIN_CASE */
Jaeden Amero5bae2272019-01-04 11:48:27 +00002656void cipher_operation_init( )
2657{
Jaeden Ameroab439972019-02-15 14:12:05 +00002658 const uint8_t input[1] = { 0 };
2659 unsigned char output[1] = { 0 };
2660 size_t output_length;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002661 /* Test each valid way of initializing the object, except for `= {0}`, as
2662 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2663 * though it's OK by the C standard. We could test for this, but we'd need
2664 * to supress the Clang warning for the test. */
2665 psa_cipher_operation_t func = psa_cipher_operation_init( );
2666 psa_cipher_operation_t init = PSA_CIPHER_OPERATION_INIT;
2667 psa_cipher_operation_t zero;
2668
2669 memset( &zero, 0, sizeof( zero ) );
2670
Jaeden Ameroab439972019-02-15 14:12:05 +00002671 /* A freshly-initialized cipher operation should not be usable. */
2672 TEST_EQUAL( psa_cipher_update( &func,
2673 input, sizeof( input ),
2674 output, sizeof( output ),
2675 &output_length ),
2676 PSA_ERROR_BAD_STATE );
2677 TEST_EQUAL( psa_cipher_update( &init,
2678 input, sizeof( input ),
2679 output, sizeof( output ),
2680 &output_length ),
2681 PSA_ERROR_BAD_STATE );
2682 TEST_EQUAL( psa_cipher_update( &zero,
2683 input, sizeof( input ),
2684 output, sizeof( output ),
2685 &output_length ),
2686 PSA_ERROR_BAD_STATE );
2687
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002688 /* A default cipher operation should be abortable without error. */
2689 PSA_ASSERT( psa_cipher_abort( &func ) );
2690 PSA_ASSERT( psa_cipher_abort( &init ) );
2691 PSA_ASSERT( psa_cipher_abort( &zero ) );
Jaeden Amero5bae2272019-01-04 11:48:27 +00002692}
2693/* END_CASE */
2694
2695/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002696void cipher_setup( int key_type_arg,
2697 data_t *key,
2698 int alg_arg,
2699 int expected_status_arg )
2700{
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002701 psa_key_type_t key_type = key_type_arg;
2702 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002703 psa_status_t expected_status = expected_status_arg;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002704 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002705 psa_status_t status;
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002706#if defined(KNOWN_SUPPORTED_MAC_ALG)
2707 const uint8_t smoke_test_key_data[16] = "kkkkkkkkkkkkkkkk";
2708#endif
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002709
Gilles Peskine8817f612018-12-18 00:18:46 +01002710 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002711
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002712 if( ! exercise_cipher_setup( key_type, key->x, key->len, alg,
2713 &operation, &status ) )
2714 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01002715 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002716
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002717 /* The operation object should be reusable. */
2718#if defined(KNOWN_SUPPORTED_CIPHER_ALG)
2719 if( ! exercise_cipher_setup( KNOWN_SUPPORTED_CIPHER_KEY_TYPE,
2720 smoke_test_key_data,
2721 sizeof( smoke_test_key_data ),
2722 KNOWN_SUPPORTED_CIPHER_ALG,
2723 &operation, &status ) )
2724 goto exit;
2725 TEST_EQUAL( status, PSA_SUCCESS );
2726#endif
2727
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002728exit:
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002729 mbedtls_psa_crypto_free( );
2730}
2731/* END_CASE */
2732
2733/* BEGIN_CASE */
Jaeden Ameroab439972019-02-15 14:12:05 +00002734void cipher_bad_order( )
2735{
2736 psa_key_handle_t handle = 0;
2737 psa_key_type_t key_type = PSA_KEY_TYPE_AES;
2738 psa_algorithm_t alg = PSA_ALG_CBC_PKCS7;
2739 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
2740 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
2741 unsigned char iv[PSA_BLOCK_CIPHER_BLOCK_SIZE(PSA_KEY_TYPE_AES)] = { 0 };
2742 const uint8_t key[] = {
2743 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2744 0xaa, 0xaa, 0xaa, 0xaa };
2745 const uint8_t text[] = {
2746 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb,
2747 0xbb, 0xbb, 0xbb, 0xbb };
2748 uint8_t buffer[PSA_BLOCK_CIPHER_BLOCK_SIZE(PSA_KEY_TYPE_AES)] = { 0 };
2749 size_t length = 0;
2750
2751 PSA_ASSERT( psa_crypto_init( ) );
2752 PSA_ASSERT( psa_allocate_key( &handle ) );
2753 psa_key_policy_set_usage( &policy,
2754 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
2755 alg );
2756 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
2757 PSA_ASSERT( psa_import_key( handle, key_type,
2758 key, sizeof(key) ) );
2759
2760
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002761 /* Call encrypt setup twice in a row. */
2762 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2763 TEST_EQUAL( psa_cipher_encrypt_setup( &operation, handle, alg ),
2764 PSA_ERROR_BAD_STATE );
2765 PSA_ASSERT( psa_cipher_abort( &operation ) );
2766
2767 /* Call decrypt setup twice in a row. */
2768 PSA_ASSERT( psa_cipher_decrypt_setup( &operation, handle, alg ) );
2769 TEST_EQUAL( psa_cipher_decrypt_setup( &operation, handle, alg ),
2770 PSA_ERROR_BAD_STATE );
2771 PSA_ASSERT( psa_cipher_abort( &operation ) );
2772
Jaeden Ameroab439972019-02-15 14:12:05 +00002773 /* Generate an IV without calling setup beforehand. */
2774 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2775 buffer, sizeof( buffer ),
2776 &length ),
2777 PSA_ERROR_BAD_STATE );
2778 PSA_ASSERT( psa_cipher_abort( &operation ) );
2779
2780 /* Generate an IV twice in a row. */
2781 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2782 PSA_ASSERT( psa_cipher_generate_iv( &operation,
2783 buffer, sizeof( buffer ),
2784 &length ) );
2785 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2786 buffer, sizeof( buffer ),
2787 &length ),
2788 PSA_ERROR_BAD_STATE );
2789 PSA_ASSERT( psa_cipher_abort( &operation ) );
2790
2791 /* Generate an IV after it's already set. */
2792 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2793 PSA_ASSERT( psa_cipher_set_iv( &operation,
2794 iv, sizeof( iv ) ) );
2795 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2796 buffer, sizeof( buffer ),
2797 &length ),
2798 PSA_ERROR_BAD_STATE );
2799 PSA_ASSERT( psa_cipher_abort( &operation ) );
2800
2801 /* Set an IV without calling setup beforehand. */
2802 TEST_EQUAL( psa_cipher_set_iv( &operation,
2803 iv, sizeof( iv ) ),
2804 PSA_ERROR_BAD_STATE );
2805 PSA_ASSERT( psa_cipher_abort( &operation ) );
2806
2807 /* Set an IV after it's already set. */
2808 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2809 PSA_ASSERT( psa_cipher_set_iv( &operation,
2810 iv, sizeof( iv ) ) );
2811 TEST_EQUAL( psa_cipher_set_iv( &operation,
2812 iv, sizeof( iv ) ),
2813 PSA_ERROR_BAD_STATE );
2814 PSA_ASSERT( psa_cipher_abort( &operation ) );
2815
2816 /* Set an IV after it's already generated. */
2817 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2818 PSA_ASSERT( psa_cipher_generate_iv( &operation,
2819 buffer, sizeof( buffer ),
2820 &length ) );
2821 TEST_EQUAL( psa_cipher_set_iv( &operation,
2822 iv, sizeof( iv ) ),
2823 PSA_ERROR_BAD_STATE );
2824 PSA_ASSERT( psa_cipher_abort( &operation ) );
2825
2826 /* Call update without calling setup beforehand. */
2827 TEST_EQUAL( psa_cipher_update( &operation,
2828 text, sizeof( text ),
2829 buffer, sizeof( buffer ),
2830 &length ),
2831 PSA_ERROR_BAD_STATE );
2832 PSA_ASSERT( psa_cipher_abort( &operation ) );
2833
2834 /* Call update without an IV where an IV is required. */
2835 TEST_EQUAL( psa_cipher_update( &operation,
2836 text, sizeof( text ),
2837 buffer, sizeof( buffer ),
2838 &length ),
2839 PSA_ERROR_BAD_STATE );
2840 PSA_ASSERT( psa_cipher_abort( &operation ) );
2841
2842 /* Call update after finish. */
2843 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2844 PSA_ASSERT( psa_cipher_set_iv( &operation,
2845 iv, sizeof( iv ) ) );
2846 PSA_ASSERT( psa_cipher_finish( &operation,
2847 buffer, sizeof( buffer ), &length ) );
2848 TEST_EQUAL( psa_cipher_update( &operation,
2849 text, sizeof( text ),
2850 buffer, sizeof( buffer ),
2851 &length ),
2852 PSA_ERROR_BAD_STATE );
2853 PSA_ASSERT( psa_cipher_abort( &operation ) );
2854
2855 /* Call finish without calling setup beforehand. */
2856 TEST_EQUAL( psa_cipher_finish( &operation,
2857 buffer, sizeof( buffer ), &length ),
2858 PSA_ERROR_BAD_STATE );
2859 PSA_ASSERT( psa_cipher_abort( &operation ) );
2860
2861 /* Call finish without an IV where an IV is required. */
2862 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2863 /* Not calling update means we are encrypting an empty buffer, which is OK
2864 * for cipher modes with padding. */
2865 TEST_EQUAL( psa_cipher_finish( &operation,
2866 buffer, sizeof( buffer ), &length ),
2867 PSA_ERROR_BAD_STATE );
2868 PSA_ASSERT( psa_cipher_abort( &operation ) );
2869
2870 /* Call finish twice in a row. */
2871 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2872 PSA_ASSERT( psa_cipher_set_iv( &operation,
2873 iv, sizeof( iv ) ) );
2874 PSA_ASSERT( psa_cipher_finish( &operation,
2875 buffer, sizeof( buffer ), &length ) );
2876 TEST_EQUAL( psa_cipher_finish( &operation,
2877 buffer, sizeof( buffer ), &length ),
2878 PSA_ERROR_BAD_STATE );
2879 PSA_ASSERT( psa_cipher_abort( &operation ) );
2880
2881exit:
2882 mbedtls_psa_crypto_free( );
2883}
2884/* END_CASE */
2885
2886/* BEGIN_CASE */
Gilles Peskine50e586b2018-06-08 14:28:46 +02002887void cipher_encrypt( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03002888 data_t *key,
2889 data_t *input, data_t *expected_output,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002890 int expected_status_arg )
Gilles Peskine50e586b2018-06-08 14:28:46 +02002891{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002892 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002893 psa_status_t status;
2894 psa_key_type_t key_type = key_type_arg;
2895 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002896 psa_status_t expected_status = expected_status_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002897 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02002898 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03002899 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002900 size_t output_buffer_size = 0;
2901 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02002902 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002903 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002904 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002905
Gilles Peskine9ad29e22018-06-21 09:40:04 +02002906 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
2907 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002908
Gilles Peskine8817f612018-12-18 00:18:46 +01002909 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002910
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002911 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03002912 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002913 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03002914
Gilles Peskine8817f612018-12-18 00:18:46 +01002915 PSA_ASSERT( psa_import_key( handle, key_type,
2916 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002917
Gilles Peskine8817f612018-12-18 00:18:46 +01002918 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
2919 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002920
Gilles Peskine8817f612018-12-18 00:18:46 +01002921 PSA_ASSERT( psa_cipher_set_iv( &operation,
2922 iv, iv_size ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01002923 output_buffer_size = ( (size_t) input->len +
2924 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02002925 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002926
Gilles Peskine8817f612018-12-18 00:18:46 +01002927 PSA_ASSERT( psa_cipher_update( &operation,
2928 input->x, input->len,
2929 output, output_buffer_size,
2930 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02002931 total_output_length += function_output_length;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002932 status = psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01002933 output + total_output_length,
2934 output_buffer_size - total_output_length,
Gilles Peskine50e586b2018-06-08 14:28:46 +02002935 &function_output_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02002936 total_output_length += function_output_length;
2937
Gilles Peskinefe11b722018-12-18 00:24:04 +01002938 TEST_EQUAL( status, expected_status );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002939 if( expected_status == PSA_SUCCESS )
2940 {
Gilles Peskine8817f612018-12-18 00:18:46 +01002941 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02002942 ASSERT_COMPARE( expected_output->x, expected_output->len,
2943 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002944 }
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02002945
Gilles Peskine50e586b2018-06-08 14:28:46 +02002946exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03002947 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002948 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002949 mbedtls_psa_crypto_free( );
2950}
2951/* END_CASE */
2952
2953/* BEGIN_CASE */
2954void cipher_encrypt_multipart( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03002955 data_t *key,
2956 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01002957 int first_part_size_arg,
2958 int output1_length_arg, int output2_length_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03002959 data_t *expected_output )
Gilles Peskine50e586b2018-06-08 14:28:46 +02002960{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002961 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002962 psa_key_type_t key_type = key_type_arg;
2963 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01002964 size_t first_part_size = first_part_size_arg;
2965 size_t output1_length = output1_length_arg;
2966 size_t output2_length = output2_length_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002967 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02002968 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03002969 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002970 size_t output_buffer_size = 0;
2971 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02002972 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002973 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002974 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02002975
Gilles Peskine9ad29e22018-06-21 09:40:04 +02002976 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
2977 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002978
Gilles Peskine8817f612018-12-18 00:18:46 +01002979 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002980
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002981 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03002982 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002983 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03002984
Gilles Peskine8817f612018-12-18 00:18:46 +01002985 PSA_ASSERT( psa_import_key( handle, key_type,
2986 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002987
Gilles Peskine8817f612018-12-18 00:18:46 +01002988 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
2989 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002990
Gilles Peskine8817f612018-12-18 00:18:46 +01002991 PSA_ASSERT( psa_cipher_set_iv( &operation,
2992 iv, sizeof( iv ) ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01002993 output_buffer_size = ( (size_t) input->len +
2994 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02002995 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02002996
Gilles Peskinee0866522019-02-19 19:44:00 +01002997 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine8817f612018-12-18 00:18:46 +01002998 PSA_ASSERT( psa_cipher_update( &operation, input->x, first_part_size,
2999 output, output_buffer_size,
3000 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003001 TEST_ASSERT( function_output_length == output1_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003002 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003003 PSA_ASSERT( psa_cipher_update( &operation,
3004 input->x + first_part_size,
3005 input->len - first_part_size,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003006 output + total_output_length,
3007 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003008 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003009 TEST_ASSERT( function_output_length == output2_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003010 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003011 PSA_ASSERT( psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003012 output + total_output_length,
3013 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003014 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003015 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003016 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003017
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003018 ASSERT_COMPARE( expected_output->x, expected_output->len,
3019 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003020
3021exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003022 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003023 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003024 mbedtls_psa_crypto_free( );
3025}
3026/* END_CASE */
3027
3028/* BEGIN_CASE */
3029void cipher_decrypt_multipart( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003030 data_t *key,
3031 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01003032 int first_part_size_arg,
3033 int output1_length_arg, int output2_length_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003034 data_t *expected_output )
Gilles Peskine50e586b2018-06-08 14:28:46 +02003035{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003036 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003037
3038 psa_key_type_t key_type = key_type_arg;
3039 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01003040 size_t first_part_size = first_part_size_arg;
3041 size_t output1_length = output1_length_arg;
3042 size_t output2_length = output2_length_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003043 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003044 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003045 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003046 size_t output_buffer_size = 0;
3047 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003048 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003049 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003050 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003051
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003052 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3053 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003054
Gilles Peskine8817f612018-12-18 00:18:46 +01003055 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003056
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003057 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003058 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003059 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003060
Gilles Peskine8817f612018-12-18 00:18:46 +01003061 PSA_ASSERT( psa_import_key( handle, key_type,
3062 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003063
Gilles Peskine8817f612018-12-18 00:18:46 +01003064 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
3065 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003066
Gilles Peskine8817f612018-12-18 00:18:46 +01003067 PSA_ASSERT( psa_cipher_set_iv( &operation,
3068 iv, sizeof( iv ) ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003069
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003070 output_buffer_size = ( (size_t) input->len +
3071 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003072 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003073
Gilles Peskinee0866522019-02-19 19:44:00 +01003074 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine8817f612018-12-18 00:18:46 +01003075 PSA_ASSERT( psa_cipher_update( &operation,
3076 input->x, first_part_size,
3077 output, output_buffer_size,
3078 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003079 TEST_ASSERT( function_output_length == output1_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003080 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003081 PSA_ASSERT( psa_cipher_update( &operation,
3082 input->x + first_part_size,
3083 input->len - first_part_size,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003084 output + total_output_length,
3085 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003086 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003087 TEST_ASSERT( function_output_length == output2_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003088 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003089 PSA_ASSERT( psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003090 output + total_output_length,
3091 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003092 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003093 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003094 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003095
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003096 ASSERT_COMPARE( expected_output->x, expected_output->len,
3097 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003098
3099exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003100 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003101 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003102 mbedtls_psa_crypto_free( );
3103}
3104/* END_CASE */
3105
Gilles Peskine50e586b2018-06-08 14:28:46 +02003106/* BEGIN_CASE */
3107void cipher_decrypt( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003108 data_t *key,
3109 data_t *input, data_t *expected_output,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003110 int expected_status_arg )
Gilles Peskine50e586b2018-06-08 14:28:46 +02003111{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003112 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003113 psa_status_t status;
3114 psa_key_type_t key_type = key_type_arg;
3115 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003116 psa_status_t expected_status = expected_status_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003117 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003118 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003119 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003120 size_t output_buffer_size = 0;
3121 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003122 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003123 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003124 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003125
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003126 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3127 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003128
Gilles Peskine8817f612018-12-18 00:18:46 +01003129 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003130
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003131 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003132 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003133 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003134
Gilles Peskine8817f612018-12-18 00:18:46 +01003135 PSA_ASSERT( psa_import_key( handle, key_type,
3136 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003137
Gilles Peskine8817f612018-12-18 00:18:46 +01003138 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
3139 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003140
Gilles Peskine8817f612018-12-18 00:18:46 +01003141 PSA_ASSERT( psa_cipher_set_iv( &operation,
3142 iv, iv_size ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003143
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003144 output_buffer_size = ( (size_t) input->len +
3145 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003146 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003147
Gilles Peskine8817f612018-12-18 00:18:46 +01003148 PSA_ASSERT( psa_cipher_update( &operation,
3149 input->x, input->len,
3150 output, output_buffer_size,
3151 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003152 total_output_length += function_output_length;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003153 status = psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003154 output + total_output_length,
3155 output_buffer_size - total_output_length,
Gilles Peskine50e586b2018-06-08 14:28:46 +02003156 &function_output_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003157 total_output_length += function_output_length;
Gilles Peskinefe11b722018-12-18 00:24:04 +01003158 TEST_EQUAL( status, expected_status );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003159
3160 if( expected_status == PSA_SUCCESS )
3161 {
Gilles Peskine8817f612018-12-18 00:18:46 +01003162 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003163 ASSERT_COMPARE( expected_output->x, expected_output->len,
3164 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003165 }
3166
Gilles Peskine50e586b2018-06-08 14:28:46 +02003167exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003168 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003169 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003170 mbedtls_psa_crypto_free( );
3171}
3172/* END_CASE */
3173
Gilles Peskine50e586b2018-06-08 14:28:46 +02003174/* BEGIN_CASE */
3175void cipher_verify_output( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003176 data_t *key,
3177 data_t *input )
mohammad1603d7d7ba52018-03-12 18:51:53 +02003178{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003179 psa_key_handle_t handle = 0;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003180 psa_key_type_t key_type = key_type_arg;
3181 psa_algorithm_t alg = alg_arg;
mohammad1603e6b67a12018-03-12 10:38:49 -07003182 unsigned char iv[16] = {0};
mohammad1603d7d7ba52018-03-12 18:51:53 +02003183 size_t iv_size = 16;
3184 size_t iv_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003185 unsigned char *output1 = NULL;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003186 size_t output1_size = 0;
3187 size_t output1_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003188 unsigned char *output2 = NULL;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003189 size_t output2_size = 0;
3190 size_t output2_length = 0;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003191 size_t function_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003192 psa_cipher_operation_t operation1 = PSA_CIPHER_OPERATION_INIT;
3193 psa_cipher_operation_t operation2 = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003194 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003195
Gilles Peskine8817f612018-12-18 00:18:46 +01003196 PSA_ASSERT( psa_crypto_init( ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003197
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003198 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003199 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003200 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003201
Gilles Peskine8817f612018-12-18 00:18:46 +01003202 PSA_ASSERT( psa_import_key( handle, key_type,
3203 key->x, key->len ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003204
Gilles Peskine8817f612018-12-18 00:18:46 +01003205 PSA_ASSERT( psa_cipher_encrypt_setup( &operation1,
3206 handle, alg ) );
3207 PSA_ASSERT( psa_cipher_decrypt_setup( &operation2,
3208 handle, alg ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003209
Gilles Peskine8817f612018-12-18 00:18:46 +01003210 PSA_ASSERT( psa_cipher_generate_iv( &operation1,
3211 iv, iv_size,
3212 &iv_length ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003213 output1_size = ( (size_t) input->len +
3214 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003215 ASSERT_ALLOC( output1, output1_size );
Moran Pekerded84402018-06-06 16:36:50 +03003216
Gilles Peskine8817f612018-12-18 00:18:46 +01003217 PSA_ASSERT( psa_cipher_update( &operation1, input->x, input->len,
3218 output1, output1_size,
3219 &output1_length ) );
3220 PSA_ASSERT( psa_cipher_finish( &operation1,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003221 output1 + output1_length,
3222 output1_size - output1_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003223 &function_output_length ) );
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003224
Gilles Peskine048b7f02018-06-08 14:20:49 +02003225 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003226
Gilles Peskine8817f612018-12-18 00:18:46 +01003227 PSA_ASSERT( psa_cipher_abort( &operation1 ) );
Moran Pekerded84402018-06-06 16:36:50 +03003228
3229 output2_size = output1_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003230 ASSERT_ALLOC( output2, output2_size );
Moran Pekerded84402018-06-06 16:36:50 +03003231
Gilles Peskine8817f612018-12-18 00:18:46 +01003232 PSA_ASSERT( psa_cipher_set_iv( &operation2,
3233 iv, iv_length ) );
3234 PSA_ASSERT( psa_cipher_update( &operation2, output1, output1_length,
3235 output2, output2_size,
3236 &output2_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003237 function_output_length = 0;
Gilles Peskine8817f612018-12-18 00:18:46 +01003238 PSA_ASSERT( psa_cipher_finish( &operation2,
3239 output2 + output2_length,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003240 output2_size - output2_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003241 &function_output_length ) );
Moran Pekerded84402018-06-06 16:36:50 +03003242
Gilles Peskine048b7f02018-06-08 14:20:49 +02003243 output2_length += function_output_length;
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003244
Gilles Peskine8817f612018-12-18 00:18:46 +01003245 PSA_ASSERT( psa_cipher_abort( &operation2 ) );
Moran Pekerded84402018-06-06 16:36:50 +03003246
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003247 ASSERT_COMPARE( input->x, input->len, output2, output2_length );
Moran Pekerded84402018-06-06 16:36:50 +03003248
3249exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003250 mbedtls_free( output1 );
3251 mbedtls_free( output2 );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003252 psa_destroy_key( handle );
Moran Pekerded84402018-06-06 16:36:50 +03003253 mbedtls_psa_crypto_free( );
3254}
3255/* END_CASE */
3256
3257/* BEGIN_CASE */
Gilles Peskine50e586b2018-06-08 14:28:46 +02003258void cipher_verify_output_multipart( int alg_arg,
3259 int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003260 data_t *key,
3261 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01003262 int first_part_size_arg )
Moran Pekerded84402018-06-06 16:36:50 +03003263{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003264 psa_key_handle_t handle = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003265 psa_key_type_t key_type = key_type_arg;
3266 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01003267 size_t first_part_size = first_part_size_arg;
Moran Pekerded84402018-06-06 16:36:50 +03003268 unsigned char iv[16] = {0};
3269 size_t iv_size = 16;
3270 size_t iv_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003271 unsigned char *output1 = NULL;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003272 size_t output1_buffer_size = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003273 size_t output1_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003274 unsigned char *output2 = NULL;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003275 size_t output2_buffer_size = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003276 size_t output2_length = 0;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003277 size_t function_output_length;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003278 psa_cipher_operation_t operation1 = PSA_CIPHER_OPERATION_INIT;
3279 psa_cipher_operation_t operation2 = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003280 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Pekerded84402018-06-06 16:36:50 +03003281
Gilles Peskine8817f612018-12-18 00:18:46 +01003282 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerded84402018-06-06 16:36:50 +03003283
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003284 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003285 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003286 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003287
Gilles Peskine8817f612018-12-18 00:18:46 +01003288 PSA_ASSERT( psa_import_key( handle, key_type,
3289 key->x, key->len ) );
Moran Pekerded84402018-06-06 16:36:50 +03003290
Gilles Peskine8817f612018-12-18 00:18:46 +01003291 PSA_ASSERT( psa_cipher_encrypt_setup( &operation1,
3292 handle, alg ) );
3293 PSA_ASSERT( psa_cipher_decrypt_setup( &operation2,
3294 handle, alg ) );
Moran Pekerded84402018-06-06 16:36:50 +03003295
Gilles Peskine8817f612018-12-18 00:18:46 +01003296 PSA_ASSERT( psa_cipher_generate_iv( &operation1,
3297 iv, iv_size,
3298 &iv_length ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003299 output1_buffer_size = ( (size_t) input->len +
3300 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003301 ASSERT_ALLOC( output1, output1_buffer_size );
Moran Pekerded84402018-06-06 16:36:50 +03003302
Gilles Peskinee0866522019-02-19 19:44:00 +01003303 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003304
Gilles Peskine8817f612018-12-18 00:18:46 +01003305 PSA_ASSERT( psa_cipher_update( &operation1, input->x, first_part_size,
3306 output1, output1_buffer_size,
3307 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003308 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003309
Gilles Peskine8817f612018-12-18 00:18:46 +01003310 PSA_ASSERT( psa_cipher_update( &operation1,
3311 input->x + first_part_size,
3312 input->len - first_part_size,
3313 output1, output1_buffer_size,
3314 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003315 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003316
Gilles Peskine8817f612018-12-18 00:18:46 +01003317 PSA_ASSERT( psa_cipher_finish( &operation1,
3318 output1 + output1_length,
3319 output1_buffer_size - output1_length,
3320 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003321 output1_length += function_output_length;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003322
Gilles Peskine8817f612018-12-18 00:18:46 +01003323 PSA_ASSERT( psa_cipher_abort( &operation1 ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003324
Gilles Peskine048b7f02018-06-08 14:20:49 +02003325 output2_buffer_size = output1_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003326 ASSERT_ALLOC( output2, output2_buffer_size );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003327
Gilles Peskine8817f612018-12-18 00:18:46 +01003328 PSA_ASSERT( psa_cipher_set_iv( &operation2,
3329 iv, iv_length ) );
Moran Pekerded84402018-06-06 16:36:50 +03003330
Gilles Peskine8817f612018-12-18 00:18:46 +01003331 PSA_ASSERT( psa_cipher_update( &operation2, output1, first_part_size,
3332 output2, output2_buffer_size,
3333 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003334 output2_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003335
Gilles Peskine8817f612018-12-18 00:18:46 +01003336 PSA_ASSERT( psa_cipher_update( &operation2,
3337 output1 + first_part_size,
3338 output1_length - first_part_size,
3339 output2, output2_buffer_size,
3340 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003341 output2_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003342
Gilles Peskine8817f612018-12-18 00:18:46 +01003343 PSA_ASSERT( psa_cipher_finish( &operation2,
3344 output2 + output2_length,
3345 output2_buffer_size - output2_length,
3346 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003347 output2_length += function_output_length;
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003348
Gilles Peskine8817f612018-12-18 00:18:46 +01003349 PSA_ASSERT( psa_cipher_abort( &operation2 ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003350
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003351 ASSERT_COMPARE( input->x, input->len, output2, output2_length );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003352
3353exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003354 mbedtls_free( output1 );
3355 mbedtls_free( output2 );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003356 psa_destroy_key( handle );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003357 mbedtls_psa_crypto_free( );
3358}
3359/* END_CASE */
Gilles Peskine7268afc2018-06-06 15:19:24 +02003360
Gilles Peskine20035e32018-02-03 22:44:14 +01003361/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003362void aead_encrypt_decrypt( int key_type_arg, data_t *key_data,
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003363 int alg_arg,
Gilles Peskine7da96b02018-08-17 18:45:42 +02003364 data_t *nonce,
3365 data_t *additional_data,
3366 data_t *input_data,
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003367 int expected_result_arg )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003368{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003369 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003370 psa_key_type_t key_type = key_type_arg;
3371 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003372 unsigned char *output_data = NULL;
3373 size_t output_size = 0;
3374 size_t output_length = 0;
3375 unsigned char *output_data2 = NULL;
3376 size_t output_length2 = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003377 size_t tag_length = 16;
Gilles Peskine4abf7412018-06-18 16:35:34 +02003378 psa_status_t expected_result = expected_result_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003379 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003380
Gilles Peskine4abf7412018-06-18 16:35:34 +02003381 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003382 ASSERT_ALLOC( output_data, output_size );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003383
Gilles Peskine8817f612018-12-18 00:18:46 +01003384 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003385
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003386 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003387 psa_key_policy_set_usage( &policy,
3388 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
3389 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003390 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003391
Gilles Peskine8817f612018-12-18 00:18:46 +01003392 PSA_ASSERT( psa_import_key( handle, key_type,
3393 key_data->x, key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003394
Gilles Peskinefe11b722018-12-18 00:24:04 +01003395 TEST_EQUAL( psa_aead_encrypt( handle, alg,
3396 nonce->x, nonce->len,
3397 additional_data->x,
3398 additional_data->len,
3399 input_data->x, input_data->len,
3400 output_data, output_size,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003401 &output_length ),
3402 expected_result );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003403
3404 if( PSA_SUCCESS == expected_result )
3405 {
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003406 ASSERT_ALLOC( output_data2, output_length );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003407
Gilles Peskinefe11b722018-12-18 00:24:04 +01003408 TEST_EQUAL( psa_aead_decrypt( handle, alg,
3409 nonce->x, nonce->len,
3410 additional_data->x,
3411 additional_data->len,
3412 output_data, output_length,
3413 output_data2, output_length,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003414 &output_length2 ),
3415 expected_result );
Gilles Peskine2d277862018-06-18 15:41:12 +02003416
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003417 ASSERT_COMPARE( input_data->x, input_data->len,
3418 output_data2, output_length2 );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003419 }
Gilles Peskine2d277862018-06-18 15:41:12 +02003420
Gilles Peskinea1cac842018-06-11 19:33:02 +02003421exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003422 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003423 mbedtls_free( output_data );
3424 mbedtls_free( output_data2 );
3425 mbedtls_psa_crypto_free( );
3426}
3427/* END_CASE */
3428
3429/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003430void aead_encrypt( int key_type_arg, data_t *key_data,
3431 int alg_arg,
3432 data_t *nonce,
3433 data_t *additional_data,
3434 data_t *input_data,
3435 data_t *expected_result )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003436{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003437 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003438 psa_key_type_t key_type = key_type_arg;
3439 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003440 unsigned char *output_data = NULL;
3441 size_t output_size = 0;
3442 size_t output_length = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003443 size_t tag_length = 16;
Jaeden Amero70261c52019-01-04 11:47:20 +00003444 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003445
Gilles Peskine4abf7412018-06-18 16:35:34 +02003446 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003447 ASSERT_ALLOC( output_data, output_size );
Gilles Peskine2d277862018-06-18 15:41:12 +02003448
Gilles Peskine8817f612018-12-18 00:18:46 +01003449 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003450
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003451 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003452 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT , alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003453 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003454
Gilles Peskine8817f612018-12-18 00:18:46 +01003455 PSA_ASSERT( psa_import_key( handle, key_type,
3456 key_data->x,
3457 key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003458
Gilles Peskine8817f612018-12-18 00:18:46 +01003459 PSA_ASSERT( psa_aead_encrypt( handle, alg,
3460 nonce->x, nonce->len,
3461 additional_data->x, additional_data->len,
3462 input_data->x, input_data->len,
3463 output_data, output_size,
3464 &output_length ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003465
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003466 ASSERT_COMPARE( expected_result->x, expected_result->len,
3467 output_data, output_length );
Gilles Peskine2d277862018-06-18 15:41:12 +02003468
Gilles Peskinea1cac842018-06-11 19:33:02 +02003469exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003470 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003471 mbedtls_free( output_data );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003472 mbedtls_psa_crypto_free( );
3473}
3474/* END_CASE */
3475
3476/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003477void aead_decrypt( int key_type_arg, data_t *key_data,
3478 int alg_arg,
3479 data_t *nonce,
3480 data_t *additional_data,
3481 data_t *input_data,
3482 data_t *expected_data,
3483 int expected_result_arg )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003484{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003485 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003486 psa_key_type_t key_type = key_type_arg;
3487 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003488 unsigned char *output_data = NULL;
3489 size_t output_size = 0;
3490 size_t output_length = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003491 size_t tag_length = 16;
Jaeden Amero70261c52019-01-04 11:47:20 +00003492 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine4abf7412018-06-18 16:35:34 +02003493 psa_status_t expected_result = expected_result_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003494
Gilles Peskine4abf7412018-06-18 16:35:34 +02003495 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003496 ASSERT_ALLOC( output_data, output_size );
Gilles Peskine2d277862018-06-18 15:41:12 +02003497
Gilles Peskine8817f612018-12-18 00:18:46 +01003498 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003499
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003500 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003501 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT , alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003502 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003503
Gilles Peskine8817f612018-12-18 00:18:46 +01003504 PSA_ASSERT( psa_import_key( handle, key_type,
3505 key_data->x,
3506 key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003507
Gilles Peskinefe11b722018-12-18 00:24:04 +01003508 TEST_EQUAL( psa_aead_decrypt( handle, alg,
3509 nonce->x, nonce->len,
3510 additional_data->x,
3511 additional_data->len,
3512 input_data->x, input_data->len,
3513 output_data, output_size,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003514 &output_length ),
3515 expected_result );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003516
Gilles Peskine2d277862018-06-18 15:41:12 +02003517 if( expected_result == PSA_SUCCESS )
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003518 ASSERT_COMPARE( expected_data->x, expected_data->len,
3519 output_data, output_length );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003520
Gilles Peskinea1cac842018-06-11 19:33:02 +02003521exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003522 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003523 mbedtls_free( output_data );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003524 mbedtls_psa_crypto_free( );
3525}
3526/* END_CASE */
3527
3528/* BEGIN_CASE */
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003529void signature_size( int type_arg,
3530 int bits,
3531 int alg_arg,
3532 int expected_size_arg )
Gilles Peskinee59236f2018-01-27 23:32:46 +01003533{
3534 psa_key_type_t type = type_arg;
3535 psa_algorithm_t alg = alg_arg;
Gilles Peskine2d277862018-06-18 15:41:12 +02003536 size_t actual_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( type, bits, alg );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003537 TEST_EQUAL( actual_size, (size_t) expected_size_arg );
Gilles Peskinee59236f2018-01-27 23:32:46 +01003538exit:
3539 ;
3540}
3541/* END_CASE */
3542
3543/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003544void sign_deterministic( int key_type_arg, data_t *key_data,
3545 int alg_arg, data_t *input_data,
3546 data_t *output_data )
Gilles Peskinee59236f2018-01-27 23:32:46 +01003547{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003548 psa_key_handle_t handle = 0;
Gilles Peskinee59236f2018-01-27 23:32:46 +01003549 psa_key_type_t key_type = key_type_arg;
3550 psa_algorithm_t alg = alg_arg;
Gilles Peskine20035e32018-02-03 22:44:14 +01003551 size_t key_bits;
Gilles Peskine20035e32018-02-03 22:44:14 +01003552 unsigned char *signature = NULL;
3553 size_t signature_size;
3554 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003555 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine20035e32018-02-03 22:44:14 +01003556
Gilles Peskine8817f612018-12-18 00:18:46 +01003557 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003558
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003559 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003560 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003561 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad1603a97cb8c2018-03-28 03:46:26 -07003562
Gilles Peskine8817f612018-12-18 00:18:46 +01003563 PSA_ASSERT( psa_import_key( handle, key_type,
3564 key_data->x,
3565 key_data->len ) );
3566 PSA_ASSERT( psa_get_key_information( handle,
3567 NULL,
3568 &key_bits ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003569
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003570 /* Allocate a buffer which has the size advertized by the
3571 * library. */
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003572 signature_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( key_type,
3573 key_bits, alg );
Gilles Peskine20035e32018-02-03 22:44:14 +01003574 TEST_ASSERT( signature_size != 0 );
Gilles Peskine69c12672018-06-28 00:07:19 +02003575 TEST_ASSERT( signature_size <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003576 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003577
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003578 /* Perform the signature. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003579 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
3580 input_data->x, input_data->len,
3581 signature, signature_size,
3582 &signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003583 /* Verify that the signature is what is expected. */
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003584 ASSERT_COMPARE( output_data->x, output_data->len,
3585 signature, signature_length );
Gilles Peskine20035e32018-02-03 22:44:14 +01003586
3587exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003588 psa_destroy_key( handle );
Gilles Peskine0189e752018-02-03 23:57:22 +01003589 mbedtls_free( signature );
Gilles Peskine20035e32018-02-03 22:44:14 +01003590 mbedtls_psa_crypto_free( );
3591}
3592/* END_CASE */
3593
3594/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003595void sign_fail( int key_type_arg, data_t *key_data,
3596 int alg_arg, data_t *input_data,
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003597 int signature_size_arg, int expected_status_arg )
Gilles Peskine20035e32018-02-03 22:44:14 +01003598{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003599 psa_key_handle_t handle = 0;
Gilles Peskine20035e32018-02-03 22:44:14 +01003600 psa_key_type_t key_type = key_type_arg;
3601 psa_algorithm_t alg = alg_arg;
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003602 size_t signature_size = signature_size_arg;
Gilles Peskine20035e32018-02-03 22:44:14 +01003603 psa_status_t actual_status;
3604 psa_status_t expected_status = expected_status_arg;
Gilles Peskine40f68b92018-03-07 16:43:36 +01003605 unsigned char *signature = NULL;
Gilles Peskine93aa0332018-02-03 23:58:03 +01003606 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003607 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine20035e32018-02-03 22:44:14 +01003608
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003609 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003610
Gilles Peskine8817f612018-12-18 00:18:46 +01003611 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003612
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003613 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003614 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003615 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad1603a97cb8c2018-03-28 03:46:26 -07003616
Gilles Peskine8817f612018-12-18 00:18:46 +01003617 PSA_ASSERT( psa_import_key( handle, key_type,
3618 key_data->x,
3619 key_data->len ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003620
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003621 actual_status = psa_asymmetric_sign( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003622 input_data->x, input_data->len,
Gilles Peskine20035e32018-02-03 22:44:14 +01003623 signature, signature_size,
3624 &signature_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003625 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003626 /* The value of *signature_length is unspecified on error, but
3627 * whatever it is, it should be less than signature_size, so that
3628 * if the caller tries to read *signature_length bytes without
3629 * checking the error code then they don't overflow a buffer. */
3630 TEST_ASSERT( signature_length <= signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003631
3632exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003633 psa_destroy_key( handle );
Gilles Peskine20035e32018-02-03 22:44:14 +01003634 mbedtls_free( signature );
3635 mbedtls_psa_crypto_free( );
3636}
3637/* END_CASE */
mohammad16038cc1cee2018-03-28 01:21:33 +03003638
3639/* BEGIN_CASE */
Gilles Peskine9911b022018-06-29 17:30:48 +02003640void sign_verify( int key_type_arg, data_t *key_data,
3641 int alg_arg, data_t *input_data )
3642{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003643 psa_key_handle_t handle = 0;
Gilles Peskine9911b022018-06-29 17:30:48 +02003644 psa_key_type_t key_type = key_type_arg;
3645 psa_algorithm_t alg = alg_arg;
3646 size_t key_bits;
3647 unsigned char *signature = NULL;
3648 size_t signature_size;
3649 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003650 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine9911b022018-06-29 17:30:48 +02003651
Gilles Peskine8817f612018-12-18 00:18:46 +01003652 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003653
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003654 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003655 psa_key_policy_set_usage( &policy,
3656 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY,
3657 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003658 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003659
Gilles Peskine8817f612018-12-18 00:18:46 +01003660 PSA_ASSERT( psa_import_key( handle, key_type,
3661 key_data->x,
3662 key_data->len ) );
3663 PSA_ASSERT( psa_get_key_information( handle,
3664 NULL,
3665 &key_bits ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003666
3667 /* Allocate a buffer which has the size advertized by the
3668 * library. */
3669 signature_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( key_type,
3670 key_bits, alg );
3671 TEST_ASSERT( signature_size != 0 );
3672 TEST_ASSERT( signature_size <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003673 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine9911b022018-06-29 17:30:48 +02003674
3675 /* Perform the signature. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003676 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
3677 input_data->x, input_data->len,
3678 signature, signature_size,
3679 &signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003680 /* Check that the signature length looks sensible. */
3681 TEST_ASSERT( signature_length <= signature_size );
3682 TEST_ASSERT( signature_length > 0 );
3683
3684 /* Use the library to verify that the signature is correct. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003685 PSA_ASSERT( psa_asymmetric_verify(
3686 handle, alg,
3687 input_data->x, input_data->len,
3688 signature, signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003689
3690 if( input_data->len != 0 )
3691 {
3692 /* Flip a bit in the input and verify that the signature is now
3693 * detected as invalid. Flip a bit at the beginning, not at the end,
3694 * because ECDSA may ignore the last few bits of the input. */
3695 input_data->x[0] ^= 1;
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003696 TEST_EQUAL( psa_asymmetric_verify( handle, alg,
3697 input_data->x, input_data->len,
3698 signature, signature_length ),
3699 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine9911b022018-06-29 17:30:48 +02003700 }
3701
3702exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003703 psa_destroy_key( handle );
Gilles Peskine9911b022018-06-29 17:30:48 +02003704 mbedtls_free( signature );
3705 mbedtls_psa_crypto_free( );
3706}
3707/* END_CASE */
3708
3709/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003710void asymmetric_verify( int key_type_arg, data_t *key_data,
3711 int alg_arg, data_t *hash_data,
3712 data_t *signature_data )
itayzafrir5c753392018-05-08 11:18:38 +03003713{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003714 psa_key_handle_t handle = 0;
itayzafrir5c753392018-05-08 11:18:38 +03003715 psa_key_type_t key_type = key_type_arg;
3716 psa_algorithm_t alg = alg_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003717 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
itayzafrir5c753392018-05-08 11:18:38 +03003718
Gilles Peskine69c12672018-06-28 00:07:19 +02003719 TEST_ASSERT( signature_data->len <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
3720
Gilles Peskine8817f612018-12-18 00:18:46 +01003721 PSA_ASSERT( psa_crypto_init( ) );
itayzafrir5c753392018-05-08 11:18:38 +03003722
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003723 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003724 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003725 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
itayzafrir5c753392018-05-08 11:18:38 +03003726
Gilles Peskine8817f612018-12-18 00:18:46 +01003727 PSA_ASSERT( psa_import_key( handle, key_type,
3728 key_data->x,
3729 key_data->len ) );
itayzafrir5c753392018-05-08 11:18:38 +03003730
Gilles Peskine8817f612018-12-18 00:18:46 +01003731 PSA_ASSERT( psa_asymmetric_verify( handle, alg,
3732 hash_data->x, hash_data->len,
3733 signature_data->x,
3734 signature_data->len ) );
itayzafrir5c753392018-05-08 11:18:38 +03003735exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003736 psa_destroy_key( handle );
itayzafrir5c753392018-05-08 11:18:38 +03003737 mbedtls_psa_crypto_free( );
3738}
3739/* END_CASE */
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003740
3741/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003742void asymmetric_verify_fail( int key_type_arg, data_t *key_data,
3743 int alg_arg, data_t *hash_data,
3744 data_t *signature_data,
3745 int expected_status_arg )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003746{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003747 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003748 psa_key_type_t key_type = key_type_arg;
3749 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003750 psa_status_t actual_status;
3751 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003752 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003753
Gilles Peskine8817f612018-12-18 00:18:46 +01003754 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003755
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003756 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003757 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003758 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03003759
Gilles Peskine8817f612018-12-18 00:18:46 +01003760 PSA_ASSERT( psa_import_key( handle, key_type,
3761 key_data->x,
3762 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003763
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003764 actual_status = psa_asymmetric_verify( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003765 hash_data->x, hash_data->len,
Gilles Peskine2d277862018-06-18 15:41:12 +02003766 signature_data->x,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003767 signature_data->len );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003768
Gilles Peskinefe11b722018-12-18 00:24:04 +01003769 TEST_EQUAL( actual_status, expected_status );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003770
3771exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003772 psa_destroy_key( handle );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003773 mbedtls_psa_crypto_free( );
3774}
3775/* END_CASE */
3776
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003777/* BEGIN_CASE */
Gilles Peskine656896e2018-06-29 19:12:28 +02003778void asymmetric_encrypt( int key_type_arg,
3779 data_t *key_data,
3780 int alg_arg,
3781 data_t *input_data,
Gilles Peskine68428122018-06-30 18:42:41 +02003782 data_t *label,
Gilles Peskine656896e2018-06-29 19:12:28 +02003783 int expected_output_length_arg,
3784 int expected_status_arg )
3785{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003786 psa_key_handle_t handle = 0;
Gilles Peskine656896e2018-06-29 19:12:28 +02003787 psa_key_type_t key_type = key_type_arg;
3788 psa_algorithm_t alg = alg_arg;
3789 size_t expected_output_length = expected_output_length_arg;
3790 size_t key_bits;
3791 unsigned char *output = NULL;
3792 size_t output_size;
3793 size_t output_length = ~0;
3794 psa_status_t actual_status;
3795 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003796 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine656896e2018-06-29 19:12:28 +02003797
Gilles Peskine8817f612018-12-18 00:18:46 +01003798 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003799
Gilles Peskine656896e2018-06-29 19:12:28 +02003800 /* Import the key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003801 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003802 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003803 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
3804 PSA_ASSERT( psa_import_key( handle, key_type,
3805 key_data->x,
3806 key_data->len ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003807
3808 /* Determine the maximum output length */
Gilles Peskine8817f612018-12-18 00:18:46 +01003809 PSA_ASSERT( psa_get_key_information( handle,
3810 NULL,
3811 &key_bits ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003812 output_size = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits, alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003813 ASSERT_ALLOC( output, output_size );
Gilles Peskine656896e2018-06-29 19:12:28 +02003814
3815 /* Encrypt the input */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003816 actual_status = psa_asymmetric_encrypt( handle, alg,
Gilles Peskine656896e2018-06-29 19:12:28 +02003817 input_data->x, input_data->len,
Gilles Peskine68428122018-06-30 18:42:41 +02003818 label->x, label->len,
Gilles Peskine656896e2018-06-29 19:12:28 +02003819 output, output_size,
3820 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003821 TEST_EQUAL( actual_status, expected_status );
3822 TEST_EQUAL( output_length, expected_output_length );
Gilles Peskine656896e2018-06-29 19:12:28 +02003823
Gilles Peskine68428122018-06-30 18:42:41 +02003824 /* If the label is empty, the test framework puts a non-null pointer
3825 * in label->x. Test that a null pointer works as well. */
3826 if( label->len == 0 )
3827 {
3828 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02003829 if( output_size != 0 )
3830 memset( output, 0, output_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003831 actual_status = psa_asymmetric_encrypt( handle, alg,
Gilles Peskine68428122018-06-30 18:42:41 +02003832 input_data->x, input_data->len,
3833 NULL, label->len,
3834 output, output_size,
3835 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003836 TEST_EQUAL( actual_status, expected_status );
3837 TEST_EQUAL( output_length, expected_output_length );
Gilles Peskine68428122018-06-30 18:42:41 +02003838 }
3839
Gilles Peskine656896e2018-06-29 19:12:28 +02003840exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003841 psa_destroy_key( handle );
Gilles Peskine656896e2018-06-29 19:12:28 +02003842 mbedtls_free( output );
3843 mbedtls_psa_crypto_free( );
3844}
3845/* END_CASE */
3846
3847/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02003848void asymmetric_encrypt_decrypt( int key_type_arg,
3849 data_t *key_data,
3850 int alg_arg,
3851 data_t *input_data,
3852 data_t *label )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003853{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003854 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003855 psa_key_type_t key_type = key_type_arg;
3856 psa_algorithm_t alg = alg_arg;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003857 size_t key_bits;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003858 unsigned char *output = NULL;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003859 size_t output_size;
3860 size_t output_length = ~0;
Nir Sonnenschein0f3bdbd2018-05-02 23:56:12 +03003861 unsigned char *output2 = NULL;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003862 size_t output2_size;
3863 size_t output2_length = ~0;
Jaeden Amero70261c52019-01-04 11:47:20 +00003864 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003865
Gilles Peskine8817f612018-12-18 00:18:46 +01003866 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003867
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003868 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003869 psa_key_policy_set_usage( &policy,
3870 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003871 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003872 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03003873
Gilles Peskine8817f612018-12-18 00:18:46 +01003874 PSA_ASSERT( psa_import_key( handle, key_type,
3875 key_data->x,
3876 key_data->len ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003877
3878 /* Determine the maximum ciphertext length */
Gilles Peskine8817f612018-12-18 00:18:46 +01003879 PSA_ASSERT( psa_get_key_information( handle,
3880 NULL,
3881 &key_bits ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003882 output_size = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits, alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003883 ASSERT_ALLOC( output, output_size );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003884 output2_size = input_data->len;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003885 ASSERT_ALLOC( output2, output2_size );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003886
Gilles Peskineeebd7382018-06-08 18:11:54 +02003887 /* We test encryption by checking that encrypt-then-decrypt gives back
3888 * the original plaintext because of the non-optional random
3889 * part of encryption process which prevents using fixed vectors. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003890 PSA_ASSERT( psa_asymmetric_encrypt( handle, alg,
3891 input_data->x, input_data->len,
3892 label->x, label->len,
3893 output, output_size,
3894 &output_length ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003895 /* We don't know what ciphertext length to expect, but check that
3896 * it looks sensible. */
3897 TEST_ASSERT( output_length <= output_size );
Nir Sonnenschein0f3bdbd2018-05-02 23:56:12 +03003898
Gilles Peskine8817f612018-12-18 00:18:46 +01003899 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
3900 output, output_length,
3901 label->x, label->len,
3902 output2, output2_size,
3903 &output2_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003904 ASSERT_COMPARE( input_data->x, input_data->len,
3905 output2, output2_length );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003906
3907exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003908 psa_destroy_key( handle );
itayzafrir3e02b3b2018-06-12 17:06:52 +03003909 mbedtls_free( output );
3910 mbedtls_free( output2 );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003911 mbedtls_psa_crypto_free( );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003912}
3913/* END_CASE */
3914
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003915/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02003916void asymmetric_decrypt( int key_type_arg,
3917 data_t *key_data,
3918 int alg_arg,
3919 data_t *input_data,
3920 data_t *label,
Gilles Peskine66763a02018-06-29 21:54:10 +02003921 data_t *expected_data )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003922{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003923 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003924 psa_key_type_t key_type = key_type_arg;
3925 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003926 unsigned char *output = NULL;
Nir Sonnenscheind70bc482018-06-04 16:31:13 +03003927 size_t output_size = 0;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003928 size_t output_length = ~0;
Jaeden Amero70261c52019-01-04 11:47:20 +00003929 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003930
Jaeden Amero412654a2019-02-06 12:57:46 +00003931 output_size = expected_data->len;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003932 ASSERT_ALLOC( output, output_size );
Gilles Peskine5b051bc2018-05-31 13:25:48 +02003933
Gilles Peskine8817f612018-12-18 00:18:46 +01003934 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003935
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003936 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003937 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003938 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03003939
Gilles Peskine8817f612018-12-18 00:18:46 +01003940 PSA_ASSERT( psa_import_key( handle, key_type,
3941 key_data->x,
3942 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003943
Gilles Peskine8817f612018-12-18 00:18:46 +01003944 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
3945 input_data->x, input_data->len,
3946 label->x, label->len,
3947 output,
3948 output_size,
3949 &output_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003950 ASSERT_COMPARE( expected_data->x, expected_data->len,
3951 output, output_length );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003952
Gilles Peskine68428122018-06-30 18:42:41 +02003953 /* If the label is empty, the test framework puts a non-null pointer
3954 * in label->x. Test that a null pointer works as well. */
3955 if( label->len == 0 )
3956 {
3957 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02003958 if( output_size != 0 )
3959 memset( output, 0, output_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01003960 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
3961 input_data->x, input_data->len,
3962 NULL, label->len,
3963 output,
3964 output_size,
3965 &output_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003966 ASSERT_COMPARE( expected_data->x, expected_data->len,
3967 output, output_length );
Gilles Peskine68428122018-06-30 18:42:41 +02003968 }
3969
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003970exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003971 psa_destroy_key( handle );
itayzafrir3e02b3b2018-06-12 17:06:52 +03003972 mbedtls_free( output );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003973 mbedtls_psa_crypto_free( );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003974}
3975/* END_CASE */
3976
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003977/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02003978void asymmetric_decrypt_fail( int key_type_arg,
3979 data_t *key_data,
3980 int alg_arg,
3981 data_t *input_data,
3982 data_t *label,
Jaeden Amerof8daab72019-02-06 12:57:46 +00003983 int output_size_arg,
Gilles Peskine2d277862018-06-18 15:41:12 +02003984 int expected_status_arg )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003985{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003986 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003987 psa_key_type_t key_type = key_type_arg;
3988 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003989 unsigned char *output = NULL;
Jaeden Amerof8daab72019-02-06 12:57:46 +00003990 size_t output_size = output_size_arg;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003991 size_t output_length = ~0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003992 psa_status_t actual_status;
3993 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003994 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003995
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003996 ASSERT_ALLOC( output, output_size );
Gilles Peskine5b051bc2018-05-31 13:25:48 +02003997
Gilles Peskine8817f612018-12-18 00:18:46 +01003998 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003999
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004000 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02004001 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004002 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03004003
Gilles Peskine8817f612018-12-18 00:18:46 +01004004 PSA_ASSERT( psa_import_key( handle, key_type,
4005 key_data->x,
4006 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004007
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004008 actual_status = psa_asymmetric_decrypt( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02004009 input_data->x, input_data->len,
Gilles Peskine68428122018-06-30 18:42:41 +02004010 label->x, label->len,
Gilles Peskine4abf7412018-06-18 16:35:34 +02004011 output, output_size,
Gilles Peskine2d277862018-06-18 15:41:12 +02004012 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004013 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004014 TEST_ASSERT( output_length <= output_size );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004015
Gilles Peskine68428122018-06-30 18:42:41 +02004016 /* If the label is empty, the test framework puts a non-null pointer
4017 * in label->x. Test that a null pointer works as well. */
4018 if( label->len == 0 )
4019 {
4020 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02004021 if( output_size != 0 )
4022 memset( output, 0, output_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004023 actual_status = psa_asymmetric_decrypt( handle, alg,
Gilles Peskine68428122018-06-30 18:42:41 +02004024 input_data->x, input_data->len,
4025 NULL, label->len,
4026 output, output_size,
4027 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004028 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004029 TEST_ASSERT( output_length <= output_size );
Gilles Peskine68428122018-06-30 18:42:41 +02004030 }
4031
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004032exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004033 psa_destroy_key( handle );
Gilles Peskine2d277862018-06-18 15:41:12 +02004034 mbedtls_free( output );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004035 mbedtls_psa_crypto_free( );
4036}
Gilles Peskine5b051bc2018-05-31 13:25:48 +02004037/* END_CASE */
Gilles Peskine05d69892018-06-19 22:00:52 +02004038
4039/* BEGIN_CASE */
Jaeden Amerod94d6712019-01-04 14:11:48 +00004040void crypto_generator_init( )
4041{
4042 /* Test each valid way of initializing the object, except for `= {0}`, as
4043 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
4044 * though it's OK by the C standard. We could test for this, but we'd need
4045 * to supress the Clang warning for the test. */
Jaeden Amero5229bbb2019-02-07 16:33:37 +00004046 size_t capacity;
Jaeden Amerod94d6712019-01-04 14:11:48 +00004047 psa_crypto_generator_t func = psa_crypto_generator_init( );
4048 psa_crypto_generator_t init = PSA_CRYPTO_GENERATOR_INIT;
4049 psa_crypto_generator_t zero;
4050
4051 memset( &zero, 0, sizeof( zero ) );
4052
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004053 /* A default generator should not be able to report its capacity. */
4054 TEST_EQUAL( psa_get_generator_capacity( &func, &capacity ),
4055 PSA_ERROR_BAD_STATE );
4056 TEST_EQUAL( psa_get_generator_capacity( &init, &capacity ),
4057 PSA_ERROR_BAD_STATE );
4058 TEST_EQUAL( psa_get_generator_capacity( &zero, &capacity ),
4059 PSA_ERROR_BAD_STATE );
Jaeden Amero5229bbb2019-02-07 16:33:37 +00004060
4061 /* A default generator should be abortable without error. */
4062 PSA_ASSERT( psa_generator_abort(&func) );
4063 PSA_ASSERT( psa_generator_abort(&init) );
4064 PSA_ASSERT( psa_generator_abort(&zero) );
Jaeden Amerod94d6712019-01-04 14:11:48 +00004065}
4066/* END_CASE */
4067
4068/* BEGIN_CASE */
Gilles Peskineea0fb492018-07-12 17:17:20 +02004069void derive_setup( int key_type_arg,
4070 data_t *key_data,
4071 int alg_arg,
4072 data_t *salt,
4073 data_t *label,
4074 int requested_capacity_arg,
4075 int expected_status_arg )
4076{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004077 psa_key_handle_t handle = 0;
Gilles Peskineea0fb492018-07-12 17:17:20 +02004078 size_t key_type = key_type_arg;
4079 psa_algorithm_t alg = alg_arg;
4080 size_t requested_capacity = requested_capacity_arg;
4081 psa_status_t expected_status = expected_status_arg;
4082 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004083 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskineea0fb492018-07-12 17:17:20 +02004084
Gilles Peskine8817f612018-12-18 00:18:46 +01004085 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004086
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004087 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004088 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004089 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004090
Gilles Peskine8817f612018-12-18 00:18:46 +01004091 PSA_ASSERT( psa_import_key( handle, key_type,
4092 key_data->x,
4093 key_data->len ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004094
Gilles Peskinefe11b722018-12-18 00:24:04 +01004095 TEST_EQUAL( psa_key_derivation( &generator, handle, alg,
4096 salt->x, salt->len,
4097 label->x, label->len,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004098 requested_capacity ),
4099 expected_status );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004100
4101exit:
4102 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004103 psa_destroy_key( handle );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004104 mbedtls_psa_crypto_free( );
4105}
4106/* END_CASE */
4107
4108/* BEGIN_CASE */
Nir Sonnenscheindd69d8b2018-11-01 12:24:23 +02004109void test_derive_invalid_generator_state( )
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004110{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004111 psa_key_handle_t handle = 0;
Nir Sonnenschein4eda37b2018-10-31 12:15:58 +02004112 size_t key_type = PSA_KEY_TYPE_DERIVE;
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004113 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Nir Sonnenschein1caf6d22018-11-01 12:27:20 +02004114 psa_algorithm_t alg = PSA_ALG_HKDF( PSA_ALG_SHA_256 );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004115 uint8_t buffer[42];
Nir Sonnenschein1caf6d22018-11-01 12:27:20 +02004116 size_t capacity = sizeof( buffer );
Nir Sonnenscheindd69d8b2018-11-01 12:24:23 +02004117 const uint8_t key_data[22] = { 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b,
4118 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b,
4119 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b};
Jaeden Amero70261c52019-01-04 11:47:20 +00004120 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004121
Gilles Peskine8817f612018-12-18 00:18:46 +01004122 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004123
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004124 PSA_ASSERT( psa_allocate_key( &handle ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004125 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004126 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004127
Gilles Peskine8817f612018-12-18 00:18:46 +01004128 PSA_ASSERT( psa_import_key( handle, key_type,
4129 key_data,
4130 sizeof( key_data ) ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004131
4132 /* valid key derivation */
Gilles Peskine8817f612018-12-18 00:18:46 +01004133 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4134 NULL, 0,
4135 NULL, 0,
4136 capacity ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004137
4138 /* state of generator shouldn't allow additional generation */
Gilles Peskinefe11b722018-12-18 00:24:04 +01004139 TEST_EQUAL( psa_key_derivation( &generator, handle, alg,
4140 NULL, 0,
4141 NULL, 0,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004142 capacity ),
4143 PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004144
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004145 PSA_ASSERT( psa_generator_read( &generator, buffer, capacity ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004146
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004147 TEST_EQUAL( psa_generator_read( &generator, buffer, capacity ),
David Saadab4ecc272019-02-14 13:48:10 +02004148 PSA_ERROR_INSUFFICIENT_DATA );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004149
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004150exit:
4151 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004152 psa_destroy_key( handle );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004153 mbedtls_psa_crypto_free( );
4154}
4155/* END_CASE */
4156
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004157/* BEGIN_CASE */
4158void test_derive_invalid_generator_tests( )
4159{
4160 uint8_t output_buffer[16];
4161 size_t buffer_size = 16;
4162 size_t capacity = 0;
4163 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4164
Nir Sonnenschein50789302018-10-31 12:16:38 +02004165 TEST_ASSERT( psa_generator_read( &generator, output_buffer, buffer_size )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004166 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004167
4168 TEST_ASSERT( psa_get_generator_capacity( &generator, &capacity )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004169 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004170
Gilles Peskine8817f612018-12-18 00:18:46 +01004171 PSA_ASSERT( psa_generator_abort( &generator ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004172
Nir Sonnenschein50789302018-10-31 12:16:38 +02004173 TEST_ASSERT( psa_generator_read( &generator, output_buffer, buffer_size )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004174 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004175
Nir Sonnenschein50789302018-10-31 12:16:38 +02004176 TEST_ASSERT( psa_get_generator_capacity( &generator, &capacity )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004177 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004178
4179exit:
4180 psa_generator_abort( &generator );
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004181}
4182/* END_CASE */
4183
4184/* BEGIN_CASE */
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004185void derive_output( int alg_arg,
4186 data_t *key_data,
4187 data_t *salt,
4188 data_t *label,
4189 int requested_capacity_arg,
4190 data_t *expected_output1,
4191 data_t *expected_output2 )
4192{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004193 psa_key_handle_t handle = 0;
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004194 psa_algorithm_t alg = alg_arg;
4195 size_t requested_capacity = requested_capacity_arg;
4196 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4197 uint8_t *expected_outputs[2] =
4198 {expected_output1->x, expected_output2->x};
4199 size_t output_sizes[2] =
4200 {expected_output1->len, expected_output2->len};
4201 size_t output_buffer_size = 0;
4202 uint8_t *output_buffer = NULL;
4203 size_t expected_capacity;
4204 size_t current_capacity;
Jaeden Amero70261c52019-01-04 11:47:20 +00004205 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004206 psa_status_t status;
4207 unsigned i;
4208
4209 for( i = 0; i < ARRAY_LENGTH( expected_outputs ); i++ )
4210 {
4211 if( output_sizes[i] > output_buffer_size )
4212 output_buffer_size = output_sizes[i];
4213 if( output_sizes[i] == 0 )
4214 expected_outputs[i] = NULL;
4215 }
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004216 ASSERT_ALLOC( output_buffer, output_buffer_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01004217 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004218
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004219 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004220 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004221 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004222
Gilles Peskine8817f612018-12-18 00:18:46 +01004223 PSA_ASSERT( psa_import_key( handle, PSA_KEY_TYPE_DERIVE,
4224 key_data->x,
4225 key_data->len ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004226
4227 /* Extraction phase. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004228 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4229 salt->x, salt->len,
4230 label->x, label->len,
4231 requested_capacity ) );
4232 PSA_ASSERT( psa_get_generator_capacity( &generator,
4233 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004234 TEST_EQUAL( current_capacity, requested_capacity );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004235 expected_capacity = requested_capacity;
4236
4237 /* Expansion phase. */
4238 for( i = 0; i < ARRAY_LENGTH( expected_outputs ); i++ )
4239 {
4240 /* Read some bytes. */
4241 status = psa_generator_read( &generator,
4242 output_buffer, output_sizes[i] );
4243 if( expected_capacity == 0 && output_sizes[i] == 0 )
4244 {
4245 /* Reading 0 bytes when 0 bytes are available can go either way. */
4246 TEST_ASSERT( status == PSA_SUCCESS ||
David Saadab4ecc272019-02-14 13:48:10 +02004247 status == PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004248 continue;
4249 }
4250 else if( expected_capacity == 0 ||
4251 output_sizes[i] > expected_capacity )
4252 {
4253 /* Capacity exceeded. */
David Saadab4ecc272019-02-14 13:48:10 +02004254 TEST_EQUAL( status, PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004255 expected_capacity = 0;
4256 continue;
4257 }
4258 /* Success. Check the read data. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004259 PSA_ASSERT( status );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004260 if( output_sizes[i] != 0 )
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004261 ASSERT_COMPARE( output_buffer, output_sizes[i],
4262 expected_outputs[i], output_sizes[i] );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004263 /* Check the generator status. */
4264 expected_capacity -= output_sizes[i];
Gilles Peskine8817f612018-12-18 00:18:46 +01004265 PSA_ASSERT( psa_get_generator_capacity( &generator,
4266 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004267 TEST_EQUAL( expected_capacity, current_capacity );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004268 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004269 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004270
4271exit:
4272 mbedtls_free( output_buffer );
4273 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004274 psa_destroy_key( handle );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004275 mbedtls_psa_crypto_free( );
4276}
4277/* END_CASE */
4278
4279/* BEGIN_CASE */
Gilles Peskined54931c2018-07-17 21:06:59 +02004280void derive_full( int alg_arg,
4281 data_t *key_data,
4282 data_t *salt,
4283 data_t *label,
4284 int requested_capacity_arg )
4285{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004286 psa_key_handle_t handle = 0;
Gilles Peskined54931c2018-07-17 21:06:59 +02004287 psa_algorithm_t alg = alg_arg;
4288 size_t requested_capacity = requested_capacity_arg;
4289 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4290 unsigned char output_buffer[16];
4291 size_t expected_capacity = requested_capacity;
4292 size_t current_capacity;
Jaeden Amero70261c52019-01-04 11:47:20 +00004293 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskined54931c2018-07-17 21:06:59 +02004294
Gilles Peskine8817f612018-12-18 00:18:46 +01004295 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004296
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004297 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004298 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004299 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004300
Gilles Peskine8817f612018-12-18 00:18:46 +01004301 PSA_ASSERT( psa_import_key( handle, PSA_KEY_TYPE_DERIVE,
4302 key_data->x,
4303 key_data->len ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004304
4305 /* Extraction phase. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004306 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4307 salt->x, salt->len,
4308 label->x, label->len,
4309 requested_capacity ) );
4310 PSA_ASSERT( psa_get_generator_capacity( &generator,
4311 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004312 TEST_EQUAL( current_capacity, expected_capacity );
Gilles Peskined54931c2018-07-17 21:06:59 +02004313
4314 /* Expansion phase. */
4315 while( current_capacity > 0 )
4316 {
4317 size_t read_size = sizeof( output_buffer );
4318 if( read_size > current_capacity )
4319 read_size = current_capacity;
Gilles Peskine8817f612018-12-18 00:18:46 +01004320 PSA_ASSERT( psa_generator_read( &generator,
4321 output_buffer,
4322 read_size ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004323 expected_capacity -= read_size;
Gilles Peskine8817f612018-12-18 00:18:46 +01004324 PSA_ASSERT( psa_get_generator_capacity( &generator,
4325 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004326 TEST_EQUAL( current_capacity, expected_capacity );
Gilles Peskined54931c2018-07-17 21:06:59 +02004327 }
4328
4329 /* Check that the generator refuses to go over capacity. */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004330 TEST_EQUAL( psa_generator_read( &generator, output_buffer, 1 ),
David Saadab4ecc272019-02-14 13:48:10 +02004331 PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskined54931c2018-07-17 21:06:59 +02004332
Gilles Peskine8817f612018-12-18 00:18:46 +01004333 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004334
4335exit:
4336 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004337 psa_destroy_key( handle );
Gilles Peskined54931c2018-07-17 21:06:59 +02004338 mbedtls_psa_crypto_free( );
4339}
4340/* END_CASE */
4341
4342/* BEGIN_CASE */
Gilles Peskine0386fba2018-07-12 17:29:22 +02004343void derive_key_exercise( int alg_arg,
4344 data_t *key_data,
4345 data_t *salt,
4346 data_t *label,
4347 int derived_type_arg,
4348 int derived_bits_arg,
4349 int derived_usage_arg,
4350 int derived_alg_arg )
4351{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004352 psa_key_handle_t base_handle = 0;
4353 psa_key_handle_t derived_handle = 0;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004354 psa_algorithm_t alg = alg_arg;
4355 psa_key_type_t derived_type = derived_type_arg;
4356 size_t derived_bits = derived_bits_arg;
4357 psa_key_usage_t derived_usage = derived_usage_arg;
4358 psa_algorithm_t derived_alg = derived_alg_arg;
4359 size_t capacity = PSA_BITS_TO_BYTES( derived_bits );
4360 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004361 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004362 psa_key_type_t got_type;
4363 size_t got_bits;
4364
Gilles Peskine8817f612018-12-18 00:18:46 +01004365 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004366
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004367 PSA_ASSERT( psa_allocate_key( &base_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004368 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004369 PSA_ASSERT( psa_set_key_policy( base_handle, &policy ) );
4370 PSA_ASSERT( psa_import_key( base_handle, PSA_KEY_TYPE_DERIVE,
4371 key_data->x,
4372 key_data->len ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004373
4374 /* Derive a key. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004375 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4376 salt->x, salt->len,
4377 label->x, label->len,
4378 capacity ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004379 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004380 psa_key_policy_set_usage( &policy, derived_usage, derived_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004381 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
4382 PSA_ASSERT( psa_generator_import_key( derived_handle,
4383 derived_type,
4384 derived_bits,
4385 &generator ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004386
4387 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01004388 PSA_ASSERT( psa_get_key_information( derived_handle,
4389 &got_type,
4390 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004391 TEST_EQUAL( got_type, derived_type );
4392 TEST_EQUAL( got_bits, derived_bits );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004393
4394 /* Exercise the derived key. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004395 if( ! exercise_key( derived_handle, derived_usage, derived_alg ) )
Gilles Peskine0386fba2018-07-12 17:29:22 +02004396 goto exit;
4397
4398exit:
4399 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004400 psa_destroy_key( base_handle );
4401 psa_destroy_key( derived_handle );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004402 mbedtls_psa_crypto_free( );
4403}
4404/* END_CASE */
4405
4406/* BEGIN_CASE */
4407void derive_key_export( int alg_arg,
4408 data_t *key_data,
4409 data_t *salt,
4410 data_t *label,
4411 int bytes1_arg,
4412 int bytes2_arg )
4413{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004414 psa_key_handle_t base_handle = 0;
4415 psa_key_handle_t derived_handle = 0;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004416 psa_algorithm_t alg = alg_arg;
4417 size_t bytes1 = bytes1_arg;
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004418 size_t derived_bits = PSA_BYTES_TO_BITS( bytes1 );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004419 size_t bytes2 = bytes2_arg;
4420 size_t capacity = bytes1 + bytes2;
4421 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004422 uint8_t *output_buffer = NULL;
4423 uint8_t *export_buffer = NULL;
Jaeden Amero70261c52019-01-04 11:47:20 +00004424 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004425 size_t length;
4426
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004427 ASSERT_ALLOC( output_buffer, capacity );
4428 ASSERT_ALLOC( export_buffer, capacity );
Gilles Peskine8817f612018-12-18 00:18:46 +01004429 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004430
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004431 PSA_ASSERT( psa_allocate_key( &base_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004432 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004433 PSA_ASSERT( psa_set_key_policy( base_handle, &policy ) );
4434 PSA_ASSERT( psa_import_key( base_handle, PSA_KEY_TYPE_DERIVE,
4435 key_data->x,
4436 key_data->len ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004437
4438 /* Derive some material and output it. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004439 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4440 salt->x, salt->len,
4441 label->x, label->len,
4442 capacity ) );
4443 PSA_ASSERT( psa_generator_read( &generator,
4444 output_buffer,
4445 capacity ) );
4446 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004447
4448 /* Derive the same output again, but this time store it in key objects. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004449 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4450 salt->x, salt->len,
4451 label->x, label->len,
4452 capacity ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004453 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004454 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, 0 );
Gilles Peskine8817f612018-12-18 00:18:46 +01004455 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
4456 PSA_ASSERT( psa_generator_import_key( derived_handle,
4457 PSA_KEY_TYPE_RAW_DATA,
4458 derived_bits,
4459 &generator ) );
4460 PSA_ASSERT( psa_export_key( derived_handle,
4461 export_buffer, bytes1,
4462 &length ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004463 TEST_EQUAL( length, bytes1 );
Gilles Peskine8817f612018-12-18 00:18:46 +01004464 PSA_ASSERT( psa_destroy_key( derived_handle ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004465 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine8817f612018-12-18 00:18:46 +01004466 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
4467 PSA_ASSERT( psa_generator_import_key( derived_handle,
4468 PSA_KEY_TYPE_RAW_DATA,
4469 PSA_BYTES_TO_BITS( bytes2 ),
4470 &generator ) );
4471 PSA_ASSERT( psa_export_key( derived_handle,
4472 export_buffer + bytes1, bytes2,
4473 &length ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004474 TEST_EQUAL( length, bytes2 );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004475
4476 /* Compare the outputs from the two runs. */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004477 ASSERT_COMPARE( output_buffer, bytes1 + bytes2,
4478 export_buffer, capacity );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004479
4480exit:
4481 mbedtls_free( output_buffer );
4482 mbedtls_free( export_buffer );
4483 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004484 psa_destroy_key( base_handle );
4485 psa_destroy_key( derived_handle );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004486 mbedtls_psa_crypto_free( );
4487}
4488/* END_CASE */
4489
4490/* BEGIN_CASE */
Gilles Peskine01d718c2018-09-18 12:01:02 +02004491void key_agreement_setup( int alg_arg,
4492 int our_key_type_arg, data_t *our_key_data,
4493 data_t *peer_key_data,
4494 int expected_status_arg )
4495{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004496 psa_key_handle_t our_key = 0;
Gilles Peskine01d718c2018-09-18 12:01:02 +02004497 psa_algorithm_t alg = alg_arg;
4498 psa_key_type_t our_key_type = our_key_type_arg;
4499 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004500 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine01d718c2018-09-18 12:01:02 +02004501
Gilles Peskine8817f612018-12-18 00:18:46 +01004502 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004503
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004504 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004505 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004506 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
4507 PSA_ASSERT( psa_import_key( our_key, our_key_type,
4508 our_key_data->x,
4509 our_key_data->len ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004510
Gilles Peskinefe11b722018-12-18 00:24:04 +01004511 TEST_EQUAL( psa_key_agreement( &generator,
4512 our_key,
4513 peer_key_data->x, peer_key_data->len,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004514 alg ),
4515 expected_status_arg );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004516
4517exit:
4518 psa_generator_abort( &generator );
4519 psa_destroy_key( our_key );
4520 mbedtls_psa_crypto_free( );
4521}
4522/* END_CASE */
4523
4524/* BEGIN_CASE */
Gilles Peskine59685592018-09-18 12:11:34 +02004525void key_agreement_capacity( int alg_arg,
4526 int our_key_type_arg, data_t *our_key_data,
4527 data_t *peer_key_data,
4528 int expected_capacity_arg )
4529{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004530 psa_key_handle_t our_key = 0;
Gilles Peskine59685592018-09-18 12:11:34 +02004531 psa_algorithm_t alg = alg_arg;
4532 psa_key_type_t our_key_type = our_key_type_arg;
4533 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004534 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine59685592018-09-18 12:11:34 +02004535 size_t actual_capacity;
Gilles Peskinebf491972018-10-25 22:36:12 +02004536 unsigned char output[16];
Gilles Peskine59685592018-09-18 12:11:34 +02004537
Gilles Peskine8817f612018-12-18 00:18:46 +01004538 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004539
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004540 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004541 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004542 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
4543 PSA_ASSERT( psa_import_key( our_key, our_key_type,
4544 our_key_data->x,
4545 our_key_data->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004546
Gilles Peskine8817f612018-12-18 00:18:46 +01004547 PSA_ASSERT( psa_key_agreement( &generator,
4548 our_key,
4549 peer_key_data->x, peer_key_data->len,
4550 alg ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004551
Gilles Peskinebf491972018-10-25 22:36:12 +02004552 /* Test the advertized capacity. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004553 PSA_ASSERT( psa_get_generator_capacity(
4554 &generator, &actual_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004555 TEST_EQUAL( actual_capacity, (size_t) expected_capacity_arg );
Gilles Peskine59685592018-09-18 12:11:34 +02004556
Gilles Peskinebf491972018-10-25 22:36:12 +02004557 /* Test the actual capacity by reading the output. */
4558 while( actual_capacity > sizeof( output ) )
4559 {
Gilles Peskine8817f612018-12-18 00:18:46 +01004560 PSA_ASSERT( psa_generator_read( &generator,
4561 output, sizeof( output ) ) );
Gilles Peskinebf491972018-10-25 22:36:12 +02004562 actual_capacity -= sizeof( output );
4563 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004564 PSA_ASSERT( psa_generator_read( &generator,
4565 output, actual_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004566 TEST_EQUAL( psa_generator_read( &generator, output, 1 ),
David Saadab4ecc272019-02-14 13:48:10 +02004567 PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskinebf491972018-10-25 22:36:12 +02004568
Gilles Peskine59685592018-09-18 12:11:34 +02004569exit:
4570 psa_generator_abort( &generator );
4571 psa_destroy_key( our_key );
4572 mbedtls_psa_crypto_free( );
4573}
4574/* END_CASE */
4575
4576/* BEGIN_CASE */
4577void key_agreement_output( int alg_arg,
4578 int our_key_type_arg, data_t *our_key_data,
4579 data_t *peer_key_data,
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004580 data_t *expected_output1, data_t *expected_output2 )
Gilles Peskine59685592018-09-18 12:11:34 +02004581{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004582 psa_key_handle_t our_key = 0;
Gilles Peskine59685592018-09-18 12:11:34 +02004583 psa_algorithm_t alg = alg_arg;
4584 psa_key_type_t our_key_type = our_key_type_arg;
4585 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004586 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004587 uint8_t *actual_output = NULL;
Gilles Peskine59685592018-09-18 12:11:34 +02004588
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004589 ASSERT_ALLOC( actual_output, MAX( expected_output1->len,
4590 expected_output2->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004591
Gilles Peskine8817f612018-12-18 00:18:46 +01004592 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004593
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004594 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004595 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004596 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
4597 PSA_ASSERT( psa_import_key( our_key, our_key_type,
4598 our_key_data->x,
4599 our_key_data->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004600
Gilles Peskine8817f612018-12-18 00:18:46 +01004601 PSA_ASSERT( psa_key_agreement( &generator,
4602 our_key,
4603 peer_key_data->x, peer_key_data->len,
4604 alg ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004605
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004606 PSA_ASSERT( psa_generator_read( &generator,
4607 actual_output,
4608 expected_output1->len ) );
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004609 ASSERT_COMPARE( actual_output, expected_output1->len,
4610 expected_output1->x, expected_output1->len );
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004611 if( expected_output2->len != 0 )
4612 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004613 PSA_ASSERT( psa_generator_read( &generator,
4614 actual_output,
4615 expected_output2->len ) );
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004616 ASSERT_COMPARE( actual_output, expected_output2->len,
4617 expected_output2->x, expected_output2->len );
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004618 }
Gilles Peskine59685592018-09-18 12:11:34 +02004619
4620exit:
4621 psa_generator_abort( &generator );
4622 psa_destroy_key( our_key );
4623 mbedtls_psa_crypto_free( );
4624 mbedtls_free( actual_output );
4625}
4626/* END_CASE */
4627
4628/* BEGIN_CASE */
Gilles Peskinea50d7392018-06-21 10:22:13 +02004629void generate_random( int bytes_arg )
Gilles Peskine05d69892018-06-19 22:00:52 +02004630{
Gilles Peskinea50d7392018-06-21 10:22:13 +02004631 size_t bytes = bytes_arg;
4632 const unsigned char trail[] = "don't overwrite me";
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004633 unsigned char *output = NULL;
4634 unsigned char *changed = NULL;
Gilles Peskinea50d7392018-06-21 10:22:13 +02004635 size_t i;
4636 unsigned run;
Gilles Peskine05d69892018-06-19 22:00:52 +02004637
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004638 ASSERT_ALLOC( output, bytes + sizeof( trail ) );
4639 ASSERT_ALLOC( changed, bytes );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004640 memcpy( output + bytes, trail, sizeof( trail ) );
Gilles Peskine05d69892018-06-19 22:00:52 +02004641
Gilles Peskine8817f612018-12-18 00:18:46 +01004642 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine05d69892018-06-19 22:00:52 +02004643
Gilles Peskinea50d7392018-06-21 10:22:13 +02004644 /* Run several times, to ensure that every output byte will be
4645 * nonzero at least once with overwhelming probability
4646 * (2^(-8*number_of_runs)). */
4647 for( run = 0; run < 10; run++ )
Gilles Peskine05d69892018-06-19 22:00:52 +02004648 {
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02004649 if( bytes != 0 )
4650 memset( output, 0, bytes );
Gilles Peskine8817f612018-12-18 00:18:46 +01004651 PSA_ASSERT( psa_generate_random( output, bytes ) );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004652
4653 /* Check that no more than bytes have been overwritten */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004654 ASSERT_COMPARE( output + bytes, sizeof( trail ),
4655 trail, sizeof( trail ) );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004656
4657 for( i = 0; i < bytes; i++ )
4658 {
4659 if( output[i] != 0 )
4660 ++changed[i];
4661 }
Gilles Peskine05d69892018-06-19 22:00:52 +02004662 }
Gilles Peskinea50d7392018-06-21 10:22:13 +02004663
4664 /* Check that every byte was changed to nonzero at least once. This
4665 * validates that psa_generate_random is overwriting every byte of
4666 * the output buffer. */
4667 for( i = 0; i < bytes; i++ )
4668 {
4669 TEST_ASSERT( changed[i] != 0 );
4670 }
Gilles Peskine05d69892018-06-19 22:00:52 +02004671
4672exit:
4673 mbedtls_psa_crypto_free( );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004674 mbedtls_free( output );
4675 mbedtls_free( changed );
Gilles Peskine05d69892018-06-19 22:00:52 +02004676}
4677/* END_CASE */
Gilles Peskine12313cd2018-06-20 00:20:32 +02004678
4679/* BEGIN_CASE */
4680void generate_key( int type_arg,
4681 int bits_arg,
4682 int usage_arg,
4683 int alg_arg,
4684 int expected_status_arg )
4685{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004686 psa_key_handle_t handle = 0;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004687 psa_key_type_t type = type_arg;
4688 psa_key_usage_t usage = usage_arg;
4689 size_t bits = bits_arg;
4690 psa_algorithm_t alg = alg_arg;
4691 psa_status_t expected_status = expected_status_arg;
4692 psa_key_type_t got_type;
4693 size_t got_bits;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004694 psa_status_t expected_info_status =
David Saadab4ecc272019-02-14 13:48:10 +02004695 expected_status == PSA_SUCCESS ? PSA_SUCCESS : PSA_ERROR_DOES_NOT_EXIST;
Jaeden Amero70261c52019-01-04 11:47:20 +00004696 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004697
Gilles Peskine8817f612018-12-18 00:18:46 +01004698 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004699
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004700 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004701 psa_key_policy_set_usage( &policy, usage, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004702 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004703
4704 /* Generate a key */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004705 TEST_EQUAL( psa_generate_key( handle, type, bits, NULL, 0 ),
4706 expected_status );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004707
4708 /* Test the key information */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004709 TEST_EQUAL( psa_get_key_information( handle, &got_type, &got_bits ),
4710 expected_info_status );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004711 if( expected_info_status != PSA_SUCCESS )
4712 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01004713 TEST_EQUAL( got_type, type );
4714 TEST_EQUAL( got_bits, bits );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004715
Gilles Peskine818ca122018-06-20 18:16:48 +02004716 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004717 if( ! exercise_key( handle, usage, alg ) )
Gilles Peskine02b75072018-07-01 22:31:34 +02004718 goto exit;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004719
4720exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004721 psa_destroy_key( handle );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004722 mbedtls_psa_crypto_free( );
4723}
4724/* END_CASE */
itayzafrir0adf0fc2018-09-06 16:24:41 +03004725
Darryl Greend49a4992018-06-18 17:27:26 +01004726/* BEGIN_CASE depends_on:MBEDTLS_PSA_CRYPTO_STORAGE_C */
4727void persistent_key_load_key_from_storage( data_t *data, int type_arg,
4728 int bits, int usage_arg,
Darryl Green0c6575a2018-11-07 16:05:30 +00004729 int alg_arg, int generation_method,
4730 int export_status )
Darryl Greend49a4992018-06-18 17:27:26 +01004731{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004732 psa_key_handle_t handle = 0;
4733 psa_key_handle_t base_key;
Darryl Greend49a4992018-06-18 17:27:26 +01004734 psa_key_type_t type = (psa_key_type_t) type_arg;
4735 psa_key_type_t type_get;
4736 size_t bits_get;
Jaeden Amero70261c52019-01-04 11:47:20 +00004737 psa_key_policy_t policy_set = PSA_KEY_POLICY_INIT;
4738 psa_key_policy_t policy_get = PSA_KEY_POLICY_INIT;
Darryl Greend49a4992018-06-18 17:27:26 +01004739 psa_key_usage_t policy_usage = (psa_key_usage_t) usage_arg;
4740 psa_algorithm_t policy_alg = (psa_algorithm_t) alg_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00004741 psa_key_policy_t base_policy_set = PSA_KEY_POLICY_INIT;
Darryl Green0c6575a2018-11-07 16:05:30 +00004742 psa_algorithm_t base_policy_alg = PSA_ALG_HKDF(PSA_ALG_SHA_256);
4743 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Darryl Greend49a4992018-06-18 17:27:26 +01004744 unsigned char *first_export = NULL;
4745 unsigned char *second_export = NULL;
4746 size_t export_size = PSA_KEY_EXPORT_MAX_SIZE( type, bits );
4747 size_t first_exported_length;
4748 size_t second_exported_length;
4749
4750 ASSERT_ALLOC( first_export, export_size );
4751 ASSERT_ALLOC( second_export, export_size );
4752
Gilles Peskine8817f612018-12-18 00:18:46 +01004753 PSA_ASSERT( psa_crypto_init() );
Darryl Greend49a4992018-06-18 17:27:26 +01004754
Gilles Peskine8817f612018-12-18 00:18:46 +01004755 PSA_ASSERT( psa_create_key( PSA_KEY_LIFETIME_PERSISTENT, 1,
Gilles Peskine8817f612018-12-18 00:18:46 +01004756 &handle ) );
Darryl Greend49a4992018-06-18 17:27:26 +01004757 psa_key_policy_set_usage( &policy_set, policy_usage,
4758 policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004759 PSA_ASSERT( psa_set_key_policy( handle, &policy_set ) );
Darryl Greend49a4992018-06-18 17:27:26 +01004760
Darryl Green0c6575a2018-11-07 16:05:30 +00004761 switch( generation_method )
4762 {
4763 case IMPORT_KEY:
4764 /* Import the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01004765 PSA_ASSERT( psa_import_key( handle, type,
4766 data->x, data->len ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004767 break;
Darryl Greend49a4992018-06-18 17:27:26 +01004768
Darryl Green0c6575a2018-11-07 16:05:30 +00004769 case GENERATE_KEY:
4770 /* Generate a key */
Gilles Peskine8817f612018-12-18 00:18:46 +01004771 PSA_ASSERT( psa_generate_key( handle, type, bits,
4772 NULL, 0 ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004773 break;
4774
4775 case DERIVE_KEY:
4776 /* Create base key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004777 PSA_ASSERT( psa_allocate_key( &base_key ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004778 psa_key_policy_set_usage( &base_policy_set, PSA_KEY_USAGE_DERIVE,
4779 base_policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004780 PSA_ASSERT( psa_set_key_policy(
4781 base_key, &base_policy_set ) );
4782 PSA_ASSERT( psa_import_key( base_key, PSA_KEY_TYPE_DERIVE,
4783 data->x, data->len ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004784 /* Derive a key. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004785 PSA_ASSERT( psa_key_derivation( &generator, base_key,
4786 base_policy_alg,
4787 NULL, 0, NULL, 0,
4788 export_size ) );
4789 PSA_ASSERT( psa_generator_import_key(
4790 handle, PSA_KEY_TYPE_RAW_DATA,
4791 bits, &generator ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004792 break;
4793 }
Darryl Greend49a4992018-06-18 17:27:26 +01004794
4795 /* Export the key */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004796 TEST_EQUAL( psa_export_key( handle,
4797 first_export, export_size,
4798 &first_exported_length ),
4799 export_status );
Darryl Greend49a4992018-06-18 17:27:26 +01004800
4801 /* Shutdown and restart */
4802 mbedtls_psa_crypto_free();
Gilles Peskine8817f612018-12-18 00:18:46 +01004803 PSA_ASSERT( psa_crypto_init() );
Darryl Greend49a4992018-06-18 17:27:26 +01004804
Darryl Greend49a4992018-06-18 17:27:26 +01004805 /* Check key slot still contains key data */
Gilles Peskine8817f612018-12-18 00:18:46 +01004806 PSA_ASSERT( psa_open_key( PSA_KEY_LIFETIME_PERSISTENT, 1,
4807 &handle ) );
4808 PSA_ASSERT( psa_get_key_information(
4809 handle, &type_get, &bits_get ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004810 TEST_EQUAL( type_get, type );
4811 TEST_EQUAL( bits_get, (size_t) bits );
Darryl Greend49a4992018-06-18 17:27:26 +01004812
Gilles Peskine8817f612018-12-18 00:18:46 +01004813 PSA_ASSERT( psa_get_key_policy( handle, &policy_get ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004814 TEST_EQUAL( psa_key_policy_get_usage( &policy_get ), policy_usage );
4815 TEST_EQUAL( psa_key_policy_get_algorithm( &policy_get ), policy_alg );
Darryl Greend49a4992018-06-18 17:27:26 +01004816
4817 /* Export the key again */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004818 TEST_EQUAL( psa_export_key( handle,
4819 second_export, export_size,
4820 &second_exported_length ),
4821 export_status );
Darryl Greend49a4992018-06-18 17:27:26 +01004822
Darryl Green0c6575a2018-11-07 16:05:30 +00004823 if( export_status == PSA_SUCCESS )
4824 {
4825 ASSERT_COMPARE( first_export, first_exported_length,
4826 second_export, second_exported_length );
Darryl Greend49a4992018-06-18 17:27:26 +01004827
Darryl Green0c6575a2018-11-07 16:05:30 +00004828 switch( generation_method )
4829 {
4830 case IMPORT_KEY:
4831 ASSERT_COMPARE( data->x, data->len,
4832 first_export, first_exported_length );
4833 break;
4834 default:
4835 break;
4836 }
4837 }
4838
4839 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004840 if( ! exercise_key( handle, policy_usage, policy_alg ) )
Darryl Green0c6575a2018-11-07 16:05:30 +00004841 goto exit;
Darryl Greend49a4992018-06-18 17:27:26 +01004842
4843exit:
4844 mbedtls_free( first_export );
4845 mbedtls_free( second_export );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004846 psa_destroy_key( handle );
Darryl Greend49a4992018-06-18 17:27:26 +01004847 mbedtls_psa_crypto_free();
4848}
4849/* END_CASE */