[Openvpn-devel,3/3] Document management request >ECDSA_SIGN and response ecdsa-sig

Message ID 1515959073-10376-4-git-send-email-selva.nair@gmail.com
State Superseded
Headers show
Series Support external EC cert/key using --management-external-xxx | expand

Commit Message

Selva Nair Jan. 14, 2018, 8:44 a.m. UTC
From: Selva Nair <selva.nair@gmail.com>

Signed-off-by: Selva Nair <selva.nair@gmail.com>
---
 doc/management-notes.txt | 30 ++++++++++++++++++++++++++++++
 1 file changed, 30 insertions(+)

Comments

Arne Schwabe Jan. 16, 2018, 11:40 a.m. UTC | #1
Am 14.01.18 um 20:44 schrieb selva.nair@gmail.com:
> From: Selva Nair <selva.nair@gmail.com>
> 
> Signed-off-by: Selva Nair <selva.nair@gmail.com>
> ---
>  doc/management-notes.txt | 30 ++++++++++++++++++++++++++++++
>  1 file changed, 30 insertions(+)
> 
> diff --git a/doc/management-notes.txt b/doc/management-notes.txt
> index a9ba18a..e2e8249 100644
> --- a/doc/management-notes.txt
> +++ b/doc/management-notes.txt
> @@ -795,6 +795,36 @@ Base64 encoded output of RSA_private_encrypt() (OpenSSL) or mbedtls_pk_sign()
>  This capability is intended to allow the use of arbitrary cryptographic
>  service providers with OpenVPN via the management interface.
>  
> +COMMAND -- ecdsa-sig (OpenVPN 2.5 or higher)
> +------------------------------------------
> +Same as rsa-sig but for EC keys: requires openssl 1.1
> +
> +Provides support for external storage of the EC private key. Requires the
> +--management-external-key option. This option can be used instead of "key"
> +in client mode, and allows the client to run without the need to load the
> +actual private key. When the SSL protocol needs to perform a sign
> +operation, the data to be signed will be sent to the management interface
> +via a notification as follows:
> +
> +>ECDSA_SIGN:[BASE64_DATA]
> +
> +The management interface client should then create a DER encoded signature of
> +the (decoded) BASE64_DATA using the private key and return the SSL signature as
> +follows:
> +
> +ecdsa-sig
> +[BASE64_SIG_LINE]
> +.
> +.
> +.
> +END
> +
> +Base64 encoded output of ECDSA_sign() (OpenSSL) or mbedtls_pk_sign()
> +(mbed TLS) will provide a correct signature.
> +

Signature.getInstance("NONEwithECDSA") worked for me in Java for this.
Any other signature algorithm did _NOT_ work e.g. SHA384withECDSA. I
think ecdsa-sign might already provided a hash to sign.

On the other hand mbedtls documentation states:

   For RSA, md_alg may be MBEDTLS_MD_NONE if hash_len != 0. For
   ECDSA md_alg may never be MBEDTLS_MD_NONE.

So this interface might not work with mbedtls.

Arne

Acked-By: Arne Schwabe



------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
Selva Nair Jan. 16, 2018, 5:41 p.m. UTC | #2
Hi,

FWIW, some remarks on the hash and the signature below.

On Tue, Jan 16, 2018 at 5:23 PM, Arne Schwabe <arne@rfc2549.org> wrote:
> Am 14.01.18 um 20:44 schrieb selva.nair@gmail.com:
>> From: Selva Nair <selva.nair@gmail.com>
>>
>> Signed-off-by: Selva Nair <selva.nair@gmail.com>
>> ---
>>  doc/management-notes.txt | 30 ++++++++++++++++++++++++++++++
>>  1 file changed, 30 insertions(+)
>>
>> diff --git a/doc/management-notes.txt b/doc/management-notes.txt
>> index a9ba18a..e2e8249 100644
>> --- a/doc/management-notes.txt
>> +++ b/doc/management-notes.txt
>> @@ -795,6 +795,36 @@ Base64 encoded output of RSA_private_encrypt() (OpenSSL) or mbedtls_pk_sign()
>>  This capability is intended to allow the use of arbitrary cryptographic
>>  service providers with OpenVPN via the management interface.
>>
>> +COMMAND -- ecdsa-sig (OpenVPN 2.5 or higher)
>> +------------------------------------------
>> +Same as rsa-sig but for EC keys: requires openssl 1.1
>> +
>> +Provides support for external storage of the EC private key. Requires the
>> +--management-external-key option. This option can be used instead of "key"
>> +in client mode, and allows the client to run without the need to load the
>> +actual private key. When the SSL protocol needs to perform a sign
>> +operation, the data to be signed will be sent to the management interface
>> +via a notification as follows:
>> +
>> +>ECDSA_SIGN:[BASE64_DATA]
>> +
>> +The management interface client should then create a DER encoded signature of
>> +the (decoded) BASE64_DATA using the private key and return the SSL signature as
>> +follows:
>> +
>> +ecdsa-sig
>> +[BASE64_SIG_LINE]
>> +.
>> +.
>> +.
>> +END
>> +
>> +Base64 encoded output of ECDSA_sign() (OpenSSL) or mbedtls_pk_sign()
>> +(mbed TLS) will provide a correct signature.
>> +
>
> Signature.getInstance("NONEwithECDSA") worked for me in Java for this.
> Any other signature algorithm did _NOT_ work e.g. SHA384withECDSA. I
> think ecdsa-sign might already provided a hash to sign.

