openssl: add support to use keys and certificates from PKCS#11 provider

In OpenSSL < 3.0, the modularity was provided by mechanism called
"engines". This is supported in curl, but the engines got deprecated
with OpenSSL 3.0 in favor of more versatile providers.

This adds a support for OpenSSL Providers, to use PKCS#11 keys, namely
through the pkcs11 provider. This is done using similar approach as the
engines and this is automatically built in when the OpenSSL 3 and newer
is used.

Signed-off-by: Jakub Jelen <jjelen@redhat.com>

Closes #15587
This commit is contained in:
Jakub Jelen 2024-11-14 17:57:48 +01:00 committed by Daniel Stenberg
parent d1336ca14a
commit 999cc818c5
No known key found for this signature in database
GPG key ID: 5CC908FDB71E12C2
9 changed files with 247 additions and 28 deletions

View file

@ -4,7 +4,7 @@ SPDX-License-Identifier: curl
Long: cert-type
Protocols: TLS
Arg: <type>
Help: Certificate type (DER/PEM/ENG/P12)
Help: Certificate type (DER/PEM/ENG/PROV/P12)
Category: tls
Added: 7.9.3
Multi: single
@ -18,9 +18,9 @@ Example:
# `--cert-type`
Set type of the provided client certificate. PEM, DER, ENG and P12 are
Set type of the provided client certificate. PEM, DER, ENG, PROV and P12 are
recognized types.
The default type depends on the TLS backend and is usually PEM, however for
Secure Transport and Schannel it is P12. If --cert is a pkcs11: URI then ENG is
the default type.
Secure Transport and Schannel it is P12. If --cert is a pkcs11: URI then ENG
or PROV is the default type (depending on OpenSSL version).

View file

@ -32,12 +32,12 @@ In the \<certificate\> portion of the argument, you must escape the character
you must escape the double quote character as \" so that it is not recognized
as an escape character.
If curl is built against OpenSSL library, and the engine pkcs11 is available,
then a PKCS#11 URI (RFC 7512) can be used to specify a certificate located in
a PKCS#11 device. A string beginning with `pkcs11:` is interpreted as a
PKCS#11 URI. If a PKCS#11 URI is provided, then the --engine option is set as
`pkcs11` if none was provided and the --cert-type option is set as `ENG` if
none was provided.
If curl is built against OpenSSL library, and the engine pkcs11 or pkcs11
provider is available, then a PKCS#11 URI (RFC 7512) can be used to specify a
certificate located in a PKCS#11 device. A string beginning with `pkcs11:` is
interpreted as a PKCS#11 URI. If a PKCS#11 URI is provided, then the --engine
option is set as `pkcs11` if none was provided and the --cert-type option is
set as `ENG` or `PROV` if none was provided (depending on OpenSSL version).
If curl is built against GnuTLS library, a PKCS#11 URI can be used to specify
a certificate located in a PKCS#11 device. A string beginning with `pkcs11:`

View file

@ -21,12 +21,12 @@ Private key filename. Allows you to provide your private key in this separate
file. For SSH, if not specified, curl tries the following candidates in order:
`~/.ssh/id_rsa`, `~/.ssh/id_dsa`, `./id_rsa`, `./id_dsa`.
If curl is built against OpenSSL library, and the engine pkcs11 is available,
then a PKCS#11 URI (RFC 7512) can be used to specify a private key located in
a PKCS#11 device. A string beginning with `pkcs11:` is interpreted as a
PKCS#11 URI. If a PKCS#11 URI is provided, then the --engine option is set as
`pkcs11` if none was provided and the --key-type option is set as `ENG` if
none was provided.
If curl is built against OpenSSL library, and the engine pkcs11 or pkcs11
provider is available, then a PKCS#11 URI (RFC 7512) can be used to specify a
private key located in a PKCS#11 device. A string beginning with `pkcs11:` is
interpreted as a PKCS#11 URI. If a PKCS#11 URI is provided, then the --engine
option is set as `pkcs11` if none was provided and the --key-type option is
set as `ENG` or `PROV` if none was provided (depending on OpenSSL version).
If curl is built against Secure Transport or Schannel then this option is
ignored for TLS protocols (HTTPS, etc). Those backends expect the private key

View file

@ -17,10 +17,10 @@ Example:
# `--proxy-cert-type`
Set type of the provided client certificate when using HTTPS proxy. PEM, DER,
ENG and P12 are recognized types.
ENG, PROV and P12 are recognized types.
The default type depends on the TLS backend and is usually PEM, however for
Secure Transport and Schannel it is P12. If --proxy-cert is a pkcs11: URI then
ENG is the default type.
ENG or PROV is the default type (depending on OpenSSL version).
Equivalent to --cert-type but used in HTTPS proxy context.

View file

@ -34,7 +34,8 @@ CURLcode curl_easy_setopt(CURL *handle, CURLOPT_PROXY_SSLKEYTYPE, char *type);
This option is for connecting to an HTTPS proxy, not an HTTPS server.
Pass a pointer to a null-terminated string as parameter. The string should be
the format of your private key. Supported formats are "PEM", "DER" and "ENG".
the format of your private key. Supported formats are "PEM", "DER", "ENG" and
"PROV" (the latter added in curl 8.12.0).
The application does not have to keep the string around after setting this
option.

View file

@ -32,12 +32,18 @@ CURLcode curl_easy_setopt(CURL *handle, CURLOPT_SSLKEYTYPE, char *type);
# DESCRIPTION
Pass a pointer to a null-terminated string as parameter. The string should be
the format of your private key. Supported formats are "PEM", "DER" and "ENG".
the format of your private key. Supported formats are "PEM", "DER", "ENG" and
"PROV".
The format "ENG" enables you to load the private key from a crypto engine. In
this case CURLOPT_SSLKEY(3) is used as an identifier passed to the engine. You
have to set the crypto engine with CURLOPT_SSLENGINE(3). "DER" format key file
currently does not work because of a bug in OpenSSL.
have to set the crypto engine with CURLOPT_SSLENGINE(3).
The format "PROV" enables you to load the private key from a crypto provider
(Added in 8.12.0). In this case CURLOPT_SSLKEY(3) is used as an identifier
passed to the provider.
The "DER" format does not work with OpenSSL.
The application does not have to keep the string around after setting this
option.