blob: d1a600928c9159efd8edf2cf17efc421cab3f60a [file] [log] [blame]
Steven Cooremana70d5882020-07-16 20:26:18 +02001/*
Steven Cooreman56250fd2020-09-04 13:07:15 +02002 * Test driver for signature functions.
3 * Currently supports signing and verifying precalculated hashes, using
4 * only deterministic ECDSA on curves secp256r1, secp384r1 and secp521r1.
Steven Cooremana70d5882020-07-16 20:26:18 +02005 */
Steven Cooreman2c7b2f82020-09-02 13:43:46 +02006/* Copyright The Mbed TLS Contributors
Steven Cooremana70d5882020-07-16 20:26:18 +02007 * SPDX-License-Identifier: Apache-2.0
8 *
9 * Licensed under the Apache License, Version 2.0 (the "License"); you may
10 * not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
12 *
13 * http://www.apache.org/licenses/LICENSE-2.0
14 *
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
17 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
Steven Cooremana70d5882020-07-16 20:26:18 +020020 */
21
22#if !defined(MBEDTLS_CONFIG_FILE)
23#include "mbedtls/config.h"
24#else
25#include MBEDTLS_CONFIG_FILE
26#endif
27
Steven Cooremanf1720ea2020-07-24 18:41:58 +020028#if defined(MBEDTLS_PSA_CRYPTO_DRIVERS) && defined(PSA_CRYPTO_DRIVER_TEST)
Steven Cooremana70d5882020-07-16 20:26:18 +020029#include "psa/crypto.h"
Steven Cooreman15f58d22020-09-04 13:05:23 +020030#include "psa_crypto_core.h"
Steven Cooremana70d5882020-07-16 20:26:18 +020031#include "mbedtls/ecp.h"
32
33#include "drivers/signature.h"
34
35#include "mbedtls/md.h"
36#include "mbedtls/ecdsa.h"
37
Steven Cooreman55ae2172020-07-17 19:46:15 +020038#include "test/random.h"
39
Steven Cooremana70d5882020-07-16 20:26:18 +020040#include <string.h>
41
42/* If non-null, on success, copy this to the output. */
43void *test_driver_forced_output = NULL;
44size_t test_driver_forced_output_length = 0;
45
46psa_status_t test_transparent_signature_sign_hash_status = PSA_ERROR_NOT_SUPPORTED;
47unsigned long test_transparent_signature_sign_hash_hit = 0;
48
Steven Cooreman55ae2172020-07-17 19:46:15 +020049psa_status_t test_transparent_signature_verify_hash_status = PSA_ERROR_NOT_SUPPORTED;
50unsigned long test_transparent_signature_verify_hash_hit = 0;
51
Steven Cooremana70d5882020-07-16 20:26:18 +020052psa_status_t test_transparent_signature_sign_hash(
53 const psa_key_attributes_t *attributes,
54 const uint8_t *key, size_t key_length,
55 psa_algorithm_t alg,
56 const uint8_t *hash, size_t hash_length,
57 uint8_t *signature, size_t signature_size, size_t *signature_length )
58{
59 ++test_transparent_signature_sign_hash_hit;
60
61 if( test_transparent_signature_sign_hash_status != PSA_SUCCESS )
62 return( test_transparent_signature_sign_hash_status );
63
64 if( test_driver_forced_output != NULL )
65 {
66 if( test_driver_forced_output_length > signature_size )
67 return( PSA_ERROR_BUFFER_TOO_SMALL );
68 memcpy( signature, test_driver_forced_output,
69 test_driver_forced_output_length );
70 *signature_length = test_driver_forced_output_length;
71 return( PSA_SUCCESS );
72 }
73
74 psa_status_t status = PSA_ERROR_NOT_SUPPORTED;
75
76#if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
77 defined(MBEDTLS_SHA256_C)
78 if( alg != PSA_ALG_DETERMINISTIC_ECDSA( PSA_ALG_SHA_256 ) )
79 return( PSA_ERROR_NOT_SUPPORTED );
80 mbedtls_ecp_group_id grp_id;
81 switch( psa_get_key_type( attributes ) )
82 {
83 case PSA_ECC_CURVE_SECP_R1:
84 switch( psa_get_key_bits( attributes ) )
85 {
86 case 256:
87 grp_id = MBEDTLS_ECP_DP_SECP256R1;
88 break;
89 case 384:
90 grp_id = MBEDTLS_ECP_DP_SECP384R1;
91 break;
92 case 521:
93 grp_id = MBEDTLS_ECP_DP_SECP521R1;
94 break;
95 default:
96 return( PSA_ERROR_NOT_SUPPORTED );
97 }
98 break;
99 default:
100 return( PSA_ERROR_NOT_SUPPORTED );
101 }
102
103 /* Beyond this point, the driver is actually doing the work of
104 * calculating the signature. */
105
106 status = PSA_ERROR_GENERIC_ERROR;
107 int ret = 0;
108 mbedtls_mpi r, s;
109 mbedtls_mpi_init( &r );
110 mbedtls_mpi_init( &s );
111 mbedtls_ecp_keypair ecp;
112 mbedtls_ecp_keypair_init( &ecp );
113 size_t curve_bytes = PSA_BITS_TO_BYTES( ecp.grp.pbits );
114
115 MBEDTLS_MPI_CHK( mbedtls_ecp_group_load( &ecp.grp, grp_id ) );
116 MBEDTLS_MPI_CHK( mbedtls_ecp_point_read_binary( &ecp.grp, &ecp.Q,
117 key, key_length ) );
118
119 /* Code adapted from psa_ecdsa_sign() in psa_crypto.c. */
120 mbedtls_md_type_t md_alg = MBEDTLS_MD_SHA256;
121 if( signature_size < 2 * curve_bytes )
122 {
123 status = PSA_ERROR_BUFFER_TOO_SMALL;
124 goto cleanup;
125 }
126 MBEDTLS_MPI_CHK( mbedtls_ecdsa_sign_det( &ecp.grp, &r, &s, &ecp.d,
127 hash, hash_length, md_alg ) );
128 MBEDTLS_MPI_CHK( mbedtls_mpi_write_binary( &r,
129 signature,
130 curve_bytes ) );
131 MBEDTLS_MPI_CHK( mbedtls_mpi_write_binary( &s,
132 signature + curve_bytes,
133 curve_bytes ) );
134cleanup:
Steven Cooreman56250fd2020-09-04 13:07:15 +0200135 status = mbedtls_to_psa_error( ret );
Steven Cooremana70d5882020-07-16 20:26:18 +0200136 mbedtls_mpi_free( &r );
137 mbedtls_mpi_free( &s );
138 mbedtls_ecp_keypair_free( &ecp );
139 if( status == PSA_SUCCESS )
140 *signature_length = 2 * curve_bytes;
141#else /* defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
142 defined(MBEDTLS_SHA256_C) */
143 (void) attributes;
144 (void) key;
145 (void) key_length;
146 (void) alg;
147 (void) hash;
148 (void) hash_length;
149#endif /* defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
150 defined(MBEDTLS_SHA256_C) */
151
152 return( status );
153}
154
155psa_status_t test_opaque_signature_sign_hash(
156 const psa_key_attributes_t *attributes,
157 const uint8_t *key, size_t key_length,
158 psa_algorithm_t alg,
159 const uint8_t *hash, size_t hash_length,
160 uint8_t *signature, size_t signature_size, size_t *signature_length )
161{
162 (void) attributes;
163 (void) key;
164 (void) key_length;
165 (void) alg;
166 (void) hash;
167 (void) hash_length;
168 (void) signature;
169 (void) signature_size;
170 (void) signature_length;
171 return( PSA_ERROR_NOT_SUPPORTED );
172}
173
Steven Cooreman55ae2172020-07-17 19:46:15 +0200174psa_status_t test_transparent_signature_verify_hash(
175 const psa_key_attributes_t *attributes,
176 const uint8_t *key, size_t key_length,
177 psa_algorithm_t alg,
178 const uint8_t *hash, size_t hash_length,
179 const uint8_t *signature, size_t signature_length )
180{
181 ++test_transparent_signature_verify_hash_hit;
182
183 if( test_transparent_signature_verify_hash_status != PSA_SUCCESS )
184 return( test_transparent_signature_verify_hash_status );
185
186 psa_status_t status = PSA_ERROR_NOT_SUPPORTED;
187
188#if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
189 defined(MBEDTLS_SHA256_C)
190 if( alg != PSA_ALG_DETERMINISTIC_ECDSA( PSA_ALG_SHA_256 ) )
191 return( PSA_ERROR_NOT_SUPPORTED );
192 mbedtls_ecp_group_id grp_id;
193 switch( psa_get_key_type( attributes ) )
194 {
195 case PSA_ECC_CURVE_SECP_R1:
196 switch( psa_get_key_bits( attributes ) )
197 {
198 case 256:
199 grp_id = MBEDTLS_ECP_DP_SECP256R1;
200 break;
201 case 384:
202 grp_id = MBEDTLS_ECP_DP_SECP384R1;
203 break;
204 case 521:
205 grp_id = MBEDTLS_ECP_DP_SECP521R1;
206 break;
207 default:
208 return( PSA_ERROR_NOT_SUPPORTED );
209 }
210 break;
211 default:
212 return( PSA_ERROR_NOT_SUPPORTED );
213 }
214
215 /* Beyond this point, the driver is actually doing the work of
216 * calculating the signature. */
217
218 status = PSA_ERROR_GENERIC_ERROR;
219 int ret = 0;
220 mbedtls_mpi r, s;
221 mbedtls_mpi_init( &r );
222 mbedtls_mpi_init( &s );
223 mbedtls_ecp_keypair ecp;
224 mbedtls_ecp_keypair_init( &ecp );
225 mbedtls_test_rnd_pseudo_info rnd_info;
226 memset( &rnd_info, 0x5A, sizeof( mbedtls_test_rnd_pseudo_info ) );
227 size_t curve_bytes = PSA_BITS_TO_BYTES( ecp.grp.pbits );
228
229 MBEDTLS_MPI_CHK( mbedtls_ecp_group_load( &ecp.grp, grp_id ) );
230
231 /* Code adapted from psa_ecdsa_verify() in psa_crypto.c. */
232 if( signature_length < 2 * curve_bytes )
233 {
234 status = PSA_ERROR_BUFFER_TOO_SMALL;
235 goto cleanup;
236 }
237
238 MBEDTLS_MPI_CHK( mbedtls_mpi_read_binary( &r,
239 signature,
240 curve_bytes ) );
241 MBEDTLS_MPI_CHK( mbedtls_mpi_read_binary( &s,
242 signature + curve_bytes,
243 curve_bytes ) );
244
245 if( PSA_KEY_TYPE_IS_PUBLIC_KEY( psa_get_key_type( attributes ) ) )
246 MBEDTLS_MPI_CHK( mbedtls_ecp_point_read_binary( &ecp.grp, &ecp.Q,
247 key, key_length ) );
248 else
249 {
250 MBEDTLS_MPI_CHK( mbedtls_mpi_read_binary( &ecp.d, key, key_length ) );
251 MBEDTLS_MPI_CHK(
252 mbedtls_ecp_mul( &ecp.grp, &ecp.Q, &ecp.d, &ecp.grp.G,
253 &mbedtls_test_rnd_pseudo_rand,
254 &rnd_info ) );
255 }
256
257 MBEDTLS_MPI_CHK( mbedtls_ecdsa_verify( &ecp.grp, hash, hash_length,
258 &ecp.Q, &r, &s ) );
259cleanup:
Steven Cooreman56250fd2020-09-04 13:07:15 +0200260 status = mbedtls_to_psa_error( ret );
Steven Cooreman55ae2172020-07-17 19:46:15 +0200261 mbedtls_mpi_free( &r );
262 mbedtls_mpi_free( &s );
263 mbedtls_ecp_keypair_free( &ecp );
264#else /* defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
265 defined(MBEDTLS_SHA256_C) */
266 (void) attributes;
267 (void) key;
268 (void) key_length;
269 (void) alg;
270 (void) hash;
271 (void) hash_length;
272#endif /* defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECDSA_DETERMINISTIC) && \
273 defined(MBEDTLS_SHA256_C) */
274
275 return( status );
276}
277
278psa_status_t test_opaque_signature_verify_hash(
279 const psa_key_attributes_t *attributes,
280 const uint8_t *key, size_t key_length,
281 psa_algorithm_t alg,
282 const uint8_t *hash, size_t hash_length,
283 const uint8_t *signature, size_t signature_length )
284{
285 (void) attributes;
286 (void) key;
287 (void) key_length;
288 (void) alg;
289 (void) hash;
290 (void) hash_length;
291 (void) signature;
292 (void) signature_length;
293 return( PSA_ERROR_NOT_SUPPORTED );
294}
295
Steven Cooremanf1720ea2020-07-24 18:41:58 +0200296#endif /* MBEDTLS_PSA_CRYPTO_DRIVERS && PSA_CRYPTO_DRIVER_TEST */