Yes, the hash is what is provided in this signature request. In this
particular case,
the data is handshake history and may not be even saved. Its the accumulated
hash that is passed in by the SSL/TLS library to the callback.

So "NONEwithECDSA" should be the right choice for Java (Sun/Oracle) -- or
ECDSAforSSL in case of IBM Java.

>
> On the other hand mbedtls documentation states:
>
>    For RSA, md_alg may be MBEDTLS_MD_NONE if hash_len != 0. For
>    ECDSA md_alg may never be MBEDTLS_MD_NONE.

External RSA keys currently work with both openssl and mbedtls.

To elaborate, for RSA, its more complicated as the hash to be encoded
with the OID of the hash algo prepended to it as specified in PKCS1 v1.5,
then padded and signed. Unless the pre TLS1.2  MD5+SHA1 mixed hash is
in use. In the latter case only padding is needed and that's the case where
mbedtls specifies hash type as none.

For RSA, openssl callback gets the encoded hash (not padded) and signing
involves padding + encryption only (hash type is not needed). But mbedtls
provides the hash and hash algorithm and the signing routine has to encode it.
However, the pkcs1 v1.5 encoding part is already present in ssl_mbedtls.c
(implemented by Stefan, I suppose) so what the management interface gets is
the same  data for both openssl and  mbedtls builds as far as RSA is concerned.

>
> So this interface might not work with mbedtls.

It should work if only we could find a way to set a callback for this
in mbedtls.
It seems they provide that facility only for RSA keys. Stefan may know.
Not sure how pkcs11-helper hooks on to it -- does it support EC keys?

Regards,

Selva

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
Steffan Karger Jan. 16, 2018, 9:47 p.m. UTC | #3
Hi,

Quickly replying without proper reading, to not postpone my response.

On 17-01-18 05:41, Selva Nair wrote:
> FWIW, some remarks on the hash and the signature below.
> 
> On Tue, Jan 16, 2018 at 5:23 PM, Arne Schwabe <arne@rfc2549.org> wrote:
>> Am 14.01.18 um 20:44 schrieb selva.nair@gmail.com:
>>> From: Selva Nair <selva.nair@gmail.com>
>>>
>>> Signed-off-by: Selva Nair <selva.nair@gmail.com>
>>> ---
>>>  doc/management-notes.txt | 30 ++++++++++++++++++++++++++++++
>>>  1 file changed, 30 insertions(+)
>>>
>>> diff --git a/doc/management-notes.txt b/doc/management-notes.txt
>>> index a9ba18a..e2e8249 100644
>>> --- a/doc/management-notes.txt
>>> +++ b/doc/management-notes.txt
>>> @@ -795,6 +795,36 @@ Base64 encoded output of RSA_private_encrypt() (OpenSSL) or mbedtls_pk_sign()
>>>  This capability is intended to allow the use of arbitrary cryptographic
>>>  service providers with OpenVPN via the management interface.
>>>
>>> +COMMAND -- ecdsa-sig (OpenVPN 2.5 or higher)
>>> +------------------------------------------
>>> +Same as rsa-sig but for EC keys: requires openssl 1.1
>>> +
>>> +Provides support for external storage of the EC private key. Requires the
>>> +--management-external-key option. This option can be used instead of "key"
>>> +in client mode, and allows the client to run without the need to load the
>>> +actual private key. When the SSL protocol needs to perform a sign
>>> +operation, the data to be signed will be sent to the management interface
>>> +via a notification as follows:
>>> +
>>> +>ECDSA_SIGN:[BASE64_DATA]
>>> +
>>> +The management interface client should then create a DER encoded signature of
>>> +the (decoded) BASE64_DATA using the private key and return the SSL signature as
>>> +follows:
>>> +
>>> +ecdsa-sig
>>> +[BASE64_SIG_LINE]
>>> +.
>>> +.
>>> +.
>>> +END
>>> +
>>> +Base64 encoded output of ECDSA_sign() (OpenSSL) or mbedtls_pk_sign()
>>> +(mbed TLS) will provide a correct signature.
>>> +
>>
>> Signature.getInstance("NONEwithECDSA") worked for me in Java for this.
>> Any other signature algorithm did _NOT_ work e.g. SHA384withECDSA. I
>> think ecdsa-sign might already provided a hash to sign.
> 
> Yes, the hash is what is provided in this signature request. In this
> particular case,
> the data is handshake history and may not be even saved. Its the accumulated
> hash that is passed in by the SSL/TLS library to the callback.
> 
> So "NONEwithECDSA" should be the right choice for Java (Sun/Oracle) -- or
> ECDSAforSSL in case of IBM Java.
> 
>>
>> On the other hand mbedtls documentation states:
>>
>>    For RSA, md_alg may be MBEDTLS_MD_NONE if hash_len != 0. For
>>    ECDSA md_alg may never be MBEDTLS_MD_NONE.
> 
> External RSA keys currently work with both openssl and mbedtls.
> 
> To elaborate, for RSA, its more complicated as the hash to be encoded
> with the OID of the hash algo prepended to it as specified in PKCS1 v1.5,
> then padded and signed. Unless the pre TLS1.2  MD5+SHA1 mixed hash is
> in use. In the latter case only padding is needed and that's the case where
> mbedtls specifies hash type as none.
> 
> For RSA, openssl callback gets the encoded hash (not padded) and signing
> involves padding + encryption only (hash type is not needed). But mbedtls
> provides the hash and hash algorithm and the signing routine has to encode it.
> However, the pkcs1 v1.5 encoding part is already present in ssl_mbedtls.c
> (implemented by Stefan, I suppose) so what the management interface gets is
> the same  data for both openssl and  mbedtls builds as far as RSA is concerned.

