Skip to content

Commit c68017c

Browse files
committed
Hash: lc_hash_set_digestsize returns error state
The function now checks whether the setting of the digest was successful. This is of particular importance when having a hash where this API is defined, but the setting will never change the digest size. This is now checked and if identified the call returns an error. This prevents accidental use of a hash in lieu of an XOF. Yet, it allows using a hash when the set digest size is identical to the requested size. Such scenario is used in ML-DSA where either a SHA3-512, SHA2-512 or SHAKE-256 is allowed to be used where the digest size is always 512 bits. Signed-off-by: Stephan Mueller <smueller@chronox.de>
1 parent 4ea67cf commit c68017c

29 files changed

+176
-111
lines changed

apps/tests/leancrypto_check_with_ietf.sh

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,7 @@ doc_init() {
117117

118118
doc_one() {
119119
local oid=$1
120-
local type=$2 #both, expandedkey, seed, priv
120+
local type=$2 #cert, both, expandedkey, seed, priv
121121
local res=$3 #Y, N
122122

123123
touch $statusfile
@@ -171,7 +171,7 @@ check_one() {
171171
local certfile=$1
172172
local certcheck_only=$2
173173
local oid=$3
174-
local type="priv"
174+
local type="cert"
175175

176176
if [ ! -f "$certfile" ]
177177
then

apps/tests/meson.build

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -316,7 +316,7 @@ if (host_machine.system() != 'windows' and
316316
lc_pkcs7_generator.full_path(),
317317
meson.project_source_root() + '/apps/tests/'
318318
],
319-
timeout: 300, suite: regression,
319+
timeout: 1000, suite: regression,
320320
should_fail: fips140_negative_expect_fail)
321321

322322
endif

curve448/src/ed448.c

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -324,12 +324,17 @@ LC_INTERFACE_FUNCTION(int, lc_ed448_keypair, struct lc_ed448_pk *pk,
324324
return lc_ed448_keypair_nocheck(pk, sk, rng_ctx);
325325
}
326326

327-
static inline void lc_ed448_xof_final(struct lc_hash_ctx *xof_ctx,
328-
uint8_t *digest, size_t digest_len)
327+
static inline int lc_ed448_xof_final(struct lc_hash_ctx *xof_ctx,
328+
uint8_t *digest, size_t digest_len)
329329
{
330-
lc_hash_set_digestsize(xof_ctx, digest_len);
330+
int ret;
331+
332+
CKINT(lc_hash_set_digestsize(xof_ctx, digest_len));
331333
lc_hash_final(xof_ctx, digest);
332334
lc_hash_zero(xof_ctx);
335+
336+
out:
337+
return ret;
333338
}
334339

335340
static int curveed448_hash_init_with_dom(struct lc_hash_ctx *hash_ctx,
@@ -420,7 +425,7 @@ curveed448_sign_internal(uint8_t signature[LC_ED448_SIGBYTES],
420425
{
421426
uint8_t nonce[2 * LC_ED448_SECRETKEYBYTES];
422427

423-
lc_ed448_xof_final(shake256_ctx, nonce, sizeof(nonce));
428+
CKINT(lc_ed448_xof_final(shake256_ctx, nonce, sizeof(nonce)));
424429
curve448_scalar_decode_long(nonce_scalar, nonce, sizeof(nonce));
425430
lc_memset_secure(nonce, 0, sizeof(nonce));
426431
}
@@ -462,7 +467,8 @@ curveed448_sign_internal(uint8_t signature[LC_ED448_SIGBYTES],
462467
lc_hash_update(shake256_ctx, message, message_len);
463468

464469
uint8_t challenge[2 * LC_ED448_SECRETKEYBYTES];
465-
lc_ed448_xof_final(shake256_ctx, challenge, sizeof(challenge));
470+
CKINT(lc_ed448_xof_final(shake256_ctx, challenge,
471+
sizeof(challenge)));
466472
curve448_scalar_decode_long(challenge_scalar, challenge,
467473
sizeof(challenge));
468474
lc_memset_secure(challenge, 0, sizeof(challenge));
@@ -701,7 +707,7 @@ curveed448_verify(const uint8_t signature[LC_ED448_SIGBYTES],
701707

702708
lc_hash_update(shake256_ctx, message, message_len);
703709

704-
lc_ed448_xof_final(shake256_ctx, challenge, sizeof(challenge));
710+
CKINT(lc_ed448_xof_final(shake256_ctx, challenge, sizeof(challenge)));
705711
curve448_scalar_decode_long(challenge_scalar, challenge,
706712
sizeof(challenge));
707713

drng/src/selftest_rng.c

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
*/
1919

2020
#include "ext_headers_internal.h"
21+
#include "ret_checkers.h"
2122
#include "selftest_rng.h"
2223

2324
/*
@@ -29,14 +30,16 @@ static int selftest_rng_gen(void *_state, const uint8_t *addtl_input,
2930
size_t addtl_input_len, uint8_t *out, size_t outlen)
3031
{
3132
struct lc_hash_ctx *state = _state;
33+
int ret;
3234

3335
(void)addtl_input;
3436
(void)addtl_input_len;
3537

36-
lc_hash_set_digestsize(state, outlen);
38+
CKINT(lc_hash_set_digestsize(state, outlen));
3739
lc_hash_final(state, out);
3840

39-
return 0;
41+
out:
42+
return ret;
4043
}
4144

4245
static int selftest_rng_seed(void *_state, const uint8_t *seed, size_t seedlen,

drng/src/selftest_shake256_rng.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,14 +30,16 @@ static int selftest_rng_gen(void *_state, const uint8_t *addtl_input,
3030
size_t addtl_input_len, uint8_t *out, size_t outlen)
3131
{
3232
struct lc_hash_ctx *state = _state;
33+
int ret;
3334

3435
(void)addtl_input;
3536
(void)addtl_input_len;
3637

37-
lc_hash_set_digestsize(state, outlen);
38+
CKINT(lc_hash_set_digestsize(state, outlen));
3839
lc_hash_final(state, out);
3940

40-
return 0;
41+
out:
42+
return ret;
4143
}
4244

4345
static int selftest_rng_seed(void *_state, const uint8_t *seed, size_t seedlen,

drng/src/xdrbg.c

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -55,11 +55,17 @@ static inline uint8_t lc_xdrbg_keysize(struct lc_xdrbg_drng_state *state)
5555
}
5656
}
5757

58-
static inline void lc_xdrbg_xof_final(struct lc_hash_ctx *xof_ctx,
59-
uint8_t *digest, size_t digest_len)
58+
static inline int lc_xdrbg_xof_final(struct lc_hash_ctx *xof_ctx,
59+
uint8_t *digest, size_t digest_len)
6060
{
61-
lc_hash_set_digestsize(xof_ctx, digest_len);
61+
int ret = lc_hash_set_digestsize(xof_ctx, digest_len);
62+
63+
if (ret)
64+
return ret;
65+
6266
lc_hash_final(xof_ctx, digest);
67+
68+
return 0;
6369
}
6470

6571
/* Maximum size of the input data to calculate the encode value */

drng/tests/xdrbg128_tester.c

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,8 @@ static int xdrbg128_drng_selftest(struct lc_rng_ctx *xdrbg128_ctx)
8989
lc_hash_update(xdrbg128_compare, seed, sizeof(seed));
9090
encode = 0;
9191
lc_hash_update(xdrbg128_compare, &encode, sizeof(encode));
92-
lc_hash_set_digestsize(xdrbg128_compare, LC_XDRBG128_DRNG_KEYSIZE);
92+
CKINT(lc_hash_set_digestsize(xdrbg128_compare,
93+
LC_XDRBG128_DRNG_KEYSIZE));
9394
lc_hash_final(xdrbg128_compare, compare1);
9495
unpoison(state->v, LC_XDRBG128_DRNG_KEYSIZE);
9596
ret += lc_compare(compare1, state->v, LC_XDRBG128_DRNG_KEYSIZE,
@@ -102,7 +103,7 @@ static int xdrbg128_drng_selftest(struct lc_rng_ctx *xdrbg128_ctx)
102103
lc_hash_update(xdrbg128_compare, compare1, LC_XDRBG128_DRNG_KEYSIZE);
103104
encode = 2 * 85;
104105
lc_hash_update(xdrbg128_compare, &encode, sizeof(encode));
105-
lc_hash_set_digestsize(xdrbg128_compare, sizeof(compare1));
106+
CKINT(lc_hash_set_digestsize(xdrbg128_compare, sizeof(compare1)));
106107
lc_hash_final(xdrbg128_compare, compare1);
107108
ret += lc_compare(compare1 + LC_XDRBG128_DRNG_KEYSIZE, exp1,
108109
sizeof(exp1), "Ascon DRNG verification");
@@ -152,7 +153,8 @@ static int xdrbg128_drng_selftest(struct lc_rng_ctx *xdrbg128_ctx)
152153
lc_hash_update(xdrbg128_compare, &encode, sizeof(encode));
153154

154155
/* Verify: Now get the key for the next operation */
155-
lc_hash_set_digestsize(xdrbg128_compare, LC_XDRBG128_DRNG_KEYSIZE);
156+
CKINT(lc_hash_set_digestsize(xdrbg128_compare,
157+
LC_XDRBG128_DRNG_KEYSIZE));
156158
lc_hash_final(xdrbg128_compare, compare1);
157159

158160
if (lc_hash_init(xdrbg128_compare))
@@ -167,8 +169,8 @@ static int xdrbg128_drng_selftest(struct lc_rng_ctx *xdrbg128_ctx)
167169
lc_hash_update(xdrbg128_compare, &encode, sizeof(encode));
168170

169171
/* Verify: Generate operation of the DRBG: generate data */
170-
lc_hash_set_digestsize(xdrbg128_compare,
171-
LC_XDRBG128_DRNG_KEYSIZE + sizeof(act2));
172+
CKINT(lc_hash_set_digestsize(xdrbg128_compare,
173+
LC_XDRBG128_DRNG_KEYSIZE + sizeof(act2)));
172174
lc_hash_final(xdrbg128_compare, compare1);
173175
ret += lc_compare(compare1 + LC_XDRBG128_DRNG_KEYSIZE, exp84,
174176
sizeof(exp84),
@@ -178,6 +180,7 @@ static int xdrbg128_drng_selftest(struct lc_rng_ctx *xdrbg128_ctx)
178180

179181
lc_hash_zero(xdrbg128_compare);
180182

183+
out:
181184
return ret;
182185
}
183186

drng/tests/xdrbg256_tester.c

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,8 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
9999
lc_hash_update(xdrbg256_compare, seed, sizeof(seed));
100100
encode = 0;
101101
lc_hash_update(xdrbg256_compare, &encode, sizeof(encode));
102-
lc_hash_set_digestsize(xdrbg256_compare, LC_XDRBG256_DRNG_KEYSIZE);
102+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
103+
LC_XDRBG256_DRNG_KEYSIZE));
103104
lc_hash_final(xdrbg256_compare, compare1);
104105
unpoison(state->v, LC_XDRBG256_DRNG_KEYSIZE);
105106
ret += lc_compare(compare1, state->v, LC_XDRBG256_DRNG_KEYSIZE,
@@ -115,10 +116,12 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
115116
encode = 2 * 85;
116117
lc_hash_update(xdrbg256_compare, &encode, sizeof(encode));
117118
/* First loop iteration: generate key */
118-
lc_hash_set_digestsize(xdrbg256_compare, LC_XDRBG256_DRNG_KEYSIZE);
119+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
120+
LC_XDRBG256_DRNG_KEYSIZE));
119121
lc_hash_final(xdrbg256_compare, compare1);
120122
/* First loop iteratipn: generate data */
121-
lc_hash_set_digestsize(xdrbg256_compare, LC_XDRBG256_DRNG_MAX_CHUNK);
123+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
124+
LC_XDRBG256_DRNG_MAX_CHUNK));
122125
lc_hash_final(xdrbg256_compare, compare1 + LC_XDRBG256_DRNG_KEYSIZE);
123126

124127
/* 2nd loop round as output size is larger than chunk size */
@@ -128,12 +131,13 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
128131
encode = 2 * 85;
129132
lc_hash_update(xdrbg256_compare, &encode, sizeof(encode));
130133
/* Second loop iteratipn: generate key */
131-
lc_hash_set_digestsize(xdrbg256_compare, LC_XDRBG256_DRNG_KEYSIZE);
134+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
135+
LC_XDRBG256_DRNG_KEYSIZE));
132136
lc_hash_final(xdrbg256_compare, compare1);
133137
/* Second loop iteratipn: generate data */
134-
lc_hash_set_digestsize(xdrbg256_compare,
135-
sizeof(compare1) - LC_XDRBG256_DRNG_MAX_CHUNK -
136-
LC_XDRBG256_DRNG_KEYSIZE);
138+
CKINT(lc_hash_set_digestsize(
139+
xdrbg256_compare, sizeof(compare1) - LC_XDRBG256_DRNG_MAX_CHUNK -
140+
LC_XDRBG256_DRNG_KEYSIZE));
137141
lc_hash_final(xdrbg256_compare, compare1 + LC_XDRBG256_DRNG_MAX_CHUNK +
138142
LC_XDRBG256_DRNG_KEYSIZE);
139143

