Skip to content

Commit 374def0

Browse files
committed
cmpClient.c: add support for ML-DSA and TPM2-held keys referenced via handle
1 parent fc603bc commit 374def0

7 files changed

Lines changed: 47 additions & 18 deletions

File tree

‎doc/Generic_CMP_client_API.odt‎

5.14 KB
Binary file not shown.

‎doc/Generic_CMP_client_API.pdf‎

14 KB
Binary file not shown.

‎doc/cmpClient.pod‎

Lines changed: 29 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -50,9 +50,9 @@ Generic message options:
5050

5151
Certificate enrollment options:
5252

53-
[B<-newkeytype> EC:I<curve>|RSA-I<len>]
53+
[B<-newkeytype> EC:I<curve>|RSA-I<len>|ML-DSA-<level>]
5454
[B<-centralkeygen>]
55-
[B<-newkey> I<filename>]
55+
[B<-newkey> I<filename>|I<url>]
5656
[B<-newkeypass> I<arg>]
5757
[B<-subject> I<name>]
5858
[B<-issuer> I<name>]
@@ -360,13 +360,21 @@ Note: any keySpec field contents received are logged as INFO.
360360
=item B<-newkeytype> I<spec>
361361

362362
In case of IR, CR, or KUR,
363-
generate or request a new key of the given type for the requested certificate.
364-
The I<spec> may be of the form C<EC:>I<curve> or C<RSA->I<length>.
365-
The key will be saved in the file specified with the B<-newkey> option.
366-
367-
This option cannot be used to create a key pair via a provider.
368-
For use with a provider, the key pair must be generated beforehand
369-
and then can be referenced via B<-newkey>.
363+
generate or request a new key pair of the given type for the requested certificate.
364+
The I<spec> may be of the form C<EC:>I<curve>, C<RSA:>I<length>, C<RSA->I<length>, or simply I<length>.
365+
Everything else is considered an ECC curve name if the OpenSSL version is below 3.5,
366+
while for OpenSSL 3.5+, it is taken as an algorithm name, potentially including parameters,
367+
such as C<ED25519> or C<ML-DSA->I<level>.
368+
For the full list of available algorithms see the output of C<openssl list -public-key-algorithms>.
369+
The RSA key length must be between 1024 and 8192 bits.
370+
The available ECC curves can be shown with the command C<openssl ecparam -list_curves>.
371+
The new key will be saved in the file specified with the B<-newkey> option,
372+
unless the key is generated on a hardware secure element such as TPM 2.0.
373+
374+
For key generation via the L<tpm2-openssl|https://github.com/tpm2-software/tpm2-openssl> provider, use this option in conjunction
375+
with the B<-newkey> option having an argument of the form C<tpm2:handle=0x>I<hex-string>.
376+
The B<-newkeytype> option so far cannot be used to create a key pair via other non-default providers,
377+
so such a key pair must be generated beforehand and then can be referenced via B<-newkey>.
370378

371379
=item B<-centralkeygen>
372380

@@ -375,15 +383,21 @@ This implies B<-popo> C<-1> = NONE.
375383
All other B<-popo> values are not consistent with this option.
376384
Default is local key generation.
377385

378-
=item B<-newkey> I<filename>
386+
=item B<-newkey> I<filename>|I<url>
379387

380-
The file to save the newly generated key
388+
This option is used only when requesting a certificate via IR, CR, or KUR.
389+
When a I<filename> or a I<url> in the C<file:> scheme is given,
390+
this specifies the file to save the newly generated key
381391
in case B<-newkeytype> or B<-centralkeygen> is given.
382-
Otherwise the file to read the private or public key from
383-
for the certificate requested in IR, CR or KUR.
384-
Defaults to the public key in the PKCS#10 CSR given with the B<-csr> option,
392+
Otherwise this gives the location (which may be handled by a provider)
393+
to read the private or public key from for the certificate requested.
394+
The key defaults to the public key in the PKCS#10 CSR given with the B<-csr> option,
385395
the public key of the reference certificate, or the current client key.
386396

397+
In conjunction with the B<-newkeytype> option,
398+
if a I<url> of the form C<tpm2:handle=0x>I<hex-string> is given,
399+
this specifies key generation and storage via the `tpm2-openssl` provider.
400+
387401
=item B<-newkeypass> I<arg>
388402

389403
Pass phrase source for the key file given with the B<-newkey> option.
@@ -1044,7 +1058,7 @@ Specifies name of supported digest to use in RFC 9810's MSG_SIG_ALG
10441058
and as the one-way function (OWF) in MSG_MAC_ALG.
10451059
If applicable, this is used for message protection and
10461060
Proof-of-Possession (POPO) signatures.
1047-
To see the list of supported digests, use B<openssl list -digest-commands>.
1061+
To see the list of supported digests, use C<openssl list -digest-commands>.
10481062
Defaults to C<sha256>.
10491063

