libfreerdp-core: fix primary orders parsing

This commit is contained in:
Marc-André Moreau 2011-08-05 01:21:32 -04:00
parent 46126a7d24
commit 6f193a8dbf
12 changed files with 219 additions and 28 deletions

View File

@ -113,7 +113,7 @@ boolean df_pre_connect(freerdp* instance)
settings->order_support[NEG_MULTI_DRAWNINEGRID_INDEX] = False;
settings->order_support[NEG_LINETO_INDEX] = True;
settings->order_support[NEG_POLYLINE_INDEX] = True;
settings->order_support[NEG_MEMBLT_INDEX] = False;
settings->order_support[NEG_MEMBLT_INDEX] = True;
settings->order_support[NEG_MEM3BLT_INDEX] = False;
settings->order_support[NEG_SAVEBITMAP_INDEX] = False;
settings->order_support[NEG_GLYPH_INDEX_INDEX] = True;

View File

@ -23,6 +23,7 @@
#include "test_orders.h"
#include "libfreerdp-core/orders.h"
#include "libfreerdp-core/update.h"
ORDER_INFO* orderInfo;
@ -63,6 +64,8 @@ int add_orders_suite(void)
add_test_function(read_create_offscreen_bitmap_order);
add_test_function(read_switch_surface_order);
add_test_function(update_recv_orders);
return 0;
}
@ -729,3 +732,47 @@ void test_read_switch_surface_order(void)
CU_ASSERT(stream_get_length(s) == (sizeof(switch_surface_order) - 1));
}
int opaque_rect_count;
int polyline_count;
uint8 orders_update[] =
"\x00\x00\x33\xd0\x07\x00\x80\xba\x0d\x0a\x7f\x1e\x2c\x4d\x00\x36"
"\x02\xd3\x00\x47\x00\x4d\x00\xf0\x01\x87\x00\xc2\xdc\xff\x05\x7f"
"\x0f\x67\x01\x90\x01\x8e\x01\xa5\x01\x67\x01\x90\x01\x28\x00\x16"
"\x00\xf0\xf0\xf0\x15\x0f\xf0\x2d\x01\x19\xfe\x2d\x01\xec\xfd\x0d"
"\x16\x77\xf0\xff\xff\x01\x01\xa8\x01\x90\x01\x0d\xf0\xf0\xf0\x04"
"\x05\x66\x6b\x14\x15\x6c\x1d\x0a\x0f\xd0\x16\x64\x01\x15\xff\x50"
"\x03\x15\x0f\xf0\x65\x01\x15\xfe\x65\x01\xb0\xfd\x1d\x16\x01\xf0"
"\xff\xff\x01\x01\x7a";
void test_opaque_rect(rdpUpdate* update, OPAQUE_RECT_ORDER* opaque_rect)
{
opaque_rect_count++;
}
void test_polyline(rdpUpdate* update, POLYLINE_ORDER* polyline)
{
polyline_count++;
}
void test_update_recv_orders(void)
{
STREAM* s;
rdpUpdate* update;
s = stream_new(0);
update = update_new(NULL);
s->p = s->data = orders_update;
opaque_rect_count = 0;
polyline_count = 0;
update->OpaqueRect = test_opaque_rect;
update->Polyline = test_polyline;
update_recv(update, s);
CU_ASSERT(opaque_rect_count == 5);
CU_ASSERT(polyline_count == 2);
}

View File

@ -43,3 +43,6 @@ void test_read_cache_brush_order(void);
void test_read_create_offscreen_bitmap_order(void);
void test_read_switch_surface_order(void);
void test_update_recv_orders(void);

View File

