blob: b9f0d5f48f2c6fb4c2716f6c9cc195f15dcd6a24 [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 ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +0200219 PSA_ASSERT( psa_import_key_to_handle( handle, key_type, key_bytes, key_length ) );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100220
221 *status = psa_mac_sign_setup( operation, handle, alg );
Gilles Peskine9e0a4a52019-02-25 22:11:18 +0100222 /* Whether setup succeeded or failed, abort must succeed. */
223 PSA_ASSERT( psa_mac_abort( operation ) );
224 /* If setup failed, reproduce the failure, so that the caller can
225 * test the resulting state of the operation object. */
226 if( *status != PSA_SUCCESS )
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100227 {
Gilles Peskine9e0a4a52019-02-25 22:11:18 +0100228 TEST_EQUAL( psa_mac_sign_setup( operation, handle, alg ),
229 *status );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100230 }
231
232 psa_destroy_key( handle );
233 return( 1 );
234
235exit:
236 psa_destroy_key( handle );
237 return( 0 );
238}
239
240int exercise_cipher_setup( psa_key_type_t key_type,
241 const unsigned char *key_bytes,
242 size_t key_length,
243 psa_algorithm_t alg,
244 psa_cipher_operation_t *operation,
245 psa_status_t *status )
246{
247 psa_key_handle_t handle = 0;
248 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
249
250 PSA_ASSERT( psa_allocate_key( &handle ) );
251 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
252 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +0200253 PSA_ASSERT( psa_import_key_to_handle( handle, key_type, key_bytes, key_length ) );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100254
255 *status = psa_cipher_encrypt_setup( operation, handle, alg );
Gilles Peskine9e0a4a52019-02-25 22:11:18 +0100256 /* Whether setup succeeded or failed, abort must succeed. */
257 PSA_ASSERT( psa_cipher_abort( operation ) );
258 /* If setup failed, reproduce the failure, so that the caller can
259 * test the resulting state of the operation object. */
260 if( *status != PSA_SUCCESS )
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100261 {
Gilles Peskine9e0a4a52019-02-25 22:11:18 +0100262 TEST_EQUAL( psa_cipher_encrypt_setup( operation, handle, alg ),
263 *status );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100264 }
265
266 psa_destroy_key( handle );
267 return( 1 );
268
269exit:
270 psa_destroy_key( handle );
271 return( 0 );
272}
273
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100274static int exercise_mac_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200275 psa_key_usage_t usage,
276 psa_algorithm_t alg )
277{
Jaeden Amero769ce272019-01-04 11:48:03 +0000278 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskine818ca122018-06-20 18:16:48 +0200279 const unsigned char input[] = "foo";
Gilles Peskine69c12672018-06-28 00:07:19 +0200280 unsigned char mac[PSA_MAC_MAX_SIZE] = {0};
Gilles Peskine818ca122018-06-20 18:16:48 +0200281 size_t mac_length = sizeof( mac );
282
283 if( usage & PSA_KEY_USAGE_SIGN )
284 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100285 PSA_ASSERT( psa_mac_sign_setup( &operation,
286 handle, alg ) );
287 PSA_ASSERT( psa_mac_update( &operation,
288 input, sizeof( input ) ) );
289 PSA_ASSERT( psa_mac_sign_finish( &operation,
290 mac, sizeof( mac ),
291 &mac_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200292 }
293
294 if( usage & PSA_KEY_USAGE_VERIFY )
295 {
296 psa_status_t verify_status =
297 ( usage & PSA_KEY_USAGE_SIGN ?
298 PSA_SUCCESS :
299 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine8817f612018-12-18 00:18:46 +0100300 PSA_ASSERT( psa_mac_verify_setup( &operation,
301 handle, alg ) );
302 PSA_ASSERT( psa_mac_update( &operation,
303 input, sizeof( input ) ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100304 TEST_EQUAL( psa_mac_verify_finish( &operation, mac, mac_length ),
305 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200306 }
307
308 return( 1 );
309
310exit:
311 psa_mac_abort( &operation );
312 return( 0 );
313}
314
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100315static int exercise_cipher_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200316 psa_key_usage_t usage,
317 psa_algorithm_t alg )
318{
Jaeden Amero5bae2272019-01-04 11:48:27 +0000319 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine818ca122018-06-20 18:16:48 +0200320 unsigned char iv[16] = {0};
321 size_t iv_length = sizeof( iv );
322 const unsigned char plaintext[16] = "Hello, world...";
323 unsigned char ciphertext[32] = "(wabblewebblewibblewobblewubble)";
324 size_t ciphertext_length = sizeof( ciphertext );
325 unsigned char decrypted[sizeof( ciphertext )];
326 size_t part_length;
327
328 if( usage & PSA_KEY_USAGE_ENCRYPT )
329 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100330 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
331 handle, alg ) );
332 PSA_ASSERT( psa_cipher_generate_iv( &operation,
333 iv, sizeof( iv ),
334 &iv_length ) );
335 PSA_ASSERT( psa_cipher_update( &operation,
336 plaintext, sizeof( plaintext ),
337 ciphertext, sizeof( ciphertext ),
338 &ciphertext_length ) );
339 PSA_ASSERT( psa_cipher_finish( &operation,
340 ciphertext + ciphertext_length,
341 sizeof( ciphertext ) - ciphertext_length,
342 &part_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200343 ciphertext_length += part_length;
344 }
345
346 if( usage & PSA_KEY_USAGE_DECRYPT )
347 {
348 psa_status_t status;
Mohammad AboMokhadb9b232018-06-28 01:52:54 -0700349 psa_key_type_t type = PSA_KEY_TYPE_NONE;
Gilles Peskine818ca122018-06-20 18:16:48 +0200350 if( ! ( usage & PSA_KEY_USAGE_ENCRYPT ) )
351 {
Gilles Peskine818ca122018-06-20 18:16:48 +0200352 size_t bits;
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100353 TEST_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200354 iv_length = PSA_BLOCK_CIPHER_BLOCK_SIZE( type );
355 }
Gilles Peskine8817f612018-12-18 00:18:46 +0100356 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
357 handle, alg ) );
358 PSA_ASSERT( psa_cipher_set_iv( &operation,
359 iv, iv_length ) );
360 PSA_ASSERT( psa_cipher_update( &operation,
361 ciphertext, ciphertext_length,
362 decrypted, sizeof( decrypted ),
363 &part_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200364 status = psa_cipher_finish( &operation,
365 decrypted + part_length,
366 sizeof( decrypted ) - part_length,
367 &part_length );
368 /* For a stream cipher, all inputs are valid. For a block cipher,
369 * if the input is some aribtrary data rather than an actual
370 ciphertext, a padding error is likely. */
Mohammad AboMokh65fa0b82018-06-28 02:14:00 -0700371 if( ( usage & PSA_KEY_USAGE_ENCRYPT ) ||
Mohammad AboMokhadb9b232018-06-28 01:52:54 -0700372 PSA_BLOCK_CIPHER_BLOCK_SIZE( type ) == 1 )
Gilles Peskine8817f612018-12-18 00:18:46 +0100373 PSA_ASSERT( status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200374 else
375 TEST_ASSERT( status == PSA_SUCCESS ||
376 status == PSA_ERROR_INVALID_PADDING );
377 }
378
379 return( 1 );
380
381exit:
382 psa_cipher_abort( &operation );
383 return( 0 );
384}
385
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100386static int exercise_aead_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200387 psa_key_usage_t usage,
388 psa_algorithm_t alg )
389{
390 unsigned char nonce[16] = {0};
391 size_t nonce_length = sizeof( nonce );
392 unsigned char plaintext[16] = "Hello, world...";
393 unsigned char ciphertext[48] = "(wabblewebblewibblewobblewubble)";
394 size_t ciphertext_length = sizeof( ciphertext );
395 size_t plaintext_length = sizeof( ciphertext );
396
397 if( usage & PSA_KEY_USAGE_ENCRYPT )
398 {
Gilles Peskine8817f612018-12-18 00:18:46 +0100399 PSA_ASSERT( psa_aead_encrypt( handle, alg,
400 nonce, nonce_length,
401 NULL, 0,
402 plaintext, sizeof( plaintext ),
403 ciphertext, sizeof( ciphertext ),
404 &ciphertext_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200405 }
406
407 if( usage & PSA_KEY_USAGE_DECRYPT )
408 {
409 psa_status_t verify_status =
410 ( usage & PSA_KEY_USAGE_ENCRYPT ?
411 PSA_SUCCESS :
412 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100413 TEST_EQUAL( psa_aead_decrypt( handle, alg,
414 nonce, nonce_length,
415 NULL, 0,
416 ciphertext, ciphertext_length,
417 plaintext, sizeof( plaintext ),
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100418 &plaintext_length ),
419 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200420 }
421
422 return( 1 );
423
424exit:
425 return( 0 );
426}
427
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100428static int exercise_signature_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200429 psa_key_usage_t usage,
430 psa_algorithm_t alg )
431{
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200432 unsigned char payload[PSA_HASH_MAX_SIZE] = {1};
433 size_t payload_length = 16;
Gilles Peskine69c12672018-06-28 00:07:19 +0200434 unsigned char signature[PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE] = {0};
Gilles Peskine818ca122018-06-20 18:16:48 +0200435 size_t signature_length = sizeof( signature );
Gilles Peskine57ab7212019-01-28 13:03:09 +0100436 psa_algorithm_t hash_alg = PSA_ALG_SIGN_GET_HASH( alg );
437
438 /* If the policy allows signing with any hash, just pick one. */
439 if( PSA_ALG_IS_HASH_AND_SIGN( alg ) && hash_alg == PSA_ALG_ANY_HASH )
440 {
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100441#if defined(KNOWN_SUPPORTED_HASH_ALG)
442 hash_alg = KNOWN_SUPPORTED_HASH_ALG;
443 alg ^= PSA_ALG_ANY_HASH ^ hash_alg;
Gilles Peskine57ab7212019-01-28 13:03:09 +0100444#else
445 test_fail( "No hash algorithm for hash-and-sign testing", __LINE__, __FILE__ );
Gilles Peskinef426e0f2019-02-25 17:42:03 +0100446 return( 1 );
Gilles Peskine57ab7212019-01-28 13:03:09 +0100447#endif
Gilles Peskine57ab7212019-01-28 13:03:09 +0100448 }
Gilles Peskine818ca122018-06-20 18:16:48 +0200449
450 if( usage & PSA_KEY_USAGE_SIGN )
451 {
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200452 /* Some algorithms require the payload to have the size of
453 * the hash encoded in the algorithm. Use this input size
454 * even for algorithms that allow other input sizes. */
Gilles Peskinef969b3a2018-06-30 00:20:25 +0200455 if( hash_alg != 0 )
456 payload_length = PSA_HASH_SIZE( hash_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +0100457 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
458 payload, payload_length,
459 signature, sizeof( signature ),
460 &signature_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200461 }
462
463 if( usage & PSA_KEY_USAGE_VERIFY )
464 {
465 psa_status_t verify_status =
466 ( usage & PSA_KEY_USAGE_SIGN ?
467 PSA_SUCCESS :
468 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100469 TEST_EQUAL( psa_asymmetric_verify( handle, alg,
470 payload, payload_length,
471 signature, signature_length ),
472 verify_status );
Gilles Peskine818ca122018-06-20 18:16:48 +0200473 }
474
475 return( 1 );
476
477exit:
478 return( 0 );
479}
480
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100481static int exercise_asymmetric_encryption_key( psa_key_handle_t handle,
Gilles Peskine818ca122018-06-20 18:16:48 +0200482 psa_key_usage_t usage,
483 psa_algorithm_t alg )
484{
485 unsigned char plaintext[256] = "Hello, world...";
486 unsigned char ciphertext[256] = "(wabblewebblewibblewobblewubble)";
487 size_t ciphertext_length = sizeof( ciphertext );
488 size_t plaintext_length = 16;
489
490 if( usage & PSA_KEY_USAGE_ENCRYPT )
491 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100492 PSA_ASSERT( psa_asymmetric_encrypt( handle, alg,
493 plaintext, plaintext_length,
494 NULL, 0,
495 ciphertext, sizeof( ciphertext ),
496 &ciphertext_length ) );
Gilles Peskine818ca122018-06-20 18:16:48 +0200497 }
498
499 if( usage & PSA_KEY_USAGE_DECRYPT )
500 {
501 psa_status_t status =
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100502 psa_asymmetric_decrypt( handle, alg,
Gilles Peskine818ca122018-06-20 18:16:48 +0200503 ciphertext, ciphertext_length,
504 NULL, 0,
505 plaintext, sizeof( plaintext ),
506 &plaintext_length );
507 TEST_ASSERT( status == PSA_SUCCESS ||
508 ( ( usage & PSA_KEY_USAGE_ENCRYPT ) == 0 &&
509 ( status == PSA_ERROR_INVALID_ARGUMENT ||
510 status == PSA_ERROR_INVALID_PADDING ) ) );
511 }
512
513 return( 1 );
514
515exit:
516 return( 0 );
517}
Gilles Peskine02b75072018-07-01 22:31:34 +0200518
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100519static int exercise_key_derivation_key( psa_key_handle_t handle,
Gilles Peskineea0fb492018-07-12 17:17:20 +0200520 psa_key_usage_t usage,
521 psa_algorithm_t alg )
522{
523 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
524 unsigned char label[16] = "This is a label.";
525 size_t label_length = sizeof( label );
526 unsigned char seed[16] = "abcdefghijklmnop";
527 size_t seed_length = sizeof( seed );
528 unsigned char output[1];
529
530 if( usage & PSA_KEY_USAGE_DERIVE )
531 {
Gilles Peskineb70a0fd2019-01-07 22:59:38 +0100532 if( PSA_ALG_IS_HKDF( alg ) )
533 {
534 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
535 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
536 PSA_KDF_STEP_SALT,
537 label,
538 label_length ) );
539 PSA_ASSERT( psa_key_derivation_input_key( &generator,
540 PSA_KDF_STEP_SECRET,
541 handle ) );
542 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
543 PSA_KDF_STEP_INFO,
544 seed,
545 seed_length ) );
546 }
547 else
548 {
549 // legacy
550 PSA_ASSERT( psa_key_derivation( &generator,
551 handle, alg,
552 label, label_length,
553 seed, seed_length,
554 sizeof( output ) ) );
555 }
Gilles Peskine8817f612018-12-18 00:18:46 +0100556 PSA_ASSERT( psa_generator_read( &generator,
557 output,
558 sizeof( output ) ) );
559 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +0200560 }
561
562 return( 1 );
563
564exit:
565 return( 0 );
566}
567
Gilles Peskinec7998b72018-11-07 18:45:02 +0100568/* We need two keys to exercise key agreement. Exercise the
569 * private key against its own public key. */
570static psa_status_t key_agreement_with_self( psa_crypto_generator_t *generator,
Gilles Peskine969c5d62019-01-16 15:53:06 +0100571 psa_key_handle_t handle )
Gilles Peskinec7998b72018-11-07 18:45:02 +0100572{
573 psa_key_type_t private_key_type;
574 psa_key_type_t public_key_type;
575 size_t key_bits;
576 uint8_t *public_key = NULL;
577 size_t public_key_length;
David Saadab4ecc272019-02-14 13:48:10 +0200578 /* Return GENERIC_ERROR if something other than the final call to
Gilles Peskinec7998b72018-11-07 18:45:02 +0100579 * psa_key_agreement fails. This isn't fully satisfactory, but it's
580 * good enough: callers will report it as a failed test anyway. */
David Saadab4ecc272019-02-14 13:48:10 +0200581 psa_status_t status = PSA_ERROR_GENERIC_ERROR;
Gilles Peskinec7998b72018-11-07 18:45:02 +0100582
Gilles Peskine8817f612018-12-18 00:18:46 +0100583 PSA_ASSERT( psa_get_key_information( handle,
584 &private_key_type,
585 &key_bits ) );
Gilles Peskinec7998b72018-11-07 18:45:02 +0100586 public_key_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( private_key_type );
587 public_key_length = PSA_KEY_EXPORT_MAX_SIZE( public_key_type, key_bits );
588 ASSERT_ALLOC( public_key, public_key_length );
Gilles Peskine8817f612018-12-18 00:18:46 +0100589 PSA_ASSERT( psa_export_public_key( handle,
590 public_key, public_key_length,
591 &public_key_length ) );
Gilles Peskinec7998b72018-11-07 18:45:02 +0100592
Gilles Peskine969c5d62019-01-16 15:53:06 +0100593 status = psa_key_agreement( generator, PSA_KDF_STEP_SECRET, handle,
594 public_key, public_key_length );
Gilles Peskinec7998b72018-11-07 18:45:02 +0100595exit:
596 mbedtls_free( public_key );
597 return( status );
598}
599
Gilles Peskine2e46e9c2019-04-11 21:24:55 +0200600/* We need two keys to exercise key agreement. Exercise the
601 * private key against its own public key. */
602static psa_status_t raw_key_agreement_with_self( psa_algorithm_t alg,
603 psa_key_handle_t handle )
604{
605 psa_key_type_t private_key_type;
606 psa_key_type_t public_key_type;
607 size_t key_bits;
608 uint8_t *public_key = NULL;
609 size_t public_key_length;
610 uint8_t output[1024];
611 size_t output_length;
612 /* Return GENERIC_ERROR if something other than the final call to
613 * psa_key_agreement fails. This isn't fully satisfactory, but it's
614 * good enough: callers will report it as a failed test anyway. */
615 psa_status_t status = PSA_ERROR_GENERIC_ERROR;
616
617 PSA_ASSERT( psa_get_key_information( handle,
618 &private_key_type,
619 &key_bits ) );
620 public_key_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( private_key_type );
621 public_key_length = PSA_KEY_EXPORT_MAX_SIZE( public_key_type, key_bits );
622 ASSERT_ALLOC( public_key, public_key_length );
623 PSA_ASSERT( psa_export_public_key( handle,
624 public_key, public_key_length,
625 &public_key_length ) );
626
627 status = psa_key_agreement_raw_shared_secret(
628 alg, handle,
629 public_key, public_key_length,
630 output, sizeof( output ), &output_length );
631exit:
632 mbedtls_free( public_key );
633 return( status );
634}
635
636static int exercise_raw_key_agreement_key( psa_key_handle_t handle,
637 psa_key_usage_t usage,
638 psa_algorithm_t alg )
639{
640 int ok = 0;
641
642 if( usage & PSA_KEY_USAGE_DERIVE )
643 {
644 /* We need two keys to exercise key agreement. Exercise the
645 * private key against its own public key. */
646 PSA_ASSERT( raw_key_agreement_with_self( alg, handle ) );
647 }
648 ok = 1;
649
650exit:
651 return( ok );
652}
653
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100654static int exercise_key_agreement_key( psa_key_handle_t handle,
Gilles Peskine01d718c2018-09-18 12:01:02 +0200655 psa_key_usage_t usage,
656 psa_algorithm_t alg )
657{
658 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Gilles Peskine01d718c2018-09-18 12:01:02 +0200659 unsigned char output[1];
660 int ok = 0;
661
662 if( usage & PSA_KEY_USAGE_DERIVE )
663 {
664 /* We need two keys to exercise key agreement. Exercise the
665 * private key against its own public key. */
Gilles Peskine969c5d62019-01-16 15:53:06 +0100666 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
667 PSA_ASSERT( key_agreement_with_self( &generator, handle ) );
Gilles Peskine8817f612018-12-18 00:18:46 +0100668 PSA_ASSERT( psa_generator_read( &generator,
669 output,
670 sizeof( output ) ) );
671 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +0200672 }
673 ok = 1;
674
675exit:
Gilles Peskine01d718c2018-09-18 12:01:02 +0200676 return( ok );
677}
678
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200679static int is_oid_of_key_type( psa_key_type_t type,
680 const uint8_t *oid, size_t oid_length )
681{
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200682 const uint8_t *expected_oid = NULL;
683 size_t expected_oid_length = 0;
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200684#if defined(MBEDTLS_RSA_C)
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200685 if( PSA_KEY_TYPE_IS_RSA( type ) )
686 {
687 expected_oid = (uint8_t *) MBEDTLS_OID_PKCS1_RSA;
688 expected_oid_length = sizeof( MBEDTLS_OID_PKCS1_RSA ) - 1;
689 }
690 else
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200691#endif /* MBEDTLS_RSA_C */
692#if defined(MBEDTLS_ECP_C)
Gilles Peskineae3d2a22018-08-13 14:14:22 +0200693 if( PSA_KEY_TYPE_IS_ECC( type ) )
694 {
695 expected_oid = (uint8_t *) MBEDTLS_OID_EC_ALG_UNRESTRICTED;
696 expected_oid_length = sizeof( MBEDTLS_OID_EC_ALG_UNRESTRICTED ) - 1;
697 }
698 else
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200699#endif /* MBEDTLS_ECP_C */
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200700 {
701 char message[40];
702 mbedtls_snprintf( message, sizeof( message ),
703 "OID not known for key type=0x%08lx",
704 (unsigned long) type );
705 test_fail( message, __LINE__, __FILE__ );
706 return( 0 );
707 }
708
Gilles Peskinebd7dea92018-09-27 13:57:19 +0200709 ASSERT_COMPARE( expected_oid, expected_oid_length, oid, oid_length );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200710 return( 1 );
711
712exit:
713 return( 0 );
714}
715
716static int asn1_skip_integer( unsigned char **p, const unsigned char *end,
717 size_t min_bits, size_t max_bits,
718 int must_be_odd )
719{
720 size_t len;
721 size_t actual_bits;
722 unsigned char msb;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100723 TEST_EQUAL( mbedtls_asn1_get_tag( p, end, &len,
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100724 MBEDTLS_ASN1_INTEGER ),
725 0 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200726 /* Tolerate a slight departure from DER encoding:
727 * - 0 may be represented by an empty string or a 1-byte string.
728 * - The sign bit may be used as a value bit. */
729 if( ( len == 1 && ( *p )[0] == 0 ) ||
730 ( len > 1 && ( *p )[0] == 0 && ( ( *p )[1] & 0x80 ) != 0 ) )
731 {
732 ++( *p );
733 --len;
734 }
735 if( min_bits == 0 && len == 0 )
736 return( 1 );
737 msb = ( *p )[0];
738 TEST_ASSERT( msb != 0 );
739 actual_bits = 8 * ( len - 1 );
740 while( msb != 0 )
741 {
742 msb >>= 1;
743 ++actual_bits;
744 }
745 TEST_ASSERT( actual_bits >= min_bits );
746 TEST_ASSERT( actual_bits <= max_bits );
747 if( must_be_odd )
748 TEST_ASSERT( ( ( *p )[len-1] & 1 ) != 0 );
749 *p += len;
750 return( 1 );
751exit:
752 return( 0 );
753}
754
755static int asn1_get_implicit_tag( unsigned char **p, const unsigned char *end,
756 size_t *len,
757 unsigned char n, unsigned char tag )
758{
759 int ret;
760 ret = mbedtls_asn1_get_tag( p, end, len,
761 MBEDTLS_ASN1_CONTEXT_SPECIFIC |
762 MBEDTLS_ASN1_CONSTRUCTED | ( n ) );
763 if( ret != 0 )
764 return( ret );
765 end = *p + *len;
766 ret = mbedtls_asn1_get_tag( p, end, len, tag );
767 if( ret != 0 )
768 return( ret );
769 if( *p + *len != end )
770 return( MBEDTLS_ERR_ASN1_LENGTH_MISMATCH );
771 return( 0 );
772}
773
774static int exported_key_sanity_check( psa_key_type_t type, size_t bits,
775 uint8_t *exported, size_t exported_length )
776{
777 if( PSA_KEY_TYPE_IS_UNSTRUCTURED( type ) )
Gilles Peskinefe11b722018-12-18 00:24:04 +0100778 TEST_EQUAL( exported_length, ( bits + 7 ) / 8 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200779 else
780 TEST_ASSERT( exported_length <= PSA_KEY_EXPORT_MAX_SIZE( type, bits ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200781
782#if defined(MBEDTLS_DES_C)
783 if( type == PSA_KEY_TYPE_DES )
784 {
785 /* Check the parity bits. */
786 unsigned i;
787 for( i = 0; i < bits / 8; i++ )
788 {
789 unsigned bit_count = 0;
790 unsigned m;
791 for( m = 1; m <= 0x100; m <<= 1 )
792 {
793 if( exported[i] & m )
794 ++bit_count;
795 }
796 TEST_ASSERT( bit_count % 2 != 0 );
797 }
798 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200799 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200800#endif
801
802#if defined(MBEDTLS_RSA_C) && defined(MBEDTLS_PK_PARSE_C)
803 if( type == PSA_KEY_TYPE_RSA_KEYPAIR )
804 {
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200805 uint8_t *p = exported;
806 uint8_t *end = exported + exported_length;
807 size_t len;
808 /* RSAPrivateKey ::= SEQUENCE {
Gilles Peskinedea46cf2018-08-21 16:12:54 +0200809 * version INTEGER, -- must be 0
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200810 * modulus INTEGER, -- n
811 * publicExponent INTEGER, -- e
812 * privateExponent INTEGER, -- d
813 * prime1 INTEGER, -- p
814 * prime2 INTEGER, -- q
815 * exponent1 INTEGER, -- d mod (p-1)
816 * exponent2 INTEGER, -- d mod (q-1)
817 * coefficient INTEGER, -- (inverse of q) mod p
818 * }
819 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100820 TEST_EQUAL( mbedtls_asn1_get_tag( &p, end, &len,
821 MBEDTLS_ASN1_SEQUENCE |
822 MBEDTLS_ASN1_CONSTRUCTED ), 0 );
823 TEST_EQUAL( p + len, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200824 if( ! asn1_skip_integer( &p, end, 0, 0, 0 ) )
825 goto exit;
826 if( ! asn1_skip_integer( &p, end, bits, bits, 1 ) )
827 goto exit;
828 if( ! asn1_skip_integer( &p, end, 2, bits, 1 ) )
829 goto exit;
830 /* Require d to be at least half the size of n. */
831 if( ! asn1_skip_integer( &p, end, bits / 2, bits, 1 ) )
832 goto exit;
833 /* Require p and q to be at most half the size of n, rounded up. */
834 if( ! asn1_skip_integer( &p, end, bits / 2, bits / 2 + 1, 1 ) )
835 goto exit;
836 if( ! asn1_skip_integer( &p, end, bits / 2, bits / 2 + 1, 1 ) )
837 goto exit;
838 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
839 goto exit;
840 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
841 goto exit;
842 if( ! asn1_skip_integer( &p, end, 1, bits / 2 + 1, 0 ) )
843 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100844 TEST_EQUAL( p, end );
Gilles Peskine0f915f12018-12-17 23:35:42 +0100845 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200846 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200847#endif /* MBEDTLS_RSA_C */
848
849#if defined(MBEDTLS_ECP_C)
850 if( PSA_KEY_TYPE_IS_ECC_KEYPAIR( type ) )
851 {
Gilles Peskine5b802a32018-10-29 19:21:41 +0100852 /* Just the secret value */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100853 TEST_EQUAL( exported_length, PSA_BITS_TO_BYTES( bits ) );
Gilles Peskine5b802a32018-10-29 19:21:41 +0100854 }
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200855 else
Gilles Peskined14664a2018-08-10 19:07:32 +0200856#endif /* MBEDTLS_ECP_C */
857
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200858 if( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) )
859 {
860 uint8_t *p = exported;
861 uint8_t *end = exported + exported_length;
862 size_t len;
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200863#if defined(MBEDTLS_RSA_C)
864 if( type == PSA_KEY_TYPE_RSA_PUBLIC_KEY )
865 {
866 /* RSAPublicKey ::= SEQUENCE {
867 * modulus INTEGER, -- n
868 * publicExponent INTEGER } -- e
869 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100870 TEST_EQUAL( mbedtls_asn1_get_tag( &p, end, &len,
871 MBEDTLS_ASN1_SEQUENCE |
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100872 MBEDTLS_ASN1_CONSTRUCTED ),
873 0 );
Gilles Peskinefe11b722018-12-18 00:24:04 +0100874 TEST_EQUAL( p + len, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200875 if( ! asn1_skip_integer( &p, end, bits, bits, 1 ) )
876 goto exit;
877 if( ! asn1_skip_integer( &p, end, 2, bits, 1 ) )
878 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +0100879 TEST_EQUAL( p, end );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200880 }
881 else
882#endif /* MBEDTLS_RSA_C */
883#if defined(MBEDTLS_ECP_C)
884 if( PSA_KEY_TYPE_IS_ECC_PUBLIC_KEY( type ) )
885 {
Jaeden Amero0ae445f2019-01-10 11:42:27 +0000886 /* The representation of an ECC public key is:
887 * - The byte 0x04;
888 * - `x_P` as a `ceiling(m/8)`-byte string, big-endian;
889 * - `y_P` as a `ceiling(m/8)`-byte string, big-endian;
890 * - where m is the bit size associated with the curve.
Jaeden Amero6b196002019-01-10 10:23:21 +0000891 */
Gilles Peskinefe11b722018-12-18 00:24:04 +0100892 TEST_EQUAL( p + 1 + 2 * PSA_BITS_TO_BYTES( bits ), end );
893 TEST_EQUAL( p[0], 4 );
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200894 }
895 else
896#endif /* MBEDTLS_ECP_C */
897 {
Jaeden Amero594a3302018-10-26 17:07:22 +0100898 char message[47];
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200899 mbedtls_snprintf( message, sizeof( message ),
900 "No sanity check for public key type=0x%08lx",
901 (unsigned long) type );
902 test_fail( message, __LINE__, __FILE__ );
903 return( 0 );
904 }
905 }
906 else
907
908 {
909 /* No sanity checks for other types */
910 }
911
912 return( 1 );
Gilles Peskined14664a2018-08-10 19:07:32 +0200913
914exit:
Gilles Peskinedd2f95b2018-08-11 01:22:42 +0200915 return( 0 );
Gilles Peskined14664a2018-08-10 19:07:32 +0200916}
917
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100918static int exercise_export_key( psa_key_handle_t handle,
Gilles Peskined14664a2018-08-10 19:07:32 +0200919 psa_key_usage_t usage )
920{
921 psa_key_type_t type;
922 size_t bits;
923 uint8_t *exported = NULL;
924 size_t exported_size = 0;
925 size_t exported_length = 0;
926 int ok = 0;
927
Gilles Peskine8817f612018-12-18 00:18:46 +0100928 PSA_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskineacec7b6f2018-09-13 20:34:11 +0200929
930 if( ( usage & PSA_KEY_USAGE_EXPORT ) == 0 &&
931 ! PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) )
Gilles Peskined14664a2018-08-10 19:07:32 +0200932 {
Gilles Peskinefe11b722018-12-18 00:24:04 +0100933 TEST_EQUAL( psa_export_key( handle, NULL, 0, &exported_length ),
934 PSA_ERROR_NOT_PERMITTED );
Gilles Peskined14664a2018-08-10 19:07:32 +0200935 return( 1 );
936 }
937
Gilles Peskined14664a2018-08-10 19:07:32 +0200938 exported_size = PSA_KEY_EXPORT_MAX_SIZE( type, bits );
Gilles Peskine8cebbba2018-09-27 13:54:18 +0200939 ASSERT_ALLOC( exported, exported_size );
Gilles Peskined14664a2018-08-10 19:07:32 +0200940
Gilles Peskine8817f612018-12-18 00:18:46 +0100941 PSA_ASSERT( psa_export_key( handle,
942 exported, exported_size,
943 &exported_length ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200944 ok = exported_key_sanity_check( type, bits, exported, exported_length );
945
946exit:
947 mbedtls_free( exported );
948 return( ok );
949}
950
Gilles Peskinebdf309c2018-12-03 15:36:32 +0100951static int exercise_export_public_key( psa_key_handle_t handle )
Gilles Peskined14664a2018-08-10 19:07:32 +0200952{
953 psa_key_type_t type;
954 psa_key_type_t public_type;
955 size_t bits;
956 uint8_t *exported = NULL;
957 size_t exported_size = 0;
958 size_t exported_length = 0;
959 int ok = 0;
960
Gilles Peskine8817f612018-12-18 00:18:46 +0100961 PSA_ASSERT( psa_get_key_information( handle, &type, &bits ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200962 if( ! PSA_KEY_TYPE_IS_ASYMMETRIC( type ) )
963 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +0100964 TEST_EQUAL( psa_export_public_key( handle, NULL, 0, &exported_length ),
Gilles Peskinefe11b722018-12-18 00:24:04 +0100965 PSA_ERROR_INVALID_ARGUMENT );
Gilles Peskined14664a2018-08-10 19:07:32 +0200966 return( 1 );
967 }
968
969 public_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( type );
970 exported_size = PSA_KEY_EXPORT_MAX_SIZE( public_type, bits );
Gilles Peskine8cebbba2018-09-27 13:54:18 +0200971 ASSERT_ALLOC( exported, exported_size );
Gilles Peskined14664a2018-08-10 19:07:32 +0200972
Gilles Peskine8817f612018-12-18 00:18:46 +0100973 PSA_ASSERT( psa_export_public_key( handle,
974 exported, exported_size,
975 &exported_length ) );
Gilles Peskined14664a2018-08-10 19:07:32 +0200976 ok = exported_key_sanity_check( public_type, bits,
977 exported, exported_length );
978
979exit:
980 mbedtls_free( exported );
981 return( ok );
982}
983
Gilles Peskinec9516fb2019-02-05 20:32:06 +0100984/** Do smoke tests on a key.
985 *
986 * Perform one of each operation indicated by \p alg (decrypt/encrypt,
987 * sign/verify, or derivation) that is permitted according to \p usage.
988 * \p usage and \p alg should correspond to the expected policy on the
989 * key.
990 *
991 * Export the key if permitted by \p usage, and check that the output
992 * looks sensible. If \p usage forbids export, check that
993 * \p psa_export_key correctly rejects the attempt. If the key is
994 * asymmetric, also check \p psa_export_public_key.
995 *
996 * If the key fails the tests, this function calls the test framework's
997 * `test_fail` function and returns false. Otherwise this function returns
998 * true. Therefore it should be used as follows:
999 * ```
1000 * if( ! exercise_key( ... ) ) goto exit;
1001 * ```
1002 *
1003 * \param handle The key to exercise. It should be capable of performing
1004 * \p alg.
1005 * \param usage The usage flags to assume.
1006 * \param alg The algorithm to exercise.
1007 *
1008 * \retval 0 The key failed the smoke tests.
1009 * \retval 1 The key passed the smoke tests.
1010 */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001011static int exercise_key( psa_key_handle_t handle,
Gilles Peskine02b75072018-07-01 22:31:34 +02001012 psa_key_usage_t usage,
1013 psa_algorithm_t alg )
1014{
1015 int ok;
1016 if( alg == 0 )
1017 ok = 1; /* If no algorihm, do nothing (used for raw data "keys"). */
1018 else if( PSA_ALG_IS_MAC( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001019 ok = exercise_mac_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +02001020 else if( PSA_ALG_IS_CIPHER( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001021 ok = exercise_cipher_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +02001022 else if( PSA_ALG_IS_AEAD( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001023 ok = exercise_aead_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +02001024 else if( PSA_ALG_IS_SIGN( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001025 ok = exercise_signature_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +02001026 else if( PSA_ALG_IS_ASYMMETRIC_ENCRYPTION( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001027 ok = exercise_asymmetric_encryption_key( handle, usage, alg );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001028 else if( PSA_ALG_IS_KEY_DERIVATION( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001029 ok = exercise_key_derivation_key( handle, usage, alg );
Gilles Peskine2e46e9c2019-04-11 21:24:55 +02001030 else if( PSA_ALG_IS_RAW_KEY_AGREEMENT( alg ) )
1031 ok = exercise_raw_key_agreement_key( handle, usage, alg );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001032 else if( PSA_ALG_IS_KEY_AGREEMENT( alg ) )
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001033 ok = exercise_key_agreement_key( handle, usage, alg );
Gilles Peskine02b75072018-07-01 22:31:34 +02001034 else
1035 {
1036 char message[40];
1037 mbedtls_snprintf( message, sizeof( message ),
1038 "No code to exercise alg=0x%08lx",
1039 (unsigned long) alg );
1040 test_fail( message, __LINE__, __FILE__ );
1041 ok = 0;
1042 }
Gilles Peskined14664a2018-08-10 19:07:32 +02001043
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001044 ok = ok && exercise_export_key( handle, usage );
1045 ok = ok && exercise_export_public_key( handle );
Gilles Peskined14664a2018-08-10 19:07:32 +02001046
Gilles Peskine02b75072018-07-01 22:31:34 +02001047 return( ok );
1048}
1049
Gilles Peskine10df3412018-10-25 22:35:43 +02001050static psa_key_usage_t usage_to_exercise( psa_key_type_t type,
1051 psa_algorithm_t alg )
1052{
1053 if( PSA_ALG_IS_MAC( alg ) || PSA_ALG_IS_SIGN( alg ) )
1054 {
1055 return( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) ?
1056 PSA_KEY_USAGE_VERIFY :
1057 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY );
1058 }
1059 else if( PSA_ALG_IS_CIPHER( alg ) || PSA_ALG_IS_AEAD( alg ) ||
1060 PSA_ALG_IS_ASYMMETRIC_ENCRYPTION( alg ) )
1061 {
1062 return( PSA_KEY_TYPE_IS_PUBLIC_KEY( type ) ?
1063 PSA_KEY_USAGE_ENCRYPT :
1064 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT );
1065 }
1066 else if( PSA_ALG_IS_KEY_DERIVATION( alg ) ||
1067 PSA_ALG_IS_KEY_AGREEMENT( alg ) )
1068 {
1069 return( PSA_KEY_USAGE_DERIVE );
1070 }
1071 else
1072 {
1073 return( 0 );
1074 }
1075
1076}
Darryl Green0c6575a2018-11-07 16:05:30 +00001077
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001078/* An overapproximation of the amount of storage needed for a key of the
1079 * given type and with the given content. The API doesn't make it easy
1080 * to find a good value for the size. The current implementation doesn't
1081 * care about the value anyway. */
1082#define KEY_BITS_FROM_DATA( type, data ) \
1083 ( data )->len
1084
Darryl Green0c6575a2018-11-07 16:05:30 +00001085typedef enum {
1086 IMPORT_KEY = 0,
1087 GENERATE_KEY = 1,
1088 DERIVE_KEY = 2
1089} generate_method;
1090
Gilles Peskinee59236f2018-01-27 23:32:46 +01001091/* END_HEADER */
1092
1093/* BEGIN_DEPENDENCIES
1094 * depends_on:MBEDTLS_PSA_CRYPTO_C
1095 * END_DEPENDENCIES
1096 */
1097
1098/* BEGIN_CASE */
Gilles Peskinee1f2d7d2018-08-21 14:54:54 +02001099void static_checks( )
1100{
1101 size_t max_truncated_mac_size =
1102 PSA_ALG_MAC_TRUNCATION_MASK >> PSA_MAC_TRUNCATION_OFFSET;
1103
1104 /* Check that the length for a truncated MAC always fits in the algorithm
1105 * encoding. The shifted mask is the maximum truncated value. The
1106 * untruncated algorithm may be one byte larger. */
1107 TEST_ASSERT( PSA_MAC_MAX_SIZE <= 1 + max_truncated_mac_size );
1108}
1109/* END_CASE */
1110
1111/* BEGIN_CASE */
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001112void import( data_t *data, int type, int expected_status_arg )
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001113{
Gilles Peskine4747d192019-04-17 15:05:45 +02001114 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001115 psa_key_handle_t handle = 0;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001116 psa_status_t expected_status = expected_status_arg;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001117 psa_status_t status;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001118
Gilles Peskine8817f612018-12-18 00:18:46 +01001119 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001120
Gilles Peskine4747d192019-04-17 15:05:45 +02001121 psa_set_key_type( &attributes, type );
1122 status = psa_import_key( &attributes, &handle, data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001123 TEST_EQUAL( status, expected_status );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001124 if( status == PSA_SUCCESS )
Gilles Peskine8817f612018-12-18 00:18:46 +01001125 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001126
1127exit:
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001128 mbedtls_psa_crypto_free( );
1129}
1130/* END_CASE */
1131
1132/* BEGIN_CASE */
Gilles Peskinea4261682018-12-03 11:34:01 +01001133void import_twice( int alg_arg, int usage_arg,
1134 int type1_arg, data_t *data1,
1135 int expected_import1_status_arg,
1136 int type2_arg, data_t *data2,
1137 int expected_import2_status_arg )
1138{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001139 psa_key_handle_t handle = 0;
Gilles Peskinea4261682018-12-03 11:34:01 +01001140 psa_algorithm_t alg = alg_arg;
1141 psa_key_usage_t usage = usage_arg;
1142 psa_key_type_t type1 = type1_arg;
1143 psa_status_t expected_import1_status = expected_import1_status_arg;
1144 psa_key_type_t type2 = type2_arg;
1145 psa_status_t expected_import2_status = expected_import2_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00001146 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea4261682018-12-03 11:34:01 +01001147 psa_status_t status;
1148
Gilles Peskine8817f612018-12-18 00:18:46 +01001149 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001150
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001151 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001152 psa_key_policy_set_usage( &policy, usage, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001153 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea4261682018-12-03 11:34:01 +01001154
Gilles Peskine87a5e562019-04-17 12:28:25 +02001155 status = psa_import_key_to_handle( handle, type1, data1->x, data1->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001156 TEST_EQUAL( status, expected_import1_status );
Gilles Peskine87a5e562019-04-17 12:28:25 +02001157 status = psa_import_key_to_handle( handle, type2, data2->x, data2->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001158 TEST_EQUAL( status, expected_import2_status );
Gilles Peskinea4261682018-12-03 11:34:01 +01001159
1160 if( expected_import1_status == PSA_SUCCESS ||
1161 expected_import2_status == PSA_SUCCESS )
1162 {
Gilles Peskinec9516fb2019-02-05 20:32:06 +01001163 if( ! exercise_key( handle, usage, alg ) )
1164 goto exit;
Gilles Peskinea4261682018-12-03 11:34:01 +01001165 }
1166
1167exit:
1168 mbedtls_psa_crypto_free( );
1169}
1170/* END_CASE */
1171
1172/* BEGIN_CASE */
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001173void import_rsa_made_up( int bits_arg, int keypair, int expected_status_arg )
1174{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001175 psa_key_handle_t handle = 0;
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001176 size_t bits = bits_arg;
1177 psa_status_t expected_status = expected_status_arg;
1178 psa_status_t status;
1179 psa_key_type_t type =
1180 keypair ? PSA_KEY_TYPE_RSA_KEYPAIR : PSA_KEY_TYPE_RSA_PUBLIC_KEY;
1181 size_t buffer_size = /* Slight overapproximations */
1182 keypair ? bits * 9 / 16 + 80 : bits / 8 + 20;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001183 unsigned char *buffer = NULL;
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001184 unsigned char *p;
1185 int ret;
1186 size_t length;
1187
Gilles Peskine8817f612018-12-18 00:18:46 +01001188 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001189 ASSERT_ALLOC( buffer, buffer_size );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001190
1191 TEST_ASSERT( ( ret = construct_fake_rsa_key( buffer, buffer_size, &p,
1192 bits, keypair ) ) >= 0 );
1193 length = ret;
1194
1195 /* Try importing the key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001196 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02001197 status = psa_import_key_to_handle( handle, type, p, length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001198 TEST_EQUAL( status, expected_status );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001199 if( status == PSA_SUCCESS )
Gilles Peskine8817f612018-12-18 00:18:46 +01001200 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskine0b352bc2018-06-28 00:16:11 +02001201
1202exit:
1203 mbedtls_free( buffer );
1204 mbedtls_psa_crypto_free( );
1205}
1206/* END_CASE */
1207
1208/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03001209void import_export( data_t *data,
Moran Pekera964a8f2018-06-04 18:42:36 +03001210 int type_arg,
1211 int alg_arg,
1212 int usage_arg,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001213 int expected_bits,
1214 int export_size_delta,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001215 int expected_export_status_arg,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001216 int canonical_input )
1217{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001218 psa_key_handle_t handle = 0;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001219 psa_key_type_t type = type_arg;
Gilles Peskine4abf7412018-06-18 16:35:34 +02001220 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001221 psa_status_t expected_export_status = expected_export_status_arg;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001222 psa_status_t status;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001223 unsigned char *exported = NULL;
1224 unsigned char *reexported = NULL;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001225 size_t export_size;
Jaeden Amerof24c7f82018-06-27 17:20:43 +01001226 size_t exported_length = INVALID_EXPORT_LENGTH;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001227 size_t reexported_length;
1228 psa_key_type_t got_type;
1229 size_t got_bits;
Gilles Peskine4747d192019-04-17 15:05:45 +02001230 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001231
Moran Pekercb088e72018-07-17 17:36:59 +03001232 export_size = (ptrdiff_t) data->len + export_size_delta;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001233 ASSERT_ALLOC( exported, export_size );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001234 if( ! canonical_input )
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001235 ASSERT_ALLOC( reexported, export_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01001236 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001237
Gilles Peskine4747d192019-04-17 15:05:45 +02001238 psa_set_key_usage_flags( &attributes, usage_arg );
1239 psa_set_key_algorithm( &attributes, alg );
1240 psa_set_key_type( &attributes, type );
mohammad1603a97cb8c2018-03-28 03:46:26 -07001241
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001242 /* Import the key */
Gilles Peskine4747d192019-04-17 15:05:45 +02001243 PSA_ASSERT( psa_import_key( &attributes, &handle, data->x, data->len ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001244
1245 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01001246 PSA_ASSERT( psa_get_key_information( handle,
1247 &got_type,
1248 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001249 TEST_EQUAL( got_type, type );
1250 TEST_EQUAL( got_bits, (size_t) expected_bits );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001251
1252 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001253 status = psa_export_key( handle,
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001254 exported, export_size,
1255 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001256 TEST_EQUAL( status, expected_export_status );
Jaeden Amerof24c7f82018-06-27 17:20:43 +01001257
1258 /* The exported length must be set by psa_export_key() to a value between 0
1259 * and export_size. On errors, the exported length must be 0. */
1260 TEST_ASSERT( exported_length != INVALID_EXPORT_LENGTH );
1261 TEST_ASSERT( status == PSA_SUCCESS || exported_length == 0 );
1262 TEST_ASSERT( exported_length <= export_size );
1263
Gilles Peskinea7aa4422018-08-14 15:17:54 +02001264 TEST_ASSERT( mem_is_char( exported + exported_length, 0,
Gilles Peskine3f669c32018-06-21 09:21:51 +02001265 export_size - exported_length ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001266 if( status != PSA_SUCCESS )
Gilles Peskinee66ca3b2018-06-20 00:11:45 +02001267 {
Gilles Peskinefe11b722018-12-18 00:24:04 +01001268 TEST_EQUAL( exported_length, 0 );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001269 goto destroy;
Gilles Peskinee66ca3b2018-06-20 00:11:45 +02001270 }
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001271
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001272 if( ! exercise_export_key( handle, usage_arg ) )
Gilles Peskine8f609232018-08-11 01:24:55 +02001273 goto exit;
1274
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001275 if( canonical_input )
Gilles Peskinebd7dea92018-09-27 13:57:19 +02001276 ASSERT_COMPARE( data->x, data->len, exported, exported_length );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001277 else
1278 {
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001279 psa_key_handle_t handle2;
Gilles Peskine4747d192019-04-17 15:05:45 +02001280 PSA_ASSERT( psa_import_key( &attributes, &handle2,
1281 exported, exported_length ) );
Gilles Peskine8817f612018-12-18 00:18:46 +01001282 PSA_ASSERT( psa_export_key( handle2,
1283 reexported,
1284 export_size,
1285 &reexported_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02001286 ASSERT_COMPARE( exported, exported_length,
1287 reexported, reexported_length );
Gilles Peskine8817f612018-12-18 00:18:46 +01001288 PSA_ASSERT( psa_close_key( handle2 ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001289 }
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001290 TEST_ASSERT( exported_length <= PSA_KEY_EXPORT_MAX_SIZE( type, got_bits ) );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001291
1292destroy:
1293 /* Destroy the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001294 PSA_ASSERT( psa_destroy_key( handle ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01001295 TEST_EQUAL( psa_get_key_information( handle, NULL, NULL ),
1296 PSA_ERROR_INVALID_HANDLE );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001297
1298exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03001299 mbedtls_free( exported );
1300 mbedtls_free( reexported );
Gilles Peskine2f9c4dc2018-01-28 13:16:24 +01001301 mbedtls_psa_crypto_free( );
1302}
1303/* END_CASE */
Gilles Peskine20035e32018-02-03 22:44:14 +01001304
Moran Pekerf709f4a2018-06-06 17:26:04 +03001305/* BEGIN_CASE */
Moran Peker28a38e62018-11-07 16:18:24 +02001306void import_key_nonempty_slot( )
1307{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001308 psa_key_handle_t handle = 0;
Moran Peker28a38e62018-11-07 16:18:24 +02001309 psa_key_type_t type = PSA_KEY_TYPE_RAW_DATA;
1310 psa_status_t status;
1311 const uint8_t data[] = { 0x1, 0x2, 0x3, 0x4, 0x5 };
Gilles Peskine8817f612018-12-18 00:18:46 +01001312 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001313
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001314 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001315
Moran Peker28a38e62018-11-07 16:18:24 +02001316 /* Import the key */
Gilles Peskine87a5e562019-04-17 12:28:25 +02001317 PSA_ASSERT( psa_import_key_to_handle( handle, type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001318 data, sizeof( data ) ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001319
1320 /* Import the key again */
Gilles Peskine87a5e562019-04-17 12:28:25 +02001321 status = psa_import_key_to_handle( handle, type, data, sizeof( data ) );
David Saadab4ecc272019-02-14 13:48:10 +02001322 TEST_EQUAL( status, PSA_ERROR_ALREADY_EXISTS );
Moran Peker28a38e62018-11-07 16:18:24 +02001323
1324exit:
1325 mbedtls_psa_crypto_free( );
1326}
1327/* END_CASE */
1328
1329/* BEGIN_CASE */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001330void export_invalid_handle( int handle, int expected_export_status_arg )
Moran Peker28a38e62018-11-07 16:18:24 +02001331{
1332 psa_status_t status;
1333 unsigned char *exported = NULL;
1334 size_t export_size = 0;
1335 size_t exported_length = INVALID_EXPORT_LENGTH;
1336 psa_status_t expected_export_status = expected_export_status_arg;
1337
Gilles Peskine8817f612018-12-18 00:18:46 +01001338 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker28a38e62018-11-07 16:18:24 +02001339
1340 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001341 status = psa_export_key( (psa_key_handle_t) handle,
Moran Peker28a38e62018-11-07 16:18:24 +02001342 exported, export_size,
1343 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001344 TEST_EQUAL( status, expected_export_status );
Moran Peker28a38e62018-11-07 16:18:24 +02001345
1346exit:
1347 mbedtls_psa_crypto_free( );
1348}
1349/* END_CASE */
1350
1351/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001352void export_with_no_key_activity( )
1353{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001354 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001355 psa_algorithm_t alg = PSA_ALG_CTR;
1356 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001357 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Peker34550092018-11-07 16:19:34 +02001358 unsigned char *exported = NULL;
1359 size_t export_size = 0;
1360 size_t exported_length = INVALID_EXPORT_LENGTH;
1361
Gilles Peskine8817f612018-12-18 00:18:46 +01001362 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001363
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001364 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001365 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001366 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Peker34550092018-11-07 16:19:34 +02001367
1368 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001369 status = psa_export_key( handle,
Moran Peker34550092018-11-07 16:19:34 +02001370 exported, export_size,
1371 &exported_length );
David Saadab4ecc272019-02-14 13:48:10 +02001372 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Peker34550092018-11-07 16:19:34 +02001373
1374exit:
1375 mbedtls_psa_crypto_free( );
1376}
1377/* END_CASE */
1378
1379/* BEGIN_CASE */
Moran Pekerce500072018-11-07 16:20:07 +02001380void cipher_with_no_key_activity( )
1381{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001382 psa_key_handle_t handle = 0;
Moran Pekerce500072018-11-07 16:20:07 +02001383 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001384 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001385 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Moran Pekerce500072018-11-07 16:20:07 +02001386 int exercise_alg = PSA_ALG_CTR;
1387
Gilles Peskine8817f612018-12-18 00:18:46 +01001388 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerce500072018-11-07 16:20:07 +02001389
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001390 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekerce500072018-11-07 16:20:07 +02001391 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, exercise_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001392 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekerce500072018-11-07 16:20:07 +02001393
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001394 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
David Saadab4ecc272019-02-14 13:48:10 +02001395 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Pekerce500072018-11-07 16:20:07 +02001396
1397exit:
1398 psa_cipher_abort( &operation );
1399 mbedtls_psa_crypto_free( );
1400}
1401/* END_CASE */
1402
1403/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001404void export_after_import_failure( data_t *data, int type_arg,
1405 int expected_import_status_arg )
1406{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001407 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001408 psa_key_type_t type = type_arg;
1409 psa_status_t status;
1410 unsigned char *exported = NULL;
1411 size_t export_size = 0;
1412 psa_status_t expected_import_status = expected_import_status_arg;
1413 size_t exported_length = INVALID_EXPORT_LENGTH;
1414
Gilles Peskine8817f612018-12-18 00:18:46 +01001415 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001416
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001417 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001418
Moran Peker34550092018-11-07 16:19:34 +02001419 /* Import the key - expect failure */
Gilles Peskine87a5e562019-04-17 12:28:25 +02001420 status = psa_import_key_to_handle( handle, type,
Gilles Peskine0f915f12018-12-17 23:35:42 +01001421 data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001422 TEST_EQUAL( status, expected_import_status );
Moran Peker34550092018-11-07 16:19:34 +02001423
1424 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001425 status = psa_export_key( handle,
Moran Peker34550092018-11-07 16:19:34 +02001426 exported, export_size,
1427 &exported_length );
David Saadab4ecc272019-02-14 13:48:10 +02001428 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Peker34550092018-11-07 16:19:34 +02001429
1430exit:
1431 mbedtls_psa_crypto_free( );
1432}
1433/* END_CASE */
1434
1435/* BEGIN_CASE */
Moran Pekerce500072018-11-07 16:20:07 +02001436void cipher_after_import_failure( data_t *data, int type_arg,
1437 int expected_import_status_arg )
1438{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001439 psa_key_handle_t handle = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001440 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Moran Pekerce500072018-11-07 16:20:07 +02001441 psa_key_type_t type = type_arg;
1442 psa_status_t status;
1443 psa_status_t expected_import_status = expected_import_status_arg;
1444 int exercise_alg = PSA_ALG_CTR;
1445
Gilles Peskine8817f612018-12-18 00:18:46 +01001446 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerce500072018-11-07 16:20:07 +02001447
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001448 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001449
Moran Pekerce500072018-11-07 16:20:07 +02001450 /* Import the key - expect failure */
Gilles Peskine87a5e562019-04-17 12:28:25 +02001451 status = psa_import_key_to_handle( handle, type,
Gilles Peskine0f915f12018-12-17 23:35:42 +01001452 data->x, data->len );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001453 TEST_EQUAL( status, expected_import_status );
Moran Pekerce500072018-11-07 16:20:07 +02001454
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001455 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
David Saadab4ecc272019-02-14 13:48:10 +02001456 TEST_EQUAL( status, PSA_ERROR_DOES_NOT_EXIST );
Moran Pekerce500072018-11-07 16:20:07 +02001457
1458exit:
1459 psa_cipher_abort( &operation );
1460 mbedtls_psa_crypto_free( );
1461}
1462/* END_CASE */
1463
1464/* BEGIN_CASE */
Moran Peker34550092018-11-07 16:19:34 +02001465void export_after_destroy_key( data_t *data, int type_arg )
1466{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001467 psa_key_handle_t handle = 0;
Moran Peker34550092018-11-07 16:19:34 +02001468 psa_key_type_t type = type_arg;
1469 psa_status_t status;
Jaeden Amero70261c52019-01-04 11:47:20 +00001470 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Peker34550092018-11-07 16:19:34 +02001471 psa_algorithm_t alg = PSA_ALG_CTR;
1472 unsigned char *exported = NULL;
1473 size_t export_size = 0;
1474 size_t exported_length = INVALID_EXPORT_LENGTH;
1475
Gilles Peskine8817f612018-12-18 00:18:46 +01001476 PSA_ASSERT( psa_crypto_init( ) );
Moran Peker34550092018-11-07 16:19:34 +02001477
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001478 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001479 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001480 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Peker34550092018-11-07 16:19:34 +02001481 export_size = (ptrdiff_t) data->len;
1482 ASSERT_ALLOC( exported, export_size );
1483
1484 /* Import the key */
Gilles Peskine87a5e562019-04-17 12:28:25 +02001485 PSA_ASSERT( psa_import_key_to_handle( handle, type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001486 data->x, data->len ) );
Moran Peker34550092018-11-07 16:19:34 +02001487
Gilles Peskine8817f612018-12-18 00:18:46 +01001488 PSA_ASSERT( psa_export_key( handle, exported, export_size,
1489 &exported_length ) );
Moran Peker34550092018-11-07 16:19:34 +02001490
1491 /* Destroy the key */
Gilles Peskine8817f612018-12-18 00:18:46 +01001492 PSA_ASSERT( psa_destroy_key( handle ) );
Moran Peker34550092018-11-07 16:19:34 +02001493
1494 /* Export the key */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001495 status = psa_export_key( handle, exported, export_size,
Moran Peker34550092018-11-07 16:19:34 +02001496 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001497 TEST_EQUAL( status, PSA_ERROR_INVALID_HANDLE );
Moran Peker34550092018-11-07 16:19:34 +02001498
1499exit:
1500 mbedtls_free( exported );
1501 mbedtls_psa_crypto_free( );
1502}
1503/* END_CASE */
1504
1505/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03001506void import_export_public_key( data_t *data,
Gilles Peskine2d277862018-06-18 15:41:12 +02001507 int type_arg,
1508 int alg_arg,
Gilles Peskine49c25912018-10-29 15:15:31 +01001509 int export_size_delta,
1510 int expected_export_status_arg,
1511 data_t *expected_public_key )
Moran Pekerf709f4a2018-06-06 17:26:04 +03001512{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001513 psa_key_handle_t handle = 0;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001514 psa_key_type_t type = type_arg;
Gilles Peskine4abf7412018-06-18 16:35:34 +02001515 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02001516 psa_status_t expected_export_status = expected_export_status_arg;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001517 psa_status_t status;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001518 unsigned char *exported = NULL;
Gilles Peskine49c25912018-10-29 15:15:31 +01001519 size_t export_size = expected_public_key->len + export_size_delta;
Jaeden Amero2a671e92018-06-27 17:47:40 +01001520 size_t exported_length = INVALID_EXPORT_LENGTH;
Gilles Peskine4747d192019-04-17 15:05:45 +02001521 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Moran Pekerf709f4a2018-06-06 17:26:04 +03001522
Gilles Peskine8817f612018-12-18 00:18:46 +01001523 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001524
Gilles Peskine4747d192019-04-17 15:05:45 +02001525 psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_EXPORT );
1526 psa_set_key_algorithm( &attributes, alg );
1527 psa_set_key_type( &attributes, type );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001528
1529 /* Import the key */
Gilles Peskine4747d192019-04-17 15:05:45 +02001530 PSA_ASSERT( psa_import_key( &attributes, &handle, data->x, data->len ) );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001531
Gilles Peskine49c25912018-10-29 15:15:31 +01001532 /* Export the public key */
1533 ASSERT_ALLOC( exported, export_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001534 status = psa_export_public_key( handle,
Gilles Peskine2d277862018-06-18 15:41:12 +02001535 exported, export_size,
1536 &exported_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001537 TEST_EQUAL( status, expected_export_status );
Gilles Peskine49c25912018-10-29 15:15:31 +01001538 if( status == PSA_SUCCESS )
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001539 {
1540 psa_key_type_t public_type = PSA_KEY_TYPE_PUBLIC_KEY_OF_KEYPAIR( type );
1541 size_t bits;
Gilles Peskine8817f612018-12-18 00:18:46 +01001542 PSA_ASSERT( psa_get_key_information( handle, NULL, &bits ) );
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001543 TEST_ASSERT( expected_public_key->len <=
1544 PSA_KEY_EXPORT_MAX_SIZE( public_type, bits ) );
Gilles Peskine49c25912018-10-29 15:15:31 +01001545 ASSERT_COMPARE( expected_public_key->x, expected_public_key->len,
1546 exported, exported_length );
Gilles Peskined8b7d4f2018-10-29 15:18:41 +01001547 }
Moran Pekerf709f4a2018-06-06 17:26:04 +03001548
1549exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03001550 mbedtls_free( exported );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001551 psa_destroy_key( handle );
Moran Pekerf709f4a2018-06-06 17:26:04 +03001552 mbedtls_psa_crypto_free( );
1553}
1554/* END_CASE */
1555
Gilles Peskine20035e32018-02-03 22:44:14 +01001556/* BEGIN_CASE */
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001557void import_and_exercise_key( data_t *data,
1558 int type_arg,
1559 int bits_arg,
1560 int alg_arg )
1561{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001562 psa_key_handle_t handle = 0;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001563 psa_key_type_t type = type_arg;
1564 size_t bits = bits_arg;
1565 psa_algorithm_t alg = alg_arg;
Gilles Peskine10df3412018-10-25 22:35:43 +02001566 psa_key_usage_t usage = usage_to_exercise( type, alg );
Gilles Peskine4747d192019-04-17 15:05:45 +02001567 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001568 psa_key_type_t got_type;
1569 size_t got_bits;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001570
Gilles Peskine8817f612018-12-18 00:18:46 +01001571 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001572
Gilles Peskine4747d192019-04-17 15:05:45 +02001573 psa_set_key_usage_flags( &attributes, usage );
1574 psa_set_key_algorithm( &attributes, alg );
1575 psa_set_key_type( &attributes, type );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001576
1577 /* Import the key */
Gilles Peskine4747d192019-04-17 15:05:45 +02001578 PSA_ASSERT( psa_import_key( &attributes, &handle, data->x, data->len ) );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001579
1580 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01001581 PSA_ASSERT( psa_get_key_information( handle,
1582 &got_type,
1583 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01001584 TEST_EQUAL( got_type, type );
1585 TEST_EQUAL( got_bits, bits );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001586
1587 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001588 if( ! exercise_key( handle, usage, alg ) )
Gilles Peskine02b75072018-07-01 22:31:34 +02001589 goto exit;
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001590
1591exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001592 psa_destroy_key( handle );
Gilles Peskinea680c7a2018-06-26 16:12:43 +02001593 mbedtls_psa_crypto_free( );
1594}
1595/* END_CASE */
1596
1597/* BEGIN_CASE */
Gilles Peskined5b33222018-06-18 22:20:03 +02001598void key_policy( int usage_arg, int alg_arg )
1599{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001600 psa_key_handle_t handle = 0;
Gilles Peskined5b33222018-06-18 22:20:03 +02001601 psa_algorithm_t alg = alg_arg;
1602 psa_key_usage_t usage = usage_arg;
1603 psa_key_type_t key_type = PSA_KEY_TYPE_AES;
1604 unsigned char key[32] = {0};
Jaeden Amero70261c52019-01-04 11:47:20 +00001605 psa_key_policy_t policy_set = PSA_KEY_POLICY_INIT;
1606 psa_key_policy_t policy_get = PSA_KEY_POLICY_INIT;
Gilles Peskined5b33222018-06-18 22:20:03 +02001607
1608 memset( key, 0x2a, sizeof( key ) );
1609
Gilles Peskine8817f612018-12-18 00:18:46 +01001610 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001611
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001612 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001613 psa_key_policy_set_usage( &policy_set, usage, alg );
1614
Gilles Peskinefe11b722018-12-18 00:24:04 +01001615 TEST_EQUAL( psa_key_policy_get_usage( &policy_set ), usage );
1616 TEST_EQUAL( psa_key_policy_get_algorithm( &policy_set ), alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001617 PSA_ASSERT( psa_set_key_policy( handle, &policy_set ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001618
Gilles Peskine87a5e562019-04-17 12:28:25 +02001619 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001620 key, sizeof( key ) ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001621
Gilles Peskine8817f612018-12-18 00:18:46 +01001622 PSA_ASSERT( psa_get_key_policy( handle, &policy_get ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001623
Gilles Peskinefe11b722018-12-18 00:24:04 +01001624 TEST_EQUAL( policy_get.usage, policy_set.usage );
1625 TEST_EQUAL( policy_get.alg, policy_set.alg );
Gilles Peskined5b33222018-06-18 22:20:03 +02001626
1627exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001628 psa_destroy_key( handle );
Gilles Peskined5b33222018-06-18 22:20:03 +02001629 mbedtls_psa_crypto_free( );
1630}
1631/* END_CASE */
1632
1633/* BEGIN_CASE */
Jaeden Amero70261c52019-01-04 11:47:20 +00001634void key_policy_init( )
1635{
1636 /* Test each valid way of initializing the object, except for `= {0}`, as
1637 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
1638 * though it's OK by the C standard. We could test for this, but we'd need
1639 * to supress the Clang warning for the test. */
1640 psa_key_policy_t func = psa_key_policy_init( );
1641 psa_key_policy_t init = PSA_KEY_POLICY_INIT;
1642 psa_key_policy_t zero;
1643
1644 memset( &zero, 0, sizeof( zero ) );
1645
Jaeden Amero5229bbb2019-02-07 16:33:37 +00001646 /* A default key policy should not permit any usage. */
1647 TEST_EQUAL( psa_key_policy_get_usage( &func ), 0 );
1648 TEST_EQUAL( psa_key_policy_get_usage( &init ), 0 );
1649 TEST_EQUAL( psa_key_policy_get_usage( &zero ), 0 );
1650
1651 /* A default key policy should not permit any algorithm. */
1652 TEST_EQUAL( psa_key_policy_get_algorithm( &func ), 0 );
1653 TEST_EQUAL( psa_key_policy_get_algorithm( &init ), 0 );
1654 TEST_EQUAL( psa_key_policy_get_algorithm( &zero ), 0 );
Jaeden Amero70261c52019-01-04 11:47:20 +00001655}
1656/* END_CASE */
1657
1658/* BEGIN_CASE */
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001659void mac_key_policy( int policy_usage,
1660 int policy_alg,
1661 int key_type,
1662 data_t *key_data,
1663 int exercise_alg )
Gilles Peskined5b33222018-06-18 22:20:03 +02001664{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001665 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001666 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero769ce272019-01-04 11:48:03 +00001667 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001668 psa_status_t status;
1669 unsigned char mac[PSA_MAC_MAX_SIZE];
Gilles Peskined5b33222018-06-18 22:20:03 +02001670
Gilles Peskine8817f612018-12-18 00:18:46 +01001671 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001672
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001673 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001674 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001675 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001676
Gilles Peskine87a5e562019-04-17 12:28:25 +02001677 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001678 key_data->x, key_data->len ) );
Gilles Peskined5b33222018-06-18 22:20:03 +02001679
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001680 status = psa_mac_sign_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001681 if( policy_alg == exercise_alg &&
1682 ( policy_usage & PSA_KEY_USAGE_SIGN ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001683 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001684 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001685 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001686 psa_mac_abort( &operation );
Gilles Peskined5b33222018-06-18 22:20:03 +02001687
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001688 memset( mac, 0, sizeof( mac ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001689 status = psa_mac_verify_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001690 if( policy_alg == exercise_alg &&
1691 ( policy_usage & PSA_KEY_USAGE_VERIFY ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001692 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001693 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001694 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001695
1696exit:
1697 psa_mac_abort( &operation );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001698 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001699 mbedtls_psa_crypto_free( );
1700}
1701/* END_CASE */
1702
1703/* BEGIN_CASE */
1704void cipher_key_policy( int policy_usage,
1705 int policy_alg,
1706 int key_type,
1707 data_t *key_data,
1708 int exercise_alg )
1709{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001710 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001711 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Jaeden Amero5bae2272019-01-04 11:48:27 +00001712 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001713 psa_status_t status;
1714
Gilles Peskine8817f612018-12-18 00:18:46 +01001715 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001716
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001717 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001718 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001719 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001720
Gilles Peskine87a5e562019-04-17 12:28:25 +02001721 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001722 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001723
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001724 status = psa_cipher_encrypt_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001725 if( policy_alg == exercise_alg &&
1726 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001727 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001728 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001729 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001730 psa_cipher_abort( &operation );
1731
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001732 status = psa_cipher_decrypt_setup( &operation, handle, exercise_alg );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001733 if( policy_alg == exercise_alg &&
1734 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001735 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001736 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001737 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001738
1739exit:
1740 psa_cipher_abort( &operation );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001741 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001742 mbedtls_psa_crypto_free( );
1743}
1744/* END_CASE */
1745
1746/* BEGIN_CASE */
1747void aead_key_policy( int policy_usage,
1748 int policy_alg,
1749 int key_type,
1750 data_t *key_data,
1751 int nonce_length_arg,
1752 int tag_length_arg,
1753 int exercise_alg )
1754{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001755 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001756 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001757 psa_status_t status;
1758 unsigned char nonce[16] = {0};
1759 size_t nonce_length = nonce_length_arg;
1760 unsigned char tag[16];
1761 size_t tag_length = tag_length_arg;
1762 size_t output_length;
1763
1764 TEST_ASSERT( nonce_length <= sizeof( nonce ) );
1765 TEST_ASSERT( tag_length <= sizeof( tag ) );
1766
Gilles Peskine8817f612018-12-18 00:18:46 +01001767 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001768
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001769 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001770 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001771 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001772
Gilles Peskine87a5e562019-04-17 12:28:25 +02001773 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001774 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001775
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001776 status = psa_aead_encrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001777 nonce, nonce_length,
1778 NULL, 0,
1779 NULL, 0,
1780 tag, tag_length,
1781 &output_length );
1782 if( policy_alg == exercise_alg &&
1783 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001784 PSA_ASSERT( status );
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
1788 memset( tag, 0, sizeof( tag ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001789 status = psa_aead_decrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001790 nonce, nonce_length,
1791 NULL, 0,
1792 tag, tag_length,
1793 NULL, 0,
1794 &output_length );
1795 if( policy_alg == exercise_alg &&
1796 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001797 TEST_EQUAL( status, PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001798 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001799 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001800
1801exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001802 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001803 mbedtls_psa_crypto_free( );
1804}
1805/* END_CASE */
1806
1807/* BEGIN_CASE */
1808void asymmetric_encryption_key_policy( int policy_usage,
1809 int policy_alg,
1810 int key_type,
1811 data_t *key_data,
1812 int exercise_alg )
1813{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001814 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001815 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001816 psa_status_t status;
1817 size_t key_bits;
1818 size_t buffer_length;
1819 unsigned char *buffer = NULL;
1820 size_t output_length;
1821
Gilles Peskine8817f612018-12-18 00:18:46 +01001822 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001823
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001824 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001825 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001826 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001827
Gilles Peskine87a5e562019-04-17 12:28:25 +02001828 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001829 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001830
Gilles Peskine8817f612018-12-18 00:18:46 +01001831 PSA_ASSERT( psa_get_key_information( handle,
1832 NULL,
1833 &key_bits ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001834 buffer_length = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits,
1835 exercise_alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02001836 ASSERT_ALLOC( buffer, buffer_length );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001837
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001838 status = psa_asymmetric_encrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001839 NULL, 0,
1840 NULL, 0,
1841 buffer, buffer_length,
1842 &output_length );
1843 if( policy_alg == exercise_alg &&
1844 ( policy_usage & PSA_KEY_USAGE_ENCRYPT ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001845 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001846 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001847 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001848
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02001849 if( buffer_length != 0 )
1850 memset( buffer, 0, buffer_length );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001851 status = psa_asymmetric_decrypt( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001852 buffer, buffer_length,
1853 NULL, 0,
1854 buffer, buffer_length,
1855 &output_length );
1856 if( policy_alg == exercise_alg &&
1857 ( policy_usage & PSA_KEY_USAGE_DECRYPT ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001858 TEST_EQUAL( status, PSA_ERROR_INVALID_PADDING );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001859 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001860 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001861
1862exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001863 psa_destroy_key( handle );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001864 mbedtls_psa_crypto_free( );
1865 mbedtls_free( buffer );
1866}
1867/* END_CASE */
1868
1869/* BEGIN_CASE */
1870void asymmetric_signature_key_policy( int policy_usage,
1871 int policy_alg,
1872 int key_type,
1873 data_t *key_data,
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001874 int exercise_alg,
1875 int payload_length_arg )
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001876{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001877 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001878 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001879 psa_status_t status;
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001880 unsigned char payload[PSA_HASH_MAX_SIZE] = {1};
1881 /* If `payload_length_arg > 0`, `exercise_alg` is supposed to be
1882 * compatible with the policy and `payload_length_arg` is supposed to be
1883 * a valid input length to sign. If `payload_length_arg <= 0`,
1884 * `exercise_alg` is supposed to be forbidden by the policy. */
1885 int compatible_alg = payload_length_arg > 0;
1886 size_t payload_length = compatible_alg ? payload_length_arg : 0;
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001887 unsigned char signature[PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE] = {0};
1888 size_t signature_length;
1889
Gilles Peskine8817f612018-12-18 00:18:46 +01001890 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001891
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001892 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001893 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001894 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001895
Gilles Peskine87a5e562019-04-17 12:28:25 +02001896 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001897 key_data->x, key_data->len ) );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001898
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001899 status = psa_asymmetric_sign( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001900 payload, payload_length,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001901 signature, sizeof( signature ),
1902 &signature_length );
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001903 if( compatible_alg && ( policy_usage & PSA_KEY_USAGE_SIGN ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001904 PSA_ASSERT( status );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001905 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001906 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001907
1908 memset( signature, 0, sizeof( signature ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001909 status = psa_asymmetric_verify( handle, exercise_alg,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001910 payload, payload_length,
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001911 signature, sizeof( signature ) );
Gilles Peskine30f77cd2019-01-14 16:06:39 +01001912 if( compatible_alg && ( policy_usage & PSA_KEY_USAGE_VERIFY ) != 0 )
Gilles Peskinefe11b722018-12-18 00:24:04 +01001913 TEST_EQUAL( status, PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine76f5c7b2018-07-06 16:53:09 +02001914 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001915 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskined5b33222018-06-18 22:20:03 +02001916
1917exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001918 psa_destroy_key( handle );
Gilles Peskined5b33222018-06-18 22:20:03 +02001919 mbedtls_psa_crypto_free( );
1920}
1921/* END_CASE */
1922
1923/* BEGIN_CASE */
Gilles Peskineea0fb492018-07-12 17:17:20 +02001924void derive_key_policy( int policy_usage,
1925 int policy_alg,
1926 int key_type,
1927 data_t *key_data,
1928 int exercise_alg )
1929{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001930 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001931 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskineea0fb492018-07-12 17:17:20 +02001932 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
1933 psa_status_t status;
1934
Gilles Peskine8817f612018-12-18 00:18:46 +01001935 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001936
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001937 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001938 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001939 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001940
Gilles Peskine87a5e562019-04-17 12:28:25 +02001941 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001942 key_data->x, key_data->len ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001943
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001944 status = psa_key_derivation( &generator, handle,
Gilles Peskineea0fb492018-07-12 17:17:20 +02001945 exercise_alg,
1946 NULL, 0,
1947 NULL, 0,
1948 1 );
1949 if( policy_alg == exercise_alg &&
1950 ( policy_usage & PSA_KEY_USAGE_DERIVE ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001951 PSA_ASSERT( status );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001952 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001953 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001954
1955exit:
1956 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001957 psa_destroy_key( handle );
Gilles Peskineea0fb492018-07-12 17:17:20 +02001958 mbedtls_psa_crypto_free( );
1959}
1960/* END_CASE */
1961
1962/* BEGIN_CASE */
Gilles Peskine01d718c2018-09-18 12:01:02 +02001963void agreement_key_policy( int policy_usage,
1964 int policy_alg,
1965 int key_type_arg,
1966 data_t *key_data,
1967 int exercise_alg )
1968{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001969 psa_key_handle_t handle = 0;
Jaeden Amero70261c52019-01-04 11:47:20 +00001970 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine01d718c2018-09-18 12:01:02 +02001971 psa_key_type_t key_type = key_type_arg;
Gilles Peskine01d718c2018-09-18 12:01:02 +02001972 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
1973 psa_status_t status;
1974
Gilles Peskine8817f612018-12-18 00:18:46 +01001975 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001976
Gilles Peskined40c1fb2019-01-19 12:20:52 +01001977 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001978 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01001979 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001980
Gilles Peskine87a5e562019-04-17 12:28:25 +02001981 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01001982 key_data->x, key_data->len ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001983
Gilles Peskine969c5d62019-01-16 15:53:06 +01001984 PSA_ASSERT( psa_key_derivation_setup( &generator, exercise_alg ) );
1985 status = key_agreement_with_self( &generator, handle );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001986
Gilles Peskine01d718c2018-09-18 12:01:02 +02001987 if( policy_alg == exercise_alg &&
1988 ( policy_usage & PSA_KEY_USAGE_DERIVE ) != 0 )
Gilles Peskine8817f612018-12-18 00:18:46 +01001989 PSA_ASSERT( status );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001990 else
Gilles Peskinefe11b722018-12-18 00:24:04 +01001991 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001992
1993exit:
1994 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01001995 psa_destroy_key( handle );
Gilles Peskine01d718c2018-09-18 12:01:02 +02001996 mbedtls_psa_crypto_free( );
1997}
1998/* END_CASE */
1999
2000/* BEGIN_CASE */
Gilles Peskine04ee2d22019-04-11 21:25:46 +02002001void raw_agreement_key_policy( int policy_usage,
2002 int policy_alg,
2003 int key_type_arg,
2004 data_t *key_data,
2005 int exercise_alg )
2006{
2007 psa_key_handle_t handle = 0;
2008 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
2009 psa_key_type_t key_type = key_type_arg;
2010 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
2011 psa_status_t status;
2012
2013 PSA_ASSERT( psa_crypto_init( ) );
2014
2015 PSA_ASSERT( psa_allocate_key( &handle ) );
2016 psa_key_policy_set_usage( &policy, policy_usage, policy_alg );
2017 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
2018
Gilles Peskine87a5e562019-04-17 12:28:25 +02002019 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine04ee2d22019-04-11 21:25:46 +02002020 key_data->x, key_data->len ) );
2021
2022 status = raw_key_agreement_with_self( exercise_alg, handle );
2023
2024 if( policy_alg == exercise_alg &&
2025 ( policy_usage & PSA_KEY_USAGE_DERIVE ) != 0 )
2026 PSA_ASSERT( status );
2027 else
2028 TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
2029
2030exit:
2031 psa_generator_abort( &generator );
2032 psa_destroy_key( handle );
2033 mbedtls_psa_crypto_free( );
2034}
2035/* END_CASE */
2036
2037/* BEGIN_CASE */
Gilles Peskine57ab7212019-01-28 13:03:09 +01002038void copy_key_policy( int source_usage_arg, int source_alg_arg,
2039 int type_arg, data_t *material,
2040 int target_usage_arg, int target_alg_arg,
2041 int constraint_usage_arg, int constraint_alg_arg,
2042 int expected_usage_arg, int expected_alg_arg )
2043{
2044 psa_key_usage_t source_usage = source_usage_arg;
2045 psa_algorithm_t source_alg = source_alg_arg;
2046 psa_key_handle_t source_handle = 0;
2047 psa_key_policy_t source_policy = PSA_KEY_POLICY_INIT;
2048 psa_key_type_t source_type = type_arg;
2049 size_t source_bits;
2050 psa_key_usage_t target_usage = target_usage_arg;
2051 psa_algorithm_t target_alg = target_alg_arg;
2052 psa_key_handle_t target_handle = 0;
2053 psa_key_policy_t target_policy = PSA_KEY_POLICY_INIT;
2054 psa_key_type_t target_type;
2055 size_t target_bits;
2056 psa_key_usage_t constraint_usage = constraint_usage_arg;
2057 psa_algorithm_t constraint_alg = constraint_alg_arg;
2058 psa_key_policy_t constraint = PSA_KEY_POLICY_INIT;
2059 psa_key_policy_t *p_constraint = NULL;
2060 psa_key_usage_t expected_usage = expected_usage_arg;
2061 psa_algorithm_t expected_alg = expected_alg_arg;
2062 uint8_t *export_buffer = NULL;
2063
2064 if( constraint_usage_arg != -1 )
2065 {
2066 p_constraint = &constraint;
2067 psa_key_policy_set_usage( p_constraint,
2068 constraint_usage, constraint_alg );
2069 }
2070
2071 PSA_ASSERT( psa_crypto_init( ) );
2072
2073 /* Populate the source slot. */
2074 PSA_ASSERT( psa_allocate_key( &source_handle ) );
2075 psa_key_policy_set_usage( &source_policy, source_usage, source_alg );
2076 PSA_ASSERT( psa_set_key_policy( source_handle, &source_policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02002077 PSA_ASSERT( psa_import_key_to_handle( source_handle, source_type,
Gilles Peskine57ab7212019-01-28 13:03:09 +01002078 material->x, material->len ) );
2079 PSA_ASSERT( psa_get_key_information( source_handle, NULL, &source_bits ) );
2080
2081 /* Prepare the target slot. */
2082 PSA_ASSERT( psa_allocate_key( &target_handle ) );
2083 psa_key_policy_set_usage( &target_policy, target_usage, target_alg );
2084 PSA_ASSERT( psa_set_key_policy( target_handle, &target_policy ) );
2085 target_policy = psa_key_policy_init();
2086
2087 /* Copy the key. */
Gilles Peskine87a5e562019-04-17 12:28:25 +02002088 PSA_ASSERT( psa_copy_key_to_handle( source_handle, target_handle, p_constraint ) );
Gilles Peskine57ab7212019-01-28 13:03:09 +01002089
2090 /* Destroy the source to ensure that this doesn't affect the target. */
2091 PSA_ASSERT( psa_destroy_key( source_handle ) );
2092
2093 /* Test that the target slot has the expected content and policy. */
2094 PSA_ASSERT( psa_get_key_information( target_handle,
2095 &target_type, &target_bits ) );
2096 TEST_EQUAL( source_type, target_type );
2097 TEST_EQUAL( source_bits, target_bits );
2098 PSA_ASSERT( psa_get_key_policy( target_handle, &target_policy ) );
2099 TEST_EQUAL( expected_usage, psa_key_policy_get_usage( &target_policy ) );
2100 TEST_EQUAL( expected_alg, psa_key_policy_get_algorithm( &target_policy ) );
2101 if( expected_usage & PSA_KEY_USAGE_EXPORT )
2102 {
2103 size_t length;
2104 ASSERT_ALLOC( export_buffer, material->len );
2105 PSA_ASSERT( psa_export_key( target_handle, export_buffer,
2106 material->len, &length ) );
2107 ASSERT_COMPARE( material->x, material->len,
2108 export_buffer, length );
2109 }
2110 if( ! exercise_key( target_handle, expected_usage, expected_alg ) )
2111 goto exit;
2112
2113 PSA_ASSERT( psa_close_key( target_handle ) );
2114
2115exit:
2116 mbedtls_psa_crypto_free( );
2117 mbedtls_free( export_buffer );
2118}
2119/* END_CASE */
2120
2121/* BEGIN_CASE */
2122void copy_fail( int source_usage_arg, int source_alg_arg,
2123 int type_arg, data_t *material,
2124 int target_usage_arg, int target_alg_arg,
2125 int constraint_usage_arg, int constraint_alg_arg,
2126 int expected_status_arg )
2127{
2128 /* Test copy failure into an empty slot. There is a test for copy failure
2129 * into an occupied slot in
2130 * test_suite_psa_crypto_slot_management.function. */
2131
2132 psa_key_usage_t source_usage = source_usage_arg;
2133 psa_algorithm_t source_alg = source_alg_arg;
2134 psa_key_handle_t source_handle = 0;
2135 psa_key_policy_t source_policy = PSA_KEY_POLICY_INIT;
2136 psa_key_type_t source_type = type_arg;
2137 size_t source_bits;
2138 psa_key_usage_t target_usage = target_usage_arg;
2139 psa_algorithm_t target_alg = target_alg_arg;
2140 psa_key_handle_t target_handle = 0;
2141 psa_key_policy_t target_policy = PSA_KEY_POLICY_INIT;
2142 psa_key_type_t target_type;
2143 size_t target_bits;
2144 psa_key_usage_t constraint_usage = constraint_usage_arg;
2145 psa_algorithm_t constraint_alg = constraint_alg_arg;
2146 psa_key_policy_t constraint = PSA_KEY_POLICY_INIT;
2147 psa_key_policy_t *p_constraint = NULL;
2148 psa_status_t expected_status = expected_status_arg;
2149
2150 if( constraint_usage_arg != -1 )
2151 {
2152 p_constraint = &constraint;
2153 psa_key_policy_set_usage( p_constraint,
2154 constraint_usage, constraint_alg );
2155 }
2156
2157 PSA_ASSERT( psa_crypto_init( ) );
2158
2159 /* Populate the source slot. */
2160 PSA_ASSERT( psa_allocate_key( &source_handle ) );
2161 psa_key_policy_set_usage( &source_policy, source_usage, source_alg );
2162 PSA_ASSERT( psa_set_key_policy( source_handle, &source_policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02002163 PSA_ASSERT( psa_import_key_to_handle( source_handle, source_type,
Gilles Peskine57ab7212019-01-28 13:03:09 +01002164 material->x, material->len ) );
2165 PSA_ASSERT( psa_get_key_information( source_handle, NULL, &source_bits ) );
2166
2167 /* Prepare the target slot. */
2168 PSA_ASSERT( psa_allocate_key( &target_handle ) );
2169 psa_key_policy_set_usage( &target_policy, target_usage, target_alg );
2170 PSA_ASSERT( psa_set_key_policy( target_handle, &target_policy ) );
2171 target_policy = psa_key_policy_init();
2172
2173 /* Copy the key. */
Gilles Peskine87a5e562019-04-17 12:28:25 +02002174 TEST_EQUAL( psa_copy_key_to_handle( source_handle, target_handle, p_constraint ),
Gilles Peskine57ab7212019-01-28 13:03:09 +01002175 expected_status );
2176
2177 /* Test that the target slot is unaffected. */
2178 TEST_EQUAL( psa_get_key_information( target_handle,
2179 &target_type, &target_bits ),
David Saadab4ecc272019-02-14 13:48:10 +02002180 PSA_ERROR_DOES_NOT_EXIST );
Gilles Peskine57ab7212019-01-28 13:03:09 +01002181 PSA_ASSERT( psa_get_key_policy( target_handle, &target_policy ) );
2182 TEST_EQUAL( target_usage, psa_key_policy_get_usage( &target_policy ) );
2183 TEST_EQUAL( target_alg, psa_key_policy_get_algorithm( &target_policy ) );
2184
2185exit:
2186 mbedtls_psa_crypto_free( );
2187}
2188/* END_CASE */
2189
2190/* BEGIN_CASE */
Jaeden Amero6a25b412019-01-04 11:47:44 +00002191void hash_operation_init( )
2192{
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002193 const uint8_t input[1] = { 0 };
Jaeden Amero6a25b412019-01-04 11:47:44 +00002194 /* Test each valid way of initializing the object, except for `= {0}`, as
2195 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2196 * though it's OK by the C standard. We could test for this, but we'd need
2197 * to supress the Clang warning for the test. */
2198 psa_hash_operation_t func = psa_hash_operation_init( );
2199 psa_hash_operation_t init = PSA_HASH_OPERATION_INIT;
2200 psa_hash_operation_t zero;
2201
2202 memset( &zero, 0, sizeof( zero ) );
2203
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002204 /* A freshly-initialized hash operation should not be usable. */
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002205 TEST_EQUAL( psa_hash_update( &func, input, sizeof( input ) ),
2206 PSA_ERROR_BAD_STATE );
2207 TEST_EQUAL( psa_hash_update( &init, input, sizeof( input ) ),
2208 PSA_ERROR_BAD_STATE );
2209 TEST_EQUAL( psa_hash_update( &zero, input, sizeof( input ) ),
2210 PSA_ERROR_BAD_STATE );
2211
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002212 /* A default hash operation should be abortable without error. */
2213 PSA_ASSERT( psa_hash_abort( &func ) );
2214 PSA_ASSERT( psa_hash_abort( &init ) );
2215 PSA_ASSERT( psa_hash_abort( &zero ) );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002216}
2217/* END_CASE */
2218
2219/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002220void hash_setup( int alg_arg,
2221 int expected_status_arg )
2222{
2223 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002224 psa_status_t expected_status = expected_status_arg;
Jaeden Amero6a25b412019-01-04 11:47:44 +00002225 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002226 psa_status_t status;
2227
Gilles Peskine8817f612018-12-18 00:18:46 +01002228 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002229
Gilles Peskineda8191d1c2018-07-08 19:46:38 +02002230 status = psa_hash_setup( &operation, alg );
Gilles Peskinefe11b722018-12-18 00:24:04 +01002231 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002232
Gilles Peskine9e0a4a52019-02-25 22:11:18 +01002233 /* Whether setup succeeded or failed, abort must succeed. */
2234 PSA_ASSERT( psa_hash_abort( &operation ) );
2235
2236 /* If setup failed, reproduce the failure, so as to
2237 * test the resulting state of the operation object. */
2238 if( status != PSA_SUCCESS )
2239 TEST_EQUAL( psa_hash_setup( &operation, alg ), status );
2240
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002241 /* Now the operation object should be reusable. */
2242#if defined(KNOWN_SUPPORTED_HASH_ALG)
2243 PSA_ASSERT( psa_hash_setup( &operation, KNOWN_SUPPORTED_HASH_ALG ) );
2244 PSA_ASSERT( psa_hash_abort( &operation ) );
2245#endif
2246
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002247exit:
2248 mbedtls_psa_crypto_free( );
2249}
2250/* END_CASE */
2251
2252/* BEGIN_CASE */
itayzafrirf86548d2018-11-01 10:44:32 +02002253void hash_bad_order( )
2254{
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002255 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrirf86548d2018-11-01 10:44:32 +02002256 unsigned char input[] = "";
2257 /* SHA-256 hash of an empty string */
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002258 const unsigned char valid_hash[] = {
itayzafrirf86548d2018-11-01 10:44:32 +02002259 0xe3, 0xb0, 0xc4, 0x42, 0x98, 0xfc, 0x1c, 0x14, 0x9a, 0xfb, 0xf4, 0xc8,
2260 0x99, 0x6f, 0xb9, 0x24, 0x27, 0xae, 0x41, 0xe4, 0x64, 0x9b, 0x93, 0x4c,
2261 0xa4, 0x95, 0x99, 0x1b, 0x78, 0x52, 0xb8, 0x55 };
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002262 unsigned char hash[sizeof(valid_hash)] = { 0 };
itayzafrirf86548d2018-11-01 10:44:32 +02002263 size_t hash_len;
Jaeden Amero6a25b412019-01-04 11:47:44 +00002264 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrirf86548d2018-11-01 10:44:32 +02002265
Gilles Peskine8817f612018-12-18 00:18:46 +01002266 PSA_ASSERT( psa_crypto_init( ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002267
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002268 /* Call setup twice in a row. */
2269 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2270 TEST_EQUAL( psa_hash_setup( &operation, alg ),
2271 PSA_ERROR_BAD_STATE );
2272 PSA_ASSERT( psa_hash_abort( &operation ) );
2273
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002274 /* Call update without calling setup beforehand. */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002275 TEST_EQUAL( psa_hash_update( &operation, input, sizeof( input ) ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002276 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002277 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002278
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002279 /* Call update after finish. */
2280 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2281 PSA_ASSERT( psa_hash_finish( &operation,
2282 hash, sizeof( hash ), &hash_len ) );
2283 TEST_EQUAL( psa_hash_update( &operation, input, sizeof( input ) ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002284 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002285 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002286
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002287 /* Call verify without calling setup beforehand. */
2288 TEST_EQUAL( psa_hash_verify( &operation,
2289 valid_hash, sizeof( valid_hash ) ),
2290 PSA_ERROR_BAD_STATE );
2291 PSA_ASSERT( psa_hash_abort( &operation ) );
2292
2293 /* Call verify after finish. */
2294 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2295 PSA_ASSERT( psa_hash_finish( &operation,
2296 hash, sizeof( hash ), &hash_len ) );
2297 TEST_EQUAL( psa_hash_verify( &operation,
2298 valid_hash, sizeof( valid_hash ) ),
2299 PSA_ERROR_BAD_STATE );
2300 PSA_ASSERT( psa_hash_abort( &operation ) );
2301
2302 /* Call verify twice in a row. */
2303 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2304 PSA_ASSERT( psa_hash_verify( &operation,
2305 valid_hash, sizeof( valid_hash ) ) );
2306 TEST_EQUAL( psa_hash_verify( &operation,
2307 valid_hash, sizeof( valid_hash ) ),
2308 PSA_ERROR_BAD_STATE );
2309 PSA_ASSERT( psa_hash_abort( &operation ) );
2310
2311 /* Call finish without calling setup beforehand. */
Gilles Peskinefe11b722018-12-18 00:24:04 +01002312 TEST_EQUAL( psa_hash_finish( &operation,
2313 hash, sizeof( hash ), &hash_len ),
Jaeden Ameroa0f625a2019-02-15 13:52:25 +00002314 PSA_ERROR_BAD_STATE );
Jaeden Amero11aa7ee2019-02-19 11:44:55 +00002315 PSA_ASSERT( psa_hash_abort( &operation ) );
2316
2317 /* Call finish twice in a row. */
2318 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2319 PSA_ASSERT( psa_hash_finish( &operation,
2320 hash, sizeof( hash ), &hash_len ) );
2321 TEST_EQUAL( psa_hash_finish( &operation,
2322 hash, sizeof( hash ), &hash_len ),
2323 PSA_ERROR_BAD_STATE );
2324 PSA_ASSERT( psa_hash_abort( &operation ) );
2325
2326 /* Call finish after calling verify. */
2327 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
2328 PSA_ASSERT( psa_hash_verify( &operation,
2329 valid_hash, sizeof( valid_hash ) ) );
2330 TEST_EQUAL( psa_hash_finish( &operation,
2331 hash, sizeof( hash ), &hash_len ),
2332 PSA_ERROR_BAD_STATE );
2333 PSA_ASSERT( psa_hash_abort( &operation ) );
itayzafrirf86548d2018-11-01 10:44:32 +02002334
2335exit:
2336 mbedtls_psa_crypto_free( );
2337}
2338/* END_CASE */
2339
itayzafrir27e69452018-11-01 14:26:34 +02002340/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2341void hash_verify_bad_args( )
itayzafrirec93d302018-10-18 18:01:10 +03002342{
2343 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrir27e69452018-11-01 14:26:34 +02002344 /* SHA-256 hash of an empty string with 2 extra bytes (0xaa and 0xbb)
2345 * appended to it */
2346 unsigned char hash[] = {
2347 0xe3, 0xb0, 0xc4, 0x42, 0x98, 0xfc, 0x1c, 0x14, 0x9a, 0xfb, 0xf4, 0xc8,
2348 0x99, 0x6f, 0xb9, 0x24, 0x27, 0xae, 0x41, 0xe4, 0x64, 0x9b, 0x93, 0x4c,
2349 0xa4, 0x95, 0x99, 0x1b, 0x78, 0x52, 0xb8, 0x55, 0xaa, 0xbb };
itayzafrirec93d302018-10-18 18:01:10 +03002350 size_t expected_size = PSA_HASH_SIZE( alg );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002351 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrirec93d302018-10-18 18:01:10 +03002352
Gilles Peskine8817f612018-12-18 00:18:46 +01002353 PSA_ASSERT( psa_crypto_init( ) );
itayzafrirec93d302018-10-18 18:01:10 +03002354
itayzafrir27e69452018-11-01 14:26:34 +02002355 /* psa_hash_verify with a smaller hash than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002356 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002357 TEST_EQUAL( psa_hash_verify( &operation, hash, expected_size - 1 ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002358 PSA_ERROR_INVALID_SIGNATURE );
itayzafrirec93d302018-10-18 18:01:10 +03002359
itayzafrir27e69452018-11-01 14:26:34 +02002360 /* psa_hash_verify with a non-matching hash */
Gilles Peskine8817f612018-12-18 00:18:46 +01002361 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002362 TEST_EQUAL( psa_hash_verify( &operation, hash + 1, expected_size ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002363 PSA_ERROR_INVALID_SIGNATURE );
itayzafrirec93d302018-10-18 18:01:10 +03002364
itayzafrir27e69452018-11-01 14:26:34 +02002365 /* psa_hash_verify with a hash longer than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002366 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002367 TEST_EQUAL( psa_hash_verify( &operation, hash, sizeof( hash ) ),
Gilles Peskinefe11b722018-12-18 00:24:04 +01002368 PSA_ERROR_INVALID_SIGNATURE );
itayzafrir4271df92018-10-24 18:16:19 +03002369
itayzafrirec93d302018-10-18 18:01:10 +03002370exit:
2371 mbedtls_psa_crypto_free( );
2372}
2373/* END_CASE */
2374
itayzafrirb2dd5ed2018-11-01 11:58:59 +02002375/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2376void hash_finish_bad_args( )
itayzafrir58028322018-10-25 10:22:01 +03002377{
2378 psa_algorithm_t alg = PSA_ALG_SHA_256;
itayzafrirb2dd5ed2018-11-01 11:58:59 +02002379 unsigned char hash[PSA_HASH_MAX_SIZE];
itayzafrir58028322018-10-25 10:22:01 +03002380 size_t expected_size = PSA_HASH_SIZE( alg );
Jaeden Amero6a25b412019-01-04 11:47:44 +00002381 psa_hash_operation_t operation = PSA_HASH_OPERATION_INIT;
itayzafrir58028322018-10-25 10:22:01 +03002382 size_t hash_len;
2383
Gilles Peskine8817f612018-12-18 00:18:46 +01002384 PSA_ASSERT( psa_crypto_init( ) );
itayzafrir58028322018-10-25 10:22:01 +03002385
itayzafrir58028322018-10-25 10:22:01 +03002386 /* psa_hash_finish with a smaller hash buffer than expected */
Gilles Peskine8817f612018-12-18 00:18:46 +01002387 PSA_ASSERT( psa_hash_setup( &operation, alg ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01002388 TEST_EQUAL( psa_hash_finish( &operation,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01002389 hash, expected_size - 1, &hash_len ),
2390 PSA_ERROR_BUFFER_TOO_SMALL );
itayzafrir58028322018-10-25 10:22:01 +03002391
2392exit:
2393 mbedtls_psa_crypto_free( );
2394}
2395/* END_CASE */
2396
Gilles Peskineebb2c3e2019-01-19 12:03:41 +01002397/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2398void hash_clone_source_state( )
2399{
2400 psa_algorithm_t alg = PSA_ALG_SHA_256;
2401 unsigned char hash[PSA_HASH_MAX_SIZE];
2402 psa_hash_operation_t op_source = PSA_HASH_OPERATION_INIT;
2403 psa_hash_operation_t op_init = PSA_HASH_OPERATION_INIT;
2404 psa_hash_operation_t op_setup = PSA_HASH_OPERATION_INIT;
2405 psa_hash_operation_t op_finished = PSA_HASH_OPERATION_INIT;
2406 psa_hash_operation_t op_aborted = PSA_HASH_OPERATION_INIT;
2407 size_t hash_len;
2408
2409 PSA_ASSERT( psa_crypto_init( ) );
2410 PSA_ASSERT( psa_hash_setup( &op_source, alg ) );
2411
2412 PSA_ASSERT( psa_hash_setup( &op_setup, alg ) );
2413 PSA_ASSERT( psa_hash_setup( &op_finished, alg ) );
2414 PSA_ASSERT( psa_hash_finish( &op_finished,
2415 hash, sizeof( hash ), &hash_len ) );
2416 PSA_ASSERT( psa_hash_setup( &op_aborted, alg ) );
2417 PSA_ASSERT( psa_hash_abort( &op_aborted ) );
2418
2419 TEST_EQUAL( psa_hash_clone( &op_source, &op_setup ),
2420 PSA_ERROR_BAD_STATE );
2421
2422 PSA_ASSERT( psa_hash_clone( &op_source, &op_init ) );
2423 PSA_ASSERT( psa_hash_finish( &op_init,
2424 hash, sizeof( hash ), &hash_len ) );
2425 PSA_ASSERT( psa_hash_clone( &op_source, &op_finished ) );
2426 PSA_ASSERT( psa_hash_finish( &op_finished,
2427 hash, sizeof( hash ), &hash_len ) );
2428 PSA_ASSERT( psa_hash_clone( &op_source, &op_aborted ) );
2429 PSA_ASSERT( psa_hash_finish( &op_aborted,
2430 hash, sizeof( hash ), &hash_len ) );
2431
2432exit:
2433 psa_hash_abort( &op_source );
2434 psa_hash_abort( &op_init );
2435 psa_hash_abort( &op_setup );
2436 psa_hash_abort( &op_finished );
2437 psa_hash_abort( &op_aborted );
2438 mbedtls_psa_crypto_free( );
2439}
2440/* END_CASE */
2441
2442/* BEGIN_CASE depends_on:MBEDTLS_SHA256_C */
2443void hash_clone_target_state( )
2444{
2445 psa_algorithm_t alg = PSA_ALG_SHA_256;
2446 unsigned char hash[PSA_HASH_MAX_SIZE];
2447 psa_hash_operation_t op_init = PSA_HASH_OPERATION_INIT;
2448 psa_hash_operation_t op_setup = PSA_HASH_OPERATION_INIT;
2449 psa_hash_operation_t op_finished = PSA_HASH_OPERATION_INIT;
2450 psa_hash_operation_t op_aborted = PSA_HASH_OPERATION_INIT;
2451 psa_hash_operation_t op_target = PSA_HASH_OPERATION_INIT;
2452 size_t hash_len;
2453
2454 PSA_ASSERT( psa_crypto_init( ) );
2455
2456 PSA_ASSERT( psa_hash_setup( &op_setup, alg ) );
2457 PSA_ASSERT( psa_hash_setup( &op_finished, alg ) );
2458 PSA_ASSERT( psa_hash_finish( &op_finished,
2459 hash, sizeof( hash ), &hash_len ) );
2460 PSA_ASSERT( psa_hash_setup( &op_aborted, alg ) );
2461 PSA_ASSERT( psa_hash_abort( &op_aborted ) );
2462
2463 PSA_ASSERT( psa_hash_clone( &op_setup, &op_target ) );
2464 PSA_ASSERT( psa_hash_finish( &op_target,
2465 hash, sizeof( hash ), &hash_len ) );
2466
2467 TEST_EQUAL( psa_hash_clone( &op_init, &op_target ), PSA_ERROR_BAD_STATE );
2468 TEST_EQUAL( psa_hash_clone( &op_finished, &op_target ),
2469 PSA_ERROR_BAD_STATE );
2470 TEST_EQUAL( psa_hash_clone( &op_aborted, &op_target ),
2471 PSA_ERROR_BAD_STATE );
2472
2473exit:
2474 psa_hash_abort( &op_target );
2475 psa_hash_abort( &op_init );
2476 psa_hash_abort( &op_setup );
2477 psa_hash_abort( &op_finished );
2478 psa_hash_abort( &op_aborted );
2479 mbedtls_psa_crypto_free( );
2480}
2481/* END_CASE */
2482
itayzafrir58028322018-10-25 10:22:01 +03002483/* BEGIN_CASE */
Jaeden Amero769ce272019-01-04 11:48:03 +00002484void mac_operation_init( )
2485{
Jaeden Amero252ef282019-02-15 14:05:35 +00002486 const uint8_t input[1] = { 0 };
2487
Jaeden Amero769ce272019-01-04 11:48:03 +00002488 /* Test each valid way of initializing the object, except for `= {0}`, as
2489 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2490 * though it's OK by the C standard. We could test for this, but we'd need
2491 * to supress the Clang warning for the test. */
2492 psa_mac_operation_t func = psa_mac_operation_init( );
2493 psa_mac_operation_t init = PSA_MAC_OPERATION_INIT;
2494 psa_mac_operation_t zero;
2495
2496 memset( &zero, 0, sizeof( zero ) );
2497
Jaeden Amero252ef282019-02-15 14:05:35 +00002498 /* A freshly-initialized MAC operation should not be usable. */
2499 TEST_EQUAL( psa_mac_update( &func,
2500 input, sizeof( input ) ),
2501 PSA_ERROR_BAD_STATE );
2502 TEST_EQUAL( psa_mac_update( &init,
2503 input, sizeof( input ) ),
2504 PSA_ERROR_BAD_STATE );
2505 TEST_EQUAL( psa_mac_update( &zero,
2506 input, sizeof( input ) ),
2507 PSA_ERROR_BAD_STATE );
2508
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002509 /* A default MAC operation should be abortable without error. */
2510 PSA_ASSERT( psa_mac_abort( &func ) );
2511 PSA_ASSERT( psa_mac_abort( &init ) );
2512 PSA_ASSERT( psa_mac_abort( &zero ) );
Jaeden Amero769ce272019-01-04 11:48:03 +00002513}
2514/* END_CASE */
2515
2516/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002517void mac_setup( int key_type_arg,
2518 data_t *key,
2519 int alg_arg,
2520 int expected_status_arg )
2521{
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002522 psa_key_type_t key_type = key_type_arg;
2523 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002524 psa_status_t expected_status = expected_status_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002525 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002526 psa_status_t status = PSA_ERROR_GENERIC_ERROR;
2527#if defined(KNOWN_SUPPORTED_MAC_ALG)
2528 const uint8_t smoke_test_key_data[16] = "kkkkkkkkkkkkkkkk";
2529#endif
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002530
Gilles Peskine8817f612018-12-18 00:18:46 +01002531 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002532
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002533 if( ! exercise_mac_setup( key_type, key->x, key->len, alg,
2534 &operation, &status ) )
2535 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01002536 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002537
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002538 /* The operation object should be reusable. */
2539#if defined(KNOWN_SUPPORTED_MAC_ALG)
2540 if( ! exercise_mac_setup( KNOWN_SUPPORTED_MAC_KEY_TYPE,
2541 smoke_test_key_data,
2542 sizeof( smoke_test_key_data ),
2543 KNOWN_SUPPORTED_MAC_ALG,
2544 &operation, &status ) )
2545 goto exit;
2546 TEST_EQUAL( status, PSA_SUCCESS );
2547#endif
2548
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002549exit:
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002550 mbedtls_psa_crypto_free( );
2551}
2552/* END_CASE */
2553
2554/* BEGIN_CASE */
Jaeden Amero252ef282019-02-15 14:05:35 +00002555void mac_bad_order( )
2556{
2557 psa_key_handle_t handle = 0;
2558 psa_key_type_t key_type = PSA_KEY_TYPE_HMAC;
2559 psa_algorithm_t alg = PSA_ALG_HMAC(PSA_ALG_SHA_256);
2560 const uint8_t key[] = {
2561 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2562 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2563 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa };
2564 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
2565 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
2566 uint8_t sign_mac[PSA_MAC_MAX_SIZE + 10] = { 0 };
2567 size_t sign_mac_length = 0;
2568 const uint8_t input[] = { 0xbb, 0xbb, 0xbb, 0xbb };
2569 const uint8_t verify_mac[] = {
2570 0x74, 0x65, 0x93, 0x8c, 0xeb, 0x1d, 0xb3, 0x76, 0x5a, 0x38, 0xe7, 0xdd,
2571 0x85, 0xc5, 0xad, 0x4f, 0x07, 0xe7, 0xd5, 0xb2, 0x64, 0xf0, 0x1a, 0x1a,
2572 0x2c, 0xf9, 0x18, 0xca, 0x59, 0x7e, 0x5d, 0xf6 };
2573
2574 PSA_ASSERT( psa_crypto_init( ) );
itayzafrir3e02b3b2018-06-12 17:06:52 +03002575 PSA_ASSERT( psa_allocate_key( &handle ) );
2576 psa_key_policy_set_usage( &policy,
2577 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY,
Gilles Peskine9ef733f2018-02-07 21:05:37 +01002578 alg );
2579 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
2580
Gilles Peskine87a5e562019-04-17 12:28:25 +02002581 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Jaeden Amero252ef282019-02-15 14:05:35 +00002582 key, sizeof(key) ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02002583
Jaeden Amero252ef282019-02-15 14:05:35 +00002584 /* Call update without calling setup beforehand. */
2585 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2586 PSA_ERROR_BAD_STATE );
2587 PSA_ASSERT( psa_mac_abort( &operation ) );
2588
2589 /* Call sign finish without calling setup beforehand. */
2590 TEST_EQUAL( psa_mac_sign_finish( &operation, sign_mac, sizeof( sign_mac ),
2591 &sign_mac_length),
2592 PSA_ERROR_BAD_STATE );
2593 PSA_ASSERT( psa_mac_abort( &operation ) );
2594
2595 /* Call verify finish without calling setup beforehand. */
2596 TEST_EQUAL( psa_mac_verify_finish( &operation,
2597 verify_mac, sizeof( verify_mac ) ),
2598 PSA_ERROR_BAD_STATE );
2599 PSA_ASSERT( psa_mac_abort( &operation ) );
2600
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002601 /* Call setup twice in a row. */
2602 PSA_ASSERT( psa_mac_sign_setup( &operation,
2603 handle, alg ) );
2604 TEST_EQUAL( psa_mac_sign_setup( &operation,
2605 handle, alg ),
2606 PSA_ERROR_BAD_STATE );
2607 PSA_ASSERT( psa_mac_abort( &operation ) );
2608
Jaeden Amero252ef282019-02-15 14:05:35 +00002609 /* Call update after sign finish. */
2610 PSA_ASSERT( psa_mac_sign_setup( &operation,
2611 handle, alg ) );
2612 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2613 PSA_ASSERT( psa_mac_sign_finish( &operation,
2614 sign_mac, sizeof( sign_mac ),
2615 &sign_mac_length ) );
2616 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2617 PSA_ERROR_BAD_STATE );
2618 PSA_ASSERT( psa_mac_abort( &operation ) );
2619
2620 /* Call update after verify finish. */
2621 PSA_ASSERT( psa_mac_verify_setup( &operation,
2622 handle, alg ) );
2623 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2624 PSA_ASSERT( psa_mac_verify_finish( &operation,
2625 verify_mac, sizeof( verify_mac ) ) );
2626 TEST_EQUAL( psa_mac_update( &operation, input, sizeof( input ) ),
2627 PSA_ERROR_BAD_STATE );
2628 PSA_ASSERT( psa_mac_abort( &operation ) );
2629
2630 /* Call sign finish twice in a row. */
2631 PSA_ASSERT( psa_mac_sign_setup( &operation,
2632 handle, alg ) );
2633 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2634 PSA_ASSERT( psa_mac_sign_finish( &operation,
2635 sign_mac, sizeof( sign_mac ),
2636 &sign_mac_length ) );
2637 TEST_EQUAL( psa_mac_sign_finish( &operation,
2638 sign_mac, sizeof( sign_mac ),
2639 &sign_mac_length ),
2640 PSA_ERROR_BAD_STATE );
2641 PSA_ASSERT( psa_mac_abort( &operation ) );
2642
2643 /* Call verify finish twice in a row. */
2644 PSA_ASSERT( psa_mac_verify_setup( &operation,
2645 handle, alg ) );
2646 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2647 PSA_ASSERT( psa_mac_verify_finish( &operation,
2648 verify_mac, sizeof( verify_mac ) ) );
2649 TEST_EQUAL( psa_mac_verify_finish( &operation,
2650 verify_mac, sizeof( verify_mac ) ),
2651 PSA_ERROR_BAD_STATE );
2652 PSA_ASSERT( psa_mac_abort( &operation ) );
2653
2654 /* Setup sign but try verify. */
2655 PSA_ASSERT( psa_mac_sign_setup( &operation,
2656 handle, alg ) );
2657 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2658 TEST_EQUAL( psa_mac_verify_finish( &operation,
2659 verify_mac, sizeof( verify_mac ) ),
2660 PSA_ERROR_BAD_STATE );
2661 PSA_ASSERT( psa_mac_abort( &operation ) );
2662
2663 /* Setup verify but try sign. */
2664 PSA_ASSERT( psa_mac_verify_setup( &operation,
2665 handle, alg ) );
2666 PSA_ASSERT( psa_mac_update( &operation, input, sizeof( input ) ) );
2667 TEST_EQUAL( psa_mac_sign_finish( &operation,
2668 sign_mac, sizeof( sign_mac ),
2669 &sign_mac_length ),
2670 PSA_ERROR_BAD_STATE );
2671 PSA_ASSERT( psa_mac_abort( &operation ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02002672
Gilles Peskine9ef733f2018-02-07 21:05:37 +01002673exit:
Gilles Peskine9ef733f2018-02-07 21:05:37 +01002674 mbedtls_psa_crypto_free( );
2675}
2676/* END_CASE */
2677
2678/* BEGIN_CASE */
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002679void mac_sign( int key_type_arg,
2680 data_t *key,
2681 int alg_arg,
2682 data_t *input,
2683 data_t *expected_mac )
2684{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002685 psa_key_handle_t handle = 0;
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002686 psa_key_type_t key_type = key_type_arg;
2687 psa_algorithm_t alg = alg_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002688 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002689 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002690 /* Leave a little extra room in the output buffer. At the end of the
2691 * test, we'll check that the implementation didn't overwrite onto
2692 * this extra room. */
2693 uint8_t actual_mac[PSA_MAC_MAX_SIZE + 10];
2694 size_t mac_buffer_size =
2695 PSA_MAC_FINAL_SIZE( key_type, PSA_BYTES_TO_BITS( key->len ), alg );
2696 size_t mac_length = 0;
2697
2698 memset( actual_mac, '+', sizeof( actual_mac ) );
2699 TEST_ASSERT( mac_buffer_size <= PSA_MAC_MAX_SIZE );
2700 TEST_ASSERT( expected_mac->len <= mac_buffer_size );
2701
Gilles Peskine8817f612018-12-18 00:18:46 +01002702 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002703
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002704 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002705 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002706 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002707
Gilles Peskine87a5e562019-04-17 12:28:25 +02002708 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01002709 key->x, key->len ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002710
2711 /* Calculate the MAC. */
Gilles Peskine8817f612018-12-18 00:18:46 +01002712 PSA_ASSERT( psa_mac_sign_setup( &operation,
2713 handle, alg ) );
2714 PSA_ASSERT( psa_mac_update( &operation,
2715 input->x, input->len ) );
2716 PSA_ASSERT( psa_mac_sign_finish( &operation,
2717 actual_mac, mac_buffer_size,
2718 &mac_length ) );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002719
2720 /* Compare with the expected value. */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01002721 ASSERT_COMPARE( expected_mac->x, expected_mac->len,
2722 actual_mac, mac_length );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002723
2724 /* Verify that the end of the buffer is untouched. */
2725 TEST_ASSERT( mem_is_char( actual_mac + mac_length, '+',
2726 sizeof( actual_mac ) - mac_length ) );
2727
2728exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002729 psa_destroy_key( handle );
Gilles Peskinea7aa4422018-08-14 15:17:54 +02002730 mbedtls_psa_crypto_free( );
2731}
2732/* END_CASE */
2733
2734/* BEGIN_CASE */
Gilles Peskinec0ec9722018-06-18 17:03:37 +02002735void mac_verify( int key_type_arg,
2736 data_t *key,
2737 int alg_arg,
2738 data_t *input,
2739 data_t *expected_mac )
Gilles Peskine8c9def32018-02-08 10:02:12 +01002740{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002741 psa_key_handle_t handle = 0;
Gilles Peskine8c9def32018-02-08 10:02:12 +01002742 psa_key_type_t key_type = key_type_arg;
2743 psa_algorithm_t alg = alg_arg;
Jaeden Amero769ce272019-01-04 11:48:03 +00002744 psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00002745 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine8c9def32018-02-08 10:02:12 +01002746
Gilles Peskine69c12672018-06-28 00:07:19 +02002747 TEST_ASSERT( expected_mac->len <= PSA_MAC_MAX_SIZE );
2748
Gilles Peskine8817f612018-12-18 00:18:46 +01002749 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002750
Gilles Peskined40c1fb2019-01-19 12:20:52 +01002751 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02002752 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01002753 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad16036df908f2018-04-02 08:34:15 -07002754
Gilles Peskine87a5e562019-04-17 12:28:25 +02002755 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01002756 key->x, key->len ) );
Gilles Peskinec0ec9722018-06-18 17:03:37 +02002757
Gilles Peskine8817f612018-12-18 00:18:46 +01002758 PSA_ASSERT( psa_mac_verify_setup( &operation,
2759 handle, alg ) );
2760 PSA_ASSERT( psa_destroy_key( handle ) );
2761 PSA_ASSERT( psa_mac_update( &operation,
2762 input->x, input->len ) );
2763 PSA_ASSERT( psa_mac_verify_finish( &operation,
2764 expected_mac->x,
2765 expected_mac->len ) );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002766
2767exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01002768 psa_destroy_key( handle );
Gilles Peskine8c9def32018-02-08 10:02:12 +01002769 mbedtls_psa_crypto_free( );
2770}
2771/* END_CASE */
2772
2773/* BEGIN_CASE */
Jaeden Amero5bae2272019-01-04 11:48:27 +00002774void cipher_operation_init( )
2775{
Jaeden Ameroab439972019-02-15 14:12:05 +00002776 const uint8_t input[1] = { 0 };
2777 unsigned char output[1] = { 0 };
2778 size_t output_length;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002779 /* Test each valid way of initializing the object, except for `= {0}`, as
2780 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
2781 * though it's OK by the C standard. We could test for this, but we'd need
2782 * to supress the Clang warning for the test. */
2783 psa_cipher_operation_t func = psa_cipher_operation_init( );
2784 psa_cipher_operation_t init = PSA_CIPHER_OPERATION_INIT;
2785 psa_cipher_operation_t zero;
2786
2787 memset( &zero, 0, sizeof( zero ) );
2788
Jaeden Ameroab439972019-02-15 14:12:05 +00002789 /* A freshly-initialized cipher operation should not be usable. */
2790 TEST_EQUAL( psa_cipher_update( &func,
2791 input, sizeof( input ),
2792 output, sizeof( output ),
2793 &output_length ),
2794 PSA_ERROR_BAD_STATE );
2795 TEST_EQUAL( psa_cipher_update( &init,
2796 input, sizeof( input ),
2797 output, sizeof( output ),
2798 &output_length ),
2799 PSA_ERROR_BAD_STATE );
2800 TEST_EQUAL( psa_cipher_update( &zero,
2801 input, sizeof( input ),
2802 output, sizeof( output ),
2803 &output_length ),
2804 PSA_ERROR_BAD_STATE );
2805
Jaeden Amero5229bbb2019-02-07 16:33:37 +00002806 /* A default cipher operation should be abortable without error. */
2807 PSA_ASSERT( psa_cipher_abort( &func ) );
2808 PSA_ASSERT( psa_cipher_abort( &init ) );
2809 PSA_ASSERT( psa_cipher_abort( &zero ) );
Jaeden Amero5bae2272019-01-04 11:48:27 +00002810}
2811/* END_CASE */
2812
2813/* BEGIN_CASE */
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002814void cipher_setup( int key_type_arg,
2815 data_t *key,
2816 int alg_arg,
2817 int expected_status_arg )
2818{
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002819 psa_key_type_t key_type = key_type_arg;
2820 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02002821 psa_status_t expected_status = expected_status_arg;
Jaeden Amero5bae2272019-01-04 11:48:27 +00002822 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002823 psa_status_t status;
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002824#if defined(KNOWN_SUPPORTED_MAC_ALG)
2825 const uint8_t smoke_test_key_data[16] = "kkkkkkkkkkkkkkkk";
2826#endif
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002827
Gilles Peskine8817f612018-12-18 00:18:46 +01002828 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002829
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002830 if( ! exercise_cipher_setup( key_type, key->x, key->len, alg,
2831 &operation, &status ) )
2832 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01002833 TEST_EQUAL( status, expected_status );
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002834
Gilles Peskinef426e0f2019-02-25 17:42:03 +01002835 /* The operation object should be reusable. */
2836#if defined(KNOWN_SUPPORTED_CIPHER_ALG)
2837 if( ! exercise_cipher_setup( KNOWN_SUPPORTED_CIPHER_KEY_TYPE,
2838 smoke_test_key_data,
2839 sizeof( smoke_test_key_data ),
2840 KNOWN_SUPPORTED_CIPHER_ALG,
2841 &operation, &status ) )
2842 goto exit;
2843 TEST_EQUAL( status, PSA_SUCCESS );
2844#endif
2845
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002846exit:
Gilles Peskine16c0f4f2018-06-20 16:05:20 +02002847 mbedtls_psa_crypto_free( );
2848}
2849/* END_CASE */
2850
2851/* BEGIN_CASE */
Jaeden Ameroab439972019-02-15 14:12:05 +00002852void cipher_bad_order( )
2853{
2854 psa_key_handle_t handle = 0;
2855 psa_key_type_t key_type = PSA_KEY_TYPE_AES;
2856 psa_algorithm_t alg = PSA_ALG_CBC_PKCS7;
2857 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
2858 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
2859 unsigned char iv[PSA_BLOCK_CIPHER_BLOCK_SIZE(PSA_KEY_TYPE_AES)] = { 0 };
2860 const uint8_t key[] = {
2861 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa,
2862 0xaa, 0xaa, 0xaa, 0xaa };
2863 const uint8_t text[] = {
2864 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb,
2865 0xbb, 0xbb, 0xbb, 0xbb };
2866 uint8_t buffer[PSA_BLOCK_CIPHER_BLOCK_SIZE(PSA_KEY_TYPE_AES)] = { 0 };
2867 size_t length = 0;
2868
2869 PSA_ASSERT( psa_crypto_init( ) );
2870 PSA_ASSERT( psa_allocate_key( &handle ) );
2871 psa_key_policy_set_usage( &policy,
2872 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
2873 alg );
2874 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02002875 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Jaeden Ameroab439972019-02-15 14:12:05 +00002876 key, sizeof(key) ) );
2877
2878
Jaeden Amero36ee5d02019-02-19 09:25:10 +00002879 /* Call encrypt setup twice in a row. */
2880 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2881 TEST_EQUAL( psa_cipher_encrypt_setup( &operation, handle, alg ),
2882 PSA_ERROR_BAD_STATE );
2883 PSA_ASSERT( psa_cipher_abort( &operation ) );
2884
2885 /* Call decrypt setup twice in a row. */
2886 PSA_ASSERT( psa_cipher_decrypt_setup( &operation, handle, alg ) );
2887 TEST_EQUAL( psa_cipher_decrypt_setup( &operation, handle, alg ),
2888 PSA_ERROR_BAD_STATE );
2889 PSA_ASSERT( psa_cipher_abort( &operation ) );
2890
Jaeden Ameroab439972019-02-15 14:12:05 +00002891 /* Generate an IV without calling setup beforehand. */
2892 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2893 buffer, sizeof( buffer ),
2894 &length ),
2895 PSA_ERROR_BAD_STATE );
2896 PSA_ASSERT( psa_cipher_abort( &operation ) );
2897
2898 /* Generate an IV twice in a row. */
2899 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2900 PSA_ASSERT( psa_cipher_generate_iv( &operation,
2901 buffer, sizeof( buffer ),
2902 &length ) );
2903 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2904 buffer, sizeof( buffer ),
2905 &length ),
2906 PSA_ERROR_BAD_STATE );
2907 PSA_ASSERT( psa_cipher_abort( &operation ) );
2908
2909 /* Generate an IV after it's already set. */
2910 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2911 PSA_ASSERT( psa_cipher_set_iv( &operation,
2912 iv, sizeof( iv ) ) );
2913 TEST_EQUAL( psa_cipher_generate_iv( &operation,
2914 buffer, sizeof( buffer ),
2915 &length ),
2916 PSA_ERROR_BAD_STATE );
2917 PSA_ASSERT( psa_cipher_abort( &operation ) );
2918
2919 /* Set an IV without calling setup beforehand. */
2920 TEST_EQUAL( psa_cipher_set_iv( &operation,
2921 iv, sizeof( iv ) ),
2922 PSA_ERROR_BAD_STATE );
2923 PSA_ASSERT( psa_cipher_abort( &operation ) );
2924
2925 /* Set an IV after it's already set. */
2926 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2927 PSA_ASSERT( psa_cipher_set_iv( &operation,
2928 iv, sizeof( iv ) ) );
2929 TEST_EQUAL( psa_cipher_set_iv( &operation,
2930 iv, sizeof( iv ) ),
2931 PSA_ERROR_BAD_STATE );
2932 PSA_ASSERT( psa_cipher_abort( &operation ) );
2933
2934 /* Set an IV after it's already generated. */
2935 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2936 PSA_ASSERT( psa_cipher_generate_iv( &operation,
2937 buffer, sizeof( buffer ),
2938 &length ) );
2939 TEST_EQUAL( psa_cipher_set_iv( &operation,
2940 iv, sizeof( iv ) ),
2941 PSA_ERROR_BAD_STATE );
2942 PSA_ASSERT( psa_cipher_abort( &operation ) );
2943
2944 /* Call update without calling setup beforehand. */
2945 TEST_EQUAL( psa_cipher_update( &operation,
2946 text, sizeof( text ),
2947 buffer, sizeof( buffer ),
2948 &length ),
2949 PSA_ERROR_BAD_STATE );
2950 PSA_ASSERT( psa_cipher_abort( &operation ) );
2951
2952 /* Call update without an IV where an IV is required. */
2953 TEST_EQUAL( psa_cipher_update( &operation,
2954 text, sizeof( text ),
2955 buffer, sizeof( buffer ),
2956 &length ),
2957 PSA_ERROR_BAD_STATE );
2958 PSA_ASSERT( psa_cipher_abort( &operation ) );
2959
2960 /* Call update after finish. */
2961 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2962 PSA_ASSERT( psa_cipher_set_iv( &operation,
2963 iv, sizeof( iv ) ) );
2964 PSA_ASSERT( psa_cipher_finish( &operation,
2965 buffer, sizeof( buffer ), &length ) );
2966 TEST_EQUAL( psa_cipher_update( &operation,
2967 text, sizeof( text ),
2968 buffer, sizeof( buffer ),
2969 &length ),
2970 PSA_ERROR_BAD_STATE );
2971 PSA_ASSERT( psa_cipher_abort( &operation ) );
2972
2973 /* Call finish without calling setup beforehand. */
2974 TEST_EQUAL( psa_cipher_finish( &operation,
2975 buffer, sizeof( buffer ), &length ),
2976 PSA_ERROR_BAD_STATE );
2977 PSA_ASSERT( psa_cipher_abort( &operation ) );
2978
2979 /* Call finish without an IV where an IV is required. */
2980 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2981 /* Not calling update means we are encrypting an empty buffer, which is OK
2982 * for cipher modes with padding. */
2983 TEST_EQUAL( psa_cipher_finish( &operation,
2984 buffer, sizeof( buffer ), &length ),
2985 PSA_ERROR_BAD_STATE );
2986 PSA_ASSERT( psa_cipher_abort( &operation ) );
2987
2988 /* Call finish twice in a row. */
2989 PSA_ASSERT( psa_cipher_encrypt_setup( &operation, handle, alg ) );
2990 PSA_ASSERT( psa_cipher_set_iv( &operation,
2991 iv, sizeof( iv ) ) );
2992 PSA_ASSERT( psa_cipher_finish( &operation,
2993 buffer, sizeof( buffer ), &length ) );
2994 TEST_EQUAL( psa_cipher_finish( &operation,
2995 buffer, sizeof( buffer ), &length ),
2996 PSA_ERROR_BAD_STATE );
2997 PSA_ASSERT( psa_cipher_abort( &operation ) );
2998
2999exit:
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003000 mbedtls_psa_crypto_free( );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003001}
3002/* END_CASE */
Gilles Peskine50e586b2018-06-08 14:28:46 +02003003
Gilles Peskine50e586b2018-06-08 14:28:46 +02003004/* BEGIN_CASE */
Gilles Peskine50e586b2018-06-08 14:28:46 +02003005void cipher_encrypt( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003006 data_t *key,
3007 data_t *input, data_t *expected_output,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003008 int expected_status_arg )
Gilles Peskine50e586b2018-06-08 14:28:46 +02003009{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003010 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003011 psa_status_t status;
3012 psa_key_type_t key_type = key_type_arg;
3013 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003014 psa_status_t expected_status = expected_status_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003015 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003016 size_t iv_size;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003017 unsigned char *output = NULL;
3018 size_t output_buffer_size = 0;
3019 size_t function_output_length = 0;
3020 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003021 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003022 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003023
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003024 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3025 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003026
Gilles Peskine8817f612018-12-18 00:18:46 +01003027 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003028
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003029 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003030 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003031 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003032
Gilles Peskine87a5e562019-04-17 12:28:25 +02003033 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003034 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003035
Gilles Peskine8817f612018-12-18 00:18:46 +01003036 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
3037 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003038
Gilles Peskine8817f612018-12-18 00:18:46 +01003039 PSA_ASSERT( psa_cipher_set_iv( &operation,
3040 iv, iv_size ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003041 output_buffer_size = ( (size_t) input->len +
3042 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003043 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003044
Gilles Peskine8817f612018-12-18 00:18:46 +01003045 PSA_ASSERT( psa_cipher_update( &operation,
3046 input->x, input->len,
3047 output, output_buffer_size,
3048 &function_output_length ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003049 total_output_length += function_output_length;
3050 status = psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003051 output + total_output_length,
3052 output_buffer_size - total_output_length,
Gilles Peskine50e586b2018-06-08 14:28:46 +02003053 &function_output_length );
3054 total_output_length += function_output_length;
3055
Gilles Peskinefe11b722018-12-18 00:24:04 +01003056 TEST_EQUAL( status, expected_status );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003057 if( expected_status == PSA_SUCCESS )
3058 {
Gilles Peskine8817f612018-12-18 00:18:46 +01003059 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003060 ASSERT_COMPARE( expected_output->x, expected_output->len,
3061 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003062 }
3063
3064exit:
3065 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003066 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003067 mbedtls_psa_crypto_free( );
3068}
3069/* END_CASE */
3070
3071/* BEGIN_CASE */
3072void cipher_encrypt_multipart( int alg_arg, int key_type_arg,
3073 data_t *key,
3074 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01003075 int first_part_size_arg,
3076 int output1_length_arg, int output2_length_arg,
Gilles Peskine50e586b2018-06-08 14:28:46 +02003077 data_t *expected_output )
3078{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003079 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003080 psa_key_type_t key_type = key_type_arg;
3081 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01003082 size_t first_part_size = first_part_size_arg;
3083 size_t output1_length = output1_length_arg;
3084 size_t output2_length = output2_length_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003085 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003086 size_t iv_size;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003087 unsigned char *output = NULL;
3088 size_t output_buffer_size = 0;
3089 size_t function_output_length = 0;
3090 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003091 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003092 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003093
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003094 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3095 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003096
Gilles Peskine8817f612018-12-18 00:18:46 +01003097 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003098
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003099 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003100 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003101 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003102
Gilles Peskine87a5e562019-04-17 12:28:25 +02003103 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003104 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003105
Gilles Peskine8817f612018-12-18 00:18:46 +01003106 PSA_ASSERT( psa_cipher_encrypt_setup( &operation,
3107 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003108
Gilles Peskine8817f612018-12-18 00:18:46 +01003109 PSA_ASSERT( psa_cipher_set_iv( &operation,
3110 iv, sizeof( iv ) ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003111 output_buffer_size = ( (size_t) input->len +
3112 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003113 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003114
Gilles Peskinee0866522019-02-19 19:44:00 +01003115 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine8817f612018-12-18 00:18:46 +01003116 PSA_ASSERT( psa_cipher_update( &operation, input->x, first_part_size,
3117 output, output_buffer_size,
3118 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003119 TEST_ASSERT( function_output_length == output1_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003120 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003121 PSA_ASSERT( psa_cipher_update( &operation,
3122 input->x + first_part_size,
3123 input->len - first_part_size,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003124 output + total_output_length,
3125 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003126 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003127 TEST_ASSERT( function_output_length == output2_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003128 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003129 PSA_ASSERT( psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003130 output + total_output_length,
3131 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003132 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003133 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003134 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003135
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003136 ASSERT_COMPARE( expected_output->x, expected_output->len,
3137 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003138
3139exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003140 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003141 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003142 mbedtls_psa_crypto_free( );
3143}
3144/* END_CASE */
3145
3146/* BEGIN_CASE */
3147void cipher_decrypt_multipart( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003148 data_t *key,
3149 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01003150 int first_part_size_arg,
3151 int output1_length_arg, int output2_length_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003152 data_t *expected_output )
Gilles Peskine50e586b2018-06-08 14:28:46 +02003153{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003154 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003155
3156 psa_key_type_t key_type = key_type_arg;
3157 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01003158 size_t first_part_size = first_part_size_arg;
3159 size_t output1_length = output1_length_arg;
3160 size_t output2_length = output2_length_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003161 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003162 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003163 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003164 size_t output_buffer_size = 0;
3165 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003166 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003167 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003168 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003169
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003170 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3171 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003172
Gilles Peskine8817f612018-12-18 00:18:46 +01003173 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003174
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003175 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003176 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003177 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003178
Gilles Peskine87a5e562019-04-17 12:28:25 +02003179 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003180 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003181
Gilles Peskine8817f612018-12-18 00:18:46 +01003182 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
3183 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003184
Gilles Peskine8817f612018-12-18 00:18:46 +01003185 PSA_ASSERT( psa_cipher_set_iv( &operation,
3186 iv, sizeof( iv ) ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003187
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003188 output_buffer_size = ( (size_t) input->len +
3189 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003190 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003191
Gilles Peskinee0866522019-02-19 19:44:00 +01003192 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine8817f612018-12-18 00:18:46 +01003193 PSA_ASSERT( psa_cipher_update( &operation,
3194 input->x, first_part_size,
3195 output, output_buffer_size,
3196 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003197 TEST_ASSERT( function_output_length == output1_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003198 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003199 PSA_ASSERT( psa_cipher_update( &operation,
3200 input->x + first_part_size,
3201 input->len - first_part_size,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003202 output + total_output_length,
3203 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003204 &function_output_length ) );
Gilles Peskinee0866522019-02-19 19:44:00 +01003205 TEST_ASSERT( function_output_length == output2_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003206 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003207 PSA_ASSERT( psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003208 output + total_output_length,
3209 output_buffer_size - total_output_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003210 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003211 total_output_length += function_output_length;
Gilles Peskine8817f612018-12-18 00:18:46 +01003212 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003213
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003214 ASSERT_COMPARE( expected_output->x, expected_output->len,
3215 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003216
3217exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003218 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003219 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003220 mbedtls_psa_crypto_free( );
3221}
3222/* END_CASE */
3223
Gilles Peskine50e586b2018-06-08 14:28:46 +02003224/* BEGIN_CASE */
3225void cipher_decrypt( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003226 data_t *key,
3227 data_t *input, data_t *expected_output,
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003228 int expected_status_arg )
Gilles Peskine50e586b2018-06-08 14:28:46 +02003229{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003230 psa_key_handle_t handle = 0;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003231 psa_status_t status;
3232 psa_key_type_t key_type = key_type_arg;
3233 psa_algorithm_t alg = alg_arg;
Gilles Peskineb866e2b2018-06-21 09:25:10 +02003234 psa_status_t expected_status = expected_status_arg;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003235 unsigned char iv[16] = {0};
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003236 size_t iv_size;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003237 unsigned char *output = NULL;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003238 size_t output_buffer_size = 0;
3239 size_t function_output_length = 0;
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003240 size_t total_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003241 psa_cipher_operation_t operation = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003242 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003243
Gilles Peskine9ad29e22018-06-21 09:40:04 +02003244 iv_size = PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type );
3245 memset( iv, 0x2a, iv_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003246
Gilles Peskine8817f612018-12-18 00:18:46 +01003247 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003248
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003249 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003250 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003251 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003252
Gilles Peskine87a5e562019-04-17 12:28:25 +02003253 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003254 key->x, key->len ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003255
Gilles Peskine8817f612018-12-18 00:18:46 +01003256 PSA_ASSERT( psa_cipher_decrypt_setup( &operation,
3257 handle, alg ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003258
Gilles Peskine8817f612018-12-18 00:18:46 +01003259 PSA_ASSERT( psa_cipher_set_iv( &operation,
3260 iv, iv_size ) );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003261
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003262 output_buffer_size = ( (size_t) input->len +
3263 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003264 ASSERT_ALLOC( output, output_buffer_size );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003265
Gilles Peskine8817f612018-12-18 00:18:46 +01003266 PSA_ASSERT( psa_cipher_update( &operation,
3267 input->x, input->len,
3268 output, output_buffer_size,
3269 &function_output_length ) );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003270 total_output_length += function_output_length;
Gilles Peskine50e586b2018-06-08 14:28:46 +02003271 status = psa_cipher_finish( &operation,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003272 output + total_output_length,
3273 output_buffer_size - total_output_length,
Gilles Peskine50e586b2018-06-08 14:28:46 +02003274 &function_output_length );
Gilles Peskinea7ec95f2018-06-08 14:40:59 +02003275 total_output_length += function_output_length;
Gilles Peskinefe11b722018-12-18 00:24:04 +01003276 TEST_EQUAL( status, expected_status );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003277
3278 if( expected_status == PSA_SUCCESS )
3279 {
Gilles Peskine8817f612018-12-18 00:18:46 +01003280 PSA_ASSERT( psa_cipher_abort( &operation ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003281 ASSERT_COMPARE( expected_output->x, expected_output->len,
3282 output, total_output_length );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003283 }
3284
Gilles Peskine50e586b2018-06-08 14:28:46 +02003285exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003286 mbedtls_free( output );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003287 psa_destroy_key( handle );
Gilles Peskine50e586b2018-06-08 14:28:46 +02003288 mbedtls_psa_crypto_free( );
3289}
3290/* END_CASE */
3291
Gilles Peskine50e586b2018-06-08 14:28:46 +02003292/* BEGIN_CASE */
3293void cipher_verify_output( int alg_arg, int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003294 data_t *key,
3295 data_t *input )
mohammad1603d7d7ba52018-03-12 18:51:53 +02003296{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003297 psa_key_handle_t handle = 0;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003298 psa_key_type_t key_type = key_type_arg;
3299 psa_algorithm_t alg = alg_arg;
mohammad1603e6b67a12018-03-12 10:38:49 -07003300 unsigned char iv[16] = {0};
mohammad1603d7d7ba52018-03-12 18:51:53 +02003301 size_t iv_size = 16;
3302 size_t iv_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003303 unsigned char *output1 = NULL;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003304 size_t output1_size = 0;
3305 size_t output1_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003306 unsigned char *output2 = NULL;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003307 size_t output2_size = 0;
3308 size_t output2_length = 0;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003309 size_t function_output_length = 0;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003310 psa_cipher_operation_t operation1 = PSA_CIPHER_OPERATION_INIT;
3311 psa_cipher_operation_t operation2 = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003312 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003313
Gilles Peskine8817f612018-12-18 00:18:46 +01003314 PSA_ASSERT( psa_crypto_init( ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003315
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003316 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003317 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003318 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003319
Gilles Peskine87a5e562019-04-17 12:28:25 +02003320 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003321 key->x, key->len ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003322
Gilles Peskine8817f612018-12-18 00:18:46 +01003323 PSA_ASSERT( psa_cipher_encrypt_setup( &operation1,
3324 handle, alg ) );
3325 PSA_ASSERT( psa_cipher_decrypt_setup( &operation2,
3326 handle, alg ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003327
Gilles Peskine8817f612018-12-18 00:18:46 +01003328 PSA_ASSERT( psa_cipher_generate_iv( &operation1,
3329 iv, iv_size,
3330 &iv_length ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003331 output1_size = ( (size_t) input->len +
3332 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003333 ASSERT_ALLOC( output1, output1_size );
Moran Pekerded84402018-06-06 16:36:50 +03003334
Gilles Peskine8817f612018-12-18 00:18:46 +01003335 PSA_ASSERT( psa_cipher_update( &operation1, input->x, input->len,
3336 output1, output1_size,
3337 &output1_length ) );
3338 PSA_ASSERT( psa_cipher_finish( &operation1,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003339 output1 + output1_length,
3340 output1_size - output1_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003341 &function_output_length ) );
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003342
Gilles Peskine048b7f02018-06-08 14:20:49 +02003343 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003344
Gilles Peskine8817f612018-12-18 00:18:46 +01003345 PSA_ASSERT( psa_cipher_abort( &operation1 ) );
Moran Pekerded84402018-06-06 16:36:50 +03003346
3347 output2_size = output1_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003348 ASSERT_ALLOC( output2, output2_size );
Moran Pekerded84402018-06-06 16:36:50 +03003349
Gilles Peskine8817f612018-12-18 00:18:46 +01003350 PSA_ASSERT( psa_cipher_set_iv( &operation2,
3351 iv, iv_length ) );
3352 PSA_ASSERT( psa_cipher_update( &operation2, output1, output1_length,
3353 output2, output2_size,
3354 &output2_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003355 function_output_length = 0;
Gilles Peskine8817f612018-12-18 00:18:46 +01003356 PSA_ASSERT( psa_cipher_finish( &operation2,
3357 output2 + output2_length,
Gilles Peskineee46fe72019-02-19 19:05:33 +01003358 output2_size - output2_length,
Gilles Peskine8817f612018-12-18 00:18:46 +01003359 &function_output_length ) );
Moran Pekerded84402018-06-06 16:36:50 +03003360
Gilles Peskine048b7f02018-06-08 14:20:49 +02003361 output2_length += function_output_length;
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003362
Gilles Peskine8817f612018-12-18 00:18:46 +01003363 PSA_ASSERT( psa_cipher_abort( &operation2 ) );
Moran Pekerded84402018-06-06 16:36:50 +03003364
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003365 ASSERT_COMPARE( input->x, input->len, output2, output2_length );
Moran Pekerded84402018-06-06 16:36:50 +03003366
3367exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003368 mbedtls_free( output1 );
3369 mbedtls_free( output2 );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003370 psa_destroy_key( handle );
Moran Pekerded84402018-06-06 16:36:50 +03003371 mbedtls_psa_crypto_free( );
3372}
3373/* END_CASE */
3374
3375/* BEGIN_CASE */
Gilles Peskine50e586b2018-06-08 14:28:46 +02003376void cipher_verify_output_multipart( int alg_arg,
3377 int key_type_arg,
itayzafrir3e02b3b2018-06-12 17:06:52 +03003378 data_t *key,
3379 data_t *input,
Gilles Peskinee0866522019-02-19 19:44:00 +01003380 int first_part_size_arg )
Moran Pekerded84402018-06-06 16:36:50 +03003381{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003382 psa_key_handle_t handle = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003383 psa_key_type_t key_type = key_type_arg;
3384 psa_algorithm_t alg = alg_arg;
Gilles Peskinee0866522019-02-19 19:44:00 +01003385 size_t first_part_size = first_part_size_arg;
Moran Pekerded84402018-06-06 16:36:50 +03003386 unsigned char iv[16] = {0};
3387 size_t iv_size = 16;
3388 size_t iv_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003389 unsigned char *output1 = NULL;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003390 size_t output1_buffer_size = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003391 size_t output1_length = 0;
itayzafrir3e02b3b2018-06-12 17:06:52 +03003392 unsigned char *output2 = NULL;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003393 size_t output2_buffer_size = 0;
Moran Pekerded84402018-06-06 16:36:50 +03003394 size_t output2_length = 0;
Gilles Peskine048b7f02018-06-08 14:20:49 +02003395 size_t function_output_length;
Jaeden Amero5bae2272019-01-04 11:48:27 +00003396 psa_cipher_operation_t operation1 = PSA_CIPHER_OPERATION_INIT;
3397 psa_cipher_operation_t operation2 = PSA_CIPHER_OPERATION_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00003398 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Moran Pekerded84402018-06-06 16:36:50 +03003399
Gilles Peskine8817f612018-12-18 00:18:46 +01003400 PSA_ASSERT( psa_crypto_init( ) );
Moran Pekerded84402018-06-06 16:36:50 +03003401
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003402 PSA_ASSERT( psa_allocate_key( &handle ) );
Moran Pekered346952018-07-05 15:22:45 +03003403 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003404 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Moran Pekered346952018-07-05 15:22:45 +03003405
Gilles Peskine87a5e562019-04-17 12:28:25 +02003406 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003407 key->x, key->len ) );
Moran Pekerded84402018-06-06 16:36:50 +03003408
Gilles Peskine8817f612018-12-18 00:18:46 +01003409 PSA_ASSERT( psa_cipher_encrypt_setup( &operation1,
3410 handle, alg ) );
3411 PSA_ASSERT( psa_cipher_decrypt_setup( &operation2,
3412 handle, alg ) );
Moran Pekerded84402018-06-06 16:36:50 +03003413
Gilles Peskine8817f612018-12-18 00:18:46 +01003414 PSA_ASSERT( psa_cipher_generate_iv( &operation1,
3415 iv, iv_size,
3416 &iv_length ) );
Gilles Peskine9d8eea72018-12-17 23:34:57 +01003417 output1_buffer_size = ( (size_t) input->len +
3418 PSA_BLOCK_CIPHER_BLOCK_SIZE( key_type ) );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003419 ASSERT_ALLOC( output1, output1_buffer_size );
Moran Pekerded84402018-06-06 16:36:50 +03003420
Gilles Peskinee0866522019-02-19 19:44:00 +01003421 TEST_ASSERT( first_part_size <= input->len );
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003422
Gilles Peskine8817f612018-12-18 00:18:46 +01003423 PSA_ASSERT( psa_cipher_update( &operation1, input->x, first_part_size,
3424 output1, output1_buffer_size,
3425 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003426 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003427
Gilles Peskine8817f612018-12-18 00:18:46 +01003428 PSA_ASSERT( psa_cipher_update( &operation1,
3429 input->x + first_part_size,
3430 input->len - first_part_size,
3431 output1, output1_buffer_size,
3432 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003433 output1_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003434
Gilles Peskine8817f612018-12-18 00:18:46 +01003435 PSA_ASSERT( psa_cipher_finish( &operation1,
3436 output1 + output1_length,
3437 output1_buffer_size - output1_length,
3438 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003439 output1_length += function_output_length;
mohammad1603d7d7ba52018-03-12 18:51:53 +02003440
Gilles Peskine8817f612018-12-18 00:18:46 +01003441 PSA_ASSERT( psa_cipher_abort( &operation1 ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003442
Gilles Peskine048b7f02018-06-08 14:20:49 +02003443 output2_buffer_size = output1_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003444 ASSERT_ALLOC( output2, output2_buffer_size );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003445
Gilles Peskine8817f612018-12-18 00:18:46 +01003446 PSA_ASSERT( psa_cipher_set_iv( &operation2,
3447 iv, iv_length ) );
Moran Pekerded84402018-06-06 16:36:50 +03003448
Gilles Peskine8817f612018-12-18 00:18:46 +01003449 PSA_ASSERT( psa_cipher_update( &operation2, output1, first_part_size,
3450 output2, output2_buffer_size,
3451 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003452 output2_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003453
Gilles Peskine8817f612018-12-18 00:18:46 +01003454 PSA_ASSERT( psa_cipher_update( &operation2,
3455 output1 + first_part_size,
3456 output1_length - first_part_size,
3457 output2, output2_buffer_size,
3458 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003459 output2_length += function_output_length;
Moran Pekerded84402018-06-06 16:36:50 +03003460
Gilles Peskine8817f612018-12-18 00:18:46 +01003461 PSA_ASSERT( psa_cipher_finish( &operation2,
3462 output2 + output2_length,
3463 output2_buffer_size - output2_length,
3464 &function_output_length ) );
Gilles Peskine048b7f02018-06-08 14:20:49 +02003465 output2_length += function_output_length;
Gilles Peskine4ca9c3f2018-06-06 18:44:09 +02003466
Gilles Peskine8817f612018-12-18 00:18:46 +01003467 PSA_ASSERT( psa_cipher_abort( &operation2 ) );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003468
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003469 ASSERT_COMPARE( input->x, input->len, output2, output2_length );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003470
3471exit:
itayzafrir3e02b3b2018-06-12 17:06:52 +03003472 mbedtls_free( output1 );
3473 mbedtls_free( output2 );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003474 psa_destroy_key( handle );
mohammad1603d7d7ba52018-03-12 18:51:53 +02003475 mbedtls_psa_crypto_free( );
3476}
3477/* END_CASE */
Gilles Peskine7268afc2018-06-06 15:19:24 +02003478
Gilles Peskine20035e32018-02-03 22:44:14 +01003479/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003480void aead_encrypt_decrypt( int key_type_arg, data_t *key_data,
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003481 int alg_arg,
Gilles Peskine7da96b02018-08-17 18:45:42 +02003482 data_t *nonce,
3483 data_t *additional_data,
3484 data_t *input_data,
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003485 int expected_result_arg )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003486{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003487 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003488 psa_key_type_t key_type = key_type_arg;
3489 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003490 unsigned char *output_data = NULL;
3491 size_t output_size = 0;
3492 size_t output_length = 0;
3493 unsigned char *output_data2 = NULL;
3494 size_t output_length2 = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003495 size_t tag_length = 16;
Gilles Peskine4abf7412018-06-18 16:35:34 +02003496 psa_status_t expected_result = expected_result_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003497 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003498
Gilles Peskine4abf7412018-06-18 16:35:34 +02003499 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003500 ASSERT_ALLOC( output_data, output_size );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003501
Gilles Peskine8817f612018-12-18 00:18:46 +01003502 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003503
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003504 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003505 psa_key_policy_set_usage( &policy,
3506 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
3507 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003508 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003509
Gilles Peskine87a5e562019-04-17 12:28:25 +02003510 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003511 key_data->x, key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003512
Gilles Peskinefe11b722018-12-18 00:24:04 +01003513 TEST_EQUAL( psa_aead_encrypt( handle, alg,
3514 nonce->x, nonce->len,
3515 additional_data->x,
3516 additional_data->len,
3517 input_data->x, input_data->len,
3518 output_data, output_size,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003519 &output_length ),
3520 expected_result );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003521
3522 if( PSA_SUCCESS == expected_result )
3523 {
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003524 ASSERT_ALLOC( output_data2, output_length );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003525
Gilles Peskinefe11b722018-12-18 00:24:04 +01003526 TEST_EQUAL( psa_aead_decrypt( handle, alg,
3527 nonce->x, nonce->len,
3528 additional_data->x,
3529 additional_data->len,
3530 output_data, output_length,
3531 output_data2, output_length,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003532 &output_length2 ),
3533 expected_result );
Gilles Peskine2d277862018-06-18 15:41:12 +02003534
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003535 ASSERT_COMPARE( input_data->x, input_data->len,
3536 output_data2, output_length2 );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003537 }
Gilles Peskine2d277862018-06-18 15:41:12 +02003538
Gilles Peskinea1cac842018-06-11 19:33:02 +02003539exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003540 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003541 mbedtls_free( output_data );
3542 mbedtls_free( output_data2 );
3543 mbedtls_psa_crypto_free( );
3544}
3545/* END_CASE */
3546
3547/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003548void aead_encrypt( int key_type_arg, data_t *key_data,
3549 int alg_arg,
3550 data_t *nonce,
3551 data_t *additional_data,
3552 data_t *input_data,
3553 data_t *expected_result )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003554{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003555 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003556 psa_key_type_t key_type = key_type_arg;
3557 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003558 unsigned char *output_data = NULL;
3559 size_t output_size = 0;
3560 size_t output_length = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003561 size_t tag_length = 16;
Jaeden Amero70261c52019-01-04 11:47:20 +00003562 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003563
Gilles Peskine4abf7412018-06-18 16:35:34 +02003564 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003565 ASSERT_ALLOC( output_data, output_size );
Gilles Peskine2d277862018-06-18 15:41:12 +02003566
Gilles Peskine8817f612018-12-18 00:18:46 +01003567 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003568
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003569 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003570 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT , alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003571 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003572
Gilles Peskine87a5e562019-04-17 12:28:25 +02003573 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003574 key_data->x,
3575 key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003576
Gilles Peskine8817f612018-12-18 00:18:46 +01003577 PSA_ASSERT( psa_aead_encrypt( handle, alg,
3578 nonce->x, nonce->len,
3579 additional_data->x, additional_data->len,
3580 input_data->x, input_data->len,
3581 output_data, output_size,
3582 &output_length ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003583
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003584 ASSERT_COMPARE( expected_result->x, expected_result->len,
3585 output_data, output_length );
Gilles Peskine2d277862018-06-18 15:41:12 +02003586
Gilles Peskinea1cac842018-06-11 19:33:02 +02003587exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003588 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003589 mbedtls_free( output_data );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003590 mbedtls_psa_crypto_free( );
3591}
3592/* END_CASE */
3593
3594/* BEGIN_CASE */
Gilles Peskine7da96b02018-08-17 18:45:42 +02003595void aead_decrypt( int key_type_arg, data_t *key_data,
3596 int alg_arg,
3597 data_t *nonce,
3598 data_t *additional_data,
3599 data_t *input_data,
3600 data_t *expected_data,
3601 int expected_result_arg )
Gilles Peskinea1cac842018-06-11 19:33:02 +02003602{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003603 psa_key_handle_t handle = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003604 psa_key_type_t key_type = key_type_arg;
3605 psa_algorithm_t alg = alg_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003606 unsigned char *output_data = NULL;
3607 size_t output_size = 0;
3608 size_t output_length = 0;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003609 size_t tag_length = 16;
Jaeden Amero70261c52019-01-04 11:47:20 +00003610 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine4abf7412018-06-18 16:35:34 +02003611 psa_status_t expected_result = expected_result_arg;
Gilles Peskinea1cac842018-06-11 19:33:02 +02003612
Gilles Peskine4abf7412018-06-18 16:35:34 +02003613 output_size = input_data->len + tag_length;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003614 ASSERT_ALLOC( output_data, output_size );
Gilles Peskine2d277862018-06-18 15:41:12 +02003615
Gilles Peskine8817f612018-12-18 00:18:46 +01003616 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003617
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003618 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003619 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT , alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003620 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003621
Gilles Peskine87a5e562019-04-17 12:28:25 +02003622 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003623 key_data->x,
3624 key_data->len ) );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003625
Gilles Peskinefe11b722018-12-18 00:24:04 +01003626 TEST_EQUAL( psa_aead_decrypt( handle, alg,
3627 nonce->x, nonce->len,
3628 additional_data->x,
3629 additional_data->len,
3630 input_data->x, input_data->len,
3631 output_data, output_size,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003632 &output_length ),
3633 expected_result );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003634
Gilles Peskine2d277862018-06-18 15:41:12 +02003635 if( expected_result == PSA_SUCCESS )
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003636 ASSERT_COMPARE( expected_data->x, expected_data->len,
3637 output_data, output_length );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003638
Gilles Peskinea1cac842018-06-11 19:33:02 +02003639exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003640 psa_destroy_key( handle );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003641 mbedtls_free( output_data );
Gilles Peskinea1cac842018-06-11 19:33:02 +02003642 mbedtls_psa_crypto_free( );
3643}
3644/* END_CASE */
3645
3646/* BEGIN_CASE */
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003647void signature_size( int type_arg,
3648 int bits,
3649 int alg_arg,
3650 int expected_size_arg )
Gilles Peskinee59236f2018-01-27 23:32:46 +01003651{
3652 psa_key_type_t type = type_arg;
3653 psa_algorithm_t alg = alg_arg;
Gilles Peskine2d277862018-06-18 15:41:12 +02003654 size_t actual_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( type, bits, alg );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003655 TEST_EQUAL( actual_size, (size_t) expected_size_arg );
Gilles Peskinee59236f2018-01-27 23:32:46 +01003656exit:
3657 ;
3658}
3659/* END_CASE */
3660
3661/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003662void sign_deterministic( int key_type_arg, data_t *key_data,
3663 int alg_arg, data_t *input_data,
3664 data_t *output_data )
Gilles Peskinee59236f2018-01-27 23:32:46 +01003665{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003666 psa_key_handle_t handle = 0;
Gilles Peskinee59236f2018-01-27 23:32:46 +01003667 psa_key_type_t key_type = key_type_arg;
3668 psa_algorithm_t alg = alg_arg;
Gilles Peskine20035e32018-02-03 22:44:14 +01003669 size_t key_bits;
Gilles Peskine20035e32018-02-03 22:44:14 +01003670 unsigned char *signature = NULL;
3671 size_t signature_size;
3672 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003673 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine20035e32018-02-03 22:44:14 +01003674
Gilles Peskine8817f612018-12-18 00:18:46 +01003675 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003676
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003677 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003678 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003679 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad1603a97cb8c2018-03-28 03:46:26 -07003680
Gilles Peskine87a5e562019-04-17 12:28:25 +02003681 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003682 key_data->x,
3683 key_data->len ) );
3684 PSA_ASSERT( psa_get_key_information( handle,
3685 NULL,
3686 &key_bits ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003687
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003688 /* Allocate a buffer which has the size advertized by the
3689 * library. */
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003690 signature_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( key_type,
3691 key_bits, alg );
Gilles Peskine20035e32018-02-03 22:44:14 +01003692 TEST_ASSERT( signature_size != 0 );
Gilles Peskine69c12672018-06-28 00:07:19 +02003693 TEST_ASSERT( signature_size <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003694 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003695
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003696 /* Perform the signature. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003697 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
3698 input_data->x, input_data->len,
3699 signature, signature_size,
3700 &signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003701 /* Verify that the signature is what is expected. */
Gilles Peskinebd7dea92018-09-27 13:57:19 +02003702 ASSERT_COMPARE( output_data->x, output_data->len,
3703 signature, signature_length );
Gilles Peskine20035e32018-02-03 22:44:14 +01003704
3705exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003706 psa_destroy_key( handle );
Gilles Peskine0189e752018-02-03 23:57:22 +01003707 mbedtls_free( signature );
Gilles Peskine20035e32018-02-03 22:44:14 +01003708 mbedtls_psa_crypto_free( );
3709}
3710/* END_CASE */
3711
3712/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003713void sign_fail( int key_type_arg, data_t *key_data,
3714 int alg_arg, data_t *input_data,
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003715 int signature_size_arg, int expected_status_arg )
Gilles Peskine20035e32018-02-03 22:44:14 +01003716{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003717 psa_key_handle_t handle = 0;
Gilles Peskine20035e32018-02-03 22:44:14 +01003718 psa_key_type_t key_type = key_type_arg;
3719 psa_algorithm_t alg = alg_arg;
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003720 size_t signature_size = signature_size_arg;
Gilles Peskine20035e32018-02-03 22:44:14 +01003721 psa_status_t actual_status;
3722 psa_status_t expected_status = expected_status_arg;
Gilles Peskine40f68b92018-03-07 16:43:36 +01003723 unsigned char *signature = NULL;
Gilles Peskine93aa0332018-02-03 23:58:03 +01003724 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003725 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine20035e32018-02-03 22:44:14 +01003726
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003727 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003728
Gilles Peskine8817f612018-12-18 00:18:46 +01003729 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003730
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003731 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003732 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003733 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
mohammad1603a97cb8c2018-03-28 03:46:26 -07003734
Gilles Peskine87a5e562019-04-17 12:28:25 +02003735 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003736 key_data->x,
3737 key_data->len ) );
Gilles Peskine20035e32018-02-03 22:44:14 +01003738
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003739 actual_status = psa_asymmetric_sign( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003740 input_data->x, input_data->len,
Gilles Peskine20035e32018-02-03 22:44:14 +01003741 signature, signature_size,
3742 &signature_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003743 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine860ce9d2018-06-28 12:23:00 +02003744 /* The value of *signature_length is unspecified on error, but
3745 * whatever it is, it should be less than signature_size, so that
3746 * if the caller tries to read *signature_length bytes without
3747 * checking the error code then they don't overflow a buffer. */
3748 TEST_ASSERT( signature_length <= signature_size );
Gilles Peskine20035e32018-02-03 22:44:14 +01003749
3750exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003751 psa_destroy_key( handle );
Gilles Peskine20035e32018-02-03 22:44:14 +01003752 mbedtls_free( signature );
3753 mbedtls_psa_crypto_free( );
3754}
3755/* END_CASE */
mohammad16038cc1cee2018-03-28 01:21:33 +03003756
3757/* BEGIN_CASE */
Gilles Peskine9911b022018-06-29 17:30:48 +02003758void sign_verify( int key_type_arg, data_t *key_data,
3759 int alg_arg, data_t *input_data )
3760{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003761 psa_key_handle_t handle = 0;
Gilles Peskine9911b022018-06-29 17:30:48 +02003762 psa_key_type_t key_type = key_type_arg;
3763 psa_algorithm_t alg = alg_arg;
3764 size_t key_bits;
3765 unsigned char *signature = NULL;
3766 size_t signature_size;
3767 size_t signature_length = 0xdeadbeef;
Jaeden Amero70261c52019-01-04 11:47:20 +00003768 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine9911b022018-06-29 17:30:48 +02003769
Gilles Peskine8817f612018-12-18 00:18:46 +01003770 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003771
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003772 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003773 psa_key_policy_set_usage( &policy,
3774 PSA_KEY_USAGE_SIGN | PSA_KEY_USAGE_VERIFY,
3775 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003776 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003777
Gilles Peskine87a5e562019-04-17 12:28:25 +02003778 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003779 key_data->x,
3780 key_data->len ) );
3781 PSA_ASSERT( psa_get_key_information( handle,
3782 NULL,
3783 &key_bits ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003784
3785 /* Allocate a buffer which has the size advertized by the
3786 * library. */
3787 signature_size = PSA_ASYMMETRIC_SIGN_OUTPUT_SIZE( key_type,
3788 key_bits, alg );
3789 TEST_ASSERT( signature_size != 0 );
3790 TEST_ASSERT( signature_size <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003791 ASSERT_ALLOC( signature, signature_size );
Gilles Peskine9911b022018-06-29 17:30:48 +02003792
3793 /* Perform the signature. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003794 PSA_ASSERT( psa_asymmetric_sign( handle, alg,
3795 input_data->x, input_data->len,
3796 signature, signature_size,
3797 &signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003798 /* Check that the signature length looks sensible. */
3799 TEST_ASSERT( signature_length <= signature_size );
3800 TEST_ASSERT( signature_length > 0 );
3801
3802 /* Use the library to verify that the signature is correct. */
Gilles Peskine8817f612018-12-18 00:18:46 +01003803 PSA_ASSERT( psa_asymmetric_verify(
3804 handle, alg,
3805 input_data->x, input_data->len,
3806 signature, signature_length ) );
Gilles Peskine9911b022018-06-29 17:30:48 +02003807
3808 if( input_data->len != 0 )
3809 {
3810 /* Flip a bit in the input and verify that the signature is now
3811 * detected as invalid. Flip a bit at the beginning, not at the end,
3812 * because ECDSA may ignore the last few bits of the input. */
3813 input_data->x[0] ^= 1;
Gilles Peskinef812dcf2018-12-18 00:33:25 +01003814 TEST_EQUAL( psa_asymmetric_verify( handle, alg,
3815 input_data->x, input_data->len,
3816 signature, signature_length ),
3817 PSA_ERROR_INVALID_SIGNATURE );
Gilles Peskine9911b022018-06-29 17:30:48 +02003818 }
3819
3820exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003821 psa_destroy_key( handle );
Gilles Peskine9911b022018-06-29 17:30:48 +02003822 mbedtls_free( signature );
3823 mbedtls_psa_crypto_free( );
3824}
3825/* END_CASE */
3826
3827/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003828void asymmetric_verify( int key_type_arg, data_t *key_data,
3829 int alg_arg, data_t *hash_data,
3830 data_t *signature_data )
itayzafrir5c753392018-05-08 11:18:38 +03003831{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003832 psa_key_handle_t handle = 0;
itayzafrir5c753392018-05-08 11:18:38 +03003833 psa_key_type_t key_type = key_type_arg;
3834 psa_algorithm_t alg = alg_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003835 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
itayzafrir5c753392018-05-08 11:18:38 +03003836
Gilles Peskine69c12672018-06-28 00:07:19 +02003837 TEST_ASSERT( signature_data->len <= PSA_ASYMMETRIC_SIGNATURE_MAX_SIZE );
3838
Gilles Peskine8817f612018-12-18 00:18:46 +01003839 PSA_ASSERT( psa_crypto_init( ) );
itayzafrir5c753392018-05-08 11:18:38 +03003840
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003841 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003842 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003843 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
itayzafrir5c753392018-05-08 11:18:38 +03003844
Gilles Peskine87a5e562019-04-17 12:28:25 +02003845 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003846 key_data->x,
3847 key_data->len ) );
itayzafrir5c753392018-05-08 11:18:38 +03003848
Gilles Peskine8817f612018-12-18 00:18:46 +01003849 PSA_ASSERT( psa_asymmetric_verify( handle, alg,
3850 hash_data->x, hash_data->len,
3851 signature_data->x,
3852 signature_data->len ) );
itayzafrir5c753392018-05-08 11:18:38 +03003853exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003854 psa_destroy_key( handle );
itayzafrir5c753392018-05-08 11:18:38 +03003855 mbedtls_psa_crypto_free( );
3856}
3857/* END_CASE */
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003858
3859/* BEGIN_CASE */
itayzafrir3e02b3b2018-06-12 17:06:52 +03003860void asymmetric_verify_fail( int key_type_arg, data_t *key_data,
3861 int alg_arg, data_t *hash_data,
3862 data_t *signature_data,
3863 int expected_status_arg )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003864{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003865 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003866 psa_key_type_t key_type = key_type_arg;
3867 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003868 psa_status_t actual_status;
3869 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003870 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003871
Gilles Peskine8817f612018-12-18 00:18:46 +01003872 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003873
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003874 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02003875 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_VERIFY, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003876 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03003877
Gilles Peskine87a5e562019-04-17 12:28:25 +02003878 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003879 key_data->x,
3880 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003881
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003882 actual_status = psa_asymmetric_verify( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003883 hash_data->x, hash_data->len,
Gilles Peskine2d277862018-06-18 15:41:12 +02003884 signature_data->x,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003885 signature_data->len );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003886
Gilles Peskinefe11b722018-12-18 00:24:04 +01003887 TEST_EQUAL( actual_status, expected_status );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003888
3889exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003890 psa_destroy_key( handle );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003891 mbedtls_psa_crypto_free( );
3892}
3893/* END_CASE */
3894
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003895/* BEGIN_CASE */
Gilles Peskine656896e2018-06-29 19:12:28 +02003896void asymmetric_encrypt( int key_type_arg,
3897 data_t *key_data,
3898 int alg_arg,
3899 data_t *input_data,
Gilles Peskine68428122018-06-30 18:42:41 +02003900 data_t *label,
Gilles Peskine656896e2018-06-29 19:12:28 +02003901 int expected_output_length_arg,
3902 int expected_status_arg )
3903{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003904 psa_key_handle_t handle = 0;
Gilles Peskine656896e2018-06-29 19:12:28 +02003905 psa_key_type_t key_type = key_type_arg;
3906 psa_algorithm_t alg = alg_arg;
3907 size_t expected_output_length = expected_output_length_arg;
3908 size_t key_bits;
3909 unsigned char *output = NULL;
3910 size_t output_size;
3911 size_t output_length = ~0;
3912 psa_status_t actual_status;
3913 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00003914 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine656896e2018-06-29 19:12:28 +02003915
Gilles Peskine8817f612018-12-18 00:18:46 +01003916 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003917
Gilles Peskine656896e2018-06-29 19:12:28 +02003918 /* Import the key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003919 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003920 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_ENCRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003921 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02003922 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003923 key_data->x,
3924 key_data->len ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003925
3926 /* Determine the maximum output length */
Gilles Peskine8817f612018-12-18 00:18:46 +01003927 PSA_ASSERT( psa_get_key_information( handle,
3928 NULL,
3929 &key_bits ) );
Gilles Peskine656896e2018-06-29 19:12:28 +02003930 output_size = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits, alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02003931 ASSERT_ALLOC( output, output_size );
Gilles Peskine656896e2018-06-29 19:12:28 +02003932
3933 /* Encrypt the input */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003934 actual_status = psa_asymmetric_encrypt( handle, alg,
Gilles Peskine656896e2018-06-29 19:12:28 +02003935 input_data->x, input_data->len,
Gilles Peskine68428122018-06-30 18:42:41 +02003936 label->x, label->len,
Gilles Peskine656896e2018-06-29 19:12:28 +02003937 output, output_size,
3938 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003939 TEST_EQUAL( actual_status, expected_status );
3940 TEST_EQUAL( output_length, expected_output_length );
Gilles Peskine656896e2018-06-29 19:12:28 +02003941
Gilles Peskine68428122018-06-30 18:42:41 +02003942 /* If the label is empty, the test framework puts a non-null pointer
3943 * in label->x. Test that a null pointer works as well. */
3944 if( label->len == 0 )
3945 {
3946 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02003947 if( output_size != 0 )
3948 memset( output, 0, output_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003949 actual_status = psa_asymmetric_encrypt( handle, alg,
Gilles Peskine68428122018-06-30 18:42:41 +02003950 input_data->x, input_data->len,
3951 NULL, label->len,
3952 output, output_size,
3953 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01003954 TEST_EQUAL( actual_status, expected_status );
3955 TEST_EQUAL( output_length, expected_output_length );
Gilles Peskine68428122018-06-30 18:42:41 +02003956 }
3957
Gilles Peskine656896e2018-06-29 19:12:28 +02003958exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003959 psa_destroy_key( handle );
Gilles Peskine656896e2018-06-29 19:12:28 +02003960 mbedtls_free( output );
3961 mbedtls_psa_crypto_free( );
3962}
3963/* END_CASE */
3964
3965/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02003966void asymmetric_encrypt_decrypt( int key_type_arg,
3967 data_t *key_data,
3968 int alg_arg,
3969 data_t *input_data,
3970 data_t *label )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003971{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01003972 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003973 psa_key_type_t key_type = key_type_arg;
3974 psa_algorithm_t alg = alg_arg;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003975 size_t key_bits;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003976 unsigned char *output = NULL;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003977 size_t output_size;
3978 size_t output_length = ~0;
Nir Sonnenschein0f3bdbd2018-05-02 23:56:12 +03003979 unsigned char *output2 = NULL;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003980 size_t output2_size;
3981 size_t output2_length = ~0;
Jaeden Amero70261c52019-01-04 11:47:20 +00003982 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003983
Gilles Peskine8817f612018-12-18 00:18:46 +01003984 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03003985
Gilles Peskined40c1fb2019-01-19 12:20:52 +01003986 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskinec1bb6c82018-06-18 16:04:39 +02003987 psa_key_policy_set_usage( &policy,
3988 PSA_KEY_USAGE_ENCRYPT | PSA_KEY_USAGE_DECRYPT,
Gilles Peskine4abf7412018-06-18 16:35:34 +02003989 alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01003990 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03003991
Gilles Peskine87a5e562019-04-17 12:28:25 +02003992 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01003993 key_data->x,
3994 key_data->len ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02003995
3996 /* Determine the maximum ciphertext length */
Gilles Peskine8817f612018-12-18 00:18:46 +01003997 PSA_ASSERT( psa_get_key_information( handle,
3998 NULL,
3999 &key_bits ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004000 output_size = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE( key_type, key_bits, alg );
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004001 ASSERT_ALLOC( output, output_size );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004002 output2_size = input_data->len;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004003 ASSERT_ALLOC( output2, output2_size );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004004
Gilles Peskineeebd7382018-06-08 18:11:54 +02004005 /* We test encryption by checking that encrypt-then-decrypt gives back
4006 * the original plaintext because of the non-optional random
4007 * part of encryption process which prevents using fixed vectors. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004008 PSA_ASSERT( psa_asymmetric_encrypt( handle, alg,
4009 input_data->x, input_data->len,
4010 label->x, label->len,
4011 output, output_size,
4012 &output_length ) );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004013 /* We don't know what ciphertext length to expect, but check that
4014 * it looks sensible. */
4015 TEST_ASSERT( output_length <= output_size );
Nir Sonnenschein0f3bdbd2018-05-02 23:56:12 +03004016
Gilles Peskine8817f612018-12-18 00:18:46 +01004017 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
4018 output, output_length,
4019 label->x, label->len,
4020 output2, output2_size,
4021 &output2_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02004022 ASSERT_COMPARE( input_data->x, input_data->len,
4023 output2, output2_length );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004024
4025exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004026 psa_destroy_key( handle );
itayzafrir3e02b3b2018-06-12 17:06:52 +03004027 mbedtls_free( output );
4028 mbedtls_free( output2 );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004029 mbedtls_psa_crypto_free( );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004030}
4031/* END_CASE */
4032
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004033/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02004034void asymmetric_decrypt( int key_type_arg,
4035 data_t *key_data,
4036 int alg_arg,
4037 data_t *input_data,
4038 data_t *label,
Gilles Peskine66763a02018-06-29 21:54:10 +02004039 data_t *expected_data )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004040{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004041 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004042 psa_key_type_t key_type = key_type_arg;
4043 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004044 unsigned char *output = NULL;
Nir Sonnenscheind70bc482018-06-04 16:31:13 +03004045 size_t output_size = 0;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004046 size_t output_length = ~0;
Jaeden Amero70261c52019-01-04 11:47:20 +00004047 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004048
Jaeden Amero412654a2019-02-06 12:57:46 +00004049 output_size = expected_data->len;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004050 ASSERT_ALLOC( output, output_size );
Gilles Peskine5b051bc2018-05-31 13:25:48 +02004051
Gilles Peskine8817f612018-12-18 00:18:46 +01004052 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004053
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004054 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02004055 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004056 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03004057
Gilles Peskine87a5e562019-04-17 12:28:25 +02004058 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004059 key_data->x,
4060 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004061
Gilles Peskine8817f612018-12-18 00:18:46 +01004062 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
4063 input_data->x, input_data->len,
4064 label->x, label->len,
4065 output,
4066 output_size,
4067 &output_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02004068 ASSERT_COMPARE( expected_data->x, expected_data->len,
4069 output, output_length );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004070
Gilles Peskine68428122018-06-30 18:42:41 +02004071 /* If the label is empty, the test framework puts a non-null pointer
4072 * in label->x. Test that a null pointer works as well. */
4073 if( label->len == 0 )
4074 {
4075 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02004076 if( output_size != 0 )
4077 memset( output, 0, output_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01004078 PSA_ASSERT( psa_asymmetric_decrypt( handle, alg,
4079 input_data->x, input_data->len,
4080 NULL, label->len,
4081 output,
4082 output_size,
4083 &output_length ) );
Gilles Peskinebd7dea92018-09-27 13:57:19 +02004084 ASSERT_COMPARE( expected_data->x, expected_data->len,
4085 output, output_length );
Gilles Peskine68428122018-06-30 18:42:41 +02004086 }
4087
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004088exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004089 psa_destroy_key( handle );
itayzafrir3e02b3b2018-06-12 17:06:52 +03004090 mbedtls_free( output );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004091 mbedtls_psa_crypto_free( );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004092}
4093/* END_CASE */
4094
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004095/* BEGIN_CASE */
Gilles Peskine68428122018-06-30 18:42:41 +02004096void asymmetric_decrypt_fail( int key_type_arg,
4097 data_t *key_data,
4098 int alg_arg,
4099 data_t *input_data,
4100 data_t *label,
Jaeden Amerof8daab72019-02-06 12:57:46 +00004101 int output_size_arg,
Gilles Peskine2d277862018-06-18 15:41:12 +02004102 int expected_status_arg )
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004103{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004104 psa_key_handle_t handle = 0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004105 psa_key_type_t key_type = key_type_arg;
4106 psa_algorithm_t alg = alg_arg;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004107 unsigned char *output = NULL;
Jaeden Amerof8daab72019-02-06 12:57:46 +00004108 size_t output_size = output_size_arg;
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004109 size_t output_length = ~0;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004110 psa_status_t actual_status;
4111 psa_status_t expected_status = expected_status_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00004112 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004113
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004114 ASSERT_ALLOC( output, output_size );
Gilles Peskine5b051bc2018-05-31 13:25:48 +02004115
Gilles Peskine8817f612018-12-18 00:18:46 +01004116 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004117
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004118 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine4abf7412018-06-18 16:35:34 +02004119 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DECRYPT, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004120 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheind7082602018-06-04 16:45:27 +03004121
Gilles Peskine87a5e562019-04-17 12:28:25 +02004122 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004123 key_data->x,
4124 key_data->len ) );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004125
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004126 actual_status = psa_asymmetric_decrypt( handle, alg,
Gilles Peskine4abf7412018-06-18 16:35:34 +02004127 input_data->x, input_data->len,
Gilles Peskine68428122018-06-30 18:42:41 +02004128 label->x, label->len,
Gilles Peskine4abf7412018-06-18 16:35:34 +02004129 output, output_size,
Gilles Peskine2d277862018-06-18 15:41:12 +02004130 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004131 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004132 TEST_ASSERT( output_length <= output_size );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004133
Gilles Peskine68428122018-06-30 18:42:41 +02004134 /* If the label is empty, the test framework puts a non-null pointer
4135 * in label->x. Test that a null pointer works as well. */
4136 if( label->len == 0 )
4137 {
4138 output_length = ~0;
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02004139 if( output_size != 0 )
4140 memset( output, 0, output_size );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004141 actual_status = psa_asymmetric_decrypt( handle, alg,
Gilles Peskine68428122018-06-30 18:42:41 +02004142 input_data->x, input_data->len,
4143 NULL, label->len,
4144 output, output_size,
4145 &output_length );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004146 TEST_EQUAL( actual_status, expected_status );
Gilles Peskine55c94dd2018-06-30 18:54:48 +02004147 TEST_ASSERT( output_length <= output_size );
Gilles Peskine68428122018-06-30 18:42:41 +02004148 }
4149
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004150exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004151 psa_destroy_key( handle );
Gilles Peskine2d277862018-06-18 15:41:12 +02004152 mbedtls_free( output );
Nir Sonnenschein39e59142018-05-02 23:16:26 +03004153 mbedtls_psa_crypto_free( );
4154}
Gilles Peskine5b051bc2018-05-31 13:25:48 +02004155/* END_CASE */
Gilles Peskine05d69892018-06-19 22:00:52 +02004156
4157/* BEGIN_CASE */
Jaeden Amerod94d6712019-01-04 14:11:48 +00004158void crypto_generator_init( )
4159{
4160 /* Test each valid way of initializing the object, except for `= {0}`, as
4161 * Clang 5 complains when `-Wmissing-field-initializers` is used, even
4162 * though it's OK by the C standard. We could test for this, but we'd need
4163 * to supress the Clang warning for the test. */
Jaeden Amero5229bbb2019-02-07 16:33:37 +00004164 size_t capacity;
Jaeden Amerod94d6712019-01-04 14:11:48 +00004165 psa_crypto_generator_t func = psa_crypto_generator_init( );
4166 psa_crypto_generator_t init = PSA_CRYPTO_GENERATOR_INIT;
4167 psa_crypto_generator_t zero;
4168
4169 memset( &zero, 0, sizeof( zero ) );
4170
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004171 /* A default generator should not be able to report its capacity. */
4172 TEST_EQUAL( psa_get_generator_capacity( &func, &capacity ),
4173 PSA_ERROR_BAD_STATE );
4174 TEST_EQUAL( psa_get_generator_capacity( &init, &capacity ),
4175 PSA_ERROR_BAD_STATE );
4176 TEST_EQUAL( psa_get_generator_capacity( &zero, &capacity ),
4177 PSA_ERROR_BAD_STATE );
Jaeden Amero5229bbb2019-02-07 16:33:37 +00004178
4179 /* A default generator should be abortable without error. */
4180 PSA_ASSERT( psa_generator_abort(&func) );
4181 PSA_ASSERT( psa_generator_abort(&init) );
4182 PSA_ASSERT( psa_generator_abort(&zero) );
Jaeden Amerod94d6712019-01-04 14:11:48 +00004183}
4184/* END_CASE */
4185
4186/* BEGIN_CASE */
Gilles Peskineea0fb492018-07-12 17:17:20 +02004187void derive_setup( int key_type_arg,
4188 data_t *key_data,
4189 int alg_arg,
4190 data_t *salt,
4191 data_t *label,
4192 int requested_capacity_arg,
4193 int expected_status_arg )
4194{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004195 psa_key_handle_t handle = 0;
Gilles Peskineea0fb492018-07-12 17:17:20 +02004196 size_t key_type = key_type_arg;
4197 psa_algorithm_t alg = alg_arg;
4198 size_t requested_capacity = requested_capacity_arg;
4199 psa_status_t expected_status = expected_status_arg;
4200 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004201 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskineea0fb492018-07-12 17:17:20 +02004202
Gilles Peskine8817f612018-12-18 00:18:46 +01004203 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004204
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004205 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004206 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004207 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004208
Gilles Peskine87a5e562019-04-17 12:28:25 +02004209 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004210 key_data->x,
4211 key_data->len ) );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004212
Gilles Peskinefe11b722018-12-18 00:24:04 +01004213 TEST_EQUAL( psa_key_derivation( &generator, handle, alg,
4214 salt->x, salt->len,
4215 label->x, label->len,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004216 requested_capacity ),
4217 expected_status );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004218
4219exit:
4220 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004221 psa_destroy_key( handle );
Gilles Peskineea0fb492018-07-12 17:17:20 +02004222 mbedtls_psa_crypto_free( );
4223}
4224/* END_CASE */
4225
4226/* BEGIN_CASE */
Nir Sonnenscheindd69d8b2018-11-01 12:24:23 +02004227void test_derive_invalid_generator_state( )
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004228{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004229 psa_key_handle_t handle = 0;
Nir Sonnenschein4eda37b2018-10-31 12:15:58 +02004230 size_t key_type = PSA_KEY_TYPE_DERIVE;
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004231 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Nir Sonnenschein1caf6d22018-11-01 12:27:20 +02004232 psa_algorithm_t alg = PSA_ALG_HKDF( PSA_ALG_SHA_256 );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004233 uint8_t buffer[42];
Nir Sonnenschein1caf6d22018-11-01 12:27:20 +02004234 size_t capacity = sizeof( buffer );
Nir Sonnenscheindd69d8b2018-11-01 12:24:23 +02004235 const uint8_t key_data[22] = { 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b,
4236 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b,
4237 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b};
Jaeden Amero70261c52019-01-04 11:47:20 +00004238 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004239
Gilles Peskine8817f612018-12-18 00:18:46 +01004240 PSA_ASSERT( psa_crypto_init( ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004241
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004242 PSA_ASSERT( psa_allocate_key( &handle ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004243 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004244 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004245
Gilles Peskine87a5e562019-04-17 12:28:25 +02004246 PSA_ASSERT( psa_import_key_to_handle( handle, key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004247 key_data,
4248 sizeof( key_data ) ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004249
4250 /* valid key derivation */
Gilles Peskine8817f612018-12-18 00:18:46 +01004251 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4252 NULL, 0,
4253 NULL, 0,
4254 capacity ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004255
4256 /* state of generator shouldn't allow additional generation */
Gilles Peskinefe11b722018-12-18 00:24:04 +01004257 TEST_EQUAL( psa_key_derivation( &generator, handle, alg,
4258 NULL, 0,
4259 NULL, 0,
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004260 capacity ),
4261 PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004262
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004263 PSA_ASSERT( psa_generator_read( &generator, buffer, capacity ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004264
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004265 TEST_EQUAL( psa_generator_read( &generator, buffer, capacity ),
David Saadab4ecc272019-02-14 13:48:10 +02004266 PSA_ERROR_INSUFFICIENT_DATA );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004267
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004268exit:
4269 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004270 psa_destroy_key( handle );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004271 mbedtls_psa_crypto_free( );
4272}
4273/* END_CASE */
4274
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004275/* BEGIN_CASE */
4276void test_derive_invalid_generator_tests( )
4277{
4278 uint8_t output_buffer[16];
4279 size_t buffer_size = 16;
4280 size_t capacity = 0;
4281 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4282
Nir Sonnenschein50789302018-10-31 12:16:38 +02004283 TEST_ASSERT( psa_generator_read( &generator, output_buffer, buffer_size )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004284 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004285
4286 TEST_ASSERT( psa_get_generator_capacity( &generator, &capacity )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004287 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004288
Gilles Peskine8817f612018-12-18 00:18:46 +01004289 PSA_ASSERT( psa_generator_abort( &generator ) );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004290
Nir Sonnenschein50789302018-10-31 12:16:38 +02004291 TEST_ASSERT( psa_generator_read( &generator, output_buffer, buffer_size )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004292 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004293
Nir Sonnenschein50789302018-10-31 12:16:38 +02004294 TEST_ASSERT( psa_get_generator_capacity( &generator, &capacity )
Jaeden Amerocf2010c2019-02-15 13:05:49 +00004295 == PSA_ERROR_BAD_STATE );
Nir Sonnenscheinb46e7ca2018-10-25 14:46:09 +03004296
4297exit:
4298 psa_generator_abort( &generator );
Nir Sonnenscheine5204c92018-10-22 17:24:55 +03004299}
4300/* END_CASE */
4301
4302/* BEGIN_CASE */
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004303void derive_output( int alg_arg,
4304 data_t *key_data,
4305 data_t *salt,
4306 data_t *label,
4307 int requested_capacity_arg,
4308 data_t *expected_output1,
4309 data_t *expected_output2 )
4310{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004311 psa_key_handle_t handle = 0;
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004312 psa_algorithm_t alg = alg_arg;
4313 size_t requested_capacity = requested_capacity_arg;
4314 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4315 uint8_t *expected_outputs[2] =
4316 {expected_output1->x, expected_output2->x};
4317 size_t output_sizes[2] =
4318 {expected_output1->len, expected_output2->len};
4319 size_t output_buffer_size = 0;
4320 uint8_t *output_buffer = NULL;
4321 size_t expected_capacity;
4322 size_t current_capacity;
Jaeden Amero70261c52019-01-04 11:47:20 +00004323 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004324 psa_status_t status;
4325 unsigned i;
4326
4327 for( i = 0; i < ARRAY_LENGTH( expected_outputs ); i++ )
4328 {
4329 if( output_sizes[i] > output_buffer_size )
4330 output_buffer_size = output_sizes[i];
4331 if( output_sizes[i] == 0 )
4332 expected_outputs[i] = NULL;
4333 }
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004334 ASSERT_ALLOC( output_buffer, output_buffer_size );
Gilles Peskine8817f612018-12-18 00:18:46 +01004335 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004336
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004337 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004338 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004339 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004340
Gilles Peskine87a5e562019-04-17 12:28:25 +02004341 PSA_ASSERT( psa_import_key_to_handle( handle, PSA_KEY_TYPE_DERIVE,
Gilles Peskine8817f612018-12-18 00:18:46 +01004342 key_data->x,
4343 key_data->len ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004344
4345 /* Extraction phase. */
Gilles Peskineb70a0fd2019-01-07 22:59:38 +01004346 if( PSA_ALG_IS_HKDF( alg ) )
4347 {
4348 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
4349 PSA_ASSERT( psa_set_generator_capacity( &generator,
4350 requested_capacity ) );
4351 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4352 PSA_KDF_STEP_SALT,
4353 salt->x, salt->len ) );
4354 PSA_ASSERT( psa_key_derivation_input_key( &generator,
4355 PSA_KDF_STEP_SECRET,
4356 handle ) );
4357 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4358 PSA_KDF_STEP_INFO,
4359 label->x, label->len ) );
4360 }
4361 else
4362 {
4363 // legacy
4364 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4365 salt->x, salt->len,
4366 label->x, label->len,
4367 requested_capacity ) );
4368 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004369 PSA_ASSERT( psa_get_generator_capacity( &generator,
4370 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004371 TEST_EQUAL( current_capacity, requested_capacity );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004372 expected_capacity = requested_capacity;
4373
4374 /* Expansion phase. */
4375 for( i = 0; i < ARRAY_LENGTH( expected_outputs ); i++ )
4376 {
4377 /* Read some bytes. */
4378 status = psa_generator_read( &generator,
4379 output_buffer, output_sizes[i] );
4380 if( expected_capacity == 0 && output_sizes[i] == 0 )
4381 {
4382 /* Reading 0 bytes when 0 bytes are available can go either way. */
4383 TEST_ASSERT( status == PSA_SUCCESS ||
David Saadab4ecc272019-02-14 13:48:10 +02004384 status == PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004385 continue;
4386 }
4387 else if( expected_capacity == 0 ||
4388 output_sizes[i] > expected_capacity )
4389 {
4390 /* Capacity exceeded. */
David Saadab4ecc272019-02-14 13:48:10 +02004391 TEST_EQUAL( status, PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004392 expected_capacity = 0;
4393 continue;
4394 }
4395 /* Success. Check the read data. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004396 PSA_ASSERT( status );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004397 if( output_sizes[i] != 0 )
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004398 ASSERT_COMPARE( output_buffer, output_sizes[i],
4399 expected_outputs[i], output_sizes[i] );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004400 /* Check the generator status. */
4401 expected_capacity -= output_sizes[i];
Gilles Peskine8817f612018-12-18 00:18:46 +01004402 PSA_ASSERT( psa_get_generator_capacity( &generator,
4403 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004404 TEST_EQUAL( expected_capacity, current_capacity );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004405 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004406 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004407
4408exit:
4409 mbedtls_free( output_buffer );
4410 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004411 psa_destroy_key( handle );
Gilles Peskine96ee5c72018-07-12 17:24:54 +02004412 mbedtls_psa_crypto_free( );
4413}
4414/* END_CASE */
4415
4416/* BEGIN_CASE */
Gilles Peskined54931c2018-07-17 21:06:59 +02004417void derive_full( int alg_arg,
4418 data_t *key_data,
4419 data_t *salt,
4420 data_t *label,
4421 int requested_capacity_arg )
4422{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004423 psa_key_handle_t handle = 0;
Gilles Peskined54931c2018-07-17 21:06:59 +02004424 psa_algorithm_t alg = alg_arg;
4425 size_t requested_capacity = requested_capacity_arg;
4426 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
4427 unsigned char output_buffer[16];
4428 size_t expected_capacity = requested_capacity;
4429 size_t current_capacity;
Jaeden Amero70261c52019-01-04 11:47:20 +00004430 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskined54931c2018-07-17 21:06:59 +02004431
Gilles Peskine8817f612018-12-18 00:18:46 +01004432 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004433
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004434 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004435 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004436 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004437
Gilles Peskine87a5e562019-04-17 12:28:25 +02004438 PSA_ASSERT( psa_import_key_to_handle( handle, PSA_KEY_TYPE_DERIVE,
Gilles Peskine8817f612018-12-18 00:18:46 +01004439 key_data->x,
4440 key_data->len ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004441
4442 /* Extraction phase. */
Gilles Peskineb70a0fd2019-01-07 22:59:38 +01004443 if( PSA_ALG_IS_HKDF( alg ) )
4444 {
4445 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
4446 PSA_ASSERT( psa_set_generator_capacity( &generator,
4447 requested_capacity ) );
4448 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4449 PSA_KDF_STEP_SALT,
4450 salt->x, salt->len ) );
4451 PSA_ASSERT( psa_key_derivation_input_key( &generator,
4452 PSA_KDF_STEP_SECRET,
4453 handle ) );
4454 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4455 PSA_KDF_STEP_INFO,
4456 label->x, label->len ) );
4457 }
4458 else
4459 {
4460 // legacy
4461 PSA_ASSERT( psa_key_derivation( &generator, handle, alg,
4462 salt->x, salt->len,
4463 label->x, label->len,
4464 requested_capacity ) );
4465 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004466 PSA_ASSERT( psa_get_generator_capacity( &generator,
4467 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004468 TEST_EQUAL( current_capacity, expected_capacity );
Gilles Peskined54931c2018-07-17 21:06:59 +02004469
4470 /* Expansion phase. */
4471 while( current_capacity > 0 )
4472 {
4473 size_t read_size = sizeof( output_buffer );
4474 if( read_size > current_capacity )
4475 read_size = current_capacity;
Gilles Peskine8817f612018-12-18 00:18:46 +01004476 PSA_ASSERT( psa_generator_read( &generator,
4477 output_buffer,
4478 read_size ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004479 expected_capacity -= read_size;
Gilles Peskine8817f612018-12-18 00:18:46 +01004480 PSA_ASSERT( psa_get_generator_capacity( &generator,
4481 &current_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004482 TEST_EQUAL( current_capacity, expected_capacity );
Gilles Peskined54931c2018-07-17 21:06:59 +02004483 }
4484
4485 /* Check that the generator refuses to go over capacity. */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004486 TEST_EQUAL( psa_generator_read( &generator, output_buffer, 1 ),
David Saadab4ecc272019-02-14 13:48:10 +02004487 PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskined54931c2018-07-17 21:06:59 +02004488
Gilles Peskine8817f612018-12-18 00:18:46 +01004489 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskined54931c2018-07-17 21:06:59 +02004490
4491exit:
4492 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004493 psa_destroy_key( handle );
Gilles Peskined54931c2018-07-17 21:06:59 +02004494 mbedtls_psa_crypto_free( );
4495}
4496/* END_CASE */
4497
4498/* BEGIN_CASE */
Gilles Peskine0386fba2018-07-12 17:29:22 +02004499void derive_key_exercise( int alg_arg,
4500 data_t *key_data,
4501 data_t *salt,
4502 data_t *label,
4503 int derived_type_arg,
4504 int derived_bits_arg,
4505 int derived_usage_arg,
4506 int derived_alg_arg )
4507{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004508 psa_key_handle_t base_handle = 0;
4509 psa_key_handle_t derived_handle = 0;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004510 psa_algorithm_t alg = alg_arg;
4511 psa_key_type_t derived_type = derived_type_arg;
4512 size_t derived_bits = derived_bits_arg;
4513 psa_key_usage_t derived_usage = derived_usage_arg;
4514 psa_algorithm_t derived_alg = derived_alg_arg;
4515 size_t capacity = PSA_BITS_TO_BYTES( derived_bits );
4516 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004517 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004518 psa_key_type_t got_type;
4519 size_t got_bits;
4520
Gilles Peskine8817f612018-12-18 00:18:46 +01004521 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004522
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004523 PSA_ASSERT( psa_allocate_key( &base_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004524 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004525 PSA_ASSERT( psa_set_key_policy( base_handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004526 PSA_ASSERT( psa_import_key_to_handle( base_handle, PSA_KEY_TYPE_DERIVE,
Gilles Peskine8817f612018-12-18 00:18:46 +01004527 key_data->x,
4528 key_data->len ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004529
4530 /* Derive a key. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004531 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4532 salt->x, salt->len,
4533 label->x, label->len,
4534 capacity ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004535 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004536 psa_key_policy_set_usage( &policy, derived_usage, derived_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004537 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004538 PSA_ASSERT( psa_generator_import_key_to_handle( derived_handle,
Gilles Peskine8817f612018-12-18 00:18:46 +01004539 derived_type,
4540 derived_bits,
4541 &generator ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004542
4543 /* Test the key information */
Gilles Peskine8817f612018-12-18 00:18:46 +01004544 PSA_ASSERT( psa_get_key_information( derived_handle,
4545 &got_type,
4546 &got_bits ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004547 TEST_EQUAL( got_type, derived_type );
4548 TEST_EQUAL( got_bits, derived_bits );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004549
4550 /* Exercise the derived key. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004551 if( ! exercise_key( derived_handle, derived_usage, derived_alg ) )
Gilles Peskine0386fba2018-07-12 17:29:22 +02004552 goto exit;
4553
4554exit:
4555 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004556 psa_destroy_key( base_handle );
4557 psa_destroy_key( derived_handle );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004558 mbedtls_psa_crypto_free( );
4559}
4560/* END_CASE */
4561
4562/* BEGIN_CASE */
4563void derive_key_export( int alg_arg,
4564 data_t *key_data,
4565 data_t *salt,
4566 data_t *label,
4567 int bytes1_arg,
4568 int bytes2_arg )
4569{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004570 psa_key_handle_t base_handle = 0;
4571 psa_key_handle_t derived_handle = 0;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004572 psa_algorithm_t alg = alg_arg;
4573 size_t bytes1 = bytes1_arg;
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004574 size_t derived_bits = PSA_BYTES_TO_BITS( bytes1 );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004575 size_t bytes2 = bytes2_arg;
4576 size_t capacity = bytes1 + bytes2;
4577 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004578 uint8_t *output_buffer = NULL;
4579 uint8_t *export_buffer = NULL;
Jaeden Amero70261c52019-01-04 11:47:20 +00004580 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine0386fba2018-07-12 17:29:22 +02004581 size_t length;
4582
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004583 ASSERT_ALLOC( output_buffer, capacity );
4584 ASSERT_ALLOC( export_buffer, capacity );
Gilles Peskine8817f612018-12-18 00:18:46 +01004585 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004586
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004587 PSA_ASSERT( psa_allocate_key( &base_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004588 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004589 PSA_ASSERT( psa_set_key_policy( base_handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004590 PSA_ASSERT( psa_import_key_to_handle( base_handle, PSA_KEY_TYPE_DERIVE,
Gilles Peskine8817f612018-12-18 00:18:46 +01004591 key_data->x,
4592 key_data->len ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004593
4594 /* Derive some material and output it. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004595 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4596 salt->x, salt->len,
4597 label->x, label->len,
4598 capacity ) );
4599 PSA_ASSERT( psa_generator_read( &generator,
4600 output_buffer,
4601 capacity ) );
4602 PSA_ASSERT( psa_generator_abort( &generator ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004603
4604 /* Derive the same output again, but this time store it in key objects. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004605 PSA_ASSERT( psa_key_derivation( &generator, base_handle, alg,
4606 salt->x, salt->len,
4607 label->x, label->len,
4608 capacity ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004609 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004610 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_EXPORT, 0 );
Gilles Peskine8817f612018-12-18 00:18:46 +01004611 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004612 PSA_ASSERT( psa_generator_import_key_to_handle( derived_handle,
Gilles Peskine8817f612018-12-18 00:18:46 +01004613 PSA_KEY_TYPE_RAW_DATA,
4614 derived_bits,
4615 &generator ) );
4616 PSA_ASSERT( psa_export_key( derived_handle,
4617 export_buffer, bytes1,
4618 &length ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004619 TEST_EQUAL( length, bytes1 );
Gilles Peskine8817f612018-12-18 00:18:46 +01004620 PSA_ASSERT( psa_destroy_key( derived_handle ) );
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004621 PSA_ASSERT( psa_allocate_key( &derived_handle ) );
Gilles Peskine8817f612018-12-18 00:18:46 +01004622 PSA_ASSERT( psa_set_key_policy( derived_handle, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004623 PSA_ASSERT( psa_generator_import_key_to_handle( derived_handle,
Gilles Peskine8817f612018-12-18 00:18:46 +01004624 PSA_KEY_TYPE_RAW_DATA,
4625 PSA_BYTES_TO_BITS( bytes2 ),
4626 &generator ) );
4627 PSA_ASSERT( psa_export_key( derived_handle,
4628 export_buffer + bytes1, bytes2,
4629 &length ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004630 TEST_EQUAL( length, bytes2 );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004631
4632 /* Compare the outputs from the two runs. */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004633 ASSERT_COMPARE( output_buffer, bytes1 + bytes2,
4634 export_buffer, capacity );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004635
4636exit:
4637 mbedtls_free( output_buffer );
4638 mbedtls_free( export_buffer );
4639 psa_generator_abort( &generator );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004640 psa_destroy_key( base_handle );
4641 psa_destroy_key( derived_handle );
Gilles Peskine0386fba2018-07-12 17:29:22 +02004642 mbedtls_psa_crypto_free( );
4643}
4644/* END_CASE */
4645
4646/* BEGIN_CASE */
Gilles Peskine01d718c2018-09-18 12:01:02 +02004647void key_agreement_setup( int alg_arg,
4648 int our_key_type_arg, data_t *our_key_data,
4649 data_t *peer_key_data,
4650 int expected_status_arg )
4651{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004652 psa_key_handle_t our_key = 0;
Gilles Peskine01d718c2018-09-18 12:01:02 +02004653 psa_algorithm_t alg = alg_arg;
4654 psa_key_type_t our_key_type = our_key_type_arg;
4655 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004656 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine77f40d82019-04-11 21:27:06 +02004657 psa_status_t expected_status = expected_status_arg;
4658 psa_status_t status;
Gilles Peskine01d718c2018-09-18 12:01:02 +02004659
Gilles Peskine8817f612018-12-18 00:18:46 +01004660 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004661
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004662 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004663 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004664 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004665 PSA_ASSERT( psa_import_key_to_handle( our_key, our_key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004666 our_key_data->x,
4667 our_key_data->len ) );
Gilles Peskine01d718c2018-09-18 12:01:02 +02004668
Gilles Peskine77f40d82019-04-11 21:27:06 +02004669 /* The tests currently include inputs that should fail at either step.
4670 * Test cases that fail at the setup step should be changed to call
4671 * key_derivation_setup instead, and this function should be renamed
4672 * to key_agreement_fail. */
4673 status = psa_key_derivation_setup( &generator, alg );
4674 if( status == PSA_SUCCESS )
4675 {
4676 TEST_EQUAL( psa_key_agreement( &generator, PSA_KDF_STEP_SECRET,
4677 our_key,
4678 peer_key_data->x, peer_key_data->len ),
4679 expected_status );
4680 }
4681 else
4682 {
4683 TEST_ASSERT( status == expected_status );
4684 }
Gilles Peskine01d718c2018-09-18 12:01:02 +02004685
4686exit:
4687 psa_generator_abort( &generator );
4688 psa_destroy_key( our_key );
4689 mbedtls_psa_crypto_free( );
4690}
4691/* END_CASE */
4692
4693/* BEGIN_CASE */
Gilles Peskinef0cba732019-04-11 22:12:38 +02004694void raw_key_agreement( int alg_arg,
4695 int our_key_type_arg, data_t *our_key_data,
4696 data_t *peer_key_data,
4697 data_t *expected_output )
4698{
4699 psa_key_handle_t our_key = 0;
4700 psa_algorithm_t alg = alg_arg;
4701 psa_key_type_t our_key_type = our_key_type_arg;
4702 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
4703 unsigned char *output = NULL;
4704 size_t output_length = ~0;
4705
4706 ASSERT_ALLOC( output, expected_output->len );
4707 PSA_ASSERT( psa_crypto_init( ) );
4708
4709 PSA_ASSERT( psa_allocate_key( &our_key ) );
4710 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
4711 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004712 PSA_ASSERT( psa_import_key_to_handle( our_key, our_key_type,
Gilles Peskinef0cba732019-04-11 22:12:38 +02004713 our_key_data->x,
4714 our_key_data->len ) );
4715
4716 PSA_ASSERT( psa_key_agreement_raw_shared_secret(
4717 alg, our_key,
4718 peer_key_data->x, peer_key_data->len,
4719 output, expected_output->len, &output_length ) );
4720 ASSERT_COMPARE( output, output_length,
4721 expected_output->x, expected_output->len );
4722
4723exit:
4724 mbedtls_free( output );
4725 psa_destroy_key( our_key );
4726 mbedtls_psa_crypto_free( );
4727}
4728/* END_CASE */
4729
4730/* BEGIN_CASE */
Gilles Peskine59685592018-09-18 12:11:34 +02004731void key_agreement_capacity( int alg_arg,
4732 int our_key_type_arg, data_t *our_key_data,
4733 data_t *peer_key_data,
4734 int expected_capacity_arg )
4735{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004736 psa_key_handle_t our_key = 0;
Gilles Peskine59685592018-09-18 12:11:34 +02004737 psa_algorithm_t alg = alg_arg;
4738 psa_key_type_t our_key_type = our_key_type_arg;
4739 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004740 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine59685592018-09-18 12:11:34 +02004741 size_t actual_capacity;
Gilles Peskinebf491972018-10-25 22:36:12 +02004742 unsigned char output[16];
Gilles Peskine59685592018-09-18 12:11:34 +02004743
Gilles Peskine8817f612018-12-18 00:18:46 +01004744 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004745
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004746 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004747 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004748 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004749 PSA_ASSERT( psa_import_key_to_handle( our_key, our_key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004750 our_key_data->x,
4751 our_key_data->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004752
Gilles Peskine969c5d62019-01-16 15:53:06 +01004753 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
4754 PSA_ASSERT( psa_key_agreement( &generator, PSA_KDF_STEP_SECRET,
Gilles Peskine8817f612018-12-18 00:18:46 +01004755 our_key,
Gilles Peskine969c5d62019-01-16 15:53:06 +01004756 peer_key_data->x, peer_key_data->len ) );
Gilles Peskinef8a9d942019-04-11 22:13:20 +02004757 if( PSA_ALG_IS_HKDF( PSA_ALG_KEY_AGREEMENT_GET_KDF( alg ) ) )
4758 {
4759 /* The test data is for info="" */
4760 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4761 PSA_KDF_STEP_INFO,
4762 NULL, 0 ) );
4763 }
Gilles Peskine59685592018-09-18 12:11:34 +02004764
Gilles Peskinebf491972018-10-25 22:36:12 +02004765 /* Test the advertized capacity. */
Gilles Peskine8817f612018-12-18 00:18:46 +01004766 PSA_ASSERT( psa_get_generator_capacity(
4767 &generator, &actual_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004768 TEST_EQUAL( actual_capacity, (size_t) expected_capacity_arg );
Gilles Peskine59685592018-09-18 12:11:34 +02004769
Gilles Peskinebf491972018-10-25 22:36:12 +02004770 /* Test the actual capacity by reading the output. */
4771 while( actual_capacity > sizeof( output ) )
4772 {
Gilles Peskine8817f612018-12-18 00:18:46 +01004773 PSA_ASSERT( psa_generator_read( &generator,
4774 output, sizeof( output ) ) );
Gilles Peskinebf491972018-10-25 22:36:12 +02004775 actual_capacity -= sizeof( output );
4776 }
Gilles Peskine8817f612018-12-18 00:18:46 +01004777 PSA_ASSERT( psa_generator_read( &generator,
4778 output, actual_capacity ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01004779 TEST_EQUAL( psa_generator_read( &generator, output, 1 ),
David Saadab4ecc272019-02-14 13:48:10 +02004780 PSA_ERROR_INSUFFICIENT_DATA );
Gilles Peskinebf491972018-10-25 22:36:12 +02004781
Gilles Peskine59685592018-09-18 12:11:34 +02004782exit:
4783 psa_generator_abort( &generator );
4784 psa_destroy_key( our_key );
4785 mbedtls_psa_crypto_free( );
4786}
4787/* END_CASE */
4788
4789/* BEGIN_CASE */
4790void key_agreement_output( int alg_arg,
4791 int our_key_type_arg, data_t *our_key_data,
4792 data_t *peer_key_data,
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004793 data_t *expected_output1, data_t *expected_output2 )
Gilles Peskine59685592018-09-18 12:11:34 +02004794{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004795 psa_key_handle_t our_key = 0;
Gilles Peskine59685592018-09-18 12:11:34 +02004796 psa_algorithm_t alg = alg_arg;
4797 psa_key_type_t our_key_type = our_key_type_arg;
4798 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Jaeden Amero70261c52019-01-04 11:47:20 +00004799 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004800 uint8_t *actual_output = NULL;
Gilles Peskine59685592018-09-18 12:11:34 +02004801
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004802 ASSERT_ALLOC( actual_output, MAX( expected_output1->len,
4803 expected_output2->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004804
Gilles Peskine8817f612018-12-18 00:18:46 +01004805 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004806
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004807 PSA_ASSERT( psa_allocate_key( &our_key ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004808 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_DERIVE, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004809 PSA_ASSERT( psa_set_key_policy( our_key, &policy ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02004810 PSA_ASSERT( psa_import_key_to_handle( our_key, our_key_type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004811 our_key_data->x,
4812 our_key_data->len ) );
Gilles Peskine59685592018-09-18 12:11:34 +02004813
Gilles Peskine969c5d62019-01-16 15:53:06 +01004814 PSA_ASSERT( psa_key_derivation_setup( &generator, alg ) );
4815 PSA_ASSERT( psa_key_agreement( &generator, PSA_KDF_STEP_SECRET,
Gilles Peskine8817f612018-12-18 00:18:46 +01004816 our_key,
Gilles Peskine969c5d62019-01-16 15:53:06 +01004817 peer_key_data->x, peer_key_data->len ) );
Gilles Peskinef8a9d942019-04-11 22:13:20 +02004818 if( PSA_ALG_IS_HKDF( PSA_ALG_KEY_AGREEMENT_GET_KDF( alg ) ) )
4819 {
4820 /* The test data is for info="" */
4821 PSA_ASSERT( psa_key_derivation_input_bytes( &generator,
4822 PSA_KDF_STEP_INFO,
4823 NULL, 0 ) );
4824 }
Gilles Peskine59685592018-09-18 12:11:34 +02004825
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004826 PSA_ASSERT( psa_generator_read( &generator,
4827 actual_output,
4828 expected_output1->len ) );
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004829 ASSERT_COMPARE( actual_output, expected_output1->len,
4830 expected_output1->x, expected_output1->len );
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004831 if( expected_output2->len != 0 )
4832 {
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004833 PSA_ASSERT( psa_generator_read( &generator,
4834 actual_output,
4835 expected_output2->len ) );
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004836 ASSERT_COMPARE( actual_output, expected_output2->len,
4837 expected_output2->x, expected_output2->len );
Gilles Peskine3ec8ed82018-10-25 22:37:15 +02004838 }
Gilles Peskine59685592018-09-18 12:11:34 +02004839
4840exit:
4841 psa_generator_abort( &generator );
4842 psa_destroy_key( our_key );
4843 mbedtls_psa_crypto_free( );
4844 mbedtls_free( actual_output );
4845}
4846/* END_CASE */
4847
4848/* BEGIN_CASE */
Gilles Peskinea50d7392018-06-21 10:22:13 +02004849void generate_random( int bytes_arg )
Gilles Peskine05d69892018-06-19 22:00:52 +02004850{
Gilles Peskinea50d7392018-06-21 10:22:13 +02004851 size_t bytes = bytes_arg;
4852 const unsigned char trail[] = "don't overwrite me";
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004853 unsigned char *output = NULL;
4854 unsigned char *changed = NULL;
Gilles Peskinea50d7392018-06-21 10:22:13 +02004855 size_t i;
4856 unsigned run;
Gilles Peskine05d69892018-06-19 22:00:52 +02004857
Gilles Peskine8cebbba2018-09-27 13:54:18 +02004858 ASSERT_ALLOC( output, bytes + sizeof( trail ) );
4859 ASSERT_ALLOC( changed, bytes );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004860 memcpy( output + bytes, trail, sizeof( trail ) );
Gilles Peskine05d69892018-06-19 22:00:52 +02004861
Gilles Peskine8817f612018-12-18 00:18:46 +01004862 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine05d69892018-06-19 22:00:52 +02004863
Gilles Peskinea50d7392018-06-21 10:22:13 +02004864 /* Run several times, to ensure that every output byte will be
4865 * nonzero at least once with overwhelming probability
4866 * (2^(-8*number_of_runs)). */
4867 for( run = 0; run < 10; run++ )
Gilles Peskine05d69892018-06-19 22:00:52 +02004868 {
Gilles Peskinef7ab5ad2018-09-26 18:19:24 +02004869 if( bytes != 0 )
4870 memset( output, 0, bytes );
Gilles Peskine8817f612018-12-18 00:18:46 +01004871 PSA_ASSERT( psa_generate_random( output, bytes ) );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004872
4873 /* Check that no more than bytes have been overwritten */
Gilles Peskine0dfba2d2018-12-18 00:40:50 +01004874 ASSERT_COMPARE( output + bytes, sizeof( trail ),
4875 trail, sizeof( trail ) );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004876
4877 for( i = 0; i < bytes; i++ )
4878 {
4879 if( output[i] != 0 )
4880 ++changed[i];
4881 }
Gilles Peskine05d69892018-06-19 22:00:52 +02004882 }
Gilles Peskinea50d7392018-06-21 10:22:13 +02004883
4884 /* Check that every byte was changed to nonzero at least once. This
4885 * validates that psa_generate_random is overwriting every byte of
4886 * the output buffer. */
4887 for( i = 0; i < bytes; i++ )
4888 {
4889 TEST_ASSERT( changed[i] != 0 );
4890 }
Gilles Peskine05d69892018-06-19 22:00:52 +02004891
4892exit:
4893 mbedtls_psa_crypto_free( );
Gilles Peskinea50d7392018-06-21 10:22:13 +02004894 mbedtls_free( output );
4895 mbedtls_free( changed );
Gilles Peskine05d69892018-06-19 22:00:52 +02004896}
4897/* END_CASE */
Gilles Peskine12313cd2018-06-20 00:20:32 +02004898
4899/* BEGIN_CASE */
4900void generate_key( int type_arg,
4901 int bits_arg,
4902 int usage_arg,
4903 int alg_arg,
4904 int expected_status_arg )
4905{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004906 psa_key_handle_t handle = 0;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004907 psa_key_type_t type = type_arg;
4908 psa_key_usage_t usage = usage_arg;
4909 size_t bits = bits_arg;
4910 psa_algorithm_t alg = alg_arg;
4911 psa_status_t expected_status = expected_status_arg;
4912 psa_key_type_t got_type;
4913 size_t got_bits;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004914 psa_status_t expected_info_status =
David Saadab4ecc272019-02-14 13:48:10 +02004915 expected_status == PSA_SUCCESS ? PSA_SUCCESS : PSA_ERROR_DOES_NOT_EXIST;
Jaeden Amero70261c52019-01-04 11:47:20 +00004916 psa_key_policy_t policy = PSA_KEY_POLICY_INIT;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004917
Gilles Peskine8817f612018-12-18 00:18:46 +01004918 PSA_ASSERT( psa_crypto_init( ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004919
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004920 PSA_ASSERT( psa_allocate_key( &handle ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004921 psa_key_policy_set_usage( &policy, usage, alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004922 PSA_ASSERT( psa_set_key_policy( handle, &policy ) );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004923
4924 /* Generate a key */
Gilles Peskine87a5e562019-04-17 12:28:25 +02004925 TEST_EQUAL( psa_generate_key_to_handle( handle, type, bits, NULL, 0 ),
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004926 expected_status );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004927
4928 /* Test the key information */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01004929 TEST_EQUAL( psa_get_key_information( handle, &got_type, &got_bits ),
4930 expected_info_status );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004931 if( expected_info_status != PSA_SUCCESS )
4932 goto exit;
Gilles Peskinefe11b722018-12-18 00:24:04 +01004933 TEST_EQUAL( got_type, type );
4934 TEST_EQUAL( got_bits, bits );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004935
Gilles Peskine818ca122018-06-20 18:16:48 +02004936 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004937 if( ! exercise_key( handle, usage, alg ) )
Gilles Peskine02b75072018-07-01 22:31:34 +02004938 goto exit;
Gilles Peskine12313cd2018-06-20 00:20:32 +02004939
4940exit:
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004941 psa_destroy_key( handle );
Gilles Peskine12313cd2018-06-20 00:20:32 +02004942 mbedtls_psa_crypto_free( );
4943}
4944/* END_CASE */
itayzafrir0adf0fc2018-09-06 16:24:41 +03004945
Darryl Greend49a4992018-06-18 17:27:26 +01004946/* BEGIN_CASE depends_on:MBEDTLS_PSA_CRYPTO_STORAGE_C */
4947void persistent_key_load_key_from_storage( data_t *data, int type_arg,
4948 int bits, int usage_arg,
Darryl Green0c6575a2018-11-07 16:05:30 +00004949 int alg_arg, int generation_method,
4950 int export_status )
Darryl Greend49a4992018-06-18 17:27:26 +01004951{
Gilles Peskinebdf309c2018-12-03 15:36:32 +01004952 psa_key_handle_t handle = 0;
4953 psa_key_handle_t base_key;
Darryl Greend49a4992018-06-18 17:27:26 +01004954 psa_key_type_t type = (psa_key_type_t) type_arg;
4955 psa_key_type_t type_get;
4956 size_t bits_get;
Jaeden Amero70261c52019-01-04 11:47:20 +00004957 psa_key_policy_t policy_set = PSA_KEY_POLICY_INIT;
4958 psa_key_policy_t policy_get = PSA_KEY_POLICY_INIT;
Darryl Greend49a4992018-06-18 17:27:26 +01004959 psa_key_usage_t policy_usage = (psa_key_usage_t) usage_arg;
4960 psa_algorithm_t policy_alg = (psa_algorithm_t) alg_arg;
Jaeden Amero70261c52019-01-04 11:47:20 +00004961 psa_key_policy_t base_policy_set = PSA_KEY_POLICY_INIT;
Darryl Green0c6575a2018-11-07 16:05:30 +00004962 psa_algorithm_t base_policy_alg = PSA_ALG_HKDF(PSA_ALG_SHA_256);
4963 psa_crypto_generator_t generator = PSA_CRYPTO_GENERATOR_INIT;
Darryl Greend49a4992018-06-18 17:27:26 +01004964 unsigned char *first_export = NULL;
4965 unsigned char *second_export = NULL;
4966 size_t export_size = PSA_KEY_EXPORT_MAX_SIZE( type, bits );
4967 size_t first_exported_length;
4968 size_t second_exported_length;
4969
4970 ASSERT_ALLOC( first_export, export_size );
4971 ASSERT_ALLOC( second_export, export_size );
4972
Gilles Peskine8817f612018-12-18 00:18:46 +01004973 PSA_ASSERT( psa_crypto_init() );
Darryl Greend49a4992018-06-18 17:27:26 +01004974
Gilles Peskine8817f612018-12-18 00:18:46 +01004975 PSA_ASSERT( psa_create_key( PSA_KEY_LIFETIME_PERSISTENT, 1,
Gilles Peskine8817f612018-12-18 00:18:46 +01004976 &handle ) );
Darryl Greend49a4992018-06-18 17:27:26 +01004977 psa_key_policy_set_usage( &policy_set, policy_usage,
4978 policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01004979 PSA_ASSERT( psa_set_key_policy( handle, &policy_set ) );
Darryl Greend49a4992018-06-18 17:27:26 +01004980
Darryl Green0c6575a2018-11-07 16:05:30 +00004981 switch( generation_method )
4982 {
4983 case IMPORT_KEY:
4984 /* Import the key */
Gilles Peskine87a5e562019-04-17 12:28:25 +02004985 PSA_ASSERT( psa_import_key_to_handle( handle, type,
Gilles Peskine8817f612018-12-18 00:18:46 +01004986 data->x, data->len ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004987 break;
Darryl Greend49a4992018-06-18 17:27:26 +01004988
Darryl Green0c6575a2018-11-07 16:05:30 +00004989 case GENERATE_KEY:
4990 /* Generate a key */
Gilles Peskine87a5e562019-04-17 12:28:25 +02004991 PSA_ASSERT( psa_generate_key_to_handle( handle, type, bits,
Gilles Peskine8817f612018-12-18 00:18:46 +01004992 NULL, 0 ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004993 break;
4994
4995 case DERIVE_KEY:
4996 /* Create base key */
Gilles Peskined40c1fb2019-01-19 12:20:52 +01004997 PSA_ASSERT( psa_allocate_key( &base_key ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00004998 psa_key_policy_set_usage( &base_policy_set, PSA_KEY_USAGE_DERIVE,
4999 base_policy_alg );
Gilles Peskine8817f612018-12-18 00:18:46 +01005000 PSA_ASSERT( psa_set_key_policy(
5001 base_key, &base_policy_set ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02005002 PSA_ASSERT( psa_import_key_to_handle( base_key, PSA_KEY_TYPE_DERIVE,
Gilles Peskine8817f612018-12-18 00:18:46 +01005003 data->x, data->len ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00005004 /* Derive a key. */
Gilles Peskine8817f612018-12-18 00:18:46 +01005005 PSA_ASSERT( psa_key_derivation( &generator, base_key,
5006 base_policy_alg,
5007 NULL, 0, NULL, 0,
5008 export_size ) );
Gilles Peskine87a5e562019-04-17 12:28:25 +02005009 PSA_ASSERT( psa_generator_import_key_to_handle(
Gilles Peskine8817f612018-12-18 00:18:46 +01005010 handle, PSA_KEY_TYPE_RAW_DATA,
5011 bits, &generator ) );
Darryl Green0c6575a2018-11-07 16:05:30 +00005012 break;
5013 }
Darryl Greend49a4992018-06-18 17:27:26 +01005014
5015 /* Export the key */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01005016 TEST_EQUAL( psa_export_key( handle,
5017 first_export, export_size,
5018 &first_exported_length ),
5019 export_status );
Darryl Greend49a4992018-06-18 17:27:26 +01005020
5021 /* Shutdown and restart */
5022 mbedtls_psa_crypto_free();
Gilles Peskine8817f612018-12-18 00:18:46 +01005023 PSA_ASSERT( psa_crypto_init() );
Darryl Greend49a4992018-06-18 17:27:26 +01005024
Darryl Greend49a4992018-06-18 17:27:26 +01005025 /* Check key slot still contains key data */
Gilles Peskine8817f612018-12-18 00:18:46 +01005026 PSA_ASSERT( psa_open_key( PSA_KEY_LIFETIME_PERSISTENT, 1,
5027 &handle ) );
5028 PSA_ASSERT( psa_get_key_information(
5029 handle, &type_get, &bits_get ) );
Gilles Peskinefe11b722018-12-18 00:24:04 +01005030 TEST_EQUAL( type_get, type );
5031 TEST_EQUAL( bits_get, (size_t) bits );
Darryl Greend49a4992018-06-18 17:27:26 +01005032
Gilles Peskine8817f612018-12-18 00:18:46 +01005033 PSA_ASSERT( psa_get_key_policy( handle, &policy_get ) );
Gilles Peskinef812dcf2018-12-18 00:33:25 +01005034 TEST_EQUAL( psa_key_policy_get_usage( &policy_get ), policy_usage );
5035 TEST_EQUAL( psa_key_policy_get_algorithm( &policy_get ), policy_alg );
Darryl Greend49a4992018-06-18 17:27:26 +01005036
5037 /* Export the key again */
Gilles Peskinef812dcf2018-12-18 00:33:25 +01005038 TEST_EQUAL( psa_export_key( handle,
5039 second_export, export_size,
5040 &second_exported_length ),
5041 export_status );
Darryl Greend49a4992018-06-18 17:27:26 +01005042
Darryl Green0c6575a2018-11-07 16:05:30 +00005043 if( export_status == PSA_SUCCESS )
5044 {
5045 ASSERT_COMPARE( first_export, first_exported_length,
5046 second_export, second_exported_length );
Darryl Greend49a4992018-06-18 17:27:26 +01005047
Darryl Green0c6575a2018-11-07 16:05:30 +00005048 switch( generation_method )
5049 {
5050 case IMPORT_KEY:
5051 ASSERT_COMPARE( data->x, data->len,
5052 first_export, first_exported_length );
5053 break;
5054 default:
5055 break;
5056 }
5057 }
5058
5059 /* Do something with the key according to its type and permitted usage. */
Gilles Peskinebdf309c2018-12-03 15:36:32 +01005060 if( ! exercise_key( handle, policy_usage, policy_alg ) )
Darryl Green0c6575a2018-11-07 16:05:30 +00005061 goto exit;
Darryl Greend49a4992018-06-18 17:27:26 +01005062
5063exit:
5064 mbedtls_free( first_export );
5065 mbedtls_free( second_export );
Gilles Peskinebdf309c2018-12-03 15:36:32 +01005066 psa_destroy_key( handle );
Darryl Greend49a4992018-06-18 17:27:26 +01005067 mbedtls_psa_crypto_free();
5068}
5069/* END_CASE */