10501064
=item B<-mac> I<name>

‎include/genericCMPClient.h‎

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -269,6 +269,13 @@ void CMPclient_finish(OPTIONAL CMP_CTX *ctx);
269269
# include <secutils/credentials/key.h>
270270
# endif
271271

272+
/* EVP_PKEY helpers */
273+
EVP_PKEY *KEY_new(const char *spec); /* may be "RSA:<length>","EC:<curve>","ML-DSA-<level>" */
274+
EVP_PKEY *KEY_new_ex(const char *spec,
275+
OPTIONAL const char *location, /* may be "tpm2:handle=0x<hex-string>" */
276+
OPTIONAL OSSL_LIB_CTX *libctx);
277+
void KEY_free(OPTIONAL EVP_PKEY *pkey);
278+
272279
/* X509_STORE helpers */
273280
EVP_PKEY *KEY_load(OPTIONAL const char *file, OPTIONAL const char *pass,
274281
OPTIONAL const char *engine, OPTIONAL const char *desc);

‎src/cmpClient.c‎

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1840,15 +1840,16 @@ static CMP_err check_set_template_options(CMP_CTX *ctx, EVP_PKEY **new_pkey,
18401840
} else {
18411841
if (opt_newkeytype != NULL || opt_centralkeygen) {
18421842
if (opt_newkey == NULL) {
1843-
LOG_err("Missing -newkey option specifying the file to save the new key");
1843+
LOG(FL_ERR, "Missing -newkey option specifying the file to save the new key%s",
1844+
opt_centralkeygen ? "" : " (or TPM2 provider handle to use)");
18441845
return -40;
18451846
}
18461847
if (opt_newkeytype != NULL && *opt_newkeytype != '\0') {
18471848
/* TODO replace hack: gen preliminary key also when central key gen is requested to quickly get key algorithm identifier */
18481849
const char *key_spec = strcmp(opt_newkeytype, "ECC") == 0
18491850
? "EC:secp256r1" : opt_newkeytype;
18501851

1851-
if ((*new_pkey = KEY_new(key_spec)) == NULL) {
1852+
if ((*new_pkey = KEY_new_ex(key_spec, opt_newkey, app_get0_libctx())) == NULL) {
18521853
LOG(FL_ERR, "Unable to generate new private key according to specification '%s'",
18531854
key_spec);
18541855
return CMP_R_GENERATE_KEY;

‎test/recipes/80-test_cmp_http_data/test_enrollment.csv‎

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,13 @@ NEED_CACHE_DISABLING,0,0,1,missing chain, -section,, -cmd,ir, -newkey,new.key,,
2626
0,*,*,*,newkeypass invalid, -section,, -cmd,ir, -newkey,new_pass_12345.key,, -newkeypass,fp:4,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -certout,test.cert.pem,, -out_trusted,root.crt,,BLANK,,BLANK,,,
2727
1,1,1,1,newkeypass no prefix, -section,, -cmd,ir, -newkey,new_pass_12345.key,, -newkeypass,12345,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -certout,test.cert.pem,, -out_trusted,root.crt,,BLANK,,BLANK,,,
2828
,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,
29+
1,1,1,1,newkeytype RSA:2048, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,RSA:2048
30+
0,0,0,0,newkeytype RSA:1023, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,RSA:1023
31+
1,1,1,1,newkeytype EC:secp256r1, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,EC:secp256r1
32+
0,0,0,0,newkeytype unknown-curve, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,unknown-curve
33+
3.5,3.5,3.5,3.5,newkeytype ML-DSA-65, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,ML-DSA-65
34+
3.5 0,3.5 0,3.5 0,3.5 0,newkeytype ML-DSA-43, -section,, -cmd,ir, -newkey,_RESULT_DIR/new.key,, -newkeypass,pass:,,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -reqout_only,_RESULT_DIR/t.der,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -newkeytype,ML-DSA-43
35+
,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,
2936
0,*,*,*,subject argument missing, -section,, -cmd,ir, -newkey,new.key,, -newkeypass,pass:, -subject,BLANK,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -certout,test.cert.pem,, -out_trusted,root.crt,,BLANK,,BLANK,,,
3037
TBD,TBD,TBD OpenSSL 3.0 still uses default,0,subject empty string, -section,, -cmd,ir, -newkey,new.key,, -newkeypass,pass:, -subject,"""",BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -certout,test.cert.pem,, -out_trusted,root.crt,,BLANK,,BLANK,,,
3138
0,0,0,Insta gives status 503 and subsequent responses are errors transactionid unmatched,subject NULL-DN, -section,, -cmd,ir, -newkey,new.key,, -newkeypass,pass:, -subject,/,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,,BLANK,, -certout,test.cert.pem,, -out_trusted,root.crt,,BLANK,,BLANK,,,, -unprotected_errors

0 commit comments

Comments
 (0)