@ -145,6 +145,15 @@ struct _DRAW_NINE_GRID_ORDER
};
typedef struct _DRAW_NINE_GRID_ORDER DRAW_NINE_GRID_ORDER;
struct _DELTA_RECT
{
sint16 left;
sint16 top;
sint16 width;
sint16 height;
};
typedef struct _DELTA_RECT DELTA_RECT;
struct _MULTI_DSTBLT_ORDER
{
sint16 nLeftRect;
@ -152,9 +161,9 @@ struct _MULTI_DSTBLT_ORDER
sint16 nWidth;
sint16 nHeight;
uint8 bRop;
uint8 nDeltaEntries;
uint8 numRectangles;
uint16 cbData;
uint8* codeDeltaList;
DELTA_RECT rectangles[45];
};
typedef struct _MULTI_DSTBLT_ORDER MULTI_DSTBLT_ORDER;
@ -172,9 +181,9 @@ struct _MULTI_PATBLT_ORDER
uint8 brushStyle;
uint8 brushHatch;
uint8 brushExtra[7];
uint8 nDeltaEntries;
uint8 numRectangles;
uint16 cbData;
uint8* codeDeltaList;
DELTA_RECT rectangles[45];
};
typedef struct _MULTI_PATBLT_ORDER MULTI_PATBLT_ORDER;
@ -187,21 +196,12 @@ struct _MULTI_SCRBLT_ORDER
uint8 bRop;
sint16 nXSrc;
sint16 nYSrc;
uint8 nDeltaEntries;
uint8 numRectangles;
uint16 cbData;
uint8* codeDeltaList;
DELTA_RECT rectangles[45];
};
typedef struct _MULTI_SCRBLT_ORDER MULTI_SCRBLT_ORDER;
struct _DELTA_RECT
{
sint16 left;
sint16 top;
sint16 width;
sint16 height;
};
typedef struct _DELTA_RECT DELTA_RECT;
struct _MULTI_OPAQUE_RECT_ORDER
{
sint16 nLeftRect;

View File

@ -20,6 +20,8 @@
set(FREERDP_CACHE_SRCS
offscreen.c
offscreen.h
color_table.c
color_table.h
cache.c
cache.h)

View File

@ -32,6 +32,7 @@ rdpCache* cache_new(rdpSettings* settings)
{
cache->settings = settings;
cache->offscreen = offscreen_new(settings);
cache->color_table = color_table_new(settings);
}
return cache;
@ -42,6 +43,7 @@ void cache_free(rdpCache* cache)
if (cache != NULL)
{
offscreen_free(cache->offscreen);
color_table_free(cache->color_table);
xfree(cache);
}
}

View File

@ -21,6 +21,7 @@
#define __CACHE_H
#include "offscreen.h"
#include "color_table.h"
#include <freerdp/types.h>
#include <freerdp/utils/stream.h>
@ -31,6 +32,7 @@ struct rdp_cache
{
rdpSettings* settings;
rdpOffscreen* offscreen;
rdpColorTable* color_table;
};
rdpCache* cache_new(rdpSettings* settings);

View File

@ -0,0 +1,81 @@
/**
* FreeRDP: A Remote Desktop Protocol Client
* Color Table Cache
*
* Copyright 2011 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <freerdp/utils/stream.h>
#include <freerdp/utils/memory.h>
#include "color_table.h"
void* color_table_get(rdpColorTable* color_table, uint8 index)
{
void* entry;
if (index > color_table->maxEntries)
{
printf("invalid color table bitmap index: 0x%04X\n", index);
return NULL;
}
entry = color_table->entries[index].color_table;
if (entry == NULL)
{
printf("invalid color table bitmap at index: 0x%04X\n", index);
return NULL;
}
return entry;
}
void color_table_put(rdpColorTable* color_table, uint8 index, void* entry)
{
if (index > color_table->maxEntries)
{
printf("invalid color table bitmap index: 0x%04X\n", index);
return;
}
color_table->entries[index].color_table = entry;
}
rdpColorTable* color_table_new(rdpSettings* settings)
{
rdpColorTable* color_table;
color_table = (rdpColorTable*) xzalloc(sizeof(rdpColorTable));
if (color_table != NULL)
{
color_table->settings = settings;
color_table->maxEntries = 6;
color_table->entries = (COLOR_TABLE_ENTRY*) xzalloc(sizeof(COLOR_TABLE_ENTRY) * color_table->maxEntries);
}
return color_table;
}
void color_table_free(rdpColorTable* color_table)
{
if (color_table != NULL)
{
xfree(color_table);
}
}

View File

@ -0,0 +1,46 @@
/**
* FreeRDP: A Remote Desktop Protocol Client
* Color Table Cache
*
* Copyright 2011 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef __COLOR_TABLE_CACHE_H
#define __COLOR_TABLE_CACHE_H
#include <freerdp/types.h>
#include <freerdp/utils/stream.h>
struct _COLOR_TABLE_ENTRY
{
void* color_table;
};
typedef struct _COLOR_TABLE_ENTRY COLOR_TABLE_ENTRY;
struct rdp_color_table
{
uint8 maxEntries;
rdpSettings* settings;
COLOR_TABLE_ENTRY* entries;
};
typedef struct rdp_color_table rdpColorTable;
void* color_table_get(rdpColorTable* color_table, uint8 index);
void color_table_put(rdpColorTable* color_table, uint8 index, void* entry);
rdpColorTable* color_table_new(rdpSettings* settings);
void color_table_free(rdpColorTable* color_table);
#endif /* __COLOR_TABLE_CACHE_H */

View File