This was written by a colleague of mine, but I sent patches to refactor
this a little while ago:

https://patchwork.openvpn.net/project/openvpn2/list/?series=57

Those are still awaiting review and might be worth to check out in this
context.

>> So this interface might not work with mbedtls.
> 
> It should work if only we could find a way to set a callback for this
> in mbedtls.
> It seems they provide that facility only for RSA keys. Stefan may know.
> Not sure how pkcs11-helper hooks on to it -- does it support EC keys?

Last time I checked there was only a way to externally sign using RSA
(in mbed), but I haven't checked in a while.  I'm fine with leaving mbed
aside in this patch set for now, as long as it doesn't break it.  I'll
then later look into implementing the mbed equivalent.

-Steffan

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
Selva Nair Jan. 25, 2018, 9:02 a.m. UTC | #4
Hi,

On Sun, Jan 14, 2018 at 2:44 PM,  <selva.nair@gmail.com> wrote:
> From: Selva Nair <selva.nair@gmail.com>
>
> Signed-off-by: Selva Nair <selva.nair@gmail.com>
> ---
>  doc/management-notes.txt | 30 ++++++++++++++++++++++++++++++
>  1 file changed, 30 insertions(+)
>

Documentation changes are now handled in the management client version
patches and v3 of ecdsa-signature patch. So please ignore this one.

Selva

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot

Patch

diff --git a/doc/management-notes.txt b/doc/management-notes.txt
index a9ba18a..e2e8249 100644
--- a/doc/management-notes.txt
+++ b/doc/management-notes.txt
@@ -795,6 +795,36 @@  Base64 encoded output of RSA_private_encrypt() (OpenSSL) or mbedtls_pk_sign()
 This capability is intended to allow the use of arbitrary cryptographic
 service providers with OpenVPN via the management interface.
 
+COMMAND -- ecdsa-sig (OpenVPN 2.5 or higher)
+------------------------------------------
+Same as rsa-sig but for EC keys: requires openssl 1.1
+
+Provides support for external storage of the EC private key. Requires the
+--management-external-key option. This option can be used instead of "key"
+in client mode, and allows the client to run without the need to load the
+actual private key. When the SSL protocol needs to perform a sign
+operation, the data to be signed will be sent to the management interface
+via a notification as follows:
+
+>ECDSA_SIGN:[BASE64_DATA]
+
+The management interface client should then create a DER encoded signature of
+the (decoded) BASE64_DATA using the private key and return the SSL signature as
+follows:
+
+ecdsa-sig
+[BASE64_SIG_LINE]
+.
+.
+.
+END
+
+Base64 encoded output of ECDSA_sign() (OpenSSL) or mbedtls_pk_sign()
+(mbed TLS) will provide a correct signature.
+
+This capability is intended to allow the use of arbitrary cryptographic
+service providers with OpenVPN via the management interface.
+
 COMMAND -- certificate (OpenVPN 2.4 or higher)
 ----------------------------------------------
 Provides support for external storage of the certificate. Requires the