[INTL]
[reactos.git] / reactos / base / applications / mstsc / secure.c
1 /* -*- c-basic-offset: 8 -*-
2 rdesktop: A Remote Desktop Protocol client.
3 Protocol services - RDP encryption and licensing
4 Copyright (C) Matthew Chapman 1999-2005
5
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 along
17 with this program; if not, write to the Free Software Foundation, Inc.,
18 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 */
20
21 #include "precomp.h"
22
23 void *
24 ssl_sha1_info_create(void);
25 void
26 ssl_sha1_info_delete(void * sha1_info);
27 void
28 ssl_sha1_clear(void * sha1_info);
29 void
30 ssl_sha1_transform(void * sha1_info, char * data, int len);
31 void
32 ssl_sha1_complete(void * sha1_info, char * data);
33 void *
34 ssl_md5_info_create(void);
35 void
36 ssl_md5_info_delete(void * md5_info);
37 void *
38 ssl_md5_info_create(void);
39 void
40 ssl_md5_info_delete(void * md5_info);
41 void
42 ssl_md5_clear(void * md5_info);
43 void
44 ssl_md5_transform(void * md5_info, char * data, int len);
45 void
46 ssl_md5_complete(void * md5_info, char * data);
47 void *
48 ssl_rc4_info_create(void);
49 void
50 ssl_rc4_info_delete(void * rc4_info);
51 void
52 ssl_rc4_set_key(void * rc4_info, char * key, int len);
53 void
54 ssl_rc4_crypt(void * rc4_info, char * in_data, char * out_data, int len);
55 int
56 ssl_mod_exp(char* out, int out_len, char* in, int in_len,
57 char* mod, int mod_len, char* exp, int exp_len);
58
59 extern char g_hostname[];
60 extern int g_width;
61 extern int g_height;
62 extern unsigned int g_keylayout;
63 extern int g_keyboard_type;
64 extern int g_keyboard_subtype;
65 extern int g_keyboard_functionkeys;
66 extern BOOL g_encryption;
67 extern BOOL g_licence_issued;
68 extern BOOL g_use_rdp5;
69 extern BOOL g_console_session;
70 extern int g_server_depth;
71 extern uint16 mcs_userid;
72 extern VCHANNEL g_channels[];
73 extern unsigned int g_num_channels;
74
75 static int rc4_key_len;
76 static void * rc4_decrypt_key = 0;
77 static void * rc4_encrypt_key = 0;
78 //static RSA *server_public_key;
79 static void * server_public_key;
80
81 static uint8 sec_sign_key[16];
82 static uint8 sec_decrypt_key[16];
83 static uint8 sec_encrypt_key[16];
84 static uint8 sec_decrypt_update_key[16];
85 static uint8 sec_encrypt_update_key[16];
86 static uint8 sec_crypted_random[SEC_MODULUS_SIZE];
87
88 uint16 g_server_rdp_version = 0;
89
90 /* These values must be available to reset state - Session Directory */
91 static int sec_encrypt_use_count = 0;
92 static int sec_decrypt_use_count = 0;
93
94 /*
95 * I believe this is based on SSLv3 with the following differences:
96 * MAC algorithm (5.2.3.1) uses only 32-bit length in place of seq_num/type/length fields
97 * MAC algorithm uses SHA1 and MD5 for the two hash functions instead of one or other
98 * key_block algorithm (6.2.2) uses 'X', 'YY', 'ZZZ' instead of 'A', 'BB', 'CCC'
99 * key_block partitioning is different (16 bytes each: MAC secret, decrypt key, encrypt key)
100 * encryption/decryption keys updated every 4096 packets
101 * See http://wp.netscape.com/eng/ssl3/draft302.txt
102 */
103
104 /*
105 * 48-byte transformation used to generate master secret (6.1) and key material (6.2.2).
106 * Both SHA1 and MD5 algorithms are used.
107 */
108 void
109 sec_hash_48(uint8 * out, uint8 * in, uint8 * salt1, uint8 * salt2, uint8 salt)
110 {
111 uint8 shasig[20];
112 uint8 pad[4];
113 void * sha;
114 void * md5;
115 int i;
116
117 for (i = 0; i < 3; i++)
118 {
119 memset(pad, salt + i, i + 1);
120 sha = ssl_sha1_info_create();
121 ssl_sha1_clear(sha);
122 ssl_sha1_transform(sha, (char *)pad, i + 1);
123 ssl_sha1_transform(sha, (char *)in, 48);
124 ssl_sha1_transform(sha, (char *)salt1, 32);
125 ssl_sha1_transform(sha, (char *)salt2, 32);
126 ssl_sha1_complete(sha, (char *)shasig);
127 ssl_sha1_info_delete(sha);
128 md5 = ssl_md5_info_create();
129 ssl_md5_clear(md5);
130 ssl_md5_transform(md5, (char *)in, 48);
131 ssl_md5_transform(md5, (char *)shasig, 20);
132 ssl_md5_complete(md5, (char *)out + i * 16);
133 ssl_md5_info_delete(md5);
134 }
135 }
136
137 /*
138 * 16-byte transformation used to generate export keys (6.2.2).
139 */
140 void
141 sec_hash_16(uint8 * out, uint8 * in, uint8 * salt1, uint8 * salt2)
142 {
143 void * md5;
144
145 md5 = ssl_md5_info_create();
146 ssl_md5_clear(md5);
147 ssl_md5_transform(md5, (char *)in, 16);
148 ssl_md5_transform(md5, (char *)salt1, 32);
149 ssl_md5_transform(md5, (char *)salt2, 32);
150 ssl_md5_complete(md5, (char *)out);
151 ssl_md5_info_delete(md5);
152 }
153
154 /* Reduce key entropy from 64 to 40 bits */
155 static void
156 sec_make_40bit(uint8 * key)
157 {
158 key[0] = 0xd1;
159 key[1] = 0x26;
160 key[2] = 0x9e;
161 }
162
163 /* Generate encryption keys given client and server randoms */
164 static void
165 sec_generate_keys(uint8 * client_random, uint8 * server_random, int rc4_key_size)
166 {
167 uint8 pre_master_secret[48];
168 uint8 master_secret[48];
169 uint8 key_block[48];
170
171 /* Construct pre-master secret */
172 memcpy(pre_master_secret, client_random, 24);
173 memcpy(pre_master_secret + 24, server_random, 24);
174
175 /* Generate master secret and then key material */
176 sec_hash_48(master_secret, pre_master_secret, client_random, server_random, 'A');
177 sec_hash_48(key_block, master_secret, client_random, server_random, 'X');
178
179 /* First 16 bytes of key material is MAC secret */
180 memcpy(sec_sign_key, key_block, 16);
181
182 /* Generate export keys from next two blocks of 16 bytes */
183 sec_hash_16(sec_decrypt_key, &key_block[16], client_random, server_random);
184 sec_hash_16(sec_encrypt_key, &key_block[32], client_random, server_random);
185
186 if (rc4_key_size == 1)
187 {
188 DEBUG(("40-bit encryption enabled\n"));
189 sec_make_40bit(sec_sign_key);
190 sec_make_40bit(sec_decrypt_key);
191 sec_make_40bit(sec_encrypt_key);
192 rc4_key_len = 8;
193 }
194 else
195 {
196 DEBUG(("rc_4_key_size == %d, 128-bit encryption enabled\n", rc4_key_size));
197 rc4_key_len = 16;
198 }
199
200 /* Save initial RC4 keys as update keys */
201 memcpy(sec_decrypt_update_key, sec_decrypt_key, 16);
202 memcpy(sec_encrypt_update_key, sec_encrypt_key, 16);
203
204 /* Initialise RC4 state arrays */
205
206 ssl_rc4_info_delete(rc4_decrypt_key);
207 rc4_decrypt_key = ssl_rc4_info_create();
208 ssl_rc4_set_key(rc4_decrypt_key, (char *)sec_decrypt_key, rc4_key_len);
209
210 ssl_rc4_info_delete(rc4_encrypt_key);
211 rc4_encrypt_key = ssl_rc4_info_create();
212 ssl_rc4_set_key(rc4_encrypt_key, (char *)sec_encrypt_key, rc4_key_len);
213 }
214
215 static uint8 pad_54[40] = {
216 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54,
217 54, 54, 54,
218 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54,
219 54, 54, 54
220 };
221
222 static uint8 pad_92[48] = {
223 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92,
224 92, 92, 92, 92, 92, 92, 92,
225 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92,
226 92, 92, 92, 92, 92, 92, 92
227 };
228
229 /* Output a uint32 into a buffer (little-endian) */
230 void
231 buf_out_uint32(uint8 * buffer, uint32 value)
232 {
233 buffer[0] = (value) & 0xff;
234 buffer[1] = (value >> 8) & 0xff;
235 buffer[2] = (value >> 16) & 0xff;
236 buffer[3] = (value >> 24) & 0xff;
237 }
238
239 /* Generate a MAC hash (5.2.3.1), using a combination of SHA1 and MD5 */
240 void
241 sec_sign(uint8 * signature, int siglen, uint8 * session_key, int keylen, uint8 * data, int datalen)
242 {
243 uint8 shasig[20];
244 uint8 md5sig[16];
245 uint8 lenhdr[4];
246 void * sha;
247 void * md5;
248
249 buf_out_uint32(lenhdr, datalen);
250
251 sha = ssl_sha1_info_create();
252 ssl_sha1_clear(sha);
253 ssl_sha1_transform(sha, (char *)session_key, keylen);
254 ssl_sha1_transform(sha, (char *)pad_54, 40);
255 ssl_sha1_transform(sha, (char *)lenhdr, 4);
256 ssl_sha1_transform(sha, (char *)data, datalen);
257 ssl_sha1_complete(sha, (char *)shasig);
258 ssl_sha1_info_delete(sha);
259
260 md5 = ssl_md5_info_create();
261 ssl_md5_clear(md5);
262 ssl_md5_transform(md5, (char *)session_key, keylen);
263 ssl_md5_transform(md5, (char *)pad_92, 48);
264 ssl_md5_transform(md5, (char *)shasig, 20);
265 ssl_md5_complete(md5, (char *)md5sig);
266 ssl_md5_info_delete(md5);
267
268 memcpy(signature, md5sig, siglen);
269 }
270
271 /* Update an encryption key */
272 static void
273 sec_update(uint8 * key, uint8 * update_key)
274 {
275 uint8 shasig[20];
276 void * sha;
277 void * md5;
278 void * update;
279
280 sha = ssl_sha1_info_create();
281 ssl_sha1_clear(sha);
282 ssl_sha1_transform(sha, (char *)update_key, rc4_key_len);
283 ssl_sha1_transform(sha, (char *)pad_54, 40);
284 ssl_sha1_transform(sha, (char *)key, rc4_key_len);
285 ssl_sha1_complete(sha, (char *)shasig);
286 ssl_sha1_info_delete(sha);
287
288 md5 = ssl_md5_info_create();
289 ssl_md5_clear(md5);
290 ssl_md5_transform(md5, (char *)update_key, rc4_key_len);
291 ssl_md5_transform(md5, (char *)pad_92, 48);
292 ssl_md5_transform(md5, (char *)shasig, 20);
293 ssl_md5_complete(md5, (char *)key);
294 ssl_md5_info_delete(md5);
295
296
297 update = ssl_rc4_info_create();
298 ssl_rc4_set_key(update, (char *)key, rc4_key_len);
299 ssl_rc4_crypt(update, (char *)key, (char *)key, rc4_key_len);
300 ssl_rc4_info_delete(update);
301
302 if (rc4_key_len == 8)
303 sec_make_40bit(key);
304 }
305
306 /* Encrypt data using RC4 */
307 static void
308 sec_encrypt(uint8 * data, int length)
309 {
310 if (sec_encrypt_use_count == 4096)
311 {
312 sec_update(sec_encrypt_key, sec_encrypt_update_key);
313 ssl_rc4_set_key(rc4_encrypt_key, (char *)sec_encrypt_key, rc4_key_len);
314 sec_encrypt_use_count = 0;
315 }
316 ssl_rc4_crypt(rc4_encrypt_key, (char *)data, (char *)data, length);
317 sec_encrypt_use_count++;
318 }
319
320 /* Decrypt data using RC4 */
321 void
322 sec_decrypt(uint8 * data, int length)
323 {
324 if (sec_decrypt_use_count == 4096)
325 {
326 sec_update(sec_decrypt_key, sec_decrypt_update_key);
327 ssl_rc4_set_key(rc4_decrypt_key, (char *)sec_decrypt_key, rc4_key_len);
328 sec_decrypt_use_count = 0;
329 }
330 ssl_rc4_crypt(rc4_decrypt_key, (char *)data, (char *)data, length);
331 sec_decrypt_use_count++;
332 }
333
334 /*static void
335 reverse(uint8 * p, int len)
336 {
337 int i, j;
338 uint8 temp;
339
340 for (i = 0, j = len - 1; i < j; i++, j--)
341 {
342 temp = p[i];
343 p[i] = p[j];
344 p[j] = temp;
345 }
346 }*/
347
348 /* Perform an RSA public key encryption operation */
349 static void
350 sec_rsa_encrypt(uint8 * out, uint8 * in, int len, uint8 * modulus, uint8 * exponent)
351 {
352 ssl_mod_exp((char *)out, 64, (char *)in, 32, (char *)modulus, 64, (char *)exponent, 4);
353 /*
354 BN_CTX *ctx;
355 BIGNUM mod, exp, x, y;
356 uint8 inr[SEC_MODULUS_SIZE];
357 int outlen;
358
359 reverse(modulus, SEC_MODULUS_SIZE);
360 reverse(exponent, SEC_EXPONENT_SIZE);
361 memcpy(inr, in, len);
362 reverse(inr, len);
363
364 ctx = BN_CTX_new();
365 BN_init(&mod);
366 BN_init(&exp);
367 BN_init(&x);
368 BN_init(&y);
369
370 BN_bin2bn(modulus, SEC_MODULUS_SIZE, &mod);
371 BN_bin2bn(exponent, SEC_EXPONENT_SIZE, &exp);
372 BN_bin2bn(inr, len, &x);
373 BN_mod_exp(&y, &x, &exp, &mod, ctx);
374 outlen = BN_bn2bin(&y, out);
375 reverse(out, outlen);
376 if (outlen < SEC_MODULUS_SIZE)
377 memset(out + outlen, 0, SEC_MODULUS_SIZE - outlen);
378
379 BN_free(&y);
380 BN_clear_free(&x);
381 BN_free(&exp);
382 BN_free(&mod);
383 BN_CTX_free(ctx);*/
384 }
385
386 /* Initialise secure transport packet */
387 STREAM
388 sec_init(uint32 flags, int maxlen)
389 {
390 int hdrlen;
391 STREAM s;
392
393 if (!g_licence_issued)
394 hdrlen = (flags & SEC_ENCRYPT) ? 12 : 4;
395 else
396 hdrlen = (flags & SEC_ENCRYPT) ? 12 : 0;
397 s = mcs_init(maxlen + hdrlen);
398 s_push_layer(s, sec_hdr, hdrlen);
399
400 return s;
401 }
402
403 /* Transmit secure transport packet over specified channel */
404 void
405 sec_send_to_channel(STREAM s, uint32 flags, uint16 channel)
406 {
407 int datalen;
408
409 s_pop_layer(s, sec_hdr);
410 if (!g_licence_issued || (flags & SEC_ENCRYPT))
411 out_uint32_le(s, flags);
412
413 if (flags & SEC_ENCRYPT)
414 {
415 flags &= ~SEC_ENCRYPT;
416 datalen = s->end - s->p - 8;
417
418 #ifdef WITH_DEBUG
419 DEBUG(("Sending encrypted packet:\n"));
420 hexdump(s->p + 8, datalen);
421 #endif
422
423 sec_sign(s->p, 8, sec_sign_key, rc4_key_len, s->p + 8, datalen);
424 sec_encrypt(s->p + 8, datalen);
425 }
426
427 mcs_send_to_channel(s, channel);
428 }
429
430 /* Transmit secure transport packet */
431
432 void
433 sec_send(STREAM s, uint32 flags)
434 {
435 sec_send_to_channel(s, flags, MCS_GLOBAL_CHANNEL);
436 }
437
438
439 /* Transfer the client random to the server */
440 static void
441 sec_establish_key(void)
442 {
443 uint32 length = SEC_MODULUS_SIZE + SEC_PADDING_SIZE;
444 uint32 flags = SEC_CLIENT_RANDOM;
445 STREAM s;
446
447 s = sec_init(flags, 76);
448
449 out_uint32_le(s, length);
450 out_uint8p(s, sec_crypted_random, SEC_MODULUS_SIZE);
451 out_uint8s(s, SEC_PADDING_SIZE);
452
453 s_mark_end(s);
454 sec_send(s, flags);
455 }
456
457 /* Output connect initial data blob */
458 static void
459 sec_out_mcs_data(STREAM s)
460 {
461 int hostlen = 2 * strlen(g_hostname);
462 int length = 158 + 76 + 12 + 4;
463 unsigned int i;
464
465 if (g_num_channels > 0)
466 length += g_num_channels * 12 + 8;
467
468 if (hostlen > 30)
469 hostlen = 30;
470
471 /* Generic Conference Control (T.124) ConferenceCreateRequest */
472 out_uint16_be(s, 5);
473 out_uint16_be(s, 0x14);
474 out_uint8(s, 0x7c);
475 out_uint16_be(s, 1);
476
477 out_uint16_be(s, (length | 0x8000)); /* remaining length */
478
479 out_uint16_be(s, 8); /* length? */
480 out_uint16_be(s, 16);
481 out_uint8(s, 0);
482 out_uint16_le(s, 0xc001);
483 out_uint8(s, 0);
484
485 out_uint32_le(s, 0x61637544); /* OEM ID: "Duca", as in Ducati. */
486 out_uint16_be(s, ((length - 14) | 0x8000)); /* remaining length */
487
488 /* Client information */
489 out_uint16_le(s, SEC_TAG_CLI_INFO);
490 out_uint16_le(s, 212); /* length */
491 out_uint16_le(s, g_use_rdp5 ? 4 : 1); /* RDP version. 1 == RDP4, 4 == RDP5. */
492 out_uint16_le(s, 8);
493 out_uint16_le(s, g_width);
494 out_uint16_le(s, g_height);
495 out_uint16_le(s, 0xca01);
496 out_uint16_le(s, 0xaa03);
497 out_uint32_le(s, g_keylayout);
498 out_uint32_le(s, 2600); /* Client build. We are now 2600 compatible :-) */
499
500 /* Unicode name of client, padded to 32 bytes */
501 rdp_out_unistr(s, g_hostname, hostlen);
502 out_uint8s(s, 30 - hostlen);
503
504 /* See
505 http://msdn.microsoft.com/library/default.asp?url=/library/en-us/wceddk40/html/cxtsksupportingremotedesktopprotocol.asp */
506 out_uint32_le(s, g_keyboard_type);
507 out_uint32_le(s, g_keyboard_subtype);
508 out_uint32_le(s, g_keyboard_functionkeys);
509 out_uint8s(s, 64); /* reserved? 4 + 12 doublewords */
510 out_uint16_le(s, 0xca01); /* colour depth? */
511 out_uint16_le(s, 1);
512
513 out_uint32(s, 0);
514 out_uint8(s, g_server_depth);
515 out_uint16_le(s, 0x0700);
516 out_uint8(s, 0);
517 out_uint32_le(s, 1);
518 out_uint8s(s, 64); /* End of client info */
519
520 out_uint16_le(s, SEC_TAG_CLI_4);
521 out_uint16_le(s, 12);
522 out_uint32_le(s, g_console_session ? 0xb : 9);
523 out_uint32(s, 0);
524
525 /* Client encryption settings */
526 out_uint16_le(s, SEC_TAG_CLI_CRYPT);
527 out_uint16_le(s, 12); /* length */
528 out_uint32_le(s, g_encryption ? 0x3 : 0); /* encryption supported, 128-bit supported */
529 out_uint32(s, 0); /* Unknown */
530
531 DEBUG_RDP5(("g_num_channels is %d\n", g_num_channels));
532 if (g_num_channels > 0)
533 {
534 out_uint16_le(s, SEC_TAG_CLI_CHANNELS);
535 out_uint16_le(s, g_num_channels * 12 + 8); /* length */
536 out_uint32_le(s, g_num_channels); /* number of virtual channels */
537 for (i = 0; i < g_num_channels; i++)
538 {
539 DEBUG_RDP5(("Requesting channel %s\n", g_channels[i].name));
540 out_uint8a(s, g_channels[i].name, 8);
541 out_uint32_be(s, g_channels[i].flags);
542 }
543 }
544
545 s_mark_end(s);
546 }
547
548 /* Parse a public key structure */
549 static BOOL
550 sec_parse_public_key(STREAM s, uint8 ** modulus, uint8 ** exponent)
551 {
552 uint32 magic, modulus_len;
553
554 in_uint32_le(s, magic);
555 if (magic != SEC_RSA_MAGIC)
556 {
557 error("RSA magic 0x%x\n", magic);
558 return False;
559 }
560
561 in_uint32_le(s, modulus_len);
562 if (modulus_len != SEC_MODULUS_SIZE + SEC_PADDING_SIZE)
563 {
564 error("modulus len 0x%x\n", modulus_len);
565 return False;
566 }
567
568 in_uint8s(s, 8); /* modulus_bits, unknown */
569 in_uint8p(s, *exponent, SEC_EXPONENT_SIZE);
570 in_uint8p(s, *modulus, SEC_MODULUS_SIZE);
571 in_uint8s(s, SEC_PADDING_SIZE);
572
573 return s_check(s);
574 }
575
576 /* Parse a crypto information structure */
577 static BOOL
578 sec_parse_crypt_info(STREAM s, uint32 * rc4_key_size,
579 uint8 ** server_random, uint8 ** modulus, uint8 ** exponent)
580 {
581 uint32 crypt_level, random_len, rsa_info_len;
582 uint32 /*cacert_len, cert_len,*/ flags;
583 //X509 *cacert, *server_cert;
584 uint16 tag, length;
585 uint8 *next_tag, *end;
586
587 in_uint32_le(s, *rc4_key_size); /* 1 = 40-bit, 2 = 128-bit */
588 in_uint32_le(s, crypt_level); /* 1 = low, 2 = medium, 3 = high */
589 if (crypt_level == 0) /* no encryption */
590 return False;
591 in_uint32_le(s, random_len);
592 in_uint32_le(s, rsa_info_len);
593
594 if (random_len != SEC_RANDOM_SIZE)
595 {
596 error("random len %d, expected %d\n", random_len, SEC_RANDOM_SIZE);
597 return False;
598 }
599
600 in_uint8p(s, *server_random, random_len);
601
602 /* RSA info */
603 end = s->p + rsa_info_len;
604 if (end > s->end)
605 return False;
606
607 in_uint32_le(s, flags); /* 1 = RDP4-style, 0x80000002 = X.509 */
608 if (flags & 1)
609 {
610 DEBUG_RDP5(("We're going for the RDP4-style encryption\n"));
611 in_uint8s(s, 8); /* unknown */
612
613 while (s->p < end)
614 {
615 in_uint16_le(s, tag);
616 in_uint16_le(s, length);
617
618 next_tag = s->p + length;
619
620 switch (tag)
621 {
622 case SEC_TAG_PUBKEY:
623 if (!sec_parse_public_key(s, modulus, exponent))
624 return False;
625 DEBUG_RDP5(("Got Public key, RDP4-style\n"));
626
627 break;
628
629 case SEC_TAG_KEYSIG:
630 /* Is this a Microsoft key that we just got? */
631 /* Care factor: zero! */
632 /* Actually, it would probably be a good idea to check if the public key is signed with this key, and then store this
633 key as a known key of the hostname. This would prevent some MITM-attacks. */
634 break;
635
636 default:
637 unimpl("crypt tag 0x%x\n", tag);
638 }
639
640 s->p = next_tag;
641 }
642 }
643 else
644 {
645 #if 0
646 uint32 certcount;
647
648 DEBUG_RDP5(("We're going for the RDP5-style encryption\n"));
649 in_uint32_le(s, certcount); /* Number of certificates */
650
651 if (certcount < 2)
652 {
653 error("Server didn't send enough X509 certificates\n");
654 return False;
655 }
656
657 for (; certcount > 2; certcount--)
658 { /* ignore all the certificates between the root and the signing CA */
659 uint32 ignorelen;
660 X509 *ignorecert;
661
662 DEBUG_RDP5(("Ignored certs left: %d\n", certcount));
663
664 in_uint32_le(s, ignorelen);
665 DEBUG_RDP5(("Ignored Certificate length is %d\n", ignorelen));
666 ignorecert = d2i_X509(NULL, &(s->p), ignorelen);
667
668 if (ignorecert == NULL)
669 { /* XXX: error out? */
670 DEBUG_RDP5(("got a bad cert: this will probably screw up the rest of the communication\n"));
671 }
672
673 #ifdef WITH_DEBUG_RDP5
674 DEBUG_RDP5(("cert #%d (ignored):\n", certcount));
675 X509_print_fp(stdout, ignorecert);
676 #endif
677 }
678
679 /* Do da funky X.509 stuffy
680
681 "How did I find out about this? I looked up and saw a
682 bright light and when I came to I had a scar on my forehead
683 and knew about X.500"
684 - Peter Gutman in a early version of
685 http://www.cs.auckland.ac.nz/~pgut001/pubs/x509guide.txt
686 */
687
688 in_uint32_le(s, cacert_len);
689 DEBUG_RDP5(("CA Certificate length is %d\n", cacert_len));
690 cacert = d2i_X509(NULL, &(s->p), cacert_len);
691 /* Note: We don't need to move s->p here - d2i_X509 is
692 "kind" enough to do it for us */
693 if (NULL == cacert)
694 {
695 error("Couldn't load CA Certificate from server\n");
696 return False;
697 }
698
699 /* Currently, we don't use the CA Certificate.
700 FIXME:
701 *) Verify the server certificate (server_cert) with the
702 CA certificate.
703 *) Store the CA Certificate with the hostname of the
704 server we are connecting to as key, and compare it
705 when we connect the next time, in order to prevent
706 MITM-attacks.
707 */
708
709 X509_free(cacert);
710
711 in_uint32_le(s, cert_len);
712 DEBUG_RDP5(("Certificate length is %d\n", cert_len));
713 server_cert = d2i_X509(NULL, &(s->p), cert_len);
714 if (NULL == server_cert)
715 {
716 error("Couldn't load Certificate from server\n");
717 return False;
718 }
719
720 in_uint8s(s, 16); /* Padding */
721
722 /* Note: Verifying the server certificate must be done here,
723 before sec_parse_public_key since we'll have to apply
724 serious violence to the key after this */
725
726 if (!sec_parse_x509_key(server_cert))
727 {
728 DEBUG_RDP5(("Didn't parse X509 correctly\n"));
729 X509_free(server_cert);
730 return False;
731 }
732 X509_free(server_cert);
733 return True; /* There's some garbage here we don't care about */
734 #endif
735 }
736 return s_check_end(s);
737 }
738
739 /* Process crypto information blob */
740 static void
741 sec_process_crypt_info(STREAM s)
742 {
743 uint8 *server_random, *modulus = NULL, *exponent = NULL;
744 uint8 client_random[SEC_RANDOM_SIZE];
745 uint32 rc4_key_size;
746 uint8 inr[SEC_MODULUS_SIZE];
747
748 if (!sec_parse_crypt_info(s, &rc4_key_size, &server_random, &modulus, &exponent))
749 {
750 DEBUG(("Failed to parse crypt info\n"));
751 return;
752 }
753
754 DEBUG(("Generating client random\n"));
755 /* Generate a client random, and hence determine encryption keys */
756 /* This is what the MS client do: */
757 memset(inr, 0, SEC_RANDOM_SIZE);
758 /* *ARIGL!* Plaintext attack, anyone?
759 I tried doing:
760 generate_random(inr);
761 ..but that generates connection errors now and then (yes,
762 "now and then". Something like 0 to 3 attempts needed before a
763 successful connection. Nice. Not!
764 */
765
766 generate_random(client_random);
767 if (NULL != server_public_key)
768 { /* Which means we should use
769 RDP5-style encryption */
770 #if 0
771 memcpy(inr + SEC_RANDOM_SIZE, client_random, SEC_RANDOM_SIZE);
772 reverse(inr + SEC_RANDOM_SIZE, SEC_RANDOM_SIZE);
773
774 RSA_public_encrypt(SEC_MODULUS_SIZE,
775 inr, sec_crypted_random, server_public_key, RSA_NO_PADDING);
776
777 reverse(sec_crypted_random, SEC_MODULUS_SIZE);
778
779 RSA_free(server_public_key);
780 server_public_key = NULL;
781 #endif
782 }
783 else
784 { /* RDP4-style encryption */
785 sec_rsa_encrypt(sec_crypted_random,
786 client_random, SEC_RANDOM_SIZE, modulus, exponent);
787 }
788 sec_generate_keys(client_random, server_random, rc4_key_size);
789 }
790
791
792 /* Process SRV_INFO, find RDP version supported by server */
793 static void
794 sec_process_srv_info(STREAM s)
795 {
796 in_uint16_le(s, g_server_rdp_version);
797 DEBUG_RDP5(("Server RDP version is %d\n", g_server_rdp_version));
798 if (1 == g_server_rdp_version)
799 {
800 g_use_rdp5 = 0;
801 g_server_depth = 8;
802 }
803 }
804
805
806 /* Process connect response data blob */
807 void
808 sec_process_mcs_data(STREAM s)
809 {
810 uint16 tag, length;
811 uint8 *next_tag;
812 uint8 len;
813
814 in_uint8s(s, 21); /* header (T.124 ConferenceCreateResponse) */
815 in_uint8(s, len);
816 if (len & 0x80)
817 in_uint8(s, len);
818
819 while (s->p < s->end)
820 {
821 in_uint16_le(s, tag);
822 in_uint16_le(s, length);
823
824 if (length <= 4)
825 return;
826
827 next_tag = s->p + length - 4;
828
829 switch (tag)
830 {
831 case SEC_TAG_SRV_INFO:
832 sec_process_srv_info(s);
833 break;
834
835 case SEC_TAG_SRV_CRYPT:
836 sec_process_crypt_info(s);
837 break;
838
839 case SEC_TAG_SRV_CHANNELS:
840 /* FIXME: We should parse this information and
841 use it to map RDP5 channels to MCS
842 channels */
843 break;
844
845 default:
846 unimpl("response tag 0x%x\n", tag);
847 }
848
849 s->p = next_tag;
850 }
851 }
852
853 /* Receive secure transport packet */
854 STREAM
855 sec_recv(uint8 * rdpver)
856 {
857 uint32 sec_flags;
858 uint16 channel;
859 STREAM s;
860
861 while ((s = mcs_recv(&channel, rdpver)) != NULL)
862 {
863 if (rdpver != NULL)
864 {
865 if (*rdpver != 3)
866 {
867 if (*rdpver & 0x80)
868 {
869 in_uint8s(s, 8); /* signature */
870 sec_decrypt(s->p, s->end - s->p);
871 }
872 return s;
873 }
874 }
875 if (g_encryption || !g_licence_issued)
876 {
877 in_uint32_le(s, sec_flags);
878
879 if (sec_flags & SEC_ENCRYPT)
880 {
881 in_uint8s(s, 8); /* signature */
882 sec_decrypt(s->p, s->end - s->p);
883 }
884
885 if (sec_flags & SEC_LICENCE_NEG)
886 {
887 licence_process(s);
888 continue;
889 }
890
891 if (sec_flags & 0x0400) /* SEC_REDIRECT_ENCRYPT */
892 {
893 uint8 swapbyte;
894
895 in_uint8s(s, 8); /* signature */
896 sec_decrypt(s->p, s->end - s->p);
897
898 /* Check for a redirect packet, starts with 00 04 */
899 if (s->p[0] == 0 && s->p[1] == 4)
900 {
901 /* for some reason the PDU and the length seem to be swapped.
902 This isn't good, but we're going to do a byte for byte
903 swap. So the first foure value appear as: 00 04 XX YY,
904 where XX YY is the little endian length. We're going to
905 use 04 00 as the PDU type, so after our swap this will look
906 like: XX YY 04 00 */
907 swapbyte = s->p[0];
908 s->p[0] = s->p[2];
909 s->p[2] = swapbyte;
910
911 swapbyte = s->p[1];
912 s->p[1] = s->p[3];
913 s->p[3] = swapbyte;
914
915 swapbyte = s->p[2];
916 s->p[2] = s->p[3];
917 s->p[3] = swapbyte;
918 }
919 #ifdef WITH_DEBUG
920 /* warning! this debug statement will show passwords in the clear! */
921 hexdump(s->p, s->end - s->p);
922 #endif
923 }
924
925 }
926
927 if (channel != MCS_GLOBAL_CHANNEL)
928 {
929 channel_process(s, channel);
930 *rdpver = 0xff;
931 return s;
932 }
933
934 return s;
935 }
936
937 return NULL;
938 }
939
940 /* Establish a secure connection */
941 BOOL
942 sec_connect(char *server, char *username)
943 {
944 struct stream mcs_data;
945
946 /* We exchange some RDP data during the MCS-Connect */
947 mcs_data.size = 512;
948 mcs_data.p = mcs_data.data = (uint8 *) xmalloc(mcs_data.size);
949 sec_out_mcs_data(&mcs_data);
950
951 if (!mcs_connect(server, &mcs_data, username))
952 return False;
953
954 /* sec_process_mcs_data(&mcs_data); */
955 if (g_encryption)
956 sec_establish_key();
957 xfree(mcs_data.data);
958 return True;
959 }
960
961 /* Establish a secure connection */
962 BOOL
963 sec_reconnect(char *server)
964 {
965 struct stream mcs_data;
966
967 /* We exchange some RDP data during the MCS-Connect */
968 mcs_data.size = 512;
969 mcs_data.p = mcs_data.data = (uint8 *) xmalloc(mcs_data.size);
970 sec_out_mcs_data(&mcs_data);
971
972 if (!mcs_reconnect(server, &mcs_data))
973 return False;
974
975 /* sec_process_mcs_data(&mcs_data); */
976 if (g_encryption)
977 sec_establish_key();
978 xfree(mcs_data.data);
979 return True;
980 }
981
982 /* Disconnect a connection */
983 void
984 sec_disconnect(void)
985 {
986 mcs_disconnect();
987 }
988
989 /* reset the state of the sec layer */
990 void
991 sec_reset_state(void)
992 {
993 g_server_rdp_version = 0;
994 sec_encrypt_use_count = 0;
995 sec_decrypt_use_count = 0;
996 mcs_reset_state();
997 }