Fix issues found in SawyerChunk decoder

This commit is contained in:
Michał Janiszewski 2021-03-03 12:59:18 +01:00
parent 0b73781df8
commit bf95260f37
1 changed files with 27 additions and 9 deletions

View File

@ -84,13 +84,22 @@ std::shared_ptr<SawyerChunk> SawyerChunkReader::ReadChunk()
}
auto buffer = static_cast<uint8_t*>(AllocateLargeTempBuffer());
size_t uncompressedLength = DecodeChunk(buffer, MAX_UNCOMPRESSED_CHUNK_SIZE, compressedData.get(), header);
if (uncompressedLength == 0)
try
{
throw SawyerChunkException(EXCEPTION_MSG_ZERO_SIZED_CHUNK);
size_t uncompressedLength = DecodeChunk(buffer, MAX_UNCOMPRESSED_CHUNK_SIZE, compressedData.get(), header);
if (uncompressedLength == 0)
{
throw SawyerChunkException(EXCEPTION_MSG_ZERO_SIZED_CHUNK);
}
buffer = static_cast<uint8_t*>(FinaliseLargeTempBuffer(buffer, uncompressedLength));
return std::make_shared<SawyerChunk>(
static_cast<SAWYER_ENCODING>(header.encoding), buffer, uncompressedLength);
}
catch (const std::exception&)
{
FreeLargeTempBuffer(buffer);
throw;
}
buffer = static_cast<uint8_t*>(FinaliseLargeTempBuffer(buffer, uncompressedLength));
return std::make_shared<SawyerChunk>(static_cast<SAWYER_ENCODING>(header.encoding), buffer, uncompressedLength);
}
default:
throw SawyerChunkException(EXCEPTION_MSG_INVALID_CHUNK_ENCODING);
@ -192,10 +201,10 @@ size_t SawyerChunkReader::DecodeChunk(void* dst, size_t dstCapacity, const void*
size_t SawyerChunkReader::DecodeChunkRLERepeat(void* dst, size_t dstCapacity, const void* src, size_t srcLength)
{
auto immBuffer = AllocateLargeTempBuffer();
auto immLength = DecodeChunkRLE(immBuffer, MAX_UNCOMPRESSED_CHUNK_SIZE, src, srcLength);
auto size = DecodeChunkRepeat(dst, dstCapacity, immBuffer, immLength);
FreeLargeTempBuffer(immBuffer);
auto immBuffer = std::unique_ptr<uint8_t, decltype(&FreeLargeTempBuffer)>(
static_cast<uint8_t*>(AllocateLargeTempBuffer()), &FreeLargeTempBuffer);
auto immLength = DecodeChunkRLE(immBuffer.get(), MAX_UNCOMPRESSED_CHUNK_SIZE, src, srcLength);
auto size = DecodeChunkRepeat(dst, dstCapacity, immBuffer.get(), immLength);
return size;
}
@ -267,6 +276,15 @@ size_t SawyerChunkReader::DecodeChunkRepeat(void* dst, size_t dstCapacity, const
{
throw SawyerChunkException(EXCEPTION_MSG_DESTINATION_TOO_SMALL);
}
if (copySrc < dst)
{
throw SawyerChunkException(EXCEPTION_MSG_CORRUPT_RLE);
}
if ((copySrc < (dst8 + count) && copySrc >= dst8)
|| ((copySrc + count) <= (dst8 + count) && (copySrc + count) > dst8))
{
throw SawyerChunkException(EXCEPTION_MSG_CORRUPT_RLE);
}
std::memcpy(dst8, copySrc, count);
dst8 += count;