diff options
author | Jay Sorg <jay.sorg@gmail.com> | 2014-06-19 06:45:43 +0400 |
---|---|---|
committer | Jay Sorg <jay.sorg@gmail.com> | 2014-06-19 06:45:43 +0400 |
commit | b013ab51c8860e763a9f0a14201679b4c2eff54e (patch) | |
tree | 7cd3070377c119946149d094ef7dce2512a3df9e | |
parent | eb62dba2932023e3e324c78bd398fad79ef71b45 (diff) |
changes to 32 bpp decompression
-rw-r--r-- | client/X11/xf_graphics.c | 5 | ||||
-rw-r--r-- | include/freerdp/codec/bitmap.h | 12 | ||||
-rw-r--r-- | include/freerdp/freerdp.h | 1 | ||||
-rw-r--r-- | libfreerdp-codec/bitmap.c | 108 | ||||
-rw-r--r-- | libfreerdp-gdi/graphics.c | 6 |
5 files changed, 100 insertions, 32 deletions
diff --git a/client/X11/xf_graphics.c b/client/X11/xf_graphics.c index 64faafb..7d51390 100644 --- a/client/X11/xf_graphics.c +++ b/client/X11/xf_graphics.c @@ -144,6 +144,7 @@ void xf_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap, int xindex; xfInfo* xfi; tbool status; + bitmapExtra be; xfi = ((xfContext*)context)->xfi; /* 15 bpp bitmaps come in at 16 for v2 bitmap cache */ @@ -197,7 +198,9 @@ void xf_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap, default: if (compressed) { - status = bitmap_decompress(data, bitmap->data, width, height, length, bpp, bpp); + memset(&be, 0, sizeof(be)); + be.temp = context->temp; + status = bitmap_decompress_ex(data, bitmap->data, width, height, length, bpp, bpp, &be); if (status == false) { diff --git a/include/freerdp/codec/bitmap.h b/include/freerdp/codec/bitmap.h index 29f412f..4b20b1a 100644 --- a/include/freerdp/codec/bitmap.h +++ b/include/freerdp/codec/bitmap.h @@ -22,6 +22,18 @@ #include <freerdp/types.h> +struct bitmap_extra +{ + uint8* temp; + int flags; + int pad0; + int pad1; + int pad2; +}; + +typedef struct bitmap_extra bitmapExtra; + FREERDP_API tbool bitmap_decompress(uint8* srcData, uint8* dstData, int width, int height, int size, int srcBpp, int dstBpp); +FREERDP_API tbool bitmap_decompress_ex(uint8* srcData, uint8* dstData, int width, int height, int size, int srcBpp, int dstBpp, bitmapExtra* be); #endif /* __BITMAP_H */ diff --git a/include/freerdp/freerdp.h b/include/freerdp/freerdp.h index e81b360..3ac773c 100644 --- a/include/freerdp/freerdp.h +++ b/include/freerdp/freerdp.h @@ -73,6 +73,7 @@ struct rdp_context rdpChannels* channels; /* 36 */ rdpGraphics* graphics; /* 37 */ uint32 paddingC[64 - 38]; /* 38 */ + uint8 temp[32 * 1024]; }; struct rdp_freerdp diff --git a/libfreerdp-codec/bitmap.c b/libfreerdp-codec/bitmap.c index a26b081..7ea1958 100644 --- a/libfreerdp-codec/bitmap.c +++ b/libfreerdp-codec/bitmap.c @@ -275,7 +275,7 @@ static int process_rle_plane(uint8* in, int width, int height, uint8* out, int s indexh = 0; while (indexh < height) { - out = (org_out + width * height * 4) - ((indexh + 1) * width * 4); + out = org_out + indexh * width; color = 0; this_line = out; indexw = 0; @@ -296,14 +296,14 @@ static int process_rle_plane(uint8* in, int width, int height, uint8* out, int s { color = IN_UINT8_MV(in); *out = color; - out += 4; + out += 1; indexw++; collen--; } while (replen > 0) { *out = color; - out += 4; + out += 1; indexw++; replen--; } @@ -336,17 +336,17 @@ static int process_rle_plane(uint8* in, int width, int height, uint8* out, int s x = x >> 1; color = x; } - x = last_line[indexw * 4] + color; + x = last_line[indexw] + color; *out = x; - out += 4; + out += 1; indexw++; collen--; } while (replen > 0) { - x = last_line[indexw * 4] + color; + x = last_line[indexw] + color; *out = x; - out += 4; + out += 1; indexw++; replen--; } @@ -358,36 +358,51 @@ static int process_rle_plane(uint8* in, int width, int height, uint8* out, int s return (int) (in - org_in); } -/** - * process a raw color plane - */ -static int process_raw_plane(uint8* srcData, int width, int height, uint8* dstData, int size) +static int unsplit4(uint8* planes[], uint8* dstData, int width, int height) { - int x, y; + int index; + int jndex; + int pixel; + int offset; + int* dst32; - for (y = 0; y < height; y++) + offset = 0; + for (jndex = 0; jndex < height; jndex++) { - for (x = 0; x < width; x++) + dst32 = (int*) dstData; + dst32 += width * height; + dst32 -= (jndex + 1) * width; + for (index = 0; index < width; index++) { - dstData[(((height - y - 1) * width) + x) * 4] = srcData[((y * width) + x)]; + pixel = planes[0][offset] << 24; + pixel |= planes[1][offset] << 16; + pixel |= planes[2][offset] << 8; + pixel |= planes[3][offset] << 0; + *dst32 = pixel; + dst32++; + offset++; } } - - return (width * height); + return 0; } /** * 4 byte bitmap decompress * RDP6_BITMAP_STREAM */ -static tbool bitmap_decompress4(uint8* srcData, uint8* dstData, int width, int height, int size) +static tbool bitmap_decompress4(uint8* srcData, uint8* dstData, int width, int height, int size, uint8* temp) { int RLE; int code; int NoAlpha; int bytes_processed; int total_processed; + uint8* planes[4]; + planes[0] = temp; + planes[1] = planes[0] + width * height; + planes[2] = planes[1] + width * height; + planes[3] = planes[2] + width * height; code = IN_UINT8_MV(srcData); RLE = code & 0x10; @@ -396,38 +411,57 @@ static tbool bitmap_decompress4(uint8* srcData, uint8* dstData, int width, int h if (NoAlpha == 0) { - bytes_processed = process_rle_plane(srcData, width, height, dstData + 3, size - total_processed); - total_processed += bytes_processed; - srcData += bytes_processed; + if (RLE != 0) + { + bytes_processed = process_rle_plane(srcData, width, height, planes[0], size - total_processed); + total_processed += bytes_processed; + srcData += bytes_processed; + } + else + { + planes[0] = srcData; + bytes_processed = width * height; + total_processed += bytes_processed; + srcData += bytes_processed; + } + } + else + { + memset(planes[0], 0xff, width * height); } if (RLE != 0) { - bytes_processed = process_rle_plane(srcData, width, height, dstData + 2, size - total_processed); + bytes_processed = process_rle_plane(srcData, width, height, planes[1], size - total_processed); total_processed += bytes_processed; srcData += bytes_processed; - bytes_processed = process_rle_plane(srcData, width, height, dstData + 1, size - total_processed); + bytes_processed = process_rle_plane(srcData, width, height, planes[2], size - total_processed); total_processed += bytes_processed; srcData += bytes_processed; - bytes_processed = process_rle_plane(srcData, width, height, dstData + 0, size - total_processed); + bytes_processed = process_rle_plane(srcData, width, height, planes[3], size - total_processed); total_processed += bytes_processed; } else { - bytes_processed = process_raw_plane(srcData, width, height, dstData + 2, size - total_processed); + planes[1] = srcData; + bytes_processed = width * height; total_processed += bytes_processed; srcData += bytes_processed; - bytes_processed = process_raw_plane(srcData, width, height, dstData + 1, size - total_processed); + planes[2] = srcData; + bytes_processed = width * height; total_processed += bytes_processed; srcData += bytes_processed; - bytes_processed = process_raw_plane(srcData, width, height, dstData + 0, size - total_processed); + planes[3] = srcData; + bytes_processed = width * height; total_processed += bytes_processed + 1; } + unsplit4(planes, dstData, width, height); + return (size == total_processed) ? true : false; } @@ -580,7 +614,7 @@ int save_bitmap(uint8* data, int width, int height, int bpp) /** * bitmap decompression routine */ -tbool bitmap_decompress(uint8* srcData, uint8* dstData, int width, int height, int size, int srcBpp, int dstBpp) +tbool bitmap_decompress_ex(uint8* srcData, uint8* dstData, int width, int height, int size, int srcBpp, int dstBpp, bitmapExtra* be) { if (srcBpp == 16 && dstBpp == 16) { @@ -591,7 +625,7 @@ tbool bitmap_decompress(uint8* srcData, uint8* dstData, int width, int height, i } else if (srcBpp == 32 && dstBpp == 32) { - if (!bitmap_decompress4(srcData, dstData, width, height, size)) + if (!bitmap_decompress4(srcData, dstData, width, height, size, be->temp)) return false; } else if (srcBpp == 15 && dstBpp == 15) @@ -616,3 +650,19 @@ tbool bitmap_decompress(uint8* srcData, uint8* dstData, int width, int height, i return true; } + +/** + * bitmap decompression routine + * do not use, for compatability + */ +tbool bitmap_decompress(uint8* srcData, uint8* dstData, int width, int height, int size, int srcBpp, int dstBpp) +{ + tbool rv; + struct bitmap_extra be; + + memset(&be, 0, sizeof(be)); + be.temp = (uint8*) xmalloc(32 * 1024); + rv = bitmap_decompress_ex(srcData, dstData, width, height, size, srcBpp, dstBpp, &be); + xfree(be.temp); + return rv; +} diff --git a/libfreerdp-gdi/graphics.c b/libfreerdp-gdi/graphics.c index 9dd41b8..adb8eda 100644 --- a/libfreerdp-gdi/graphics.c +++ b/libfreerdp-gdi/graphics.c @@ -105,6 +105,7 @@ void gdi_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap, int xindex; rdpGdi* gdi; tbool status; + bitmapExtra be; size = width * height * (bpp + 7) / 8; @@ -152,8 +153,9 @@ void gdi_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap, default: if (compressed) { - status = bitmap_decompress(data, bitmap->data, width, height, length, bpp, bpp); - + memset(&be, 0, sizeof(be)); + be.temp = context->temp; + status = bitmap_decompress_ex(data, bitmap->data, width, height, length, bpp, bpp, &be); if (status == false) { printf("gdi_Bitmap_Decompress: Bitmap Decompression Failed\n"); |