added brush cache bits for clients that support it

This commit is contained in:
jsorg71 2008-06-24 05:43:10 +00:00
parent 756fcef1c8
commit bfe555e3b6
10 changed files with 151 additions and 3 deletions

View File

@ -227,6 +227,9 @@
#define RDP_CAPSET_FONT 14
#define RDP_CAPLEN_FONT 0x04
#define RDP_CAPSET_BRUSHCACHE 15
#define RDP_CAPLEN_BRUSHCACHE 0x08
#define RDP_CAPSET_BITMAP_OFFSCREEN 18
#define RDP_CAPLEN_BITMAP_OFFSCREEN 0x08
@ -414,6 +417,7 @@
#define RDP_ORDER_FONTCACHE 3
#define RDP_ORDER_RAW_BMPCACHE2 4
#define RDP_ORDER_BMPCACHE2 5
#define RDP_ORDER_BRUSHCACHE 7
/* drawable types */
#define WND_TYPE_BITMAP 0

View File

@ -716,3 +716,14 @@ libxrdp_send_to_channel(struct xrdp_session* session, int channel_id,
free_stream(s);
return 0;
}
/*****************************************************************************/
int EXPORT_CC
libxrdp_orders_send_brush(struct xrdp_session* session,
int width, int height, int bpp, int type,
int size, char* data, int cache_id)
{
return xrdp_orders_send_brush((struct xrdp_orders*)session->orders,
width, height, bpp, type, size, data,
cache_id);
}

View File

@ -379,6 +379,9 @@ int APP_CC
xrdp_orders_send_bitmap2(struct xrdp_orders* self,
int width, int height, int bpp, char* data,
int cache_id, int cache_idx);
int APP_CC
xrdp_orders_send_brush(struct xrdp_orders* self, int width, int height,
int bpp, int type, int size, char* data, int cache_id);
/* xrdp_bitmap_compress.c */
int APP_CC

View File

@ -61,6 +61,8 @@ struct xrdp_client_info
int sound_code; /* 1 = leave sound at server */
int is_mce;
int rdp5_performanceflags;
int brush_cache_code; /* 0 = no cache 1 = 8x8 standard cache
2 = arbitrary dimensions */
};
struct xrdp_brush
@ -207,5 +209,9 @@ libxrdp_get_channel_id(struct xrdp_session* session, char* name);
int DEFAULT_CC
libxrdp_send_to_channel(struct xrdp_session* session, int channel_id,
char* data, int data_len);
int DEFAULT_CC
libxrdp_orders_send_brush(struct xrdp_session* session,
int width, int height, int bpp, int type,
int size, char* data, int cache_id);
#endif

View File

@ -1841,3 +1841,31 @@ height(%d)", lines_sending, height);
free_stream(temp_s);
return 0;
}
/*****************************************************************************/
/* returns error */
/* send a brush cache entry */
int APP_CC
xrdp_orders_send_brush(struct xrdp_orders* self, int width, int height,
int bpp, int type, int size, char* data, int cache_id)
{
int order_flags;
int len;
xrdp_orders_check(self, size + 12);
self->order_count++;
order_flags = RDP_ORDER_STANDARD | RDP_ORDER_SECONDARY;
out_uint8(self->out_s, order_flags);
len = (size + 6) - 7; /* length after type minus 7 */
out_uint16_le(self->out_s, len);
out_uint16_le(self->out_s, 0); /* flags */
out_uint8(self->out_s, RDP_ORDER_BRUSHCACHE); /* type */
out_uint8(self->out_s, cache_id);
out_uint8(self->out_s, bpp);
out_uint8(self->out_s, width);
out_uint8(self->out_s, height);
out_uint8(self->out_s, type);
out_uint8(self->out_s, size);
out_uint8a(self->out_s, data, size);
return 0;
}

View File

@ -695,6 +695,19 @@ xrdp_process_capset_pointercache(struct xrdp_rdp* self, struct stream* s,
return 0;
}
/*****************************************************************************/
/* get the type of client brush cache */
static int APP_CC
xrdp_process_capset_brushcache(struct xrdp_rdp* self, struct stream* s,
int len)
{
int code;
in_uint32_le(s, code);
self->client_info.brush_cache_code = code;
return 0;
}
/*****************************************************************************/
int APP_CC
xrdp_rdp_process_confirm_active(struct xrdp_rdp* self, struct stream* s)
@ -762,8 +775,8 @@ xrdp_rdp_process_confirm_active(struct xrdp_rdp* self, struct stream* s)
case 14: /* 14 */
DEBUG(("--14"));
break;
case 15: /* 15 */
DEBUG(("--15"));
case RDP_CAPSET_BRUSHCACHE: /* 15 */
xrdp_process_capset_brushcache(self, s, len);
break;
case 16: /* 16 */
DEBUG(("--16"));

