1 /* -*- c-basic-offset: 8 -*-
2 rdesktop: A Remote Desktop Protocol client.
3 Protocol services - RDP encryption and licensing
4 Copyright (C) Matthew Chapman <matthewc.unsw.edu.au> 1999-2008
5 Copyright 2005-2011 Peter Astrand <astrand@cendio.se> for Cendio AB
7 This program is free software: you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation, either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
24 rdssl_sha1_info_create(void);
26 rdssl_sha1_info_delete(void * sha1_info
);
28 rdssl_sha1_clear(void * sha1_info
);
30 rdssl_sha1_transform(void * sha1_info
, char * data
, int len
);
32 rdssl_sha1_complete(void * sha1_info
, char * data
);
34 rdssl_md5_info_create(void);
36 rdssl_md5_info_delete(void * md5_info
);
38 rdssl_md5_info_create(void);
40 rdssl_md5_info_delete(void * md5_info
);
42 rdssl_md5_clear(void * md5_info
);
44 rdssl_md5_transform(void * md5_info
, char * data
, int len
);
46 rdssl_md5_complete(void * md5_info
, char * data
);
48 rdssl_rc4_info_create(void);
50 rdssl_rc4_info_delete(void * rc4_info
);
52 rdssl_rc4_set_key(void * rc4_info
, char * key
, int len
);
54 rdssl_rc4_crypt(void * rc4_info
, char * in_data
, char * out_data
, int len
);
56 rdssl_mod_exp(char* out
, int out_len
, char* in
, int in_len
,
57 char* mod
, int mod_len
, char* exp
, int exp_len
);
59 rdssl_sign_ok(char* e_data
, int e_len
, char* n_data
, int n_len
,
60 char* sign_data
, int sign_len
, char* sign_data2
, int sign_len2
, char* testkey
);
62 extern char g_hostname
[16];
65 extern unsigned int g_keylayout
;
66 extern int g_keyboard_type
;
67 extern int g_keyboard_subtype
;
68 extern int g_keyboard_functionkeys
;
69 extern RD_BOOL g_encryption
;
70 extern RD_BOOL g_licence_issued
;
71 extern RD_BOOL g_licence_error_result
;
72 extern RDP_VERSION g_rdp_version
;
73 extern RD_BOOL g_console_session
;
74 extern uint32 g_redirect_session_id
;
75 extern int g_server_depth
;
76 extern VCHANNEL g_channels
[];
77 extern unsigned int g_num_channels
;
78 extern uint8 g_client_random
[SEC_RANDOM_SIZE
];
80 static int g_rc4_key_len
;
81 static void * g_rc4_decrypt_key
;
82 static void * g_rc4_encrypt_key
;
83 static uint32 g_server_public_key_len
;
85 static uint8 g_sec_sign_key
[16];
86 static uint8 g_sec_decrypt_key
[16];
87 static uint8 g_sec_encrypt_key
[16];
88 static uint8 g_sec_decrypt_update_key
[16];
89 static uint8 g_sec_encrypt_update_key
[16];
90 static uint8 g_sec_crypted_random
[SEC_MAX_MODULUS_SIZE
];
92 uint16 g_server_rdp_version
= 0;
94 /* These values must be available to reset state - Session Directory */
95 static int g_sec_encrypt_use_count
= 0;
96 static int g_sec_decrypt_use_count
= 0;
98 #define SEC_MODULUS_SIZE 64
100 static uint8 g_testkey
[176] =
102 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
103 0x01, 0x00, 0x00, 0x00, 0x06, 0x00, 0x5c, 0x00,
104 0x52, 0x53, 0x41, 0x31, 0x48, 0x00, 0x00, 0x00,
105 0x00, 0x02, 0x00, 0x00, 0x3f, 0x00, 0x00, 0x00,
106 0x01, 0x00, 0x01, 0x00, 0x79, 0x6f, 0xb4, 0xdf,
107 0xa6, 0x95, 0xb9, 0xa9, 0x61, 0xe3, 0xc4, 0x5e,
108 0xff, 0x6b, 0xd8, 0x81, 0x8a, 0x12, 0x4a, 0x93,
109 0x42, 0x97, 0x18, 0x93, 0xac, 0xd1, 0x3a, 0x38,
110 0x3c, 0x68, 0x50, 0x19, 0x31, 0xb6, 0x84, 0x51,
111 0x79, 0xfb, 0x1c, 0xe7, 0xe3, 0x99, 0x20, 0xc7,
112 0x84, 0xdf, 0xd1, 0xaa, 0xb5, 0x15, 0xef, 0x47,
113 0x7e, 0xfc, 0x88, 0xeb, 0x29, 0xc3, 0x27, 0x5a,
114 0x35, 0xf8, 0xfd, 0xaa, 0x00, 0x00, 0x00, 0x00,
115 0x00, 0x00, 0x00, 0x00,
116 0x08, 0x00, 0x48, 0x00,
117 0x32, 0x3b, 0xde, 0x6f, 0x18, 0x97, 0x1e, 0xc3,
118 0x6b, 0x2b, 0x2d, 0xe4, 0xfc, 0x2d, 0xa2, 0x8e,
119 0x32, 0x3c, 0xf3, 0x1b, 0x24, 0x90, 0x57, 0x4d,
120 0x8e, 0xe4, 0x69, 0xfc, 0x16, 0x8d, 0x41, 0x92,
121 0x78, 0xc7, 0x9c, 0xb4, 0x26, 0xff, 0xe8, 0x3e,
122 0xa1, 0x8a, 0xf5, 0x57, 0xc0, 0x7f, 0x3e, 0x21,
123 0x17, 0x32, 0x30, 0x6f, 0x79, 0xe1, 0x36, 0xcd,
124 0xb6, 0x8e, 0xbe, 0x57, 0x57, 0xd2, 0xa9, 0x36
128 * I believe this is based on SSLv3 with the following differences:
129 * MAC algorithm (5.2.3.1) uses only 32-bit length in place of seq_num/type/length fields
130 * MAC algorithm uses SHA1 and MD5 for the two hash functions instead of one or other
131 * key_block algorithm (6.2.2) uses 'X', 'YY', 'ZZZ' instead of 'A', 'BB', 'CCC'
132 * key_block partitioning is different (16 bytes each: MAC secret, decrypt key, encrypt key)
133 * encryption/decryption keys updated every 4096 packets
134 * See http://wp.netscape.com/eng/ssl3/draft302.txt
138 * 48-byte transformation used to generate master secret (6.1) and key material (6.2.2).
139 * Both SHA1 and MD5 algorithms are used.
142 sec_hash_48(uint8
* out
, uint8
* in
, uint8
* salt1
, uint8
* salt2
, uint8 salt
)
150 for (i
= 0; i
< 3; i
++)
152 memset(pad
, salt
+ i
, i
+ 1);
153 sha
= rdssl_sha1_info_create();
154 rdssl_sha1_clear(sha
);
155 rdssl_sha1_transform(sha
, (char *)pad
, i
+ 1);
156 rdssl_sha1_transform(sha
, (char *)in
, 48);
157 rdssl_sha1_transform(sha
, (char *)salt1
, 32);
158 rdssl_sha1_transform(sha
, (char *)salt2
, 32);
159 rdssl_sha1_complete(sha
, (char *)shasig
);
160 rdssl_sha1_info_delete(sha
);
161 md5
= rdssl_md5_info_create();
162 rdssl_md5_clear(md5
);
163 rdssl_md5_transform(md5
, (char *)in
, 48);
164 rdssl_md5_transform(md5
, (char *)shasig
, 20);
165 rdssl_md5_complete(md5
, (char *)out
+ i
* 16);
166 rdssl_md5_info_delete(md5
);
171 * 16-byte transformation used to generate export keys (6.2.2).
174 sec_hash_16(uint8
* out
, uint8
* in
, uint8
* salt1
, uint8
* salt2
)
178 md5
= rdssl_md5_info_create();
179 rdssl_md5_clear(md5
);
180 rdssl_md5_transform(md5
, (char *)in
, 16);
181 rdssl_md5_transform(md5
, (char *)salt1
, 32);
182 rdssl_md5_transform(md5
, (char *)salt2
, 32);
183 rdssl_md5_complete(md5
, (char *)out
);
184 rdssl_md5_info_delete(md5
);
191 sec_hash_sha1_16(uint8
* out
, uint8
* in
, uint8
* salt1
)
194 sha
= rdssl_sha1_info_create();
195 rdssl_sha1_clear(sha
);
196 rdssl_sha1_transform(&sha
, (char *)in
, 16);
197 rdssl_sha1_transform(&sha
, (char *)salt1
, 16);
198 rdssl_sha1_complete(&sha
, (char *)out
);
199 rdssl_sha1_info_delete(sha
);
202 /* create string from hash */
204 sec_hash_to_string(char *out
, int out_size
, uint8
* in
, int in_size
)
207 memset(out
, 0, out_size
);
208 for (k
= 0; k
< in_size
; k
++, out
+= 2)
210 sprintf(out
, "%.2x", in
[k
]);
214 /* Reduce key entropy from 64 to 40 bits */
216 sec_make_40bit(uint8
* key
)
223 /* Generate encryption keys given client and server randoms */
225 sec_generate_keys(uint8
* client_random
, uint8
* server_random
, int rc4_key_size
)
227 uint8 pre_master_secret
[48];
228 uint8 master_secret
[48];
231 /* Construct pre-master secret */
232 memcpy(pre_master_secret
, client_random
, 24);
233 memcpy(pre_master_secret
+ 24, server_random
, 24);
235 /* Generate master secret and then key material */
236 sec_hash_48(master_secret
, pre_master_secret
, client_random
, server_random
, 'A');
237 sec_hash_48(key_block
, master_secret
, client_random
, server_random
, 'X');
239 /* First 16 bytes of key material is MAC secret */
240 memcpy(g_sec_sign_key
, key_block
, 16);
242 /* Generate export keys from next two blocks of 16 bytes */
243 sec_hash_16(g_sec_decrypt_key
, &key_block
[16], client_random
, server_random
);
244 sec_hash_16(g_sec_encrypt_key
, &key_block
[32], client_random
, server_random
);
246 if (rc4_key_size
== 1)
248 DEBUG(("40-bit encryption enabled\n"));
249 sec_make_40bit(g_sec_sign_key
);
250 sec_make_40bit(g_sec_decrypt_key
);
251 sec_make_40bit(g_sec_encrypt_key
);
256 DEBUG(("rc_4_key_size == %d, 128-bit encryption enabled\n", rc4_key_size
));
260 /* Save initial RC4 keys as update keys */
261 memcpy(g_sec_decrypt_update_key
, g_sec_decrypt_key
, 16);
262 memcpy(g_sec_encrypt_update_key
, g_sec_encrypt_key
, 16);
264 /* Initialise RC4 state arrays */
266 rdssl_rc4_info_delete(g_rc4_decrypt_key
);
267 g_rc4_decrypt_key
= rdssl_rc4_info_create();
268 rdssl_rc4_set_key(g_rc4_decrypt_key
, (char *)g_sec_decrypt_key
, g_rc4_key_len
);
270 rdssl_rc4_info_delete(g_rc4_encrypt_key
);
271 g_rc4_encrypt_key
= rdssl_rc4_info_create();
272 rdssl_rc4_set_key(g_rc4_encrypt_key
, (char *)g_sec_encrypt_key
, g_rc4_key_len
);
275 static uint8 pad_54
[40] = {
276 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54,
278 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54,
282 static uint8 pad_92
[48] = {
283 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92,
284 92, 92, 92, 92, 92, 92, 92,
285 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92,
286 92, 92, 92, 92, 92, 92, 92
289 /* Output a uint32 into a buffer (little-endian) */
291 buf_out_uint32(uint8
* buffer
, uint32 value
)
293 buffer
[0] = (value
) & 0xff;
294 buffer
[1] = (value
>> 8) & 0xff;
295 buffer
[2] = (value
>> 16) & 0xff;
296 buffer
[3] = (value
>> 24) & 0xff;
299 /* Generate a MAC hash (5.2.3.1), using a combination of SHA1 and MD5 */
301 sec_sign(uint8
* signature
, int siglen
, uint8
* session_key
, int keylen
, uint8
* data
, int datalen
)
309 buf_out_uint32(lenhdr
, datalen
);
311 sha
= rdssl_sha1_info_create();
312 rdssl_sha1_clear(sha
);
313 rdssl_sha1_transform(sha
, (char *)session_key
, keylen
);
314 rdssl_sha1_transform(sha
, (char *)pad_54
, 40);
315 rdssl_sha1_transform(sha
, (char *)lenhdr
, 4);
316 rdssl_sha1_transform(sha
, (char *)data
, datalen
);
317 rdssl_sha1_complete(sha
, (char *)shasig
);
318 rdssl_sha1_info_delete(sha
);
320 md5
= rdssl_md5_info_create();
321 rdssl_md5_clear(md5
);
322 rdssl_md5_transform(md5
, (char *)session_key
, keylen
);
323 rdssl_md5_transform(md5
, (char *)pad_92
, 48);
324 rdssl_md5_transform(md5
, (char *)shasig
, 20);
325 rdssl_md5_complete(md5
, (char *)md5sig
);
326 rdssl_md5_info_delete(md5
);
328 memcpy(signature
, md5sig
, siglen
);
331 /* Update an encryption key */
333 sec_update(uint8
* key
, uint8
* update_key
)
340 sha
= rdssl_sha1_info_create();
341 rdssl_sha1_clear(sha
);
342 rdssl_sha1_transform(sha
, (char *)update_key
, g_rc4_key_len
);
343 rdssl_sha1_transform(sha
, (char *)pad_54
, 40);
344 rdssl_sha1_transform(sha
, (char *)key
, g_rc4_key_len
);
345 rdssl_sha1_complete(sha
, (char *)shasig
);
346 rdssl_sha1_info_delete(sha
);
348 md5
= rdssl_md5_info_create();
349 rdssl_md5_clear(md5
);
350 rdssl_md5_transform(md5
, (char *)update_key
, g_rc4_key_len
);
351 rdssl_md5_transform(md5
, (char *)pad_92
, 48);
352 rdssl_md5_transform(md5
, (char *)shasig
, 20);
353 rdssl_md5_complete(md5
, (char *)key
);
354 rdssl_md5_info_delete(md5
);
357 update
= rdssl_rc4_info_create();
358 rdssl_rc4_set_key(update
, (char *)key
, g_rc4_key_len
);
359 rdssl_rc4_crypt(update
, (char *)key
, (char *)key
, g_rc4_key_len
);
360 rdssl_rc4_info_delete(update
);
362 if (g_rc4_key_len
== 8)
366 /* Encrypt data using RC4 */
368 sec_encrypt(uint8
* data
, int length
)
370 if (g_sec_encrypt_use_count
== 4096)
372 sec_update(g_sec_encrypt_key
, g_sec_encrypt_update_key
);
373 rdssl_rc4_set_key(g_rc4_encrypt_key
, (char *)g_sec_encrypt_key
, g_rc4_key_len
);
374 g_sec_encrypt_use_count
= 0;
377 rdssl_rc4_crypt(g_rc4_encrypt_key
, (char *)data
, (char *)data
, length
);
378 g_sec_encrypt_use_count
++;
381 /* Decrypt data using RC4 */
383 sec_decrypt(uint8
* data
, int length
)
385 if (g_sec_decrypt_use_count
== 4096)
387 sec_update(g_sec_decrypt_key
, g_sec_decrypt_update_key
);
388 rdssl_rc4_set_key(g_rc4_decrypt_key
, (char *)g_sec_decrypt_key
, g_rc4_key_len
);
389 g_sec_decrypt_use_count
= 0;
392 rdssl_rc4_crypt(g_rc4_decrypt_key
,(char *)data
, (char *)data
, length
);
393 g_sec_decrypt_use_count
++;
396 /* Perform an RSA public key encryption operation */
398 sec_rsa_encrypt(uint8
* out
, uint8
* in
, int len
, uint32 modulus_size
, uint8
* modulus
,
401 rdssl_mod_exp((char *)out
, 64, (char *)in
, 32, (char *)modulus
, 64, (char *)exponent
, 4);
404 /* Initialise secure transport packet */
406 sec_init(uint32 flags
, int maxlen
)
411 if (!g_licence_issued
&& !g_licence_error_result
)
412 hdrlen
= (flags
& SEC_ENCRYPT
) ? 12 : 4;
414 hdrlen
= (flags
& SEC_ENCRYPT
) ? 12 : 0;
415 s
= mcs_init(maxlen
+ hdrlen
);
416 s_push_layer(s
, sec_hdr
, hdrlen
);
421 /* Transmit secure transport packet over specified channel */
423 sec_send_to_channel(STREAM s
, uint32 flags
, uint16 channel
)
428 scard_lock(SCARD_LOCK_SEC
);
431 s_pop_layer(s
, sec_hdr
);
432 if ((!g_licence_issued
&& !g_licence_error_result
) || (flags
& SEC_ENCRYPT
))
433 out_uint32_le(s
, flags
);
435 if (flags
& SEC_ENCRYPT
)
437 flags
&= ~SEC_ENCRYPT
;
438 datalen
= s
->end
- s
->p
- 8;
441 DEBUG(("Sending encrypted packet:\n"));
442 hexdump(s
->p
+ 8, datalen
);
445 sec_sign(s
->p
, 8, g_sec_sign_key
, g_rc4_key_len
, s
->p
+ 8, datalen
);
446 sec_encrypt(s
->p
+ 8, datalen
);
449 mcs_send_to_channel(s
, channel
);
452 scard_unlock(SCARD_LOCK_SEC
);
456 /* Transmit secure transport packet */
459 sec_send(STREAM s
, uint32 flags
)
461 sec_send_to_channel(s
, flags
, MCS_GLOBAL_CHANNEL
);
465 /* Transfer the client random to the server */
467 sec_establish_key(void)
469 uint32 length
= g_server_public_key_len
+ SEC_PADDING_SIZE
;
470 uint32 flags
= SEC_EXCHANGE_PKT
;
473 s
= sec_init(flags
, length
+ 4);
475 out_uint32_le(s
, length
);
476 out_uint8p(s
, g_sec_crypted_random
, g_server_public_key_len
);
477 out_uint8s(s
, SEC_PADDING_SIZE
);
483 /* Output connect initial data blob */
485 sec_out_mcs_data(STREAM s
, uint32 selected_protocol
)
487 int hostlen
= 2 * strlen(g_hostname
);
488 int length
= 162 + 76 + 12 + 4;
490 uint32 cluster_flags
= 0;
492 if (g_num_channels
> 0)
493 length
+= g_num_channels
* 12 + 8;
498 /* Generic Conference Control (T.124) ConferenceCreateRequest */
500 out_uint16_be(s
, 0x14);
504 out_uint16_be(s
, (length
| 0x8000)); /* remaining length */
506 out_uint16_be(s
, 8); /* length? */
507 out_uint16_be(s
, 16);
509 out_uint16_le(s
, 0xc001);
512 out_uint32_le(s
, 0x61637544); /* OEM ID: "Duca", as in Ducati. */
513 out_uint16_be(s
, ((length
- 14) | 0x8000)); /* remaining length */
515 /* Client information */
516 out_uint16_le(s
, SEC_TAG_CLI_INFO
);
517 out_uint16_le(s
, 216); /* length */
518 out_uint16_le(s
, (g_rdp_version
>= RDP_V5
) ? 4 : 1); /* RDP version. 1 == RDP4, 4 >= RDP5 to RDP8 */
520 out_uint16_le(s
, g_width
);
521 out_uint16_le(s
, g_height
);
522 out_uint16_le(s
, 0xca01);
523 out_uint16_le(s
, 0xaa03);
524 out_uint32_le(s
, g_keylayout
);
525 out_uint32_le(s
, 2600); /* Client build. We are now 2600 compatible :-) */
527 /* Unicode name of client, padded to 32 bytes */
528 rdp_out_unistr(s
, g_hostname
, hostlen
);
529 out_uint8s(s
, 30 - hostlen
);
532 http://msdn.microsoft.com/library/default.asp?url=/library/en-us/wceddk40/html/cxtsksupportingremotedesktopprotocol.asp */
533 out_uint32_le(s
, g_keyboard_type
);
534 out_uint32_le(s
, g_keyboard_subtype
);
535 out_uint32_le(s
, g_keyboard_functionkeys
);
536 out_uint8s(s
, 64); /* reserved? 4 + 12 doublewords */
537 out_uint16_le(s
, 0xca01); /* colour depth? */
541 out_uint8(s
, g_server_depth
);
542 out_uint16_le(s
, 0x0700);
546 out_uint32_le(s
, selected_protocol
); /* End of client info */
548 /* Write a Client Cluster Data (TS_UD_CS_CLUSTER) */
549 out_uint16_le(s
, SEC_TAG_CLI_CLUSTER
); /* header.type */
550 out_uint16_le(s
, 12); /* length */
552 cluster_flags
|= SEC_CC_REDIRECTION_SUPPORTED
;
553 cluster_flags
|= (SEC_CC_REDIRECT_VERSION_3
<< 2);
555 if (g_console_session
|| g_redirect_session_id
!= 0)
556 cluster_flags
|= SEC_CC_REDIRECT_SESSIONID_FIELD_VALID
;
558 out_uint32_le(s
, cluster_flags
);
559 out_uint32(s
, g_redirect_session_id
);
561 /* Client encryption settings */
562 out_uint16_le(s
, SEC_TAG_CLI_CRYPT
);
563 out_uint16_le(s
, 12); /* length */
564 out_uint32_le(s
, g_encryption
? 0x3 : 0); /* encryption supported, 128-bit supported */
565 out_uint32(s
, 0); /* Unknown */
567 DEBUG_RDP5(("g_num_channels is %d\n", g_num_channels
));
568 if (g_num_channels
> 0)
570 out_uint16_le(s
, SEC_TAG_CLI_CHANNELS
);
571 out_uint16_le(s
, g_num_channels
* 12 + 8); /* length */
572 out_uint32_le(s
, g_num_channels
); /* number of virtual channels */
573 for (i
= 0; i
< g_num_channels
; i
++)
575 DEBUG_RDP5(("Requesting channel %s\n", g_channels
[i
].name
));
576 out_uint8a(s
, g_channels
[i
].name
, 8);
577 out_uint32_be(s
, g_channels
[i
].flags
);
584 /* Parse a public key structure */
586 sec_parse_public_key(STREAM s
, uint8
* modulus
, uint8
* exponent
)
588 uint32 magic
, modulus_len
;
590 in_uint32_le(s
, magic
);
591 if (magic
!= SEC_RSA_MAGIC
)
593 error("RSA magic 0x%x\n", magic
);
597 in_uint32_le(s
, modulus_len
);
598 modulus_len
-= SEC_PADDING_SIZE
;
599 if ((modulus_len
< SEC_MODULUS_SIZE
) || (modulus_len
> SEC_MAX_MODULUS_SIZE
))
601 error("Bad server public key size (%u bits)\n", modulus_len
* 8);
605 in_uint8s(s
, 8); /* modulus_bits, unknown */
606 in_uint8a(s
, exponent
, SEC_EXPONENT_SIZE
);
607 in_uint8a(s
, modulus
, modulus_len
);
608 in_uint8s(s
, SEC_PADDING_SIZE
);
609 g_server_public_key_len
= modulus_len
;
614 /* Parse a public signature structure */
616 sec_parse_public_sig(STREAM s
, uint32 len
, uint8
* modulus
, uint8
* exponent
)
618 uint8 signature
[SEC_MAX_MODULUS_SIZE
];
619 uint8 signature_
[SEC_MAX_MODULUS_SIZE
];
626 memset(signature
, 0, sizeof(signature
));
628 in_uint8a(s
, signature
, sig_len
);
629 if(rdssl_sign_ok((char *)exponent
, SEC_EXPONENT_SIZE
, (char *)modulus
, g_server_public_key_len
,
630 (char *)signature_
, SEC_MODULUS_SIZE
, (char *)signature
, sig_len
, (char *)g_testkey
))
632 DEBUG_RDP5(("key signature doesn't match test key\n"));
637 /* Parse a crypto information structure */
639 sec_parse_crypt_info(STREAM s
, uint32
* rc4_key_size
,
640 uint8
** server_random
, uint8
* modulus
, uint8
* exponent
)
642 uint32 crypt_level
, random_len
, rsa_info_len
;
643 uint32
/*cacert_len, cert_len,*/ flags
;
644 //RDSSL_CERT *cacert, *server_cert;
645 //RDSSL_RKEY *server_public_key;
647 uint8
*next_tag
, *end
;
649 in_uint32_le(s
, *rc4_key_size
); /* 1 = 40-bit, 2 = 128-bit */
650 in_uint32_le(s
, crypt_level
); /* 1 = low, 2 = medium, 3 = high */
651 if (crypt_level
== 0)
657 in_uint32_le(s
, random_len
);
658 in_uint32_le(s
, rsa_info_len
);
660 if (random_len
!= SEC_RANDOM_SIZE
)
662 error("random len %d, expected %d\n", random_len
, SEC_RANDOM_SIZE
);
666 in_uint8p(s
, *server_random
, random_len
);
669 end
= s
->p
+ rsa_info_len
;
673 in_uint32_le(s
, flags
); /* 1 = RDP4-style, 0x80000002 = X.509 */
676 DEBUG_RDP5(("We're going for the RDP4-style encryption\n"));
677 in_uint8s(s
, 8); /* unknown */
681 in_uint16_le(s
, tag
);
682 in_uint16_le(s
, length
);
684 next_tag
= s
->p
+ length
;
689 if (!sec_parse_public_key(s
, modulus
, exponent
))
691 DEBUG_RDP5(("Got Public key, RDP4-style\n"));
696 if (!sec_parse_public_sig(s
, length
, modulus
, exponent
))
701 unimpl("crypt tag 0x%x\n", tag
);
712 DEBUG_RDP5(("We're going for the RDP5-style encryption\n"));
713 in_uint32_le(s
, certcount
); /* Number of certificates */
716 error("Server didn't send enough X509 certificates\n");
719 for (; certcount
> 2; certcount
--)
720 { /* ignore all the certificates between the root and the signing CA */
722 RDSSL_CERT
*ignorecert
;
724 DEBUG_RDP5(("Ignored certs left: %d\n", certcount
));
725 in_uint32_le(s
, ignorelen
);
726 DEBUG_RDP5(("Ignored Certificate length is %d\n", ignorelen
));
727 ignorecert
= rdssl_cert_read(s
->p
, ignorelen
);
728 in_uint8s(s
, ignorelen
);
729 if (ignorecert
== NULL
)
730 { /* XXX: error out? */
731 DEBUG_RDP5(("got a bad cert: this will probably screw up the rest of the communication\n"));
734 #ifdef WITH_DEBUG_RDP5
735 DEBUG_RDP5(("cert #%d (ignored):\n", certcount
));
736 rdssl_cert_print_fp(stdout
, ignorecert
);
739 /* Do da funky X.509 stuffy
741 "How did I find out about this? I looked up and saw a
742 bright light and when I came to I had a scar on my forehead
743 and knew about X.500"
744 - Peter Gutman in a early version of
745 http://www.cs.auckland.ac.nz/~pgut001/pubs/x509guide.txt
747 in_uint32_le(s
, cacert_len
);
748 DEBUG_RDP5(("CA Certificate length is %d\n", cacert_len
));
749 cacert
= rdssl_cert_read(s
->p
, cacert_len
);
750 in_uint8s(s
, cacert_len
);
753 error("Couldn't load CA Certificate from server\n");
756 in_uint32_le(s
, cert_len
);
757 DEBUG_RDP5(("Certificate length is %d\n", cert_len
));
758 server_cert
= rdssl_cert_read(s
->p
, cert_len
);
759 in_uint8s(s
, cert_len
);
760 if (NULL
== server_cert
)
762 rdssl_cert_free(cacert
);
763 error("Couldn't load Certificate from server\n");
766 if (!rdssl_certs_ok(server_cert
, cacert
))
768 rdssl_cert_free(server_cert
);
769 rdssl_cert_free(cacert
);
770 error("Security error CA Certificate invalid\n");
773 rdssl_cert_free(cacert
);
774 in_uint8s(s
, 16); /* Padding */
775 server_public_key
= rdssl_cert_to_rkey(server_cert
, &g_server_public_key_len
);
776 if (NULL
== server_public_key
)
778 DEBUG_RDP5(("Didn't parse X509 correctly\n"));
779 rdssl_cert_free(server_cert
);
782 rdssl_cert_free(server_cert
);
783 if ((g_server_public_key_len
< SEC_MODULUS_SIZE
) ||
784 (g_server_public_key_len
> SEC_MAX_MODULUS_SIZE
))
786 error("Bad server public key size (%u bits)\n",
787 g_server_public_key_len
* 8);
788 rdssl_rkey_free(server_public_key
);
791 if (rdssl_rkey_get_exp_mod(server_public_key
, exponent
, SEC_EXPONENT_SIZE
,
792 modulus
, SEC_MAX_MODULUS_SIZE
) != 0)
794 error("Problem extracting RSA exponent, modulus");
795 rdssl_rkey_free(server_public_key
);
798 rdssl_rkey_free(server_public_key
);
799 return True
; /* There's some garbage here we don't care about */
802 return s_check_end(s
);
805 /* Process crypto information blob */
807 sec_process_crypt_info(STREAM s
)
809 uint8
*server_random
= NULL
;
810 uint8 modulus
[SEC_MAX_MODULUS_SIZE
];
811 uint8 exponent
[SEC_EXPONENT_SIZE
];
814 memset(modulus
, 0, sizeof(modulus
));
815 memset(exponent
, 0, sizeof(exponent
));
816 if (!sec_parse_crypt_info(s
, &rc4_key_size
, &server_random
, modulus
, exponent
))
818 DEBUG(("Failed to parse crypt info\n"));
821 DEBUG(("Generating client random\n"));
822 generate_random(g_client_random
);
823 sec_rsa_encrypt(g_sec_crypted_random
, g_client_random
, SEC_RANDOM_SIZE
,
824 g_server_public_key_len
, modulus
, exponent
);
825 sec_generate_keys(g_client_random
, server_random
, rc4_key_size
);
829 /* Process SRV_INFO, find RDP version supported by server */
831 sec_process_srv_info(STREAM s
)
833 in_uint16_le(s
, g_server_rdp_version
);
834 DEBUG_RDP5(("Server RDP version is %d\n", g_server_rdp_version
));
835 if (1 == g_server_rdp_version
)
837 g_rdp_version
= RDP_V4
;
843 /* Process connect response data blob */
845 sec_process_mcs_data(STREAM s
)
851 in_uint8s(s
, 21); /* header (T.124 ConferenceCreateResponse) */
856 while (s
->p
< s
->end
)
858 in_uint16_le(s
, tag
);
859 in_uint16_le(s
, length
);
864 next_tag
= s
->p
+ length
- 4;
868 case SEC_TAG_SRV_INFO
:
869 sec_process_srv_info(s
);
872 case SEC_TAG_SRV_CRYPT
:
873 sec_process_crypt_info(s
);
876 case SEC_TAG_SRV_CHANNELS
:
877 /* FIXME: We should parse this information and
878 use it to map RDP5 channels to MCS
883 unimpl("response tag 0x%x\n", tag
);
890 /* Receive secure transport packet */
892 sec_recv(uint8
* rdpver
)
895 /* uint16 sec_flags_hi; */
899 while ((s
= mcs_recv(&channel
, rdpver
)) != NULL
)
907 in_uint8s(s
, 8); /* signature */
908 sec_decrypt(s
->p
, s
->end
- s
->p
);
913 if (g_encryption
|| (!g_licence_issued
&& !g_licence_error_result
))
915 /* TS_SECURITY_HEADER */
916 in_uint16_le(s
, sec_flags
);
917 in_uint8s(s
, 2); /* sec_flags_hi */
921 if (sec_flags
& SEC_ENCRYPT
)
923 in_uint8s(s
, 8); /* signature */
924 sec_decrypt(s
->p
, s
->end
- s
->p
);
927 if (sec_flags
& SEC_LICENSE_PKT
)
933 if (sec_flags
& SEC_REDIRECTION_PKT
) /* SEC_REDIRECT_ENCRYPT */
937 in_uint8s(s
, 8); /* signature */
938 sec_decrypt(s
->p
, s
->end
- s
->p
);
940 /* Check for a redirect packet, starts with 00 04 */
941 if (s
->p
[0] == 0 && s
->p
[1] == 4)
943 /* for some reason the PDU and the length seem to be swapped.
944 This isn't good, but we're going to do a byte for byte
945 swap. So the first four values appear as: 00 04 XX YY,
946 where XX YY is the little endian length. We're going to
947 use 04 00 as the PDU type, so after our swap this will look
962 /* warning! this debug statement will show passwords in the clear! */
963 hexdump(s
->p
, s
->end
- s
->p
);
969 if (sec_flags
& SEC_LICENSE_PKT
)
978 if (channel
!= MCS_GLOBAL_CHANNEL
)
980 channel_process(s
, channel
);
992 /* Establish a secure connection */
994 sec_connect(char *server
, char *username
, char *domain
, char *password
, RD_BOOL reconnect
)
996 uint32 selected_proto
;
997 struct stream mcs_data
;
999 /* Start a MCS connect sequence */
1000 if (!mcs_connect_start(server
, username
, domain
, password
, reconnect
, &selected_proto
))
1003 /* We exchange some RDP data during the MCS-Connect */
1004 mcs_data
.size
= 512;
1005 mcs_data
.p
= mcs_data
.data
= (uint8
*) xmalloc(mcs_data
.size
);
1006 sec_out_mcs_data(&mcs_data
, selected_proto
);
1008 /* finalize the MCS connect sequence */
1009 if (!mcs_connect_finalize(&mcs_data
))
1012 /* sec_process_mcs_data(&mcs_data); */
1014 sec_establish_key();
1015 xfree(mcs_data
.data
);
1019 /* Disconnect a connection */
1021 sec_disconnect(void)
1026 /* reset the state of the sec layer */
1028 sec_reset_state(void)
1030 g_server_rdp_version
= 0;
1031 g_sec_encrypt_use_count
= 0;
1032 g_sec_decrypt_use_count
= 0;
1033 g_licence_issued
= 0;
1034 g_licence_error_result
= 0;