boringssl/crypto/bn/bn_asn1.c
David Benjamin 4c60d356a9 Work around even more Estonian ID card misissuances.
Not content with signing negative RSA moduli, still other Estonian IDs have too
many leading zeros. Work around those too.

This workaround will be removed in six months.

BUG=534766

Change-Id: Ica23b1b1499f9dbe39e94cf7b540900860e8e135
Reviewed-on: https://boringssl-review.googlesource.com/5980
Reviewed-by: Adam Langley <agl@google.com>
2015-09-23 20:35:47 +00:00

94 lines
2.8 KiB
C

/* Copyright (c) 2015, Google Inc.
*
* Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
#include <openssl/bn.h>
#include <openssl/bytestring.h>
#include <openssl/err.h>
int BN_cbs2unsigned(CBS *cbs, BIGNUM *ret) {
CBS child;
if (!CBS_get_asn1(cbs, &child, CBS_ASN1_INTEGER) ||
CBS_len(&child) == 0) {
OPENSSL_PUT_ERROR(BN, BN_R_BAD_ENCODING);
return 0;
}
if (CBS_data(&child)[0] & 0x80) {
OPENSSL_PUT_ERROR(BN, BN_R_NEGATIVE_NUMBER);
return 0;
}
/* INTEGERs must be minimal. */
if (CBS_data(&child)[0] == 0x00 &&
CBS_len(&child) > 1 &&
!(CBS_data(&child)[1] & 0x80)) {
OPENSSL_PUT_ERROR(BN, BN_R_BAD_ENCODING);
return 0;
}
return BN_bin2bn(CBS_data(&child), CBS_len(&child), ret) != NULL;
}
int BN_cbs2unsigned_buggy(CBS *cbs, BIGNUM *ret) {
CBS child;
if (!CBS_get_asn1(cbs, &child, CBS_ASN1_INTEGER) ||
CBS_len(&child) == 0) {
OPENSSL_PUT_ERROR(BN, BN_R_BAD_ENCODING);
return 0;
}
/* This function intentionally does not reject negative numbers or non-minimal
* encodings. Estonian IDs issued between September 2014 to September 2015 are
* broken. See https://crbug.com/532048 and https://crbug.com/534766.
*
* TODO(davidben): Remove this code and callers in March 2016. */
return BN_bin2bn(CBS_data(&child), CBS_len(&child), ret) != NULL;
}
int BN_bn2cbb(CBB *cbb, const BIGNUM *bn) {
/* Negative numbers are unsupported. */
if (BN_is_negative(bn)) {
OPENSSL_PUT_ERROR(BN, BN_R_NEGATIVE_NUMBER);
return 0;
}
CBB child;
if (!CBB_add_asn1(cbb, &child, CBS_ASN1_INTEGER)) {
OPENSSL_PUT_ERROR(BN, BN_R_ENCODE_ERROR);
return 0;
}
/* The number must be padded with a leading zero if the high bit would
* otherwise be set (or |bn| is zero). */
if (BN_num_bits(bn) % 8 == 0 &&
!CBB_add_u8(&child, 0x00)) {
OPENSSL_PUT_ERROR(BN, BN_R_ENCODE_ERROR);
return 0;
}
uint8_t *out;
if (!CBB_add_space(&child, &out, BN_num_bytes(bn))) {
OPENSSL_PUT_ERROR(BN, BN_R_ENCODE_ERROR);
return 0;
}
BN_bn2bin(bn, out);
if (!CBB_flush(cbb)) {
OPENSSL_PUT_ERROR(BN, BN_R_ENCODE_ERROR);
return 0;
}
return 1;
}