View File

@ -72,6 +72,9 @@ int APP_CC
xrdp_cache_add_pointer_static(struct xrdp_cache* self,
struct xrdp_pointer_item* pointer_item,
int index);
int APP_CC
xrdp_cache_add_brush(struct xrdp_cache* self,
char* brush_item_data);
/* xrdp_wm.c */
struct xrdp_wm* APP_CC

View File

@ -486,3 +486,49 @@ xrdp_cache_add_pointer_static(struct xrdp_cache* self,
DEBUG(("adding pointer at %d", index));
return index;
}
/*****************************************************************************/
/* this does not take owership of brush_item_data, it makes a copy */
int APP_CC
xrdp_cache_add_brush(struct xrdp_cache* self,
char* brush_item_data)
{
int i;
int oldest;
int index;
if (self == 0)
{
return 0;
}
self->brush_stamp++;
/* look for match */
for (i = 0; i < 64; i++)
{
if (g_memcmp(self->brush_items[i].pattern,
brush_item_data, 8) == 0)
{
self->brush_items[i].stamp = self->brush_stamp;
DEBUG(("found brush at %d", i));
return i;
}
}
/* look for oldest */
index = 0;
oldest = 0x7fffffff;
for (i = 0; i < 64; i++)
{
if (self->brush_items[i].stamp < oldest)
{
oldest = self->brush_items[i].stamp;
index = i;
}
}
g_memcpy(self->brush_items[index].pattern,
brush_item_data, 8);
self->brush_items[index].stamp = self->brush_stamp;
libxrdp_orders_send_brush(self->session, 8, 8, 1, 0x81, 8,
self->brush_items[index].pattern, index);
DEBUG(("adding brush at %d", index));
return index;
}

View File

@ -229,6 +229,28 @@ xrdp_painter_text_height(struct xrdp_painter* self, char* text)
return rv;
}
/*****************************************************************************/
static int APP_CC
xrdp_painter_setup_brush(struct xrdp_painter* self,
struct xrdp_brush* out_brush,
struct xrdp_brush* in_brush)
{
int cache_id;
g_memcpy(out_brush, in_brush, sizeof(struct xrdp_brush));
if (in_brush->style == 3)
{
if (self->session->client_info->brush_cache_code == 1)
{
cache_id = xrdp_cache_add_brush(self->wm->cache, in_brush->pattern);
g_memset(out_brush->pattern, 0, 8);
out_brush->pattern[0] = cache_id;
out_brush->style = 0x81;
}
}
return 0;
}
/*****************************************************************************/
/* fill in an area of the screen with one color */
int APP_CC
@ -240,6 +262,7 @@ xrdp_painter_fill_rect(struct xrdp_painter* self,
struct xrdp_rect draw_rect;
struct xrdp_rect rect;
struct xrdp_region* region;
struct xrdp_brush brush;
int k;
int dx;
int dy;
@ -314,13 +337,14 @@ xrdp_painter_fill_rect(struct xrdp_painter* self,
break;
}
}
xrdp_painter_setup_brush(self, &brush, &self->brush);
while (xrdp_region_get_rect(region, k, &rect) == 0)
{
if (rect_intersect(&rect, &clip_rect, &draw_rect))
{
libxrdp_orders_pat_blt(self->session, x, y, cx, cy,
rop, self->bg_color, self->fg_color,
&self->brush, &draw_rect);
&brush, &draw_rect);
}
k++;
}

View File

@ -130,6 +130,14 @@ struct xrdp_pointer_item
char mask[32 * 32 / 8];
};
struct xrdp_brush_item
{
int stamp;
/* expand this to a structure to handle more complicated brushes
for now its 8x8 1bpp brushes only */
char pattern[8];
};
/* differnce caches */
struct xrdp_cache
{
@ -157,6 +165,8 @@ struct xrdp_cache
int pointer_stamp;
struct xrdp_pointer_item pointer_items[32];
int pointer_cache_entries;
int brush_stamp;
struct xrdp_brush_item brush_items[64];
};
struct xrdp_mm