Fix PKCS7 CBC padding oracle in EnvelopedData and EncryptedData (ZD 21422)

Replace single last-byte padding check with full PKCS#5/PKCS#7
validation: verify padLen is non-zero and within block size.
Both wc_PKCS7_DecodeEnvelopedData and wc_PKCS7_DecodeEncryptedData
paths are fixed.
This commit is contained in:
Anthony Hu
2026-03-27 09:15:14 -04:00
committed by JacobBarthelmeh
parent d14b506c51
commit c563f3932a
+32 -2
View File
@@ -13262,10 +13262,24 @@ int wc_PKCS7_DecodeEnvelopedData(wc_PKCS7* pkcs7, byte* in,
padLen = encryptedContent[encryptedContentSz-1];
/* copy plaintext to output */
if (padLen > encryptedContentSz) {
if (padLen == 0 || padLen > expBlockSz ||
padLen > encryptedContentSz) {
ret = BUFFER_E;
break;
}
/* Constant-time check all padding bytes */
{
byte padCheck = 0;
int pi;
for (pi = encryptedContentSz - padLen;
pi < encryptedContentSz; pi++) {
padCheck |= encryptedContent[pi] ^ padLen;
}
if (padCheck != 0) {
ret = BUFFER_E;
break;
}
}
#ifdef ASN_BER_TO_DER
if (pkcs7->streamOutCb) {
@@ -15315,12 +15329,28 @@ int wc_PKCS7_DecodeEncryptedData(wc_PKCS7* pkcs7, byte* in, word32 inSz,
if (ret == 0) {
padLen = encryptedContent[encryptedContentSz-1];
if (padLen > encryptedContentSz) {
if (padLen == 0 || padLen > expBlockSz ||
padLen > encryptedContentSz) {
WOLFSSL_MSG("Bad padding size found");
ret = BUFFER_E;
XFREE(encryptedContent, pkcs7->heap, DYNAMIC_TYPE_PKCS7);
break;
}
/* Constant-time check all padding bytes */
{
byte padCheck = 0;
int pi;
for (pi = encryptedContentSz - padLen;
pi < encryptedContentSz; pi++) {
padCheck |= encryptedContent[pi] ^ padLen;
}
if (padCheck != 0) {
WOLFSSL_MSG("Bad padding bytes found");
ret = BUFFER_E;
XFREE(encryptedContent, pkcs7->heap, DYNAMIC_TYPE_PKCS7);
break;
}
}
/* copy plaintext to output */
if ((word32)(encryptedContentSz - padLen) > outputSz) {