From f4d5ec776f07c6e99216afa3a8ca2ffe462ce305 Mon Sep 17 00:00:00 2001 From: Norbert Federa Date: Thu, 27 Feb 2020 16:43:01 +0100 Subject: [PATCH] rdpegfx: use 1-based indexing for bitmap cache Weird but Microsoft uses 1-based indexing in the RDPGFX bitmap cache PDU's. This does not seem to be documented but can be deducted from the RDP client test code in Microsoft's "Windows Protocol Test Suites" GitHub repository and the observation that mstsc aborts with a protocol error if the cacheSlot index value 0 is used in e.g. a GFX surface to cache PDU. --- channels/rdpgfx/client/rdpgfx_main.c | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/channels/rdpgfx/client/rdpgfx_main.c b/channels/rdpgfx/client/rdpgfx_main.c index 0da0bc058..4979820fb 100644 --- a/channels/rdpgfx/client/rdpgfx_main.c +++ b/channels/rdpgfx/client/rdpgfx_main.c @@ -1991,14 +1991,15 @@ static UINT rdpgfx_set_cache_slot_data(RdpgfxClientContext* context, UINT16 cach { RDPGFX_PLUGIN* gfx = (RDPGFX_PLUGIN*)context->handle; - if (cacheSlot >= gfx->MaxCacheSlot) + /* Microsoft uses 1-based indexing for the egfx bitmap cache ! */ + if (cacheSlot == 0 || cacheSlot > gfx->MaxCacheSlot) { - WLog_ERR(TAG, "%s: invalid cache slot %" PRIu16 " maxAllowed=%" PRIu16 "", __FUNCTION__, + WLog_ERR(TAG, "%s: invalid cache slot %" PRIu16 ", must be between 1 and %" PRIu16 "", __FUNCTION__, cacheSlot, gfx->MaxCacheSlot); return ERROR_INVALID_INDEX; } - gfx->CacheSlots[cacheSlot] = pData; + gfx->CacheSlots[cacheSlot - 1] = pData; return CHANNEL_RC_OK; } @@ -2007,14 +2008,15 @@ static void* rdpgfx_get_cache_slot_data(RdpgfxClientContext* context, UINT16 cac void* pData = NULL; RDPGFX_PLUGIN* gfx = (RDPGFX_PLUGIN*)context->handle; - if (cacheSlot >= gfx->MaxCacheSlot) + /* Microsoft uses 1-based indexing for the egfx bitmap cache ! */ + if (cacheSlot == 0 || cacheSlot > gfx->MaxCacheSlot) { - WLog_ERR(TAG, "%s: invalid cache slot %" PRIu16 " maxAllowed=%" PRIu16 "", __FUNCTION__, + WLog_ERR(TAG, "%s: invalid cache slot %" PRIu16 ", must be between 1 and %" PRIu16 "", __FUNCTION__, cacheSlot, gfx->MaxCacheSlot); return NULL; } - pData = gfx->CacheSlots[cacheSlot]; + pData = gfx->CacheSlots[cacheSlot - 1]; return pData; }