adding initial support for ECDSA (19) to netpgp. tested using p256/sha256, p384/sha384, and p521/sha512

This commit is contained in:
jhigh 2022-08-26 19:18:38 +00:00
parent 5c869fd70e
commit 0294a66b69
11 changed files with 418 additions and 12 deletions

View File

@ -57,7 +57,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: create.c,v 1.38 2010/11/15 08:03:39 agc Exp $");
__RCSID("$NetBSD: create.c,v 1.39 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <sys/types.h>
@ -250,6 +250,11 @@ write_pubkey_body(const pgp_pubkey_t *key, pgp_output_t *output)
pgp_write_mpi(output, key->key.dsa.g) &&
pgp_write_mpi(output, key->key.dsa.y);
case PGP_PKA_ECDSA:
return pgp_write(output, &key->key.ecdsa.len, 1) &&
pgp_write(output, key->key.ecdsa.oid, key->key.ecdsa.len) &&
pgp_write_mpi(output, key->key.ecdsa.p);
case PGP_PKA_RSA:
case PGP_PKA_RSA_ENCRYPT_ONLY:
case PGP_PKA_RSA_SIGN_ONLY:

View File

@ -58,7 +58,9 @@
#include "memory.h"
#include "packet-parse.h"
#include <openssl/evp.h>
#include <openssl/dsa.h>
#include <openssl/ecdsa.h>
#define PGP_MIN_HASH_SIZE 16
@ -119,6 +121,10 @@ unsigned pgp_dsa_verify(const uint8_t *, size_t,
const pgp_dsa_sig_t *,
const pgp_dsa_pubkey_t *);
unsigned pgp_ecdsa_verify(const uint8_t *, size_t,
const pgp_ecdsa_sig_t *,
const pgp_ecdsa_pubkey_t *);
int pgp_rsa_public_decrypt(uint8_t *, const uint8_t *, size_t,
const pgp_rsa_pubkey_t *);
int pgp_rsa_public_encrypt(uint8_t *, const uint8_t *, size_t,
@ -214,6 +220,10 @@ DSA_SIG *pgp_dsa_sign(uint8_t *, unsigned,
const pgp_dsa_seckey_t *,
const pgp_dsa_pubkey_t *);
ECDSA_SIG *pgp_ecdsa_sign(uint8_t *, unsigned,
const pgp_ecdsa_seckey_t *,
const pgp_ecdsa_pubkey_t *);
int openssl_read_pem_seckey(const char *, pgp_key_t *, const char *, int);
/** pgp_reader_t */

View File

@ -57,7 +57,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: misc.c,v 1.43 2020/04/18 19:27:48 jhigh Exp $");
__RCSID("$NetBSD: misc.c,v 1.44 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <sys/types.h>
@ -96,6 +96,18 @@ __RCSID("$NetBSD: misc.c,v 1.43 2020/04/18 19:27:48 jhigh Exp $");
#define vsnprintf _vsnprintf
#endif
struct ecdsa_map {
char *sname;
int nid;
int bits;
int len;
uint8_t oid[8];
} ecdsa_map[] = {
{ "P-256", NID_X9_62_prime256v1, 256, 8, {0x2A, 0x86, 0x48, 0xCE, 0x3D, 0x03, 0x01, 0x07} },
{ "P-384", NID_secp384r1, 384, 5, {0x2B, 0x81, 0x04, 0x00, 0x22} },
{ "P-521", NID_secp521r1, 521, 5, {0x2B, 0x81, 0x04, 0x00, 0x23} },
{ NULL, 0, 0, 0, {0} }
};
typedef struct {
pgp_keyring_t *keyring;
@ -1364,3 +1376,75 @@ netpgp_strcasecmp(const char *s1, const char *s2)
}
return n;
}
int
ecdsa_nid(const pgp_ecdsa_pubkey_t * pub)
{
int i;
for (i = 0; ecdsa_map[i].sname; i++ ) {
if (pub->len == ecdsa_map[i].len) {
if (memcmp(pub->oid, ecdsa_map[i].oid, pub->len) == 0) {
return ecdsa_map[i].nid;
}
}
}
return -1;
}
int
ecdsa_numbits(const pgp_ecdsa_pubkey_t * pub)
{
int i;
for (i = 0; ecdsa_map[i].sname; i++ ) {
if (pub->len == ecdsa_map[i].len) {
if (memcmp(pub->oid, ecdsa_map[i].oid, pub->len) == 0) {
return ecdsa_map[i].bits;
}
}
}
return -1;
}
int
ecdsa_hashsize(const pgp_ecdsa_pubkey_t * pub)
{
int bits;
bits = ecdsa_numbits(pub);
if (bits == -1) {
return -1;
}
return (bits/8) - (bits%8);
}
pgp_hash_alg_t
ecdsa_hashalg(const pgp_ecdsa_pubkey_t * pub)
{
int nid;
if (pub == NULL) {
return PGP_HASH_UNKNOWN;
}
nid = ecdsa_nid(pub);
switch (nid) {
case NID_X9_62_prime256v1:
return PGP_HASH_SHA256;
case NID_secp384r1:
return PGP_HASH_SHA384;
case NID_secp521r1:
return PGP_HASH_SHA512;
default:
(void) fprintf(stderr, "ecdsa_hashalg: unknown NID\n");
}
return PGP_HASH_UNKNOWN;
}

View File

@ -74,5 +74,9 @@ void netpgp_log(const char *, ...) __printflike(1, 2);
int netpgp_strcasecmp(const char *, const char *);
char *netpgp_strdup(const char *);
int ecdsa_numbits(const pgp_ecdsa_pubkey_t *);
int ecdsa_nid(const pgp_ecdsa_pubkey_t *);
pgp_hash_alg_t ecdsa_hashalg(const pgp_ecdsa_pubkey_t *);
int ecdsa_hashsize(const pgp_ecdsa_pubkey_t *);
#endif

View File

@ -57,7 +57,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: openssl_crypto.c,v 1.34 2018/02/05 23:56:01 christos Exp $");
__RCSID("$NetBSD: openssl_crypto.c,v 1.35 2022/08/26 19:18:38 jhigh Exp $");
#endif
#ifdef HAVE_OPENSSL_DSA_H
@ -87,6 +87,7 @@ __RCSID("$NetBSD: openssl_crypto.c,v 1.34 2018/02/05 23:56:01 christos Exp $");
#include "readerwriter.h"
#include "netpgpdefs.h"
#include "netpgpdigest.h"
#include "netpgpsdk.h"
#include "packet.h"
static void
@ -223,6 +224,103 @@ takeDSA(const DSA *odsa, pgp_dsa_seckey_t *sk)
sk->x = BN_dup(x);
}
static ECDSA_SIG *
makeECDSADSA_SIG(const pgp_ecdsa_sig_t *sig)
{
ECDSA_SIG *osig;
BIGNUM *r, *s;
osig = ECDSA_SIG_new();
r = BN_dup(sig->r);
s = BN_dup(sig->s);
#if OPENSSL_VERSION_NUMBER >= 0x10100000L
ECDSA_SIG_set0(osig, r, s);
#else
BN_free(osig->r);
BN_free(osig->s);
osig->r = r;
osig->s = s;
#endif
return osig;
}
static EC_KEY *
makeECDSA(const pgp_ecdsa_pubkey_t *ecdsa, const pgp_ecdsa_seckey_t *sececdsa)
{
EC_KEY *key;
BIGNUM *x;
BIGNUM *y;
EC_GROUP *group;
EC_POINT *pub_key;
EC_POINT *point;
int nid;
key = EC_KEY_new();
x = BN_new();
y = BN_new();
nid = ecdsa_nid(ecdsa);
if (nid == -1) {
(void) fprintf(stderr,"makeECDSA: failed to determine NID\n");
return 0;
}
group = EC_GROUP_new_by_curve_name(nid);
if (group == NULL) {
(void) fprintf(stderr,"makeECDSA: failed to get group for specified NID\n");
return 0;
}
pub_key = EC_POINT_new(group);
if (pub_key == NULL) {
(void) fprintf(stderr,"makeECDSA: failed to alloc point\n");
return 0;
}
point = EC_POINT_bn2point(group, ecdsa->p, NULL, NULL);
if (point == NULL) {
(void) fprintf(stderr,"makeECDSA: failed to conv BN to point\n");
return 0;
}
if ((EC_POINT_get_affine_coordinates(group, point, x, y, NULL)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to get coordinates from point\n");
return 0;
}
if ((EC_POINT_set_affine_coordinates(group, pub_key, x, y, NULL)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to set coordinates from point\n");
return 0;
}
if ((EC_KEY_set_group(key, group)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to set group for key\n");
return 0;
}
if ((EC_KEY_set_public_key(key, pub_key)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to set pubkey for key\n");
return 0;
}
if (sececdsa) {
if ((EC_KEY_set_private_key(key, sececdsa->x)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to set seckey for key\n");
return 0;
}
if ((EC_POINT_mul(group, pub_key, sececdsa->x, NULL, NULL, NULL)) == 0) {
(void) fprintf(stderr,"makeECDSA: failed to calculate generator\n");
return 0;
}
}
return key;
}
static void
test_seckey(const pgp_seckey_t *seckey)
{
@ -587,6 +685,36 @@ pgp_dsa_verify(const uint8_t *hash, size_t hash_length,
return (unsigned)ret;
}
unsigned
pgp_ecdsa_verify(const uint8_t *hash, size_t hash_length,
const pgp_ecdsa_sig_t *sig,
const pgp_ecdsa_pubkey_t *ecdsa)
{
unsigned qlen;
ECDSA_SIG *osig = makeECDSADSA_SIG(sig);
EC_KEY *oecdsa = makeECDSA(ecdsa, NULL);
int ret;
if (pgp_get_debug_level(__FILE__)) {
hexdump(stderr, "input hash", hash, hash_length);
}
ret = ECDSA_do_verify(hash, (int)hash_length, osig, oecdsa);
if (pgp_get_debug_level(__FILE__)) {
(void) fprintf(stderr, "ret=%d\n", ret);
}
if (ret <= 0) {
(void) fprintf(stderr, "pgp_ecdsa_verify: ECDSA verification failed\n");
return 0;
}
ECDSA_SIG_free(osig);
return (unsigned)ret;
}
/**
\ingroup Core_Crypto
\brief Recovers message digest from the signature
@ -916,6 +1044,27 @@ pgp_dsa_sign(uint8_t *hashbuf,
return dsasig;
}
ECDSA_SIG *
pgp_ecdsa_sign(uint8_t *hashbuf,
unsigned hashsize,
const pgp_ecdsa_seckey_t *sececdsa,
const pgp_ecdsa_pubkey_t *pubecdsa)
{
ECDSA_SIG * ecdsasig;
EC_KEY * eckey = makeECDSA(pubecdsa, sececdsa);
ecdsasig = ECDSA_do_sign(hashbuf, (int)hashsize, eckey);
if (ecdsasig == NULL) {
printf("do_sign returned null\n");
return 0;
}
EC_KEY_free(eckey);
return ecdsasig;
}
int
openssl_read_pem_seckey(const char *f, pgp_key_t *key, const char *type, int verbose)
{

View File

@ -58,7 +58,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: packet-parse.c,v 1.53 2020/10/14 05:19:41 jhigh Exp $");
__RCSID("$NetBSD: packet-parse.c,v 1.54 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <sys/types.h>
@ -940,6 +940,11 @@ sig_free(pgp_sig_t *sig)
free_BN(&sig->info.sig.dsa.s);
break;
case PGP_PKA_ECDSA:
free_BN(&sig->info.sig.ecdsa.r);
free_BN(&sig->info.sig.ecdsa.s);
break;
case PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN:
free_BN(&sig->info.sig.elgamal.r);
free_BN(&sig->info.sig.elgamal.s);
@ -1176,6 +1181,10 @@ pgp_pubkey_free(pgp_pubkey_t *p)
free_BN(&p->key.dsa.y);
break;
case PGP_PKA_ECDSA:
free_BN(&p->key.ecdsa.p);
break;
case PGP_PKA_ELGAMAL:
case PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN:
free_BN(&p->key.elgamal.p);
@ -1245,6 +1254,14 @@ parse_pubkey_data(pgp_pubkey_t *key, pgp_region_t *region,
}
break;
case PGP_PKA_ECDSA:
if (!limread(&key->key.ecdsa.len, 1, region, stream) ||
!limread(key->key.ecdsa.oid, key->key.ecdsa.len, region, stream) ||
!limread_mpi(&key->key.ecdsa.p, region, stream)) {
return 0;
}
break;
case PGP_PKA_RSA:
case PGP_PKA_RSA_ENCRYPT_ONLY:
case PGP_PKA_RSA_SIGN_ONLY:
@ -1496,6 +1513,13 @@ parse_v3_sig(pgp_region_t *region,
}
break;
case PGP_PKA_ECDSA:
if (!limread_mpi(&pkt.u.sig.info.sig.ecdsa.r, region, stream) ||
!limread_mpi(&pkt.u.sig.info.sig.ecdsa.s, region, stream)) {
return 0;
}
break;
case PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN:
if (!limread_mpi(&pkt.u.sig.info.sig.elgamal.r, region,
stream) ||
@ -2035,6 +2059,13 @@ parse_v4_sig(pgp_region_t *region, pgp_stream_t *stream)
}
break;
case PGP_PKA_ECDSA:
if (!limread_mpi(&pkt.u.sig.info.sig.ecdsa.r, region, stream) ||
!limread_mpi(&pkt.u.sig.info.sig.ecdsa.s, region, stream)) {
return 0;
}
break;
case PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN:
if (!limread_mpi(&pkt.u.sig.info.sig.elgamal.r, region,
stream) ||
@ -2322,6 +2353,10 @@ pgp_seckey_free(pgp_seckey_t *key)
free_BN(&key->key.dsa.x);
break;
case PGP_PKA_ECDSA:
free_BN(&key->key.ecdsa.x);
break;
default:
(void) fprintf(stderr,
"pgp_seckey_free: Unknown algorithm: %d (%s)\n",
@ -2632,6 +2667,12 @@ parse_seckey(pgp_region_t *region, pgp_stream_t *stream)
}
break;
case PGP_PKA_ECDSA:
if (!limread_mpi(&pkt.u.seckey.key.ecdsa.x, region, stream)) {
ret = 0;
}
break;
case PGP_PKA_ELGAMAL:
if (!limread_mpi(&pkt.u.seckey.key.elgamal.x, region, stream)) {
ret = 0;

View File

@ -58,7 +58,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: packet-print.c,v 1.43 2021/07/28 22:31:45 jhigh Exp $");
__RCSID("$NetBSD: packet-print.c,v 1.44 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <string.h>
@ -325,6 +325,8 @@ numkeybits(const pgp_pubkey_t *pubkey)
default:
return 0;
}
case PGP_PKA_ECDSA:
return ecdsa_numbits(&pubkey->key.ecdsa);
case PGP_PKA_ELGAMAL:
return BN_num_bytes(pubkey->key.elgamal.y) * 8;
default:
@ -659,7 +661,9 @@ pgp_print_pubkey(const pgp_pubkey_t *pubkey)
print_bn(0, "g", pubkey->key.dsa.g);
print_bn(0, "y", pubkey->key.dsa.y);
break;
case PGP_PKA_ECDSA:
print_bn(0, "p", pubkey->key.ecdsa.p);
break;
case PGP_PKA_RSA:
case PGP_PKA_RSA_ENCRYPT_ONLY:
case PGP_PKA_RSA_SIGN_ONLY:
@ -974,6 +978,11 @@ pgp_print_packet(pgp_printstate_t *print, const pgp_packet_t *pkt)
print_bn(print->indent, "s", content->sig.info.sig.dsa.s);
break;
case PGP_PKA_ECDSA:
print_bn(print->indent, "r", content->sig.info.sig.ecdsa.r);
print_bn(print->indent, "s", content->sig.info.sig.ecdsa.s);
break;
case PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN:
print_bn(print->indent, "r", content->sig.info.sig.elgamal.r);
print_bn(print->indent, "s", content->sig.info.sig.elgamal.s);

View File

@ -60,7 +60,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: packet-show.c,v 1.22 2021/07/28 22:31:45 jhigh Exp $");
__RCSID("$NetBSD: packet-show.c,v 1.23 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <stdlib.h>
@ -218,7 +218,7 @@ static pgp_map_t pubkey_alg_map[] =
{PGP_PKA_ELGAMAL, "Elgamal (Encrypt-Only)"},
{PGP_PKA_DSA, "DSA"},
{PGP_PKA_RESERVED_ELLIPTIC_CURVE, "Reserved for Elliptic Curve"},
{PGP_PKA_RESERVED_ECDSA, "Reserved for ECDSA"},
{PGP_PKA_ECDSA, "ECDSA"},
{PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN, "Reserved (formerly Elgamal Encrypt or Sign"},
{PGP_PKA_RESERVED_DH, "Reserved for Diffie-Hellman (X9.42)"},
{PGP_PKA_PRIVATE00, "Private/Experimental"},

View File

@ -348,7 +348,7 @@ typedef enum {
PGP_PKA_DSA = 17, /* DSA (Digital Signature Algorithm) */
PGP_PKA_RESERVED_ELLIPTIC_CURVE = 18, /* Reserved for Elliptic
* Curve */
PGP_PKA_RESERVED_ECDSA = 19, /* Reserved for ECDSA */
PGP_PKA_ECDSA = 19, /* ECDSA */
PGP_PKA_ELGAMAL_ENCRYPT_OR_SIGN = 20, /* Deprecated. */
PGP_PKA_RESERVED_DH = 21, /* Reserved for Diffie-Hellman
* (X9.42, as defined for
@ -378,6 +378,16 @@ typedef struct {
* with x being the secret) */
} pgp_dsa_pubkey_t;
/** Structure to hold one ECDSA public key params.
*
* \see RFC6637 9
*/
typedef struct {
uint8_t len;
uint8_t oid[8];
BIGNUM *p;
} pgp_ecdsa_pubkey_t;
/** Structure to hold an RSA public key.
*
* \see RFC4880 5.5.2
@ -422,6 +432,7 @@ typedef struct {
pgp_pubkey_alg_t alg; /* Public Key Algorithm type */
union {
pgp_dsa_pubkey_t dsa; /* A DSA public key */
pgp_ecdsa_pubkey_t ecdsa; /* An ECDSA public key */
pgp_rsa_pubkey_t rsa; /* An RSA public key */
pgp_elgamal_pubkey_t elgamal; /* An ElGamal public key */
} key; /* Public Key Parameters */
@ -441,6 +452,11 @@ typedef struct {
BIGNUM *x;
} pgp_dsa_seckey_t;
/** pgp_ecdsa_seckey_t */
typedef struct {
BIGNUM *x;
} pgp_ecdsa_seckey_t;
/** pgp_elgamal_seckey_t */
typedef struct {
BIGNUM *x;
@ -542,6 +558,7 @@ typedef struct pgp_seckey_t {
union {
pgp_rsa_seckey_t rsa;
pgp_dsa_seckey_t dsa;
pgp_ecdsa_seckey_t ecdsa;
pgp_elgamal_seckey_t elgamal;
} key;
unsigned checksum;
@ -599,6 +616,12 @@ typedef struct pgp_dsa_sig_t {
BIGNUM *s; /* DSA value s */
} pgp_dsa_sig_t;
/** Struct to hold params of an ECDSA signature */
typedef struct pgp_ecdsa_sig_t {
BIGNUM *r; /* ECDSA value r */
BIGNUM *s; /* ECDSA value s */
} pgp_ecdsa_sig_t;
/** pgp_elgamal_signature_t */
typedef struct pgp_elgamal_sig_t {
BIGNUM *r;
@ -625,6 +648,7 @@ typedef struct pgp_sig_info_t {
union {
pgp_rsa_sig_t rsa; /* An RSA Signature */
pgp_dsa_sig_t dsa; /* A DSA Signature */
pgp_ecdsa_sig_t ecdsa; /* An ECDSA Signature */
pgp_elgamal_sig_t elgamal; /* deprecated */
pgp_data_t unknown; /* private or experimental */
} sig; /* signature params */

View File

@ -57,7 +57,7 @@
#if defined(__NetBSD__)
__COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
__RCSID("$NetBSD: signature.c,v 1.38 2018/02/05 23:56:01 christos Exp $");
__RCSID("$NetBSD: signature.c,v 1.39 2022/08/26 19:18:38 jhigh Exp $");
#endif
#include <sys/types.h>
@ -265,6 +265,56 @@ dsa_sign(pgp_hash_t *hash,
return 1;
}
static int
ecdsa_sign(pgp_hash_t *hash,
const pgp_ecdsa_pubkey_t *ecdsa,
const pgp_ecdsa_seckey_t *secdsa,
pgp_output_t *output)
{
unsigned hashsize;
unsigned t;
uint8_t hashbuf[NETPGP_BUFSIZ];
ECDSA_SIG *ecdsasig;
const BIGNUM *r, *s;
hashsize = ecdsa_hashsize(ecdsa);
if (hashsize == -1) {
return 0;
}
t = hash->finish(hash, &hashbuf[0]);
if (t != hashsize) {
(void) fprintf(stderr, "ecdsa_sign: hashfinish %d not %d\n", t, hashsize);
return 0;
}
pgp_write(output, &hashbuf[0], 2);
/* write signature to buf */
ecdsasig = pgp_ecdsa_sign(hashbuf, hashsize, secdsa, ecdsa);
if (ecdsasig == NULL) {
(void) fprintf(stderr, "ecdsa_sign: invalid ecdsa sig\n");
return 0;
}
/* convert and write the sig out to memory */
#if OPENSSL_VERSION_NUMBER >= 0x10100000
ECDSA_SIG_get0(ecdsasig, &r, &s);
#else
r = ecdsasig->r;
s = ecdsasig->s;
#endif
pgp_write_mpi(output, r);
pgp_write_mpi(output, s);
ECDSA_SIG_free(ecdsasig);
return 1;
}
static unsigned
rsa_verify(pgp_hash_alg_t type,
const uint8_t *hash,
@ -430,6 +480,12 @@ pgp_check_sig(const uint8_t *hash, unsigned length,
&signer->key.dsa);
break;
case PGP_PKA_ECDSA:
ret = pgp_ecdsa_verify(hash, length,
&sig->info.sig.ecdsa,
&signer->key.ecdsa);
break;
case PGP_PKA_RSA:
ret = rsa_verify(sig->info.hash_alg, hash, length,
&sig->info.sig.rsa,
@ -764,6 +820,14 @@ pgp_write_sig(pgp_output_t *output,
}
break;
case PGP_PKA_ECDSA:
if (seckey->key.ecdsa.x == NULL) {
(void) fprintf(stderr, "pgp_write_sig: null ecdsa.x\n");
return 0;
}
break;
default:
(void) fprintf(stderr, "Unsupported algorithm %d\n",
seckey->pubkey.alg);
@ -817,6 +881,15 @@ pgp_write_sig(pgp_output_t *output,
}
break;
case PGP_PKA_ECDSA:
if (!ecdsa_sign(&sig->hash, &key->key.ecdsa, &seckey->key.ecdsa,
sig->output)) {
(void) fprintf(stderr,
"pgp_write_sig: ecdsa_sign failure\n");
return 0;
}
break;
default:
(void) fprintf(stderr, "Unsupported algorithm %d\n",
seckey->pubkey.alg);
@ -972,7 +1045,14 @@ pgp_sign_file(pgp_io_t *io,
fd_out = 0;
/* find the hash algorithm */
hash_alg = pgp_str_to_hash_alg(hashname);
switch (seckey->pubkey.alg) {
case PGP_PKA_ECDSA:
hash_alg = ecdsa_hashalg(&seckey->pubkey.key.ecdsa);
break;
default:
hash_alg = pgp_str_to_hash_alg(hashname);
}
if (hash_alg == PGP_HASH_UNKNOWN) {
(void) fprintf(io->errs,
"pgp_sign_file: unknown hash algorithm: \"%s\"\n",

View File

@ -58,7 +58,7 @@
#endif
/* development versions have .99 suffix */
#define NETPGP_BASE_VERSION "3.99.17"
#define NETPGP_BASE_VERSION "3.99.18"
#define NETPGP_VERSION_CAT(a, b) "NetPGP portable " a "/[" b "]"
#define NETPGP_VERSION_STRING \