@@ -185,7 +189,8 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
185189
lc_hash_update(xdrbg256_compare, &encode, sizeof(encode));
186190

187191
/* Verify: Now get the key for the next operation */
188-
lc_hash_set_digestsize(xdrbg256_compare, LC_XDRBG256_DRNG_KEYSIZE);
192+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
193+
LC_XDRBG256_DRNG_KEYSIZE));
189194
lc_hash_final(xdrbg256_compare, compare1);
190195

191196
if (lc_hash_init(xdrbg256_compare))
@@ -200,8 +205,8 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
200205
lc_hash_update(xdrbg256_compare, &encode, sizeof(encode));
201206

202207
/* Verify: Generate operation of the DRBG: generate data */
203-
lc_hash_set_digestsize(xdrbg256_compare,
204-
LC_XDRBG256_DRNG_KEYSIZE + sizeof(act2));
208+
CKINT(lc_hash_set_digestsize(xdrbg256_compare,
209+
LC_XDRBG256_DRNG_KEYSIZE + sizeof(act2)));
205210
lc_hash_final(xdrbg256_compare, compare1);
206211
ret += lc_compare(compare1 + LC_XDRBG256_DRNG_KEYSIZE, exp84,
207212
sizeof(exp84),
@@ -211,6 +216,7 @@ static int xdrbg256_drng_selftest(struct lc_rng_ctx *xdrbg256_ctx)
211216

212217
lc_hash_zero(xdrbg256_compare);
213218

219+
out:
214220
return ret;
215221
}
216222

