Commit fe08f0c5 authored by vysheng's avatar vysheng

more code

parent bf86f756
...@@ -1126,9 +1126,7 @@ static void replay_log_event (void) { ...@@ -1126,9 +1126,7 @@ static void replay_log_event (void) {
assert (rptr < wptr); assert (rptr < wptr);
int op = *rptr; int op = *rptr;
if (verbosity >= 2) { vlogprintf (E_DEBUG, "replay_log_event: log_pos=%lld, op=0x%08x\n", binlog_pos, op);
logprintf ("log_pos %lld, op 0x%08x\n", binlog_pos, op);
}
in_ptr = rptr; in_ptr = rptr;
in_end = wptr; in_end = wptr;
...@@ -1201,7 +1199,7 @@ static void replay_log_event (void) { ...@@ -1201,7 +1199,7 @@ static void replay_log_event (void) {
FETCH_COMBINATOR_FUNCTION (binlog_set_msg_id) FETCH_COMBINATOR_FUNCTION (binlog_set_msg_id)
FETCH_COMBINATOR_FUNCTION (binlog_delete_msg) FETCH_COMBINATOR_FUNCTION (binlog_delete_msg)
default: default:
logprintf ("Unknown op 0x%08x\n", op); vlogprintf (E_ERROR, "Unknown op 0x%08x\n", op);
assert (0); assert (0);
} }
assert (ok >= 0); assert (ok >= 0);
...@@ -1287,9 +1285,7 @@ void tgl_reopen_binlog_for_writing (void) { ...@@ -1287,9 +1285,7 @@ void tgl_reopen_binlog_for_writing (void) {
} }
static void add_log_event (const int *data, int len) { static void add_log_event (const int *data, int len) {
if (verbosity) { vlogprintf (E_DEBUG, "Add log event: magic = 0x%08x, len = %d\n", data[0], len);
logprintf ("Add log event: magic = 0x%08x, len = %d\n", data[0], len);
}
assert (!(len & 3)); assert (!(len & 3));
rptr = (void *)data; rptr = (void *)data;
wptr = rptr + (len / 4); wptr = rptr + (len / 4);
...@@ -1297,7 +1293,7 @@ static void add_log_event (const int *data, int len) { ...@@ -1297,7 +1293,7 @@ static void add_log_event (const int *data, int len) {
int *end = in_end; int *end = in_end;
replay_log_event (); replay_log_event ();
if (rptr != wptr) { if (rptr != wptr) {
logprintf ("Unread %lld ints. Len = %d\n", (long long)(wptr - rptr), len); vlogprintf (E_ERROR, "Unread %lld ints. Len = %d\n", (long long)(wptr - rptr), len);
assert (rptr == wptr); assert (rptr == wptr);
} }
if (tgl_state.binlog_enabled) { if (tgl_state.binlog_enabled) {
......
...@@ -34,11 +34,6 @@ ...@@ -34,11 +34,6 @@
#define COLOR_INVERSE "\033[7m" #define COLOR_INVERSE "\033[7m"
#define E_ERROR 0
#define E_WARNING 1
#define E_NOTICE 2
#define E_DEBUG 3
char *get_default_prompt (void); char *get_default_prompt (void);
char *complete_none (const char *text, int state); char *complete_none (const char *text, int state);
char **complete_text (char *text, int start, int end); char **complete_text (char *text, int start, int end);
......
...@@ -155,7 +155,7 @@ char *get_state_filename (void); ...@@ -155,7 +155,7 @@ char *get_state_filename (void);
char *get_secret_chat_filename (void); char *get_secret_chat_filename (void);
int zero[512]; int zero[512];
/*
void write_dc (int auth_file_fd, struct dc *DC) { void write_dc (int auth_file_fd, struct dc *DC) {
assert (write (auth_file_fd, &DC->port, 4) == 4); assert (write (auth_file_fd, &DC->port, 4) == 4);
int l = strlen (DC->ip); int l = strlen (DC->ip);
...@@ -436,7 +436,7 @@ void write_secret_chat_file (void) { ...@@ -436,7 +436,7 @@ void write_secret_chat_file (void) {
assert (write (fd, encr_prime, 256) == 256); assert (write (fd, encr_prime, 256) == 256);
} }
close (fd); close (fd);
} }*/
extern int max_chat_size; extern int max_chat_size;
int mcs (void) { int mcs (void) {
......
...@@ -49,7 +49,6 @@ ...@@ -49,7 +49,6 @@
#include "telegram.h" #include "telegram.h"
#include "loop.h" #include "loop.h"
#include "mtproto-client.h"
#include "interface.h" #include "interface.h"
#include "tools.h" #include "tools.h"
...@@ -59,8 +58,8 @@ ...@@ -59,8 +58,8 @@
#include "tgl.h" #include "tgl.h"
#define PROGNAME "telegram-client" #define PROGNAME "telegram-cli"
#define VERSION "0.01" #define VERSION "0.07"
#define CONFIG_DIRECTORY "." PROG_NAME #define CONFIG_DIRECTORY "." PROG_NAME
#define CONFIG_FILE "config" #define CONFIG_FILE "config"
...@@ -319,13 +318,20 @@ void parse_config (void) { ...@@ -319,13 +318,20 @@ void parse_config (void) {
config_directory = make_full_path (config_directory); config_directory = make_full_path (config_directory);
parse_config_val (&conf, &auth_file_name, "auth_file", AUTH_KEY_FILE, config_directory); parse_config_val (&conf, &auth_file_name, "auth_file", AUTH_KEY_FILE, config_directory);
parse_config_val (&conf, &state_file_name, "state_file", STATE_FILE, config_directory);
parse_config_val (&conf, &secret_chat_file_name, "secret", SECRET_CHAT_FILE, config_directory);
parse_config_val (&conf, &downloads_directory, "downloads", DOWNLOADS_DIRECTORY, config_directory); parse_config_val (&conf, &downloads_directory, "downloads", DOWNLOADS_DIRECTORY, config_directory);
parse_config_val (&conf, &binlog_file_name, "binlog", BINLOG_FILE, config_directory); parse_config_val (&conf, &binlog_file_name, "binlog", BINLOG_FILE, config_directory);
strcpy (buf + l, "binlog_enabled"); strcpy (buf + l, "binlog_enabled");
config_lookup_bool (&conf, buf, &binlog_enabled); config_lookup_bool (&conf, buf, &binlog_enabled);
if (binlog_enabled) {
tgl_set_binlog_mode (1);
tgl_set_binlog_path (binlog_file_name);
} else {
tgl_set_binlog_mode (0);
tgl_set_auth_file_path (auth_file_name);
}
tgl_set_download_directory (downloads_directory);
if (!mkdir (config_directory, CONFIG_DIRECTORY_MODE)) { if (!mkdir (config_directory, CONFIG_DIRECTORY_MODE)) {
printf ("[%s] created\n", config_directory); printf ("[%s] created\n", config_directory);
...@@ -338,10 +344,17 @@ void parse_config (void) { ...@@ -338,10 +344,17 @@ void parse_config (void) {
void parse_config (void) { void parse_config (void) {
printf ("libconfig not enabled\n"); printf ("libconfig not enabled\n");
tasprintf (&auth_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, AUTH_KEY_FILE); tasprintf (&auth_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, AUTH_KEY_FILE);
tasprintf (&state_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, STATE_FILE);
tasprintf (&secret_chat_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, SECRET_CHAT_FILE);
tasprintf (&downloads_directory, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, DOWNLOADS_DIRECTORY); tasprintf (&downloads_directory, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, DOWNLOADS_DIRECTORY);
tasprintf (&binlog_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, BINLOG_FILE); tasprintf (&binlog_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, BINLOG_FILE);
if (binlog_enabled) {
tgl_set_binlog_mode (1);
tgl_set_binlog_path (binlog_file_name);
} else {
tgl_set_binlog_mode (0);
tgl_set_auth_file_path (auth_file_name;
}
tgl_set_download_directory (downloads_directory);
} }
#endif #endif
...@@ -488,7 +501,7 @@ int main (int argc, char **argv) { ...@@ -488,7 +501,7 @@ int main (int argc, char **argv) {
args_parse (argc, argv); args_parse (argc, argv);
printf ( printf (
"Telegram-client version " TG_VERSION ", Copyright (C) 2013 Vitaly Valtman\n" "Telegram-client version " TGL_VERSION ", Copyright (C) 2013 Vitaly Valtman\n"
"Telegram-client comes with ABSOLUTELY NO WARRANTY; for details type `show_license'.\n" "Telegram-client comes with ABSOLUTELY NO WARRANTY; for details type `show_license'.\n"
"This is free software, and you are welcome to redistribute it\n" "This is free software, and you are welcome to redistribute it\n"
"under certain conditions; type `show_license' for details.\n" "under certain conditions; type `show_license' for details.\n"
......
...@@ -50,7 +50,6 @@ ...@@ -50,7 +50,6 @@
#include "include.h" #include "include.h"
#include "queries.h" #include "queries.h"
#include "loop.h" #include "loop.h"
#include "interface.h"
#include "structures.h" #include "structures.h"
#include "binlog.h" #include "binlog.h"
#include "auto.h" #include "auto.h"
...@@ -142,18 +141,18 @@ static int rsa_load_public_key (const char *public_key_name) { ...@@ -142,18 +141,18 @@ static int rsa_load_public_key (const char *public_key_name) {
pubKey = NULL; pubKey = NULL;
FILE *f = fopen (public_key_name, "r"); FILE *f = fopen (public_key_name, "r");
if (f == NULL) { if (f == NULL) {
logprintf ( "Couldn't open public key file: %s\n", public_key_name); vlogprintf (E_WARNING, "Couldn't open public key file: %s\n", public_key_name);
return -1; return -1;
} }
pubKey = PEM_read_RSAPublicKey (f, NULL, NULL, NULL); pubKey = PEM_read_RSAPublicKey (f, NULL, NULL, NULL);
fclose (f); fclose (f);
if (pubKey == NULL) { if (pubKey == NULL) {
logprintf ( "PEM_read_RSAPublicKey returns NULL.\n"); vlogprintf (E_WARNING, "PEM_read_RSAPublicKey returns NULL.\n");
return -1; return -1;
} }
if (verbosity) { if (verbosity) {
logprintf ( "public key '%s' loaded successfully\n", rsa_public_key_name); vlogprintf (E_WARNING, "public key '%s' loaded successfully\n", rsa_public_key_name);
} }
return 0; return 0;
...@@ -267,9 +266,7 @@ unsigned p1, p2; ...@@ -267,9 +266,7 @@ unsigned p1, p2;
int process_respq_answer (struct connection *c, char *packet, int len) { int process_respq_answer (struct connection *c, char *packet, int len) {
int i; int i;
if (verbosity) { vlogprintf (E_DEBUG, "process_respq_answer(), len=%d\n", len);
logprintf ( "process_respq_answer(), len=%d\n", len);
}
assert (len >= 76); assert (len >= 76);
assert (!*(long long *) packet); assert (!*(long long *) packet);
assert (*(int *) (packet + 16) == len - 20); assert (*(int *) (packet + 16) == len - 20);
...@@ -289,10 +286,6 @@ int process_respq_answer (struct connection *c, char *packet, int len) { ...@@ -289,10 +286,6 @@ int process_respq_answer (struct connection *c, char *packet, int len) {
p1 = 0, p2 = 0; p1 = 0, p2 = 0;
if (verbosity >= 2) {
logprintf ( "%lld received\n", what);
}
int it = 0; int it = 0;
unsigned long long g = 0; unsigned long long g = 0;
for (i = 0; i < 3 || it < 1000; i++) { for (i = 0; i < 3 || it < 1000; i++) {
...@@ -337,10 +330,6 @@ int process_respq_answer (struct connection *c, char *packet, int len) { ...@@ -337,10 +330,6 @@ int process_respq_answer (struct connection *c, char *packet, int len) {
} }
if (verbosity) {
logprintf ( "p1 = %d, p2 = %d, %d iterations\n", p1, p2, it);
}
/// ++p1; /// /// ++p1; ///
assert (*(int *) (from) == CODE_vector); assert (*(int *) (from) == CODE_vector);
...@@ -354,7 +343,7 @@ int process_respq_answer (struct connection *c, char *packet, int len) { ...@@ -354,7 +343,7 @@ int process_respq_answer (struct connection *c, char *packet, int len) {
} }
} }
if (i == fingerprints_num) { if (i == fingerprints_num) {
logprintf ( "fatal: don't have any matching keys (%016llx expected)\n", pk_fingerprint); vlogprintf (E_ERROR, "fatal: don't have any matching keys (%016llx expected)\n", pk_fingerprint);
exit (2); exit (2);
} }
// create inner part (P_Q_inner_data) // create inner part (P_Q_inner_data)
...@@ -519,7 +508,7 @@ int check_g (unsigned char p[256], BIGNUM *g) { ...@@ -519,7 +508,7 @@ int check_g (unsigned char p[256], BIGNUM *g) {
ok = 1; ok = 1;
break; break;
} else if (s[i] > p[i]) { } else if (s[i] > p[i]) {
logprintf ("i = %d (%d %d)\n", i, (int)s[i], (int)p[i]); vlogprintf (E_WARNING, "i = %d (%d %d)\n", i, (int)s[i], (int)p[i]);
return -1; return -1;
} }
} }
...@@ -536,11 +525,9 @@ int check_g_bn (BIGNUM *p, BIGNUM *g) { ...@@ -536,11 +525,9 @@ int check_g_bn (BIGNUM *p, BIGNUM *g) {
} }
int process_dh_answer (struct connection *c, char *packet, int len) { int process_dh_answer (struct connection *c, char *packet, int len) {
if (verbosity) { vlogprintf (E_DEBUG, "process_dh_answer(), len=%d\n", len);
logprintf ( "process_dh_answer(), len=%d\n", len);
}
if (len < 116) { if (len < 116) {
logprintf ( "%u * %u = %llu", p1, p2, what); vlogprintf (E_ERROR, "%u * %u = %llu", p1, p2, what);
} }
assert (len >= 116); assert (len >= 116);
assert (!*(long long *) packet); assert (!*(long long *) packet);
...@@ -636,9 +623,7 @@ int process_dh_answer (struct connection *c, char *packet, int len) { ...@@ -636,9 +623,7 @@ int process_dh_answer (struct connection *c, char *packet, int len) {
int process_auth_complete (struct connection *c UU, char *packet, int len) { int process_auth_complete (struct connection *c UU, char *packet, int len) {
if (verbosity) { vlogprintf (E_DEBUG, "process_dh_answer(), len=%d\n", len);
logprintf ( "process_dh_answer(), len=%d\n", len);
}
assert (len == 72); assert (len == 72);
assert (!*(long long *) packet); assert (!*(long long *) packet);
assert (*(int *) (packet + 16) == len - 20); assert (*(int *) (packet + 16) == len - 20);
...@@ -659,9 +644,6 @@ int process_auth_complete (struct connection *c UU, char *packet, int len) { ...@@ -659,9 +644,6 @@ int process_auth_complete (struct connection *c UU, char *packet, int len) {
assert (!memcmp (packet + 56, sha1_buffer + 4, 16)); assert (!memcmp (packet + 56, sha1_buffer + 4, 16));
GET_DC(c)->server_salt = *(long long *)server_nonce ^ *(long long *)new_nonce; GET_DC(c)->server_salt = *(long long *)server_nonce ^ *(long long *)new_nonce;
if (verbosity >= 3) {
logprintf ( "auth_key_id=%016llx\n", GET_DC(c)->auth_key_id);
}
//kprintf ("OK\n"); //kprintf ("OK\n");
//c->status = conn_error; //c->status = conn_error;
...@@ -669,9 +651,7 @@ int process_auth_complete (struct connection *c UU, char *packet, int len) { ...@@ -669,9 +651,7 @@ int process_auth_complete (struct connection *c UU, char *packet, int len) {
c_state = st_authorized; c_state = st_authorized;
//return 1; //return 1;
if (verbosity) { vlogprintf (E_DEBUG, "Auth success\n");
logprintf ( "Auth success\n");
}
auth_success ++; auth_success ++;
GET_DC(c)->flags |= 1; GET_DC(c)->flags |= 1;
write_auth_file (); write_auth_file ();
...@@ -735,9 +715,7 @@ int aes_encrypt_message (struct dc *DC, struct encrypted_message *enc) { ...@@ -735,9 +715,7 @@ int aes_encrypt_message (struct dc *DC, struct encrypted_message *enc) {
assert (enc->msg_len >= 0 && enc->msg_len <= MAX_MESSAGE_INTS * 4 - 16 && !(enc->msg_len & 3)); assert (enc->msg_len >= 0 && enc->msg_len <= MAX_MESSAGE_INTS * 4 - 16 && !(enc->msg_len & 3));
sha1 ((unsigned char *) &enc->server_salt, enc_len, sha1_buffer); sha1 ((unsigned char *) &enc->server_salt, enc_len, sha1_buffer);
//printf ("enc_len is %d\n", enc_len); //printf ("enc_len is %d\n", enc_len);
if (verbosity >= 2) { vlogprintf (E_DEBUG, "sending message with sha1 %08x\n", *(int *)sha1_buffer);
logprintf ( "sending message with sha1 %08x\n", *(int *)sha1_buffer);
}
memcpy (enc->msg_key, sha1_buffer + 4, 16); memcpy (enc->msg_key, sha1_buffer + 4, 16);
init_aes_auth (DC->auth_key, enc->msg_key, AES_ENCRYPT); init_aes_auth (DC->auth_key, enc->msg_key, AES_ENCRYPT);
//hexdump ((char *)enc, (char *)enc + enc_len + 24); //hexdump ((char *)enc, (char *)enc + enc_len + 24);
...@@ -831,7 +809,7 @@ void fetch_date (void) { ...@@ -831,7 +809,7 @@ void fetch_date (void) {
void fetch_seq (void) { void fetch_seq (void) {
int x = fetch_int (); int x = fetch_int ();
if (x > seq + 1) { if (x > seq + 1) {
logprintf ("Hole in seq: seq = %d, x = %d\n", seq, x); vlogprintf (E_NOTICE, "Hole in seq: seq = %d, x = %d\n", seq, x);
//tgl_do_get_difference (); //tgl_do_get_difference ();
//seq = x; //seq = x;
} else if (x == seq + 1) { } else if (x == seq + 1) {
...@@ -911,9 +889,11 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -911,9 +889,11 @@ void work_update (struct connection *c UU, long long msg_id UU) {
struct tgl_message *M = tglf_fetch_alloc_message (); struct tgl_message *M = tglf_fetch_alloc_message ();
assert (M); assert (M);
fetch_pts (); fetch_pts ();
unread_messages ++;
print_message (M); tgl_state.callback.new_msg (M);
update_prompt (); //unread_messages ++;
//print_message (M);
//update_prompt ();
break; break;
}; };
case CODE_update_message_i_d: case CODE_update_message_i_d:
...@@ -930,30 +910,38 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -930,30 +910,38 @@ void work_update (struct connection *c UU, long long msg_id UU) {
{ {
assert (fetch_int () == (int)CODE_vector); assert (fetch_int () == (int)CODE_vector);
int n = fetch_int (); int n = fetch_int ();
struct tgl_message **ML = talloc (n * sizeof (void *));
int p = 0;
int i; int i;
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
int id = fetch_int (); int id = fetch_int ();
struct tgl_message *M = tgl_message_get (id); struct tgl_message *M = tgl_message_get (id);
if (M) { if (M) {
bl_do_set_unread (M, 0); bl_do_set_unread (M, 0);
ML[p ++] = M;
} }
} }
fetch_pts (); fetch_pts ();
if (log_level >= 1) { tgl_state.callback.marked_read (p, ML);
tfree (ML, sizeof (void *) * n);
/*if (log_level >= 1) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" %d messages marked as read\n", n); printf (" %d messages marked as read\n", n);
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
} }
break; break;
case CODE_update_user_typing: case CODE_update_user_typing:
{ {
tgl_peer_id_t id = TGL_MK_USER (fetch_int ()); tgl_peer_id_t id = TGL_MK_USER (fetch_int ());
tgl_peer_t *U = tgl_peer_get (id); tgl_peer_t *U = tgl_peer_get (id);
if (log_level >= 2) {
tgl_state.callback.type_notification (id, (void *)U);
/*if (log_level >= 2) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
...@@ -962,7 +950,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -962,7 +950,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
printf (" is typing....\n"); printf (" is typing....\n");
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
} }
break; break;
case CODE_update_chat_user_typing: case CODE_update_chat_user_typing:
...@@ -971,7 +959,9 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -971,7 +959,9 @@ void work_update (struct connection *c UU, long long msg_id UU) {
tgl_peer_id_t id = TGL_MK_USER (fetch_int ()); tgl_peer_id_t id = TGL_MK_USER (fetch_int ());
tgl_peer_t *C = tgl_peer_get (chat_id); tgl_peer_t *C = tgl_peer_get (chat_id);
tgl_peer_t *U = tgl_peer_get (id); tgl_peer_t *U = tgl_peer_get (id);
if (log_level >= 2) {
tgl_state.callback.type_in_chat_notification (id, (void *)U, chat_id, (void *)C);
/*if (log_level >= 2) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
...@@ -982,7 +972,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -982,7 +972,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
printf ("....\n"); printf ("....\n");
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
} }
break; break;
case CODE_update_user_status: case CODE_update_user_status:
...@@ -991,7 +981,8 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -991,7 +981,8 @@ void work_update (struct connection *c UU, long long msg_id UU) {
tgl_peer_t *U = tgl_peer_get (user_id); tgl_peer_t *U = tgl_peer_get (user_id);
if (U) { if (U) {
tglf_fetch_user_status (&U->user.status); tglf_fetch_user_status (&U->user.status);
if (log_level >= 3) { tgl_state.callback.status_notification ((void *)U);
/*if (log_level >= 3) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
...@@ -1001,7 +992,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1001,7 +992,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
printf ("%s\n", (U->user.status.online > 0) ? "online" : "offline"); printf ("%s\n", (U->user.status.online > 0) ? "online" : "offline");
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
} else { } else {
struct tgl_user_status t; struct tgl_user_status t;
tglf_fetch_user_status (&t); tglf_fetch_user_status (&t);
...@@ -1019,7 +1010,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1019,7 +1010,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
char *l = fetch_str (l2); char *l = fetch_str (l2);
struct tgl_user *U = &UC->user; struct tgl_user *U = &UC->user;
bl_do_user_set_real_name (U, f, l1, l, l2); bl_do_user_set_real_name (U, f, l1, l, l2);
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" User "); printf (" User ");
...@@ -1028,7 +1019,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1028,7 +1019,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
print_user_name (user_id, UC); print_user_name (user_id, UC);
printf ("\n"); printf ("\n");
pop_color (); pop_color ();
print_end (); print_end ();*/
} else { } else {
fetch_skip_str (); fetch_skip_str ();
fetch_skip_str (); fetch_skip_str ();
...@@ -1060,14 +1051,14 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1060,14 +1051,14 @@ void work_update (struct connection *c UU, long long msg_id UU) {
} }
bl_do_set_user_profile_photo (U, photo_id, &big, &small); bl_do_set_user_profile_photo (U, photo_id, &big, &small);
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" User "); printf (" User ");
print_user_name (user_id, UC); print_user_name (user_id, UC);
printf (" updated profile photo\n"); printf (" updated profile photo\n");
pop_color (); pop_color ();
print_end (); print_end ();*/
} else { } else {
struct tgl_file_location t; struct tgl_file_location t;
unsigned y = fetch_int (); unsigned y = fetch_int ();
...@@ -1086,12 +1077,12 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1086,12 +1077,12 @@ void work_update (struct connection *c UU, long long msg_id UU) {
{ {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" Restored %d messages\n", n); printf (" Restored %d messages\n", n);
pop_color (); pop_color ();
print_end (); print_end ();*/
fetch_skip (n); fetch_skip (n);
fetch_pts (); fetch_pts ();
} }
...@@ -1100,12 +1091,12 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1100,12 +1091,12 @@ void work_update (struct connection *c UU, long long msg_id UU) {
{ {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" Deleted %d messages\n", n); printf (" Deleted %d messages\n", n);
pop_color (); pop_color ();
print_end (); print_end ();*/
fetch_skip (n); fetch_skip (n);
fetch_pts (); fetch_pts ();
} }
...@@ -1142,7 +1133,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1142,7 +1133,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
fetch_int (); // version fetch_int (); // version
} }
} }
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" Chat "); printf (" Chat ");
...@@ -1153,7 +1144,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1153,7 +1144,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
printf (" changed list, but we are forbidden to know about it (Why this update even was sent to us?\n"); printf (" changed list, but we are forbidden to know about it (Why this update even was sent to us?\n");
} }
pop_color (); pop_color ();
print_end (); print_end ();*/
} }
break; break;
case CODE_update_contact_registered: case CODE_update_contact_registered:
...@@ -1161,28 +1152,29 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1161,28 +1152,29 @@ void work_update (struct connection *c UU, long long msg_id UU) {
tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ());
tgl_peer_t *U = tgl_peer_get (user_id); tgl_peer_t *U = tgl_peer_get (user_id);
fetch_int (); // date fetch_int (); // date
print_start (); tgl_state.callback.user_registered (U);
/*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" User "); printf (" User ");
print_user_name (user_id, U); print_user_name (user_id, U);
printf (" registered\n"); printf (" registered\n");
pop_color (); pop_color ();
print_end (); print_end ();*/
} }
break; break;
case CODE_update_contact_link: case CODE_update_contact_link:
{ {
tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ());
tgl_peer_t *U = tgl_peer_get (user_id); tgl_peer_t *U = tgl_peer_get (user_id);
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
printf (" Updated link with user "); printf (" Updated link with user ");
print_user_name (user_id, U); print_user_name (user_id, U);
printf ("\n"); printf ("\n");
pop_color (); pop_color ();
print_end (); print_end ();*/
unsigned t = fetch_int (); unsigned t = fetch_int ();
assert (t == CODE_contacts_my_link_empty || t == CODE_contacts_my_link_requested || t == CODE_contacts_my_link_contact); assert (t == CODE_contacts_my_link_empty || t == CODE_contacts_my_link_requested || t == CODE_contacts_my_link_contact);
if (t == CODE_contacts_my_link_requested) { if (t == CODE_contacts_my_link_requested) {
...@@ -1246,9 +1238,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1246,9 +1238,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
case CODE_update_encryption: case CODE_update_encryption:
{ {
struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (); struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat ();
if (verbosity >= 2) { vlogprintf (E_DEBUG, "Secret chat state = %d\n", E->state);
logprintf ("Secret chat state = %d\n", E->state);
}
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
print_date (time (0)); print_date (time (0));
...@@ -1415,7 +1405,7 @@ void work_update (struct connection *c UU, long long msg_id UU) { ...@@ -1415,7 +1405,7 @@ void work_update (struct connection *c UU, long long msg_id UU) {
} }
break; break;
default: default:
logprintf ("Unknown update type %08x\n", op); vlogprintf (E_ERROR, "Unknown update type %08x\n", op);
; ;
} }
} }
...@@ -1476,9 +1466,7 @@ void work_update_short_chat_message (struct connection *c UU, long long msg_id U ...@@ -1476,9 +1466,7 @@ void work_update_short_chat_message (struct connection *c UU, long long msg_id U
} }
void work_container (struct connection *c, long long msg_id UU) { void work_container (struct connection *c, long long msg_id UU) {
if (verbosity) { vlogprintf (E_DEBUG, "work_container: msg_id = %lld\n", msg_id);
logprintf ( "work_container: msg_id = %lld\n", msg_id);
}
assert (fetch_int () == CODE_msg_container); assert (fetch_int () == CODE_msg_container);
int n = fetch_int (); int n = fetch_int ();
int i; int i;
...@@ -1499,9 +1487,7 @@ void work_container (struct connection *c, long long msg_id UU) { ...@@ -1499,9 +1487,7 @@ void work_container (struct connection *c, long long msg_id UU) {
} }
void work_new_session_created (struct connection *c, long long msg_id UU) { void work_new_session_created (struct connection *c, long long msg_id UU) {
if (verbosity) { vlogprintf (E_DEBUG, "work_new_session_created: msg_id = %lld\n", msg_id);
logprintf ( "work_new_session_created: msg_id = %lld\n", msg_id);
}
assert (fetch_int () == (int)CODE_new_session_created); assert (fetch_int () == (int)CODE_new_session_created);
fetch_long (); // first message id fetch_long (); // first message id
//DC->session_id = fetch_long (); //DC->session_id = fetch_long ();
...@@ -1511,26 +1497,20 @@ void work_new_session_created (struct connection *c, long long msg_id UU) { ...@@ -1511,26 +1497,20 @@ void work_new_session_created (struct connection *c, long long msg_id UU) {
} }
void work_msgs_ack (struct connection *c UU, long long msg_id UU) { void work_msgs_ack (struct connection *c UU, long long msg_id UU) {
if (verbosity) { vlogprintf (E_DEBUG, "work_msgs_ack: msg_id = %lld\n", msg_id);
logprintf ( "work_msgs_ack: msg_id = %lld\n", msg_id);
}
assert (fetch_int () == CODE_msgs_ack); assert (fetch_int () == CODE_msgs_ack);
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
int i; int i;
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
long long id = fetch_long (); long long id = fetch_long ();
if (verbosity) { vlogprintf (E_DEBUG + 1, "ack for %lld\n", id);
logprintf ("ack for %lld\n", id);
}
query_ack (id); query_ack (id);
} }
} }
void work_rpc_result (struct connection *c UU, long long msg_id UU) { void work_rpc_result (struct connection *c UU, long long msg_id UU) {
if (verbosity) { vlogprintf (E_DEBUG, "work_rpc_result: msg_id = %lld\n", msg_id);
logprintf ( "work_rpc_result: msg_id = %lld\n", msg_id);
}
assert (fetch_int () == (int)CODE_rpc_result); assert (fetch_int () == (int)CODE_rpc_result);
long long id = fetch_long (); long long id = fetch_long ();
int op = prefetch_int (); int op = prefetch_int ();
...@@ -1558,10 +1538,6 @@ void work_packed (struct connection *c, long long msg_id) { ...@@ -1558,10 +1538,6 @@ void work_packed (struct connection *c, long long msg_id) {
//assert (total_out % 4 == 0); //assert (total_out % 4 == 0);
in_ptr = buf; in_ptr = buf;
in_end = in_ptr + total_out / 4; in_end = in_ptr + total_out / 4;
if (verbosity >= 4) {
logprintf ( "Unzipped data: ");
hexdump_in ();
}
rpc_execute_answer (c, msg_id); rpc_execute_answer (c, msg_id);
in_ptr = end; in_ptr = end;
in_end = eend; in_end = eend;
...@@ -1601,7 +1577,7 @@ void work_new_detailed_info (struct connection *c UU, long long msg_id UU) { ...@@ -1601,7 +1577,7 @@ void work_new_detailed_info (struct connection *c UU, long long msg_id UU) {
void work_updates_to_long (struct connection *c UU, long long msg_id UU) { void work_updates_to_long (struct connection *c UU, long long msg_id UU) {
assert (fetch_int () == (int)CODE_updates_too_long); assert (fetch_int () == (int)CODE_updates_too_long);
logprintf ("updates to long... Getting difference\n"); vlogprintf (E_NOTICE, "updates to long... Getting difference\n");
tgl_do_get_difference (); tgl_do_get_difference ();
} }
...@@ -1610,14 +1586,10 @@ void work_bad_msg_notification (struct connection *c UU, long long msg_id UU) { ...@@ -1610,14 +1586,10 @@ void work_bad_msg_notification (struct connection *c UU, long long msg_id UU) {
long long m1 = fetch_long (); long long m1 = fetch_long ();
int s = fetch_int (); int s = fetch_int ();
int e = fetch_int (); int e = fetch_int ();
logprintf ("bad_msg_notification: msg_id = %lld, seq = %d, error = %d\n", m1, s, e); vlogprintf (E_NOTICE, "bad_msg_notification: msg_id = %lld, seq = %d, error = %d\n", m1, s, e);
} }
void rpc_execute_answer (struct connection *c, long long msg_id UU) { void rpc_execute_answer (struct connection *c, long long msg_id UU) {
if (verbosity >= 5) {
logprintf ("rpc_execute_answer: fd=%d\n", c->fd);
hexdump_in ();
}
int op = prefetch_int (); int op = prefetch_int ();
switch (op) { switch (op) {
case CODE_msg_container: case CODE_msg_container:
...@@ -1666,17 +1638,14 @@ void rpc_execute_answer (struct connection *c, long long msg_id UU) { ...@@ -1666,17 +1638,14 @@ void rpc_execute_answer (struct connection *c, long long msg_id UU) {
work_bad_msg_notification (c, msg_id); work_bad_msg_notification (c, msg_id);
return; return;
} }
logprintf ( "Unknown message: \n"); vlogprintf (E_WARNING, "Unknown message: %08x\n", op);
hexdump_in ();
in_ptr = in_end; // Will not fail due to assertion in_ptr == in_end in_ptr = in_end; // Will not fail due to assertion in_ptr == in_end
} }
int process_rpc_message (struct connection *c UU, struct encrypted_message *enc, int len) { int process_rpc_message (struct connection *c UU, struct encrypted_message *enc, int len) {
const int MINSZ = offsetof (struct encrypted_message, message); const int MINSZ = offsetof (struct encrypted_message, message);
const int UNENCSZ = offsetof (struct encrypted_message, server_salt); const int UNENCSZ = offsetof (struct encrypted_message, server_salt);
if (verbosity) { vlogprintf (E_DEBUG, "process_rpc_message(), len=%d\n", len);
logprintf ( "process_rpc_message(), len=%d\n", len);
}
assert (len >= MINSZ && (len & 15) == (UNENCSZ & 15)); assert (len >= MINSZ && (len & 15) == (UNENCSZ & 15));
struct dc *DC = GET_DC(c); struct dc *DC = GET_DC(c);
assert (enc->auth_key_id == DC->auth_key_id); assert (enc->auth_key_id == DC->auth_key_id);
...@@ -1702,10 +1671,9 @@ int process_rpc_message (struct connection *c UU, struct encrypted_message *enc, ...@@ -1702,10 +1671,9 @@ int process_rpc_message (struct connection *c UU, struct encrypted_message *enc,
} }
double st = get_server_time (DC); double st = get_server_time (DC);
if (this_server_time < st - 300 || this_server_time > st + 30) { if (this_server_time < st - 300 || this_server_time > st + 30) {
logprintf ("salt = %lld, session_id = %lld, msg_id = %lld, seq_no = %d, st = %lf, now = %lf\n", enc->server_salt, enc->session_id, enc->msg_id, enc->seq_no, st, get_utime (CLOCK_REALTIME)); vlogprintf (E_WARNING, "salt = %lld, session_id = %lld, msg_id = %lld, seq_no = %d, st = %lf, now = %lf\n", enc->server_salt, enc->session_id, enc->msg_id, enc->seq_no, st, get_utime (CLOCK_REALTIME));
in_ptr = enc->message; in_ptr = enc->message;
in_end = in_ptr + (enc->msg_len / 4); in_end = in_ptr + (enc->msg_len / 4);
hexdump_in ();
} }
assert (this_server_time >= st - 300 && this_server_time <= st + 30); assert (this_server_time >= st - 300 && this_server_time <= st + 30);
......
...@@ -39,7 +39,6 @@ ...@@ -39,7 +39,6 @@
#include <openssl/sha.h> #include <openssl/sha.h>
#include "mtproto-common.h" #include "mtproto-common.h"
#include "interface.h"
#include "include.h" #include "include.h"
#ifdef __MACH__ #ifdef __MACH__
...@@ -61,9 +60,7 @@ int get_random_bytes (unsigned char *buf, int n) { ...@@ -61,9 +60,7 @@ int get_random_bytes (unsigned char *buf, int n) {
if (h >= 0) { if (h >= 0) {
r = read (h, buf, n); r = read (h, buf, n);
if (r > 0) { if (r > 0) {
if (verbosity >= 3) { vlogprintf (E_DEBUG, "added %d bytes of real entropy to secure random numbers seed\n", r);
logprintf ( "added %d bytes of real entropy to secure random numbers seed\n", r);
}
} else { } else {
r = 0; r = 0;
} }
...@@ -143,16 +140,14 @@ void prng_seed (const char *password_filename, int password_length) { ...@@ -143,16 +140,14 @@ void prng_seed (const char *password_filename, int password_length) {
if (password_filename && password_length > 0) { if (password_filename && password_length > 0) {
int fd = open (password_filename, O_RDONLY); int fd = open (password_filename, O_RDONLY);
if (fd < 0) { if (fd < 0) {
logprintf ( "Warning: fail to open password file - \"%s\", %m.\n", password_filename); vlogprintf (E_WARNING, "Warning: fail to open password file - \"%s\", %m.\n", password_filename);
} else { } else {
unsigned char *a = talloc0 (password_length); unsigned char *a = talloc0 (password_length);
int l = read (fd, a, password_length); int l = read (fd, a, password_length);
if (l < 0) { if (l < 0) {
logprintf ( "Warning: fail to read password file - \"%s\", %m.\n", password_filename); vlogprintf (E_WARNING, "Warning: fail to read password file - \"%s\", %m.\n", password_filename);
} else { } else {
if (verbosity > 0) { vlogprintf (E_DEBUG, "read %d bytes from password file.\n", l);
logprintf ( "read %d bytes from password file.\n", l);
}
RAND_add (a, l, l); RAND_add (a, l, l);
} }
close (fd); close (fd);
......
...@@ -26,9 +26,11 @@ ...@@ -26,9 +26,11 @@
#include <openssl/aes.h> #include <openssl/aes.h>
#include <stdio.h> #include <stdio.h>
#include "interface.h" //#include "interface.h"
#include "tools.h" #include "tools.h"
#include "auto/constants.h" #include "auto/constants.h"
#include "tgl.h"
/* DH key exchange protocol data structures */ /* DH key exchange protocol data structures */
#define CODE_req_pq 0x60469778 #define CODE_req_pq 0x60469778
#define CODE_resPQ 0x05162463 #define CODE_resPQ 0x05162463
...@@ -178,9 +180,7 @@ static inline int prefetch_strlen (void) { ...@@ -178,9 +180,7 @@ static inline int prefetch_strlen (void) {
extern int verbosity; extern int verbosity;
static inline char *fetch_str (int len) { static inline char *fetch_str (int len) {
assert (len >= 0); assert (len >= 0);
if (verbosity > 6) { vlogprintf (E_DEBUG + 3, "fetch_string: len = %d\n", len);
logprintf ("fetch_string: len = %d\n", len);
}
if (len < 254) { if (len < 254) {
char *str = (char *) in_ptr + 1; char *str = (char *) in_ptr + 1;
in_ptr += 1 + (len >> 2); in_ptr += 1 + (len >> 2);
...@@ -272,16 +272,12 @@ int fetch_bignum (BIGNUM *x); ...@@ -272,16 +272,12 @@ int fetch_bignum (BIGNUM *x);
static inline int fetch_int (void) { static inline int fetch_int (void) {
assert (in_ptr + 1 <= in_end); assert (in_ptr + 1 <= in_end);
if (verbosity > 6) { vlogprintf (E_DEBUG + 3, "fetch_int: 0x%08x (%d)\n", *in_ptr, *in_ptr);
logprintf ("fetch_int: 0x%08x (%d)\n", *in_ptr, *in_ptr);
}
return *(in_ptr ++); return *(in_ptr ++);
} }
static inline int fetch_bool (void) { static inline int fetch_bool (void) {
if (verbosity > 6) { vlogprintf (E_DEBUG + 3, "fetch_bool: 0x%08x (%d)\n", *in_ptr, *in_ptr);
logprintf ("fetch_bool: 0x%08x (%d)\n", *in_ptr, *in_ptr);
}
assert (in_ptr + 1 <= in_end); assert (in_ptr + 1 <= in_end);
assert (*(in_ptr) == (int)CODE_bool_true || *(in_ptr) == (int)CODE_bool_false); assert (*(in_ptr) == (int)CODE_bool_true || *(in_ptr) == (int)CODE_bool_false);
return *(in_ptr ++) == (int)CODE_bool_true; return *(in_ptr ++) == (int)CODE_bool_true;
...@@ -349,14 +345,14 @@ void init_aes_unauth (const char server_nonce[16], const char hidden_client_nonc ...@@ -349,14 +345,14 @@ void init_aes_unauth (const char server_nonce[16], const char hidden_client_nonc
void init_aes_auth (char auth_key[192], char msg_key[16], int encrypt); void init_aes_auth (char auth_key[192], char msg_key[16], int encrypt);
int pad_aes_encrypt (char *from, int from_len, char *to, int size); int pad_aes_encrypt (char *from, int from_len, char *to, int size);
int pad_aes_decrypt (char *from, int from_len, char *to, int size); int pad_aes_decrypt (char *from, int from_len, char *to, int size);
/*
static inline void hexdump_in (void) { static inline void hexdump_in (void) {
hexdump (in_ptr, in_end); hexdump (in_ptr, in_end);
} }
static inline void hexdump_out (void) { static inline void hexdump_out (void) {
hexdump (packet_buffer, packet_ptr); hexdump (packet_buffer, packet_ptr);
} }*/
#ifdef __MACH__ #ifdef __MACH__
#define CLOCK_REALTIME 0 #define CLOCK_REALTIME 0
......
...@@ -26,9 +26,6 @@ struct dc; ...@@ -26,9 +26,6 @@ struct dc;
#define TG_SERVER_TEST "173.240.5.253" #define TG_SERVER_TEST "173.240.5.253"
#define TG_APP_HASH "36722c72256a24c1225de00eb6a1ca74" #define TG_APP_HASH "36722c72256a24c1225de00eb6a1ca74"
#define TG_APP_ID 2899 #define TG_APP_ID 2899
#define TG_BUILD "209"
#define TG_VERSION "0.01-beta"
#define ACK_TIMEOUT 1 #define ACK_TIMEOUT 1
#define MAX_DC_ID 10 #define MAX_DC_ID 10
......
...@@ -43,7 +43,7 @@ ...@@ -43,7 +43,7 @@
#include "telegram.h" #include "telegram.h"
#include "loop.h" #include "loop.h"
#include "structures.h" #include "structures.h"
#include "interface.h" //#include "interface.h"
#include "net.h" #include "net.h"
#include <openssl/bn.h> #include <openssl/bn.h>
#include <openssl/rand.h> #include <openssl/rand.h>
...@@ -64,21 +64,21 @@ ...@@ -64,21 +64,21 @@
#define OPEN_BIN "xdg-open %s" #define OPEN_BIN "xdg-open %s"
#endif #endif
int want_dc_num;
char *get_downloads_directory (void); char *get_downloads_directory (void);
int verbosity; //extern int offline_mode;
extern int offline_mode;
long long cur_uploading_bytes; //long long cur_uploading_bytes;
long long cur_uploaded_bytes; //long long cur_uploaded_bytes;
long long cur_downloading_bytes; //long long cur_downloading_bytes;
long long cur_downloaded_bytes; //long long cur_downloaded_bytes;
extern int binlog_enabled; //extern int binlog_enabled;
extern int sync_from_start; //extern int sync_from_start;
int queries_num; static int queries_num;
void out_peer_id (tgl_peer_id_t id); static void out_peer_id (tgl_peer_id_t id);
#define QUERY_TIMEOUT 6.0 #define QUERY_TIMEOUT 6.0
#define memcmp8(a,b) memcmp ((a), (b), 8) #define memcmp8(a,b) memcmp ((a), (b), 8)
...@@ -97,9 +97,7 @@ struct query *query_get (long long id) { ...@@ -97,9 +97,7 @@ struct query *query_get (long long id) {
int alarm_query (struct query *q) { int alarm_query (struct query *q) {
assert (q); assert (q);
if (verbosity >= 1) { vlogprintf (E_DEBUG, "Alarm query %lld\n", q->msg_id);
logprintf ("Alarm query %lld\n", q->msg_id);
}
q->ev.timeout = get_double_time () + QUERY_TIMEOUT; q->ev.timeout = get_double_time () + QUERY_TIMEOUT;
insert_event_timer (&q->ev); insert_event_timer (&q->ev);
...@@ -127,15 +125,13 @@ void query_restart (long long id) { ...@@ -127,15 +125,13 @@ void query_restart (long long id) {
} }
} }
struct query *send_query (struct dc *DC, int ints, void *data, struct query_methods *methods, void *extra) { struct query *send_query (struct dc *DC, int ints, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra) {
assert (DC); assert (DC);
assert (DC->auth_key_id); assert (DC->auth_key_id);
if (!DC->sessions[0]) { if (!DC->sessions[0]) {
dc_create_session (DC); dc_create_session (DC);
} }
if (verbosity) { vlogprintf (E_DEBUG, "Sending query of size %d to DC (%s:%d)\n", 4 * ints, DC->ip, DC->port);
logprintf ( "Sending query of size %d to DC (%s:%d)\n", 4 * ints, DC->ip, DC->port);
}
struct query *q = talloc0 (sizeof (*q)); struct query *q = talloc0 (sizeof (*q));
q->data_len = ints; q->data_len = ints;
q->data = talloc (4 * ints); q->data = talloc (4 * ints);
...@@ -143,15 +139,11 @@ struct query *send_query (struct dc *DC, int ints, void *data, struct query_meth ...@@ -143,15 +139,11 @@ struct query *send_query (struct dc *DC, int ints, void *data, struct query_meth
q->msg_id = encrypt_send_message (DC->sessions[0]->c, data, ints, 1); q->msg_id = encrypt_send_message (DC->sessions[0]->c, data, ints, 1);
q->session = DC->sessions[0]; q->session = DC->sessions[0];
q->seq_no = DC->sessions[0]->seq_no - 1; q->seq_no = DC->sessions[0]->seq_no - 1;
if (verbosity) { vlogprintf (E_DEBUG, "Msg_id is %lld %p\n", q->msg_id, q);
logprintf ( "Msg_id is %lld %p\n", q->msg_id, q);
}
q->methods = methods; q->methods = methods;
q->DC = DC; q->DC = DC;
if (queries_tree) { if (queries_tree) {
if (verbosity >= 2) { vlogprintf (E_DEBUG + 2, "%lld %lld\n", q->msg_id, queries_tree->x->msg_id);
logprintf ( "%lld %lld\n", q->msg_id, queries_tree->x->msg_id);
}
} }
queries_tree = tree_insert_query (queries_tree, q, lrand48 ()); queries_tree = tree_insert_query (queries_tree, q, lrand48 ());
...@@ -161,10 +153,18 @@ struct query *send_query (struct dc *DC, int ints, void *data, struct query_meth ...@@ -161,10 +153,18 @@ struct query *send_query (struct dc *DC, int ints, void *data, struct query_meth
insert_event_timer (&q->ev); insert_event_timer (&q->ev);
q->extra = extra; q->extra = extra;
q->callback = callback;
q->callback_extra = callback_extra;
queries_num ++; queries_num ++;
return q; return q;
} }
static int fail_on_error (struct query *q UU, int error_code UU, int l UU, char *error UU) {
fprintf (stderr, "error #%d: %.*s\n", error_code, l, error);
assert (0);
return 0;
}
void query_ack (long long id) { void query_ack (long long id) {
struct query *q = query_get (id); struct query *q = query_get (id);
if (q && !(q->flags & QUERY_ACK_RECEIVED)) { if (q && !(q->flags & QUERY_ACK_RECEIVED)) {
...@@ -179,14 +179,10 @@ void query_error (long long id) { ...@@ -179,14 +179,10 @@ void query_error (long long id) {
int error_code = fetch_int (); int error_code = fetch_int ();
int error_len = prefetch_strlen (); int error_len = prefetch_strlen ();
char *error = fetch_str (error_len); char *error = fetch_str (error_len);
if (verbosity) { vlogprintf (E_WARNING, "error for query #%lld: #%d :%.*s\n", id, error_code, error_len, error);
logprintf ( "error for query #%lld: #%d :%.*s\n", id, error_code, error_len, error);
}
struct query *q = query_get (id); struct query *q = query_get (id);
if (!q) { if (!q) {
if (verbosity) { vlogprintf (E_WARNING, "No such query\n");
logprintf ( "No such query\n");
}
} else { } else {
if (!(q->flags & QUERY_ACK_RECEIVED)) { if (!(q->flags & QUERY_ACK_RECEIVED)) {
remove_event_timer (&q->ev); remove_event_timer (&q->ev);
...@@ -195,7 +191,7 @@ void query_error (long long id) { ...@@ -195,7 +191,7 @@ void query_error (long long id) {
if (q->methods && q->methods->on_error) { if (q->methods && q->methods->on_error) {
q->methods->on_error (q, error_code, error_len, error); q->methods->on_error (q, error_code, error_len, error);
} else { } else {
logprintf ( "error for query #%lld: #%d :%.*s\n", id, error_code, error_len, error); vlogprintf ( E_WARNING, "error for query #%lld: #%d :%.*s\n", id, error_code, error_len, error);
} }
tfree (q->data, q->data_len * 4); tfree (q->data, q->data_len * 4);
tfree (q, sizeof (*q)); tfree (q, sizeof (*q));
...@@ -207,13 +203,11 @@ void query_error (long long id) { ...@@ -207,13 +203,11 @@ void query_error (long long id) {
static int packed_buffer[MAX_PACKED_SIZE / 4]; static int packed_buffer[MAX_PACKED_SIZE / 4];
void query_result (long long id UU) { void query_result (long long id UU) {
if (verbosity) { vlogprintf (E_DEBUG, "result for query #%lld\n", id);
logprintf ( "result for query #%lld\n", id); /*if (verbosity >= 4) {
}
if (verbosity >= 4) {
logprintf ( "result: "); logprintf ( "result: ");
hexdump_in (); hexdump_in ();
} }*/
int op = prefetch_int (); int op = prefetch_int ();
int *end = 0; int *end = 0;
int *eend = 0; int *eend = 0;
...@@ -227,16 +221,17 @@ void query_result (long long id UU) { ...@@ -227,16 +221,17 @@ void query_result (long long id UU) {
//assert (total_out % 4 == 0); //assert (total_out % 4 == 0);
in_ptr = packed_buffer; in_ptr = packed_buffer;
in_end = in_ptr + total_out / 4; in_end = in_ptr + total_out / 4;
if (verbosity >= 4) { /*if (verbosity >= 4) {
logprintf ( "Unzipped data: "); logprintf ( "Unzipped data: ");
hexdump_in (); hexdump_in ();
} }*/
} }
struct query *q = query_get (id); struct query *q = query_get (id);
if (!q) { if (!q) {
if (verbosity) { //if (verbosity) {
logprintf ( "No such query\n"); // logprintf ( "No such query\n");
} //}
vlogprintf (E_WARNING, "No such query\n");
in_ptr = in_end; in_ptr = in_end;
} else { } else {
if (!(q->flags & QUERY_ACK_RECEIVED)) { if (!(q->flags & QUERY_ACK_RECEIVED)) {
...@@ -247,7 +242,7 @@ void query_result (long long id UU) { ...@@ -247,7 +242,7 @@ void query_result (long long id UU) {
if (q->methods->type) { if (q->methods->type) {
int *save = in_ptr; int *save = in_ptr;
if (skip_type_any (q->methods->type) < 0) { if (skip_type_any (q->methods->type) < 0) {
logprintf ("Skipped %ld int out of %ld (type %s)\n", in_ptr - save, in_end - save, q->methods->type->type->id); vlogprintf (E_ERROR, "Skipped %ld int out of %ld (type %s)\n", in_ptr - save, in_end - save, q->methods->type->type->id);
assert (0); assert (0);
} }
...@@ -272,16 +267,12 @@ DEFINE_TREE (timer, struct event_timer *, event_timer_cmp, 0) ...@@ -272,16 +267,12 @@ DEFINE_TREE (timer, struct event_timer *, event_timer_cmp, 0)
struct tree_timer *timer_tree; struct tree_timer *timer_tree;
void insert_event_timer (struct event_timer *ev) { void insert_event_timer (struct event_timer *ev) {
if (verbosity > 2) { vlogprintf (E_DEBUG + 2, "INSERT: %lf %p %p\n", ev->timeout, ev->self, ev->alarm);
logprintf ( "INSERT: %lf %p %p\n", ev->timeout, ev->self, ev->alarm);
}
timer_tree = tree_insert_timer (timer_tree, ev, lrand48 ()); timer_tree = tree_insert_timer (timer_tree, ev, lrand48 ());
} }
void remove_event_timer (struct event_timer *ev) { void remove_event_timer (struct event_timer *ev) {
if (verbosity > 2) { vlogprintf (E_DEBUG + 2, "REMOVE: %lf %p %p\n", ev->timeout, ev->self, ev->alarm);
logprintf ( "REMOVE: %lf %p %p\n", ev->timeout, ev->self, ev->alarm);
}
timer_tree = tree_delete_timer (timer_tree, ev); timer_tree = tree_delete_timer (timer_tree, ev);
} }
...@@ -298,21 +289,19 @@ void work_timers (void) { ...@@ -298,21 +289,19 @@ void work_timers (void) {
if (ev->timeout > t) { break; } if (ev->timeout > t) { break; }
remove_event_timer (ev); remove_event_timer (ev);
assert (ev->alarm); assert (ev->alarm);
if (verbosity) { vlogprintf (E_DEBUG, "Alarm\n");
logprintf ("Alarm\n");
}
ev->alarm (ev->self); ev->alarm (ev->self);
} }
} }
int max_chat_size; int max_chat_size;
int max_bcast_size; int max_bcast_size;
int want_dc_num; //int want_dc_num;
int new_dc_num; //int new_dc_num;
extern struct dc *DC_list[]; extern struct dc *DC_list[];
extern struct dc *DC_working; extern struct dc *DC_working;
void out_random (int n) { static void out_random (int n) {
assert (n <= 32); assert (n <= 32);
static char buf[32]; static char buf[32];
secure_random (buf, n); secure_random (buf, n);
...@@ -331,19 +320,19 @@ void tgl_do_insert_header (void) { ...@@ -331,19 +320,19 @@ void tgl_do_insert_header (void) {
static char buf[4096]; static char buf[4096];
tsnprintf (buf, sizeof (buf), "%.999s %.999s %.999s\n", st.sysname, st.release, st.version); tsnprintf (buf, sizeof (buf), "%.999s %.999s %.999s\n", st.sysname, st.release, st.version);
out_string (buf); out_string (buf);
out_string (TG_VERSION " (build " TG_BUILD ")"); out_string (TGL_VERSION " (build " TGL_BUILD ")");
out_string ("En"); out_string ("En");
} else { } else {
out_string ("x86"); out_string ("x86");
out_string ("Linux"); out_string ("Linux");
out_string (TG_VERSION); out_string (TGL_VERSION);
out_string ("en"); out_string ("en");
} }
} }
/* {{{ Get config */ /* {{{ Get config */
void fetch_dc_option (void) { static void fetch_dc_option (void) {
assert (fetch_int () == CODE_dc_option); assert (fetch_int () == CODE_dc_option);
int id = fetch_int (); int id = fetch_int ();
int l1 = prefetch_strlen (); int l1 = prefetch_strlen ();
...@@ -351,14 +340,12 @@ void fetch_dc_option (void) { ...@@ -351,14 +340,12 @@ void fetch_dc_option (void) {
int l2 = prefetch_strlen (); int l2 = prefetch_strlen ();
char *ip = fetch_str (l2); char *ip = fetch_str (l2);
int port = fetch_int (); int port = fetch_int ();
if (verbosity) { vlogprintf (E_DEBUG, "id = %d, name = %.*s ip = %.*s port = %d\n", id, l1, name, l2, ip, port);
logprintf ( "id = %d, name = %.*s ip = %.*s port = %d\n", id, l1, name, l2, ip, port);
}
bl_do_dc_option (id, l1, name, l2, ip, port); bl_do_dc_option (id, l1, name, l2, ip, port);
} }
int help_get_config_on_answer (struct query *q UU) { static int help_get_config_on_answer (struct query *q UU) {
unsigned op = fetch_int (); unsigned op = fetch_int ();
assert (op == CODE_config || op == CODE_config_old); assert (op == CODE_config || op == CODE_config_old);
fetch_int (); fetch_int ();
...@@ -367,9 +354,7 @@ int help_get_config_on_answer (struct query *q UU) { ...@@ -367,9 +354,7 @@ int help_get_config_on_answer (struct query *q UU) {
assert (test_mode == CODE_bool_true || test_mode == CODE_bool_false); assert (test_mode == CODE_bool_true || test_mode == CODE_bool_false);
assert (test_mode == CODE_bool_false || test_mode == CODE_bool_true); assert (test_mode == CODE_bool_false || test_mode == CODE_bool_true);
int this_dc = fetch_int (); int this_dc = fetch_int ();
if (verbosity) { vlogprintf (E_DEBUG, "this_dc = %d\n", this_dc);
logprintf ( "this_dc = %d\n", this_dc);
}
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
assert (n <= 10); assert (n <= 10);
...@@ -381,30 +366,32 @@ int help_get_config_on_answer (struct query *q UU) { ...@@ -381,30 +366,32 @@ int help_get_config_on_answer (struct query *q UU) {
if (op == CODE_config) { if (op == CODE_config) {
max_bcast_size = fetch_int (); max_bcast_size = fetch_int ();
} }
if (verbosity >= 2) { vlogprintf (E_DEBUG, "chat_size = %d\n", max_chat_size);
logprintf ( "chat_size = %d\n", max_chat_size);
if (q->callback) {
((void (*)(void *, int))(q->callback))(q->callback_extra, 1);
} }
return 0; return 0;
} }
struct query_methods help_get_config_methods = { static struct query_methods help_get_config_methods = {
.on_answer = help_get_config_on_answer, .on_answer = help_get_config_on_answer,
.type = TYPE_TO_PARAM(config) .type = TYPE_TO_PARAM(config)
}; };
void tgl_do_help_get_config (void) { void tgl_do_help_get_config (void (*callback)(void *, int), void *callback_extra) {
clear_packet (); clear_packet ();
tgl_do_insert_header (); tgl_do_insert_header ();
out_int (CODE_help_get_config); out_int (CODE_help_get_config);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &help_get_config_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &help_get_config_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Send code */ /* {{{ Send code */
char *phone_code_hash; static char *phone_code_hash;
int send_code_on_answer (struct query *q UU) { static int send_code_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_auth_sent_code); assert (fetch_int () == (int)CODE_auth_sent_code);
fetch_bool (); int registered = fetch_bool ();
int l = prefetch_strlen (); int l = prefetch_strlen ();
char *s = fetch_str (l); char *s = fetch_str (l);
if (phone_code_hash) { if (phone_code_hash) {
...@@ -414,10 +401,13 @@ int send_code_on_answer (struct query *q UU) { ...@@ -414,10 +401,13 @@ int send_code_on_answer (struct query *q UU) {
fetch_int (); fetch_int ();
fetch_bool (); fetch_bool ();
want_dc_num = -1; want_dc_num = -1;
if (q->callback) {
((void (*)(void *, int, int, const char *))(q->callback)) (q->callback_extra, 1, registered, phone_code_hash);
}
return 0; return 0;
} }
int send_code_on_error (struct query *q UU, int error_code, int l, char *error) { static int send_code_on_error (struct query *q UU, int error_code, int l, char *error) {
int s = strlen ("PHONE_MIGRATE_"); int s = strlen ("PHONE_MIGRATE_");
int s2 = strlen ("NETWORK_MIGRATE_"); int s2 = strlen ("NETWORK_MIGRATE_");
if (l >= s && !memcmp (error, "PHONE_MIGRATE_", s)) { if (l >= s && !memcmp (error, "PHONE_MIGRATE_", s)) {
...@@ -427,31 +417,26 @@ int send_code_on_error (struct query *q UU, int error_code, int l, char *error) ...@@ -427,31 +417,26 @@ int send_code_on_error (struct query *q UU, int error_code, int l, char *error)
int i = error[s2] - '0'; int i = error[s2] - '0';
want_dc_num = i; want_dc_num = i;
} else { } else {
logprintf ( "error_code = %d, error = %.*s\n", error_code, l, error); vlogprintf (E_ERROR, "error_code = %d, error = %.*s\n", error_code, l, error);
assert (0); assert (0);
} }
if (q->callback) {
((void (*)(void *, int, int, const char *))(q->callback)) (q->callback_extra, 0, 0, 0);
}
return 0; return 0;
} }
struct query_methods send_code_methods = { static struct query_methods send_code_methods = {
.on_answer = send_code_on_answer, .on_answer = send_code_on_answer,
.on_error = send_code_on_error, .on_error = send_code_on_error,
.type = TYPE_TO_PARAM(auth_sent_code) .type = TYPE_TO_PARAM(auth_sent_code)
}; };
int code_is_sent (void) { //char *suser;
return want_dc_num;
}
int config_got (void) {
return DC_list[want_dc_num] != 0;
}
char *suser;
extern int dc_working_num; extern int dc_working_num;
void tgl_do_send_code (const char *user) { void tgl_do_send_code (const char *user, void (*callback)(void *callback_extra, int success, int registered, const char *hash), void *callback_extra) {
logprintf ("sending code\n"); vlogprintf (E_DEBUG, "sending code to dc %d\n", dc_working_num);
suser = tstrdup (user); //suser = tstrdup (user);
want_dc_num = 0; want_dc_num = 0;
clear_packet (); clear_packet ();
tgl_do_insert_header (); tgl_do_insert_header ();
...@@ -462,56 +447,26 @@ void tgl_do_send_code (const char *user) { ...@@ -462,56 +447,26 @@ void tgl_do_send_code (const char *user) {
out_string (TG_APP_HASH); out_string (TG_APP_HASH);
out_string ("en"); out_string ("en");
logprintf ("send_code: dc_num = %d\n", dc_working_num); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_code_methods, 0, callback, callback_extra);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_code_methods, 0);
net_loop (0, code_is_sent);
if (want_dc_num == -1) { return; }
DC_working = DC_list[want_dc_num];
if (!DC_working->sessions[0]) {
dc_create_session (DC_working);
}
dc_working_num = want_dc_num;
bl_do_set_working_dc (dc_working_num);
logprintf ("send_code: dc_num = %d\n", dc_working_num);
want_dc_num = 0;
clear_packet ();
tgl_do_insert_header ();
out_int (CODE_auth_send_code);
out_string (user);
out_int (0);
out_int (TG_APP_ID);
out_string (TG_APP_HASH);
out_string ("en");
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_code_methods, 0);
net_loop (0, code_is_sent);
assert (want_dc_num == -1);
} }
int phone_call_on_answer (struct query *q UU) { static int phone_call_on_answer (struct query *q UU) {
fetch_bool (); fetch_bool ();
if (q->callback) {
((void (*)(void *, int))(q->callback))(q->callback_extra, 1);
}
return 0; return 0;
} }
int phone_call_on_error (struct query *q UU, int error_code, int l, char *error) { static struct query_methods phone_call_methods = {
logprintf ( "error_code = %d, error = %.*s\n", error_code, l, error);
assert (0);
return 0;
}
struct query_methods phone_call_methods = {
.on_answer = phone_call_on_answer, .on_answer = phone_call_on_answer,
.on_error = phone_call_on_error,
.type = TYPE_TO_PARAM(bool) .type = TYPE_TO_PARAM(bool)
}; };
void tgl_do_phone_call (const char *user) { void tgl_do_phone_call (const char *user, void (*callback)(void *callback_extra, int success), void *callback_extra) {
logprintf ("calling user\n"); vlogprintf (E_DEBUG, "calling user\n");
suser = tstrdup (user); //suser = tstrdup (user);
want_dc_num = 0; want_dc_num = 0;
clear_packet (); clear_packet ();
tgl_do_insert_header (); tgl_do_insert_header ();
...@@ -519,13 +474,12 @@ void tgl_do_phone_call (const char *user) { ...@@ -519,13 +474,12 @@ void tgl_do_phone_call (const char *user) {
out_string (user); out_string (user);
out_string (phone_code_hash); out_string (phone_code_hash);
logprintf ("tgl_do_phone_call: dc_num = %d\n", dc_working_num); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &phone_call_methods, 0, callback, callback_extra);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &phone_call_methods, 0);
} }
/* }}} */ /* }}} */
/* {{{ Check phone */ /* {{{ Check phone */
int check_phone_result; /*int check_phone_result;
int cr_f (void) { int cr_f (void) {
return check_phone_result >= 0; return check_phone_result >= 0;
} }
...@@ -586,11 +540,11 @@ int tgl_do_auth_check_phone (const char *user) { ...@@ -586,11 +540,11 @@ int tgl_do_auth_check_phone (const char *user) {
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &check_phone_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &check_phone_methods, 0);
net_loop (0, cr_f); net_loop (0, cr_f);
return check_phone_result; return check_phone_result;
} }*/
/* }}} */ /* }}} */
/* {{{ Nearest DC */ /* {{{ Nearest DC */
int nearest_dc_num; /*int nearest_dc_num;
int nr_f (void) { int nr_f (void) {
return nearest_dc_num >= 0; return nearest_dc_num >= 0;
} }
...@@ -607,12 +561,6 @@ int nearest_dc_on_answer (struct query *q UU) { ...@@ -607,12 +561,6 @@ int nearest_dc_on_answer (struct query *q UU) {
return 0; return 0;
} }
int fail_on_error (struct query *q UU, int error_code UU, int l UU, char *error UU) {
fprintf (stderr, "error #%d: %.*s\n", error_code, l, error);
assert (0);
return 0;
}
struct query_methods nearest_dc_methods = { struct query_methods nearest_dc_methods = {
.on_answer = nearest_dc_on_answer, .on_answer = nearest_dc_on_answer,
.on_error = fail_on_error, .on_error = fail_on_error,
...@@ -626,79 +574,58 @@ int tgl_do_get_nearest_dc (void) { ...@@ -626,79 +574,58 @@ int tgl_do_get_nearest_dc (void) {
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &nearest_dc_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &nearest_dc_methods, 0);
net_loop (0, nr_f); net_loop (0, nr_f);
return nearest_dc_num; return nearest_dc_num;
} }*/
/* }}} */ /* }}} */
/* {{{ Sign in / Sign up */ /* {{{ Sign in / Sign up */
int sign_in_ok; static int sign_in_on_answer (struct query *q UU) {
int sign_in_is_ok (void) {
return sign_in_ok;
}
struct tgl_user User;
int sign_in_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_auth_authorization); assert (fetch_int () == (int)CODE_auth_authorization);
int expires = fetch_int (); int expires = fetch_int ();
tglf_fetch_user (&User); vlogprintf (E_DEBUG, "Expires in %d\n", expires);
if (!tgl_state.our_id) {
bl_do_set_our_id (tgl_get_peer_id (User.id)); struct tgl_user *U = tglf_fetch_alloc_user ();
}
sign_in_ok = 1;
if (verbosity) {
logprintf ( "authorized successfully: name = '%s %s', phone = '%s', expires = %d\n", User.first_name, User.last_name, User.phone, (int)(expires - get_double_time ()));
}
DC_working->has_auth = 1; DC_working->has_auth = 1;
bl_do_dc_signed (DC_working->id); bl_do_dc_signed (DC_working->id);
return 0; if (q->callback) {
} ((void (*)(void *, int, struct tgl_user *))q->callback) (q->callback_extra, 1, U);
}
int sign_in_on_error (struct query *q UU, int error_code, int l, char *error) {
logprintf ( "error_code = %d, error = %.*s\n", error_code, l, error);
sign_in_ok = -1;
assert (0);
return 0; return 0;
} }
struct query_methods sign_in_methods = { static struct query_methods sign_in_methods = {
.on_answer = sign_in_on_answer, .on_answer = sign_in_on_answer,
.on_error = sign_in_on_error,
.type = TYPE_TO_PARAM(auth_authorization) .type = TYPE_TO_PARAM(auth_authorization)
}; };
int tgl_do_send_code_result (const char *code) { int tgl_do_send_code_result (const char *user, const char *code, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_auth_sign_in); out_int (CODE_auth_sign_in);
out_string (suser); out_string (user);
out_string (phone_code_hash); out_string (phone_code_hash);
out_string (code); out_string (code);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0, callback, callback_extra);
sign_in_ok = 0; return 0;
net_loop (0, sign_in_is_ok);
return sign_in_ok;
} }
int tgl_do_send_code_result_auth (const char *code, const char *first_name, const char *last_name) { int tgl_do_send_code_result_auth (const char *user, const char *code, const char *first_name, const char *last_name, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_auth_sign_up); out_int (CODE_auth_sign_up);
out_string (suser); out_string (user);
out_string (phone_code_hash); out_string (phone_code_hash);
out_string (code); out_string (code);
out_string (first_name); out_string (first_name);
out_string (last_name); out_string (last_name);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0, callback, callback_extra);
sign_in_ok = 0; return 0;
net_loop (0, sign_in_is_ok);
return sign_in_ok;
} }
/* }}} */ /* }}} */
/* {{{ Get contacts */ /* {{{ Get contacts */
extern char *user_list[]; static int get_contacts_on_answer (struct query *q UU) {
int get_contacts_on_answer (struct query *q UU) {
int i; int i;
assert (fetch_int () == (int)CODE_contacts_contacts); assert (fetch_int () == (int)CODE_contacts_contacts);
...@@ -711,7 +638,15 @@ int get_contacts_on_answer (struct query *q UU) { ...@@ -711,7 +638,15 @@ int get_contacts_on_answer (struct query *q UU) {
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
struct tgl_user **list = talloc (sizeof (void *) * n);
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
list[i] = tglf_fetch_alloc_user ();
}
if (q->callback) {
((void (*)(void *, int, int, struct tgl_user **))q->callback) (q->callback_extra, 1, n, list);
}
tfree (list, sizeof (void *) * n);
/* for (i = 0; i < n; i++) {
struct tgl_user *U = tglf_fetch_alloc_user (); struct tgl_user *U = tglf_fetch_alloc_user ();
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
...@@ -739,30 +674,30 @@ int get_contacts_on_answer (struct query *q UU) { ...@@ -739,30 +674,30 @@ int get_contacts_on_answer (struct query *q UU) {
} }
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
return 0; return 0;
} }
struct query_methods get_contacts_methods = { static struct query_methods get_contacts_methods = {
.on_answer = get_contacts_on_answer, .on_answer = get_contacts_on_answer,
.type = TYPE_TO_PARAM(contacts_contacts) .type = TYPE_TO_PARAM(contacts_contacts)
}; };
void tgl_do_update_contact_list (void) { void tgl_do_update_contact_list (void (*callback) (void *callback_extra, int success, int size, struct tgl_user *contacts[]), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_contacts_get_contacts); out_int (CODE_contacts_get_contacts);
out_string (""); out_string ("");
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_contacts_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_contacts_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Encrypt decrypted */ /* {{{ Encrypt decrypted */
int *encr_extra; static int *encr_extra;
int *encr_ptr; static int *encr_ptr;
int *encr_end; static int *encr_end;
char *encrypt_decrypted_message (struct tgl_secret_chat *E) { static char *encrypt_decrypted_message (struct tgl_secret_chat *E) {
static int msg_key[4]; static int msg_key[4];
static unsigned char sha1a_buffer[20]; static unsigned char sha1a_buffer[20];
static unsigned char sha1b_buffer[20]; static unsigned char sha1b_buffer[20];
...@@ -848,22 +783,25 @@ void tgl_do_send_encr_chat_layer (struct tgl_secret_chat *E) { ...@@ -848,22 +783,25 @@ void tgl_do_send_encr_chat_layer (struct tgl_secret_chat *E) {
struct tgl_message *M = tgl_message_get (t); struct tgl_message *M = tgl_message_get (t);
assert (M); assert (M);
tgl_do_send_msg (M); tgl_do_send_msg (M, 0, 0);
print_message (M); //print_message (M);
} }
/* {{{ Seng msg (plain text) */ /* {{{ Seng msg (plain text) */
int msg_send_encr_on_answer (struct query *q UU) { static int msg_send_encr_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_messages_sent_encrypted_message); assert (fetch_int () == CODE_messages_sent_encrypted_message);
rprintf ("Sent\n");
struct tgl_message *M = q->extra; struct tgl_message *M = q->extra;
//M->date = fetch_int (); //M->date = fetch_int ();
fetch_int (); fetch_int ();
bl_do_set_message_sent (M); bl_do_set_message_sent (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback) (q->callback_extra, 1, M);
}
return 0; return 0;
} }
int msg_send_on_answer (struct query *q UU) { static int msg_send_on_answer (struct query *q UU) {
unsigned x = fetch_int (); unsigned x = fetch_int ();
assert (x == CODE_messages_sent_message || x == CODE_messages_sent_message_link); assert (x == CODE_messages_sent_message || x == CODE_messages_sent_message_link);
int id = fetch_int (); // id int id = fetch_int (); // id
...@@ -873,6 +811,9 @@ int msg_send_on_answer (struct query *q UU) { ...@@ -873,6 +811,9 @@ int msg_send_on_answer (struct query *q UU) {
fetch_pts (); fetch_pts ();
fetch_seq (); fetch_seq ();
if (x == CODE_messages_sent_message_link) { if (x == CODE_messages_sent_message_link) {
assert (skip_type_any (TYPE_TO_PARAM_1 (vector, TYPE_TO_PARAM (contacts_link))) >= 0);
}
/*if (x == CODE_messages_sent_message_link) {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
int i; int i;
...@@ -910,35 +851,46 @@ int msg_send_on_answer (struct query *q UU) { ...@@ -910,35 +851,46 @@ int msg_send_on_answer (struct query *q UU) {
pop_color (); pop_color ();
print_end (); print_end ();
} }
} }*/
rprintf ("Sent: id = %d\n", id);
bl_do_set_message_sent (M); bl_do_set_message_sent (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback) (q->callback_extra, 1, M);
}
return 0; return 0;
} }
int msg_send_on_error (struct query *q, int error_code, int error_len, char *error) { static int msg_send_on_error (struct query *q, int error_code, int error_len, char *error) {
logprintf ( "error for query #%lld: #%d :%.*s\n", q->msg_id, error_code, error_len, error); vlogprintf (E_WARNING, "error for query #%lld: #%d :%.*s\n", q->msg_id, error_code, error_len, error);
struct tgl_message *M = q->extra; struct tgl_message *M = q->extra;
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback) (q->callback_extra, 0, M);
}
bl_do_delete_msg (M); bl_do_delete_msg (M);
return 0; return 0;
} }
struct query_methods msg_send_methods = { static struct query_methods msg_send_methods = {
.on_answer = msg_send_on_answer, .on_answer = msg_send_on_answer,
.on_error = msg_send_on_error, .on_error = msg_send_on_error,
.type = TYPE_TO_PARAM(messages_sent_message) .type = TYPE_TO_PARAM(messages_sent_message)
}; };
struct query_methods msg_send_encr_methods = { static struct query_methods msg_send_encr_methods = {
.on_answer = msg_send_encr_on_answer, .on_answer = msg_send_encr_on_answer,
.type = TYPE_TO_PARAM(messages_sent_encrypted_message) .type = TYPE_TO_PARAM(messages_sent_encrypted_message)
}; };
int out_message_num; //int out_message_num;
void tgl_do_send_encr_msg_action (struct tgl_message *M) { void tgl_do_send_encr_msg_action (struct tgl_message *M, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
tgl_peer_t *P = tgl_peer_get (M->to_id); tgl_peer_t *P = tgl_peer_get (M->to_id);
if (!P || P->encr_chat.state != sc_ok) { return; } if (!P || P->encr_chat.state != sc_ok) {
vlogprintf (E_WARNING, "Unknown encrypted chat\n");
if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, M);
}
return;
}
clear_packet (); clear_packet ();
out_int (CODE_messages_send_encrypted_service); out_int (CODE_messages_send_encrypted_service);
...@@ -963,16 +915,22 @@ void tgl_do_send_encr_msg_action (struct tgl_message *M) { ...@@ -963,16 +915,22 @@ void tgl_do_send_encr_msg_action (struct tgl_message *M) {
} }
encr_finish (&P->encr_chat); encr_finish (&P->encr_chat);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M, callback, callback_extra);
} }
void tgl_do_send_encr_msg (struct tgl_message *M) { void tgl_do_send_encr_msg (struct tgl_message *M, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
if (M->service) { if (M->service) {
tgl_do_send_encr_msg_action (M); tgl_do_send_encr_msg_action (M, callback, callback_extra);
return; return;
} }
tgl_peer_t *P = tgl_peer_get (M->to_id); tgl_peer_t *P = tgl_peer_get (M->to_id);
if (!P || P->encr_chat.state != sc_ok) { return; } if (!P || P->encr_chat.state != sc_ok) {
vlogprintf (E_WARNING, "Unknown encrypted chat\n");
if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, M);
}
return;
}
clear_packet (); clear_packet ();
out_int (CODE_messages_send_encrypted); out_int (CODE_messages_send_encrypted);
...@@ -990,12 +948,12 @@ void tgl_do_send_encr_msg (struct tgl_message *M) { ...@@ -990,12 +948,12 @@ void tgl_do_send_encr_msg (struct tgl_message *M) {
out_int (CODE_decrypted_message_media_empty); out_int (CODE_decrypted_message_media_empty);
encr_finish (&P->encr_chat); encr_finish (&P->encr_chat);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M, callback, callback_extra);
} }
void tgl_do_send_msg (struct tgl_message *M) { void tgl_do_send_msg (struct tgl_message *M, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
if (tgl_get_peer_type (M->to_id) == TGL_PEER_ENCR_CHAT) { if (tgl_get_peer_type (M->to_id) == TGL_PEER_ENCR_CHAT) {
tgl_do_send_encr_msg (M); tgl_do_send_encr_msg (M, callback, callback_extra);
return; return;
} }
clear_packet (); clear_packet ();
...@@ -1003,50 +961,60 @@ void tgl_do_send_msg (struct tgl_message *M) { ...@@ -1003,50 +961,60 @@ void tgl_do_send_msg (struct tgl_message *M) {
out_peer_id (M->to_id); out_peer_id (M->to_id);
out_cstring (M->message, M->message_len); out_cstring (M->message, M->message_len);
out_long (M->id); out_long (M->id);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_methods, M); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_methods, M, callback, callback_extra);
} }
void tgl_do_send_message (tgl_peer_id_t id, const char *msg, int len) { void tgl_do_send_message (tgl_peer_id_t id, const char *msg, int len, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) {
tgl_peer_t *P = tgl_peer_get (id); tgl_peer_t *P = tgl_peer_get (id);
if (!P) { if (!P) {
logprintf ("Can not send to unknown encrypted chat\n"); vlogprintf (E_WARNING, "Unknown encrypted chat\n");
if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, 0);
}
return; return;
} }
if (P->encr_chat.state != sc_ok) { if (P->encr_chat.state != sc_ok) {
logprintf ("Chat is not yet initialized\n"); vlogprintf (E_WARNING, "Chat is not yet initialized\n");
if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, 0);
}
return; return;
} }
} }
long long t; long long t;
secure_random (&t, 8); secure_random (&t, 8);
logprintf ("t = %lld, len = %d\n", t, len); vlogprintf (E_DEBUG, "t = %lld, len = %d\n", t, len);
bl_do_send_message_text (t, tgl_state.our_id, tgl_get_peer_type (id), tgl_get_peer_id (id), time (0), len, msg); bl_do_send_message_text (t, tgl_state.our_id, tgl_get_peer_type (id), tgl_get_peer_id (id), time (0), len, msg);
struct tgl_message *M = tgl_message_get (t); struct tgl_message *M = tgl_message_get (t);
assert (M); assert (M);
tgl_do_send_msg (M); tgl_do_send_msg (M, callback, callback_extra);
print_message (M); //print_message (M);
} }
/* }}} */ /* }}} */
/* {{{ Send text file */ /* {{{ Send text file */
void tgl_do_send_text (tgl_peer_id_t id, char *file_name) { void tgl_do_send_text (tgl_peer_id_t id, char *file_name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
int fd = open (file_name, O_RDONLY); int fd = open (file_name, O_RDONLY);
if (fd < 0) { if (fd < 0) {
rprintf ("No such file '%s'\n", file_name); vlogprintf (E_WARNING, "No such file '%s'\n", file_name);
tfree_str (file_name); if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, 0);
}
return; return;
} }
static char buf[(1 << 20) + 1]; static char buf[(1 << 20) + 1];
int x = read (fd, buf, (1 << 20) + 1); int x = read (fd, buf, (1 << 20) + 1);
assert (x >= 0); assert (x >= 0);
if (x == (1 << 20) + 1) { if (x == (1 << 20) + 1) {
rprintf ("Too big file '%s'\n", file_name); vlogprintf (E_WARNING, "Too big file '%s'\n", file_name);
tfree_str (file_name);
close (fd); close (fd);
if (callback) {
((void (*)(void *, int, struct tgl_message *))callback) (callback_extra, 0, 0);
}
} else { } else {
buf[x] = 0; buf[x] = 0;
tgl_do_send_message (id, buf, x); tgl_do_send_message (id, buf, x, callback, callback_extra);
tfree_str (file_name); tfree_str (file_name);
close (fd); close (fd);
} }
...@@ -1054,96 +1022,93 @@ void tgl_do_send_text (tgl_peer_id_t id, char *file_name) { ...@@ -1054,96 +1022,93 @@ void tgl_do_send_text (tgl_peer_id_t id, char *file_name) {
/* }}} */ /* }}} */
/* {{{ Mark read */ /* {{{ Mark read */
int mark_read_on_receive (struct query *q UU) { static int mark_read_on_receive (struct query *q UU) {
assert (fetch_int () == (int)CODE_messages_affected_history); assert (fetch_int () == (int)CODE_messages_affected_history);
fetch_pts (); fetch_pts ();
fetch_seq (); fetch_seq ();
fetch_int (); // offset fetch_int (); // offset
if (q->callback) {
((void (*)(void *, int))q->callback)(q->callback_extra, 1);
}
return 0; return 0;
} }
int mark_read_encr_on_receive (struct query *q UU) { static int mark_read_encr_on_receive (struct query *q UU) {
fetch_bool (); fetch_bool ();
if (q->callback) {
((void (*)(void *, int))q->callback)(q->callback_extra, 1);
}
return 0; return 0;
} }
struct query_methods mark_read_methods = { static struct query_methods mark_read_methods = {
.on_answer = mark_read_on_receive, .on_answer = mark_read_on_receive,
.type = TYPE_TO_PARAM(messages_affected_history) .type = TYPE_TO_PARAM(messages_affected_history)
}; };
struct query_methods mark_read_encr_methods = { static struct query_methods mark_read_encr_methods = {
.on_answer = mark_read_encr_on_receive, .on_answer = mark_read_encr_on_receive,
.type = TYPE_TO_PARAM(bool) .type = TYPE_TO_PARAM(bool)
}; };
void tgl_do_messages_mark_read (tgl_peer_id_t id, int max_id) { void tgl_do_messages_mark_read (tgl_peer_id_t id, int max_id, void (*callback)(void *callback_extra, int), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_read_history); out_int (CODE_messages_read_history);
out_peer_id (id); out_peer_id (id);
out_int (max_id); out_int (max_id);
out_int (0); out_int (0);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_methods, 0, callback, callback_extra);
} }
void tgl_do_messages_mark_read_encr (tgl_peer_id_t id, long long access_hash, int last_time) { void tgl_do_messages_mark_read_encr (tgl_peer_id_t id, long long access_hash, int last_time, void (*callback)(void *callback_extra, int), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_read_encrypted_history); out_int (CODE_messages_read_encrypted_history);
out_int (CODE_input_encrypted_chat); out_int (CODE_input_encrypted_chat);
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
out_long (access_hash); out_long (access_hash);
out_int (last_time); out_int (last_time);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_encr_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_encr_methods, 0, callback, callback_extra);
} }
void tgl_do_mark_read (tgl_peer_id_t id) { void tgl_do_mark_read (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success), void *callback_extra) {
tgl_peer_t *P = tgl_peer_get (id); tgl_peer_t *P = tgl_peer_get (id);
if (!P) { if (!P) {
rprintf ("Unknown peer\n"); vlogprintf (E_WARNING, "Unknown peer\n");
callback (callback_extra, 0);
return; return;
} }
if (tgl_get_peer_type (id) == TGL_PEER_USER || tgl_get_peer_type (id) == TGL_PEER_CHAT) { if (tgl_get_peer_type (id) == TGL_PEER_USER || tgl_get_peer_type (id) == TGL_PEER_CHAT) {
if (!P->last) { if (!P->last) {
rprintf ("Unknown last peer message\n"); vlogprintf (E_WARNING, "Unknown last peer message\n");
callback (callback_extra, 0);
return; return;
} }
tgl_do_messages_mark_read (id, P->last->id); tgl_do_messages_mark_read (id, P->last->id, callback, callback_extra);
return; return;
} }
assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT); assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT);
if (P->last) { if (P->last) {
tgl_do_messages_mark_read_encr (id, P->encr_chat.access_hash, P->last->date); tgl_do_messages_mark_read_encr (id, P->encr_chat.access_hash, P->last->date, callback, callback_extra);
} else { } else {
tgl_do_messages_mark_read_encr (id, P->encr_chat.access_hash, time (0) - 10); tgl_do_messages_mark_read_encr (id, P->encr_chat.access_hash, time (0) - 10, callback, callback_extra);
} }
} }
/* }}} */ /* }}} */
/* {{{ Get history */ /* {{{ Get history */
int get_history_on_answer (struct query *q UU) { static int get_history_on_answer (struct query *q UU) {
static struct tgl_message *ML[10000];
int i; int i;
int x = fetch_int (); int x = fetch_int ();
if (x == (int)CODE_messages_messages_slice) { assert (x == (int)CODE_messages_messages_slice || x == (int)CODE_messages_messages);
fetch_int ();
rprintf ("...\n");
} else {
assert (x == (int)CODE_messages_messages);
}
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
struct tgl_message **ML = talloc (sizeof (void *) * n);
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
struct tgl_message *M = tglf_fetch_alloc_message (); ML[i] = tglf_fetch_alloc_message ();
if (i <= 9999) {
ML[i] = M;
}
} }
if (n > 10000) { n = 10000; }
int sn = n; int sn = n;
for (i = n - 1; i >= 0; i--) {
print_message (ML[i]);
}
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
...@@ -1154,20 +1119,32 @@ int get_history_on_answer (struct query *q UU) { ...@@ -1154,20 +1119,32 @@ int get_history_on_answer (struct query *q UU) {
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
tglf_fetch_alloc_user (); tglf_fetch_alloc_user ();
} }
if (q->callback) {
((void (*)(void *, int, int, struct tgl_message **))q->callback) (q->callback_extra, 1, sn, ML);
}
tfree (ML, sizeof (void *) * n);
/*for (i = n - 1; i >= 0; i--) {
print_message (ML[i]);
}*/
if (sn > 0 && q->extra) { if (sn > 0 && q->extra) {
tgl_do_messages_mark_read (*(tgl_peer_id_t *)&(q->extra), ML[0]->id); tgl_do_messages_mark_read (*(tgl_peer_id_t *)&(q->extra), ML[0]->id, 0, 0);
} }
return 0; return 0;
} }
struct query_methods get_history_methods = { static struct query_methods get_history_methods = {
.on_answer = get_history_on_answer, .on_answer = get_history_on_answer,
.type = TYPE_TO_PARAM(messages_messages) .type = TYPE_TO_PARAM(messages_messages)
}; };
void tgl_do_get_local_history (tgl_peer_id_t id, int limit) { void tgl_do_get_local_history (tgl_peer_id_t id, int limit, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) {
tgl_peer_t *P = tgl_peer_get (id); tgl_peer_t *P = tgl_peer_get (id);
if (!P || !P->last) { return; } if (!P || !P->last) {
callback (callback_extra, 0, 0, 0);
return;
}
struct tgl_message *M = P->last; struct tgl_message *M = P->last;
int count = 1; int count = 1;
assert (!M->prev); assert (!M->prev);
...@@ -1175,16 +1152,23 @@ void tgl_do_get_local_history (tgl_peer_id_t id, int limit) { ...@@ -1175,16 +1152,23 @@ void tgl_do_get_local_history (tgl_peer_id_t id, int limit) {
M = M->next; M = M->next;
count ++; count ++;
} }
while (M) { struct tgl_message **ML = talloc (sizeof (void *) * count);
print_message (M); M = P->last;
M = M->prev; ML[0] = M;
count = 1;
while (count < limit && M->next) {
M = M->next;
ML[count ++] = M->next;
} }
callback (callback_extra, 1, count, ML);
tfree (ML, sizeof (void *) * count);
} }
void tgl_do_get_history (tgl_peer_id_t id, int limit) { void tgl_do_get_history (tgl_peer_id_t id, int limit, int offline_mode, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) {
if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT || offline_mode) { if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT || offline_mode) {
tgl_do_get_local_history (id, limit); tgl_do_get_local_history (id, limit, callback, callback_extra);
tgl_do_mark_read (id); tgl_do_mark_read (id, 0, 0);
return; return;
} }
clear_packet (); clear_packet ();
...@@ -1193,13 +1177,12 @@ void tgl_do_get_history (tgl_peer_id_t id, int limit) { ...@@ -1193,13 +1177,12 @@ void tgl_do_get_history (tgl_peer_id_t id, int limit) {
out_int (0); out_int (0);
out_int (0); out_int (0);
out_int (limit); out_int (limit);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_history_methods, (void *)*(long *)&id); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_history_methods, (void *)*(long *)&id, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Get dialogs */ /* {{{ Get dialogs */
int dialog_list_got; static int get_dialogs_on_answer (struct query *q UU) {
int get_dialogs_on_answer (struct query *q UU) {
unsigned x = fetch_int (); unsigned x = fetch_int ();
assert (x == CODE_messages_dialogs || x == CODE_messages_dialogs_slice); assert (x == CODE_messages_dialogs || x == CODE_messages_dialogs_slice);
if (x == CODE_messages_dialogs_slice) { if (x == CODE_messages_dialogs_slice) {
...@@ -1208,20 +1191,16 @@ int get_dialogs_on_answer (struct query *q UU) { ...@@ -1208,20 +1191,16 @@ int get_dialogs_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n, i; int n, i;
n = fetch_int (); n = fetch_int ();
static int dlist[2 * 100];
static tgl_peer_id_t plist[100];
int dl_size = n; int dl_size = n;
tgl_peer_id_t *PL = talloc0 (sizeof (tgl_peer_id_t) * n);
int *UC = talloc0 (4 * n);
int *LM = talloc0 (4 * n);
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
assert (fetch_int () == (int)CODE_dialog); assert (fetch_int () == (int)CODE_dialog);
if (i < 100) { PL[i] = tglf_fetch_peer_id ();
plist[i] = tglf_fetch_peer_id (); LM[i] = fetch_int ();
dlist[2 * i + 0] = fetch_int (); UC[i] = fetch_int ();
dlist[2 * i + 1] = fetch_int ();
} else {
tglf_fetch_peer_id ();
fetch_int ();
fetch_int ();
}
assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0); assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0);
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
...@@ -1239,7 +1218,7 @@ int get_dialogs_on_answer (struct query *q UU) { ...@@ -1239,7 +1218,7 @@ int get_dialogs_on_answer (struct query *q UU) {
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
tglf_fetch_alloc_user (); tglf_fetch_alloc_user ();
} }
print_start (); /*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
for (i = dl_size - 1; i >= 0; i--) { for (i = dl_size - 1; i >= 0; i--) {
tgl_peer_t *UC; tgl_peer_t *UC;
...@@ -1261,23 +1240,31 @@ int get_dialogs_on_answer (struct query *q UU) { ...@@ -1261,23 +1240,31 @@ int get_dialogs_on_answer (struct query *q UU) {
pop_color (); pop_color ();
print_end (); print_end ();
dialog_list_got = 1; dialog_list_got = 1;*/
if (q->callback) {
((void (*)(void *, int, int, tgl_peer_id_t *, int *, int *))q->callback) (q->callback_extra, 1, dl_size, PL, LM, UC);
}
tfree (PL, sizeof (tgl_peer_id_t) * dl_size);
tfree (UC, 4 * dl_size);
tfree (LM, 4 * dl_size);
return 0; return 0;
} }
struct query_methods get_dialogs_methods = { static struct query_methods get_dialogs_methods = {
.on_answer = get_dialogs_on_answer, .on_answer = get_dialogs_on_answer,
.type = TYPE_TO_PARAM(messages_dialogs) .type = TYPE_TO_PARAM(messages_dialogs)
}; };
void tgl_do_get_dialog_list (void) { void tgl_do_get_dialog_list (void (*callback)(void *callback_extra, int success, int size, tgl_peer_id_t peers[], int last_msg_id[], int unread_count[]), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_get_dialogs); out_int (CODE_messages_get_dialogs);
out_int (0); out_int (0);
out_int (0); out_int (0);
out_int (1000); out_int (1000);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dialogs_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dialogs_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
...@@ -1301,7 +1288,7 @@ struct send_file { ...@@ -1301,7 +1288,7 @@ struct send_file {
unsigned char *key; unsigned char *key;
}; };
void out_peer_id (tgl_peer_id_t id) { static void out_peer_id (tgl_peer_id_t id) {
tgl_peer_t *U; tgl_peer_t *U;
switch (tgl_get_peer_type (id)) { switch (tgl_get_peer_type (id)) {
case TGL_PEER_CHAT: case TGL_PEER_CHAT:
...@@ -1324,14 +1311,14 @@ void out_peer_id (tgl_peer_id_t id) { ...@@ -1324,14 +1311,14 @@ void out_peer_id (tgl_peer_id_t id) {
} }
} }
void send_part (struct send_file *f); static void send_part (struct send_file *f, void *callback, void *callback_extra);
int send_file_part_on_answer (struct query *q) { static int send_file_part_on_answer (struct query *q) {
assert (fetch_int () == (int)CODE_bool_true); assert (fetch_int () == (int)CODE_bool_true);
send_part (q->extra); send_part (q->extra, q->callback, q->callback_extra);
return 0; return 0;
} }
int send_file_on_answer (struct query *q UU) { static int send_file_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_messages_stated_message); assert (fetch_int () == (int)CODE_messages_stated_message);
struct tgl_message *M = tglf_fetch_alloc_message (); struct tgl_message *M = tglf_fetch_alloc_message ();
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
...@@ -1347,14 +1334,15 @@ int send_file_on_answer (struct query *q UU) { ...@@ -1347,14 +1334,15 @@ int send_file_on_answer (struct query *q UU) {
} }
fetch_pts (); fetch_pts ();
fetch_seq (); fetch_seq ();
print_message (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback)(q->callback_extra, 1, M);
}
//print_message (M);
return 0; return 0;
} }
int send_encr_file_on_answer (struct query *q UU) { static int send_encr_file_on_answer (struct query *q UU) {
if (prefetch_int () != (int)CODE_messages_sent_encrypted_file) {
hexdump_in ();
}
assert (fetch_int () == (int)CODE_messages_sent_encrypted_file); assert (fetch_int () == (int)CODE_messages_sent_encrypted_file);
struct tgl_message *M = q->extra; struct tgl_message *M = q->extra;
M->date = fetch_int (); M->date = fetch_int ();
...@@ -1365,30 +1353,34 @@ int send_encr_file_on_answer (struct query *q UU) { ...@@ -1365,30 +1353,34 @@ int send_encr_file_on_answer (struct query *q UU) {
fetch_int (); fetch_int ();
M->media.encr_photo.dc_id = fetch_int (); M->media.encr_photo.dc_id = fetch_int ();
assert (fetch_int () == M->media.encr_photo.key_fingerprint); assert (fetch_int () == M->media.encr_photo.key_fingerprint);
print_message (M); //print_message (M);
tglm_message_insert (M); tglm_message_insert (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback)(q->callback_extra, 1, M);
}
return 0; return 0;
} }
struct query_methods send_file_part_methods = { static struct query_methods send_file_part_methods = {
.on_answer = send_file_part_on_answer, .on_answer = send_file_part_on_answer,
.type = TYPE_TO_PARAM(bool) .type = TYPE_TO_PARAM(bool)
}; };
struct query_methods send_file_methods = { static struct query_methods send_file_methods = {
.on_answer = send_file_on_answer, .on_answer = send_file_on_answer,
.type = TYPE_TO_PARAM(messages_stated_message) .type = TYPE_TO_PARAM(messages_stated_message)
}; };
struct query_methods send_encr_file_methods = { static struct query_methods send_encr_file_methods = {
.on_answer = send_encr_file_on_answer, .on_answer = send_encr_file_on_answer,
.type = TYPE_TO_PARAM(messages_sent_encrypted_message) .type = TYPE_TO_PARAM(messages_sent_encrypted_message)
}; };
void send_part (struct send_file *f) { static void send_part (struct send_file *f, void *callback, void *callback_extra) {
if (f->fd >= 0) { if (f->fd >= 0) {
if (!f->part_num) { if (!f->part_num) {
cur_uploading_bytes += f->size; tgl_state.cur_uploading_bytes += f->size;
} }
clear_packet (); clear_packet ();
if (f->size < (16 << 20)) { if (f->size < (16 << 20)) {
...@@ -1405,7 +1397,7 @@ void send_part (struct send_file *f) { ...@@ -1405,7 +1397,7 @@ void send_part (struct send_file *f) {
int x = read (f->fd, buf, f->part_size); int x = read (f->fd, buf, f->part_size);
assert (x > 0); assert (x > 0);
f->offset += x; f->offset += x;
cur_uploaded_bytes += x; tgl_state.cur_uploaded_bytes += x;
if (f->encr) { if (f->encr) {
if (x & 15) { if (x & 15) {
...@@ -1420,21 +1412,19 @@ void send_part (struct send_file *f) { ...@@ -1420,21 +1412,19 @@ void send_part (struct send_file *f) {
memset (&aes_key, 0, sizeof (aes_key)); memset (&aes_key, 0, sizeof (aes_key));
} }
out_cstring (buf, x); out_cstring (buf, x);
if (verbosity >= 2) { vlogprintf (E_DEBUG, "offset=%lld size=%lld\n", f->offset, f->size);
logprintf ("offset=%lld size=%lld\n", f->offset, f->size);
}
if (f->offset == f->size) { if (f->offset == f->size) {
close (f->fd); close (f->fd);
f->fd = -1; f->fd = -1;
} else { } else {
assert (f->part_size == x); assert (f->part_size == x);
} }
update_prompt (); //update_prompt ();
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f, callback, callback_extra);
} else { } else {
cur_uploaded_bytes -= f->size; tgl_state.cur_uploaded_bytes -= f->size;
cur_uploading_bytes -= f->size; tgl_state.cur_uploading_bytes -= f->size;
update_prompt (); //update_prompt ();
clear_packet (); clear_packet ();
assert (f->media_type == CODE_input_media_uploaded_photo || f->media_type == CODE_input_media_uploaded_video || f->media_type == CODE_input_media_uploaded_thumb_video || f->media_type == CODE_input_media_uploaded_audio || f->media_type == CODE_input_media_uploaded_document || f->media_type == CODE_input_media_uploaded_thumb_document); assert (f->media_type == CODE_input_media_uploaded_photo || f->media_type == CODE_input_media_uploaded_video || f->media_type == CODE_input_media_uploaded_thumb_video || f->media_type == CODE_input_media_uploaded_audio || f->media_type == CODE_input_media_uploaded_document || f->media_type == CODE_input_media_uploaded_thumb_document);
if (!f->encr) { if (!f->encr) {
...@@ -1477,7 +1467,7 @@ void send_part (struct send_file *f) { ...@@ -1477,7 +1467,7 @@ void send_part (struct send_file *f) {
} }
out_long (-lrand48 () * (1ll << 32) - lrand48 ()); out_long (-lrand48 () * (1ll << 32) - lrand48 ());
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_methods, 0, callback, callback_extra);
} else { } else {
struct tgl_message *M = talloc0 (sizeof (*M)); struct tgl_message *M = talloc0 (sizeof (*M));
...@@ -1568,38 +1558,37 @@ void send_part (struct send_file *f) { ...@@ -1568,38 +1558,37 @@ void send_part (struct send_file *f) {
M->id = r; M->id = r;
M->date = time (0); M->date = time (0);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_file_methods, M); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_file_methods, M, callback, callback_extra);
} }
tfree_str (f->file_name); tfree_str (f->file_name);
tfree (f, sizeof (*f)); tfree (f, sizeof (*f));
} }
} }
void send_file_thumb (struct send_file *f) { /*void send_file_thumb (struct send_file *f, void *callback, void *callback_extra) {
clear_packet (); clear_packet ();
f->thumb_id = lrand48 () * (1ll << 32) + lrand48 (); f->thumb_id = lrand48 () * (1ll << 32) + lrand48 ();
out_int (CODE_upload_save_file_part); out_int (CODE_upload_save_file_part);
out_long (f->thumb_id); out_long (f->thumb_id);
out_int (0); out_int (0);
out_cstring ((void *)thumb_file, thumb_file_size); out_cstring ((void *)thumb_file, thumb_file_size);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f, callback, callback_extra);
} }*/
void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name) { void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
int fd = open (file_name, O_RDONLY); int fd = open (file_name, O_RDONLY);
if (fd < 0) { if (fd < 0) {
rprintf ("No such file '%s'\n", file_name); vlogprintf (E_WARNING, "No such file '%s'\n", file_name);
tfree_str (file_name); callback (callback_extra, 0, 0);
return; return;
} }
struct stat buf; struct stat buf;
fstat (fd, &buf); fstat (fd, &buf);
long long size = buf.st_size; long long size = buf.st_size;
if (size <= 0) { if (size <= 0) {
rprintf ("File has zero length\n"); vlogprintf (E_WARNING, "File has zero length\n");
tfree_str (file_name);
close (fd); close (fd);
callback (callback_extra, 0, 0);
return; return;
} }
struct send_file *f = talloc0 (sizeof (*f)); struct send_file *f = talloc0 (sizeof (*f));
...@@ -1615,16 +1604,16 @@ void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name) { ...@@ -1615,16 +1604,16 @@ void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name) {
if (f->part_size > (512 << 10)) { if (f->part_size > (512 << 10)) {
close (fd); close (fd);
rprintf ("Too big file. Maximal supported size is %d.\n", (512 << 10) * 1000); vlogprintf (E_WARNING, "Too big file. Maximal supported size is %d.\n", (512 << 10) * 1000);
tfree (f, sizeof (*f)); tfree (f, sizeof (*f));
tfree_str (file_name); callback (callback_extra, 0, 0);
return; return;
} }
f->id = lrand48 () * (1ll << 32) + lrand48 (); f->id = lrand48 () * (1ll << 32) + lrand48 ();
f->to_id = to_id; f->to_id = to_id;
f->media_type = type; f->media_type = type;
f->file_name = file_name; f->file_name = tstrdup (file_name);
if (tgl_get_peer_type (f->to_id) == TGL_PEER_ENCR_CHAT) { if (tgl_get_peer_type (f->to_id) == TGL_PEER_ENCR_CHAT) {
f->encr = 1; f->encr = 1;
f->iv = talloc (32); f->iv = talloc (32);
...@@ -1643,12 +1632,12 @@ void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name) { ...@@ -1643,12 +1632,12 @@ void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name) {
} else { } else {
send_part (f); send_part (f);
}*/ }*/
send_part (f); send_part (f, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Forward */ /* {{{ Forward */
int fwd_msg_on_answer (struct query *q UU) { static int fwd_msg_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_messages_stated_message); assert (fetch_int () == (int)CODE_messages_stated_message);
struct tgl_message *M = tglf_fetch_alloc_message (); struct tgl_message *M = tglf_fetch_alloc_message ();
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
...@@ -1664,18 +1653,22 @@ int fwd_msg_on_answer (struct query *q UU) { ...@@ -1664,18 +1653,22 @@ int fwd_msg_on_answer (struct query *q UU) {
} }
fetch_pts (); fetch_pts ();
fetch_seq (); fetch_seq ();
print_message (M); //print_message (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback) (q->callback_extra, 1, M);
}
return 0; return 0;
} }
struct query_methods fwd_msg_methods = { static struct query_methods fwd_msg_methods = {
.on_answer = fwd_msg_on_answer, .on_answer = fwd_msg_on_answer,
.type = TYPE_TO_PARAM(messages_stated_message) .type = TYPE_TO_PARAM(messages_stated_message)
}; };
void tgl_do_forward_message (tgl_peer_id_t id, int n) { void tgl_do_forward_message (tgl_peer_id_t id, int n, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) {
rprintf ("Can not forward messages from secret chat\n"); vlogprintf (E_WARNING, "Can not forward messages from secret chat\n");
callback (callback_extra, 0, 0);
return; return;
} }
clear_packet (); clear_packet ();
...@@ -1683,12 +1676,12 @@ void tgl_do_forward_message (tgl_peer_id_t id, int n) { ...@@ -1683,12 +1676,12 @@ void tgl_do_forward_message (tgl_peer_id_t id, int n) {
out_peer_id (id); out_peer_id (id);
out_int (n); out_int (n);
out_long (lrand48 () * (1ll << 32) + lrand48 ()); out_long (lrand48 () * (1ll << 32) + lrand48 ());
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Rename chat */ /* {{{ Rename chat */
int rename_chat_on_answer (struct query *q UU) { static int rename_chat_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_messages_stated_message); assert (fetch_int () == (int)CODE_messages_stated_message);
struct tgl_message *M = tglf_fetch_alloc_message (); struct tgl_message *M = tglf_fetch_alloc_message ();
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
...@@ -1704,27 +1697,30 @@ int rename_chat_on_answer (struct query *q UU) { ...@@ -1704,27 +1697,30 @@ int rename_chat_on_answer (struct query *q UU) {
} }
fetch_pts (); fetch_pts ();
fetch_seq (); fetch_seq ();
print_message (M); //print_message (M);
if (q->callback) {
((void (*)(void *, int, struct tgl_message *))q->callback) (q->callback_extra, 1, M);
}
return 0; return 0;
} }
struct query_methods rename_chat_methods = { static struct query_methods rename_chat_methods = {
.on_answer = rename_chat_on_answer, .on_answer = rename_chat_on_answer,
.type = TYPE_TO_PARAM(messages_stated_message) .type = TYPE_TO_PARAM(messages_stated_message)
}; };
void tgl_do_rename_chat (tgl_peer_id_t id, char *name UU) { void tgl_do_rename_chat (tgl_peer_id_t id, char *name UU, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_edit_chat_title); out_int (CODE_messages_edit_chat_title);
assert (tgl_get_peer_type (id) == TGL_PEER_CHAT); assert (tgl_get_peer_type (id) == TGL_PEER_CHAT);
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
out_string (name); out_string (name);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &rename_chat_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &rename_chat_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Chat info */ /* {{{ Chat info */
void print_chat_info (struct tgl_chat *C) { /*void print_chat_info (struct tgl_chat *C) {
tgl_peer_t *U = (void *)C; tgl_peer_t *U = (void *)C;
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
...@@ -1746,26 +1742,31 @@ void print_chat_info (struct tgl_chat *C) { ...@@ -1746,26 +1742,31 @@ void print_chat_info (struct tgl_chat *C) {
} }
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
int chat_info_on_answer (struct query *q UU) { static int chat_info_on_answer (struct query *q UU) {
struct tgl_chat *C = tglf_fetch_alloc_chat_full (); struct tgl_chat *C = tglf_fetch_alloc_chat_full ();
print_chat_info (C); //print_chat_info (C);
if (q->callback) {
((void (*)(void *, int, struct tgl_chat *))q->callback) (q->callback_extra, 0, C);
}
return 0; return 0;
} }
struct query_methods chat_info_methods = { static struct query_methods chat_info_methods = {
.on_answer = chat_info_on_answer, .on_answer = chat_info_on_answer,
.type = TYPE_TO_PARAM(messages_chat_full) .type = TYPE_TO_PARAM(messages_chat_full)
}; };
void tgl_do_get_chat_info (tgl_peer_id_t id) { void tgl_do_get_chat_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_chat *C), void *callback_extra) {
if (offline_mode) { if (offline_mode) {
tgl_peer_t *C = tgl_peer_get (id); tgl_peer_t *C = tgl_peer_get (id);
if (!C) { if (!C) {
rprintf ("No such chat\n"); vlogprintf (E_WARNING, "No such chat\n");
callback (callback_extra, 0, 0);
} else { } else {
print_chat_info (&C->chat); //print_chat_info (&C->chat);
callback (callback_extra, 1, &C->chat);
} }
return; return;
} }
...@@ -1773,13 +1774,13 @@ void tgl_do_get_chat_info (tgl_peer_id_t id) { ...@@ -1773,13 +1774,13 @@ void tgl_do_get_chat_info (tgl_peer_id_t id) {
out_int (CODE_messages_get_full_chat); out_int (CODE_messages_get_full_chat);
assert (tgl_get_peer_type (id) == TGL_PEER_CHAT); assert (tgl_get_peer_type (id) == TGL_PEER_CHAT);
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &chat_info_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &chat_info_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ User info */ /* {{{ User info */
void print_user_info (struct tgl_user *U) { /*void print_user_info (struct tgl_user *U) {
tgl_peer_t *C = (void *)U; tgl_peer_t *C = (void *)U;
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
...@@ -1797,26 +1798,29 @@ void print_user_info (struct tgl_user *U) { ...@@ -1797,26 +1798,29 @@ void print_user_info (struct tgl_user *U) {
} }
pop_color (); pop_color ();
print_end (); print_end ();
} }*/
int user_info_on_answer (struct query *q UU) { static int user_info_on_answer (struct query *q UU) {
struct tgl_user *U = tglf_fetch_alloc_user_full (); struct tgl_user *U = tglf_fetch_alloc_user_full ();
print_user_info (U); if (q->callback) {
((void (*)(void *, int, struct tgl_user *))q->callback) (q->callback_extra, 0, U);
}
return 0; return 0;
} }
struct query_methods user_info_methods = { static struct query_methods user_info_methods = {
.on_answer = user_info_on_answer, .on_answer = user_info_on_answer,
.type = TYPE_TO_PARAM(user_full) .type = TYPE_TO_PARAM(user_full)
}; };
void tgl_do_get_user_info (tgl_peer_id_t id) { void tgl_do_get_user_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_user *U), void *callback_extra) {
if (offline_mode) { if (offline_mode) {
tgl_peer_t *C = tgl_peer_get (id); tgl_peer_t *C = tgl_peer_get (id);
if (!C) { if (!C) {
rprintf ("No such user\n"); vlogprintf (E_WARNING, "No such user\n");
callback (callback_extra, 0, 0);
} else { } else {
print_user_info (&C->user); callback (callback_extra, 1, &C->user);
} }
return; return;
} }
...@@ -1832,12 +1836,12 @@ void tgl_do_get_user_info (tgl_peer_id_t id) { ...@@ -1832,12 +1836,12 @@ void tgl_do_get_user_info (tgl_peer_id_t id) {
out_int (CODE_input_user_contact); out_int (CODE_input_user_contact);
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
} }
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &user_info_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &user_info_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Get user info silently */ /* {{{ Get user info silently */
int user_list_info_silent_on_answer (struct query *q UU) { /*int user_list_info_silent_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
int i; int i;
...@@ -1864,7 +1868,7 @@ void tgl_do_get_user_list_info_silent (int num, int *list) { ...@@ -1864,7 +1868,7 @@ void tgl_do_get_user_list_info_silent (int num, int *list) {
//out_long (0); //out_long (0);
} }
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &user_list_info_silent_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &user_list_info_silent_methods, 0);
} }*/
/* }}} */ /* }}} */
/* {{{ Load photo/video */ /* {{{ Load photo/video */
...@@ -1886,12 +1890,12 @@ struct download { ...@@ -1886,12 +1890,12 @@ struct download {
}; };
void end_load (struct download *D) { static void end_load (struct download *D, void *callback, void *callback_extra) {
cur_downloading_bytes -= D->size; tgl_state.cur_downloading_bytes -= D->size;
cur_downloaded_bytes -= D->size; tgl_state.cur_downloaded_bytes -= D->size;
update_prompt (); //update_prompt ();
close (D->fd); close (D->fd);
if (D->next == 1) { /*if (D->next == 1) {
logprintf ("Done: %s\n", D->name); logprintf ("Done: %s\n", D->name);
} else if (D->next == 2) { } else if (D->next == 2) {
static char buf[PATH_MAX]; static char buf[PATH_MAX];
...@@ -1904,7 +1908,12 @@ void end_load (struct download *D) { ...@@ -1904,7 +1908,12 @@ void end_load (struct download *D) {
logprintf ("Image is at %s\n", D->name); logprintf ("Image is at %s\n", D->name);
} }
} }
}*/
if (callback) {
((void (*)(void *, int, char *))callback) (callback_extra, 1, D->name);
} }
if (D->iv) { if (D->iv) {
tfree_secure (D->iv, 32); tfree_secure (D->iv, 32);
} }
...@@ -1912,8 +1921,8 @@ void end_load (struct download *D) { ...@@ -1912,8 +1921,8 @@ void end_load (struct download *D) {
tfree (D, sizeof (*D)); tfree (D, sizeof (*D));
} }
void load_next_part (struct download *D); static void load_next_part (struct download *D, void *callback, void *callback_extra);
int download_on_answer (struct query *q) { static int download_on_answer (struct query *q) {
assert (fetch_int () == (int)CODE_upload_file); assert (fetch_int () == (int)CODE_upload_file);
unsigned x = fetch_int (); unsigned x = fetch_int ();
assert (x); assert (x);
...@@ -1924,8 +1933,8 @@ int download_on_answer (struct query *q) { ...@@ -1924,8 +1933,8 @@ int download_on_answer (struct query *q) {
fetch_int (); // mtime fetch_int (); // mtime
int len = prefetch_strlen (); int len = prefetch_strlen ();
assert (len >= 0); assert (len >= 0);
cur_downloaded_bytes += len; tgl_state.cur_downloaded_bytes += len;
update_prompt (); //update_prompt ();
if (D->iv) { if (D->iv) {
unsigned char *ptr = (void *)fetch_str (len); unsigned char *ptr = (void *)fetch_str (len);
assert (!(len & 15)); assert (!(len & 15));
...@@ -1942,20 +1951,20 @@ int download_on_answer (struct query *q) { ...@@ -1942,20 +1951,20 @@ int download_on_answer (struct query *q) {
} }
D->offset += len; D->offset += len;
if (D->offset < D->size) { if (D->offset < D->size) {
load_next_part (D); load_next_part (D, q->callback, q->callback_extra);
return 0; return 0;
} else { } else {
end_load (D); end_load (D, q->callback, q->callback_extra);
return 0; return 0;
} }
} }
struct query_methods download_methods = { static struct query_methods download_methods = {
.on_answer = download_on_answer, .on_answer = download_on_answer,
.type = TYPE_TO_PARAM(upload_file) .type = TYPE_TO_PARAM(upload_file)
}; };
void load_next_part (struct download *D) { static void load_next_part (struct download *D, void *callback, void *callback_extra) {
if (!D->offset) { if (!D->offset) {
static char buf[PATH_MAX]; static char buf[PATH_MAX];
int l; int l;
...@@ -1965,7 +1974,7 @@ void load_next_part (struct download *D) { ...@@ -1965,7 +1974,7 @@ void load_next_part (struct download *D) {
l = tsnprintf (buf, sizeof (buf), "%s/download_%lld", get_downloads_directory (), D->id); l = tsnprintf (buf, sizeof (buf), "%s/download_%lld", get_downloads_directory (), D->id);
} }
if (l >= (int) sizeof (buf)) { if (l >= (int) sizeof (buf)) {
logprintf ("Download filename is too long"); vlogprintf (E_ERROR, "Download filename is too long");
exit (1); exit (1);
} }
D->name = tstrdup (buf); D->name = tstrdup (buf);
...@@ -1973,17 +1982,17 @@ void load_next_part (struct download *D) { ...@@ -1973,17 +1982,17 @@ void load_next_part (struct download *D) {
if (stat (buf, &st) >= 0) { if (stat (buf, &st) >= 0) {
D->offset = st.st_size; D->offset = st.st_size;
if (D->offset >= D->size) { if (D->offset >= D->size) {
cur_downloading_bytes += D->size; tgl_state.cur_downloading_bytes += D->size;
cur_downloaded_bytes += D->offset; tgl_state.cur_downloaded_bytes += D->offset;
rprintf ("Already downloaded\n"); vlogprintf (E_NOTICE, "Already downloaded\n");
end_load (D); end_load (D, callback, callback_extra);
return; return;
} }
} }
cur_downloading_bytes += D->size; tgl_state.cur_downloading_bytes += D->size;
cur_downloaded_bytes += D->offset; tgl_state.cur_downloaded_bytes += D->offset;
update_prompt (); //update_prompt ();
} }
clear_packet (); clear_packet ();
out_int (CODE_upload_get_file); out_int (CODE_upload_get_file);
...@@ -2003,18 +2012,18 @@ void load_next_part (struct download *D) { ...@@ -2003,18 +2012,18 @@ void load_next_part (struct download *D) {
} }
out_int (D->offset); out_int (D->offset);
out_int (1 << 14); out_int (1 << 14);
send_query (DC_list[D->dc], packet_ptr - packet_buffer, packet_buffer, &download_methods, D); send_query (DC_list[D->dc], packet_ptr - packet_buffer, packet_buffer, &download_methods, D, callback, callback_extra);
//send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &download_methods, D); //send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &download_methods, D);
} }
void tgl_do_load_photo_size (struct tgl_photo_size *P, int next) { void tgl_do_load_photo_size (struct tgl_photo_size *P, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
if (!P->loc.dc) { if (!P->loc.dc) {
rprintf ("Bad video thumb\n"); vlogprintf (E_WARNING, "Bad video thumb\n");
callback (callback_extra, 0, 0);
return; return;
} }
assert (P); assert (P);
assert (next);
struct download *D = talloc0 (sizeof (*D)); struct download *D = talloc0 (sizeof (*D));
D->id = 0; D->id = 0;
D->offset = 0; D->offset = 0;
...@@ -2023,14 +2032,17 @@ void tgl_do_load_photo_size (struct tgl_photo_size *P, int next) { ...@@ -2023,14 +2032,17 @@ void tgl_do_load_photo_size (struct tgl_photo_size *P, int next) {
D->dc = P->loc.dc; D->dc = P->loc.dc;
D->local_id = P->loc.local_id; D->local_id = P->loc.local_id;
D->secret = P->loc.secret; D->secret = P->loc.secret;
D->next = next;
D->name = 0; D->name = 0;
D->fd = -1; D->fd = -1;
load_next_part (D); load_next_part (D, callback, callback_extra);
} }
void tgl_do_load_photo (struct tgl_photo *photo, int next) { void tgl_do_load_photo (struct tgl_photo *photo, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
if (!photo->sizes_num) { return; } if (!photo->sizes_num) {
vlogprintf (E_WARNING, "No sizes\n");
callback (callback_extra, 0, 0);
return;
}
int max = -1; int max = -1;
int maxi = 0; int maxi = 0;
int i; int i;
...@@ -2040,81 +2052,73 @@ void tgl_do_load_photo (struct tgl_photo *photo, int next) { ...@@ -2040,81 +2052,73 @@ void tgl_do_load_photo (struct tgl_photo *photo, int next) {
maxi = i; maxi = i;
} }
} }
tgl_do_load_photo_size (&photo->sizes[maxi], next); tgl_do_load_photo_size (&photo->sizes[maxi], callback, callback_extra);
} }
void tgl_do_load_video_thumb (struct tgl_video *video, int next) { void tgl_do_load_video_thumb (struct tgl_video *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
tgl_do_load_photo_size (&video->thumb, next); tgl_do_load_photo_size (&video->thumb, callback, callback_extra);
} }
void tgl_do_load_document_thumb (struct tgl_document *video, int next) { void tgl_do_load_document_thumb (struct tgl_document *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
tgl_do_load_photo_size (&video->thumb, next); tgl_do_load_photo_size (&video->thumb, callback, callback_extra);
} }
void tgl_do_load_video (struct tgl_video *V, int next) { void tgl_do_load_video (struct tgl_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
assert (V); assert (V);
assert (next);
struct download *D = talloc0 (sizeof (*D)); struct download *D = talloc0 (sizeof (*D));
D->offset = 0; D->offset = 0;
D->size = V->size; D->size = V->size;
D->id = V->id; D->id = V->id;
D->access_hash = V->access_hash; D->access_hash = V->access_hash;
D->dc = V->dc_id; D->dc = V->dc_id;
D->next = next;
D->name = 0; D->name = 0;
D->fd = -1; D->fd = -1;
D->type = CODE_input_video_file_location; D->type = CODE_input_video_file_location;
load_next_part (D); load_next_part (D, callback, callback_extra);
} }
void tgl_do_load_audio (struct tgl_video *V, int next) { void tgl_do_load_audio (struct tgl_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
assert (V); assert (V);
assert (next);
struct download *D = talloc0 (sizeof (*D)); struct download *D = talloc0 (sizeof (*D));
D->offset = 0; D->offset = 0;
D->size = V->size; D->size = V->size;
D->id = V->id; D->id = V->id;
D->access_hash = V->access_hash; D->access_hash = V->access_hash;
D->dc = V->dc_id; D->dc = V->dc_id;
D->next = next;
D->name = 0; D->name = 0;
D->fd = -1; D->fd = -1;
D->type = CODE_input_audio_file_location; D->type = CODE_input_audio_file_location;
load_next_part (D); load_next_part (D, callback, callback_extra);
} }
void tgl_do_load_document (struct tgl_document *V, int next) { void tgl_do_load_document (struct tgl_document *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
assert (V); assert (V);
assert (next);
struct download *D = talloc0 (sizeof (*D)); struct download *D = talloc0 (sizeof (*D));
D->offset = 0; D->offset = 0;
D->size = V->size; D->size = V->size;
D->id = V->id; D->id = V->id;
D->access_hash = V->access_hash; D->access_hash = V->access_hash;
D->dc = V->dc_id; D->dc = V->dc_id;
D->next = next;
D->name = 0; D->name = 0;
D->fd = -1; D->fd = -1;
D->type = CODE_input_document_file_location; D->type = CODE_input_document_file_location;
load_next_part (D); load_next_part (D, callback, callback_extra);
} }
void tgl_do_load_encr_video (struct tgl_encr_video *V, int next) { void tgl_do_load_encr_video (struct tgl_encr_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra) {
assert (V); assert (V);
assert (next);
struct download *D = talloc0 (sizeof (*D)); struct download *D = talloc0 (sizeof (*D));
D->offset = 0; D->offset = 0;
D->size = V->size; D->size = V->size;
D->id = V->id; D->id = V->id;
D->access_hash = V->access_hash; D->access_hash = V->access_hash;
D->dc = V->dc_id; D->dc = V->dc_id;
D->next = next;
D->name = 0; D->name = 0;
D->fd = -1; D->fd = -1;
D->key = V->key; D->key = V->key;
D->iv = talloc (32); D->iv = talloc (32);
memcpy (D->iv, V->iv, 32); memcpy (D->iv, V->iv, 32);
load_next_part (D); load_next_part (D, callback, callback_extra);
unsigned char md5[16]; unsigned char md5[16];
unsigned char str[64]; unsigned char str[64];
...@@ -2126,78 +2130,64 @@ void tgl_do_load_encr_video (struct tgl_encr_video *V, int next) { ...@@ -2126,78 +2130,64 @@ void tgl_do_load_encr_video (struct tgl_encr_video *V, int next) {
/* }}} */ /* }}} */
/* {{{ Export auth */ /* {{{ Export auth */
char *export_auth_str;
int export_auth_str_len; static int import_auth_on_answer (struct query *q UU) {
int is_export_auth_str (void) { assert (fetch_int () == (int)CODE_auth_authorization);
return export_auth_str != 0; fetch_int (); // expires
} tglf_fetch_alloc_user ();
int isn_export_auth_str (void) {
return export_auth_str == 0; if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
return 0;
} }
int export_auth_on_answer (struct query *q UU) { static struct query_methods import_auth_methods = {
.on_answer = import_auth_on_answer,
.on_error = fail_on_error,
.type = TYPE_TO_PARAM(auth_authorization)
};
static int export_auth_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_auth_exported_authorization); assert (fetch_int () == (int)CODE_auth_exported_authorization);
bl_do_set_our_id (fetch_int ()); bl_do_set_our_id (fetch_int ());
int l = prefetch_strlen (); int l = prefetch_strlen ();
char *s = talloc (l); char *s = talloc (l);
memcpy (s, fetch_str (l), l); memcpy (s, fetch_str (l), l);
export_auth_str_len = l;
export_auth_str = s; clear_packet ();
tgl_do_insert_header ();
out_int (CODE_auth_import_authorization);
out_int (tgl_state.our_id);
out_cstring (s, l);
send_query (q->extra, packet_ptr - packet_buffer, packet_buffer, &import_auth_methods, 0, q->callback, q->callback_extra);
tfree (s, l);
return 0; return 0;
} }
struct query_methods export_auth_methods = { static struct query_methods export_auth_methods = {
.on_answer = export_auth_on_answer, .on_answer = export_auth_on_answer,
.on_error = fail_on_error, .on_error = fail_on_error,
.type = TYPE_TO_PARAM(auth_exported_authorization) .type = TYPE_TO_PARAM(auth_exported_authorization)
}; };
void tgl_do_export_auth (int num) { void tgl_do_export_auth (int num, void (*callback) (void *callback_extra, int success), void *callback_extra) {
export_auth_str = 0;
clear_packet (); clear_packet ();
out_int (CODE_auth_export_authorization); out_int (CODE_auth_export_authorization);
out_int (num); out_int (num);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &export_auth_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &export_auth_methods, DC_list[num], callback, callback_extra);
net_loop (0, is_export_auth_str);
}
/* }}} */
/* {{{ Import auth */
int import_auth_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_auth_authorization);
fetch_int (); // expires
tglf_fetch_alloc_user ();
tfree (export_auth_str, export_auth_str_len);
export_auth_str = 0;
return 0;
}
struct query_methods import_auth_methods = {
.on_answer = import_auth_on_answer,
.on_error = fail_on_error,
.type = TYPE_TO_PARAM(auth_authorization)
};
void tgl_do_import_auth (int num) {
clear_packet ();
tgl_do_insert_header ();
out_int (CODE_auth_import_authorization);
out_int (tgl_state.our_id);
out_cstring (export_auth_str, export_auth_str_len);
send_query (DC_list[num], packet_ptr - packet_buffer, packet_buffer, &import_auth_methods, 0);
net_loop (0, isn_export_auth_str);
} }
/* }}} */ /* }}} */
/* {{{ Add contact */ /* {{{ Add contact */
int add_contact_on_answer (struct query *q UU) { static int add_contact_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_contacts_imported_contacts); assert (fetch_int () == (int)CODE_contacts_imported_contacts);
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
if (n > 0) { if (n > 0) {
logprintf ("Added successfully"); vlogprintf (E_DEBUG, "Added successfully");
} else { } else {
logprintf ("Not added"); vlogprintf (E_DEBUG, "Not added");
} }
int i; int i;
for (i = 0; i < n ; i++) { for (i = 0; i < n ; i++) {
...@@ -2209,11 +2199,16 @@ int add_contact_on_answer (struct query *q UU) { ...@@ -2209,11 +2199,16 @@ int add_contact_on_answer (struct query *q UU) {
n = fetch_int (); n = fetch_int ();
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
long long id = fetch_long (); long long id = fetch_long ();
logprintf ("contact #%lld not added. Please retry\n", id); vlogprintf (E_NOTICE, "contact #%lld not added. Please retry\n", id);
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
for (i = 0; i < n ; i++) {
struct tgl_user **UL = talloc (n * sizeof (void *));
for (i = 0; i < n; i++) {
UL[i] = tglf_fetch_alloc_user ();
}
/*for (i = 0; i < n ; i++) {
struct tgl_user *U = tglf_fetch_alloc_user (); struct tgl_user *U = tglf_fetch_alloc_user ();
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
...@@ -2242,16 +2237,21 @@ int add_contact_on_answer (struct query *q UU) { ...@@ -2242,16 +2237,21 @@ int add_contact_on_answer (struct query *q UU) {
pop_color (); pop_color ();
print_end (); print_end ();
}*/
if (q->callback) {
((void (*)(void *, int, int, struct tgl_user **))q->callback) (q->callback_extra, 1, n, UL);
} }
tfree (UL, n * sizeof (void *));
return 0; return 0;
} }
struct query_methods add_contact_methods = { static struct query_methods add_contact_methods = {
.on_answer = add_contact_on_answer, .on_answer = add_contact_on_answer,
.type = TYPE_TO_PARAM(contacts_imported_contacts) .type = TYPE_TO_PARAM(contacts_imported_contacts)
}; };
void tgl_do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force) { void tgl_do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force, void (*callback)(void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_contacts_import_contacts); out_int (CODE_contacts_import_contacts);
out_int (CODE_vector); out_int (CODE_vector);
...@@ -2262,23 +2262,26 @@ void tgl_do_add_contact (const char *phone, int phone_len, const char *first_nam ...@@ -2262,23 +2262,26 @@ void tgl_do_add_contact (const char *phone, int phone_len, const char *first_nam
out_cstring (first_name, first_name_len); out_cstring (first_name, first_name_len);
out_cstring (last_name, last_name_len); out_cstring (last_name, last_name_len);
out_int (force ? CODE_bool_true : CODE_bool_false); out_int (force ? CODE_bool_true : CODE_bool_false);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_contact_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_contact_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Msg search */ /* {{{ Msg search */
int msg_search_on_answer (struct query *q UU) { static int msg_search_on_answer (struct query *q UU) {
return get_history_on_answer (q); return get_history_on_answer (q);
} }
struct query_methods msg_search_methods = { static struct query_methods msg_search_methods = {
.on_answer = msg_search_on_answer, .on_answer = msg_search_on_answer,
.type = TYPE_TO_PARAM(messages_messages) .type = TYPE_TO_PARAM(messages_messages)
}; };
void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const char *s) { void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const char *s, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) {
if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) {
rprintf ("Can not search in secure chat\n"); vlogprintf (E_WARNING, "Can not search in secure chat\n");
if (callback) {
callback (callback_extra, 0, 0, 0);
}
return; return;
} }
clear_packet (); clear_packet ();
...@@ -2295,12 +2298,12 @@ void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const cha ...@@ -2295,12 +2298,12 @@ void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const cha
out_int (0); // offset out_int (0); // offset
out_int (0); // max_id out_int (0); // max_id
out_int (limit); out_int (limit);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_search_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_search_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Contacts search */ /* {{{ Contacts search */
int contacts_search_on_answer (struct query *q UU) { static int contacts_search_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_contacts_found); assert (fetch_int () == CODE_contacts_found);
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
...@@ -2311,7 +2314,12 @@ int contacts_search_on_answer (struct query *q UU) { ...@@ -2311,7 +2314,12 @@ int contacts_search_on_answer (struct query *q UU) {
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
print_start ();
struct tgl_user **UL = talloc (sizeof (void *) * n);
for (i = 0; i < n; i++) {
UL[i] = tglf_fetch_alloc_user ();
}
/*print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
struct tgl_user *U = tglf_fetch_alloc_user (); struct tgl_user *U = tglf_fetch_alloc_user ();
...@@ -2322,29 +2330,33 @@ int contacts_search_on_answer (struct query *q UU) { ...@@ -2322,29 +2330,33 @@ int contacts_search_on_answer (struct query *q UU) {
printf (". Phone %s\n", U->phone); printf (". Phone %s\n", U->phone);
} }
pop_color (); pop_color ();
print_end (); print_end ();*/
if (q->callback) {
((void (*)(void *, int, int, struct tgl_user **))q->callback) (q->callback_extra, 1, n, UL);
}
tfree (UL, sizeof (void *) * n);
return 0; return 0;
} }
struct query_methods contacts_search_methods = { static struct query_methods contacts_search_methods = {
.on_answer = contacts_search_on_answer, .on_answer = contacts_search_on_answer,
.type = TYPE_TO_PARAM(contacts_found) .type = TYPE_TO_PARAM(contacts_found)
}; };
void tgl_do_contacts_search (int limit, const char *s) { void tgl_do_contacts_search (int limit, const char *s, void (*callback) (void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_contacts_search); out_int (CODE_contacts_search);
out_string (s); out_string (s);
out_int (limit); out_int (limit);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &contacts_search_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &contacts_search_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Encr accept */ /* {{{ Encr accept */
int send_encr_accept_on_answer (struct query *q UU) { static int send_encr_accept_on_answer (struct query *q UU) {
struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (); struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat ();
if (E->state == sc_ok) { /*if (E->state == sc_ok) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
printf ("Encrypted connection with "); printf ("Encrypted connection with ");
...@@ -2360,13 +2372,17 @@ int send_encr_accept_on_answer (struct query *q UU) { ...@@ -2360,13 +2372,17 @@ int send_encr_accept_on_answer (struct query *q UU) {
printf (" failed\n"); printf (" failed\n");
pop_color (); pop_color ();
print_end (); print_end ();
}*/
if (q->callback) {
((void (*)(void *, int, struct tgl_secret_chat *))q->callback) (q->callback_extra, E->state == sc_ok, E);
} }
return 0; return 0;
} }
int send_encr_request_on_answer (struct query *q UU) { static int send_encr_request_on_answer (struct query *q UU) {
struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (); struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat ();
if (E->state == sc_deleted) { /*if (E->state == sc_deleted) {
print_start (); print_start ();
push_color (COLOR_YELLOW); push_color (COLOR_YELLOW);
printf ("Encrypted connection with "); printf ("Encrypted connection with ");
...@@ -2384,26 +2400,30 @@ int send_encr_request_on_answer (struct query *q UU) { ...@@ -2384,26 +2400,30 @@ int send_encr_request_on_answer (struct query *q UU) {
print_end (); print_end ();
assert (E->state == sc_waiting); assert (E->state == sc_waiting);
}*/
if (q->callback) {
((void (*)(void *, int, struct tgl_secret_chat *))q->callback) (q->callback_extra, E->state != sc_deleted, E);
} }
return 0; return 0;
} }
struct query_methods send_encr_accept_methods = { static struct query_methods send_encr_accept_methods = {
.on_answer = send_encr_accept_on_answer, .on_answer = send_encr_accept_on_answer,
.type = TYPE_TO_PARAM(encrypted_chat) .type = TYPE_TO_PARAM(encrypted_chat)
}; };
struct query_methods send_encr_request_methods = { static struct query_methods send_encr_request_methods = {
.on_answer = send_encr_request_on_answer, .on_answer = send_encr_request_on_answer,
.type = TYPE_TO_PARAM(encrypted_chat) .type = TYPE_TO_PARAM(encrypted_chat)
}; };
int encr_root; //int encr_root;
unsigned char *encr_prime; //unsigned char *encr_prime;
int encr_param_version; //int encr_param_version;
BN_CTX *ctx; static BN_CTX *ctx;
void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *random) { void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *random, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) {
int i; int i;
int ok = 0; int ok = 0;
for (i = 0; i < 64; i++) { for (i = 0; i < 64; i++) {
...@@ -2412,7 +2432,10 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran ...@@ -2412,7 +2432,10 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran
break; break;
} }
} }
if (ok) { return; } // Already generated key for this chat if (ok) {
callback (callback_extra, 1, E);
return;
} // Already generated key for this chat
unsigned char random_here[256]; unsigned char random_here[256];
secure_random (random_here, 256); secure_random (random_here, 256);
for (i = 0; i < 256; i++) { for (i = 0; i < 256; i++) {
...@@ -2422,12 +2445,12 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran ...@@ -2422,12 +2445,12 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran
ensure_ptr (b); ensure_ptr (b);
BIGNUM *g_a = BN_bin2bn (E->g_key, 256, 0); BIGNUM *g_a = BN_bin2bn (E->g_key, 256, 0);
ensure_ptr (g_a); ensure_ptr (g_a);
assert (check_g (encr_prime, g_a) >= 0); assert (check_g (tgl_state.encr_prime, g_a) >= 0);
if (!ctx) { if (!ctx) {
ctx = BN_CTX_new (); ctx = BN_CTX_new ();
ensure_ptr (ctx); ensure_ptr (ctx);
} }
BIGNUM *p = BN_bin2bn (encr_prime, 256, 0); BIGNUM *p = BN_bin2bn (tgl_state.encr_prime, 256, 0);
ensure_ptr (p); ensure_ptr (p);
BIGNUM *r = BN_new (); BIGNUM *r = BN_new ();
ensure_ptr (r); ensure_ptr (r);
...@@ -2449,7 +2472,7 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran ...@@ -2449,7 +2472,7 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran
out_int (tgl_get_peer_id (E->id)); out_int (tgl_get_peer_id (E->id));
out_long (E->access_hash); out_long (E->access_hash);
ensure (BN_set_word (g_a, encr_root)); ensure (BN_set_word (g_a, tgl_state.encr_root));
ensure (BN_mod_exp (r, g_a, b, p, ctx)); ensure (BN_mod_exp (r, g_a, b, p, ctx));
static unsigned char buf[256]; static unsigned char buf[256];
memset (buf, 0, sizeof (buf)); memset (buf, 0, sizeof (buf));
...@@ -2462,19 +2485,19 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran ...@@ -2462,19 +2485,19 @@ void tgl_do_send_accept_encr_chat (struct tgl_secret_chat *E, unsigned char *ran
BN_clear_free (p); BN_clear_free (p);
BN_clear_free (r); BN_clear_free (r);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_accept_methods, E); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_accept_methods, E, callback, callback_extra);
} }
void tgl_do_create_keys_end (struct tgl_secret_chat *U) { void tgl_do_create_keys_end (struct tgl_secret_chat *U) {
assert (encr_prime); assert (tgl_state.encr_prime);
BIGNUM *g_b = BN_bin2bn (U->g_key, 256, 0); BIGNUM *g_b = BN_bin2bn (U->g_key, 256, 0);
ensure_ptr (g_b); ensure_ptr (g_b);
assert (check_g (encr_prime, g_b) >= 0); assert (check_g (tgl_state.encr_prime, g_b) >= 0);
if (!ctx) { if (!ctx) {
ctx = BN_CTX_new (); ctx = BN_CTX_new ();
ensure_ptr (ctx); ensure_ptr (ctx);
} }
BIGNUM *p = BN_bin2bn (encr_prime, 256, 0); BIGNUM *p = BN_bin2bn (tgl_state.encr_prime, 256, 0);
ensure_ptr (p); ensure_ptr (p);
BIGNUM *r = BN_new (); BIGNUM *r = BN_new ();
ensure_ptr (r); ensure_ptr (r);
...@@ -2496,13 +2519,7 @@ void tgl_do_create_keys_end (struct tgl_secret_chat *U) { ...@@ -2496,13 +2519,7 @@ void tgl_do_create_keys_end (struct tgl_secret_chat *U) {
sha1 ((void *)U->key, 256, sha_buffer); sha1 ((void *)U->key, 256, sha_buffer);
long long k = *(long long *)(sha_buffer + 12); long long k = *(long long *)(sha_buffer + 12);
if (k != U->key_fingerprint) { if (k != U->key_fingerprint) {
logprintf ("version = %d\n", encr_param_version); vlogprintf (E_WARNING, "Key fingerprint mismatch (my 0x%llx 0x%llx)\n", (unsigned long long)k, (unsigned long long)U->key_fingerprint);
hexdump ((void *)U->nonce, (void *)(U->nonce + 256));
hexdump ((void *)U->g_key, (void *)(U->g_key + 256));
hexdump ((void *)U->key, (void *)(U->key + 64));
hexdump ((void *)t, (void *)(t + 256));
hexdump ((void *)sha_buffer, (void *)(sha_buffer + 20));
logprintf ("!!Key fingerprint mismatch (my 0x%llx 0x%llx)\n", (unsigned long long)k, (unsigned long long)U->key_fingerprint);
U->state = sc_deleted; U->state = sc_deleted;
} }
...@@ -2514,7 +2531,7 @@ void tgl_do_create_keys_end (struct tgl_secret_chat *U) { ...@@ -2514,7 +2531,7 @@ void tgl_do_create_keys_end (struct tgl_secret_chat *U) {
BN_clear_free (a); BN_clear_free (a);
} }
void tgl_do_send_create_encr_chat (void *x, unsigned char *random) { void tgl_do_send_create_encr_chat (void *x, unsigned char *random, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) {
int user_id = (long)x; int user_id = (long)x;
int i; int i;
unsigned char random_here[256]; unsigned char random_here[256];
...@@ -2528,13 +2545,13 @@ void tgl_do_send_create_encr_chat (void *x, unsigned char *random) { ...@@ -2528,13 +2545,13 @@ void tgl_do_send_create_encr_chat (void *x, unsigned char *random) {
} }
BIGNUM *a = BN_bin2bn (random, 256, 0); BIGNUM *a = BN_bin2bn (random, 256, 0);
ensure_ptr (a); ensure_ptr (a);
BIGNUM *p = BN_bin2bn (encr_prime, 256, 0); BIGNUM *p = BN_bin2bn (tgl_state.encr_prime, 256, 0);
ensure_ptr (p); ensure_ptr (p);
BIGNUM *g = BN_new (); BIGNUM *g = BN_new ();
ensure_ptr (g); ensure_ptr (g);
ensure (BN_set_word (g, encr_root)); ensure (BN_set_word (g, tgl_state.encr_root));
BIGNUM *r = BN_new (); BIGNUM *r = BN_new ();
ensure_ptr (r); ensure_ptr (r);
...@@ -2578,10 +2595,10 @@ void tgl_do_send_create_encr_chat (void *x, unsigned char *random) { ...@@ -2578,10 +2595,10 @@ void tgl_do_send_create_encr_chat (void *x, unsigned char *random) {
BN_clear_free (p); BN_clear_free (p);
BN_clear_free (r); BN_clear_free (r);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_request_methods, E); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_request_methods, E, callback, callback_extra);
} }
int get_dh_config_on_answer (struct query *q UU) { static int get_dh_config_on_answer (struct query *q UU) {
unsigned x = fetch_int (); unsigned x = fetch_int ();
assert (x == CODE_messages_dh_config || x == CODE_messages_dh_config_not_modified); assert (x == CODE_messages_dh_config || x == CODE_messages_dh_config_not_modified);
if (x == CODE_messages_dh_config) { if (x == CODE_messages_dh_config) {
...@@ -2603,7 +2620,7 @@ int get_dh_config_on_answer (struct query *q UU) { ...@@ -2603,7 +2620,7 @@ int get_dh_config_on_answer (struct query *q UU) {
memcpy (random, fetch_str (256), 256); memcpy (random, fetch_str (256), 256);
if (q->extra) { if (q->extra) {
void **x = q->extra; void **x = q->extra;
((void (*)(void *, void *))(*x))(x[1], random); ((void (*)(void *, void *, void *, void *))(*x))(x[1], random, q->callback, q->callback_extra);
tfree (x, 2 * sizeof (void *)); tfree (x, 2 * sizeof (void *));
tfree_secure (random, 256); tfree_secure (random, 256);
} else { } else {
...@@ -2612,81 +2629,84 @@ int get_dh_config_on_answer (struct query *q UU) { ...@@ -2612,81 +2629,84 @@ int get_dh_config_on_answer (struct query *q UU) {
return 0; return 0;
} }
struct query_methods get_dh_config_methods = { static struct query_methods get_dh_config_methods = {
.on_answer = get_dh_config_on_answer, .on_answer = get_dh_config_on_answer,
.type = TYPE_TO_PARAM(messages_dh_config) .type = TYPE_TO_PARAM(messages_dh_config)
}; };
void tgl_do_accept_encr_chat_request (struct tgl_secret_chat *E) { void tgl_do_accept_encr_chat_request (struct tgl_secret_chat *E, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) {
assert (E->state == sc_request); assert (E->state == sc_request);
clear_packet (); clear_packet ();
out_int (CODE_messages_get_dh_config); out_int (CODE_messages_get_dh_config);
out_int (encr_param_version); out_int (tgl_state.encr_param_version);
out_int (256); out_int (256);
void **x = talloc (2 * sizeof (void *)); void **x = talloc (2 * sizeof (void *));
x[0] = tgl_do_send_accept_encr_chat; x[0] = tgl_do_send_accept_encr_chat;
x[1] = E; x[1] = E;
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x, callback, callback_extra);
} }
void tgl_do_create_encr_chat_request (int user_id) { void tgl_do_create_encr_chat_request (int user_id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_get_dh_config); out_int (CODE_messages_get_dh_config);
out_int (encr_param_version); out_int (tgl_state.encr_param_version);
out_int (256); out_int (256);
void **x = talloc (2 * sizeof (void *)); void **x = talloc (2 * sizeof (void *));
x[0] = tgl_do_send_create_encr_chat; x[0] = tgl_do_send_create_encr_chat;
x[1] = (void *)(long)(user_id); x[1] = (void *)(long)(user_id);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Get difference */ /* {{{ Get difference */
int unread_messages; //int unread_messages;
int difference_got; //int difference_got;
int seq, pts, qts, last_date; //int seq, pts, qts, last_date;
int get_state_on_answer (struct query *q UU) { static int get_state_on_answer (struct query *q UU) {
assert (fetch_int () == (int)CODE_updates_state); assert (fetch_int () == (int)CODE_updates_state);
bl_do_set_pts (fetch_int ()); bl_do_set_pts (fetch_int ());
bl_do_set_qts (fetch_int ()); bl_do_set_qts (fetch_int ());
bl_do_set_date (fetch_int ()); bl_do_set_date (fetch_int ());
bl_do_set_seq (fetch_int ()); bl_do_set_seq (fetch_int ());
unread_messages = fetch_int (); //unread_messages = fetch_int ();
write_state_file (); fetch_int ();
difference_got = 1; //write_state_file ();
//difference_got = 1;
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
return 0; return 0;
} }
int get_difference_active; //int get_difference_active;
int get_difference_on_answer (struct query *q UU) { static int get_difference_on_answer (struct query *q UU) {
get_difference_active = 0; //get_difference_active = 0;
unsigned x = fetch_int (); unsigned x = fetch_int ();
if (x == CODE_updates_difference_empty) { if (x == CODE_updates_difference_empty) {
bl_do_set_date (fetch_int ()); bl_do_set_date (fetch_int ());
bl_do_set_seq (fetch_int ()); bl_do_set_seq (fetch_int ());
difference_got = 1; //difference_got = 1;
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
} else if (x == CODE_updates_difference || x == CODE_updates_difference_slice) { } else if (x == CODE_updates_difference || x == CODE_updates_difference_slice) {
int n, i; int n, i;
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
static struct tgl_message *ML[10000]; struct tgl_message **ML = talloc (n * sizeof (void *));
int ml_pos = 0; int ml_pos = 0;
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
if (ml_pos < 10000) { ML[ml_pos ++] = tglf_fetch_alloc_message ();
ML[ml_pos ++] = tglf_fetch_alloc_message ();
} else {
tglf_fetch_alloc_message ();
}
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
struct tgl_message **EL = talloc (n * sizeof (void *));
int el_pos = 0;
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
if (ml_pos < 10000) { EL[el_pos ++] = tglf_fetch_alloc_encrypted_message ();
ML[ml_pos ++] = tglf_fetch_alloc_encrypted_message ();
} else {
tglf_fetch_alloc_encrypted_message ();
}
} }
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
n = fetch_int (); n = fetch_int ();
...@@ -2708,15 +2728,28 @@ int get_difference_on_answer (struct query *q UU) { ...@@ -2708,15 +2728,28 @@ int get_difference_on_answer (struct query *q UU) {
bl_do_set_qts (fetch_int ()); bl_do_set_qts (fetch_int ());
bl_do_set_date (fetch_int ()); bl_do_set_date (fetch_int ());
bl_do_set_seq (fetch_int ()); bl_do_set_seq (fetch_int ());
unread_messages = fetch_int (); //unread_messages = fetch_int ();
write_state_file (); fetch_int ();
for (i = 0; i < ml_pos; i++) { //write_state_file ();
/*for (i = 0; i < ml_pos; i++) {
print_message (ML[i]); print_message (ML[i]);
}*/
for (i = 0; i < ml_pos; i++) {
tgl_state.callback.new_msg (ML[i]);
}
for (i = 0; i < el_pos; i++) {
tgl_state.callback.new_msg (EL[i]);
} }
tfree (ML, ml_pos * sizeof (void *));
tfree (EL, el_pos * sizeof (void *));
if (x == CODE_updates_difference_slice) { if (x == CODE_updates_difference_slice) {
tgl_do_get_difference (); tgl_do_get_difference (0, q->callback, q->callback_extra);
} else { } else {
difference_got = 1; //difference_got = 1;
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
} }
} else { } else {
assert (0); assert (0);
...@@ -2724,39 +2757,39 @@ int get_difference_on_answer (struct query *q UU) { ...@@ -2724,39 +2757,39 @@ int get_difference_on_answer (struct query *q UU) {
return 0; return 0;
} }
struct query_methods get_state_methods = { static struct query_methods get_state_methods = {
.on_answer = get_state_on_answer, .on_answer = get_state_on_answer,
.type = TYPE_TO_PARAM(updates_state) .type = TYPE_TO_PARAM(updates_state)
}; };
struct query_methods get_difference_methods = { static struct query_methods get_difference_methods = {
.on_answer = get_difference_on_answer, .on_answer = get_difference_on_answer,
.type = TYPE_TO_PARAM(updates_difference) .type = TYPE_TO_PARAM(updates_difference)
}; };
void tgl_do_get_difference (void) { void tgl_do_get_difference (int sync_from_start, void (*callback)(void *callback_extra, int success), void *callback_extra) {
get_difference_active = 1; //get_difference_active = 1;
difference_got = 0; //difference_got = 0;
clear_packet (); clear_packet ();
tgl_do_insert_header (); tgl_do_insert_header ();
if (seq > 0 || sync_from_start) { if (tgl_state.seq > 0 || sync_from_start) {
if (pts == 0) { pts = 1; } if (tgl_state.pts == 0) { tgl_state.pts = 1; }
if (qts == 0) { qts = 1; } if (tgl_state.qts == 0) { tgl_state.qts = 1; }
if (last_date == 0) { last_date = 1; } if (tgl_state.date == 0) { tgl_state.date = 1; }
out_int (CODE_updates_get_difference); out_int (CODE_updates_get_difference);
out_int (pts); out_int (tgl_state.pts);
out_int (last_date); out_int (tgl_state.date);
out_int (qts); out_int (tgl_state.qts);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_difference_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_difference_methods, 0, callback, callback_extra);
} else { } else {
out_int (CODE_updates_get_state); out_int (CODE_updates_get_state);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_state_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_state_methods, 0, callback, callback_extra);
} }
} }
/* }}} */ /* }}} */
/* {{{ Visualize key */ /* {{{ Visualize key */
char *colors[4] = {COLOR_GREY, COLOR_CYAN, COLOR_BLUE, COLOR_GREEN}; /*char *colors[4] = {COLOR_GREY, COLOR_CYAN, COLOR_BLUE, COLOR_GREEN};
void tgl_do_visualize_key (tgl_peer_id_t id) { void tgl_do_visualize_key (tgl_peer_id_t id) {
assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT); assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT);
...@@ -2784,11 +2817,24 @@ void tgl_do_visualize_key (tgl_peer_id_t id) { ...@@ -2784,11 +2817,24 @@ void tgl_do_visualize_key (tgl_peer_id_t id) {
if (i & 1) { printf ("\n"); } if (i & 1) { printf ("\n"); }
} }
print_end (); print_end ();
}*/
void tgl_do_visualize_key (tgl_peer_id_t id, unsigned char buf[16]) {
assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT);
tgl_peer_t *P = tgl_peer_get (id);
assert (P);
if (P->encr_chat.state != sc_ok) {
vlogprintf (E_WARNING, "Chat is not initialized yet\n");
return;
}
unsigned char res[20];
SHA1 ((void *)P->encr_chat.key, 256, res);
memcpy (buf, res, 16);
} }
/* }}} */ /* }}} */
/* {{{ Get suggested */ /* {{{ Get suggested */
int get_suggested_on_answer (struct query *q UU) { /*int get_suggested_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_contacts_suggested); assert (fetch_int () == CODE_contacts_suggested);
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
...@@ -2827,17 +2873,17 @@ void tgl_do_get_suggested (void) { ...@@ -2827,17 +2873,17 @@ void tgl_do_get_suggested (void) {
out_int (CODE_contacts_get_suggested); out_int (CODE_contacts_get_suggested);
out_int (100); out_int (100);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_suggested_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &get_suggested_methods, 0);
} }*/
/* }}} */ /* }}} */
/* {{{ Add user to chat */ /* {{{ Add user to chat */
struct query_methods add_user_to_chat_methods = { static struct query_methods add_user_to_chat_methods = {
.on_answer = fwd_msg_on_answer, .on_answer = fwd_msg_on_answer,
.type = TYPE_TO_PARAM(message_action) .type = TYPE_TO_PARAM(message_action)
}; };
void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit) { void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_add_chat_user); out_int (CODE_messages_add_chat_user);
out_int (tgl_get_peer_id (chat_id)); out_int (tgl_get_peer_id (chat_id));
...@@ -2853,10 +2899,10 @@ void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit ...@@ -2853,10 +2899,10 @@ void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
} }
out_int (limit); out_int (limit);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0, callback, callback_extra);
} }
void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id) { void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_delete_chat_user); out_int (CODE_messages_delete_chat_user);
out_int (tgl_get_peer_id (chat_id)); out_int (tgl_get_peer_id (chat_id));
...@@ -2871,36 +2917,36 @@ void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id) { ...@@ -2871,36 +2917,36 @@ void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id) {
out_int (CODE_input_user_contact); out_int (CODE_input_user_contact);
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
} }
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Create secret chat */ /* {{{ Create secret chat */
char *create_print_name (tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4); //char *create_print_name (tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4);
void tgl_do_create_secret_chat (tgl_peer_id_t id) { void tgl_do_create_secret_chat (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) {
assert (tgl_get_peer_type (id) == TGL_PEER_USER); assert (tgl_get_peer_type (id) == TGL_PEER_USER);
tgl_peer_t *U = tgl_peer_get (id); tgl_peer_t *U = tgl_peer_get (id);
if (!U) { if (!U) {
rprintf ("Can not create chat with unknown user\n"); vlogprintf (E_WARNING, "Can not create chat with unknown user\n");
return; return;
} }
tgl_do_create_encr_chat_request (tgl_get_peer_id (id)); tgl_do_create_encr_chat_request (tgl_get_peer_id (id), callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Create group chat */ /* {{{ Create group chat */
struct query_methods create_group_chat_methods = { static struct query_methods create_group_chat_methods = {
.on_answer = fwd_msg_on_answer, .on_answer = fwd_msg_on_answer,
.type = TYPE_TO_PARAM(message_action) .type = TYPE_TO_PARAM(message_action)
}; };
void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic) { void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra) {
assert (tgl_get_peer_type (id) == TGL_PEER_USER); assert (tgl_get_peer_type (id) == TGL_PEER_USER);
tgl_peer_t *U = tgl_peer_get (id); tgl_peer_t *U = tgl_peer_get (id);
if (!U) { if (!U) {
rprintf ("Can not create chat with unknown user\n"); vlogprintf (E_WARNING, "Can not create chat with unknown user\n");
return; return;
} }
clear_packet (); clear_packet ();
...@@ -2916,62 +2962,74 @@ void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic) { ...@@ -2916,62 +2962,74 @@ void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic) {
out_int (tgl_get_peer_id (id)); out_int (tgl_get_peer_id (id));
} }
out_string (chat_topic); out_string (chat_topic);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &create_group_chat_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &create_group_chat_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Delete msg */ /* {{{ Delete msg */
int delete_msg_on_answer (struct query *q UU) { static int delete_msg_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
fetch_skip (n); fetch_skip (n);
logprintf ("Deleted %d messages\n", n);
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
return 0; return 0;
} }
struct query_methods delete_msg_methods = { static struct query_methods delete_msg_methods = {
.on_answer = delete_msg_on_answer, .on_answer = delete_msg_on_answer,
.type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int)) .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int))
}; };
void tgl_do_delete_msg (long long id) { void tgl_do_delete_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_delete_messages); out_int (CODE_messages_delete_messages);
out_int (CODE_vector); out_int (CODE_vector);
out_int (1); out_int (1);
out_int (id); out_int (id);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &delete_msg_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &delete_msg_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
/* {{{ Restore msg */ /* {{{ Restore msg */
int restore_msg_on_answer (struct query *q UU) { static int restore_msg_on_answer (struct query *q UU) {
assert (fetch_int () == CODE_vector); assert (fetch_int () == CODE_vector);
int n = fetch_int (); int n = fetch_int ();
fetch_skip (n); fetch_skip (n);
logprintf ("Restored %d messages\n", n); //logprintf ("Restored %d messages\n", n);
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
return 0; return 0;
} }
struct query_methods restore_msg_methods = { static struct query_methods restore_msg_methods = {
.on_answer = restore_msg_on_answer, .on_answer = restore_msg_on_answer,
.type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int)) .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int))
}; };
void tgl_do_restore_msg (long long id) { void tgl_do_restore_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_messages_restore_messages); out_int (CODE_messages_restore_messages);
out_int (CODE_vector); out_int (CODE_vector);
out_int (1); out_int (1);
out_int (id); out_int (id);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &restore_msg_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &restore_msg_methods, 0, callback, callback_extra);
} }
/* }}} */ /* }}} */
int update_status_on_answer (struct query *q UU) { int update_status_on_answer (struct query *q UU) {
fetch_bool (); fetch_bool ();
if (q->callback) {
((void (*)(void *, int))q->callback) (q->callback_extra, 1);
}
return 0; return 0;
} }
...@@ -2980,9 +3038,9 @@ struct query_methods update_status_methods = { ...@@ -2980,9 +3038,9 @@ struct query_methods update_status_methods = {
.type = TYPE_TO_PARAM(bool) .type = TYPE_TO_PARAM(bool)
}; };
void tgl_do_update_status (int online UU) { void tgl_do_update_status (int online UU, void (*callback)(void *callback_extra, int success), void *callback_extra) {
clear_packet (); clear_packet ();
out_int (CODE_account_update_status); out_int (CODE_account_update_status);
out_int (online ? CODE_bool_false : CODE_bool_true); out_int (online ? CODE_bool_false : CODE_bool_true);
send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &update_status_methods, 0); send_query (DC_working, packet_ptr - packet_buffer, packet_buffer, &update_status_methods, 0, callback, callback_extra);
} }
...@@ -50,10 +50,12 @@ struct query { ...@@ -50,10 +50,12 @@ struct query {
struct dc *DC; struct dc *DC;
struct session *session; struct session *session;
void *extra; void *extra;
void *callback;
void *callback_extra;
}; };
struct query *send_query (struct dc *DC, int len, void *data, struct query_methods *methods, void *extra); struct query *send_query (struct dc *DC, int len, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra);
void query_ack (long long id); void query_ack (long long id);
void query_error (long long id); void query_error (long long id);
void query_result (long long id); void query_result (long long id);
...@@ -64,13 +66,13 @@ void remove_event_timer (struct event_timer *ev); ...@@ -64,13 +66,13 @@ void remove_event_timer (struct event_timer *ev);
double next_timer_in (void); double next_timer_in (void);
void work_timers (void); void work_timers (void);
extern struct query_methods help_get_config_methods; //extern struct query_methods help_get_config_methods;
double get_double_time (void); double get_double_time (void);
// For binlog // For binlog
int get_dh_config_on_answer (struct query *q); //int get_dh_config_on_answer (struct query *q);
void fetch_dc_option (void); //void fetch_dc_option (void);
#endif #endif
...@@ -1628,9 +1628,9 @@ void tglm_message_remove_unsent (struct tgl_message *M) { ...@@ -1628,9 +1628,9 @@ void tglm_message_remove_unsent (struct tgl_message *M) {
static void __send_msg (struct tgl_message *M) { static void __send_msg (struct tgl_message *M) {
vlogprintf (E_NOTICE, "Resending message...\n"); vlogprintf (E_NOTICE, "Resending message...\n");
print_message (M); //print_message (M);
tgl_do_send_msg (M); tgl_do_send_msg (M, 0, 0);
} }
void tglm_send_all_unsent (void ) { void tglm_send_all_unsent (void ) {
......
...@@ -5,3 +5,19 @@ ...@@ -5,3 +5,19 @@
#include "tgl.h" #include "tgl.h"
struct tgl_state tgl_state; struct tgl_state tgl_state;
void tgl_set_binlog_mode (int mode) {
tgl_state.binlog_enabled = mode;
}
void tgl_set_binlog_path (const char *path) {
tgl_state.binlog_name = tstrdup (path);
}
void tgl_set_auth_file_path (const char *path) {
tgl_state.auth_file = tstrdup (path);
}
void tgl_set_download_directory (const char *path) {
tgl_state.downloads_directory = tstrdup (path);
}
...@@ -6,7 +6,33 @@ ...@@ -6,7 +6,33 @@
#define TGL_MAX_DC_NUM 100 #define TGL_MAX_DC_NUM 100
#define TGL_BUILD "1828"
#define TGL_VERSION "0.9-beta"
// Do not modify this structure, unless you know what you do // Do not modify this structure, unless you know what you do
struct tgl_update_callback {
void (*new_msg)(struct tgl_message *M);
void (*marked_read)(int num, struct tgl_message *list[]);
void (*logprintf)(const char *format, ...) __attribute__ ((format (printf, 1, 2)));
void (*type_notification)(tgl_peer_id_t id, struct tgl_user *U);
void (*type_in_chat_notification)(tgl_peer_id_t id, struct tgl_user *U, tgl_peer_id_t chat_id, struct tgl_chat *C);
void (*status_notification)(struct tgl_user *U);
void (*user_registered)(struct tgl_user *U);
};
#define vlogprintf(verbosity_level,...) \
do { \
if (tgl_state.verbosity >= verbosity_level) { \
tgl_state.callback.logprintf (__VA_ARGS__); \
} \
} while (0)
#define E_ERROR 0
#define E_WARNING 1
#define E_NOTICE 2
#define E_DEBUG 3
struct tgl_state { struct tgl_state {
int our_id; // ID of logged in user int our_id; // ID of logged in user
int encr_root; int encr_root;
...@@ -29,6 +55,12 @@ struct tgl_state { ...@@ -29,6 +55,12 @@ struct tgl_state {
long long cur_uploaded_bytes; long long cur_uploaded_bytes;
long long cur_downloading_bytes; long long cur_downloading_bytes;
long long cur_downloaded_bytes; long long cur_downloaded_bytes;
char *binlog_name;
char *auth_file;
char *downloads_directory;
struct tgl_update_callback callback;
}; };
extern struct tgl_state tgl_state; extern struct tgl_state tgl_state;
...@@ -57,6 +89,12 @@ int tgl_complete_peer_list (int index, const char *text, int len, char **R); ...@@ -57,6 +89,12 @@ int tgl_complete_peer_list (int index, const char *text, int len, char **R);
#define TGL_MK_CHAT(id) tgl_set_peer_id (TGL_PEER_CHAT,id) #define TGL_MK_CHAT(id) tgl_set_peer_id (TGL_PEER_CHAT,id)
#define TGL_MK_GEO_CHAT(id) tgl_set_peer_id (TGL_PEER_GEO_CHAT,id) #define TGL_MK_GEO_CHAT(id) tgl_set_peer_id (TGL_PEER_GEO_CHAT,id)
#define TGL_MK_ENCR_CHAT(id) tgl_set_peer_id (TGL_PEER_ENCR_CHAT,id) #define TGL_MK_ENCR_CHAT(id) tgl_set_peer_id (TGL_PEER_ENCR_CHAT,id)
void tgl_set_binlog_mode (int mode);
void tgl_set_binlog_path (const char *path);
void tgl_set_auth_file_path (const char *path);
void tgl_set_download_directory (const char *path);
static inline int tgl_get_peer_type (tgl_peer_id_t id) { static inline int tgl_get_peer_type (tgl_peer_id_t id) {
return id.type; return id.type;
...@@ -89,52 +127,49 @@ static inline void tgl_set_test_mode (void) { ...@@ -89,52 +127,49 @@ static inline void tgl_set_test_mode (void) {
tgl_state.test_mode ++; tgl_state.test_mode ++;
} }
void tgl_do_send_code (const char *user); void tgl_do_help_get_config (void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_phone_call (const char *user); void tgl_do_send_code (const char *user, void (*callback)(void *callback_extra, int success, int registered, const char *hash), void *callback_extra);
int tgl_do_send_code_result (const char *code); void tgl_do_phone_call (const char *user, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_update_contact_list (void); int tgl_do_send_code_result (const char *user, const char *code, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) ;
void tgl_do_send_message (tgl_peer_id_t id, const char *msg, int len); int tgl_do_send_code_result_auth (const char *user, const char *code, const char *first_name, const char *last_name, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra);
void tgl_do_send_text (tgl_peer_id_t id, char *file); void tgl_do_update_contact_list (void (*callback) (void *callback_extra, int success, int size, struct tgl_user *contacts[]), void *callback_extra);
void tgl_do_get_history (tgl_peer_id_t id, int limit); void tgl_do_send_message (tgl_peer_id_t id, const char *msg, int len, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_get_dialog_list (void); void tgl_do_send_msg (struct tgl_message *M, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_get_dialog_list_ex (void); void tgl_do_send_text (tgl_peer_id_t id, char *file, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name); void tgl_do_mark_read (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_get_chat_info (tgl_peer_id_t id); void tgl_do_get_history (tgl_peer_id_t id, int limit, int offline_mode, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra);
void tgl_do_get_user_list_info_silent (int num, int *list); void tgl_do_get_dialog_list (void (*callback)(void *callback_extra, int success, int size, tgl_peer_id_t peers[], int last_msg_id[], int unread_count[]), void *callback_extra);
void tgl_do_get_user_info (tgl_peer_id_t id); void tgl_do_send_photo (int type, tgl_peer_id_t to_id, char *file_name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_forward_message (tgl_peer_id_t id, int n); void tgl_do_forward_message (tgl_peer_id_t id, int n, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_rename_chat (tgl_peer_id_t id, char *name); void tgl_do_rename_chat (tgl_peer_id_t id, char *name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_load_encr_video (struct tgl_encr_video *V, int next); void tgl_do_get_chat_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_chat *C), void *callback_extra);
void tgl_do_create_encr_chat_request (int user_id); void tgl_do_get_user_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_user *U), void *callback_extra);
void tgl_do_create_secret_chat (tgl_peer_id_t id); void tgl_do_load_photo (struct tgl_photo *photo, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic); void tgl_do_load_video_thumb (struct tgl_video *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_get_suggested (void); void tgl_do_load_audio (struct tgl_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_load_video (struct tgl_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_load_photo (struct tgl_photo *photo, int next); void tgl_do_load_document (struct tgl_document *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_load_video_thumb (struct tgl_video *video, int next); void tgl_do_load_document_thumb (struct tgl_document *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_load_audio (struct tgl_video *V, int next); void tgl_do_load_encr_video (struct tgl_encr_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
void tgl_do_load_video (struct tgl_video *V, int next); void tgl_do_export_auth (int num, void (*callback) (void *callback_extra, int success), void *callback_extra);
void tgl_do_load_document (struct tgl_document *V, int next); void tgl_do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force, void (*callback)(void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra);
void tgl_do_load_document_thumb (struct tgl_document *video, int next); void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const char *s, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra);
void tgl_do_help_get_config (void); void tgl_do_contacts_search (int limit, const char *s, void (*callback) (void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra);
int tgl_do_auth_check_phone (const char *user); void tgl_do_create_encr_chat_request (int user_id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
int tgl_do_get_nearest_dc (void); void tgl_do_create_secret_chat (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
int tgl_do_send_code_result_auth (const char *code, const char *first_name, const char *last_name); void tgl_do_accept_encr_chat_request (struct tgl_secret_chat *E, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
void tgl_do_import_auth (int num); void tgl_do_get_difference (int sync_from_start, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_export_auth (int num); void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force); void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, const char *s); void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
void tgl_do_accept_encr_chat_request (struct tgl_secret_chat *E); void tgl_do_delete_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_get_difference (void); void tgl_do_restore_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_mark_read (tgl_peer_id_t id); void tgl_do_update_status (int online, void (*callback)(void *callback_extra, int success), void *callback_extra);
void tgl_do_visualize_key (tgl_peer_id_t id);
void tgl_do_visualize_key (tgl_peer_id_t id, unsigned char buf[16]);
//void tgl_do_get_suggested (void);
void tgl_do_create_keys_end (struct tgl_secret_chat *U); void tgl_do_create_keys_end (struct tgl_secret_chat *U);
void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit);
void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id);
void tgl_do_update_status (int online);
void tgl_do_contacts_search (int limit, const char *s);
void tgl_do_send_msg (struct tgl_message *M);
void tgl_do_delete_msg (long long id);
void tgl_do_restore_msg (long long id);
void tgl_do_send_encr_chat_layer (struct tgl_secret_chat *E); void tgl_do_send_encr_chat_layer (struct tgl_secret_chat *E);
#endif #endif
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment