dgst commandline support for one shot signing algorithms

Reviewed-by: Paul Dale <ppzgs1@gmail.com>
Reviewed-by: Tim Hudson <tjh@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/26697)
This commit is contained in:
slontis 2025-02-10 20:00:03 +11:00 committed by Tomas Mraz
parent bd8954bfe5
commit 7cf5300e6b
10 changed files with 621 additions and 76 deletions

View File

@ -24,6 +24,9 @@
#undef BUFSIZE
#define BUFSIZE 1024*8
static int do_fp_oneshot_sign(BIO *out, EVP_MD_CTX *ctx, BIO *in, int sep, int binout,
EVP_PKEY *key, unsigned char *sigin, int siglen,
const char *sig_name, const char *file);
int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen,
EVP_PKEY *key, unsigned char *sigin, int siglen,
const char *sig_name, const char *md_name,
@ -93,7 +96,7 @@ const OPTIONS dgst_options[] = {
int dgst_main(int argc, char **argv)
{
BIO *in = NULL, *inp, *bmd = NULL, *out = NULL;
BIO *in = NULL, *inp = NULL, *bmd = NULL, *out = NULL;
ENGINE *e = NULL, *impl = NULL;
EVP_PKEY *sigkey = NULL;
STACK_OF(OPENSSL_STRING) *sigopts = NULL, *macopts = NULL;
@ -111,6 +114,8 @@ int dgst_main(int argc, char **argv)
unsigned char *buf = NULL, *sigbuf = NULL;
int engine_impl = 0;
struct doall_dgst_digests dec;
EVP_MD_CTX *signctx = NULL;
int oneshot_sign = 0;
buf = app_malloc(BUFSIZE, "I/O buffer");
md = (EVP_MD *)EVP_get_digestbyname(argv[0]);
@ -278,8 +283,6 @@ int dgst_main(int argc, char **argv)
}
if (keyfile != NULL) {
int type;
if (want_pub)
sigkey = load_pubkey(keyfile, keyform, 0, NULL, e, "public key");
else
@ -290,14 +293,16 @@ int dgst_main(int argc, char **argv)
*/
goto end;
}
type = EVP_PKEY_get_id(sigkey);
if (type == EVP_PKEY_ED25519 || type == EVP_PKEY_ED448) {
/*
* We implement PureEdDSA for these which doesn't have a separate
* digest, and only supports one shot.
*/
BIO_printf(bio_err, "Key type not supported for this operation\n");
goto end;
{
char def_md[80];
if (EVP_PKEY_get_default_digest_name(sigkey, def_md,
sizeof(def_md)) == 2
&& strcmp(def_md, "UNDEF") == 0)
oneshot_sign = 1;
signctx = EVP_MD_CTX_new();
if (signctx == NULL)
goto end;
}
}
@ -342,7 +347,9 @@ int dgst_main(int argc, char **argv)
EVP_PKEY_CTX *pctx = NULL;
int res;
if (BIO_get_md_ctx(bmd, &mctx) <= 0) {
if (oneshot_sign) {
mctx = signctx;
} else if (BIO_get_md_ctx(bmd, &mctx) <= 0) {
BIO_printf(bio_err, "Error getting context\n");
goto end;
}
@ -379,6 +386,11 @@ int dgst_main(int argc, char **argv)
/* we use md as a filter, reading from 'in' */
else {
EVP_MD_CTX *mctx = NULL;
if (oneshot_sign) {
BIO_printf(bio_err, "Oneshot algorithms don't use a digest\n");
goto end;
}
if (BIO_get_md_ctx(bmd, &mctx) <= 0) {
BIO_printf(bio_err, "Error getting context\n");
goto end;
@ -407,17 +419,18 @@ int dgst_main(int argc, char **argv)
goto end;
}
}
inp = BIO_push(bmd, in);
if (!oneshot_sign) {
inp = BIO_push(bmd, in);
if (md == NULL) {
EVP_MD_CTX *tctx;
if (md == NULL) {
EVP_MD_CTX *tctx;
BIO_get_md_ctx(bmd, &tctx);
md = EVP_MD_CTX_get1_md(tctx);
BIO_get_md_ctx(bmd, &tctx);
md = EVP_MD_CTX_get1_md(tctx);
}
if (md != NULL)
md_name = EVP_MD_get0_name(md);
}
if (md != NULL)
md_name = EVP_MD_get0_name(md);
if (xoflen > 0) {
if (!EVP_MD_xof(md)) {
BIO_printf(bio_err, "Length can only be specified for XOF\n");
@ -436,8 +449,12 @@ int dgst_main(int argc, char **argv)
if (argc == 0) {
BIO_set_fp(in, stdin, BIO_NOCLOSE);
ret = do_fp(out, buf, inp, separator, out_bin, xoflen, sigkey, sigbuf,
siglen, NULL, md_name, "stdin");
if (oneshot_sign)
ret = do_fp_oneshot_sign(out, signctx, in, separator, out_bin,
sigkey, sigbuf, siglen, NULL, "stdin");
else
ret = do_fp(out, buf, inp, separator, out_bin, xoflen,
sigkey, sigbuf, siglen, NULL, md_name, "stdin");
} else {
const char *sig_name = NULL;
@ -452,9 +469,16 @@ int dgst_main(int argc, char **argv)
ret = EXIT_FAILURE;
continue;
} else {
if (do_fp(out, buf, inp, separator, out_bin, xoflen,
sigkey, sigbuf, siglen, sig_name, md_name, argv[i]))
ret = EXIT_FAILURE;
if (oneshot_sign) {
if (do_fp_oneshot_sign(out, signctx, in, separator, out_bin,
sigkey, sigbuf, siglen, sig_name,
argv[i]))
ret = EXIT_FAILURE;
} else {
if (do_fp(out, buf, inp, separator, out_bin, xoflen,
sigkey, sigbuf, siglen, sig_name, md_name, argv[i]))
ret = EXIT_FAILURE;
}
}
(void)BIO_reset(bmd);
}
@ -468,6 +492,7 @@ int dgst_main(int argc, char **argv)
BIO_free_all(out);
EVP_MD_free(md);
EVP_PKEY_free(sigkey);
EVP_MD_CTX_free(signctx);
sk_OPENSSL_STRING_free(sigopts);
sk_OPENSSL_STRING_free(macopts);
OPENSSL_free(sigbuf);
@ -544,6 +569,54 @@ static const char *newline_escape_filename(const char *file, int *backslash)
return (const char*)file_cpy;
}
static void print_out(BIO *out, unsigned char *buf, size_t len,
int sep, int binout,
const char *sig_name, const char *md_name, const char *file)
{
int i, backslash = 0;
if (binout) {
BIO_write(out, buf, len);
} else if (sep == 2) {
file = newline_escape_filename(file, &backslash);
if (backslash == 1)
BIO_puts(out, "\\");
for (i = 0; i < (int)len; i++)
BIO_printf(out, "%02x", buf[i]);
BIO_printf(out, " *%s\n", file);
OPENSSL_free((char *)file);
} else {
if (sig_name != NULL) {
BIO_puts(out, sig_name);
if (md_name != NULL)
BIO_printf(out, "-%s", md_name);
BIO_printf(out, "(%s)= ", file);
} else if (md_name != NULL) {
BIO_printf(out, "%s(%s)= ", md_name, file);
} else {
BIO_printf(out, "(%s)= ", file);
}
for (i = 0; i < (int)len; i++) {
if (sep && (i != 0))
BIO_printf(out, ":");
BIO_printf(out, "%02x", buf[i]);
}
BIO_printf(out, "\n");
}
}
static void print_verify_result(BIO *out, int i)
{
if (i > 0)
BIO_printf(out, "Verified OK\n");
else if (i == 0)
BIO_printf(out, "Verification failure\n");
else
BIO_printf(bio_err, "Error verifying data\n");
}
int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen,
EVP_PKEY *key, unsigned char *sigin, int siglen,
@ -551,7 +624,7 @@ int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen
const char *file)
{
size_t len = BUFSIZE;
int i, backslash = 0, ret = EXIT_FAILURE;
int i, ret = EXIT_FAILURE;
unsigned char *allocated_buf = NULL;
while (BIO_pending(bp) || !BIO_eof(bp)) {
@ -567,16 +640,9 @@ int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen
EVP_MD_CTX *ctx;
BIO_get_md_ctx(bp, &ctx);
i = EVP_DigestVerifyFinal(ctx, sigin, (unsigned int)siglen);
if (i > 0) {
BIO_printf(out, "Verified OK\n");
} else if (i == 0) {
BIO_printf(out, "Verification failure\n");
goto end;
} else {
BIO_printf(bio_err, "Error verifying data\n");
goto end;
}
ret = EXIT_SUCCESS;
print_verify_result(out, i);
if (i > 0)
ret = EXIT_SUCCESS;
goto end;
}
if (key != NULL) {
@ -617,39 +683,7 @@ int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen
if ((int)len < 0)
goto end;
}
if (binout) {
BIO_write(out, buf, len);
} else if (sep == 2) {
file = newline_escape_filename(file, &backslash);
if (backslash == 1)
BIO_puts(out, "\\");
for (i = 0; i < (int)len; i++)
BIO_printf(out, "%02x", buf[i]);
BIO_printf(out, " *%s\n", file);
OPENSSL_free((char *)file);
} else {
if (sig_name != NULL) {
BIO_puts(out, sig_name);
if (md_name != NULL)
BIO_printf(out, "-%s", md_name);
BIO_printf(out, "(%s)= ", file);
} else if (md_name != NULL) {
BIO_printf(out, "%s(%s)= ", md_name, file);
} else {
BIO_printf(out, "(%s)= ", file);
}
for (i = 0; i < (int)len; i++) {
if (sep && (i != 0))
BIO_printf(out, ":");
BIO_printf(out, "%02x", buf[i]);
}
BIO_printf(out, "\n");
}
print_out(out, buf, len, sep, binout, sig_name, md_name, file);
ret = EXIT_SUCCESS;
end:
if (allocated_buf != NULL)
@ -657,3 +691,55 @@ int do_fp(BIO *out, unsigned char *buf, BIO *bp, int sep, int binout, int xoflen
return ret;
}
/*
* Some new algorithms only support one shot operations.
* For these we need to buffer all input and then do the sign on the
* total buffered input. These algorithms set a NULL digest name which is
* then used inside EVP_DigestVerify() and EVP_DigestSign().
*/
static int do_fp_oneshot_sign(BIO *out, EVP_MD_CTX *ctx, BIO *in, int sep, int binout,
EVP_PKEY *key, unsigned char *sigin, int siglen,
const char *sig_name, const char *file)
{
int res, ret = EXIT_FAILURE;
size_t len = 0;
int buflen = 0;
int maxlen = 16 * 1024 * 1024;
uint8_t *buf = NULL, *sig = NULL;
buflen = bio_to_mem(&buf, maxlen, in);
if (buflen <= 0) {
BIO_printf(bio_err, "Read error in %s\n", file);
goto end;
}
if (sigin != NULL) {
res = EVP_DigestVerify(ctx, sigin, siglen, buf, buflen);
print_verify_result(out, res);
if (res > 0)
ret = EXIT_SUCCESS;
goto end;
}
if (key != NULL) {
if (EVP_DigestSign(ctx, NULL, &len, buf, buflen) != 1) {
BIO_printf(bio_err, "Error getting maximum length of signed data\n");
goto end;
}
sig = app_malloc(len, "Signature buffer");
if (EVP_DigestSign(ctx, sig, &len, buf, buflen) != 1) {
BIO_printf(bio_err, "Error signing data\n");
goto end;
}
print_out(out, sig, len, sep, binout, sig_name, NULL, file);
ret = EXIT_SUCCESS;
} else {
BIO_printf(bio_err, "key must be set for one-shot algorithms\n");
goto end;
}
end:
OPENSSL_free(sig);
OPENSSL_clear_free(buf, buflen);
return ret;
}

View File

@ -116,9 +116,13 @@ Filename to output to, or standard output by default.
=item B<-sign> I<filename>|I<uri>
Digitally sign the digest using the given private key. Note this option
does not support Ed25519 or Ed448 private keys. Use the L<openssl-pkeyutl(1)>
command instead for this.
Digitally sign the digest using the given private key.
Note that for algorithms that only support one-shot signing
(such as Ed25519, ED448, ML-DSA-44, ML-DSA-65 andML-DSA-87) the digest must not
be set. For these algorithms the input is buffered (and not digested) before
signing. For these algorithms, if the input is larger than 16MB an error
will occur.
=item B<-keyform> B<DER>|B<PEM>|B<P12>|B<ENGINE>

View File

@ -17,7 +17,7 @@ use OpenSSL::Test::Utils;
setup("test_dgst");
plan tests => 14;
plan tests => 17;
sub tsignverify {
my $testtext = shift;
@ -131,8 +131,6 @@ SKIP: {
skip "EdDSA is not supported by this OpenSSL build", 2
if disabled("ecx");
skip "EdDSA is not supported with `dgst` CLI", 2;
subtest "Ed25519 signature generation and verification with `dgst` CLI" => sub {
tsignverify("Ed25519",
srctop_file("test","tested25519.pem"),
@ -146,6 +144,27 @@ SKIP: {
};
}
SKIP: {
skip "ML-DSA is not supported by this OpenSSL build", 3
if disabled("ml-dsa");
subtest "ML-DSA-44 signature generation and verification with `dgst` CLI" => sub {
tsignverify("Ml-DSA-44",
srctop_file("test","testmldsa44.pem"),
srctop_file("test","testmldsa44pub.pem"));
};
subtest "ML-DSA-65 signature generation and verification with `dgst` CLI" => sub {
tsignverify("Ml-DSA-65",
srctop_file("test","testmldsa65.pem"),
srctop_file("test","testmldsa65pub.pem"));
};
subtest "ML-DSA-87 signature generation and verification with `dgst` CLI" => sub {
tsignverify("Ml-DSA-87",
srctop_file("test","testmldsa87.pem"),
srctop_file("test","testmldsa87pub.pem"));
};
}
SKIP: {
skip "dgst with engine is not supported by this OpenSSL build", 1
if disabled("engine") || disabled("dynamic-engine");

View File

@ -24,7 +24,61 @@ use lib srctop_dir('Configurations');
use lib bldtop_dir('.');
plan skip_all => 'ML-DSA is not supported in this build' if disabled('ml-dsa');
plan tests => 2;
plan tests => 12;
require_ok(srctop_file('test','recipes','tconversion.pl'));
subtest "ml-dsa-44 conversions using 'openssl pkey' -- private key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa44.pem"),
-prefix => "mldsa44-pkey-priv" );
};
subtest "ml-dsa-44 conversions using 'openssl pkey' -- pkcs8 key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa44.pem"),
-args => ["pkey"],
-prefix => "mldsa44-pkey-pkcs8" );
};
subtest "ml-dsa-44 conversions using 'openssl pkey' -- pub key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa44pub.pem"),
-args => ["pkey", "-pubin", "-pubout"],
-prefix => "mldsa44-pkey-pub" );
};
subtest "ml-dsa-65 conversions using 'openssl pkey' -- private key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa65.pem"),
-prefix => "mldsa65-pkey-priv");
};
subtest "ml-dsa-65 conversions using 'openssl pkey' -- pkcs8 key" => sub {
tconversion( -type => "pkey", -in => srctop_file("test","testmldsa65.pem"),
-args => ["pkey"], -prefix => "mldsa65-pkey-pkcs8");
};
subtest "ml-dsa-65 conversions using 'openssl pkey' -- pub key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa65pub.pem"),
-args => ["pkey", "-pubin", "-pubout"],
-prefix => "mldsa65-pkey-pub" );
};
subtest "ml-dsa-87 conversions using 'openssl pkey' -- private key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa87.pem"),
-prefix => "mldsa87-pkey-priv" );
};
subtest "ml-dsa-87 conversions using 'openssl pkey' -- pkcs8 key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa87.pem"),
-args => ["pkey"],
-prefix => "mldsa87-pkey-pkcs8" );
};
subtest "ml-dsa-87 conversions using 'openssl pkey' -- pub key" => sub {
tconversion( -type => "pkey",
-in => srctop_file("test","testmldsa87pub.pem"),
-args => ["pkey", "-pubin", "-pubout"],
-prefix => "mldsa87-pkey-pub" );
};
ok(run(test(["ml_dsa_test"])), "running ml_dsa_test");

