From 2c340e59bf16238ab94ee52bbd878c3479c9a876 Mon Sep 17 00:00:00 2001 From: Vysheng Date: Wed, 12 Nov 2014 17:38:44 +0300 Subject: [PATCH] Detached libtgl --- .gitmodules | 3 + Makefile.in | 66 +- Makefile.tgl | 47 + Makefile.tl-parser | 7 + README.md | 7 +- append.tl | 2 - binlog.tl | 83 - crc32.c | 668 ------- crc32.h | 59 - encrypted_scheme.tl | 1 - encrypted_scheme16.tl | 22 - encrypted_scheme17.tl | 31 - gen_constants_h.awk | 37 - generate.c | 1829 ------------------- generate.h | 171 -- include.h | 24 - interface.c | 11 +- interface.h | 4 +- loop.c | 9 +- lua-tg.c | 9 +- lua-tg.h | 3 +- main.c | 4 +- mtproto-client.c | 1462 ---------------- mtproto-client.h | 60 - mtproto-common.c | 394 ----- mtproto-common.h | 384 ---- net.c | 623 ------- net.h | 87 - no-preview.h | 106 -- queries.c | 3879 ----------------------------------------- queries.h | 75 - scheme.tl | 1 - scheme12.tl | 505 ------ scheme15.tl | 522 ------ scheme16.tl | 504 ------ scheme17.tl | 528 ------ scheme18.tl | 535 ------ structures.c | 2039 ---------------------- structures.h | 57 - tgl | 1 + tgl-fetch.h | 54 - tgl-inner.h | 31 - tgl-layout.h | 447 ----- tgl-timers.c | 69 - tgl-timers.h | 27 - tgl.c | 86 - tgl.h | 395 ----- tools.c | 297 ---- tools.h | 119 -- updates.c | 594 ------- updates.h | 39 - 51 files changed, 91 insertions(+), 16926 deletions(-) create mode 100644 .gitmodules create mode 100644 Makefile.tgl create mode 100644 Makefile.tl-parser delete mode 100644 append.tl delete mode 100644 binlog.tl delete mode 100644 crc32.c delete mode 100644 crc32.h delete mode 120000 encrypted_scheme.tl delete mode 100644 encrypted_scheme16.tl delete mode 100644 encrypted_scheme17.tl delete mode 100644 gen_constants_h.awk delete mode 100644 generate.c delete mode 100644 generate.h delete mode 100644 include.h delete mode 100644 mtproto-client.c delete mode 100644 mtproto-client.h delete mode 100644 mtproto-common.c delete mode 100644 mtproto-common.h delete mode 100644 net.c delete mode 100644 net.h delete mode 100644 no-preview.h delete mode 100644 queries.c delete mode 100644 queries.h delete mode 120000 scheme.tl delete mode 100644 scheme12.tl delete mode 100644 scheme15.tl delete mode 100644 scheme16.tl delete mode 100644 scheme17.tl delete mode 100644 scheme18.tl delete mode 100644 structures.c delete mode 100644 structures.h create mode 160000 tgl delete mode 100644 tgl-fetch.h delete mode 100644 tgl-inner.h delete mode 100644 tgl-layout.h delete mode 100644 tgl-timers.c delete mode 100644 tgl-timers.h delete mode 100644 tgl.c delete mode 100644 tgl.h delete mode 100644 tools.c delete mode 100644 tools.h delete mode 100644 updates.c delete mode 100644 updates.h diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..dffe6ca --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "tgl"] + path = tgl + url = https://github.com/vysheng/tgl.git diff --git a/Makefile.in b/Makefile.in index 817b847..d9034bd 100644 --- a/Makefile.in +++ b/Makefile.in @@ -10,24 +10,16 @@ EXTRA_LIBS=@LIBS@ @EXTRA_LIBS@ @OPENSSL_LIBS@ LOCAL_LDFLAGS=-rdynamic -ggdb -levent ${EXTRA_LIBS} LINK_FLAGS=${LDFLAGS} ${LOCAL_LDFLAGS} -DEP=${srcdir}/dep -AUTO=${srcdir}/auto -EXE=${srcdir}/bin -OBJ=${srcdir}/objs -LIB=${srcdir}/libs +DEP=dep +AUTO=auto +EXE=bin +OBJ=objs +LIB=libs DIR_LIST=${DEP} ${AUTO} ${EXE} ${OBJ} ${LIB} ${DEP}/auto ${OBJ}/auto -EXE_LIST=${EXE}/generate ${EXE}/tlc ${EXE}/telegram-cli -LIB_LIST=${LIB}/libtgl.a +EXE_LIST=${EXE}/telegram-cli -TG_OBJECTS=${OBJ}/main.o ${OBJ}/loop.o ${OBJ}/interface.o ${OBJ}/net.o ${OBJ}/lua-tg.o ${OBJ}/tgl-timers.o -TGL_OBJECTS=${OBJ}/mtproto-common.o ${OBJ}/mtproto-client.o ${OBJ}/queries.o ${OBJ}/structures.o ${OBJ}/binlog.o ${OBJ}/auto/auto.o ${OBJ}/tgl.o ${OBJ}/updates.o -TLC_OBJECTS=${OBJ}/tlc.o ${OBJ}/tl-parser.o ${OBJ}/crc32.o -TLD_OBJECTS=${OBJ}/dump-tl-file.o -GENERATE_OBJECTS=${OBJ}/generate.o -COMMON_OBJECTS=${OBJ}/tools.o -OBJ_LIST=${TG_OBJECTS} ${TLC_OBJECTS} ${GENERATE_OBJECTS} ${COMMON_OBJECTS} ${TGL_OBJECTS} ${TLD_OBJECTS} -OBJ_C=${TLC_OBJECTS} ${GENERATE_OBJECTS} ${COMMON_OBJECTS} ${TGL_OBJECTS} ${TLD_OBJECTS} +TG_OBJECTS=${OBJ}/main.o ${OBJ}/loop.o ${OBJ}/interface.o ${OBJ}/lua-tg.o DEPENDENCE=$(subst ${OBJ}/,${DEP}/,$(patsubst %.o,%.d,${OBJ_LIST})) DEPENDENCE_LIST=${DEPENDENCE} @@ -39,56 +31,24 @@ CC=@CC@ .SUFFIXES: .c .h .o -all: ${EXE_LIST} ${DIR_LIST} ${LIB_LIST} +all: ${EXE_LIST} ${DIR_LIST} create_dirs_and_headers: ${DIR_LIST} ${AUTO}/auto.c ${AUTO}/auto-header.h ${AUTO}/constants.h create_dirs: ${DIR_LIST} dump-tl: ${EXE}/dump-tl-file +include ${srcdir}/Makefile.tl-parser +include ${srcdir}/Makefile.tgl + ${DIR_LIST}: @test -d $@ || mkdir -p $@ -include ${DEPENDENCE_LIST} -${TG_OBJECTS} ${TGL_OBJECTS}: ${AUTO}/constants.h ${AUTO}/auto-header.h - ${TG_OBJECTS}: ${OBJ}/%.o: %.c | create_dirs_and_headers ${CC} ${INCLUDE} ${COMPILE_FLAGS} -c -MP -MD -MF ${DEP}/$*.d -MQ ${OBJ}/$*.o -o $@ $< -${OBJ_C}: ${OBJ}/%.o: %.c | create_dirs - ${CC} ${INCLUDE} ${COMPILE_FLAGS} -c -MP -MD -MF ${DEP}/$*.d -MQ ${OBJ}/$*.o -o $@ $< - -${EXE}/tlc: ${TLC_OBJECTS} ${COMMON_OBJECTS} - ${CC} ${TLC_OBJECTS} ${COMMON_OBJECTS} ${LINK_FLAGS} -o $@ - -${EXE}/telegram-cli: ${TG_OBJECTS} ${COMMON_OBJECTS} ${LIB}/libtgl.a - ${CC} ${TG_OBJECTS} ${COMMON_OBJECTS} ${LINK_FLAGS} -L${LIB} -l tgl -o $@ - -${LIB}/libtgl.a: ${TGL_OBJECTS} ${COMMON_OBJECTS} - ar ruv $@ ${TGL_OBJECTS} ${COMMON_OBJECTS} - -${EXE}/generate: ${GENERATE_OBJECTS} ${COMMON_OBJECTS} - ${CC} ${GENERATE_OBJECTS} ${COMMON_OBJECTS} ${LINK_FLAGS} -o $@ - -${AUTO}/scheme.tlo: ${AUTO}/scheme.tl ${EXE}/tlc - ${EXE}/tlc -e $@ ${AUTO}/scheme.tl - -${AUTO}/scheme.tl: ${srcdir}/scheme.tl ${srcdir}/encrypted_scheme.tl ${srcdir}/binlog.tl ${srcdir}/append.tl | ${AUTO} - cat $^ > $@ - -${AUTO}/scheme2.tl: ${AUTO}/scheme.tl ${EXE}/tlc - ${EXE}/tlc -E ${AUTO}/scheme.tl 2> $@ || ( cat $@ && rm $@ && false ) - -${AUTO}/auto.c: ${AUTO}/scheme.tlo ${EXE}/generate - ${EXE}/generate ${AUTO}/scheme.tlo > $@ - -${AUTO}/auto-header.h: ${AUTO}/scheme.tlo ${EXE}/generate - ${EXE}/generate -H ${AUTO}/scheme.tlo > $@ - -${AUTO}/constants.h: ${AUTO}/scheme2.tl ${srcdir}/gen_constants_h.awk - awk -f ${srcdir}/gen_constants_h.awk < $< > $@ - -${EXE}/dump-tl-file: ${OBJ}/auto/auto.o ${TLD_OBJECTS} - ${CC} ${OBJ}/auto/auto.o ${TLD_OBJECTS} ${LINK_FLAGS} -o $@ +${EXE}/telegram-cli: ${TG_OBJECTS} ${LIB}/libtgl.a + ${CC} $^ ${LINK_FLAGS} -o $@ clean: rm -rf ${DIR_LIST} config.log config.status > /dev/null || echo "all clean" diff --git a/Makefile.tgl b/Makefile.tgl new file mode 100644 index 0000000..4ed85b6 --- /dev/null +++ b/Makefile.tgl @@ -0,0 +1,47 @@ +TGL_OBJECTS=${OBJ}/mtproto-common.o ${OBJ}/mtproto-client.o ${OBJ}/queries.o ${OBJ}/structures.o ${OBJ}/binlog.o ${OBJ}/tgl.o ${OBJ}/updates.o ${OBJ}/tgl-net.o ${OBJ}/tgl-timers.o +TLD_OBJECTS=${OBJ}/dump-tl-file.o +GENERATE_OBJECTS=${OBJ}/generate.o +TGL_COMMON_OBJECTS=${OBJ}/tools.o +TGL_OBJ_C=${GENERATE_OBJECTS} ${TGL_COMMON_OBJECTS} ${TGL_OBJECTS} ${TLD_OBJECTS} + +.SUFFIXES: + +.SUFFIXES: .c .h .o + +dump-tl: ${EXE}/dump-tl-file + +${OBJ}/auto/auto.o ${TGL_OBJECTS}: ${AUTO}/constants.h ${AUTO}/auto-header.h + +${TGL_OBJ_C}: ${OBJ}/%.o: ${srcdir}/tgl/%.c | create_dirs + ${CC} ${INCLUDE} ${COMPILE_FLAGS} -iquote ${srcdir}/tgl -c -MP -MD -MF ${DEP}/$*.d -MQ ${OBJ}/$*.o -o $@ $< + +${OBJ}/auto/auto.o: ${AUTO}/auto.c + ${CC} ${INCLUDE} ${COMPILE_FLAGS} -iquote ${srcdir}/tgl -c -MP -MD -MF ${DEP}/auto/auto.d -MQ ${OBJ}/auto/auto.o -o $@ $< + +${LIB}/libtgl.a: ${TGL_OBJECTS} ${TGL_COMMON_OBJECTS} ${OBJ}/auto/auto.o + ar ruv $@ $^ + +${EXE}/generate: ${GENERATE_OBJECTS} ${TGL_COMMON_OBJECTS} + ${CC} ${GENERATE_OBJECTS} ${TGL_COMMON_OBJECTS} ${LINK_FLAGS} -o $@ + +${AUTO}/scheme.tlo: ${AUTO}/scheme.tl ${EXE}/tl-parser + ${EXE}/tl-parser -e $@ ${AUTO}/scheme.tl + +${AUTO}/scheme.tl: ${srcdir}/tgl/scheme.tl ${srcdir}/tgl/encrypted_scheme.tl ${srcdir}/tgl/binlog.tl ${srcdir}/tgl/append.tl | ${AUTO} + cat $^ > $@ + +${AUTO}/scheme2.tl: ${AUTO}/scheme.tl ${EXE}/tl-parser + ${EXE}/tl-parser -E ${AUTO}/scheme.tl 2> $@ || ( cat $@ && rm $@ && false ) + +${AUTO}/auto.c: ${AUTO}/scheme.tlo ${EXE}/generate + ${EXE}/generate ${AUTO}/scheme.tlo > $@ + +${AUTO}/auto-header.h: ${AUTO}/scheme.tlo ${EXE}/generate + ${EXE}/generate -H ${AUTO}/scheme.tlo > $@ + +${AUTO}/constants.h: ${AUTO}/scheme2.tl ${srcdir}/tgl/gen_constants_h.awk + awk -f ${srcdir}/tgl/gen_constants_h.awk < $< > $@ + +${EXE}/dump-tl-file: ${OBJ}/auto/auto.o ${TLD_OBJECTS} + ${CC} ${OBJ}/auto/auto.o ${TLD_OBJECTS} ${LINK_FLAGS} -o $@ + diff --git a/Makefile.tl-parser b/Makefile.tl-parser new file mode 100644 index 0000000..eb3284d --- /dev/null +++ b/Makefile.tl-parser @@ -0,0 +1,7 @@ +TL_PARSER_OBJECTS=${OBJ}/tl-parser.o ${OBJ}/tlc.o ${OBJ}/crc32.o + +${TL_PARSER_OBJECTS}: ${OBJ}/%.o: ${srcdir}/tgl/tl-parser/%.c | create_dirs + ${CC} ${INCLUDE} ${COMPILE_FLAGS} -iquote ${srcdir}/tgl/tl-parser -c -MP -MD -MF ${DEP}/$*.d -MQ ${OBJ}/$*.o -o $@ $< + +${EXE}/tl-parser: ${TL_PARSER_OBJECTS} + ${CC} $^ ${LINK_FLAGS} -o $@ diff --git a/README.md b/README.md index 656c612..abecd53 100644 --- a/README.md +++ b/README.md @@ -22,12 +22,7 @@ Fourth, in peer_name '#' are substitued to '@'. (Not applied to appending of '#% Clone GitHub Repository - git clone https://github.com/vysheng/tg.git && cd tg - -or download and extract zip - - wget https://github.com/vysheng/tg/archive/master.zip -O tg-master.zip - unzip tg-master.zip && cd tg-master + git clone --recursive https://github.com/vysheng/tg.git && cd tg #### Linux and BSDs diff --git a/append.tl b/append.tl deleted file mode 100644 index 0b5711b..0000000 --- a/append.tl +++ /dev/null @@ -1,2 +0,0 @@ -decryptedMessageMediaVideoL12#4cee6ef3 thumb:bytes thumb_w:int thumb_h:int duration:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaAudioL12#6080758f duration:int size:int key:bytes iv:bytes = DecryptedMessageMedia; diff --git a/binlog.tl b/binlog.tl deleted file mode 100644 index 9557b0c..0000000 --- a/binlog.tl +++ /dev/null @@ -1,83 +0,0 @@ ----types--- -binlog.fileLocation dc:int volume:long local_id:int secret:long = binlog.FileLocation; -binlog.chatParticipant user:int inviter:int date:int = binlog.ChatParticipant; - -binlog.start = binlog.Update; - -binlog.dcOption id:int name:string ip:string port:int = binlog.Update; -binlog.authKey dc:int key_id:long key:64*[int] = binlog.Update; -binlog.defaultDc dc:int = binlog.Update; -binlog.ourId id:int = binlog.Update; -binlog.dcSigned id:int = binlog.Update; -binlog.dcSalt id:int salt:long = binlog.Update; - -binlog.setDhParams root:int prime:64*[int] version:int = binlog.Update; -binlog.setPts pts:int = binlog.Update; -binlog.setQts qts:int = binlog.Update; -binlog.setDate date:int = binlog.Update; -binlog.setSeq seq:int = binlog.Update; - -binlog.userAdd id:int first_name:string last_name:string hash:long phone:string is_contact:int = binlog.Update; -binlog.userDelete id:int = binlog.Update; -binlog.userSetAccessHash id:int hash:long = binlog.Update; -binlog.userSetPhone id:int phone:string = binlog.Update; -binlog.userSetFriend id:int friend:int = binlog.Update; -binlog.userSetFullPhoto id:int photo:Photo = binlog.Update; -binlog.userSetBlocked id:int blocked:int = binlog.Update; -binlog.userSetRealName id:int real_first_name:string real_last_name:string = binlog.Update; -binlog.userSetName id:int first_name:string last_name:string = binlog.Update; -binlog.userSetPhoto id:int photo:UserProfilePhoto = binlog.Update; -binlog.userSetUsername id:int username:string = binlog.Update; - -binlog.encrChatDelete id:int = binlog.Update; -binlog.encrChatRequested id:int hash:long date:int admin:int user:int key:64*[int] nonce:64*[int] = binlog.Update; -binlog.encrChatAccepted id:int key:64*[int] nonce:64*[int] fingerprint:long = binlog.Update; -binlog.encrChatInit id:int user:int key:64*[int] g_key:64*[int] = binlog.Update; -binlog.encrChatCreate id:int user_id:int admin_id:int name:string = binlog.Update; - -binlog.encrChatSetAccessHash id:int hash:long = binlog.Update; -binlog.encrChatSetDate id:int date:int = binlog.Update; -binlog.encrChatSetTtl id:int ttl:int = binlog.Update; -binlog.encrChatSetLayer id:int layer:int = binlog.Update; -binlog.encrChatSetState id:int state:int = binlog.Update; -binlog.encrChatSetKey id:int key:64*[int] fingerprint:long = binlog.Update; - -binlog.encrChatUpdateSeq id:int in_seq_no:int out_seq_no:int = binlog.Update; -binlog.encrChatSetSeq id:int in_seq_no:int last_in_seq_no:int out_seq_no:int = binlog.Update; - -binlog.chatCreate id:int flags:int title:string user_num:int date:int version:int photo_big:%binlog.FileLocation photo_small:%binlog.FileLocation = binlog.Update; -binlog.chatChangeFlags id:int set_flags:int clear_flags:int = binlog.Update; -binlog.chatSetTitle id:int title:string = binlog.Update; -binlog.chatSetPhoto id:int photo_big:%binlog.FileLocation photo_small:%binlog.FileLocation = binlog.Update; -binlog.chatSetDate id:int date:int = binlog.Update; -binlog.chatSetVersion id:int version:int users_num:int = binlog.Update; -binlog.chatSetAdmin id:int admin:int = binlog.Update; -binlog.chatSetParticipants id:int version:int participants:%(Vector %binlog.ChatParticipant) = binlog.Update; -binlog.chatSetFullPhoto id:int photo:Photo = binlog.Update; -binlog.chatAddParticipant id:int version:int user:%binlog.ChatParticipant = binlog.Update; -binlog.chatDelParticipant id:int version:int user:int = binlog.Update; - -binlog.createMessageText id:int from_id:int to_type:int to_id:int date:int unread:int text:string = binlog.Update; -binlog.sendMessageText id:long from_id:int to_type:int to_id:int date:int text:string = binlog.Update; -binlog.sendMessageActionEncr id:long from_id:int to_type:int to_id:int date:int action:DecryptedMessageAction = binlog.Update; -binlog.createMessageTextFwd id:int from_id:int to_type:int to_id:int date:int fwd_from_id:int fwd_date:int unread:int text:string = binlog.Update; -binlog.createMessageMedia id:int from_id:int to_type:int to_id:int date:int unread:int text:string media:MessageMedia = binlog.Update; -binlog.createMessageMediaEncr id:long from_id:int to_type:int to_id:int date:int text:string media:DecryptedMessageMedia file:EncryptedFile = binlog.Update; -binlog.createMessageMediaEncrPending id:long from_id:int to_type:int to_id:int date:int text:string media:DecryptedMessageMedia = binlog.Update; -binlog.createMessageMediaEncrSent id:long file:EncryptedFile = binlog.Update; -binlog.createMessageMediaFwd id:int from_id:int to_type:int to_id:int date:int fwd_from_id:int fwd_date:int unread:int text:string media:MessageMedia = binlog.Update; -binlog.createMessageService id:int from_id:int to_type:int to_id:int date:int unread:int action:MessageAction = binlog.Update; -binlog.createMessageServiceEncr id:long from_id:int to_type:int to_id:int date:int action:DecryptedMessageAction = binlog.Update; -binlog.createMessageServiceFwd id:int from_id:int to_type:int to_id:int date:int fwd_from_id:int fwd_date:int unread:int action:MessageAction = binlog.Update; -binlog.messageSetUnread id:int = binlog.Update; -binlog.messageSetUnreadLong id:long = binlog.Update; -binlog.setMessageSent id:long = binlog.Update; -binlog.setMsgId old_id:long new_id:int = binlog.Update; -binlog.deleteMsg id:long = binlog.Update; - -binlog.msgSeqUpdate id:long = binlog.Update; -binlog.msgUpdate id:long = binlog.Update; - -binlog.resetAuthorization = binlog.Update; - -//binlog.addDc id:int ip:string port:int auth_key_id:long auth_key:64*[int] = binlog.Update; diff --git a/crc32.c b/crc32.c deleted file mode 100644 index 1fc4e61..0000000 --- a/crc32.c +++ /dev/null @@ -1,668 +0,0 @@ -/* - This file is part of VK/KittenPHP-DB-Engine Library. - - VK/KittenPHP-DB-Engine Library is free software: you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - VK/KittenPHP-DB-Engine Library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with VK/KittenPHP-DB-Engine Library. If not, see . - - Copyright 2009-2012 Vkontakte Ltd - 2009-2012 Nikolai Durov - 2009-2012 Andrei Lopatin - 2012 Anton Maydell -*/ - -#include -#include -#include -#include "config.h" - -#ifdef HAVE_CONFIG_H -#include "crc32.h" -#endif - -#ifndef HAVE___BUILTIN_BSWAP32 -static inline unsigned __builtin_bswap32(unsigned x) { - return ((x << 24) & 0xff000000 ) | - ((x << 8) & 0x00ff0000 ) | - ((x >> 8) & 0x0000ff00 ) | - ((x >> 24) & 0x000000ff ); -} -#endif - -unsigned int crc32_table[256] = -{ - 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, - 0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3, - 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988, - 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91, - 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de, - 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, - 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, - 0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5, - 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172, - 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, - 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940, - 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59, - 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, - 0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f, - 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, - 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, - 0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a, - 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433, - 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, - 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01, - 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, - 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457, - 0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c, - 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65, - 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, - 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb, - 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0, - 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9, - 0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086, - 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f, - 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, - 0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad, - 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a, - 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683, - 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8, - 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, - 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, - 0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7, - 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc, - 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, - 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252, - 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b, - 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, - 0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79, - 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, - 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, - 0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04, - 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d, - 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, - 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713, - 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, - 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, - 0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e, - 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777, - 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, - 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45, - 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2, - 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db, - 0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0, - 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9, - 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, - 0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf, - 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94, - 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d -}; - -unsigned int crc32_table2[256] = -{ - 0x00000000, 0x191b3141, 0x32366282, 0x2b2d53c3, - 0x646cc504, 0x7d77f445, 0x565aa786, 0x4f4196c7, - 0xc8d98a08, 0xd1c2bb49, 0xfaefe88a, 0xe3f4d9cb, - 0xacb54f0c, 0xb5ae7e4d, 0x9e832d8e, 0x87981ccf, - 0x4ac21251, 0x53d92310, 0x78f470d3, 0x61ef4192, - 0x2eaed755, 0x37b5e614, 0x1c98b5d7, 0x05838496, - 0x821b9859, 0x9b00a918, 0xb02dfadb, 0xa936cb9a, - 0xe6775d5d, 0xff6c6c1c, 0xd4413fdf, 0xcd5a0e9e, - 0x958424a2, 0x8c9f15e3, 0xa7b24620, 0xbea97761, - 0xf1e8e1a6, 0xe8f3d0e7, 0xc3de8324, 0xdac5b265, - 0x5d5daeaa, 0x44469feb, 0x6f6bcc28, 0x7670fd69, - 0x39316bae, 0x202a5aef, 0x0b07092c, 0x121c386d, - 0xdf4636f3, 0xc65d07b2, 0xed705471, 0xf46b6530, - 0xbb2af3f7, 0xa231c2b6, 0x891c9175, 0x9007a034, - 0x179fbcfb, 0x0e848dba, 0x25a9de79, 0x3cb2ef38, - 0x73f379ff, 0x6ae848be, 0x41c51b7d, 0x58de2a3c, - 0xf0794f05, 0xe9627e44, 0xc24f2d87, 0xdb541cc6, - 0x94158a01, 0x8d0ebb40, 0xa623e883, 0xbf38d9c2, - 0x38a0c50d, 0x21bbf44c, 0x0a96a78f, 0x138d96ce, - 0x5ccc0009, 0x45d73148, 0x6efa628b, 0x77e153ca, - 0xbabb5d54, 0xa3a06c15, 0x888d3fd6, 0x91960e97, - 0xded79850, 0xc7cca911, 0xece1fad2, 0xf5facb93, - 0x7262d75c, 0x6b79e61d, 0x4054b5de, 0x594f849f, - 0x160e1258, 0x0f152319, 0x243870da, 0x3d23419b, - 0x65fd6ba7, 0x7ce65ae6, 0x57cb0925, 0x4ed03864, - 0x0191aea3, 0x188a9fe2, 0x33a7cc21, 0x2abcfd60, - 0xad24e1af, 0xb43fd0ee, 0x9f12832d, 0x8609b26c, - 0xc94824ab, 0xd05315ea, 0xfb7e4629, 0xe2657768, - 0x2f3f79f6, 0x362448b7, 0x1d091b74, 0x04122a35, - 0x4b53bcf2, 0x52488db3, 0x7965de70, 0x607eef31, - 0xe7e6f3fe, 0xfefdc2bf, 0xd5d0917c, 0xcccba03d, - 0x838a36fa, 0x9a9107bb, 0xb1bc5478, 0xa8a76539, - 0x3b83984b, 0x2298a90a, 0x09b5fac9, 0x10aecb88, - 0x5fef5d4f, 0x46f46c0e, 0x6dd93fcd, 0x74c20e8c, - 0xf35a1243, 0xea412302, 0xc16c70c1, 0xd8774180, - 0x9736d747, 0x8e2de606, 0xa500b5c5, 0xbc1b8484, - 0x71418a1a, 0x685abb5b, 0x4377e898, 0x5a6cd9d9, - 0x152d4f1e, 0x0c367e5f, 0x271b2d9c, 0x3e001cdd, - 0xb9980012, 0xa0833153, 0x8bae6290, 0x92b553d1, - 0xddf4c516, 0xc4eff457, 0xefc2a794, 0xf6d996d5, - 0xae07bce9, 0xb71c8da8, 0x9c31de6b, 0x852aef2a, - 0xca6b79ed, 0xd37048ac, 0xf85d1b6f, 0xe1462a2e, - 0x66de36e1, 0x7fc507a0, 0x54e85463, 0x4df36522, - 0x02b2f3e5, 0x1ba9c2a4, 0x30849167, 0x299fa026, - 0xe4c5aeb8, 0xfdde9ff9, 0xd6f3cc3a, 0xcfe8fd7b, - 0x80a96bbc, 0x99b25afd, 0xb29f093e, 0xab84387f, - 0x2c1c24b0, 0x350715f1, 0x1e2a4632, 0x07317773, - 0x4870e1b4, 0x516bd0f5, 0x7a468336, 0x635db277, - 0xcbfad74e, 0xd2e1e60f, 0xf9ccb5cc, 0xe0d7848d, - 0xaf96124a, 0xb68d230b, 0x9da070c8, 0x84bb4189, - 0x03235d46, 0x1a386c07, 0x31153fc4, 0x280e0e85, - 0x674f9842, 0x7e54a903, 0x5579fac0, 0x4c62cb81, - 0x8138c51f, 0x9823f45e, 0xb30ea79d, 0xaa1596dc, - 0xe554001b, 0xfc4f315a, 0xd7626299, 0xce7953d8, - 0x49e14f17, 0x50fa7e56, 0x7bd72d95, 0x62cc1cd4, - 0x2d8d8a13, 0x3496bb52, 0x1fbbe891, 0x06a0d9d0, - 0x5e7ef3ec, 0x4765c2ad, 0x6c48916e, 0x7553a02f, - 0x3a1236e8, 0x230907a9, 0x0824546a, 0x113f652b, - 0x96a779e4, 0x8fbc48a5, 0xa4911b66, 0xbd8a2a27, - 0xf2cbbce0, 0xebd08da1, 0xc0fdde62, 0xd9e6ef23, - 0x14bce1bd, 0x0da7d0fc, 0x268a833f, 0x3f91b27e, - 0x70d024b9, 0x69cb15f8, 0x42e6463b, 0x5bfd777a, - 0xdc656bb5, 0xc57e5af4, 0xee530937, 0xf7483876, - 0xb809aeb1, 0xa1129ff0, 0x8a3fcc33, 0x9324fd72, -}; - -unsigned int crc32_table1[256] = -{ - 0x00000000, 0x01c26a37, 0x0384d46e, 0x0246be59, - 0x0709a8dc, 0x06cbc2eb, 0x048d7cb2, 0x054f1685, - 0x0e1351b8, 0x0fd13b8f, 0x0d9785d6, 0x0c55efe1, - 0x091af964, 0x08d89353, 0x0a9e2d0a, 0x0b5c473d, - 0x1c26a370, 0x1de4c947, 0x1fa2771e, 0x1e601d29, - 0x1b2f0bac, 0x1aed619b, 0x18abdfc2, 0x1969b5f5, - 0x1235f2c8, 0x13f798ff, 0x11b126a6, 0x10734c91, - 0x153c5a14, 0x14fe3023, 0x16b88e7a, 0x177ae44d, - 0x384d46e0, 0x398f2cd7, 0x3bc9928e, 0x3a0bf8b9, - 0x3f44ee3c, 0x3e86840b, 0x3cc03a52, 0x3d025065, - 0x365e1758, 0x379c7d6f, 0x35dac336, 0x3418a901, - 0x3157bf84, 0x3095d5b3, 0x32d36bea, 0x331101dd, - 0x246be590, 0x25a98fa7, 0x27ef31fe, 0x262d5bc9, - 0x23624d4c, 0x22a0277b, 0x20e69922, 0x2124f315, - 0x2a78b428, 0x2bbade1f, 0x29fc6046, 0x283e0a71, - 0x2d711cf4, 0x2cb376c3, 0x2ef5c89a, 0x2f37a2ad, - 0x709a8dc0, 0x7158e7f7, 0x731e59ae, 0x72dc3399, - 0x7793251c, 0x76514f2b, 0x7417f172, 0x75d59b45, - 0x7e89dc78, 0x7f4bb64f, 0x7d0d0816, 0x7ccf6221, - 0x798074a4, 0x78421e93, 0x7a04a0ca, 0x7bc6cafd, - 0x6cbc2eb0, 0x6d7e4487, 0x6f38fade, 0x6efa90e9, - 0x6bb5866c, 0x6a77ec5b, 0x68315202, 0x69f33835, - 0x62af7f08, 0x636d153f, 0x612bab66, 0x60e9c151, - 0x65a6d7d4, 0x6464bde3, 0x662203ba, 0x67e0698d, - 0x48d7cb20, 0x4915a117, 0x4b531f4e, 0x4a917579, - 0x4fde63fc, 0x4e1c09cb, 0x4c5ab792, 0x4d98dda5, - 0x46c49a98, 0x4706f0af, 0x45404ef6, 0x448224c1, - 0x41cd3244, 0x400f5873, 0x4249e62a, 0x438b8c1d, - 0x54f16850, 0x55330267, 0x5775bc3e, 0x56b7d609, - 0x53f8c08c, 0x523aaabb, 0x507c14e2, 0x51be7ed5, - 0x5ae239e8, 0x5b2053df, 0x5966ed86, 0x58a487b1, - 0x5deb9134, 0x5c29fb03, 0x5e6f455a, 0x5fad2f6d, - 0xe1351b80, 0xe0f771b7, 0xe2b1cfee, 0xe373a5d9, - 0xe63cb35c, 0xe7fed96b, 0xe5b86732, 0xe47a0d05, - 0xef264a38, 0xeee4200f, 0xeca29e56, 0xed60f461, - 0xe82fe2e4, 0xe9ed88d3, 0xebab368a, 0xea695cbd, - 0xfd13b8f0, 0xfcd1d2c7, 0xfe976c9e, 0xff5506a9, - 0xfa1a102c, 0xfbd87a1b, 0xf99ec442, 0xf85cae75, - 0xf300e948, 0xf2c2837f, 0xf0843d26, 0xf1465711, - 0xf4094194, 0xf5cb2ba3, 0xf78d95fa, 0xf64fffcd, - 0xd9785d60, 0xd8ba3757, 0xdafc890e, 0xdb3ee339, - 0xde71f5bc, 0xdfb39f8b, 0xddf521d2, 0xdc374be5, - 0xd76b0cd8, 0xd6a966ef, 0xd4efd8b6, 0xd52db281, - 0xd062a404, 0xd1a0ce33, 0xd3e6706a, 0xd2241a5d, - 0xc55efe10, 0xc49c9427, 0xc6da2a7e, 0xc7184049, - 0xc25756cc, 0xc3953cfb, 0xc1d382a2, 0xc011e895, - 0xcb4dafa8, 0xca8fc59f, 0xc8c97bc6, 0xc90b11f1, - 0xcc440774, 0xcd866d43, 0xcfc0d31a, 0xce02b92d, - 0x91af9640, 0x906dfc77, 0x922b422e, 0x93e92819, - 0x96a63e9c, 0x976454ab, 0x9522eaf2, 0x94e080c5, - 0x9fbcc7f8, 0x9e7eadcf, 0x9c381396, 0x9dfa79a1, - 0x98b56f24, 0x99770513, 0x9b31bb4a, 0x9af3d17d, - 0x8d893530, 0x8c4b5f07, 0x8e0de15e, 0x8fcf8b69, - 0x8a809dec, 0x8b42f7db, 0x89044982, 0x88c623b5, - 0x839a6488, 0x82580ebf, 0x801eb0e6, 0x81dcdad1, - 0x8493cc54, 0x8551a663, 0x8717183a, 0x86d5720d, - 0xa9e2d0a0, 0xa820ba97, 0xaa6604ce, 0xaba46ef9, - 0xaeeb787c, 0xaf29124b, 0xad6fac12, 0xacadc625, - 0xa7f18118, 0xa633eb2f, 0xa4755576, 0xa5b73f41, - 0xa0f829c4, 0xa13a43f3, 0xa37cfdaa, 0xa2be979d, - 0xb5c473d0, 0xb40619e7, 0xb640a7be, 0xb782cd89, - 0xb2cddb0c, 0xb30fb13b, 0xb1490f62, 0xb08b6555, - 0xbbd72268, 0xba15485f, 0xb853f606, 0xb9919c31, - 0xbcde8ab4, 0xbd1ce083, 0xbf5a5eda, 0xbe9834ed, -}; - -unsigned int crc32_table0[256] = { - 0x00000000, 0xb8bc6765, 0xaa09c88b, 0x12b5afee, - 0x8f629757, 0x37def032, 0x256b5fdc, 0x9dd738b9, - 0xc5b428ef, 0x7d084f8a, 0x6fbde064, 0xd7018701, - 0x4ad6bfb8, 0xf26ad8dd, 0xe0df7733, 0x58631056, - 0x5019579f, 0xe8a530fa, 0xfa109f14, 0x42acf871, - 0xdf7bc0c8, 0x67c7a7ad, 0x75720843, 0xcdce6f26, - 0x95ad7f70, 0x2d111815, 0x3fa4b7fb, 0x8718d09e, - 0x1acfe827, 0xa2738f42, 0xb0c620ac, 0x087a47c9, - 0xa032af3e, 0x188ec85b, 0x0a3b67b5, 0xb28700d0, - 0x2f503869, 0x97ec5f0c, 0x8559f0e2, 0x3de59787, - 0x658687d1, 0xdd3ae0b4, 0xcf8f4f5a, 0x7733283f, - 0xeae41086, 0x525877e3, 0x40edd80d, 0xf851bf68, - 0xf02bf8a1, 0x48979fc4, 0x5a22302a, 0xe29e574f, - 0x7f496ff6, 0xc7f50893, 0xd540a77d, 0x6dfcc018, - 0x359fd04e, 0x8d23b72b, 0x9f9618c5, 0x272a7fa0, - 0xbafd4719, 0x0241207c, 0x10f48f92, 0xa848e8f7, - 0x9b14583d, 0x23a83f58, 0x311d90b6, 0x89a1f7d3, - 0x1476cf6a, 0xaccaa80f, 0xbe7f07e1, 0x06c36084, - 0x5ea070d2, 0xe61c17b7, 0xf4a9b859, 0x4c15df3c, - 0xd1c2e785, 0x697e80e0, 0x7bcb2f0e, 0xc377486b, - 0xcb0d0fa2, 0x73b168c7, 0x6104c729, 0xd9b8a04c, - 0x446f98f5, 0xfcd3ff90, 0xee66507e, 0x56da371b, - 0x0eb9274d, 0xb6054028, 0xa4b0efc6, 0x1c0c88a3, - 0x81dbb01a, 0x3967d77f, 0x2bd27891, 0x936e1ff4, - 0x3b26f703, 0x839a9066, 0x912f3f88, 0x299358ed, - 0xb4446054, 0x0cf80731, 0x1e4da8df, 0xa6f1cfba, - 0xfe92dfec, 0x462eb889, 0x549b1767, 0xec277002, - 0x71f048bb, 0xc94c2fde, 0xdbf98030, 0x6345e755, - 0x6b3fa09c, 0xd383c7f9, 0xc1366817, 0x798a0f72, - 0xe45d37cb, 0x5ce150ae, 0x4e54ff40, 0xf6e89825, - 0xae8b8873, 0x1637ef16, 0x048240f8, 0xbc3e279d, - 0x21e91f24, 0x99557841, 0x8be0d7af, 0x335cb0ca, - 0xed59b63b, 0x55e5d15e, 0x47507eb0, 0xffec19d5, - 0x623b216c, 0xda874609, 0xc832e9e7, 0x708e8e82, - 0x28ed9ed4, 0x9051f9b1, 0x82e4565f, 0x3a58313a, - 0xa78f0983, 0x1f336ee6, 0x0d86c108, 0xb53aa66d, - 0xbd40e1a4, 0x05fc86c1, 0x1749292f, 0xaff54e4a, - 0x322276f3, 0x8a9e1196, 0x982bbe78, 0x2097d91d, - 0x78f4c94b, 0xc048ae2e, 0xd2fd01c0, 0x6a4166a5, - 0xf7965e1c, 0x4f2a3979, 0x5d9f9697, 0xe523f1f2, - 0x4d6b1905, 0xf5d77e60, 0xe762d18e, 0x5fdeb6eb, - 0xc2098e52, 0x7ab5e937, 0x680046d9, 0xd0bc21bc, - 0x88df31ea, 0x3063568f, 0x22d6f961, 0x9a6a9e04, - 0x07bda6bd, 0xbf01c1d8, 0xadb46e36, 0x15080953, - 0x1d724e9a, 0xa5ce29ff, 0xb77b8611, 0x0fc7e174, - 0x9210d9cd, 0x2aacbea8, 0x38191146, 0x80a57623, - 0xd8c66675, 0x607a0110, 0x72cfaefe, 0xca73c99b, - 0x57a4f122, 0xef189647, 0xfdad39a9, 0x45115ecc, - 0x764dee06, 0xcef18963, 0xdc44268d, 0x64f841e8, - 0xf92f7951, 0x41931e34, 0x5326b1da, 0xeb9ad6bf, - 0xb3f9c6e9, 0x0b45a18c, 0x19f00e62, 0xa14c6907, - 0x3c9b51be, 0x842736db, 0x96929935, 0x2e2efe50, - 0x2654b999, 0x9ee8defc, 0x8c5d7112, 0x34e11677, - 0xa9362ece, 0x118a49ab, 0x033fe645, 0xbb838120, - 0xe3e09176, 0x5b5cf613, 0x49e959fd, 0xf1553e98, - 0x6c820621, 0xd43e6144, 0xc68bceaa, 0x7e37a9cf, - 0xd67f4138, 0x6ec3265d, 0x7c7689b3, 0xc4caeed6, - 0x591dd66f, 0xe1a1b10a, 0xf3141ee4, 0x4ba87981, - 0x13cb69d7, 0xab770eb2, 0xb9c2a15c, 0x017ec639, - 0x9ca9fe80, 0x241599e5, 0x36a0360b, 0x8e1c516e, - 0x866616a7, 0x3eda71c2, 0x2c6fde2c, 0x94d3b949, - 0x090481f0, 0xb1b8e695, 0xa30d497b, 0x1bb12e1e, - 0x43d23e48, 0xfb6e592d, 0xe9dbf6c3, 0x516791a6, - 0xccb0a91f, 0x740cce7a, 0x66b96194, 0xde0506f1, -}; - -unsigned crc32_partial_old (const void *data, int len, unsigned crc) { - const char *p = data; - for (; len > 0; len--) { - crc = crc32_table[(crc ^ *p++) & 0xff] ^ (crc >> 8); - } - return crc; -} - -/* -unsigned crc32_partial_fast (const void *data, int len, unsigned crc) { - const int *p = (const int *) data; - int x; - for (x = (len >> 2); x > 0; x--) { - crc ^= *p++; - crc = crc32_table0[crc & 0xff] ^ crc32_table1[(crc & 0xff00) >> 8] ^ crc32_table2[(crc & 0xff0000) >> 16] ^ crc32_table[crc >> 24]; - } - const char *q = (const char *) p; - switch (len & 3) { - case 3: - crc = crc32_table[(crc ^ *q++) & 0xff] ^ (crc >> 8); - case 2: - crc = crc32_table[(crc ^ *q++) & 0xff] ^ (crc >> 8); - case 1: - crc = crc32_table[(crc ^ *q++) & 0xff] ^ (crc >> 8); - } - return crc; -} -*/ - -unsigned crc32_partial (const void *data, int len, unsigned crc) { - const int *p = (const int *) data; - int x; -#define DO_ONE(v) crc ^= v; crc = crc32_table0[crc & 0xff] ^ crc32_table1[(crc & 0xff00) >> 8] ^ crc32_table2[(crc & 0xff0000) >> 16] ^ crc32_table[crc >> 24]; -#define DO_FOUR(p) DO_ONE((p)[0]); DO_ONE((p)[1]); DO_ONE((p)[2]); DO_ONE((p)[3]); - - for (x = (len >> 5); x > 0; x--) { - DO_FOUR (p); - DO_FOUR (p + 4); - p += 8; - } - if (len & 16) { - DO_FOUR (p); - p += 4; - } - if (len & 8) { - DO_ONE (p[0]); - DO_ONE (p[1]); - p += 2; - } - if (len & 4) { - DO_ONE (*p++); - } - /* - for (x = (len >> 2) & 7; x > 0; x--) { - DO_ONE (*p++); - } - */ -#undef DO_ONE -#undef DO_FOUR - const char *q = (const char *) p; - if (len & 2) { - crc = crc32_table[(crc ^ q[0]) & 0xff] ^ (crc >> 8); - crc = crc32_table[(crc ^ q[1]) & 0xff] ^ (crc >> 8); - q += 2; - } - if (len & 1) { - crc = crc32_table[(crc ^ *q++) & 0xff] ^ (crc >> 8); - } - return crc; -} - -unsigned compute_crc32 (const void *data, int len) { - return crc32_partial (data, len, -1) ^ -1; -} - -unsigned long long crc64_table[256] = { - 0x0000000000000000LL, 0xb32e4cbe03a75f6fLL, 0xf4843657a840a05bLL, 0x47aa7ae9abe7ff34LL, - 0x7bd0c384ff8f5e33LL, 0xc8fe8f3afc28015cLL, 0x8f54f5d357cffe68LL, 0x3c7ab96d5468a107LL, - 0xf7a18709ff1ebc66LL, 0x448fcbb7fcb9e309LL, 0x0325b15e575e1c3dLL, 0xb00bfde054f94352LL, - 0x8c71448d0091e255LL, 0x3f5f08330336bd3aLL, 0x78f572daa8d1420eLL, 0xcbdb3e64ab761d61LL, - 0x7d9ba13851336649LL, 0xceb5ed8652943926LL, 0x891f976ff973c612LL, 0x3a31dbd1fad4997dLL, - 0x064b62bcaebc387aLL, 0xb5652e02ad1b6715LL, 0xf2cf54eb06fc9821LL, 0x41e11855055bc74eLL, - 0x8a3a2631ae2dda2fLL, 0x39146a8fad8a8540LL, 0x7ebe1066066d7a74LL, 0xcd905cd805ca251bLL, - 0xf1eae5b551a2841cLL, 0x42c4a90b5205db73LL, 0x056ed3e2f9e22447LL, 0xb6409f5cfa457b28LL, - 0xfb374270a266cc92LL, 0x48190ecea1c193fdLL, 0x0fb374270a266cc9LL, 0xbc9d3899098133a6LL, - 0x80e781f45de992a1LL, 0x33c9cd4a5e4ecdceLL, 0x7463b7a3f5a932faLL, 0xc74dfb1df60e6d95LL, - 0x0c96c5795d7870f4LL, 0xbfb889c75edf2f9bLL, 0xf812f32ef538d0afLL, 0x4b3cbf90f69f8fc0LL, - 0x774606fda2f72ec7LL, 0xc4684a43a15071a8LL, 0x83c230aa0ab78e9cLL, 0x30ec7c140910d1f3LL, - 0x86ace348f355aadbLL, 0x3582aff6f0f2f5b4LL, 0x7228d51f5b150a80LL, 0xc10699a158b255efLL, - 0xfd7c20cc0cdaf4e8LL, 0x4e526c720f7dab87LL, 0x09f8169ba49a54b3LL, 0xbad65a25a73d0bdcLL, - 0x710d64410c4b16bdLL, 0xc22328ff0fec49d2LL, 0x85895216a40bb6e6LL, 0x36a71ea8a7ace989LL, - 0x0adda7c5f3c4488eLL, 0xb9f3eb7bf06317e1LL, 0xfe5991925b84e8d5LL, 0x4d77dd2c5823b7baLL, - 0x64b62bcaebc387a1LL, 0xd7986774e864d8ceLL, 0x90321d9d438327faLL, 0x231c512340247895LL, - 0x1f66e84e144cd992LL, 0xac48a4f017eb86fdLL, 0xebe2de19bc0c79c9LL, 0x58cc92a7bfab26a6LL, - 0x9317acc314dd3bc7LL, 0x2039e07d177a64a8LL, 0x67939a94bc9d9b9cLL, 0xd4bdd62abf3ac4f3LL, - 0xe8c76f47eb5265f4LL, 0x5be923f9e8f53a9bLL, 0x1c4359104312c5afLL, 0xaf6d15ae40b59ac0LL, - 0x192d8af2baf0e1e8LL, 0xaa03c64cb957be87LL, 0xeda9bca512b041b3LL, 0x5e87f01b11171edcLL, - 0x62fd4976457fbfdbLL, 0xd1d305c846d8e0b4LL, 0x96797f21ed3f1f80LL, 0x2557339fee9840efLL, - 0xee8c0dfb45ee5d8eLL, 0x5da24145464902e1LL, 0x1a083bacedaefdd5LL, 0xa9267712ee09a2baLL, - 0x955cce7fba6103bdLL, 0x267282c1b9c65cd2LL, 0x61d8f8281221a3e6LL, 0xd2f6b4961186fc89LL, - 0x9f8169ba49a54b33LL, 0x2caf25044a02145cLL, 0x6b055fede1e5eb68LL, 0xd82b1353e242b407LL, - 0xe451aa3eb62a1500LL, 0x577fe680b58d4a6fLL, 0x10d59c691e6ab55bLL, 0xa3fbd0d71dcdea34LL, - 0x6820eeb3b6bbf755LL, 0xdb0ea20db51ca83aLL, 0x9ca4d8e41efb570eLL, 0x2f8a945a1d5c0861LL, - 0x13f02d374934a966LL, 0xa0de61894a93f609LL, 0xe7741b60e174093dLL, 0x545a57dee2d35652LL, - 0xe21ac88218962d7aLL, 0x5134843c1b317215LL, 0x169efed5b0d68d21LL, 0xa5b0b26bb371d24eLL, - 0x99ca0b06e7197349LL, 0x2ae447b8e4be2c26LL, 0x6d4e3d514f59d312LL, 0xde6071ef4cfe8c7dLL, - 0x15bb4f8be788911cLL, 0xa6950335e42fce73LL, 0xe13f79dc4fc83147LL, 0x521135624c6f6e28LL, - 0x6e6b8c0f1807cf2fLL, 0xdd45c0b11ba09040LL, 0x9aefba58b0476f74LL, 0x29c1f6e6b3e0301bLL, - 0xc96c5795d7870f42LL, 0x7a421b2bd420502dLL, 0x3de861c27fc7af19LL, 0x8ec62d7c7c60f076LL, - 0xb2bc941128085171LL, 0x0192d8af2baf0e1eLL, 0x4638a2468048f12aLL, 0xf516eef883efae45LL, - 0x3ecdd09c2899b324LL, 0x8de39c222b3eec4bLL, 0xca49e6cb80d9137fLL, 0x7967aa75837e4c10LL, - 0x451d1318d716ed17LL, 0xf6335fa6d4b1b278LL, 0xb199254f7f564d4cLL, 0x02b769f17cf11223LL, - 0xb4f7f6ad86b4690bLL, 0x07d9ba1385133664LL, 0x4073c0fa2ef4c950LL, 0xf35d8c442d53963fLL, - 0xcf273529793b3738LL, 0x7c0979977a9c6857LL, 0x3ba3037ed17b9763LL, 0x888d4fc0d2dcc80cLL, - 0x435671a479aad56dLL, 0xf0783d1a7a0d8a02LL, 0xb7d247f3d1ea7536LL, 0x04fc0b4dd24d2a59LL, - 0x3886b22086258b5eLL, 0x8ba8fe9e8582d431LL, 0xcc0284772e652b05LL, 0x7f2cc8c92dc2746aLL, - 0x325b15e575e1c3d0LL, 0x8175595b76469cbfLL, 0xc6df23b2dda1638bLL, 0x75f16f0cde063ce4LL, - 0x498bd6618a6e9de3LL, 0xfaa59adf89c9c28cLL, 0xbd0fe036222e3db8LL, 0x0e21ac88218962d7LL, - 0xc5fa92ec8aff7fb6LL, 0x76d4de52895820d9LL, 0x317ea4bb22bfdfedLL, 0x8250e80521188082LL, - 0xbe2a516875702185LL, 0x0d041dd676d77eeaLL, 0x4aae673fdd3081deLL, 0xf9802b81de97deb1LL, - 0x4fc0b4dd24d2a599LL, 0xfceef8632775faf6LL, 0xbb44828a8c9205c2LL, 0x086ace348f355aadLL, - 0x34107759db5dfbaaLL, 0x873e3be7d8faa4c5LL, 0xc094410e731d5bf1LL, 0x73ba0db070ba049eLL, - 0xb86133d4dbcc19ffLL, 0x0b4f7f6ad86b4690LL, 0x4ce50583738cb9a4LL, 0xffcb493d702be6cbLL, - 0xc3b1f050244347ccLL, 0x709fbcee27e418a3LL, 0x3735c6078c03e797LL, 0x841b8ab98fa4b8f8LL, - 0xadda7c5f3c4488e3LL, 0x1ef430e13fe3d78cLL, 0x595e4a08940428b8LL, 0xea7006b697a377d7LL, - 0xd60abfdbc3cbd6d0LL, 0x6524f365c06c89bfLL, 0x228e898c6b8b768bLL, 0x91a0c532682c29e4LL, - 0x5a7bfb56c35a3485LL, 0xe955b7e8c0fd6beaLL, 0xaeffcd016b1a94deLL, 0x1dd181bf68bdcbb1LL, - 0x21ab38d23cd56ab6LL, 0x9285746c3f7235d9LL, 0xd52f0e859495caedLL, 0x6601423b97329582LL, - 0xd041dd676d77eeaaLL, 0x636f91d96ed0b1c5LL, 0x24c5eb30c5374ef1LL, 0x97eba78ec690119eLL, - 0xab911ee392f8b099LL, 0x18bf525d915feff6LL, 0x5f1528b43ab810c2LL, 0xec3b640a391f4fadLL, - 0x27e05a6e926952ccLL, 0x94ce16d091ce0da3LL, 0xd3646c393a29f297LL, 0x604a2087398eadf8LL, - 0x5c3099ea6de60cffLL, 0xef1ed5546e415390LL, 0xa8b4afbdc5a6aca4LL, 0x1b9ae303c601f3cbLL, - 0x56ed3e2f9e224471LL, 0xe5c372919d851b1eLL, 0xa26908783662e42aLL, 0x114744c635c5bb45LL, - 0x2d3dfdab61ad1a42LL, 0x9e13b115620a452dLL, 0xd9b9cbfcc9edba19LL, 0x6a978742ca4ae576LL, - 0xa14cb926613cf817LL, 0x1262f598629ba778LL, 0x55c88f71c97c584cLL, 0xe6e6c3cfcadb0723LL, - 0xda9c7aa29eb3a624LL, 0x69b2361c9d14f94bLL, 0x2e184cf536f3067fLL, 0x9d36004b35545910LL, - 0x2b769f17cf112238LL, 0x9858d3a9ccb67d57LL, 0xdff2a94067518263LL, 0x6cdce5fe64f6dd0cLL, - 0x50a65c93309e7c0bLL, 0xe388102d33392364LL, 0xa4226ac498dedc50LL, 0x170c267a9b79833fLL, - 0xdcd7181e300f9e5eLL, 0x6ff954a033a8c131LL, 0x28532e49984f3e05LL, 0x9b7d62f79be8616aLL, - 0xa707db9acf80c06dLL, 0x14299724cc279f02LL, 0x5383edcd67c06036LL, 0xe0ada17364673f59LL -}; - -unsigned long long crc64_partial (const void *data, int len, unsigned long long crc) { - const char *p = data; - for (; len > 0; len--) { - crc = crc64_table[(crc ^ *p++) & 0xff] ^ (crc >> 8); - } - return crc; -} - -unsigned long long crc64 (const void *data, int len) { - return crc64_partial (data, len, -1LL) ^ -1LL; -} - -static unsigned gf32_matrix_times (unsigned *matrix, unsigned vector) { - unsigned sum = 0; - while (vector) { - if (vector & 1) { - sum ^= *matrix; - } - vector >>= 1; - matrix++; - } - return sum; -} - -static void gf32_matrix_square (unsigned *square, unsigned *matrix) { - int n = 0; - do { - square[n] = gf32_matrix_times (matrix, matrix[n]); - } while (++n < 32); -} - -unsigned compute_crc32_combine (unsigned crc1, unsigned crc2, int len2) { - assert (len2 < (1 << 29)); - static int power_buf_initialized = 0; - static unsigned power_buf[1024]; - int n; - /* degenerate case (also disallow negative lengths) */ - if (len2 <= 0) { - return crc1; - } - if (!power_buf_initialized) { - power_buf[0] = 0xedb88320UL; - for (n = 0; n < 31; n++) { - power_buf[n+1] = 1U << n; - } - for (n = 1; n < 32; n++) { - gf32_matrix_square (power_buf + (n << 5), power_buf + ((n - 1) << 5)); - } - power_buf_initialized = 1; - } - - unsigned int *p = power_buf + 64; - do { - p += 32; - if (len2 & 1) { - crc1 = gf32_matrix_times (p, crc1); - } - len2 >>= 1; - } while (len2); - return crc1 ^ crc2; -} - - -/********************************* crc32 repair ************************/ -struct fcb_table_entry { - unsigned p; //zeta ^ k - int i; -}; - -static inline unsigned gf32_mod (unsigned long long r, int high_bit) { - int j = high_bit; - for (j = high_bit; j >= 32; j--) { - if ((1ULL << j) & r) { - r ^= 0x04C11DB7ULL << (j - 32); - } - } - return (unsigned) r; -} - -static unsigned gf32_mult (unsigned a, unsigned b) { - int i; - const unsigned long long m = b; - unsigned long long r = 0; - for (i = 0; i < 32; i++) { - if (a & (1U << i)) { - r ^= m << i; - } - } - return gf32_mod (r, 62); -} - -static unsigned gf32_shl (unsigned int a, int shift) { - unsigned long long r = a; - r <<= shift; - return gf32_mod (r, 31 + shift); -} - -static unsigned gf32_pow (unsigned a, int k) { - if (!k) { return 1; } - unsigned x = gf32_pow (gf32_mult (a, a), k >> 1); - if (k & 1) { - x = gf32_mult (x, a); - } - return x; -} - -static int cmp_fcb_table_entry (const void *a, const void *b) { - const struct fcb_table_entry *x = a; - const struct fcb_table_entry *y = b; - if (x->p < y->p) { return -1; } - if (x->p > y->p) { return 1; } - if (x->i < y->i) { return -1; } - if (x->i > y->i) { return 1; } - return 0; -} - -#define GROUP_SWAP(x,m,s) ((x & m) << s) | ((x & (~m)) >> s) -static unsigned revbin (unsigned x) { - x = GROUP_SWAP(x,0x55555555U,1); - x = GROUP_SWAP(x,0x33333333U,2); - x = GROUP_SWAP(x,0x0f0f0f0fU,4); - x = __builtin_bswap32 (x); - return x; -} -#undef GROUP_SWAP - -static inline unsigned xmult (unsigned a) { - unsigned r = a << 1; - if (a & (1U<<31)) { - r ^= 0x04C11DB7U; - } - return r; -} - -static int find_corrupted_bit (int size, unsigned d) { - int i, j; - size += 4; - d = revbin (d); - int n = size << 3; - int r = (int) (sqrt (n) + 0.5); - struct fcb_table_entry *T = calloc (r, sizeof (struct fcb_table_entry)); - assert (T != NULL); - T[0].i = 0; - T[0].p = 1; - for (i = 1; i < r; i++) { - T[i].i = i; - T[i].p = xmult (T[i-1].p); - } - assert (xmult (0x82608EDB) == 1); - qsort (T, r, sizeof (T[0]), cmp_fcb_table_entry); - unsigned q = gf32_pow (0x82608EDB, r); - - unsigned A[32]; - for (i = 0; i < 32; i++) { - A[i] = gf32_shl (q, i); - } - - unsigned x = d; - int max_j = n / r, res = -1; - for (j = 0; j <= max_j; j++) { - int a = -1, b = r; - while (b - a > 1) { - int c = ((a + b) >> 1); - if (T[c].p <= x) { a = c; } else { b = c; } - } - if (a >= 0 && T[a].p == x) { - res = T[a].i + r * j; - break; - } - x = gf32_matrix_times (A, x); - } - free (T); - return res; -} - -static int repair_bit (unsigned char *input, int l, int k) { - if (k < 0) { - return -1; - } - int idx = k >> 5, bit = k & 31, i = (l - 1) - (idx - 1) * 4; - while (bit >= 8) { - i--; - bit -= 8; - } - if (i < 0) { - return -2; - } - if (i >= l) { - return -3; - } - int j = 7 - bit; - input[i] ^= 1 << j; - return 0; -} - -int crc32_check_and_repair (void *input, int l, unsigned *input_crc32, int force_exit) { - unsigned computed_crc32 = compute_crc32 (input, l); - const unsigned crc32_diff = computed_crc32 ^ (*input_crc32); - if (!crc32_diff) { - return 0; - } - int k = find_corrupted_bit (l, crc32_diff); - int r = repair_bit (input, l, k); - if (!r) { - assert (compute_crc32 (input, l) == *input_crc32); - return 1; - } - if (!(crc32_diff & (crc32_diff - 1))) { /* crc32_diff is power of 2 */ - *input_crc32 = computed_crc32; - return 2; - } - assert (!force_exit); - *input_crc32 = computed_crc32; - return -1; -} diff --git a/crc32.h b/crc32.h deleted file mode 100644 index fdf8da8..0000000 --- a/crc32.h +++ /dev/null @@ -1,59 +0,0 @@ -/* - This file is part of VK/KittenPHP-DB-Engine Library. - - VK/KittenPHP-DB-Engine Library is free software: you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - VK/KittenPHP-DB-Engine Library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with VK/KittenPHP-DB-Engine Library. If not, see . - - Copyright 2009-2012 Vkontakte Ltd - 2009-2012 Nikolai Durov - 2009-2012 Andrei Lopatin - 2012 Anton Maydell -*/ - -#ifndef __CRC32_H__ -#define __CRC32_H__ - - -#ifdef __cplusplus -extern "C" { -#endif - -extern unsigned int crc32_table[256]; -unsigned crc32_partial (const void *data, int len, unsigned crc); - //unsigned crc32_partial_fast (const void *data, int len, unsigned crc); - //unsigned crc32_partial_fastest (const void *data, int len, unsigned crc); -unsigned compute_crc32 (const void *data, int len); -unsigned compute_crc32_combine (unsigned crc1, unsigned crc2, int len2); - -extern unsigned long long crc64_table[256]; -unsigned long long crc64_partial (const void *data, int len, unsigned long long crc); -unsigned long long crc64 (const void *data, int len); - -//unsigned gf32_matrix_times (unsigned *matrix, unsigned vector); - -/* crc32_check_and_repair returns - 0 : Cyclic redundancy check is ok - 1 : Cyclic redundancy check fails, but we fix one bit in input - 2 : Cyclic redundancy check fails, but we fix one bit in input_crc32 - -1 : Cyclic redundancy check fails, no repair possible. - In this case *input_crc32 will be equal crc32 (input, l) - - Case force_exit == 1 (case 1, 2: kprintf call, case -1: assert fail). -*/ -int crc32_check_and_repair (void *input, int l, unsigned *input_crc32, int force_exit); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/encrypted_scheme.tl b/encrypted_scheme.tl deleted file mode 120000 index b45af3d..0000000 --- a/encrypted_scheme.tl +++ /dev/null @@ -1 +0,0 @@ -encrypted_scheme17.tl \ No newline at end of file diff --git a/encrypted_scheme16.tl b/encrypted_scheme16.tl deleted file mode 100644 index eb58ed4..0000000 --- a/encrypted_scheme16.tl +++ /dev/null @@ -1,22 +0,0 @@ ----types--- -decryptedMessageLayer#99a438cf layer:int message:DecryptedMessage = DecryptedMessageLayer; -decryptedMessage#1f814f1f random_id:long random_bytes:bytes message:string media:DecryptedMessageMedia = DecryptedMessage; -decryptedMessageService#aa48327d random_id:long random_bytes:bytes action:DecryptedMessageAction = DecryptedMessage; -decryptedMessageMediaEmpty#89f5c4a = DecryptedMessageMedia; -decryptedMessageMediaPhoto#32798a8c thumb:bytes thumb_w:int thumb_h:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -//decryptedMessageMediaVideo#4cee6ef3 thumb:bytes thumb_w:int thumb_h:int duration:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaGeoPoint#35480a59 lat:double long:double = DecryptedMessageMedia; -decryptedMessageMediaContact#588a0a97 phone_number:string first_name:string last_name:string user_id:int = DecryptedMessageMedia; -decryptedMessageActionSetMessageTTL#a1733aec ttl_seconds:int = DecryptedMessageAction; - -decryptedMessageMediaDocument#b095434b thumb:bytes thumb_w:int thumb_h:int file_name:string mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -//decryptedMessageMediaAudio#6080758f duration:int size:int key:bytes iv:bytes = DecryptedMessageMedia; - -decryptedMessageMediaVideo#524a415d thumb:bytes thumb_w:int thumb_h:int duration:int mime_type:string w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaAudio#57e0a9cb duration:int mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageActionReadMessages#c4f40be random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionDeleteMessages#65614304 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionScreenshotMessages#8ac1f475 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionFlushHistory#6719e45c = DecryptedMessageAction; -decryptedMessageActionNotifyLayer#f3048883 layer:int = DecryptedMessageAction; ----functions--- diff --git a/encrypted_scheme17.tl b/encrypted_scheme17.tl deleted file mode 100644 index 95e661b..0000000 --- a/encrypted_scheme17.tl +++ /dev/null @@ -1,31 +0,0 @@ ----types--- -decryptedMessageLayer#1be31789 layer:int message:DecryptedMessage = DecryptedMessageLayer; -decryptedMessage_l16#1f814f1f random_id:long random_bytes:bytes message:string media:DecryptedMessageMedia = DecryptedMessage; -decryptedMessageService_l16#aa48327d random_id:long random_bytes:bytes action:DecryptedMessageAction = DecryptedMessage; - -decryptedMessage#204d3878 in_seq_no:int out_seq_no:int ttl:int random_id:long random_bytes:bytes message:string media:DecryptedMessageMedia = DecryptedMessage; -decryptedMessageService#73164160 in_seq_no:int out_seq_no:int random_id:long random_bytes:bytes action:DecryptedMessageAction = DecryptedMessage; - -decryptedMessageMediaEmpty#89f5c4a = DecryptedMessageMedia; -decryptedMessageMediaPhoto#32798a8c thumb:bytes thumb_w:int thumb_h:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -//decryptedMessageMediaVideo#4cee6ef3 thumb:bytes thumb_w:int thumb_h:int duration:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaGeoPoint#35480a59 lat:double long:double = DecryptedMessageMedia; -decryptedMessageMediaContact#588a0a97 phone_number:string first_name:string last_name:string user_id:int = DecryptedMessageMedia; -decryptedMessageActionSetMessageTTL#a1733aec ttl_seconds:int = DecryptedMessageAction; - -decryptedMessageMediaDocument#b095434b thumb:bytes thumb_w:int thumb_h:int file_name:string mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -//decryptedMessageMediaAudio#6080758f duration:int size:int key:bytes iv:bytes = DecryptedMessageMedia; - -decryptedMessageMediaVideo#524a415d thumb:bytes thumb_w:int thumb_h:int duration:int mime_type:string w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaAudio#57e0a9cb duration:int mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageActionReadMessages#c4f40be random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionDeleteMessages#65614304 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionScreenshotMessages#8ac1f475 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionFlushHistory#6719e45c = DecryptedMessageAction; -decryptedMessageActionNotifyLayer#f3048883 layer:int = DecryptedMessageAction; - -decryptedMessageActionResend#511110b0 start_seq_no:int end_seq_no:int = DecryptedMessageAction; - -decryptedMessageActionTyping#ccb27641 action:SendMessageAction = DecryptedMessageAction; - ----functions--- diff --git a/gen_constants_h.awk b/gen_constants_h.awk deleted file mode 100644 index 17e7e12..0000000 --- a/gen_constants_h.awk +++ /dev/null @@ -1,37 +0,0 @@ -BEGIN { - print "/*"; - print " This file is part of telegram-client."; - print ""; - print " Telegram-client is free software: you can redistribute it and/or modify"; - print " it under the terms of the GNU General Public License as published by"; - print " the Free Software Foundation, either version 2 of the License, or"; - print " (at your option) any later version."; - print ""; - print " Telegram-client is distributed in the hope that it will be useful,"; - print " but WITHOUT ANY WARRANTY; without even the implied warranty of"; - print " MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the"; - print " GNU General Public License for more details."; - print ""; - print " You should have received a copy of the GNU General Public License"; - print " along with this telegram-client. If not, see ."; - print ""; - print " Copyright Vitaly Valtman 2013"; - print "*/"; - print "#ifndef CONSTANTS_H"; - print "#define CONSTANTS_H"; -} -// { - if (split ($1, a, "#") == 2) { - gsub (/[ABCDEFGHIJKLMNOPQRSTUVWXYZ]/, "_&", a[1]); - gsub (/[.]/, "_", a[1]); - if (a[2] in h) { - print "ERROR: Duplicate magic " a[2] " for define " a[1] " and " h[a[2]] >"/dev/stderr/" - exit 1; - } - h[a[2]] = a[1]; - print "#define", "CODE_" tolower(a[1]), "0x" a[2]; - } -} -END { - print "#endif"; -} diff --git a/generate.c b/generate.c deleted file mode 100644 index f42177c..0000000 --- a/generate.c +++ /dev/null @@ -1,1829 +0,0 @@ -/* - This file is part of tgl-libary/generate - - Tgl-library/generate is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - Tgl-library/generate is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this tgl-library/generate. If not, see . - - Copyright Vitaly Valtman 2014 - - It is derivative work of VK/KittenPHP-DB-Engine (https://github.com/vk-com/kphp-kdb/) - Copyright 2012-2013 Vkontakte Ltd - 2012-2013 Vitaliy Valtman -*/ - -#define _GNU_SOURCE - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "tl-tl.h" -#include "generate.h" - -#include "tree.h" -#include "config.h" - -int header; - -#define tl_type_name_cmp(a,b) (a->name > b->name ? 1 : a->name < b->name ? -1 : 0) - -DEFINE_TREE (tl_type, struct tl_type *, tl_type_name_cmp, 0) -DEFINE_TREE (tl_combinator, struct tl_combinator *, tl_type_name_cmp, 0) - -struct tree_tl_type *type_tree; -struct tree_tl_combinator *function_tree; - -void tl_function_insert_by_name (struct tl_combinator *c) { - function_tree = tree_insert_tl_combinator (function_tree, c, lrand48 ()); -} - -struct tl_type *tl_type_get_by_name (int name) { - static struct tl_type t; - t.name = name; - - return tree_lookup_tl_type (type_tree, &t); -} - -void tl_type_insert_by_name (struct tl_type *t) { - type_tree = tree_insert_tl_type (type_tree, t, lrand48 ()); -} - -int is_empty (struct tl_type *t) { - if (t->name == NAME_INT || t->name == NAME_LONG || t->name == NAME_DOUBLE || t->name == NAME_STRING) { return 1; } - if (t->constructors_num != 1) { return 0; } - int count = 0; - int i; - struct tl_combinator *c = t->constructors[0]; - for (i = 0; i < c->args_num; i++) { - if (!(c->args[i]->flags & FLAG_OPT_VAR)) { count ++; } - } - return count == 1; -} - - -static char buf[1 << 20]; -int buf_size; -int *buf_ptr = (int *)buf; -int *buf_end; -#ifndef DISABLE_EXTF -int skip_only = 0; -#else -int skip_only = 1; -#endif - -int verbosity; - -int get_int (void) { - assert (buf_ptr < buf_end); - return *(buf_ptr ++); -} - -long long get_long (void) { - assert (buf_ptr + 1 < buf_end); - long long r = *(long long *)buf_ptr; - buf_ptr += 2; - return r; -} - -static void *malloc0 (int size) { - void *r = malloc (size); - assert (r); - memset (r, 0, size); - return r; -} - -char *get_string (void) { - int l = *(unsigned char *)buf_ptr; - assert (l != 0xff); - - char *res; - int tlen = 0; - if (l == 0xfe) { - l = ((unsigned)get_int ()) >> 8; - res = (char *)buf_ptr; - tlen = l; - } else { - res = ((char *)buf_ptr) + 1; - tlen = 1 + l; - } - - int len = l; - - tlen += ((-tlen) & 3); - assert (!(tlen & 3)); - - buf_ptr += tlen / 4; - assert (buf_ptr <= buf_end); - - char *r = strndup (res, len); - assert (r); - return r; -} - - -int tn, fn, cn; -struct tl_type **tps; -struct tl_combinator **fns; - -struct tl_tree *read_tree (int *var_num); -struct tl_tree *read_nat_expr (int *var_num); -struct tl_tree *read_type_expr (int *var_num); -int read_args_list (struct arg **args, int args_num, int *var_num); - -#define use_var_nat_full_form(x) 0 - -void *int_to_var_nat_const_init (long long x) { - if (use_var_nat_full_form (x)) { - struct tl_tree_nat_const *T = malloc (sizeof (*T)); - assert (T); - T->self.flags = 0; - T->self.methods = &tl_pnat_const_full_methods; - T->value = x; - return T; - } else { - return (void *)(long)(x * 2 - 0x80000001l); - } -} - -long long var_nat_const_to_int (void *x) { - if (((long)x) & 1) { - return (((long)x) + 0x80000001l) / 2; - } else { - return ((struct tl_tree_nat_const *)x)->value; - } -} - -int tl_tree_type_type (struct tl_tree *x) { - return NODE_TYPE_TYPE; -} - -int tl_tree_type_array (struct tl_tree *x) { - return NODE_TYPE_ARRAY; -} - -int tl_tree_type_nat_const (struct tl_tree *x) { - return NODE_TYPE_NAT_CONST; -} - -int tl_tree_type_var_num (struct tl_tree *x) { - return NODE_TYPE_VAR_NUM; -} - -int tl_tree_type_var_type (struct tl_tree *x) { - return NODE_TYPE_VAR_TYPE; -} - -struct tl_tree_methods tl_var_num_methods = { - .type = tl_tree_type_var_num -}; - -struct tl_tree_methods tl_var_type_methods = { - .type = tl_tree_type_var_type -}; - -struct tl_tree_methods tl_type_methods = { - .type = tl_tree_type_type -}; - -struct tl_tree_methods tl_nat_const_methods = { - .type = tl_tree_type_nat_const -}; - -struct tl_tree_methods tl_array_methods = { - .type = tl_tree_type_array -}; - -struct tl_tree_methods tl_ptype_methods = { - .type = tl_tree_type_type -}; - -struct tl_tree_methods tl_parray_methods = { - .type = tl_tree_type_array -}; - -struct tl_tree_methods tl_pvar_num_methods = { - .type = tl_tree_type_var_num -}; - -struct tl_tree_methods tl_pvar_type_methods = { - .type = tl_tree_type_var_type -}; - -struct tl_tree_methods tl_nat_const_full_methods = { - .type = tl_tree_type_nat_const -}; - -struct tl_tree_methods tl_pnat_const_full_methods = { - .type = tl_tree_type_nat_const -}; - -struct tl_tree *read_num_const (int *var_num) { - return (void *)int_to_var_nat_const_init (get_int ()); -} - - -int gen_uni_skip (struct tl_tree *t, char *cur_name, int *vars, int first, int fun) { - assert (t); - int x = TL_TREE_METHODS (t)->type (t); - int l = 0; - int i; - int j; - struct tl_tree_type *t1; - struct tl_tree_array *t2; - int y; - int L = strlen (cur_name); - char *fail = fun ? "return 0;" : "return -1;"; - switch (x) { - case NODE_TYPE_TYPE: - t1 = (void *)t; - if (!first) { - printf (" if (ODDP(%s) || %s->type->name != 0x%08x) { %s }\n", cur_name, cur_name, t1->type->name, fail); - } else { - printf (" if (ODDP(%s) || (%s->type->name != 0x%08x && %s->type->name != 0x%08x)) { %s }\n", cur_name, cur_name, t1->type->name, cur_name, ~t1->type->name, fail); - } - for (i = 0; i < t1->children_num; i++) { - sprintf (cur_name + L, "->params[%d]", i); - gen_uni_skip (t1->children[i], cur_name, vars, 0, fun); - cur_name[L] = 0; - } - return 0; - case NODE_TYPE_NAT_CONST: - printf (" if (EVENP(%s) || ((long)%s) != %lld) { %s }\n", cur_name, cur_name, var_nat_const_to_int (t) * 2 + 1, fail); - return 0; - case NODE_TYPE_ARRAY: - printf (" if (ODDP(%s) || %s->type->name != TL_TYPE_ARRAY) { %s }\n", cur_name, cur_name, fail); - t2 = (void *)t; - - sprintf (cur_name + L, "->params[0]"); - y = gen_uni_skip (t2->multiplicity, cur_name, vars, 0, fun); - cur_name[L] = 0; - - sprintf (cur_name + L, "->params[1]"); - y += gen_uni_skip (t2->args[0]->type, cur_name, vars, 0, fun); - cur_name[L] = 0; - return 0; - case NODE_TYPE_VAR_TYPE: - printf (" if (ODDP(%s)) { %s }\n", cur_name, fail); - i = ((struct tl_tree_var_type *)t)->var_num; - if (!vars[i]) { - printf (" struct paramed_type *var%d = %s; assert (var%d);\n", i, cur_name, i); - vars[i] = 1; - } else if (vars[i] == 1) { - printf (" if (compare_types (var%d, %s) < 0) { %s }\n", i, cur_name, fail); - } else { - assert (0); - return -1; - } - return l; - case NODE_TYPE_VAR_NUM: - printf (" if (EVENP(%s)) { %s }\n", cur_name, fail); - i = ((struct tl_tree_var_num *)t)->var_num; - j = ((struct tl_tree_var_num *)t)->dif; - if (!vars[i]) { - printf (" struct paramed_type *var%d = ((void *)%s) + %d; assert (var%d);\n", i, cur_name, 2 * j, i); - vars[i] = 2; - } else if (vars[i] == 2) { - printf (" if (var%d != ((void *)%s) + %d) { %s }\n", i, cur_name, 2 * j, fail); - } else { - assert (0); - return -1; - } - return 0; - default: - assert (0); - return -1; - } -} - -void print_offset (int len) { - int i; - for (i = 0; i < len; i++) { printf (" "); } -} - -int gen_create (struct tl_tree *t, int *vars, int offset) { - int x = TL_TREE_METHODS (t)->type (t); - int i; - struct tl_tree_type *t1; - struct tl_tree_array *t2; - switch (x) { - case NODE_TYPE_TYPE: - print_offset (offset); - printf ("&(struct paramed_type){\n"); - print_offset (offset + 2); - t1 = (void *)t; - if (t1->self.flags & FLAG_BARE) { - printf (".type = &(struct tl_type_descr) {.name = 0x%08x, .id = \"Bare_%s\", .params_num = %d, .params_types = %lld},\n", ~t1->type->name, t1->type->id, t1->type->arity, t1->type->params_types); - } else { - printf (".type = &(struct tl_type_descr) {.name = 0x%08x, .id = \"%s\", .params_num = %d, .params_types = %lld},\n", t1->type->name, t1->type->id, t1->type->arity, t1->type->params_types); - } - if (t1->children_num) { - print_offset (offset + 2); - printf (".params = (struct paramed_type *[]){\n"); - for (i = 0; i < t1->children_num; i++) { - assert (gen_create (t1->children[i], vars, offset + 4) >= 0); - printf (",\n"); - } - print_offset (offset + 2); - printf ("}\n"); - } else { - print_offset (offset + 2); - printf (".params = 0,\n"); - } - print_offset (offset); - printf ("}"); - return 0; - case NODE_TYPE_NAT_CONST: - print_offset (offset); - printf ("INT2PTR (%d)", (int)var_nat_const_to_int (t)); - return 0; - case NODE_TYPE_ARRAY: - print_offset (offset); - printf ("&(struct paramed_type){\n"); - print_offset (offset + 2); - t2 = (void *)t; - printf (".type = &(struct tl_type_descr) {.name = NAME_ARRAY, .id = \"array\", .params_num = 2, .params_types = 1},\n"); - print_offset (offset + 2); - printf (".params = (struct paramed_type **){\n"); - gen_create (t2->multiplicity, vars, offset + 4); - printf (",\n"); - gen_create (t2->args[0]->type, vars, offset + 4); - printf (",\n"); - print_offset (offset + 2); - printf ("}\n"); - print_offset (offset); - printf ("}"); - return 0; - case NODE_TYPE_VAR_TYPE: - print_offset (offset); - printf ("var%d", ((struct tl_tree_var_type *)t)->var_num); - return 0; - case NODE_TYPE_VAR_NUM: - print_offset (offset); - printf ("((void *)var%d) + %d", ((struct tl_tree_var_type *)t)->var_num, 2 * ((struct tl_tree_var_num *)t)->dif); - return 0; - default: - assert (0); - return -1; - } -} - -int gen_field_skip (struct arg *arg, int *vars, int num) { - assert (arg); - char *offset = " "; - int o = 0; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - o = 2; - } - if (arg->var_num >= 0) { - assert (TL_TREE_METHODS (arg->type)->type (arg->type) == NODE_TYPE_TYPE); - int t = ((struct tl_tree_type *)arg->type)->type->name; - if (t == NAME_VAR_TYPE) { - fprintf (stderr, "Not supported yet\n"); - assert (0); - } else { - assert (t == NAME_VAR_NUM); - if (vars[arg->var_num] == 0) { - printf ("%sif (in_remaining () < 4) { return -1;}\n", offset); - printf ("%sstruct paramed_type *var%d = INT2PTR (fetch_int ());\n", offset, arg->var_num); - vars[arg->var_num] = 2; - } else if (vars[arg->var_num] == 2) { - printf ("%sif (in_remaining () < 4) { return -1;}\n", offset); - printf ("%sif (vars%d != INT2PTR (fetch_int ())) { return -1; }\n", offset, arg->var_num); - } else { - assert (0); - return -1; - } - } - } else { - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - if (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE) { - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (arg->type, vars, 2 + o) >= 0); - printf (";\n"); - int bare = arg->flags & FLAG_BARE; - if (!bare && t == NODE_TYPE_TYPE) { - bare = ((struct tl_tree_type *)arg->type)->self.flags & FLAG_BARE; - } - if (!bare) { - printf ("%sif (skip_type_%s (field%d) < 0) { return -1;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num); - } else { - printf ("%sif (skip_type_bare_%s (field%d) < 0) { return -1;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num); - } - } else { - assert (t == NODE_TYPE_ARRAY); - printf ("%sint multiplicity%d = PTR2INT (\n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->multiplicity, vars, 2 + o) >= 0); - printf ("%s);\n", offset); - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->args[0]->type, vars, 2 + o) >= 0); - printf (";\n"); - printf ("%swhile (multiplicity%d -- > 0) {\n", offset, num); - printf ("%s if (skip_type_%s (field%d) < 0) { return -1;}\n", offset, "any", num); - printf ("%s}\n", offset); - } - } - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -int gen_field_fetch (struct arg *arg, int *vars, int num, int empty) { - assert (arg); - char *offset = " "; - int o = 0; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - o = 2; - } - if (!empty) { - printf("%sif (multiline_output >= 2) { print_offset (); }\n", offset); - } - if (arg->id && strlen (arg->id) && !empty) { - printf ("%sif (!disable_field_names) { eprintf (\" %s :\"); }\n", offset, arg->id); - } - if (arg->var_num >= 0) { - assert (TL_TREE_METHODS (arg->type)->type (arg->type) == NODE_TYPE_TYPE); - int t = ((struct tl_tree_type *)arg->type)->type->name; - if (t == NAME_VAR_TYPE) { - fprintf (stderr, "Not supported yet\n"); - assert (0); - } else { - assert (t == NAME_VAR_NUM); - if (vars[arg->var_num] == 0) { - printf ("%sif (in_remaining () < 4) { return -1;}\n", offset); - printf ("%seprintf (\" %%d\", prefetch_int ());\n", offset); - printf ("%sstruct paramed_type *var%d = INT2PTR (fetch_int ());\n", offset, arg->var_num); - vars[arg->var_num] = 2; - } else if (vars[arg->var_num] == 2) { - printf ("%sif (in_remaining () < 4) { return -1;}\n", offset); - printf ("%seprintf (\" %%d\", prefetch_int ());\n", offset); - printf ("%sif (vars%d != INT2PTR (fetch_int ())) { return -1; }\n", offset, arg->var_num); - } else { - assert (0); - return -1; - } - } - } else { - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - if (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE) { - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (arg->type, vars, 2 + o) >= 0); - printf (";\n"); - int bare = arg->flags & FLAG_BARE; - if (!bare && t == NODE_TYPE_TYPE) { - bare = ((struct tl_tree_type *)arg->type)->self.flags & FLAG_BARE; - } - if (!bare) { - printf ("%sif (fetch_type_%s (field%d) < 0) { return -1;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num); - } else { - printf ("%sif (fetch_type_bare_%s (field%d) < 0) { return -1;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num); - } - } else { - assert (t == NODE_TYPE_ARRAY); - printf ("%sint multiplicity%d = PTR2INT (\n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->multiplicity, vars, 2 + o) >= 0); - printf ("%s);\n", offset); - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->args[0]->type, vars, 2 + o) >= 0); - printf (";\n"); - printf ("%seprintf (\" [\");\n", offset); - printf ("%sif (multiline_output >= 1) { eprintf (\"\\n\"); }\n", offset); - printf ("%sif (multiline_output >= 1) { multiline_offset += multiline_offset_size;}\n", offset); - printf ("%swhile (multiplicity%d -- > 0) {\n", offset, num); - printf ("%s if (multiline_output >= 1) { print_offset (); }\n", offset); - printf ("%s if (fetch_type_%s (field%d) < 0) { return -1;}\n", offset, "any", num); - printf ("%s if (multiline_output >= 1) { eprintf (\"\\n\"); }\n", offset); - printf ("%s}\n", offset); - printf ("%sif (multiline_output >= 1) { multiline_offset -= multiline_offset_size; print_offset ();}\n", offset); - printf ("%seprintf (\" ]\");\n", offset); - } - } - if (!empty) { - printf("%sif (multiline_output >= 2) { eprintf (\"\\n\"); }\n", offset); - } - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -int gen_field_store (struct arg *arg, int *vars, int num, int from_func) { - assert (arg); - char *offset = " "; - int o = 0; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - o = 2; - } - char *fail = from_func ? "0" : "-1"; - char *expect = from_func ? "expect_token_ptr" : "expect_token"; - if (arg->id && strlen (arg->id) > 0) { - printf ("%sif (cur_token_len >= 0 && cur_token_len == %d && !cur_token_quoted && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s local_next_token ();\n", offset); - printf ("%s %s (\":\", 1);\n", offset, expect); - printf ("%s}\n", offset); - } - if (arg->var_num >= 0) { - printf ("%sif (cur_token_len < 0) { return %s; }\n", offset, fail); - assert (TL_TREE_METHODS (arg->type)->type (arg->type) == NODE_TYPE_TYPE); - int t = ((struct tl_tree_type *)arg->type)->type->name; - if (t == NAME_VAR_TYPE) { - fprintf (stderr, "Not supported yet\n"); - assert (0); - } else { - assert (t == NAME_VAR_NUM); - if (vars[arg->var_num] == 0) { - printf ("%sif (!is_int ()) { return %s;}\n", offset, fail); - printf ("%sstruct paramed_type *var%d = INT2PTR (get_int ());\n", offset, arg->var_num); - printf ("%sout_int (get_int ());\n", offset); - printf ("%sassert (var%d);\n", offset, arg->var_num); - printf ("%slocal_next_token ();\n", offset); - vars[arg->var_num] = 2; - } else if (vars[arg->var_num] == 2) { - printf ("%sif (!is_int ()) { return %s;}\n", offset, fail); - printf ("%sif (vars%d != INT2PTR (get_int ())) { return %s; }\n", offset, arg->var_num, fail); - printf ("%sout_int (get_int ());\n", offset); - printf ("%slocal_next_token ();\n", offset); - } else { - assert (0); - return -1; - } - } - } else { - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - if (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE) { - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (arg->type, vars, 2 + o) >= 0); - printf (";\n"); - int bare = arg->flags & FLAG_BARE; - if (!bare && t == NODE_TYPE_TYPE) { - bare = ((struct tl_tree_type *)arg->type)->self.flags & FLAG_BARE; - } - if (!bare) { - printf ("%sif (store_type_%s (field%d) < 0) { return %s;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num, fail); - } else { - printf ("%sif (store_type_bare_%s (field%d) < 0) { return %s;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num, fail); - } - } else { - printf ("%s%s (\"[\", 1);\n", offset, expect); - - assert (t == NODE_TYPE_ARRAY); - printf ("%sint multiplicity%d = PTR2INT (\n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->multiplicity, vars, 2 + o) >= 0); - printf ("%s);\n", offset); - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->args[0]->type, vars, 2 + o) >= 0); - printf (";\n"); - printf ("%swhile (multiplicity%d -- > 0) {\n", offset, num); - printf ("%s if (store_type_%s (field%d) < 0) { return %s;}\n", offset, "any", num, fail); - printf ("%s}\n", offset); - - printf ("%s%s (\"]\", 1);\n", offset, expect); - } - } - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -int gen_field_autocomplete (struct arg *arg, int *vars, int num, int from_func) { - assert (arg); - char *offset = " "; - int o = 0; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - o = 2; - } - char *fail = from_func ? "0" : "-1"; - char *expect = from_func ? "expect_token_ptr_autocomplete" : "expect_token_autocomplete"; - if (arg->id && strlen (arg->id) > 0) { - printf ("%sif (cur_token_len == -3 && cur_token_real_len <= %d && !cur_token_quoted && !memcmp (cur_token, \"%s\", cur_token_real_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s set_autocomplete_string (\"%s\");\n", offset, arg->id); - printf ("%s return %s;\n", offset, fail); - printf ("%s}\n", offset); - - printf ("%sif (cur_token_len >= 0 && cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s local_next_token ();\n", offset); - printf ("%s %s (\":\", 1);\n", offset, expect); - printf ("%s}\n", offset); - } - if (arg->var_num >= 0) { - printf ("%sif (cur_token_len < 0) { return %s; }\n", offset, fail); - assert (TL_TREE_METHODS (arg->type)->type (arg->type) == NODE_TYPE_TYPE); - int t = ((struct tl_tree_type *)arg->type)->type->name; - if (t == NAME_VAR_TYPE) { - fprintf (stderr, "Not supported yet\n"); - assert (0); - } else { - assert (t == NAME_VAR_NUM); - if (vars[arg->var_num] == 0) { - printf ("%sif (!is_int ()) { return %s;}\n", offset, fail); - printf ("%sstruct paramed_type *var%d = INT2PTR (get_int ());\n", offset, arg->var_num); - printf ("%sassert (var%d);\n", offset, arg->var_num); - printf ("%slocal_next_token ();\n", offset); - vars[arg->var_num] = 2; - } else if (vars[arg->var_num] == 2) { - printf ("%sif (!is_int ()) { return %s;}\n", offset, fail); - printf ("%sif (vars%d != INT2PTR (get_int ())) { return %s; }\n", offset, arg->var_num, fail); - printf ("%slocal_next_token ();\n", offset); - } else { - assert (0); - return -1; - } - } - } else { - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - if (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE) { - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (arg->type, vars, 2 + o) >= 0); - printf (";\n"); - int bare = arg->flags & FLAG_BARE; - if (!bare && t == NODE_TYPE_TYPE) { - bare = ((struct tl_tree_type *)arg->type)->self.flags & FLAG_BARE; - } - if (!bare) { - printf ("%sif (autocomplete_type_%s (field%d) < 0) { return %s;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num, fail); - } else { - printf ("%sif (autocomplete_type_bare_%s (field%d) < 0) { return %s;}\n", offset, t == NODE_TYPE_VAR_TYPE ? "any" : ((struct tl_tree_type *)arg->type)->type->print_id, num, fail); - } - } else { - printf ("%s%s (\"[\", 1);\n", offset, expect); - - assert (t == NODE_TYPE_ARRAY); - printf ("%sint multiplicity%d = PTR2INT (\n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->multiplicity, vars, 2 + o) >= 0); - printf ("%s);\n", offset); - printf ("%sstruct paramed_type *field%d = \n", offset, num); - assert (gen_create (((struct tl_tree_array *)arg->type)->args[0]->type, vars, 2 + o) >= 0); - printf (";\n"); - printf ("%swhile (multiplicity%d -- > 0) {\n", offset, num); - printf ("%s if (autocomplete_type_%s (field%d) < 0) { return %s;}\n", offset, "any", num, fail); - printf ("%s}\n", offset); - - printf ("%s%s (\"]\", 1);\n", offset, expect); - } - } - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -int gen_field_autocomplete_excl (struct arg *arg, int *vars, int num, int from_func) { - assert (arg); - assert (arg->var_num < 0); - char *offset = " "; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - } - char *fail = from_func ? "0" : "-1"; - char *expect = from_func ? "expect_token_ptr_autocomplete" : "expect_token_autocomplete"; - if (arg->id && strlen (arg->id) > 0) { - printf ("%sif (cur_token_len == -3 && cur_token_real_len <= %d && !cur_token_quoted && !memcmp (cur_token, \"%s\", cur_token_real_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s set_autocomplete_string (\"%s\");\n", offset, arg->id); - printf ("%s return %s;\n", offset, fail); - printf ("%s}\n", offset); - - printf ("%sif (cur_token_len >= 0 && cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s local_next_token ();\n", offset); - printf ("%s %s (\":\", 1);\n", offset, expect); - printf ("%s}\n", offset); - } - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - assert (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE); - printf ("%sstruct paramed_type *field%d = autocomplete_function_any ();\n", offset, num); - printf ("%sif (!field%d) { return 0; }\n", offset, num); - printf ("%sadd_var_to_be_freed (field%d);\n", offset, num); - static char s[20]; - sprintf (s, "field%d", num); - gen_uni_skip (arg->type, s, vars, 1, 1); - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -int gen_field_store_excl (struct arg *arg, int *vars, int num, int from_func) { - assert (arg); - assert (arg->var_num < 0); - char *offset = " "; - if (arg->exist_var_num >= 0) { - printf (" if (PTR2INT (var%d) & (1 << %d)) {\n", arg->exist_var_num, arg->exist_var_bit); - offset = " "; - } - char *expect = from_func ? "expect_token_ptr" : "expect_token"; - if (arg->id && strlen (arg->id) > 0) { - printf ("%sif (cur_token_len >= 0 && cur_token_len == %d && !cur_token_quoted && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", offset, (int)(strlen (arg->id)), arg->id); - printf ("%s local_next_token ();\n", offset); - printf ("%s %s (\":\", 1);\n", offset, expect); - printf ("%s}\n", offset); - } - int t = TL_TREE_METHODS (arg->type)->type (arg->type); - assert (t == NODE_TYPE_TYPE || t == NODE_TYPE_VAR_TYPE); - printf ("%sstruct paramed_type *field%d = store_function_any ();\n", offset, num); - printf ("%sif (!field%d) { return 0; }\n", offset, num); - static char s[20]; - sprintf (s, "field%d", num); - gen_uni_skip (arg->type, s, vars, 1, 1); - if (arg->exist_var_num >= 0) { - printf (" }\n"); - } - return 0; -} - -void gen_constructor_skip (struct tl_combinator *c) { - printf ("int skip_constructor_%s (struct paramed_type *T) {\n", c->print_id); - int i; - for (i = 0; i < c->args_num; i++) if (c->args[i]->flags & FLAG_EXCL) { - printf (" return -1;\n"); - printf ("}\n"); - return; - } - static char s[10000]; - sprintf (s, "T"); - - int *vars = malloc0 (c->var_num * 4);; - gen_uni_skip (c->result, s, vars, 1, 0); - - if (c->name == NAME_INT) { - printf (" if (in_remaining () < 4) { return -1;}\n"); - printf (" fetch_int ();\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_LONG) { - printf (" if (in_remaining () < 8) { return -1;}\n"); - printf (" fetch_long ();\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_STRING) { - printf (" int l = prefetch_strlen ();\n"); - printf (" if (l < 0) { return -1;}\n"); - printf (" fetch_str (l);\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_DOUBLE) { - printf (" if (in_remaining () < 8) { return -1;}\n"); - printf (" fetch_double ();\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } - - for (i = 0; i < c->args_num; i++) if (!(c->args[i]->flags & FLAG_OPT_VAR)) { - assert (gen_field_skip (c->args[i], vars, i + 1) >= 0); - } - free (vars); - printf (" return 0;\n"); - printf ("}\n"); -} - -void gen_constructor_fetch (struct tl_combinator *c) { - printf ("int fetch_constructor_%s (struct paramed_type *T) {\n", c->print_id); - int i; - for (i = 0; i < c->args_num; i++) if (c->args[i]->flags & FLAG_EXCL) { - printf (" return -1;\n"); - printf ("}\n"); - return; - } - static char s[10000]; - sprintf (s, "T"); - - int *vars = malloc0 (c->var_num * 4);; - gen_uni_skip (c->result, s, vars, 1, 0); - - if (c->name == NAME_INT) { - printf (" if (in_remaining () < 4) { return -1;}\n"); - printf (" eprintf (\" %%d\", fetch_int ());\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_LONG) { - printf (" if (in_remaining () < 8) { return -1;}\n"); - printf (" eprintf (\" %%lld\", fetch_long ());\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_STRING) { - printf (" static char buf[1 << 22];\n"); - printf (" int l = prefetch_strlen ();\n"); - printf (" if (l < 0 || (l >= (1 << 22) - 2)) { return -1; }\n"); - printf (" memcpy (buf, fetch_str (l), l);\n"); - printf (" buf[l] = 0;\n"); - printf (" print_escaped_string (buf, l);\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_DOUBLE) { - printf (" if (in_remaining () < 8) { return -1;}\n"); - printf (" eprintf (\" %%lf\", fetch_double ());\n"); - printf (" return 0;\n"); - printf ("}\n"); - return; - } - - assert (c->result->methods->type (c->result) == NODE_TYPE_TYPE); - int empty = is_empty (((struct tl_tree_type *)c->result)->type); - if (!empty) { - printf (" eprintf (\" %s\");\n", c->id); - printf (" if (multiline_output >= 2) { eprintf (\"\\n\"); }\n"); - } - - - for (i = 0; i < c->args_num; i++) if (!(c->args[i]->flags & FLAG_OPT_VAR)) { - assert (gen_field_fetch (c->args[i], vars, i + 1, empty) >= 0); - } - free (vars); - printf (" return 0;\n"); - printf ("}\n"); -} - -void gen_constructor_store (struct tl_combinator *c) { - printf ("int store_constructor_%s (struct paramed_type *T) {\n", c->print_id); - int i; - for (i = 0; i < c->args_num; i++) if (c->args[i]->flags & FLAG_EXCL) { - printf (" return -1;\n"); - printf ("}\n"); - return; - } - static char s[10000]; - sprintf (s, "T"); - - int *vars = malloc0 (c->var_num * 4);; - assert (c->var_num <= 10); - gen_uni_skip (c->result, s, vars, 1, 0); - - if (c->name == NAME_INT) { - printf (" if (is_int ()) {\n"); - printf (" out_int (get_int ());\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_LONG) { - printf (" if (is_int ()) {\n"); - printf (" out_long (get_int ());\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_STRING) { - printf (" if (cur_token_len >= 0) {\n"); - printf (" out_cstring (cur_token, cur_token_len);\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_DOUBLE) { - printf (" if (is_double ()) {\n"); - printf (" out_double (get_double());\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } - - for (i = 0; i < c->args_num; i++) if (!(c->args[i]->flags & FLAG_OPT_VAR)) { - assert (gen_field_store (c->args[i], vars, i + 1, 0) >= 0); - } - - free (vars); - printf (" return 0;\n"); - printf ("}\n"); -} - -void gen_constructor_autocomplete (struct tl_combinator *c) { - printf ("int autocomplete_constructor_%s (struct paramed_type *T) {\n", c->print_id); - int i; - for (i = 0; i < c->args_num; i++) if (c->args[i]->flags & FLAG_EXCL) { - printf (" return -1;\n"); - printf ("}\n"); - return; - } - static char s[10000]; - sprintf (s, "T"); - - int *vars = malloc0 (c->var_num * 4);; - assert (c->var_num <= 10); - gen_uni_skip (c->result, s, vars, 1, 0); - - if (c->name == NAME_INT) { - printf (" if (is_int ()) {\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_LONG) { - printf (" if (is_int ()) {\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_STRING) { - printf (" if (cur_token_len >= 0) {\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } else if (c->name == NAME_DOUBLE) { - printf (" if (is_double ()) {\n"); - printf (" local_next_token ();\n"); - printf (" return 0;\n"); - printf (" } else {\n"); - printf (" return -1;\n"); - printf (" }\n"); - printf ("}\n"); - return; - } - - for (i = 0; i < c->args_num; i++) if (!(c->args[i]->flags & FLAG_OPT_VAR)) { - assert (gen_field_autocomplete (c->args[i], vars, i + 1, 0) >= 0); - } - - free (vars); - printf (" return 0;\n"); - printf ("}\n"); -} - -void gen_type_skip (struct tl_type *t) { - printf ("int skip_type_%s (struct paramed_type *T) {\n", t->print_id); - printf (" if (in_remaining () < 4) { return -1;}\n"); - printf (" int magic = fetch_int ();\n"); - printf (" switch (magic) {\n"); - int i; - for (i = 0; i < t->constructors_num; i++) { - printf (" case 0x%08x: return skip_constructor_%s (T);\n", t->constructors[i]->name, t->constructors[i]->print_id); - } - printf (" default: return -1;\n"); - printf (" }\n"); - printf ("}\n"); - printf ("int skip_type_bare_%s (struct paramed_type *T) {\n", t->print_id); - if (t->constructors_num > 1) { - printf (" int *save_in_ptr = in_ptr;\n"); - for (i = 0; i < t->constructors_num; i++) { - printf (" if (skip_constructor_%s (T) >= 0) { return 0; }\n", t->constructors[i]->print_id); - printf (" in_ptr = save_in_ptr;\n"); - } - } else { - for (i = 0; i < t->constructors_num; i++) { - printf (" if (skip_constructor_%s (T) >= 0) { return 0; }\n", t->constructors[i]->print_id); - } - } - printf (" return -1;\n"); - printf ("}\n"); -} - -void gen_type_fetch (struct tl_type *t) { - int empty = is_empty (t);; - printf ("int fetch_type_%s (struct paramed_type *T) {\n", t->print_id); - printf (" if (in_remaining () < 4) { return -1;}\n"); - if (!empty) { - printf (" if (multiline_output >= 2) { multiline_offset += multiline_offset_size; }\n"); - printf (" eprintf (\" (\");\n"); - } - printf (" int magic = fetch_int ();\n"); - printf (" int res = -1;\n"); - printf (" switch (magic) {\n"); - int i; - for (i = 0; i < t->constructors_num; i++) { - printf (" case 0x%08x: res = fetch_constructor_%s (T); break;\n", t->constructors[i]->name, t->constructors[i]->print_id); - } - printf (" default: return -1;\n"); - printf (" }\n"); - if (!empty) { - printf (" if (res >= 0) {\n"); - printf (" if (multiline_output >= 2) { multiline_offset -= multiline_offset_size; print_offset (); }\n"); - printf (" eprintf (\" )\");\n"); - //printf (" if (multiline_output >= 2) { printf (\"\\n\"); }\n"); - printf (" }\n"); - } - printf (" return res;\n"); - printf ("}\n"); - printf ("int fetch_type_bare_%s (struct paramed_type *T) {\n", t->print_id); - if (t->constructors_num > 1) { - printf (" int *save_in_ptr = in_ptr;\n"); - - if (!empty) { - printf (" if (multiline_output >= 2) { multiline_offset += multiline_offset_size; }\n"); - } - for (i = 0; i < t->constructors_num; i++) { - printf (" if (skip_constructor_%s (T) >= 0) { in_ptr = save_in_ptr; %sassert (!fetch_constructor_%s (T)); %sreturn 0; }\n", t->constructors[i]->print_id, empty ? "" : "eprintf (\" (\"); ", t->constructors[i]->print_id , empty ? "" : "if (multiline_output >= 2) { multiline_offset -= multiline_offset_size; print_offset (); } eprintf (\" )\");"); - printf (" in_ptr = save_in_ptr;\n"); - } - } else { - for (i = 0; i < t->constructors_num; i++) { - if (!empty) { - printf (" if (multiline_output >= 2) { multiline_offset += multiline_offset_size; }\n"); - printf (" eprintf (\" (\");\n"); - } - printf (" if (fetch_constructor_%s (T) >= 0) { %sreturn 0; }\n", t->constructors[i]->print_id, empty ? "" : "if (multiline_output >= 2) { multiline_offset -= multiline_offset_size; print_offset (); } eprintf (\" )\");" ); - } - } - printf (" return -1;\n"); - printf ("}\n"); -} - -void gen_type_store (struct tl_type *t) { - int empty = is_empty (t);; - int k = 0; - for (k = 0; k < 2; k++) { - printf ("int store_type_%s%s (struct paramed_type *T) {\n", k == 0 ? "" : "bare_", t->print_id); - if (empty) { - printf (" if (store_constructor_%s (T) < 0) { return -1; }\n", t->constructors[0]->print_id); - printf (" return 0;\n"); - printf ("}\n"); - } else { - printf (" expect_token (\"(\", 1);\n"); - printf (" if (cur_token_len < 0) { return -1; }\n"); - printf (" if (cur_token_len < 0) { return -1; }\n"); - int i; - for (i = 0; i < t->constructors_num; i++) { - printf (" if (cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", (int)strlen (t->constructors[i]->id), t->constructors[i]->id); - if (!k) { - printf (" out_int (0x%08x);\n", t->constructors[i]->name); - } - printf (" local_next_token ();\n"); - printf (" if (store_constructor_%s (T) < 0) { return -1; }\n", t->constructors[i]->print_id); - printf (" expect_token (\")\", 1);\n"); - printf (" return 0;\n"); - printf (" }\n"); - } - /*if (t->constructors_num == 1) { - printf (" if (!force) {\n"); - if (!k) { - printf (" out_int (0x%08x);\n", t->constructors[0]->name); - } - printf (" if (store_constructor_%s (T) < 0) { return -1; }\n", t->constructors[0]->print_id); - printf (" expect_token (\")\", 1);\n"); - printf (" return 0;\n"); - printf (" }\n"); - }*/ - printf (" return -1;\n"); - printf ("}\n"); - } - } -} - -void gen_type_autocomplete (struct tl_type *t) { - int empty = is_empty (t);; - int k = 0; - for (k = 0; k < 2; k++) { - printf ("int autocomplete_type_%s%s (struct paramed_type *T) {\n", k == 0 ? "" : "bare_", t->print_id); - if (empty) { - printf (" if (autocomplete_constructor_%s (T) < 0) { return -1; }\n", t->constructors[0]->print_id); - printf (" return 0;\n"); - printf ("}\n"); - } else { - printf (" expect_token_autocomplete (\"(\", 1);\n"); - printf (" if (cur_token_len == -3) { set_autocomplete_type (do_autocomplete_type_%s); return -1; }\n", t->print_id); - printf (" if (cur_token_len < 0) { return -1; }\n"); - int i; - for (i = 0; i < t->constructors_num; i++) { - printf (" if (cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", (int)strlen (t->constructors[i]->id), t->constructors[i]->id); - printf (" local_next_token ();\n"); - printf (" if (autocomplete_constructor_%s (T) < 0) { return -1; }\n", t->constructors[i]->print_id); - printf (" expect_token_autocomplete (\")\", 1);\n"); - printf (" return 0;\n"); - printf (" }\n"); - } - /*if (t->constructors_num == 1) { - printf (" if (!force) {\n"); - printf (" if (autocomplete_constructor_%s (T) < 0) { return -1; }\n", t->constructors[0]->print_id); - printf (" expect_token_autocomplete (\")\", 1);\n"); - printf (" return 0;\n"); - printf (" }\n"); - }*/ - printf (" return -1;\n"); - printf ("}\n"); - } - } -} - -void gen_function_store (struct tl_combinator *f) { - printf ("struct paramed_type *store_function_%s (void) {\n", f->print_id); - int i; - - int *vars = malloc0 (f->var_num * 4);; - assert (f->var_num <= 10); - - for (i = 0; i < f->args_num; i++) if (!(f->args[i]->flags & FLAG_OPT_VAR)) { - if (f->args[i]->flags & FLAG_EXCL) { - assert (gen_field_store_excl (f->args[i], vars, i + 1, 1) >= 0); - } else { - assert (gen_field_store (f->args[i], vars, i + 1, 1) >= 0); - } - } - - - printf (" struct paramed_type *R = \n"); - assert (gen_create (f->result, vars, 2) >= 0); - printf (";\n"); - - free (vars); - printf (" return paramed_type_dup (R);\n"); - printf ("}\n"); -} - -void gen_function_autocomplete (struct tl_combinator *f) { - printf ("struct paramed_type *autocomplete_function_%s (void) {\n", f->print_id); - int i; - - int *vars = malloc0 (f->var_num * 4);; - assert (f->var_num <= 10); - - for (i = 0; i < f->args_num; i++) if (!(f->args[i]->flags & FLAG_OPT_VAR)) { - if (f->args[i]->flags & FLAG_EXCL) { - assert (gen_field_autocomplete_excl (f->args[i], vars, i + 1, 1) >= 0); - } else { - assert (gen_field_autocomplete (f->args[i], vars, i + 1, 1) >= 0); - } - } - - printf (" struct paramed_type *R = \n"); - assert (gen_create (f->result, vars, 2) >= 0); - printf (";\n"); - - free (vars); - printf (" return paramed_type_dup (R);\n"); - printf ("}\n"); -} - -void gen_type_do_autocomplete (struct tl_type *t) { - printf ("int do_autocomplete_type_%s (const char *text, int text_len, int index, char **R) {\n", t->print_id); - printf (" index ++;\n"); - int i; - for (i = 0; i < t->constructors_num; i++) { - printf (" if (index == %d) { if (!strncmp (text, \"%s\", text_len)) { *R = tstrdup (\"%s\"); return index; } else { index ++; }}\n", i, t->constructors[i]->id, t->constructors[i]->id); - } - printf (" *R = 0;\n"); - printf (" return 0;\n"); - printf ("}\n"); -} - -struct tl_tree *read_num_var (int *var_num) { - struct tl_tree_var_num *T = malloc0 (sizeof (*T)); - T->self.flags = 0; - T->self.methods = &tl_pvar_num_methods;; - T->dif = get_int (); - T->var_num = get_int (); - - if (T->var_num >= *var_num) { - *var_num = T->var_num + 1; - } - assert (!(T->self.flags & FLAG_NOVAR)); - return (void *)T; -} - -struct tl_tree *read_type_var (int *var_num) { - struct tl_tree_var_type *T = malloc0 (sizeof (*T)); - T->self.methods = &tl_pvar_type_methods; - T->var_num = get_int (); - T->self.flags = get_int (); - if (T->var_num >= *var_num) { - *var_num = T->var_num + 1; - } - assert (!(T->self.flags & (FLAG_NOVAR | FLAG_BARE))); - return (void *)T; -} - -struct tl_tree *read_array (int *var_num) { - struct tl_tree_array *T = malloc0 (sizeof (*T)); - T->self.methods = &tl_parray_methods; - T->self.flags = 0; - T->multiplicity = read_nat_expr (var_num); - assert (T->multiplicity); - - T->args_num = get_int (); - assert (T->args_num >= 0 && T->args_num <= 1000); - T->args = malloc0 (sizeof (void *) * T->args_num); - - assert (read_args_list (T->args, T->args_num, var_num) >= 0); - T->self.flags |= FLAG_NOVAR; - int i; - for (i = 0; i < T->args_num; i++) { - if (!(T->args[i]->flags & FLAG_NOVAR)) { - T->self.flags &= ~FLAG_NOVAR; - } - } - return (void *)T; -} - -struct tl_tree *read_type (int *var_num) { - struct tl_tree_type *T = malloc0 (sizeof (*T)); - T->self.methods = &tl_ptype_methods; - - T->type = tl_type_get_by_name (get_int ()); - assert (T->type); - T->self.flags = get_int (); - T->children_num = get_int (); - assert (T->type->arity == T->children_num); - T->children = malloc0 (sizeof (void *) * T->children_num); - int i; - T->self.flags |= FLAG_NOVAR; - for (i = 0; i < T->children_num; i++) { - int t = get_int (); - if (t == (int)TLS_EXPR_NAT) { - assert ((T->type->params_types & (1 << i))); - T->children[i] = read_nat_expr (var_num); - } else if (t == (int)TLS_EXPR_TYPE) { - assert (!(T->type->params_types & (1 << i))); - T->children[i] = read_type_expr (var_num); - } else { - assert (0); - } - if (!TL_IS_NAT_VAR (T->children[i]) && !(T->children[i]->flags & FLAG_NOVAR)) { - T->self.flags &= ~FLAG_NOVAR; - } - } - return (void *)T; -} - -struct tl_tree *read_tree (int *var_num) { - int x = get_int (); - if (verbosity >= 2) { - fprintf (stderr, "read_tree: constructor = 0x%08x\n", x); - } - switch (x) { - case TLS_TREE_NAT_CONST: - return read_num_const (var_num); - case TLS_TREE_NAT_VAR: - return read_num_var (var_num); - case TLS_TREE_TYPE_VAR: - return read_type_var (var_num); - case TLS_TREE_TYPE: - return read_type (var_num); - case TLS_TREE_ARRAY: - return read_array (var_num); - default: - if (verbosity) { - fprintf (stderr, "x = %d\n", x); - } - assert (0); - return 0; - } -} - -struct tl_tree *read_type_expr (int *var_num) { - int x = get_int (); - if (verbosity >= 2) { - fprintf (stderr, "read_type_expr: constructor = 0x%08x\n", x); - } - switch (x) { - case TLS_TYPE_VAR: - return read_type_var (var_num); - case TLS_TYPE_EXPR: - return read_type (var_num); - case TLS_ARRAY: - return read_array (var_num); - default: - if (verbosity) { - fprintf (stderr, "x = %d\n", x); - } - assert (0); - return 0; - } -} - -struct tl_tree *read_nat_expr (int *var_num) { - int x = get_int (); - if (verbosity >= 2) { - fprintf (stderr, "read_nat_expr: constructor = 0x%08x\n", x); - } - switch (x) { - case TLS_NAT_CONST: - return read_num_const (var_num); - case TLS_NAT_VAR: - return read_num_var (var_num); - default: - if (verbosity) { - fprintf (stderr, "x = %d\n", x); - } - assert (0); - return 0; - } -} - -struct tl_tree *read_expr (int *var_num) { - int x = get_int (); - if (verbosity >= 2) { - fprintf (stderr, "read_nat_expr: constructor = 0x%08x\n", x); - } - switch (x) { - case TLS_EXPR_NAT: - return read_nat_expr (var_num); - case TLS_EXPR_TYPE: - return read_type_expr (var_num); - default: - if (verbosity) { - fprintf (stderr, "x = %d\n", x); - } - assert (0); - return 0; - } -} - -int read_args_list (struct arg **args, int args_num, int *var_num) { - int i; - for (i = 0; i < args_num; i++) { - args[i] = malloc0 (sizeof (struct arg)); - args[i]->exist_var_num = -1; - args[i]->exist_var_bit = 0; - assert (get_int () == TLS_ARG_V2); - args[i]->id = get_string (); - args[i]->flags = get_int (); - - if (args[i]->flags & 2) { - args[i]->flags &= ~2; - args[i]->flags |= (1 << 20); - } - if (args[i]->flags & 4) { - args[i]->flags &= ~4; - args[i]->var_num = get_int (); - } else { - args[i]->var_num = -1; - } - - int x = args[i]->flags & 6; - args[i]->flags &= ~6; - if (x & 2) { args[i]->flags |= 4; } - if (x & 4) { args[i]->flags |= 2; } - - if (args[i]->var_num >= *var_num) { - *var_num = args[i]->var_num + 1; - } - if (args[i]->flags & FLAG_OPT_FIELD) { - args[i]->exist_var_num = get_int (); - args[i]->exist_var_bit = get_int (); - } - args[i]->type = read_type_expr (var_num); - assert (args[i]->type); - - if (args[i]->var_num < 0 && args[i]->exist_var_num < 0 && (TL_IS_NAT_VAR(args[i]->type) || (args[i]->type->flags & FLAG_NOVAR))) { - args[i]->flags |= FLAG_NOVAR; - } - } - return 1; -} - -int read_combinator_args_list (struct tl_combinator *c) { - c->args_num = get_int (); - if (verbosity >= 2) { - fprintf (stderr, "c->id = %s, c->args_num = %d\n", c->id, c->args_num); - } - assert (c->args_num >= 0 && c->args_num <= 1000); - c->args = malloc0 (sizeof (void *) * c->args_num); - c->var_num = 0; - return read_args_list (c->args, c->args_num, &c->var_num); -} - -int read_combinator_right (struct tl_combinator *c) { - assert (get_int () == TLS_COMBINATOR_RIGHT_V2); - c->result = read_type_expr (&c->var_num); - assert (c->result); - return 1; -} - -int read_combinator_left (struct tl_combinator *c) { - int x = get_int (); - - if (x == (int)TLS_COMBINATOR_LEFT_BUILTIN) { - c->args_num = 0; - c->var_num = 0; - c->args = 0; - return 1; - } else if (x == TLS_COMBINATOR_LEFT) { - return read_combinator_args_list (c); - } else { - assert (0); - return -1; - } -} - -char *gen_print_id (const char *id) { - static char s[1000]; - char *ptr = s; - int first = 1; - while (*id) { - if (*id == '.') { - *(ptr ++) = '_'; - } else if (*id >= 'A' && *id <= 'Z') { - if (!first && *(ptr - 1) != '_') { - *(ptr ++) = '_'; - } - *(ptr ++) = *id - 'A' + 'a'; - } else { - *(ptr ++) = *id; - } - id ++; - first = 0; - } - *ptr = 0; - return s; -} - -struct tl_combinator *read_combinators (int v) { - struct tl_combinator *c = malloc0 (sizeof (*c)); - c->name = get_int (); - c->id = get_string (); - c->print_id = strdup (gen_print_id (c->id)); - assert (c->print_id); - //char *s = c->id; - //while (*s) { if (*s == '.') { *s = '_'; } ; s ++;} - int x = get_int (); - struct tl_type *t = tl_type_get_by_name (x); - assert (t || (!x && v == 3)); - - if (v == 2) { - assert (t->extra < t->constructors_num); - t->constructors[t->extra ++] = c; - c->is_fun = 0; - } else { - assert (v == 3); - tl_function_insert_by_name (c); - c->is_fun = 1; - } - assert (read_combinator_left (c) >= 0); - assert (read_combinator_right (c) >= 0); - return c; -} - -struct tl_type *read_types (void) { - struct tl_type *t = malloc0 (sizeof (*t)); - t->name = get_int (); - t->id = get_string (); - t->print_id = strdup (gen_print_id (t->id)); - assert (t->print_id); - - t->constructors_num = get_int (); - assert (t->constructors_num >= 0 && t->constructors_num <= 1000); - - t->constructors = malloc0 (sizeof (void *) * t->constructors_num); - t->flags = get_int (); - t->arity = get_int (); - t->params_types = get_long (); // params_types - t->extra = 0; - tl_type_insert_by_name (t); - return t; -} - - - -int parse_tlo_file (void) { - buf_end = buf_ptr + (buf_size / 4); - assert (get_int () == TLS_SCHEMA_V2); - - get_int (); // version - get_int (); // date - - tn = 0; - fn = 0; - cn = 0; - int i; - - tn = get_int (); - assert (tn >= 0 && tn < 10000); - tps = malloc0 (sizeof (void *) * tn); - - if (verbosity >= 2) { - fprintf (stderr, "Found %d types\n", tn); - } - - for (i = 0; i < tn; i++) { - assert (get_int () == TLS_TYPE); - tps[i] = read_types (); - assert (tps[i]); - } - - cn = get_int (); - assert (cn >= 0); - - if (verbosity >= 2) { - fprintf (stderr, "Found %d constructors\n", cn); - } - - for (i = 0; i < cn; i++) { - assert (get_int () == TLS_COMBINATOR); - assert (read_combinators (2)); - } - - fn = get_int (); - assert (fn >= 0 && fn < 10000); - - fns = malloc0 (sizeof (void *) * fn); - - if (verbosity >= 2) { - fprintf (stderr, "Found %d functions\n", fn); - } - - for (i = 0; i < fn; i++) { - assert (get_int () == TLS_COMBINATOR); - fns[i] = read_combinators (3); - assert (fns[i]); - } - - assert (buf_ptr == buf_end); - - - int j; - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type")) { - tps[i]->name = 0; - for (j = 0; j < tps[i]->constructors_num; j ++) { - tps[i]->name ^= tps[i]->constructors[j]->name; - } - } - - if (!header) { - printf ("#include \"auto.h\"\n"); - printf ("#include \n"); - - - printf ("#include \"auto-static.c\"\n"); - for (i = 0; i < tn; i++) { - for (j = 0; j < tps[i]->constructors_num; j ++) { - gen_constructor_skip (tps[i]->constructors[j]); - if (!skip_only) { - gen_constructor_store (tps[i]->constructors[j]); - gen_constructor_fetch (tps[i]->constructors[j]); - gen_constructor_autocomplete (tps[i]->constructors[j]); - } - } - } - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type")) { - gen_type_skip (tps[i]); - if (!skip_only) { - gen_type_store (tps[i]); - gen_type_fetch (tps[i]); - gen_type_autocomplete (tps[i]); - gen_type_do_autocomplete (tps[i]); - } - } - if (!skip_only) { - for (i = 0; i < fn; i++) { - gen_function_store (fns[i]); - gen_function_autocomplete (fns[i]); - } - } - printf ("int skip_type_any (struct paramed_type *T) {\n"); - printf (" switch (T->type->name) {\n"); - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type") && tps[i]->name) { - printf (" case 0x%08x: return skip_type_%s (T);\n", tps[i]->name, tps[i]->print_id); - printf (" case 0x%08x: return skip_type_bare_%s (T);\n", ~tps[i]->name, tps[i]->print_id); - } - printf (" default: return -1; }\n"); - printf ("}\n"); - if (!skip_only) { - printf ("int store_type_any (struct paramed_type *T) {\n"); - printf (" switch (T->type->name) {\n"); - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type") && tps[i]->name) { - printf (" case 0x%08x: return store_type_%s (T);\n", tps[i]->name, tps[i]->print_id); - printf (" case 0x%08x: return store_type_bare_%s (T);\n", ~tps[i]->name, tps[i]->print_id); - } - printf (" default: return -1; }\n"); - printf ("}\n"); - printf ("int fetch_type_any (struct paramed_type *T) {\n"); - printf (" switch (T->type->name) {\n"); - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type") && tps[i]->name) { - printf (" case 0x%08x: return fetch_type_%s (T);\n", tps[i]->name, tps[i]->print_id); - printf (" case 0x%08x: return fetch_type_bare_%s (T);\n", ~tps[i]->name, tps[i]->print_id); - } - printf (" default: return -1; }\n"); - printf ("}\n"); - printf ("int autocomplete_type_any (struct paramed_type *T) {\n"); - printf (" switch (T->type->name) {\n"); - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type") && tps[i]->name) { - printf (" case 0x%08x: return autocomplete_type_%s (T);\n", tps[i]->name, tps[i]->print_id); - printf (" case 0x%08x: return autocomplete_type_bare_%s (T);\n", ~tps[i]->name, tps[i]->print_id); - } - printf (" default: return -1; }\n"); - printf ("}\n"); - printf ("struct paramed_type *store_function_any (void) {\n"); - printf (" if (cur_token_len != 1 || *cur_token != '(') { return 0; }\n"); - printf (" local_next_token ();\n"); - printf (" if (cur_token_len == 1 || *cur_token == '.') { \n"); - printf (" local_next_token ();\n"); - printf (" if (cur_token_len != 1 || *cur_token != '=') { return 0; }\n"); - printf (" local_next_token ();\n"); - printf (" };\n"); - printf (" if (cur_token_len < 0) { return 0; }\n"); - for (i = 0; i < fn; i++) { - printf (" if (cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", (int)strlen (fns[i]->id), fns[i]->id); - printf (" out_int (0x%08x);\n", fns[i]->name); - printf (" local_next_token ();\n"); - printf (" struct paramed_type *P = store_function_%s ();\n", fns[i]->print_id); - printf (" if (!P) { return 0; }\n"); - printf (" if (cur_token_len != 1 || *cur_token != ')') { return 0; }\n"); - printf (" local_next_token ();\n"); - printf (" return P;\n"); - printf (" }\n"); - } - printf (" return 0;\n"); - printf ("}\n"); - printf ("int do_autocomplete_function (const char *text, int text_len, int index, char **R) {\n"); - printf (" index ++;\n"); - int i; - for (i = 0; i < fn; i++) { - printf (" if (index == %d) { if (!strncmp (text, \"%s\", text_len)) { *R = tstrdup (\"%s\"); return index; } else { index ++; }}\n", i, fns[i]->id, fns[i]->id); - } - printf (" *R = 0;\n"); - printf (" return 0;\n"); - printf ("}\n"); - printf ("struct paramed_type *autocomplete_function_any (void) {\n"); - printf (" expect_token_ptr_autocomplete (\"(\", 1);\n"); - printf (" if (cur_token_len == -3) { set_autocomplete_type (do_autocomplete_function); }\n"); - printf (" if (cur_token_len < 0) { return 0; }\n"); - for (i = 0; i < fn; i++) { - printf (" if (cur_token_len == %d && !memcmp (cur_token, \"%s\", cur_token_len)) {\n", (int)strlen (fns[i]->id), fns[i]->id); - printf (" local_next_token ();\n"); - printf (" struct paramed_type *P = autocomplete_function_%s ();\n", fns[i]->print_id); - printf (" if (!P) { return 0; }\n"); - printf (" expect_token_ptr_autocomplete (\")\", 1);\n"); - printf (" return P;\n"); - printf (" }\n"); - } - printf (" return 0;\n"); - printf ("}\n"); - } - } else { - for (i = 0; i < tn; i++) { - for (j = 0; j < tps[i]->constructors_num; j ++) { - printf ("int skip_constructor_%s (struct paramed_type *T);\n", tps[i]->constructors[j]->print_id); - printf ("int store_constructor_%s (struct paramed_type *T);\n", tps[i]->constructors[j]->print_id); - printf ("int fetch_constructor_%s (struct paramed_type *T);\n", tps[i]->constructors[j]->print_id); - printf ("int autocomplete_constructor_%s (struct paramed_type *T);\n", tps[i]->constructors[j]->print_id); - } - } - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type")) { - printf ("int skip_type_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int skip_type_bare_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int store_type_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int store_type_bare_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int fetch_type_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int fetch_type_bare_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int autocomplete_type_%s (struct paramed_type *T);\n", tps[i]->print_id); - printf ("int do_autocomplete_type_%s (const char *text, int len, int index, char **R);\n", tps[i]->print_id); - printf ("int autocomplete_type_bare_%s (struct paramed_type *T);\n", tps[i]->print_id); - } - for (i = 0; i < fn; i++) { - printf ("struct paramed_type *store_function_%s (void);\n", fns[i]->print_id); - printf ("struct paramed_type *autocomplete_function_%s (void);\n", fns[i]->print_id); - } - printf ("int skip_type_any (struct paramed_type *T);\n"); - printf ("int store_type_any (struct paramed_type *T);\n"); - printf ("int fetch_type_any (struct paramed_type *T);\n"); - printf ("int autocomplete_type_any (struct paramed_type *T);\n"); - printf ("struct paramed_type *store_function_any (void);\n"); - printf ("struct paramed_type *autocomplete_function_any (void);\n"); - - /*for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#') { - printf ("extern struct tl_type tl_type_%s;\n", tps[i]->id); - }*/ - for (i = 0; i < tn; i++) if (tps[i]->id[0] != '#' && strcmp (tps[i]->id, "Type")) { - printf ("static struct tl_type_descr tl_type_%s __attribute__ ((unused));\n", tps[i]->print_id); - printf ("static struct tl_type_descr tl_type_%s = {\n", tps[i]->print_id); - printf (" .name = 0x%08x,\n", tps[i]->name); - printf (" .id = \"%s\"\n,", tps[i]->id); - printf (" .params_num = %d,\n", tps[i]->arity); - printf (" .params_types = %lld\n", tps[i]->params_types); - printf ("};\n"); - printf ("static struct tl_type_descr tl_type_bare_%s __attribute__ ((unused));\n", tps[i]->print_id); - printf ("static struct tl_type_descr tl_type_bare_%s = {\n", tps[i]->print_id); - printf (" .name = 0x%08x,\n", ~tps[i]->name); - printf (" .id = \"Bare_%s\",\n", tps[i]->id); - printf (" .params_num = %d,\n", tps[i]->arity); - printf (" .params_types = %lld\n", tps[i]->params_types); - printf ("};\n"); - } - } - - - return 0; -} - -void usage (void) { - printf ("usage: generate [-v] [-h] \n" - ); - exit (2); -} - -void logprintf (const char *format, ...) __attribute__ ((format (printf, 1, 2))); -void logprintf (const char *format __attribute__ ((unused)), ...) { -} -/* -void hexdump (int *in_ptr, int *in_end) { - int *ptr = in_ptr; - while (ptr < in_end) { printf (" %08x", *(ptr ++)); } - printf ("\n"); -}*/ - -#ifdef HAVE_EXECINFO_H -void print_backtrace (void) { - void *buffer[255]; - const int calls = backtrace (buffer, sizeof (buffer) / sizeof (void *)); - backtrace_symbols_fd (buffer, calls, 1); -} -#else -void print_backtrace (void) { - if (write (1, "No libexec. Backtrace disabled\n", 32) < 0) { - // Sad thing - } -} -#endif - -void sig_segv_handler (int signum __attribute__ ((unused))) { - if (write (1, "SIGSEGV received\n", 18) < 0) { - // Sad thing - } - print_backtrace (); - exit (EXIT_FAILURE); -} - -void sig_abrt_handler (int signum __attribute__ ((unused))) { - if (write (1, "SIGABRT received\n", 18) < 0) { - // Sad thing - } - print_backtrace (); - exit (EXIT_FAILURE); -} - -int main (int argc, char **argv) { - signal (SIGSEGV, sig_segv_handler); - signal (SIGABRT, sig_abrt_handler); - int i; - while ((i = getopt (argc, argv, "vhH")) != -1) { - switch (i) { - case 'h': - usage (); - return 2; - case 'v': - verbosity++; - break; - case 'H': - header ++; - break; - } - } - - if (argc != optind + 1) { - usage (); - } - - int fd = open (argv[optind], O_RDONLY); - if (fd < 0) { - fprintf (stderr, "Can not open file '%s'. Error %m\n", argv[optind]); - exit (1); - } - buf_size = read (fd, buf, (1 << 20)); - if (fd == (1 << 20)) { - fprintf (stderr, "Too big tlo file\n"); - exit (2); - } - return parse_tlo_file (); -} diff --git a/generate.h b/generate.h deleted file mode 100644 index be5bc94..0000000 --- a/generate.h +++ /dev/null @@ -1,171 +0,0 @@ -/* - This file is part of tgl-libary/generate - - Tgl-library/generate is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - Tgl-library/generate is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this tgl-library/generate. If not, see . - - Copyright Vitaly Valtman 2014 - - It is derivative work of VK/KittenPHP-DB-Engine (https://github.com/vk-com/kphp-kdb/) - Copyright 2012-2013 Vkontakte Ltd - 2012-2013 Vitaliy Valtman -*/ - -#ifndef __GENERATE_H__ -#define __GENERATE_H__ - -struct tl_combinator; - -struct tl_type { -// struct tl_type_methods *methods; - char *id; - char *print_id; - unsigned name; - int arity; - int flags; - int constructors_num; - struct tl_combinator **constructors; - long long params_types; - int extra; -}; - -#define NODE_TYPE_TYPE 1 -#define NODE_TYPE_NAT_CONST 2 -#define NODE_TYPE_VAR_TYPE 3 -#define NODE_TYPE_VAR_NUM 4 -#define NODE_TYPE_ARRAY 5 - -#define MAX_COMBINATOR_VARS 64 - -#define NAME_VAR_NUM 0x70659eff -#define NAME_VAR_TYPE 0x2cecf817 -#define NAME_INT 0xa8509bda -#define NAME_LONG 0x22076cba -#define NAME_DOUBLE 0x2210c154 -#define NAME_STRING 0xb5286e24 -#define NAME_VECTOR 0x1cb5c415 -#define NAME_MAYBE_TRUE 0x3f9c8ef8 -#define NAME_MAYBE_FALSE 0x27930a7b -#define NAME_BOOL_FALSE 0xbc799737 -#define NAME_BOOL_TRUE 0x997275b5 - -#define FLAG_OPT_VAR (1 << 17) -#define FLAG_EXCL (1 << 18) -#define FLAG_OPT_FIELD (1 << 20) -#define FLAG_NOVAR (1 << 21) -#define FLAG_BARE 1 -#define FLAGS_MASK ((1 << 16) - 1) -#define FLAG_DEFAULT_CONSTRUCTOR (1 << 25) -#define FLAG_NOCONS (1 << 1) - -extern struct tl_tree_methods tl_nat_const_methods; -extern struct tl_tree_methods tl_nat_const_full_methods; -extern struct tl_tree_methods tl_pnat_const_full_methods; -extern struct tl_tree_methods tl_array_methods; -extern struct tl_tree_methods tl_type_methods; -extern struct tl_tree_methods tl_parray_methods; -extern struct tl_tree_methods tl_ptype_methods; -extern struct tl_tree_methods tl_var_num_methods; -extern struct tl_tree_methods tl_var_type_methods; -extern struct tl_tree_methods tl_pvar_num_methods; -extern struct tl_tree_methods tl_pvar_type_methods; -#define TL_IS_NAT_VAR(x) (((long)x) & 1) -#define TL_TREE_METHODS(x) (TL_IS_NAT_VAR (x) ? &tl_nat_const_methods : ((struct tl_tree *)(x))->methods) - -#define DEC_REF(x) (TL_TREE_METHODS(x)->dec_ref ((void *)x)) -#define INC_REF(x) (TL_TREE_METHODS(x)->inc_ref ((void *)x)) -#define TYPE(x) (TL_TREE_METHODS(x)->type ((void *)x)) - -typedef unsigned long long tl_tree_hash_t; -struct tl_tree; - -struct tl_tree_methods { - int (*type)(struct tl_tree *T); - int (*eq)(struct tl_tree *T, struct tl_tree *U); - void (*inc_ref)(struct tl_tree *T); - void (*dec_ref)(struct tl_tree *T); -}; - -struct tl_tree { - int ref_cnt; - int flags; - //tl_tree_hash_t hash; - struct tl_tree_methods *methods; -}; -/* -struct tl_tree_nat_const { - struct tl_tree self; - int value; -};*/ - -struct tl_tree_type { - struct tl_tree self; - - struct tl_type *type; - int children_num; - struct tl_tree **children; -}; - -struct tl_tree_array { - struct tl_tree self; - - struct tl_tree *multiplicity; - int args_num; - struct arg **args; -}; - -struct tl_tree_var_type { - struct tl_tree self; - - int var_num; -}; - -struct tl_tree_var_num { - struct tl_tree self; - - int var_num; - int dif; -}; - -struct tl_tree_nat_const { - struct tl_tree self; - - long long value; -}; - -struct arg { - char *id; - int var_num; - int flags; - int exist_var_num; - int exist_var_bit; - struct tl_tree *type; -}; - -struct tl_combinator { - //struct tl_combinator_methods *methods; - char *id; - char *print_id; - unsigned name; - int is_fun; - int var_num; - int args_num; - struct arg **args; - struct tl_tree *result; - void **IP; - void **fIP; - int IP_len; - int fIP_len; -}; - -#endif diff --git a/include.h b/include.h deleted file mode 100644 index bf290a1..0000000 --- a/include.h +++ /dev/null @@ -1,24 +0,0 @@ -/* - This file is part of telegram-client. - - Telegram-client is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - Telegram-client is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this telegram-client. If not, see . - - Copyright Vitaly Valtman 2013 -*/ -#ifndef __INCLUDE_H__ -#define __INCLUDE_H__ - -#define UU __attribute__ ((unused)) - -#endif diff --git a/interface.c b/interface.c index 8c7e225..057b0e0 100644 --- a/interface.c +++ b/interface.c @@ -38,7 +38,6 @@ #endif #include -#include "include.h" //#include "queries.h" #include "interface.h" @@ -62,7 +61,7 @@ //#include "mtproto-common.h" -#include "tgl.h" +#include #include "loop.h" #ifndef PATH_MAX @@ -496,7 +495,7 @@ char *get_default_prompt (void) { return buf; } -char *complete_none (const char *text UU, int state UU) { +char *complete_none (const char *text, int state) { return 0; } @@ -1371,7 +1370,7 @@ char *command_generator (const char *text, int state) { } } -char **complete_text (char *text, int start UU, int end UU) { +char **complete_text (char *text, int start, int end) { return (char **) rl_completion_matches (text, command_generator); } @@ -2045,7 +2044,7 @@ struct tgl_update_callback upd_cb = { }; -void interpreter_ex (char *line UU, void *ex) { +void interpreter_ex (char *line, void *ex) { force_end_mode = 1; assert (!in_readline); in_readline = 1; @@ -2279,7 +2278,7 @@ void interpreter_ex (char *line UU, void *ex) { in_readline = 0; } -void interpreter (char *line UU) { +void interpreter (char *line) { interpreter_ex (line, 0); } diff --git a/interface.h b/interface.h index 81fa41b..cc9c64c 100644 --- a/interface.h +++ b/interface.h @@ -18,8 +18,8 @@ */ #ifndef __INTERFACE_H__ #define __INTERFACE_H__ -#include "structures.h" -#include "tgl-layout.h" +#include +#include #define COLOR_RED "\033[0;31m" #define COLOR_REDB "\033[1;31m" diff --git a/loop.c b/loop.c index 65e6335..1c7892e 100644 --- a/loop.c +++ b/loop.c @@ -57,10 +57,10 @@ #include "telegram.h" #include "loop.h" #include "lua-tg.h" -#include "tgl.h" -#include "binlog.h" -#include "net.h" -#include "tgl-timers.h" +#include +#include +#include +#include int verbosity; extern int readline_disabled; @@ -708,6 +708,7 @@ int loop (void) { tgl_set_ev_base (TLS, ev); tgl_set_net_methods (TLS, &tgl_conn_methods); tgl_set_timer_methods (TLS, &tgl_libevent_timers); + assert (TLS->timer_methods); tgl_set_download_directory (TLS, get_downloads_directory ()); tgl_init (TLS); diff --git a/lua-tg.c b/lua-tg.c index f27ccb0..57bb119 100644 --- a/lua-tg.c +++ b/lua-tg.c @@ -24,7 +24,6 @@ #ifdef USE_LUA #include "lua-tg.h" -#include "include.h" #include #include @@ -42,7 +41,7 @@ lua_State *luaState; //#include "interface.h" //#include "auto/constants.h" -#include "tgl.h" +#include #include "interface.h" #include @@ -52,7 +51,7 @@ extern struct tgl_state *TLS; static int have_file; #define my_lua_checkstack(L,x) assert (lua_checkstack (L, x)) -void push_user (tgl_peer_t *P UU); +void push_user (tgl_peer_t *P); void push_peer (tgl_peer_id_t id, tgl_peer_t *P); void lua_add_string_field (const char *name, const char *value) { @@ -96,7 +95,7 @@ void push_tgl_peer_type (int x) { } } -void push_user (tgl_peer_t *P UU) { +void push_user (tgl_peer_t *P) { my_lua_checkstack (luaState, 4); lua_add_string_field ("first_name", P->user.first_name); lua_add_string_field ("last_name", P->user.last_name); @@ -387,7 +386,7 @@ void lua_our_id (int id) { } } -void lua_new_msg (struct tgl_message *M UU) { +void lua_new_msg (struct tgl_message *M) { if (!have_file) { return; } lua_settop (luaState, 0); //lua_checkstack (luaState, 20); diff --git a/lua-tg.h b/lua-tg.h index 65346a6..2db43b8 100644 --- a/lua-tg.h +++ b/lua-tg.h @@ -20,8 +20,7 @@ #define __LUA_TG_H__ #include -#include "lua-tg.h" -#include "tgl.h" +#include void lua_init (const char *file); void lua_new_msg (struct tgl_message *M); diff --git a/main.c b/main.c index 83fa3c1..16e2bf9 100644 --- a/main.c +++ b/main.c @@ -64,13 +64,13 @@ #include "telegram.h" #include "loop.h" #include "interface.h" -#include "tools.h" +#include #ifdef USE_LUA # include "lua-tg.h" #endif -#include "tgl.h" +#include #define PROGNAME "telegram-cli" #define VERSION "0.07" diff --git a/mtproto-client.c b/mtproto-client.c deleted file mode 100644 index e97423e..0000000 --- a/mtproto-client.c +++ /dev/null @@ -1,1462 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Nikolay Durov, Andrey Lopatin 2012-2013 - Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#define _FILE_OFFSET_BITS 64 - -#include -#include -#include -#include -#include -#include -#include -#if defined(__FreeBSD__) || defined(__OpenBSD__) -#include -#endif -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -//#include "telegram.h" -#include "include.h" -#include "queries.h" -//#include "loop.h" -#include "structures.h" -#include "binlog.h" -#include "auto.h" -#include "tgl.h" -#include "mtproto-client.h" -#include "tools.h" -#include "tree.h" -#include "updates.h" - -#if defined(__FreeBSD__) -#define __builtin_bswap32(x) bswap32(x) -#endif - -#if defined(__OpenBSD__) -#define __builtin_bswap32(x) __swap32gen(x) -#endif - -#define sha1 SHA1 - -#include "mtproto-common.h" - -#define MAX_NET_RES (1L << 16) -//extern int log_level; - -#if !defined(HAVE___BUILTIN_BSWAP32) && !defined(__FreeBSD__) && !defined(__OpenBSD__) -static inline unsigned __builtin_bswap32(unsigned x) { - return ((x << 24) & 0xff000000 ) | - ((x << 8) & 0x00ff0000 ) | - ((x >> 8) & 0x0000ff00 ) | - ((x >> 24) & 0x000000ff ); -} -#endif - -//int verbosity; -//static enum tgl_dc_state c_state; -//extern int binlog_enabled; -//extern int disable_auto_accept; -//extern int allow_weak_random; - -static int total_packets_sent; -static long long total_data_sent; - - -static int rpc_execute (struct tgl_state *TLS, struct connection *c, int op, int len); -static int rpc_becomes_ready (struct tgl_state *TLS, struct connection *c); -static int rpc_close (struct tgl_state *TLS, struct connection *c); - -static long long precise_time; - -static double get_utime (int clock_id) { - struct timespec T; - tgl_my_clock_gettime (clock_id, &T); - double res = T.tv_sec + (double) T.tv_nsec * 1e-9; - if (clock_id == CLOCK_REALTIME) { - precise_time = (long long) (res * (1LL << 32)); - } - return res; -} - - -//#define STATS_BUFF_SIZE (64 << 10) -//static int stats_buff_len; -//static char stats_buff[STATS_BUFF_SIZE]; - -#define MAX_RESPONSE_SIZE (1L << 24) - -//static int Response_len; - -/* - * - * STATE MACHINE - * - */ - -#define TG_SERVER_PUBKEY_FILENAME "tg-server.pub" -//static char *rsa_public_key_name; // = TG_SERVER_PUBKEY_FILENAME; -//static RSA *pubKey; -static long long pk_fingerprint; - -static int rsa_load_public_key (struct tgl_state *TLS, const char *public_key_name) { - TLS->pubKey = NULL; - FILE *f = fopen (public_key_name, "r"); - if (f == NULL) { - vlogprintf (E_WARNING, "Couldn't open public key file: %s\n", public_key_name); - return -1; - } - TLS->pubKey = PEM_read_RSAPublicKey (f, NULL, NULL, NULL); - fclose (f); - if (TLS->pubKey == NULL) { - vlogprintf (E_WARNING, "PEM_read_RSAPublicKey returns NULL.\n"); - return -1; - } - - vlogprintf (E_WARNING, "public key '%s' loaded successfully\n", public_key_name); - - return 0; -} - - - - - -/* - * - * UNAUTHORIZED (DH KEY EXCHANGE) PROTOCOL PART - * - */ - -static BIGNUM dh_prime, dh_g, g_a, auth_key_num; -static char s_power [256]; - -static struct { - long long auth_key_id; - long long out_msg_id; - int msg_len; -} unenc_msg_header; - - -#define ENCRYPT_BUFFER_INTS 16384 -static int encrypt_buffer[ENCRYPT_BUFFER_INTS]; - -#define DECRYPT_BUFFER_INTS 16384 -static int decrypt_buffer[ENCRYPT_BUFFER_INTS]; - -static int encrypt_packet_buffer (struct tgl_state *TLS) { - return tgl_pad_rsa_encrypt (TLS, (char *) packet_buffer, (packet_ptr - packet_buffer) * 4, (char *) encrypt_buffer, ENCRYPT_BUFFER_INTS * 4, ((RSA *)TLS->pubKey)->n, ((RSA *)TLS->pubKey)->e); -} - -static int encrypt_packet_buffer_aes_unauth (const char server_nonce[16], const char hidden_client_nonce[32]) { - tgl_init_aes_unauth (server_nonce, hidden_client_nonce, AES_ENCRYPT); - return tgl_pad_aes_encrypt ((char *) packet_buffer, (packet_ptr - packet_buffer) * 4, (char *) encrypt_buffer, ENCRYPT_BUFFER_INTS * 4); -} - - -static int rpc_send_packet (struct tgl_state *TLS, struct connection *c) { - int len = (packet_ptr - packet_buffer) * 4; - //c->out_packet_num ++; - TLS->net_methods->incr_out_packet_num (c); - long long next_msg_id = (long long) ((1LL << 32) * get_utime (CLOCK_REALTIME)) & -4; - if (next_msg_id <= unenc_msg_header.out_msg_id) { - unenc_msg_header.out_msg_id += 4; - } else { - unenc_msg_header.out_msg_id = next_msg_id; - } - unenc_msg_header.msg_len = len; - - int total_len = len + 20; - assert (total_len > 0 && !(total_len & 0xfc000003)); - total_len >>= 2; - vlogprintf (E_DEBUG, "writing packet: total_len = %d, len = %d\n", total_len, len); - if (total_len < 0x7f) { - assert (TLS->net_methods->write_out (c, &total_len, 1) == 1); - } else { - total_len = (total_len << 8) | 0x7f; - assert (TLS->net_methods->write_out (c, &total_len, 4) == 4); - } - TLS->net_methods->write_out (c, &unenc_msg_header, 20); - TLS->net_methods->write_out (c, packet_buffer, len); - TLS->net_methods->flush_out (c); - - total_packets_sent ++; - total_data_sent += total_len; - return 1; -} - -static int rpc_send_message (struct tgl_state *TLS, struct connection *c, void *data, int len) { - assert (len > 0 && !(len & 0xfc000003)); - int total_len = len >> 2; - if (total_len < 0x7f) { - assert (TLS->net_methods->write_out (c, &total_len, 1) == 1); - } else { - total_len = (total_len << 8) | 0x7f; - assert (TLS->net_methods->write_out (c, &total_len, 4) == 4); - } - - TLS->net_methods->incr_out_packet_num (c); - assert (TLS->net_methods->write_out (c, data, len) == len); - TLS->net_methods->flush_out (c); - - total_packets_sent ++; - total_data_sent += total_len; - return 1; -} - -static int send_req_pq_packet (struct tgl_state *TLS, struct connection *c) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - assert (D->state == st_init); - - tglt_secure_random (D->nonce, 16); - unenc_msg_header.out_msg_id = 0; - clear_packet (); - out_int (CODE_req_pq); - out_ints ((int *)D->nonce, 4); - rpc_send_packet (TLS, c); - - D->state = st_reqpq_sent; - return 1; -} - -static int send_req_pq_temp_packet (struct tgl_state *TLS, struct connection *c) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - assert (D->state == st_authorized); - - tglt_secure_random (D->nonce, 16); - unenc_msg_header.out_msg_id = 0; - clear_packet (); - out_int (CODE_req_pq); - out_ints ((int *)D->nonce, 4); - rpc_send_packet (TLS, c); - - D->state = st_reqpq_sent_temp; - return 1; -} - - -static unsigned long long gcd (unsigned long long a, unsigned long long b) { - return b ? gcd (b, a % b) : a; -} - -//typedef unsigned int uint128_t __attribute__ ((mode(TI))); - -static int process_respq_answer (struct tgl_state *TLS, struct connection *c, char *packet, int len, int temp_key) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - unsigned long long what; - unsigned p1, p2; - int i; - - long long packet_auth_key_id = *(long long *)packet; - if (packet_auth_key_id) { - assert (temp_key); - vlogprintf (E_WARNING, "received packet during creation of temp auth key. Probably answer on old query. Drop\n"); - return 0; - } - vlogprintf (E_DEBUG, "process_respq_answer(), len=%d, op=0x%08x\n", len, *(int *)(packet + 20)); - assert (len >= 76); - assert (!*(long long *) packet); - assert (*(int *) (packet + 16) == len - 20); - assert (!(len & 3)); - assert (*(int *) (packet + 20) == CODE_resPQ); - assert (!memcmp (packet + 24, D->nonce, 16)); - memcpy (D->server_nonce, packet + 40, 16); - char *from = packet + 56; - int clen = *from++; - assert (clen <= 8); - what = 0; - for (i = 0; i < clen; i++) { - what = (what << 8) + (unsigned char)*from++; - } - - while (((unsigned long)from) & 3) ++from; - - p1 = 0, p2 = 0; - - int it = 0; - unsigned long long g = 0; - for (i = 0; i < 3 || it < 1000; i++) { - int q = ((lrand48() & 15) + 17) % what; - unsigned long long x = (long long)lrand48 () % (what - 1) + 1, y = x; - int lim = 1 << (i + 18); - int j; - for (j = 1; j < lim; j++) { - ++it; - unsigned long long a = x, b = x, c = q; - while (b) { - if (b & 1) { - c += a; - if (c >= what) { - c -= what; - } - } - a += a; - if (a >= what) { - a -= what; - } - b >>= 1; - } - x = c; - unsigned long long z = x < y ? what + x - y : x - y; - g = gcd (z, what); - if (g != 1) { - break; - } - if (!(j & (j - 1))) { - y = x; - } - } - if (g > 1 && g < what) break; - } - - assert (g > 1 && g < what); - p1 = g; - p2 = what / g; - if (p1 > p2) { - unsigned t = p1; p1 = p2; p2 = t; - } - - - /// ++p1; /// - - assert (*(int *) (from) == CODE_vector); - int fingerprints_num = *(int *)(from + 4); - assert (fingerprints_num >= 1 && fingerprints_num <= 64 && len == fingerprints_num * 8 + 8 + (from - packet)); - long long *fingerprints = (long long *) (from + 8); - for (i = 0; i < fingerprints_num; i++) { - if (fingerprints[i] == pk_fingerprint) { - //logprintf ( "found our public key at position %d\n", i); - break; - } - } - if (i == fingerprints_num) { - vlogprintf (E_ERROR, "fatal: don't have any matching keys (%016llx expected)\n", pk_fingerprint); - exit (2); - } - // create inner part (P_Q_inner_data) - clear_packet (); - packet_ptr += 5; - out_int (temp_key ? CODE_p_q_inner_data_temp : CODE_p_q_inner_data); - out_cstring (packet + 57, clen); - //out_int (0x0f01); // pq=15 - - if (p1 < 256) { - clen = 1; - } else if (p1 < 65536) { - clen = 2; - } else if (p1 < 16777216) { - clen = 3; - } else { - clen = 4; - } - p1 = __builtin_bswap32 (p1); - out_cstring ((char *)&p1 + 4 - clen, clen); - p1 = __builtin_bswap32 (p1); - - if (p2 < 256) { - clen = 1; - } else if (p2 < 65536) { - clen = 2; - } else if (p2 < 16777216) { - clen = 3; - } else { - clen = 4; - } - p2 = __builtin_bswap32 (p2); - out_cstring ((char *)&p2 + 4 - clen, clen); - p2 = __builtin_bswap32 (p2); - - //out_int (0x0301); // p=3 - //out_int (0x0501); // q=5 - out_ints ((int *) D->nonce, 4); - out_ints ((int *) D->server_nonce, 4); - tglt_secure_random (D->new_nonce, 32); - out_ints ((int *) D->new_nonce, 8); - if (temp_key) { - out_int (TLS->temp_key_expire_time); - } - sha1 ((unsigned char *) (packet_buffer + 5), (packet_ptr - packet_buffer - 5) * 4, (unsigned char *) packet_buffer); - - int l = encrypt_packet_buffer (TLS); - - clear_packet (); - out_int (CODE_req_DH_params); - out_ints ((int *) D->nonce, 4); - out_ints ((int *) D->server_nonce, 4); - //out_int (0x0301); // p=3 - //out_int (0x0501); // q=5 - if (p1 < 256) { - clen = 1; - } else if (p1 < 65536) { - clen = 2; - } else if (p1 < 16777216) { - clen = 3; - } else { - clen = 4; - } - p1 = __builtin_bswap32 (p1); - out_cstring ((char *)&p1 + 4 - clen, clen); - p1 = __builtin_bswap32 (p1); - if (p2 < 256) { - clen = 1; - } else if (p2 < 65536) { - clen = 2; - } else if (p2 < 16777216) { - clen = 3; - } else { - clen = 4; - } - p2 = __builtin_bswap32 (p2); - out_cstring ((char *)&p2 + 4 - clen, clen); - p2 = __builtin_bswap32 (p2); - - out_long (pk_fingerprint); - out_cstring ((char *) encrypt_buffer, l); - - D->state = temp_key ? st_reqdh_sent_temp : st_reqdh_sent; - - return rpc_send_packet (TLS, c); -} - -static int check_prime (struct tgl_state *TLS, BIGNUM *p) { - int r = BN_is_prime (p, BN_prime_checks, 0, TLS->BN_ctx, 0); - ensure (r >= 0); - return r; -} - -int tglmp_check_DH_params (struct tgl_state *TLS, BIGNUM *p, int g) { - if (g < 2 || g > 7) { return -1; } - if (BN_num_bits (p) != 2048) { return -1; } - BIGNUM t; - BN_init (&t); - - BN_init (&dh_g); - ensure (BN_set_word (&dh_g, 4 * g)); - - ensure (BN_mod (&t, p, &dh_g, TLS->BN_ctx)); - int x = BN_get_word (&t); - assert (x >= 0 && x < 4 * g); - - BN_free (&dh_g); - - switch (g) { - case 2: - if (x != 7) { return -1; } - break; - case 3: - if (x % 3 != 2 ) { return -1; } - break; - case 4: - break; - case 5: - if (x % 5 != 1 && x % 5 != 4) { return -1; } - break; - case 6: - if (x != 19 && x != 23) { return -1; } - break; - case 7: - if (x % 7 != 3 && x % 7 != 5 && x % 7 != 6) { return -1; } - break; - } - - if (!check_prime (TLS, p)) { return -1; } - - BIGNUM b; - BN_init (&b); - ensure (BN_set_word (&b, 2)); - ensure (BN_div (&t, 0, p, &b, TLS->BN_ctx)); - if (!check_prime (TLS, &t)) { return -1; } - BN_free (&b); - BN_free (&t); - return 0; -} - -int tglmp_check_g (struct tgl_state *TLS, unsigned char p[256], BIGNUM *g) { - static unsigned char s[256]; - memset (s, 0, 256); - assert (BN_num_bytes (g) <= 256); - BN_bn2bin (g, s + (256 - BN_num_bytes (g))); - int ok = 0; - int i; - for (i = 0; i < 64; i++) { - if (s[i]) { - ok = 1; - break; - } - } - if (!ok) { return -1; } - ok = 0; - for (i = 0; i < 64; i++) { - if (s[255 - i]) { - ok = 1; - break; - } - } - if (!ok) { return -1; } - ok = 0; - for (i = 0; i < 64; i++) { - if (s[i] < p[i]) { - ok = 1; - break; - } else if (s[i] > p[i]) { - vlogprintf (E_WARNING, "i = %d (%d %d)\n", i, (int)s[i], (int)p[i]); - return -1; - } - } - if (!ok) { return -1; } - return 0; -} - -int tglmp_check_g_bn (struct tgl_state *TLS, BIGNUM *p, BIGNUM *g) { - static unsigned char s[256]; - memset (s, 0, 256); - assert (BN_num_bytes (p) == 256); - BN_bn2bin (p, s); - return tglmp_check_g (TLS, s, g); -} - -static int process_dh_answer (struct tgl_state *TLS, struct connection *c, char *packet, int len, int temp_key) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - vlogprintf (E_DEBUG, "process_dh_answer(), len=%d\n", len); - //if (len < 116) { - // vlogprintf (E_ERROR, "%u * %u = %llu", p1, p2, what); - //} - long long packet_auth_key_id = *(long long *)packet; - if (packet_auth_key_id) { - assert (temp_key); - vlogprintf (E_WARNING, "received packet during creation of temp auth key. Probably answer on old query. Drop\n"); - return 0; - } - assert (len >= 116); - assert (!*(long long *) packet); - assert (*(int *) (packet + 16) == len - 20); - assert (!(len & 3)); - assert (*(int *) (packet + 20) == (int)CODE_server_DH_params_ok); - assert (!memcmp (packet + 24, D->nonce, 16)); - assert (!memcmp (packet + 40, D->server_nonce, 16)); - tgl_init_aes_unauth (D->server_nonce, D->new_nonce, AES_DECRYPT); - in_ptr = (int *)(packet + 56); - in_end = (int *)(packet + len); - int l = prefetch_strlen (); - assert (l > 0); - l = tgl_pad_aes_decrypt (fetch_str (l), l, (char *) decrypt_buffer, DECRYPT_BUFFER_INTS * 4 - 16); - assert (in_ptr == in_end); - assert (l >= 60); - assert (decrypt_buffer[5] == (int)CODE_server_DH_inner_data); - assert (!memcmp (decrypt_buffer + 6, D->nonce, 16)); - assert (!memcmp (decrypt_buffer + 10, D->server_nonce, 16)); - int g = decrypt_buffer[14]; - in_ptr = decrypt_buffer + 15; - in_end = decrypt_buffer + (l >> 2); - BN_init (&dh_prime); - BN_init (&g_a); - assert (fetch_bignum (&dh_prime) > 0); - assert (fetch_bignum (&g_a) > 0); - assert (tglmp_check_g_bn (TLS, &dh_prime, &g_a) >= 0); - int server_time = *in_ptr++; - assert (in_ptr <= in_end); - - assert (tglmp_check_DH_params (TLS, &dh_prime, g) >= 0); - - static char sha1_buffer[20]; - sha1 ((unsigned char *) decrypt_buffer + 20, (in_ptr - decrypt_buffer - 5) * 4, (unsigned char *) sha1_buffer); - assert (!memcmp (decrypt_buffer, sha1_buffer, 20)); - assert ((char *) in_end - (char *) in_ptr < 16); - - D->server_time_delta = server_time - time (0); - D->server_time_udelta = server_time - get_utime (CLOCK_MONOTONIC); - //logprintf ( "server time is %d, delta = %d\n", server_time, server_time_delta); - - // Build set_client_DH_params answer - clear_packet (); - packet_ptr += 5; - out_int (CODE_client_DH_inner_data); - out_ints ((int *) D->nonce, 4); - out_ints ((int *) D->server_nonce, 4); - out_long (0LL); - - BN_init (&dh_g); - ensure (BN_set_word (&dh_g, g)); - - tglt_secure_random (s_power, 256); - BIGNUM *dh_power = BN_bin2bn ((unsigned char *)s_power, 256, 0); - ensure_ptr (dh_power); - - BIGNUM *y = BN_new (); - ensure_ptr (y); - ensure (BN_mod_exp (y, &dh_g, dh_power, &dh_prime, TLS->BN_ctx)); - out_bignum (y); - BN_free (y); - - BN_init (&auth_key_num); - ensure (BN_mod_exp (&auth_key_num, &g_a, dh_power, &dh_prime, TLS->BN_ctx)); - l = BN_num_bytes (&auth_key_num); - assert (l >= 250 && l <= 256); - assert (BN_bn2bin (&auth_key_num, (unsigned char *)(temp_key ? D->temp_auth_key : D->auth_key))); - if (l < 256) { - char *key = temp_key ? D->temp_auth_key : D->auth_key; - memmove (key + 256 - l, key, l); - memset (key, 0, 256 - l); - } - - BN_free (dh_power); - BN_free (&auth_key_num); - BN_free (&dh_g); - BN_free (&g_a); - BN_free (&dh_prime); - - //hexdump (auth_key, auth_key + 256); - - sha1 ((unsigned char *) (packet_buffer + 5), (packet_ptr - packet_buffer - 5) * 4, (unsigned char *) packet_buffer); - - //hexdump ((char *)packet_buffer, (char *)packet_ptr); - - l = encrypt_packet_buffer_aes_unauth (D->server_nonce, D->new_nonce); - - clear_packet (); - out_int (CODE_set_client_DH_params); - out_ints ((int *) D->nonce, 4); - out_ints ((int *) D->server_nonce, 4); - out_cstring ((char *) encrypt_buffer, l); - - D->state = temp_key ? st_client_dh_sent_temp : st_client_dh_sent;; - - return rpc_send_packet (TLS, c); -} - -static void create_temp_auth_key (struct tgl_state *TLS, struct connection *c) { - send_req_pq_temp_packet (TLS, c); -} - -int tglmp_encrypt_inner_temp (struct tgl_state *TLS, struct connection *c, int *msg, int msg_ints, int useful, void *data, long long msg_id); -static long long generate_next_msg_id (struct tgl_state *TLS, struct tgl_dc *DC); -static long long msg_id_override; -static void mpc_on_get_config (struct tgl_state *TLS, void *extra, int success); -static int process_auth_complete (struct tgl_state *TLS, struct connection *c UU, char *packet, int len, int temp_key) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - vlogprintf (E_DEBUG - 1, "process_dh_answer(), len=%d\n", len); - - long long packet_auth_key_id = *(long long *)packet; - if (packet_auth_key_id) { - assert (temp_key); - vlogprintf (E_WARNING, "received packet during creation of temp auth key. Probably answer on old query. Drop\n"); - return 0; - } - assert (len == 72); - assert (!*(long long *) packet); - assert (*(int *) (packet + 16) == len - 20); - assert (!(len & 3)); - assert (*(int *) (packet + 20) == CODE_dh_gen_ok); - assert (!memcmp (packet + 24, D->nonce, 16)); - assert (!memcmp (packet + 40, D->server_nonce, 16)); - static unsigned char tmp[44], sha1_buffer[20]; - memcpy (tmp, D->new_nonce, 32); - tmp[32] = 1; - //GET_DC(c)->auth_key_id = *(long long *)(sha1_buffer + 12); - - if (!temp_key) { - bl_do_set_auth_key_id (TLS, D->id, (unsigned char *)D->auth_key); - sha1 ((unsigned char *)D->auth_key, 256, sha1_buffer); - } else { - sha1 ((unsigned char *)D->temp_auth_key, 256, sha1_buffer); - D->temp_auth_key_id = *(long long *)(sha1_buffer + 12); - } - - memcpy (tmp + 33, sha1_buffer, 8); - sha1 (tmp, 41, sha1_buffer); - assert (!memcmp (packet + 56, sha1_buffer + 4, 16)); - D->server_salt = *(long long *)D->server_nonce ^ *(long long *)D->new_nonce; - - //kprintf ("OK\n"); - - //c->status = conn_error; - //sleep (1); - - D->state = st_authorized; - //return 1; - vlogprintf (E_DEBUG, "Auth success\n"); - if (temp_key) { - //D->flags |= 2; - - long long msg_id = generate_next_msg_id (TLS, D); - clear_packet (); - out_int (CODE_bind_auth_key_inner); - long long rand; - tglt_secure_random (&rand, 8); - out_long (rand); - out_long (D->temp_auth_key_id); - out_long (D->auth_key_id); - - struct tgl_session *S = TLS->net_methods->get_session (c); - if (!S->session_id) { - tglt_secure_random (&S->session_id, 8); - } - out_long (S->session_id); - int expires = time (0) + D->server_time_delta + TLS->temp_key_expire_time; - out_int (expires); - - static int data[1000]; - int len = tglmp_encrypt_inner_temp (TLS, c, packet_buffer, packet_ptr - packet_buffer, 0, data, msg_id); - msg_id_override = msg_id; - tgl_do_send_bind_temp_key (TLS, D, rand, expires, (void *)data, len, msg_id); - msg_id_override = 0; - } else { - D->flags |= 1; - if (TLS->enable_pfs) { - create_temp_auth_key (TLS, c); - } else { - D->temp_auth_key_id = D->auth_key_id; - memcpy (D->temp_auth_key, D->auth_key, 256); - D->flags |= 2; - if (!(D->flags & 4)) { - tgl_do_help_get_config_dc (TLS, D, mpc_on_get_config, D); - } - } - } - - //write_auth_file (); - - return 1; -} - -/* - * - * AUTHORIZED (MAIN) PROTOCOL PART - * - */ - -static struct encrypted_message enc_msg; - -static long long client_last_msg_id, server_last_msg_id; - -static double get_server_time (struct tgl_dc *DC) { - if (!DC->server_time_udelta) { - DC->server_time_udelta = get_utime (CLOCK_REALTIME) - get_utime (CLOCK_MONOTONIC); - } - return get_utime (CLOCK_MONOTONIC) + DC->server_time_udelta; -} - -static long long generate_next_msg_id (struct tgl_state *TLS, struct tgl_dc *DC) { - long long next_id = (long long) (get_server_time (DC) * (1LL << 32)) & -4; - if (next_id <= client_last_msg_id) { - next_id = client_last_msg_id += 4; - } else { - client_last_msg_id = next_id; - } - return next_id; -} - -static void init_enc_msg (struct tgl_state *TLS, struct tgl_session *S, int useful) { - struct tgl_dc *DC = S->dc; - assert (DC->state == st_authorized); - //assert (DC->flags & 2); - assert (DC->temp_auth_key_id); - vlogprintf (E_DEBUG, "temp_auth_key_id = 0x%016llx, auth_key_id = 0x%016llx\n", DC->temp_auth_key_id, DC->auth_key_id); - enc_msg.auth_key_id = DC->temp_auth_key_id; -// assert (DC->server_salt); - enc_msg.server_salt = DC->server_salt; - if (!S->session_id) { - tglt_secure_random (&S->session_id, 8); - } - enc_msg.session_id = S->session_id; - //enc_msg.auth_key_id2 = auth_key_id; - enc_msg.msg_id = msg_id_override ? msg_id_override : generate_next_msg_id (TLS, DC); - //enc_msg.msg_id -= 0x10000000LL * (lrand48 () & 15); - //kprintf ("message id %016llx\n", enc_msg.msg_id); - enc_msg.seq_no = S->seq_no; - if (useful) { - enc_msg.seq_no |= 1; - } - S->seq_no += 2; -}; - -static void init_enc_msg_inner_temp (struct tgl_dc *DC, long long msg_id) { - enc_msg.auth_key_id = DC->auth_key_id; - tglt_secure_random (&enc_msg.server_salt, 8); - tglt_secure_random (&enc_msg.session_id, 8); - enc_msg.msg_id = msg_id; - enc_msg.seq_no = 0; -}; - - -static int aes_encrypt_message (struct tgl_state *TLS, char *key, struct encrypted_message *enc) { - unsigned char sha1_buffer[20]; - const int MINSZ = offsetof (struct encrypted_message, message); - const int UNENCSZ = offsetof (struct encrypted_message, server_salt); - int enc_len = (MINSZ - UNENCSZ) + enc->msg_len; - 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); - //printf ("enc_len is %d\n", enc_len); - vlogprintf (E_DEBUG, "sending message with sha1 %08x\n", *(int *)sha1_buffer); - memcpy (enc->msg_key, sha1_buffer + 4, 16); - tgl_init_aes_auth (key, enc->msg_key, AES_ENCRYPT); - //hexdump ((char *)enc, (char *)enc + enc_len + 24); - return tgl_pad_aes_encrypt ((char *) &enc->server_salt, enc_len, (char *) &enc->server_salt, MAX_MESSAGE_INTS * 4 + (MINSZ - UNENCSZ)); -} - -long long tglmp_encrypt_send_message (struct tgl_state *TLS, struct connection *c, int *msg, int msg_ints, int flags) { - struct tgl_dc *DC = TLS->net_methods->get_dc (c); - if (!(DC->flags & 4) && !(flags & 2)) { - return generate_next_msg_id (TLS, DC); - } - struct tgl_session *S = TLS->net_methods->get_session (c); - assert (S); - - const int UNENCSZ = offsetof (struct encrypted_message, server_salt); - if (msg_ints <= 0 || msg_ints > MAX_MESSAGE_INTS - 4) { - return -1; - } - if (msg) { - memcpy (enc_msg.message, msg, msg_ints * 4); - enc_msg.msg_len = msg_ints * 4; - } else { - if ((enc_msg.msg_len & 0x80000003) || enc_msg.msg_len > MAX_MESSAGE_INTS * 4 - 16) { - return -1; - } - } - init_enc_msg (TLS, S, flags & 1); - - //hexdump ((char *)msg, (char *)msg + (msg_ints * 4)); - int l = aes_encrypt_message (TLS, DC->temp_auth_key, &enc_msg); - //hexdump ((char *)&enc_msg, (char *)&enc_msg + l + 24); - assert (l > 0); - vlogprintf (E_DEBUG, "Sending message to DC%d: %s:%d with key_id=%lld\n", DC->id, DC->ip, DC->port, enc_msg.auth_key_id); - rpc_send_message (TLS, c, &enc_msg, l + UNENCSZ); - - - return client_last_msg_id; -} - -int tglmp_encrypt_inner_temp (struct tgl_state *TLS, struct connection *c, int *msg, int msg_ints, int useful, void *data, long long msg_id) { - struct tgl_dc *DC = TLS->net_methods->get_dc (c); - struct tgl_session *S = TLS->net_methods->get_session (c); - assert (S); - - const int UNENCSZ = offsetof (struct encrypted_message, server_salt); - if (msg_ints <= 0 || msg_ints > MAX_MESSAGE_INTS - 4) { - return -1; - } - memcpy (enc_msg.message, msg, msg_ints * 4); - enc_msg.msg_len = msg_ints * 4; - - init_enc_msg_inner_temp (DC, msg_id); - - int l = aes_encrypt_message (TLS, DC->auth_key, &enc_msg); - assert (l > 0); - //rpc_send_message (c, &enc_msg, l + UNENCSZ); - memcpy (data, &enc_msg, l + UNENCSZ); - - return l + UNENCSZ; -} - -static int good_messages; - -static void rpc_execute_answer (struct tgl_state *TLS, struct connection *c, long long msg_id UU); - -//int unread_messages; -//int pts; -//int qts; -//int last_date; -//int seq; - -static void work_container (struct tgl_state *TLS, struct connection *c, long long msg_id UU) { - vlogprintf (E_DEBUG, "work_container: msg_id = %lld\n", msg_id); - assert (fetch_int () == CODE_msg_container); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - long long id = fetch_long (); - //int seqno = fetch_int (); - fetch_int (); // seq_no - if (id & 1) { - tgln_insert_msg_id (TLS, TLS->net_methods->get_session (c), id); - } - int bytes = fetch_int (); - int *t = in_end; - in_end = in_ptr + (bytes / 4); - rpc_execute_answer (TLS, c, id); - assert (in_ptr == in_end); - in_end = t; - } -} - -static void work_new_session_created (struct tgl_state *TLS, struct connection *c, long long msg_id UU) { - vlogprintf (E_DEBUG, "work_new_session_created: msg_id = %lld\n", msg_id); - assert (fetch_int () == (int)CODE_new_session_created); - fetch_long (); // first message id - //DC->session_id = fetch_long (); - fetch_long (); // unique_id - TLS->net_methods->get_dc (c)->server_salt = fetch_long (); - if (TLS->started && !(TLS->locks & TGL_LOCK_DIFF)) { - tgl_do_get_difference (TLS, 0, 0, 0); - } -} - -static void work_msgs_ack (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - vlogprintf (E_DEBUG, "work_msgs_ack: msg_id = %lld\n", msg_id); - assert (fetch_int () == CODE_msgs_ack); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - long long id = fetch_long (); - vlogprintf (E_DEBUG + 1, "ack for %lld\n", id); - tglq_query_ack (TLS, id); - } -} - -static void work_rpc_result (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - vlogprintf (E_DEBUG, "work_rpc_result: msg_id = %lld\n", msg_id); - assert (fetch_int () == (int)CODE_rpc_result); - long long id = fetch_long (); - int op = prefetch_int (); - if (op == CODE_rpc_error) { - tglq_query_error (TLS, id); - } else { - tglq_query_result (TLS, id); - } -} - -#define MAX_PACKED_SIZE (1 << 24) -static void work_packed (struct tgl_state *TLS, struct connection *c, long long msg_id) { - assert (fetch_int () == CODE_gzip_packed); - static int in_gzip; - static int buf[MAX_PACKED_SIZE >> 2]; - assert (!in_gzip); - in_gzip = 1; - - int l = prefetch_strlen (); - char *s = fetch_str (l); - - int total_out = tgl_inflate (s, l, buf, MAX_PACKED_SIZE); - int *end = in_ptr; - int *eend = in_end; - //assert (total_out % 4 == 0); - in_ptr = buf; - in_end = in_ptr + total_out / 4; - rpc_execute_answer (TLS, c, msg_id); - in_ptr = end; - in_end = eend; - in_gzip = 0; -} - -static void work_bad_server_salt (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - assert (fetch_int () == (int)CODE_bad_server_salt); - long long id = fetch_long (); - tglq_query_restart (TLS, id); - fetch_int (); // seq_no - fetch_int (); // error_code - long long new_server_salt = fetch_long (); - TLS->net_methods->get_dc (c)->server_salt = new_server_salt; -} - -static void work_pong (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - assert (fetch_int () == CODE_pong); - fetch_long (); // msg_id - fetch_long (); // ping_id -} - -static void work_detailed_info (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - assert (fetch_int () == CODE_msg_detailed_info); - fetch_long (); // msg_id - fetch_long (); // answer_msg_id - fetch_int (); // bytes - fetch_int (); // status -} - -static void work_new_detailed_info (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - assert (fetch_int () == (int)CODE_msg_new_detailed_info); - fetch_long (); // answer_msg_id - fetch_int (); // bytes - fetch_int (); // status -} - -static void work_bad_msg_notification (struct tgl_state *TLS, struct connection *c UU, long long msg_id UU) { - assert (fetch_int () == (int)CODE_bad_msg_notification); - long long m1 = fetch_long (); - int s = fetch_int (); - int e = fetch_int (); - vlogprintf (E_NOTICE, "bad_msg_notification: msg_id = %lld, seq = %d, error = %d\n", m1, s, e); -} - -static void rpc_execute_answer (struct tgl_state *TLS, struct connection *c, long long msg_id UU) { - int op = prefetch_int (); - switch (op) { - case CODE_msg_container: - work_container (TLS, c, msg_id); - return; - case CODE_new_session_created: - work_new_session_created (TLS, c, msg_id); - return; - case CODE_msgs_ack: - work_msgs_ack (TLS, c, msg_id); - return; - case CODE_rpc_result: - work_rpc_result (TLS, c, msg_id); - return; - case CODE_update_short: - tglu_work_update_short (TLS, c, msg_id); - return; - case CODE_updates: - tglu_work_updates (TLS, c, msg_id); - return; - case CODE_update_short_message: - tglu_work_update_short_message (TLS, c, msg_id); - return; - case CODE_update_short_chat_message: - tglu_work_update_short_chat_message (TLS, c, msg_id); - return; - case CODE_gzip_packed: - work_packed (TLS, c, msg_id); - return; - case CODE_bad_server_salt: - work_bad_server_salt (TLS, c, msg_id); - return; - case CODE_pong: - work_pong (TLS, c, msg_id); - return; - case CODE_msg_detailed_info: - work_detailed_info (TLS, c, msg_id); - return; - case CODE_msg_new_detailed_info: - work_new_detailed_info (TLS, c, msg_id); - return; - case CODE_updates_too_long: - tglu_work_updates_to_long (TLS, c, msg_id); - return; - case CODE_bad_msg_notification: - work_bad_msg_notification (TLS, c, msg_id); - return; - } - vlogprintf (E_WARNING, "Unknown message: %08x\n", op); - in_ptr = in_end; // Will not fail due to assertion in_ptr == in_end -} - -static int process_rpc_message (struct tgl_state *TLS, struct connection *c UU, struct encrypted_message *enc, int len) { - const int MINSZ = offsetof (struct encrypted_message, message); - const int UNENCSZ = offsetof (struct encrypted_message, server_salt); - vlogprintf (E_DEBUG, "process_rpc_message(), len=%d\n", len); - assert (len >= MINSZ && (len & 15) == (UNENCSZ & 15)); - struct tgl_dc *DC = TLS->net_methods->get_dc (c); - if (enc->auth_key_id != DC->temp_auth_key_id && enc->auth_key_id != DC->auth_key_id) { - vlogprintf (E_WARNING, "received msg from dc %d with auth_key_id %lld (perm_auth_key_id %lld temp_auth_key_id %lld). Dropping\n", - DC->id, enc->auth_key_id, DC->auth_key_id, DC->temp_auth_key_id); - return 0; - } - if (enc->auth_key_id == DC->temp_auth_key_id) { - assert (enc->auth_key_id == DC->temp_auth_key_id); - assert (DC->temp_auth_key_id); - tgl_init_aes_auth (DC->temp_auth_key + 8, enc->msg_key, AES_DECRYPT); - } else { - assert (enc->auth_key_id == DC->auth_key_id); - assert (DC->auth_key_id); - tgl_init_aes_auth (DC->auth_key + 8, enc->msg_key, AES_DECRYPT); - } - int l = tgl_pad_aes_decrypt ((char *)&enc->server_salt, len - UNENCSZ, (char *)&enc->server_salt, len - UNENCSZ); - assert (l == len - UNENCSZ); - //assert (enc->auth_key_id2 == enc->auth_key_id); - assert (!(enc->msg_len & 3) && enc->msg_len > 0 && enc->msg_len <= len - MINSZ && len - MINSZ - enc->msg_len <= 12); - static unsigned char sha1_buffer[20]; - sha1 ((void *)&enc->server_salt, enc->msg_len + (MINSZ - UNENCSZ), sha1_buffer); - assert (!memcmp (&enc->msg_key, sha1_buffer + 4, 16)); - //assert (enc->server_salt == server_salt); //in fact server salt can change - if (DC->server_salt != enc->server_salt) { - DC->server_salt = enc->server_salt; - //write_auth_file (); - } - - - int this_server_time = enc->msg_id >> 32LL; - if (!DC->server_time_delta) { - DC->server_time_delta = this_server_time - get_utime (CLOCK_REALTIME); - DC->server_time_udelta = this_server_time - get_utime (CLOCK_MONOTONIC); - } - double st = get_server_time (DC); - if (this_server_time < st - 300 || this_server_time > st + 30) { - 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)); - return 0; - } - - - assert (this_server_time >= st - 300 && this_server_time <= st + 30); - //assert (enc->msg_id > server_last_msg_id && (enc->msg_id & 3) == 1); - vlogprintf (E_DEBUG, "received mesage id %016llx\n", enc->msg_id); - server_last_msg_id = enc->msg_id; - - //*(long long *)(longpoll_query + 3) = *(long long *)((char *)(&enc->msg_id) + 0x3c); - //*(long long *)(longpoll_query + 5) = *(long long *)((char *)(&enc->msg_id) + 0x3c); - - assert (l >= (MINSZ - UNENCSZ) + 8); - //assert (enc->message[0] == CODE_rpc_result && *(long long *)(enc->message + 1) == client_last_msg_id); - ++good_messages; - - in_ptr = enc->message; - in_end = in_ptr + (enc->msg_len / 4); - - /*{ - assert (len <= 10000); - static char s[1 << 20]; - int p = 0; - int i; - //static int buf[10000]; - //assert (TLS->net_methods->read_in_lookup (c, buf, len) == len); - - for (i = 0; i < in_end - in_ptr; i++) { - p += sprintf (s + p, "%08x ", *(int *)(in_ptr + i)); - } - vlogprintf (E_DEBUG, "%s\n", s); - }*/ - - struct tgl_session *S = TLS->net_methods->get_session (c); - if (enc->msg_id & 1) { - tgln_insert_msg_id (TLS, S, enc->msg_id); - } - assert (S->session_id == enc->session_id); - rpc_execute_answer (TLS, c, enc->msg_id); - assert (in_ptr == in_end); - return 0; -} - - -static int rpc_execute (struct tgl_state *TLS, struct connection *c, int op, int len) { - struct tgl_dc *D = TLS->net_methods->get_dc (c); - vlogprintf (E_DEBUG, "outbound rpc connection from dc #%d (%s:%d) : received rpc answer %d with %d content bytes\n", D->id, D->ip, D->port, op, len); - - /*{ - assert (len <= 10000); - static char s[1 << 20]; - int p = 0; - int i; - static int buf[10000]; - assert (TLS->net_methods->read_in_lookup (c, buf, len) == len); - - for (i = 0; i < len / 4; i++) { - p += sprintf (s + p, "%08x ", *(int *)(buf + i)); - } - vlogprintf (E_DEBUG, "%s\n", s); - }*/ - /* if (op < 0) { - assert (TLS->net_methods->read_in (c, Response, Response_len) == Response_len); - return 0; - }*/ - - if (len >= MAX_RESPONSE_SIZE/* - 12*/ || len < 0/*12*/) { - vlogprintf (E_WARNING, "answer too long (%d bytes), skipping\n", len); - return 0; - } - - int Response_len = len; - - static char Response[MAX_RESPONSE_SIZE]; - vlogprintf (E_DEBUG, "Response_len = %d\n", Response_len); - assert (TLS->net_methods->read_in (c, Response, Response_len) == Response_len); - Response[Response_len] = 0; - -#if !defined(__MACH__) && !defined(__FreeBSD__) && !defined(__OpenBSD__) && !defined (__CYGWIN__) -// setsockopt (c->fd, IPPROTO_TCP, TCP_QUICKACK, (int[]){0}, 4); -#endif - int o = D->state; - //if (D->flags & 1) { o = st_authorized;} - switch (o) { - case st_reqpq_sent: - process_respq_answer (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 0); - return 0; - case st_reqdh_sent: - process_dh_answer (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 0); - return 0; - case st_client_dh_sent: - process_auth_complete (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 0); - return 0; - case st_reqpq_sent_temp: - process_respq_answer (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 1); - return 0; - case st_reqdh_sent_temp: - process_dh_answer (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 1); - return 0; - case st_client_dh_sent_temp: - process_auth_complete (TLS, c, Response/* + 8*/, Response_len/* - 12*/, 1); - return 0; - case st_authorized: - if (op < 0 && op >= -999) { - vlogprintf (E_WARNING, "Server error %d\n", op); - } else { - process_rpc_message (TLS, c, (void *)(Response/* + 8*/), Response_len/* - 12*/); - } - return 0; - default: - vlogprintf (E_ERROR, "fatal: cannot receive answer in state %d\n", D->state); - exit (2); - } - - return 0; -} - - -static int tc_close (struct tgl_state *TLS, struct connection *c, int who) { - vlogprintf (E_DEBUG, "outbound rpc connection from dc #%d : closing by %d\n", TLS->net_methods->get_dc(c)->id, who); - return 0; -} - -static void mpc_on_get_config (struct tgl_state *TLS, void *extra, int success) { - assert (success); - struct tgl_dc *D = extra; - D->flags |= 4; -} - -static int tc_becomes_ready (struct tgl_state *TLS, struct connection *c) { - vlogprintf (E_DEBUG, "outbound rpc connection from dc #%d becomed ready\n", TLS->net_methods->get_dc(c)->id); - //char byte = 0xef; - //assert (TLS->net_methods->write_out (c, &byte, 1) == 1); - //TLS->net_methods->flush_out (c); - - struct tgl_dc *D = TLS->net_methods->get_dc (c); - if (D->flags & 1) { D->state = st_authorized; } - int o = D->state; - if (o == st_authorized && !TLS->enable_pfs) { - D->temp_auth_key_id = D->auth_key_id; - memcpy (D->temp_auth_key, D->auth_key, 256); - D->flags |= 2; - } - switch (o) { - case st_init: - send_req_pq_packet (TLS, c); - break; - case st_authorized: - if (!(D->flags & 2)) { - assert (!D->temp_auth_key_id); - create_temp_auth_key (TLS, c); - } else if (!(D->flags & 4)) { - tgl_do_help_get_config_dc (TLS, D, mpc_on_get_config, D); - } - break; - default: - vlogprintf (E_DEBUG, "c_state = %d\n", D->state); - assert (0); - } - return 0; -} - -static int rpc_becomes_ready (struct tgl_state *TLS, struct connection *c) { - return tc_becomes_ready (TLS, c); -} - -static int rpc_close (struct tgl_state *TLS, struct connection *c) { - return tc_close (TLS, c, 0); -} - - -#define RANDSEED_PASSWORD_FILENAME NULL -#define RANDSEED_PASSWORD_LENGTH 0 -void tglmp_on_start (struct tgl_state *TLS) { - tgl_prng_seed (TLS, RANDSEED_PASSWORD_FILENAME, RANDSEED_PASSWORD_LENGTH); - - int i; - int ok = 0; - for (i = 0; i < TLS->rsa_key_num; i++) { - char *key = TLS->rsa_key_list[i]; - if (rsa_load_public_key (TLS, key) < 0) { - vlogprintf (E_WARNING, "Can not load key %s\n", key); - } else { - ok = 1; - break; - } - } - - if (!ok) { - vlogprintf (E_ERROR, "No public keys found\n"); - exit (1); - } - - pk_fingerprint = tgl_do_compute_rsa_key_fingerprint (TLS->pubKey); -} - -void tgl_dc_authorize (struct tgl_state *TLS, struct tgl_dc *DC) { - //c_state = 0; - if (!DC->sessions[0]) { - tglmp_dc_create_session (TLS, DC); - } - vlogprintf (E_DEBUG, "Starting authorization for DC #%d: %s:%d\n", DC->id, DC->ip, DC->port); - //net_loop (0, auth_ok); -} - -#define long_cmp(a,b) ((a) > (b) ? 1 : (a) == (b) ? 0 : -1) -DEFINE_TREE(long,long long,long_cmp,0) - -static int send_all_acks (struct tgl_state *TLS, struct tgl_session *S) { - clear_packet (); - out_int (CODE_msgs_ack); - out_int (CODE_vector); - out_int (tree_count_long (S->ack_tree)); - while (S->ack_tree) { - long long x = tree_get_min_long (S->ack_tree); - out_long (x); - S->ack_tree = tree_delete_long (S->ack_tree, x); - } - tglmp_encrypt_send_message (TLS, S->c, packet_buffer, packet_ptr - packet_buffer, 0); - return 0; -} - -static void send_all_acks_gateway (struct tgl_state *TLS, void *arg) { - send_all_acks (TLS, arg); -} - - -void tgln_insert_msg_id (struct tgl_state *TLS, struct tgl_session *S, long long id) { - if (!S->ack_tree) { - TLS->timer_methods->insert (S->ev, ACK_TIMEOUT); - } - if (!tree_lookup_long (S->ack_tree, id)) { - S->ack_tree = tree_insert_long (S->ack_tree, id, lrand48 ()); - } -} - -//extern struct tgl_dc *DC_list[]; - - -static void regen_temp_key_gw (struct tgl_state *TLS, void *arg) { - tglmp_regenerate_temp_auth_key (TLS, arg); -} - -struct tgl_dc *tglmp_alloc_dc (struct tgl_state *TLS, int id, char *ip, int port UU) { - //assert (!TLS->DC_list[id]); - if (!TLS->DC_list[id]) { - struct tgl_dc *DC = talloc0 (sizeof (*DC)); - DC->id = id; - DC->ip = ip; - DC->port = port; - TLS->DC_list[id] = DC; - if (id > TLS->max_dc_num) { - TLS->max_dc_num = id; - } - DC->ev = TLS->timer_methods->alloc (TLS, regen_temp_key_gw, DC); - TLS->timer_methods->insert (DC->ev, 0); - return DC; - } else { - struct tgl_dc *DC = TLS->DC_list[id]; - tfree_str (DC->ip); - DC->ip = tstrdup (ip); - return DC; - } -} - -static struct mtproto_methods mtproto_methods = { - .execute = rpc_execute, - .ready = rpc_becomes_ready, - .close = rpc_close -}; - -void tglmp_dc_create_session (struct tgl_state *TLS, struct tgl_dc *DC) { - struct tgl_session *S = talloc0 (sizeof (*S)); - assert (RAND_pseudo_bytes ((unsigned char *) &S->session_id, 8) >= 0); - S->dc = DC; - S->c = TLS->net_methods->create_connection (TLS, DC->ip, DC->port, S, DC, &mtproto_methods); - if (!S->c) { - vlogprintf (E_DEBUG, "Can not create connection to DC. Is network down?\n"); - exit (1); - } - S->ev = TLS->timer_methods->alloc (TLS, send_all_acks_gateway, S); - assert (!DC->sessions[0]); - DC->sessions[0] = S; -} - -void tgl_do_send_ping (struct tgl_state *TLS, struct connection *c) { - int x[3]; - x[0] = CODE_ping; - *(long long *)(x + 1) = lrand48 () * (1ll << 32) + lrand48 (); - tglmp_encrypt_send_message (TLS, c, x, 3, 0); -} - -void tgl_dc_iterator (struct tgl_state *TLS, void (*iterator)(struct tgl_dc *DC)) { - int i; - for (i = 0; i <= TLS->max_dc_num; i++) { - iterator (TLS->DC_list[i]); - } -} - -void tgl_dc_iterator_ex (struct tgl_state *TLS, void (*iterator)(struct tgl_dc *DC, void *extra), void *extra) { - int i; - for (i = 0; i <= TLS->max_dc_num; i++) { - iterator (TLS->DC_list[i], extra); - } -} - - -void tglmp_regenerate_temp_auth_key (struct tgl_state *TLS, struct tgl_dc *D) { - D->flags &= ~6; - D->temp_auth_key_id = 0; - memset (D->temp_auth_key, 0, 256); - - if (!D->sessions[0]) { - tgl_dc_authorize (TLS, D); - return; - } - - - struct tgl_session *S = D->sessions[0]; - tglt_secure_random (&S->session_id, 8); - S->seq_no = 0; - - TLS->timer_methods->delete (S->ev); - S->ack_tree = tree_clear_long (S->ack_tree); - - if (D->state != st_authorized) { - return; - } - - if (S->c) { - create_temp_auth_key (TLS, S->c); - } -} - -void tgls_free_session (struct tgl_state *TLS, struct tgl_session *S) { - S->ack_tree = tree_clear_long (S->ack_tree); - if (S->ev) { TLS->timer_methods->free (S->ev); } - if (S->c) { - TLS->net_methods->free (S->c); - } - tfree (S, sizeof (*S)); -} - -void tgls_free_dc (struct tgl_state *TLS, struct tgl_dc *DC) { - if (DC->ip) { tfree_str (DC->ip); } - - struct tgl_session *S = DC->sessions[0]; - if (S) { tgls_free_session (TLS, S); } - - if (DC->ev) { TLS->timer_methods->free (DC->ev); } - tfree (DC, sizeof (*DC)); -} - -void tgls_free_pubkey (struct tgl_state *TLS) { - RSA_free (TLS->pubKey); -} diff --git a/mtproto-client.h b/mtproto-client.h deleted file mode 100644 index 692a4b8..0000000 --- a/mtproto-client.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Nikolay Durov, Andrey Lopatin 2012-2013 - Vitaly Valtman 2013-2014 -*/ -#ifndef __MTPROTO_CLIENT_H__ -#define __MTPROTO_CLIENT_H__ -//#include "net.h" -#include -//void on_start (void); -//..long long encrypt_send_message (struct connection *c, int *msg, int msg_ints, int useful); -//void dc_authorize (struct tgl_dc *DC); -//void work_update (struct connection *c, long long msg_id); -//void work_update_binlog (void); -//int check_g (unsigned char p[256], BIGNUM *g); -//int check_g_bn (BIGNUM *p, BIGNUM *g); -//int check_DH_params (BIGNUM *p, int g); -//void secure_random (void *s, int l); - -#include "tgl.h" - -struct connection; -struct tgl_dc; -//#include "queries.h" -#define TG_APP_HASH "36722c72256a24c1225de00eb6a1ca74" -#define TG_APP_ID 2899 - -#define ACK_TIMEOUT 1 -#define MAX_DC_ID 10 - -struct connection; - -long long tglmp_encrypt_send_message (struct tgl_state *TLS, struct connection *c, int *msg, int msg_ints, int flags); -void tglmp_dc_create_session (struct tgl_state *TLS, struct tgl_dc *DC); -int tglmp_check_g (struct tgl_state *TLS, unsigned char p[256], BIGNUM *g); -int tglmp_check_DH_params (struct tgl_state *TLS, BIGNUM *p, int g); -struct tgl_dc *tglmp_alloc_dc (struct tgl_state *TLS, int id, char *ip, int port); -void tglmp_regenerate_temp_auth_key (struct tgl_state *TLS, struct tgl_dc *D); - -void tgln_insert_msg_id (struct tgl_state *TLS, struct tgl_session *S, long long id); -void tglmp_on_start (struct tgl_state *TLS); -void tgl_dc_authorize (struct tgl_state *TLS, struct tgl_dc *DC); -void tgls_free_dc (struct tgl_state *TLS, struct tgl_dc *DC); -void tgls_free_pubkey (struct tgl_state *TLS); -#endif diff --git a/mtproto-common.c b/mtproto-common.c deleted file mode 100644 index dd8caaf..0000000 --- a/mtproto-common.c +++ /dev/null @@ -1,394 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Nikolay Durov, Andrey Lopatin 2012-2013 - Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#define _FILE_OFFSET_BITS 64 - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "mtproto-common.h" -#include "include.h" -#include "tools.h" - -#ifdef __MACH__ -#include -#include -#endif - - -static int __packet_buffer[PACKET_BUFFER_SIZE + 16]; -int *tgl_packet_ptr; -int *tgl_packet_buffer = __packet_buffer + 16; - -static long long rsa_encrypted_chunks, rsa_decrypted_chunks; - -//int verbosity; - -static int get_random_bytes (struct tgl_state *TLS, unsigned char *buf, int n) { - int r = 0, h = open ("/dev/random", O_RDONLY | O_NONBLOCK); - if (h >= 0) { - r = read (h, buf, n); - if (r > 0) { - vlogprintf (E_DEBUG, "added %d bytes of real entropy to secure random numbers seed\n", r); - } else { - r = 0; - } - close (h); - } - - if (r < n) { - h = open ("/dev/urandom", O_RDONLY); - if (h < 0) { - return r; - } - int s = read (h, buf + r, n - r); - close (h); - if (s > 0) { - r += s; - } - } - - if (r >= (int) sizeof (long)) { - *(long *)buf ^= lrand48 (); - srand48 (*(long *)buf); - } - - return r; -} - - -/* RDTSC */ -#if defined(__i386__) -#define HAVE_RDTSC -static __inline__ unsigned long long rdtsc (void) { - unsigned long long int x; - __asm__ volatile ("rdtsc" : "=A" (x)); - return x; -} -#elif defined(__x86_64__) -#define HAVE_RDTSC -static __inline__ unsigned long long rdtsc (void) { - unsigned hi, lo; - __asm__ __volatile__ ("rdtsc" : "=a"(lo), "=d"(hi)); - return ((unsigned long long) lo) | (((unsigned long long) hi) << 32); -} -#endif - -void tgl_prng_seed (struct tgl_state *TLS, const char *password_filename, int password_length) { - struct timespec T; - tgl_my_clock_gettime (CLOCK_REALTIME, &T); - RAND_add (&T, sizeof (T), 4.0); -#ifdef HAVE_RDTSC - unsigned long long r = rdtsc (); - RAND_add (&r, 8, 4.0); -#endif - unsigned short p = getpid (); - RAND_add (&p, sizeof (p), 0.0); - p = getppid (); - RAND_add (&p, sizeof (p), 0.0); - unsigned char rb[32]; - int s = get_random_bytes (TLS, rb, 32); - if (s > 0) { - RAND_add (rb, s, s); - } - memset (rb, 0, sizeof (rb)); - if (password_filename && password_length > 0) { - int fd = open (password_filename, O_RDONLY); - if (fd < 0) { - vlogprintf (E_WARNING, "Warning: fail to open password file - \"%s\", %m.\n", password_filename); - } else { - unsigned char *a = talloc0 (password_length); - int l = read (fd, a, password_length); - if (l < 0) { - vlogprintf (E_WARNING, "Warning: fail to read password file - \"%s\", %m.\n", password_filename); - } else { - vlogprintf (E_DEBUG, "read %d bytes from password file.\n", l); - RAND_add (a, l, l); - } - close (fd); - tfree_secure (a, password_length); - } - } - TLS->BN_ctx = BN_CTX_new (); - ensure_ptr (TLS->BN_ctx); -} - -int tgl_serialize_bignum (BIGNUM *b, char *buffer, int maxlen) { - int itslen = BN_num_bytes (b); - int reqlen; - if (itslen < 254) { - reqlen = itslen + 1; - } else { - reqlen = itslen + 4; - } - int newlen = (reqlen + 3) & -4; - int pad = newlen - reqlen; - reqlen = newlen; - if (reqlen > maxlen) { - return -reqlen; - } - if (itslen < 254) { - *buffer++ = itslen; - } else { - *(int *)buffer = (itslen << 8) + 0xfe; - buffer += 4; - } - int l = BN_bn2bin (b, (unsigned char *)buffer); - assert (l == itslen); - buffer += l; - while (pad --> 0) { - *buffer++ = 0; - } - return reqlen; -} - - -long long tgl_do_compute_rsa_key_fingerprint (RSA *key) { - static char tempbuff[4096]; - static unsigned char sha[20]; - assert (key->n && key->e); - int l1 = tgl_serialize_bignum (key->n, tempbuff, 4096); - assert (l1 > 0); - int l2 = tgl_serialize_bignum (key->e, tempbuff + l1, 4096 - l1); - assert (l2 > 0 && l1 + l2 <= 4096); - SHA1 ((unsigned char *)tempbuff, l1 + l2, sha); - return *(long long *)(sha + 12); -} - -void tgl_out_cstring (const char *str, long len) { - assert (len >= 0 && len < (1 << 24)); - assert ((char *) packet_ptr + len + 8 < (char *) (packet_buffer + PACKET_BUFFER_SIZE)); - char *dest = (char *) packet_ptr; - if (len < 254) { - *dest++ = len; - } else { - *packet_ptr = (len << 8) + 0xfe; - dest += 4; - } - memcpy (dest, str, len); - dest += len; - while ((long) dest & 3) { - *dest++ = 0; - } - packet_ptr = (int *) dest; -} - -void tgl_out_cstring_careful (const char *str, long len) { - assert (len >= 0 && len < (1 << 24)); - assert ((char *) packet_ptr + len + 8 < (char *) (packet_buffer + PACKET_BUFFER_SIZE)); - char *dest = (char *) packet_ptr; - if (len < 254) { - dest++; - if (dest != str) { - memmove (dest, str, len); - } - dest[-1] = len; - } else { - dest += 4; - if (dest != str) { - memmove (dest, str, len); - } - *packet_ptr = (len << 8) + 0xfe; - } - dest += len; - while ((long) dest & 3) { - *dest++ = 0; - } - packet_ptr = (int *) dest; -} - - -void tgl_out_data (const void *data, long len) { - assert (len >= 0 && len < (1 << 24) && !(len & 3)); - assert ((char *) packet_ptr + len + 8 < (char *) (packet_buffer + PACKET_BUFFER_SIZE)); - memcpy (packet_ptr, data, len); - packet_ptr += len >> 2; -} - -int *tgl_in_ptr, *tgl_in_end; - -int tgl_fetch_bignum (BIGNUM *x) { - int l = prefetch_strlen (); - if (l < 0) { - return l; - } - char *str = fetch_str (l); - assert (BN_bin2bn ((unsigned char *) str, l, x) == x); - return l; -} - -int tgl_pad_rsa_encrypt (struct tgl_state *TLS, char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *E) { - int pad = (255000 - from_len - 32) % 255 + 32; - int chunks = (from_len + pad) / 255; - int bits = BN_num_bits (N); - assert (bits >= 2041 && bits <= 2048); - assert (from_len > 0 && from_len <= 2550); - assert (size >= chunks * 256); - assert (RAND_pseudo_bytes ((unsigned char *) from + from_len, pad) >= 0); - int i; - BIGNUM x, y; - BN_init (&x); - BN_init (&y); - rsa_encrypted_chunks += chunks; - for (i = 0; i < chunks; i++) { - BN_bin2bn ((unsigned char *) from, 255, &x); - assert (BN_mod_exp (&y, &x, E, N, TLS->BN_ctx) == 1); - unsigned l = 256 - BN_num_bytes (&y); - assert (l <= 256); - memset (to, 0, l); - BN_bn2bin (&y, (unsigned char *) to + l); - to += 256; - } - BN_free (&x); - BN_free (&y); - return chunks * 256; -} - -int tgl_pad_rsa_decrypt (struct tgl_state *TLS, char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *D) { - if (from_len < 0 || from_len > 0x1000 || (from_len & 0xff)) { - return -1; - } - int chunks = (from_len >> 8); - int bits = BN_num_bits (N); - assert (bits >= 2041 && bits <= 2048); - assert (size >= chunks * 255); - int i; - BIGNUM x, y; - BN_init (&x); - BN_init (&y); - for (i = 0; i < chunks; i++) { - ++rsa_decrypted_chunks; - BN_bin2bn ((unsigned char *) from, 256, &x); - assert (BN_mod_exp (&y, &x, D, N, TLS->BN_ctx) == 1); - int l = BN_num_bytes (&y); - if (l > 255) { - BN_free (&x); - BN_free (&y); - return -1; - } - assert (l >= 0 && l <= 255); - memset (to, 0, 255 - l); - BN_bn2bin (&y, (unsigned char *) to + 255 - l); - to += 255; - } - BN_free (&x); - BN_free (&y); - return chunks * 255; -} - -static unsigned char aes_key_raw[32], aes_iv[32]; -static AES_KEY aes_key; - -void tgl_init_aes_unauth (const char server_nonce[16], const char hidden_client_nonce[32], int encrypt) { - static unsigned char buffer[64], hash[20]; - memcpy (buffer, hidden_client_nonce, 32); - memcpy (buffer + 32, server_nonce, 16); - SHA1 (buffer, 48, aes_key_raw); - memcpy (buffer + 32, hidden_client_nonce, 32); - SHA1 (buffer, 64, aes_iv + 8); - memcpy (buffer, server_nonce, 16); - memcpy (buffer + 16, hidden_client_nonce, 32); - SHA1 (buffer, 48, hash); - memcpy (aes_key_raw + 20, hash, 12); - memcpy (aes_iv, hash + 12, 8); - memcpy (aes_iv + 28, hidden_client_nonce, 4); - if (encrypt == AES_ENCRYPT) { - AES_set_encrypt_key (aes_key_raw, 32*8, &aes_key); - } else { - AES_set_decrypt_key (aes_key_raw, 32*8, &aes_key); - } - memset (aes_key_raw, 0, sizeof (aes_key_raw)); -} - -void tgl_init_aes_auth (char auth_key[192], char msg_key[16], int encrypt) { - static unsigned char buffer[48], hash[20]; - // sha1_a = SHA1 (msg_key + substr (auth_key, 0, 32)); - // sha1_b = SHA1 (substr (auth_key, 32, 16) + msg_key + substr (auth_key, 48, 16)); - // sha1_с = SHA1 (substr (auth_key, 64, 32) + msg_key); - // sha1_d = SHA1 (msg_key + substr (auth_key, 96, 32)); - // aes_key = substr (sha1_a, 0, 8) + substr (sha1_b, 8, 12) + substr (sha1_c, 4, 12); - // aes_iv = substr (sha1_a, 8, 12) + substr (sha1_b, 0, 8) + substr (sha1_c, 16, 4) + substr (sha1_d, 0, 8); - memcpy (buffer, msg_key, 16); - memcpy (buffer + 16, auth_key, 32); - SHA1 (buffer, 48, hash); - memcpy (aes_key_raw, hash, 8); - memcpy (aes_iv, hash + 8, 12); - - memcpy (buffer, auth_key + 32, 16); - memcpy (buffer + 16, msg_key, 16); - memcpy (buffer + 32, auth_key + 48, 16); - SHA1 (buffer, 48, hash); - memcpy (aes_key_raw + 8, hash + 8, 12); - memcpy (aes_iv + 12, hash, 8); - - memcpy (buffer, auth_key + 64, 32); - memcpy (buffer + 32, msg_key, 16); - SHA1 (buffer, 48, hash); - memcpy (aes_key_raw + 20, hash + 4, 12); - memcpy (aes_iv + 20, hash + 16, 4); - - memcpy (buffer, msg_key, 16); - memcpy (buffer + 16, auth_key + 96, 32); - SHA1 (buffer, 48, hash); - memcpy (aes_iv + 24, hash, 8); - - if (encrypt == AES_ENCRYPT) { - AES_set_encrypt_key (aes_key_raw, 32*8, &aes_key); - } else { - AES_set_decrypt_key (aes_key_raw, 32*8, &aes_key); - } - memset (aes_key_raw, 0, sizeof (aes_key_raw)); -} - -int tgl_pad_aes_encrypt (char *from, int from_len, char *to, int size) { - int padded_size = (from_len + 15) & -16; - assert (from_len > 0 && padded_size <= size); - if (from_len < padded_size) { - assert (RAND_pseudo_bytes ((unsigned char *) from + from_len, padded_size - from_len) >= 0); - } - AES_ige_encrypt ((unsigned char *) from, (unsigned char *) to, padded_size, &aes_key, aes_iv, AES_ENCRYPT); - return padded_size; -} - -int tgl_pad_aes_decrypt (char *from, int from_len, char *to, int size) { - if (from_len <= 0 || from_len > size || (from_len & 15)) { - return -1; - } - AES_ige_encrypt ((unsigned char *) from, (unsigned char *) to, from_len, &aes_key, aes_iv, AES_DECRYPT); - return from_len; -} - - diff --git a/mtproto-common.h b/mtproto-common.h deleted file mode 100644 index a1d1ce5..0000000 --- a/mtproto-common.h +++ /dev/null @@ -1,384 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Nikolay Durov, Andrey Lopatin 2012-2013 - Vitaly Valtman 2013-2014 -*/ -#ifndef __MTPROTO_COMMON_H__ -#define __MTPROTO_COMMON_H__ - -#include -#include -#include -#include -#include -#include - -//#include "interface.h" -#include "tools.h" -#include "auto/constants.h" - -#include "tgl.h" -#include "tgl-inner.h" -/* DH key exchange protocol data structures */ -#define CODE_req_pq 0x60469778 -#define CODE_resPQ 0x05162463 -#define CODE_req_DH_params 0xd712e4be -#define CODE_p_q_inner_data 0x83c95aec -#define CODE_p_q_inner_data_temp 0x3c6a84d4 -#define CODE_server_DH_inner_data 0xb5890dba -#define CODE_server_DH_params_fail 0x79cb045d -#define CODE_server_DH_params_ok 0xd0e8075c -#define CODE_set_client_DH_params 0xf5045f1f -#define CODE_client_DH_inner_data 0x6643b654 -#define CODE_dh_gen_ok 0x3bcbf734 -#define CODE_dh_gen_retry 0x46dc1fb9 -#define CODE_dh_gen_fail 0xa69dae02 - -#define CODE_bind_auth_key_inner 0x75a3f765 - -/* service messages */ -#define CODE_rpc_result 0xf35c6d01 -#define CODE_rpc_error 0x2144ca19 -#define CODE_msg_container 0x73f1f8dc -#define CODE_msg_copy 0xe06046b2 -#define CODE_msgs_ack 0x62d6b459 -#define CODE_bad_msg_notification 0xa7eff811 -#define CODE_bad_server_salt 0xedab447b -#define CODE_msgs_state_req 0xda69fb52 -#define CODE_msgs_state_info 0x04deb57d -#define CODE_msgs_all_info 0x8cc0d131 -#define CODE_new_session_created 0x9ec20908 -#define CODE_msg_resend_req 0x7d861a08 -#define CODE_ping 0x7abe77ec -#define CODE_pong 0x347773c5 -#define CODE_destroy_session 0xe7512126 -#define CODE_destroy_session_ok 0xe22045fc -#define CODE_destroy_session_none 0x62d350c9 -#define CODE_destroy_sessions 0x9a6face8 -#define CODE_destroy_sessions_res 0xa8164668 -#define CODE_get_future_salts 0xb921bd04 -#define CODE_future_salt 0x0949d9dc -#define CODE_future_salts 0xae500895 -#define CODE_rpc_drop_answer 0x58e4a740 -#define CODE_rpc_answer_unknown 0x5e2ad36e -#define CODE_rpc_answer_dropped_running 0xcd78e586 -#define CODE_rpc_answer_dropped 0xa43ad8b7 -#define CODE_msg_detailed_info 0x276d3ec6 -#define CODE_msg_new_detailed_info 0x809db6df -#define CODE_ping_delay_disconnect 0xf3427b8c -#define CODE_gzip_packed 0x3072cfa1 - -#define CODE_input_peer_notify_settings_old 0x3cf4b1be -#define CODE_peer_notify_settings_old 0xddbcd4a5 -#define CODE_user_profile_photo_old 0x990d1493 -#define CODE_config_old 0x232d5905 - -#define CODE_msg_new_detailed_info 0x809db6df - -#define CODE_msg_detailed_info 0x276d3ec6 -/* not really a limit, for struct encrypted_message only */ -// #define MAX_MESSAGE_INTS 16384 -#define MAX_MESSAGE_INTS 1048576 -#define MAX_PROTO_MESSAGE_INTS 1048576 - -#define PACKET_BUFFER_SIZE (16384 * 100 + 16) // temp fix -#pragma pack(push,4) -struct encrypted_message { - // unencrypted header - long long auth_key_id; - char msg_key[16]; - // encrypted part, starts with encrypted header - long long server_salt; - long long session_id; - // long long auth_key_id2; // removed - // first message follows - long long msg_id; - int seq_no; - int msg_len; // divisible by 4 - int message[MAX_MESSAGE_INTS]; -}; - -#pragma pack(pop) - -//BN_CTX *BN_ctx; - -void tgl_prng_seed (struct tgl_state *TLS, const char *password_filename, int password_length); -int tgl_serialize_bignum (BIGNUM *b, char *buffer, int maxlen); -long long tgl_do_compute_rsa_key_fingerprint (RSA *key); - -#define packet_buffer tgl_packet_buffer -#define packet_ptr tgl_packet_ptr - -extern int *tgl_packet_buffer; -extern int *tgl_packet_ptr; - -static inline void out_ints (const int *what, int len) { - assert (packet_ptr + len <= packet_buffer + PACKET_BUFFER_SIZE); - memcpy (packet_ptr, what, len * 4); - packet_ptr += len; -} - - -static inline void out_int (int x) { - assert (packet_ptr + 1 <= packet_buffer + PACKET_BUFFER_SIZE); - *packet_ptr++ = x; -} - - -static inline void out_long (long long x) { - assert (packet_ptr + 2 <= packet_buffer + PACKET_BUFFER_SIZE); - *(long long *)packet_ptr = x; - packet_ptr += 2; -} - -static inline void out_double (double x) { - assert (packet_ptr + 2 <= packet_buffer + PACKET_BUFFER_SIZE); - *(double *)packet_ptr = x; - packet_ptr += 2; -} - -static inline void clear_packet (void) { - packet_ptr = packet_buffer; -} - -void tgl_out_cstring (const char *str, long len); -void tgl_out_cstring_careful (const char *str, long len); -void tgl_out_data (const void *data, long len); - -#define out_cstring tgl_out_cstring -#define out_cstring_careful tgl_out_cstring_careful -#define out_data tgl_out_data - -static inline void out_string (const char *str) { - out_cstring (str, strlen (str)); -} - -static inline void out_bignum (BIGNUM *n) { - int l = tgl_serialize_bignum (n, (char *)packet_ptr, (PACKET_BUFFER_SIZE - (packet_ptr - packet_buffer)) * 4); - assert (l > 0); - packet_ptr += l >> 2; -} - -#define in_ptr tgl_in_ptr -#define in_end tgl_in_end -extern int *tgl_in_ptr, *tgl_in_end; - - -//void fetch_pts (void); -//void fetch_qts (void); -//void fetch_date (void); -//void fetch_seq (void); -static inline int prefetch_strlen (void) { - if (in_ptr >= in_end) { - return -1; - } - unsigned l = *in_ptr; - if ((l & 0xff) < 0xfe) { - l &= 0xff; - return (in_end >= in_ptr + (l >> 2) + 1) ? (int)l : -1; - } else if ((l & 0xff) == 0xfe) { - l >>= 8; - return (l >= 254 && in_end >= in_ptr + ((l + 7) >> 2)) ? (int)l : -1; - } else { - return -1; - } -} - -static inline char *fetch_str (int len) { - assert (len >= 0); - if (len < 254) { - char *str = (char *) in_ptr + 1; - in_ptr += 1 + (len >> 2); - return str; - } else { - char *str = (char *) in_ptr + 4; - in_ptr += (len + 7) >> 2; - return str; - } -} - -static inline char *fetch_str_dup (void) { - int l = prefetch_strlen (); - assert (l >= 0); - int i; - char *s = fetch_str (l); - for (i = 0; i < l; i++) { - if (!s[i]) { break; } - } - char *r = talloc (i + 1); - memcpy (r, s, i); - r[i] = 0; - return r; -} - -static inline int fetch_update_str (char **s) { - if (!*s) { - *s = fetch_str_dup (); - return 1; - } - int l = prefetch_strlen (); - char *r = fetch_str (l); - if (memcmp (*s, r, l) || (*s)[l]) { - tfree_str (*s); - *s = talloc (l + 1); - memcpy (*s, r, l); - (*s)[l] = 0; - return 1; - } - return 0; -} - -static inline int fetch_update_int (int *value) { - if (*value == *in_ptr) { - in_ptr ++; - return 0; - } else { - *value = *(in_ptr ++); - return 1; - } -} - -static inline int fetch_update_long (long long *value) { - if (*value == *(long long *)in_ptr) { - in_ptr += 2; - return 0; - } else { - *value = *(long long *)(in_ptr); - in_ptr += 2; - return 1; - } -} - -static inline int set_update_int (int *value, int new_value) { - if (*value == new_value) { - return 0; - } else { - *value = new_value; - return 1; - } -} - -static inline void fetch_skip (int n) { - in_ptr += n; - assert (in_ptr <= in_end); -} - -static inline void fetch_skip_str (void) { - int l = prefetch_strlen (); - assert (l >= 0); - fetch_str (l); -} - -static inline long have_prefetch_ints (void) { - return in_end - in_ptr; -} - -int tgl_fetch_bignum (BIGNUM *x); -#define fetch_bignum tgl_fetch_bignum - -static inline int fetch_int (void) { - assert (in_ptr + 1 <= in_end); - return *(in_ptr ++); -} - -static inline int fetch_bool (void) { - assert (in_ptr + 1 <= in_end); - assert (*(in_ptr) == (int)CODE_bool_true || *(in_ptr) == (int)CODE_bool_false); - return *(in_ptr ++) == (int)CODE_bool_true; -} - -static inline int prefetch_int (void) { - assert (in_ptr < in_end); - return *(in_ptr); -} - -static inline void prefetch_data (void *data, int size) { - assert (in_ptr + (size >> 2) <= in_end); - memcpy (data, in_ptr, size); -} - -static inline void fetch_data (void *data, int size) { - assert (in_ptr + (size >> 2) <= in_end); - memcpy (data, in_ptr, size); - assert (!(size & 3)); - in_ptr += (size >> 2); -} - -static inline long long fetch_long (void) { - assert (in_ptr + 2 <= in_end); - long long r = *(long long *)in_ptr; - in_ptr += 2; - return r; -} - -static inline double fetch_double (void) { - assert (in_ptr + 2 <= in_end); - double r = *(double *)in_ptr; - in_ptr += 2; - return r; -} - -static inline void fetch_ints (void *data, int count) { - assert (in_ptr + count <= in_end); - memcpy (data, in_ptr, 4 * count); - in_ptr += count; -} - -static inline void fetch256 (void *buf) { - int l = prefetch_strlen (); - assert (l >= 0); - char *s = fetch_str (l); - if (l < 256) { - memcpy (buf + 256 - l, s, l); - } else { - memcpy (buf, s + (l - 256), 256); - } -} - -static inline int in_remaining (void) { - return 4 * (in_end - in_ptr); -} - -//int get_random_bytes (unsigned char *buf, int n); - -int tgl_pad_rsa_encrypt (struct tgl_state *TLS, char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *E); -int tgl_pad_rsa_decrypt (struct tgl_state *TLS, char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *D); - -//extern long long rsa_encrypted_chunks, rsa_decrypted_chunks; - -//extern unsigned char aes_key_raw[32], aes_iv[32]; -//extern AES_KEY aes_key; - -void tgl_init_aes_unauth (const char server_nonce[16], const char hidden_client_nonce[32], int encrypt); -void tgl_init_aes_auth (char auth_key[192], char msg_key[16], int encrypt); -int tgl_pad_aes_encrypt (char *from, int from_len, char *to, int size); -int tgl_pad_aes_decrypt (char *from, int from_len, char *to, int size); -/* -static inline void hexdump_in (void) { - hexdump (in_ptr, in_end); -} - -static inline void hexdump_out (void) { - hexdump (packet_buffer, packet_ptr); -}*/ - -#ifdef __MACH__ -#define CLOCK_REALTIME 0 -#define CLOCK_MONOTONIC 1 -#endif -#endif diff --git a/net.c b/net.c deleted file mode 100644 index 8f48e80..0000000 --- a/net.c +++ /dev/null @@ -1,623 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#define _GNU_SOURCE -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#ifdef EVENT_V2 -#include -#else -#include -#include "event-old.h" -#endif -#include -#include - -#include "net.h" -#include "include.h" -#include "tgl.h" -#include "tgl-inner.h" -//#include "mtproto-client.h" -//#include "mtproto-common.h" -#include "tree.h" -#include "tools.h" - -#ifndef POLLRDHUP -#define POLLRDHUP 0 -#endif - -//double get_utime (int clock_id); - -//extern struct mtproto_methods auth_methods; - -static void fail_connection (struct connection *c); - -#define PING_TIMEOUT 10 - -static void start_ping_timer (struct connection *c); -static void ping_alarm (evutil_socket_t fd, short what, void *arg) { - struct connection *c = arg; - struct tgl_state *TLS = c->TLS; - vlogprintf (E_DEBUG + 2,"ping alarm\n"); - assert (c->state == conn_ready || c->state == conn_connecting); - if (tglt_get_double_time () - c->last_receive_time > 6 * PING_TIMEOUT) { - vlogprintf (E_WARNING, "fail connection: reason: ping timeout\n"); - c->state = conn_failed; - fail_connection (c); - } else if (tglt_get_double_time () - c->last_receive_time > 3 * PING_TIMEOUT && c->state == conn_ready) { - tgl_do_send_ping (c->TLS, c); - start_ping_timer (c); - } else { - start_ping_timer (c); - } -} - -static void stop_ping_timer (struct connection *c) { - event_del (c->ping_ev); -} - -static void start_ping_timer (struct connection *c) { - static struct timeval ptimeout = { PING_TIMEOUT, 0}; - event_add (c->ping_ev, &ptimeout); -} - -static void restart_connection (struct connection *c); - -static void fail_alarm (evutil_socket_t fd, short what, void *arg) { - struct connection *c = arg; - c->in_fail_timer = 0; - restart_connection (c); -} - -static void start_fail_timer (struct connection *c) { - if (c->in_fail_timer) { return; } - c->in_fail_timer = 1; - - static struct timeval ptimeout = { 10, 0}; - event_add (c->fail_ev, &ptimeout); -} - -static struct connection_buffer *new_connection_buffer (int size) { - struct connection_buffer *b = talloc0 (sizeof (*b)); - b->start = talloc (size); - b->end = b->start + size; - b->rptr = b->wptr = b->start; - return b; -} - -static void delete_connection_buffer (struct connection_buffer *b) { - tfree (b->start, b->end - b->start); - tfree (b, sizeof (*b)); -} - -int tgln_write_out (struct connection *c, const void *_data, int len) { - struct tgl_state *TLS = c->TLS; - vlogprintf (E_DEBUG, "write_out: %d bytes\n", len); - const unsigned char *data = _data; - if (!len) { return 0; } - assert (len > 0); - int x = 0; - if (!c->out_bytes) { - event_add (c->write_ev, 0); - } - if (!c->out_head) { - struct connection_buffer *b = new_connection_buffer (1 << 20); - c->out_head = c->out_tail = b; - } - while (len) { - if (c->out_tail->end - c->out_tail->wptr >= len) { - memcpy (c->out_tail->wptr, data, len); - c->out_tail->wptr += len; - c->out_bytes += len; - return x + len; - } else { - int y = c->out_tail->end - c->out_tail->wptr; - assert (y < len); - memcpy (c->out_tail->wptr, data, y); - x += y; - len -= y; - data += y; - struct connection_buffer *b = new_connection_buffer (1 << 20); - c->out_tail->next = b; - b->next = 0; - c->out_tail = b; - c->out_bytes += y; - } - } - return x; -} - -int tgln_read_in (struct connection *c, void *_data, int len) { - unsigned char *data = _data; - if (!len) { return 0; } - assert (len > 0); - if (len > c->in_bytes) { - len = c->in_bytes; - } - int x = 0; - while (len) { - int y = c->in_head->wptr - c->in_head->rptr; - if (y > len) { - memcpy (data, c->in_head->rptr, len); - c->in_head->rptr += len; - c->in_bytes -= len; - return x + len; - } else { - memcpy (data, c->in_head->rptr, y); - c->in_bytes -= y; - x += y; - data += y; - len -= y; - void *old = c->in_head; - c->in_head = c->in_head->next; - if (!c->in_head) { - c->in_tail = 0; - } - delete_connection_buffer (old); - } - } - return x; -} - -int tgln_read_in_lookup (struct connection *c, void *_data, int len) { - unsigned char *data = _data; - if (!len || !c->in_bytes) { return 0; } - assert (len > 0); - if (len > c->in_bytes) { - len = c->in_bytes; - } - int x = 0; - struct connection_buffer *b = c->in_head; - while (len) { - int y = b->wptr - b->rptr; - if (y >= len) { - memcpy (data, b->rptr, len); - return x + len; - } else { - memcpy (data, b->rptr, y); - x += y; - data += y; - len -= y; - b = b->next; - } - } - return x; -} - -void tgln_flush_out (struct connection *c UU) { -} - -#define MAX_CONNECTIONS 100 -static struct connection *Connections[MAX_CONNECTIONS]; -static int max_connection_fd; - -static void rotate_port (struct connection *c) { - switch (c->port) { - case 443: - c->port = 80; - break; - case 80: - c->port = 25; - break; - case 25: - c->port = 443; - break; - } -} - -static void try_read (struct connection *c); -static void try_write (struct connection *c); - -static void conn_try_read (evutil_socket_t fd, short what, void *arg) { - struct connection *c = arg; - struct tgl_state *TLS = c->TLS; - vlogprintf (E_DEBUG + 1, "Try read. Fd = %d\n", c->fd); - try_read (c); -} -static void conn_try_write (evutil_socket_t fd, short what, void *arg) { - struct connection *c = arg; - struct tgl_state *TLS = c->TLS; - if (c->state == conn_connecting) { - c->state = conn_ready; - c->methods->ready (TLS, c); - } - try_write (c); - if (c->out_bytes) { - event_add (c->write_ev, 0); - } -} - -struct connection *tgln_create_connection (struct tgl_state *TLS, const char *host, int port, struct tgl_session *session, struct tgl_dc *dc, struct mtproto_methods *methods) { - struct connection *c = talloc0 (sizeof (*c)); - c->TLS = TLS; - int fd = socket (AF_INET, SOCK_STREAM, 0); - if (fd == -1) { - vlogprintf (E_ERROR, "Can not create socket: %m\n"); - exit (1); - } - assert (fd >= 0 && fd < MAX_CONNECTIONS); - if (fd > max_connection_fd) { - max_connection_fd = fd; - } - int flags = -1; - setsockopt (fd, SOL_SOCKET, SO_REUSEADDR, &flags, sizeof (flags)); - setsockopt (fd, SOL_SOCKET, SO_KEEPALIVE, &flags, sizeof (flags)); - setsockopt (fd, IPPROTO_TCP, TCP_NODELAY, &flags, sizeof (flags)); - - struct sockaddr_in addr; - addr.sin_family = AF_INET; - addr.sin_port = htons (port); - addr.sin_addr.s_addr = inet_addr (host); - - - fcntl (fd, F_SETFL, O_NONBLOCK); - - if (connect (fd, (struct sockaddr *) &addr, sizeof (addr)) == -1) { - //vlogprintf (E_ERROR, "Can not connect to %s:%d %m\n", host, port); - if (errno != EINPROGRESS) { - vlogprintf (E_ERROR, "Can not connect to %s:%d %m\n", host, port); - close (fd); - tfree (c, sizeof (*c)); - return 0; - } - } - - c->fd = fd; - c->state = conn_connecting; - c->last_receive_time = tglt_get_double_time (); - c->ip = tstrdup (host); - c->flags = 0; - c->port = port; - assert (!Connections[fd]); - Connections[fd] = c; - - c->ping_ev = evtimer_new (TLS->ev_base, ping_alarm, c); - c->fail_ev = evtimer_new (TLS->ev_base, fail_alarm, c); - c->write_ev = event_new (TLS->ev_base, c->fd, EV_WRITE, conn_try_write, c); - - struct timeval tv = {5, 0}; - c->read_ev = event_new (TLS->ev_base, c->fd, EV_READ | EV_PERSIST, conn_try_read, c); - event_add (c->read_ev, &tv); - - start_ping_timer (c); - - c->dc = dc; - c->session = session; - c->methods = methods; - - char byte = 0xef; - assert (tgln_write_out (c, &byte, 1) == 1); - tgln_flush_out (c); - - return c; -} - -static void restart_connection (struct connection *c) { - struct tgl_state *TLS = c->TLS; - if (c->last_connect_time == time (0)) { - start_fail_timer (c); - return; - } - - c->last_connect_time = time (0); - int fd = socket (AF_INET, SOCK_STREAM, 0); - if (fd == -1) { - vlogprintf (E_ERROR, "Can not create socket: %m\n"); - exit (1); - } - assert (fd >= 0 && fd < MAX_CONNECTIONS); - if (fd > max_connection_fd) { - max_connection_fd = fd; - } - int flags = -1; - setsockopt (fd, SOL_SOCKET, SO_REUSEADDR, &flags, sizeof (flags)); - setsockopt (fd, SOL_SOCKET, SO_KEEPALIVE, &flags, sizeof (flags)); - setsockopt (fd, IPPROTO_TCP, TCP_NODELAY, &flags, sizeof (flags)); - - struct sockaddr_in addr; - addr.sin_family = AF_INET; - addr.sin_port = htons (c->port); - if (strcmp (c->ip, c->dc->ip)) { - tfree_str (c->ip); - c->ip = tstrdup (c->dc->ip); - } - addr.sin_addr.s_addr = inet_addr (c->ip); - - - fcntl (fd, F_SETFL, O_NONBLOCK); - - if (connect (fd, (struct sockaddr *) &addr, sizeof (addr)) == -1) { - if (errno != EINPROGRESS) { - vlogprintf (E_WARNING, "Can not connect to %s:%d %m\n", c->ip, c->port); - start_fail_timer (c); - close (fd); - return; - } - } - - c->fd = fd; - c->state = conn_connecting; - c->last_receive_time = tglt_get_double_time (); - start_ping_timer (c); - Connections[fd] = c; - - c->write_ev = event_new (TLS->ev_base, c->fd, EV_WRITE, conn_try_write, c); - - struct timeval tv = {5, 0}; - c->read_ev = event_new (TLS->ev_base, c->fd, EV_READ | EV_PERSIST, conn_try_read, c); - event_add (c->read_ev, &tv); - - char byte = 0xef; - assert (tgln_write_out (c, &byte, 1) == 1); - tgln_flush_out (c); -} - -static void fail_connection (struct connection *c) { - struct tgl_state *TLS = c->TLS; - if (c->state == conn_ready || c->state == conn_connecting) { - stop_ping_timer (c); - } - event_free (c->write_ev); - event_free (c->read_ev); - - rotate_port (c); - struct connection_buffer *b = c->out_head; - while (b) { - struct connection_buffer *d = b; - b = b->next; - delete_connection_buffer (d); - } - b = c->in_head; - while (b) { - struct connection_buffer *d = b; - b = b->next; - delete_connection_buffer (d); - } - c->out_head = c->out_tail = c->in_head = c->in_tail = 0; - c->state = conn_failed; - c->out_bytes = c->in_bytes = 0; - close (c->fd); - Connections[c->fd] = 0; - vlogprintf (E_NOTICE, "Lost connection to server... %s:%d\n", c->ip, c->port); - restart_connection (c); -} - -//extern FILE *log_net_f; -static void try_write (struct connection *c) { - struct tgl_state *TLS = c->TLS; - vlogprintf (E_DEBUG, "try write: fd = %d\n", c->fd); - int x = 0; - while (c->out_head) { - int r = write (c->fd, c->out_head->rptr, c->out_head->wptr - c->out_head->rptr); - if (r >= 0) { - x += r; - c->out_head->rptr += r; - if (c->out_head->rptr != c->out_head->wptr) { - break; - } - struct connection_buffer *b = c->out_head; - c->out_head = b->next; - if (!c->out_head) { - c->out_tail = 0; - } - delete_connection_buffer (b); - } else { - if (errno != EAGAIN && errno != EWOULDBLOCK) { - vlogprintf (E_NOTICE, "fail_connection: write_error %m\n"); - fail_connection (c); - return; - } else { - break; - } - } - } - vlogprintf (E_DEBUG, "Sent %d bytes to %d\n", x, c->fd); - c->out_bytes -= x; -} - -static void try_rpc_read (struct connection *c) { - assert (c->in_head); - struct tgl_state *TLS = c->TLS; - - while (1) { - if (c->in_bytes < 1) { return; } - unsigned len = 0; - unsigned t = 0; - assert (tgln_read_in_lookup (c, &len, 1) == 1); - if (len >= 1 && len <= 0x7e) { - if (c->in_bytes < (int)(1 + 4 * len)) { return; } - } else { - if (c->in_bytes < 4) { return; } - assert (tgln_read_in_lookup (c, &len, 4) == 4); - len = (len >> 8); - if (c->in_bytes < (int)(4 + 4 * len)) { return; } - len = 0x7f; - } - - if (len >= 1 && len <= 0x7e) { - assert (tgln_read_in (c, &t, 1) == 1); - assert (t == len); - assert (len >= 1); - } else { - assert (len == 0x7f); - assert (tgln_read_in (c, &len, 4) == 4); - len = (len >> 8); - assert (len >= 1); - } - len *= 4; - int op; - assert (tgln_read_in_lookup (c, &op, 4) == 4); - c->methods->execute (TLS, c, op, len); - } -} - -static void try_read (struct connection *c) { - struct tgl_state *TLS = c->TLS; - vlogprintf (E_DEBUG, "try read: fd = %d\n", c->fd); - if (!c->in_tail) { - c->in_head = c->in_tail = new_connection_buffer (1 << 20); - } - #ifdef EVENT_V1 - struct timeval tv = {5, 0}; - event_add (c->read_ev, &tv); - #endif - int x = 0; - while (1) { - int r = read (c->fd, c->in_tail->wptr, c->in_tail->end - c->in_tail->wptr); - if (r > 0) { - c->last_receive_time = tglt_get_double_time (); - stop_ping_timer (c); - start_ping_timer (c); - } - if (r >= 0) { - c->in_tail->wptr += r; - x += r; - if (c->in_tail->wptr != c->in_tail->end) { - break; - } - struct connection_buffer *b = new_connection_buffer (1 << 20); - c->in_tail->next = b; - c->in_tail = b; - } else { - if (errno != EAGAIN && errno != EWOULDBLOCK) { - vlogprintf (E_NOTICE, "fail_connection: read_error %m\n"); - fail_connection (c); - return; - } else { - break; - } - } - } - vlogprintf (E_DEBUG, "Received %d bytes from %d\n", x, c->fd); - c->in_bytes += x; - if (x) { - try_rpc_read (c); - } -} -/* -int tgl_connections_make_poll_array (struct pollfd *fds, int max) { - int _max = max; - int i; - for (i = 0; i <= max_connection_fd; i++) { - if (Connections[i] && Connections[i]->state == conn_failed) { - restart_connection (Connections[i]); - } - if (Connections[i] && Connections[i]->state != conn_failed) { - assert (max > 0); - struct connection *c = Connections[i]; - fds[0].fd = c->fd; - fds[0].events = POLLERR | POLLHUP | POLLRDHUP | POLLIN; - if (c->out_bytes || c->state == conn_connecting) { - fds[0].events |= POLLOUT; - } - fds ++; - max --; - } - } - return _max - max; -} - -void tgl_connections_poll_result (struct pollfd *fds, int max) { - int i; - for (i = 0; i < max; i++) { - struct connection *c = Connections[fds[i].fd]; - if (fds[i].revents & POLLIN) { - try_read (c); - } - if (fds[i].revents & (POLLHUP | POLLERR | POLLRDHUP)) { - vlogprintf (E_NOTICE, "fail_connection: events_mask=0x%08x\n", fds[i].revents); - fail_connection (c); - } else if (fds[i].revents & POLLOUT) { - if (c->state == conn_connecting) { - vlogprintf (E_DEBUG, "connection ready\n"); - c->state = conn_ready; - c->last_receive_time = tglt_get_double_time (); - } - if (c->out_bytes) { - try_write (c); - } - } - } -}*/ - -static void incr_out_packet_num (struct connection *c) { - c->out_packet_num ++; -} - -static struct tgl_dc *get_dc (struct connection *c) { - return c->dc; -} - -static struct tgl_session *get_session (struct connection *c) { - return c->session; -} - -static void tgln_free (struct connection *c) { - if (c->ip) { tfree_str (c->ip); } - struct connection_buffer *b = c->out_head; - while (b) { - struct connection_buffer *d = b; - b = b->next; - delete_connection_buffer (d); - } - b = c->in_head; - while (b) { - struct connection_buffer *d = b; - b = b->next; - delete_connection_buffer (d); - } - - if (c->ping_ev) { event_free (c->ping_ev); } - if (c->fail_ev) { event_free (c->fail_ev); } - if (c->read_ev) { event_free (c->read_ev); } - if (c->write_ev) { event_free (c->write_ev); } - - if (c->fd >= 0) { close (c->fd); } - tfree (c, sizeof (*c)); -} - -struct tgl_net_methods tgl_conn_methods = { - .write_out = tgln_write_out, - .read_in = tgln_read_in, - .read_in_lookup = tgln_read_in_lookup, - .flush_out = tgln_flush_out, - .incr_out_packet_num = incr_out_packet_num, - .get_dc = get_dc, - .get_session = get_session, - .create_connection = tgln_create_connection, - .free = tgln_free -}; diff --git a/net.h b/net.h deleted file mode 100644 index 00d7da2..0000000 --- a/net.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ -#ifndef __NET_H__ -#define __NET_H__ - -struct connection_buffer { - unsigned char *start; - unsigned char *end; - unsigned char *rptr; - unsigned char *wptr; - struct connection_buffer *next; -}; - -enum conn_state { - conn_none, - conn_connecting, - conn_ready, - conn_failed, - conn_stopped -}; - -struct connection { - int fd; - char *ip; - int port; - int flags; - enum conn_state state; - int ipv6[4]; - struct connection_buffer *in_head; - struct connection_buffer *in_tail; - struct connection_buffer *out_head; - struct connection_buffer *out_tail; - int in_bytes; - int out_bytes; - int packet_num; - int out_packet_num; - int last_connect_time; - int in_fail_timer; - struct mtproto_methods *methods; - struct tgl_state *TLS; - struct tgl_session *session; - struct tgl_dc *dc; - void *extra; - struct event *ping_ev; - struct event *fail_ev; - struct event *read_ev; - struct event *write_ev; - double last_receive_time; -}; - -//extern struct connection *Connections[]; - -int tgln_write_out (struct connection *c, const void *data, int len); -void tgln_flush_out (struct connection *c); -int tgln_read_in (struct connection *c, void *data, int len); -int tgln_read_in_lookup (struct connection *c, void *data, int len); - -//void tgln_insert_msg_id (struct tgl_session *S, long long id); - -extern struct tgl_net_methods tgl_conn_methods; - -//void create_all_outbound_connections (void); - -//struct connection *create_connection (const char *host, int port, struct tgl_session *session, struct connection_methods *methods); -//struct tgl_dc *tgln_alloc_dc (int id, char *ip, int port); -//void tgln_dc_create_session (struct tgl_dc *DC, struct mtproto_methods *methods); -struct connection *tgln_create_connection (struct tgl_state *TLS, const char *host, int port, struct tgl_session *session, struct tgl_dc *dc, struct mtproto_methods *methods); - -#define GET_DC(c) (c->session->dc) -#endif diff --git a/no-preview.h b/no-preview.h deleted file mode 100644 index 50d1274..0000000 --- a/no-preview.h +++ /dev/null @@ -1,106 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -// Just sample jpg file 90x90 - -int thumb_file_size = (82 * 6 - 2) * 4; -int thumb_file [] = { -0xe0ffd8ff, 0x464a1000, 0x01004649, 0x64000101, 0x00006400, 0xa002e2ff, -0x5f434349, 0x464f5250, 0x00454c49, 0x00000101, 0x636c9002, 0x3004736d, -0x6e6d0000, 0x47527274, 0x59582042, 0xdd07205a, 0x04000b00, 0x1b001600, -0x63612400, 0x50417073, 0x00004c50, 0x00000000, 0x00000000, 0x00000000, -0x00000000, 0x00000000, 0x00000000, 0x0100d6f6, 0x00000000, 0x636c2dd3, -0x0000736d, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, -0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, -0x65640b00, 0x00006373, 0x00000801, 0x70633800, 0x00007472, 0x00004001, -0x74774e00, 0x00007470, 0x00009001, 0x68631400, 0x00006461, 0x0000a401, -0x58722c00, 0x00005a59, 0x0000d001, 0x58621400, 0x00005a59, 0x0000e401, -0x58671400, 0x00005a59, 0x0000f801, 0x54721400, 0x00004352, 0x00000c02, -0x54672000, 0x00004352, 0x00002c02, 0x54622000, 0x00004352, 0x00004c02, -0x68632000, 0x00006d72, 0x00006c02, 0x6c6d2400, 0x00006375, 0x00000000, -0x00000100, 0x6e650c00, 0x00005355, 0x00001c00, 0x73001c00, 0x47005200, -0x20004200, 0x75006200, 0x6c006900, 0x2d007400, 0x6e006900, 0x6c6d0000, -0x00006375, 0x00000000, 0x00000100, 0x6e650c00, 0x00005355, 0x00003200, -0x4e001c00, 0x20006f00, 0x6f006300, 0x79007000, 0x69007200, 0x68006700, -0x2c007400, 0x75002000, 0x65007300, 0x66002000, 0x65007200, 0x6c006500, -0x00007900, 0x59580000, 0x0000205a, 0x00000000, 0x0100d6f6, 0x00000000, -0x66732dd3, 0x00003233, 0x01000000, 0x00004a0c, 0xffffe305, 0x00002af3, -0x00009b07, 0xffff87fd, 0xffffa2fb, 0x0000a3fd, 0x0000d803, 0x595894c0, -0x0000205a, 0x00000000, 0x0000946f, 0x0000ee38, 0x59589003, 0x0000205a, -0x00000000, 0x00009d24, 0x0000830f, 0x5958beb6, 0x0000205a, 0x00000000, -0x0000a562, 0x000090b7, 0x6170de18, 0x00006172, 0x03000000, 0x02000000, -0x00006666, 0x0000a7f2, 0x0000590d, 0x0000d013, 0x61705b0a, 0x00006172, -0x03000000, 0x02000000, 0x00006666, 0x0000a7f2, 0x0000590d, 0x0000d013, -0x61705b0a, 0x00006172, 0x03000000, 0x02000000, 0x00006666, 0x0000a7f2, -0x0000590d, 0x0000d013, 0x68635b0a, 0x00006d72, 0x03000000, 0x00000000, -0x0000d7a3, 0x00007b54, 0x0000cd4c, 0x00009a99, 0x00006626, 0xdbff5c0f, -0x14004300, 0x0f120f0e, 0x1112140d, 0x14161712, 0x21331f18, 0x1f1c1c1f, -0x252f2d3f, 0x4e414a33, 0x4841494d, 0x765c5246, 0x6f575264, 0x66484658, -0x7a6f688c, 0x8485847d, 0x9b91634f, 0x769a808f, 0xff7f8481, 0x014300db, -0x1f171716, 0x213c1f1b, 0x547f3c21, 0x7f7f5448, 0x7f7f7f7f, 0x7f7f7f7f, -0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, -0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, 0x7f7f7f7f, 0x1100c0ff, 0x005a0008, -0x2201035a, 0x01110200, 0xff011103, 0x001900c4, 0x01010101, 0x00000101, -0x00000000, 0x00000000, 0x02030400, 0xc4ff0605, 0x00103600, 0x02010401, -0x06050304, 0x00000306, 0x01000000, 0x11030200, 0x05211204, 0x13514131, -0x32146122, 0x23918171, 0x72423424, 0x432515a1, 0xa2827444, 0xc4fff0b3, -0x01011400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x1400c4ff, -0x00000111, 0x00000000, 0x00000000, 0x00000000, 0xdaff0000, 0x01030c00, -0x03110200, 0x003f0011, 0x404434fb, 0xbcb4875c, 0x006b38b0, 0x03dcdb12, -0xf4637f74, 0xe519f153, 0x09d7c5c7, 0x47d29160, 0x20692f18, 0xd06d786a, -0x53f7f922, 0x17b3e260, 0x2fe8668c, 0x1786a473, 0x9775efbd, 0xe917e43a, -0x1d0a1bb0, 0x114d0f82, 0x14651110, 0x35f299ed, 0xe9b09680, 0xf5a4fc2f, -0xe975bd03, 0xb506737b, 0x04444440, 0x5c444044, 0x8e8dedbd, 0xc61adc7b, -0x689c738b, 0x92a0dc01, 0x58e2b77f, 0x7bfb37d1, 0xb5b5e79d, 0xdbf968cc, -0xead3f48d, 0x38ed1313, 0xdea77c86, 0xae089963, 0xc743435a, 0x403fe4ce, -0x392ee1b9, 0xed39e718, 0xd6517e2d, 0x7fc4aa03, 0xb7ad7590, 0x77e7e6ab, -0x34bf705d, 0x7c77ca53, 0x3dea1299, 0x7fb0bcf4, 0x241fadc5, 0x95a7a816, -0x13fbe6f3, 0x3182b135, 0xd1b4b224, 0x1b0d48a2, 0xbf9d26d8, 0x82dc3640, -0x63569a2a, 0xbbd224c3, 0xb9b4714c, 0x1680aec6, 0x3d311856, 0x9b59be91, -0x09876ca6, 0x61d86564, 0x5a9f06d2, 0x36f51b0d, 0x8682e476, 0xacb1b131, -0xd1584363, 0x00456b4d, 0x22d2053b, 0x22202202, 0xf3f30222, 0xe3e513e5, -0xf1e6e1f0, 0x2380496e, 0x5fdcdb68, 0x549b3a27, 0x825e6a6c, 0x6522028b, -0xaf91ccc8, 0x341cf26b, 0x58dbc4b5, 0xf2289add, 0x0854ddbd, 0x0b9247d5, -0xf02b5c54, 0x3f917f92, 0xaf56affd, 0xe3760637, 0x05cebde0, 0xed4c76ce, -0x3cef1b63, 0x7fd8aff8, 0xa0c902ea, 0x7e730d0a, 0x435834f3, 0x26edbb76, -0xd3ec00fd, 0x76d48efa, 0xa8560f2d, 0x0e766331, 0xd319993c, 0x20243209, -0x61b7e6c8, 0x998331d0, 0x640ee802, 0x47a3d493, 0xfab99413, 0x4fd871f1, -0xe9443792, 0x627e051c, 0xd8f3051c, 0x2f28f558, 0x64b51745, 0x1b2bfee3, -0xb8783953, 0x9900fff6, 0xd8176a65, 0x5a3bf56a, 0x1b331fdb, 0x64b3572f, -0xd59a3643, 0xaf3abce1, 0x11dd20bd, 0x01111110, 0x5c141011, 0xb3e3083f, -0xd9b19cc4, 0x17edb20e, 0xa78e9aa1, 0x4ef4de06, 0x00c0bfe7, 0x7e1e442d, -0x9221fe38, 0xedb5c7dc, 0x6338078a, 0x62495b8d, 0xc11d9b8c, 0x49e81b16, -0x51d02bea, 0x3eb86d70, 0xc8bc4f13, 0xa10ec758, 0xd40751c0, 0x5ac94710, -0xc4c8b080, 0x95492b83, 0x975ee696, 0xb7bd96b4, 0x17379cce, 0x82e856e8, -0xe4c2c82a, 0x398e935f, 0x632437ea, 0x7c9c87d2, 0xdc1ddb7c, 0x65a80a48, -0x2309f164, 0x51fab475, 0x081dc11d, 0xda45573b, 0x6622f3f3, 0x48f1b214, -0x676c4edb, 0x243468c7, 0x00ffde60, 0xf1630350, 0xa0076c1d, 0x8f2c0c8b, -0x2383c26b, 0x361a8f4e, 0xaceea6c9, 0x01dd5a5d, 0x11111011, 0xc3780c04, -0xbf093ee2, 0xc7972c0b, 0x00d99040, 0xc0c20eb7, 0x659d3bd4, 0x269ab85e, -0x468e114f, 0x11ad4fdb, 0x83d083d8, 0x8c52f4bd, 0x3c9664bf, 0xa4f9c77c, -0x22a68876, 0xadb18784, 0xf480be83, 0x885a00ea, 0x220e0a88, 0xc303e4f6, -0xc866e058, 0xdddbd661, 0xdf395db1, 0xbad64343, 0xe6e65b03, 0x668e81c3, -0xad619e98, 0xeeb94563, 0xd4d19a3c, 0x3316ce95, 0x9d65f1e1, 0x3bf324fe, -0x0e468f53, 0xc386068c, 0xa89e24f7, 0xf0c7c73b, 0xb60e391f, 0x1b8827cb, -0x58601954, 0xc54f90f9, 0x80886ec5, 0x88088888, 0x1b7bb980, 0xb4c71c23, -0xe6148e39, 0xb12358b8, 0xbd08225d, 0x0ffef085, 0x72b4f025, 0x635ce389, -0xb90277e4, 0x0d05e000, 0x9bf9dbb9, 0x8e749fbc, 0x7ee6abbf, 0x4ddbf4af, -0x728df7f3, 0x10b59adf, 0xe3c38f49, 0xb23c638a, 0xdb3d9349, 0x66899a64, -0x00004dd5, 0xf51b5adf, 0x2220a255, 0xd9ff0f22}; diff --git a/queries.c b/queries.c deleted file mode 100644 index a80c104..0000000 --- a/queries.c +++ /dev/null @@ -1,3879 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#define _FILE_OFFSET_BITS 64 -#include -#include -#include -#include -#include -#include -#include -#include - - -#include "include.h" -#include "mtproto-client.h" -#include "queries.h" -#include "tree.h" -#include "mtproto-common.h" -//#include "telegram.h" -#include "structures.h" -//#include "interface.h" -//#include "net.h" -#include -#include -#include -#include -#include - -#include "no-preview.h" -#include "binlog.h" -#include "updates.h" -#include "auto.h" -#include "tgl.h" - -#define sha1 SHA1 - -#ifndef PATH_MAX -#define PATH_MAX 4096 -#endif - -//int want_dc_num; -//char *get_downloads_directory (void); -//extern int offline_mode; - -//long long cur_uploading_bytes; -//long long cur_uploaded_bytes; -//long long cur_downloading_bytes; -//long long cur_downloaded_bytes; - -//extern int binlog_enabled; -//extern int sync_from_start; - -//static int queries_num; - -static void out_peer_id (struct tgl_state *TLS, tgl_peer_id_t id); -#define QUERY_TIMEOUT 6.0 - -#define memcmp8(a,b) memcmp ((a), (b), 8) -DEFINE_TREE (query, struct query *, memcmp8, 0) ; - -struct query *tglq_query_get (struct tgl_state *TLS, long long id) { - return tree_lookup_query (TLS->queries_tree, (void *)&id); -} - -static int alarm_query (struct tgl_state *TLS, struct query *q) { - assert (q); - vlogprintf (E_DEBUG - 1, "Alarm query %lld\n", q->msg_id); - - TLS->timer_methods->insert (q->ev, QUERY_TIMEOUT); - - if (q->session->session_id == q->session_id) { - clear_packet (); - out_int (CODE_msg_container); - out_int (1); - out_long (q->msg_id); - out_int (q->seq_no); - out_int (4 * q->data_len); - out_ints (q->data, q->data_len); - - tglmp_encrypt_send_message (TLS, q->session->c, packet_buffer, packet_ptr - packet_buffer, q->flags & QUERY_FORCE_SEND); - } else { - q->flags &= ~QUERY_ACK_RECEIVED; - if (tree_lookup_query (TLS->queries_tree, q)) { - TLS->queries_tree = tree_delete_query (TLS->queries_tree, q); - } - q->msg_id = tglmp_encrypt_send_message (TLS, q->session->c, q->data, q->data_len, (q->flags & QUERY_FORCE_SEND) | 1); - TLS->queries_tree = tree_insert_query (TLS->queries_tree, q, lrand48 ()); - q->session_id = q->session->session_id; - if (!(q->session->dc->flags & 4) && !(q->flags & QUERY_FORCE_SEND)) { - q->session_id = 0; - } - } - return 0; -} - -void tglq_query_restart (struct tgl_state *TLS, long long id) { - struct query *q = tglq_query_get (TLS, id); - if (q) { - TLS->timer_methods->delete (q->ev); - alarm_query (TLS, q); - } -} - -static void alarm_query_gateway (struct tgl_state *TLS, void *arg) { - alarm_query (TLS, arg); -} - - -struct query *tglq_send_query_ex (struct tgl_state *TLS, struct tgl_dc *DC, int ints, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra, int flags) { - assert (DC); - assert (DC->auth_key_id); - if (!DC->sessions[0]) { - tglmp_dc_create_session (TLS, DC); - } - vlogprintf (E_DEBUG, "Sending query of size %d to DC (%s:%d)\n", 4 * ints, DC->ip, DC->port); - struct query *q = talloc0 (sizeof (*q)); - q->data_len = ints; - q->data = talloc (4 * ints); - memcpy (q->data, data, 4 * ints); - q->msg_id = tglmp_encrypt_send_message (TLS, DC->sessions[0]->c, data, ints, 1 | (flags & QUERY_FORCE_SEND)); - q->session = DC->sessions[0]; - q->seq_no = q->session->seq_no - 1; - q->session_id = q->session->session_id; - if (!(DC->flags & 4) && !(flags & QUERY_FORCE_SEND)) { - q->session_id = 0; - } - vlogprintf (E_DEBUG, "Msg_id is %lld %p\n", q->msg_id, q); - q->methods = methods; - q->type = methods->type; - q->DC = DC; - q->flags = flags & QUERY_FORCE_SEND; - if (TLS->queries_tree) { - vlogprintf (E_DEBUG + 2, "%lld %lld\n", q->msg_id, TLS->queries_tree->x->msg_id); - } - TLS->queries_tree = tree_insert_query (TLS->queries_tree, q, lrand48 ()); - - q->ev = TLS->timer_methods->alloc (TLS, alarm_query_gateway, q); - TLS->timer_methods->insert (q->ev, QUERY_TIMEOUT); - - q->extra = extra; - q->callback = callback; - q->callback_extra = callback_extra; - TLS->active_queries ++; - return q; -} - -struct query *tglq_send_query (struct tgl_state *TLS, struct tgl_dc *DC, int ints, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra) { - return tglq_send_query_ex (TLS, DC, ints, data, methods, extra, callback, callback_extra, 0); -} - -static int fail_on_error (struct tgl_state *TLS, 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 tglq_query_ack (struct tgl_state *TLS, long long id) { - struct query *q = tglq_query_get (TLS, id); - if (q && !(q->flags & QUERY_ACK_RECEIVED)) { - assert (q->msg_id == id); - q->flags |= QUERY_ACK_RECEIVED; - TLS->timer_methods->delete (q->ev); - } -} - -void tglq_query_error (struct tgl_state *TLS, long long id) { - assert (fetch_int () == CODE_rpc_error); - int error_code = fetch_int (); - int error_len = prefetch_strlen (); - char *error = fetch_str (error_len); - vlogprintf (E_WARNING, "error for query #%lld: #%d :%.*s\n", id, error_code, error_len, error); - struct query *q = tglq_query_get (TLS, id); - if (!q) { - vlogprintf (E_WARNING, "No such query\n"); - } else { - if (!(q->flags & QUERY_ACK_RECEIVED)) { - TLS->timer_methods->delete (q->ev); - } - TLS->queries_tree = tree_delete_query (TLS->queries_tree, q); - int res = 0; - if (q->methods && q->methods->on_error && error_code != 500) { - res = q->methods->on_error (TLS, q, error_code, error_len, error); - } else { - if (error_code == 420 || error_code == 500) { - int wait; - if (error_code == 420) { - if (strncmp (error, "FLOOD_WAIT_", 11)) { - vlogprintf (E_ERROR, "error = '%s'\n", error); - wait = 10; - } else { - wait = atoll (error + 11); - } - } else { - wait = 10; - } - q->flags &= ~QUERY_ACK_RECEIVED; - TLS->timer_methods->insert (q->ev, wait); - q->session_id = 0; - res = 1; - } - } - if (res <= 0) { - tfree (q->data, q->data_len * 4); - TLS->timer_methods->free (q->ev); - } - } - TLS->active_queries --; -} - -#define MAX_PACKED_SIZE (1 << 24) -static int packed_buffer[MAX_PACKED_SIZE / 4]; - -void tglq_query_result (struct tgl_state *TLS, long long id UU) { - vlogprintf (E_DEBUG, "result for query #%lld. Size %ld bytes\n", id, (long)4 * (in_end - in_ptr)); - /*if (verbosity >= 4) { - logprintf ( "result: "); - hexdump_in (); - }*/ - int op = prefetch_int (); - int *end = 0; - int *eend = 0; - if (op == CODE_gzip_packed) { - fetch_int (); - int l = prefetch_strlen (); - char *s = fetch_str (l); - int total_out = tgl_inflate (s, l, packed_buffer, MAX_PACKED_SIZE); - vlogprintf (E_DEBUG, "inflated %d bytes\n", total_out); - end = in_ptr; - eend = in_end; - //assert (total_out % 4 == 0); - in_ptr = packed_buffer; - in_end = in_ptr + total_out / 4; - /*if (verbosity >= 4) { - logprintf ( "Unzipped data: "); - hexdump_in (); - }*/ - } - struct query *q = tglq_query_get (TLS, id); - if (!q) { - //if (verbosity) { - // logprintf ( "No such query\n"); - //} - vlogprintf (E_WARNING, "No such query\n"); - in_ptr = in_end; - } else { - if (!(q->flags & QUERY_ACK_RECEIVED)) { - TLS->timer_methods->delete (q->ev); - } - TLS->queries_tree = tree_delete_query (TLS->queries_tree, q); - if (q->methods && q->methods->on_answer) { - if (q->type) { - int *save = in_ptr; - vlogprintf (E_DEBUG, "in_ptr = %p, end_ptr = %p\n", in_ptr, in_end); - if (skip_type_any (q->type) < 0) { - vlogprintf (E_ERROR, "Skipped %ld int out of %ld (type %s)\n", (long)(in_ptr - save), (long)(in_end - save), q->type->type->id); - assert (0); - } - - assert (in_ptr == in_end); - in_ptr = save; - } - q->methods->on_answer (TLS, q); - assert (in_ptr == in_end); - } - tfree (q->data, 4 * q->data_len); - TLS->timer_methods->free (q->ev); - tfree (q, sizeof (*q)); - - } - if (end) { - in_ptr = end; - in_end = eend; - } - TLS->active_queries --; -} - - -//int max_chat_size; -//int max_bcast_size; -//int want_dc_num; -//int new_dc_num; -//extern struct tgl_dc *DC_list[]; -//extern struct tgl_dc *TLS->DC_working; - -static void out_random (int n) { - assert (n <= 32); - static char buf[32]; - tglt_secure_random (buf, n); - out_cstring (buf, n); -} - -int allow_send_linux_version; -void tgl_do_insert_header (void) { - out_int (CODE_invoke_with_layer18); - //out_int (0x50858a19); - out_int (CODE_init_connection); - out_int (TG_APP_ID); - if (allow_send_linux_version) { - struct utsname st; - uname (&st); - out_string (st.machine); - static char buf[4096]; - tsnprintf (buf, sizeof (buf), "%.999s %.999s %.999s\n", st.sysname, st.release, st.version); - out_string (buf); - out_string (TGL_VERSION " (build " TGL_BUILD ")"); - out_string ("En"); - } else { - out_string ("x86"); - out_string ("Linux"); - out_string (TGL_VERSION); - out_string ("en"); - } -} - -/* {{{ Get config */ - -static void fetch_dc_option (struct tgl_state *TLS) { - assert (fetch_int () == CODE_dc_option); - int id = fetch_int (); - int l1 = prefetch_strlen (); - char *name = fetch_str (l1); - int l2 = prefetch_strlen (); - char *ip = fetch_str (l2); - int port = fetch_int (); - - bl_do_dc_option (TLS, id, l1, name, l2, ip, port); -} - -static int help_get_config_on_answer (struct tgl_state *TLS, struct query *q UU) { - unsigned op = fetch_int (); - assert (op == CODE_config || op == CODE_config_old); - fetch_int (); - - unsigned test_mode = fetch_int (); - assert (test_mode == CODE_bool_true || test_mode == CODE_bool_false); - assert (test_mode == CODE_bool_false || test_mode == CODE_bool_true); - int this_dc = fetch_int (); - vlogprintf (E_DEBUG, "this_dc = %d\n", this_dc); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - assert (n <= 10); - int i; - for (i = 0; i < n; i++) { - fetch_dc_option (TLS); - } - int max_chat_size = fetch_int (); - int max_bcast_size = 0; - if (op == CODE_config) { - max_bcast_size = fetch_int (); - } - vlogprintf (E_DEBUG, "chat_size = %d, bcast_size = %d\n", max_chat_size, max_bcast_size); - - if (q->callback) { - ((void (*)(struct tgl_state *,void *, int))(q->callback))(TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods help_get_config_methods = { - .on_answer = help_get_config_on_answer, - .type = TYPE_TO_PARAM(config) -}; - -void tgl_do_help_get_config (struct tgl_state *TLS, void (*callback)(struct tgl_state *,void *, int), void *callback_extra) { - clear_packet (); - tgl_do_insert_header (); - out_int (CODE_help_get_config); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &help_get_config_methods, 0, callback, callback_extra); -} - -void tgl_do_help_get_config_dc (struct tgl_state *TLS, struct tgl_dc *D, void (*callback)(struct tgl_state *, void *, int), void *callback_extra) { - clear_packet (); - tgl_do_insert_header (); - out_int (CODE_help_get_config); - tglq_send_query_ex (TLS, D, packet_ptr - packet_buffer, packet_buffer, &help_get_config_methods, 0, callback, callback_extra, 2); -} -/* }}} */ - -/* {{{ Send code */ -static int send_code_on_answer (struct tgl_state *TLS, struct query *q UU) { - static char *phone_code_hash; - assert (fetch_int () == (int)CODE_auth_sent_code); - int registered = fetch_bool (); - int l = prefetch_strlen (); - char *s = fetch_str (l); - if (phone_code_hash) { - tfree_str (phone_code_hash); - } - phone_code_hash = tstrndup (s, l); - fetch_int (); - fetch_bool (); - tfree_str (q->extra); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, const char *))(q->callback)) (TLS, q->callback_extra, 1, registered, phone_code_hash); - } - return 0; -} - -static int send_code_on_error (struct tgl_state *TLS, struct query *q UU, int error_code, int l, char *error) { - int s = strlen ("PHONE_MIGRATE_"); - int s2 = strlen ("NETWORK_MIGRATE_"); - int want_dc_num = 0; - if (l >= s && !memcmp (error, "PHONE_MIGRATE_", s)) { - int i = error[s] - '0'; - want_dc_num = i; - } else if (l >= s2 && !memcmp (error, "NETWORK_MIGRATE_", s2)) { - int i = error[s2] - '0'; - want_dc_num = i; - } else { - vlogprintf (E_ERROR, "error_code = %d, error = %.*s\n", error_code, l, error); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, const char *))(q->callback)) (TLS, q->callback_extra, 0, 0, 0); - } - return 0; - } - bl_do_set_working_dc (TLS, want_dc_num); - //if (q->callback) { - // ((void (*)(void *, int, int, const char *))(q->callback)) (q->callback_extra, 0, 0, 0); - //} - assert (TLS->DC_working->id == want_dc_num); - tgl_do_send_code (TLS, q->extra, q->callback, q->callback_extra); - tfree_str (q->extra); - return 0; -} - -static struct query_methods send_code_methods = { - .on_answer = send_code_on_answer, - .on_error = send_code_on_error, - .type = TYPE_TO_PARAM(auth_sent_code) -}; - -//char *suser; -//extern int dc_working_num; -void tgl_do_send_code (struct tgl_state *TLS, const char *user, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int registered, const char *hash), void *callback_extra) { - vlogprintf (E_DEBUG, "sending code to dc %d\n", TLS->dc_working_num); - //suser = tstrdup (user); - 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"); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_code_methods, tstrdup (user), callback, callback_extra); -} - - -static int phone_call_on_answer (struct tgl_state *TLS, struct query *q UU) { - fetch_bool (); - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int))(q->callback))(TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods phone_call_methods = { - .on_answer = phone_call_on_answer, - .type = TYPE_TO_PARAM(bool) -}; - -void tgl_do_phone_call (struct tgl_state *TLS, const char *user, const char *hash,void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - vlogprintf (E_DEBUG, "calling user\n"); - //suser = tstrdup (user); - //want_dc_num = 0; - clear_packet (); - tgl_do_insert_header (); - out_int (CODE_auth_send_call); - out_string (user); - out_string (hash); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &phone_call_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Sign in / Sign up */ -static int sign_in_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_auth_authorization); - int expires = fetch_int (); - vlogprintf (E_DEBUG, "Expires in %d\n", expires); - - struct tgl_user *U = tglf_fetch_alloc_user (TLS); - - TLS->DC_working->has_auth = 1; - - bl_do_dc_signed (TLS, TLS->DC_working->id); - - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int, struct tgl_user *))q->callback) (TLS, q->callback_extra, 1, U); - } - - return 0; -} - -static struct query_methods sign_in_methods = { - .on_answer = sign_in_on_answer, - .type = TYPE_TO_PARAM(auth_authorization) -}; - -int tgl_do_send_code_result (struct tgl_state *TLS, const char *user, const char *hash, const char *code, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) { - clear_packet (); - out_int (CODE_auth_sign_in); - out_string (user); - out_string (hash); - out_string (code); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0, callback, callback_extra); - return 0; -} - -int tgl_do_send_code_result_auth (struct tgl_state *TLS, const char *user, const char *hash, const char *code, const char *first_name, const char *last_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) { - clear_packet (); - out_int (CODE_auth_sign_up); - out_string (user); - out_string (hash); - out_string (code); - out_string (first_name); - out_string (last_name); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &sign_in_methods, 0, callback, callback_extra); - return 0; -} -/* }}} */ - -/* {{{ Get contacts */ -static int get_contacts_on_answer (struct tgl_state *TLS, struct query *q UU) { - int i; - - assert (fetch_int () == (int)CODE_contacts_contacts); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - for (i = 0; i < n; i++) { - assert (fetch_int () == (int)CODE_contact); - fetch_int (); // id - fetch_int (); // mutual - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - struct tgl_user **list = talloc (sizeof (void *) * n); - for (i = 0; i < n; i++) { - list[i] = tglf_fetch_alloc_user (TLS); - } - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int, int, struct tgl_user **))q->callback) (TLS, 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 (TLS); - print_start (); - push_color (COLOR_YELLOW); - printf ("User #%d: ", tgl_get_peer_id (U->id)); - print_user_name (U->id, (tgl_peer_t *)U); - push_color (COLOR_GREEN); - printf (" ("); - printf ("%s", U->print_name); - if (U->phone) { - printf (" "); - printf ("%s", U->phone); - } - printf (") "); - pop_color (); - if (U->status.online > 0) { - printf ("online\n"); - } else { - if (U->status.online < 0) { - printf ("offline. Was online "); - print_date_full (U->status.when); - } else { - printf ("offline permanent"); - } - printf ("\n"); - } - pop_color (); - print_end (); - }*/ - return 0; -} - -static struct query_methods get_contacts_methods = { - .on_answer = get_contacts_on_answer, - .type = TYPE_TO_PARAM(contacts_contacts) -}; - - -void tgl_do_update_contact_list (struct tgl_state *TLS, void (*callback) (struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_user *contacts[]), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_get_contacts); - out_string (""); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_contacts_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Encrypt decrypted */ -static int *encr_extra; -static int *encr_ptr; -static int *encr_end; - -static char *encrypt_decrypted_message (struct tgl_secret_chat *E) { - static int msg_key[4]; - static unsigned char sha1a_buffer[20]; - static unsigned char sha1b_buffer[20]; - static unsigned char sha1c_buffer[20]; - static unsigned char sha1d_buffer[20]; - int x = *(encr_ptr); - assert (x >= 0 && !(x & 3)); - sha1 ((void *)encr_ptr, 4 + x, sha1a_buffer); - memcpy (msg_key, sha1a_buffer + 4, 16); - - static unsigned char buf[64]; - memcpy (buf, msg_key, 16); - memcpy (buf + 16, E->key, 32); - sha1 (buf, 48, sha1a_buffer); - - memcpy (buf, E->key + 8, 16); - memcpy (buf + 16, msg_key, 16); - memcpy (buf + 32, E->key + 12, 16); - sha1 (buf, 48, sha1b_buffer); - - memcpy (buf, E->key + 16, 32); - memcpy (buf + 32, msg_key, 16); - sha1 (buf, 48, sha1c_buffer); - - memcpy (buf, msg_key, 16); - memcpy (buf + 16, E->key + 24, 32); - sha1 (buf, 48, sha1d_buffer); - - static unsigned char key[32]; - memcpy (key, sha1a_buffer + 0, 8); - memcpy (key + 8, sha1b_buffer + 8, 12); - memcpy (key + 20, sha1c_buffer + 4, 12); - - static unsigned char iv[32]; - memcpy (iv, sha1a_buffer + 8, 12); - memcpy (iv + 12, sha1b_buffer + 0, 8); - memcpy (iv + 20, sha1c_buffer + 16, 4); - memcpy (iv + 24, sha1d_buffer + 0, 8); - - AES_KEY aes_key; - AES_set_encrypt_key (key, 256, &aes_key); - AES_ige_encrypt ((void *)encr_ptr, (void *)encr_ptr, 4 * (encr_end - encr_ptr), &aes_key, iv, 1); - memset (&aes_key, 0, sizeof (aes_key)); - - return (void *)msg_key; -} - -static void encr_start (void) { - encr_extra = packet_ptr; - packet_ptr += 1; // str len - packet_ptr += 2; // fingerprint - packet_ptr += 4; // msg_key - packet_ptr += 1; // len -} - - -static void encr_finish (struct tgl_secret_chat *E) { - int l = packet_ptr - (encr_extra + 8); - while (((packet_ptr - encr_extra) - 3) & 3) { - int t; - tglt_secure_random (&t, 4); - out_int (t); - } - - *encr_extra = ((packet_ptr - encr_extra) - 1) * 4 * 256 + 0xfe; - encr_extra ++; - *(long long *)encr_extra = E->key_fingerprint; - encr_extra += 2; - encr_extra[4] = l * 4; - encr_ptr = encr_extra + 4; - encr_end = packet_ptr; - memcpy (encr_extra, encrypt_decrypted_message (E), 16); -} -/* }}} */ - -void tgl_do_send_encr_chat_layer (struct tgl_state *TLS, struct tgl_secret_chat *E) { - long long t; - tglt_secure_random (&t, 8); - int action[2]; - action[0] = CODE_decrypted_message_action_notify_layer; - action[1] = TGL_ENCRYPTED_LAYER; - bl_do_send_message_action_encr (TLS, t, TLS->our_id, tgl_get_peer_type (E->id), tgl_get_peer_id (E->id), time (0), 2, action); - - struct tgl_message *M = tgl_message_get (TLS, t); - assert (M); - assert (M->action.type == tgl_message_action_notify_layer); - tgl_do_send_msg (TLS, M, 0, 0); - //print_message (M); -} - -void tgl_do_set_encr_chat_ttl (struct tgl_state *TLS, struct tgl_secret_chat *E, int ttl, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - long long t; - tglt_secure_random (&t, 8); - int action[2]; - action[0] = CODE_decrypted_message_action_set_message_t_t_l; - action[1] = ttl; - bl_do_send_message_action_encr (TLS, t, TLS->our_id, tgl_get_peer_type (E->id), tgl_get_peer_id (E->id), time (0), 2, action); - - struct tgl_message *M = tgl_message_get (TLS, t); - assert (M); - assert (M->action.type == tgl_message_action_set_message_ttl); - tgl_do_send_msg (TLS, M, callback, callback_extra); - //print_message (M); -} - -/* {{{ Seng msg (plain text) */ -static int msg_send_encr_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == CODE_messages_sent_encrypted_message); - struct tgl_message *M = q->extra; - //M->date = fetch_int (); - fetch_int (); - if (M->flags & FLAG_PENDING) { - bl_do_set_message_sent (TLS, M); - bl_do_msg_update (TLS, M->id); - } - - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int, struct tgl_message *))q->callback) (TLS, q->callback_extra, 1, M); - } - return 0; -} - -static int msg_send_on_answer (struct tgl_state *TLS, struct query *q UU) { - unsigned x = fetch_int (); - assert (x == CODE_messages_sent_message || x == CODE_messages_sent_message_link); - int id = fetch_int (); // id - long long y = *(long long *)q->extra; - tfree (q->extra, 8); - struct tgl_message *M = tgl_message_get (TLS, y); - if (M && M->id != id) { - bl_do_set_msg_id (TLS, M, id); - } - int date = fetch_int (); - int pts = fetch_int (); - //tglu_fetch_seq (); - //bl_do_ - int seq = fetch_int (); - if (seq == TLS->seq + 1 && !(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_set_date (TLS, date); - bl_do_set_pts (TLS, pts); - bl_do_msg_seq_update (TLS, id); - } else { - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq\n"); - tgl_do_get_difference (TLS, 0, 0, 0); - } - } - 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); - int n = fetch_int (); - int i; - unsigned a, b; - for (i = 0; i < n; i++) { - assert (fetch_int () == (int)CODE_contacts_link); - a = fetch_int (); - assert (a == CODE_contacts_my_link_empty || a == CODE_contacts_my_link_requested || a == CODE_contacts_my_link_contact); - if (a == CODE_contacts_my_link_requested) { - fetch_bool (); - } - b = fetch_int (); - assert (b == CODE_contacts_foreign_link_unknown || b == CODE_contacts_foreign_link_requested || b == CODE_contacts_foreign_link_mutual); - if (b == CODE_contacts_foreign_link_requested) { - fetch_bool (); - } - struct tgl_user *U = tglf_fetch_alloc_user (TLS); - - U->flags &= ~(FLAG_USER_IN_CONTACT | FLAG_USER_OUT_CONTACT); - if (a == CODE_contacts_my_link_contact) { - U->flags |= FLAG_USER_IN_CONTACT; - } - U->flags &= ~(FLAG_USER_IN_CONTACT | FLAG_USER_OUT_CONTACT); - if (b == CODE_contacts_foreign_link_mutual) { - U->flags |= FLAG_USER_IN_CONTACT | FLAG_USER_OUT_CONTACT; - } - if (b == CODE_contacts_foreign_link_requested) { - U->flags |= FLAG_USER_OUT_CONTACT; - } - print_start (); - push_color (COLOR_YELLOW); - printf ("Link with user "); - print_user_name (U->id, (void *)U); - printf (" changed\n"); - pop_color (); - print_end (); - } - }*/ - if (M->flags & FLAG_PENDING) { - bl_do_set_message_sent (TLS, M); - } - if (q->callback) { - ((void (*)(struct tgl_state *,void *, int, struct tgl_message *))q->callback) (TLS, q->callback_extra, 1, M); - } - return 0; -} - -static int msg_send_on_error (struct tgl_state *TLS, struct query *q, int error_code, int error_len, char *error) { - //vlogprintf (E_WARNING, "error for query #%lld: #%d :%.*s\n", q->msg_id, error_code, error_len, error); - if (error_code == 420) { - assert (!strncmp (error, "FLOOD_WAIT_", 11)); - int wait = atoll (error + 11); - q->flags &= ~QUERY_ACK_RECEIVED; - - TLS->timer_methods->insert (q->ev, wait); - q->session_id = 0; - return 1; - } - long long x = *(long long *)q->extra; - tfree (q->extra, 8); - struct tgl_message *M = tgl_message_get (TLS, x); - if (q->callback) { - ((void (*)(struct tgl_state *,void *, int, struct tgl_message *))q->callback) (TLS, q->callback_extra, 0, M); - } - if (M) { - bl_do_delete_msg (TLS, M); - } - return 0; -} - -static struct query_methods msg_send_methods = { - .on_answer = msg_send_on_answer, - .on_error = msg_send_on_error, - .type = TYPE_TO_PARAM(messages_sent_message) -}; - -static struct query_methods msg_send_encr_methods = { - .on_answer = msg_send_encr_on_answer, - .type = TYPE_TO_PARAM(messages_sent_encrypted_message) -}; - -//int out_message_num; - -void tgl_do_send_encr_msg_action (struct tgl_state *TLS, struct tgl_message *M, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - tgl_peer_t *P = tgl_peer_get (TLS, M->to_id); - if (!P || P->encr_chat.state != sc_ok) { - vlogprintf (E_WARNING, "Unknown encrypted chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - - clear_packet (); - out_int (CODE_messages_send_encrypted_service); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (M->to_id)); - out_long (P->encr_chat.access_hash); - out_long (M->id); - encr_start (); - if (P->encr_chat.layer <= 16) { - out_int (CODE_decrypted_message_service_l16); - } else { - out_int (CODE_decrypted_message_layer); - out_random (15 + 4 * (lrand48 () % 3)); - out_int (TGL_ENCRYPTED_LAYER); - out_int (2 * P->encr_chat.in_seq_no + (P->encr_chat.admin_id != TLS->our_id)); - out_int (2 * P->encr_chat.out_seq_no + (P->encr_chat.admin_id == TLS->our_id) - 2); - out_int (CODE_decrypted_message_service); - } - out_long (M->id); - if (P->encr_chat.layer < 17) { - out_random (15 + 4 * (lrand48 () % 3)); - } - - switch (M->action.type) { - case tgl_message_action_notify_layer: - out_int (CODE_decrypted_message_action_notify_layer); - out_int (M->action.layer); - break; - case tgl_message_action_set_message_ttl: - out_int (CODE_decrypted_message_action_set_message_t_t_l); - out_int (M->action.ttl); - break; - default: - assert (0); - } - encr_finish (&P->encr_chat); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M, callback, callback_extra); -} - -void tgl_do_send_encr_msg (struct tgl_state *TLS, struct tgl_message *M, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (M->service) { - tgl_do_send_encr_msg_action (TLS, M, callback, callback_extra); - return; - } - tgl_peer_t *P = tgl_peer_get (TLS, M->to_id); - if (!P || P->encr_chat.state != sc_ok) { - vlogprintf (E_WARNING, "Unknown encrypted chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, M); - } - return; - } - - clear_packet (); - out_int (CODE_messages_send_encrypted); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (M->to_id)); - out_long (P->encr_chat.access_hash); - out_long (M->id); - encr_start (); - if (P->encr_chat.layer <= 16) { - out_int (CODE_decrypted_message_service_l16); - } else { - out_int (CODE_decrypted_message_layer); - out_random (15 + 4 * (lrand48 () % 3)); - out_int (TGL_ENCRYPTED_LAYER); - out_int (2 * P->encr_chat.in_seq_no + (P->encr_chat.admin_id != TLS->our_id)); - out_int (2 * P->encr_chat.out_seq_no + (P->encr_chat.admin_id == TLS->our_id) - 2); - out_int (CODE_decrypted_message); - } - out_long (M->id); - if (P->encr_chat.layer < 17) { - out_random (15 + 4 * (lrand48 () % 3)); - } else { - out_int (0); - } - out_cstring ((void *)M->message, M->message_len); - out_int (CODE_decrypted_message_media_empty); - encr_finish (&P->encr_chat); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M, callback, callback_extra); -} - -void tgl_do_send_msg (struct tgl_state *TLS, struct tgl_message *M, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (M->to_id) == TGL_PEER_ENCR_CHAT) { - tgl_do_send_encr_msg (TLS, M, callback, callback_extra); - return; - } - clear_packet (); - out_int (CODE_messages_send_message); - out_peer_id (TLS, M->to_id); - out_cstring (M->message, M->message_len); - out_long (M->id); - long long *x = talloc (8); - *x = M->id; - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_methods, x, callback, callback_extra); -} - -void tgl_do_send_message (struct tgl_state *TLS, tgl_peer_id_t id, const char *msg, int len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (!P) { - vlogprintf (E_WARNING, "Unknown encrypted chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - if (P->encr_chat.state != sc_ok) { - vlogprintf (E_WARNING, "Chat is not yet initialized\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - } - long long t; - tglt_secure_random (&t, 8); - vlogprintf (E_DEBUG, "t = %lld, len = %d\n", t, len); - bl_do_send_message_text (TLS, t, TLS->our_id, tgl_get_peer_type (id), tgl_get_peer_id (id), time (0), len, msg); - struct tgl_message *M = tgl_message_get (TLS, t); - assert (M); - tgl_do_send_msg (TLS, M, callback, callback_extra); - //print_message (M); -} -/* }}} */ - -/* {{{ Send text file */ -void tgl_do_send_text (struct tgl_state *TLS, tgl_peer_id_t id, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - int fd = open (file_name, O_RDONLY); - if (fd < 0) { - vlogprintf (E_WARNING, "No such file '%s'\n", file_name); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - static char buf[(1 << 20) + 1]; - int x = read (fd, buf, (1 << 20) + 1); - assert (x >= 0); - if (x == (1 << 20) + 1) { - vlogprintf (E_WARNING, "Too big file '%s'\n", file_name); - close (fd); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - } else { - buf[x] = 0; - tgl_do_send_message (TLS, id, buf, x, callback, callback_extra); - //tfree_str (file_name); - close (fd); - } -} -/* }}} */ - -/* {{{ Mark read */ -void tgl_do_messages_mark_read (struct tgl_state *TLS, tgl_peer_id_t id, int max_id, int offset, void (*callback)(struct tgl_state *TLS, void *callback_extra, int), void *callback_extra); -static int mark_read_on_receive (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_messages_affected_history); - //tglu_fetch_pts (); - int pts = fetch_int (); - //tglu_fetch_seq (); - int seq = fetch_int (); // seq - - if (seq == TLS->seq + 1 && !(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_set_pts (TLS, pts); - bl_do_set_seq (TLS, seq); - } else { - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq\n"); - tgl_do_get_difference (TLS, 0, 0, 0); - } - } - - int offset = fetch_int (); // offset - int *t = q->extra; - if (offset > 0) { - tgl_do_messages_mark_read (TLS, tgl_set_peer_id (t[0], t[1]), t[2], offset, q->callback, q->callback_extra); - } else { - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback)(TLS, q->callback_extra, 1); - } - } - tfree (t, 12); - return 0; -} - -static int mark_read_encr_on_receive (struct tgl_state *TLS, struct query *q UU) { - fetch_bool (); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback)(TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods mark_read_methods = { - .on_answer = mark_read_on_receive, - .type = TYPE_TO_PARAM(messages_affected_history) -}; - -static struct query_methods mark_read_encr_methods = { - .on_answer = mark_read_encr_on_receive, - .type = TYPE_TO_PARAM(bool) -}; - -void tgl_do_messages_mark_read (struct tgl_state *TLS, tgl_peer_id_t id, int max_id, int offset, void (*callback)(struct tgl_state *TLS, void *callback_extra, int), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_read_history); - out_peer_id (TLS, id); - out_int (max_id); - out_int (offset); - out_int (CODE_bool_true); - int *t = talloc (12); - t[0] = tgl_get_peer_type (id); - t[1] = tgl_get_peer_id (id); - t[2] = max_id; - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_methods, t, callback, callback_extra); -} - -void tgl_do_messages_mark_read_encr (struct tgl_state *TLS, tgl_peer_id_t id, long long access_hash, int last_time, void (*callback)(struct tgl_state *TLS, void *callback_extra, int), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_read_encrypted_history); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (id)); - out_long (access_hash); - out_int (last_time); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &mark_read_encr_methods, 0, callback, callback_extra); -} - -void tgl_do_mark_read (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_USER || tgl_get_peer_type (id) == TGL_PEER_CHAT) { - tgl_do_messages_mark_read (TLS, id, 0, 0, callback, callback_extra); - return; - } - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (!P) { - vlogprintf (E_WARNING, "Unknown peer\n"); - callback (TLS, callback_extra, 0); - return; - } - assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT); - if (P->last) { - tgl_do_messages_mark_read_encr (TLS, id, P->encr_chat.access_hash, P->last->date, callback, callback_extra); - } else { - tgl_do_messages_mark_read_encr (TLS, id, P->encr_chat.access_hash, 0, callback, callback_extra); - } -} -/* }}} */ - -/* {{{ Get history */ -void _tgl_do_get_history (struct tgl_state *TLS, tgl_peer_id_t id, int limit, int offset, int max_id, int list_offset, int list_size, struct tgl_message *ML[], void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra); -static int get_history_on_answer (struct tgl_state *TLS, struct query *q UU) { - int count = -1; - int i; - int x = fetch_int (); - assert (x == (int)CODE_messages_messages_slice || x == (int)CODE_messages_messages); - if (x == (int)CODE_messages_messages_slice) { - count = fetch_int (); - //fetch_int (); - } - assert (fetch_int () == CODE_vector); - void **T = q->extra; - struct tgl_message **ML = T[0]; - int list_offset = (long)T[1]; - int list_size = (long)T[2]; - tgl_peer_id_t id = tgl_set_peer_id ((long)T[4], (long)T[3]); - int limit = (long)T[5]; - int offset = (long)T[6]; - tfree (T, sizeof (void *) * 7); - - int n = fetch_int (); - - if (list_size - list_offset < n) { - int new_list_size = 2 * list_size; - if (new_list_size - list_offset < n) { - new_list_size = n + list_offset; - } - ML = trealloc (ML, list_size * sizeof (void *), new_list_size * sizeof (void *)); - assert (ML); - list_size = new_list_size; - } - //struct tgl_message **ML = talloc (sizeof (void *) * n); - for (i = 0; i < n; i++) { - ML[i + list_offset] = tglf_fetch_alloc_message (TLS); - } - list_offset += n; - offset += n; - limit -= n; - if (count >= 0 && limit + offset >= count) { - limit = count - offset; - if (limit < 0) { limit = 0; } - } - assert (limit >= 0); - - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - - - if (limit <= 0 || x == (int)CODE_messages_messages) { - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int, int, struct tgl_message **))q->callback) (TLS, q->callback_extra, 1, list_offset, ML); - } - if (list_offset > 0) { - tgl_do_messages_mark_read (TLS, id, ML[0]->id, 0, 0, 0); - } - - - tfree (ML, sizeof (void *) * list_size); - } else { - _tgl_do_get_history (TLS, id, limit, 0, ML[list_offset - 1]->id, list_offset, list_size, ML, q->callback, q->callback_extra); - } - return 0; -} - -static struct query_methods get_history_methods = { - .on_answer = get_history_on_answer, - .type = TYPE_TO_PARAM(messages_messages) -}; - -void tgl_do_get_local_history (struct tgl_state *TLS, tgl_peer_id_t id, int limit, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) { - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (!P || !P->last) { - if (callback) { - callback (TLS, callback_extra, 0, 0, 0); - } - return; - } - struct tgl_message *M = P->last; - int count = 1; - assert (!M->prev); - while (count < limit && M->next) { - M = M->next; - count ++; - } - struct tgl_message **ML = talloc (sizeof (void *) * count); - M = P->last; - ML[0] = M; - count = 1; - while (count < limit && M->next) { - M = M->next; - ML[count ++] = M; - } - - if (callback) { - callback (TLS, callback_extra, 1, count, ML); - } - tfree (ML, sizeof (void *) * count); -} - -void tgl_do_get_local_history_ext (struct tgl_state *TLS, tgl_peer_id_t id, int offset, int limit, void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) { - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (!P || !P->last) { - if (callback) { - callback (TLS, callback_extra, 0, 0, 0); - } - return; - } - struct tgl_message *M = P->last; - int count = 1; - assert (!M->prev); - while (count < limit + offset && M->next) { - M = M->next; - count ++; - } - if (count <= offset) { - if (callback) { - callback (TLS, callback_extra, 1, 0, 0); - } - return; - } - struct tgl_message **ML = talloc (sizeof (void *) * (count - offset)); - M = P->last; - ML[0] = M; - count = 1; - while (count < limit && M->next) { - M = M->next; - if (count >= offset) { - ML[count - offset] = M; - } - count ++; - } - - if (callback) { - callback (TLS, callback_extra, 1, count - offset, ML); - } - tfree (ML, sizeof (void *) * (count) - offset); -} - - - -void _tgl_do_get_history (struct tgl_state *TLS, tgl_peer_id_t id, int limit, int offset, int max_id, int list_offset, int list_size, struct tgl_message *ML[], void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) { - void **T = talloc (sizeof (void *) * 7); - T[0] = ML; - T[1] = (void *)(long)list_offset; - T[2] = (void *)(long)list_size; - T[3] = (void *)(long)tgl_get_peer_id (id); - T[4] = (void *)(long)tgl_get_peer_type (id); - T[5] = (void *)(long)limit; - T[6] = (void *)(long)offset; - - clear_packet (); - out_int (CODE_messages_get_history); - out_peer_id (TLS, id); - out_int (offset); - out_int (max_id); - out_int (limit); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_history_methods, T, callback, callback_extra); -} - -void tgl_do_get_history (struct tgl_state *TLS, tgl_peer_id_t id, int limit, int offline_mode, void (*callback)(struct tgl_state *TLS, 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) { - tgl_do_get_local_history (TLS, id, limit, callback, callback_extra); - tgl_do_mark_read (TLS, id, 0, 0); - return; - } - _tgl_do_get_history (TLS, id, limit, 0, 0, 0, 0, 0, callback, callback_extra); -} - -void tgl_do_get_history_ext (struct tgl_state *TLS, tgl_peer_id_t id, int offset, int limit, int offline_mode, void (*callback)(struct tgl_state *TLS, 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) { - tgl_do_get_local_history (TLS, id, limit, callback, callback_extra); - tgl_do_mark_read (TLS, id, 0, 0); - return; - } - _tgl_do_get_history (TLS, id, limit, offset, 0, 0, 0, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Get dialogs */ -static int get_dialogs_on_answer (struct tgl_state *TLS, struct query *q UU) { - unsigned x = fetch_int (); - assert (x == CODE_messages_dialogs || x == CODE_messages_dialogs_slice); - if (x == CODE_messages_dialogs_slice) { - fetch_int (); // total_count - } - assert (fetch_int () == CODE_vector); - int n, i; - n = fetch_int (); - 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++) { - assert (fetch_int () == (int)CODE_dialog); - PL[i] = tglf_fetch_peer_id (TLS); - LM[i] = fetch_int (); - UC[i] = fetch_int (); - assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_message (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - /*print_start (); - push_color (COLOR_YELLOW); - for (i = dl_size - 1; i >= 0; i--) { - tgl_peer_t *UC; - switch (tgl_get_peer_type (plist[i])) { - case TGL_PEER_USER: - UC = tgl_peer_get (TLS, plist[i]); - printf ("User "); - print_user_name (plist[i], UC); - printf (": %d unread\n", dlist[2 * i + 1]); - break; - case TGL_PEER_CHAT: - UC = tgl_peer_get (TLS, plist[i]); - printf ("Chat "); - print_chat_name (plist[i], UC); - printf (": %d unread\n", dlist[2 * i + 1]); - break; - } - } - pop_color (); - print_end (); - - dialog_list_got = 1;*/ - - if (q->callback) { - ((void (*)(struct tgl_state *TLS, void *, int, int, tgl_peer_id_t *, int *, int *))q->callback) (TLS, 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; -} - -static struct query_methods get_dialogs_methods = { - .on_answer = get_dialogs_on_answer, - .type = TYPE_TO_PARAM(messages_dialogs) -}; - - -void tgl_do_get_dialog_list (struct tgl_state *TLS, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, tgl_peer_id_t peers[], int last_msg_id[], int unread_count[]), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_get_dialogs); - out_int (0); - out_int (0); - out_int (1000); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dialogs_methods, 0, callback, callback_extra); -} -/* }}} */ - -int allow_send_linux_version = 1; - -/* {{{ Send photo/video file */ -struct send_file { - int fd; - long long size; - long long offset; - int part_num; - int part_size; - long long id; - long long thumb_id; - tgl_peer_id_t to_id; - unsigned media_type; - char *file_name; - int encr; - int avatar; - unsigned char *iv; - unsigned char *init_iv; - unsigned char *key; -}; - -static void out_peer_id (struct tgl_state *TLS, tgl_peer_id_t id) { - tgl_peer_t *U; - switch (tgl_get_peer_type (id)) { - case TGL_PEER_CHAT: - out_int (CODE_input_peer_chat); - out_int (tgl_get_peer_id (id)); - break; - case TGL_PEER_USER: - U = tgl_peer_get (TLS, id); - if (U && U->user.access_hash) { - out_int (CODE_input_peer_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_peer_contact); - out_int (tgl_get_peer_id (id)); - } - break; - default: - assert (0); - } -} - -static void send_part (struct tgl_state *TLS, struct send_file *f, void *callback, void *callback_extra); -static int send_file_part_on_answer (struct tgl_state *TLS, struct query *q) { - assert (fetch_int () == (int)CODE_bool_true); - send_part (TLS, q->extra, q->callback, q->callback_extra); - return 0; -} - -static int send_file_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_messages_stated_message); - struct tgl_message *M = tglf_fetch_alloc_message (TLS); - assert (fetch_int () == CODE_vector); - int n, i; - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - //tglu_fetch_pts (); - int pts = fetch_int (); - //tglu_fetch_seq (); - - int seq = fetch_int (); - if (seq == TLS->seq + 1 && !(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_set_pts (TLS, pts); - bl_do_msg_seq_update (TLS, M->id); - } else { - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq\n"); - tgl_do_get_difference (TLS, 0, 0, 0); - } - } - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_message *))q->callback)(TLS, q->callback_extra, 1, M); - } - //print_message (M); - return 0; -} - -static int send_encr_file_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_messages_sent_encrypted_file); - struct tgl_message *M = q->extra; - //M->date = fetch_int (); - fetch_int (); - int *save = in_ptr; - - assert (skip_type_any (TYPE_TO_PARAM (encrypted_file)) >= 0); - - //print_message (M); - if (M->flags & FLAG_PENDING) { - bl_do_create_message_media_encr_sent (TLS, M->id, save, in_ptr - save); - //bl_do_set_message_sent (M); - bl_do_msg_update (TLS, M->id); - } - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_message *))q->callback)(TLS, q->callback_extra, 1, M); - } - return 0; -} - -static int set_photo_on_answer (struct tgl_state *TLS, struct query *q) { - assert (skip_type_any (TYPE_TO_PARAM(photos_photo)) >= 0); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback)(TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods send_file_part_methods = { - .on_answer = send_file_part_on_answer, - .type = TYPE_TO_PARAM(bool) -}; - -static struct query_methods send_file_methods = { - .on_answer = send_file_on_answer, - .type = TYPE_TO_PARAM(messages_stated_message) -}; - -static struct query_methods set_photo_methods = { - .on_answer = set_photo_on_answer, - .type = TYPE_TO_PARAM(photos_photo) -}; - -static struct query_methods send_encr_file_methods = { - .on_answer = send_encr_file_on_answer, - .type = TYPE_TO_PARAM(messages_sent_encrypted_message) -}; - -static void send_part (struct tgl_state *TLS, struct send_file *f, void *callback, void *callback_extra) { - if (f->fd >= 0) { - if (!f->part_num) { - TLS->cur_uploading_bytes += f->size; - } - clear_packet (); - if (f->size < (16 << 20)) { - out_int (CODE_upload_save_file_part); - out_long (f->id); - out_int (f->part_num ++); - } else { - out_int (CODE_upload_save_big_file_part); - out_long (f->id); - out_int (f->part_num ++); - out_int ((f->size + f->part_size - 1) / f->part_size); - } - static char buf[512 << 10]; - int x = read (f->fd, buf, f->part_size); - assert (x > 0); - f->offset += x; - TLS->cur_uploaded_bytes += x; - - if (f->encr) { - if (x & 15) { - assert (f->offset == f->size); - tglt_secure_random (buf + x, (-x) & 15); - x = (x + 15) & ~15; - } - - AES_KEY aes_key; - AES_set_encrypt_key (f->key, 256, &aes_key); - AES_ige_encrypt ((void *)buf, (void *)buf, x, &aes_key, f->iv, 1); - memset (&aes_key, 0, sizeof (aes_key)); - } - out_cstring (buf, x); - vlogprintf (E_DEBUG, "offset=%lld size=%lld\n", f->offset, f->size); - if (f->offset == f->size) { - close (f->fd); - f->fd = -1; - } else { - assert (f->part_size == x); - } - //update_prompt (); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f, callback, callback_extra); - } else { - TLS->cur_uploaded_bytes -= f->size; - TLS->cur_uploading_bytes -= f->size; - //update_prompt (); - 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); - if (f->avatar) { - assert (!f->encr); - if (f->avatar > 0) { - out_int (CODE_messages_edit_chat_photo); - out_int (f->avatar); - out_int (CODE_input_chat_uploaded_photo); - if (f->size < (16 << 20)) { - out_int (CODE_input_file); - } else { - out_int (CODE_input_file_big); - } - out_long (f->id); - out_int (f->part_num); - /*char *s = f->file_name + strlen (f->file_name); - while (s >= f->file_name && *s != '/') { s --;} - out_string (s + 1);*/ - out_string (""); - if (f->size < (16 << 20)) { - out_string (""); - } - out_int (CODE_input_photo_crop_auto); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_methods, 0, callback, callback_extra); - } else { - out_int (CODE_photos_upload_profile_photo); - if (f->size < (16 << 20)) { - out_int (CODE_input_file); - } else { - out_int (CODE_input_file_big); - } - out_long (f->id); - out_int (f->part_num); - char *s = f->file_name + strlen (f->file_name); - while (s >= f->file_name && *s != '/') { s --;} - out_string (s + 1); - if (f->size < (16 << 20)) { - out_string (""); - } - out_string ("profile photo"); - out_int (CODE_input_geo_point_empty); - out_int (CODE_input_photo_crop_auto); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &set_photo_methods, 0, callback, callback_extra); - } - } else if (!f->encr) { - out_int (CODE_messages_send_media); - out_peer_id (TLS, f->to_id); - out_int (f->media_type); - if (f->size < (16 << 20)) { - out_int (CODE_input_file); - } else { - out_int (CODE_input_file_big); - } - out_long (f->id); - out_int (f->part_num); - char *s = f->file_name + strlen (f->file_name); - while (s >= f->file_name && *s != '/') { s --;} - out_string (s + 1); - if (f->size < (16 << 20)) { - out_string (""); - } - if (f->media_type == CODE_input_media_uploaded_thumb_video || f->media_type == CODE_input_media_uploaded_thumb_document) { - out_int (CODE_input_file); - out_long (f->thumb_id); - out_int (1); - out_string ("thumb.jpg"); - out_string (""); - } - if (f->media_type == CODE_input_media_uploaded_video || f->media_type == CODE_input_media_uploaded_thumb_video) { - out_int (100); - out_int (100); - out_int (100); - out_string ("video"); - } - if (f->media_type == CODE_input_media_uploaded_document || f->media_type == CODE_input_media_uploaded_thumb_document) { - out_string (s + 1); - out_string ("text"); - } - if (f->media_type == CODE_input_media_uploaded_audio) { - out_int (60); - out_string ("audio"); - } - - long long r; - tglt_secure_random (&r, 8); - out_long (r); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_methods, 0, callback, callback_extra); - } else { - //struct tgl_message *M = talloc0 (sizeof (*M)); - - out_int (CODE_messages_send_encrypted_file); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (f->to_id)); - tgl_peer_t *P = tgl_peer_get (TLS, f->to_id); - assert (P); - out_long (P->encr_chat.access_hash); - long long r; - tglt_secure_random (&r, 8); - out_long (r); - encr_start (); - if (P->encr_chat.layer <= 16) { - out_int (CODE_decrypted_message_service_l16); - } else { - out_int (CODE_decrypted_message_layer); - out_random (15 + 4 * (lrand48 () % 3)); - out_int (TGL_ENCRYPTED_LAYER); - out_int (2 * P->encr_chat.in_seq_no + (P->encr_chat.admin_id != TLS->our_id)); - out_int (2 * P->encr_chat.out_seq_no + (P->encr_chat.admin_id == TLS->our_id)); - out_int (CODE_decrypted_message); - } - out_long (r); - if (P->encr_chat.layer < 17) { - out_random (15 + 4 * (lrand48 () % 3)); - } else { - out_int (0); - } - out_string (""); - int *save_ptr = packet_ptr; - if (f->media_type == CODE_input_media_uploaded_photo) { - out_int (CODE_decrypted_message_media_photo); - //M->media.type = CODE_decrypted_message_media_photo; - } else if (f->media_type == CODE_input_media_uploaded_video) { - out_int (CODE_decrypted_message_media_video); - //M->media.type = CODE_decrypted_message_media_video; - } else if (f->media_type == CODE_input_media_uploaded_audio) { - out_int (CODE_decrypted_message_media_audio); - //M->media.type = CODE_decrypted_message_media_audio; - } else if (f->media_type == CODE_input_media_uploaded_document) { - out_int (CODE_decrypted_message_media_document); - //M->media.type = CODE_decrypted_message_media_document;; - } else { - assert (0); - } - if (f->media_type != CODE_input_media_uploaded_audio) { - out_cstring ((void *)thumb_file, thumb_file_size); - out_int (90); - out_int (90); - } - if (f->media_type == CODE_input_media_uploaded_video) { - out_int (0); - out_string ("video"); - } - if (f->media_type == CODE_input_media_uploaded_document) { - out_string (f->file_name); - out_string ("text"); - } - if (f->media_type == CODE_input_media_uploaded_audio) { - out_int (60); - out_string ("audio"); - } - if (f->media_type == CODE_input_media_uploaded_video || f->media_type == CODE_input_media_uploaded_photo) { - out_int (100); - out_int (100); - } - out_int (f->size); - out_cstring ((void *)f->key, 32); - out_cstring ((void *)f->init_iv, 32); - - bl_do_create_message_media_encr_pending (TLS, r, TLS->our_id, tgl_get_peer_type (f->to_id), tgl_get_peer_id (f->to_id), time (0), 0, 0, save_ptr, packet_ptr - save_ptr); - - encr_finish (&P->encr_chat); - if (f->size < (16 << 20)) { - out_int (CODE_input_encrypted_file_uploaded); - } else { - out_int (CODE_input_encrypted_file_big_uploaded); - } - out_long (f->id); - out_int (f->part_num); - if (f->size < (16 << 20)) { - out_string (""); - } - - unsigned char md5[16]; - unsigned char str[64]; - memcpy (str, f->key, 32); - memcpy (str + 32, f->init_iv, 32); - MD5 (str, 64, md5); - out_int ((*(int *)md5) ^ (*(int *)(md5 + 4))); - - tfree_secure (f->iv, 32); - struct tgl_message *M = tgl_message_get (TLS, r); - assert (M); - - //M->media.encr_photo.key = f->key; - //M->media.encr_photo.iv = f->init_iv; - //M->media.encr_photo.key_fingerprint = (*(int *)md5) ^ (*(int *)(md5 + 4)); - //M->media.encr_photo.size = f->size; - - //M->flags = FLAG_ENCRYPTED; - //M->from_id = TGL_MK_USER (TLS->our_id); - //M->to_id = f->to_id; - //M->unread = 1; - //M->message = tstrdup (""); - //M->out = 1; - //M->id = r; - //M->date = time (0); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_file_methods, M, callback, callback_extra); - } - tfree_str (f->file_name); - tfree (f, sizeof (*f)); - } -} - -/*void send_file_thumb (struct send_file *f, void *callback, void *callback_extra) { - clear_packet (); - f->thumb_id = lrand48 () * (1ll << 32) + lrand48 (); - out_int (CODE_upload_save_file_part); - out_long (f->thumb_id); - out_int (0); - out_cstring ((void *)thumb_file, thumb_file_size); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_file_part_methods, f, callback, callback_extra); -}*/ - -void _tgl_do_send_photo (struct tgl_state *TLS, enum tgl_message_media_type type, tgl_peer_id_t to_id, char *file_name, int avatar, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - int fd = open (file_name, O_RDONLY); - if (fd < 0) { - vlogprintf (E_WARNING, "No such file '%s'\n", file_name); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - struct stat buf; - fstat (fd, &buf); - long long size = buf.st_size; - if (size <= 0) { - vlogprintf (E_WARNING, "File has zero length\n"); - close (fd); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - struct send_file *f = talloc0 (sizeof (*f)); - f->fd = fd; - f->size = size; - f->offset = 0; - f->part_num = 0; - f->avatar = avatar; - int tmp = ((size + 2999) / 3000); - f->part_size = (1 << 14); - while (f->part_size < tmp) { - f->part_size *= 2; - } - - if (f->part_size > (512 << 10)) { - close (fd); - vlogprintf (E_WARNING, "Too big file. Maximal supported size is %d.\n", (512 << 10) * 1000); - tfree (f, sizeof (*f)); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - - tglt_secure_random (&f->id, 8); - f->to_id = to_id; - switch (type) { - case tgl_message_media_photo: - f->media_type = CODE_input_media_uploaded_photo; - break; - case tgl_message_media_video: - f->media_type = CODE_input_media_uploaded_video; - break; - case tgl_message_media_audio: - f->media_type = CODE_input_media_uploaded_audio; - break; - case tgl_message_media_document: - f->media_type = CODE_input_media_uploaded_document; - break; - default: - close (fd); - vlogprintf (E_WARNING, "Unknown type %d.\n", type); - tfree (f, sizeof (*f)); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - f->file_name = tstrdup (file_name); - if (tgl_get_peer_type (f->to_id) == TGL_PEER_ENCR_CHAT) { - f->encr = 1; - f->iv = talloc (32); - tglt_secure_random (f->iv, 32); - f->init_iv = talloc (32); - memcpy (f->init_iv, f->iv, 32); - f->key = talloc (32); - tglt_secure_random (f->key, 32); - } - /*if (f->media_type == CODE_input_media_uploaded_video && !f->encr) { - f->media_type = CODE_input_media_uploaded_thumb_video; - send_file_thumb (f); - } else if (f->media_type == CODE_input_media_uploaded_document && !f->encr) { - f->media_type = CODE_input_media_uploaded_thumb_document; - send_file_thumb (f); - } else { - send_part (f); - }*/ - send_part (TLS, f, callback, callback_extra); -} - -void tgl_do_send_photo (struct tgl_state *TLS, enum tgl_message_media_type type, tgl_peer_id_t to_id, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - _tgl_do_send_photo (TLS, type, to_id, file_name, 0, callback, callback_extra); -} - -void tgl_do_set_chat_photo (struct tgl_state *TLS, tgl_peer_id_t chat_id, char *file_name, void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - assert (tgl_get_peer_type (chat_id) == TGL_PEER_CHAT); - _tgl_do_send_photo (TLS, tgl_message_media_photo, chat_id, file_name, tgl_get_peer_id (chat_id), callback, callback_extra); -} - -void tgl_do_set_profile_photo (struct tgl_state *TLS, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - _tgl_do_send_photo (TLS, tgl_message_media_photo, TGL_MK_USER(TLS->our_id), file_name, -1, (void *)callback, callback_extra); -} -/* }}} */ - -/* {{{ Profile name */ - -int set_profile_name_on_answer (struct tgl_state *TLS, struct query *q) { - struct tgl_user *U = tglf_fetch_alloc_user (TLS); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_user *))q->callback) (TLS, q->callback_extra, 1, U); - } - return 0; -} - -static struct query_methods set_profile_name_methods = { - .on_answer = set_profile_name_on_answer, - .type = TYPE_TO_PARAM(user) -}; - -void tgl_do_set_profile_name (struct tgl_state *TLS, char *first_name, char *last_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra) { - clear_packet (); - out_int (CODE_account_update_profile); - out_string (first_name); - out_string (last_name); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &set_profile_name_methods, 0, callback, callback_extra); -} - -void tgl_do_set_username (struct tgl_state *TLS, char *name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra) { - clear_packet (); - out_int (CODE_account_update_username); - out_string (name); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &set_profile_name_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Contacts search */ - -int contact_search_on_answer (struct tgl_state *TLS, struct query *q) { - assert (fetch_int () == CODE_contacts_found); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - assert (fetch_int () == (int)CODE_contact_found); - fetch_int (); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - - struct tgl_user **UL = talloc (sizeof (void *) * n); - for (i = 0; i < n; i++) { - UL[i] = tglf_fetch_alloc_user (TLS); - } - - if (q->callback) { - ((void (*)(struct tgl_state *,void *, int, int, struct tgl_user **))q->callback) (TLS, q->callback_extra, 1, n, UL); - } - tfree (UL, sizeof (void *) * n); - return 0; -} - -static struct query_methods contact_search_methods = { - .on_answer = contact_search_on_answer, - .type = TYPE_TO_PARAM(contacts_found) -}; - -void tgl_do_contact_search (struct tgl_state *TLS, char *name, int limit, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int cnt, struct tgl_user *U[]), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_search); - out_string (name); - out_int (limit); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &contact_search_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Forward */ -static int fwd_msg_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_messages_stated_message); - struct tgl_message *M = tglf_fetch_alloc_message (TLS); - assert (fetch_int () == CODE_vector); - int n, i; - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - //tglu_fetch_pts (); - int pts = fetch_int (); - - int seq = fetch_int (); - if (seq == TLS->seq + 1 && !(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_set_pts (TLS, pts); - bl_do_msg_seq_update (TLS, M->id); - } else { - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq\n"); - tgl_do_get_difference (TLS, 0, 0, 0); - } - } - //print_message (M); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_message *))q->callback) (TLS, q->callback_extra, 1, M); - } - return 0; -} - -static struct query_methods fwd_msg_methods = { - .on_answer = fwd_msg_on_answer, - .type = TYPE_TO_PARAM(messages_stated_message) -}; - -void tgl_do_forward_message (struct tgl_state *TLS, tgl_peer_id_t id, int n, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - vlogprintf (E_WARNING, "Can not forward messages from secret chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - clear_packet (); - out_int (CODE_messages_forward_message); - out_peer_id (TLS, id); - out_int (n); - long long r; - tglt_secure_random (&r, 8); - out_long (r); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0, callback, callback_extra); -} - -void tgl_do_send_contact (struct tgl_state *TLS, tgl_peer_id_t id, const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - long long t; - tglt_secure_random (&t, 8); - vlogprintf (E_DEBUG, "t = %lld\n", t); - - clear_packet (); - out_int (CODE_messages_send_media); - out_peer_id (TLS, id); - out_int (CODE_input_media_contact); - out_cstring (phone, phone_len); - out_cstring (first_name, first_name_len); - out_cstring (last_name, last_name_len); - out_long (t); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0, callback, callback_extra); -} - -void tgl_do_forward_media (struct tgl_state *TLS, tgl_peer_id_t id, int n, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - vlogprintf (E_WARNING, "Can not forward messages from secret chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - struct tgl_message *M = tgl_message_get (TLS, n); - if (!M) { - vlogprintf (E_WARNING, "No such message\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - if (M->flags & FLAG_ENCRYPTED) { - vlogprintf (E_WARNING, "Can not forward media from encrypted message\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - if (M->media.type != tgl_message_media_photo && M->media.type != tgl_message_media_video && M->media.type != tgl_message_media_audio && M->media.type != tgl_message_media_document) { - vlogprintf (E_WARNING, "Can only forward photo/audio/video/document\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - clear_packet (); - out_int (CODE_messages_send_media); - out_peer_id (TLS, id); - switch (M->media.type) { - case tgl_message_media_photo: - out_int (CODE_input_media_photo); - out_int (CODE_input_photo); - out_long (M->media.photo.id); - out_long (M->media.photo.access_hash); - break; - case tgl_message_media_video: - out_int (CODE_input_media_video); - out_int (CODE_input_video); - out_long (M->media.video.id); - out_long (M->media.video.access_hash); - break; - case tgl_message_media_audio: - out_int (CODE_input_media_audio); - out_int (CODE_input_audio); - out_long (M->media.audio.id); - out_long (M->media.audio.access_hash); - break; - case tgl_message_media_document: - out_int (CODE_input_media_document); - out_int (CODE_input_document); - out_long (M->media.document.id); - out_long (M->media.document.access_hash); - break; - default: - assert (0); - } - long long r; - tglt_secure_random (&r, 8); - out_long (r); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Send location */ - -void tgl_do_send_location(struct tgl_state *TLS, tgl_peer_id_t id, double latitude, double longitude, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - clear_packet (); - out_int (CODE_messages_send_encrypted); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (id)); - tgl_peer_t *P = tgl_peer_get (TLS, id); - assert (P); - out_long (P->encr_chat.access_hash); - - long long r; - tglt_secure_random (&r, 8); - out_long (r); - encr_start (); - if (P->encr_chat.layer <= 16) { - out_int (CODE_decrypted_message_service_l16); - } else { - out_int (CODE_decrypted_message_layer); - out_random (15 + 4 * (lrand48 () % 3)); - out_int (TGL_ENCRYPTED_LAYER); - out_int (2 * P->encr_chat.in_seq_no + (P->encr_chat.admin_id != TLS->our_id)); - out_int (2 * P->encr_chat.out_seq_no + (P->encr_chat.admin_id == TLS->our_id)); - out_int (CODE_decrypted_message); - } - out_long (r); - if (P->encr_chat.layer < 17) { - out_random (15 + 4 * (lrand48 () % 3)); - } else { - out_int (0); - } - out_string (""); - int *save_ptr = packet_ptr; - out_int (CODE_decrypted_message_media_geo_point); - out_double (latitude); - out_double (longitude); - - bl_do_create_message_media_encr_pending (TLS, r, TLS->our_id, tgl_get_peer_type (id), tgl_get_peer_id (id), time (0), 0, 0, save_ptr, packet_ptr - save_ptr); - - encr_finish (&P->encr_chat); - - struct tgl_message *M = tgl_message_get (TLS, r); - assert (M); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_send_encr_methods, M, callback, callback_extra); - } else { - long long t; - tglt_secure_random (&t, 8); - vlogprintf (E_DEBUG, "t = %lld\n", t); - - clear_packet (); - out_int (CODE_messages_send_media); - out_peer_id (TLS, id); - out_int (CODE_input_media_geo_point); - out_int (CODE_input_geo_point); - out_double (latitude); - out_double (longitude); - out_long (t); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &fwd_msg_methods, 0, callback, callback_extra); - } -} -/* }}} */ - -/* {{{ Rename chat */ -static int rename_chat_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_messages_stated_message); - struct tgl_message *M = tglf_fetch_alloc_message (TLS); - assert (fetch_int () == CODE_vector); - int n, i; - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - //tglu_fetch_pts (); - int pts = fetch_int (); - - int seq = fetch_int (); - if (seq == TLS->seq + 1 && !(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_set_pts (TLS, pts); - bl_do_msg_seq_update (TLS, M->id); - } else { - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq\n"); - tgl_do_get_difference (TLS, 0, 0, 0); - } - } - //print_message (M); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_message *))q->callback) (TLS, q->callback_extra, 1, M); - } - return 0; -} - -static struct query_methods rename_chat_methods = { - .on_answer = rename_chat_on_answer, - .type = TYPE_TO_PARAM(messages_stated_message) -}; - -void tgl_do_rename_chat (struct tgl_state *TLS, tgl_peer_id_t id, char *name UU, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_edit_chat_title); - assert (tgl_get_peer_type (id) == TGL_PEER_CHAT); - out_int (tgl_get_peer_id (id)); - out_string (name); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &rename_chat_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Chat info */ -/*void print_chat_info (struct tgl_chat *C) { - tgl_peer_t *U = (void *)C; - print_start (); - push_color (COLOR_YELLOW); - printf ("Chat "); - print_chat_name (U->id, U); - printf (" members:\n"); - int i; - for (i = 0; i < C->user_list_size; i++) { - printf ("\t\t"); - print_user_name (TGL_MK_USER (C->user_list[i].user_id), tgl_peer_get (TLS, TGL_MK_USER (C->user_list[i].user_id))); - printf (" invited by "); - print_user_name (TGL_MK_USER (C->user_list[i].inviter_id), tgl_peer_get (TLS, TGL_MK_USER (C->user_list[i].inviter_id))); - printf (" at "); - print_date_full (C->user_list[i].date); - if (C->user_list[i].user_id == C->admin_id) { - printf (" admin"); - } - printf ("\n"); - } - pop_color (); - print_end (); -}*/ - -static int chat_info_on_answer (struct tgl_state *TLS, struct query *q UU) { - struct tgl_chat *C = tglf_fetch_alloc_chat_full (TLS); - //print_chat_info (C); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_chat *))q->callback) (TLS, q->callback_extra, 1, C); - } - return 0; -} - -static struct query_methods chat_info_methods = { - .on_answer = chat_info_on_answer, - .type = TYPE_TO_PARAM(messages_chat_full) -}; - -void tgl_do_get_chat_info (struct tgl_state *TLS, tgl_peer_id_t id, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_chat *C), void *callback_extra) { - if (offline_mode) { - tgl_peer_t *C = tgl_peer_get (TLS, id); - if (!C) { - vlogprintf (E_WARNING, "No such chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - } else { - //print_chat_info (&C->chat); - if (callback) { - callback (TLS, callback_extra, 1, &C->chat); - } - } - return; - } - clear_packet (); - out_int (CODE_messages_get_full_chat); - assert (tgl_get_peer_type (id) == TGL_PEER_CHAT); - out_int (tgl_get_peer_id (id)); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &chat_info_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ User info */ - -/*void print_user_info (struct tgl_user *U) { - tgl_peer_t *C = (void *)U; - print_start (); - push_color (COLOR_YELLOW); - printf ("User "); - print_user_name (U->id, C); - printf (":\n"); - printf ("\treal name: %s %s\n", U->real_first_name, U->real_last_name); - printf ("\tphone: %s\n", U->phone); - if (U->status.online > 0) { - printf ("\tonline\n"); - } else { - printf ("\toffline (was online "); - print_date_full (U->status.when); - printf (")\n"); - } - pop_color (); - print_end (); -}*/ - -static int user_info_on_answer (struct tgl_state *TLS, struct query *q UU) { - struct tgl_user *U = tglf_fetch_alloc_user_full (TLS); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_user *))q->callback) (TLS, q->callback_extra, 1, U); - } - return 0; -} - -static struct query_methods user_info_methods = { - .on_answer = user_info_on_answer, - .type = TYPE_TO_PARAM(user_full) -}; - -void tgl_do_get_user_info (struct tgl_state *TLS, tgl_peer_id_t id, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra) { - if (offline_mode) { - tgl_peer_t *C = tgl_peer_get (TLS, id); - if (!C) { - vlogprintf (E_WARNING, "No such user\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - } else { - if (callback) { - callback (TLS, callback_extra, 1, &C->user); - } - } - return; - } - clear_packet (); - out_int (CODE_users_get_full_user); - assert (tgl_get_peer_type (id) == TGL_PEER_USER); - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &user_info_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Get user info silently */ -/*int user_list_info_silent_on_answer (struct query *q UU) { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - return 0; -} - -struct query_methods user_list_info_silent_methods = { - .on_answer = user_list_info_silent_on_answer, - .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM(user)) -}; - -void tgl_do_get_user_list_info_silent (int num, int *list) { - clear_packet (); - out_int (CODE_users_get_users); - out_int (CODE_vector); - out_int (num); - int i; - for (i = 0; i < num; i++) { - out_int (CODE_input_user_contact); - out_int (list[i]); - //out_long (0); - } - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &user_list_info_silent_methods, 0); -}*/ -/* }}} */ - -/* {{{ Load photo/video */ -struct download { - int offset; - int size; - long long volume; - long long secret; - long long access_hash; - int local_id; - int dc; - int next; - int fd; - char *name; - long long id; - unsigned char *iv; - unsigned char *key; - int type; - int refcnt; -}; - - -static void end_load (struct tgl_state *TLS, struct download *D, void *callback, void *callback_extra) { - TLS->cur_downloading_bytes -= D->size; - TLS->cur_downloaded_bytes -= D->size; - //update_prompt (); - close (D->fd); - /*if (D->next == 1) { - logprintf ("Done: %s\n", D->name); - } else if (D->next == 2) { - static char buf[PATH_MAX]; - if (tsnprintf (buf, sizeof (buf), OPEN_BIN, D->name) >= (int) sizeof (buf)) { - logprintf ("Open image command buffer overflow\n"); - } else { - int x = system (buf); - if (x < 0) { - logprintf ("Can not open image viewer: %m\n"); - logprintf ("Image is at %s\n", D->name); - } - } - }*/ - - if (callback) { - ((void (*)(struct tgl_state *, void *, int, char *))callback) (TLS, callback_extra, 1, D->name); - } - - if (D->iv) { - tfree_secure (D->iv, 32); - } - tfree_str (D->name); - tfree (D, sizeof (*D)); -} - -static void load_next_part (struct tgl_state *TLS, struct download *D, void *callback, void *callback_extra); -static int download_on_answer (struct tgl_state *TLS, struct query *q) { - assert (fetch_int () == (int)CODE_upload_file); - unsigned x = fetch_int (); - assert (x); - struct download *D = q->extra; - if (D->fd == -1) { - D->fd = open (D->name, O_CREAT | O_WRONLY, 0640); - if (D->fd < 0) { - vlogprintf (E_ERROR, "Can not open for writing: %m\n"); - assert (D->fd >= 0); - } - } - fetch_int (); // mtime - int len = prefetch_strlen (); - assert (len >= 0); - TLS->cur_downloaded_bytes += len; - //update_prompt (); - if (D->iv) { - unsigned char *ptr = (void *)fetch_str (len); - assert (!(len & 15)); - AES_KEY aes_key; - AES_set_decrypt_key (D->key, 256, &aes_key); - AES_ige_encrypt (ptr, ptr, len, &aes_key, D->iv, 0); - memset (&aes_key, 0, sizeof (aes_key)); - if (len > D->size - D->offset) { - len = D->size - D->offset; - } - assert (write (D->fd, ptr, len) == len); - } else { - assert (write (D->fd, fetch_str (len), len) == len); - } - D->offset += len; - D->refcnt --; - if (D->offset < D->size) { - load_next_part (TLS, D, q->callback, q->callback_extra); - return 0; - } else { - if (!D->refcnt) { - end_load (TLS, D, q->callback, q->callback_extra); - } - return 0; - } -} - -static struct query_methods download_methods = { - .on_answer = download_on_answer, - .type = TYPE_TO_PARAM(upload_file) -}; - -static void load_next_part (struct tgl_state *TLS, struct download *D, void *callback, void *callback_extra) { - if (!D->offset) { - static char buf[PATH_MAX]; - int l; - if (!D->id) { - l = tsnprintf (buf, sizeof (buf), "%s/download_%lld_%d.jpg", TLS->downloads_directory, D->volume, D->local_id); - } else { - l = tsnprintf (buf, sizeof (buf), "%s/download_%lld", TLS->downloads_directory, D->id); - } - if (l >= (int) sizeof (buf)) { - vlogprintf (E_ERROR, "Download filename is too long"); - exit (1); - } - D->name = tstrdup (buf); - struct stat st; - if (stat (buf, &st) >= 0) { - D->offset = st.st_size; - if (D->offset >= D->size) { - TLS->cur_downloading_bytes += D->size; - TLS->cur_downloaded_bytes += D->offset; - vlogprintf (E_NOTICE, "Already downloaded\n"); - end_load (TLS, D, callback, callback_extra); - return; - } - } - - TLS->cur_downloading_bytes += D->size; - TLS->cur_downloaded_bytes += D->offset; - //update_prompt (); - } - D->refcnt ++; - clear_packet (); - out_int (CODE_upload_get_file); - if (!D->id) { - out_int (CODE_input_file_location); - out_long (D->volume); - out_int (D->local_id); - out_long (D->secret); - } else { - if (D->iv) { - out_int (CODE_input_encrypted_file_location); - } else { - out_int (D->type); - } - out_long (D->id); - out_long (D->access_hash); - } - out_int (D->offset); - out_int (1 << 14); - tglq_send_query (TLS, TLS->DC_list[D->dc], packet_ptr - packet_buffer, packet_buffer, &download_methods, D, callback, callback_extra); - //tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &download_methods, D); -} - -void tgl_do_load_photo_size (struct tgl_state *TLS, struct tgl_photo_size *P, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - if (!P->loc.dc) { - vlogprintf (E_WARNING, "Bad video thumb\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - - assert (P); - struct download *D = talloc0 (sizeof (*D)); - D->id = 0; - D->offset = 0; - D->size = P->size; - D->volume = P->loc.volume; - D->dc = P->loc.dc; - D->local_id = P->loc.local_id; - D->secret = P->loc.secret; - D->name = 0; - D->fd = -1; - load_next_part (TLS, D, callback, callback_extra); -} - -void tgl_do_load_photo (struct tgl_state *TLS, struct tgl_photo *photo, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - if (!photo->sizes_num) { - vlogprintf (E_WARNING, "No sizes\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - int max = -1; - int maxi = 0; - int i; - for (i = 0; i < photo->sizes_num; i++) { - if (photo->sizes[i].w + photo->sizes[i].h > max) { - max = photo->sizes[i].w + photo->sizes[i].h; - maxi = i; - } - } - tgl_do_load_photo_size (TLS, &photo->sizes[maxi], callback, callback_extra); -} - -void tgl_do_load_video_thumb (struct tgl_state *TLS, struct tgl_video *video, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - tgl_do_load_photo_size (TLS, &video->thumb, callback, callback_extra); -} - -void tgl_do_load_document_thumb (struct tgl_state *TLS, struct tgl_document *video, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - tgl_do_load_photo_size (TLS, &video->thumb, callback, callback_extra); -} - -void tgl_do_load_video (struct tgl_state *TLS, struct tgl_video *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - assert (V); - struct download *D = talloc0 (sizeof (*D)); - D->offset = 0; - D->size = V->size; - D->id = V->id; - D->access_hash = V->access_hash; - D->dc = V->dc_id; - D->name = 0; - D->fd = -1; - D->type = CODE_input_video_file_location; - load_next_part (TLS, D, callback, callback_extra); -} - -void tgl_do_load_audio (struct tgl_state *TLS, struct tgl_audio *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - assert (V); - struct download *D = talloc0 (sizeof (*D)); - D->offset = 0; - D->size = V->size; - D->id = V->id; - D->access_hash = V->access_hash; - D->dc = V->dc_id; - D->name = 0; - D->fd = -1; - D->type = CODE_input_audio_file_location; - load_next_part (TLS, D, callback, callback_extra); -} - -void tgl_do_load_document (struct tgl_state *TLS, struct tgl_document *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - assert (V); - struct download *D = talloc0 (sizeof (*D)); - D->offset = 0; - D->size = V->size; - D->id = V->id; - D->access_hash = V->access_hash; - D->dc = V->dc_id; - D->name = 0; - D->fd = -1; - D->type = CODE_input_document_file_location; - load_next_part (TLS, D, callback, callback_extra); -} - -void tgl_do_load_encr_video (struct tgl_state *TLS, struct tgl_encr_video *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra) { - assert (V); - struct download *D = talloc0 (sizeof (*D)); - D->offset = 0; - D->size = V->size; - D->id = V->id; - D->access_hash = V->access_hash; - D->dc = V->dc_id; - D->name = 0; - D->fd = -1; - D->key = V->key; - D->iv = talloc (32); - memcpy (D->iv, V->iv, 32); - load_next_part (TLS, D, callback, callback_extra); - - unsigned char md5[16]; - unsigned char str[64]; - memcpy (str, V->key, 32); - memcpy (str + 32, V->iv, 32); - MD5 (str, 64, md5); - assert (V->key_fingerprint == ((*(int *)md5) ^ (*(int *)(md5 + 4)))); -} -/* }}} */ - -/* {{{ Export auth */ - -static int import_auth_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_auth_authorization); - fetch_int (); // expires - tglf_fetch_alloc_user (TLS); - - bl_do_dc_signed (TLS, ((struct tgl_dc *)q->extra)->id); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -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 tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_auth_exported_authorization); - bl_do_set_our_id (TLS, fetch_int ()); - int l = prefetch_strlen (); - char *s = talloc (l); - memcpy (s, fetch_str (l), l); - - clear_packet (); - tgl_do_insert_header (); - out_int (CODE_auth_import_authorization); - out_int (TLS->our_id); - out_cstring (s, l); - tglq_send_query (TLS, q->extra, packet_ptr - packet_buffer, packet_buffer, &import_auth_methods, q->extra, q->callback, q->callback_extra); - tfree (s, l); - return 0; -} - -static struct query_methods export_auth_methods = { - .on_answer = export_auth_on_answer, - .on_error = fail_on_error, - .type = TYPE_TO_PARAM(auth_exported_authorization) -}; - -void tgl_do_export_auth (struct tgl_state *TLS, int num, void (*callback) (struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - clear_packet (); - out_int (CODE_auth_export_authorization); - out_int (num); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &export_auth_methods, TLS->DC_list[num], callback, callback_extra); -} -/* }}} */ - -/* {{{ Add contact */ -static int add_contact_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_contacts_imported_contacts); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - if (n > 0) { - vlogprintf (E_DEBUG, "Added successfully"); - } else { - vlogprintf (E_DEBUG, "Not added"); - } - int i; - for (i = 0; i < n ; i++) { - assert (fetch_int () == (int)CODE_imported_contact); - fetch_int (); // uid - fetch_long (); // client_id - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - long long id = fetch_long (); - vlogprintf (E_NOTICE, "contact #%lld not added. Please retry\n", id); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - - struct tgl_user **UL = talloc (n * sizeof (void *)); - for (i = 0; i < n; i++) { - UL[i] = tglf_fetch_alloc_user (TLS); - } - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, struct tgl_user **))q->callback) (TLS, q->callback_extra, 1, n, UL); - } - tfree (UL, n * sizeof (void *)); - return 0; -} - -static struct query_methods add_contact_methods = { - .on_answer = add_contact_on_answer, - .type = TYPE_TO_PARAM(contacts_imported_contacts) -}; - -void tgl_do_add_contact (struct tgl_state *TLS, 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)(struct tgl_state *TLS,void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_import_contacts); - out_int (CODE_vector); - out_int (1); - out_int (CODE_input_phone_contact); - long long r; - tglt_secure_random (&r, 8); - out_long (r); - out_cstring (phone, phone_len); - out_cstring (first_name, first_name_len); - out_cstring (last_name, last_name_len); - out_int (force ? CODE_bool_true : CODE_bool_false); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &add_contact_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Add contact */ -static int del_contact_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (skip_type_contacts_link (TYPE_TO_PARAM(contacts_link)) >= 0); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods del_contact_methods = { - .on_answer = del_contact_on_answer, - .type = TYPE_TO_PARAM(contacts_link) -}; - -void tgl_do_del_contact (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - if (tgl_get_peer_type (id) != TGL_PEER_USER) { - if (callback) { - callback (TLS, callback_extra, 0); - } - return; - } - clear_packet (); - out_int (CODE_contacts_delete_contact); - - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &del_contact_methods, 0, callback, callback_extra); -} - /* }}} */ - -/* {{{ Msg search */ -void _tgl_do_msg_search (struct tgl_state *TLS, tgl_peer_id_t id, int from, int to, int limit, int offset, int max_id, char *s, int list_offset, int list_size, struct tgl_message **list, void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra); -static int msg_search_on_answer (struct tgl_state *TLS, struct query *q UU) { - int count = -1; - int i; - int x = fetch_int (); - assert (x == (int)CODE_messages_messages_slice || x == (int)CODE_messages_messages); - if (x == (int)CODE_messages_messages_slice) { - count = fetch_int (); - //fetch_int (); - } - assert (fetch_int () == CODE_vector); - void **T = q->extra; - struct tgl_message **ML = T[0]; - int list_offset = (long)T[1]; - int list_size = (long)T[2]; - tgl_peer_id_t id = tgl_set_peer_id ((long)T[4], (long)T[3]); - int limit = (long)T[5]; - int offset = (long)T[6]; - int from = (long)T[7]; - int to = (long)T[8]; - char *s = T[9]; - tfree (T, sizeof (void *) * 10); - - int n = fetch_int (); - - if (list_size - list_offset < n) { - int new_list_size = 2 * list_size; - if (new_list_size - list_offset < n) { - new_list_size = n + list_offset; - } - ML = trealloc (ML, list_size * sizeof (void *), new_list_size * sizeof (void *)); - assert (ML); - list_size = new_list_size; - } - //struct tgl_message **ML = talloc (sizeof (void *) * n); - for (i = 0; i < n; i++) { - ML[i + list_offset] = tglf_fetch_alloc_message (TLS); - } - list_offset += n; - offset += n; - limit -= n; - if (count >= 0 && limit + offset >= count) { - limit = count - offset; - if (limit < 0) { limit = 0; } - } - assert (limit >= 0); - - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - - - if (limit <= 0 || x == (int)CODE_messages_messages) { - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, struct tgl_message **))q->callback) (TLS, q->callback_extra, 1, list_offset, ML); - } - - tfree_str (s); - tfree (ML, sizeof (void *) * list_size); - } else { - _tgl_do_msg_search (TLS, id, from, to, limit, 0, ML[list_offset - 1]->id, s, list_offset, list_size, ML, q->callback, q->callback_extra); - } - return 0; -} - -static struct query_methods msg_search_methods = { - .on_answer = msg_search_on_answer, - .type = TYPE_TO_PARAM(messages_messages) -}; - -void _tgl_do_msg_search (struct tgl_state *TLS, tgl_peer_id_t id, int from, int to, int limit, int offset, int max_id, char *s, int list_offset, int list_size, struct tgl_message **list, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) { - if (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT) { - vlogprintf (E_WARNING, "Can not search in secure chat\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0, 0); - } - return; - } - clear_packet (); - out_int (CODE_messages_search); - if (tgl_get_peer_type (id) == TGL_PEER_UNKNOWN) { - out_int (CODE_input_peer_empty); - } else { - out_peer_id (TLS, id); - } - void **T = talloc (sizeof (void *) * 10); - T[0] = list; - T[1] = (void *)(long)list_offset; - T[2] = (void *)(long)list_size; - T[3] = (void *)(long)tgl_get_peer_id (id); - T[4] = (void *)(long)tgl_get_peer_type (id); - T[5] = (void *)(long)limit; - T[6] = (void *)(long)offset; - T[7] = (void *)(long)from; - T[8] = (void *)(long)to; - T[9] = s; - - out_string (s); - out_int (CODE_input_messages_filter_empty); - out_int (from); - out_int (to); - out_int (offset); // offset - out_int (max_id); // max_id - out_int (limit); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &msg_search_methods, T, callback, callback_extra); -} - -void tgl_do_msg_search (struct tgl_state *TLS, tgl_peer_id_t id, int from, int to, int limit, int offset, const char *s, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra) { - _tgl_do_msg_search (TLS, id, from, to, limit, offset, 0, tstrdup (s), 0, 0, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Contacts search */ -static int contacts_search_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == CODE_contacts_found); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - assert (fetch_int () == (int)CODE_contact_found); - fetch_int (); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - - struct tgl_user **UL = talloc (sizeof (void *) * n); - for (i = 0; i < n; i++) { - UL[i] = tglf_fetch_alloc_user (TLS); - } - /*print_start (); - push_color (COLOR_YELLOW); - for (i = 0; i < n; i++) { - struct tgl_user *U = tglf_fetch_alloc_user (TLS); - printf ("User "); - push_color (COLOR_RED); - printf ("%s %s", U->first_name, U->last_name); - pop_color (); - printf (". Phone %s\n", U->phone); - } - pop_color (); - print_end ();*/ - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, struct tgl_user **))q->callback) (TLS, q->callback_extra, 1, n, UL); - } - tfree (UL, sizeof (void *) * n); - return 0; -} - -static struct query_methods contacts_search_methods = { - .on_answer = contacts_search_on_answer, - .type = TYPE_TO_PARAM(contacts_found) -}; - -void tgl_do_contacts_search (struct tgl_state *TLS, int limit, const char *s, void (*callback) (struct tgl_state *, void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_search); - out_string (s); - out_int (limit); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &contacts_search_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Encr accept */ -static int send_encr_accept_on_answer (struct tgl_state *TLS, struct query *q UU) { - struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (TLS); - - /*if (E->state == sc_ok) { - print_start (); - push_color (COLOR_YELLOW); - printf ("Encrypted connection with "); - print_encr_chat_name (E->id, (void *)E); - printf (" established\n"); - pop_color (); - print_end (); - } else { - print_start (); - push_color (COLOR_YELLOW); - printf ("Encrypted connection with "); - print_encr_chat_name (E->id, (void *)E); - printf (" failed\n"); - pop_color (); - print_end (); - }*/ - - if (E->state == sc_ok) { - tgl_do_send_encr_chat_layer (TLS, E); - } - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_secret_chat *))q->callback) (TLS, q->callback_extra, E->state == sc_ok, E); - } - return 0; -} - -static int send_encr_request_on_answer (struct tgl_state *TLS, struct query *q UU) { - struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (TLS); - /*if (E->state == sc_deleted) { - print_start (); - push_color (COLOR_YELLOW); - printf ("Encrypted connection with "); - print_encr_chat_name (E->id, (void *)E); - printf (" can not be established\n"); - pop_color (); - print_end (); - } else { - print_start (); - push_color (COLOR_YELLOW); - printf ("Establishing connection with "); - print_encr_chat_name (E->id, (void *)E); - printf ("\n"); - pop_color (); - print_end (); - - assert (E->state == sc_waiting); - }*/ - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_secret_chat *))q->callback) (TLS, q->callback_extra, E->state != sc_deleted, E); - } - return 0; -} - -static struct query_methods send_encr_accept_methods = { - .on_answer = send_encr_accept_on_answer, - .type = TYPE_TO_PARAM(encrypted_chat) -}; - -static struct query_methods send_encr_request_methods = { - .on_answer = send_encr_request_on_answer, - .type = TYPE_TO_PARAM(encrypted_chat) -}; - -//int encr_root; -//unsigned char *encr_prime; -//int encr_param_version; -//static BN_CTX *ctx; - -void tgl_do_send_accept_encr_chat (struct tgl_state *TLS, struct tgl_secret_chat *E, unsigned char *random, void (*callback)(struct tgl_state *TLS,void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) { - int i; - int ok = 0; - for (i = 0; i < 64; i++) { - if (E->key[i]) { - ok = 1; - break; - } - } - if (ok) { - if (callback) { - callback (TLS, callback_extra, 1, E); - } - return; - } // Already generated key for this chat - assert (E->g_key); - assert (TLS->BN_ctx); - unsigned char random_here[256]; - tglt_secure_random (random_here, 256); - for (i = 0; i < 256; i++) { - random[i] ^= random_here[i]; - } - BIGNUM *b = BN_bin2bn (random, 256, 0); - ensure_ptr (b); - BIGNUM *g_a = BN_bin2bn (E->g_key, 256, 0); - ensure_ptr (g_a); - assert (tglmp_check_g (TLS, TLS->encr_prime, g_a) >= 0); - //if (!ctx) { - // ctx = BN_CTX_new (); - // ensure_ptr (ctx); - //} - BIGNUM *p = BN_bin2bn (TLS->encr_prime, 256, 0); - ensure_ptr (p); - BIGNUM *r = BN_new (); - ensure_ptr (r); - ensure (BN_mod_exp (r, g_a, b, p, TLS->BN_ctx)); - static unsigned char kk[256]; - memset (kk, 0, sizeof (kk)); - BN_bn2bin (r, kk + (256 - BN_num_bytes (r))); - for (i = 0; i < 256; i++) { - kk[i] ^= E->nonce[i]; - } - static unsigned char sha_buffer[20]; - sha1 (kk, 256, sha_buffer); - - bl_do_encr_chat_set_key (TLS, E, kk, *(long long *)(sha_buffer + 12)); - - clear_packet (); - out_int (CODE_messages_accept_encryption); - out_int (CODE_input_encrypted_chat); - out_int (tgl_get_peer_id (E->id)); - out_long (E->access_hash); - - ensure (BN_set_word (g_a, TLS->encr_root)); - ensure (BN_mod_exp (r, g_a, b, p, TLS->BN_ctx)); - static unsigned char buf[256]; - memset (buf, 0, sizeof (buf)); - BN_bn2bin (r, buf + (256 - BN_num_bytes (r))); - out_cstring ((void *)buf, 256); - - out_long (E->key_fingerprint); - BN_clear_free (b); - BN_clear_free (g_a); - BN_clear_free (p); - BN_clear_free (r); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_accept_methods, E, callback, callback_extra); -} - -void tgl_do_create_keys_end (struct tgl_state *TLS, struct tgl_secret_chat *U) { - assert (TLS->encr_prime); - BIGNUM *g_b = BN_bin2bn (U->g_key, 256, 0); - ensure_ptr (g_b); - assert (tglmp_check_g (TLS, TLS->encr_prime, g_b) >= 0); - BIGNUM *p = BN_bin2bn (TLS->encr_prime, 256, 0); - ensure_ptr (p); - BIGNUM *r = BN_new (); - ensure_ptr (r); - BIGNUM *a = BN_bin2bn ((void *)U->key, 256, 0); - ensure_ptr (a); - ensure (BN_mod_exp (r, g_b, a, p, TLS->BN_ctx)); - - unsigned char *t = talloc (256); - memcpy (t, U->key, 256); - - memset (U->key, 0, sizeof (U->key)); - BN_bn2bin (r, (void *)(((char *)(U->key)) + (256 - BN_num_bytes (r)))); - int i; - for (i = 0; i < 64; i++) { - U->key[i] ^= *(((int *)U->nonce) + i); - } - - static unsigned char sha_buffer[20]; - sha1 ((void *)U->key, 256, sha_buffer); - long long k = *(long long *)(sha_buffer + 12); - if (k != U->key_fingerprint) { - vlogprintf (E_WARNING, "Key fingerprint mismatch (my 0x%llx 0x%llx)\n", (unsigned long long)k, (unsigned long long)U->key_fingerprint); - U->state = sc_deleted; - } - - tfree_secure (t, 256); - - BN_clear_free (p); - BN_clear_free (g_b); - BN_clear_free (r); - BN_clear_free (a); -} - -void tgl_do_send_create_encr_chat (struct tgl_state *TLS, void *x, unsigned char *random, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) { - int user_id = (long)x; - int i; - unsigned char random_here[256]; - tglt_secure_random (random_here, 256); - for (i = 0; i < 256; i++) { - random[i] ^= random_here[i]; - } - BIGNUM *a = BN_bin2bn (random, 256, 0); - ensure_ptr (a); - BIGNUM *p = BN_bin2bn (TLS->encr_prime, 256, 0); - ensure_ptr (p); - - BIGNUM *g = BN_new (); - ensure_ptr (g); - - ensure (BN_set_word (g, TLS->encr_root)); - - BIGNUM *r = BN_new (); - ensure_ptr (r); - - ensure (BN_mod_exp (r, g, a, p, TLS->BN_ctx)); - - BN_clear_free (a); - - static char g_a[256]; - memset (g_a, 0, 256); - - BN_bn2bin (r, (void *)(g_a + (256 - BN_num_bytes (r)))); - - int t = lrand48 (); - while (tgl_peer_get (TLS, TGL_MK_ENCR_CHAT (t))) { - t = lrand48 (); - } - - bl_do_encr_chat_init (TLS, t, user_id, (void *)random, (void *)g_a); - tgl_peer_t *_E = tgl_peer_get (TLS, TGL_MK_ENCR_CHAT (t)); - assert (_E); - struct tgl_secret_chat *E = &_E->encr_chat; - - clear_packet (); - out_int (CODE_messages_request_encryption); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_USER (E->user_id)); - assert (U); - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (E->user_id); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (E->user_id); - } - out_int (tgl_get_peer_id (E->id)); - out_cstring (g_a, 256); - //write_secret_chat_file (); - - BN_clear_free (g); - BN_clear_free (p); - BN_clear_free (r); - - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &send_encr_request_methods, E, callback, callback_extra); -} - -static int get_dh_config_on_answer (struct tgl_state *TLS, struct query *q UU) { - unsigned x = fetch_int (); - assert (x == CODE_messages_dh_config || x == CODE_messages_dh_config_not_modified); - if (x == CODE_messages_dh_config) { - int a = fetch_int (); - int l = prefetch_strlen (); - assert (l == 256); - char *s = fetch_str (l); - int v = fetch_int (); - bl_do_set_dh_params (TLS, a, (void *)s, v); - - BIGNUM *p = BN_bin2bn ((void *)s, 256, 0); - ensure_ptr (p); - assert (tglmp_check_DH_params (TLS, p, a) >= 0); - BN_free (p); - } else { - assert (TLS->encr_param_version); - } - int l = prefetch_strlen (); - assert (l == 256); - unsigned char *random = talloc (256); - memcpy (random, fetch_str (256), 256); - if (q->extra) { - void **x = q->extra; - ((void (*)(struct tgl_state *, void *, void *, void *, void *))(*x))(TLS, x[1], random, q->callback, q->callback_extra); - tfree (x, 2 * sizeof (void *)); - tfree_secure (random, 256); - } else { - tfree_secure (random, 256); - } - return 0; -} - -static struct query_methods get_dh_config_methods = { - .on_answer = get_dh_config_on_answer, - .type = TYPE_TO_PARAM(messages_dh_config) -}; - -void tgl_do_accept_encr_chat_request (struct tgl_state *TLS, struct tgl_secret_chat *E, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) { - if (E->state != sc_request) { - if (callback) { - callback (TLS, callback_extra, 0, E); - } - return; - } - assert (E->state == sc_request); - - clear_packet (); - out_int (CODE_messages_get_dh_config); - out_int (TLS->encr_param_version); - out_int (256); - void **x = talloc (2 * sizeof (void *)); - x[0] = tgl_do_send_accept_encr_chat; - x[1] = E; - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x, callback, callback_extra); -} - -void tgl_do_create_encr_chat_request (struct tgl_state *TLS, int user_id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_get_dh_config); - out_int (TLS->encr_param_version); - out_int (256); - void **x = talloc (2 * sizeof (void *)); - x[0] = tgl_do_send_create_encr_chat; - x[1] = (void *)(long)(user_id); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_dh_config_methods, x, callback, callback_extra); -} -/* }}} */ - -/* {{{ Get difference */ -//int unread_messages; -//int difference_got; -//int seq, pts, qts, last_date; -static int get_state_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (TLS->locks & TGL_LOCK_DIFF); - TLS->locks ^= TGL_LOCK_DIFF; - assert (fetch_int () == (int)CODE_updates_state); - bl_do_set_pts (TLS, fetch_int ()); - bl_do_set_qts (TLS, fetch_int ()); - bl_do_set_date (TLS, fetch_int ()); - bl_do_set_seq (TLS, fetch_int ()); - //unread_messages = fetch_int (); - fetch_int (); - //write_state_file (); - //difference_got = 1; - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -static int lookup_state_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_updates_state); - int pts = fetch_int (); - int qts = fetch_int (); - fetch_int (); - int seq = fetch_int (); - fetch_int (); - - if (pts > TLS->pts || qts > TLS->qts || seq > TLS->seq) { - tgl_do_get_difference (TLS, 0, 0, 0); - } - return 0; -} - - -//int get_difference_active; -static int get_difference_on_answer (struct tgl_state *TLS, struct query *q UU) { - //get_difference_active = 0; - assert (TLS->locks & TGL_LOCK_DIFF); - TLS->locks ^= TGL_LOCK_DIFF; - - unsigned x = fetch_int (); - if (x == CODE_updates_difference_empty) { - bl_do_set_date (TLS, fetch_int ()); - bl_do_set_seq (TLS, fetch_int ()); - //difference_got = 1; - - vlogprintf (E_DEBUG, "Empty difference. Seq = %d\n", TLS->seq); - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - } else if (x == CODE_updates_difference || x == CODE_updates_difference_slice) { - int n, i; - assert (fetch_int () == CODE_vector); - n = fetch_int (); - struct tgl_message **ML = talloc (n * sizeof (void *)); - int ml_pos = 0; - for (i = 0; i < n; i++) { - ML[ml_pos ++] = tglf_fetch_alloc_message (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - struct tgl_message **EL = talloc (n * sizeof (void *)); - int el_pos = 0; - for (i = 0; i < n; i++) { - EL[el_pos ++] = tglf_fetch_alloc_encrypted_message (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglu_work_update (TLS, 0, 0); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - assert (fetch_int () == (int)CODE_updates_state); - bl_do_set_pts (TLS, fetch_int ()); - bl_do_set_qts (TLS, fetch_int ()); - bl_do_set_date (TLS, fetch_int ()); - if (x == CODE_updates_difference) { - bl_do_set_seq (TLS, fetch_int ()); - vlogprintf (E_DEBUG, "Difference end. New seq = %d\n", TLS->seq); - } else { - fetch_int (); - } - //unread_messages = fetch_int (); - fetch_int (); - //write_state_file (); - /*for (i = 0; i < ml_pos; i++) { - print_message (ML[i]); - }*/ - for (i = 0; i < ml_pos; i++) { - //TLS->callback.new_msg (ML[i]); - bl_do_msg_update (TLS, ML[i]->id); - } - for (i = 0; i < el_pos; i++) { - //TLS->callback.new_msg (EL[i]); - bl_do_msg_update (TLS, EL[i]->id); - } - tfree (ML, ml_pos * sizeof (void *)); - tfree (EL, el_pos * sizeof (void *)); - - if (x == CODE_updates_difference_slice) { - //if (q->callback) { - // ((void (*)(void *, int))q->callback) (q->callback_extra, 1); - //} - tgl_do_get_difference (TLS, 0, q->callback, q->callback_extra); - } else { - //difference_got = 1; - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - } - } else { - assert (0); - } - return 0; -} - -static struct query_methods lookup_state_methods = { - .on_answer = lookup_state_on_answer, - .type = TYPE_TO_PARAM(updates_state) -}; - -static struct query_methods get_state_methods = { - .on_answer = get_state_on_answer, - .type = TYPE_TO_PARAM(updates_state) -}; - -static struct query_methods get_difference_methods = { - .on_answer = get_difference_on_answer, - .type = TYPE_TO_PARAM(updates_difference) -}; - -void tgl_do_lookup_state (struct tgl_state *TLS) { - if (TLS->locks & TGL_LOCK_DIFF) { - return; - } - clear_packet (); - tgl_do_insert_header (); - out_int (CODE_updates_get_state); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &lookup_state_methods, 0, 0, 0); -} - -void tgl_do_get_difference (struct tgl_state *TLS, int sync_from_start, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - //get_difference_active = 1; - //difference_got = 0; - if (TLS->locks & TGL_LOCK_DIFF) { - if (callback) { - callback (TLS, callback_extra, 0); - } - return; - } - TLS->locks |= TGL_LOCK_DIFF; - clear_packet (); - tgl_do_insert_header (); - if (TLS->pts > 0 || sync_from_start) { - if (TLS->pts == 0) { TLS->pts = 1; } - //if (TLS->qts == 0) { TLS->qts = 1; } - if (TLS->date == 0) { TLS->date = 1; } - out_int (CODE_updates_get_difference); - out_int (TLS->pts); - out_int (TLS->date); - out_int (TLS->qts); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_difference_methods, 0, callback, callback_extra); - } else { - out_int (CODE_updates_get_state); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_state_methods, 0, callback, callback_extra); - } -} -/* }}} */ - -/* {{{ Visualize key */ -/*char *colors[4] = {COLOR_GREY, COLOR_CYAN, COLOR_BLUE, COLOR_GREEN}; - -void tgl_do_visualize_key (tgl_peer_id_t id) { - assert (tgl_get_peer_type (id) == TGL_PEER_ENCR_CHAT); - tgl_peer_t *P = tgl_peer_get (TLS, id); - assert (P); - if (P->encr_chat.state != sc_ok) { - rprintf ("Chat is not initialized yet\n"); - return; - } - unsigned char buf[20]; - SHA1 ((void *)P->encr_chat.key, 256, buf); - print_start (); - int i; - for (i = 0; i < 16; i++) { - int x = buf[i]; - int j; - for (j = 0; j < 4; j ++) { - push_color (colors[x & 3]); - push_color (COLOR_INVERSE); - printf (" "); - pop_color (); - pop_color (); - x = x >> 2; - } - if (i & 1) { printf ("\n"); } - } - print_end (); -}*/ - -void tgl_do_visualize_key (struct tgl_state *TLS, 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 (TLS, 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 */ -/*int get_suggested_on_answer (struct query *q UU) { - assert (fetch_int () == CODE_contacts_suggested); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - logprintf ("n = %d\n", n); - assert (n <= 200); - int l[400]; - int i; - for (i = 0; i < n; i++) { - assert (fetch_int () == CODE_contact_suggested); - l[2 * i] = fetch_int (); - l[2 * i + 1] = fetch_int (); - } - assert (fetch_int () == CODE_vector); - int m = fetch_int (); - assert (n == m); - print_start (); - push_color (COLOR_YELLOW); - for (i = 0; i < m; i++) { - tgl_peer_t *U = (void *)tglf_fetch_alloc_user (TLS); - assert (tgl_get_peer_id (U->id) == l[2 * i]); - print_user_name (U->id, U); - printf (" phone %s: %d mutual friends\n", U->user.phone, l[2 * i + 1]); - } - pop_color (); - print_end (); - return 0; -} - -struct query_methods get_suggested_methods = { - .on_answer = get_suggested_on_answer, - .type = TYPE_TO_PARAM(contacts_suggested) -}; - -void tgl_do_get_suggested (void) { - clear_packet (); - out_int (CODE_contacts_get_suggested); - out_int (100); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &get_suggested_methods, 0); -}*/ -/* }}} */ - -/* {{{ Add user to chat */ - -static struct query_methods add_user_to_chat_methods = { - .on_answer = fwd_msg_on_answer, - .type = TYPE_TO_PARAM(messages_stated_message) -}; - -void tgl_do_add_user_to_chat (struct tgl_state *TLS, tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_add_chat_user); - out_int (tgl_get_peer_id (chat_id)); - - assert (tgl_get_peer_type (id) == TGL_PEER_USER); - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - out_int (limit); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0, callback, callback_extra); -} - -void tgl_do_del_user_from_chat (struct tgl_state *TLS, tgl_peer_id_t chat_id, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_delete_chat_user); - out_int (tgl_get_peer_id (chat_id)); - - assert (tgl_get_peer_type (id) == TGL_PEER_USER); - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &add_user_to_chat_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Create secret chat */ -//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 (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra) { - assert (tgl_get_peer_type (id) == TGL_PEER_USER); - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (!U) { - vlogprintf (E_WARNING, "Can not create chat with unknown user\n"); - return; - } - - tgl_do_create_encr_chat_request (TLS, tgl_get_peer_id (id), callback, callback_extra); -} -/* }}} */ - -/* {{{ Create group chat */ -static struct query_methods create_group_chat_methods = { - .on_answer = fwd_msg_on_answer, - .type = TYPE_TO_PARAM(messages_stated_message) -}; - -void tgl_do_create_group_chat (struct tgl_state *TLS, tgl_peer_id_t id, char *chat_topic, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - assert (tgl_get_peer_type (id) == TGL_PEER_USER); - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (!U) { - vlogprintf (E_WARNING, "Can not create chat with unknown user\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - clear_packet (); - out_int (CODE_messages_create_chat); - out_int (CODE_vector); - out_int (1); // Number of users, currently we support only 1 user. - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - out_string (chat_topic); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &create_group_chat_methods, 0, callback, callback_extra); -} - -void tgl_do_create_group_chat_ex (struct tgl_state *TLS, int users_num, tgl_peer_id_t ids[], char *chat_topic, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_create_chat); - out_int (CODE_vector); - out_int (users_num); // Number of users, currently we support only 1 user. - int i; - for (i = 0; i < users_num; i++) { - tgl_peer_id_t id = ids[i]; - tgl_peer_t *U = tgl_peer_get (TLS, id); - if (!U || tgl_get_peer_type (id) != TGL_PEER_USER) { - vlogprintf (E_WARNING, "Can not create chat with unknown user\n"); - if (callback) { - callback (TLS, callback_extra, 0, 0); - } - return; - } - if (U && U->user.access_hash) { - out_int (CODE_input_user_foreign); - out_int (tgl_get_peer_id (id)); - out_long (U->user.access_hash); - } else { - out_int (CODE_input_user_contact); - out_int (tgl_get_peer_id (id)); - } - } - out_string (chat_topic); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &create_group_chat_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Delete msg */ - -static int delete_msg_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - fetch_skip (n); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods delete_msg_methods = { - .on_answer = delete_msg_on_answer, - .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int)) -}; - -void tgl_do_delete_msg (struct tgl_state *TLS, long long id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_delete_messages); - out_int (CODE_vector); - out_int (1); - out_int (id); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &delete_msg_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Restore msg */ - -static int restore_msg_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - fetch_skip (n); - //logprintf ("Restored %d messages\n", n); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods restore_msg_methods = { - .on_answer = restore_msg_on_answer, - .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int)) -}; - -void tgl_do_restore_msg (struct tgl_state *TLS, long long id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - clear_packet (); - out_int (CODE_messages_restore_messages); - out_int (CODE_vector); - out_int (1); - out_int (id); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &restore_msg_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Export card */ - -static int export_card_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - //logprintf ("Restored %d messages\n", n); - int *r = talloc (4 * n); - fetch_ints (r, n); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, int, int *))q->callback) (TLS, q->callback_extra, 1, n, r); - } - free (r); - return 0; -} - -static struct query_methods export_card_methods = { - .on_answer = export_card_on_answer, - .type = TYPE_TO_PARAM_1(vector, TYPE_TO_PARAM (bare_int)) -}; - -void tgl_do_export_card (struct tgl_state *TLS, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, int *card), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_export_card); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &export_card_methods, 0, callback, callback_extra); -} -/* }}} */ - -/* {{{ Import card */ - -static int import_card_on_answer (struct tgl_state *TLS, struct query *q UU) { - struct tgl_user *U = tglf_fetch_alloc_user (TLS); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int, struct tgl_user *))q->callback) (TLS, q->callback_extra, 1, U); - } - return 0; -} - -static struct query_methods import_card_methods = { - .on_answer = import_card_on_answer, - .type = TYPE_TO_PARAM (user) -}; - -void tgl_do_import_card (struct tgl_state *TLS, int size, int *card, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra) { - clear_packet (); - out_int (CODE_contacts_import_card); - out_int (CODE_vector); - out_int (size); - out_ints (card, size); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &import_card_methods, 0, callback, callback_extra); -} -/* }}} */ - -#ifndef DISABLE_EXTF -static int ext_query_on_answer (struct tgl_state *TLS, struct query *q UU) { - if (q->callback) { - char *buf = tglf_extf_fetch (TLS, q->type); - ((void (*)(struct tgl_state *, void *, int, char *))q->callback) (TLS, q->callback_extra, 1, buf); - } - tgl_paramed_type_free (q->type); - return 0; -} - -static struct query_methods ext_query_methods = { - .on_answer = ext_query_on_answer, -}; - -void tgl_do_send_extf (struct tgl_state *TLS, char *data, int data_len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *buf), void *callback_extra) { - clear_packet (); - - ext_query_methods.type = tglf_extf_store (TLS, data, data_len); - - if (ext_query_methods.type) { - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &ext_query_methods, 0, callback, callback_extra); - } -} -#else -void tgl_do_send_extf (struct tgl_state *TLS, char *data, int data_len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *buf), void *callback_extra) { - if (callback) { - callback (TLS, callback_extra, 0, 0); - } -} -#endif - -static void set_flag_4 (struct tgl_state *TLS, void *_D, int success) { - struct tgl_dc *D = _D; - assert (success); - D->flags |= 4; - - TLS->timer_methods->insert (D->ev, TLS->temp_key_expire_time * 0.9); -} - -static int send_bind_temp_on_answer (struct tgl_state *TLS, struct query *q UU) { - assert (fetch_int () == (int)CODE_bool_true); - struct tgl_dc *D = q->extra; - D->flags |= 2; - tgl_do_help_get_config_dc (TLS, D, set_flag_4, D); - vlogprintf (E_DEBUG, "Bind successful in dc %d\n", D->id); - return 0; -} - -static struct query_methods send_bind_temp_methods = { - .on_answer = send_bind_temp_on_answer, - .on_error = fail_on_error, - .type = TYPE_TO_PARAM (bool) -}; - -void tgl_do_send_bind_temp_key (struct tgl_state *TLS, struct tgl_dc *D, long long nonce, int expires_at, void *data, int len, long long msg_id) { - clear_packet (); - out_int (CODE_auth_bind_temp_auth_key); - out_long (D->auth_key_id); - out_long (nonce); - out_int (expires_at); - out_cstring (data, len); - struct query *q = tglq_send_query_ex (TLS, D, packet_ptr - packet_buffer, packet_buffer, &send_bind_temp_methods, D, 0, 0, 2); - assert (q->msg_id == msg_id); -} - -static int update_status_on_answer (struct tgl_state *TLS, struct query *q UU) { - fetch_bool (); - - if (q->callback) { - ((void (*)(struct tgl_state *, void *, int))q->callback) (TLS, q->callback_extra, 1); - } - return 0; -} - -static struct query_methods update_status_methods = { - .on_answer = update_status_on_answer, - .type = TYPE_TO_PARAM(bool) -}; - -void tgl_do_update_status (struct tgl_state *TLS, int online UU, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra) { - clear_packet (); - out_int (CODE_account_update_status); - out_int (online ? CODE_bool_false : CODE_bool_true); - tglq_send_query (TLS, TLS->DC_working, packet_ptr - packet_buffer, packet_buffer, &update_status_methods, 0, callback, callback_extra); -} diff --git a/queries.h b/queries.h deleted file mode 100644 index 51c61c2..0000000 --- a/queries.h +++ /dev/null @@ -1,75 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ -//#include "net.h" -#ifndef __QUERIES_H__ -#define __QUERIES_H__ -#include "structures.h" -#include "auto.h" -#include "tgl-layout.h" - -#define QUERY_ACK_RECEIVED 1 -#define QUERY_FORCE_SEND 2 - -struct query; -struct query_methods { - int (*on_answer)(struct tgl_state *TLS, struct query *q); - int (*on_error)(struct tgl_state *TLS, struct query *q, int error_code, int len, char *error); - int (*on_timeout)(struct tgl_state *TLS, struct query *q); - struct paramed_type *type; -}; - -struct query { - long long msg_id; - int data_len; - int flags; - int seq_no; - long long session_id; - void *data; - struct query_methods *methods; - struct tgl_timer *ev; - struct tgl_dc *DC; - struct tgl_session *session; - struct paramed_type *type; - void *extra; - void *callback; - void *callback_extra; -}; - - -struct query *tglq_send_query (struct tgl_state *TLS, struct tgl_dc *DC, int len, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra); -void tglq_query_ack (struct tgl_state *TLS, long long id); -void tglq_query_error (struct tgl_state *TLS, long long id); -void tglq_query_result (struct tgl_state *TLS, long long id); -void tglq_query_restart (struct tgl_state *TLS, long long id); - -//double next_timer_in (void); -//void work_timers (void); - -//extern struct query_methods help_get_config_methods; - -double get_double_time (void); - -void tgl_do_send_bind_temp_key (struct tgl_state *TLS, struct tgl_dc *D, long long nonce, int expires_at, void *data, int len, long long msg_id); - -// For binlog - -//int get_dh_config_on_answer (struct query *q); -//void fetch_dc_option (void); -#endif diff --git a/scheme.tl b/scheme.tl deleted file mode 120000 index 40329f0..0000000 --- a/scheme.tl +++ /dev/null @@ -1 +0,0 @@ -scheme18.tl \ No newline at end of file diff --git a/scheme12.tl b/scheme12.tl deleted file mode 100644 index 7d37a6f..0000000 --- a/scheme12.tl +++ /dev/null @@ -1,505 +0,0 @@ -int ?= Int; -long ?= Long; -double ?= Double; -string ?= String; - -bytes string = Bytes; - -boolFalse#bc799737 = Bool; -boolTrue#997275b5 = Bool; - -vector#1cb5c415 {t:Type} # [ t ] = Vector t; - -error#c4b9f9bb code:int text:string = Error; - -null#56730bcc = Null; - -inputPeerEmpty#7f3b18ea = InputPeer; -inputPeerSelf#7da07ec9 = InputPeer; -inputPeerContact#1023dbe8 user_id:int = InputPeer; -inputPeerForeign#9b447325 user_id:int access_hash:long = InputPeer; -inputPeerChat#179be863 chat_id:int = InputPeer; - -inputUserEmpty#b98886cf = InputUser; -inputUserSelf#f7c1b13f = InputUser; -inputUserContact#86e94f65 user_id:int = InputUser; -inputUserForeign#655e74ff user_id:int access_hash:long = InputUser; - -inputPhoneContact#f392b7f4 client_id:long phone:string first_name:string last_name:string = InputContact; - -inputFile#f52ff27f id:long parts:int name:string md5_checksum:string = InputFile; - -inputMediaEmpty#9664f57f = InputMedia; -inputMediaUploadedPhoto#2dc53a7d file:InputFile = InputMedia; -inputMediaPhoto#8f2ab2ec id:InputPhoto = InputMedia; -inputMediaGeoPoint#f9c44144 geo_point:InputGeoPoint = InputMedia; -inputMediaContact#a6e45987 phone_number:string first_name:string last_name:string = InputMedia; -inputMediaUploadedVideo#4847d92a file:InputFile duration:int w:int h:int = InputMedia; -inputMediaUploadedThumbVideo#e628a145 file:InputFile thumb:InputFile duration:int w:int h:int = InputMedia; -inputMediaVideo#7f023ae6 id:InputVideo = InputMedia; - -inputChatPhotoEmpty#1ca48f57 = InputChatPhoto; -inputChatUploadedPhoto#94254732 file:InputFile crop:InputPhotoCrop = InputChatPhoto; -inputChatPhoto#b2e1bf08 id:InputPhoto crop:InputPhotoCrop = InputChatPhoto; - -inputGeoPointEmpty#e4c123d6 = InputGeoPoint; -inputGeoPoint#f3b7acc9 lat:double long:double = InputGeoPoint; - -inputPhotoEmpty#1cd7bf0d = InputPhoto; -inputPhoto#fb95c6c4 id:long access_hash:long = InputPhoto; - -inputVideoEmpty#5508ec75 = InputVideo; -inputVideo#ee579652 id:long access_hash:long = InputVideo; - -inputFileLocation#14637196 volume_id:long local_id:int secret:long = InputFileLocation; -inputVideoFileLocation#3d0364ec id:long access_hash:long = InputFileLocation; - -inputPhotoCropAuto#ade6b004 = InputPhotoCrop; -inputPhotoCrop#d9915325 crop_left:double crop_top:double crop_width:double = InputPhotoCrop; - -inputAppEvent#770656a8 time:double type:string peer:long data:string = InputAppEvent; - -peerUser#9db1bc6d user_id:int = Peer; -peerChat#bad0e5bb chat_id:int = Peer; - -storage.fileUnknown#aa963b05 = storage.FileType; -storage.fileJpeg#7efe0e = storage.FileType; -storage.fileGif#cae1aadf = storage.FileType; -storage.filePng#a4f63c0 = storage.FileType; -storage.filePdf#ae1e508d = storage.FileType; -storage.fileMp3#528a0677 = storage.FileType; -storage.fileMov#4b09ebbc = storage.FileType; -storage.filePartial#40bc6f52 = storage.FileType; -storage.fileMp4#b3cea0e4 = storage.FileType; -storage.fileWebp#1081464c = storage.FileType; - -fileLocationUnavailable#7c596b46 volume_id:long local_id:int secret:long = FileLocation; -fileLocation#53d69076 dc_id:int volume_id:long local_id:int secret:long = FileLocation; - -userEmpty#200250ba id:int = User; -userSelf#720535ec id:int first_name:string last_name:string phone:string photo:UserProfilePhoto status:UserStatus inactive:Bool = User; -userContact#f2fb8319 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userRequest#22e8ceb0 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userForeign#5214c89d id:int first_name:string last_name:string access_hash:long photo:UserProfilePhoto status:UserStatus = User; -userDeleted#b29ad7cc id:int first_name:string last_name:string = User; - -userProfilePhotoEmpty#4f11bae1 = UserProfilePhoto; -userProfilePhoto#d559d8c8 photo_id:long photo_small:FileLocation photo_big:FileLocation = UserProfilePhoto; - -userStatusEmpty#9d05049 = UserStatus; -userStatusOnline#edb93949 expires:int = UserStatus; -userStatusOffline#8c703f was_online:int = UserStatus; - -chatEmpty#9ba2d800 id:int = Chat; -chat#6e9c9bc7 id:int title:string photo:ChatPhoto participants_count:int date:int left:Bool version:int = Chat; -chatForbidden#fb0ccc41 id:int title:string date:int = Chat; - -chatFull#630e61be id:int participants:ChatParticipants chat_photo:Photo notify_settings:PeerNotifySettings = ChatFull; - -chatParticipant#c8d7493e user_id:int inviter_id:int date:int = ChatParticipant; - -chatParticipantsForbidden#fd2bb8a chat_id:int = ChatParticipants; -chatParticipants#7841b415 chat_id:int admin_id:int participants:Vector version:int = ChatParticipants; - -chatPhotoEmpty#37c1011c = ChatPhoto; -chatPhoto#6153276a photo_small:FileLocation photo_big:FileLocation = ChatPhoto; - -messageEmpty#83e5de54 id:int = Message; -message#22eb6aba id:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageForwarded#5f46804 id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageService#9f8d60bb id:int from_id:int to_id:Peer out:Bool unread:Bool date:int action:MessageAction = Message; - -messageMediaEmpty#3ded6320 = MessageMedia; -messageMediaPhoto#c8c45a2a photo:Photo = MessageMedia; -messageMediaVideo#a2d24290 video:Video = MessageMedia; -messageMediaGeo#56e0d474 geo:GeoPoint = MessageMedia; -messageMediaContact#5e7d2f39 phone_number:string first_name:string last_name:string user_id:int = MessageMedia; -messageMediaUnsupported#29632a36 bytes:bytes = MessageMedia; - -messageActionEmpty#b6aef7b0 = MessageAction; -messageActionChatCreate#a6638b9a title:string users:Vector = MessageAction; -messageActionChatEditTitle#b5a1ce5a title:string = MessageAction; -messageActionChatEditPhoto#7fcb13a8 photo:Photo = MessageAction; -messageActionChatDeletePhoto#95e3fbef = MessageAction; -messageActionChatAddUser#5e3cfc4b user_id:int = MessageAction; -messageActionChatDeleteUser#b2ae9b0c user_id:int = MessageAction; - -dialog#214a8cdf peer:Peer top_message:int unread_count:int = Dialog; - -photoEmpty#2331b22d id:long = Photo; -photo#22b56751 id:long access_hash:long user_id:int date:int caption:string geo:GeoPoint sizes:Vector = Photo; - -photoSizeEmpty#e17e23c type:string = PhotoSize; -photoSize#77bfb61b type:string location:FileLocation w:int h:int size:int = PhotoSize; -photoCachedSize#e9a734fa type:string location:FileLocation w:int h:int bytes:bytes = PhotoSize; - -videoEmpty#c10658a8 id:long = Video; -video#5a04a49f id:long access_hash:long user_id:int date:int caption:string duration:int size:int thumb:PhotoSize dc_id:int w:int h:int = Video; - -geoPointEmpty#1117dd5f = GeoPoint; -geoPoint#2049d70c long:double lat:double = GeoPoint; - -auth.checkedPhone#e300cc3b phone_registered:Bool phone_invited:Bool = auth.CheckedPhone; - -auth.sentCode#efed51d9 phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -auth.authorization#f6b673a4 expires:int user:User = auth.Authorization; - -auth.exportedAuthorization#df969c2d id:int bytes:bytes = auth.ExportedAuthorization; - -inputNotifyPeer#b8bc5b0c peer:InputPeer = InputNotifyPeer; -inputNotifyUsers#193b4417 = InputNotifyPeer; -inputNotifyChats#4a95e84e = InputNotifyPeer; -inputNotifyAll#a429b886 = InputNotifyPeer; - -inputPeerNotifyEventsEmpty#f03064d8 = InputPeerNotifyEvents; -inputPeerNotifyEventsAll#e86a2c74 = InputPeerNotifyEvents; - -inputPeerNotifySettings#46a2ce98 mute_until:int sound:string show_previews:Bool events_mask:int = InputPeerNotifySettings; - -peerNotifyEventsEmpty#add53cb3 = PeerNotifyEvents; -peerNotifyEventsAll#6d1ded88 = PeerNotifyEvents; - -peerNotifySettingsEmpty#70a68512 = PeerNotifySettings; -peerNotifySettings#8d5e11ee mute_until:int sound:string show_previews:Bool events_mask:int = PeerNotifySettings; - -wallPaper#ccb03657 id:int title:string sizes:Vector color:int = WallPaper; - -userFull#771095da user:User link:contacts.Link profile_photo:Photo notify_settings:PeerNotifySettings blocked:Bool real_first_name:string real_last_name:string = UserFull; - -contact#f911c994 user_id:int mutual:Bool = Contact; - -importedContact#d0028438 user_id:int client_id:long = ImportedContact; - -contactBlocked#561bc879 user_id:int date:int = ContactBlocked; - -contactFound#ea879f95 user_id:int = ContactFound; - -contactSuggested#3de191a1 user_id:int mutual_contacts:int = ContactSuggested; - -contactStatus#aa77b873 user_id:int expires:int = ContactStatus; - -chatLocated#3631cf4c chat_id:int distance:int = ChatLocated; - -contacts.foreignLinkUnknown#133421f8 = contacts.ForeignLink; -contacts.foreignLinkRequested#a7801f47 has_phone:Bool = contacts.ForeignLink; -contacts.foreignLinkMutual#1bea8ce1 = contacts.ForeignLink; - -contacts.myLinkEmpty#d22a1c60 = contacts.MyLink; -contacts.myLinkRequested#6c69efee contact:Bool = contacts.MyLink; -contacts.myLinkContact#c240ebd9 = contacts.MyLink; - -contacts.link#eccea3f5 my_link:contacts.MyLink foreign_link:contacts.ForeignLink user:User = contacts.Link; - -contacts.contacts#6f8b8cb2 contacts:Vector users:Vector = contacts.Contacts; -contacts.contactsNotModified#b74ba9d2 = contacts.Contacts; - -contacts.importedContacts#d1cd0a4c imported:Vector users:Vector = contacts.ImportedContacts; - -contacts.blocked#1c138d15 blocked:Vector users:Vector = contacts.Blocked; -contacts.blockedSlice#900802a1 count:int blocked:Vector users:Vector = contacts.Blocked; - -contacts.found#566000e results:Vector users:Vector = contacts.Found; - -contacts.suggested#5649dcc5 results:Vector users:Vector = contacts.Suggested; - -messages.dialogs#15ba6c40 dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; -messages.dialogsSlice#71e094f3 count:int dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; - -messages.messages#8c718e87 messages:Vector chats:Vector users:Vector = messages.Messages; -messages.messagesSlice#b446ae3 count:int messages:Vector chats:Vector users:Vector = messages.Messages; - -messages.messageEmpty#3f4e0648 = messages.Message; -messages.message#ff90c417 message:Message chats:Vector users:Vector = messages.Message; - -messages.statedMessages#969478bb messages:Vector chats:Vector users:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessage#d07ae726 message:Message chats:Vector users:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessage#d1f4d35c id:int date:int pts:int seq:int = messages.SentMessage; - -messages.chat#40e9002a chat:Chat users:Vector = messages.Chat; - -messages.chats#8150cbd8 chats:Vector users:Vector = messages.Chats; - -messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector users:Vector = messages.ChatFull; - -messages.affectedHistory#b7de36f2 pts:int seq:int offset:int = messages.AffectedHistory; - -inputMessagesFilterEmpty#57e2f66c = MessagesFilter; -inputMessagesFilterPhotos#9609a51c = MessagesFilter; -inputMessagesFilterVideo#9fc00e65 = MessagesFilter; -inputMessagesFilterPhotoVideo#56e9f0e4 = MessagesFilter; -inputMessagesFilterDocument#9eddf188 = MessagesFilter; -inputMessagesFilterAudio#cfc87522 = MessagesFilter; - -updateNewMessage#13abdb3 message:Message pts:int = Update; -updateMessageID#4e90bfd6 id:int random_id:long = Update; -updateReadMessages#c6649e31 messages:Vector pts:int = Update; -updateDeleteMessages#a92bfe26 messages:Vector pts:int = Update; -updateRestoreMessages#d15de04d messages:Vector pts:int = Update; -updateUserTyping#6baa8508 user_id:int = Update; -updateChatUserTyping#3c46cfe6 chat_id:int user_id:int = Update; -updateChatParticipants#7761198 participants:ChatParticipants = Update; -updateUserStatus#1bfbd823 user_id:int status:UserStatus = Update; -updateUserName#da22d9ad user_id:int first_name:string last_name:string = Update; -updateUserPhoto#95313b0c user_id:int date:int photo:UserProfilePhoto previous:Bool = Update; -updateContactRegistered#2575bbb9 user_id:int date:int = Update; -updateContactLink#51a48a9a user_id:int my_link:contacts.MyLink foreign_link:contacts.ForeignLink = Update; -updateActivation#6f690963 user_id:int = Update; -updateNewAuthorization#8f06529a auth_key_id:long date:int device:string location:string = Update; - -updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State; - -updates.differenceEmpty#5d75a138 date:int seq:int = updates.Difference; -updates.difference#f49ca0 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector state:updates.State = updates.Difference; -updates.differenceSlice#a8fb1981 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector intermediate_state:updates.State = updates.Difference; - -updatesTooLong#e317af7e = Updates; -updateShortMessage#d3f45784 id:int from_id:int message:string pts:int date:int seq:int = Updates; -updateShortChatMessage#2b2fbd4e id:int from_id:int chat_id:int message:string pts:int date:int seq:int = Updates; -updateShort#78d4dec1 update:Update date:int = Updates; -updatesCombined#725b04c3 updates:Vector users:Vector chats:Vector date:int seq_start:int seq:int = Updates; -updates#74ae4240 updates:Vector users:Vector chats:Vector date:int seq:int = Updates; - -photos.photos#8dca6aa5 photos:Vector users:Vector = photos.Photos; -photos.photosSlice#15051f54 count:int photos:Vector users:Vector = photos.Photos; - -photos.photo#20212ca8 photo:Photo users:Vector = photos.Photo; - -upload.file#96a18d5 type:storage.FileType mtime:int bytes:bytes = upload.File; - -dcOption#2ec2a43c id:int hostname:string ip_address:string port:int = DcOption; - -config#2e54dd74 date:int test_mode:Bool this_dc:int dc_options:Vector chat_size_max:int broadcast_size_max:int = Config; - -nearestDc#8e1a1775 country:string this_dc:int nearest_dc:int = NearestDc; - -help.appUpdate#8987f311 id:int critical:Bool url:string text:string = help.AppUpdate; -help.noAppUpdate#c45a6536 = help.AppUpdate; - -help.inviteText#18cb9f78 message:string = help.InviteText; - -messages.statedMessagesLinks#3e74f5c6 messages:Vector chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessageLink#a9af2881 message:Message chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector = messages.SentMessage; - -inputGeoChat#74d456fa chat_id:int access_hash:long = InputGeoChat; - -inputNotifyGeoChatPeer#4d8ddec8 peer:InputGeoChat = InputNotifyPeer; - -geoChat#75eaea5a id:int access_hash:long title:string address:string venue:string geo:GeoPoint photo:ChatPhoto participants_count:int date:int checked_in:Bool version:int = Chat; - -geoChatMessageEmpty#60311a9b chat_id:int id:int = GeoChatMessage; -geoChatMessage#4505f8e1 chat_id:int id:int from_id:int date:int message:string media:MessageMedia = GeoChatMessage; -geoChatMessageService#d34fa24e chat_id:int id:int from_id:int date:int action:MessageAction = GeoChatMessage; - -geochats.statedMessage#17b1578b message:GeoChatMessage chats:Vector users:Vector seq:int = geochats.StatedMessage; - -geochats.located#48feb267 results:Vector messages:Vector chats:Vector users:Vector = geochats.Located; - -geochats.messages#d1526db1 messages:Vector chats:Vector users:Vector = geochats.Messages; -geochats.messagesSlice#bc5863e8 count:int messages:Vector chats:Vector users:Vector = geochats.Messages; - -messageActionGeoChatCreate#6f038ebc title:string address:string = MessageAction; -messageActionGeoChatCheckin#c7d53de = MessageAction; - -updateNewGeoChatMessage#5a68e3f7 message:GeoChatMessage = Update; - -wallPaperSolid#63117f24 id:int title:string bg_color:int color:int = WallPaper; - -updateNewEncryptedMessage#12bcbd9a message:EncryptedMessage qts:int = Update; -updateEncryptedChatTyping#1710f156 chat_id:int = Update; -updateEncryption#b4a2e88d chat:EncryptedChat date:int = Update; -updateEncryptedMessagesRead#38fe25b7 chat_id:int max_date:int date:int = Update; - -encryptedChatEmpty#ab7ec0a0 id:int = EncryptedChat; -encryptedChatWaiting#3bf703dc id:int access_hash:long date:int admin_id:int participant_id:int = EncryptedChat; -encryptedChatRequested#c878527e id:int access_hash:long date:int admin_id:int participant_id:int g_a:bytes = EncryptedChat; -encryptedChat#fa56ce36 id:int access_hash:long date:int admin_id:int participant_id:int g_a_or_b:bytes key_fingerprint:long = EncryptedChat; -encryptedChatDiscarded#13d6dd27 id:int = EncryptedChat; - -inputEncryptedChat#f141b5e1 chat_id:int access_hash:long = InputEncryptedChat; - -encryptedFileEmpty#c21f497e = EncryptedFile; -encryptedFile#4a70994c id:long access_hash:long size:int dc_id:int key_fingerprint:int = EncryptedFile; - -inputEncryptedFileEmpty#1837c364 = InputEncryptedFile; -inputEncryptedFileUploaded#64bd0306 id:long parts:int md5_checksum:string key_fingerprint:int = InputEncryptedFile; -inputEncryptedFile#5a17b5e5 id:long access_hash:long = InputEncryptedFile; - -inputEncryptedFileLocation#f5235d55 id:long access_hash:long = InputFileLocation; - -encryptedMessage#ed18c118 random_id:long chat_id:int date:int bytes:bytes file:EncryptedFile = EncryptedMessage; -encryptedMessageService#23734b06 random_id:long chat_id:int date:int bytes:bytes = EncryptedMessage; - -decryptedMessageLayer#99a438cf layer:int message:DecryptedMessage = DecryptedMessageLayer; - -decryptedMessage#1f814f1f random_id:long random_bytes:bytes message:string media:DecryptedMessageMedia = DecryptedMessage; -decryptedMessageService#aa48327d random_id:long random_bytes:bytes action:DecryptedMessageAction = DecryptedMessage; - -decryptedMessageMediaEmpty#89f5c4a = DecryptedMessageMedia; -decryptedMessageMediaPhoto#32798a8c thumb:bytes thumb_w:int thumb_h:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaVideo#4cee6ef3 thumb:bytes thumb_w:int thumb_h:int duration:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaGeoPoint#35480a59 lat:double long:double = DecryptedMessageMedia; -decryptedMessageMediaContact#588a0a97 phone_number:string first_name:string last_name:string user_id:int = DecryptedMessageMedia; - -decryptedMessageActionSetMessageTTL#a1733aec ttl_seconds:int = DecryptedMessageAction; - -messages.dhConfigNotModified#c0e24635 random:bytes = messages.DhConfig; -messages.dhConfig#2c221edd g:int p:bytes version:int random:bytes = messages.DhConfig; - -messages.sentEncryptedMessage#560f8935 date:int = messages.SentEncryptedMessage; -messages.sentEncryptedFile#9493ff32 date:int file:EncryptedFile = messages.SentEncryptedMessage; - -inputFileBig#fa4f0bb5 id:long parts:int name:string = InputFile; - -inputEncryptedFileBigUploaded#2dc173c8 id:long parts:int key_fingerprint:int = InputEncryptedFile; - -updateChatParticipantAdd#3a0eeb22 chat_id:int user_id:int inviter_id:int version:int = Update; -updateChatParticipantDelete#6e5f8c22 chat_id:int user_id:int version:int = Update; -updateDcOptions#8e5e9873 dc_options:Vector = Update; - -inputMediaUploadedAudio#61a6d436 file:InputFile duration:int = InputMedia; -inputMediaAudio#89938781 id:InputAudio = InputMedia; -inputMediaUploadedDocument#34e794bd file:InputFile file_name:string mime_type:string = InputMedia; -inputMediaUploadedThumbDocument#3e46de5d file:InputFile thumb:InputFile file_name:string mime_type:string = InputMedia; -inputMediaDocument#d184e841 id:InputDocument = InputMedia; - -messageMediaDocument#2fda2204 document:Document = MessageMedia; -messageMediaAudio#c6b68300 audio:Audio = MessageMedia; - -inputAudioEmpty#d95adc84 = InputAudio; -inputAudio#77d440ff id:long access_hash:long = InputAudio; - -inputDocumentEmpty#72f0eaae = InputDocument; -inputDocument#18798952 id:long access_hash:long = InputDocument; - -inputAudioFileLocation#74dc404d id:long access_hash:long = InputFileLocation; -inputDocumentFileLocation#4e45abe9 id:long access_hash:long = InputFileLocation; - -decryptedMessageMediaDocument#b095434b thumb:bytes thumb_w:int thumb_h:int file_name:string mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaAudio#6080758f duration:int size:int key:bytes iv:bytes = DecryptedMessageMedia; - -audioEmpty#586988d8 id:long = Audio; -audio#427425e7 id:long access_hash:long user_id:int date:int duration:int size:int dc_id:int = Audio; - -documentEmpty#36f8c871 id:long = Document; -document#9efc6326 id:long access_hash:long user_id:int date:int file_name:string mime_type:string size:int thumb:PhotoSize dc_id:int = Document; - -help.support#17c6b5f6 phone_number:string user:User = help.Support; - ----functions--- - -invokeAfterMsg#cb9f372d {X:Type} msg_id:long query:!X = X; - -invokeAfterMsgs#3dc4b4f0 {X:Type} msg_ids:Vector query:!X = X; - -auth.checkPhone#6fe51dfb phone_number:string = auth.CheckedPhone; -auth.sendCode#768d5f4d phone_number:string sms_type:int api_id:int api_hash:string lang_code:string = auth.SentCode; -auth.sendCall#3c51564 phone_number:string phone_code_hash:string = Bool; -auth.signUp#1b067634 phone_number:string phone_code_hash:string phone_code:string first_name:string last_name:string = auth.Authorization; -auth.signIn#bcd51581 phone_number:string phone_code_hash:string phone_code:string = auth.Authorization; -auth.logOut#5717da40 = Bool; -auth.resetAuthorizations#9fab0d1a = Bool; -auth.sendInvites#771c1d97 phone_numbers:Vector message:string = Bool; -auth.exportAuthorization#e5bfffcd dc_id:int = auth.ExportedAuthorization; -auth.importAuthorization#e3ef9613 id:int bytes:bytes = auth.Authorization; - -account.registerDevice#446c712c token_type:int token:string device_model:string system_version:string app_version:string app_sandbox:Bool lang_code:string = Bool; -account.unregisterDevice#65c55b40 token_type:int token:string = Bool; -account.updateNotifySettings#84be5b93 peer:InputNotifyPeer settings:InputPeerNotifySettings = Bool; -account.getNotifySettings#12b3ad31 peer:InputNotifyPeer = PeerNotifySettings; -account.resetNotifySettings#db7e1747 = Bool; -account.updateProfile#f0888d68 first_name:string last_name:string = User; -account.updateStatus#6628562c offline:Bool = Bool; -account.getWallPapers#c04cfac2 = Vector; - -users.getUsers#d91a548 id:Vector = Vector; -users.getFullUser#ca30a5b1 id:InputUser = UserFull; - -contacts.getStatuses#c4a353ee = Vector; -contacts.getContacts#22c6aa08 hash:string = contacts.Contacts; -contacts.importContacts#da30b32d contacts:Vector replace:Bool = contacts.ImportedContacts; -contacts.search#11f812d8 q:string limit:int = contacts.Found; -contacts.getSuggested#cd773428 limit:int = contacts.Suggested; -contacts.deleteContact#8e953744 id:InputUser = contacts.Link; -contacts.deleteContacts#59ab389e id:Vector = Bool; -contacts.block#332b49fc id:InputUser = Bool; -contacts.unblock#e54100bd id:InputUser = Bool; -contacts.getBlocked#f57c350f offset:int limit:int = contacts.Blocked; - -messages.getMessages#4222fa74 id:Vector = messages.Messages; -messages.getDialogs#eccf1df6 offset:int max_id:int limit:int = messages.Dialogs; -messages.getHistory#92a1df2f peer:InputPeer offset:int max_id:int limit:int = messages.Messages; -messages.search#7e9f2ab peer:InputPeer q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = messages.Messages; -messages.readHistory#b04f2510 peer:InputPeer max_id:int offset:int = messages.AffectedHistory; -messages.deleteHistory#f4f8fb61 peer:InputPeer offset:int = messages.AffectedHistory; -messages.deleteMessages#14f2dd0a id:Vector = Vector; -messages.restoreMessages#395f9d7e id:Vector = Vector; -messages.receivedMessages#28abcb68 max_id:int = Vector; -messages.setTyping#719839e9 peer:InputPeer typing:Bool = Bool; -messages.sendMessage#4cde0aab peer:InputPeer message:string random_id:long = messages.SentMessage; -messages.sendMedia#a3c85d76 peer:InputPeer media:InputMedia random_id:long = messages.StatedMessage; -messages.forwardMessages#514cd10f peer:InputPeer id:Vector = messages.StatedMessages; -messages.getChats#3c6aa187 id:Vector = messages.Chats; -messages.getFullChat#3b831c66 chat_id:int = messages.ChatFull; -messages.editChatTitle#b4bc68b5 chat_id:int title:string = messages.StatedMessage; -messages.editChatPhoto#d881821d chat_id:int photo:InputChatPhoto = messages.StatedMessage; -messages.addChatUser#2ee9ee9e chat_id:int user_id:InputUser fwd_limit:int = messages.StatedMessage; -messages.deleteChatUser#c3c5cd23 chat_id:int user_id:InputUser = messages.StatedMessage; -messages.createChat#419d9aee users:Vector title:string = messages.StatedMessage; - -updates.getState#edd4882a = updates.State; -updates.getDifference#a041495 pts:int date:int qts:int = updates.Difference; - -photos.updateProfilePhoto#eef579a0 id:InputPhoto crop:InputPhotoCrop = UserProfilePhoto; -photos.uploadProfilePhoto#d50f9c88 file:InputFile caption:string geo_point:InputGeoPoint crop:InputPhotoCrop = photos.Photo; - -upload.saveFilePart#b304a621 file_id:long file_part:int bytes:bytes = Bool; -upload.getFile#e3a6cfb5 location:InputFileLocation offset:int limit:int = upload.File; - -help.getConfig#c4f9186b = Config; -help.getNearestDc#1fb33026 = NearestDc; -help.getAppUpdate#c812ac7e device_model:string system_version:string app_version:string lang_code:string = help.AppUpdate; -help.saveAppLog#6f02f748 events:Vector = Bool; -help.getInviteText#a4a95186 lang_code:string = help.InviteText; - -photos.getUserPhotos#b7ee553c user_id:InputUser offset:int max_id:int limit:int = photos.Photos; - -messages.forwardMessage#3f3f4f2 peer:InputPeer id:int random_id:long = messages.StatedMessage; -messages.sendBroadcast#41bb0972 contacts:Vector message:string media:InputMedia = messages.StatedMessages; - -geochats.getLocated#7f192d8f geo_point:InputGeoPoint radius:int limit:int = geochats.Located; -geochats.getRecents#e1427e6f offset:int limit:int = geochats.Messages; -geochats.checkin#55b3e8fb peer:InputGeoChat = geochats.StatedMessage; -geochats.getFullChat#6722dd6f peer:InputGeoChat = messages.ChatFull; -geochats.editChatTitle#4c8e2273 peer:InputGeoChat title:string address:string = geochats.StatedMessage; -geochats.editChatPhoto#35d81a95 peer:InputGeoChat photo:InputChatPhoto = geochats.StatedMessage; -geochats.search#cfcdc44d peer:InputGeoChat q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = geochats.Messages; -geochats.getHistory#b53f7a68 peer:InputGeoChat offset:int max_id:int limit:int = geochats.Messages; -geochats.setTyping#8b8a729 peer:InputGeoChat typing:Bool = Bool; -geochats.sendMessage#61b0044 peer:InputGeoChat message:string random_id:long = geochats.StatedMessage; -geochats.sendMedia#b8f0deff peer:InputGeoChat media:InputMedia random_id:long = geochats.StatedMessage; -geochats.createGeoChat#e092e16 title:string geo_point:InputGeoPoint address:string venue:string = geochats.StatedMessage; - -messages.getDhConfig#26cf8950 version:int random_length:int = messages.DhConfig; -messages.requestEncryption#f64daf43 user_id:InputUser random_id:int g_a:bytes = EncryptedChat; -messages.acceptEncryption#3dbc0415 peer:InputEncryptedChat g_b:bytes key_fingerprint:long = EncryptedChat; -messages.discardEncryption#edd923c5 chat_id:int = Bool; -messages.setEncryptedTyping#791451ed peer:InputEncryptedChat typing:Bool = Bool; -messages.readEncryptedHistory#7f4b690a peer:InputEncryptedChat max_date:int = Bool; -messages.sendEncrypted#a9776773 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.sendEncryptedFile#9a901b66 peer:InputEncryptedChat random_id:long data:bytes file:InputEncryptedFile = messages.SentEncryptedMessage; -messages.sendEncryptedService#32d439a4 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.receivedQueue#55a5bb66 max_qts:int = Vector; - -upload.saveBigFilePart#de7b673d file_id:long file_part:int file_total_parts:int bytes:bytes = Bool; - -initConnection#69796de9 {X:Type} api_id:int device_model:string system_version:string app_version:string lang_code:string query:!X = X; - -help.getSupport#9cdf08cd = help.Support; - -invokeWithLayer12#dda60d3c {X:Type} query:!X = X; diff --git a/scheme15.tl b/scheme15.tl deleted file mode 100644 index 4e18fad..0000000 --- a/scheme15.tl +++ /dev/null @@ -1,522 +0,0 @@ -int ?= Int; -long ?= Long; -double ?= Double; -string ?= String; - -bytes string = Bytes; - -boolFalse#bc799737 = Bool; -boolTrue#997275b5 = Bool; - -vector#1cb5c415 {t:Type} # [ t ] = Vector t; - -error#c4b9f9bb code:int text:string = Error; - -null#56730bcc = Null; - -inputPeerEmpty#7f3b18ea = InputPeer; -inputPeerSelf#7da07ec9 = InputPeer; -inputPeerContact#1023dbe8 user_id:int = InputPeer; -inputPeerForeign#9b447325 user_id:int access_hash:long = InputPeer; -inputPeerChat#179be863 chat_id:int = InputPeer; - -inputUserEmpty#b98886cf = InputUser; -inputUserSelf#f7c1b13f = InputUser; -inputUserContact#86e94f65 user_id:int = InputUser; -inputUserForeign#655e74ff user_id:int access_hash:long = InputUser; - -inputPhoneContact#f392b7f4 client_id:long phone:string first_name:string last_name:string = InputContact; - -inputFile#f52ff27f id:long parts:int name:string md5_checksum:string = InputFile; - -inputMediaEmpty#9664f57f = InputMedia; -inputMediaUploadedPhoto#2dc53a7d file:InputFile = InputMedia; -inputMediaPhoto#8f2ab2ec id:InputPhoto = InputMedia; -inputMediaGeoPoint#f9c44144 geo_point:InputGeoPoint = InputMedia; -inputMediaContact#a6e45987 phone_number:string first_name:string last_name:string = InputMedia; -inputMediaUploadedVideo#133ad6f6 file:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaUploadedThumbVideo#9912dabf file:InputFile thumb:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaVideo#7f023ae6 id:InputVideo = InputMedia; - -inputChatPhotoEmpty#1ca48f57 = InputChatPhoto; -inputChatUploadedPhoto#94254732 file:InputFile crop:InputPhotoCrop = InputChatPhoto; -inputChatPhoto#b2e1bf08 id:InputPhoto crop:InputPhotoCrop = InputChatPhoto; - -inputGeoPointEmpty#e4c123d6 = InputGeoPoint; -inputGeoPoint#f3b7acc9 lat:double long:double = InputGeoPoint; - -inputPhotoEmpty#1cd7bf0d = InputPhoto; -inputPhoto#fb95c6c4 id:long access_hash:long = InputPhoto; - -inputVideoEmpty#5508ec75 = InputVideo; -inputVideo#ee579652 id:long access_hash:long = InputVideo; - -inputFileLocation#14637196 volume_id:long local_id:int secret:long = InputFileLocation; -inputVideoFileLocation#3d0364ec id:long access_hash:long = InputFileLocation; - -inputPhotoCropAuto#ade6b004 = InputPhotoCrop; -inputPhotoCrop#d9915325 crop_left:double crop_top:double crop_width:double = InputPhotoCrop; - -inputAppEvent#770656a8 time:double type:string peer:long data:string = InputAppEvent; - -peerUser#9db1bc6d user_id:int = Peer; -peerChat#bad0e5bb chat_id:int = Peer; - -storage.fileUnknown#aa963b05 = storage.FileType; -storage.fileJpeg#007efe0e = storage.FileType; -storage.fileGif#cae1aadf = storage.FileType; -storage.filePng#0a4f63c0 = storage.FileType; -storage.filePdf#ae1e508d = storage.FileType; -storage.fileMp3#528a0677 = storage.FileType; -storage.fileMov#4b09ebbc = storage.FileType; -storage.filePartial#40bc6f52 = storage.FileType; -storage.fileMp4#b3cea0e4 = storage.FileType; -storage.fileWebp#1081464c = storage.FileType; - -fileLocationUnavailable#7c596b46 volume_id:long local_id:int secret:long = FileLocation; -fileLocation#53d69076 dc_id:int volume_id:long local_id:int secret:long = FileLocation; - -userEmpty#200250ba id:int = User; -userSelf#720535ec id:int first_name:string last_name:string phone:string photo:UserProfilePhoto status:UserStatus inactive:Bool = User; -userContact#f2fb8319 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userRequest#22e8ceb0 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userForeign#5214c89d id:int first_name:string last_name:string access_hash:long photo:UserProfilePhoto status:UserStatus = User; -userDeleted#b29ad7cc id:int first_name:string last_name:string = User; - -userProfilePhotoEmpty#4f11bae1 = UserProfilePhoto; -userProfilePhoto#d559d8c8 photo_id:long photo_small:FileLocation photo_big:FileLocation = UserProfilePhoto; - -userStatusEmpty#09d05049 = UserStatus; -userStatusOnline#edb93949 expires:int = UserStatus; -userStatusOffline#008c703f was_online:int = UserStatus; - -chatEmpty#9ba2d800 id:int = Chat; -chat#6e9c9bc7 id:int title:string photo:ChatPhoto participants_count:int date:int left:Bool version:int = Chat; -chatForbidden#fb0ccc41 id:int title:string date:int = Chat; - -chatFull#630e61be id:int participants:ChatParticipants chat_photo:Photo notify_settings:PeerNotifySettings = ChatFull; - -chatParticipant#c8d7493e user_id:int inviter_id:int date:int = ChatParticipant; - -chatParticipantsForbidden#0fd2bb8a chat_id:int = ChatParticipants; -chatParticipants#7841b415 chat_id:int admin_id:int participants:Vector version:int = ChatParticipants; - -chatPhotoEmpty#37c1011c = ChatPhoto; -chatPhoto#6153276a photo_small:FileLocation photo_big:FileLocation = ChatPhoto; - -messageEmpty#83e5de54 id:int = Message; -message#22eb6aba id:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageForwarded#05f46804 id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageService#9f8d60bb id:int from_id:int to_id:Peer out:Bool unread:Bool date:int action:MessageAction = Message; - -messageMediaEmpty#3ded6320 = MessageMedia; -messageMediaPhoto#c8c45a2a photo:Photo = MessageMedia; -messageMediaVideo#a2d24290 video:Video = MessageMedia; -messageMediaGeo#56e0d474 geo:GeoPoint = MessageMedia; -messageMediaContact#5e7d2f39 phone_number:string first_name:string last_name:string user_id:int = MessageMedia; -messageMediaUnsupported#29632a36 bytes:bytes = MessageMedia; - -messageActionEmpty#b6aef7b0 = MessageAction; -messageActionChatCreate#a6638b9a title:string users:Vector = MessageAction; -messageActionChatEditTitle#b5a1ce5a title:string = MessageAction; -messageActionChatEditPhoto#7fcb13a8 photo:Photo = MessageAction; -messageActionChatDeletePhoto#95e3fbef = MessageAction; -messageActionChatAddUser#5e3cfc4b user_id:int = MessageAction; -messageActionChatDeleteUser#b2ae9b0c user_id:int = MessageAction; - -dialog#ab3a99ac peer:Peer top_message:int unread_count:int notify_settings:PeerNotifySettings = Dialog; - -photoEmpty#2331b22d id:long = Photo; -photo#22b56751 id:long access_hash:long user_id:int date:int caption:string geo:GeoPoint sizes:Vector = Photo; - -photoSizeEmpty#0e17e23c type:string = PhotoSize; -photoSize#77bfb61b type:string location:FileLocation w:int h:int size:int = PhotoSize; -photoCachedSize#e9a734fa type:string location:FileLocation w:int h:int bytes:bytes = PhotoSize; - -videoEmpty#c10658a8 id:long = Video; -video#388fa391 id:long access_hash:long user_id:int date:int caption:string duration:int mime_type:string size:int thumb:PhotoSize dc_id:int w:int h:int = Video; - -geoPointEmpty#1117dd5f = GeoPoint; -geoPoint#2049d70c long:double lat:double = GeoPoint; - -auth.checkedPhone#e300cc3b phone_registered:Bool phone_invited:Bool = auth.CheckedPhone; - -auth.sentCode#efed51d9 phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -auth.authorization#f6b673a4 expires:int user:User = auth.Authorization; - -auth.exportedAuthorization#df969c2d id:int bytes:bytes = auth.ExportedAuthorization; - -inputNotifyPeer#b8bc5b0c peer:InputPeer = InputNotifyPeer; -inputNotifyUsers#193b4417 = InputNotifyPeer; -inputNotifyChats#4a95e84e = InputNotifyPeer; -inputNotifyAll#a429b886 = InputNotifyPeer; - -inputPeerNotifyEventsEmpty#f03064d8 = InputPeerNotifyEvents; -inputPeerNotifyEventsAll#e86a2c74 = InputPeerNotifyEvents; - -inputPeerNotifySettings#46a2ce98 mute_until:int sound:string show_previews:Bool events_mask:int = InputPeerNotifySettings; - -peerNotifyEventsEmpty#add53cb3 = PeerNotifyEvents; -peerNotifyEventsAll#6d1ded88 = PeerNotifyEvents; - -peerNotifySettingsEmpty#70a68512 = PeerNotifySettings; -peerNotifySettings#8d5e11ee mute_until:int sound:string show_previews:Bool events_mask:int = PeerNotifySettings; - -wallPaper#ccb03657 id:int title:string sizes:Vector color:int = WallPaper; - -userFull#771095da user:User link:contacts.Link profile_photo:Photo notify_settings:PeerNotifySettings blocked:Bool real_first_name:string real_last_name:string = UserFull; - -contact#f911c994 user_id:int mutual:Bool = Contact; - -importedContact#d0028438 user_id:int client_id:long = ImportedContact; - -contactBlocked#561bc879 user_id:int date:int = ContactBlocked; - -contactFound#ea879f95 user_id:int = ContactFound; - -contactSuggested#3de191a1 user_id:int mutual_contacts:int = ContactSuggested; - -contactStatus#aa77b873 user_id:int expires:int = ContactStatus; - -chatLocated#3631cf4c chat_id:int distance:int = ChatLocated; - -contacts.foreignLinkUnknown#133421f8 = contacts.ForeignLink; -contacts.foreignLinkRequested#a7801f47 has_phone:Bool = contacts.ForeignLink; -contacts.foreignLinkMutual#1bea8ce1 = contacts.ForeignLink; - -contacts.myLinkEmpty#d22a1c60 = contacts.MyLink; -contacts.myLinkRequested#6c69efee contact:Bool = contacts.MyLink; -contacts.myLinkContact#c240ebd9 = contacts.MyLink; - -contacts.link#eccea3f5 my_link:contacts.MyLink foreign_link:contacts.ForeignLink user:User = contacts.Link; - -contacts.contacts#6f8b8cb2 contacts:Vector users:Vector = contacts.Contacts; -contacts.contactsNotModified#b74ba9d2 = contacts.Contacts; - -contacts.importedContacts#ad524315 imported:Vector retry_contacts:Vector users:Vector = contacts.ImportedContacts; - -contacts.blocked#1c138d15 blocked:Vector users:Vector = contacts.Blocked; -contacts.blockedSlice#900802a1 count:int blocked:Vector users:Vector = contacts.Blocked; - -contacts.found#0566000e results:Vector users:Vector = contacts.Found; - -contacts.suggested#5649dcc5 results:Vector users:Vector = contacts.Suggested; - -messages.dialogs#15ba6c40 dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; -messages.dialogsSlice#71e094f3 count:int dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; - -messages.messages#8c718e87 messages:Vector chats:Vector users:Vector = messages.Messages; -messages.messagesSlice#0b446ae3 count:int messages:Vector chats:Vector users:Vector = messages.Messages; - -messages.messageEmpty#3f4e0648 = messages.Message; -messages.message#ff90c417 message:Message chats:Vector users:Vector = messages.Message; - -messages.statedMessages#969478bb messages:Vector chats:Vector users:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessage#d07ae726 message:Message chats:Vector users:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessage#d1f4d35c id:int date:int pts:int seq:int = messages.SentMessage; - -messages.chat#40e9002a chat:Chat users:Vector = messages.Chat; - -messages.chats#8150cbd8 chats:Vector users:Vector = messages.Chats; - -messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector users:Vector = messages.ChatFull; - -messages.affectedHistory#b7de36f2 pts:int seq:int offset:int = messages.AffectedHistory; - -inputMessagesFilterEmpty#57e2f66c = MessagesFilter; -inputMessagesFilterPhotos#9609a51c = MessagesFilter; -inputMessagesFilterVideo#9fc00e65 = MessagesFilter; -inputMessagesFilterPhotoVideo#56e9f0e4 = MessagesFilter; -inputMessagesFilterDocument#9eddf188 = MessagesFilter; -inputMessagesFilterAudio#cfc87522 = MessagesFilter; - -updateNewMessage#013abdb3 message:Message pts:int = Update; -updateMessageID#4e90bfd6 id:int random_id:long = Update; -updateReadMessages#c6649e31 messages:Vector pts:int = Update; -updateDeleteMessages#a92bfe26 messages:Vector pts:int = Update; -updateRestoreMessages#d15de04d messages:Vector pts:int = Update; -updateUserTyping#6baa8508 user_id:int = Update; -updateChatUserTyping#3c46cfe6 chat_id:int user_id:int = Update; -updateChatParticipants#07761198 participants:ChatParticipants = Update; -updateUserStatus#1bfbd823 user_id:int status:UserStatus = Update; -updateUserName#da22d9ad user_id:int first_name:string last_name:string = Update; -updateUserPhoto#95313b0c user_id:int date:int photo:UserProfilePhoto previous:Bool = Update; -updateContactRegistered#2575bbb9 user_id:int date:int = Update; -updateContactLink#51a48a9a user_id:int my_link:contacts.MyLink foreign_link:contacts.ForeignLink = Update; -updateActivation#6f690963 user_id:int = Update; -updateNewAuthorization#8f06529a auth_key_id:long date:int device:string location:string = Update; - -updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State; - -updates.differenceEmpty#5d75a138 date:int seq:int = updates.Difference; -updates.difference#00f49ca0 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector state:updates.State = updates.Difference; -updates.differenceSlice#a8fb1981 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector intermediate_state:updates.State = updates.Difference; - -updatesTooLong#e317af7e = Updates; -updateShortMessage#d3f45784 id:int from_id:int message:string pts:int date:int seq:int = Updates; -updateShortChatMessage#2b2fbd4e id:int from_id:int chat_id:int message:string pts:int date:int seq:int = Updates; -updateShort#78d4dec1 update:Update date:int = Updates; -updatesCombined#725b04c3 updates:Vector users:Vector chats:Vector date:int seq_start:int seq:int = Updates; -updates#74ae4240 updates:Vector users:Vector chats:Vector date:int seq:int = Updates; - -photos.photos#8dca6aa5 photos:Vector users:Vector = photos.Photos; -photos.photosSlice#15051f54 count:int photos:Vector users:Vector = photos.Photos; - -photos.photo#20212ca8 photo:Photo users:Vector = photos.Photo; - -upload.file#096a18d5 type:storage.FileType mtime:int bytes:bytes = upload.File; - -dcOption#2ec2a43c id:int hostname:string ip_address:string port:int = DcOption; - -config#2e54dd74 date:int test_mode:Bool this_dc:int dc_options:Vector chat_size_max:int broadcast_size_max:int = Config; - -nearestDc#8e1a1775 country:string this_dc:int nearest_dc:int = NearestDc; - -help.appUpdate#8987f311 id:int critical:Bool url:string text:string = help.AppUpdate; -help.noAppUpdate#c45a6536 = help.AppUpdate; - -help.inviteText#18cb9f78 message:string = help.InviteText; - -messages.statedMessagesLinks#3e74f5c6 messages:Vector chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessageLink#a9af2881 message:Message chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector = messages.SentMessage; - -inputGeoChat#74d456fa chat_id:int access_hash:long = InputGeoChat; - -inputNotifyGeoChatPeer#4d8ddec8 peer:InputGeoChat = InputNotifyPeer; - -geoChat#75eaea5a id:int access_hash:long title:string address:string venue:string geo:GeoPoint photo:ChatPhoto participants_count:int date:int checked_in:Bool version:int = Chat; - -geoChatMessageEmpty#60311a9b chat_id:int id:int = GeoChatMessage; -geoChatMessage#4505f8e1 chat_id:int id:int from_id:int date:int message:string media:MessageMedia = GeoChatMessage; -geoChatMessageService#d34fa24e chat_id:int id:int from_id:int date:int action:MessageAction = GeoChatMessage; - -geochats.statedMessage#17b1578b message:GeoChatMessage chats:Vector users:Vector seq:int = geochats.StatedMessage; - -geochats.located#48feb267 results:Vector messages:Vector chats:Vector users:Vector = geochats.Located; - -geochats.messages#d1526db1 messages:Vector chats:Vector users:Vector = geochats.Messages; -geochats.messagesSlice#bc5863e8 count:int messages:Vector chats:Vector users:Vector = geochats.Messages; - -messageActionGeoChatCreate#6f038ebc title:string address:string = MessageAction; -messageActionGeoChatCheckin#0c7d53de = MessageAction; - -updateNewGeoChatMessage#5a68e3f7 message:GeoChatMessage = Update; - -wallPaperSolid#63117f24 id:int title:string bg_color:int color:int = WallPaper; - -updateNewEncryptedMessage#12bcbd9a message:EncryptedMessage qts:int = Update; -updateEncryptedChatTyping#1710f156 chat_id:int = Update; -updateEncryption#b4a2e88d chat:EncryptedChat date:int = Update; -updateEncryptedMessagesRead#38fe25b7 chat_id:int max_date:int date:int = Update; - -encryptedChatEmpty#ab7ec0a0 id:int = EncryptedChat; -encryptedChatWaiting#3bf703dc id:int access_hash:long date:int admin_id:int participant_id:int = EncryptedChat; -encryptedChatRequested#c878527e id:int access_hash:long date:int admin_id:int participant_id:int g_a:bytes = EncryptedChat; -encryptedChat#fa56ce36 id:int access_hash:long date:int admin_id:int participant_id:int g_a_or_b:bytes key_fingerprint:long = EncryptedChat; -encryptedChatDiscarded#13d6dd27 id:int = EncryptedChat; - -inputEncryptedChat#f141b5e1 chat_id:int access_hash:long = InputEncryptedChat; - -encryptedFileEmpty#c21f497e = EncryptedFile; -encryptedFile#4a70994c id:long access_hash:long size:int dc_id:int key_fingerprint:int = EncryptedFile; - -inputEncryptedFileEmpty#1837c364 = InputEncryptedFile; -inputEncryptedFileUploaded#64bd0306 id:long parts:int md5_checksum:string key_fingerprint:int = InputEncryptedFile; -inputEncryptedFile#5a17b5e5 id:long access_hash:long = InputEncryptedFile; - -inputEncryptedFileLocation#f5235d55 id:long access_hash:long = InputFileLocation; - -encryptedMessage#ed18c118 random_id:long chat_id:int date:int bytes:bytes file:EncryptedFile = EncryptedMessage; -encryptedMessageService#23734b06 random_id:long chat_id:int date:int bytes:bytes = EncryptedMessage; - -decryptedMessageLayer#99a438cf layer:int message:DecryptedMessage = DecryptedMessageLayer; - -decryptedMessage#1f814f1f random_id:long random_bytes:bytes message:string media:DecryptedMessageMedia = DecryptedMessage; -decryptedMessageService#aa48327d random_id:long random_bytes:bytes action:DecryptedMessageAction = DecryptedMessage; - -decryptedMessageMediaEmpty#089f5c4a = DecryptedMessageMedia; -decryptedMessageMediaPhoto#32798a8c thumb:bytes thumb_w:int thumb_h:int w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaVideo#524a415d thumb:bytes thumb_w:int thumb_h:int duration:int mime_type:string w:int h:int size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaGeoPoint#35480a59 lat:double long:double = DecryptedMessageMedia; -decryptedMessageMediaContact#588a0a97 phone_number:string first_name:string last_name:string user_id:int = DecryptedMessageMedia; - -decryptedMessageActionSetMessageTTL#a1733aec ttl_seconds:int = DecryptedMessageAction; - -messages.dhConfigNotModified#c0e24635 random:bytes = messages.DhConfig; -messages.dhConfig#2c221edd g:int p:bytes version:int random:bytes = messages.DhConfig; - -messages.sentEncryptedMessage#560f8935 date:int = messages.SentEncryptedMessage; -messages.sentEncryptedFile#9493ff32 date:int file:EncryptedFile = messages.SentEncryptedMessage; - -inputFileBig#fa4f0bb5 id:long parts:int name:string = InputFile; - -inputEncryptedFileBigUploaded#2dc173c8 id:long parts:int key_fingerprint:int = InputEncryptedFile; - -updateChatParticipantAdd#3a0eeb22 chat_id:int user_id:int inviter_id:int version:int = Update; -updateChatParticipantDelete#6e5f8c22 chat_id:int user_id:int version:int = Update; -updateDcOptions#8e5e9873 dc_options:Vector = Update; - -inputMediaUploadedAudio#4e498cab file:InputFile duration:int mime_type:string = InputMedia; -inputMediaAudio#89938781 id:InputAudio = InputMedia; -inputMediaUploadedDocument#34e794bd file:InputFile file_name:string mime_type:string = InputMedia; -inputMediaUploadedThumbDocument#3e46de5d file:InputFile thumb:InputFile file_name:string mime_type:string = InputMedia; -inputMediaDocument#d184e841 id:InputDocument = InputMedia; - -messageMediaDocument#2fda2204 document:Document = MessageMedia; -messageMediaAudio#c6b68300 audio:Audio = MessageMedia; - -inputAudioEmpty#d95adc84 = InputAudio; -inputAudio#77d440ff id:long access_hash:long = InputAudio; - -inputDocumentEmpty#72f0eaae = InputDocument; -inputDocument#18798952 id:long access_hash:long = InputDocument; - -inputAudioFileLocation#74dc404d id:long access_hash:long = InputFileLocation; -inputDocumentFileLocation#4e45abe9 id:long access_hash:long = InputFileLocation; - -decryptedMessageMediaDocument#b095434b thumb:bytes thumb_w:int thumb_h:int file_name:string mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; -decryptedMessageMediaAudio#57e0a9cb duration:int mime_type:string size:int key:bytes iv:bytes = DecryptedMessageMedia; - -audioEmpty#586988d8 id:long = Audio; -audio#c7ac6496 id:long access_hash:long user_id:int date:int duration:int mime_type:string size:int dc_id:int = Audio; - -documentEmpty#36f8c871 id:long = Document; -document#9efc6326 id:long access_hash:long user_id:int date:int file_name:string mime_type:string size:int thumb:PhotoSize dc_id:int = Document; - -help.support#17c6b5f6 phone_number:string user:User = help.Support; - -decryptedMessageActionReadMessages#0c4f40be random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionDeleteMessages#65614304 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionScreenshotMessages#8ac1f475 random_ids:Vector = DecryptedMessageAction; -decryptedMessageActionFlushHistory#6719e45c = DecryptedMessageAction; -decryptedMessageActionNotifyLayer#f3048883 layer:int = DecryptedMessageAction; - -notifyPeer#9fd40bd8 peer:Peer = NotifyPeer; -notifyUsers#b4c83b4c = NotifyPeer; -notifyChats#c007cec3 = NotifyPeer; -notifyAll#74d07c60 = NotifyPeer; - -updateUserBlocked#80ece81a user_id:int blocked:Bool = Update; -updateNotifySettings#bec268ef peer:NotifyPeer notify_settings:PeerNotifySettings = Update; - -za int = Z 0; -zb {n:#} int %(Vector int) = Z (n + 1); - ----functions--- - -invokeAfterMsg#cb9f372d {X:Type} msg_id:long query:!X = X; - -invokeAfterMsgs#3dc4b4f0 {X:Type} msg_ids:Vector query:!X = X; - -auth.checkPhone#6fe51dfb phone_number:string = auth.CheckedPhone; -auth.sendCode#768d5f4d phone_number:string sms_type:int api_id:int api_hash:string lang_code:string = auth.SentCode; -auth.sendCall#03c51564 phone_number:string phone_code_hash:string = Bool; -auth.signUp#1b067634 phone_number:string phone_code_hash:string phone_code:string first_name:string last_name:string = auth.Authorization; -auth.signIn#bcd51581 phone_number:string phone_code_hash:string phone_code:string = auth.Authorization; -auth.logOut#5717da40 = Bool; -auth.resetAuthorizations#9fab0d1a = Bool; -auth.sendInvites#771c1d97 phone_numbers:Vector message:string = Bool; -auth.exportAuthorization#e5bfffcd dc_id:int = auth.ExportedAuthorization; -auth.importAuthorization#e3ef9613 id:int bytes:bytes = auth.Authorization; - -account.registerDevice#446c712c token_type:int token:string device_model:string system_version:string app_version:string app_sandbox:Bool lang_code:string = Bool; -account.unregisterDevice#65c55b40 token_type:int token:string = Bool; -account.updateNotifySettings#84be5b93 peer:InputNotifyPeer settings:InputPeerNotifySettings = Bool; -account.getNotifySettings#12b3ad31 peer:InputNotifyPeer = PeerNotifySettings; -account.resetNotifySettings#db7e1747 = Bool; -account.updateProfile#f0888d68 first_name:string last_name:string = User; -account.updateStatus#6628562c offline:Bool = Bool; -account.getWallPapers#c04cfac2 = Vector; - -users.getUsers#0d91a548 id:Vector = Vector; -users.getFullUser#ca30a5b1 id:InputUser = UserFull; - -contacts.getStatuses#c4a353ee = Vector; -contacts.getContacts#22c6aa08 hash:string = contacts.Contacts; -contacts.importContacts#da30b32d contacts:Vector replace:Bool = contacts.ImportedContacts; -contacts.search#11f812d8 q:string limit:int = contacts.Found; -contacts.getSuggested#cd773428 limit:int = contacts.Suggested; -contacts.deleteContact#8e953744 id:InputUser = contacts.Link; -contacts.deleteContacts#59ab389e id:Vector = Bool; -contacts.block#332b49fc id:InputUser = Bool; -contacts.unblock#e54100bd id:InputUser = Bool; -contacts.getBlocked#f57c350f offset:int limit:int = contacts.Blocked; - -messages.getMessages#4222fa74 id:Vector = messages.Messages; -messages.getDialogs#eccf1df6 offset:int max_id:int limit:int = messages.Dialogs; -messages.getHistory#92a1df2f peer:InputPeer offset:int max_id:int limit:int = messages.Messages; -messages.search#07e9f2ab peer:InputPeer q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = messages.Messages; -messages.readHistory#b04f2510 peer:InputPeer max_id:int offset:int = messages.AffectedHistory; -messages.deleteHistory#f4f8fb61 peer:InputPeer offset:int = messages.AffectedHistory; -messages.deleteMessages#14f2dd0a id:Vector = Vector; -messages.restoreMessages#395f9d7e id:Vector = Vector; -messages.receivedMessages#28abcb68 max_id:int = Vector; -messages.setTyping#719839e9 peer:InputPeer typing:Bool = Bool; -messages.sendMessage#4cde0aab peer:InputPeer message:string random_id:long = messages.SentMessage; -messages.sendMedia#a3c85d76 peer:InputPeer media:InputMedia random_id:long = messages.StatedMessage; -messages.forwardMessages#514cd10f peer:InputPeer id:Vector = messages.StatedMessages; -messages.getChats#3c6aa187 id:Vector = messages.Chats; -messages.getFullChat#3b831c66 chat_id:int = messages.ChatFull; -messages.editChatTitle#b4bc68b5 chat_id:int title:string = messages.StatedMessage; -messages.editChatPhoto#d881821d chat_id:int photo:InputChatPhoto = messages.StatedMessage; -messages.addChatUser#2ee9ee9e chat_id:int user_id:InputUser fwd_limit:int = messages.StatedMessage; -messages.deleteChatUser#c3c5cd23 chat_id:int user_id:InputUser = messages.StatedMessage; -messages.createChat#419d9aee users:Vector title:string = messages.StatedMessage; - -updates.getState#edd4882a = updates.State; -updates.getDifference#0a041495 pts:int date:int qts:int = updates.Difference; - -photos.updateProfilePhoto#eef579a0 id:InputPhoto crop:InputPhotoCrop = UserProfilePhoto; -photos.uploadProfilePhoto#d50f9c88 file:InputFile caption:string geo_point:InputGeoPoint crop:InputPhotoCrop = photos.Photo; - -upload.saveFilePart#b304a621 file_id:long file_part:int bytes:bytes = Bool; -upload.getFile#e3a6cfb5 location:InputFileLocation offset:int limit:int = upload.File; - -help.getConfig#c4f9186b = Config; -help.getNearestDc#1fb33026 = NearestDc; -help.getAppUpdate#c812ac7e device_model:string system_version:string app_version:string lang_code:string = help.AppUpdate; -help.saveAppLog#6f02f748 events:Vector = Bool; -help.getInviteText#a4a95186 lang_code:string = help.InviteText; - -photos.getUserPhotos#b7ee553c user_id:InputUser offset:int max_id:int limit:int = photos.Photos; - -messages.forwardMessage#03f3f4f2 peer:InputPeer id:int random_id:long = messages.StatedMessage; -messages.sendBroadcast#41bb0972 contacts:Vector message:string media:InputMedia = messages.StatedMessages; - -geochats.getLocated#7f192d8f geo_point:InputGeoPoint radius:int limit:int = geochats.Located; -geochats.getRecents#e1427e6f offset:int limit:int = geochats.Messages; -geochats.checkin#55b3e8fb peer:InputGeoChat = geochats.StatedMessage; -geochats.getFullChat#6722dd6f peer:InputGeoChat = messages.ChatFull; -geochats.editChatTitle#4c8e2273 peer:InputGeoChat title:string address:string = geochats.StatedMessage; -geochats.editChatPhoto#35d81a95 peer:InputGeoChat photo:InputChatPhoto = geochats.StatedMessage; -geochats.search#cfcdc44d peer:InputGeoChat q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = geochats.Messages; -geochats.getHistory#b53f7a68 peer:InputGeoChat offset:int max_id:int limit:int = geochats.Messages; -geochats.setTyping#08b8a729 peer:InputGeoChat typing:Bool = Bool; -geochats.sendMessage#061b0044 peer:InputGeoChat message:string random_id:long = geochats.StatedMessage; -geochats.sendMedia#b8f0deff peer:InputGeoChat media:InputMedia random_id:long = geochats.StatedMessage; -geochats.createGeoChat#0e092e16 title:string geo_point:InputGeoPoint address:string venue:string = geochats.StatedMessage; - -messages.getDhConfig#26cf8950 version:int random_length:int = messages.DhConfig; -messages.requestEncryption#f64daf43 user_id:InputUser random_id:int g_a:bytes = EncryptedChat; -messages.acceptEncryption#3dbc0415 peer:InputEncryptedChat g_b:bytes key_fingerprint:long = EncryptedChat; -messages.discardEncryption#edd923c5 chat_id:int = Bool; -messages.setEncryptedTyping#791451ed peer:InputEncryptedChat typing:Bool = Bool; -messages.readEncryptedHistory#7f4b690a peer:InputEncryptedChat max_date:int = Bool; -messages.sendEncrypted#a9776773 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.sendEncryptedFile#9a901b66 peer:InputEncryptedChat random_id:long data:bytes file:InputEncryptedFile = messages.SentEncryptedMessage; -messages.sendEncryptedService#32d439a4 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.receivedQueue#55a5bb66 max_qts:int = Vector; - -upload.saveBigFilePart#de7b673d file_id:long file_part:int file_total_parts:int bytes:bytes = Bool; - -initConnection#69796de9 {X:Type} api_id:int device_model:string system_version:string app_version:string lang_code:string query:!X = X; - -help.getSupport#9cdf08cd = help.Support; - -invokeWithLayer15#b4418b64 {X:Type} query:!X = X; diff --git a/scheme16.tl b/scheme16.tl deleted file mode 100644 index b1e1f19..0000000 --- a/scheme16.tl +++ /dev/null @@ -1,504 +0,0 @@ -int ?= Int; -long ?= Long; -double ?= Double; -string ?= String; - -bytes string = Bytes; - -boolFalse#bc799737 = Bool; -boolTrue#997275b5 = Bool; - -vector#1cb5c415 {t:Type} # [ t ] = Vector t; - -error#c4b9f9bb code:int text:string = Error; - -null#56730bcc = Null; - -inputPeerEmpty#7f3b18ea = InputPeer; -inputPeerSelf#7da07ec9 = InputPeer; -inputPeerContact#1023dbe8 user_id:int = InputPeer; -inputPeerForeign#9b447325 user_id:int access_hash:long = InputPeer; -inputPeerChat#179be863 chat_id:int = InputPeer; - -inputUserEmpty#b98886cf = InputUser; -inputUserSelf#f7c1b13f = InputUser; -inputUserContact#86e94f65 user_id:int = InputUser; -inputUserForeign#655e74ff user_id:int access_hash:long = InputUser; - -inputPhoneContact#f392b7f4 client_id:long phone:string first_name:string last_name:string = InputContact; - -inputFile#f52ff27f id:long parts:int name:string md5_checksum:string = InputFile; - -inputMediaEmpty#9664f57f = InputMedia; -inputMediaUploadedPhoto#2dc53a7d file:InputFile = InputMedia; -inputMediaPhoto#8f2ab2ec id:InputPhoto = InputMedia; -inputMediaGeoPoint#f9c44144 geo_point:InputGeoPoint = InputMedia; -inputMediaContact#a6e45987 phone_number:string first_name:string last_name:string = InputMedia; -inputMediaUploadedVideo#133ad6f6 file:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaUploadedThumbVideo#9912dabf file:InputFile thumb:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaVideo#7f023ae6 id:InputVideo = InputMedia; - -inputChatPhotoEmpty#1ca48f57 = InputChatPhoto; -inputChatUploadedPhoto#94254732 file:InputFile crop:InputPhotoCrop = InputChatPhoto; -inputChatPhoto#b2e1bf08 id:InputPhoto crop:InputPhotoCrop = InputChatPhoto; - -inputGeoPointEmpty#e4c123d6 = InputGeoPoint; -inputGeoPoint#f3b7acc9 lat:double long:double = InputGeoPoint; - -inputPhotoEmpty#1cd7bf0d = InputPhoto; -inputPhoto#fb95c6c4 id:long access_hash:long = InputPhoto; - -inputVideoEmpty#5508ec75 = InputVideo; -inputVideo#ee579652 id:long access_hash:long = InputVideo; - -inputFileLocation#14637196 volume_id:long local_id:int secret:long = InputFileLocation; -inputVideoFileLocation#3d0364ec id:long access_hash:long = InputFileLocation; - -inputPhotoCropAuto#ade6b004 = InputPhotoCrop; -inputPhotoCrop#d9915325 crop_left:double crop_top:double crop_width:double = InputPhotoCrop; - -inputAppEvent#770656a8 time:double type:string peer:long data:string = InputAppEvent; - -peerUser#9db1bc6d user_id:int = Peer; -peerChat#bad0e5bb chat_id:int = Peer; - -storage.fileUnknown#aa963b05 = storage.FileType; -storage.fileJpeg#7efe0e = storage.FileType; -storage.fileGif#cae1aadf = storage.FileType; -storage.filePng#a4f63c0 = storage.FileType; -storage.filePdf#ae1e508d = storage.FileType; -storage.fileMp3#528a0677 = storage.FileType; -storage.fileMov#4b09ebbc = storage.FileType; -storage.filePartial#40bc6f52 = storage.FileType; -storage.fileMp4#b3cea0e4 = storage.FileType; -storage.fileWebp#1081464c = storage.FileType; - -fileLocationUnavailable#7c596b46 volume_id:long local_id:int secret:long = FileLocation; -fileLocation#53d69076 dc_id:int volume_id:long local_id:int secret:long = FileLocation; - -userEmpty#200250ba id:int = User; -userSelf#720535ec id:int first_name:string last_name:string phone:string photo:UserProfilePhoto status:UserStatus inactive:Bool = User; -userContact#f2fb8319 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userRequest#22e8ceb0 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userForeign#5214c89d id:int first_name:string last_name:string access_hash:long photo:UserProfilePhoto status:UserStatus = User; -userDeleted#b29ad7cc id:int first_name:string last_name:string = User; - -userProfilePhotoEmpty#4f11bae1 = UserProfilePhoto; -userProfilePhoto#d559d8c8 photo_id:long photo_small:FileLocation photo_big:FileLocation = UserProfilePhoto; - -userStatusEmpty#9d05049 = UserStatus; -userStatusOnline#edb93949 expires:int = UserStatus; -userStatusOffline#8c703f was_online:int = UserStatus; - -chatEmpty#9ba2d800 id:int = Chat; -chat#6e9c9bc7 id:int title:string photo:ChatPhoto participants_count:int date:int left:Bool version:int = Chat; -chatForbidden#fb0ccc41 id:int title:string date:int = Chat; - -chatFull#630e61be id:int participants:ChatParticipants chat_photo:Photo notify_settings:PeerNotifySettings = ChatFull; - -chatParticipant#c8d7493e user_id:int inviter_id:int date:int = ChatParticipant; - -chatParticipantsForbidden#fd2bb8a chat_id:int = ChatParticipants; -chatParticipants#7841b415 chat_id:int admin_id:int participants:Vector version:int = ChatParticipants; - -chatPhotoEmpty#37c1011c = ChatPhoto; -chatPhoto#6153276a photo_small:FileLocation photo_big:FileLocation = ChatPhoto; - -messageEmpty#83e5de54 id:int = Message; -message#22eb6aba id:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageForwarded#5f46804 id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -messageService#9f8d60bb id:int from_id:int to_id:Peer out:Bool unread:Bool date:int action:MessageAction = Message; - -messageMediaEmpty#3ded6320 = MessageMedia; -messageMediaPhoto#c8c45a2a photo:Photo = MessageMedia; -messageMediaVideo#a2d24290 video:Video = MessageMedia; -messageMediaGeo#56e0d474 geo:GeoPoint = MessageMedia; -messageMediaContact#5e7d2f39 phone_number:string first_name:string last_name:string user_id:int = MessageMedia; -messageMediaUnsupported#29632a36 bytes:bytes = MessageMedia; - -messageActionEmpty#b6aef7b0 = MessageAction; -messageActionChatCreate#a6638b9a title:string users:Vector = MessageAction; -messageActionChatEditTitle#b5a1ce5a title:string = MessageAction; -messageActionChatEditPhoto#7fcb13a8 photo:Photo = MessageAction; -messageActionChatDeletePhoto#95e3fbef = MessageAction; -messageActionChatAddUser#5e3cfc4b user_id:int = MessageAction; -messageActionChatDeleteUser#b2ae9b0c user_id:int = MessageAction; - -dialog#ab3a99ac peer:Peer top_message:int unread_count:int notify_settings:PeerNotifySettings = Dialog; - -photoEmpty#2331b22d id:long = Photo; -photo#22b56751 id:long access_hash:long user_id:int date:int caption:string geo:GeoPoint sizes:Vector = Photo; - -photoSizeEmpty#e17e23c type:string = PhotoSize; -photoSize#77bfb61b type:string location:FileLocation w:int h:int size:int = PhotoSize; -photoCachedSize#e9a734fa type:string location:FileLocation w:int h:int bytes:bytes = PhotoSize; - -videoEmpty#c10658a8 id:long = Video; -video#388fa391 id:long access_hash:long user_id:int date:int caption:string duration:int mime_type:string size:int thumb:PhotoSize dc_id:int w:int h:int = Video; - -geoPointEmpty#1117dd5f = GeoPoint; -geoPoint#2049d70c long:double lat:double = GeoPoint; - -auth.checkedPhone#e300cc3b phone_registered:Bool phone_invited:Bool = auth.CheckedPhone; - -auth.sentCode#efed51d9 phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -auth.authorization#f6b673a4 expires:int user:User = auth.Authorization; - -auth.exportedAuthorization#df969c2d id:int bytes:bytes = auth.ExportedAuthorization; - -inputNotifyPeer#b8bc5b0c peer:InputPeer = InputNotifyPeer; -inputNotifyUsers#193b4417 = InputNotifyPeer; -inputNotifyChats#4a95e84e = InputNotifyPeer; -inputNotifyAll#a429b886 = InputNotifyPeer; - -inputPeerNotifyEventsEmpty#f03064d8 = InputPeerNotifyEvents; -inputPeerNotifyEventsAll#e86a2c74 = InputPeerNotifyEvents; - -inputPeerNotifySettings#46a2ce98 mute_until:int sound:string show_previews:Bool events_mask:int = InputPeerNotifySettings; - -peerNotifyEventsEmpty#add53cb3 = PeerNotifyEvents; -peerNotifyEventsAll#6d1ded88 = PeerNotifyEvents; - -peerNotifySettingsEmpty#70a68512 = PeerNotifySettings; -peerNotifySettings#8d5e11ee mute_until:int sound:string show_previews:Bool events_mask:int = PeerNotifySettings; - -wallPaper#ccb03657 id:int title:string sizes:Vector color:int = WallPaper; - -userFull#771095da user:User link:contacts.Link profile_photo:Photo notify_settings:PeerNotifySettings blocked:Bool real_first_name:string real_last_name:string = UserFull; - -contact#f911c994 user_id:int mutual:Bool = Contact; - -importedContact#d0028438 user_id:int client_id:long = ImportedContact; - -contactBlocked#561bc879 user_id:int date:int = ContactBlocked; - -contactFound#ea879f95 user_id:int = ContactFound; - -contactSuggested#3de191a1 user_id:int mutual_contacts:int = ContactSuggested; - -contactStatus#aa77b873 user_id:int expires:int = ContactStatus; - -chatLocated#3631cf4c chat_id:int distance:int = ChatLocated; - -contacts.foreignLinkUnknown#133421f8 = contacts.ForeignLink; -contacts.foreignLinkRequested#a7801f47 has_phone:Bool = contacts.ForeignLink; -contacts.foreignLinkMutual#1bea8ce1 = contacts.ForeignLink; - -contacts.myLinkEmpty#d22a1c60 = contacts.MyLink; -contacts.myLinkRequested#6c69efee contact:Bool = contacts.MyLink; -contacts.myLinkContact#c240ebd9 = contacts.MyLink; - -contacts.link#eccea3f5 my_link:contacts.MyLink foreign_link:contacts.ForeignLink user:User = contacts.Link; - -contacts.contacts#6f8b8cb2 contacts:Vector users:Vector = contacts.Contacts; -contacts.contactsNotModified#b74ba9d2 = contacts.Contacts; - -contacts.importedContacts#ad524315 imported:Vector retry_contacts:Vector users:Vector = contacts.ImportedContacts; - -contacts.blocked#1c138d15 blocked:Vector users:Vector = contacts.Blocked; -contacts.blockedSlice#900802a1 count:int blocked:Vector users:Vector = contacts.Blocked; - -contacts.found#566000e results:Vector users:Vector = contacts.Found; - -contacts.suggested#5649dcc5 results:Vector users:Vector = contacts.Suggested; - -messages.dialogs#15ba6c40 dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; -messages.dialogsSlice#71e094f3 count:int dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; - -messages.messages#8c718e87 messages:Vector chats:Vector users:Vector = messages.Messages; -messages.messagesSlice#b446ae3 count:int messages:Vector chats:Vector users:Vector = messages.Messages; - -messages.messageEmpty#3f4e0648 = messages.Message; -messages.message#ff90c417 message:Message chats:Vector users:Vector = messages.Message; - -messages.statedMessages#969478bb messages:Vector chats:Vector users:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessage#d07ae726 message:Message chats:Vector users:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessage#d1f4d35c id:int date:int pts:int seq:int = messages.SentMessage; - -messages.chat#40e9002a chat:Chat users:Vector = messages.Chat; - -messages.chats#8150cbd8 chats:Vector users:Vector = messages.Chats; - -messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector users:Vector = messages.ChatFull; - -messages.affectedHistory#b7de36f2 pts:int seq:int offset:int = messages.AffectedHistory; - -inputMessagesFilterEmpty#57e2f66c = MessagesFilter; -inputMessagesFilterPhotos#9609a51c = MessagesFilter; -inputMessagesFilterVideo#9fc00e65 = MessagesFilter; -inputMessagesFilterPhotoVideo#56e9f0e4 = MessagesFilter; -inputMessagesFilterDocument#9eddf188 = MessagesFilter; -inputMessagesFilterAudio#cfc87522 = MessagesFilter; - -updateNewMessage#13abdb3 message:Message pts:int = Update; -updateMessageID#4e90bfd6 id:int random_id:long = Update; -updateReadMessages#c6649e31 messages:Vector pts:int = Update; -updateDeleteMessages#a92bfe26 messages:Vector pts:int = Update; -updateRestoreMessages#d15de04d messages:Vector pts:int = Update; -updateUserTyping#6baa8508 user_id:int = Update; -updateChatUserTyping#3c46cfe6 chat_id:int user_id:int = Update; -updateChatParticipants#7761198 participants:ChatParticipants = Update; -updateUserStatus#1bfbd823 user_id:int status:UserStatus = Update; -updateUserName#da22d9ad user_id:int first_name:string last_name:string = Update; -updateUserPhoto#95313b0c user_id:int date:int photo:UserProfilePhoto previous:Bool = Update; -updateContactRegistered#2575bbb9 user_id:int date:int = Update; -updateContactLink#51a48a9a user_id:int my_link:contacts.MyLink foreign_link:contacts.ForeignLink = Update; -updateActivation#6f690963 user_id:int = Update; -updateNewAuthorization#8f06529a auth_key_id:long date:int device:string location:string = Update; - -updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State; - -updates.differenceEmpty#5d75a138 date:int seq:int = updates.Difference; -updates.difference#f49ca0 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector state:updates.State = updates.Difference; -updates.differenceSlice#a8fb1981 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector intermediate_state:updates.State = updates.Difference; - -updatesTooLong#e317af7e = Updates; -updateShortMessage#d3f45784 id:int from_id:int message:string pts:int date:int seq:int = Updates; -updateShortChatMessage#2b2fbd4e id:int from_id:int chat_id:int message:string pts:int date:int seq:int = Updates; -updateShort#78d4dec1 update:Update date:int = Updates; -updatesCombined#725b04c3 updates:Vector users:Vector chats:Vector date:int seq_start:int seq:int = Updates; -updates#74ae4240 updates:Vector users:Vector chats:Vector date:int seq:int = Updates; - -photos.photos#8dca6aa5 photos:Vector users:Vector = photos.Photos; -photos.photosSlice#15051f54 count:int photos:Vector users:Vector = photos.Photos; - -photos.photo#20212ca8 photo:Photo users:Vector = photos.Photo; - -upload.file#96a18d5 type:storage.FileType mtime:int bytes:bytes = upload.File; - -dcOption#2ec2a43c id:int hostname:string ip_address:string port:int = DcOption; - -config#2e54dd74 date:int test_mode:Bool this_dc:int dc_options:Vector chat_size_max:int broadcast_size_max:int = Config; - -nearestDc#8e1a1775 country:string this_dc:int nearest_dc:int = NearestDc; - -help.appUpdate#8987f311 id:int critical:Bool url:string text:string = help.AppUpdate; -help.noAppUpdate#c45a6536 = help.AppUpdate; - -help.inviteText#18cb9f78 message:string = help.InviteText; - -messages.statedMessagesLinks#3e74f5c6 messages:Vector chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessageLink#a9af2881 message:Message chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector = messages.SentMessage; - -inputGeoChat#74d456fa chat_id:int access_hash:long = InputGeoChat; - -inputNotifyGeoChatPeer#4d8ddec8 peer:InputGeoChat = InputNotifyPeer; - -geoChat#75eaea5a id:int access_hash:long title:string address:string venue:string geo:GeoPoint photo:ChatPhoto participants_count:int date:int checked_in:Bool version:int = Chat; - -geoChatMessageEmpty#60311a9b chat_id:int id:int = GeoChatMessage; -geoChatMessage#4505f8e1 chat_id:int id:int from_id:int date:int message:string media:MessageMedia = GeoChatMessage; -geoChatMessageService#d34fa24e chat_id:int id:int from_id:int date:int action:MessageAction = GeoChatMessage; - -geochats.statedMessage#17b1578b message:GeoChatMessage chats:Vector users:Vector seq:int = geochats.StatedMessage; - -geochats.located#48feb267 results:Vector messages:Vector chats:Vector users:Vector = geochats.Located; - -geochats.messages#d1526db1 messages:Vector chats:Vector users:Vector = geochats.Messages; -geochats.messagesSlice#bc5863e8 count:int messages:Vector chats:Vector users:Vector = geochats.Messages; - -messageActionGeoChatCreate#6f038ebc title:string address:string = MessageAction; -messageActionGeoChatCheckin#c7d53de = MessageAction; - -updateNewGeoChatMessage#5a68e3f7 message:GeoChatMessage = Update; - -wallPaperSolid#63117f24 id:int title:string bg_color:int color:int = WallPaper; - -updateNewEncryptedMessage#12bcbd9a message:EncryptedMessage qts:int = Update; -updateEncryptedChatTyping#1710f156 chat_id:int = Update; -updateEncryption#b4a2e88d chat:EncryptedChat date:int = Update; -updateEncryptedMessagesRead#38fe25b7 chat_id:int max_date:int date:int = Update; - -encryptedChatEmpty#ab7ec0a0 id:int = EncryptedChat; -encryptedChatWaiting#3bf703dc id:int access_hash:long date:int admin_id:int participant_id:int = EncryptedChat; -encryptedChatRequested#c878527e id:int access_hash:long date:int admin_id:int participant_id:int g_a:bytes = EncryptedChat; -encryptedChat#fa56ce36 id:int access_hash:long date:int admin_id:int participant_id:int g_a_or_b:bytes key_fingerprint:long = EncryptedChat; -encryptedChatDiscarded#13d6dd27 id:int = EncryptedChat; - -inputEncryptedChat#f141b5e1 chat_id:int access_hash:long = InputEncryptedChat; - -encryptedFileEmpty#c21f497e = EncryptedFile; -encryptedFile#4a70994c id:long access_hash:long size:int dc_id:int key_fingerprint:int = EncryptedFile; - -inputEncryptedFileEmpty#1837c364 = InputEncryptedFile; -inputEncryptedFileUploaded#64bd0306 id:long parts:int md5_checksum:string key_fingerprint:int = InputEncryptedFile; -inputEncryptedFile#5a17b5e5 id:long access_hash:long = InputEncryptedFile; - -inputEncryptedFileLocation#f5235d55 id:long access_hash:long = InputFileLocation; - -encryptedMessage#ed18c118 random_id:long chat_id:int date:int bytes:bytes file:EncryptedFile = EncryptedMessage; -encryptedMessageService#23734b06 random_id:long chat_id:int date:int bytes:bytes = EncryptedMessage; - -messages.dhConfigNotModified#c0e24635 random:bytes = messages.DhConfig; -messages.dhConfig#2c221edd g:int p:bytes version:int random:bytes = messages.DhConfig; - -messages.sentEncryptedMessage#560f8935 date:int = messages.SentEncryptedMessage; -messages.sentEncryptedFile#9493ff32 date:int file:EncryptedFile = messages.SentEncryptedMessage; - -inputFileBig#fa4f0bb5 id:long parts:int name:string = InputFile; - -inputEncryptedFileBigUploaded#2dc173c8 id:long parts:int key_fingerprint:int = InputEncryptedFile; - -updateChatParticipantAdd#3a0eeb22 chat_id:int user_id:int inviter_id:int version:int = Update; -updateChatParticipantDelete#6e5f8c22 chat_id:int user_id:int version:int = Update; -updateDcOptions#8e5e9873 dc_options:Vector = Update; - -inputMediaUploadedAudio#4e498cab file:InputFile duration:int mime_type:string = InputMedia; -inputMediaAudio#89938781 id:InputAudio = InputMedia; -inputMediaUploadedDocument#34e794bd file:InputFile file_name:string mime_type:string = InputMedia; -inputMediaUploadedThumbDocument#3e46de5d file:InputFile thumb:InputFile file_name:string mime_type:string = InputMedia; -inputMediaDocument#d184e841 id:InputDocument = InputMedia; - -messageMediaDocument#2fda2204 document:Document = MessageMedia; -messageMediaAudio#c6b68300 audio:Audio = MessageMedia; - -inputAudioEmpty#d95adc84 = InputAudio; -inputAudio#77d440ff id:long access_hash:long = InputAudio; - -inputDocumentEmpty#72f0eaae = InputDocument; -inputDocument#18798952 id:long access_hash:long = InputDocument; - -inputAudioFileLocation#74dc404d id:long access_hash:long = InputFileLocation; -inputDocumentFileLocation#4e45abe9 id:long access_hash:long = InputFileLocation; - -audioEmpty#586988d8 id:long = Audio; -audio#c7ac6496 id:long access_hash:long user_id:int date:int duration:int mime_type:string size:int dc_id:int = Audio; - -documentEmpty#36f8c871 id:long = Document; -document#9efc6326 id:long access_hash:long user_id:int date:int file_name:string mime_type:string size:int thumb:PhotoSize dc_id:int = Document; - -help.support#17c6b5f6 phone_number:string user:User = help.Support; - -notifyPeer#9fd40bd8 peer:Peer = NotifyPeer; -notifyUsers#b4c83b4c = NotifyPeer; -notifyChats#c007cec3 = NotifyPeer; -notifyAll#74d07c60 = NotifyPeer; - -updateUserBlocked#80ece81a user_id:int blocked:Bool = Update; -updateNotifySettings#bec268ef peer:NotifyPeer notify_settings:PeerNotifySettings = Update; - -auth.sentAppCode#e325edcf phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - ----functions--- - -invokeAfterMsg#cb9f372d {X:Type} msg_id:long query:!X = X; - -invokeAfterMsgs#3dc4b4f0 {X:Type} msg_ids:Vector query:!X = X; - -auth.checkPhone#6fe51dfb phone_number:string = auth.CheckedPhone; -auth.sendCode#768d5f4d phone_number:string sms_type:int api_id:int api_hash:string lang_code:string = auth.SentCode; -auth.sendCall#3c51564 phone_number:string phone_code_hash:string = Bool; -auth.signUp#1b067634 phone_number:string phone_code_hash:string phone_code:string first_name:string last_name:string = auth.Authorization; -auth.signIn#bcd51581 phone_number:string phone_code_hash:string phone_code:string = auth.Authorization; -auth.logOut#5717da40 = Bool; -auth.resetAuthorizations#9fab0d1a = Bool; -auth.sendInvites#771c1d97 phone_numbers:Vector message:string = Bool; -auth.exportAuthorization#e5bfffcd dc_id:int = auth.ExportedAuthorization; -auth.importAuthorization#e3ef9613 id:int bytes:bytes = auth.Authorization; -auth.bindTempAuthKey#cdd42a05 perm_auth_key_id:long nonce:long expires_at:int encrypted_message:bytes = Bool; - -account.registerDevice#446c712c token_type:int token:string device_model:string system_version:string app_version:string app_sandbox:Bool lang_code:string = Bool; -account.unregisterDevice#65c55b40 token_type:int token:string = Bool; -account.updateNotifySettings#84be5b93 peer:InputNotifyPeer settings:InputPeerNotifySettings = Bool; -account.getNotifySettings#12b3ad31 peer:InputNotifyPeer = PeerNotifySettings; -account.resetNotifySettings#db7e1747 = Bool; -account.updateProfile#f0888d68 first_name:string last_name:string = User; -account.updateStatus#6628562c offline:Bool = Bool; -account.getWallPapers#c04cfac2 = Vector; - -users.getUsers#d91a548 id:Vector = Vector; -users.getFullUser#ca30a5b1 id:InputUser = UserFull; - -contacts.getStatuses#c4a353ee = Vector; -contacts.getContacts#22c6aa08 hash:string = contacts.Contacts; -contacts.importContacts#da30b32d contacts:Vector replace:Bool = contacts.ImportedContacts; -contacts.search#11f812d8 q:string limit:int = contacts.Found; -contacts.getSuggested#cd773428 limit:int = contacts.Suggested; -contacts.deleteContact#8e953744 id:InputUser = contacts.Link; -contacts.deleteContacts#59ab389e id:Vector = Bool; -contacts.block#332b49fc id:InputUser = Bool; -contacts.unblock#e54100bd id:InputUser = Bool; -contacts.getBlocked#f57c350f offset:int limit:int = contacts.Blocked; -contacts.exportCard#84e53737 = Vector; -contacts.importCard#4fe196fe export_card:Vector = User; - -messages.getMessages#4222fa74 id:Vector = messages.Messages; -messages.getDialogs#eccf1df6 offset:int max_id:int limit:int = messages.Dialogs; -messages.getHistory#92a1df2f peer:InputPeer offset:int max_id:int limit:int = messages.Messages; -messages.search#7e9f2ab peer:InputPeer q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = messages.Messages; -messages.readHistory#b04f2510 peer:InputPeer max_id:int offset:int = messages.AffectedHistory; -messages.deleteHistory#f4f8fb61 peer:InputPeer offset:int = messages.AffectedHistory; -messages.deleteMessages#14f2dd0a id:Vector = Vector; -messages.restoreMessages#395f9d7e id:Vector = Vector; -messages.receivedMessages#28abcb68 max_id:int = Vector; -messages.setTyping#719839e9 peer:InputPeer typing:Bool = Bool; -messages.sendMessage#4cde0aab peer:InputPeer message:string random_id:long = messages.SentMessage; -messages.sendMedia#a3c85d76 peer:InputPeer media:InputMedia random_id:long = messages.StatedMessage; -messages.forwardMessages#514cd10f peer:InputPeer id:Vector = messages.StatedMessages; -messages.getChats#3c6aa187 id:Vector = messages.Chats; -messages.getFullChat#3b831c66 chat_id:int = messages.ChatFull; -messages.editChatTitle#b4bc68b5 chat_id:int title:string = messages.StatedMessage; -messages.editChatPhoto#d881821d chat_id:int photo:InputChatPhoto = messages.StatedMessage; -messages.addChatUser#2ee9ee9e chat_id:int user_id:InputUser fwd_limit:int = messages.StatedMessage; -messages.deleteChatUser#c3c5cd23 chat_id:int user_id:InputUser = messages.StatedMessage; -messages.createChat#419d9aee users:Vector title:string = messages.StatedMessage; - -updates.getState#edd4882a = updates.State; -updates.getDifference#a041495 pts:int date:int qts:int = updates.Difference; - -photos.updateProfilePhoto#eef579a0 id:InputPhoto crop:InputPhotoCrop = UserProfilePhoto; -photos.uploadProfilePhoto#d50f9c88 file:InputFile caption:string geo_point:InputGeoPoint crop:InputPhotoCrop = photos.Photo; - -upload.saveFilePart#b304a621 file_id:long file_part:int bytes:bytes = Bool; -upload.getFile#e3a6cfb5 location:InputFileLocation offset:int limit:int = upload.File; - -help.getConfig#c4f9186b = Config; -help.getNearestDc#1fb33026 = NearestDc; -help.getAppUpdate#c812ac7e device_model:string system_version:string app_version:string lang_code:string = help.AppUpdate; -help.saveAppLog#6f02f748 events:Vector = Bool; -help.getInviteText#a4a95186 lang_code:string = help.InviteText; - -photos.getUserPhotos#b7ee553c user_id:InputUser offset:int max_id:int limit:int = photos.Photos; - -messages.forwardMessage#3f3f4f2 peer:InputPeer id:int random_id:long = messages.StatedMessage; -messages.sendBroadcast#41bb0972 contacts:Vector message:string media:InputMedia = messages.StatedMessages; - -geochats.getLocated#7f192d8f geo_point:InputGeoPoint radius:int limit:int = geochats.Located; -geochats.getRecents#e1427e6f offset:int limit:int = geochats.Messages; -geochats.checkin#55b3e8fb peer:InputGeoChat = geochats.StatedMessage; -geochats.getFullChat#6722dd6f peer:InputGeoChat = messages.ChatFull; -geochats.editChatTitle#4c8e2273 peer:InputGeoChat title:string address:string = geochats.StatedMessage; -geochats.editChatPhoto#35d81a95 peer:InputGeoChat photo:InputChatPhoto = geochats.StatedMessage; -geochats.search#cfcdc44d peer:InputGeoChat q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = geochats.Messages; -geochats.getHistory#b53f7a68 peer:InputGeoChat offset:int max_id:int limit:int = geochats.Messages; -geochats.setTyping#8b8a729 peer:InputGeoChat typing:Bool = Bool; -geochats.sendMessage#61b0044 peer:InputGeoChat message:string random_id:long = geochats.StatedMessage; -geochats.sendMedia#b8f0deff peer:InputGeoChat media:InputMedia random_id:long = geochats.StatedMessage; -geochats.createGeoChat#e092e16 title:string geo_point:InputGeoPoint address:string venue:string = geochats.StatedMessage; - -messages.getDhConfig#26cf8950 version:int random_length:int = messages.DhConfig; -messages.requestEncryption#f64daf43 user_id:InputUser random_id:int g_a:bytes = EncryptedChat; -messages.acceptEncryption#3dbc0415 peer:InputEncryptedChat g_b:bytes key_fingerprint:long = EncryptedChat; -messages.discardEncryption#edd923c5 chat_id:int = Bool; -messages.setEncryptedTyping#791451ed peer:InputEncryptedChat typing:Bool = Bool; -messages.readEncryptedHistory#7f4b690a peer:InputEncryptedChat max_date:int = Bool; -messages.sendEncrypted#a9776773 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.sendEncryptedFile#9a901b66 peer:InputEncryptedChat random_id:long data:bytes file:InputEncryptedFile = messages.SentEncryptedMessage; -messages.sendEncryptedService#32d439a4 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.receivedQueue#55a5bb66 max_qts:int = Vector; - -upload.saveBigFilePart#de7b673d file_id:long file_part:int file_total_parts:int bytes:bytes = Bool; - -initConnection#69796de9 {X:Type} api_id:int device_model:string system_version:string app_version:string lang_code:string query:!X = X; - -help.getSupport#9cdf08cd = help.Support; - -auth.sendSms#da9f3e8 phone_number:string phone_code_hash:string = Bool; - -invokeWithLayer16#cf5f0987 {X:Type} query:!X = X; diff --git a/scheme17.tl b/scheme17.tl deleted file mode 100644 index c564155..0000000 --- a/scheme17.tl +++ /dev/null @@ -1,528 +0,0 @@ -int ?= Int; -long ?= Long; -double ?= Double; -string ?= String; - -bytes string = Bytes; - -boolFalse#bc799737 = Bool; -boolTrue#997275b5 = Bool; - -vector#1cb5c415 {t:Type} # [ t ] = Vector t; - -error#c4b9f9bb code:int text:string = Error; - -null#56730bcc = Null; - -inputPeerEmpty#7f3b18ea = InputPeer; -inputPeerSelf#7da07ec9 = InputPeer; -inputPeerContact#1023dbe8 user_id:int = InputPeer; -inputPeerForeign#9b447325 user_id:int access_hash:long = InputPeer; -inputPeerChat#179be863 chat_id:int = InputPeer; - -inputUserEmpty#b98886cf = InputUser; -inputUserSelf#f7c1b13f = InputUser; -inputUserContact#86e94f65 user_id:int = InputUser; -inputUserForeign#655e74ff user_id:int access_hash:long = InputUser; - -inputPhoneContact#f392b7f4 client_id:long phone:string first_name:string last_name:string = InputContact; - -inputFile#f52ff27f id:long parts:int name:string md5_checksum:string = InputFile; - -inputMediaEmpty#9664f57f = InputMedia; -inputMediaUploadedPhoto#2dc53a7d file:InputFile = InputMedia; -inputMediaPhoto#8f2ab2ec id:InputPhoto = InputMedia; -inputMediaGeoPoint#f9c44144 geo_point:InputGeoPoint = InputMedia; -inputMediaContact#a6e45987 phone_number:string first_name:string last_name:string = InputMedia; -inputMediaUploadedVideo#133ad6f6 file:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaUploadedThumbVideo#9912dabf file:InputFile thumb:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaVideo#7f023ae6 id:InputVideo = InputMedia; - -inputChatPhotoEmpty#1ca48f57 = InputChatPhoto; -inputChatUploadedPhoto#94254732 file:InputFile crop:InputPhotoCrop = InputChatPhoto; -inputChatPhoto#b2e1bf08 id:InputPhoto crop:InputPhotoCrop = InputChatPhoto; - -inputGeoPointEmpty#e4c123d6 = InputGeoPoint; -inputGeoPoint#f3b7acc9 lat:double long:double = InputGeoPoint; - -inputPhotoEmpty#1cd7bf0d = InputPhoto; -inputPhoto#fb95c6c4 id:long access_hash:long = InputPhoto; - -inputVideoEmpty#5508ec75 = InputVideo; -inputVideo#ee579652 id:long access_hash:long = InputVideo; - -inputFileLocation#14637196 volume_id:long local_id:int secret:long = InputFileLocation; -inputVideoFileLocation#3d0364ec id:long access_hash:long = InputFileLocation; - -inputPhotoCropAuto#ade6b004 = InputPhotoCrop; -inputPhotoCrop#d9915325 crop_left:double crop_top:double crop_width:double = InputPhotoCrop; - -inputAppEvent#770656a8 time:double type:string peer:long data:string = InputAppEvent; - -peerUser#9db1bc6d user_id:int = Peer; -peerChat#bad0e5bb chat_id:int = Peer; - -storage.fileUnknown#aa963b05 = storage.FileType; -storage.fileJpeg#7efe0e = storage.FileType; -storage.fileGif#cae1aadf = storage.FileType; -storage.filePng#a4f63c0 = storage.FileType; -storage.filePdf#ae1e508d = storage.FileType; -storage.fileMp3#528a0677 = storage.FileType; -storage.fileMov#4b09ebbc = storage.FileType; -storage.filePartial#40bc6f52 = storage.FileType; -storage.fileMp4#b3cea0e4 = storage.FileType; -storage.fileWebp#1081464c = storage.FileType; - -fileLocationUnavailable#7c596b46 volume_id:long local_id:int secret:long = FileLocation; -fileLocation#53d69076 dc_id:int volume_id:long local_id:int secret:long = FileLocation; - -userEmpty#200250ba id:int = User; -userSelf#720535ec id:int first_name:string last_name:string phone:string photo:UserProfilePhoto status:UserStatus inactive:Bool = User; -userContact#f2fb8319 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userRequest#22e8ceb0 id:int first_name:string last_name:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userForeign#5214c89d id:int first_name:string last_name:string access_hash:long photo:UserProfilePhoto status:UserStatus = User; -userDeleted#b29ad7cc id:int first_name:string last_name:string = User; - -userProfilePhotoEmpty#4f11bae1 = UserProfilePhoto; -userProfilePhoto#d559d8c8 photo_id:long photo_small:FileLocation photo_big:FileLocation = UserProfilePhoto; - -userStatusEmpty#9d05049 = UserStatus; -userStatusOnline#edb93949 expires:int = UserStatus; -userStatusOffline#8c703f was_online:int = UserStatus; - -chatEmpty#9ba2d800 id:int = Chat; -chat#6e9c9bc7 id:int title:string photo:ChatPhoto participants_count:int date:int left:Bool version:int = Chat; -chatForbidden#fb0ccc41 id:int title:string date:int = Chat; - -chatFull#630e61be id:int participants:ChatParticipants chat_photo:Photo notify_settings:PeerNotifySettings = ChatFull; - -chatParticipant#c8d7493e user_id:int inviter_id:int date:int = ChatParticipant; - -chatParticipantsForbidden#fd2bb8a chat_id:int = ChatParticipants; -chatParticipants#7841b415 chat_id:int admin_id:int participants:Vector version:int = ChatParticipants; - -chatPhotoEmpty#37c1011c = ChatPhoto; -chatPhoto#6153276a photo_small:FileLocation photo_big:FileLocation = ChatPhoto; - -messageEmpty#83e5de54 id:int = Message; -//message#22eb6aba id:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -//messageForwarded#5f46804 id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -//messageService#9f8d60bb id:int from_id:int to_id:Peer out:Bool unread:Bool date:int action:MessageAction = Message; - -messageMediaEmpty#3ded6320 = MessageMedia; -messageMediaPhoto#c8c45a2a photo:Photo = MessageMedia; -messageMediaVideo#a2d24290 video:Video = MessageMedia; -messageMediaGeo#56e0d474 geo:GeoPoint = MessageMedia; -messageMediaContact#5e7d2f39 phone_number:string first_name:string last_name:string user_id:int = MessageMedia; -messageMediaUnsupported#29632a36 bytes:bytes = MessageMedia; - -messageActionEmpty#b6aef7b0 = MessageAction; -messageActionChatCreate#a6638b9a title:string users:Vector = MessageAction; -messageActionChatEditTitle#b5a1ce5a title:string = MessageAction; -messageActionChatEditPhoto#7fcb13a8 photo:Photo = MessageAction; -messageActionChatDeletePhoto#95e3fbef = MessageAction; -messageActionChatAddUser#5e3cfc4b user_id:int = MessageAction; -messageActionChatDeleteUser#b2ae9b0c user_id:int = MessageAction; - -dialog#ab3a99ac peer:Peer top_message:int unread_count:int notify_settings:PeerNotifySettings = Dialog; - -photoEmpty#2331b22d id:long = Photo; -photo#22b56751 id:long access_hash:long user_id:int date:int caption:string geo:GeoPoint sizes:Vector = Photo; - -photoSizeEmpty#e17e23c type:string = PhotoSize; -photoSize#77bfb61b type:string location:FileLocation w:int h:int size:int = PhotoSize; -photoCachedSize#e9a734fa type:string location:FileLocation w:int h:int bytes:bytes = PhotoSize; - -videoEmpty#c10658a8 id:long = Video; -video#388fa391 id:long access_hash:long user_id:int date:int caption:string duration:int mime_type:string size:int thumb:PhotoSize dc_id:int w:int h:int = Video; - -geoPointEmpty#1117dd5f = GeoPoint; -geoPoint#2049d70c long:double lat:double = GeoPoint; - -auth.checkedPhone#e300cc3b phone_registered:Bool phone_invited:Bool = auth.CheckedPhone; - -auth.sentCode#efed51d9 phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -auth.authorization#f6b673a4 expires:int user:User = auth.Authorization; - -auth.exportedAuthorization#df969c2d id:int bytes:bytes = auth.ExportedAuthorization; - -inputNotifyPeer#b8bc5b0c peer:InputPeer = InputNotifyPeer; -inputNotifyUsers#193b4417 = InputNotifyPeer; -inputNotifyChats#4a95e84e = InputNotifyPeer; -inputNotifyAll#a429b886 = InputNotifyPeer; - -inputPeerNotifyEventsEmpty#f03064d8 = InputPeerNotifyEvents; -inputPeerNotifyEventsAll#e86a2c74 = InputPeerNotifyEvents; - -inputPeerNotifySettings#46a2ce98 mute_until:int sound:string show_previews:Bool events_mask:int = InputPeerNotifySettings; - -peerNotifyEventsEmpty#add53cb3 = PeerNotifyEvents; -peerNotifyEventsAll#6d1ded88 = PeerNotifyEvents; - -peerNotifySettingsEmpty#70a68512 = PeerNotifySettings; -peerNotifySettings#8d5e11ee mute_until:int sound:string show_previews:Bool events_mask:int = PeerNotifySettings; - -wallPaper#ccb03657 id:int title:string sizes:Vector color:int = WallPaper; - -userFull#771095da user:User link:contacts.Link profile_photo:Photo notify_settings:PeerNotifySettings blocked:Bool real_first_name:string real_last_name:string = UserFull; - -contact#f911c994 user_id:int mutual:Bool = Contact; - -importedContact#d0028438 user_id:int client_id:long = ImportedContact; - -contactBlocked#561bc879 user_id:int date:int = ContactBlocked; - -contactFound#ea879f95 user_id:int = ContactFound; - -contactSuggested#3de191a1 user_id:int mutual_contacts:int = ContactSuggested; - -contactStatus#aa77b873 user_id:int expires:int = ContactStatus; - -chatLocated#3631cf4c chat_id:int distance:int = ChatLocated; - -contacts.foreignLinkUnknown#133421f8 = contacts.ForeignLink; -contacts.foreignLinkRequested#a7801f47 has_phone:Bool = contacts.ForeignLink; -contacts.foreignLinkMutual#1bea8ce1 = contacts.ForeignLink; - -contacts.myLinkEmpty#d22a1c60 = contacts.MyLink; -contacts.myLinkRequested#6c69efee contact:Bool = contacts.MyLink; -contacts.myLinkContact#c240ebd9 = contacts.MyLink; - -contacts.link#eccea3f5 my_link:contacts.MyLink foreign_link:contacts.ForeignLink user:User = contacts.Link; - -contacts.contacts#6f8b8cb2 contacts:Vector users:Vector = contacts.Contacts; -contacts.contactsNotModified#b74ba9d2 = contacts.Contacts; - -contacts.importedContacts#ad524315 imported:Vector retry_contacts:Vector users:Vector = contacts.ImportedContacts; - -contacts.blocked#1c138d15 blocked:Vector users:Vector = contacts.Blocked; -contacts.blockedSlice#900802a1 count:int blocked:Vector users:Vector = contacts.Blocked; - -contacts.found#566000e results:Vector users:Vector = contacts.Found; - -contacts.suggested#5649dcc5 results:Vector users:Vector = contacts.Suggested; - -messages.dialogs#15ba6c40 dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; -messages.dialogsSlice#71e094f3 count:int dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; - -messages.messages#8c718e87 messages:Vector chats:Vector users:Vector = messages.Messages; -messages.messagesSlice#b446ae3 count:int messages:Vector chats:Vector users:Vector = messages.Messages; - -messages.messageEmpty#3f4e0648 = messages.Message; -messages.message#ff90c417 message:Message chats:Vector users:Vector = messages.Message; - -messages.statedMessages#969478bb messages:Vector chats:Vector users:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessage#d07ae726 message:Message chats:Vector users:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessage#d1f4d35c id:int date:int pts:int seq:int = messages.SentMessage; - -messages.chat#40e9002a chat:Chat users:Vector = messages.Chat; - -messages.chats#8150cbd8 chats:Vector users:Vector = messages.Chats; - -messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector users:Vector = messages.ChatFull; - -messages.affectedHistory#b7de36f2 pts:int seq:int offset:int = messages.AffectedHistory; - -inputMessagesFilterEmpty#57e2f66c = MessagesFilter; -inputMessagesFilterPhotos#9609a51c = MessagesFilter; -inputMessagesFilterVideo#9fc00e65 = MessagesFilter; -inputMessagesFilterPhotoVideo#56e9f0e4 = MessagesFilter; -inputMessagesFilterDocument#9eddf188 = MessagesFilter; -inputMessagesFilterAudio#cfc87522 = MessagesFilter; - -updateNewMessage#13abdb3 message:Message pts:int = Update; -updateMessageID#4e90bfd6 id:int random_id:long = Update; -updateReadMessages#c6649e31 messages:Vector pts:int = Update; -updateDeleteMessages#a92bfe26 messages:Vector pts:int = Update; -updateRestoreMessages#d15de04d messages:Vector pts:int = Update; -//updateUserTyping#6baa8508 user_id:int = Update; -//updateChatUserTyping#3c46cfe6 chat_id:int user_id:int = Update; -updateChatParticipants#7761198 participants:ChatParticipants = Update; -updateUserStatus#1bfbd823 user_id:int status:UserStatus = Update; -updateUserName#da22d9ad user_id:int first_name:string last_name:string = Update; -updateUserPhoto#95313b0c user_id:int date:int photo:UserProfilePhoto previous:Bool = Update; -updateContactRegistered#2575bbb9 user_id:int date:int = Update; -updateContactLink#51a48a9a user_id:int my_link:contacts.MyLink foreign_link:contacts.ForeignLink = Update; -updateActivation#6f690963 user_id:int = Update; -updateNewAuthorization#8f06529a auth_key_id:long date:int device:string location:string = Update; - -updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State; - -updates.differenceEmpty#5d75a138 date:int seq:int = updates.Difference; -updates.difference#f49ca0 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector state:updates.State = updates.Difference; -updates.differenceSlice#a8fb1981 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector intermediate_state:updates.State = updates.Difference; - -updatesTooLong#e317af7e = Updates; -updateShortMessage#d3f45784 id:int from_id:int message:string pts:int date:int seq:int = Updates; -updateShortChatMessage#2b2fbd4e id:int from_id:int chat_id:int message:string pts:int date:int seq:int = Updates; -updateShort#78d4dec1 update:Update date:int = Updates; -updatesCombined#725b04c3 updates:Vector users:Vector chats:Vector date:int seq_start:int seq:int = Updates; -updates#74ae4240 updates:Vector users:Vector chats:Vector date:int seq:int = Updates; - -photos.photos#8dca6aa5 photos:Vector users:Vector = photos.Photos; -photos.photosSlice#15051f54 count:int photos:Vector users:Vector = photos.Photos; - -photos.photo#20212ca8 photo:Photo users:Vector = photos.Photo; - -upload.file#96a18d5 type:storage.FileType mtime:int bytes:bytes = upload.File; - -dcOption#2ec2a43c id:int hostname:string ip_address:string port:int = DcOption; - -config#2e54dd74 date:int test_mode:Bool this_dc:int dc_options:Vector chat_size_max:int broadcast_size_max:int = Config; - -nearestDc#8e1a1775 country:string this_dc:int nearest_dc:int = NearestDc; - -help.appUpdate#8987f311 id:int critical:Bool url:string text:string = help.AppUpdate; -help.noAppUpdate#c45a6536 = help.AppUpdate; - -help.inviteText#18cb9f78 message:string = help.InviteText; - -messages.statedMessagesLinks#3e74f5c6 messages:Vector chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessageLink#a9af2881 message:Message chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector = messages.SentMessage; - -inputGeoChat#74d456fa chat_id:int access_hash:long = InputGeoChat; - -inputNotifyGeoChatPeer#4d8ddec8 peer:InputGeoChat = InputNotifyPeer; - -geoChat#75eaea5a id:int access_hash:long title:string address:string venue:string geo:GeoPoint photo:ChatPhoto participants_count:int date:int checked_in:Bool version:int = Chat; - -geoChatMessageEmpty#60311a9b chat_id:int id:int = GeoChatMessage; -geoChatMessage#4505f8e1 chat_id:int id:int from_id:int date:int message:string media:MessageMedia = GeoChatMessage; -geoChatMessageService#d34fa24e chat_id:int id:int from_id:int date:int action:MessageAction = GeoChatMessage; - -geochats.statedMessage#17b1578b message:GeoChatMessage chats:Vector users:Vector seq:int = geochats.StatedMessage; - -geochats.located#48feb267 results:Vector messages:Vector chats:Vector users:Vector = geochats.Located; - -geochats.messages#d1526db1 messages:Vector chats:Vector users:Vector = geochats.Messages; -geochats.messagesSlice#bc5863e8 count:int messages:Vector chats:Vector users:Vector = geochats.Messages; - -messageActionGeoChatCreate#6f038ebc title:string address:string = MessageAction; -messageActionGeoChatCheckin#c7d53de = MessageAction; - -updateNewGeoChatMessage#5a68e3f7 message:GeoChatMessage = Update; - -wallPaperSolid#63117f24 id:int title:string bg_color:int color:int = WallPaper; - -updateNewEncryptedMessage#12bcbd9a message:EncryptedMessage qts:int = Update; -updateEncryptedChatTyping#1710f156 chat_id:int = Update; -updateEncryption#b4a2e88d chat:EncryptedChat date:int = Update; -updateEncryptedMessagesRead#38fe25b7 chat_id:int max_date:int date:int = Update; - -encryptedChatEmpty#ab7ec0a0 id:int = EncryptedChat; -encryptedChatWaiting#3bf703dc id:int access_hash:long date:int admin_id:int participant_id:int = EncryptedChat; -encryptedChatRequested#c878527e id:int access_hash:long date:int admin_id:int participant_id:int g_a:bytes = EncryptedChat; -encryptedChat#fa56ce36 id:int access_hash:long date:int admin_id:int participant_id:int g_a_or_b:bytes key_fingerprint:long = EncryptedChat; -encryptedChatDiscarded#13d6dd27 id:int = EncryptedChat; - -inputEncryptedChat#f141b5e1 chat_id:int access_hash:long = InputEncryptedChat; - -encryptedFileEmpty#c21f497e = EncryptedFile; -encryptedFile#4a70994c id:long access_hash:long size:int dc_id:int key_fingerprint:int = EncryptedFile; - -inputEncryptedFileEmpty#1837c364 = InputEncryptedFile; -inputEncryptedFileUploaded#64bd0306 id:long parts:int md5_checksum:string key_fingerprint:int = InputEncryptedFile; -inputEncryptedFile#5a17b5e5 id:long access_hash:long = InputEncryptedFile; - -inputEncryptedFileLocation#f5235d55 id:long access_hash:long = InputFileLocation; - -encryptedMessage#ed18c118 random_id:long chat_id:int date:int bytes:bytes file:EncryptedFile = EncryptedMessage; -encryptedMessageService#23734b06 random_id:long chat_id:int date:int bytes:bytes = EncryptedMessage; - -messages.dhConfigNotModified#c0e24635 random:bytes = messages.DhConfig; -messages.dhConfig#2c221edd g:int p:bytes version:int random:bytes = messages.DhConfig; - -messages.sentEncryptedMessage#560f8935 date:int = messages.SentEncryptedMessage; -messages.sentEncryptedFile#9493ff32 date:int file:EncryptedFile = messages.SentEncryptedMessage; - -inputFileBig#fa4f0bb5 id:long parts:int name:string = InputFile; - -inputEncryptedFileBigUploaded#2dc173c8 id:long parts:int key_fingerprint:int = InputEncryptedFile; - -updateChatParticipantAdd#3a0eeb22 chat_id:int user_id:int inviter_id:int version:int = Update; -updateChatParticipantDelete#6e5f8c22 chat_id:int user_id:int version:int = Update; -updateDcOptions#8e5e9873 dc_options:Vector = Update; - -inputMediaUploadedAudio#4e498cab file:InputFile duration:int mime_type:string = InputMedia; -inputMediaAudio#89938781 id:InputAudio = InputMedia; -inputMediaUploadedDocument#34e794bd file:InputFile file_name:string mime_type:string = InputMedia; -inputMediaUploadedThumbDocument#3e46de5d file:InputFile thumb:InputFile file_name:string mime_type:string = InputMedia; -inputMediaDocument#d184e841 id:InputDocument = InputMedia; - -messageMediaDocument#2fda2204 document:Document = MessageMedia; -messageMediaAudio#c6b68300 audio:Audio = MessageMedia; - -inputAudioEmpty#d95adc84 = InputAudio; -inputAudio#77d440ff id:long access_hash:long = InputAudio; - -inputDocumentEmpty#72f0eaae = InputDocument; -inputDocument#18798952 id:long access_hash:long = InputDocument; - -inputAudioFileLocation#74dc404d id:long access_hash:long = InputFileLocation; -inputDocumentFileLocation#4e45abe9 id:long access_hash:long = InputFileLocation; - -audioEmpty#586988d8 id:long = Audio; -audio#c7ac6496 id:long access_hash:long user_id:int date:int duration:int mime_type:string size:int dc_id:int = Audio; - -documentEmpty#36f8c871 id:long = Document; -document#9efc6326 id:long access_hash:long user_id:int date:int file_name:string mime_type:string size:int thumb:PhotoSize dc_id:int = Document; - -help.support#17c6b5f6 phone_number:string user:User = help.Support; - -notifyPeer#9fd40bd8 peer:Peer = NotifyPeer; -notifyUsers#b4c83b4c = NotifyPeer; -notifyChats#c007cec3 = NotifyPeer; -notifyAll#74d07c60 = NotifyPeer; - -updateUserBlocked#80ece81a user_id:int blocked:Bool = Update; -updateNotifySettings#bec268ef peer:NotifyPeer notify_settings:PeerNotifySettings = Update; - -auth.sentAppCode#e325edcf phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -updateUserTyping#5c486927 user_id:int action:SendMessageAction = Update; -updateChatUserTyping#9a65ea1f chat_id:int user_id:int action:SendMessageAction = Update; - - -message#567699b3 flags:int id:int from_id:int to_id:Peer date:int message:string media:MessageMedia = Message; -messageForwarded#a367e716 flags:int id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer date:int message:string media:MessageMedia = Message; -messageService#1d86f70e flags:int id:int from_id:int to_id:Peer date:int action:MessageAction = Message; - - -sendMessageTypingAction#16bf744e = SendMessageAction; -sendMessageCancelAction#fd5ec8f5 = SendMessageAction; -sendMessageRecordVideoAction#a187d66f = SendMessageAction; -sendMessageUploadVideoAction#92042ff7 = SendMessageAction; -sendMessageRecordAudioAction#d52f73f7 = SendMessageAction; -sendMessageUploadAudioAction#e6ac8a6f = SendMessageAction; -sendMessageUploadPhotoAction#990a3c1a = SendMessageAction; -sendMessageUploadDocumentAction#8faee98e = SendMessageAction; -sendMessageGeoLocationAction#176f8ba1 = SendMessageAction; -sendMessageChooseContactAction#628cbc6f = SendMessageAction; - ----functions--- - -invokeAfterMsg#cb9f372d {X:Type} msg_id:long query:!X = X; - -invokeAfterMsgs#3dc4b4f0 {X:Type} msg_ids:Vector query:!X = X; - -auth.checkPhone#6fe51dfb phone_number:string = auth.CheckedPhone; -auth.sendCode#768d5f4d phone_number:string sms_type:int api_id:int api_hash:string lang_code:string = auth.SentCode; -auth.sendCall#3c51564 phone_number:string phone_code_hash:string = Bool; -auth.signUp#1b067634 phone_number:string phone_code_hash:string phone_code:string first_name:string last_name:string = auth.Authorization; -auth.signIn#bcd51581 phone_number:string phone_code_hash:string phone_code:string = auth.Authorization; -auth.logOut#5717da40 = Bool; -auth.resetAuthorizations#9fab0d1a = Bool; -auth.sendInvites#771c1d97 phone_numbers:Vector message:string = Bool; -auth.exportAuthorization#e5bfffcd dc_id:int = auth.ExportedAuthorization; -auth.importAuthorization#e3ef9613 id:int bytes:bytes = auth.Authorization; -auth.bindTempAuthKey#cdd42a05 perm_auth_key_id:long nonce:long expires_at:int encrypted_message:bytes = Bool; - -account.registerDevice#446c712c token_type:int token:string device_model:string system_version:string app_version:string app_sandbox:Bool lang_code:string = Bool; -account.unregisterDevice#65c55b40 token_type:int token:string = Bool; -account.updateNotifySettings#84be5b93 peer:InputNotifyPeer settings:InputPeerNotifySettings = Bool; -account.getNotifySettings#12b3ad31 peer:InputNotifyPeer = PeerNotifySettings; -account.resetNotifySettings#db7e1747 = Bool; -account.updateProfile#f0888d68 first_name:string last_name:string = User; -account.updateStatus#6628562c offline:Bool = Bool; -account.getWallPapers#c04cfac2 = Vector; - -users.getUsers#d91a548 id:Vector = Vector; -users.getFullUser#ca30a5b1 id:InputUser = UserFull; - -contacts.getStatuses#c4a353ee = Vector; -contacts.getContacts#22c6aa08 hash:string = contacts.Contacts; -contacts.importContacts#da30b32d contacts:Vector replace:Bool = contacts.ImportedContacts; -contacts.search#11f812d8 q:string limit:int = contacts.Found; -contacts.getSuggested#cd773428 limit:int = contacts.Suggested; -contacts.deleteContact#8e953744 id:InputUser = contacts.Link; -contacts.deleteContacts#59ab389e id:Vector = Bool; -contacts.block#332b49fc id:InputUser = Bool; -contacts.unblock#e54100bd id:InputUser = Bool; -contacts.getBlocked#f57c350f offset:int limit:int = contacts.Blocked; -contacts.exportCard#84e53737 = Vector; -contacts.importCard#4fe196fe export_card:Vector = User; - -messages.getMessages#4222fa74 id:Vector = messages.Messages; -messages.getDialogs#eccf1df6 offset:int max_id:int limit:int = messages.Dialogs; -messages.getHistory#92a1df2f peer:InputPeer offset:int max_id:int limit:int = messages.Messages; -messages.search#7e9f2ab peer:InputPeer q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = messages.Messages; -messages.readHistory#eed884c6 peer:InputPeer max_id:int offset:int read_contents:Bool = messages.AffectedHistory; -messages.deleteHistory#f4f8fb61 peer:InputPeer offset:int = messages.AffectedHistory; -messages.deleteMessages#14f2dd0a id:Vector = Vector; -messages.restoreMessages#395f9d7e id:Vector = Vector; -messages.receivedMessages#28abcb68 max_id:int = Vector; -messages.setTyping#a3825e50 peer:InputPeer action:SendMessageAction = Bool; -messages.sendMessage#4cde0aab peer:InputPeer message:string random_id:long = messages.SentMessage; -messages.sendMedia#a3c85d76 peer:InputPeer media:InputMedia random_id:long = messages.StatedMessage; -messages.forwardMessages#514cd10f peer:InputPeer id:Vector = messages.StatedMessages; -messages.getChats#3c6aa187 id:Vector = messages.Chats; -messages.getFullChat#3b831c66 chat_id:int = messages.ChatFull; -messages.editChatTitle#b4bc68b5 chat_id:int title:string = messages.StatedMessage; -messages.editChatPhoto#d881821d chat_id:int photo:InputChatPhoto = messages.StatedMessage; -messages.addChatUser#2ee9ee9e chat_id:int user_id:InputUser fwd_limit:int = messages.StatedMessage; -messages.deleteChatUser#c3c5cd23 chat_id:int user_id:InputUser = messages.StatedMessage; -messages.createChat#419d9aee users:Vector title:string = messages.StatedMessage; - -updates.getState#edd4882a = updates.State; -updates.getDifference#a041495 pts:int date:int qts:int = updates.Difference; - -photos.updateProfilePhoto#eef579a0 id:InputPhoto crop:InputPhotoCrop = UserProfilePhoto; -photos.uploadProfilePhoto#d50f9c88 file:InputFile caption:string geo_point:InputGeoPoint crop:InputPhotoCrop = photos.Photo; - -upload.saveFilePart#b304a621 file_id:long file_part:int bytes:bytes = Bool; -upload.getFile#e3a6cfb5 location:InputFileLocation offset:int limit:int = upload.File; - -help.getConfig#c4f9186b = Config; -help.getNearestDc#1fb33026 = NearestDc; -help.getAppUpdate#c812ac7e device_model:string system_version:string app_version:string lang_code:string = help.AppUpdate; -help.saveAppLog#6f02f748 events:Vector = Bool; -help.getInviteText#a4a95186 lang_code:string = help.InviteText; - -photos.getUserPhotos#b7ee553c user_id:InputUser offset:int max_id:int limit:int = photos.Photos; - -messages.forwardMessage#3f3f4f2 peer:InputPeer id:int random_id:long = messages.StatedMessage; -messages.sendBroadcast#41bb0972 contacts:Vector message:string media:InputMedia = messages.StatedMessages; - -geochats.getLocated#7f192d8f geo_point:InputGeoPoint radius:int limit:int = geochats.Located; -geochats.getRecents#e1427e6f offset:int limit:int = geochats.Messages; -geochats.checkin#55b3e8fb peer:InputGeoChat = geochats.StatedMessage; -geochats.getFullChat#6722dd6f peer:InputGeoChat = messages.ChatFull; -geochats.editChatTitle#4c8e2273 peer:InputGeoChat title:string address:string = geochats.StatedMessage; -geochats.editChatPhoto#35d81a95 peer:InputGeoChat photo:InputChatPhoto = geochats.StatedMessage; -geochats.search#cfcdc44d peer:InputGeoChat q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = geochats.Messages; -geochats.getHistory#b53f7a68 peer:InputGeoChat offset:int max_id:int limit:int = geochats.Messages; -geochats.setTyping#8b8a729 peer:InputGeoChat typing:Bool = Bool; -geochats.sendMessage#61b0044 peer:InputGeoChat message:string random_id:long = geochats.StatedMessage; -geochats.sendMedia#b8f0deff peer:InputGeoChat media:InputMedia random_id:long = geochats.StatedMessage; -geochats.createGeoChat#e092e16 title:string geo_point:InputGeoPoint address:string venue:string = geochats.StatedMessage; - -messages.getDhConfig#26cf8950 version:int random_length:int = messages.DhConfig; -messages.requestEncryption#f64daf43 user_id:InputUser random_id:int g_a:bytes = EncryptedChat; -messages.acceptEncryption#3dbc0415 peer:InputEncryptedChat g_b:bytes key_fingerprint:long = EncryptedChat; -messages.discardEncryption#edd923c5 chat_id:int = Bool; -messages.setEncryptedTyping#791451ed peer:InputEncryptedChat typing:Bool = Bool; -messages.readEncryptedHistory#7f4b690a peer:InputEncryptedChat max_date:int = Bool; -messages.sendEncrypted#a9776773 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.sendEncryptedFile#9a901b66 peer:InputEncryptedChat random_id:long data:bytes file:InputEncryptedFile = messages.SentEncryptedMessage; -messages.sendEncryptedService#32d439a4 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.receivedQueue#55a5bb66 max_qts:int = Vector; - -upload.saveBigFilePart#de7b673d file_id:long file_part:int file_total_parts:int bytes:bytes = Bool; - -initConnection#69796de9 {X:Type} api_id:int device_model:string system_version:string app_version:string lang_code:string query:!X = X; - -help.getSupport#9cdf08cd = help.Support; - -auth.sendSms#da9f3e8 phone_number:string phone_code_hash:string = Bool; - -messages.readMessageContents id:Vector = Vector; - - -invokeWithLayer17#50858a19 {X:Type} query:!X = X; - diff --git a/scheme18.tl b/scheme18.tl deleted file mode 100644 index 6b7fdd5..0000000 --- a/scheme18.tl +++ /dev/null @@ -1,535 +0,0 @@ -int ?= Int; -long ?= Long; -double ?= Double; -string ?= String; - -bytes string = Bytes; - -boolFalse#bc799737 = Bool; -boolTrue#997275b5 = Bool; - -vector#1cb5c415 {t:Type} # [ t ] = Vector t; - -error#c4b9f9bb code:int text:string = Error; - -null#56730bcc = Null; - -inputPeerEmpty#7f3b18ea = InputPeer; -inputPeerSelf#7da07ec9 = InputPeer; -inputPeerContact#1023dbe8 user_id:int = InputPeer; -inputPeerForeign#9b447325 user_id:int access_hash:long = InputPeer; -inputPeerChat#179be863 chat_id:int = InputPeer; - -inputUserEmpty#b98886cf = InputUser; -inputUserSelf#f7c1b13f = InputUser; -inputUserContact#86e94f65 user_id:int = InputUser; -inputUserForeign#655e74ff user_id:int access_hash:long = InputUser; - -inputPhoneContact#f392b7f4 client_id:long phone:string first_name:string last_name:string = InputContact; - -inputFile#f52ff27f id:long parts:int name:string md5_checksum:string = InputFile; - -inputMediaEmpty#9664f57f = InputMedia; -inputMediaUploadedPhoto#2dc53a7d file:InputFile = InputMedia; -inputMediaPhoto#8f2ab2ec id:InputPhoto = InputMedia; -inputMediaGeoPoint#f9c44144 geo_point:InputGeoPoint = InputMedia; -inputMediaContact#a6e45987 phone_number:string first_name:string last_name:string = InputMedia; -inputMediaUploadedVideo#133ad6f6 file:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaUploadedThumbVideo#9912dabf file:InputFile thumb:InputFile duration:int w:int h:int mime_type:string = InputMedia; -inputMediaVideo#7f023ae6 id:InputVideo = InputMedia; - -inputChatPhotoEmpty#1ca48f57 = InputChatPhoto; -inputChatUploadedPhoto#94254732 file:InputFile crop:InputPhotoCrop = InputChatPhoto; -inputChatPhoto#b2e1bf08 id:InputPhoto crop:InputPhotoCrop = InputChatPhoto; - -inputGeoPointEmpty#e4c123d6 = InputGeoPoint; -inputGeoPoint#f3b7acc9 lat:double long:double = InputGeoPoint; - -inputPhotoEmpty#1cd7bf0d = InputPhoto; -inputPhoto#fb95c6c4 id:long access_hash:long = InputPhoto; - -inputVideoEmpty#5508ec75 = InputVideo; -inputVideo#ee579652 id:long access_hash:long = InputVideo; - -inputFileLocation#14637196 volume_id:long local_id:int secret:long = InputFileLocation; -inputVideoFileLocation#3d0364ec id:long access_hash:long = InputFileLocation; - -inputPhotoCropAuto#ade6b004 = InputPhotoCrop; -inputPhotoCrop#d9915325 crop_left:double crop_top:double crop_width:double = InputPhotoCrop; - -inputAppEvent#770656a8 time:double type:string peer:long data:string = InputAppEvent; - -peerUser#9db1bc6d user_id:int = Peer; -peerChat#bad0e5bb chat_id:int = Peer; - -storage.fileUnknown#aa963b05 = storage.FileType; -storage.fileJpeg#7efe0e = storage.FileType; -storage.fileGif#cae1aadf = storage.FileType; -storage.filePng#a4f63c0 = storage.FileType; -storage.filePdf#ae1e508d = storage.FileType; -storage.fileMp3#528a0677 = storage.FileType; -storage.fileMov#4b09ebbc = storage.FileType; -storage.filePartial#40bc6f52 = storage.FileType; -storage.fileMp4#b3cea0e4 = storage.FileType; -storage.fileWebp#1081464c = storage.FileType; - -fileLocationUnavailable#7c596b46 volume_id:long local_id:int secret:long = FileLocation; -fileLocation#53d69076 dc_id:int volume_id:long local_id:int secret:long = FileLocation; - -userEmpty#200250ba id:int = User; -userSelf#7007b451 id:int first_name:string last_name:string username:string phone:string photo:UserProfilePhoto status:UserStatus inactive:Bool = User; -userContact#cab35e18 id:int first_name:string last_name:string username:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userRequest#d9ccc4ef id:int first_name:string last_name:string username:string access_hash:long phone:string photo:UserProfilePhoto status:UserStatus = User; -userForeign#75cf7a8 id:int first_name:string last_name:string username:string access_hash:long photo:UserProfilePhoto status:UserStatus = User; -userDeleted#d6016d7a id:int first_name:string last_name:string username:string = User; - - -userProfilePhotoEmpty#4f11bae1 = UserProfilePhoto; -userProfilePhoto#d559d8c8 photo_id:long photo_small:FileLocation photo_big:FileLocation = UserProfilePhoto; - -userStatusEmpty#9d05049 = UserStatus; -userStatusOnline#edb93949 expires:int = UserStatus; -userStatusOffline#8c703f was_online:int = UserStatus; - -chatEmpty#9ba2d800 id:int = Chat; -chat#6e9c9bc7 id:int title:string photo:ChatPhoto participants_count:int date:int left:Bool version:int = Chat; -chatForbidden#fb0ccc41 id:int title:string date:int = Chat; - -chatFull#630e61be id:int participants:ChatParticipants chat_photo:Photo notify_settings:PeerNotifySettings = ChatFull; - -chatParticipant#c8d7493e user_id:int inviter_id:int date:int = ChatParticipant; - -chatParticipantsForbidden#fd2bb8a chat_id:int = ChatParticipants; -chatParticipants#7841b415 chat_id:int admin_id:int participants:Vector version:int = ChatParticipants; - -chatPhotoEmpty#37c1011c = ChatPhoto; -chatPhoto#6153276a photo_small:FileLocation photo_big:FileLocation = ChatPhoto; - -messageEmpty#83e5de54 id:int = Message; -//message#22eb6aba id:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -//messageForwarded#5f46804 id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer out:Bool unread:Bool date:int message:string media:MessageMedia = Message; -//messageService#9f8d60bb id:int from_id:int to_id:Peer out:Bool unread:Bool date:int action:MessageAction = Message; - -messageMediaEmpty#3ded6320 = MessageMedia; -messageMediaPhoto#c8c45a2a photo:Photo = MessageMedia; -messageMediaVideo#a2d24290 video:Video = MessageMedia; -messageMediaGeo#56e0d474 geo:GeoPoint = MessageMedia; -messageMediaContact#5e7d2f39 phone_number:string first_name:string last_name:string user_id:int = MessageMedia; -messageMediaUnsupported#29632a36 bytes:bytes = MessageMedia; - -messageActionEmpty#b6aef7b0 = MessageAction; -messageActionChatCreate#a6638b9a title:string users:Vector = MessageAction; -messageActionChatEditTitle#b5a1ce5a title:string = MessageAction; -messageActionChatEditPhoto#7fcb13a8 photo:Photo = MessageAction; -messageActionChatDeletePhoto#95e3fbef = MessageAction; -messageActionChatAddUser#5e3cfc4b user_id:int = MessageAction; -messageActionChatDeleteUser#b2ae9b0c user_id:int = MessageAction; - -dialog#ab3a99ac peer:Peer top_message:int unread_count:int notify_settings:PeerNotifySettings = Dialog; - -photoEmpty#2331b22d id:long = Photo; -photo#22b56751 id:long access_hash:long user_id:int date:int caption:string geo:GeoPoint sizes:Vector = Photo; - -photoSizeEmpty#e17e23c type:string = PhotoSize; -photoSize#77bfb61b type:string location:FileLocation w:int h:int size:int = PhotoSize; -photoCachedSize#e9a734fa type:string location:FileLocation w:int h:int bytes:bytes = PhotoSize; - -videoEmpty#c10658a8 id:long = Video; -video#388fa391 id:long access_hash:long user_id:int date:int caption:string duration:int mime_type:string size:int thumb:PhotoSize dc_id:int w:int h:int = Video; - -geoPointEmpty#1117dd5f = GeoPoint; -geoPoint#2049d70c long:double lat:double = GeoPoint; - -auth.checkedPhone#e300cc3b phone_registered:Bool phone_invited:Bool = auth.CheckedPhone; - -auth.sentCode#efed51d9 phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -auth.authorization#f6b673a4 expires:int user:User = auth.Authorization; - -auth.exportedAuthorization#df969c2d id:int bytes:bytes = auth.ExportedAuthorization; - -inputNotifyPeer#b8bc5b0c peer:InputPeer = InputNotifyPeer; -inputNotifyUsers#193b4417 = InputNotifyPeer; -inputNotifyChats#4a95e84e = InputNotifyPeer; -inputNotifyAll#a429b886 = InputNotifyPeer; - -inputPeerNotifyEventsEmpty#f03064d8 = InputPeerNotifyEvents; -inputPeerNotifyEventsAll#e86a2c74 = InputPeerNotifyEvents; - -inputPeerNotifySettings#46a2ce98 mute_until:int sound:string show_previews:Bool events_mask:int = InputPeerNotifySettings; - -peerNotifyEventsEmpty#add53cb3 = PeerNotifyEvents; -peerNotifyEventsAll#6d1ded88 = PeerNotifyEvents; - -peerNotifySettingsEmpty#70a68512 = PeerNotifySettings; -peerNotifySettings#8d5e11ee mute_until:int sound:string show_previews:Bool events_mask:int = PeerNotifySettings; - -wallPaper#ccb03657 id:int title:string sizes:Vector color:int = WallPaper; - -userFull#771095da user:User link:contacts.Link profile_photo:Photo notify_settings:PeerNotifySettings blocked:Bool real_first_name:string real_last_name:string = UserFull; - -contact#f911c994 user_id:int mutual:Bool = Contact; - -importedContact#d0028438 user_id:int client_id:long = ImportedContact; - -contactBlocked#561bc879 user_id:int date:int = ContactBlocked; - -contactFound#ea879f95 user_id:int = ContactFound; - -contactSuggested#3de191a1 user_id:int mutual_contacts:int = ContactSuggested; - -contactStatus#aa77b873 user_id:int expires:int = ContactStatus; - -chatLocated#3631cf4c chat_id:int distance:int = ChatLocated; - -contacts.foreignLinkUnknown#133421f8 = contacts.ForeignLink; -contacts.foreignLinkRequested#a7801f47 has_phone:Bool = contacts.ForeignLink; -contacts.foreignLinkMutual#1bea8ce1 = contacts.ForeignLink; - -contacts.myLinkEmpty#d22a1c60 = contacts.MyLink; -contacts.myLinkRequested#6c69efee contact:Bool = contacts.MyLink; -contacts.myLinkContact#c240ebd9 = contacts.MyLink; - -contacts.link#eccea3f5 my_link:contacts.MyLink foreign_link:contacts.ForeignLink user:User = contacts.Link; - -contacts.contacts#6f8b8cb2 contacts:Vector users:Vector = contacts.Contacts; -contacts.contactsNotModified#b74ba9d2 = contacts.Contacts; - -contacts.importedContacts#ad524315 imported:Vector retry_contacts:Vector users:Vector = contacts.ImportedContacts; - -contacts.blocked#1c138d15 blocked:Vector users:Vector = contacts.Blocked; -contacts.blockedSlice#900802a1 count:int blocked:Vector users:Vector = contacts.Blocked; - -contacts.found#566000e results:Vector users:Vector = contacts.Found; - -contacts.suggested#5649dcc5 results:Vector users:Vector = contacts.Suggested; - -messages.dialogs#15ba6c40 dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; -messages.dialogsSlice#71e094f3 count:int dialogs:Vector messages:Vector chats:Vector users:Vector = messages.Dialogs; - -messages.messages#8c718e87 messages:Vector chats:Vector users:Vector = messages.Messages; -messages.messagesSlice#b446ae3 count:int messages:Vector chats:Vector users:Vector = messages.Messages; - -messages.messageEmpty#3f4e0648 = messages.Message; -messages.message#ff90c417 message:Message chats:Vector users:Vector = messages.Message; - -messages.statedMessages#969478bb messages:Vector chats:Vector users:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessage#d07ae726 message:Message chats:Vector users:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessage#d1f4d35c id:int date:int pts:int seq:int = messages.SentMessage; - -messages.chat#40e9002a chat:Chat users:Vector = messages.Chat; - -messages.chats#8150cbd8 chats:Vector users:Vector = messages.Chats; - -messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector users:Vector = messages.ChatFull; - -messages.affectedHistory#b7de36f2 pts:int seq:int offset:int = messages.AffectedHistory; - -inputMessagesFilterEmpty#57e2f66c = MessagesFilter; -inputMessagesFilterPhotos#9609a51c = MessagesFilter; -inputMessagesFilterVideo#9fc00e65 = MessagesFilter; -inputMessagesFilterPhotoVideo#56e9f0e4 = MessagesFilter; -inputMessagesFilterDocument#9eddf188 = MessagesFilter; -inputMessagesFilterAudio#cfc87522 = MessagesFilter; - -updateNewMessage#13abdb3 message:Message pts:int = Update; -updateMessageID#4e90bfd6 id:int random_id:long = Update; -updateReadMessages#c6649e31 messages:Vector pts:int = Update; -updateDeleteMessages#a92bfe26 messages:Vector pts:int = Update; -updateRestoreMessages#d15de04d messages:Vector pts:int = Update; -//updateUserTyping#6baa8508 user_id:int = Update; -//updateChatUserTyping#3c46cfe6 chat_id:int user_id:int = Update; -updateChatParticipants#7761198 participants:ChatParticipants = Update; -updateUserStatus#1bfbd823 user_id:int status:UserStatus = Update; -updateUserPhoto#95313b0c user_id:int date:int photo:UserProfilePhoto previous:Bool = Update; -updateContactRegistered#2575bbb9 user_id:int date:int = Update; -updateContactLink#51a48a9a user_id:int my_link:contacts.MyLink foreign_link:contacts.ForeignLink = Update; -updateActivation#6f690963 user_id:int = Update; -updateNewAuthorization#8f06529a auth_key_id:long date:int device:string location:string = Update; - -updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State; - -updates.differenceEmpty#5d75a138 date:int seq:int = updates.Difference; -updates.difference#f49ca0 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector state:updates.State = updates.Difference; -updates.differenceSlice#a8fb1981 new_messages:Vector new_encrypted_messages:Vector other_updates:Vector chats:Vector users:Vector intermediate_state:updates.State = updates.Difference; - -updatesTooLong#e317af7e = Updates; -updateShortMessage#d3f45784 id:int from_id:int message:string pts:int date:int seq:int = Updates; -updateShortChatMessage#2b2fbd4e id:int from_id:int chat_id:int message:string pts:int date:int seq:int = Updates; -updateShort#78d4dec1 update:Update date:int = Updates; -updatesCombined#725b04c3 updates:Vector users:Vector chats:Vector date:int seq_start:int seq:int = Updates; -updates#74ae4240 updates:Vector users:Vector chats:Vector date:int seq:int = Updates; - -photos.photos#8dca6aa5 photos:Vector users:Vector = photos.Photos; -photos.photosSlice#15051f54 count:int photos:Vector users:Vector = photos.Photos; - -photos.photo#20212ca8 photo:Photo users:Vector = photos.Photo; - -upload.file#96a18d5 type:storage.FileType mtime:int bytes:bytes = upload.File; - -dcOption#2ec2a43c id:int hostname:string ip_address:string port:int = DcOption; - -config#2e54dd74 date:int test_mode:Bool this_dc:int dc_options:Vector chat_size_max:int broadcast_size_max:int = Config; - -nearestDc#8e1a1775 country:string this_dc:int nearest_dc:int = NearestDc; - -help.appUpdate#8987f311 id:int critical:Bool url:string text:string = help.AppUpdate; -help.noAppUpdate#c45a6536 = help.AppUpdate; - -help.inviteText#18cb9f78 message:string = help.InviteText; - -messages.statedMessagesLinks#3e74f5c6 messages:Vector chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessages; - -messages.statedMessageLink#a9af2881 message:Message chats:Vector users:Vector links:Vector pts:int seq:int = messages.StatedMessage; - -messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector = messages.SentMessage; - -inputGeoChat#74d456fa chat_id:int access_hash:long = InputGeoChat; - -inputNotifyGeoChatPeer#4d8ddec8 peer:InputGeoChat = InputNotifyPeer; - -geoChat#75eaea5a id:int access_hash:long title:string address:string venue:string geo:GeoPoint photo:ChatPhoto participants_count:int date:int checked_in:Bool version:int = Chat; - -geoChatMessageEmpty#60311a9b chat_id:int id:int = GeoChatMessage; -geoChatMessage#4505f8e1 chat_id:int id:int from_id:int date:int message:string media:MessageMedia = GeoChatMessage; -geoChatMessageService#d34fa24e chat_id:int id:int from_id:int date:int action:MessageAction = GeoChatMessage; - -geochats.statedMessage#17b1578b message:GeoChatMessage chats:Vector users:Vector seq:int = geochats.StatedMessage; - -geochats.located#48feb267 results:Vector messages:Vector chats:Vector users:Vector = geochats.Located; - -geochats.messages#d1526db1 messages:Vector chats:Vector users:Vector = geochats.Messages; -geochats.messagesSlice#bc5863e8 count:int messages:Vector chats:Vector users:Vector = geochats.Messages; - -messageActionGeoChatCreate#6f038ebc title:string address:string = MessageAction; -messageActionGeoChatCheckin#c7d53de = MessageAction; - -updateNewGeoChatMessage#5a68e3f7 message:GeoChatMessage = Update; - -wallPaperSolid#63117f24 id:int title:string bg_color:int color:int = WallPaper; - -updateNewEncryptedMessage#12bcbd9a message:EncryptedMessage qts:int = Update; -updateEncryptedChatTyping#1710f156 chat_id:int = Update; -updateEncryption#b4a2e88d chat:EncryptedChat date:int = Update; -updateEncryptedMessagesRead#38fe25b7 chat_id:int max_date:int date:int = Update; - -encryptedChatEmpty#ab7ec0a0 id:int = EncryptedChat; -encryptedChatWaiting#3bf703dc id:int access_hash:long date:int admin_id:int participant_id:int = EncryptedChat; -encryptedChatRequested#c878527e id:int access_hash:long date:int admin_id:int participant_id:int g_a:bytes = EncryptedChat; -encryptedChat#fa56ce36 id:int access_hash:long date:int admin_id:int participant_id:int g_a_or_b:bytes key_fingerprint:long = EncryptedChat; -encryptedChatDiscarded#13d6dd27 id:int = EncryptedChat; - -inputEncryptedChat#f141b5e1 chat_id:int access_hash:long = InputEncryptedChat; - -encryptedFileEmpty#c21f497e = EncryptedFile; -encryptedFile#4a70994c id:long access_hash:long size:int dc_id:int key_fingerprint:int = EncryptedFile; - -inputEncryptedFileEmpty#1837c364 = InputEncryptedFile; -inputEncryptedFileUploaded#64bd0306 id:long parts:int md5_checksum:string key_fingerprint:int = InputEncryptedFile; -inputEncryptedFile#5a17b5e5 id:long access_hash:long = InputEncryptedFile; - -inputEncryptedFileLocation#f5235d55 id:long access_hash:long = InputFileLocation; - -encryptedMessage#ed18c118 random_id:long chat_id:int date:int bytes:bytes file:EncryptedFile = EncryptedMessage; -encryptedMessageService#23734b06 random_id:long chat_id:int date:int bytes:bytes = EncryptedMessage; - -messages.dhConfigNotModified#c0e24635 random:bytes = messages.DhConfig; -messages.dhConfig#2c221edd g:int p:bytes version:int random:bytes = messages.DhConfig; - -messages.sentEncryptedMessage#560f8935 date:int = messages.SentEncryptedMessage; -messages.sentEncryptedFile#9493ff32 date:int file:EncryptedFile = messages.SentEncryptedMessage; - -inputFileBig#fa4f0bb5 id:long parts:int name:string = InputFile; - -inputEncryptedFileBigUploaded#2dc173c8 id:long parts:int key_fingerprint:int = InputEncryptedFile; - -updateChatParticipantAdd#3a0eeb22 chat_id:int user_id:int inviter_id:int version:int = Update; -updateChatParticipantDelete#6e5f8c22 chat_id:int user_id:int version:int = Update; -updateDcOptions#8e5e9873 dc_options:Vector = Update; - -inputMediaUploadedAudio#4e498cab file:InputFile duration:int mime_type:string = InputMedia; -inputMediaAudio#89938781 id:InputAudio = InputMedia; -inputMediaUploadedDocument#34e794bd file:InputFile file_name:string mime_type:string = InputMedia; -inputMediaUploadedThumbDocument#3e46de5d file:InputFile thumb:InputFile file_name:string mime_type:string = InputMedia; -inputMediaDocument#d184e841 id:InputDocument = InputMedia; - -messageMediaDocument#2fda2204 document:Document = MessageMedia; -messageMediaAudio#c6b68300 audio:Audio = MessageMedia; - -inputAudioEmpty#d95adc84 = InputAudio; -inputAudio#77d440ff id:long access_hash:long = InputAudio; - -inputDocumentEmpty#72f0eaae = InputDocument; -inputDocument#18798952 id:long access_hash:long = InputDocument; - -inputAudioFileLocation#74dc404d id:long access_hash:long = InputFileLocation; -inputDocumentFileLocation#4e45abe9 id:long access_hash:long = InputFileLocation; - -audioEmpty#586988d8 id:long = Audio; -audio#c7ac6496 id:long access_hash:long user_id:int date:int duration:int mime_type:string size:int dc_id:int = Audio; - -documentEmpty#36f8c871 id:long = Document; -document#9efc6326 id:long access_hash:long user_id:int date:int file_name:string mime_type:string size:int thumb:PhotoSize dc_id:int = Document; - -help.support#17c6b5f6 phone_number:string user:User = help.Support; - -notifyPeer#9fd40bd8 peer:Peer = NotifyPeer; -notifyUsers#b4c83b4c = NotifyPeer; -notifyChats#c007cec3 = NotifyPeer; -notifyAll#74d07c60 = NotifyPeer; - -updateUserBlocked#80ece81a user_id:int blocked:Bool = Update; -updateNotifySettings#bec268ef peer:NotifyPeer notify_settings:PeerNotifySettings = Update; - -auth.sentAppCode#e325edcf phone_registered:Bool phone_code_hash:string send_call_timeout:int is_password:Bool = auth.SentCode; - -updateUserTyping#5c486927 user_id:int action:SendMessageAction = Update; -updateChatUserTyping#9a65ea1f chat_id:int user_id:int action:SendMessageAction = Update; - -updateUserName user_id:int first_name:string last_name:string username:string = Update; -updateServiceNotification type:string message:string media:MessageMedia popup:Bool = Update; - -message#567699b3 flags:int id:int from_id:int to_id:Peer date:int message:string media:MessageMedia = Message; -messageForwarded#a367e716 flags:int id:int fwd_from_id:int fwd_date:int from_id:int to_id:Peer date:int message:string media:MessageMedia = Message; -messageService#1d86f70e flags:int id:int from_id:int to_id:Peer date:int action:MessageAction = Message; - - -sendMessageTypingAction#16bf744e = SendMessageAction; -sendMessageCancelAction#fd5ec8f5 = SendMessageAction; -sendMessageRecordVideoAction#a187d66f = SendMessageAction; -sendMessageUploadVideoAction#92042ff7 = SendMessageAction; -sendMessageRecordAudioAction#d52f73f7 = SendMessageAction; -sendMessageUploadAudioAction#e6ac8a6f = SendMessageAction; -sendMessageUploadPhotoAction#990a3c1a = SendMessageAction; -sendMessageUploadDocumentAction#8faee98e = SendMessageAction; -sendMessageGeoLocationAction#176f8ba1 = SendMessageAction; -sendMessageChooseContactAction#628cbc6f = SendMessageAction; - ----functions--- - -invokeAfterMsg#cb9f372d {X:Type} msg_id:long query:!X = X; - -invokeAfterMsgs#3dc4b4f0 {X:Type} msg_ids:Vector query:!X = X; - -auth.checkPhone#6fe51dfb phone_number:string = auth.CheckedPhone; -auth.sendCode#768d5f4d phone_number:string sms_type:int api_id:int api_hash:string lang_code:string = auth.SentCode; -auth.sendCall#3c51564 phone_number:string phone_code_hash:string = Bool; -auth.signUp#1b067634 phone_number:string phone_code_hash:string phone_code:string first_name:string last_name:string = auth.Authorization; -auth.signIn#bcd51581 phone_number:string phone_code_hash:string phone_code:string = auth.Authorization; -auth.logOut#5717da40 = Bool; -auth.resetAuthorizations#9fab0d1a = Bool; -auth.sendInvites#771c1d97 phone_numbers:Vector message:string = Bool; -auth.exportAuthorization#e5bfffcd dc_id:int = auth.ExportedAuthorization; -auth.importAuthorization#e3ef9613 id:int bytes:bytes = auth.Authorization; -auth.bindTempAuthKey#cdd42a05 perm_auth_key_id:long nonce:long expires_at:int encrypted_message:bytes = Bool; - -account.registerDevice#446c712c token_type:int token:string device_model:string system_version:string app_version:string app_sandbox:Bool lang_code:string = Bool; -account.unregisterDevice#65c55b40 token_type:int token:string = Bool; -account.updateNotifySettings#84be5b93 peer:InputNotifyPeer settings:InputPeerNotifySettings = Bool; -account.getNotifySettings#12b3ad31 peer:InputNotifyPeer = PeerNotifySettings; -account.resetNotifySettings#db7e1747 = Bool; -account.updateProfile#f0888d68 first_name:string last_name:string = User; -account.updateStatus#6628562c offline:Bool = Bool; -account.getWallPapers#c04cfac2 = Vector; - -users.getUsers#d91a548 id:Vector = Vector; -users.getFullUser#ca30a5b1 id:InputUser = UserFull; - -contacts.getStatuses#c4a353ee = Vector; -contacts.getContacts#22c6aa08 hash:string = contacts.Contacts; -contacts.importContacts#da30b32d contacts:Vector replace:Bool = contacts.ImportedContacts; -contacts.getSuggested#cd773428 limit:int = contacts.Suggested; -contacts.deleteContact#8e953744 id:InputUser = contacts.Link; -contacts.deleteContacts#59ab389e id:Vector = Bool; -contacts.block#332b49fc id:InputUser = Bool; -contacts.unblock#e54100bd id:InputUser = Bool; -contacts.getBlocked#f57c350f offset:int limit:int = contacts.Blocked; -contacts.exportCard#84e53737 = Vector; -contacts.importCard#4fe196fe export_card:Vector = User; - -messages.getMessages#4222fa74 id:Vector = messages.Messages; -messages.getDialogs#eccf1df6 offset:int max_id:int limit:int = messages.Dialogs; -messages.getHistory#92a1df2f peer:InputPeer offset:int max_id:int limit:int = messages.Messages; -messages.search#7e9f2ab peer:InputPeer q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = messages.Messages; -messages.readHistory#eed884c6 peer:InputPeer max_id:int offset:int read_contents:Bool = messages.AffectedHistory; -messages.deleteHistory#f4f8fb61 peer:InputPeer offset:int = messages.AffectedHistory; -messages.deleteMessages#14f2dd0a id:Vector = Vector; -messages.restoreMessages#395f9d7e id:Vector = Vector; -messages.receivedMessages#28abcb68 max_id:int = Vector; -messages.setTyping#a3825e50 peer:InputPeer action:SendMessageAction = Bool; -messages.sendMessage#4cde0aab peer:InputPeer message:string random_id:long = messages.SentMessage; -messages.sendMedia#a3c85d76 peer:InputPeer media:InputMedia random_id:long = messages.StatedMessage; -messages.forwardMessages#514cd10f peer:InputPeer id:Vector = messages.StatedMessages; -messages.getChats#3c6aa187 id:Vector = messages.Chats; -messages.getFullChat#3b831c66 chat_id:int = messages.ChatFull; -messages.editChatTitle#b4bc68b5 chat_id:int title:string = messages.StatedMessage; -messages.editChatPhoto#d881821d chat_id:int photo:InputChatPhoto = messages.StatedMessage; -messages.addChatUser#2ee9ee9e chat_id:int user_id:InputUser fwd_limit:int = messages.StatedMessage; -messages.deleteChatUser#c3c5cd23 chat_id:int user_id:InputUser = messages.StatedMessage; -messages.createChat#419d9aee users:Vector title:string = messages.StatedMessage; - -updates.getState#edd4882a = updates.State; -updates.getDifference#a041495 pts:int date:int qts:int = updates.Difference; - -photos.updateProfilePhoto#eef579a0 id:InputPhoto crop:InputPhotoCrop = UserProfilePhoto; -photos.uploadProfilePhoto#d50f9c88 file:InputFile caption:string geo_point:InputGeoPoint crop:InputPhotoCrop = photos.Photo; - -upload.saveFilePart#b304a621 file_id:long file_part:int bytes:bytes = Bool; -upload.getFile#e3a6cfb5 location:InputFileLocation offset:int limit:int = upload.File; - -help.getConfig#c4f9186b = Config; -help.getNearestDc#1fb33026 = NearestDc; -help.getAppUpdate#c812ac7e device_model:string system_version:string app_version:string lang_code:string = help.AppUpdate; -help.saveAppLog#6f02f748 events:Vector = Bool; -help.getInviteText#a4a95186 lang_code:string = help.InviteText; - -photos.getUserPhotos#b7ee553c user_id:InputUser offset:int max_id:int limit:int = photos.Photos; - -messages.forwardMessage#3f3f4f2 peer:InputPeer id:int random_id:long = messages.StatedMessage; -messages.sendBroadcast#41bb0972 contacts:Vector message:string media:InputMedia = messages.StatedMessages; - -geochats.getLocated#7f192d8f geo_point:InputGeoPoint radius:int limit:int = geochats.Located; -geochats.getRecents#e1427e6f offset:int limit:int = geochats.Messages; -geochats.checkin#55b3e8fb peer:InputGeoChat = geochats.StatedMessage; -geochats.getFullChat#6722dd6f peer:InputGeoChat = messages.ChatFull; -geochats.editChatTitle#4c8e2273 peer:InputGeoChat title:string address:string = geochats.StatedMessage; -geochats.editChatPhoto#35d81a95 peer:InputGeoChat photo:InputChatPhoto = geochats.StatedMessage; -geochats.search#cfcdc44d peer:InputGeoChat q:string filter:MessagesFilter min_date:int max_date:int offset:int max_id:int limit:int = geochats.Messages; -geochats.getHistory#b53f7a68 peer:InputGeoChat offset:int max_id:int limit:int = geochats.Messages; -geochats.setTyping#8b8a729 peer:InputGeoChat typing:Bool = Bool; -geochats.sendMessage#61b0044 peer:InputGeoChat message:string random_id:long = geochats.StatedMessage; -geochats.sendMedia#b8f0deff peer:InputGeoChat media:InputMedia random_id:long = geochats.StatedMessage; -geochats.createGeoChat#e092e16 title:string geo_point:InputGeoPoint address:string venue:string = geochats.StatedMessage; - -messages.getDhConfig#26cf8950 version:int random_length:int = messages.DhConfig; -messages.requestEncryption#f64daf43 user_id:InputUser random_id:int g_a:bytes = EncryptedChat; -messages.acceptEncryption#3dbc0415 peer:InputEncryptedChat g_b:bytes key_fingerprint:long = EncryptedChat; -messages.discardEncryption#edd923c5 chat_id:int = Bool; -messages.setEncryptedTyping#791451ed peer:InputEncryptedChat typing:Bool = Bool; -messages.readEncryptedHistory#7f4b690a peer:InputEncryptedChat max_date:int = Bool; -messages.sendEncrypted#a9776773 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.sendEncryptedFile#9a901b66 peer:InputEncryptedChat random_id:long data:bytes file:InputEncryptedFile = messages.SentEncryptedMessage; -messages.sendEncryptedService#32d439a4 peer:InputEncryptedChat random_id:long data:bytes = messages.SentEncryptedMessage; -messages.receivedQueue#55a5bb66 max_qts:int = Vector; - -upload.saveBigFilePart#de7b673d file_id:long file_part:int file_total_parts:int bytes:bytes = Bool; - -initConnection#69796de9 {X:Type} api_id:int device_model:string system_version:string app_version:string lang_code:string query:!X = X; - -help.getSupport#9cdf08cd = help.Support; - -auth.sendSms#da9f3e8 phone_number:string phone_code_hash:string = Bool; - -messages.readMessageContents id:Vector = Vector; - - -account.checkUsername username:string = Bool; -account.updateUsername username:string = User; - -contacts.search q:string limit:int = contacts.Found; - -//invokeWithLayer18 {X:Type} query:!X = X; -invokeWithLayer18#1c900537 {X:Type} query:!X = X; - diff --git a/structures.c b/structures.c deleted file mode 100644 index 632625b..0000000 --- a/structures.c +++ /dev/null @@ -1,2039 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include "structures.h" -#include "mtproto-common.h" -//#include "telegram.h" -#include "tree.h" -#include -#include -#include -#include "queries.h" -#include "binlog.h" -#include "updates.h" -#include "mtproto-client.h" - -#include "tgl.h" - -#define sha1 SHA1 - -static int id_cmp (struct tgl_message *M1, struct tgl_message *M2); -#define peer_cmp(a,b) (tgl_cmp_peer_id (a->id, b->id)) -#define peer_cmp_name(a,b) (strcmp (a->print_name, b->print_name)) -DEFINE_TREE(peer,tgl_peer_t *,peer_cmp,0) -DEFINE_TREE(peer_by_name,tgl_peer_t *,peer_cmp_name,0) -DEFINE_TREE(message,struct tgl_message *,id_cmp,0) - - - - - - - -char *tgls_default_create_print_name (struct tgl_state *TLS, tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4) { - const char *d[4]; - d[0] = a1; d[1] = a2; d[2] = a3; d[3] = a4; - static char buf[10000]; - buf[0] = 0; - int i; - int p = 0; - for (i = 0; i < 4; i++) { - if (d[i] && strlen (d[i])) { - p += tsnprintf (buf + p, 9999 - p, "%s%s", p ? "_" : "", d[i]); - assert (p < 9990); - } - } - char *s = buf; - while (*s) { - if (((unsigned char)*s) <= ' ') { *s = '_'; } - if (*s == '#') { *s = '@'; } - s++; - } - s = buf; - int fl = strlen (s); - int cc = 0; - while (1) { - tgl_peer_t *P = tgl_peer_get_by_name (TLS, s); - if (!P || !tgl_cmp_peer_id (P->id, id)) { - break; - } - cc ++; - assert (cc <= 9999); - tsnprintf (s + fl, 9999 - fl, "#%d", cc); - } - return tstrdup (s); -} - -enum tgl_typing_status tglf_fetch_typing (void) { - switch (fetch_int ()) { - case CODE_send_message_typing_action: - return tgl_typing_typing; - case CODE_send_message_cancel_action: - return tgl_typing_cancel; - case CODE_send_message_record_video_action: - return tgl_typing_record_video; - case CODE_send_message_upload_video_action: - return tgl_typing_upload_video; - case CODE_send_message_record_audio_action: - return tgl_typing_record_audio; - case CODE_send_message_upload_audio_action: - return tgl_typing_upload_audio; - case CODE_send_message_upload_photo_action: - return tgl_typing_upload_photo; - case CODE_send_message_upload_document_action: - return tgl_typing_upload_document; - case CODE_send_message_geo_location_action: - return tgl_typing_geo; - case CODE_send_message_choose_contact_action: - return tgl_typing_choose_contact; - default: - assert (0); - return tgl_typing_none; - } -} - -/* {{{ Fetch */ - -int tglf_fetch_file_location (struct tgl_state *TLS, struct tgl_file_location *loc) { - int x = fetch_int (); - assert (x == CODE_file_location_unavailable || x == CODE_file_location); - - if (x == CODE_file_location_unavailable) { - loc->dc = -1; - loc->volume = fetch_long (); - loc->local_id = fetch_int (); - loc->secret = fetch_long (); - } else { - loc->dc = fetch_int (); - loc->volume = fetch_long (); - loc->local_id = fetch_int (); - loc->secret = fetch_long (); - } - return 0; -} - -int tglf_fetch_user_status (struct tgl_state *TLS, struct tgl_user_status *S, struct tgl_user *U) { - unsigned x = fetch_int (); - assert (x == CODE_user_status_empty || x == CODE_user_status_online || x == CODE_user_status_offline); - switch (x) { - case CODE_user_status_empty: - if (S->online) { - tgl_insert_status_update (TLS, U); - tgl_remove_status_expire (TLS, U); - } - S->online = 0; - S->when = 0; - break; - case CODE_user_status_online: - { - int when = fetch_int (); - if (S->online != 1) { - tgl_insert_status_update (TLS, U); - tgl_insert_status_expire (TLS, U); - S->online = 1; - } else { - if (when != S->when) { - tgl_remove_status_expire (TLS, U); - tgl_insert_status_expire (TLS, U); - } - } - } - break; - case CODE_user_status_offline: - if (S->online != -1) { - tgl_insert_status_update (TLS, U); - if (S->online == 1) { - tgl_remove_status_expire (TLS, U); - } - } - S->online = -1; - S->when = fetch_int (); - break; - default: - assert (0); - } - return 0; -} - -long long tglf_fetch_user_photo (struct tgl_state *TLS, struct tgl_user *U) { - unsigned x = fetch_int (); - assert (x == CODE_user_profile_photo || x == CODE_user_profile_photo_old || x == CODE_user_profile_photo_empty); - if (x == CODE_user_profile_photo_empty) { - bl_do_set_user_profile_photo (TLS, U, 0, 0, 0); - return 0; - } - long long photo_id = 1; - if (x == CODE_user_profile_photo) { - photo_id = fetch_long (); - } - static struct tgl_file_location big; - static struct tgl_file_location small; - assert (tglf_fetch_file_location (TLS, &small) >= 0); - assert (tglf_fetch_file_location (TLS, &big) >= 0); - - bl_do_set_user_profile_photo (TLS, U, photo_id, &big, &small); - return 0; -} - -int tglf_fetch_user (struct tgl_state *TLS, struct tgl_user *U) { - unsigned x = fetch_int (); - assert (x == CODE_user_empty || x == CODE_user_self || x == CODE_user_contact || x == CODE_user_request || x == CODE_user_foreign || x == CODE_user_deleted); - U->id = TGL_MK_USER (fetch_int ()); - if (x == CODE_user_empty) { - return 0; - } - - if (x == CODE_user_self) { - bl_do_set_our_id (TLS, tgl_get_peer_id (U->id)); - } - - int new = !(U->flags & FLAG_CREATED); - if (new) { - int l1 = prefetch_strlen (); - assert (l1 >= 0); - char *s1 = fetch_str (l1); - int l2 = prefetch_strlen (); - assert (l2 >= 0); - char *s2 = fetch_str (l2); - - int l3 = prefetch_strlen (); - char *s3 = fetch_str (l3); - - if (x == CODE_user_deleted && !(U->flags & FLAG_DELETED)) { - bl_do_user_add (TLS, tgl_get_peer_id (U->id), s1, l1, s2, l2, 0, 0, 0, 0); - bl_do_user_set_username (TLS, U, s3, l3); - bl_do_user_delete (TLS, U); - } - if (x != CODE_user_deleted) { - long long access_hash = 0; - if (x != CODE_user_self) { - access_hash = fetch_long (); - } - int phone_len = 0; - char *phone = 0; - if (x != CODE_user_foreign) { - phone_len = prefetch_strlen (); - assert (phone_len >= 0); - phone = fetch_str (phone_len); - } - bl_do_user_add (TLS, tgl_get_peer_id (U->id), s1, l1, s2, l2, access_hash, phone, phone_len, x == CODE_user_contact); - bl_do_user_set_username (TLS, U, s3, l3); - assert (tglf_fetch_user_photo (TLS, U) >= 0); - assert (tglf_fetch_user_status (TLS, &U->status, U) >= 0); - - if (x == CODE_user_self) { - fetch_bool (); - } - } - } else { - int l1 = prefetch_strlen (); - char *s1 = fetch_str (l1); - int l2 = prefetch_strlen (); - char *s2 = fetch_str (l2); - - bl_do_user_set_name (TLS, U, s1, l1, s2, l2); - - int l3 = prefetch_strlen (); - char *s3 = fetch_str (l3); - bl_do_user_set_username (TLS, U, s3, l3); - - if (x == CODE_user_deleted && !(U->flags & FLAG_DELETED)) { - bl_do_user_delete (TLS, U); - } - if (x != CODE_user_deleted) { - if (x != CODE_user_self) { - bl_do_user_set_access_hash (TLS, U, fetch_long ()); - } - if (x != CODE_user_foreign) { - int l = prefetch_strlen (); - char *s = fetch_str (l); - bl_do_user_set_phone (TLS, U, s, l); - } - assert (tglf_fetch_user_photo (TLS, U) >= 0); - - tglf_fetch_user_status (TLS, &U->status, U); - if (x == CODE_user_self) { - fetch_bool (); - } - - if (x == CODE_user_contact) { - bl_do_user_set_friend (TLS, U, 1); - } else { - bl_do_user_set_friend (TLS, U, 0); - } - } - } - return 0; -} - -void tglf_fetch_user_full (struct tgl_state *TLS, struct tgl_user *U) { - assert (fetch_int () == CODE_user_full); - tglf_fetch_alloc_user (TLS); - assert (skip_type_any (TYPE_TO_PARAM (contacts_link)) >= 0); - - int *start = in_ptr; - assert (skip_type_any (TYPE_TO_PARAM (photo)) >= 0); - bl_do_user_set_full_photo (TLS, U, start, 4 * (in_ptr - start)); - - assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0); - - bl_do_user_set_blocked (TLS, U, fetch_bool ()); - int l1 = prefetch_strlen (); - char *s1 = fetch_str (l1); - int l2 = prefetch_strlen (); - char *s2 = fetch_str (l2); - if (U && (U->flags & FLAG_CREATED)) { - bl_do_user_set_real_name (TLS, U, s1, l1, s2, l2); - } -} - -void tglf_fetch_encrypted_chat (struct tgl_state *TLS, struct tgl_secret_chat *U) { - unsigned x = fetch_int (); - assert (x == CODE_encrypted_chat_empty || x == CODE_encrypted_chat_waiting || x == CODE_encrypted_chat_requested || x == CODE_encrypted_chat || x == CODE_encrypted_chat_discarded); - U->id = TGL_MK_ENCR_CHAT (fetch_int ()); - if (x == CODE_encrypted_chat_empty) { - return; - } - int new = !(U->flags & FLAG_CREATED); - - if (x == CODE_encrypted_chat_discarded) { - if (new) { - vlogprintf (E_WARNING, "Unknown chat in deleted state. May be we forgot something...\n"); - return; - } - bl_do_encr_chat_delete (TLS, U); - //write_secret_chat_file (); - return; - } - - static char g_key[256]; - static char nonce[256]; - if (new) { - long long access_hash = fetch_long (); - int date = fetch_int (); - int admin_id = fetch_int (); - int user_id = fetch_int () + admin_id - TLS->our_id; - - if (x == CODE_encrypted_chat_waiting) { - vlogprintf (E_WARNING, "Unknown chat in waiting state. May be we forgot something...\n"); - return; - } - if (x == CODE_encrypted_chat_requested || x == CODE_encrypted_chat) { - memset (g_key, 0, sizeof (g_key)); - } - - fetch256 (g_key); - - if (x == CODE_encrypted_chat) { - fetch_long (); // fingerprint - } - - if (x == CODE_encrypted_chat) { - vlogprintf (E_WARNING, "Unknown chat in ok state. May be we forgot something...\n"); - return; - } - - bl_do_encr_chat_requested (TLS, U, access_hash, date, admin_id, user_id, (void *)g_key, (void *)nonce); - //write_secret_chat_file (); - } else { - bl_do_encr_chat_set_access_hash (TLS, U, fetch_long ()); - bl_do_encr_chat_set_date (TLS, U, fetch_int ()); - if (fetch_int () != U->admin_id) { - vlogprintf (E_WARNING, "Changed admin in secret chat. WTF?\n"); - return; - } - if (U->user_id != U->admin_id + fetch_int () - TLS->our_id) { - vlogprintf (E_WARNING, "Changed partner in secret chat. WTF?\n"); - return; - } - if (x == CODE_encrypted_chat_waiting) { - bl_do_encr_chat_set_state (TLS, U, sc_waiting); - //write_secret_chat_file (); - return; // We needed only access hash from here - } - - if (x == CODE_encrypted_chat_requested || x == CODE_encrypted_chat) { - memset (g_key, 0, sizeof (g_key)); - } - - fetch256 (g_key); - - if (x == CODE_encrypted_chat_requested) { - return; // Duplicate? - } - bl_do_encr_chat_accepted (TLS, U, (void *)g_key, (void *)nonce, fetch_long ()); - //write_secret_chat_file (); - } -} - -void tglf_fetch_chat (struct tgl_state *TLS, struct tgl_chat *C) { - unsigned x = fetch_int (); - assert (x == CODE_chat_empty || x == CODE_chat || x == CODE_chat_forbidden); - C->id = TGL_MK_CHAT (fetch_int ()); - if (x == CODE_chat_empty) { - return; - } - int new = !(C->flags & FLAG_CREATED); - if (new) { - int y = 0; - if (x == CODE_chat_forbidden) { - y |= FLAG_FORBIDDEN; - } - int l = prefetch_strlen (); - char *s = fetch_str (l); - - struct tgl_file_location small; - struct tgl_file_location big; - memset (&small, 0, sizeof (small)); - memset (&big, 0, sizeof (big)); - int users_num = -1; - int date = 0; - int version = -1; - - if (x == CODE_chat) { - unsigned z = fetch_int (); - if (z == CODE_chat_photo_empty) { - small.dc = -2; - big.dc = -2; - } else { - assert (z == CODE_chat_photo); - tglf_fetch_file_location (TLS, &small); - tglf_fetch_file_location (TLS, &big); - } - users_num = fetch_int (); - date = fetch_int (); - if (fetch_bool ()) { - y |= FLAG_CHAT_IN_CHAT; - } - version = fetch_int (); - } else { - small.dc = -2; - big.dc = -2; - users_num = -1; - date = fetch_int (); - version = -1; - } - - bl_do_create_chat (TLS, C, y, s, l, users_num, date, version, &big, &small); - } else { - if (x == CODE_chat_forbidden) { - bl_do_chat_forbid (TLS, C, 1); - } else { - bl_do_chat_forbid (TLS, C, 0); - } - int l = prefetch_strlen (); - char *s = fetch_str (l); - bl_do_chat_set_title (TLS, C, s, l); - - struct tgl_file_location small; - struct tgl_file_location big; - memset (&small, 0, sizeof (small)); - memset (&big, 0, sizeof (big)); - - if (x == CODE_chat) { - unsigned y = fetch_int (); - if (y == CODE_chat_photo_empty) { - small.dc = -2; - big.dc = -2; - } else { - assert (y == CODE_chat_photo); - tglf_fetch_file_location (TLS, &small); - tglf_fetch_file_location (TLS, &big); - } - bl_do_chat_set_photo (TLS, C, &big, &small); - int users_num = fetch_int (); - bl_do_chat_set_date (TLS, C, fetch_int ()); - bl_do_chat_set_set_in_chat (TLS, C, fetch_bool ()); - bl_do_chat_set_version (TLS, C, users_num, fetch_int ()); - } else { - bl_do_chat_set_date (TLS, C, fetch_int ()); - } - } -} - -void tglf_fetch_chat_full (struct tgl_state *TLS, struct tgl_chat *C) { - unsigned x = fetch_int (); - assert (x == CODE_messages_chat_full); - assert (fetch_int () == CODE_chat_full); - C->id = TGL_MK_CHAT (fetch_int ()); - x = fetch_int (); - int version = 0; - struct tgl_chat_user *users = 0; - int users_num = 0; - int admin_id = 0; - - if (x == CODE_chat_participants) { - assert (fetch_int () == tgl_get_peer_id (C->id)); - admin_id = fetch_int (); - assert (fetch_int () == CODE_vector); - users_num = fetch_int (); - users = talloc (sizeof (struct tgl_chat_user) * users_num); - int i; - for (i = 0; i < users_num; i++) { - assert (fetch_int () == (int)CODE_chat_participant); - users[i].user_id = fetch_int (); - users[i].inviter_id = fetch_int (); - users[i].date = fetch_int (); - } - version = fetch_int (); - } else { - fetch_int (); - } - int *start = in_ptr; - assert (skip_type_any (TYPE_TO_PARAM (photo)) >= 0); - int *end = in_ptr; - assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0); - - int n, i; - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - if (admin_id) { - bl_do_chat_set_admin (TLS, C, admin_id); - } - if (version > 0) { - bl_do_chat_set_participants (TLS, C, version, users_num, users); - tfree (users, sizeof (struct tgl_chat_user) * users_num); - } - bl_do_chat_set_full_photo (TLS, C, start, 4 * (end - start)); -} - -void tglf_fetch_photo_size (struct tgl_state *TLS, struct tgl_photo_size *S) { - memset (S, 0, sizeof (*S)); - unsigned x = fetch_int (); - assert (x == CODE_photo_size || x == CODE_photo_cached_size || x == CODE_photo_size_empty); - S->type = fetch_str_dup (); - if (x != CODE_photo_size_empty) { - tglf_fetch_file_location (TLS, &S->loc); - S->w = fetch_int (); - S->h = fetch_int (); - if (x == CODE_photo_size) { - S->size = fetch_int (); - } else { - S->size = prefetch_strlen (); - fetch_str (S->size); - } - } -} - -void tglf_fetch_geo (struct tgl_state *TLS, struct tgl_geo *G) { - unsigned x = fetch_int (); - if (x == CODE_geo_point) { - G->longitude = fetch_double (); - G->latitude = fetch_double (); - } else { - assert (x == CODE_geo_point_empty); - G->longitude = 0; - G->latitude = 0; - } -} - -void tglf_fetch_photo (struct tgl_state *TLS, struct tgl_photo *P) { - memset (P, 0, sizeof (*P)); - unsigned x = fetch_int (); - assert (x == CODE_photo_empty || x == CODE_photo); - P->id = fetch_long (); - if (x == CODE_photo_empty) { return; } - P->access_hash = fetch_long (); - P->user_id = fetch_int (); - P->date = fetch_int (); - P->caption = fetch_str_dup (); - tglf_fetch_geo (TLS, &P->geo); - assert (fetch_int () == CODE_vector); - P->sizes_num = fetch_int (); - P->sizes = talloc (sizeof (struct tgl_photo_size) * P->sizes_num); - int i; - for (i = 0; i < P->sizes_num; i++) { - tglf_fetch_photo_size (TLS, &P->sizes[i]); - } -} - -void tglf_fetch_video (struct tgl_state *TLS, struct tgl_video *V) { - memset (V, 0, sizeof (*V)); - unsigned x = fetch_int (); - V->id = fetch_long (); - if (x == CODE_video_empty) { return; } - V->access_hash = fetch_long (); - V->user_id = fetch_int (); - V->date = fetch_int (); - V->caption = fetch_str_dup (); - V->duration = fetch_int (); - V->mime_type = fetch_str_dup (); - V->size = fetch_int (); - tglf_fetch_photo_size (TLS, &V->thumb); - V->dc_id = fetch_int (); - V->w = fetch_int (); - V->h = fetch_int (); -} - -void tglf_fetch_audio (struct tgl_state *TLS, struct tgl_audio *V) { - memset (V, 0, sizeof (*V)); - unsigned x = fetch_int (); - V->id = fetch_long (); - if (x == CODE_audio_empty) { return; } - V->access_hash = fetch_long (); - V->user_id = fetch_int (); - V->date = fetch_int (); - V->duration = fetch_int (); - V->mime_type = fetch_str_dup (); - V->size = fetch_int (); - V->dc_id = fetch_int (); -} - -void tglf_fetch_document (struct tgl_state *TLS, struct tgl_document *V) { - memset (V, 0, sizeof (*V)); - unsigned x = fetch_int (); - V->id = fetch_long (); - if (x == CODE_document_empty) { return; } - V->access_hash = fetch_long (); - V->user_id = fetch_int (); - V->date = fetch_int (); - V->caption = fetch_str_dup (); - V->mime_type = fetch_str_dup (); - V->size = fetch_int (); - tglf_fetch_photo_size (TLS, &V->thumb); - V->dc_id = fetch_int (); -} - -void tglf_fetch_message_action (struct tgl_state *TLS, struct tgl_message_action *M) { - memset (M, 0, sizeof (*M)); - unsigned x = fetch_int (); - switch (x) { - case CODE_message_action_empty: - M->type = tgl_message_action_none; - break; - case CODE_message_action_geo_chat_create: - { - M->type = tgl_message_action_geo_chat_create; - int l = prefetch_strlen (); // title - char *s = fetch_str (l); - int l2 = prefetch_strlen (); // checkin - char *s2 = fetch_str (l2); - vlogprintf (E_ERROR, "Message action: Created geochat %.*s in address %.*s. You are in magic land now, since nobody ever tested geochats in this app\n", l, s, l2, s2); - } - break; - case CODE_message_action_geo_chat_checkin: - M->type = tgl_message_action_geo_chat_checkin; - break; - case CODE_message_action_chat_create: - M->type = tgl_message_action_chat_create; - M->title = fetch_str_dup (); - assert (fetch_int () == (int)CODE_vector); - M->user_num = fetch_int (); - M->users = talloc (M->user_num * 4); - fetch_ints (M->users, M->user_num); - break; - case CODE_message_action_chat_edit_title: - M->type = tgl_message_action_chat_edit_title; - M->new_title = fetch_str_dup (); - break; - case CODE_message_action_chat_edit_photo: - M->type = tgl_message_action_chat_edit_photo; - tglf_fetch_photo (TLS, &M->photo); - break; - case CODE_message_action_chat_delete_photo: - M->type = tgl_message_action_chat_delete_photo; - break; - case CODE_message_action_chat_add_user: - M->type = tgl_message_action_chat_add_user; - M->user = fetch_int (); - break; - case CODE_message_action_chat_delete_user: - M->type = tgl_message_action_chat_delete_user; - M->user = fetch_int (); - break; - default: - vlogprintf (E_ERROR, "type = %d\n", x); - assert (0); - } -} - -void tglf_fetch_message_short (struct tgl_state *TLS, struct tgl_message *M) { - int new = !(M->flags & FLAG_CREATED); - - if (new) { - int id = fetch_int (); - int from_id = fetch_int (); - int to_id = TLS->our_id; - int l = prefetch_strlen (); - char *s = fetch_str (l); - - int pts = fetch_int (); - - int date = fetch_int (); - //tglu_fetch_seq (); - int seq = fetch_int (); - assert (seq == TLS->seq + 1); - - bl_do_create_message_text (TLS, id, from_id, TGL_PEER_USER, to_id, date, 1, l, s); - - tgl_peer_t *P = tgl_peer_get (TLS, TGL_MK_USER (from_id)); - if (!P || !(P->flags & FLAG_CREATED)) { - tgl_do_get_difference (TLS, 0, 0, 0); - } else { - bl_do_set_pts (TLS, pts); - bl_do_set_date (TLS, date); - } - //bl_do_msg_seq_update (id); - } else { - fetch_int (); // id - fetch_int (); // from_id - int l = prefetch_strlen (); - fetch_str (l); // text - - tglu_fetch_pts (TLS); - fetch_int (); - //tglu_fetch_seq (); - int seq = fetch_int (); - assert (seq == TLS->seq + 1); - //bl_do_msg_seq_update (id); - } -} - -void tglf_fetch_message_short_chat (struct tgl_state *TLS, struct tgl_message *M) { - int new = !(M->flags & FLAG_CREATED); - - if (new) { - int id = fetch_int (); - int from_id = fetch_int (); - int to_id = fetch_int (); - int l = prefetch_strlen (); - char *s = fetch_str (l); - - int pts = fetch_int (); - int date = fetch_int (); - //tglu_fetch_seq (); - - int seq = fetch_int (); - assert (seq == TLS->seq + 1); - bl_do_create_message_text (TLS, id, from_id, TGL_PEER_CHAT, to_id, date, 1, l, s); - - tgl_peer_t *P = tgl_peer_get (TLS, TGL_MK_CHAT (to_id)); - if (!P || !(P->flags & FLAG_CREATED)) { - tgl_do_get_difference (TLS, 0, 0, 0); - } else { - P = tgl_peer_get (TLS, TGL_MK_USER (from_id)); - if (!P || !(P->flags & FLAG_CREATED)) { - tgl_do_get_difference (TLS, 0, 0, 0); - } else { - bl_do_set_pts (TLS, pts); - bl_do_set_date (TLS, date); - } - } - //bl_do_msg_seq_update (id); - } else { - fetch_int (); // id - fetch_int (); // from_id - fetch_int (); // to_id - int l = prefetch_strlen (); - fetch_str (l); // text - - tglu_fetch_pts (TLS); - fetch_int (); - //tglu_fetch_seq (); - int seq = fetch_int (); - assert (seq == TLS->seq + 1); - //bl_do_msg_seq_update (id); - } -} - - -void tglf_fetch_message_media (struct tgl_state *TLS, struct tgl_message_media *M) { - memset (M, 0, sizeof (*M)); - //M->type = fetch_int (); - int x = fetch_int (); - switch (x) { - case CODE_message_media_empty: - M->type = tgl_message_media_none; - break; - case CODE_message_media_photo: - M->type = tgl_message_media_photo; - tglf_fetch_photo (TLS, &M->photo); - break; - case CODE_message_media_video: - M->type = tgl_message_media_video; - tglf_fetch_video (TLS, &M->video); - break; - case CODE_message_media_audio: - M->type = tgl_message_media_audio; - tglf_fetch_audio (TLS, &M->audio); - break; - case CODE_message_media_document: - M->type = tgl_message_media_document; - tglf_fetch_document (TLS, &M->document); - break; - case CODE_message_media_geo: - M->type = tgl_message_media_geo; - tglf_fetch_geo (TLS, &M->geo); - break; - case CODE_message_media_contact: - M->type = tgl_message_media_contact; - M->phone = fetch_str_dup (); - M->first_name = fetch_str_dup (); - M->last_name = fetch_str_dup (); - M->user_id = fetch_int (); - break; - case CODE_message_media_unsupported: - M->type = tgl_message_media_unsupported; - M->data_size = prefetch_strlen (); - M->data = talloc (M->data_size); - memcpy (M->data, fetch_str (M->data_size), M->data_size); - break; - default: - vlogprintf (E_ERROR, "type = 0x%08x\n", M->type); - assert (0); - } -} - -void tglf_fetch_message_media_encrypted (struct tgl_state *TLS, struct tgl_message_media *M) { - memset (M, 0, sizeof (*M)); - unsigned x = fetch_int (); - int l; - switch (x) { - case CODE_decrypted_message_media_empty: - M->type = tgl_message_media_none; - //M->type = CODE_message_media_empty; - break; - case CODE_decrypted_message_media_photo: - M->type = tgl_message_media_photo_encr; - //M->type = x; - l = prefetch_strlen (); - fetch_str (l); // thumb - fetch_int (); // thumb_w - fetch_int (); // thumb_h - M->encr_photo.w = fetch_int (); - M->encr_photo.h = fetch_int (); - M->encr_photo.size = fetch_int (); - - l = prefetch_strlen (); - assert (l > 0); - M->encr_photo.key = talloc (32); - memset (M->encr_photo.key, 0, 32); - if (l <= 32) { - memcpy (M->encr_photo.key + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_photo.key, fetch_str (l) + (l - 32), 32); - } - M->encr_photo.iv = talloc (32); - l = prefetch_strlen (); - assert (l > 0); - memset (M->encr_photo.iv, 0, 32); - if (l <= 32) { - memcpy (M->encr_photo.iv + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_photo.iv, fetch_str (l) + (l - 32), 32); - } - break; - case CODE_decrypted_message_media_video: - case CODE_decrypted_message_media_video_l12: - //M->type = CODE_decrypted_message_media_video; - M->type = tgl_message_media_video_encr; - l = prefetch_strlen (); - fetch_str (l); // thumb - fetch_int (); // thumb_w - fetch_int (); // thumb_h - M->encr_video.duration = fetch_int (); - if (x == CODE_decrypted_message_media_video) { - M->encr_video.mime_type = fetch_str_dup (); - } - M->encr_video.w = fetch_int (); - M->encr_video.h = fetch_int (); - M->encr_video.size = fetch_int (); - - l = prefetch_strlen (); - assert (l > 0); - M->encr_video.key = talloc0 (32); - if (l <= 32) { - memcpy (M->encr_video.key + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.key, fetch_str (l) + (l - 32), 32); - } - M->encr_video.iv = talloc (32); - l = prefetch_strlen (); - assert (l > 0); - memset (M->encr_video.iv, 0, 32); - if (l <= 32) { - memcpy (M->encr_video.iv + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.iv, fetch_str (l) + (l - 32), 32); - } - break; - case CODE_decrypted_message_media_audio: - case CODE_decrypted_message_media_audio_l12: - //M->type = CODE_decrypted_message_media_audio; - M->type = tgl_message_media_audio_encr; - M->encr_audio.duration = fetch_int (); - if (x == CODE_decrypted_message_media_audio) { - M->encr_audio.mime_type = fetch_str_dup (); - } - M->encr_audio.size = fetch_int (); - - l = prefetch_strlen (); - assert (l > 0); - M->encr_video.key = talloc0 (32); - if (l <= 32) { - memcpy (M->encr_video.key + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.key, fetch_str (l) + (l - 32), 32); - } - M->encr_video.iv = talloc0 (32); - l = prefetch_strlen (); - assert (l > 0); - if (l <= 32) { - memcpy (M->encr_video.iv + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.iv, fetch_str (l) + (l - 32), 32); - } - break; - case CODE_decrypted_message_media_document: - M->type = tgl_message_media_document_encr; - l = prefetch_strlen (); - fetch_str (l); // thumb - fetch_int (); // thumb_w - fetch_int (); // thumb_h - M->encr_document.file_name = fetch_str_dup (); - M->encr_document.mime_type = fetch_str_dup (); - M->encr_video.size = fetch_int (); - - l = prefetch_strlen (); - assert (l > 0); - M->encr_video.key = talloc0 (32); - if (l <= 32) { - memcpy (M->encr_video.key + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.key, fetch_str (l) + (l - 32), 32); - } - M->encr_video.iv = talloc0 (32); - l = prefetch_strlen (); - assert (l > 0); - if (l <= 32) { - memcpy (M->encr_video.iv + (32 - l), fetch_str (l), l); - } else { - memcpy (M->encr_video.iv, fetch_str (l) + (l - 32), 32); - } - break; -/* case CODE_decrypted_message_media_file: - M->type = x; - M->encr_file.filename = fetch_str_dup (); - l = prefetch_strlen (); - fetch_str (l); // thumb - l = fetch_int (); - assert (l > 0); - M->encr_file.key = talloc (l); - memcpy (M->encr_file.key, fetch_str (l), l); - - l = fetch_int (); - assert (l > 0); - M->encr_file.iv = talloc (l); - memcpy (M->encr_file.iv, fetch_str (l), l); - break; - */ - case CODE_decrypted_message_media_geo_point: - M->type = tgl_message_media_geo; - M->geo.latitude = fetch_double (); - M->geo.longitude = fetch_double (); - break; - case CODE_decrypted_message_media_contact: - M->type = tgl_message_media_contact; - M->phone = fetch_str_dup (); - M->first_name = fetch_str_dup (); - M->last_name = fetch_str_dup (); - M->user_id = fetch_int (); - break; - default: - vlogprintf (E_ERROR, "type = 0x%08x\n", x); - assert (0); - } -} - -void tglf_fetch_message_action_encrypted (struct tgl_state *TLS, struct tgl_message_action *M) { - unsigned x = fetch_int (); - switch (x) { - case CODE_decrypted_message_action_set_message_t_t_l: - M->type = tgl_message_action_set_message_ttl; - M->ttl = fetch_int (); - break; - case CODE_decrypted_message_action_read_messages: - M->type = tgl_message_action_read_messages; - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - M->read_cnt = n; - while (n -- > 0) { - long long id = fetch_long (); - struct tgl_message *N = tgl_message_get (TLS, id); - if (N) { - N->unread = 0; - } - } - } - break; - case CODE_decrypted_message_action_delete_messages: - M->type = tgl_message_action_delete_messages; - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - M->delete_cnt = n; - while (n -- > 0) { - fetch_long (); - } - } - break; - case CODE_decrypted_message_action_screenshot_messages: - M->type = tgl_message_action_screenshot_messages; - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - M->screenshot_cnt = n; - while (n -- > 0) { - fetch_long (); - } - } - break; - case CODE_decrypted_message_action_notify_layer: - M->type = tgl_message_action_notify_layer; - M->layer = fetch_int (); - break; - case CODE_decrypted_message_action_flush_history: - M->type = tgl_message_action_flush_history; - break; - case CODE_decrypted_message_action_typing: - M->type = tgl_message_action_typing; - M->typing = tglf_fetch_typing (); - break; - case CODE_decrypted_message_action_resend: - M->type = tgl_message_action_resend; - M->start_seq_no = fetch_int (); - M->end_seq_no = fetch_int (); - break; - default: - vlogprintf (E_ERROR, "x = 0x%08x\n", x); - assert (0); - } -} - -tgl_peer_id_t tglf_fetch_peer_id (struct tgl_state *TLS) { - unsigned x =fetch_int (); - if (x == CODE_peer_user) { - return TGL_MK_USER (fetch_int ()); - } else { - assert (CODE_peer_chat); - return TGL_MK_CHAT (fetch_int ()); - } -} - -void tglf_fetch_message (struct tgl_state *TLS, struct tgl_message *M) { - unsigned x = fetch_int (); - assert (x == CODE_message_empty || x == CODE_message || x == CODE_message_forwarded || x == CODE_message_service); - int flags = 0; - if (x != CODE_message_empty) { - flags = fetch_int (); - } - int id = fetch_int (); - assert (M->id == id); - if (x == CODE_message_empty) { - return; - } - int fwd_from_id = 0; - int fwd_date = 0; - - if (x == CODE_message_forwarded) { - fwd_from_id = fetch_int (); - fwd_date = fetch_int (); - } - int from_id = fetch_int (); - tgl_peer_id_t to_id = tglf_fetch_peer_id (TLS); - - //fetch_bool (); // out. - - //int unread = fetch_bool (); - int date = fetch_int (); - - int unread = (flags & 1) != 0; - int new = !(M->flags & FLAG_CREATED); - - if (x == CODE_message_service) { - int *start = in_ptr; - - assert (skip_type_any (TYPE_TO_PARAM (message_action)) >= 0); - - if (new) { - if (fwd_from_id) { - bl_do_create_message_service_fwd (TLS, id, from_id, tgl_get_peer_type (to_id), tgl_get_peer_id (to_id), date, fwd_from_id, fwd_date, unread, start, (in_ptr - start)); - } else { - bl_do_create_message_service (TLS, id, from_id, tgl_get_peer_type (to_id), tgl_get_peer_id (to_id), date, unread, start, (in_ptr - start)); - } - } - } else { - int l = prefetch_strlen (); - char *s = fetch_str (l); - int *start = in_ptr; - - assert (skip_type_any (TYPE_TO_PARAM (message_media)) >= 0); - - if (new) { - if (fwd_from_id) { - bl_do_create_message_media_fwd (TLS, id, from_id, tgl_get_peer_type (to_id), tgl_get_peer_id (to_id), date, fwd_from_id, fwd_date, unread, l, s, start, in_ptr - start); - } else { - bl_do_create_message_media (TLS, id, from_id, tgl_get_peer_type (to_id), tgl_get_peer_id (to_id), date, unread, l, s, start, in_ptr - start); - } - } - } - bl_do_set_unread (TLS, M, unread); -} - -void tglf_tglf_fetch_geo_message (struct tgl_state *TLS, struct tgl_message *M) { - memset (M, 0, sizeof (*M)); - unsigned x = fetch_int (); - assert (x == CODE_geo_chat_message_empty || x == CODE_geo_chat_message || x == CODE_geo_chat_message_service); - M->to_id = TGL_MK_GEO_CHAT (fetch_int ()); - M->id = fetch_int (); - if (x == CODE_geo_chat_message_empty) { - M->flags |= 1; - return; - } - M->from_id = TGL_MK_USER (fetch_int ()); - M->date = fetch_int (); - if (x == CODE_geo_chat_message_service) { - M->service = 1; - tglf_fetch_message_action (TLS, &M->action); - } else { - M->message = fetch_str_dup (); - M->message_len = strlen (M->message); - tglf_fetch_message_media (TLS, &M->media); - } -} - -static int *decr_ptr; -static int *decr_end; - -static int decrypt_encrypted_message (struct tgl_secret_chat *E) { - int *msg_key = decr_ptr; - decr_ptr += 4; - assert (decr_ptr < decr_end); - static unsigned char sha1a_buffer[20]; - static unsigned char sha1b_buffer[20]; - static unsigned char sha1c_buffer[20]; - static unsigned char sha1d_buffer[20]; - - static unsigned char buf[64]; - memcpy (buf, msg_key, 16); - memcpy (buf + 16, E->key, 32); - sha1 (buf, 48, sha1a_buffer); - - memcpy (buf, E->key + 8, 16); - memcpy (buf + 16, msg_key, 16); - memcpy (buf + 32, E->key + 12, 16); - sha1 (buf, 48, sha1b_buffer); - - memcpy (buf, E->key + 16, 32); - memcpy (buf + 32, msg_key, 16); - sha1 (buf, 48, sha1c_buffer); - - memcpy (buf, msg_key, 16); - memcpy (buf + 16, E->key + 24, 32); - sha1 (buf, 48, sha1d_buffer); - - static unsigned char key[32]; - memcpy (key, sha1a_buffer + 0, 8); - memcpy (key + 8, sha1b_buffer + 8, 12); - memcpy (key + 20, sha1c_buffer + 4, 12); - - static unsigned char iv[32]; - memcpy (iv, sha1a_buffer + 8, 12); - memcpy (iv + 12, sha1b_buffer + 0, 8); - memcpy (iv + 20, sha1c_buffer + 16, 4); - memcpy (iv + 24, sha1d_buffer + 0, 8); - - AES_KEY aes_key; - AES_set_decrypt_key (key, 256, &aes_key); - AES_ige_encrypt ((void *)decr_ptr, (void *)decr_ptr, 4 * (decr_end - decr_ptr), &aes_key, iv, 0); - memset (&aes_key, 0, sizeof (aes_key)); - - int x = *(decr_ptr); - if (x < 0 || (x & 3)) { - return -1; - } - assert (x >= 0 && !(x & 3)); - sha1 ((void *)decr_ptr, 4 + x, sha1a_buffer); - - if (memcmp (sha1a_buffer + 4, msg_key, 16)) { - return -1; - } - return 0; -} - -void tglf_fetch_encrypted_message (struct tgl_state *TLS, struct tgl_message *M) { - unsigned x = fetch_int (); - assert (x == CODE_encrypted_message || x == CODE_encrypted_message_service); - unsigned sx = x; - int new = !(M->flags & FLAG_CREATED); - long long id = fetch_long (); - int to_id = fetch_int (); - tgl_peer_id_t chat = TGL_MK_ENCR_CHAT (to_id); - int date = fetch_int (); - - tgl_peer_t *P = tgl_peer_get (TLS, chat); - if (!P) { - vlogprintf (E_WARNING, "Encrypted message to unknown chat. Dropping\n"); - M->flags |= FLAG_MESSAGE_EMPTY; - } - - - int len = prefetch_strlen (); - assert ((len & 15) == 8); - decr_ptr = (void *)fetch_str (len); - decr_end = decr_ptr + (len / 4); - int ok = 0; - if (P) { - if (*(long long *)decr_ptr != P->encr_chat.key_fingerprint) { - vlogprintf (E_WARNING, "Encrypted message with bad fingerprint to chat %s\n", P->print_name); - P = 0; - } - decr_ptr += 2; - } - int l = 0; - char *s = 0; - int *start = 0; - int *end = 0; - x = 0; - int out_seq_no = -1; - int in_seq_no = -1; - int drop = 0; - if (P && decrypt_encrypted_message (&P->encr_chat) >= 0 && new) { - ok = 1; - int *save_in_ptr = in_ptr; - int *save_in_end = in_end; - in_ptr = decr_ptr; - int ll = fetch_int (); - in_end = in_ptr + ll; - x = fetch_int (); - if (x == CODE_decrypted_message_layer) { - ll = prefetch_strlen (); - fetch_str (ll); // random_bytes - - int layer = fetch_int (); - assert (layer >= 0); - if (P && ((P->flags) & FLAG_CREATED)) { - bl_do_encr_chat_set_layer (TLS, (void *)P, layer); - } - //x = fetch_int (); - //assert (x == CODE_decrypted_message || x == CODE_decrypted_message_service); - - - out_seq_no = fetch_int (); - in_seq_no = fetch_int (); - if (in_seq_no / 2 != P->encr_chat.in_seq_no) { - vlogprintf (E_WARNING, "Hole in seq in secret chat. in_seq_no = %d, expect_seq_no = %d\n", in_seq_no / 2, P->encr_chat.in_seq_no); - drop = 1; - } - if ((in_seq_no & 1) != 1 - (P->encr_chat.admin_id == TLS->our_id) || - (out_seq_no & 1) != (P->encr_chat.admin_id == TLS->our_id)) { - vlogprintf (E_WARNING, "Bad msg admin\n"); - drop = 1; - } - if (out_seq_no / 2 > P->encr_chat.out_seq_no) { - vlogprintf (E_WARNING, "In seq no is bigger than our's out seq no (out_seq_no = %d, our_out_seq_no = %d). Drop\n", out_seq_no / 2, P->encr_chat.out_seq_no); - drop = 1; - } - if (out_seq_no / 2 < P->encr_chat.last_in_seq_no) { - vlogprintf (E_WARNING, "Clients in_seq_no decreased (out_seq_no = %d, last_out_seq_no = %d). Drop\n", out_seq_no / 2, P->encr_chat.last_in_seq_no); - drop = 1; - } - //vlogprintf (E_WARNING, "in = %d, out = %d\n", in_seq_no, out_seq_no); - //P->encr_chat.in_seq_no = in_seq_no / 2; - x = fetch_int (); - vlogprintf (E_DEBUG - 2, "layer = %d, in = %d, out = %d\n", layer, in_seq_no, out_seq_no); - } - if (!(x == CODE_decrypted_message || x == CODE_decrypted_message_service || x == CODE_decrypted_message_l16 || x == CODE_decrypted_message_service_l16)) { - vlogprintf (E_ERROR, "Incorrect message: x = 0x%08x\n", x); - drop = 1; - } - //assert (id == fetch_long ()); - if (!drop) { - long long new_id = fetch_long (); - if (P && P->encr_chat.layer >= 17) { - assert (new_id == id); - } - if (x == CODE_decrypted_message || x == CODE_decrypted_message_service) { - if (x == CODE_decrypted_message) { - fetch_int (); // ttl - } - } else { - ll = prefetch_strlen (); - fetch_str (ll); // random_bytes - } - if (x == CODE_decrypted_message || x == CODE_decrypted_message_l16) { - l = prefetch_strlen (); - s = fetch_str (l); - start = in_ptr; - assert (skip_type_any (TYPE_TO_PARAM (decrypted_message_media)) >= 0); - end = in_ptr; - } else { - start = in_ptr; - if (skip_type_any (TYPE_TO_PARAM (decrypted_message_action)) < 0) { - vlogprintf (E_ERROR, "Can not decrypt: Skipped %ld int out of %ld. Magic = 0x%08x\n", (long)(in_ptr - start), (long)(in_end - start), *start); - drop = 1; - } - end = in_ptr; - } - } - in_ptr = save_in_ptr; - in_end = save_in_end; - } - if (sx == CODE_encrypted_message) { - if (ok) { - int *start_file = in_ptr; - assert (skip_type_any (TYPE_TO_PARAM (encrypted_file)) >= 0); - if (x == CODE_decrypted_message || x == CODE_decrypted_message_l16) { - if (!drop) { - bl_do_create_message_media_encr (TLS, id, P->encr_chat.user_id, TGL_PEER_ENCR_CHAT, to_id, date, l, s, start, end - start, start_file, in_ptr - start_file); - } - } else if (x == CODE_decrypted_message_service || x == CODE_decrypted_message_service_l16) { - if (!drop) { - bl_do_create_message_service_encr (TLS, id, P->encr_chat.user_id, TGL_PEER_ENCR_CHAT, to_id, date, start, end - start); - } - } - } else { - if (!drop) { - assert (skip_type_any (TYPE_TO_PARAM (encrypted_file)) >= 0); - M->media.type = CODE_message_media_empty; - } - } - } else { - if (ok && (x == CODE_decrypted_message_service || x == CODE_decrypted_message_service_l16)) { - if (!drop) { - bl_do_create_message_service_encr (TLS, id, P->encr_chat.user_id, TGL_PEER_ENCR_CHAT, to_id, date, start, end - start); - } - } - } - if (!drop) { - if (in_seq_no >= 0 && out_seq_no >= 0) { - bl_do_encr_chat_update_seq (TLS, (void *)P, in_seq_no / 2 + 1, out_seq_no / 2); - assert (P->encr_chat.in_seq_no == in_seq_no / 2 + 1); - } - } -} - -void tglf_fetch_encrypted_message_file (struct tgl_state *TLS, struct tgl_message_media *M) { - unsigned x = fetch_int (); - assert (x == CODE_encrypted_file || x == CODE_encrypted_file_empty); - if (x == CODE_encrypted_file_empty) { - assert (M->type != tgl_message_media_photo_encr && M->type != tgl_message_media_video_encr); - } else { - assert (M->type == tgl_message_media_document_encr || M->type == tgl_message_media_photo_encr || M->type == tgl_message_media_video_encr || M->type == tgl_message_media_audio_encr); - - M->encr_photo.id = fetch_long(); - M->encr_photo.access_hash = fetch_long(); - if (!M->encr_photo.size) { - M->encr_photo.size = fetch_int (); - } else { - fetch_int (); - } - M->encr_photo.dc_id = fetch_int(); - M->encr_photo.key_fingerprint = fetch_int(); - } -} - -static int id_cmp (struct tgl_message *M1, struct tgl_message *M2) { - if (M1->id < M2->id) { return -1; } - else if (M1->id > M2->id) { return 1; } - else { return 0; } -} - -static void increase_peer_size (struct tgl_state *TLS) { - if (TLS->peer_num == TLS->peer_size) { - int new_size = TLS->peer_size ? 2 * TLS->peer_size : 10; - int old_size = TLS->peer_size; - if (old_size) { - TLS->Peers = trealloc (TLS->Peers, old_size * sizeof (void *), new_size * sizeof (void *)); - } else { - TLS->Peers = talloc (new_size * sizeof (void *)); - } - TLS->peer_size = new_size; - } -} - -struct tgl_user *tglf_fetch_alloc_user (struct tgl_state *TLS) { - int data[2]; - prefetch_data (data, 8); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_USER (data[1])); - if (!U) { - TLS->users_allocated ++; - U = talloc0 (sizeof (*U)); - U->id = TGL_MK_USER (data[1]); - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, U, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = U; - } - tglf_fetch_user (TLS, &U->user); - return &U->user; -} - -struct tgl_secret_chat *tglf_fetch_alloc_encrypted_chat (struct tgl_state *TLS) { - int data[2]; - prefetch_data (data, 8); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_ENCR_CHAT (data[1])); - if (!U) { - U = talloc0 (sizeof (*U)); - U->id = TGL_MK_ENCR_CHAT (data[1]); - TLS->encr_chats_allocated ++; - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, U, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = U; - } - tglf_fetch_encrypted_chat (TLS, &U->encr_chat); - return &U->encr_chat; -} - -struct tgl_user *tglf_fetch_alloc_user_full (struct tgl_state *TLS) { - int data[3]; - prefetch_data (data, 12); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_USER (data[2])); - if (U) { - tglf_fetch_user_full (TLS, &U->user); - return &U->user; - } else { - TLS->users_allocated ++; - U = talloc0 (sizeof (*U)); - U->id = TGL_MK_USER (data[2]); - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, U, lrand48 ()); - tglf_fetch_user_full (TLS, &U->user); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = U; - return &U->user; - } -} - -struct tgl_message *tglf_fetch_alloc_message (struct tgl_state *TLS) { - int data[3]; - prefetch_data (data, 12); - struct tgl_message *M = tgl_message_get (TLS, data[0] != (int)CODE_message_empty ? data[2] : data[1]); - - if (!M) { - M = tglm_message_alloc (TLS, data[0] != (int)CODE_message_empty ? data[2] : data[1]); - } - tglf_fetch_message (TLS, M); - return M; -} - -struct tgl_message *tglf_fetch_alloc_geo_message (struct tgl_state *TLS) { - struct tgl_message *M = talloc (sizeof (*M)); - tglf_tglf_fetch_geo_message (TLS, M); - struct tgl_message *M1 = tree_lookup_message (TLS->message_tree, M); - TLS->messages_allocated ++; - if (M1) { - tglm_message_del_use (TLS, M1); - tglm_message_del_peer (TLS, M1); - tgls_clear_message (TLS, M1); - memcpy (M1, M, sizeof (*M)); - tfree (M, sizeof (*M)); - tglm_message_add_use (TLS, M1); - tglm_message_add_peer (TLS, M1); - TLS->messages_allocated --; - return M1; - } else { - tglm_message_add_use (TLS, M); - tglm_message_add_peer (TLS, M); - TLS->message_tree = tree_insert_message (TLS->message_tree, M, lrand48 ()); - return M; - } -} - -struct tgl_message *tglf_fetch_alloc_encrypted_message (struct tgl_state *TLS) { - int data[3]; - prefetch_data (data, 12); - struct tgl_message *M = tgl_message_get (TLS, *(long long *)(data + 1)); - - if (!M) { - M = talloc0 (sizeof (*M)); - M->id = *(long long *)(data + 1); - tglm_message_insert_tree (TLS, M); - TLS->messages_allocated ++; - assert (tgl_message_get (TLS, M->id) == M); - } - tglf_fetch_encrypted_message (TLS, M); - return M; -} - -struct tgl_message *tglf_fetch_alloc_message_short (struct tgl_state *TLS) { - int data[1]; - prefetch_data (data, 4); - struct tgl_message *M = tgl_message_get (TLS, data[0]); - - if (!M) { - M = talloc0 (sizeof (*M)); - M->id = data[0]; - tglm_message_insert_tree (TLS, M); - TLS->messages_allocated ++; - } - tglf_fetch_message_short (TLS, M); - return M; -} - -struct tgl_message *tglf_fetch_alloc_message_short_chat (struct tgl_state *TLS) { - int data[1]; - prefetch_data (data, 4); - struct tgl_message *M = tgl_message_get (TLS, data[0]); - - if (!M) { - M = talloc0 (sizeof (*M)); - M->id = data[0]; - tglm_message_insert_tree (TLS, M); - TLS->messages_allocated ++; - } - tglf_fetch_message_short_chat (TLS, M); - return M; -} - -struct tgl_chat *tglf_fetch_alloc_chat (struct tgl_state *TLS) { - int data[2]; - prefetch_data (data, 8); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_CHAT (data[1])); - if (!U) { - TLS->chats_allocated ++; - U = talloc0 (sizeof (*U)); - U->id = TGL_MK_CHAT (data[1]); - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, U, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = U; - } - tglf_fetch_chat (TLS, &U->chat); - return &U->chat; -} - -struct tgl_chat *tglf_fetch_alloc_chat_full (struct tgl_state *TLS) { - int data[3]; - prefetch_data (data, 12); - tgl_peer_t *U = tgl_peer_get (TLS, TGL_MK_CHAT (data[2])); - if (U) { - tglf_fetch_chat_full (TLS, &U->chat); - return &U->chat; - } else { - TLS->chats_allocated ++; - U = talloc0 (sizeof (*U)); - U->id = TGL_MK_CHAT (data[2]); - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, U, lrand48 ()); - tglf_fetch_chat_full (TLS, &U->chat); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = U; - return &U->chat; - } -} -/* }}} */ - -void tglp_insert_encrypted_chat (struct tgl_state *TLS, tgl_peer_t *P) { - TLS->encr_chats_allocated ++; - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, P, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = P; -} - -void tglp_insert_user (struct tgl_state *TLS, tgl_peer_t *P) { - TLS->users_allocated ++; - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, P, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = P; -} - -void tglp_insert_chat (struct tgl_state *TLS, tgl_peer_t *P) { - TLS->chats_allocated ++; - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, P, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = P; -} - -void tgl_insert_empty_user (struct tgl_state *TLS, int uid) { - tgl_peer_id_t id = TGL_MK_USER (uid); - if (tgl_peer_get (TLS, id)) { return; } - tgl_peer_t *P = talloc0 (sizeof (*P)); - P->id = id; - tglp_insert_user (TLS, P); -} - -void tgl_insert_empty_chat (struct tgl_state *TLS, int cid) { - tgl_peer_id_t id = TGL_MK_CHAT (cid); - if (tgl_peer_get (TLS, id)) { return; } - tgl_peer_t *P = talloc0 (sizeof (*P)); - P->id = id; - tglp_insert_chat (TLS, P); -} - -/* {{{ Free */ - -void tgls_free_photo_size (struct tgl_state *TLS, struct tgl_photo_size *S) { - tfree_str (S->type); - if (S->data) { - tfree (S->data, S->size); - } -} - -void tgls_free_photo (struct tgl_state *TLS, struct tgl_photo *P) { - if (P->caption) { tfree_str (P->caption); } - if (P->sizes) { - int i; - for (i = 0; i < P->sizes_num; i++) { - tgls_free_photo_size (TLS, &P->sizes[i]); - } - tfree (P->sizes, sizeof (struct tgl_photo_size) * P->sizes_num); - } -} - -void tgls_free_video (struct tgl_state *TLS, struct tgl_video *V) { - tfree_str (V->mime_type); - if (!V->access_hash) { return; } - tfree_str (V->caption); - tgls_free_photo_size (TLS, &V->thumb); -} - -void tgls_free_audio (struct tgl_state *TLS, struct tgl_audio *A) { - tfree_str (A->mime_type); -} - -void tgls_free_document (struct tgl_state *TLS, struct tgl_document *D) { - if (!D->access_hash) { return; } - if (D->mime_type) { tfree_str (D->mime_type);} - if (D->caption) {tfree_str (D->caption);} - tgls_free_photo_size (TLS, &D->thumb); -} - -void tgls_free_message_media (struct tgl_state *TLS, struct tgl_message_media *M) { - switch (M->type) { - case tgl_message_media_none: - case tgl_message_media_geo: - return; - case tgl_message_media_audio: - tgls_free_audio (TLS, &M->audio); - return; - case tgl_message_media_photo: - tgls_free_photo (TLS, &M->photo); - return; - case tgl_message_media_video: - tgls_free_video (TLS, &M->video); - return; - case tgl_message_media_contact: - tfree_str (M->phone); - tfree_str (M->first_name); - tfree_str (M->last_name); - return; - case tgl_message_media_document: - tgls_free_document (TLS, &M->document); - return; - case tgl_message_media_unsupported: - tfree (M->data, M->data_size); - return; - case tgl_message_media_photo_encr: - case tgl_message_media_video_encr: - case tgl_message_media_audio_encr: - case tgl_message_media_document_encr: - tfree_secure (M->encr_photo.key, 32); - tfree_secure (M->encr_photo.iv, 32); - return; - default: - vlogprintf (E_ERROR, "type = 0x%08x\n", M->type); - assert (0); - } -} - -void tgls_free_message_action (struct tgl_state *TLS, struct tgl_message_action *M) { - switch (M->type) { - case tgl_message_action_none: - break; - case tgl_message_action_chat_create: - tfree_str (M->title); - tfree (M->users, M->user_num * 4); - break; - case tgl_message_action_chat_edit_title: - tfree_str (M->new_title); - break; - case tgl_message_action_chat_edit_photo: - tgls_free_photo (TLS, &M->photo); - break; - case tgl_message_action_chat_delete_photo: - case tgl_message_action_chat_add_user: - case tgl_message_action_chat_delete_user: - case tgl_message_action_geo_chat_create: - case tgl_message_action_geo_chat_checkin: - case tgl_message_action_set_message_ttl: - case tgl_message_action_read_messages: - case tgl_message_action_delete_messages: - case tgl_message_action_screenshot_messages: - case tgl_message_action_flush_history: - case tgl_message_action_resend: - case tgl_message_action_notify_layer: - break; - - default: - vlogprintf (E_ERROR, "type = 0x%08x\n", M->type); - assert (0); - } -} - -void tgls_clear_message (struct tgl_state *TLS, struct tgl_message *M) { - if (!M->service) { - if (M->message) { tfree (M->message, M->message_len + 1); } - tgls_free_message_media (TLS, &M->media); - } else { - tgls_free_message_action (TLS, &M->action); - } -} - -void tgls_free_message (struct tgl_state *TLS, struct tgl_message *M) { - tgls_clear_message (TLS, M); - tfree (M, sizeof (*M)); -} - -void tgls_free_chat (struct tgl_state *TLS, struct tgl_chat *U) { - if (U->title) { tfree_str (U->title); } - if (U->print_title) { tfree_str (U->print_title); } - if (U->user_list) { - tfree (U->user_list, U->user_list_size * 12); - } - tgls_free_photo (TLS, &U->photo); - tfree (U, sizeof (*U)); -} - -void tgls_free_user (struct tgl_state *TLS, struct tgl_user *U) { - if (U->first_name) { tfree_str (U->first_name); } - if (U->last_name) { tfree_str (U->last_name); } - if (U->print_name) { tfree_str (U->print_name); } - if (U->phone) { tfree_str (U->phone); } - if (U->real_first_name) { tfree_str (U->real_first_name); } - if (U->real_last_name) { tfree_str (U->real_last_name); } - tgls_free_photo (TLS, &U->photo); - tfree (U, sizeof (*U)); -} - -void tgls_free_encr_chat (struct tgl_state *TLS, struct tgl_secret_chat *U) { - if (U->print_name) { tfree_str (U->print_name); } - if (U->g_key) { tfree (U->g_key, 256); } - if (U->nonce) { tfree (U->nonce, 256); } - tfree (U, sizeof (*U)); -} - -void tgls_free_peer (struct tgl_state *TLS, tgl_peer_t *P) { - if (tgl_get_peer_type (P->id) == TGL_PEER_USER) { - tgls_free_user (TLS, (void *)P); - } else if (tgl_get_peer_type (P->id) == TGL_PEER_CHAT) { - tgls_free_chat (TLS, (void *)P); - } else if (tgl_get_peer_type (P->id) == TGL_PEER_ENCR_CHAT) { - tgls_free_encr_chat (TLS, (void *)P); - } else { - assert (0); - } -} -/* }}} */ - -/* Messages {{{ */ - -void tglm_message_del_use (struct tgl_state *TLS, struct tgl_message *M) { - M->next_use->prev_use = M->prev_use; - M->prev_use->next_use = M->next_use; -} - -void tglm_message_add_use (struct tgl_state *TLS, struct tgl_message *M) { - M->next_use = TLS->message_list.next_use; - M->prev_use = &TLS->message_list; - M->next_use->prev_use = M; - M->prev_use->next_use = M; -} - -void tglm_message_add_peer (struct tgl_state *TLS, struct tgl_message *M) { - tgl_peer_id_t id; - if (!tgl_cmp_peer_id (M->to_id, TGL_MK_USER (TLS->our_id))) { - id = M->from_id; - } else { - id = M->to_id; - } - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (!P) { - P = talloc0 (sizeof (*P)); - P->id = id; - switch (tgl_get_peer_type (id)) { - case TGL_PEER_USER: - TLS->users_allocated ++; - break; - case TGL_PEER_CHAT: - TLS->chats_allocated ++; - break; - case TGL_PEER_GEO_CHAT: - TLS->geo_chats_allocated ++; - break; - case TGL_PEER_ENCR_CHAT: - TLS->encr_chats_allocated ++; - break; - } - TLS->peer_tree = tree_insert_peer (TLS->peer_tree, P, lrand48 ()); - increase_peer_size (TLS); - TLS->Peers[TLS->peer_num ++] = P; - } - if (!P->last) { - P->last = M; - M->prev = M->next = 0; - } else { - if (tgl_get_peer_type (P->id) != TGL_PEER_ENCR_CHAT) { - struct tgl_message *N = P->last; - struct tgl_message *NP = 0; - while (N && N->id > M->id) { - NP = N; - N = N->next; - } - if (N) { assert (N->id < M->id); } - M->next = N; - M->prev = NP; - if (N) { N->prev = M; } - if (NP) { NP->next = M; } - else { P->last = M; } - } else { - struct tgl_message *N = P->last; - struct tgl_message *NP = 0; - M->next = N; - M->prev = NP; - if (N) { N->prev = M; } - if (NP) { NP->next = M; } - else { P->last = M; } - } - } -} - -void tglm_message_del_peer (struct tgl_state *TLS, struct tgl_message *M) { - tgl_peer_id_t id; - if (!tgl_cmp_peer_id (M->to_id, TGL_MK_USER (TLS->our_id))) { - id = M->from_id; - } else { - id = M->to_id; - } - tgl_peer_t *P = tgl_peer_get (TLS, id); - if (M->prev) { - M->prev->next = M->next; - } - if (M->next) { - M->next->prev = M->prev; - } - if (P && P->last == M) { - P->last = M->next; - } -} - -struct tgl_message *tglm_message_alloc (struct tgl_state *TLS, long long id) { - struct tgl_message *M = talloc0 (sizeof (*M)); - M->id = id; - tglm_message_insert_tree (TLS, M); - TLS->messages_allocated ++; - return M; -} - -void tglm_update_message_id (struct tgl_state *TLS, struct tgl_message *M, long long id) { - TLS->message_tree = tree_delete_message (TLS->message_tree, M); - M->id = id; - TLS->message_tree = tree_insert_message (TLS->message_tree, M, lrand48 ()); -} - -void tglm_message_insert_tree (struct tgl_state *TLS, struct tgl_message *M) { - assert (M->id); - TLS->message_tree = tree_insert_message (TLS->message_tree, M, lrand48 ()); -} - -void tglm_message_remove_tree (struct tgl_state *TLS, struct tgl_message *M) { - assert (M->id); - TLS->message_tree = tree_delete_message (TLS->message_tree, M); -} - -void tglm_message_insert (struct tgl_state *TLS, struct tgl_message *M) { - tglm_message_add_use (TLS, M); - tglm_message_add_peer (TLS, M); -} - -void tglm_message_insert_unsent (struct tgl_state *TLS, struct tgl_message *M) { - TLS->message_unsent_tree = tree_insert_message (TLS->message_unsent_tree, M, lrand48 ()); -} - -void tglm_message_remove_unsent (struct tgl_state *TLS, struct tgl_message *M) { - TLS->message_unsent_tree = tree_delete_message (TLS->message_unsent_tree, M); -} - -static void __send_msg (struct tgl_message *M, void *_TLS) { - struct tgl_state *TLS = _TLS; - vlogprintf (E_NOTICE, "Resending message...\n"); - //print_message (M); - - if (M->media.type != tgl_message_media_none) { - assert (M->flags & FLAG_ENCRYPTED); - bl_do_delete_msg (TLS, M); - } else { - tgl_do_send_msg (TLS, M, 0, 0); - } -} - -void tglm_send_all_unsent (struct tgl_state *TLS) { - tree_act_ex_message (TLS->message_unsent_tree, __send_msg, TLS); -} -/* }}} */ - -void tglp_peer_insert_name (struct tgl_state *TLS, tgl_peer_t *P) { - TLS->peer_by_name_tree = tree_insert_peer_by_name (TLS->peer_by_name_tree, P, lrand48 ()); -} - -void tglp_peer_delete_name (struct tgl_state *TLS, tgl_peer_t *P) { - TLS->peer_by_name_tree = tree_delete_peer_by_name (TLS->peer_by_name_tree, P); -} - -tgl_peer_t *tgl_peer_get (struct tgl_state *TLS, tgl_peer_id_t id) { - static tgl_peer_t U; - U.id = id; - return tree_lookup_peer (TLS->peer_tree, &U); -} - -struct tgl_message *tgl_message_get (struct tgl_state *TLS, long long id) { - struct tgl_message M; - M.id = id; - return tree_lookup_message (TLS->message_tree, &M); -} - -tgl_peer_t *tgl_peer_get_by_name (struct tgl_state *TLS, const char *s) { - static tgl_peer_t P; - P.print_name = (void *)s; - tgl_peer_t *R = tree_lookup_peer_by_name (TLS->peer_by_name_tree, &P); - return R; -} - -void tgl_peer_iterator_ex (struct tgl_state *TLS, void (*it)(tgl_peer_t *P, void *extra), void *extra) { - tree_act_ex_peer (TLS->peer_tree, it, extra); -} - -int tgl_complete_user_list (struct tgl_state *TLS, int index, const char *text, int len, char **R) { - index ++; - while (index < TLS->peer_num && (!TLS->Peers[index]->print_name || strncmp (TLS->Peers[index]->print_name, text, len) || tgl_get_peer_type (TLS->Peers[index]->id) != TGL_PEER_USER)) { - index ++; - } - if (index < TLS->peer_num) { - *R = strdup (TLS->Peers[index]->print_name); - assert (*R); - return index; - } else { - return -1; - } -} - -int tgl_complete_chat_list (struct tgl_state *TLS, int index, const char *text, int len, char **R) { - index ++; - while (index < TLS->peer_num && (!TLS->Peers[index]->print_name || strncmp (TLS->Peers[index]->print_name, text, len) || tgl_get_peer_type (TLS->Peers[index]->id) != TGL_PEER_CHAT)) { - index ++; - } - if (index < TLS->peer_num) { - *R = strdup (TLS->Peers[index]->print_name); - assert (*R); - return index; - } else { - return -1; - } -} - -int tgl_complete_encr_chat_list (struct tgl_state *TLS, int index, const char *text, int len, char **R) { - index ++; - while (index < TLS->peer_num && (!TLS->Peers[index]->print_name || strncmp (TLS->Peers[index]->print_name, text, len) || tgl_get_peer_type (TLS->Peers[index]->id) != TGL_PEER_ENCR_CHAT)) { - index ++; - } - if (index < TLS->peer_num) { - *R = strdup (TLS->Peers[index]->print_name); - assert (*R); - return index; - } else { - return -1; - } -} - -int tgl_complete_peer_list (struct tgl_state *TLS, int index, const char *text, int len, char **R) { - index ++; - while (index < TLS->peer_num && (!TLS->Peers[index]->print_name || strncmp (TLS->Peers[index]->print_name, text, len))) { - index ++; - } - if (index < TLS->peer_num) { - *R = strdup (TLS->Peers[index]->print_name); - assert (*R); - return index; - } else { - return -1; - } -} - -void tgls_free_peer_gw (tgl_peer_t *P, void *TLS) { - tgls_free_peer (TLS, P); -} - -void tgls_free_message_gw (struct tgl_message *M, void *TLS) { - tgls_free_message (TLS, M); -} - -void tgl_free_all (struct tgl_state *TLS) { - tree_act_ex_peer (TLS->peer_tree, tgls_free_peer_gw, TLS); - TLS->peer_tree = tree_clear_peer (TLS->peer_tree); - TLS->peer_by_name_tree = tree_clear_peer_by_name (TLS->peer_by_name_tree); - tree_act_ex_message (TLS->message_tree, tgls_free_message_gw, TLS); - TLS->message_tree = tree_clear_message (TLS->message_tree); - tree_act_ex_message (TLS->message_unsent_tree, tgls_free_message_gw, TLS); - TLS->message_unsent_tree = tree_clear_message (TLS->message_unsent_tree); - - if (TLS->encr_prime) { tfree (TLS->encr_prime, 256); } - - - if (TLS->binlog_name) { tfree_str (TLS->binlog_name); } - if (TLS->auth_file) { tfree_str (TLS->auth_file); } - if (TLS->downloads_directory) { tfree_str (TLS->downloads_directory); } - - int i; - for (i = 0; i < TLS->rsa_key_num; i++) { - tfree_str (TLS->rsa_key_list[i]); - } - - for (i = 0; i <= TLS->max_dc_num; i++) if (TLS->DC_list[i]) { - tgls_free_dc (TLS, TLS->DC_list[i]); - } - BN_CTX_free (TLS->BN_ctx); - tgls_free_pubkey (TLS); -} - -int tgl_print_stat (struct tgl_state *TLS, char *s, int len) { - return tsnprintf (s, len, - "users_allocated\t%d\n" - "chats_allocated\t%d\n" - "encr_chats_allocated\t%d\n" - "peer_num\t%d\n" - "messages_allocated\t%d\n", - TLS->users_allocated, - TLS->chats_allocated, - TLS->encr_chats_allocated, - TLS->peer_num, - TLS->messages_allocated - ); -} diff --git a/structures.h b/structures.h deleted file mode 100644 index b7855bb..0000000 --- a/structures.h +++ /dev/null @@ -1,57 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ -#ifndef __STRUCTURES_H__ -#define __STRUCTURES_H__ - -#include -#include "tgl-layout.h" -#include "tgl-fetch.h" -#include "tgl.h" - -char *tgls_default_create_print_name (struct tgl_state *TLS, tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4); - - -void tgls_free_user (struct tgl_state *TLS, struct tgl_user *U); -void tgls_free_chat (struct tgl_state *TLS, struct tgl_chat *U); -void tgls_free_photo (struct tgl_state *TLS, struct tgl_photo *P); -void tgls_free_message (struct tgl_state *TLS, struct tgl_message *M); -void tgls_clear_message (struct tgl_state *TLS, struct tgl_message *M); - -struct tgl_message *tglm_message_alloc (struct tgl_state *TLS, long long id); -void tglm_message_insert_tree (struct tgl_state *TLS, struct tgl_message *M); -void tglm_update_message_id (struct tgl_state *TLS, struct tgl_message *M, long long id); -void tglm_message_insert (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_insert_unsent (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_remove_unsent (struct tgl_state *TLS, struct tgl_message *M); -void tglm_send_all_unsent (struct tgl_state *TLS); -void tglm_message_remove_tree (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_add_peer (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_del_peer (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_del_use (struct tgl_state *TLS, struct tgl_message *M); -void tglm_message_add_use (struct tgl_state *TLS, struct tgl_message *M); - -void tglp_peer_insert_name (struct tgl_state *TLS, tgl_peer_t *P); -void tglp_peer_delete_name (struct tgl_state *TLS, tgl_peer_t *P); -void tglp_insert_encrypted_chat (struct tgl_state *TLS, tgl_peer_t *P); -void tglp_insert_user (struct tgl_state *TLS, tgl_peer_t *P); -void tglp_insert_chat (struct tgl_state *TLS, tgl_peer_t *P); -enum tgl_typing_status tglf_fetch_typing (void); - -#endif diff --git a/tgl b/tgl new file mode 160000 index 0000000..6a59fd3 --- /dev/null +++ b/tgl @@ -0,0 +1 @@ +Subproject commit 6a59fd311c1246aba4f6fb2c9a28e40e7abb3f2e diff --git a/tgl-fetch.h b/tgl-fetch.h deleted file mode 100644 index 428f32e..0000000 --- a/tgl-fetch.h +++ /dev/null @@ -1,54 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2014 -*/ -#ifndef __TGL_FETCH_H__ -#define __TGL_FETCH_H__ -#include "tgl.h" - -int tglf_fetch_file_location (struct tgl_state *TLS, struct tgl_file_location *loc); -int tglf_fetch_user_status (struct tgl_state *TLS, struct tgl_user_status *S, struct tgl_user *U); -int tglf_fetch_user (struct tgl_state *TLS, struct tgl_user *U); -struct tgl_user *tglf_fetch_alloc_user (struct tgl_state *TLS); -struct tgl_user *tglf_fetch_alloc_user_full (struct tgl_state *TLS); -struct tgl_chat *tglf_fetch_alloc_chat (struct tgl_state *TLS); -struct tgl_chat *tglf_fetch_alloc_chat_full (struct tgl_state *TLS); -struct tgl_secret_chat *tglf_fetch_alloc_encrypted_chat (struct tgl_state *TLS); -struct tgl_message *tglf_fetch_alloc_message (struct tgl_state *TLS); -struct tgl_message *tglf_fetch_alloc_geo_message (struct tgl_state *TLS); -struct tgl_message *tglf_fetch_alloc_message_short (struct tgl_state *TLS); -struct tgl_message *tglf_fetch_alloc_message_short_chat (struct tgl_state *TLS); -struct tgl_message *tglf_fetch_alloc_encrypted_message (struct tgl_state *TLS); -void tglf_fetch_encrypted_message_file (struct tgl_state *TLS, struct tgl_message_media *M); -tgl_peer_id_t tglf_fetch_peer_id (struct tgl_state *TLS); - -void tglf_fetch_message_media (struct tgl_state *TLS, struct tgl_message_media *M); -void tglf_fetch_message_media_encrypted (struct tgl_state *TLS, struct tgl_message_media *M); -void tglf_fetch_message_action (struct tgl_state *TLS, struct tgl_message_action *M); -void tglf_fetch_message_action_encrypted (struct tgl_state *TLS, struct tgl_message_action *M); -void tglf_fetch_photo (struct tgl_state *TLS, struct tgl_photo *P); - -void tglf_fetch_chat (struct tgl_state *TLS, struct tgl_chat *C); -void tglf_fetch_chat_full (struct tgl_state *TLS, struct tgl_chat *C); - -void tglf_fetch_audio (struct tgl_state *TLS, struct tgl_audio *V); -void tglf_fetch_video (struct tgl_state *TLS, struct tgl_video *V); -void tglf_fetch_document (struct tgl_state *TLS, struct tgl_document *V); -void tglf_fetch_message (struct tgl_state *TLS, struct tgl_message *M); -void tglf_fetch_geo_message (struct tgl_state *TLS, struct tgl_message *M); -#endif diff --git a/tgl-inner.h b/tgl-inner.h deleted file mode 100644 index acb3855..0000000 --- a/tgl-inner.h +++ /dev/null @@ -1,31 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2014 -*/ - -#ifndef __TGL_INNER_H__ -#define __TGL_INNER_H__ - -#define vlogprintf(verbosity_level,...) \ - do { \ - if (TLS->verbosity >= verbosity_level) { \ - TLS->callback.logprintf (__VA_ARGS__); \ - } \ - } while (0) - -#endif diff --git a/tgl-layout.h b/tgl-layout.h deleted file mode 100644 index 50177ef..0000000 --- a/tgl-layout.h +++ /dev/null @@ -1,447 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2014 -*/ -#ifndef __TGL_LAYOUT_H__ -#define __TGL_LAYOUT_H__ - -#define FLAG_MESSAGE_EMPTY 1 -#define FLAG_DELETED 2 -#define FLAG_FORBIDDEN 4 -#define FLAG_HAS_PHOTO 8 -#define FLAG_CREATED 16 - -#define FLAG_USER_SELF 128 -#define FLAG_USER_FOREIGN 256 -#define FLAG_USER_CONTACT 512 -#define FLAG_USER_IN_CONTACT 1024 -#define FLAG_USER_OUT_CONTACT 2048 - -#define FLAG_CHAT_IN_CHAT 128 - -#define FLAG_ENCRYPTED 4096 -#define FLAG_PENDING 8192 - -#pragma pack(push,4) - -typedef struct { int type; int id; } tgl_peer_id_t; - -enum tgl_dc_state { - st_init, - st_reqpq_sent, - st_reqdh_sent, - st_client_dh_sent, - st_init_temp, - st_reqpq_sent_temp, - st_reqdh_sent_temp, - st_client_dh_sent_temp, - st_authorized, - st_error -}; - -#define MAX_DC_SESSIONS 3 - -struct tgl_session { - struct tgl_dc *dc; - long long session_id; - int seq_no; - struct connection *c; - struct tree_long *ack_tree; - struct tgl_timer *ev; -}; - -struct tgl_dc { - int id; - int port; - int flags; - enum tgl_dc_state state; - char *ip; - //char *user; - struct tgl_session *sessions[MAX_DC_SESSIONS]; - char auth_key[256]; - char temp_auth_key[256]; - char nonce[256]; - char new_nonce[256]; - char server_nonce[256]; - long long auth_key_id; - long long temp_auth_key_id; - - long long server_salt; - struct tgl_timer *ev; - - int server_time_delta; - double server_time_udelta; - int has_auth; -}; - -enum tgl_message_media_type { - tgl_message_media_none, - tgl_message_media_photo, - tgl_message_media_video, - tgl_message_media_audio, - tgl_message_media_document, - tgl_message_media_geo, - tgl_message_media_contact, - tgl_message_media_unsupported, - tgl_message_media_photo_encr, - tgl_message_media_video_encr, - tgl_message_media_audio_encr, - tgl_message_media_document_encr, -}; - -enum tgl_message_action_type { - tgl_message_action_none, - tgl_message_action_geo_chat_create, - tgl_message_action_geo_chat_checkin, - tgl_message_action_chat_create, - tgl_message_action_chat_edit_title, - tgl_message_action_chat_edit_photo, - tgl_message_action_chat_delete_photo, - tgl_message_action_chat_add_user, - tgl_message_action_chat_delete_user, - tgl_message_action_set_message_ttl, - tgl_message_action_read_messages, - tgl_message_action_delete_messages, - tgl_message_action_screenshot_messages, - tgl_message_action_flush_history, - tgl_message_action_resend, - tgl_message_action_notify_layer, - tgl_message_action_typing -}; - -enum tgl_typing_status { - tgl_typing_none, - tgl_typing_typing, - tgl_typing_cancel, - tgl_typing_record_video, - tgl_typing_upload_video, - tgl_typing_record_audio, - tgl_typing_upload_audio, - tgl_typing_upload_photo, - tgl_typing_upload_document, - tgl_typing_geo, - tgl_typing_choose_contact -}; - -struct tgl_file_location { - int dc; - long long volume; - int local_id; - long long secret; -}; - -struct tgl_photo_size { - char *type; - struct tgl_file_location loc; - int w; - int h; - int size; - char *data; -}; - -struct tgl_geo { - double longitude; - double latitude; -}; - -struct tgl_photo { - long long id; - long long access_hash; - int user_id; - int date; - char *caption; - struct tgl_geo geo; - int sizes_num; - struct tgl_photo_size *sizes; -}; - -struct tgl_encr_photo { - long long id; - long long access_hash; - int dc_id; - int size; - int key_fingerprint; - - unsigned char *key; - unsigned char *iv; - int w; - int h; -}; - -struct tgl_encr_video { - long long id; - long long access_hash; - int dc_id; - int size; - int key_fingerprint; - - unsigned char *key; - unsigned char *iv; - int w; - int h; - int duration; - char *mime_type; -}; - -struct tgl_encr_audio { - long long id; - long long access_hash; - int dc_id; - int size; - int key_fingerprint; - - unsigned char *key; - unsigned char *iv; - int duration; - char *mime_type; -}; - -struct tgl_encr_document { - long long id; - long long access_hash; - int dc_id; - int size; - int key_fingerprint; - - unsigned char *key; - unsigned char *iv; - char *file_name; - char *mime_type; -}; - -struct tgl_encr_file { - char *filename; - unsigned char *key; - unsigned char *iv; -}; - - -struct tgl_user_status { - int online; - int when; - struct tgl_timer *ev; -}; - -struct tgl_user { - tgl_peer_id_t id; - int flags; - struct tgl_message *last; - char *print_name; - int structure_version; - struct tgl_file_location photo_big; - struct tgl_file_location photo_small; - long long photo_id; - struct tgl_photo photo; - char *first_name; - char *last_name; - char *phone; - long long access_hash; - struct tgl_user_status status; - int blocked; - char *real_first_name; - char *real_last_name; - char *username; -}; - -struct tgl_chat_user { - int user_id; - int inviter_id; - int date; -}; - -struct tgl_chat { - tgl_peer_id_t id; - int flags; - struct tgl_message *last; - char *print_title; - int structure_version; - struct tgl_file_location photo_big; - struct tgl_file_location photo_small; - struct tgl_photo photo; - char *title; - int users_num; - int user_list_size; - int user_list_version; - struct tgl_chat_user *user_list; - int date; - int version; - int admin_id; -}; - -enum tgl_secret_chat_state { - sc_none, - sc_waiting, - sc_request, - sc_ok, - sc_deleted -}; - -struct tgl_secret_chat { - tgl_peer_id_t id; - int flags; - struct tgl_message *last; - char *print_name; - int structure_version; - struct tgl_file_location photo_big; - struct tgl_file_location photo_small; - struct tgl_photo photo; - int user_id; - int admin_id; - int date; - int ttl; - int layer; - int in_seq_no; - int out_seq_no; - int last_in_seq_no; - long long access_hash; - unsigned char *g_key; - unsigned char *nonce; - - enum tgl_secret_chat_state state; - int key[64]; - long long key_fingerprint; -}; - -typedef union tgl_peer { - struct { - tgl_peer_id_t id; - int flags; - struct tgl_message *last; - char *print_name; - int structure_version; - struct tgl_file_location photo_big; - struct tgl_file_location photo_small; - struct tgl_photo photo; - }; - struct tgl_user user; - struct tgl_chat chat; - struct tgl_secret_chat encr_chat; -} tgl_peer_t; - -struct tgl_video { - long long id; - long long access_hash; - int user_id; - int date; - int size; - int dc_id; - struct tgl_photo_size thumb; - char *caption; - int duration; - int w; - int h; - char *mime_type; -}; - -struct tgl_audio { - long long id; - long long access_hash; - int user_id; - int date; - int size; - int dc_id; - int duration; - char *mime_type; -}; - -struct tgl_document { - long long id; - long long access_hash; - int user_id; - int date; - int size; - int dc_id; - struct tgl_photo_size thumb; - char *caption; - char *mime_type; -}; - -struct tgl_message_action { - enum tgl_message_action_type type; - union { - struct { - char *title; - int user_num; - int *users; - }; - char *new_title; - struct tgl_photo photo; - int user; - int ttl; - int layer; - int read_cnt; - int delete_cnt; - int screenshot_cnt; - enum tgl_typing_status typing; - struct { - int start_seq_no; - int end_seq_no; - }; - }; -}; - -struct tgl_message_media { - enum tgl_message_media_type type; - union { - struct tgl_photo photo; - struct tgl_video video; - struct tgl_audio audio; - struct tgl_document document; - struct tgl_geo geo; - struct { - char *phone; - char *first_name; - char *last_name; - int user_id; - }; - struct tgl_encr_photo encr_photo; - struct tgl_encr_video encr_video; - struct tgl_encr_audio encr_audio; - struct tgl_encr_document encr_document; - struct tgl_encr_file encr_file; - struct { - void *data; - int data_size; - }; - }; -}; - -struct tgl_message { - struct tgl_message *next_use, *prev_use; - struct tgl_message *next, *prev; - long long id; - int flags; - tgl_peer_id_t fwd_from_id; - int fwd_date; - tgl_peer_id_t from_id; - tgl_peer_id_t to_id; - int out; - int unread; - int date; - int service; - union { - struct tgl_message_action action; - struct { - char *message; - int message_len; - struct tgl_message_media media; - }; - }; -}; -#pragma pack(pop) -#endif diff --git a/tgl-timers.c b/tgl-timers.c deleted file mode 100644 index b78581a..0000000 --- a/tgl-timers.c +++ /dev/null @@ -1,69 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ -#include "config.h" -#ifdef EVENT_V2 -#include -#include -#include -#else -#include -#include "event-old.h" -#endif - -#include "tgl.h" -#include - -static void timer_alarm (evutil_socket_t fd, short what, void *arg) { - void **p = arg; - ((void (*)(struct tgl_state *, void *))p[1]) (p[0], p[2]); -} - -struct tgl_timer *tgl_timer_alloc (struct tgl_state *TLS, void (*cb)(struct tgl_state *TLS, void *arg), void *arg) { - void **p = malloc (sizeof (void *) * 3); - p[0] = TLS; - p[1] = cb; - p[2] = arg; - return (void *)evtimer_new (TLS->ev_base, timer_alarm, p); -} - -void tgl_timer_insert (struct tgl_timer *t, double p) { - if (p < 0) { p = 0; } - double e = p - (int)p; - if (e < 0) { e = 0; } - struct timeval pv = { (int)p, (int)(e * 1e6)}; - event_add ((void *)t, &pv); -} - -void tgl_timer_delete (struct tgl_timer *t) { - event_del ((void *)t); -} - -void tgl_timer_free (struct tgl_timer *t) { - void *arg = event_get_callback_arg ((void *)t); - free (arg); - event_free ((void *)t); -} - -struct tgl_timer_methods tgl_libevent_timers = { - .alloc = tgl_timer_alloc, - .insert = tgl_timer_insert, - .delete = tgl_timer_delete, - .free = tgl_timer_free -}; diff --git a/tgl-timers.h b/tgl-timers.h deleted file mode 100644 index 052dd56..0000000 --- a/tgl-timers.h +++ /dev/null @@ -1,27 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifndef __TGL_TIMERS_H__ -#define __TGL_TIMERS_H__ - -#include "tgl.h" -extern struct tgl_timer_methods tgl_libevent_timers; - -#endif diff --git a/tgl.c b/tgl.c deleted file mode 100644 index c6a1d77..0000000 --- a/tgl.c +++ /dev/null @@ -1,86 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "tgl.h" -#include "tools.h" -#include "mtproto-client.h" -#include "structures.h" -//#include "net.h" - -#include - -struct tgl_state tgl_state; - - -void tgl_set_binlog_mode (struct tgl_state *TLS, int mode) { - TLS->binlog_enabled = mode; -} - -void tgl_set_binlog_path (struct tgl_state *TLS, const char *path) { - TLS->binlog_name = tstrdup (path); -} - -void tgl_set_auth_file_path (struct tgl_state *TLS, const char *path) { - TLS->auth_file = tstrdup (path); -} - -void tgl_set_download_directory (struct tgl_state *TLS, const char *path) { - TLS->downloads_directory = tstrdup (path); -} - -void tgl_set_callback (struct tgl_state *TLS, struct tgl_update_callback *cb) { - TLS->callback = *cb; -} - -void tgl_set_rsa_key (struct tgl_state *TLS, const char *key) { - assert (TLS->rsa_key_num < TGL_MAX_RSA_KEYS_NUM); - TLS->rsa_key_list[TLS->rsa_key_num ++] = tstrdup (key); -} - -void tgl_init (struct tgl_state *TLS) { - assert (TLS->timer_methods); - assert (TLS->net_methods); - if (!TLS->callback.create_print_name) { - TLS->callback.create_print_name = tgls_default_create_print_name; - } - if (!TLS->temp_key_expire_time) { - TLS->temp_key_expire_time = 100000; - } - - TLS->message_list.next_use = &TLS->message_list; - TLS->message_list.prev_use = &TLS->message_list; - - tglmp_on_start (TLS); -} - -int tgl_authorized_dc (struct tgl_state *TLS, struct tgl_dc *DC) { - assert (DC); - return (DC->flags & 4) != 0;//DC->auth_key_id; -} - -int tgl_signed_dc (struct tgl_state *TLS, struct tgl_dc *DC) { - assert (DC); - return DC->has_auth; -} - diff --git a/tgl.h b/tgl.h deleted file mode 100644 index 33e19b5..0000000 --- a/tgl.h +++ /dev/null @@ -1,395 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2014 -*/ -#ifndef __TGL_H__ -#define __TGL_H__ - -#include -#include -#include - -#define TGL_MAX_DC_NUM 100 -#define TG_SERVER_1 "173.240.5.1" -#define TG_SERVER_2 "149.154.167.51" -#define TG_SERVER_3 "174.140.142.6" -#define TG_SERVER_4 "149.154.167.91" -#define TG_SERVER_5 "149.154.171.5" -#define TG_SERVER_DEFAULT 4 - -#define TG_SERVER_TEST_1 "173.240.5.253" -#define TG_SERVER_TEST_2 "149.154.167.40" -#define TG_SERVER_TEST_3 "174.140.142.5" -#define TG_SERVER_TEST_DEFAULT 2 - -// JUST RANDOM STRING -#define TGL_BUILD "2590" -#define TGL_VERSION "1.1.0" - -#define TGL_ENCRYPTED_LAYER 17 - -struct connection; -struct mtproto_methods; -struct tgl_session; -struct tgl_dc; - -#define TGL_UPDATE_CREATED 1 -#define TGL_UPDATE_DELETED 2 -#define TGL_UPDATE_PHONE 4 -#define TGL_UPDATE_CONTACT 8 -#define TGL_UPDATE_PHOTO 16 -#define TGL_UPDATE_BLOCKED 32 -#define TGL_UPDATE_REAL_NAME 64 -#define TGL_UPDATE_NAME 128 -#define TGL_UPDATE_REQUESTED 256 -#define TGL_UPDATE_WORKING 512 -#define TGL_UPDATE_FLAGS 1024 -#define TGL_UPDATE_TITLE 2048 -#define TGL_UPDATE_ADMIN 4096 -#define TGL_UPDATE_MEMBERS 8192 -#define TGL_UPDATE_ACCESS_HASH 16384 -#define TGL_UPDATE_USERNAME (1 << 15) - -struct tgl_allocator { - void *(*alloc)(size_t size); - void *(*realloc)(void *ptr, size_t old_size, size_t size); - void (*free)(void *ptr, int size); - void (*check)(void); - void (*exists)(void *ptr, int size); -}; -extern struct tgl_allocator tgl_allocator_release; -extern struct tgl_allocator tgl_allocator_debug; -struct tgl_state; - -struct tgl_update_callback { - void (*new_msg)(struct tgl_state *TLS, struct tgl_message *M); - void (*marked_read)(struct tgl_state *TLS, int num, struct tgl_message *list[]); - void (*logprintf)(const char *format, ...) __attribute__ ((format (printf, 1, 2))); - void (*type_notification)(struct tgl_state *TLS, struct tgl_user *U, enum tgl_typing_status status); - void (*type_in_chat_notification)(struct tgl_state *TLS, struct tgl_user *U, struct tgl_chat *C, enum tgl_typing_status status); - void (*type_in_secret_chat_notification)(struct tgl_state *TLS, struct tgl_secret_chat *E); - void (*status_notification)(struct tgl_state *TLS, struct tgl_user *U); - void (*user_registered)(struct tgl_state *TLS, struct tgl_user *U); - void (*user_activated)(struct tgl_state *TLS, struct tgl_user *U); - void (*new_authorization)(struct tgl_state *TLS, const char *device, const char *location); - void (*chat_update)(struct tgl_state *TLS, struct tgl_chat *C, unsigned flags); - void (*user_update)(struct tgl_state *TLS, struct tgl_user *C, unsigned flags); - void (*secret_chat_update)(struct tgl_state *TLS, struct tgl_secret_chat *C, unsigned flags); - void (*msg_receive)(struct tgl_state *TLS, struct tgl_message *M); - void (*our_id)(struct tgl_state *TLS, int id); - void (*notification)(struct tgl_state *TLS, char *type, char *message); - void (*user_status_update)(struct tgl_state *TLS, struct tgl_user *U); - char *(*create_print_name) (struct tgl_state *TLS, tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4); -}; - -struct tgl_net_methods { - int (*write_out) (struct connection *c, const void *data, int len); - int (*read_in) (struct connection *c, void *data, int len); - int (*read_in_lookup) (struct connection *c, void *data, int len); - void (*flush_out) (struct connection *c); - void (*incr_out_packet_num) (struct connection *c); - void (*free) (struct connection *c); - struct tgl_dc *(*get_dc) (struct connection *c); - struct tgl_session *(*get_session) (struct connection *c); - - struct connection *(*create_connection) (struct tgl_state *TLS, const char *host, int port, struct tgl_session *session, struct tgl_dc *dc, struct mtproto_methods *methods); -}; - -struct mtproto_methods { - int (*ready) (struct tgl_state *TLS, struct connection *c); - int (*close) (struct tgl_state *TLS, struct connection *c); - int (*execute) (struct tgl_state *TLS, struct connection *c, int op, int len); -}; - -struct tgl_timer; - -struct tgl_timer_methods { - struct tgl_timer *(*alloc) (struct tgl_state *TLS, void (*cb)(struct tgl_state *TLS, void *arg), void *arg); - void (*insert) (struct tgl_timer *t, double timeout); - void (*delete) (struct tgl_timer *t); - void (*free) (struct tgl_timer *t); -}; - -#define E_ERROR 0 -#define E_WARNING 1 -#define E_NOTICE 2 -#define E_DEBUG 6 - -#define TGL_LOCK_DIFF 1 - -#define TGL_MAX_RSA_KEYS_NUM 10 -// Do not modify this structure, unless you know what you do - -#pragma pack(push,4) -struct tgl_state { - int our_id; // ID of logged in user - int encr_root; - unsigned char *encr_prime; - int encr_param_version; - int pts; - int qts; - int date; - int seq; - int binlog_enabled; - int test_mode; - int verbosity; - int unread_messages; - int active_queries; - int max_msg_id; - int started; - - long long locks; - struct tgl_dc *DC_list[TGL_MAX_DC_NUM]; - struct tgl_dc *DC_working; - int max_dc_num; - int dc_working_num; - int enable_pfs; - int temp_key_expire_time; - - long long cur_uploading_bytes; - long long cur_uploaded_bytes; - long long cur_downloading_bytes; - long long cur_downloaded_bytes; - - char *binlog_name; - char *auth_file; - char *downloads_directory; - - struct tgl_update_callback callback; - struct tgl_net_methods *net_methods; - void *ev_base; - - char *rsa_key_list[TGL_MAX_RSA_KEYS_NUM]; - int rsa_key_num; - struct bignum_ctx *BN_ctx; - - struct tgl_allocator allocator; - - struct tree_peer *peer_tree; - struct tree_peer_by_name *peer_by_name_tree; - struct tree_message *message_tree; - struct tree_message *message_unsent_tree; - - int users_allocated; - int chats_allocated; - int messages_allocated; - int peer_num; - int peer_size; - int encr_chats_allocated; - int geo_chats_allocated; - - tgl_peer_t **Peers; - struct tgl_message message_list; - - int binlog_fd; - - struct tgl_timer_methods *timer_methods; - - void *pubKey; - - struct tree_query *queries_tree; - - char *base_path; - - struct tree_user *online_updates; - - struct tgl_timer *online_updates_timer; -}; -#pragma pack(pop) -//extern struct tgl_state tgl_state; - -void tgl_reopen_binlog_for_writing (struct tgl_state *TLS); -void tgl_replay_log (struct tgl_state *TLS); - -int tgl_print_stat (struct tgl_state *TLS, char *s, int len); -tgl_peer_t *tgl_peer_get (struct tgl_state *TLS, tgl_peer_id_t id); -tgl_peer_t *tgl_peer_get_by_name (struct tgl_state *TLS, const char *s); - -struct tgl_message *tgl_message_get (struct tgl_state *TLS, long long id); -void tgl_peer_iterator_ex (struct tgl_state *TLS, void (*it)(tgl_peer_t *P, void *extra), void *extra); - -int tgl_complete_user_list (struct tgl_state *TLS, int index, const char *text, int len, char **R); -int tgl_complete_chat_list (struct tgl_state *TLS, int index, const char *text, int len, char **R); -int tgl_complete_encr_chat_list (struct tgl_state *TLS, int index, const char *text, int len, char **R); -int tgl_complete_peer_list (struct tgl_state *TLS, int index, const char *text, int len, char **R); - -#define TGL_PEER_USER 1 -#define TGL_PEER_CHAT 2 -#define TGL_PEER_GEO_CHAT 3 -#define TGL_PEER_ENCR_CHAT 4 -#define TGL_PEER_UNKNOWN 0 - -#define TGL_MK_USER(id) tgl_set_peer_id (TGL_PEER_USER,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_ENCR_CHAT(id) tgl_set_peer_id (TGL_PEER_ENCR_CHAT,id) - -void tgl_set_binlog_mode (struct tgl_state *TLS, int mode); -void tgl_set_binlog_path (struct tgl_state *TLS, const char *path); -void tgl_set_auth_file_path (struct tgl_state *TLS, const char *path); -void tgl_set_download_directory (struct tgl_state *TLS, const char *path); -void tgl_set_callback (struct tgl_state *TLS, struct tgl_update_callback *cb); -void tgl_set_rsa_key (struct tgl_state *TLS, const char *key); - - -static inline int tgl_get_peer_type (tgl_peer_id_t id) { - return id.type; -} - -static inline int tgl_get_peer_id (tgl_peer_id_t id) { - return id.id; -} - -static inline tgl_peer_id_t tgl_set_peer_id (int type, int id) { - tgl_peer_id_t ID; - ID.id = id; - ID.type = type; - return ID; -} - -static inline int tgl_cmp_peer_id (tgl_peer_id_t a, tgl_peer_id_t b) { - return memcmp (&a, &b, sizeof (a)); -} - -static inline void tgl_incr_verbosity (struct tgl_state *TLS) { - TLS->verbosity ++; -} - -static inline void tgl_set_verbosity (struct tgl_state *TLS, int val) { - TLS->verbosity = val; -} - -static inline void tgl_enable_pfs (struct tgl_state *TLS) { - TLS->enable_pfs = 1; -} - -static inline void tgl_set_test_mode (struct tgl_state *TLS) { - TLS->test_mode ++; -} - -static inline void tgl_set_net_methods (struct tgl_state *TLS, struct tgl_net_methods *methods) { - TLS->net_methods = methods; -} - -static inline void tgl_set_timer_methods (struct tgl_state *TLS, struct tgl_timer_methods *methods) { - TLS->timer_methods = methods; -} - -static inline void tgl_set_ev_base (struct tgl_state *TLS, void *ev_base) { - TLS->ev_base = ev_base; -} - -//struct pollfd; -//int tgl_connections_make_poll_array (struct tgl_state *TLS, struct pollfd *fds, int max); -//void tgl_connections_poll_result (struct tgl_state *TLS, struct pollfd *fds, int max); - -void tgl_do_help_get_config (struct tgl_state *TLS, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_send_code (struct tgl_state *TLS, const char *user, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int registered, const char *hash), void *callback_extra); -void tgl_do_phone_call (struct tgl_state *TLS, const char *user, const char *hash, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -int tgl_do_send_code_result (struct tgl_state *TLS, const char *user, const char *hash, const char *code, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) ; -int tgl_do_send_code_result_auth (struct tgl_state *TLS, const char *user, const char *hash, const char *code, const char *first_name, const char *last_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *Self), void *callback_extra); -void tgl_do_update_contact_list (struct tgl_state *TLS, void (*callback) (struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_user *contacts[]), void *callback_extra); -void tgl_do_send_message (struct tgl_state *TLS, tgl_peer_id_t id, const char *msg, int len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_send_msg (struct tgl_state *TLS, struct tgl_message *M, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_send_text (struct tgl_state *TLS, tgl_peer_id_t id, char *file, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_mark_read (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_get_history (struct tgl_state *TLS, tgl_peer_id_t id, int limit, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra); -void tgl_do_get_history_ext (struct tgl_state *TLS, tgl_peer_id_t id, int offset, int limit, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra); -void tgl_do_get_dialog_list (struct tgl_state *TLS, void (*callback)(struct tgl_state *TLS, 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_send_photo (struct tgl_state *TLS, enum tgl_message_media_type type, tgl_peer_id_t to_id, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_set_chat_photo (struct tgl_state *TLS, tgl_peer_id_t chat_id, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_set_profile_photo (struct tgl_state *TLS, char *file_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_set_profile_name (struct tgl_state *TLS, char *first_name, char *last_name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra); -void tgl_do_set_username (struct tgl_state *TLS, char *name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra); -void tgl_do_forward_message (struct tgl_state *TLS, tgl_peer_id_t id, int n, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_rename_chat (struct tgl_state *TLS, tgl_peer_id_t id, char *name, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_get_chat_info (struct tgl_state *TLS, tgl_peer_id_t id, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_chat *C), void *callback_extra); -void tgl_do_get_user_info (struct tgl_state *TLS, tgl_peer_id_t id, int offline_mode, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra); -void tgl_do_load_photo (struct tgl_state *TLS, struct tgl_photo *photo, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_video_thumb (struct tgl_state *TLS, struct tgl_video *video, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_audio (struct tgl_state *TLS, struct tgl_audio *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_video (struct tgl_state *TLS, struct tgl_video *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_document (struct tgl_state *TLS, struct tgl_document *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_document_thumb (struct tgl_state *TLS, struct tgl_document *video, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_load_encr_video (struct tgl_state *TLS, struct tgl_encr_video *V, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *filename), void *callback_extra); -void tgl_do_export_auth (struct tgl_state *TLS, int num, void (*callback) (struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_add_contact (struct tgl_state *TLS, 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)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra); -void tgl_do_msg_search (struct tgl_state *TLS, tgl_peer_id_t id, int from, int to, int limit, int offset, const char *s, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra); -//void tgl_do_contacts_search (int limit, const char *s, void (*callback) (struct tgl_state *TLS, void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra); -void tgl_do_create_encr_chat_request (struct tgl_state *TLS, int user_id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra); -void tgl_do_create_secret_chat (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra); -void tgl_do_accept_encr_chat_request (struct tgl_state *TLS, struct tgl_secret_chat *E, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra); -void tgl_do_get_difference (struct tgl_state *TLS, int sync_from_start, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_lookup_state (struct tgl_state *TLS); -void tgl_do_add_user_to_chat (struct tgl_state *TLS, tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_del_user_from_chat (struct tgl_state *TLS, tgl_peer_id_t chat_id, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_create_group_chat (struct tgl_state *TLS, tgl_peer_id_t id, char *chat_topic, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_create_group_chat_ex (struct tgl_state *TLS, int users_num, tgl_peer_id_t ids[], char *chat_topic, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_delete_msg (struct tgl_state *TLS, long long id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_restore_msg (struct tgl_state *TLS, long long id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_update_status (struct tgl_state *TLS, int online, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_help_get_config_dc (struct tgl_state *TLS, struct tgl_dc *D, void (*callback)(struct tgl_state *TLS, void *, int), void *callback_extra); -void tgl_do_export_card (struct tgl_state *TLS, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int size, int *card), void *callback_extra); -void tgl_do_import_card (struct tgl_state *TLS, int size, int *card, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_user *U), void *callback_extra); -void tgl_do_send_contact (struct tgl_state *TLS, tgl_peer_id_t id, const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_forward_media (struct tgl_state *TLS, tgl_peer_id_t id, int n, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_del_contact (struct tgl_state *TLS, tgl_peer_id_t id, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success), void *callback_extra); -void tgl_do_set_encr_chat_ttl (struct tgl_state *TLS, struct tgl_secret_chat *E, int ttl, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_send_location (struct tgl_state *TLS, tgl_peer_id_t id, double latitude, double longitude, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, struct tgl_message *M), void *callback_extra); -void tgl_do_contact_search (struct tgl_state *TLS, char *name, int limit, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, int cnt, struct tgl_user *U[]), void *callback_extra); - - -void tgl_do_visualize_key (struct tgl_state *TLS, tgl_peer_id_t id, unsigned char buf[16]); - -void tgl_do_send_ping (struct tgl_state *TLS, struct connection *c); - -void tgl_do_send_extf (struct tgl_state *TLS, char *data, int data_len, void (*callback)(struct tgl_state *TLS, void *callback_extra, int success, char *data), void *callback_extra); - -int tgl_authorized_dc (struct tgl_state *TLS, struct tgl_dc *DC); -int tgl_signed_dc (struct tgl_state *TLS, struct tgl_dc *DC); - -//void tgl_do_get_suggested (void); - -void tgl_do_create_keys_end (struct tgl_state *TLS, struct tgl_secret_chat *U); -void tgl_do_send_encr_chat_layer (struct tgl_state *TLS, struct tgl_secret_chat *E); - -void tgl_init (struct tgl_state *TLS); -void tgl_dc_authorize (struct tgl_state *TLS, struct tgl_dc *DC); - -void tgl_dc_iterator (struct tgl_state *TLS, void (*iterator)(struct tgl_dc *DC)); -void tgl_dc_iterator_ex (struct tgl_state *TLS, void (*iterator)(struct tgl_dc *DC, void *extra), void *extra); - -double tglt_get_double_time (void); - -void tgl_insert_empty_user (struct tgl_state *TLS, int id); -void tgl_insert_empty_chat (struct tgl_state *TLS, int id); - -int tglf_extf_autocomplete (struct tgl_state *TLS, const char *text, int text_len, int index, char **R, char *data, int data_len); -struct paramed_type *tglf_extf_store (struct tgl_state *TLS, const char *data, int data_len); -char *tglf_extf_fetch (struct tgl_state *TLS, struct paramed_type *T); - -void tgl_free_all (struct tgl_state *TLS); - -static inline struct tgl_state *tgl_state_alloc (void) { - struct tgl_state *TLS = malloc (sizeof (*TLS)); - if (!TLS) { return NULL; } - memset (TLS, 0, sizeof (*TLS)); - return TLS; -} - -#endif diff --git a/tools.c b/tools.c deleted file mode 100644 index 9447858..0000000 --- a/tools.c +++ /dev/null @@ -1,297 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#define _GNU_SOURCE - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -//#include "interface.h" -#include "tools.h" - -#ifdef __MACH__ -#include -#include -#endif - -#ifdef __MACH__ -#define CLOCK_REALTIME 0 -#define CLOCK_MONOTONIC 1 -#endif - -#define RES_PRE 8 -#define RES_AFTER 8 -#define MAX_BLOCKS 1000000 -static void *blocks[MAX_BLOCKS]; -static void *free_blocks[MAX_BLOCKS]; -static int used_blocks; -static int free_blocks_cnt; - -static long long total_allocated_bytes; - -void logprintf (const char *format, ...) __attribute__ ((format (printf, 1, 2), weak)); -void logprintf (const char *format, ...) { - va_list ap; - va_start (ap, format); - vfprintf (stdout, format, ap); - va_end (ap); -} - -//extern int verbosity; - -//static long long total_allocated_bytes; - -int tgl_snprintf (char *buf, int len, const char *format, ...) { - va_list ap; - va_start (ap, format); - int r = vsnprintf (buf, len, format, ap); - va_end (ap); - assert (r <= len && "tsnprintf buffer overflow"); - return r; -} - -int tgl_asprintf (char **res, const char *format, ...) { - va_list ap; - va_start (ap, format); - int r = vasprintf (res, format, ap); - assert (r >= 0); - va_end (ap); - void *rs = talloc (strlen (*res) + 1); - memcpy (rs, *res, strlen (*res) + 1); - free (*res); - *res = rs; - return r; -} - -void tgl_free_debug (void *ptr, int size __attribute__ ((unused))) { - total_allocated_bytes -= size; - ptr -= RES_PRE; - if (size != (int)((*(int *)ptr) ^ 0xbedabeda)) { - logprintf ("size = %d, ptr = %d\n", size, (*(int *)ptr) ^ 0xbedabeda); - } - assert (*(int *)ptr == (int)((size) ^ 0xbedabeda)); - assert (*(int *)(ptr + RES_PRE + size) == (int)((size) ^ 0x7bed7bed)); - assert (*(int *)(ptr + 4) == size); - int block_num = *(int *)(ptr + 4 + RES_PRE + size); - if (block_num >= used_blocks) { - logprintf ("block_num = %d, used = %d\n", block_num, used_blocks); - } - assert (block_num < used_blocks); - if (block_num < used_blocks - 1) { - void *p = blocks[used_blocks - 1]; - int s = (*(int *)p) ^ 0xbedabeda; - *(int *)(p + 4 + RES_PRE + s) = block_num; - blocks[block_num] = p; - } - blocks[--used_blocks] = 0; - memset (ptr, 0, size + RES_PRE + RES_AFTER); - *(int *)ptr = size + 12; - free_blocks[free_blocks_cnt ++] = ptr; -} - -void tgl_free_release (void *ptr, int size) { - free (ptr); -} - - - -void *tgl_realloc_debug (void *ptr, size_t old_size __attribute__ ((unused)), size_t size) { - void *p = talloc (size); - memcpy (p, ptr, size >= old_size ? old_size : size); - tfree (ptr, old_size); - return p; -} - -void *tgl_realloc_release (void *ptr, size_t old_size __attribute__ ((unused)), size_t size) { - void *p = realloc (ptr, size); - ensure_ptr (p); - return p; -} - -void *tgl_alloc_debug (size_t size) { - total_allocated_bytes += size; - void *p = malloc (size + RES_PRE + RES_AFTER); - ensure_ptr (p); - *(int *)p = size ^ 0xbedabeda; - *(int *)(p + 4) = size; - *(int *)(p + RES_PRE + size) = size ^ 0x7bed7bed; - *(int *)(p + RES_AFTER + 4 + size) = used_blocks; - blocks[used_blocks ++] = p; - - if (used_blocks - 1 == 24867) { - assert (0); - } - tcheck (); - return p + 8; -} - -void *tgl_alloc_release (size_t size) { - void *p = malloc (size); - ensure_ptr (p); - return p; -} - -void *tgl_alloc0 (size_t size) { - void *p = talloc (size); - memset (p, 0, size); - return p; -} - -char *tgl_strdup (const char *s) { - int l = strlen (s); - char *p = talloc (l + 1); - memcpy (p, s, l + 1); - return p; -} - -char *tgl_strndup (const char *s, size_t n) { - size_t l = 0; - for (l = 0; l < n && s[l]; l++) { } - char *p = talloc (l + 1); - memcpy (p, s, l); - p[l] = 0; - return p; -} - - -int tgl_inflate (void *input, int ilen, void *output, int olen) { - z_stream strm; - memset (&strm, 0, sizeof (strm)); - assert (inflateInit2 (&strm, 16 + MAX_WBITS) == Z_OK); - strm.avail_in = ilen; - strm.next_in = input; - strm.avail_out = olen ; - strm.next_out = output; - int err = inflate (&strm, Z_FINISH); - int total_out = strm.total_out; - - if (err != Z_OK && err != Z_STREAM_END) { - logprintf ( "inflate error = %d\n", err); - logprintf ( "inflated %d bytes\n", (int) strm.total_out); - total_out = 0; - } - inflateEnd (&strm); - return total_out; -} - -void tgl_check_debug (void) { - int i; - for (i = 0; i < used_blocks; i++) { - void *ptr = blocks[i]; - int size = (*(int *)ptr) ^ 0xbedabeda; - if (!(*(int *)(ptr + 4) == size) || - !(*(int *)(ptr + RES_PRE + size) == (size ^ 0x7bed7bed)) || - !(*(int *)(ptr + RES_PRE + 4 + size) == i)) { - logprintf ("Bad block at address %p (size %d, num %d)\n", ptr, size, i); - assert (0 && "Bad block"); - } - } - for (i = 0; i < free_blocks_cnt; i++) { - void *ptr = free_blocks[i]; - int l = *(int *)ptr; - int j = 0; - for (j = 0; j < l; j++) { - if (*(char *)(ptr + 4 + j)) { - hexdump (ptr + 8, ptr + 8 + l + ((-l) & 3)); - logprintf ("Used freed memory size = %d. ptr = %p\n", l + 4 - RES_PRE - RES_AFTER, ptr); - assert (0); - } - } - } - //logprintf ("ok. Used_blocks = %d. Free blocks = %d\n", used_blocks, free_blocks_cnt); -} - -void tgl_exists_debug (void *ptr, int size) { - ptr -= RES_PRE; - if (size != (int)((*(int *)ptr) ^ 0xbedabeda)) { - logprintf ("size = %d, ptr = %d\n", size, (*(int *)ptr) ^ 0xbedabeda); - } - assert (*(int *)ptr == (int)((size) ^ 0xbedabeda)); - assert (*(int *)(ptr + RES_PRE + size) == (int)((size) ^ 0x7bed7bed)); - assert (*(int *)(ptr + 4) == size); - int block_num = *(int *)(ptr + 4 + RES_PRE + size); - if (block_num >= used_blocks) { - logprintf ("block_num = %d, used = %d\n", block_num, used_blocks); - } - assert (block_num < used_blocks); -} - -void tgl_exists_release (void *ptr, int size) {} -void tgl_check_release (void) {} - -void tgl_my_clock_gettime (int clock_id, struct timespec *T) { -#ifdef __MACH__ - // We are ignoring MONOTONIC and hope time doesn't go back too often - clock_serv_t cclock; - mach_timespec_t mts; - host_get_clock_service(mach_host_self(), CALENDAR_CLOCK, &cclock); - clock_get_time(cclock, &mts); - mach_port_deallocate(mach_task_self(), cclock); - T->tv_sec = mts.tv_sec; - T->tv_nsec = mts.tv_nsec; -#else - assert (clock_gettime(clock_id, T) >= 0); -#endif -} - -double tglt_get_double_time (void) { - struct timespec tv; - tgl_my_clock_gettime (CLOCK_REALTIME, &tv); - return tv.tv_sec + 1e-9 * tv.tv_nsec; -} - -void tglt_secure_random (void *s, int l) { - if (RAND_bytes (s, l) <= 0) { - /*if (allow_weak_random) { - RAND_pseudo_bytes (s, l); - } else {*/ - assert (0 && "End of random. If you want, you can start with -w"); - //} - } -} - -struct tgl_allocator tgl_allocator_debug = { - .alloc = tgl_alloc_debug, - .realloc = tgl_realloc_debug, - .free = tgl_free_debug, - .check = tgl_check_debug, - .exists = tgl_exists_debug -}; - -struct tgl_allocator tgl_allocator_release = { - .alloc = tgl_alloc_release, - .realloc = tgl_realloc_release, - .free = tgl_free_release, - .check = tgl_check_release, - .exists = tgl_exists_release -}; - -struct tgl_allocator *tgl_allocator = &tgl_allocator_release; diff --git a/tools.h b/tools.h deleted file mode 100644 index cf20027..0000000 --- a/tools.h +++ /dev/null @@ -1,119 +0,0 @@ -/* - This file is part of telegram-client. - - Telegram-client is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 2 of the License, or - (at your option) any later version. - - Telegram-client is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this telegram-client. If not, see . - - Copyright Vitaly Valtman 2013 -*/ - -#ifndef __TOOLS_H__ -#define __TOOLS_H__ -#include -#include -#include -#include "tgl.h" - -#define talloc tgl_allocator->alloc -#define talloc0 tgl_alloc0 -#define tfree tgl_allocator->free -#define tfree_str tgl_free_str -#define tfree_secure tgl_free_secure -#define trealloc tgl_allocator->realloc -#define tcheck tgl_allocator->check -#define texists tgl_allocator->exists -#define tstrdup tgl_strdup -#define tstrndup tgl_strndup -#define tasprintf tgl_asprintf -#define tsnprintf tgl_snprintf - - -struct tgl_allocator *tgl_allocator; -double tglt_get_double_time (void); - -int tgl_inflate (void *input, int ilen, void *output, int olen); -//void ensure (int r); -//void ensure_ptr (void *p); - -static inline void out_of_memory (void) { - fprintf (stderr, "Out of memory\n"); - exit (1); -} - -static inline void ensure (int r) { - if (!r) { - fprintf (stderr, "Open SSL error\n"); - ERR_print_errors_fp (stderr); - assert (0); - } -} - -static inline void ensure_ptr (void *p) { - if (p == NULL) { - out_of_memory (); - } -} - -void *tgl_alloc_debug (size_t size); -void *tgl_alloc_release (size_t size); - -void *tgl_realloc_debug (void *ptr, size_t old_size, size_t size); -void *tgl_realloc_release (void *ptr, size_t old_size, size_t size); - -void *tgl_alloc0 (size_t size); -char *tgl_strdup (const char *s); -char *tgl_strndup (const char *s, size_t n); - -void tgl_free_debug (void *ptr, int size); -void tgl_free_release (void *ptr, int size); -//void tgl_free_str (void *ptr); -//void tgl_free_secure (void *ptr, int size); - -void tgl_check_debug (void); -void tgl_exists_debug (void *ptr, int size); -void tgl_check_release (void); -void tgl_exists_release (void *ptr, int size); - - -int tgl_snprintf (char *buf, int len, const char *format, ...) __attribute__ ((format (printf, 3, 4))); -int tgl_asprintf (char **res, const char *format, ...) __attribute__ ((format (printf, 2, 3))); - -void tglt_secure_random (void *s, int l); -void tgl_my_clock_gettime (int clock_id, struct timespec *T); - -static inline void tgl_free_str (void *ptr) { - if (!ptr) { return; } - tfree (ptr, strlen (ptr) + 1); -} - -static inline void tgl_free_secure (void *ptr, int size) { - memset (ptr, 0, size); - tfree (ptr, size); -} - -static inline void hexdump (void *ptr, void *end_ptr) { - int total = 0; - while (ptr < end_ptr) { - fprintf (stderr, "%08x", (int)*(char *)ptr); - ptr ++; - total ++; - if (total == 16) { - fprintf (stderr, "\n"); - total = 0; - } - } - if (total) { fprintf (stderr, "\n"); } -} - - -#endif diff --git a/updates.c b/updates.c deleted file mode 100644 index d01bfdc..0000000 --- a/updates.c +++ /dev/null @@ -1,594 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ -#include "tgl.h" -#include "updates.h" -#include "mtproto-common.h" -#include "binlog.h" -#include "auto.h" -#include "structures.h" -#include "tree.h" - -#include - -void tglu_fetch_pts (struct tgl_state *TLS) { - int p = fetch_int (); - if (p <= TLS->pts) { return; } - bl_do_set_pts (TLS, p); -} - -void tglu_fetch_qts (struct tgl_state *TLS) { - int p = fetch_int (); - if (p <= TLS->qts) { return; } - bl_do_set_qts (TLS, p); -} - -void tglu_fetch_date (struct tgl_state *TLS) { - int p = fetch_int (); - if (p > TLS->date) { - //TLS->date = p; - bl_do_set_date (TLS, TLS->date); - } -} - -static void fetch_dc_option (struct tgl_state *TLS) { - assert (fetch_int () == CODE_dc_option); - int id = fetch_int (); - int l1 = prefetch_strlen (); - char *name = fetch_str (l1); - int l2 = prefetch_strlen (); - char *ip = fetch_str (l2); - int port = fetch_int (); - vlogprintf (E_DEBUG, "id = %d, name = %.*s ip = %.*s port = %d\n", id, l1, name, l2, ip, port); - - bl_do_dc_option (TLS, id, l1, name, l2, ip, port); -} - -void tglu_work_update (struct tgl_state *TLS, struct connection *c, long long msg_id) { - unsigned op = fetch_int (); - switch (op) { - case CODE_update_new_message: - { - struct tgl_message *M = tglf_fetch_alloc_message (TLS); - assert (M); - tglu_fetch_pts (TLS); - bl_do_msg_update (TLS, M->id); - break; - }; - case CODE_update_message_i_d: - { - int id = fetch_int (); // id - int new = fetch_long (); // random_id - struct tgl_message *M = tgl_message_get (TLS, new); - if (M) { - bl_do_set_msg_id (TLS, M, id); - } - } - break; - case CODE_update_read_messages: - { - assert (fetch_int () == (int)CODE_vector); - int n = fetch_int (); - - //int p = 0; - int i; - for (i = 0; i < n; i++) { - int id = fetch_int (); - struct tgl_message *M = tgl_message_get (TLS, id); - if (M) { - bl_do_set_unread (TLS, M, 0); - } - } - tglu_fetch_pts (TLS); - } - break; - case CODE_update_user_typing: - { - //vlogprintf (E_ERROR, "user typing\n"); - tgl_peer_id_t id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *U = tgl_peer_get (TLS, id); - enum tgl_typing_status status = tglf_fetch_typing (); - - if (TLS->callback.type_notification && U) { - TLS->callback.type_notification (TLS, (void *)U, status); - } - } - break; - case CODE_update_chat_user_typing: - { - //vlogprintf (E_ERROR, "chat typing\n"); - tgl_peer_id_t chat_id = TGL_MK_CHAT (fetch_int ()); - tgl_peer_id_t id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *C = tgl_peer_get (TLS, chat_id); - tgl_peer_t *U = tgl_peer_get (TLS, id); - enum tgl_typing_status status = tglf_fetch_typing (); - - if (U && C) { - if (TLS->callback.type_in_chat_notification) { - TLS->callback.type_in_chat_notification (TLS, (void *)U, (void *)C, status); - } - } - } - break; - case CODE_update_user_status: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *U = tgl_peer_get (TLS, user_id); - if (U) { - tglf_fetch_user_status (TLS, &U->user.status, &U->user); - - if (TLS->callback.status_notification) { - TLS->callback.status_notification (TLS, (void *)U); - } - } else { - assert (skip_type_any (TYPE_TO_PARAM (user_status)) >= 0); - } - } - break; - case CODE_update_user_name: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *UC = tgl_peer_get (TLS, user_id); - if (UC && (UC->flags & FLAG_CREATED)) { - int l1 = prefetch_strlen (); - char *f = fetch_str (l1); - int l2 = prefetch_strlen (); - char *l = fetch_str (l2); - struct tgl_user *U = &UC->user; - bl_do_user_set_real_name (TLS, U, f, l1, l, l2); - int l3 = prefetch_strlen (); - f = fetch_str (l3); - bl_do_user_set_username (TLS, U, f, l3); - } else { - fetch_skip_str (); - fetch_skip_str (); - fetch_skip_str (); - } - } - break; - case CODE_update_user_photo: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *UC = tgl_peer_get (TLS, user_id); - tglu_fetch_date (TLS); - if (UC && (UC->flags & FLAG_CREATED)) { - struct tgl_user *U = &UC->user; - unsigned y = fetch_int (); - long long photo_id; - struct tgl_file_location big; - struct tgl_file_location small; - memset (&big, 0, sizeof (big)); - memset (&small, 0, sizeof (small)); - if (y == CODE_user_profile_photo_empty) { - photo_id = 0; - big.dc = -2; - small.dc = -2; - } else { - assert (y == CODE_user_profile_photo); - photo_id = fetch_long (); - tglf_fetch_file_location (TLS, &small); - tglf_fetch_file_location (TLS, &big); - } - bl_do_set_user_profile_photo (TLS, U, photo_id, &big, &small); - } else { - struct tgl_file_location t; - unsigned y = fetch_int (); - if (y == CODE_user_profile_photo_empty) { - } else { - assert (y == CODE_user_profile_photo); - fetch_long (); // photo_id - tglf_fetch_file_location (TLS, &t); - tglf_fetch_file_location (TLS, &t); - } - } - fetch_bool (); - } - break; - case CODE_update_restore_messages: - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - fetch_skip (n); - tglu_fetch_pts (TLS); - } - break; - case CODE_update_delete_messages: - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - fetch_skip (n); - tglu_fetch_pts (TLS); - } - break; - case CODE_update_chat_participants: - { - unsigned x = fetch_int (); - assert (x == CODE_chat_participants || x == CODE_chat_participants_forbidden); - tgl_peer_id_t chat_id = TGL_MK_CHAT (fetch_int ()); - int n = 0; - tgl_peer_t *C = tgl_peer_get (TLS, chat_id); - if (C && (C->flags & FLAG_CREATED)) { - if (x == CODE_chat_participants) { - bl_do_chat_set_admin (TLS, &C->chat, fetch_int ()); - assert (fetch_int () == CODE_vector); - n = fetch_int (); - struct tgl_chat_user *users = talloc (12 * n); - int i; - for (i = 0; i < n; i++) { - assert (fetch_int () == (int)CODE_chat_participant); - users[i].user_id = fetch_int (); - users[i].inviter_id = fetch_int (); - users[i].date = fetch_int (); - } - int version = fetch_int (); - bl_do_chat_set_participants (TLS, &C->chat, version, n, users); - } - } else { - if (x == CODE_chat_participants) { - fetch_int (); // admin_id - assert (fetch_int () == CODE_vector); - n = fetch_int (); - fetch_skip (n * 4); - fetch_int (); // version - } - } - } - break; - case CODE_update_contact_registered: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *U = tgl_peer_get (TLS, user_id); - fetch_int (); // date - if (TLS->callback.user_registered && U) { - TLS->callback.user_registered (TLS, (void *)U); - } - } - break; - case CODE_update_contact_link: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *U = tgl_peer_get (TLS, user_id); - unsigned t = fetch_int (); - 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) { - fetch_bool (); // has_phone - } - t = fetch_int (); - assert (t == CODE_contacts_foreign_link_unknown || t == CODE_contacts_foreign_link_requested || t == CODE_contacts_foreign_link_mutual); - if (t == CODE_contacts_foreign_link_requested) { - fetch_bool (); // has_phone - } - if (U) {} - } - break; - case CODE_update_activation: - { - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_t *U = tgl_peer_get (TLS, user_id); - - if (TLS->callback.user_activated && U) { - TLS->callback.user_activated (TLS, (void *)U); - } - } - break; - case CODE_update_new_authorization: - { - fetch_long (); // auth_key_id - fetch_int (); // date - char *s = fetch_str_dup (); - char *location = fetch_str_dup (); - if (TLS->callback.new_authorization) { - TLS->callback.new_authorization (TLS, s, location); - } - tfree_str (s); - tfree_str (location); - } - break; - case CODE_update_new_geo_chat_message: - { - struct tgl_message *M = tglf_fetch_alloc_geo_message (TLS); - assert (M); - bl_do_msg_update (TLS, M->id); - } - break; - case CODE_update_new_encrypted_message: - { - struct tgl_message *M = tglf_fetch_alloc_encrypted_message (TLS); - assert (M); - tglu_fetch_qts (TLS); - bl_do_msg_update (TLS, M->id); - } - break; - case CODE_update_encryption: - { - struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat (TLS); - vlogprintf (E_DEBUG, "Secret chat state = %d\n", E->state); - if (E->state == sc_ok) { - tgl_do_send_encr_chat_layer (TLS, E); - } - fetch_int (); // date - } - break; - case CODE_update_encrypted_chat_typing: - { - tgl_peer_id_t id = TGL_MK_ENCR_CHAT (fetch_int ()); - tgl_peer_t *P = tgl_peer_get (TLS, id); - - if (P) { - if (TLS->callback.type_in_secret_chat_notification) { - TLS->callback.type_in_secret_chat_notification (TLS, (void *)P); - } - } - } - break; - case CODE_update_encrypted_messages_read: - { - tgl_peer_id_t id = TGL_MK_ENCR_CHAT (fetch_int ()); // chat_id - fetch_int (); // max_date - fetch_int (); // date - tgl_peer_t *P = tgl_peer_get (TLS, id); - //int x = -1; - if (P && P->last) { - //x = 0; - struct tgl_message *M = P->last; - while (M && (!M->out || M->unread)) { - if (M->out) { - bl_do_set_unread (TLS, M, 0); - } - M = M->next; - } - } - } - break; - case CODE_update_chat_participant_add: - { - tgl_peer_id_t chat_id = TGL_MK_CHAT (fetch_int ()); - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - tgl_peer_id_t inviter_id = TGL_MK_USER (fetch_int ()); - int version = fetch_int (); - - tgl_peer_t *C = tgl_peer_get (TLS, chat_id); - if (C && (C->flags & FLAG_CREATED)) { - bl_do_chat_add_user (TLS, &C->chat, version, tgl_get_peer_id (user_id), tgl_get_peer_id (inviter_id), time (0)); - } - } - break; - case CODE_update_chat_participant_delete: - { - tgl_peer_id_t chat_id = TGL_MK_CHAT (fetch_int ()); - tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ()); - int version = fetch_int (); - - tgl_peer_t *C = tgl_peer_get (TLS, chat_id); - if (C && (C->flags & FLAG_CREATED)) { - bl_do_chat_del_user (TLS, &C->chat, version, tgl_get_peer_id (user_id)); - } - } - break; - case CODE_update_dc_options: - { - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - assert (n >= 0); - int i; - for (i = 0; i < n; i++) { - fetch_dc_option (TLS); - } - } - break; - case CODE_update_user_blocked: - { - int id = fetch_int (); - int blocked = fetch_bool (); - tgl_peer_t *P = tgl_peer_get (TLS, TGL_MK_USER (id)); - if (P && (P->flags & FLAG_CREATED)) { - bl_do_user_set_blocked (TLS, &P->user, blocked); - } - } - break; - case CODE_update_notify_settings: - { - assert (skip_type_any (TYPE_TO_PARAM (notify_peer)) >= 0); - assert (skip_type_any (TYPE_TO_PARAM (peer_notify_settings)) >= 0); - } - break; - case CODE_update_service_notification: - { - int l1 = prefetch_strlen (); - char *type = fetch_str (l1); - int l2 = prefetch_strlen (); - char *message = fetch_str (l2); - skip_type_message_media (TYPE_TO_PARAM(message_media)); - fetch_bool (); - vlogprintf (E_ERROR, "Notification %.*s: %.*s\n", l1, type, l2, message); - if (TLS->callback.notification) { - char *t = tstrndup (type, l1); - char *m = tstrndup (message, l2); - TLS->callback.notification (TLS, t, m); - tfree_str (t); - tfree_str (m); - } - } - break; - default: - vlogprintf (E_ERROR, "Unknown update type %08x\n", op); - ; - } -} - -void tglu_work_update_short (struct tgl_state *TLS, struct connection *c, long long msg_id) { - int *save = in_ptr; - assert (!skip_type_any (TYPE_TO_PARAM (updates))); - int *save_end = in_ptr; - in_ptr = save; - - assert (fetch_int () == CODE_update_short); - tglu_work_update (TLS, c, msg_id); - tglu_fetch_date (TLS); - - assert (save_end == in_ptr); -} - -static int do_skip_seq (struct tgl_state *TLS, int seq) { - if (TLS->seq) { - if (seq <= TLS->seq) { - vlogprintf (E_NOTICE, "Duplicate message with seq=%d\n", seq); - return -1; - } - if (seq > TLS->seq + 1) { - vlogprintf (E_NOTICE, "Hole in seq (seq = %d, cur_seq = %d)\n", seq, TLS->seq); - //vlogprintf (E_NOTICE, "lock_diff = %s\n", (TLS->locks & TGL_LOCK_DIFF) ? "true" : "false"); - tgl_do_get_difference (TLS, 0, 0, 0); - return -1; - } - if (TLS->locks & TGL_LOCK_DIFF) { - vlogprintf (E_DEBUG, "Update during get_difference. seq = %d\n", seq); - return -1; - } - vlogprintf (E_DEBUG, "Ok update. seq = %d\n", seq); - return 0; - } else { - return -1; - } -} - -void tglu_work_updates (struct tgl_state *TLS, struct connection *c, long long msg_id) { - int *save = in_ptr; - assert (!skip_type_any (TYPE_TO_PARAM (updates))); - if (do_skip_seq (TLS, *(in_ptr - 1)) < 0) { - return; - } - int *save_end = in_ptr; - in_ptr = save; - assert (fetch_int () == CODE_updates); - assert (fetch_int () == CODE_vector); - int n = fetch_int (); - int i; - for (i = 0; i < n; i++) { - tglu_work_update (TLS, c, msg_id); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_user (TLS); - } - assert (fetch_int () == CODE_vector); - n = fetch_int (); - for (i = 0; i < n; i++) { - tglf_fetch_alloc_chat (TLS); - } - bl_do_set_date (TLS, fetch_int ()); - //bl_do_set_seq (fetch_int ()); - int seq = fetch_int (); - assert (seq == TLS->seq + 1); - bl_do_set_seq (TLS, seq); - assert (save_end == in_ptr); -} - -void tglu_work_update_short_message (struct tgl_state *TLS, struct connection *c, long long msg_id) { - int *save = in_ptr; - assert (!skip_type_any (TYPE_TO_PARAM (updates))); - if (do_skip_seq (TLS, *(in_ptr - 1)) < 0) { - return; - } - int *save_end = in_ptr; - in_ptr = save; - - assert (fetch_int () == (int)CODE_update_short_message); - struct tgl_message *M = tglf_fetch_alloc_message_short (TLS); - assert (M); - - assert (save_end == in_ptr); - if (!(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_msg_seq_update (TLS, M->id); - } -} - -void tglu_work_update_short_chat_message (struct tgl_state *TLS, struct connection *c, long long msg_id) { - int *save = in_ptr; - assert (!skip_type_any (TYPE_TO_PARAM (updates))); - if (do_skip_seq (TLS, *(in_ptr - 1)) < 0) { - return; - } - int *save_end = in_ptr; - in_ptr = save; - - assert (fetch_int () == CODE_update_short_chat_message); - struct tgl_message *M = tglf_fetch_alloc_message_short_chat (TLS); - assert (M); - assert (save_end == in_ptr); - - if (!(TLS->locks & TGL_LOCK_DIFF)) { - bl_do_msg_seq_update (TLS, M->id); - } -} - -void tglu_work_updates_to_long (struct tgl_state *TLS, struct connection *c, long long msg_id) { - assert (fetch_int () == (int)CODE_updates_too_long); - vlogprintf (E_NOTICE, "updates too long... Getting difference\n"); - tgl_do_get_difference (TLS, 0, 0, 0); -} - -#define user_cmp(a,b) (tgl_get_peer_id ((a)->id) - tgl_get_peer_id ((b)->id)) -DEFINE_TREE(user, struct tgl_user *,user_cmp,0) - -static void notify_status (struct tgl_user *U, void *ex) { - struct tgl_state *TLS = ex; - if (TLS->callback.user_status_update) { - TLS->callback.user_status_update (TLS, U); - } -} - -static void status_notify (struct tgl_state *TLS, void *arg) { - tree_act_ex_user (TLS->online_updates, notify_status, TLS); - tree_clear_user (TLS->online_updates); - TLS->online_updates = NULL; - TLS->timer_methods->free (TLS->online_updates_timer); - TLS->online_updates_timer = NULL; -} - -void tgl_insert_status_update (struct tgl_state *TLS, struct tgl_user *U) { - if (!tree_lookup_user (TLS->online_updates, U)) { - TLS->online_updates = tree_insert_user (TLS->online_updates, U, lrand48 ()); - } - if (!TLS->online_updates_timer) { - TLS->online_updates_timer = TLS->timer_methods->alloc (TLS, status_notify, 0); - TLS->timer_methods->insert (TLS->online_updates_timer, 0); - } -} - -static void user_expire (struct tgl_state *TLS, void *arg) { - struct tgl_user *U = arg; - TLS->timer_methods->free (U->status.ev); - U->status.ev = 0; - U->status.online = -1; - U->status.when = tglt_get_double_time (); - tgl_insert_status_update (TLS, U); -} - -void tgl_insert_status_expire (struct tgl_state *TLS, struct tgl_user *U) { - assert (!U->status.ev); - U->status.ev = TLS->timer_methods->alloc (TLS, user_expire, U); - TLS->timer_methods->insert (U->status.ev, U->status.when - tglt_get_double_time ()); -} - -void tgl_remove_status_expire (struct tgl_state *TLS, struct tgl_user *U) { - TLS->timer_methods->free (U->status.ev); - U->status.ev = 0; -} diff --git a/updates.h b/updates.h deleted file mode 100644 index c586888..0000000 --- a/updates.h +++ /dev/null @@ -1,39 +0,0 @@ -/* - This file is part of tgl-library - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - - Copyright Vitaly Valtman 2013-2014 -*/ - -#ifndef __UPDATES_H__ -#define __UPDATES_H__ -struct connection; -void tglu_work_update (struct tgl_state *TLS, struct connection *c, long long msg_id); -void tglu_work_updates_to_long (struct tgl_state *TLS, struct connection *c, long long msg_id); -void tglu_work_update_short_chat_message (struct tgl_state *TLS, struct connection *c, long long msg_id); -void tglu_work_update_short_message (struct tgl_state *TLS, struct connection *c, long long msg_id); -void tglu_work_update_short (struct tgl_state *TLS, struct connection *c, long long msg_id); -void tglu_work_updates (struct tgl_state *TLS, struct connection *c, long long msg_id); - -void tglu_fetch_pts (struct tgl_state *TLS); -void tglu_fetch_qts (struct tgl_state *TLS); -void tglu_fetch_seq (struct tgl_state *TLS); -void tglu_fetch_date (struct tgl_state *TLS); - -void tgl_insert_status_update (struct tgl_state *TLS, struct tgl_user *U); -void tgl_insert_status_expire (struct tgl_state *TLS, struct tgl_user *U); -void tgl_remove_status_expire (struct tgl_state *TLS, struct tgl_user *U); -#endif