drng/tests/xdrbg512_tester.c

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,8 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
101101
lc_hash_update(xdrbg512_compare, seed, sizeof(seed));
102102
encode = 0;
103103
lc_hash_update(xdrbg512_compare, &encode, sizeof(encode));
104-
lc_hash_set_digestsize(xdrbg512_compare, LC_XDRBG512_DRNG_KEYSIZE);
104+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
105+
LC_XDRBG512_DRNG_KEYSIZE));
105106
lc_hash_final(xdrbg512_compare, compare1);
106107
unpoison(state->v, LC_XDRBG512_DRNG_KEYSIZE);
107108
ret += lc_compare(compare1, state->v, LC_XDRBG512_DRNG_KEYSIZE,
@@ -117,10 +118,12 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
117118
encode = 2 * 85;
118119
lc_hash_update(xdrbg512_compare, &encode, sizeof(encode));
119120
/* First loop iteration: generate key */
120-
lc_hash_set_digestsize(xdrbg512_compare, LC_XDRBG512_DRNG_KEYSIZE);
121+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
122+
LC_XDRBG512_DRNG_KEYSIZE));
121123
lc_hash_final(xdrbg512_compare, compare1);
122124
/* First loop iteratipn: generate data */
123-
lc_hash_set_digestsize(xdrbg512_compare, LC_XDRBG512_DRNG_MAX_CHUNK);
125+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
126+
LC_XDRBG512_DRNG_MAX_CHUNK));
124127
lc_hash_final(xdrbg512_compare, compare1 + LC_XDRBG512_DRNG_KEYSIZE);
125128

