/[rdesktop]/sourceforge.net/trunk/rdesktop/rdesktop.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

Diff of /sourceforge.net/trunk/rdesktop/rdesktop.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 58 by jsorg71, Sun Jul 14 00:34:21 2002 UTC revision 240 by matthewc, Thu Oct 24 08:21:33 2002 UTC
# Line 1  Line 1 
1  /*  /*
2     rdesktop: A Remote Desktop Protocol client.     rdesktop: A Remote Desktop Protocol client.
3     Entrypoint and utility functions     Entrypoint and utility functions
4     Copyright (C) Matthew Chapman 1999-2001     Copyright (C) Matthew Chapman 1999-2002
5      
6     This program is free software; you can redistribute it and/or modify     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     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     the Free Software Foundation; either version 2 of the License, or
9     (at your option) any later version.     (at your option) any later version.
10      
11     This program is distributed in the hope that it will be useful,     This program is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.     GNU General Public License for more details.
15      
16     You should have received a copy of the GNU General Public License     You should have received a copy of the GNU General Public License
17     along with this program; if not, write to the Free Software     along with this program; if not, write to the Free Software
18     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19  */  */
20    
 #include <stdlib.h>             /* malloc realloc free */  
21  #include <stdarg.h>             /* va_list va_start va_end */  #include <stdarg.h>             /* va_list va_start va_end */
22  #include <unistd.h>             /* read close getuid getgid getpid getppid gethostname */  #include <unistd.h>             /* read close getuid getgid getpid getppid gethostname */
23  #include <fcntl.h>              /* open */  #include <fcntl.h>              /* open */
24  #include <pwd.h>                /* getpwuid */  #include <pwd.h>                /* getpwuid */
25  #include <limits.h>             /* PATH_MAX */  #include <limits.h>             /* PATH_MAX */
26    #include <termios.h>            /* tcgetattr tcsetattr */
27  #include <sys/stat.h>           /* stat */  #include <sys/stat.h>           /* stat */
28  #include <sys/time.h>           /* gettimeofday */  #include <sys/time.h>           /* gettimeofday */
29  #include <sys/times.h>          /* times */  #include <sys/times.h>          /* times */
30  #include "rdesktop.h"  #include "rdesktop.h"
31    
32    #ifdef EGD_SOCKET
33    #include <sys/socket.h>         /* socket connect */
34    #include <sys/un.h>             /* sockaddr_un */
35    #endif
36    
37    #ifdef WITH_OPENSSL
38    #include <openssl/md5.h>
39    #else
40    #include "crypto/md5.h"
41    #endif
42    
43    char title[32] = "";
44  char username[16];  char username[16];
45  char hostname[16];  char hostname[16];
46  char keymapname[16];  char keymapname[16];
47  int keylayout;  int keylayout = 0x409;          /* Defaults to US keyboard layout */
48  int width;  int width = 800;
49  int height;  int height = 600;
50  int tcp_port_rdp = TCP_PORT_RDP;  int tcp_port_rdp = TCP_PORT_RDP;
51  BOOL bitmap_compression = True;  BOOL bitmap_compression = True;
52  BOOL sendmotion = True;  BOOL sendmotion = True;
53  BOOL orders = True;  BOOL orders = True;
 BOOL licence = True;  