@ -96,6 +96,7 @@ uint8 PRIMARY_DRAWING_ORDER_FIELD_BYTES[] =
LINE_TO_ORDER_FIELD_BYTES,
OPAQUE_RECT_ORDER_FIELD_BYTES,
SAVE_BITMAP_ORDER_FIELD_BYTES,
0,
MEMBLT_ORDER_FIELD_BYTES,
MEM3BLT_ORDER_FIELD_BYTES,
MULTI_DSTBLT_ORDER_FIELD_BYTES,
@ -106,6 +107,7 @@ uint8 PRIMARY_DRAWING_ORDER_FIELD_BYTES[] =
POLYGON_SC_ORDER_FIELD_BYTES,
POLYGON_CB_ORDER_FIELD_BYTES,
POLYLINE_ORDER_FIELD_BYTES,
0,
FAST_GLYPH_ORDER_FIELD_BYTES,
ELLIPSE_SC_ORDER_FIELD_BYTES,
ELLIPSE_CB_ORDER_FIELD_BYTES,
@ -463,24 +465,22 @@ void update_read_opaque_rect_order(STREAM* s, ORDER_INFO* orderInfo, OPAQUE_RECT
if (orderInfo->fieldFlags & ORDER_FIELD_04)
update_read_coord(s, &opaque_rect->nHeight, orderInfo->deltaCoordinates);
opaque_rect->color = 0;
if (orderInfo->fieldFlags & ORDER_FIELD_05)
{
stream_read_uint8(s, byte);
opaque_rect->color = byte;
opaque_rect->color = (opaque_rect->color & 0xFFFFFF00) | byte;
}
if (orderInfo->fieldFlags & ORDER_FIELD_06)
{
stream_read_uint8(s, byte);
opaque_rect->color |= (byte << 8);
opaque_rect->color = (opaque_rect->color & 0xFFFF00FF) | (byte << 8);
}
if (orderInfo->fieldFlags & ORDER_FIELD_07)
{
stream_read_uint8(s, byte);
opaque_rect->color |= (byte << 16);
opaque_rect->color = (opaque_rect->color & 0xFF00FFFF) | (byte << 16);
}
}
@ -520,12 +520,12 @@ void update_read_multi_dstblt_order(STREAM* s, ORDER_INFO* orderInfo, MULTI_DSTB
stream_read_uint8(s, multi_dstblt->bRop);
if (orderInfo->fieldFlags & ORDER_FIELD_06)
stream_read_uint8(s, multi_dstblt->nDeltaEntries);
stream_read_uint8(s, multi_dstblt->numRectangles);
if (orderInfo->fieldFlags & ORDER_FIELD_07)
{
stream_read_uint16(s, multi_dstblt->cbData);
stream_seek(s, multi_dstblt->cbData);
update_read_delta_rects(s, multi_dstblt->rectangles, multi_dstblt->numRectangles);
}
}
@ -568,12 +568,12 @@ void update_read_multi_patblt_order(STREAM* s, ORDER_INFO* orderInfo, MULTI_PATB
stream_read(s, multi_patblt->brushExtra, 7);
if (orderInfo->fieldFlags & ORDER_FIELD_13)
stream_read_uint8(s, multi_patblt->nDeltaEntries);
stream_read_uint8(s, multi_patblt->numRectangles);
if (orderInfo->fieldFlags & ORDER_FIELD_14)
{
stream_read_uint16(s, multi_patblt->cbData);
stream_seek(s, multi_patblt->cbData);
update_read_delta_rects(s, multi_patblt->rectangles, multi_patblt->numRectangles);
}
}
@ -601,12 +601,12 @@ void update_read_multi_scrblt_order(STREAM* s, ORDER_INFO* orderInfo, MULTI_SCRB
update_read_coord(s, &multi_scrblt->nYSrc, orderInfo->deltaCoordinates);
if (orderInfo->fieldFlags & ORDER_FIELD_08)
stream_read_uint8(s, multi_scrblt->nDeltaEntries);
stream_read_uint8(s, multi_scrblt->numRectangles);
if (orderInfo->fieldFlags & ORDER_FIELD_09)
{
stream_read_uint16(s, multi_scrblt->cbData);
stream_seek(s, multi_scrblt->cbData);
update_read_delta_rects(s, multi_scrblt->rectangles, multi_scrblt->numRectangles);
}
}

View File

@ -94,7 +94,7 @@ rdpSettings* settings_new()
settings->frame_marker = False;
settings->bitmap_cache_v3 = False;
settings->bitmap_cache = False;
settings->bitmap_cache = True;
settings->persistent_bitmap_cache = False;
settings->offscreen_bitmap_cache = False;

View File

@ -1291,6 +1291,12 @@ void gdi_switch_surface(rdpUpdate* update, SWITCH_SURFACE_ORDER* switch_surface)
}
}
void gdi_cache_color_table(rdpUpdate* update, CACHE_COLOR_TABLE_ORDER* cache_color_table)
{
GDI* gdi = GET_GDI(update);
color_table_put(gdi->cache->color_table, cache_color_table->cacheIndex, (void*) cache_color_table->colorTable);
}
/**
* Register GDI callbacks with libfreerdp-core.
* @param inst current instance
@ -1326,6 +1332,8 @@ void gdi_register_update_callbacks(rdpUpdate* update)
update->EllipseCB = NULL;
update->CreateOffscreenBitmap = gdi_create_offscreen_bitmap;
update->SwitchSurface = gdi_switch_surface;
update->CacheColorTable = gdi_cache_color_table;
}
/**