57
test/testmldsa44.pem Normal file
View File

@ -0,0 +1,57 @@
-----BEGIN PRIVATE KEY-----
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
-----END PRIVATE KEY-----

30
test/testmldsa44pub.pem Normal file
View File

@ -0,0 +1,30 @@
-----BEGIN PUBLIC KEY-----
MIIFMjALBglghkgBZQMEAxEDggUhALpx+fZOEbrrWPqcb7tuFOYfGGQ9q0lbR1Oa
kWbKAZgTHET4JrvVbjTlXbXl4tczSF456iYPxgAMXqS6gNNFXN5TtG80SCrt/VRQ
/C4bpPJdFfnBRCQvs5u1IocYkDDFBJjhcXt8dYsZCmdI6pqj96yq8sfLUm7XF8n3
muuEIU+lzY3tkqDD+hVYgQ8SxwUKNncI0ZbNJOWvl0kErtjkzohy6GlrC3vKUORS
zX0w6ppK2sAxHWcsa96EliQLB0MUY3CIlc2br8MWMtc5dkk4j9r8v30wWj3ppJXs
p0M6j4O6DwslxBPG45yW631pGzTTfON/HurRzyF+Je807s8/fGD4S47f3ehAXU+D
JXbGHvmOCi8o2hh3AJU5JPaGuUYUcFvPU9M/7dQ0jt3b3yi1Bl4fIHdQQ+hc+TH4
KReTY6Gn50BKg47AAIawl2OG/mN8mCRHV+P3ad3URnRxv61nD5oF+CRu5Qp7Hq+H
/EBpw64qogMyWBF3kvC81J4IP9G8dJar/ynMlOSGiyEhTtMWUlOZphD73UqA58gH
FfKVeOKoS7QL3dvZ9HoRtufaEYobZY01norvVetGtTdrW2VZeZhKkivuv8WbzWAN
UwnczXLb8Hh9uLp1e1N8Hq/VwPUOpLyVg1SeKCmkLCjKwkjJbXgSTEcVmxiu3XVK
uhexnUMPt49jPqnSb1SpvVD42Pa3NZT4KJdufqCcU7u58RpWyVB/uJuaXrwDejcm
epX4W41kypcZKxCmb0F7P2H+nKVxMKSP2SXq4qtVAtVxyKUZA8HTmPTB92p+EXQ5
dq/bxpfyMJSjzXYf+Whd4y4J+zwordRTSQMAvHyJ3AF4AJYHFyKUV3XyZOGwYjvP
RhnHEsg4dhIF2HaRt17zYBlsu56bkqDUxO1iMm5QJNd1ELjuLHQmzCLq4gncnxO9
5r8I9ecYG9O0WUULRRpRU5pxXCHWfdMw61lw2wDZ7b+ygisDb6E7r+uG2Nx4hm4/
jUPlPXjMpVlab6+Ia13BEvHPStz6h1gA2QtIiDr5cxb+FQaHP8FX5XDqy/0iKGjR
QjQQGWavtr+ZQIKSU6lTraifx1a2qEn3CsuYOOafqlC7p14+icKttX6G0IirmwSi
jmcHCRciQ+xeAAilzq8/hyL0hzAllv/XVa0bgqScNLNGlRW0aqKQzYbuOOp6m+Px
A2EDNbUxzKMz3f4ysUUQ9LB++V/GaE6MRUqSwQ27XVnHp8Y/swX+iBln2Z5mnrYy
hAWCVgu0A0MdQPdaSVSQhIIngpKCH06pHkLnj6SMruPINhRtz9c40RfpLpoVE30o
6OaktGImUMtBNQTLOjNdRL7sV0bBwpSx6MuZy2CNko+M41Y2MsUh8j0TxhqPYcAd
+Mlsc2DbTzxoql0v3TQqYv80WcEWOJQhq0PoWExFiCtQ5uTpbbbwuP3okNXb+tzY
hpC0SeZCQN2yAjdH8wg2PjAap3dXFp/GFQYo1ZILWqGrHIy/RMsA4CXXh51ytHnj
r1MRx4VyVZDanIm5/DuEUHaVVOtE0gProruu+crSI3ARwupE7/APKZpI/+KMqT3f
hfdmCCQu+NbMJGEKHiB4/KxPk4XDFJBeyqguVTkW2U0afB7GUqoIiXCD2qLrsXdf
vEca4nd315BOqfG5K8rD2KMVhCYIe2RbEQjw1l/sk3icBTdDyhT9Y9BemLZS3yuc
L/nOBfGUBwP/snP4Dg4nMuyplg2YG0z9O3u4BFs8ODBUa53Y2w0=
-----END PUBLIC KEY-----

88
test/testmldsa65.pem Normal file
View File

@ -0,0 +1,88 @@
-----BEGIN PRIVATE KEY-----
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
KyQlPne7UzntzuTeClPzfpyg
-----END PRIVATE KEY-----

44
test/testmldsa65pub.pem Normal file
View File

@ -0,0 +1,44 @@
-----BEGIN PUBLIC KEY-----
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
b7MltSbq
-----END PUBLIC KEY-----

106
test/testmldsa87.pem Normal file
View File

@ -0,0 +1,106 @@
-----BEGIN PRIVATE KEY-----
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
wjUH4o18r/cGsoZyv2Rf878L
-----END PRIVATE KEY-----

57
test/testmldsa87pub.pem Normal file
View File

@ -0,0 +1,57 @@
-----BEGIN PUBLIC KEY-----
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
Pam8XbG1Ud+5Hps0PStXt2NDlobUow==
-----END PUBLIC KEY-----