Check boundaries in B64 decode

ERR_get_error will always return a positive error code
This commit is contained in:
Juliusz Sosinowicz
2020-01-13 10:45:23 +01:00
parent 58c239a49f
commit 9a0d3ba369
4 changed files with 30 additions and 24 deletions

View File

@@ -34453,7 +34453,7 @@ int wolfSSL_EC_POINT_oct2point(const WOLFSSL_EC_GROUP *group,
(void)ctx; (void)ctx;
return wolfSSL_ECPoint_d2i((unsigned char*)buf, len, group, p); return wolfSSL_ECPoint_d2i((unsigned char*)buf, (unsigned int)len, group, p);
} }
/* wolfSSL_EC_POINT_point2bn should return "in" if not null */ /* wolfSSL_EC_POINT_point2bn should return "in" if not null */
@@ -34484,7 +34484,7 @@ WOLFSSL_BIGNUM *wolfSSL_EC_POINT_point2bn(const WOLFSSL_EC_GROUP *group,
if (wolfSSL_EC_POINT_point2oct(group, p, form, if (wolfSSL_EC_POINT_point2oct(group, p, form,
buf, len, ctx) == len) { buf, len, ctx) == len) {
ret = wolfSSL_BN_bin2bn(buf, len, in); ret = wolfSSL_BN_bin2bn(buf, (int)len, in);
} }
XFREE(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER); XFREE(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
@@ -42535,7 +42535,6 @@ WOLFSSL_EVP_PKEY* wolfSSL_d2i_PrivateKey_EVP(WOLFSSL_EVP_PKEY** out,
wolfSSL_EVP_PKEY_free(pkey); wolfSSL_EVP_PKEY_free(pkey);
return NULL; return NULL;
} }
pkey->rsa->pkey = pkey;
if (wolfSSL_RSA_LoadDer_ex(pkey->rsa, if (wolfSSL_RSA_LoadDer_ex(pkey->rsa,
(const unsigned char*)pkey->pkey.ptr, (const unsigned char*)pkey->pkey.ptr,
@@ -46829,7 +46828,7 @@ int wolfSSL_BN_hex2bn(WOLFSSL_BIGNUM** bn, const char* str)
return WOLFSSL_FAILURE; return WOLFSSL_FAILURE;
} }
strLen = XSTRLEN(str); strLen = (int)XSTRLEN(str);
/* ignore trailing new lines */ /* ignore trailing new lines */
while (str[strLen-1] == '\n' && strLen > 0) strLen--; while (str[strLen-1] == '\n' && strLen > 0) strLen--;

View File

@@ -23171,12 +23171,7 @@ static void test_wolfSSL_ERR_put_error(void)
AssertIntEQ(ERR_get_error_line_data(&file, &line, NULL, NULL), 0); AssertIntEQ(ERR_get_error_line_data(&file, &line, NULL, NULL), 0);
PEMerr(4,4); PEMerr(4,4);
#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || \
defined(WOLFSSL_HAPROXY)
AssertIntEQ(ERR_get_error(), -4);
#else
AssertIntEQ(ERR_get_error(), 4); AssertIntEQ(ERR_get_error(), 4);
#endif
/* Empty and free up all error nodes */ /* Empty and free up all error nodes */
ERR_clear_error(); ERR_clear_error();

View File

@@ -10334,15 +10334,15 @@ int PemToDer(const unsigned char* buff, long longSz, int type,
/* look for matching footer */ /* look for matching footer */
footer = XSTRNSTR(beginEnd, footer = XSTRNSTR(beginEnd,
beginBuf + STR_SIZEOF(BEGIN_PRIV_KEY_PREFIX), beginBuf + STR_SIZEOF(BEGIN_PRIV_KEY_PREFIX),
(char*)buff + sz - beginEnd); (unsigned int)((char*)buff + sz - beginEnd));
if (!footer) { if (!footer) {
WOLFSSL_MSG("Couldn't find PEM footer"); WOLFSSL_MSG("Couldn't find PEM footer");
return ASN_NO_PEM_HEADER; return ASN_NO_PEM_HEADER;
} }
footer -= STR_SIZEOF(END_PRIV_KEY_PREFIX); footer -= STR_SIZEOF(END_PRIV_KEY_PREFIX);
endLen = beginEnd - headerEnd - endLen = (unsigned int)(beginEnd - headerEnd -
(STR_SIZEOF(BEGIN_PRIV_KEY_PREFIX) - (STR_SIZEOF(BEGIN_PRIV_KEY_PREFIX) -
STR_SIZEOF(END_PRIV_KEY_PREFIX)); STR_SIZEOF(END_PRIV_KEY_PREFIX)));
XMEMCPY(endBuf, footer, endLen); XMEMCPY(endBuf, footer, endLen);
endBuf[endLen] = '\0'; endBuf[endLen] = '\0';
@@ -10394,7 +10394,7 @@ int PemToDer(const unsigned char* buff, long longSz, int type,
#endif /* WOLFSSL_ENCRYPTED_KEYS */ #endif /* WOLFSSL_ENCRYPTED_KEYS */
/* find footer */ /* find footer */
footerEnd = XSTRNSTR(headerEnd, footer, (char*)buff + sz - headerEnd); footerEnd = XSTRNSTR(headerEnd, footer, (unsigned int)((char*)buff + sz - headerEnd));
if (!footerEnd) { if (!footerEnd) {
if (info) if (info)
info->consumed = longSz; /* No more certs if no footer */ info->consumed = longSz; /* No more certs if no footer */

View File

@@ -57,21 +57,21 @@ const byte base64Decode[] = { 62, BAD, BAD, BAD, 63, /* + starts at 0x2B */
46, 47, 48, 49, 50, 51 46, 47, 48, 49, 50, 51
}; };
static WC_INLINE int Base64_SkipNewline(const byte* in, word32 *outLen, word32 *outJ) static WC_INLINE int Base64_SkipNewline(const byte* in, word32 *inLen, word32 *outJ)
{ {
word32 inLen = *outLen; word32 len = *inLen;
word32 j = *outJ; word32 j = *outJ;
if (inLen && (in[j] == ' ' || in[j] == '\r' || in[j] == '\n')) { if (len && (in[j] == ' ' || in[j] == '\r' || in[j] == '\n')) {
byte endLine = in[j++]; byte endLine = in[j++];
inLen--; len--;
while (inLen && endLine == ' ') { /* allow trailing whitespace */ while (len && endLine == ' ') { /* allow trailing whitespace */
endLine = in[j++]; endLine = in[j++];
inLen--; len--;
} }
if (endLine == '\r') { if (endLine == '\r') {
if (inLen) { if (len) {
endLine = in[j++]; endLine = in[j++];
inLen--; len--;
} }
} }
if (endLine != '\n') { if (endLine != '\n') {
@@ -79,7 +79,10 @@ static WC_INLINE int Base64_SkipNewline(const byte* in, word32 *outLen, word32 *
return ASN_INPUT_E; return ASN_INPUT_E;
} }
} }
*outLen = inLen; if (!len) {
return BUFFER_E;
}
*inLen = len;
*outJ = j; *outJ = j;
return 0; return 0;
} }
@@ -101,21 +104,32 @@ int Base64_Decode(const byte* in, word32 inLen, byte* out, word32* outLen)
byte b1, b2, b3; byte b1, b2, b3;
if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) { if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) {
if (ret == BUFFER_E) {
/* Running out of buffer here is not an error */
break;
}
return ret; return ret;
} }
byte e1 = in[j++]; byte e1 = in[j++];
if (e1 == '\0') {
break;
}
inLen--;
if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) { if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) {
return ret; return ret;
} }
byte e2 = in[j++]; byte e2 = in[j++];
inLen--;
if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) { if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) {
return ret; return ret;
} }
byte e3 = in[j++]; byte e3 = in[j++];
inLen--;
if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) { if ((ret = Base64_SkipNewline(in, &inLen, &j)) != 0) {
return ret; return ret;
} }
byte e4 = in[j++]; byte e4 = in[j++];
inLen--;
if (e1 == 0) /* end file 0's */ if (e1 == 0) /* end file 0's */
break; break;
@@ -155,8 +169,6 @@ int Base64_Decode(const byte* in, word32 inLen, byte* out, word32* outLen)
out[i++] = b3; out[i++] = b3;
else else
break; break;
inLen -= 4;
} }
/* If the output buffer has a room for an extra byte, add a null terminator */ /* If the output buffer has a room for an extra byte, add a null terminator */
if (out && *outLen > i) if (out && *outLen > i)