-
Notifications
You must be signed in to change notification settings - Fork 121
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #596 from DominicDams/upstream-merge-8-22
Upstream Merge 08-22-22
- Loading branch information
Showing
142 changed files
with
20,376 additions
and
19,344 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -66,195 +66,200 @@ | |
#include "internal.h" | ||
|
||
|
||
int ASN1_BIT_STRING_set(ASN1_BIT_STRING *x, const unsigned char *d, int len) | ||
{ | ||
return ASN1_STRING_set(x, d, len); | ||
int ASN1_BIT_STRING_set(ASN1_BIT_STRING *x, const unsigned char *d, int len) { | ||
return ASN1_STRING_set(x, d, len); | ||
} | ||
|
||
int asn1_bit_string_length(const ASN1_BIT_STRING *str, | ||
uint8_t *out_padding_bits) { | ||
int len = str->length; | ||
if (str->flags & ASN1_STRING_FLAG_BITS_LEFT) { | ||
// If the string is already empty, it cannot have padding bits. | ||
*out_padding_bits = len == 0 ? 0 : str->flags & 0x07; | ||
return len; | ||
} | ||
int len = str->length; | ||
if (str->flags & ASN1_STRING_FLAG_BITS_LEFT) { | ||
// If the string is already empty, it cannot have padding bits. | ||
*out_padding_bits = len == 0 ? 0 : str->flags & 0x07; | ||
return len; | ||
} | ||
|
||
// TODO(https://crbug.com/boringssl/447): If we move this logic to | ||
// |ASN1_BIT_STRING_set_bit|, can we remove this representation? | ||
while (len > 0 && str->data[len - 1] == 0) { | ||
len--; | ||
} | ||
uint8_t padding_bits = 0; | ||
if (len > 0) { | ||
uint8_t last = str->data[len - 1]; | ||
assert(last != 0); | ||
for (; padding_bits < 7; padding_bits++) { | ||
if (last & (1 << padding_bits)) { | ||
break; | ||
} | ||
} | ||
// TODO(https://crbug.com/boringssl/447): If we move this logic to | ||
// |ASN1_BIT_STRING_set_bit|, can we remove this representation? | ||
while (len > 0 && str->data[len - 1] == 0) { | ||
len--; | ||
} | ||
uint8_t padding_bits = 0; | ||
if (len > 0) { | ||
uint8_t last = str->data[len - 1]; | ||
assert(last != 0); | ||
for (; padding_bits < 7; padding_bits++) { | ||
if (last & (1 << padding_bits)) { | ||
break; | ||
} | ||
} | ||
*out_padding_bits = padding_bits; | ||
return len; | ||
} | ||
*out_padding_bits = padding_bits; | ||
return len; | ||
} | ||
|
||
int ASN1_BIT_STRING_num_bytes(const ASN1_BIT_STRING *str, size_t *out) { | ||
uint8_t padding_bits; | ||
int len = asn1_bit_string_length(str, &padding_bits); | ||
if (padding_bits != 0) { | ||
return 0; | ||
} | ||
*out = len; | ||
return 1; | ||
uint8_t padding_bits; | ||
int len = asn1_bit_string_length(str, &padding_bits); | ||
if (padding_bits != 0) { | ||
return 0; | ||
} | ||
*out = len; | ||
return 1; | ||
} | ||
|
||
int i2c_ASN1_BIT_STRING(const ASN1_BIT_STRING *a, unsigned char **pp) | ||
{ | ||
if (a == NULL) { | ||
return 0; | ||
} | ||
int i2c_ASN1_BIT_STRING(const ASN1_BIT_STRING *a, unsigned char **pp) { | ||
if (a == NULL) { | ||
return 0; | ||
} | ||
|
||
uint8_t bits; | ||
int len = asn1_bit_string_length(a, &bits); | ||
int ret = 1 + len; | ||
if (pp == NULL) { | ||
return ret; | ||
} | ||
uint8_t bits; | ||
int len = asn1_bit_string_length(a, &bits); | ||
int ret = 1 + len; | ||
if (pp == NULL) { | ||
return ret; | ||
} | ||
|
||
uint8_t *p = *pp; | ||
*(p++) = bits; | ||
OPENSSL_memcpy(p, a->data, len); | ||
if (len > 0) { | ||
p[len - 1] &= (0xff << bits); | ||
} | ||
p += len; | ||
*pp = p; | ||
return (ret); | ||
uint8_t *p = *pp; | ||
*(p++) = bits; | ||
OPENSSL_memcpy(p, a->data, len); | ||
if (len > 0) { | ||
p[len - 1] &= (0xff << bits); | ||
} | ||
p += len; | ||
*pp = p; | ||
return (ret); | ||
} | ||
|
||
ASN1_BIT_STRING *c2i_ASN1_BIT_STRING(ASN1_BIT_STRING **a, | ||
const unsigned char **pp, long len) | ||
{ | ||
ASN1_BIT_STRING *ret = NULL; | ||
const unsigned char *p; | ||
unsigned char *s; | ||
int padding; | ||
const unsigned char **pp, long len) { | ||
ASN1_BIT_STRING *ret = NULL; | ||
const unsigned char *p; | ||
unsigned char *s; | ||
int padding; | ||
|
||
if (len < 1) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_STRING_TOO_SHORT); | ||
goto err; | ||
} | ||
if (len < 1) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_STRING_TOO_SHORT); | ||
goto err; | ||
} | ||
|
||
if (len > INT_MAX) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_STRING_TOO_LONG); | ||
goto err; | ||
} | ||
if (len > INT_MAX) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_STRING_TOO_LONG); | ||
goto err; | ||
} | ||
|
||
if ((a == NULL) || ((*a) == NULL)) { | ||
if ((ret = ASN1_BIT_STRING_new()) == NULL) | ||
return (NULL); | ||
} else | ||
ret = (*a); | ||
|
||
p = *pp; | ||
padding = *(p++); | ||
len--; | ||
if (padding > 7) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_INVALID_BIT_STRING_BITS_LEFT); | ||
goto err; | ||
if ((a == NULL) || ((*a) == NULL)) { | ||
if ((ret = ASN1_BIT_STRING_new()) == NULL) { | ||
return (NULL); | ||
} | ||
} else { | ||
ret = (*a); | ||
} | ||
|
||
/* Unused bits in a BIT STRING must be zero. */ | ||
uint8_t padding_mask = (1 << padding) - 1; | ||
if (padding != 0 && | ||
(len < 1 || (p[len - 1] & padding_mask) != 0)) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_INVALID_BIT_STRING_PADDING); | ||
goto err; | ||
} | ||
p = *pp; | ||
padding = *(p++); | ||
len--; | ||
if (padding > 7) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_INVALID_BIT_STRING_BITS_LEFT); | ||
goto err; | ||
} | ||
|
||
/* | ||
* We do this to preserve the settings. If we modify the settings, via | ||
* the _set_bit function, we will recalculate on output | ||
*/ | ||
ret->flags &= ~(ASN1_STRING_FLAG_BITS_LEFT | 0x07); /* clear */ | ||
ret->flags |= (ASN1_STRING_FLAG_BITS_LEFT | padding); /* set */ | ||
/* Unused bits in a BIT STRING must be zero. */ | ||
uint8_t padding_mask = (1 << padding) - 1; | ||
if (padding != 0 && (len < 1 || (p[len - 1] & padding_mask) != 0)) { | ||
OPENSSL_PUT_ERROR(ASN1, ASN1_R_INVALID_BIT_STRING_PADDING); | ||
goto err; | ||
} | ||
|
||
if (len > 0) { | ||
s = OPENSSL_memdup(p, len); | ||
if (s == NULL) { | ||
OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); | ||
goto err; | ||
} | ||
p += len; | ||
} else { | ||
s = NULL; | ||
/* | ||
* We do this to preserve the settings. If we modify the settings, via | ||
* the _set_bit function, we will recalculate on output | ||
*/ | ||
ret->flags &= ~(ASN1_STRING_FLAG_BITS_LEFT | 0x07); /* clear */ | ||
ret->flags |= (ASN1_STRING_FLAG_BITS_LEFT | padding); /* set */ | ||
|
||
if (len > 0) { | ||
s = OPENSSL_memdup(p, len); | ||
if (s == NULL) { | ||
OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); | ||
goto err; | ||
} | ||
p += len; | ||
} else { | ||
s = NULL; | ||
} | ||
|
||
ret->length = (int)len; | ||
OPENSSL_free(ret->data); | ||
ret->data = s; | ||
ret->type = V_ASN1_BIT_STRING; | ||
if (a != NULL) | ||
(*a) = ret; | ||
*pp = p; | ||
return (ret); | ||
err: | ||
if ((ret != NULL) && ((a == NULL) || (*a != ret))) | ||
ASN1_BIT_STRING_free(ret); | ||
return (NULL); | ||
ret->length = (int)len; | ||
OPENSSL_free(ret->data); | ||
ret->data = s; | ||
ret->type = V_ASN1_BIT_STRING; | ||
if (a != NULL) { | ||
(*a) = ret; | ||
} | ||
*pp = p; | ||
return (ret); | ||
err: | ||
if ((ret != NULL) && ((a == NULL) || (*a != ret))) { | ||
ASN1_BIT_STRING_free(ret); | ||
} | ||
return (NULL); | ||
} | ||
|
||
/* | ||
* These next 2 functions from Goetz Babin-Ebell <[email protected]> | ||
*/ | ||
int ASN1_BIT_STRING_set_bit(ASN1_BIT_STRING *a, int n, int value) | ||
{ | ||
int w, v, iv; | ||
unsigned char *c; | ||
int ASN1_BIT_STRING_set_bit(ASN1_BIT_STRING *a, int n, int value) { | ||
int w, v, iv; | ||
unsigned char *c; | ||
|
||
w = n / 8; | ||
v = 1 << (7 - (n & 0x07)); | ||
iv = ~v; | ||
if (!value) | ||
v = 0; | ||
w = n / 8; | ||
v = 1 << (7 - (n & 0x07)); | ||
iv = ~v; | ||
if (!value) { | ||
v = 0; | ||
} | ||
|
||
if (a == NULL) | ||
return 0; | ||
if (a == NULL) { | ||
return 0; | ||
} | ||
|
||
a->flags &= ~(ASN1_STRING_FLAG_BITS_LEFT | 0x07); /* clear, set on write */ | ||
a->flags &= ~(ASN1_STRING_FLAG_BITS_LEFT | 0x07); /* clear, set on write */ | ||
|
||
if ((a->length < (w + 1)) || (a->data == NULL)) { | ||
if (!value) | ||
return (1); /* Don't need to set */ | ||
if (a->data == NULL) | ||
c = (unsigned char *)OPENSSL_malloc(w + 1); | ||
else | ||
c = (unsigned char *)OPENSSL_realloc(a->data, w + 1); | ||
if (c == NULL) { | ||
OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); | ||
return 0; | ||
} | ||
if (w + 1 - a->length > 0) | ||
OPENSSL_memset(c + a->length, 0, w + 1 - a->length); | ||
a->data = c; | ||
a->length = w + 1; | ||
if ((a->length < (w + 1)) || (a->data == NULL)) { | ||
if (!value) { | ||
return (1); /* Don't need to set */ | ||
} | ||
a->data[w] = ((a->data[w]) & iv) | v; | ||
while ((a->length > 0) && (a->data[a->length - 1] == 0)) | ||
a->length--; | ||
return (1); | ||
if (a->data == NULL) { | ||
c = (unsigned char *)OPENSSL_malloc(w + 1); | ||
} else { | ||
c = (unsigned char *)OPENSSL_realloc(a->data, w + 1); | ||
} | ||
if (c == NULL) { | ||
OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); | ||
return 0; | ||
} | ||
if (w + 1 - a->length > 0) { | ||
OPENSSL_memset(c + a->length, 0, w + 1 - a->length); | ||
} | ||
a->data = c; | ||
a->length = w + 1; | ||
} | ||
a->data[w] = ((a->data[w]) & iv) | v; | ||
while ((a->length > 0) && (a->data[a->length - 1] == 0)) { | ||
a->length--; | ||
} | ||
return (1); | ||
} | ||
|
||
int ASN1_BIT_STRING_get_bit(const ASN1_BIT_STRING *a, int n) | ||
{ | ||
int w, v; | ||
int ASN1_BIT_STRING_get_bit(const ASN1_BIT_STRING *a, int n) { | ||
int w, v; | ||
|
||
w = n / 8; | ||
v = 1 << (7 - (n & 0x07)); | ||
if ((a == NULL) || (a->length < (w + 1)) || (a->data == NULL)) | ||
return (0); | ||
return ((a->data[w] & v) != 0); | ||
w = n / 8; | ||
v = 1 << (7 - (n & 0x07)); | ||
if ((a == NULL) || (a->length < (w + 1)) || (a->data == NULL)) { | ||
return (0); | ||
} | ||
return ((a->data[w] & v) != 0); | ||
} | ||
|
||
/* | ||
|
@@ -263,22 +268,22 @@ int ASN1_BIT_STRING_get_bit(const ASN1_BIT_STRING *a, int n) | |
* which is not specified in 'flags', 1 otherwise. | ||
* 'len' is the length of 'flags'. | ||
*/ | ||
int ASN1_BIT_STRING_check(const ASN1_BIT_STRING *a, | ||
const unsigned char *flags, int flags_len) | ||
{ | ||
int i, ok; | ||
/* Check if there is one bit set at all. */ | ||
if (!a || !a->data) | ||
return 1; | ||
int ASN1_BIT_STRING_check(const ASN1_BIT_STRING *a, const unsigned char *flags, | ||
int flags_len) { | ||
int i, ok; | ||
/* Check if there is one bit set at all. */ | ||
if (!a || !a->data) { | ||
return 1; | ||
} | ||
|
||
/* | ||
* Check each byte of the internal representation of the bit string. | ||
*/ | ||
ok = 1; | ||
for (i = 0; i < a->length && ok; ++i) { | ||
unsigned char mask = i < flags_len ? ~flags[i] : 0xff; | ||
/* We are done if there is an unneeded bit set. */ | ||
ok = (a->data[i] & mask) == 0; | ||
} | ||
return ok; | ||
/* | ||
* Check each byte of the internal representation of the bit string. | ||
*/ | ||
ok = 1; | ||
for (i = 0; i < a->length && ok; ++i) { | ||
unsigned char mask = i < flags_len ? ~flags[i] : 0xff; | ||
/* We are done if there is an unneeded bit set. */ | ||
ok = (a->data[i] & mask) == 0; | ||
} | ||
return ok; | ||
} |
Oops, something went wrong.