126129
/* 2nd loop round as output size is larger than chunk size */
@@ -130,12 +133,13 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
130133
encode = 2 * 85;
131134
lc_hash_update(xdrbg512_compare, &encode, sizeof(encode));
132135
/* Second loop iteratipn: generate key */
133-
lc_hash_set_digestsize(xdrbg512_compare, LC_XDRBG512_DRNG_KEYSIZE);
136+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
137+
LC_XDRBG512_DRNG_KEYSIZE));
134138
lc_hash_final(xdrbg512_compare, compare1);
135139
/* Second loop iteratipn: generate data */
136-
lc_hash_set_digestsize(xdrbg512_compare,
137-
sizeof(compare1) - LC_XDRBG512_DRNG_MAX_CHUNK -
138-
LC_XDRBG512_DRNG_KEYSIZE);
140+
CKINT(lc_hash_set_digestsize(
141+
xdrbg512_compare, sizeof(compare1) - LC_XDRBG512_DRNG_MAX_CHUNK -
142+
LC_XDRBG512_DRNG_KEYSIZE));
139143
lc_hash_final(xdrbg512_compare, compare1 + LC_XDRBG512_DRNG_MAX_CHUNK +
140144
LC_XDRBG512_DRNG_KEYSIZE);
141145

@@ -190,7 +194,8 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
190194
lc_hash_update(xdrbg512_compare, &encode, sizeof(encode));
191195

