Skip to content

Commit 2c643c5

Browse files
committed
Fix length-related wycheproof testcases
Signed-off-by: Steffen Jaeckel <[email protected]>
1 parent 8913fd5 commit 2c643c5

File tree

5 files changed

+23
-5
lines changed

5 files changed

+23
-5
lines changed

src/headers/tomcrypt_pk.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -784,9 +784,17 @@ enum ltc_der_seq {
784784
LTC_DER_SEQ_RELAXED = LTC_DER_SEQ_ZERO,
785785
LTC_DER_SEQ_STRICT = 0x2u,
786786

787+
/** Bit2 - [0]=Relaxed Length Check
788+
* [1]=Strict Length Check */
789+
LTC_DER_SEQ_LEN_RELAXED = LTC_DER_SEQ_ZERO,
790+
LTC_DER_SEQ_LEN_STRICT = 0x4u,
791+
787792
/** Alternative naming */
788793
LTC_DER_SEQ_SET = LTC_DER_SEQ_UNORDERED,
789794
LTC_DER_SEQ_SEQUENCE = LTC_DER_SEQ_ORDERED,
795+
796+
LTC_DER_SEQ_ALL_STRICT = LTC_DER_SEQ_STRICT | LTC_DER_SEQ_LEN_STRICT,
797+
790798
};
791799

792800
int der_decode_sequence_ex(const unsigned char *in, unsigned long inlen,

src/headers/tomcrypt_private.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -666,7 +666,8 @@ int der_decode_asn1_identifier(const unsigned char *in, unsigned long *inlen, lt
666666
int der_length_asn1_identifier(const ltc_asn1_list *id, unsigned long *idlen);
667667

668668
int der_encode_asn1_length(unsigned long len, unsigned char* out, unsigned long* outlen);
669-
int der_decode_asn1_length(const unsigned char *in, unsigned long *inlen, unsigned long *outlen);
669+
int der_decode_asn1_length_ex(const unsigned char *in, unsigned long *inlen, unsigned long *outlen, unsigned int flags);
670+
#define der_decode_asn1_length(i, il, ol) der_decode_asn1_length_ex(i, il, ol, 0)
670671
int der_length_asn1_length(unsigned long len, unsigned long *outlen);
671672

672673
int der_length_sequence_ex(const ltc_asn1_list *list, unsigned long inlen,

src/pk/asn1/der/custom_type/der_decode_custom_type.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ int der_decode_custom_type_ex(const unsigned char *in, unsigned long inlen,
4747
int err, seq_err, i, ordered;
4848
ltc_asn1_type type;
4949
ltc_asn1_list ident;
50+
unsigned int f;
5051
unsigned long size, x, y, z, blksize;
5152
unsigned char* in_new = NULL;
5253
void *data;
@@ -63,7 +64,8 @@ int der_decode_custom_type_ex(const unsigned char *in, unsigned long inlen,
6364
LTC_ARGCHK(list != NULL);
6465

6566
/* sequence type? We allow 0x30 SEQUENCE and 0x31 SET since fundamentally they're the same structure */
66-
if (in[x] != 0x30 && in[x] != 0x31) {
67+
f = flags & ~(LTC_DER_SEQ_ALL_STRICT);
68+
if (((f == LTC_DER_SEQ_SEQUENCE) && (in[x] != 0x30)) || (((f == LTC_DER_SEQ_SET) && (in[x] != 0x31)))) {
6769
return CRYPT_INVALID_PACKET;
6870
}
6971
++x;
@@ -116,7 +118,7 @@ int der_decode_custom_type_ex(const unsigned char *in, unsigned long inlen,
116118
} else {
117119

118120
y = inlen - x;
119-
if ((err = der_decode_asn1_length(&in[x], &y, &blksize)) != CRYPT_OK) {
121+
if ((err = der_decode_asn1_length_ex(&in[x], &y, &blksize, flags)) != CRYPT_OK) {
120122
goto LBL_ERR;
121123
}
122124
x += y;

src/pk/asn1/der/general/der_decode_asn1_length.c

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
@param outlen [out] The decoded ASN.1 length
1616
@return CRYPT_OK if successful
1717
*/
18-
int der_decode_asn1_length(const unsigned char *in, unsigned long *inlen, unsigned long *outlen)
18+
int der_decode_asn1_length_ex(const unsigned char *in, unsigned long *inlen, unsigned long *outlen, unsigned int flags)
1919
{
2020
unsigned long real_len, decoded_len, offset, i;
2121

@@ -42,10 +42,17 @@ int der_decode_asn1_length(const unsigned char *in, unsigned long *inlen, unsign
4242
if (real_len > (*inlen - 1)) {
4343
return CRYPT_BUFFER_OVERFLOW;
4444
}
45+
flags &= LTC_DER_SEQ_LEN_STRICT;
4546
decoded_len = 0;
4647
offset = 1 + real_len;
4748
for (i = 0; i < real_len; i++) {
4849
decoded_len = (decoded_len << 8) | in[1 + i];
50+
if ((flags == LTC_DER_SEQ_LEN_STRICT) && (decoded_len == 0)) {
51+
return CRYPT_PK_ASN1_ERROR;
52+
}
53+
}
54+
if ((flags == LTC_DER_SEQ_LEN_STRICT) && (real_len == 1) && (decoded_len < 128)) {
55+
return CRYPT_PK_ASN1_ERROR;
4956
}
5057
}
5158

src/pk/ecc/ecc_verify_hash_x962.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ int ecc_verify_hash_x962(const unsigned char *sig, unsigned long siglen,
2222
if ((err = ltc_mp_init_multi(&r, &s, NULL)) != CRYPT_OK) return err;
2323

2424
/* ANSI X9.62 format - ASN.1 encoded SEQUENCE{ INTEGER(r), INTEGER(s) } */
25-
if ((err = der_decode_sequence_multi_ex(sig, siglen, LTC_DER_SEQ_SEQUENCE | LTC_DER_SEQ_STRICT,
25+
if ((err = der_decode_sequence_multi_ex(sig, siglen, LTC_DER_SEQ_SEQUENCE | LTC_DER_SEQ_ALL_STRICT,
2626
LTC_ASN1_INTEGER, 1UL, r,
2727
LTC_ASN1_INTEGER, 1UL, s,
2828
LTC_ASN1_EOL, 0UL, LTC_NULL)) != CRYPT_OK) { goto error; }

0 commit comments

Comments
 (0)