54  BOOL encryption = True;  BOOL encryption = True;
55  BOOL desktop_save = True;  BOOL desktop_save = True;
56  BOOL fullscreen = False;  BOOL fullscreen = False;
57    BOOL grab_keyboard = True;
58    
59  /* Display usage information */  /* Display usage information */
60  static void  static void
61  usage(char *program)  usage(char *program)
62  {  {
63          printf("Usage: %s [options] server\n", program);          fprintf(stderr, "rdesktop: A Remote Desktop Protocol client.\n");
64          printf("   -u: user name\n");          fprintf(stderr, "Version " VERSION ". Copyright (C) 1999-2002 Matt Chapman.\n");
65          printf("   -d: domain\n");          fprintf(stderr, "See http://www.rdesktop.org/ for more information.\n\n");
66          printf("   -s: shell\n");  
67          printf("   -c: working directory\n");          fprintf(stderr, "Usage: %s [options] server[:port]\n", program);
68          printf("   -p: password (autologon)\n");          fprintf(stderr, "   -u: user name\n");
69          printf("   -n: client hostname\n");          fprintf(stderr, "   -d: domain\n");
70          printf("   -k: keyboard layout\n");          fprintf(stderr, "   -s: shell\n");
71          printf("   -g: desktop geometry (WxH)\n");          fprintf(stderr, "   -c: working directory\n");
72          printf("   -f: full-screen mode\n");          fprintf(stderr, "   -p: password (- to prompt)\n");
73          printf("   -b: force bitmap updates\n");          fprintf(stderr, "   -n: client hostname\n");
74          printf("   -e: disable encryption (French TS)\n");          fprintf(stderr, "   -k: keyboard layout on terminal server (us,sv,gr,etc.)\n");
75          printf("   -m: do not send motion events\n");          fprintf(stderr, "   -g: desktop geometry (WxH)\n");
76          printf("   -l: do not request licence\n");          fprintf(stderr, "   -f: full-screen mode\n");
77          printf("   -t: rdp tcp port\n\n");          fprintf(stderr, "   -b: force bitmap updates\n");
78            fprintf(stderr, "   -e: disable encryption (French TS)\n");
79            fprintf(stderr, "   -m: do not send motion events\n");
80            fprintf(stderr, "   -K: keep window manager key bindings\n");
81            fprintf(stderr, "   -T: window title\n");
82    }
83    
84    static BOOL
85    read_password(char *password, int size)
86    {
87            struct termios tios;
88            BOOL ret = False;
89            int istty = 0;
90            char *p;
91    
92            if (tcgetattr(STDIN_FILENO, &tios) == 0)
93            {
94                    fprintf(stderr, "Password: ");
95                    tios.c_lflag &= ~ECHO;
96                    tcsetattr(STDIN_FILENO, TCSANOW, &tios);
97                    istty = 1;
98            }
99    
100            if (fgets(password, size, stdin) != NULL)
101            {
102                    ret = True;
103    
104                    /* strip final newline */
105                    p = strchr(password, '\n');
106                    if (p != NULL)
107                            *p = 0;
108            }
109    
110            if (istty)
111            {
112                    tios.c_lflag |= ECHO;
113                    tcsetattr(STDIN_FILENO, TCSANOW, &tios);
114                    fprintf(stderr, "\n");
115            }
116    
117            return ret;
118  }  }
119    
120  /* Client program */  /* Client program */
121  int  int
122  main(int argc, char *argv[])  main(int argc, char *argv[])
123  {  {
124            char server[64];
125          char fullhostname[64];          char fullhostname[64];
126          char domain[16];          char domain[16];
127          char password[16];          char password[16];
128          char shell[32];          char shell[128];
129          char directory[32];          char directory[32];
130          char title[32];          BOOL prompt_password;
131          struct passwd *pw;          struct passwd *pw;
         char *server, *p;  
132          uint32 flags;          uint32 flags;
133            char *p;
134          int c;          int c;
135    
         printf("rdesktop: A Remote Desktop Protocol client.\n");  
         printf("Version " VERSION ". Copyright (C) 1999-2001 Matt Chapman.\n");  
         printf("See http://www.rdesktop.org/ for more information.\n\n");  
   
136          flags = RDP_LOGON_NORMAL;          flags = RDP_LOGON_NORMAL;
137            prompt_password = False;
138          domain[0] = password[0] = shell[0] = directory[0] = 0;          domain[0] = password[0] = shell[0] = directory[0] = 0;
139          strcpy(keymapname, "us");          strcpy(keymapname, "en-us");
140    
141          while ((c = getopt(argc, argv, "u:d:s:c:p:n:k:g:t:fbemlh?")) != -1)          while ((c = getopt(argc, argv, "u:d:s:c:p:n:k:g:fbemKT:h?")) != -1)
142          {          {
143                  switch (c)                  switch (c)
144                  {                  {
# Line 109  main(int argc, char *argv[]) Line 159  main(int argc, char *argv[])
159                                  break;                                  break;
160    
161                          case 'p':                          case 'p':
162                                    if ((optarg[0] == '-') && (optarg[1] == 0))
163                                    {
164                                            prompt_password = True;
165                                            break;
166                                    }
167    
168                                  STRNCPY(password, optarg, sizeof(password));                                  STRNCPY(password, optarg, sizeof(password));
169                                  flags |= RDP_LOGON_AUTO;                                  flags |= RDP_LOGON_AUTO;
170    
171                                    /* try to overwrite argument so it won't appear in ps */
172                                    p = optarg;
173                                    while (*p)
174                                            *(p++) = 'X';
175                                  break;                                  break;
176    
177                          case 'n':                          case 'n':
# Line 124  main(int argc, char *argv[]) Line 185  main(int argc, char *argv[])
185                          case 'g':                          case 'g':
186                                  width = strtol(optarg, &p, 10);                                  width = strtol(optarg, &p, 10);
187                                  if (*p == 'x')                                  if (*p == 'x')
188                                          height = strtol(p+1, NULL, 10);                                          height = strtol(p + 1, NULL, 10);
189    
190                                  if ((width == 0) || (height == 0))                                  if ((width == 0) || (height == 0))
191                                  {                                  {
# Line 149  main(int argc, char *argv[]) Line 210  main(int argc, char *argv[])
210                                  sendmotion = False;                                  sendmotion = False;
211                                  break;                                  break;
212    
213                          case 'l':                          case 'K':
214                                  licence = False;                                  grab_keyboard = False;
215                                  break;                                  break;
216    
217                          case 't':                          case 'T':
218                                  tcp_port_rdp = strtol(optarg, NULL, 10);                                  STRNCPY(title, optarg, sizeof(title));
219                                  break;                                  break;
220    
221                          case 'h':                          case 'h':
# Line 171  main(int argc, char *argv[]) Line 232  main(int argc, char *argv[])
232                  return 1;                  return 1;
233          }          }
234    
235          server = argv[optind];          STRNCPY(server, argv[optind], sizeof(server));
236            p = strchr(server, ':');
237            if (p != NULL)
238            {
239                    tcp_port_rdp = strtol(p + 1, NULL, 10);
240                    *p = 0;
241            }
242    
243          if (username[0] == 0)          if (username[0] == 0)
244          {          {
# Line 200  main(int argc, char *argv[]) Line 267  main(int argc, char *argv[])
267                  STRNCPY(hostname, fullhostname, sizeof(hostname));                  STRNCPY(hostname, fullhostname, sizeof(hostname));
268          }          }
269    
270          if (!strcmp(password, "-"))          if (prompt_password && read_password(password, sizeof(password)))
271          {                  flags |= RDP_LOGON_AUTO;
                 p = getpass("Password: ");  
                 if (p == NULL)  
                 {  
                         error("failed to read password\n");  
                         return 0;  
                 }  
                 STRNCPY(password, p, sizeof(password));  
         }  
272    
273          if ((width == 0) || (height == 0))          if (title[0] == 0)
274          {          {
275                  width = 800;                  strcpy(title, "rdesktop - ");
276                  height = 600;                  strncat(title, server, sizeof(title) - sizeof("rdesktop - "));
277          }          }
278    
279          strcpy(title, "rdesktop - ");          if (!ui_init())
280          strncat(title, server, sizeof(title) - sizeof("rdesktop - "));                  return 1;
281    
282          if (!rdp_connect(server, flags, domain, password, shell, directory))          if (!rdp_connect(server, flags, domain, password, shell, directory))
283                  return 1;                  return 1;
284    
285          printf("Connection successful.\n");          DEBUG(("Connection successful.\n"));
286            memset(password, 0, sizeof(password));
287    
288          if (ui_create_window(title))          if (ui_create_window())
289          {          {
290                  rdp_main_loop();                  rdp_main_loop();
291                  ui_destroy_window();                  ui_destroy_window();
292          }          }
293    
294          printf("Disconnecting...\n");          DEBUG(("Disconnecting...\n"));
295          rdp_disconnect();          rdp_disconnect();
296            ui_deinit();
297          return 0;          return 0;
298  }  }
299    
300    #ifdef EGD_SOCKET
301    /* Read 32 random bytes from PRNGD or EGD socket (based on OpenSSL RAND_egd) */
302    static BOOL
303    generate_random_egd(uint8 * buf)
304    {
305            struct sockaddr_un addr;
306            BOOL ret = False;
307            int fd;
308    
309            fd = socket(AF_UNIX, SOCK_STREAM, 0);
310            if (fd == -1)
311                    return False;
312    
313            addr.sun_family = AF_UNIX;
314            memcpy(addr.sun_path, EGD_SOCKET, sizeof(EGD_SOCKET));
315            if (connect(fd, (struct sockaddr *)&addr, sizeof(addr)) == -1)
316                    goto err;
317    
318            /* PRNGD and EGD use a simple communications protocol */
319            buf[0] = 1;  /* Non-blocking (similar to /dev/urandom) */
320            buf[1] = 32; /* Number of requested random bytes */
321            if (write(fd, buf, 2) != 2)
322                    goto err;
323    
324            if ((read(fd, buf, 1) != 1) || (buf[0] == 0)) /* Available? */
325                    goto err;
326    
327            if (read(fd, buf, 32) != 32)
328                    goto err;
329    
330            ret = True;
331    
332    err:
333            close(fd);
334            return ret;
335    }
336    #endif
337    
338  /* Generate a 32-byte random for the secure transport code. */  /* Generate a 32-byte random for the secure transport code. */
339  void  void
340  generate_random(uint8 *random)  generate_random(uint8 * random)
341  {  {
342          struct stat st;          struct stat st;
343          struct tms tmsbuf;          struct tms tmsbuf;
344          uint32 *r = (uint32 *) random;          MD5_CTX md5;
345          int fd;          uint32 *r;
346            int fd, n;
347    
348          /* If we have a kernel random device, use it. */          /* If we have a kernel random device, try that first */
349          if (((fd = open("/dev/urandom", O_RDONLY)) != -1)          if (((fd = open("/dev/urandom", O_RDONLY)) != -1)
350              || ((fd = open("/dev/random", O_RDONLY)) != -1))              || ((fd = open("/dev/random", O_RDONLY)) != -1))
351          {          {
352                  read(fd, random, 32);                  n = read(fd, random, 32);
353                  close(fd);                  close(fd);
354                  return;                  if (n == 32)
355                            return;
356          }          }
357    
358    #ifdef EGD_SOCKET
359            /* As a second preference use an EGD */
360            if (generate_random_egd(random))
361                    return;
362    #endif
363    
364          /* Otherwise use whatever entropy we can gather - ideas welcome. */          /* Otherwise use whatever entropy we can gather - ideas welcome. */
365            r = (uint32 *)random;
366          r[0] = (getpid()) | (getppid() << 16);          r[0] = (getpid()) | (getppid() << 16);
367          r[1] = (getuid()) | (getgid() << 16);          r[1] = (getuid()) | (getgid() << 16);
368          r[2] = times(&tmsbuf);  /* system uptime (clocks) */          r[2] = times(&tmsbuf);  /* system uptime (clocks) */
# Line 263  generate_random(uint8 *random) Line 371  generate_random(uint8 *random)
371          r[5] = st.st_atime;          r[5] = st.st_atime;
372          r[6] = st.st_mtime;          r[6] = st.st_mtime;
373          r[7] = st.st_ctime;          r[7] = st.st_ctime;
374    
375            /* Hash both halves with MD5 to obscure possible patterns */
376            MD5_Init(&md5);
377            MD5_Update(&md5, random, 16);
378            MD5_Final(random, &md5);
379            MD5_Update(&md5, random+16, 16);
380            MD5_Final(random+16, &md5);
381  }  }
382    
383  /* malloc; exit if out of memory */  /* malloc; exit if out of memory */
# Line 343  hexdump(unsigned char *p, unsigned int l Line 458  hexdump(unsigned char *p, unsigned int l
458                          printf("%02x ", line[i]);                          printf("%02x ", line[i]);
459    
460                  for (; i < 16; i++)                  for (; i < 16; i++)
461                                  printf("   ");                          printf("   ");
462    
463                  for (i = 0; i < thisline; i++)                  for (i = 0; i < thisline; i++)
464                          printf("%c",                          printf("%c", (line[i] >= 0x20 && line[i] < 0x7f) ? line[i] : '.');
                                (line[i] >= 0x20  
                                 && line[i] < 0x7f) ? line[i] : '.');  
465    
466                  printf("\n");                  printf("\n");
467                  offset += thisline;                  offset += thisline;
# Line 356  hexdump(unsigned char *p, unsigned int l Line 469  hexdump(unsigned char *p, unsigned int l
469          }          }
470  }  }
471    
472    #ifdef SAVE_LICENCE
473  int  int
474  load_licence(unsigned char **data)  load_licence(unsigned char **data)
475  {  {
# Line 369  load_licence(unsigned char **data) Line 483  load_licence(unsigned char **data)
483                  return -1;                  return -1;
484    
485          STRNCPY(path, home, sizeof(path));          STRNCPY(path, home, sizeof(path));
486          strncat(path, "/.rdesktop/licence", sizeof(path)-strlen(path)-1);          strncat(path, "/.rdesktop/licence", sizeof(path) - strlen(path) - 1);
487    
488          fd = open(path, O_RDONLY);          fd = open(path, O_RDONLY);
489          if (fd == -1)          if (fd == -1)
# Line 394  save_licence(unsigned char *data, int le Line 508  save_licence(unsigned char *data, int le
508                  return;                  return;
509    
510          STRNCPY(path, home, sizeof(path));          STRNCPY(path, home, sizeof(path));
511          strncat(path, "/.rdesktop", sizeof(path)-strlen(path)-1);          strncat(path, "/.rdesktop", sizeof(path) - strlen(path) - 1);
512          mkdir(path, 0700);          mkdir(path, 0700);
513    
514          strncat(path, "/licence", sizeof(path)-strlen(path)-1);          strncat(path, "/licence", sizeof(path) - strlen(path) - 1);
515    
516          fd = open(path, O_WRONLY|O_CREAT|O_TRUNC, 0600);          fd = open(path, O_WRONLY | O_CREAT | O_TRUNC, 0600);
517          if (fd == -1)          if (fd == -1)
518          {          {
519                  perror("open");                  perror("open");
# Line 409  save_licence(unsigned char *data, int le Line 523  save_licence(unsigned char *data, int le
523          write(fd, data, length);          write(fd, data, length);
524          close(fd);          close(fd);
525  }  }
526    #endif

Legend:
Removed from v.58  
changed lines
  Added in v.240

  ViewVC Help
Powered by ViewVC 1.1.26