Fixed progressive decoding without subbanddiff
(cherry picked from commit e3445eefab
)
This commit is contained in:
parent
84693e93b6
commit
1a4c1de6a8
@ -38,7 +38,10 @@ extern "C"
|
||||
#endif
|
||||
|
||||
FREERDP_API int progressive_compress(PROGRESSIVE_CONTEXT* progressive, const BYTE* pSrcData,
|
||||
UINT32 SrcSize, BYTE** ppDstData, UINT32* pDstSize);
|
||||
UINT32 SrcSize, UINT32 SrcFormat, UINT32 Width,
|
||||
UINT32 Height, UINT32 ScanLine,
|
||||
const REGION16* invalidRegion, BYTE** ppDstData,
|
||||
UINT32* pDstSize);
|
||||
|
||||
FREERDP_API INT32 progressive_decompress(PROGRESSIVE_CONTEXT* progressive, const BYTE* pSrcData,
|
||||
UINT32 SrcSize, BYTE* pDstData, UINT32 DstFormat,
|
||||
|
@ -2466,7 +2466,7 @@ int progressive_compress(PROGRESSIVE_CONTEXT* progressive, const BYTE* pSrcData,
|
||||
RFX_RECT* rects = NULL;
|
||||
RFX_MESSAGE* message;
|
||||
|
||||
if (!progressive || !pSrcData || !ppDstData || !pDstSize)
|
||||
if (!progressive || !pSrcData || !ppDstData || !pDstSize || !invalidRegion)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
@ -2494,57 +2494,34 @@ int progressive_compress(PROGRESSIVE_CONTEXT* progressive, const BYTE* pSrcData,
|
||||
if (SrcSize < Height * ScanLine)
|
||||
return -4;
|
||||
|
||||
if (!invalidRegion)
|
||||
{
|
||||
numRects = (Width + 63) / 64;
|
||||
numRects *= (Height + 63) / 64;
|
||||
}
|
||||
else
|
||||
numRects = region16_n_rects(invalidRegion);
|
||||
|
||||
if (numRects == 0)
|
||||
return 0;
|
||||
|
||||
numRects = (Width + 63) / 64;
|
||||
numRects *= (Height + 63) / 64;
|
||||
if (!Stream_EnsureCapacity(progressive->rects, numRects * sizeof(RFX_RECT)))
|
||||
return -5;
|
||||
rects = (RFX_RECT*)Stream_Buffer(progressive->rects);
|
||||
if (invalidRegion)
|
||||
{
|
||||
const RECTANGLE_16* r = region16_rects(invalidRegion, NULL);
|
||||
for (x = 0; x < numRects; x++)
|
||||
{
|
||||
rects[x].x = r[x].left;
|
||||
rects[x].y = r[x].top;
|
||||
rects[x].width = r[x].right - r[x].left;
|
||||
rects[x].height = r[x].bottom - r[x].top;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
x = 0;
|
||||
y = 0;
|
||||
for (i = 0; i < numRects; i++)
|
||||
{
|
||||
RFX_RECT* r = &rects[i];
|
||||
r->x = x;
|
||||
r->y = y;
|
||||
r->width = MIN(64, Width - x);
|
||||
r->height = MIN(64, Height - y);
|
||||
|
||||
if (x + 64 >= Width)
|
||||
{
|
||||
y += 64;
|
||||
x = 0;
|
||||
}
|
||||
else
|
||||
x += 64;
|
||||
}
|
||||
}
|
||||
s = progressive->buffer;
|
||||
Stream_SetPosition(s, 0);
|
||||
|
||||
progressive->rfx_context->mode = RLGR1;
|
||||
|
||||
x = 0;
|
||||
y = 0;
|
||||
for (i = 0; i < numRects; i++)
|
||||
{
|
||||
RFX_RECT* r = &rects[i];
|
||||
r->x = x;
|
||||
r->y = y;
|
||||
r->width = MIN(64, Width - x);
|
||||
r->height = MIN(64, Height - y);
|
||||
|
||||
if (x + 64 >= Width)
|
||||
{
|
||||
y += 64;
|
||||
x = 0;
|
||||
}
|
||||
else
|
||||
x += 64;
|
||||
}
|
||||
message = rfx_encode_message(progressive->rfx_context, rects, numRects, pSrcData, Width, Height,
|
||||
ScanLine);
|
||||
if (!message)
|
||||
|
@ -37,8 +37,8 @@
|
||||
|
||||
#include "rfx_decode.h"
|
||||
|
||||
static void rfx_decode_component(RFX_CONTEXT* context, const UINT32* quantization_values,
|
||||
const BYTE* data, int size, INT16* buffer)
|
||||
void rfx_decode_component(RFX_CONTEXT* context, const UINT32* quantization_values, const BYTE* data,
|
||||
int size, INT16* buffer)
|
||||
{
|
||||
INT16* dwt_buffer;
|
||||
dwt_buffer = BufferPool_Take(context->priv->BufferPool, -1); /* dwt_buffer */
|
||||
|
@ -26,5 +26,6 @@
|
||||
/* stride is bytes between rows in the output buffer. */
|
||||
FREERDP_LOCAL BOOL rfx_decode_rgb(RFX_CONTEXT* context, const RFX_TILE* tile, BYTE* rgb_buffer,
|
||||
UINT32 stride);
|
||||
|
||||
FREERDP_LOCAL void rfx_decode_component(RFX_CONTEXT* context, const UINT32* quantization_values,
|
||||
const BYTE* data, int size, INT16* buffer);
|
||||
#endif /* FREERDP_LIB_CODEC_RFX_DECODE_H */
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "rfx_dwt.h"
|
||||
|
||||
void rfx_dwt_2d_decode_block(INT16* buffer, INT16* idwt, int subband_width)
|
||||
static void rfx_dwt_2d_decode_block(INT16* buffer, INT16* idwt, int subband_width)
|
||||
{
|
||||
INT16 *dst, *l, *h;
|
||||
INT16 *l_dst, *h_dst;
|
||||
|
@ -23,7 +23,6 @@
|
||||
#include <freerdp/codec/rfx.h>
|
||||
#include <freerdp/api.h>
|
||||
|
||||
FREERDP_LOCAL void rfx_dwt_2d_decode_block(INT16* buffer, INT16* idwt, int subband_width);
|
||||
FREERDP_LOCAL void rfx_dwt_2d_decode(INT16* buffer, INT16* dwt_buffer);
|
||||
FREERDP_LOCAL void rfx_dwt_2d_encode(INT16* buffer, INT16* dwt_buffer);
|
||||
|
||||
|
@ -20,6 +20,8 @@ create_test_sourcelist(${MODULE_PREFIX}_SRCS
|
||||
${${MODULE_PREFIX}_DRIVER}
|
||||
${${MODULE_PREFIX}_TESTS})
|
||||
|
||||
add_definitions(-DCMAKE_CURRENT_SOURCE_DIR="${CMAKE_CURRENT_SOURCE_DIR}")
|
||||
add_definitions(-DCMAKE_CURRENT_BINARY_DIR="${CMAKE_CURRENT_BINARY_DIR}")
|
||||
add_executable(${MODULE_NAME} ${${MODULE_PREFIX}_SRCS})
|
||||
|
||||
target_link_libraries(${MODULE_NAME} freerdp winpr)
|
||||
|
@ -4,6 +4,7 @@
|
||||
#include <winpr/image.h>
|
||||
#include <winpr/print.h>
|
||||
#include <winpr/wlog.h>
|
||||
#include <winpr/image.h>
|
||||
#include <winpr/sysinfo.h>
|
||||
|
||||
#include <freerdp/codec/region.h>
|
||||
@ -267,7 +268,7 @@ static int test_image_fill_unused_quarters(BYTE* pDstData, int nDstStep, int nWi
|
||||
return 1;
|
||||
}
|
||||
|
||||
static BYTE* test_progressive_load_file(char* path, char* file, size_t* size)
|
||||
static BYTE* test_progressive_load_file(const char* path, const char* file, size_t* size)
|
||||
{
|
||||
FILE* fp;
|
||||
BYTE* buffer;
|
||||
@ -1017,30 +1018,141 @@ static int test_progressive_ms_sample(char* ms_sample_path)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static BOOL diff(BYTE a, BYTE b)
|
||||
{
|
||||
BYTE big = MAX(a, b);
|
||||
BYTE little = MIN(a, b);
|
||||
if (big - little <= 0x25)
|
||||
return TRUE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static BOOL colordiff(UINT32 format, UINT32 a, UINT32 b)
|
||||
{
|
||||
BYTE ar, ag, ab, aa;
|
||||
BYTE br, bg, bb, ba;
|
||||
SplitColor(a, format, &ar, &ag, &ab, &aa, NULL);
|
||||
SplitColor(b, format, &br, &bg, &bb, &ba, NULL);
|
||||
if (!diff(aa, ba) || !diff(ar, br) || !diff(ag, bg) || !diff(ab, bb))
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL test_encode_decode(const char* path)
|
||||
{
|
||||
int x, y;
|
||||
BOOL res = FALSE;
|
||||
int rc;
|
||||
BYTE* resultData = NULL;
|
||||
BYTE* dstData = NULL;
|
||||
UINT32 dstSize = 0;
|
||||
UINT32 ColorFormat = PIXEL_FORMAT_BGRX32;
|
||||
REGION16 invalidRegion = { 0 };
|
||||
wImage* image = winpr_image_new();
|
||||
wImage* dstImage = winpr_image_new();
|
||||
char* name = GetCombinedPath(path, "progressive.bmp");
|
||||
PROGRESSIVE_CONTEXT* progressiveEnc = progressive_context_new(TRUE);
|
||||
PROGRESSIVE_CONTEXT* progressiveDec = progressive_context_new(FALSE);
|
||||
|
||||
region16_init(&invalidRegion);
|
||||
if (!image || !dstImage || !name || !progressiveEnc || !progressiveDec)
|
||||
goto fail;
|
||||
|
||||
rc = winpr_image_read(image, name);
|
||||
if (rc <= 0)
|
||||
goto fail;
|
||||
|
||||
resultData = calloc(image->scanline, image->height);
|
||||
if (!resultData)
|
||||
goto fail;
|
||||
|
||||
// Progressive encode
|
||||
rc = progressive_compress(progressiveEnc, image->data, image->scanline * image->height,
|
||||
ColorFormat, image->width, image->height, image->scanline,
|
||||
&invalidRegion, &dstData, &dstSize);
|
||||
|
||||
// Progressive decode
|
||||
rc = progressive_create_surface_context(progressiveDec, 0, image->width, image->height);
|
||||
if (rc <= 0)
|
||||
goto fail;
|
||||
|
||||
rc = progressive_decompress(progressiveDec, dstData, dstSize, resultData, ColorFormat,
|
||||
image->scanline, 0, 0, &invalidRegion, 0);
|
||||
if (rc < 0)
|
||||
goto fail;
|
||||
|
||||
// Compare result
|
||||
if (0) // Dump result image for manual inspection
|
||||
{
|
||||
*dstImage = *image;
|
||||
dstImage->data = resultData;
|
||||
winpr_image_write(dstImage, "/tmp/test.bmp");
|
||||
}
|
||||
for (y = 0; y < image->height; y++)
|
||||
{
|
||||
const BYTE* orig = &image->data[y * image->scanline];
|
||||
const BYTE* dec = &resultData[y * image->scanline];
|
||||
for (x = 0; x < image->width; x++)
|
||||
{
|
||||
const BYTE* po = &orig[x * 4];
|
||||
const BYTE* pd = &dec[x * 4];
|
||||
|
||||
const DWORD a = ReadColor(po, ColorFormat);
|
||||
const DWORD b = ReadColor(pd, ColorFormat);
|
||||
if (!colordiff(ColorFormat, a, b))
|
||||
{
|
||||
printf("xxxxxxx [%u:%u] %08X != %08X\n", x, y, a, b);
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
}
|
||||
res = TRUE;
|
||||
fail:
|
||||
region16_uninit(&invalidRegion);
|
||||
progressive_context_free(progressiveEnc);
|
||||
progressive_context_free(progressiveDec);
|
||||
winpr_image_free(image, TRUE);
|
||||
winpr_image_free(dstImage, FALSE);
|
||||
free(resultData);
|
||||
free(name);
|
||||
return res;
|
||||
}
|
||||
|
||||
int TestFreeRDPCodecProgressive(int argc, char* argv[])
|
||||
{
|
||||
int rc = -1;
|
||||
char* ms_sample_path;
|
||||
char name[8192];
|
||||
SYSTEMTIME systemTime;
|
||||
WINPR_UNUSED(argc);
|
||||
WINPR_UNUSED(argv);
|
||||
|
||||
GetSystemTime(&systemTime);
|
||||
sprintf_s(name, sizeof(name),
|
||||
"EGFX_PROGRESSIVE_MS_SAMPLE-%04" PRIu16 "%02" PRIu16 "%02" PRIu16 "%02" PRIu16
|
||||
"%02" PRIu16 "%02" PRIu16 "%04" PRIu16,
|
||||
systemTime.wYear, systemTime.wMonth, systemTime.wDay, systemTime.wHour,
|
||||
systemTime.wMinute, systemTime.wSecond, systemTime.wMilliseconds);
|
||||
ms_sample_path = GetKnownSubPath(KNOWN_PATH_TEMP, name);
|
||||
ms_sample_path = _strdup(CMAKE_CURRENT_SOURCE_DIR);
|
||||
|
||||
if (!ms_sample_path)
|
||||
{
|
||||
printf("Memory allocation failed\n");
|
||||
return -1;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (PathFileExistsA(ms_sample_path))
|
||||
return test_progressive_ms_sample(ms_sample_path);
|
||||
{
|
||||
/*
|
||||
if (test_progressive_ms_sample(ms_sample_path) < 0)
|
||||
goto fail;
|
||||
*/
|
||||
if (!test_encode_decode(ms_sample_path))
|
||||
goto fail;
|
||||
rc = 0;
|
||||
}
|
||||
|
||||
fail:
|
||||
free(ms_sample_path);
|
||||
return 0;
|
||||
return rc;
|
||||
}
|
||||
|
BIN
libfreerdp/codec/test/progressive.bmp
Normal file
BIN
libfreerdp/codec/test/progressive.bmp
Normal file
Binary file not shown.
After Width: | Height: | Size: 3.3 MiB |
@ -39,8 +39,9 @@ static wHashTable* create_channel_ids_map()
|
||||
}
|
||||
|
||||
/* Proxy context initialization callback */
|
||||
static BOOL client_to_proxy_context_new(freerdp_peer* client, pServerContext* context)
|
||||
static BOOL client_to_proxy_context_new(freerdp_peer* client, rdpContext* ctx)
|
||||
{
|
||||
pServerContext* context = (pServerContext*)ctx;
|
||||
proxyServer* server = (proxyServer*)client->ContextExtra;
|
||||
proxyConfig* config = server->config;
|
||||
|
||||
@ -82,8 +83,9 @@ error:
|
||||
}
|
||||
|
||||
/* Proxy context free callback */
|
||||
static void client_to_proxy_context_free(freerdp_peer* client, pServerContext* context)
|
||||
static void client_to_proxy_context_free(freerdp_peer* client, rdpContext* ctx)
|
||||
{
|
||||
pServerContext* context = (pServerContext*)ctx;
|
||||
proxyServer* server;
|
||||
|
||||
if (!client || !context)
|
||||
@ -106,8 +108,8 @@ static void client_to_proxy_context_free(freerdp_peer* client, pServerContext* c
|
||||
BOOL pf_context_init_server_context(freerdp_peer* client)
|
||||
{
|
||||
client->ContextSize = sizeof(pServerContext);
|
||||
client->ContextNew = (psPeerContextNew)client_to_proxy_context_new;
|
||||
client->ContextFree = (psPeerContextFree)client_to_proxy_context_free;
|
||||
client->ContextNew = client_to_proxy_context_new;
|
||||
client->ContextFree = client_to_proxy_context_free;
|
||||
|
||||
return freerdp_peer_context_new(client);
|
||||
}
|
||||
|
@ -927,11 +927,11 @@ static BOOL shadow_client_send_surface_bits(rdpShadowClient* client, BYTE* pSrcD
|
||||
int nXSrc, int nYSrc, int nWidth, int nHeight)
|
||||
{
|
||||
BOOL ret = TRUE;
|
||||
int i;
|
||||
size_t i;
|
||||
BOOL first;
|
||||
BOOL last;
|
||||
wStream* s;
|
||||
int numMessages;
|
||||
size_t numMessages;
|
||||
UINT32 frameId = 0;
|
||||
rdpUpdate* update;
|
||||
rdpContext* context = (rdpContext*)client;
|
||||
|
Loading…
Reference in New Issue
Block a user