192196
/* Verify: Now get the key for the next operation */
193-
lc_hash_set_digestsize(xdrbg512_compare, LC_XDRBG512_DRNG_KEYSIZE);
197+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
198+
LC_XDRBG512_DRNG_KEYSIZE));
194199
lc_hash_final(xdrbg512_compare, compare1);
195200

196201
if (lc_hash_init(xdrbg512_compare))
@@ -205,8 +210,8 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
205210
lc_hash_update(xdrbg512_compare, &encode, sizeof(encode));
206211

207212
/* Verify: Generate operation of the DRBG: generate data */
208-
lc_hash_set_digestsize(xdrbg512_compare,
209-
LC_XDRBG512_DRNG_KEYSIZE + sizeof(act2));
213+
CKINT(lc_hash_set_digestsize(xdrbg512_compare,
214+
LC_XDRBG512_DRNG_KEYSIZE + sizeof(act2)));
210215
lc_hash_final(xdrbg512_compare, compare1);
211216
ret += lc_compare(compare1 + LC_XDRBG512_DRNG_KEYSIZE, exp84,
212217
sizeof(exp84),
@@ -216,6 +221,7 @@ static int xdrbg512_drng_selftest(struct lc_rng_ctx *xdrbg512_ctx)
216221

217222
lc_hash_zero(xdrbg512_compare);
218223

224+
out:
219225
return ret;
220226
}
221227

hash/api/lc_cshake.h

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -72,12 +72,20 @@ int lc_cshake_init(struct lc_hash_ctx *ctx, const uint8_t *n, size_t nlen,
7272
* @param [out] out Buffer allocated by caller that is filled with the message
7373
* digest data.
7474
* @param [in] outlen Size of the output buffer to be filled.
75+
*
76+
* @return 0 on success; < 0 on error
7577
*/
76-
static inline void lc_cshake_final(struct lc_hash_ctx *ctx, uint8_t *out,
77-
size_t outlen)
78+
static inline int lc_cshake_final(struct lc_hash_ctx *ctx, uint8_t *out,
79+
size_t outlen)
7880
{
79-
lc_hash_set_digestsize(ctx, outlen);
81+
int ret;
82+
83+
ret = lc_hash_set_digestsize(ctx, outlen);
84+
if (ret)
85+
return ret;
8086
lc_hash_final(ctx, out);
87+
88+
return 0;
8189
}
8290

8391
/*

0 commit comments

Comments
 (0)