In the JacksonAvroParserImpl::_finishShortText(int) method, there is a missing bound check-in handling the value reading from the byte array inputBuf and could cause unexpected IndexOutOfBoundsException if the provided input is not correctly ended.
In the first line of the do..while loop, the current index pointed by the inPtr variable is retrieved, processed and stored. Then the inPtr value is increased by one. From the study of the code, the value of inPtr must be within the range of the byte array inputBuf, but since it has increased by one in this line, the value of inPtr may be larger or equals to the length of inputBuf on some invalid input. This causes the subsequent inputBuf value access with the out-of-bound inPtr to throw an unexpected IndexOutOfBoundsException.
...
final int[] codes = sUtf8UnitLengths;
do {
i = inputBuf[inPtr++] & 0xFF;
switch (codes[i]) {
case 0:
break;
case 1:
i = ((i & 0x1F) << 6) | (inputBuf[inPtr++] & 0x3F);
break;
case 2:
i = ((i & 0x0F) << 12)
| ((inputBuf[inPtr++] & 0x3F) << 6)
| (inputBuf[inPtr++] & 0x3F);
break;
case 3:
i = ((i & 0x07) << 18)
| ((inputBuf[inPtr++] & 0x3F) << 12)
| ((inputBuf[inPtr++] & 0x3F) << 6)
| (inputBuf[inPtr++] & 0x3F);
// note: this is the codepoint value; need to split, too
i -= 0x10000;
outBuf[outPtr++] = (char) (0xD800 | (i >> 10));
i = 0xDC00 | (i & 0x3FF);
break;
default: // invalid
_reportError("Invalid byte "+Integer.toHexString(i)+" in Unicode text block");
}
outBuf[outPtr++] = (char) i;
} while (inPtr < end);
return _textBuffer.setCurrentAndReturn(outPtr);
...
Similar problem happened in JacksonAvroParserImpl::_finishLongText(int) method.
private final void _finishLongText(int len) throws IOException
...
case 3: // 4-byte UTF
c = _decodeUTF8_4(c);
// Let's add first part right away:
outBuf[outPtr++] = (char) (0xD800 | (c >> 10));
The suggested fix is to add a bound checking in the do..while loop after the inPtr++ process to ensure the inPtr is still within bound and throws an error if not for identifying invalid input.
We found this issue by OSS-Fuzz and it is reported in https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=65618 and We found this issue by OSS-Fuzz and it is reported in https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=65649.
In the
JacksonAvroParserImpl::_finishShortText(int)method, there is a missing bound check-in handling the value reading from the byte arrayinputBufand could cause unexpectedIndexOutOfBoundsExceptionif the provided input is not correctly ended.In the first line of the
do..whileloop, the current index pointed by theinPtrvariable is retrieved, processed and stored. Then theinPtrvalue is increased by one. From the study of the code, the value ofinPtrmust be within the range of the byte arrayinputBuf, but since it has increased by one in this line, the value ofinPtrmay be larger or equals to the length ofinputBufon some invalid input. This causes the subsequentinputBufvalue access with the out-of-boundinPtrto throw an unexpectedIndexOutOfBoundsException.... final int[] codes = sUtf8UnitLengths; do { i = inputBuf[inPtr++] & 0xFF; switch (codes[i]) { case 0: break; case 1: i = ((i & 0x1F) << 6) | (inputBuf[inPtr++] & 0x3F); break; case 2: i = ((i & 0x0F) << 12) | ((inputBuf[inPtr++] & 0x3F) << 6) | (inputBuf[inPtr++] & 0x3F); break; case 3: i = ((i & 0x07) << 18) | ((inputBuf[inPtr++] & 0x3F) << 12) | ((inputBuf[inPtr++] & 0x3F) << 6) | (inputBuf[inPtr++] & 0x3F); // note: this is the codepoint value; need to split, too i -= 0x10000; outBuf[outPtr++] = (char) (0xD800 | (i >> 10)); i = 0xDC00 | (i & 0x3FF); break; default: // invalid _reportError("Invalid byte "+Integer.toHexString(i)+" in Unicode text block"); } outBuf[outPtr++] = (char) i; } while (inPtr < end); return _textBuffer.setCurrentAndReturn(outPtr); ...Similar problem happened in
JacksonAvroParserImpl::_finishLongText(int)method.The suggested fix is to add a bound checking in the
do..whileloop after theinPtr++process to ensure theinPtris still within bound and throws an error if not for identifying invalid input.We found this issue by OSS-Fuzz and it is reported in https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=65618 and We found this issue by OSS-Fuzz and it is reported in https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=65649.