From b2ba81e761f476dd86ceceab2654d7cca6e00c0f Mon Sep 17 00:00:00 2001 From: vysheng Date: Wed, 25 Dec 2013 03:42:05 +0400 Subject: [PATCH] Fixed random on sensible parts (generation auth_key, session_id and keys for secret chats) --- main.c | 4 ++++ mtproto-client.c | 19 ++++++++++++++----- mtproto-client.h | 1 + queries.c | 6 ++++-- 4 files changed, 23 insertions(+), 7 deletions(-) diff --git a/main.c b/main.c index 1de65d8..f0cd56d 100644 --- a/main.c +++ b/main.c @@ -78,6 +78,7 @@ char *binlog_file_name; int binlog_enabled; extern int log_level; int sync_from_start; +int allow_weak_random; void set_default_username (const char *s) { if (default_username) { @@ -375,6 +376,9 @@ void args_parse (int argc, char **argv) { case 'E': disable_auto_accept = 1; break; + case 'w': + allow_weak_random = 1; + break; case 'h': default: usage (); diff --git a/mtproto-client.c b/mtproto-client.c index c22bb5a..a010d85 100644 --- a/mtproto-client.c +++ b/mtproto-client.c @@ -69,7 +69,7 @@ char new_nonce[256]; char server_nonce[256]; extern int binlog_enabled; extern int disable_auto_accept; - +extern int allow_weak_random; int total_packets_sent; long long total_data_sent; @@ -98,6 +98,15 @@ double get_utime (int clock_id) { return res; } +void do_rand (void *s, int l) { + if (RAND_bytes (s, l) < 0) { + if (allow_weak_random) { + RAND_pseudo_bytes (s, l); + } else { + assert (0 && "End of random. If you want, you can start with -w"); + } + } +} #define STATS_BUFF_SIZE (64 << 10) @@ -223,7 +232,7 @@ int rpc_send_message (struct connection *c, void *data, int len) { int send_req_pq_packet (struct connection *c) { assert (c_state == st_init); - assert (RAND_pseudo_bytes ((unsigned char *) nonce, 16) >= 0); + do_rand (nonce, 16); unenc_msg_header.out_msg_id = 0; clear_packet (); out_int (CODE_req_pq); @@ -371,7 +380,7 @@ int process_respq_answer (struct connection *c, char *packet, int len) { //out_int (0x0501); // q=5 out_ints ((int *) nonce, 4); out_ints ((int *) server_nonce, 4); - assert (RAND_pseudo_bytes ((unsigned char *) new_nonce, 32) >= 0); + do_rand (new_nonce, 32); out_ints ((int *) new_nonce, 8); sha1 ((unsigned char *) (packet_buffer + 5), (packet_ptr - packet_buffer - 5) * 4, (unsigned char *) packet_buffer); @@ -564,7 +573,7 @@ int process_dh_answer (struct connection *c, char *packet, int len) { BN_init (&dh_g); BN_set_word (&dh_g, g); - assert (RAND_pseudo_bytes ((unsigned char *)s_power, 256) >= 0); + do_rand (s_power, 256); BIGNUM *dh_power = BN_new (); assert (BN_bin2bn ((unsigned char *)s_power, 256, dh_power) == dh_power); @@ -683,7 +692,7 @@ void init_enc_msg (struct session *S, int useful) { // assert (DC->server_salt); enc_msg.server_salt = DC->server_salt; if (!S->session_id) { - assert (RAND_pseudo_bytes ((unsigned char *) &S->session_id, 8) >= 0); + do_rand (&S->session_id, 8); } enc_msg.session_id = S->session_id; //enc_msg.auth_key_id2 = auth_key_id; diff --git a/mtproto-client.h b/mtproto-client.h index 458d6c5..5f04dea 100644 --- a/mtproto-client.h +++ b/mtproto-client.h @@ -29,4 +29,5 @@ void work_update_binlog (void); int check_g (unsigned char p[256], BIGNUM *g); int check_g_bn (BIGNUM *p, BIGNUM *g); int check_DH_params (BIGNUM *p, int g); +void do_rand (void *s, int l); #endif diff --git a/queries.c b/queries.c index ec35d15..3719de7 100644 --- a/queries.c +++ b/queries.c @@ -2263,8 +2263,10 @@ void do_send_accept_encr_chat (struct secret_chat *E, unsigned char *random) { } } if (ok) { return; } // Already generated key for this chat - for (i = 0; i < 64; i++) { - *(((int *)random) + i) ^= mrand48 (); + unsigned char random_here[256]; + do_rand (random_here, 256); + for (i = 0; i < 256; i++) { + random[i] ^= random_here[i]; } BIGNUM *b = BN_bin2bn (random, 256, 0); assert (b);