/[rdesktop]/sourceforge.net/trunk/rdesktop/uiports/svgawin.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Annotation of /sourceforge.net/trunk/rdesktop/uiports/svgawin.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 849 - (hide annotations)
Sun Mar 13 03:45:27 2005 UTC (19 years, 3 months ago) by jsorg71
File MIME type: text/plain
File size: 47446 byte(s)
some new orders

1 jsorg71 735 /* -*- c-basic-offset: 8 -*-
2     rdesktop: A Remote Desktop Protocol client.
3     User interface services - SVGA lib
4 jsorg71 849 Copyright (C) Jay Sorg 2004-2005
5 jsorg71 735
6     This program is free software; you can redistribute it and/or modify
7     it under the terms of the GNU General Public License as published by
8     the Free Software Foundation; either version 2 of the License, or
9     (at your option) any later version.
10    
11     This program is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14     GNU General Public License for more details.
15    
16     You should have received a copy of the GNU General Public License
17     along with this program; if not, write to the Free Software
18     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19     */
20    
21     #include "../rdesktop.h"
22    
23     #include <vga.h>
24     #include <vgakeyboard.h>
25     #include <vgamouse.h>
26     #include <vgagl.h>
27    
28     #include <unistd.h> // gethostname
29     #include <pwd.h> // getpwuid
30     #include <stdarg.h> // va_list va_start va_end
31    
32 jsorg71 811 #include <sys/ioctl.h>
33     #include <linux/keyboard.h>
34     #include <linux/kd.h>
35     #include <fcntl.h>
36    
37 jsorg71 735 extern int g_tcp_port_rdp;
38     int g_use_rdp5 = 0;
39     char g_hostname[16] = "";
40     char g_username[64] = "";
41     int g_height = 600;
42     int g_width = 800;
43     int g_server_bpp = 8;
44     int g_encryption = 1;
45 jsorg71 849 int g_desktop_save = 1;
46     int g_polygon_ellipse_orders = 0;
47 jsorg71 735 int g_bitmap_cache = 1;
48     int g_bitmap_cache_persist_enable = False;
49     int g_bitmap_cache_precache = True;
50     int g_bitmap_compression = 1;
51     int g_rdp5_performanceflags = 0;
52     int g_console_session = 0;
53     int g_keylayout = 0x409; /* Defaults to US keyboard layout */
54    
55     /* hack globals */
56     int g_argc = 0;
57     char** g_argv = 0;
58     int UpAndRunning = 0;
59     int g_sock = 0;
60     int deactivated = 0;
61     uint32 ext_disc_reason = 0;
62     char g_servername[128] = "";
63     static uint32* colmap = 0;
64     static uint8* desk_save = 0;
65     static int g_server_Bpp = 1;
66    
67 jsorg71 811 /* Keyboard LEDS */
68     static int numlock;
69     static int capslock;
70     static int scrolllock;
71    
72 jsorg71 735 // this is non null if vgalib has non accel functions available
73     // reading from video memory is sooo slow
74     static uint8* sdata = 0;
75     static int g_save_mem = 0; // for video memory use eg sdata == 0
76    
77     // video acceleration
78     static int use_accel = 1;
79     static int has_fill_box = 0;
80     static int has_screen_copy = 0;
81     static int has_put_image = 0;
82    
83     // clip
84     int clip_startx;
85     int clip_starty;
86     int clip_endx;
87     int clip_endy;
88    
89     // mouse
90     uint8 mouse_under[32 * 32 * 4]; // save area under mouse
91     int mousex = 0;
92     int mousey = 0;
93     int mouseb = 0;
94    
95     // mouse info
96     typedef struct
97     {
98     uint8 andmask[32 * 32];
99     uint8 xormask[32 * 32];
100     int x;
101     int y;
102     int w;
103     int h;
104     } tcursor;
105    
106     // mouse global
107     static tcursor mcursor;
108    
109     static int g_draw_mouse = 1;
110    
111     // bitmap
112     typedef struct
113     {
114     int width;
115     int height;
116     uint8* data;
117     uint8 Bpp;
118     } bitmap;
119    
120     typedef struct
121     {
122     int x;
123     int y;
124     int cx;
125     int cy;
126     void* prev;
127     void* next;
128     } myrect;
129    
130     myrect* head_rect = 0;
131    
132 jsorg71 849 //*****************************************************************************
133 jsorg71 811 // Keyboard stuff - PeterS
134     static void setled(int mask, int state)
135     {
136     int fd;
137     long int leds;
138 jsorg71 849
139 jsorg71 811 if (( fd=open("/dev/console", O_NOCTTY)) != -1 )
140     {
141     if (ioctl (fd, KDGETLED, &leds) != -1)
142     {
143     leds &= 7;
144     if (state)
145     leds |= mask;
146     else
147 jsorg71 849 leds &= ~mask;
148     ioctl (fd, KDSETLED, leds);
149 jsorg71 811 }
150     close(fd);
151     }
152     }
153    
154    
155 jsorg71 735 //*****************************************************************************
156     // do a raster op
157     int rop(int rop, int src, int dst)
158     {
159     switch (rop)
160     {
161     case 0x0: return 0;
162     case 0x1: return ~(src | dst);
163     case 0x2: return (~src) & dst;
164     case 0x3: return ~src;
165     case 0x4: return src & (~dst);
166     case 0x5: return ~(dst);
167     case 0x6: return src ^ dst;
168     case 0x7: return ~(src & dst);
169     case 0x8: return src & dst;
170     case 0x9: return ~(src) ^ dst;
171     case 0xa: return dst;
172     case 0xb: return (~src) | dst;
173     case 0xc: return src;
174     case 0xd: return src | (~dst);
175     case 0xe: return src | dst;
176     case 0xf: return ~0;
177     }
178     return dst;
179     }
180    
181     //*****************************************************************************
182     // get a screen pixel
183     int get_pixel(int x, int y)
184     {
185     if (x >= 0 && x < g_width && y >= 0 && y < g_height)
186     {
187     if (sdata != 0)
188     {
189     if (g_server_Bpp == 1)
190     return sdata[y * g_width + x];
191     else if (g_server_Bpp == 2)
192     return ((uint16*)sdata)[y * g_width + x];
193     else
194     return 0;
195     }
196     else
197     return vga_getpixel(x, y);
198     }
199     else
200     return 0;
201     }
202    
203     //*****************************************************************************
204     // set a screen pixel
205     void set_pixel(int x, int y, int pixel, int op)
206     {
207     if (x >= clip_startx && x < clip_endx && y >= clip_starty && y < clip_endy)
208     {
209     if (x >= 0 && x < g_width && y >= 0 && y < g_height)
210     {
211     if (op == 0x0)
212     pixel = 0;
213     else if (op == 0xf)
214     pixel = -1;
215     else if (op != 0xc)
216     pixel = rop(op, pixel, get_pixel(x, y));
217     if (sdata != 0)
218     {
219     if (g_server_Bpp == 1)
220     sdata[y * g_width + x] = pixel;
221     else if (g_server_Bpp == 2)
222     ((uint16*)sdata)[y * g_width + x] = pixel;
223     }
224     else
225     {
226     vga_setcolor(pixel);
227     vga_drawpixel(x, y);
228     }
229     }
230     }
231     }
232    
233     //*****************************************************************************
234     // get a pixel from a bitmap
235     int get_pixel2(int x, int y, uint8* data, int width, int bpp)
236     {
237     if (bpp == 8)
238     return data[y * width + x];
239     else if (bpp == 16)
240     return ((uint16*)data)[y * width + x];
241     else
242     return 0;
243     }
244    
245     //*****************************************************************************
246     // set a pixel in a bitmap
247     void set_pixel2(int x, int y, int pixel, uint8* data, int width, int bpp)
248     {
249     if (bpp == 8)
250     data[y * width + x] = pixel;
251     else if (bpp == 16)
252     ((uint16*)data)[y * width + x] = pixel;
253     }
254    
255     //*****************************************************************************
256     // get a pointer into a bitmap
257     uint8* get_ptr(int x, int y, uint8* data, int width, int bpp)
258     {
259     if (bpp == 8)
260     return data + (y * width + x);
261     else if (bpp == 16)
262     return data + (y * width + x) * 2;
263     else
264     return 0;
265     }
266    
267     //*****************************************************************************
268     // check if a certain pixel is set in a bitmap
269     BOOL is_pixel_on(uint8* data, int x, int y, int width, int bpp)
270     {
271     int start;
272     int shift;
273    
274     if (bpp == 1)
275     {
276     width = (width + 7) / 8;
277     start = (y * width) + x / 8;
278     shift = x % 8;
279     return (data[start] & (0x80 >> shift)) != 0;
280     }
281     else if (bpp == 8)
282     {
283     return data[y * width + x] != 0;
284     }
285     else if (bpp == 24)
286     {
287     return data[(y * 3) * width + (x * 3)] != 0 &&
288     data[(y * 3) * width + (x * 3) + 1] != 0 &&
289     data[(y * 3) * width + (x * 3) + 2] != 0;
290     }
291     else
292     return False;
293     }
294    
295     //*****************************************************************************
296     void set_pixel_on(uint8* data, int x, int y, int width, int bpp, int pixel)
297     {
298     if (bpp == 8)
299     {
300     data[y * width + x] = pixel;
301     }
302     }
303    
304     /*****************************************************************************/
305     int warp_coords(int* x, int* y, int* cx, int* cy, int* srcx, int* srcy)
306     {
307     int dx;
308     int dy;
309     // int lx = *x, ly = *y, lcx = *cx, lcy = *cy;
310    
311     if (clip_startx > *x)
312     dx = clip_startx - *x;
313     else
314     dx = 0;
315     if (clip_starty > *y)
316     dy = clip_starty - *y;
317     else
318     dy = 0;
319     if (*x + *cx > clip_endx)
320     *cx = (*cx - ((*x + *cx) - clip_endx)) /*+ 1*/;
321     if (*y + *cy > clip_endy)
322     *cy = (*cy - ((*y + *cy) - clip_endy)) /*+ 1*/;
323     *cx = *cx - dx;
324     *cy = *cy - dy;
325     if (*cx <= 0)
326     return False;
327     if (*cy <= 0)
328     return False;
329     *x = *x + dx;
330     *y = *y + dy;
331     if (srcx != NULL)
332     *srcx = *srcx + dx;
333     if (srcy != NULL)
334     *srcy = *srcy + dy;
335    
336     // if (*x != lx || *y != ly || *cx != lcx || *cy != lcy)
337     // printf("%d %d %d %d to %d %d %d %d\n", lx, ly, lcx, lcy, *x, *y, *cx, *cy);
338    
339     return True;
340     }
341    
342     //*****************************************************************************
343     void copy_mem(uint8* d, uint8* s, int n)
344     {
345     while (n & (~7))
346     {
347     *(d++) = *(s++);
348     *(d++) = *(s++);
349     *(d++) = *(s++);
350     *(d++) = *(s++);
351     *(d++) = *(s++);
352     *(d++) = *(s++);
353     *(d++) = *(s++);
354     *(d++) = *(s++);
355     n = n - 8;
356     }
357     while (n > 0)
358     {
359     *(d++) = *(s++);
360     n--;
361     }
362     }
363    
364     //*****************************************************************************
365     void copy_memb(uint8* d, uint8* s, int n)
366     {
367     d = (d + n) - 1;
368     s = (s + n) - 1;
369     while (n & (~7))
370     {
371     *(d--) = *(s--);
372     *(d--) = *(s--);
373     *(d--) = *(s--);
374     *(d--) = *(s--);
375     *(d--) = *(s--);
376     *(d--) = *(s--);
377     *(d--) = *(s--);
378     *(d--) = *(s--);
379     n = n - 8;
380     }
381     while (n > 0)
382     {
383     *(d--) = *(s--);
384     n--;
385     }
386     }
387    
388     //*****************************************************************************
389     // all in pixel except line_size is in bytes
390     void accel_draw_box(int x, int y, int cx, int cy, uint8* data, int line_size)
391     {
392     int i;
393     uint8* s;
394     uint8* d;
395    
396     if (sdata != 0)
397     {
398     s = data;
399     d = get_ptr(x, y, sdata, g_width, g_server_bpp);
400     for (i = 0; i < cy; i++)
401     {
402     copy_mem(d, s, cx * g_server_Bpp);
403     s = s + line_size;
404     d = d + g_width * g_server_Bpp;
405     }
406     }
407     else if (has_put_image && line_size == cx * g_server_Bpp)
408     {
409     vga_accel(ACCEL_PUTIMAGE, x, y, cx, cy, data);
410     }
411     else
412     {
413     s = data;
414     for (i = 0; i < cy; i++)
415     {
416     vga_drawscansegment(s, x, y + i, cx * g_server_Bpp);
417     s = s + line_size;
418     }
419     }
420     }
421    
422     //*****************************************************************************
423     void accel_fill_rect(int x, int y, int cx, int cy, int color)
424     {
425     int i;
426     uint8* temp;
427     uint8* d;
428    
429     if (sdata != 0)
430     {
431     temp = xmalloc(cx * g_server_Bpp);
432     if (g_server_Bpp == 1)
433     for (i = 0; i < cx; i++)
434     temp[i] = color;
435     else if (g_server_Bpp == 2)
436     for (i = 0; i < cx; i++)
437     ((uint16*)temp)[i] = color;
438     d = get_ptr(x, y, sdata, g_width, g_server_bpp);
439     for (i = 0; i < cy; i++)
440     {
441     copy_mem(d, temp, cx * g_server_Bpp);
442     d = d + g_width * g_server_Bpp;
443     }
444     xfree(temp);
445     }
446     else if (has_fill_box)
447     {
448     vga_accel(ACCEL_SETFGCOLOR, color);
449     vga_accel(ACCEL_FILLBOX, x, y, cx, cy);
450     }
451     else
452     {
453     temp = xmalloc(cx * g_server_Bpp);
454     if (g_server_Bpp == 1)
455     for (i = 0; i < cx; i++)
456     temp[i] = color;
457     else if (g_server_Bpp == 2)
458     for (i = 0; i < cx; i++)
459     ((uint16*)temp)[i] = color;
460     for (i = 0; i < cy; i++)
461     vga_drawscansegment(temp, x, y + i, cx * g_server_Bpp);
462     xfree(temp);
463     }
464     }
465    
466     //*****************************************************************************
467     void accel_screen_copy(int x, int y, int cx, int cy, int srcx, int srcy)
468     {
469     uint8* temp;
470     uint8* s;
471     uint8* d;
472     int i;
473    
474     if (sdata != 0)
475     {
476     if (srcy < y)
477     { // bottom to top
478     s = get_ptr(srcx, (srcy + cy) - 1, sdata, g_width, g_server_bpp);
479     d = get_ptr(x, (y + cy) - 1, sdata, g_width, g_server_bpp);
480     for (i = 0; i < cy; i++) // copy down
481     {
482     copy_mem(d, s, cx * g_server_Bpp);
483     s = s - g_width * g_server_Bpp;
484     d = d - g_width * g_server_Bpp;
485     }
486     }
487     else if (srcy > y || srcx > x) // copy up or left
488     { // top to bottom
489     s = get_ptr(srcx, srcy, sdata, g_width, g_server_bpp);
490     d = get_ptr(x, y, sdata, g_width, g_server_bpp);
491     for (i = 0; i < cy; i++)
492     {
493     copy_mem(d, s, cx * g_server_Bpp);
494     s = s + g_width * g_server_Bpp;
495     d = d + g_width * g_server_Bpp;
496     }
497     }
498     else // copy straight right
499     {
500     s = get_ptr(srcx, srcy, sdata, g_width, g_server_bpp);
501     d = get_ptr(x, y, sdata, g_width, g_server_bpp);
502     for (i = 0; i < cy; i++)
503     {
504     copy_memb(d, s, cx * g_server_Bpp);
505     s = s + g_width * g_server_Bpp;
506     d = d + g_width * g_server_Bpp;
507     }
508     }
509     }
510     else if (has_screen_copy)
511     {
512     vga_accel(ACCEL_SCREENCOPY, srcx, srcy, x, y, cx, cy);
513     }
514     else
515     {
516     // slow
517     temp = (uint8*)xmalloc(cx * cy * g_server_Bpp);
518     for (i = 0; i < cy; i++)
519     vga_getscansegment(get_ptr(0, i, temp, cx, g_server_bpp), srcx, srcy + i, cx * g_server_Bpp);
520     for (i = 0; i < cy; i++)
521     vga_drawscansegment(get_ptr(0, i, temp, cx, g_server_bpp), x, y + i, cx * g_server_Bpp);
522     xfree(temp);
523     }
524     }
525    
526     //*****************************************************************************
527     // return bool
528     int contains_mouse(int x, int y, int cx, int cy)
529     {
530     if (mousex + 32 >= x &&
531     mousey + 32 >= y &&
532     mousex <= x + cx &&
533     mousey <= y + cy)
534     return 1;
535     else
536     return 0;
537     }
538    
539     //*****************************************************************************
540     void fill_rect(int x, int y, int cx, int cy, int colour, int opcode)
541     {
542     int i;
543     int j;
544    
545     if (warp_coords(&x, &y, &cx, &cy, NULL, NULL))
546     {
547     if (opcode == 0xc)
548     accel_fill_rect(x, y, cx, cy, colour);
549     else if (opcode == 0xf)
550     accel_fill_rect(x, y, cx, cy, -1);
551     else if (opcode == 0x0)
552     accel_fill_rect(x, y, cx, cy, 0);
553     else
554     {
555     for (i = 0; i < cy; i++)
556     for (j = 0; j < cx; j++)
557     set_pixel(x + j, y + i, colour, opcode);
558     }
559     }
560     }
561    
562     //*****************************************************************************
563     void get_rect(int x, int y, int cx, int cy, uint8* p)
564     {
565     int i;
566    
567     if (x < 0)
568     {
569     cx = cx + x;
570     x = 0;
571     }
572     if (y < 0)
573     {
574     cy = cy + y;
575     y = 0;
576     }
577     if (sdata != 0)
578     {
579     for (i = 0; i < cy; i++)
580     {
581     copy_mem(p, get_ptr(x, y + i, sdata, g_width, g_server_bpp), cx * g_server_Bpp);
582     p = p + cx * g_server_Bpp;
583     }
584     }
585     else
586     {
587     for (i = 0; i < cy; i++)
588     {
589     vga_getscansegment(p, x, y + i, cx * g_server_Bpp);
590     p = p + cx * g_server_Bpp;
591     }
592     }
593     }
594    
595     /*****************************************************************************/
596     // return true if r1 is contained by r2
597     int is_contained_by(myrect* r1, myrect* r2)
598     {
599     if (r1->x >= r2->x &&
600     r1->y >= r2->y &&
601     r1->x + r1->cx <= r2->x + r2->cx &&
602     r1->y + r1->cy <= r2->y + r2->cy)
603     return 1;
604     else
605     return 0;
606     }
607    
608     /*****************************************************************************/
609     void draw_cursor_under(int ox, int oy)
610     {
611     int i;
612     int j;
613     int k;
614     uint8* ptr;
615     int len;
616    
617     if (ox < 0)
618     k = -ox;
619     else
620     k = 0;
621     j = g_width - ox;
622     if (j > 32)
623     j = 32;
624     if (j > 0)
625     {
626     for (i = 0; i < 32; i++)
627     {
628     ptr = get_ptr(k, i, mouse_under, 32, g_server_bpp);
629     len = (j - k) * g_server_Bpp;
630     if (ox + k >= 0 && oy + i >= 0 && ox + k < g_width && oy + i < g_height)
631     vga_drawscansegment(ptr, ox + k, oy + i, len);
632     }
633     }
634     g_draw_mouse = 1;
635     }
636    
637     /*****************************************************************************/
638     void draw_cursor(void)
639     {
640     int i;
641     int j;
642     int k;
643     int pixel;
644     uint8 mouse_a[32 * 32 * 4];
645     uint8* ptr;
646     int len;
647    
648     if (!g_draw_mouse)
649     return;
650     memset(mouse_under, 0, sizeof(mouse_under));
651     for (i = 0; i < 32; i++)
652     {
653     for (j = 0; j < 32; j++)
654     {
655     pixel = get_pixel(mousex + j, mousey + i);
656     set_pixel2(j, i, pixel, mouse_under, 32, g_server_bpp);
657     if (mcursor.andmask[i * 32 + j] == 0)
658     k = 0;
659     else
660     k = ~0;
661     pixel = rop(0x8, k, pixel);
662     if (mcursor.xormask[i * 32 + j] == 0)
663     k = 0;
664     else
665     k = ~0;
666     pixel = rop(0x6, k, pixel);
667     set_pixel2(j, i, pixel, mouse_a, 32, g_server_bpp);
668     }
669     }
670     if (mousex < 0)
671     k = -mousex;
672     else
673     k = 0;
674     j = g_width - mousex;
675     if (j > 32)
676     j = 32;
677     if (j > 0)
678     {
679     for (i = mousey; i < mousey + 32; i++)
680     if (i < g_height && i >= 0)
681     {
682     ptr = get_ptr(k, i - mousey, mouse_a, 32, g_server_bpp);
683     len = (j - k) * g_server_Bpp;
684     vga_drawscansegment(ptr, mousex + k, i, len);
685     }
686     }
687     g_draw_mouse = 0;
688     }
689    
690     /*****************************************************************************/
691     // add a rect to cache
692     void cache_rect(int x, int y, int cx, int cy, int do_warp)
693     {
694     myrect* rect;
695     myrect* walk_rect;
696    
697     if (sdata == 0)
698     {
699     draw_cursor();
700     return;
701     }
702     if (do_warp)
703     if (!warp_coords(&x, &y, &cx, &cy, NULL, NULL))
704     return;
705     rect = (myrect*)xmalloc(sizeof(myrect));
706     rect->x = x;
707     rect->y = y;
708     rect->cx = cx;
709     rect->cy = cy;
710     rect->next = 0;
711     rect->prev = 0;
712     if (head_rect == 0)
713     head_rect = rect;
714     else
715     {
716     walk_rect = 0;
717     do
718     {
719     if (walk_rect == 0)
720     walk_rect = head_rect;
721     else
722     walk_rect = walk_rect->next;
723     if (is_contained_by(rect, walk_rect))
724     {
725     xfree(rect);
726     return;
727     }
728     }
729     while (walk_rect->next != 0);
730     walk_rect->next = rect;
731     rect->prev = walk_rect;
732     }
733     }
734    
735     //*****************************************************************************
736     void draw_cache_rects(void)
737     {
738     int i;
739     myrect* rect;
740     myrect* rect1;
741     uint8* p;
742    
743     // draw all the rects
744     rect = head_rect;
745     while (rect != 0)
746     {
747     p = get_ptr(rect->x, rect->y, sdata, g_width, g_server_bpp);
748     for (i = 0; i < rect->cy; i++)
749     {
750     vga_drawscansegment(p, rect->x, rect->y + i, rect->cx * g_server_Bpp);
751     p = p + g_width * g_server_Bpp;
752     }
753     rect1 = rect;
754     rect = rect->next;
755     xfree(rect1);
756     }
757     head_rect = 0;
758     }
759    
760     /*****************************************************************************/
761     void key_event(int scancode, int pressed)
762     {
763     int rdpkey;
764     int ext;
765    
766     if (!UpAndRunning)
767     return;
768     rdpkey = scancode;
769     ext = 0;
770 jsorg71 811
771     // Keyboard LEDS
772     if ((scancode == SCANCODE_CAPSLOCK) && pressed)
773     {
774     capslock = !capslock;
775     setled(LED_CAP, capslock);
776     }
777     if ((scancode == SCANCODE_SCROLLLOCK) && pressed)
778     {
779     scrolllock = !scrolllock;
780     setled(LED_SCR, scrolllock);
781     }
782    
783     if ((scancode == SCANCODE_NUMLOCK) && pressed)
784     {
785     numlock = !numlock;
786     setled(LED_NUM, numlock);
787     }
788    
789 jsorg71 735 switch (scancode)
790     {
791     case SCANCODE_CURSORBLOCKUP: rdpkey = 0xc8; ext = KBD_FLAG_EXT; break; // up arrow
792     case SCANCODE_CURSORBLOCKDOWN: rdpkey = 0xd0; ext = KBD_FLAG_EXT; break; // down arrow
793     case SCANCODE_CURSORBLOCKRIGHT: rdpkey = 0xcd; ext = KBD_FLAG_EXT; break; // right arrow
794     case SCANCODE_CURSORBLOCKLEFT: rdpkey = 0xcb; ext = KBD_FLAG_EXT; break; // left arrow
795     case SCANCODE_PAGEDOWN: rdpkey = 0xd1; ext = KBD_FLAG_EXT; break; // page down
796     case SCANCODE_PAGEUP: rdpkey = 0xc9; ext = KBD_FLAG_EXT; break; // page up
797     case SCANCODE_HOME: rdpkey = 0xc7; ext = KBD_FLAG_EXT; break; // home
798     case SCANCODE_END: rdpkey = 0xcf; ext = KBD_FLAG_EXT; break; // end
799     case SCANCODE_INSERT: rdpkey = 0xd2; ext = KBD_FLAG_EXT; break; // insert
800     case SCANCODE_REMOVE: rdpkey = 0xd3; ext = KBD_FLAG_EXT; break; // delete
801     case SCANCODE_KEYPADDIVIDE: rdpkey = 0x35; break; // /
802     case SCANCODE_KEYPADENTER: rdpkey = 0x1c; break; // enter
803     case SCANCODE_RIGHTCONTROL: rdpkey = 0x1d; break; // right ctrl
804     case SCANCODE_RIGHTALT: rdpkey = 0x38; break; // right alt
805 jsorg71 811 case SCANCODE_LEFTWIN: rdpkey = 0x5b; ext = KBD_FLAG_EXT; break; // left win
806     case SCANCODE_RIGHTWIN: rdpkey = 0x5c; ext = KBD_FLAG_EXT; break; // right win
807     case 127: rdpkey = 0x5d; ext = KBD_FLAG_EXT; break; // menu key
808     case SCANCODE_PRINTSCREEN: rdpkey = 0x37; ext = KBD_FLAG_EXT; break; // print screen
809     case SCANCODE_BREAK: //rdpkey = 0; break; // break
810     {
811     if (pressed)
812     {
813     ext = KBD_FLAG_EXT;
814     rdp_send_input(0, RDP_INPUT_SCANCODE, RDP_KEYPRESS | ext, 0x46, 0);
815     rdp_send_input(0, RDP_INPUT_SCANCODE, RDP_KEYPRESS | ext, 0xc6, 0);
816     }
817     rdpkey = 0;
818     }
819     case SCANCODE_SCROLLLOCK: rdpkey = 0x46; break; // scroll lock
820 jsorg71 735 case 112: // mouse down
821     {
822     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_DOWN | MOUSE_FLAG_BUTTON4,
823     mouse_getx(), mouse_gety());
824     return;
825     }
826     case 113: // mouse up
827     {
828     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_DOWN | MOUSE_FLAG_BUTTON5,
829     mouse_getx(), mouse_gety());
830     return;
831     }
832     }
833     // printf("%d %d\n", scancode, pressed);
834     if (pressed)
835     rdp_send_input(0, RDP_INPUT_SCANCODE, RDP_KEYPRESS | ext, rdpkey, 0);
836     else
837     rdp_send_input(0, RDP_INPUT_SCANCODE, RDP_KEYRELEASE | ext, rdpkey, 0);
838 jsorg71 811
839 jsorg71 735
840     }
841    
842     /*****************************************************************************/
843     int ui_init(void)
844     {
845     vga_init();
846     memset(&mcursor, 0, sizeof(tcursor));
847     desk_save = (uint8*)xmalloc(0x38400 * g_server_Bpp);
848     return 1;
849     }
850    
851     /*****************************************************************************/
852     void ui_deinit(void)
853     {
854     xfree(desk_save);
855     }
856    
857     /*****************************************************************************/
858     int ui_create_window(void)
859     {
860     int vgamode;
861     int i;
862    
863     vgamode = G800x600x256;
864     if (g_width == 640 && g_height == 480)
865     {
866     if (g_server_Bpp == 1)
867     vgamode = G640x480x256;
868     else if (g_server_Bpp == 2)
869     vgamode = G640x480x64K;
870     }
871     else if (g_width == 800 && g_height == 600)
872     {
873     if (g_server_Bpp == 1)
874     vgamode = G800x600x256;
875     else if (g_server_Bpp == 2)
876     vgamode = G800x600x64K;
877     }
878     else if (g_width == 1024 && g_height == 768)
879     {
880     if (g_server_Bpp == 1)
881     vgamode = G1024x768x256;
882     else if (g_server_Bpp == 2)
883     vgamode = G1024x768x64K;
884     }
885     else
886     {
887     error("Invalid width / height");
888     return 0;
889     }
890     ui_reset_clip();
891     if (!vga_hasmode(vgamode))
892     {
893     error("Graphics unavailable");
894     return 0;
895     }
896     vga_setmousesupport(1);
897     mouse_setposition(g_width / 2, g_height / 2);
898     vga_setmode(vgamode);
899     if (keyboard_init())
900     {
901     error("Keyboard unavailable");
902     return 0;
903     }
904     keyboard_seteventhandler(key_event);
905     if (use_accel)
906     {
907     i = vga_ext_set(VGA_EXT_AVAILABLE, VGA_AVAIL_ACCEL);
908     if (i & ACCELFLAG_PUTIMAGE)
909     has_put_image = 1;
910     if (i & ACCELFLAG_SCREENCOPY)
911     has_screen_copy = 1;
912     if (i & ACCELFLAG_FILLBOX)
913     has_fill_box = 1;
914     printf("accel %d\n", i);
915     }
916     if (!has_screen_copy && !g_save_mem)
917     sdata = xmalloc(g_width * g_height * g_server_Bpp);
918     return 1;
919     }
920    
921     /*****************************************************************************/
922     void ui_destroy_window(void)
923     {
924     keyboard_close(); /* Don't forget this! */
925     vga_setmode(TEXT);
926     if (sdata != 0)
927     xfree(sdata);
928     }
929    
930     /*****************************************************************************/
931     void process_mouse(void)
932     {
933     int ox = mousex;
934     int oy = mousey;
935     int ob = mouseb;
936    
937     if (!UpAndRunning)
938     return;
939     mousex = mouse_getx() - mcursor.x;
940     mousey = mouse_gety() - mcursor.y;
941     mouseb = mouse_getbutton();
942    
943     if (mouseb != ob) // button
944     {
945     // right button
946     if (mouseb & 1)
947     if (!(ob & 1))
948     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_DOWN | MOUSE_FLAG_BUTTON2,
949     mousex + mcursor.x, mousey + mcursor.y);
950     if (ob & 1)
951     if (!(mouseb & 1))
952     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_BUTTON2,
953     mousex + mcursor.x, mousey + mcursor.y);
954     // middle button
955     if (mouseb & 2)
956     if (!(ob & 2))
957     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_DOWN | MOUSE_FLAG_BUTTON3,
958     mousex + mcursor.x, mousey + mcursor.y);
959     if (ob & 2)
960     if (!(mouseb & 2))
961     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_BUTTON3,
962     mousex + mcursor.x, mousey + mcursor.y);
963     // left button
964     if (mouseb & 4)
965     if (!(ob & 4))
966     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_DOWN | MOUSE_FLAG_BUTTON1,
967     mousex + mcursor.x, mousey + mcursor.y);
968     if (ob & 4)
969     if (!(mouseb & 4))
970     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_BUTTON1,
971     mousex + mcursor.x, mousey + mcursor.y);
972     }
973     if (mousex != ox || mousey != oy) // movement
974     {
975     rdp_send_input(0, RDP_INPUT_MOUSE, MOUSE_FLAG_MOVE,
976     mousex + mcursor.x, mousey + mcursor.y);
977     draw_cursor_under(ox, oy);
978     draw_cursor();
979     }
980     }
981    
982     /*****************************************************************************/
983     void process_keyboard(void)
984     {
985     if (!UpAndRunning)
986     return;
987     }
988    
989     /*****************************************************************************/
990     BOOL ui_main_loop(void)
991     {
992     int sel;
993     fd_set rfds;
994    
995     if (!rdp_connect(g_servername, RDP_LOGON_NORMAL, "", "", "", ""))
996     return False;
997     UpAndRunning = 1;
998     FD_ZERO(&rfds);
999     FD_SET(g_sock, &rfds);
1000     sel = vga_waitevent(3, &rfds, NULL, NULL, NULL);
1001     while (sel >= 0)
1002     {
1003     if (sel & 1) /* mouse */
1004     {
1005     process_mouse();
1006     }
1007     else if (sel & 2) /* keyboard */
1008     {
1009     process_keyboard();
1010     }
1011     else
1012     {
1013     if (!rdp_loop(&deactivated, &ext_disc_reason))
1014     return True; /* ok */
1015     }
1016     FD_ZERO(&rfds);
1017     FD_SET(g_sock, &rfds);
1018     sel = vga_waitevent(3, &rfds, NULL, NULL, NULL);
1019     }
1020     return True;
1021     }
1022    
1023     /*****************************************************************************/
1024     void ui_bell(void)
1025     {
1026     }
1027    
1028     /*****************************************************************************/
1029     int ui_select(int in)
1030     {
1031     g_sock = in;
1032     return 1;
1033     }
1034    
1035     /*****************************************************************************/
1036     void* ui_create_glyph(int width, int height, uint8* data)
1037     {
1038     int i, j;
1039     uint8* glyph_data;
1040     bitmap* the_glyph;
1041    
1042     glyph_data = (uint8*)xmalloc(width * height);
1043     the_glyph = (bitmap*)xmalloc(sizeof(bitmap));
1044     the_glyph->width = width;
1045     the_glyph->height = height;
1046     the_glyph->data = glyph_data;
1047     memset(glyph_data, 0, width * height);
1048     for (i = 0; i < height; i++)
1049     for (j = 0; j < width; j++)
1050     if (is_pixel_on(data, j, i, width, 1))
1051     set_pixel_on(glyph_data, j, i, width, 8, 255);
1052     return the_glyph;
1053     }
1054    
1055     /*****************************************************************************/
1056     void ui_destroy_glyph(void* glyph)
1057     {
1058     bitmap* the_glyph;
1059    
1060     the_glyph = (bitmap*)glyph;
1061     if (the_glyph != NULL)
1062     {
1063     if (the_glyph->data != NULL)
1064     xfree(the_glyph->data);
1065     xfree(the_glyph);
1066     }
1067     }
1068    
1069     /*****************************************************************************/
1070     void ui_destroy_bitmap(void* bmp)
1071     {
1072     bitmap* b;
1073    
1074     b = (bitmap*)bmp;
1075     xfree(b->data);
1076     xfree(b);
1077     }
1078    
1079     /*****************************************************************************/
1080     void ui_reset_clip(void)
1081     {
1082     clip_startx = 0;
1083     clip_starty = 0;
1084     clip_endx = g_width;
1085     clip_endy = g_height;
1086     }
1087    
1088     /*****************************************************************************/
1089     void ui_set_clip(int x, int y, int cx, int cy)
1090     {
1091     clip_startx = x;
1092     clip_starty = y;
1093     clip_endx = x + cx;
1094     clip_endy = y + cy;
1095     }
1096    
1097     /*****************************************************************************/
1098     void* ui_create_colourmap(COLOURMAP * colours)
1099     {
1100     int i = 0;
1101     int n = colours->ncolours;
1102     COLOURENTRY* c = colours->colours;
1103     int* cmap = (int*)xmalloc(3 * 256 * sizeof (int));
1104     if (n > 256)
1105     n = 256;
1106     bzero(cmap, 256 * 3 * sizeof (int));
1107     for (i = 0; i < (3 * n); c++)
1108     {
1109     cmap[i++] = (c->red) >> 2;
1110     cmap[i++] = (c->green) >> 2;
1111     cmap[i++] = (c->blue) >> 2;
1112     }
1113     return cmap;
1114     }
1115    
1116     /*****************************************************************************/
1117     void ui_destroy_colourmap(HCOLOURMAP map)
1118     {
1119     if (colmap == map)
1120     colmap = 0;
1121     xfree(map);
1122     }
1123    
1124     /*****************************************************************************/
1125     void ui_set_colourmap(void* map)
1126     {
1127     if (colmap != 0)
1128     xfree(colmap);
1129     vga_setpalvec(0, 256, (int*)map);
1130     colmap = map;
1131     }
1132    
1133     /*****************************************************************************/
1134     HBITMAP ui_create_bitmap(int width, int height, uint8* data)
1135     {
1136     bitmap* b;
1137    
1138     b = (bitmap*)xmalloc(sizeof(bitmap));
1139     b->data = (uint8*)xmalloc(width * height * g_server_Bpp);
1140     b->width = width;
1141     b->height = height;
1142     b->Bpp = g_server_Bpp;
1143     copy_mem(b->data, data, width * height * g_server_Bpp);
1144     return (void*)b;
1145     }
1146    
1147     //*****************************************************************************
1148     void draw_glyph (int x, int y, HGLYPH glyph, int fgcolour)
1149     {
1150     bitmap* the_glyph;
1151     int i, j;
1152    
1153     the_glyph = (bitmap*)glyph;
1154     if (the_glyph == NULL)
1155     return;
1156     for (i = 0; i < the_glyph->height; i++)
1157     for (j = 0; j < the_glyph->width; j++)
1158     if (is_pixel_on(the_glyph->data, j, i, the_glyph->width, 8))
1159     set_pixel(x + j, y + i, fgcolour, 0xc);
1160     }
1161    
1162     #define DO_GLYPH(ttext,idx) \
1163     {\
1164     glyph = cache_get_font (font, ttext[idx]);\
1165     if (!(flags & TEXT2_IMPLICIT_X))\
1166     {\
1167     xyoffset = ttext[++idx];\
1168     if ((xyoffset & 0x80))\
1169     {\
1170     if (flags & TEXT2_VERTICAL) \
1171     y += ttext[idx+1] | (ttext[idx+2] << 8);\
1172     else\
1173     x += ttext[idx+1] | (ttext[idx+2] << 8);\
1174     idx += 2;\
1175     }\
1176     else\
1177     {\
1178     if (flags & TEXT2_VERTICAL) \
1179     y += xyoffset;\
1180     else\
1181     x += xyoffset;\
1182     }\
1183     }\
1184     if (glyph != NULL)\
1185     {\
1186     draw_glyph (x + glyph->offset, y + glyph->baseline, glyph->pixmap, fgcolour);\
1187     if (flags & TEXT2_IMPLICIT_X)\
1188     x += glyph->width;\
1189     }\
1190     }
1191    
1192     /*****************************************************************************/
1193 jsorg71 847 void ui_draw_text(uint8 font, uint8 flags, uint8 opcode, int mixmode,
1194 jsorg71 735 int x, int y,
1195     int clipx, int clipy, int clipcx, int clipcy,
1196 jsorg71 847 int boxx, int boxy, int boxcx, int boxcy, BRUSH * brush,
1197 jsorg71 735 int bgcolour, int fgcolour, uint8* text, uint8 length)
1198     {
1199     int i;
1200     int j;
1201     int xyoffset;
1202     DATABLOB* entry;
1203     FONTGLYPH* glyph;
1204    
1205     if (boxcx > 1)
1206     {
1207     if (contains_mouse(boxx, boxy, boxcx, boxcy))
1208     draw_cursor_under(mousex, mousey);
1209     fill_rect(boxx, boxy, boxcx, boxcy, bgcolour, 0xc);
1210     }
1211     else
1212     {
1213     if (contains_mouse(clipx, clipy, clipcx, clipcy))
1214     draw_cursor_under(mousex, mousey);
1215     if (mixmode == MIX_OPAQUE)
1216     fill_rect(clipx, clipy, clipcx, clipcy, bgcolour, 0xc);
1217     }
1218    
1219     /* Paint text, character by character */
1220     for (i = 0; i < length;)
1221     {
1222     switch (text[i])
1223     {
1224     case 0xff:
1225     if (i + 2 < length)
1226     cache_put_text(text[i + 1], text, text[i + 2]);
1227     else
1228     {
1229     error("this shouldn't be happening\n");
1230     exit(1);
1231     }
1232     /* this will move pointer from start to first character after FF command */
1233     length -= i + 3;
1234     text = &(text[i + 3]);
1235     i = 0;
1236     break;
1237    
1238     case 0xfe:
1239     entry = cache_get_text(text[i + 1]);
1240     if (entry != NULL)
1241     {
1242     if ((((uint8 *) (entry->data))[1] == 0) && (!(flags & TEXT2_IMPLICIT_X)))
1243     {
1244     if (flags & TEXT2_VERTICAL)
1245     y += text[i + 2];
1246     else
1247     x += text[i + 2];
1248     }
1249     for (j = 0; j < entry->size; j++)
1250     DO_GLYPH(((uint8 *) (entry->data)), j);
1251     }
1252     if (i + 2 < length)
1253     i += 3;
1254     else
1255     i += 2;
1256     length -= i;
1257     /* this will move pointer from start to first character after FE command */
1258     text = &(text[i]);
1259     i = 0;
1260     break;
1261    
1262     default:
1263     DO_GLYPH(text, i);
1264     i++;
1265     break;
1266     }
1267     }
1268     if (boxcx > 1)
1269     cache_rect(boxx, boxy, boxcx, boxcy, True);
1270     else
1271     cache_rect(clipx, clipy, clipcx, clipcy, True);
1272     }
1273    
1274     //*****************************************************************************
1275     // Bresenham's line drawing algorithm
1276     void ui_line(uint8 opcode, int startx, int starty, int endx,
1277     int endy, PEN* pen)
1278     {
1279     int dx;
1280     int dy;
1281     int incx;
1282     int incy;
1283     int dpr;
1284     int dpru;
1285     int p;
1286     int left;
1287     int top;
1288     int right;
1289     int bottom;
1290    
1291     if (startx > endx)
1292     {
1293     dx = startx - endx;
1294     incx = -1;
1295     left = endx;
1296     right = startx;
1297     }
1298     else
1299     {
1300     dx = endx - startx;
1301     incx = 1;
1302     left = startx;
1303     right = endx;
1304     }
1305     if (starty > endy)
1306     {
1307     dy = starty - endy;
1308     incy = -1;
1309     top = endy;
1310     bottom = starty;
1311     }
1312     else
1313     {
1314     dy = endy - starty;
1315     incy = 1;
1316     top = starty;
1317     bottom = endy;
1318     }
1319     if (contains_mouse(left, top, (right - left) + 1, (bottom - top) + 1))
1320     draw_cursor_under(mousex, mousey);
1321     if (dx >= dy)
1322     {
1323     dpr = dy << 1;
1324     dpru = dpr - (dx << 1);
1325     p = dpr - dx;
1326     for (; dx >= 0; dx--)
1327     {
1328     set_pixel(startx, starty, pen->colour, opcode);
1329     if (p > 0)
1330     {
1331     startx += incx;
1332     starty += incy;
1333     p += dpru;
1334     }
1335     else
1336     {
1337     startx += incx;
1338     p += dpr;
1339     }
1340     }
1341     }
1342     else
1343     {
1344     dpr = dx << 1;
1345     dpru = dpr - (dy << 1);
1346     p = dpr - dy;
1347     for (; dy >= 0; dy--)
1348     {
1349     set_pixel(startx, starty, pen->colour, opcode);
1350     if (p > 0)
1351     {
1352     startx += incx;
1353     starty += incy;
1354     p += dpru;
1355     }
1356     else
1357     {
1358     starty += incy;
1359     p += dpr;
1360     }
1361     }
1362     }
1363     cache_rect(left, top, (right - left) + 1, (bottom - top) + 1, True);
1364     }
1365    
1366     /*****************************************************************************/
1367     void ui_triblt(uint8 opcode, int x, int y, int cx, int cy,
1368     HBITMAP src, int srcx, int srcy,
1369     BRUSH* brush, int bgcolour, int fgcolour)
1370     {
1371     // non used
1372     }
1373    
1374     /*****************************************************************************/
1375     void ui_memblt(uint8 opcode, int x, int y, int cx, int cy,
1376     HBITMAP src, int srcx, int srcy)
1377     {
1378     bitmap* b;
1379     int i;
1380     int j;
1381     int pixel;
1382    
1383     if (warp_coords(&x, &y, &cx, &cy, &srcx, &srcy))
1384     {
1385     if (contains_mouse(x, y, cx, cy))
1386     draw_cursor_under(mousex, mousey);
1387     b = (bitmap*)src;
1388     if (opcode == 0xc)
1389     accel_draw_box(x, y, cx, cy, get_ptr(srcx, srcy, b->data, b->width, g_server_bpp),
1390     b->width * g_server_Bpp);
1391     else
1392     {
1393     for (i = 0; i < cy; i++)
1394     {
1395     for (j = 0; j < cx; j++)
1396     {
1397     pixel = get_pixel2(srcx + j, srcy + i, b->data, b->width, g_server_bpp);
1398     set_pixel(x + j, y + i, pixel, opcode);
1399     }
1400     }
1401     }
1402     cache_rect(x, y, cx, cy, False);
1403     }
1404     }
1405    
1406     /*****************************************************************************/
1407     void ui_desktop_restore(uint32 offset, int x, int y, int cx, int cy)
1408     {
1409     uint8* p;
1410    
1411     if (offset > 0x38400)
1412     offset = 0;
1413     if (offset + cx * cy > 0x38400)
1414     return;
1415     p = desk_save + offset * g_server_Bpp;
1416     ui_paint_bitmap(x, y, cx, cy, cx, cy, p);
1417     }
1418    
1419     /*****************************************************************************/
1420     void ui_desktop_save(uint32 offset, int x, int y, int cx, int cy)
1421     {
1422     uint8* p;
1423    
1424     if (offset > 0x38400)
1425     offset = 0;
1426     if (offset + cx * cy > 0x38400)
1427     return;
1428     if (contains_mouse(x, y, cx, cy))
1429     draw_cursor_under(mousex, mousey);
1430     p = desk_save + offset * g_server_Bpp;
1431     get_rect(x, y, cx, cy, p);
1432     }
1433    
1434     /*****************************************************************************/
1435     void ui_rect(int x, int y, int cx, int cy, int colour)
1436     {
1437     if (warp_coords(&x, &y, &cx, &cy, NULL, NULL))
1438     {
1439     if (contains_mouse(x, y, cx, cy))
1440     draw_cursor_under(mousex, mousey);
1441     accel_fill_rect(x, y, cx, cy, colour);
1442     cache_rect(x, y, cx, cy, False);
1443     }
1444     }
1445    
1446     /*****************************************************************************/
1447     void ui_screenblt(uint8 opcode, int x, int y, int cx, int cy,
1448     int srcx, int srcy)
1449     {
1450     int i;
1451     int j;
1452     uint8* temp;
1453    
1454     if (x == srcx && y == srcy)
1455     return;
1456     if (warp_coords(&x, &y, &cx, &cy, &srcx, &srcy))
1457     {
1458     if (contains_mouse(x, y, cx, cy) || contains_mouse(srcx, srcy, cx, cy))
1459     draw_cursor_under(mousex, mousey);
1460     if (opcode == 0xc) /* copy */
1461     accel_screen_copy(x, y, cx, cy, srcx, srcy);
1462     else
1463     {
1464     temp = (uint8*)xmalloc(cx * cy * g_server_Bpp);
1465     for (i = 0; i < cy; i++)
1466     for (j = 0; j < cx; j++)
1467     set_pixel2(j, i, get_pixel(srcx + j, srcy + i), temp, cx, g_server_bpp);
1468     for (i = 0; i < cy; i++)
1469     for (j = 0; j < cx; j++)
1470     set_pixel(x + j, y + i, get_pixel2(j, i, temp, cx, g_server_bpp), opcode);
1471     xfree(temp);
1472     }
1473     cache_rect(x, y, cx, cy, False);
1474     draw_cache_rects(); // draw them all so screen is not jumpy
1475     }
1476     }
1477    
1478     /*****************************************************************************/
1479     void ui_patblt(uint8 opcode, int x, int y, int cx, int cy,
1480     BRUSH * brush, int bgcolour, int fgcolour)
1481     {
1482     int i;
1483     int j;
1484     uint8 ipattern[8];
1485    
1486     if (warp_coords(&x, &y, &cx, &cy, NULL, NULL))
1487     {
1488     if (contains_mouse(x, y, cx, cy))
1489     draw_cursor_under(mousex, mousey);
1490     switch (brush->style)
1491     {
1492     case 0:
1493     fill_rect(x, y, cx, cy, fgcolour, opcode);
1494     break;
1495     case 3:
1496     for (i = 0; i < 8; i++)
1497     ipattern[i] = ~brush->pattern[7 - i];
1498     for (i = 0; i < cy; i++)
1499     for (j = 0; j < cx; j++)
1500     if (is_pixel_on(ipattern, (x + j + brush->xorigin) % 8,
1501     (y + i + brush->yorigin) % 8, 8, 1))
1502     set_pixel(x + j, y + i, fgcolour, opcode);
1503     else
1504     set_pixel(x + j, y + i, bgcolour, opcode);
1505     break;
1506     }
1507     cache_rect(x, y, cx, cy, False);
1508     }
1509     }
1510    
1511     /*****************************************************************************/
1512     void ui_destblt(uint8 opcode, int x, int y, int cx, int cy)
1513     {
1514     if (warp_coords(&x, &y, &cx, &cy, NULL, NULL))
1515     {
1516     if (contains_mouse(x, y, cx, cy))
1517     draw_cursor_under(mousex, mousey);
1518     fill_rect(x, y, cx, cy, -1, opcode);
1519     cache_rect(x, y, cx, cy, False);
1520     }
1521     }
1522    
1523     /*****************************************************************************/
1524     void ui_move_pointer(int x, int y)
1525     {
1526     }
1527    
1528     /*****************************************************************************/
1529     void ui_set_null_cursor(void)
1530     {
1531     draw_cursor_under(mousex, mousey);
1532     mousex = mousex - mcursor.x;
1533     mousey = mousey - mcursor.y;
1534     memset(&mcursor, 0, sizeof(mcursor));
1535     memset(mcursor.andmask, 255, sizeof(mcursor.andmask));
1536     memset(mcursor.xormask, 0, sizeof(mcursor.xormask));
1537     draw_cursor();
1538     }
1539    
1540     /*****************************************************************************/
1541     void ui_paint_bitmap(int x, int y, int cx, int cy,
1542     int width, int height, uint8* data)
1543     {
1544     if (warp_coords(&x, &y, &cx, &cy, NULL, NULL))
1545     {
1546     if (contains_mouse(x, y, cx, cy))
1547     draw_cursor_under(mousex, mousey);
1548     accel_draw_box(x, y, cx, cy, data, width * g_server_Bpp);
1549     cache_rect(x, y, cx, cy, False);
1550     }
1551     }
1552    
1553     /*****************************************************************************/
1554     void* ui_create_cursor(unsigned int x, unsigned int y,
1555     int width, int height,
1556     uint8* andmask, uint8* xormask)
1557     {
1558     tcursor* c;
1559     int i;
1560     int j;
1561    
1562     c = (tcursor*)xmalloc(sizeof(tcursor));
1563     memset(c, 0, sizeof(tcursor));
1564     c->w = width;
1565     c->h = height;
1566     c->x = x;
1567     c->y = y;
1568     for (i = 0; i < 32; i++)
1569     {
1570     for (j = 0; j < 32; j++)
1571     {
1572     if (is_pixel_on(andmask, j, i, 32, 1))
1573     set_pixel_on(c->andmask, j, 31 - i, 32, 8, 255);
1574     if (is_pixel_on(xormask, j, i, 32, 24))
1575     set_pixel_on(c->xormask, j, 31 - i, 32, 8, 255);
1576     }
1577     }
1578     return (void*)c;
1579     }
1580    
1581     /*****************************************************************************/
1582     void ui_destroy_cursor(void* cursor)
1583     {
1584     if (cursor != NULL)
1585     xfree(cursor);
1586     }
1587    
1588     /*****************************************************************************/
1589     void ui_set_cursor(void* cursor)
1590     {
1591     int x;
1592     int y;
1593     int ox;
1594     int oy;
1595    
1596     ox = mousex;
1597     oy = mousey;
1598     x = mousex + mcursor.x;
1599     y = mousey + mcursor.y;
1600     memcpy(&mcursor, cursor, sizeof(tcursor));
1601     mousex = x - mcursor.x;
1602     mousey = y - mcursor.y;
1603     draw_cursor_under(ox, oy);
1604     draw_cursor();
1605     }
1606    
1607     /*****************************************************************************/
1608     uint16 ui_get_numlock_state(unsigned int state)
1609     {
1610     return 0;
1611     }
1612    
1613     /*****************************************************************************/
1614     unsigned int read_keyboard_state(void)
1615     {
1616     return 0;
1617     }
1618    
1619     /*****************************************************************************/
1620     void ui_resize_window(void)
1621     {
1622     }
1623    
1624     /*****************************************************************************/
1625     void ui_begin_update(void)
1626     {
1627     }
1628    
1629     /*****************************************************************************/
1630     void ui_end_update(void)
1631     {
1632     draw_cache_rects();
1633     draw_cursor();
1634     }
1635    
1636     /*****************************************************************************/
1637 jsorg71 847 void ui_polygon(uint8 opcode, uint8 fillmode, POINT * point, int npoints,
1638     BRUSH * brush, int bgcolour, int fgcolour)
1639     {
1640     }
1641    
1642     /*****************************************************************************/
1643     void ui_polyline(uint8 opcode, POINT * points, int npoints, PEN * pen)
1644     {
1645     }
1646    
1647     /*****************************************************************************/
1648     void ui_ellipse(uint8 opcode, uint8 fillmode,
1649     int x, int y, int cx, int cy,
1650     BRUSH * brush, int bgcolour, int fgcolour)
1651     {
1652     }
1653    
1654     /*****************************************************************************/
1655 jsorg71 735 void generate_random(uint8* random)
1656     {
1657     memcpy(random, "12345678901234567890123456789012", 32);
1658     }
1659    
1660     /*****************************************************************************/
1661     void save_licence(uint8* data, int length)
1662     {
1663     }
1664    
1665     /*****************************************************************************/
1666     int load_licence(uint8** data)
1667     {
1668     return 0;
1669     }
1670    
1671     /*****************************************************************************/
1672     void* xrealloc(void* in_val, int size)
1673     {
1674     return realloc(in_val, size);
1675     }
1676    
1677     /*****************************************************************************/
1678     void* xmalloc(int size)
1679     {
1680     return malloc(size);
1681     }
1682    
1683     /*****************************************************************************/
1684     void xfree(void* in_val)
1685     {
1686     free(in_val);
1687     }
1688    
1689     /*****************************************************************************/
1690     void warning(char* format, ...)
1691     {
1692     va_list ap;
1693    
1694     fprintf(stderr, "WARNING: ");
1695     va_start(ap, format);
1696     vfprintf(stderr, format, ap);
1697     va_end(ap);
1698     }
1699    
1700     /*****************************************************************************/
1701     void unimpl(char* format, ...)
1702     {
1703     va_list ap;
1704    
1705     fprintf(stderr, "NOT IMPLEMENTED: ");
1706     va_start(ap, format);
1707     vfprintf(stderr, format, ap);
1708     va_end(ap);
1709     }
1710    
1711     /*****************************************************************************/
1712     void error(char* format, ...)
1713     {
1714     va_list ap;
1715    
1716     fprintf(stderr, "ERROR: ");
1717     va_start(ap, format);
1718     vfprintf(stderr, format, ap);
1719     va_end(ap);
1720     }
1721    
1722     BOOL rd_pstcache_mkdir(void)
1723     {
1724     return 0;
1725     }
1726    
1727     /*****************************************************************************/
1728     int rd_open_file(char *filename)
1729     {
1730     return 0;
1731     }
1732    
1733     /*****************************************************************************/
1734     void rd_close_file(int fd)
1735     {
1736     return;
1737     }
1738    
1739     /*****************************************************************************/
1740     int rd_read_file(int fd, void *ptr, int len)
1741     {
1742     return 0;
1743     }
1744    
1745     /*****************************************************************************/
1746     int rd_write_file(int fd, void* ptr, int len)
1747     {
1748     return 0;
1749     }
1750    
1751     /*****************************************************************************/
1752     int rd_lseek_file(int fd, int offset)
1753     {
1754     return 0;
1755     }
1756    
1757     /*****************************************************************************/
1758     BOOL rd_lock_file(int fd, int start, int len)
1759     {
1760     return False;
1761     }
1762    
1763     /*****************************************************************************/
1764     void get_username_and_hostname(void)
1765     {
1766     char fullhostname[64];
1767     char* p;
1768     struct passwd* pw;
1769    
1770     STRNCPY(g_username, "unknown", sizeof(g_username));
1771     STRNCPY(g_hostname, "unknown", sizeof(g_hostname));
1772     pw = getpwuid(getuid());
1773     if (pw != NULL && pw->pw_name != NULL)
1774     {
1775     STRNCPY(g_username, pw->pw_name, sizeof(g_username));
1776     }
1777     if (gethostname(fullhostname, sizeof(fullhostname)) != -1)
1778     {
1779     p = strchr(fullhostname, '.');
1780     if (p != NULL)
1781     *p = 0;
1782     STRNCPY(g_hostname, fullhostname, sizeof(g_hostname));
1783     }
1784     }
1785    
1786     /*****************************************************************************/
1787     void out_params(void)
1788     {
1789     fprintf(stderr, "rdesktop: A Remote Desktop Protocol client.\n");
1790     fprintf(stderr, "Version " VERSION ". Copyright (C) 1999-2003 Matt Chapman.\n");
1791     fprintf(stderr, "See http://www.rdesktop.org/ for more information.\n\n");
1792     fprintf(stderr, "Usage: svgardesktop [options] server\n");
1793     fprintf(stderr, " -g: desktop geometry (WxH)\n");
1794     fprintf(stderr, " -4: use RDP version 4\n");
1795     fprintf(stderr, " -5: use RDP version 5 (default)\n");
1796     fprintf(stderr, " -t: tcp port\n");
1797     fprintf(stderr, " -u: user name\n");
1798     fprintf(stderr, " -n: client hostname\n");
1799     fprintf(stderr, " -d: disable accel funcs\n");
1800     fprintf(stderr, " -a: connection colour depth\n");
1801     fprintf(stderr, " -l: low memory\n");
1802     fprintf(stderr, "\n");
1803     }
1804    
1805     /* produce a hex dump */
1806     void hexdump(uint8* p, uint32 len)
1807     {
1808     uint8* line;
1809     int i;
1810     int thisline;
1811     int offset;
1812    
1813     line = p;
1814     offset = 0;
1815     while (offset < len)
1816     {
1817     printf("%04x ", offset);
1818     thisline = len - offset;
1819     if (thisline > 16)
1820     thisline = 16;
1821    
1822     for (i = 0; i < thisline; i++)
1823     printf("%02x ", line[i]);
1824    
1825     for (; i < 16; i++)
1826     printf(" ");
1827    
1828     for (i = 0; i < thisline; i++)
1829     printf("%c", (line[i] >= 0x20 && line[i] < 0x7f) ? line[i] : '.');
1830    
1831     printf("\n");
1832     offset += thisline;
1833     line += thisline;
1834     }
1835     }
1836    
1837     /*****************************************************************************/
1838     int parse_parameters(int in_argc, char** in_argv)
1839     {
1840     int i;
1841     char* p;
1842    
1843     if (in_argc <= 1)
1844     {
1845     out_params();
1846     return 0;
1847     }
1848     g_argc = in_argc;
1849     g_argv = in_argv;
1850     for (i = 1; i < in_argc; i++)
1851     {
1852     strcpy(g_servername, in_argv[i]);
1853     if (strcmp(in_argv[i], "-g") == 0)
1854     {
1855     g_width = strtol(in_argv[i + 1], &p, 10);
1856     if (g_width <= 0)
1857     {
1858     error("invalid geometry\n");
1859     return 0;
1860     }
1861     if (*p == 'x')
1862     g_height = strtol(p + 1, NULL, 10);
1863     if (g_height <= 0)
1864     {
1865     error("invalid geometry\n");
1866     return 0;
1867     }
1868     g_width = (g_width + 3) & ~3;
1869     }
1870     else if (strcmp(in_argv[i], "-4") == 0)
1871     g_use_rdp5 = 0;
1872     else if (strcmp(in_argv[i], "-5") == 0)
1873     g_use_rdp5 = 1;
1874     else if (strcmp(in_argv[i], "-t") == 0)
1875     g_tcp_port_rdp = strtol(in_argv[i + 1], &p, 10);
1876     else if (strcmp(in_argv[i], "-h") == 0)
1877     {
1878     out_params();
1879     return 0;
1880     }
1881     else if (strcmp(in_argv[i], "-n") == 0)
1882     {
1883     STRNCPY(g_hostname, in_argv[i + 1], sizeof(g_hostname));
1884     }
1885     else if (strcmp(in_argv[i], "-u") == 0)
1886     {
1887     STRNCPY(g_username, in_argv[i + 1], sizeof(g_username));
1888     }
1889     else if (strcmp(in_argv[i], "-d") == 0)
1890     {
1891     use_accel = 0;
1892     }
1893     else if (strcmp(in_argv[i], "-a") == 0)
1894     {
1895     g_server_bpp = strtol(in_argv[i + 1], NULL, 10);
1896     if (g_server_bpp != 8 && g_server_bpp != 16)
1897     {
1898     error("invalid server bpp\n");
1899     return 0;
1900     }
1901     g_server_Bpp = (g_server_bpp + 7) / 8;
1902     }
1903     else if (strcmp(in_argv[i], "-l") == 0)
1904     g_save_mem = 1;
1905     }
1906     return 1;
1907     }
1908    
1909     /*****************************************************************************/
1910     int main(int in_argc, char** in_argv)
1911     {
1912     get_username_and_hostname();
1913     if (!parse_parameters(in_argc, in_argv))
1914     return 0;
1915     if (!ui_init())
1916     return 1;
1917     if (!ui_create_window())
1918     return 1;
1919     ui_main_loop();
1920     ui_destroy_window();
1921     ui_deinit();
1922     return 0;
1923     }

  ViewVC Help
Powered by ViewVC 1.1.26