From 10a29dbc99ac01465ef86cbc21b4b0daa13d65fe Mon Sep 17 00:00:00 2001 From: Armin Novak Date: Sat, 5 Aug 2023 10:53:29 +0200 Subject: [PATCH] [codec,nsc] fix missing plane length check reported by @pwn2carr --- libfreerdp/codec/nsc.c | 59 +++++++++++++++++++----------------------- 1 file changed, 26 insertions(+), 33 deletions(-) diff --git a/libfreerdp/codec/nsc.c b/libfreerdp/codec/nsc.c index 86066c224..752834486 100644 --- a/libfreerdp/codec/nsc.c +++ b/libfreerdp/codec/nsc.c @@ -176,20 +176,16 @@ static BOOL nsc_rle_decode(BYTE* in, BYTE* out, UINT32 outSize, UINT32 originalS static BOOL nsc_rle_decompress_data(NSC_CONTEXT* context) { - UINT16 i; - BYTE* rle; - UINT32 planeSize; - UINT32 originalSize; - if (!context) return FALSE; - rle = context->Planes; + BYTE* rle = context->Planes; + WINPR_ASSERT(rle); - for (i = 0; i < 4; i++) + for (size_t i = 0; i < 4; i++) { - originalSize = context->OrgByteCount[i]; - planeSize = context->PlaneByteCount[i]; + const UINT32 originalSize = context->OrgByteCount[i]; + const UINT32 planeSize = context->PlaneByteCount[i]; if (planeSize == 0) { @@ -220,54 +216,53 @@ static BOOL nsc_rle_decompress_data(NSC_CONTEXT* context) static BOOL nsc_stream_initialize(NSC_CONTEXT* context, wStream* s) { - int i; - - if (!Stream_CheckAndLogRequiredLength(TAG, s, 20)) + WINPR_ASSERT(context); + WINPR_ASSERT(context->priv); + if (!Stream_CheckAndLogRequiredLengthWLog(context->priv->log, s, 20)) return FALSE; - for (i = 0; i < 4; i++) + size_t total = 0; + for (size_t i = 0; i < 4; i++) + { Stream_Read_UINT32(s, context->PlaneByteCount[i]); + total += context->PlaneByteCount[i]; + } Stream_Read_UINT8(s, context->ColorLossLevel); /* ColorLossLevel (1 byte) */ Stream_Read_UINT8(s, context->ChromaSubsamplingLevel); /* ChromaSubsamplingLevel (1 byte) */ Stream_Seek(s, 2); /* Reserved (2 bytes) */ context->Planes = Stream_Pointer(s); - return TRUE; + return Stream_CheckAndLogRequiredLengthWLog(context->priv->log, s, total); } static BOOL nsc_context_initialize(NSC_CONTEXT* context, wStream* s) { - int i; - UINT32 length; - UINT32 tempWidth; - UINT32 tempHeight; - if (!nsc_stream_initialize(context, s)) return FALSE; - length = context->width * context->height * 4; + const size_t blength = context->width * context->height * 4; - if (!context->BitmapData || (length > context->BitmapDataLength)) + if (!context->BitmapData || (blength > context->BitmapDataLength)) { - void* tmp = winpr_aligned_recalloc(context->BitmapData, length + 16, sizeof(BYTE), 32); + void* tmp = winpr_aligned_recalloc(context->BitmapData, blength + 16, sizeof(BYTE), 32); if (!tmp) return FALSE; context->BitmapData = tmp; - context->BitmapDataLength = length; + context->BitmapDataLength = blength; } - tempWidth = ROUND_UP_TO(context->width, 8); - tempHeight = ROUND_UP_TO(context->height, 2); + const UINT32 tempWidth = ROUND_UP_TO(context->width, 8); + const UINT32 tempHeight = ROUND_UP_TO(context->height, 2); /* The maximum length a decoded plane can reach in all cases */ - length = tempWidth * tempHeight; + const size_t plength = tempWidth * tempHeight; - if (length > context->priv->PlaneBuffersLength) + if (plength > context->priv->PlaneBuffersLength) { - for (i = 0; i < 4; i++) + for (size_t i = 0; i < 4; i++) { - void* tmp = (BYTE*)winpr_aligned_recalloc(context->priv->PlaneBuffers[i], length, + void* tmp = (BYTE*)winpr_aligned_recalloc(context->priv->PlaneBuffers[i], plength, sizeof(BYTE), 32); if (!tmp) @@ -276,13 +271,11 @@ static BOOL nsc_context_initialize(NSC_CONTEXT* context, wStream* s) context->priv->PlaneBuffers[i] = tmp; } - context->priv->PlaneBuffersLength = length; + context->priv->PlaneBuffersLength = plength; } - for (i = 0; i < 4; i++) - { + for (size_t i = 0; i < 4; i++) context->OrgByteCount[i] = context->width * context->height; - } if (context->ChromaSubsamplingLevel) {