Compare commits
205 commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
5ec9a88872 | ||
![]() |
4f7778c8e9 | ||
![]() |
6f60ed5818 | ||
![]() |
ef37551f04 | ||
![]() |
39819d2eb9 | ||
![]() |
a0a3361d7d | ||
![]() |
998b89d124 | ||
![]() |
8eeac24783 | ||
![]() |
95a9edbd8a | ||
![]() |
508d23cebc | ||
![]() |
dc27be5eae | ||
![]() |
4440f5b80e | ||
![]() |
7c32c52116 | ||
![]() |
05e1606d03 | ||
![]() |
d577731f98 | ||
![]() |
7a0fdd7f35 | ||
![]() |
990221ea4d | ||
![]() |
11e6e19272 | ||
![]() |
76e7c8fd38 | ||
![]() |
02b37e503e | ||
![]() |
db85bf4836 | ||
![]() |
48e96f3a7a | ||
![]() |
9d40537345 | ||
![]() |
53e9491914 | ||
![]() |
997116ff43 | ||
![]() |
3fcfe6fc3b | ||
![]() |
82dad2b1f4 | ||
![]() |
65843d7695 | ||
![]() |
3a7da2d67b | ||
![]() |
d56cd2e2cb | ||
![]() |
35f90fd0b9 | ||
![]() |
5c2f7d688e | ||
![]() |
a6af86a266 | ||
![]() |
0326dbf69e | ||
![]() |
c9a0346971 | ||
![]() |
9488f56f4b | ||
![]() |
8bdaf6e55b | ||
![]() |
efebedc08a | ||
![]() |
1896b2b905 | ||
![]() |
3e868b4249 | ||
![]() |
342a7f323c | ||
![]() |
4e55083b41 | ||
![]() |
324221f5de | ||
![]() |
ecc1ef02f5 | ||
![]() |
a240e3536b | ||
![]() |
56b30ac358 | ||
![]() |
a7e0f25a6a | ||
![]() |
51b3f5295b | ||
![]() |
01746fe177 | ||
![]() |
f9528ff627 | ||
![]() |
c7a15630c6 | ||
![]() |
595346391e | ||
![]() |
2cd6465440 | ||
![]() |
ba10513786 | ||
![]() |
dd4e757ea5 | ||
![]() |
da451e6436 | ||
![]() |
9f90a325b7 | ||
![]() |
41287c13d7 | ||
![]() |
6b9ce8a2b6 | ||
![]() |
47ef058f84 | ||
![]() |
dfc0578302 | ||
![]() |
1c46ba8e3a | ||
![]() |
8f84df8789 | ||
![]() |
55ce5bac99 | ||
![]() |
db4d36c8b6 | ||
![]() |
d3f2ac2eba | ||
![]() |
4e35360aff | ||
![]() |
1d58448e19 | ||
![]() |
30656e49be | ||
![]() |
5539d232d5 | ||
![]() |
74de6b24d1 | ||
![]() |
22e9f7778d | ||
![]() |
bb1fd17d08 | ||
![]() |
bfe3d140b3 | ||
![]() |
e6efa4097c | ||
![]() |
9eef9444d5 | ||
![]() |
6d2fa85b70 | ||
![]() |
6074086de6 | ||
![]() |
ff805e1140 | ||
![]() |
b15ea055d0 | ||
![]() |
da201171ab | ||
![]() |
8b558db00b | ||
![]() |
d28209e3d1 | ||
![]() |
c9ed692d24 | ||
![]() |
5369423e3c | ||
![]() |
6d8deb9135 | ||
![]() |
3dd341a08f | ||
![]() |
34b81ab400 | ||
![]() |
fac3ddf2d8 | ||
![]() |
613867fb09 | ||
![]() |
7ac53571d2 | ||
![]() |
743cc4b3f3 | ||
![]() |
176d19fc4b | ||
![]() |
8f50bab9f0 | ||
![]() |
3871561c09 | ||
![]() |
44a8a813c8 | ||
![]() |
2e7d468397 | ||
![]() |
56f31ae3be | ||
![]() |
62cefe5a8e | ||
![]() |
91871043b1 | ||
![]() |
66d35aea76 | ||
![]() |
a245f86dd5 | ||
![]() |
8d923387ba | ||
![]() |
05f6824de7 | ||
![]() |
e113d3469b | ||
![]() |
a60ae1ae93 | ||
![]() |
6a5b001de7 | ||
![]() |
6d8f975567 | ||
![]() |
017851107c | ||
![]() |
ad6a38454e | ||
![]() |
f4f4be579e | ||
![]() |
523fa3f6d5 | ||
![]() |
ce462d4a70 | ||
![]() |
6937fa0bee | ||
![]() |
d2ac430c9c | ||
![]() |
6c9d18cacf | ||
![]() |
6fb56f1496 | ||
![]() |
c711019ea8 | ||
![]() |
784db14d6a | ||
![]() |
306c571794 | ||
![]() |
e0782b77a3 | ||
![]() |
0e13277938 | ||
![]() |
1814b2f581 | ||
![]() |
5731386848 | ||
![]() |
c840b636c3 | ||
![]() |
f51f3b4da3 | ||
![]() |
c1fa31c3d7 | ||
![]() |
8ce965f045 | ||
![]() |
d5109e2545 | ||
![]() |
c7bd5587ff | ||
![]() |
d44dfa859d | ||
![]() |
4b3c936cd4 | ||
![]() |
92c9d0d7f0 | ||
![]() |
63605c7971 | ||
![]() |
4fb3d3503b | ||
![]() |
548f4fe997 | ||
![]() |
13313af979 | ||
![]() |
d954f87514 | ||
![]() |
654df2c05c | ||
![]() |
a7b8b1286c | ||
![]() |
5e653e85c8 | ||
![]() |
d39193f2f7 | ||
![]() |
cdb6b9cec5 | ||
![]() |
c66d07ce35 | ||
![]() |
050560ece9 | ||
![]() |
abdae6a6f7 | ||
![]() |
8fd05fdba4 | ||
![]() |
3bf992f0cb | ||
![]() |
ecc239e291 | ||
![]() |
d67fc774bf | ||
![]() |
29d06e6d1e | ||
![]() |
e5534b6545 | ||
![]() |
152ebc3898 | ||
![]() |
1bd7d2cfad | ||
![]() |
eb4e9055b7 | ||
![]() |
82e9e0b09d | ||
![]() |
8b2aec9703 | ||
![]() |
fef8398860 | ||
![]() |
ca34ddd404 | ||
![]() |
6f711aa1fb | ||
![]() |
cf7e7b45bb | ||
![]() |
93cb32a43f | ||
![]() |
b083e80dc7 | ||
![]() |
ab5b9c306f | ||
![]() |
29d2e32912 | ||
![]() |
e2e18c9f34 | ||
![]() |
e7b04da661 | ||
![]() |
c97cba7e9e | ||
![]() |
021db46dc4 | ||
![]() |
cfca590a30 | ||
![]() |
1cd379abd0 | ||
![]() |
6d56f4ac6b | ||
![]() |
3c1d61bf26 | ||
![]() |
e7d554dc81 | ||
![]() |
3ae872010e | ||
![]() |
07b1646423 | ||
![]() |
0299a6375d | ||
![]() |
ec15b4b1b6 | ||
![]() |
e58ff46e96 | ||
![]() |
8c58fb7f00 | ||
![]() |
bd4e59b6ab | ||
![]() |
45778cffdf | ||
![]() |
3b58fed8e4 | ||
![]() |
64981ad777 | ||
![]() |
311489b168 | ||
![]() |
52b5a2d3ce | ||
![]() |
d08a64a481 | ||
![]() |
b1cbaa5105 | ||
![]() |
e0ded4a86c | ||
![]() |
4a48059e8a | ||
![]() |
3dde03db86 | ||
![]() |
3b5458de54 | ||
![]() |
cb95039f51 | ||
![]() |
bc1648a7c7 | ||
![]() |
ddbe7ba88c | ||
![]() |
c05bb2683e | ||
![]() |
143d672884 | ||
![]() |
c34e6a3abe | ||
![]() |
fc8a20b74c | ||
![]() |
7741fe8da9 | ||
![]() |
30f949ee75 | ||
![]() |
474a76a010 | ||
![]() |
a8fae1278f | ||
![]() |
9b622ba083 | ||
![]() |
74b05dbf8e |
71 changed files with 21706 additions and 7838 deletions
5
.gitignore
vendored
5
.gitignore
vendored
|
@ -7,3 +7,8 @@ config.log
|
|||
config.status
|
||||
.idea/
|
||||
nbproject/
|
||||
bin/
|
||||
objs/
|
||||
dep/
|
||||
auto/
|
||||
libs/
|
||||
|
|
|
@ -9,6 +9,7 @@ install:
|
|||
- sudo apt-get install libreadline6-dev
|
||||
- sudo apt-get install libssl-dev
|
||||
- sudo apt-get install liblua5.2-dev lua5.2
|
||||
- sudo apt-get install libevent-dev
|
||||
|
||||
script:
|
||||
- ./configure
|
||||
|
|
13
CHANGELOG
Normal file
13
CHANGELOG
Normal file
|
@ -0,0 +1,13 @@
|
|||
1.0.5
|
||||
* listening socket (tcp and unix) for commands
|
||||
1.0.4
|
||||
* changed create_group_chat format
|
||||
* changed search query
|
||||
* rewritten interface code. Support for escaped characters in quotes
|
||||
1.0.3
|
||||
* options to help to run telegram-cli as daemon
|
||||
1.0.2
|
||||
* Bug fixes
|
||||
1.0.1
|
||||
* Added pfs support. To use it you should add 'pfs_enabled=true' line to config.
|
||||
* Added export_card/import_card methods
|
83
Makefile.in
83
Makefile.in
|
@ -1,35 +1,90 @@
|
|||
srcdir=@srcdir@
|
||||
|
||||
CFLAGS=@CFLAGS@
|
||||
LDFLAGS=@LDFLAGS@
|
||||
CPPFLAGS=@CPPFLAGS@
|
||||
LDFLAGS=@LDFLAGS@ @OPENSSL_LDFLAGS@
|
||||
CPPFLAGS=@CPPFLAGS@ @OPENSSL_INCLUDES@
|
||||
DEFS=@DEFS@
|
||||
COMPILE_FLAGS=${CFLAGS} ${CPPFLAGS} ${DEFS} -Wall -Wextra -Werror -Wno-deprecated-declarations -fno-strict-aliasing -fno-omit-frame-pointer -ggdb
|
||||
COMPILE_FLAGS=${CFLAGS} ${CPFLAGS} ${CPPFLAGS} ${DEFS} -Wall -Wextra -Werror -Wno-deprecated-declarations -fno-strict-aliasing -fno-omit-frame-pointer -ggdb -Wno-unused-parameter -fPIC
|
||||
|
||||
EXTRA_LIBS=@LIBS@ @EXTRA_LIBS@
|
||||
LOCAL_LDFLAGS=-rdynamic -ggdb ${EXTRA_LIBS}
|
||||
EXTRA_LIBS=@LIBS@ @EXTRA_LIBS@ @OPENSSL_LIBS@
|
||||
LOCAL_LDFLAGS=-rdynamic -ggdb -levent ${EXTRA_LIBS}
|
||||
LINK_FLAGS=${LDFLAGS} ${LOCAL_LDFLAGS}
|
||||
|
||||
HEADERS= ${srcdir}/constants.h ${srcdir}/include.h ${srcdir}/interface.h ${srcdir}/LICENSE.h ${srcdir}/loop.h ${srcdir}/mtproto-client.h ${srcdir}/mtproto-common.h ${srcdir}/net.h ${srcdir}/no-preview.h ${srcdir}/queries.h ${srcdir}/structures.h ${srcdir}/telegram.h ${srcdir}/tree.h ${srcdir}/config.h ${srcdir}/binlog.h ${srcdir}/tools.h ${srcdir}/lua-tg.h
|
||||
DEP=${srcdir}/dep
|
||||
AUTO=${srcdir}/auto
|
||||
EXE=${srcdir}/bin
|
||||
OBJ=${srcdir}/objs
|
||||
LIB=${srcdir}/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
|
||||
|
||||
TG_OBJECTS=${OBJ}/main.o ${OBJ}/loop.o ${OBJ}/interface.o ${OBJ}/lua-tg.o
|
||||
TGL_OBJECTS=${OBJ}/net.o ${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
|
||||
GENERATE_OBJECTS=${OBJ}/generate.o
|
||||
COMMON_OBJECTS=${OBJ}/tools.o
|
||||
OBJ_LIST=${TG_OBJECTS} ${TLC_OBJECTS} ${GENERATE_OBJECTS} ${COMMON_OBJECTS} ${TGL_OBJECTS}
|
||||
OBJ_C=${TLC_OBJECTS} ${GENERATE_OBJECTS} ${COMMON_OBJECTS} ${TGL_OBJECTS}
|
||||
|
||||
DEPENDENCE=$(subst ${OBJ}/,${DEP}/,$(patsubst %.o,%.d,${OBJ_LIST}))
|
||||
DEPENDENCE_LIST=${DEPENDENCE}
|
||||
|
||||
INCLUDE=-I. -I${srcdir}
|
||||
CC=@CC@
|
||||
OBJECTS=main.o loop.o interface.o net.o mtproto-common.o mtproto-client.o queries.o structures.o binlog.o tools.o lua-tg.o
|
||||
|
||||
.SUFFIXES:
|
||||
|
||||
.SUFFIXES: .c .h .o
|
||||
|
||||
all: telegram
|
||||
all: ${EXE_LIST} ${DIR_LIST} ${LIB_LIST}
|
||||
create_dirs_and_headers: ${DIR_LIST} ${AUTO}/auto.c ${AUTO}/auto-header.h ${AUTO}/constants.h
|
||||
create_dirs: ${DIR_LIST}
|
||||
|
||||
${OBJECTS}: ${HEADERS}
|
||||
${DIR_LIST}:
|
||||
@test -d $@ || mkdir -p $@
|
||||
|
||||
telegram: ${OBJECTS}
|
||||
${CC} ${OBJECTS} ${LINK_FLAGS} -o $@
|
||||
-include ${DEPENDENCE_LIST}
|
||||
|
||||
.c.o :
|
||||
${CC} ${COMPILE_FLAGS} ${INCLUDE} -c $< -o $@
|
||||
${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 < $< > $@
|
||||
|
||||
clean:
|
||||
rm -rf *.o telegram config.log config.status > /dev/null || echo "all clean"
|
||||
rm -rf ${DIR_LIST} config.log config.status > /dev/null || echo "all clean"
|
||||
|
||||
|
|
78
README-LUA
Normal file
78
README-LUA
Normal file
|
@ -0,0 +1,78 @@
|
|||
To use lua with client you should write lua script. You can specify it from config ("lua_script" option) or from command_line [-s].
|
||||
|
||||
It should have several functions:
|
||||
on_binlog_replay_end() - it is called when replay of old events end. Any updates prior this call were already received by this client
|
||||
some time ago.
|
||||
|
||||
on_get_difference_end() - it is called after first get_difference call. So we received all updates after last client execute.
|
||||
|
||||
on_our_id(our_id) - Informs about id of currently logged in user.
|
||||
|
||||
on_msg_receive(msg) - it is called when we receive new msg (!! may be called before on_binlog_replay_end, than it is old msg).
|
||||
|
||||
on_user_update(user,what_changed) - updated info about user. what_changed is array of strings.
|
||||
on_chat_update(user,what_changed) - updated info about user. what_changed is array of strings.
|
||||
on_secret_chat_update(user,what_changed) - updated info about user. what_changed is array of strings.
|
||||
|
||||
|
||||
|
||||
Also, you can call several functions. Each this function last two arguments, are cb_function and cb_extra.
|
||||
These functions may return false immidiately if something is bad with args, or return true and call cb_function in future.
|
||||
cb_function would have two or three arguments: first cb_extra, second success (1 or 0), third result (if applicable).
|
||||
|
||||
If you want to pass msg to function, you should pass it's id.
|
||||
If you want to pass peer to function, you should pass it's print_name.
|
||||
Or, you can pass string user#id<id> chat#id<id> and secret_chat#id<id> as peer. It is in some cases better. For example if you want to postpone and you are afraid, that print_name would be changed in the meantime.
|
||||
|
||||
Function_list (arguments are listed aside from cb_function and cb_extra, :
|
||||
get_contact_list ()
|
||||
get_dialog_list ()
|
||||
|
||||
rename_chat (chat, new_name)
|
||||
chat_set_photo (chat, file)
|
||||
|
||||
send_msg (peer, text)
|
||||
fwd_msg (peer, msg)
|
||||
|
||||
send_photo (peer, file)
|
||||
send_video (peer, file)
|
||||
send_audio (peer, file)
|
||||
send_document (peer, file)
|
||||
send_text (peer, file)
|
||||
|
||||
load_photo(msg)
|
||||
load_video(msg)
|
||||
load_video_thumb(msg)
|
||||
load_audio(msg)
|
||||
load_document(msg)
|
||||
load_document_thumb(msg)
|
||||
|
||||
chat_info (chat)
|
||||
user_info (user)
|
||||
|
||||
get_history (peer, limit)
|
||||
|
||||
chat_add_user (chat, user)
|
||||
chat_del_user (chat, user)
|
||||
|
||||
add_contactt (phone, first_name, last_name)
|
||||
rename_contactt (phone, first_name, last_name)
|
||||
|
||||
msg_search (peer, text)
|
||||
msg_global_search (text)
|
||||
|
||||
mark_read (peer)
|
||||
|
||||
set_profile_photo (file)
|
||||
|
||||
create_secret_chat (user)
|
||||
create_group_chat (user, name)
|
||||
|
||||
delete_msg (msg)
|
||||
restore_msg (number)
|
||||
|
||||
status_online ()
|
||||
status_offline ()
|
||||
|
||||
Also, you have function
|
||||
postpone (cb_function, cb_extra, timeout). It will call your cb_function in specified number of seconds (number of seconds may be double).
|
|
@ -1,5 +1,8 @@
|
|||
## Telegram messenger CLI [](https://travis-ci.org/vysheng/tg)
|
||||
|
||||
!!!! May be outdated. Please refer to english README as more actual.
|
||||
|
||||
|
||||
Interfaz de línea de comandos para: [Telegram](http://telegram.org). Usa interfaz readline.
|
||||
|
||||
### Documentación del API y el protocolo
|
||||
|
|
64
README.md
64
README.md
|
@ -8,6 +8,16 @@ Documentation for Telegram API is available here: http://core.telegram.org/api
|
|||
|
||||
Documentation for MTproto protocol is available here: http://core.telegram.org/mtproto
|
||||
|
||||
### Upgrading to version 1.0
|
||||
|
||||
First of all, the binary is now in ./bin folder and is named telegram-cli. So be careful, not to use old binary.
|
||||
|
||||
Second, config folder is now ${HOME}/.telegram-cli
|
||||
|
||||
Third, database is not compatible with older versions, so you'll have to login again.
|
||||
|
||||
Fourth, in peer_name '#' are substitued to '@'. (Not applied to appending of '#%d' in case of two peers having same name).
|
||||
|
||||
### Installation
|
||||
|
||||
Clone GitHub Repository
|
||||
|
@ -24,13 +34,13 @@ or download and extract zip
|
|||
Install libs: readline or libedit, openssl and (if you want to use config) libconfig and liblua.
|
||||
If you do not want to use them pass options --disable-libconfig and --disable-liblua respectively.
|
||||
|
||||
On ubuntu use:
|
||||
On Ubuntu/Debian use:
|
||||
|
||||
sudo apt-get install libreadline-dev libconfig-dev libssl-dev lua5.2 liblua5.2-dev
|
||||
sudo apt-get install libreadline-dev libconfig-dev libssl-dev lua5.2 liblua5.2-dev libevent-dev
|
||||
|
||||
On gentoo:
|
||||
|
||||
sudo emerge -av sys-libs/readline dev-libs/libconfig dev-libs/openssl dev-lang/lua
|
||||
sudo emerge -av sys-libs/readline dev-libs/libconfig dev-libs/openssl dev-lang/lua dev-libs/libevent
|
||||
|
||||
On Fedora:
|
||||
|
||||
|
@ -49,9 +59,17 @@ Then,
|
|||
./configure
|
||||
make
|
||||
|
||||
#### Other methods to install on linux
|
||||
|
||||
On Gentoo: use ebuild provided.
|
||||
|
||||
On Arch: https://aur.archlinux.org/packages/telegram-git/
|
||||
|
||||
#### Mac OS X
|
||||
|
||||
The client depends on [readline library](http://cnswww.cns.cwru.edu/php/chet/readline/rltop.html) and [libconfig](http://www.hyperrealm.com/libconfig/), which are not included in OS X by default. You have to install these libraries manually, e.g. using [Homebrew](http://brew.sh/).
|
||||
The client depends on [readline library](http://cnswww.cns.cwru.edu/php/chet/readline/rltop.html) and [libconfig](http://www.hyperrealm.com/libconfig/), which are not included in OS X by default. You have to install these libraries manually.
|
||||
|
||||
If using [Homebrew](http://brew.sh/):
|
||||
|
||||
brew install libconfig
|
||||
brew install readline
|
||||
|
@ -62,6 +80,14 @@ The client depends on [readline library](http://cnswww.cns.cwru.edu/php/chet/rea
|
|||
|
||||
Thanks to [@jfontan](https://github.com/vysheng/tg/issues/3#issuecomment-28293731) for this solution.
|
||||
|
||||
If using [MacPorts](https://www.macports.org):
|
||||
|
||||
sudo port install libconfig-hr
|
||||
sudo port install readline
|
||||
sudo port install lua51
|
||||
export CFLAGS="-I/usr/local/include -I/opt/local/include"
|
||||
export LDFLAGS="-L/usr/local/lib -L/opt/local/lib/"
|
||||
./configure && make
|
||||
|
||||
Install these ports:
|
||||
|
||||
|
@ -78,13 +104,17 @@ Then build:
|
|||
|
||||
If you manage to launch it on other UNIX, please let me know.
|
||||
|
||||
### Contacts
|
||||
If you would like to ask a question, you can write to my telegram or to the github (or both). To contact me via telegram, you should use import_card method with argument 000653bf:0738ca5d:5521fbac:29246815:a27d0cda
|
||||
|
||||
|
||||
### Usage
|
||||
|
||||
./telegram -k <public-server-key>
|
||||
bin/telegram-cli -k <public-server-key>
|
||||
|
||||
By default public key is stored in the same folder named tg-server.pub or in /etc/telegram/server.pub, if it's not, specify where to find it:
|
||||
By default public key is stored in the same folder named tg-server.pub or in /etc/telegram-cli/server.pub, if it's not, specify where to find it:
|
||||
|
||||
./telegram -k tg-server.pub
|
||||
bin/telegram-cli -k tg-server.pub
|
||||
|
||||
Client support TAB completion and command history.
|
||||
|
||||
|
@ -105,14 +135,19 @@ If two or more peers have same name, <sharp>number is appended to the name. (for
|
|||
* **add_contact** \<phone-number\> \<first-name\> \<last-name\> - tries to add contact to contact-list by phone
|
||||
* **rename_contact** \<user\> \<first-name\> \<last-name\> - tries to rename contact. If you have another device it will be a fight
|
||||
* **mark_read** \<peer\> - mark read all received messages with peer
|
||||
* **delete_msg** \<msg-seqno\> - deletes message (not completly, though)
|
||||
* **restore_msg** \<msg-seqno\> - restores delete message. Impossible for secret chats. Only possible short time (one hour, I think) after deletion
|
||||
|
||||
#### Multimedia
|
||||
|
||||
* **send_photo** \<peer\> \<photo-file-name\> - sends photo to peer
|
||||
* **send_video** \<peer\> \<video-file-name\> - sends video to peer
|
||||
* **send_text** \<peer\> \<text-file-name> - sends text file as plain messages
|
||||
* **load_photo**/load_video/load_video_thumb \<msg-seqno\> - loads photo/video to download dir
|
||||
* **view_photo**/view_video/view_video_thumb \<msg-seqno\> - loads photo/video to download dir and starts system default viewer
|
||||
* **load_photo**/load_video/load_video_thumb/load_audio/load_document/load_document_thumb \<msg-seqno\> - loads photo/video/audio/document to download dir
|
||||
* **view_photo**/view_video/view_video_thumb/view_audio/view_document/view_document_thumb \<msg-seqno\> - loads photo/video to download dir and starts system default viewer
|
||||
* **fwd_media** \<msg-seqno\> send media in your message. Use this to prevent sharing info about author of media (though, it is possible to determine user_id from media itself, it is not possible get access_hash of this user)
|
||||
* **set_profile_photo** \<photo-file-name\> - sets userpic. Photo should be square, or server will cut biggest central square part
|
||||
|
||||
|
||||
#### Group chat options
|
||||
|
||||
|
@ -121,6 +156,7 @@ If two or more peers have same name, <sharp>number is appended to the name. (for
|
|||
* **chat_del_user** \<chat\> \<user\> - remove user from chat
|
||||
* **rename_chat** \<chat\> \<new-name\>
|
||||
* **create_group_chat** \<user\> \<chat topic\> - creates a groupchat with user, use chat_add_user to add more users
|
||||
* **chat_set_photo** \<chat\> \<photo-file-name\> - sets group chat photo. Same limits as for profile photos.
|
||||
|
||||
#### Search
|
||||
|
||||
|
@ -131,6 +167,8 @@ If two or more peers have same name, <sharp>number is appended to the name. (for
|
|||
|
||||
* **create_secret_chat** \<user\> - creates secret chat with this user
|
||||
* **visualize_key** \<secret_chat\> - prints visualization of encryption key. You should compare it to your partner's one
|
||||
* **set_ttl** \<secret_chat\> \<ttl\> - sets ttl to secret chat. Though client does ignore it, client on other end can make use of it
|
||||
* **accept_secret_chat** \<secret_chat\> - manually accept secret chat (only useful when starting with -E key)
|
||||
|
||||
#### Stats and various info
|
||||
|
||||
|
@ -142,3 +180,11 @@ If two or more peers have same name, <sharp>number is appended to the name. (for
|
|||
* **stats** - just for debugging
|
||||
* **show_license** - prints contents of GPLv2
|
||||
* **help** - prints this help
|
||||
|
||||
#### Card
|
||||
* **export_card** - print your 'card' that anyone can later use to import your contact
|
||||
* **import_card** \<card\> - gets user by card. You can write messages to him after that.
|
||||
|
||||
#### Other
|
||||
* **quit** - quit
|
||||
* **safe_quit** - wait for all queries to end then quit
|
||||
|
|
2
append.tl
Normal file
2
append.tl
Normal file
|
@ -0,0 +1,2 @@
|
|||
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;
|
437
auto-static.c
Normal file
437
auto-static.c
Normal file
|
@ -0,0 +1,437 @@
|
|||
/*
|
||||
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
|
||||
*/
|
||||
|
||||
#include "mtproto-common.h"
|
||||
#include <string.h>
|
||||
|
||||
static int cur_token_len;
|
||||
static char *cur_token;
|
||||
static int cur_token_real_len;
|
||||
static int cur_token_quoted;
|
||||
static int multiline_output = 1;
|
||||
static int multiline_offset;
|
||||
static int multiline_offset_size = 2;
|
||||
|
||||
static int disable_field_names;
|
||||
|
||||
#define expect_token(token,len) \
|
||||
if (len != cur_token_len || memcmp (cur_token, token, cur_token_len)) { return -1; } \
|
||||
local_next_token ();
|
||||
|
||||
#define expect_token_ptr(token,len) \
|
||||
if (len != cur_token_len || memcmp (cur_token, token, cur_token_len)) { return 0; } \
|
||||
local_next_token ();
|
||||
|
||||
#define expect_token_autocomplete(token,len) \
|
||||
if (cur_token_len == -3 && len >= cur_token_real_len && !memcmp (cur_token, token, cur_token_real_len)) { set_autocomplete_string (token); return -1; }\
|
||||
if (len != cur_token_len || memcmp (cur_token, token, cur_token_len)) { return -1; } \
|
||||
local_next_token ();
|
||||
|
||||
#define expect_token_ptr_autocomplete(token,len) \
|
||||
if (cur_token_len == -3 && len >= cur_token_real_len && !memcmp (cur_token, token, cur_token_real_len)) { set_autocomplete_string (token); return 0; }\
|
||||
if (len != cur_token_len || memcmp (cur_token, token, cur_token_len)) { return 0; } \
|
||||
local_next_token ();
|
||||
|
||||
|
||||
static int autocomplete_mode;
|
||||
static char *autocomplete_string;
|
||||
static int (*autocomplete_fun)(const char *, int, int, char **);
|
||||
|
||||
static void set_autocomplete_string (const char *s) {
|
||||
if (autocomplete_string) { free (autocomplete_string); }
|
||||
autocomplete_string = strdup (s);
|
||||
assert (autocomplete_string);
|
||||
autocomplete_mode = 1;
|
||||
}
|
||||
|
||||
static void set_autocomplete_type (int (*f)(const char *, int, int, char **)) {
|
||||
autocomplete_fun = f;
|
||||
autocomplete_mode = 2;
|
||||
}
|
||||
|
||||
static int is_int (void) {
|
||||
if (cur_token_len <= 0) { return 0; }
|
||||
char c = cur_token[cur_token_len];
|
||||
cur_token[cur_token_len] = 0;
|
||||
char *p = 0;
|
||||
|
||||
if (strtoll (cur_token, &p, 10)) {}
|
||||
cur_token[cur_token_len] = c;
|
||||
|
||||
return p == cur_token + cur_token_len;
|
||||
}
|
||||
|
||||
static long long get_int (void) {
|
||||
if (cur_token_len <= 0) { return 0; }
|
||||
char c = cur_token[cur_token_len];
|
||||
cur_token[cur_token_len] = 0;
|
||||
char *p = 0;
|
||||
|
||||
long long val = strtoll (cur_token, &p, 0);
|
||||
cur_token[cur_token_len] = c;
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
static int is_double (void) {
|
||||
if (cur_token_len <= 0) { return 0; }
|
||||
char c = cur_token[cur_token_len];
|
||||
cur_token[cur_token_len] = 0;
|
||||
char *p = 0;
|
||||
|
||||
if (strtod (cur_token, &p)) {}
|
||||
cur_token[cur_token_len] = c;
|
||||
|
||||
return p == cur_token + cur_token_len;
|
||||
}
|
||||
|
||||
static double get_double (void) {
|
||||
if (cur_token_len <= 0) { return 0; }
|
||||
char c = cur_token[cur_token_len];
|
||||
cur_token[cur_token_len] = 0;
|
||||
char *p = 0;
|
||||
|
||||
double val = strtod (cur_token, &p);
|
||||
cur_token[cur_token_len] = c;
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
static struct paramed_type *paramed_type_dup (struct paramed_type *P) {
|
||||
if (ODDP (P)) { return P; }
|
||||
struct paramed_type *R = malloc (sizeof (*R));
|
||||
assert (R);
|
||||
R->type = malloc (sizeof (*R->type));
|
||||
assert (R->type);
|
||||
memcpy (R->type, P->type, sizeof (*P->type));
|
||||
R->type->id = strdup (P->type->id);
|
||||
assert (R->type->id);
|
||||
|
||||
if (P->type->params_num) {
|
||||
R->params = malloc (sizeof (void *) * P->type->params_num);
|
||||
assert (R->params);
|
||||
int i;
|
||||
for (i = 0; i < P->type->params_num; i++) {
|
||||
R->params[i] = paramed_type_dup (P->params[i]);
|
||||
}
|
||||
}
|
||||
return R;
|
||||
}
|
||||
|
||||
void tgl_paramed_type_free (struct paramed_type *P) {
|
||||
if (ODDP (P)) { return; }
|
||||
if (P->type->params_num) {
|
||||
int i;
|
||||
for (i = 0; i < P->type->params_num; i++) {
|
||||
tgl_paramed_type_free (P->params[i]);
|
||||
}
|
||||
free (P->params);
|
||||
}
|
||||
free (P->type->id);
|
||||
free (P->type);
|
||||
free (P);
|
||||
}
|
||||
|
||||
static char *buffer_pos, *buffer_end;
|
||||
|
||||
static int is_wspc (char c) {
|
||||
return c <= 32 && c > 0;
|
||||
}
|
||||
|
||||
static void skip_wspc (void) {
|
||||
while (buffer_pos < buffer_end && is_wspc (*buffer_pos)) {
|
||||
buffer_pos ++;
|
||||
}
|
||||
}
|
||||
|
||||
static int is_letter (char c) {
|
||||
return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || (c >= '0' && c <= '9') || c == '.' || c == '_' || c == '-';
|
||||
}
|
||||
|
||||
|
||||
static char exp_buffer[1 << 25];;
|
||||
static int exp_buffer_pos;
|
||||
|
||||
static inline int is_hex (char c) {
|
||||
return (c >= '0' && c <= '9') || (c >= 'a' && c <= 'f');
|
||||
}
|
||||
|
||||
static inline int hex2dec (char c) {
|
||||
if (c >= '0' && c <= '9') { return c - '0'; }
|
||||
else { return c - 'a' + 10; }
|
||||
}
|
||||
|
||||
static void expand_backslashed (char *s, int len) {
|
||||
int backslashed = 0;
|
||||
exp_buffer_pos = 0;
|
||||
int i = 0;
|
||||
while (i < len) {
|
||||
assert (i + 3 <= (1 << 25));
|
||||
if (backslashed) {
|
||||
backslashed = 0;
|
||||
switch (s[i ++]) {
|
||||
case 'n':
|
||||
exp_buffer[exp_buffer_pos ++] = '\n';
|
||||
break;
|
||||
case 'r':
|
||||
exp_buffer[exp_buffer_pos ++] = '\r';
|
||||
break;
|
||||
case 't':
|
||||
exp_buffer[exp_buffer_pos ++] = '\t';
|
||||
break;
|
||||
case 'b':
|
||||
exp_buffer[exp_buffer_pos ++] = '\b';
|
||||
break;
|
||||
case 'a':
|
||||
exp_buffer[exp_buffer_pos ++] = '\a';
|
||||
break;
|
||||
case '\\':
|
||||
exp_buffer[exp_buffer_pos ++] = '\\';
|
||||
break;
|
||||
case 'x':
|
||||
if (i + 2 > len || !is_hex (s[i]) || !is_hex (s[i + 1])) {
|
||||
exp_buffer_pos = -1;
|
||||
return;
|
||||
}
|
||||
exp_buffer[exp_buffer_pos ++] = hex2dec (s[i]) * 16 + hex2dec (s[i + 1]);
|
||||
i += 2;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
if (s[i] == '\\') {
|
||||
backslashed = 1;
|
||||
i ++;
|
||||
} else {
|
||||
exp_buffer[exp_buffer_pos ++] = s[i ++];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void local_next_token (void) {
|
||||
skip_wspc ();
|
||||
cur_token_quoted = 0;
|
||||
if (buffer_pos >= buffer_end) {
|
||||
cur_token_len = -3;
|
||||
cur_token_real_len = 0;
|
||||
return;
|
||||
}
|
||||
char c = *buffer_pos;
|
||||
if (is_letter (c)) {
|
||||
cur_token = buffer_pos;
|
||||
while (buffer_pos < buffer_end && is_letter (*buffer_pos)) {
|
||||
buffer_pos ++;
|
||||
}
|
||||
if (buffer_pos < buffer_end) {
|
||||
cur_token_len = buffer_pos - cur_token;
|
||||
} else {
|
||||
cur_token_real_len = buffer_pos - cur_token;
|
||||
cur_token_len = -3;
|
||||
}
|
||||
return;
|
||||
} else if (c == '"') {
|
||||
cur_token_quoted = 1;
|
||||
cur_token = buffer_pos ++;
|
||||
int backslashed = 0;
|
||||
while (buffer_pos < buffer_end && (*buffer_pos != '"' || backslashed)) {
|
||||
if (*buffer_pos == '\\') {
|
||||
backslashed ^= 1;
|
||||
} else {
|
||||
backslashed = 0;
|
||||
}
|
||||
buffer_pos ++;
|
||||
}
|
||||
if (*buffer_pos == '"') {
|
||||
buffer_pos ++;
|
||||
expand_backslashed (cur_token + 1, buffer_pos - cur_token - 2);
|
||||
if (exp_buffer_pos < 0) {
|
||||
cur_token_len = -2;
|
||||
} else {
|
||||
cur_token_len = exp_buffer_pos;
|
||||
cur_token = exp_buffer;
|
||||
}
|
||||
} else {
|
||||
cur_token_len = -2;
|
||||
}
|
||||
return;
|
||||
} else {
|
||||
if (c) {
|
||||
cur_token = buffer_pos ++;
|
||||
cur_token_len = 1;
|
||||
} else {
|
||||
cur_token_len = -3;
|
||||
cur_token_real_len = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#define MAX_FVARS 100
|
||||
static struct paramed_type *fvars[MAX_FVARS];
|
||||
static int fvars_pos;
|
||||
|
||||
static void add_var_to_be_freed (struct paramed_type *P) {
|
||||
assert (fvars_pos < MAX_FVARS);
|
||||
fvars[fvars_pos ++] = P;
|
||||
}
|
||||
|
||||
static void free_vars_to_be_freed (void) {
|
||||
int i;
|
||||
for (i = 0; i < fvars_pos; i++) {
|
||||
tgl_paramed_type_free (fvars[i]);
|
||||
}
|
||||
fvars_pos = 0;
|
||||
}
|
||||
|
||||
int tglf_extf_autocomplete (const char *text, int text_len, int index, char **R, char *data, int data_len) {
|
||||
if (index == -1) {
|
||||
buffer_pos = data;
|
||||
buffer_end = data + data_len;
|
||||
autocomplete_mode = 0;
|
||||
local_next_token ();
|
||||
struct paramed_type *P = autocomplete_function_any ();
|
||||
free_vars_to_be_freed ();
|
||||
if (P) { tgl_paramed_type_free (P); }
|
||||
}
|
||||
if (autocomplete_mode == 0) { return -1; }
|
||||
int len = strlen (text);
|
||||
if (autocomplete_mode == 1) {
|
||||
if (index >= 0) { return -1; }
|
||||
index = 0;
|
||||
if (!strncmp (text, autocomplete_string, len)) {
|
||||
*R = strdup (autocomplete_string);
|
||||
assert (*R);
|
||||
return index;
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
return autocomplete_fun (text, len, index, R);
|
||||
}
|
||||
}
|
||||
|
||||
struct paramed_type *tglf_extf_store (const char *data, int data_len) {
|
||||
buffer_pos = (char *)data;
|
||||
buffer_end = (char *)(data + data_len);
|
||||
local_next_token ();
|
||||
return store_function_any ();
|
||||
}
|
||||
|
||||
#define OUT_BUF_SIZE (1 << 25)
|
||||
static char out_buf[OUT_BUF_SIZE];
|
||||
static int out_buf_pos;
|
||||
|
||||
#define eprintf(...) \
|
||||
do { \
|
||||
out_buf_pos += snprintf (out_buf + out_buf_pos, OUT_BUF_SIZE - out_buf_pos, __VA_ARGS__);\
|
||||
assert (out_buf_pos < OUT_BUF_SIZE);\
|
||||
} while (0)\
|
||||
|
||||
static int valid_utf8_char (const char *str) {
|
||||
unsigned char c = (unsigned char) *str;
|
||||
int n = 0;
|
||||
|
||||
if ((c & 0x80) == 0x00) {
|
||||
n = 0;
|
||||
} else if ((c & 0xe0) == 0xc0) {
|
||||
n = 1;
|
||||
} else if ((c & 0xf0) == 0xe0) {
|
||||
n = 2;
|
||||
} else if ((c & 0xf8) == 0xf0) {
|
||||
n = 3;
|
||||
} else if ((c & 0xfc) == 0xf8) {
|
||||
n = 4;
|
||||
} else if ((c & 0xfe) == 0xfc) {
|
||||
n = 5;
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
|
||||
int i;
|
||||
for (i = 0; i < n; i ++) {
|
||||
if ((((unsigned char)(str[i + 1])) & 0xc0) != 0x80) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return n + 1;
|
||||
}
|
||||
|
||||
static void print_escaped_string (const char *str, int len) {
|
||||
eprintf ("\"");
|
||||
const char *end = str + len;
|
||||
while (str < end) {
|
||||
int n = valid_utf8_char (str);
|
||||
if (n < 0) {
|
||||
eprintf ("\\x%02x", (int)(unsigned char)*str);
|
||||
str ++;
|
||||
} else if (n >= 2) {
|
||||
int i;
|
||||
for (i = 0; i < n; i++) {
|
||||
eprintf ("%c", *(str ++));
|
||||
}
|
||||
} else if (((unsigned char)*str) >= ' ' && *str != '"' && *str != '\\') {
|
||||
eprintf ("%c", *str);
|
||||
str ++;
|
||||
} else {
|
||||
switch (*str) {
|
||||
case '\n':
|
||||
eprintf("\\n");
|
||||
break;
|
||||
case '\r':
|
||||
eprintf("\\r");
|
||||
break;
|
||||
case '\t':
|
||||
eprintf("\\t");
|
||||
break;
|
||||
case '\b':
|
||||
eprintf("\\b");
|
||||
break;
|
||||
case '\a':
|
||||
eprintf("\\a");
|
||||
break;
|
||||
case '\\':
|
||||
eprintf ("\\\\");
|
||||
break;
|
||||
case '"':
|
||||
eprintf ("\\\"");
|
||||
break;
|
||||
default:
|
||||
eprintf ("\\x%02x", (int)(unsigned char)*str);
|
||||
break;
|
||||
}
|
||||
str ++;
|
||||
}
|
||||
}
|
||||
eprintf ("\"");
|
||||
}
|
||||
|
||||
static void print_offset (void) {
|
||||
int i;
|
||||
for (i = 0; i < multiline_offset; i++) {
|
||||
eprintf (" ");
|
||||
}
|
||||
}
|
||||
|
||||
char *tglf_extf_fetch (struct paramed_type *T) {
|
||||
out_buf_pos = 0;
|
||||
fetch_type_any (T);
|
||||
return out_buf;
|
||||
}
|
48
auto.h
Normal file
48
auto.h
Normal file
|
@ -0,0 +1,48 @@
|
|||
/*
|
||||
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 __AUTO_H__
|
||||
#define __AUTO_H__
|
||||
|
||||
struct tl_type_descr {
|
||||
unsigned name;
|
||||
char *id;
|
||||
int params_num;
|
||||
long long params_types;
|
||||
};
|
||||
|
||||
struct paramed_type {
|
||||
struct tl_type_descr *type;
|
||||
struct paramed_type **params;
|
||||
};
|
||||
|
||||
#define NAME_ARRAY 0x89932ad9
|
||||
|
||||
#define TYPE_TO_PARAM(NAME) (&(struct paramed_type) {.type = &tl_type_## NAME, .params=0})
|
||||
#define TYPE_TO_PARAM_1(NAME,PARAM1) (&(struct paramed_type) {.type = &tl_type_## NAME, .params=(struct paramed_type *[1]){PARAM1}})
|
||||
#define ODDP(x) (((long)(x)) & 1)
|
||||
#define EVENP(x) (!ODDP(x))
|
||||
#define INT2PTR(x) (void *)(long)(((long)x) * 2 + 1)
|
||||
#define PTR2INT(x) ((((long)x) - 1) / 2)
|
||||
|
||||
void tgl_paramed_type_free (struct paramed_type *P);
|
||||
|
||||
#include "auto/auto-header.h"
|
||||
|
||||
#endif
|
185
binlog.h
185
binlog.h
|
@ -1,115 +1,54 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __BINLOG_H__
|
||||
#define __BINLOG_H__
|
||||
|
||||
#include "structures.h"
|
||||
//#include "structures.h"
|
||||
#include "tgl.h"
|
||||
|
||||
#define LOG_START 0x8948329a
|
||||
#define LOG_AUTH_KEY 0x984932aa
|
||||
#define LOG_DEFAULT_DC 0x95382908
|
||||
#define LOG_OUR_ID 0x8943211a
|
||||
#define LOG_DC_SIGNED 0x234f9893
|
||||
#define LOG_DC_SALT 0x92192ffa
|
||||
#define LOG_DH_CONFIG 0x8983402b
|
||||
#define LOG_ENCR_CHAT_KEY 0x894320aa
|
||||
#define LOG_ENCR_CHAT_SEND_ACCEPT 0x12ab01c4
|
||||
#define LOG_ENCR_CHAT_SEND_CREATE 0xab091e24
|
||||
#define LOG_ENCR_CHAT_DELETED 0x99481230
|
||||
#define LOG_ENCR_CHAT_WAITING 0x7102100a
|
||||
#define LOG_ENCR_CHAT_REQUESTED 0x9011011a
|
||||
#define LOG_ENCR_CHAT_OK 0x7612ce13
|
||||
|
||||
#define CODE_binlog_new_user 0xe04f30de
|
||||
#define CODE_binlog_user_delete 0xf7a27c79
|
||||
#define CODE_binlog_set_user_access_token 0x1349f615
|
||||
#define CODE_binlog_set_user_phone 0x5d3afde2
|
||||
#define CODE_binlog_set_user_friend 0x75a7ec5a
|
||||
#define CODE_binlog_dc_option 0x08c0ef19
|
||||
#define CODE_binlog_user_full_photo 0xfaa35824
|
||||
#define CODE_binlog_user_blocked 0xb2dea7cd
|
||||
#define CODE_binlog_set_user_full_name 0x4ceb4cf0
|
||||
#define CODE_binlog_encr_chat_delete 0xb9d33f87
|
||||
#define CODE_binlog_encr_chat_requested 0xf57d1ea2
|
||||
#define CODE_binlog_set_encr_chat_access_hash 0xe5612bb3
|
||||
#define CODE_binlog_set_encr_chat_date 0x54f16911
|
||||
#define CODE_binlog_set_encr_chat_state 0x76a6e45b
|
||||
#define CODE_binlog_encr_chat_accepted 0x4627e926
|
||||
#define CODE_binlog_set_encr_chat_key 0x179df2d4
|
||||
#define CODE_binlog_set_dh_params 0x20ba46bc
|
||||
#define CODE_binlog_encr_chat_init 0x939cd1c7
|
||||
#define CODE_binlog_set_pts 0x844e4c1c
|
||||
#define CODE_binlog_set_qts 0x3cf22b79
|
||||
#define CODE_binlog_set_date 0x33dfe392
|
||||
#define CODE_binlog_set_seq 0xb9294837
|
||||
#define CODE_binlog_chat_create 0xbaa75791
|
||||
#define CODE_binlog_chat_change_flags 0x1e494031
|
||||
#define CODE_binlog_set_chat_title 0x7dd9bea8
|
||||
#define CODE_binlog_set_chat_photo 0xb4ea1fd2
|
||||
#define CODE_binlog_set_chat_date 0x78d1114e
|
||||
#define CODE_binlog_set_chat_version 0xa5d3504f
|
||||
#define CODE_binlog_set_chat_admin 0x1e7cea04
|
||||
#define CODE_binlog_set_chat_participants 0x3a29d335
|
||||
#define CODE_binlog_chat_full_photo 0x6cca6629
|
||||
#define CODE_binlog_add_chat_participant 0x63345108
|
||||
#define CODE_binlog_del_chat_participant 0x82d1f0ee
|
||||
#define CODE_binlog_create_message_text 0x269acd5b
|
||||
#define CODE_binlog_create_message_text_fwd 0xa3d864cd
|
||||
#define CODE_binlog_create_message_service 0xbbe5e94b
|
||||
#define CODE_binlog_create_message_service_fwd 0xea9c57ae
|
||||
#define CODE_binlog_create_message_media 0x62a92d19
|
||||
#define CODE_binlog_create_message_media_fwd 0xbefdc462
|
||||
#define CODE_binlog_send_message_text 0x31cfd652
|
||||
#define CODE_binlog_set_unread 0x21d4c909
|
||||
#define CODE_binlog_set_message_sent 0xc335282b
|
||||
#define CODE_binlog_set_msg_id 0xf3285b6a
|
||||
#define CODE_binlog_create_message_media_encr 0x19cd7c9d
|
||||
#define CODE_binlog_create_message_service_encr 0x8b4b9395
|
||||
#define CODE_binlog_delete_msg 0xa1d6ab6d
|
||||
|
||||
void *alloc_log_event (int l);
|
||||
void replay_log (void);
|
||||
void add_log_event (const int *data, int l);
|
||||
void write_binlog (void);
|
||||
void bl_do_set_auth_key_id (int num, unsigned char *buf);
|
||||
|
||||
void bl_do_dc_option (int id, int l1, const char *name, int l2, const char *ip, int port);
|
||||
|
||||
void bl_do_set_our_id (int id);
|
||||
void bl_do_new_user (int id, const char *f, int fl, const char *l, int ll, long long access_token, const char *p, int pl, int contact);
|
||||
void bl_do_user_delete (struct user *U);
|
||||
void bl_do_set_user_profile_photo (struct user *U, long long photo_id, struct file_location *big, struct file_location *small);
|
||||
void bl_do_set_user_name (struct user *U, const char *f, int fl, const char *l, int ll);
|
||||
void bl_do_set_user_access_token (struct user *U, long long access_token);
|
||||
void bl_do_set_user_phone (struct user *U, const char *p, int pl);
|
||||
void bl_do_set_user_friend (struct user *U, int friend);
|
||||
void bl_do_set_user_full_photo (struct user *U, const int *start, int len);
|
||||
void bl_do_set_user_blocked (struct user *U, int blocked);
|
||||
void bl_do_set_user_real_name (struct user *U, const char *f, int fl, const char *l, int ll);
|
||||
void bl_do_user_add (int id, const char *f, int fl, const char *l, int ll, long long access_token, const char *p, int pl, int contact);
|
||||
void bl_do_user_delete (struct tgl_user *U);
|
||||
void bl_do_set_user_profile_photo (struct tgl_user *U, long long photo_id, struct tgl_file_location *big, struct tgl_file_location *small);
|
||||
void bl_do_user_set_name (struct tgl_user *U, const char *f, int fl, const char *l, int ll);
|
||||
void bl_do_user_set_access_hash (struct tgl_user *U, long long access_token);
|
||||
void bl_do_user_set_phone (struct tgl_user *U, const char *p, int pl);
|
||||
void bl_do_user_set_friend (struct tgl_user *U, int friend);
|
||||
void bl_do_user_set_full_photo (struct tgl_user *U, const int *start, int len);
|
||||
void bl_do_user_set_blocked (struct tgl_user *U, int blocked);
|
||||
void bl_do_user_set_real_name (struct tgl_user *U, const char *f, int fl, const char *l, int ll);
|
||||
|
||||
void bl_do_encr_chat_delete (struct secret_chat *U);
|
||||
void bl_do_encr_chat_requested (struct secret_chat *U, long long access_hash, int date, int admin_id, int user_id, unsigned char g_key[], unsigned char nonce[]);
|
||||
void bl_do_set_encr_chat_access_hash (struct secret_chat *U, long long access_hash);
|
||||
void bl_do_set_encr_chat_date (struct secret_chat *U, int date);
|
||||
void bl_do_set_encr_chat_state (struct secret_chat *U, enum secret_chat_state state);
|
||||
void bl_do_encr_chat_accepted (struct secret_chat *U, const unsigned char g_key[], const unsigned char nonce[], long long key_fingerprint);
|
||||
void bl_do_set_encr_chat_key (struct secret_chat *E, unsigned char key[], long long key_fingerprint);
|
||||
void bl_do_encr_chat_delete (struct tgl_secret_chat *U);
|
||||
void bl_do_encr_chat_requested (struct tgl_secret_chat *U, long long access_hash, int date, int admin_id, int user_id, unsigned char g_key[], unsigned char nonce[]);
|
||||
void bl_do_encr_chat_create (int id, int user_id, int admin_id, char *name, int name_len);
|
||||
void bl_do_encr_chat_set_access_hash (struct tgl_secret_chat *U, long long access_hash);
|
||||
void bl_do_encr_chat_set_date (struct tgl_secret_chat *U, int date);
|
||||
void bl_do_encr_chat_set_state (struct tgl_secret_chat *U, enum tgl_secret_chat_state state);
|
||||
void bl_do_encr_chat_set_ttl (struct tgl_secret_chat *U, int ttl);
|
||||
void bl_do_encr_chat_set_layer (struct tgl_secret_chat *U, int layer);
|
||||
void bl_do_encr_chat_accepted (struct tgl_secret_chat *U, const unsigned char g_key[], const unsigned char nonce[], long long key_fingerprint);
|
||||
void bl_do_encr_chat_set_key (struct tgl_secret_chat *E, unsigned char key[], long long key_fingerprint);
|
||||
void bl_do_encr_chat_init (int id, int user_id, unsigned char random[], unsigned char g_a[]);
|
||||
|
||||
void bl_do_dc_signed (int id);
|
||||
|
@ -121,30 +60,40 @@ void bl_do_set_qts (int qts);
|
|||
void bl_do_set_seq (int seq);
|
||||
void bl_do_set_date (int date);
|
||||
|
||||
void bl_do_create_chat (struct chat *C, int y, const char *s, int l, int users_num, int date, int version, struct file_location *big, struct file_location *small);
|
||||
void bl_do_chat_forbid (struct chat *C, int on);
|
||||
void bl_do_set_chat_title (struct chat *C, const char *s, int l);
|
||||
void bl_do_set_chat_photo (struct chat *C, struct file_location *big, struct file_location *small);
|
||||
void bl_do_set_chat_date (struct chat *C, int date);
|
||||
void bl_do_set_chat_set_in_chat (struct chat *C, int on);
|
||||
void bl_do_set_chat_version (struct chat *C, int version, int user_num);
|
||||
void bl_do_set_chat_admin (struct chat *C, int admin);
|
||||
void bl_do_set_chat_participants (struct chat *C, int version, int user_num, struct chat_user *users);
|
||||
void bl_do_set_chat_full_photo (struct chat *U, const int *start, int len);
|
||||
void bl_do_chat_add_user (struct chat *C, int version, int user, int inviter, int date);
|
||||
void bl_do_chat_del_user (struct chat *C, int version, int user);
|
||||
void bl_do_create_chat (struct tgl_chat *C, int y, const char *s, int l, int users_num, int date, int version, struct tgl_file_location *big, struct tgl_file_location *small);
|
||||
void bl_do_chat_forbid (struct tgl_chat *C, int on);
|
||||
void bl_do_chat_set_title (struct tgl_chat *C, const char *s, int l);
|
||||
void bl_do_chat_set_photo (struct tgl_chat *C, struct tgl_file_location *big, struct tgl_file_location *small);
|
||||
void bl_do_chat_set_date (struct tgl_chat *C, int date);
|
||||
void bl_do_chat_set_set_in_chat (struct tgl_chat *C, int on);
|
||||
void bl_do_chat_set_version (struct tgl_chat *C, int version, int user_num);
|
||||
void bl_do_chat_set_admin (struct tgl_chat *C, int admin);
|
||||
void bl_do_chat_set_participants (struct tgl_chat *C, int version, int user_num, struct tgl_chat_user *users);
|
||||
void bl_do_chat_set_full_photo (struct tgl_chat *U, const int *start, int len);
|
||||
void bl_do_chat_add_user (struct tgl_chat *C, int version, int user, int inviter, int date);
|
||||
void bl_do_chat_del_user (struct tgl_chat *C, int version, int user);
|
||||
|
||||
void bl_do_create_message_text (int msg_id, int from_id, int to_type, int to_id, int date, int l, const char *s);
|
||||
void bl_do_create_message_text_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, int l, const char *s);
|
||||
void bl_do_create_message_service (int msg_id, int from_id, int to_type, int to_id, int date, const int *data, int len);
|
||||
void bl_do_create_message_service_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, const int *data, int len);
|
||||
void bl_do_create_message_media (int msg_id, int from_id, int to_type, int to_id, int date, int l, const char *s, const int *data, int len);
|
||||
void bl_do_create_message_media_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, int l, const char *s, const int *data, int len);
|
||||
void bl_do_create_message_text (int msg_id, int from_id, int to_type, int to_id, int date, int unread, int l, const char *s);
|
||||
void bl_do_create_message_text_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, int unread, int l, const char *s);
|
||||
void bl_do_create_message_service (int msg_id, int from_id, int to_type, int to_id, int date, int unread, const int *data, int len);
|
||||
void bl_do_create_message_service_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, int unread, const int *data, int len);
|
||||
void bl_do_create_message_media (int msg_id, int from_id, int to_type, int to_id, int date, int unread, int l, const char *s, const int *data, int len);
|
||||
void bl_do_create_message_media_encr_pending (long long msg_id, int from_id, int to_type, int to_id, int date, int l, const char *s, const int *data, int len);
|
||||
void bl_do_create_message_media_encr_sent (long long msg_id, const int *data, int len);
|
||||
void bl_do_create_message_media_fwd (int msg_id, int from_id, int to_type, int to_id, int date, int fwd, int fwd_date, int unread, int l, const char *s, const int *data, int len);
|
||||
void bl_do_create_message_media_encr (long long msg_id, int from_id, int to_type, int to_id, int date, int l, const char *s, const int *data, int len, const int *data2, int len2);
|
||||
void bl_do_create_message_service_encr (long long msg_id, int from_id, int to_type, int to_id, int date, const int *data, int len);
|
||||
void bl_do_send_message_text (long long msg_id, int from_id, int to_type, int to_id, int date, int l, const char *s);
|
||||
void bl_do_set_unread (struct message *M, int unread);
|
||||
void bl_do_set_message_sent (struct message *M);
|
||||
void bl_do_set_msg_id (struct message *M, int id);
|
||||
void bl_do_delete_msg (struct message *M);
|
||||
void bl_do_send_message_action_encr (long long msg_id, int from_id, int to_type, int to_id, int date, int l, const int *s);
|
||||
void bl_do_set_unread (struct tgl_message *M, int unread);
|
||||
void bl_do_set_message_sent (struct tgl_message *M);
|
||||
void bl_do_set_msg_id (struct tgl_message *M, int id);
|
||||
void bl_do_delete_msg (struct tgl_message *M);
|
||||
|
||||
void bl_do_msg_seq_update (long long id);
|
||||
void bl_do_msg_update (long long id);
|
||||
|
||||
void bl_do_reset_authorization (void);
|
||||
|
||||
//void bl_do_add_dc (int id, const char *ip, int l, int port, long long auth_key_id, const char *auth_key);
|
||||
#endif
|
||||
|
|
81
binlog.tl
81
binlog.tl
|
@ -1,10 +1,79 @@
|
|||
log.peer peer_type:int peer_id:int = log.Peer;
|
||||
---types---
|
||||
binlog.fileLocation dc:int volume:long local_id:int secret:long = binlog.FileLocation;
|
||||
binlog.chatParticipant user:int inviter:int date:int = binlog.ChatParticipant;
|
||||
|
||||
log.dc num:int hostname:string ip:string port:int = log.Event;
|
||||
log.dcRenum old_num:int new_num:int = log.Event;
|
||||
log.authKey dc:int key:bytes key_id:long = log.Event;
|
||||
log.signIn dc:int id:int = log.Event;
|
||||
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;
|
||||
|
||||
log.user id:int flags:int access_hash:long first_name:string last_name:string real_first_name:string real_last_name:string phone:string photo:log.Photo photo_id:long photo_big:log.FileLocation photo_small:long.FileLocation = log.Event;
|
||||
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.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.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;
|
||||
|
|
24
config.h.in
24
config.h.in
|
@ -1,5 +1,11 @@
|
|||
/* config.h.in. Generated from configure.ac by autoheader. */
|
||||
|
||||
/* Use libevent v1 */
|
||||
#undef EVENT_V1
|
||||
|
||||
/* Use libevent v2 */
|
||||
#undef EVENT_V2
|
||||
|
||||
/* Define to 1 if you have the `alarm' function. */
|
||||
#undef HAVE_ALARM
|
||||
|
||||
|
@ -24,16 +30,13 @@
|
|||
/* Define to 1 if you have the `config' library (-lconfig). */
|
||||
#undef HAVE_LIBCONFIG
|
||||
|
||||
/* Define to 1 if you have the `crypto' library (-lcrypto). */
|
||||
#undef HAVE_LIBCRYPTO
|
||||
|
||||
/* Define to 1 if you have the `edit' library (-ledit). */
|
||||
#undef HAVE_LIBEDIT
|
||||
/* Define to 1 if you have the `event' library (-levent). */
|
||||
#undef HAVE_LIBEVENT
|
||||
|
||||
/* Define to 1 if you have the `m' library (-lm). */
|
||||
#undef HAVE_LIBM
|
||||
|
||||
/* Define to 1 if you have the `z' library (-lz). */
|
||||
/* Define to 1 if you have `z' library (-lz) */
|
||||
#undef HAVE_LIBZ
|
||||
|
||||
/* Define to 1 if you have the <luaconf.h> header file. */
|
||||
|
@ -122,6 +125,9 @@
|
|||
/* Define to 1 if you have the <unistd.h> header file. */
|
||||
#undef HAVE_UNISTD_H
|
||||
|
||||
/* Define to 1 if the system has the `__builtin_bswap32' built-in function */
|
||||
#undef HAVE___BUILTIN_BSWAP32
|
||||
|
||||
/* Define to the address where bug reports for this package should be sent. */
|
||||
#undef PACKAGE_BUGREPORT
|
||||
|
||||
|
@ -143,12 +149,6 @@
|
|||
/* Use custom prog name */
|
||||
#undef PROG_NAME
|
||||
|
||||
/* Use libedit */
|
||||
#undef READLINE_EDIT
|
||||
|
||||
/* Use gnu libreadline */
|
||||
#undef READLINE_GNU
|
||||
|
||||
/* Define to 1 if you have the ANSI C header files. */
|
||||
#undef STDC_HEADERS
|
||||
|
||||
|
|
37
configure.ac
37
configure.ac
|
@ -1,9 +1,12 @@
|
|||
AC_PREREQ([2.68])
|
||||
AC_INIT([telegram], [0.1])
|
||||
AC_INIT([telegram-cli], [1.0])
|
||||
AC_CONFIG_SRCDIR([config.h.in])
|
||||
AC_CONFIG_HEADERS([config.h])
|
||||
|
||||
m4_include([ax_lua.m4])
|
||||
m4_include([m4_ax_check_openssl.m4])
|
||||
m4_include([m4_ax_check_zlib.m4])
|
||||
m4_include([m4-ax_gcc_builtin.m4])
|
||||
|
||||
# Checks for programs.
|
||||
AC_PROG_CC
|
||||
|
@ -16,22 +19,24 @@ LDFLAGS="$LDFLAGS -L/usr/local/lib"
|
|||
AC_CHECK_LIB([m], [sqrt])
|
||||
AC_SEARCH_LIBS([clock_gettime], [rt])
|
||||
AC_SEARCH_LIBS([backtrace], [execinfo])
|
||||
AC_CHECK_LIB([z], [inflate])
|
||||
AC_CHECK_LIB([crypto], [AES_set_encrypt_key])
|
||||
AC_CHECK_LIB([event], [event_base_new], [], [AC_MSG_ERROR([no libevent found])])
|
||||
|
||||
EVENT_VER=""
|
||||
|
||||
AC_CHECK_HEADER(event2/event.h, [AC_DEFINE([EVENT_V2], [1], [Use libevent v2])], [
|
||||
AC_CHECK_HEADER(event.h, [AC_DEFINE([EVENT_V1], [1], [Use libevent v1])], [AC_MSG_ERROR([no libevent found])])
|
||||
])
|
||||
|
||||
EXTRA_LIBS=""
|
||||
|
||||
AC_CHECK_LIB([readline], [rl_save_prompt],
|
||||
[
|
||||
AC_DEFINE([READLINE_GNU], [1], [Use gnu libreadline])
|
||||
[ EXTRA_LIBS="${EXTRA_LIBS} -lreadline" ; ]
|
||||
],
|
||||
[
|
||||
AC_SEARCH_LIBS([tgetnum], [ncursesw ncurses curses])
|
||||
AC_CHECK_LIB([edit], [rl_set_prompt])
|
||||
AC_DEFINE([READLINE_EDIT], [1], [Use libedit])
|
||||
[ EXTRA_LIBS="${EXTRA_LIBS} -ledit" ; ]
|
||||
]
|
||||
)
|
||||
# OPENSSL_INCLUDES to the include directives required
|
||||
# OPENSSL_LIBS to the -l directives required
|
||||
# OPENSSL_LDFLAGS to the -L or -R flags required
|
||||
|
||||
AX_CHECK_OPENSSL(,[AC_MSG_ERROR([No openssl found])])
|
||||
AX_CHECK_ZLIB(, [AC_MSG_ERROR([No zlib found])])
|
||||
|
||||
AC_CHECK_LIB([readline], [rl_save_prompt], [ EXTRA_LIBS="${EXTRA_LIBS} -lreadline" ; ], [AC_MSG_ERROR([no libreadline found])])
|
||||
|
||||
AC_MSG_CHECKING([for libconfig])
|
||||
AC_ARG_ENABLE(libconfig,[--enable-libconfig/--disable-libconfig],
|
||||
|
@ -109,6 +114,8 @@ AC_FUNC_MALLOC
|
|||
AC_FUNC_REALLOC
|
||||
AC_CHECK_FUNCS([alarm endpwent memset memmove mkdir select socket strdup strndup uname])
|
||||
|
||||
AX_GCC_BUILTIN(__builtin_bswap32)
|
||||
|
||||
AC_SUBST(EXTRA_LIBS)
|
||||
AC_CONFIG_FILES([Makefile])
|
||||
AC_OUTPUT
|
||||
|
|
383
constants.h
383
constants.h
|
@ -1,383 +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 <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013
|
||||
*/
|
||||
#ifndef CONSTANTS_H
|
||||
#define CONSTANTS_H
|
||||
#define CODE_bool_false 0xbc799737
|
||||
#define CODE_bool_true 0x997275b5
|
||||
#define CODE_vector 0x1cb5c415
|
||||
#define CODE_error 0xc4b9f9bb
|
||||
#define CODE_null 0x56730bcc
|
||||
#define CODE_input_peer_empty 0x7f3b18ea
|
||||
#define CODE_input_peer_self 0x7da07ec9
|
||||
#define CODE_input_peer_contact 0x1023dbe8
|
||||
#define CODE_input_peer_foreign 0x9b447325
|
||||
#define CODE_input_peer_chat 0x179be863
|
||||
#define CODE_input_user_empty 0xb98886cf
|
||||
#define CODE_input_user_self 0xf7c1b13f
|
||||
#define CODE_input_user_contact 0x86e94f65
|
||||
#define CODE_input_user_foreign 0x655e74ff
|
||||
#define CODE_input_phone_contact 0xf392b7f4
|
||||
#define CODE_input_file 0xf52ff27f
|
||||
#define CODE_input_media_empty 0x9664f57f
|
||||
#define CODE_input_media_uploaded_photo 0x2dc53a7d
|
||||
#define CODE_input_media_photo 0x8f2ab2ec
|
||||
#define CODE_input_media_geo_point 0xf9c44144
|
||||
#define CODE_input_media_contact 0xa6e45987
|
||||
#define CODE_input_media_uploaded_video 0x4847d92a
|
||||
#define CODE_input_media_uploaded_thumb_video 0xe628a145
|
||||
#define CODE_input_media_video 0x7f023ae6
|
||||
#define CODE_input_chat_photo_empty 0x1ca48f57
|
||||
#define CODE_input_chat_uploaded_photo 0x94254732
|
||||
#define CODE_input_chat_photo 0xb2e1bf08
|
||||
#define CODE_input_geo_point_empty 0xe4c123d6
|
||||
#define CODE_input_geo_point 0xf3b7acc9
|
||||
#define CODE_input_photo_empty 0x1cd7bf0d
|
||||
#define CODE_input_photo 0xfb95c6c4
|
||||
#define CODE_input_video_empty 0x5508ec75
|
||||
#define CODE_input_video 0xee579652
|
||||
#define CODE_input_file_location 0x14637196
|
||||
#define CODE_input_video_file_location 0x3d0364ec
|
||||
#define CODE_input_photo_crop_auto 0xade6b004
|
||||
#define CODE_input_photo_crop 0xd9915325
|
||||
#define CODE_input_app_event 0x770656a8
|
||||
#define CODE_peer_user 0x9db1bc6d
|
||||
#define CODE_peer_chat 0xbad0e5bb
|
||||
#define CODE_storage_file_unknown 0xaa963b05
|
||||
#define CODE_storage_file_jpeg 0x7efe0e
|
||||
#define CODE_storage_file_gif 0xcae1aadf
|
||||
#define CODE_storage_file_png 0xa4f63c0
|
||||
#define CODE_storage_file_mp3 0x528a0677
|
||||
#define CODE_storage_file_mov 0x4b09ebbc
|
||||
#define CODE_storage_file_partial 0x40bc6f52
|
||||
#define CODE_storage_file_mp4 0xb3cea0e4
|
||||
#define CODE_storage_file_webp 0x1081464c
|
||||
#define CODE_file_location_unavailable 0x7c596b46
|
||||
#define CODE_file_location 0x53d69076
|
||||
#define CODE_user_empty 0x200250ba
|
||||
#define CODE_user_self 0x720535ec
|
||||
#define CODE_user_contact 0xf2fb8319
|
||||
#define CODE_user_request 0x22e8ceb0
|
||||
#define CODE_user_foreign 0x5214c89d
|
||||
#define CODE_user_deleted 0xb29ad7cc
|
||||
#define CODE_user_profile_photo_empty 0x4f11bae1
|
||||
#define CODE_user_profile_photo 0xd559d8c8
|
||||
#define CODE_user_status_empty 0x9d05049
|
||||
#define CODE_user_status_online 0xedb93949
|
||||
#define CODE_user_status_offline 0x8c703f
|
||||
#define CODE_chat_empty 0x9ba2d800
|
||||
#define CODE_chat 0x6e9c9bc7
|
||||
#define CODE_chat_forbidden 0xfb0ccc41
|
||||
#define CODE_chat_full 0x630e61be
|
||||
#define CODE_chat_participant 0xc8d7493e
|
||||
#define CODE_chat_participants_forbidden 0xfd2bb8a
|
||||
#define CODE_chat_participants 0x7841b415
|
||||
#define CODE_chat_photo_empty 0x37c1011c
|
||||
#define CODE_chat_photo 0x6153276a
|
||||
#define CODE_message_empty 0x83e5de54
|
||||
#define CODE_message 0x22eb6aba
|
||||
#define CODE_message_forwarded 0x5f46804
|
||||
#define CODE_message_service 0x9f8d60bb
|
||||
#define CODE_message_media_empty 0x3ded6320
|
||||
#define CODE_message_media_photo 0xc8c45a2a
|
||||
#define CODE_message_media_video 0xa2d24290
|
||||
#define CODE_message_media_geo 0x56e0d474
|
||||
#define CODE_message_media_contact 0x5e7d2f39
|
||||
#define CODE_message_media_unsupported 0x29632a36
|
||||
#define CODE_message_action_empty 0xb6aef7b0
|
||||
#define CODE_message_action_chat_create 0xa6638b9a
|
||||
#define CODE_message_action_chat_edit_title 0xb5a1ce5a
|
||||
#define CODE_message_action_chat_edit_photo 0x7fcb13a8
|
||||
#define CODE_message_action_chat_delete_photo 0x95e3fbef
|
||||
#define CODE_message_action_chat_add_user 0x5e3cfc4b
|
||||
#define CODE_message_action_chat_delete_user 0xb2ae9b0c
|
||||
#define CODE_dialog 0x214a8cdf
|
||||
#define CODE_photo_empty 0x2331b22d
|
||||
#define CODE_photo 0x22b56751
|
||||
#define CODE_photo_size_empty 0xe17e23c
|
||||
#define CODE_photo_size 0x77bfb61b
|
||||
#define CODE_photo_cached_size 0xe9a734fa
|
||||
#define CODE_video_empty 0xc10658a8
|
||||
#define CODE_video 0x5a04a49f
|
||||
#define CODE_geo_point_empty 0x1117dd5f
|
||||
#define CODE_geo_point 0x2049d70c
|
||||
#define CODE_auth_checked_phone 0xe300cc3b
|
||||
#define CODE_auth_sent_code 0xefed51d9
|
||||
#define CODE_auth_authorization 0xf6b673a4
|
||||
#define CODE_auth_exported_authorization 0xdf969c2d
|
||||
#define CODE_input_notify_peer 0xb8bc5b0c
|
||||
#define CODE_input_notify_users 0x193b4417
|
||||
#define CODE_input_notify_chats 0x4a95e84e
|
||||
#define CODE_input_notify_all 0xa429b886
|
||||
#define CODE_input_peer_notify_events_empty 0xf03064d8
|
||||
#define CODE_input_peer_notify_events_all 0xe86a2c74
|
||||
#define CODE_input_peer_notify_settings 0x46a2ce98
|
||||
#define CODE_peer_notify_events_empty 0xadd53cb3
|
||||
#define CODE_peer_notify_events_all 0x6d1ded88
|
||||
#define CODE_peer_notify_settings_empty 0x70a68512
|
||||
#define CODE_peer_notify_settings 0x8d5e11ee
|
||||
#define CODE_wall_paper 0xccb03657
|
||||
#define CODE_user_full 0x771095da
|
||||
#define CODE_contact 0xf911c994
|
||||
#define CODE_imported_contact 0xd0028438
|
||||
#define CODE_contact_blocked 0x561bc879
|
||||
#define CODE_contact_found 0xea879f95
|
||||
#define CODE_contact_suggested 0x3de191a1
|
||||
#define CODE_contact_status 0xaa77b873
|
||||
#define CODE_chat_located 0x3631cf4c
|
||||
#define CODE_contacts_foreign_link_unknown 0x133421f8
|
||||
#define CODE_contacts_foreign_link_requested 0xa7801f47
|
||||
#define CODE_contacts_foreign_link_mutual 0x1bea8ce1
|
||||
#define CODE_contacts_my_link_empty 0xd22a1c60
|
||||
#define CODE_contacts_my_link_requested 0x6c69efee
|
||||
#define CODE_contacts_my_link_contact 0xc240ebd9
|
||||
#define CODE_contacts_link 0xeccea3f5
|
||||
#define CODE_contacts_contacts 0x6f8b8cb2
|
||||
#define CODE_contacts_contacts_not_modified 0xb74ba9d2
|
||||
#define CODE_contacts_imported_contacts 0xd1cd0a4c
|
||||
#define CODE_contacts_blocked 0x1c138d15
|
||||
#define CODE_contacts_blocked_slice 0x900802a1
|
||||
#define CODE_contacts_found 0x566000e
|
||||
#define CODE_contacts_suggested 0x5649dcc5
|
||||
#define CODE_messages_dialogs 0x15ba6c40
|
||||
#define CODE_messages_dialogs_slice 0x71e094f3
|
||||
#define CODE_messages_messages 0x8c718e87
|
||||
#define CODE_messages_messages_slice 0xb446ae3
|
||||
#define CODE_messages_message_empty 0x3f4e0648
|
||||
#define CODE_messages_message 0xff90c417
|
||||
#define CODE_messages_stated_messages 0x969478bb
|
||||
#define CODE_messages_stated_message 0xd07ae726
|
||||
#define CODE_messages_sent_message 0xd1f4d35c
|
||||
#define CODE_messages_chat 0x40e9002a
|
||||
#define CODE_messages_chats 0x8150cbd8
|
||||
#define CODE_messages_chat_full 0xe5d7d19c
|
||||
#define CODE_messages_affected_history 0xb7de36f2
|
||||
#define CODE_input_messages_filter_empty 0x57e2f66c
|
||||
#define CODE_input_messages_filter_photos 0x9609a51c
|
||||
#define CODE_input_messages_filter_video 0x9fc00e65
|
||||
#define CODE_input_messages_filter_photo_video 0x56e9f0e4
|
||||
#define CODE_update_new_message 0x13abdb3
|
||||
#define CODE_update_message_i_d 0x4e90bfd6
|
||||
#define CODE_update_read_messages 0xc6649e31
|
||||
#define CODE_update_delete_messages 0xa92bfe26
|
||||
#define CODE_update_restore_messages 0xd15de04d
|
||||
#define CODE_update_user_typing 0x6baa8508
|
||||
#define CODE_update_chat_user_typing 0x3c46cfe6
|
||||
#define CODE_update_chat_participants 0x7761198
|
||||
#define CODE_update_user_status 0x1bfbd823
|
||||
#define CODE_update_user_name 0xda22d9ad
|
||||
#define CODE_update_user_photo 0x95313b0c
|
||||
#define CODE_update_contact_registered 0x2575bbb9
|
||||
#define CODE_update_contact_link 0x51a48a9a
|
||||
#define CODE_update_activation 0x6f690963
|
||||
#define CODE_update_new_authorization 0x8f06529a
|
||||
#define CODE_updates_state 0xa56c2a3e
|
||||
#define CODE_updates_difference_empty 0x5d75a138
|
||||
#define CODE_updates_difference 0xf49ca0
|
||||
#define CODE_updates_difference_slice 0xa8fb1981
|
||||
#define CODE_updates_too_long 0xe317af7e
|
||||
#define CODE_update_short_message 0xd3f45784
|
||||
#define CODE_update_short_chat_message 0x2b2fbd4e
|
||||
#define CODE_update_short 0x78d4dec1
|
||||
#define CODE_updates_combined 0x725b04c3
|
||||
#define CODE_updates 0x74ae4240
|
||||
#define CODE_photos_photos 0x8dca6aa5
|
||||
#define CODE_photos_photos_slice 0x15051f54
|
||||
#define CODE_photos_photo 0x20212ca8
|
||||
#define CODE_upload_file 0x96a18d5
|
||||
#define CODE_dc_option 0x2ec2a43c
|
||||
#define CODE_config 0x2e54dd74
|
||||
#define CODE_nearest_dc 0x8e1a1775
|
||||
#define CODE_help_app_update 0x8987f311
|
||||
#define CODE_help_no_app_update 0xc45a6536
|
||||
#define CODE_help_invite_text 0x18cb9f78
|
||||
#define CODE_messages_stated_messages_links 0x3e74f5c6
|
||||
#define CODE_messages_stated_message_link 0xa9af2881
|
||||
#define CODE_messages_sent_message_link 0xe9db4a3f
|
||||
#define CODE_input_geo_chat 0x74d456fa
|
||||
#define CODE_input_notify_geo_chat_peer 0x4d8ddec8
|
||||
#define CODE_geo_chat 0x75eaea5a
|
||||
#define CODE_geo_chat_message_empty 0x60311a9b
|
||||
#define CODE_geo_chat_message 0x4505f8e1
|
||||
#define CODE_geo_chat_message_service 0xd34fa24e
|
||||
#define CODE_geochats_stated_message 0x17b1578b
|
||||
#define CODE_geochats_located 0x48feb267
|
||||
#define CODE_geochats_messages 0xd1526db1
|
||||
#define CODE_geochats_messages_slice 0xbc5863e8
|
||||
#define CODE_message_action_geo_chat_create 0x6f038ebc
|
||||
#define CODE_message_action_geo_chat_checkin 0xc7d53de
|
||||
#define CODE_update_new_geo_chat_message 0x5a68e3f7
|
||||
#define CODE_wall_paper_solid 0x63117f24
|
||||
#define CODE_update_new_encrypted_message 0x12bcbd9a
|
||||
#define CODE_update_encrypted_chat_typing 0x1710f156
|
||||
#define CODE_update_encryption 0xb4a2e88d
|
||||
#define CODE_update_encrypted_messages_read 0x38fe25b7
|
||||
#define CODE_encrypted_chat_empty 0xab7ec0a0
|
||||
#define CODE_encrypted_chat_waiting 0x3bf703dc
|
||||
#define CODE_encrypted_chat_requested 0xc878527e
|
||||
#define CODE_encrypted_chat 0xfa56ce36
|
||||
#define CODE_encrypted_chat_discarded 0x13d6dd27
|
||||
#define CODE_input_encrypted_chat 0xf141b5e1
|
||||
#define CODE_encrypted_file_empty 0xc21f497e
|
||||
#define CODE_encrypted_file 0x4a70994c
|
||||
#define CODE_input_encrypted_file_empty 0x1837c364
|
||||
#define CODE_input_encrypted_file_uploaded 0x64bd0306
|
||||
#define CODE_input_encrypted_file 0x5a17b5e5
|
||||
#define CODE_input_encrypted_file_location 0xf5235d55
|
||||
#define CODE_encrypted_message 0xed18c118
|
||||
#define CODE_encrypted_message_service 0x23734b06
|
||||
#define CODE_decrypted_message_layer 0x99a438cf
|
||||
#define CODE_decrypted_message 0x1f814f1f
|
||||
#define CODE_decrypted_message_service 0xaa48327d
|
||||
#define CODE_decrypted_message_media_empty 0x89f5c4a
|
||||
#define CODE_decrypted_message_media_photo 0x32798a8c
|
||||
#define CODE_decrypted_message_media_video 0x4cee6ef3
|
||||
#define CODE_decrypted_message_media_geo_point 0x35480a59
|
||||
#define CODE_decrypted_message_media_contact 0x588a0a97
|
||||
#define CODE_decrypted_message_action_set_message_t_t_l 0xa1733aec
|
||||
#define CODE_messages_dh_config_not_modified 0xc0e24635
|
||||
#define CODE_messages_dh_config 0x2c221edd
|
||||
#define CODE_messages_sent_encrypted_message 0x560f8935
|
||||
#define CODE_messages_sent_encrypted_file 0x9493ff32
|
||||
#define CODE_input_file_big 0xfa4f0bb5
|
||||
#define CODE_input_encrypted_file_big_uploaded 0x2dc173c8
|
||||
#define CODE_update_chat_participant_add 0x3a0eeb22
|
||||
#define CODE_update_chat_participant_delete 0x6e5f8c22
|
||||
#define CODE_update_dc_options 0x8e5e9873
|
||||
#define CODE_input_media_uploaded_audio 0x61a6d436
|
||||
#define CODE_input_media_audio 0x89938781
|
||||
#define CODE_input_media_uploaded_document 0x34e794bd
|
||||
#define CODE_input_media_uploaded_thumb_document 0x3e46de5d
|
||||
#define CODE_input_media_document 0xd184e841
|
||||
#define CODE_message_media_document 0x2fda2204
|
||||
#define CODE_message_media_audio 0xc6b68300
|
||||
#define CODE_input_audio_empty 0xd95adc84
|
||||
#define CODE_input_audio 0x77d440ff
|
||||
#define CODE_input_document_empty 0x72f0eaae
|
||||
#define CODE_input_document 0x18798952
|
||||
#define CODE_input_audio_file_location 0x74dc404d
|
||||
#define CODE_input_document_file_location 0x4e45abe9
|
||||
#define CODE_decrypted_message_media_document 0xb095434b
|
||||
#define CODE_decrypted_message_media_audio 0x6080758f
|
||||
#define CODE_audio_empty 0x586988d8
|
||||
#define CODE_audio 0x427425e7
|
||||
#define CODE_document_empty 0x36f8c871
|
||||
#define CODE_document 0x9efc6326
|
||||
#define CODE_invoke_after_msg 0xcb9f372d
|
||||
#define CODE_invoke_after_msgs 0x3dc4b4f0
|
||||
#define CODE_invoke_with_layer1 0x53835315
|
||||
#define CODE_auth_check_phone 0x6fe51dfb
|
||||
#define CODE_auth_send_code 0x768d5f4d
|
||||
#define CODE_auth_send_call 0x3c51564
|
||||
#define CODE_auth_sign_up 0x1b067634
|
||||
#define CODE_auth_sign_in 0xbcd51581
|
||||
#define CODE_auth_log_out 0x5717da40
|
||||
#define CODE_auth_reset_authorizations 0x9fab0d1a
|
||||
#define CODE_auth_send_invites 0x771c1d97
|
||||
#define CODE_auth_export_authorization 0xe5bfffcd
|
||||
#define CODE_auth_import_authorization 0xe3ef9613
|
||||
#define CODE_account_register_device 0x446c712c
|
||||
#define CODE_account_unregister_device 0x65c55b40
|
||||
#define CODE_account_update_notify_settings 0x84be5b93
|
||||
#define CODE_account_get_notify_settings 0x12b3ad31
|
||||
#define CODE_account_reset_notify_settings 0xdb7e1747
|
||||
#define CODE_account_update_profile 0xf0888d68
|
||||
#define CODE_account_update_status 0x6628562c
|
||||
#define CODE_account_get_wall_papers 0xc04cfac2
|
||||
#define CODE_users_get_users 0xd91a548
|
||||
#define CODE_users_get_full_user 0xca30a5b1
|
||||
#define CODE_contacts_get_statuses 0xc4a353ee
|
||||
#define CODE_contacts_get_contacts 0x22c6aa08
|
||||
#define CODE_contacts_import_contacts 0xda30b32d
|
||||
#define CODE_contacts_search 0x11f812d8
|
||||
#define CODE_contacts_get_suggested 0xcd773428
|
||||
#define CODE_contacts_delete_contact 0x8e953744
|
||||
#define CODE_contacts_delete_contacts 0x59ab389e
|
||||
#define CODE_contacts_block 0x332b49fc
|
||||
#define CODE_contacts_unblock 0xe54100bd
|
||||
#define CODE_contacts_get_blocked 0xf57c350f
|
||||
#define CODE_messages_get_messages 0x4222fa74
|
||||
#define CODE_messages_get_dialogs 0xeccf1df6
|
||||
#define CODE_messages_get_history 0x92a1df2f
|
||||
#define CODE_messages_search 0x7e9f2ab
|
||||
#define CODE_messages_read_history 0xb04f2510
|
||||
#define CODE_messages_delete_history 0xf4f8fb61
|
||||
#define CODE_messages_delete_messages 0x14f2dd0a
|
||||
#define CODE_messages_restore_messages 0x395f9d7e
|
||||
#define CODE_messages_received_messages 0x28abcb68
|
||||
#define CODE_messages_set_typing 0x719839e9
|
||||
#define CODE_messages_send_message 0x4cde0aab
|
||||
#define CODE_messages_send_media 0xa3c85d76
|
||||
#define CODE_messages_forward_messages 0x514cd10f
|
||||
#define CODE_messages_get_chats 0x3c6aa187
|
||||
#define CODE_messages_get_full_chat 0x3b831c66
|
||||
#define CODE_messages_edit_chat_title 0xb4bc68b5
|
||||
#define CODE_messages_edit_chat_photo 0xd881821d
|
||||
#define CODE_messages_add_chat_user 0x2ee9ee9e
|
||||
#define CODE_messages_delete_chat_user 0xc3c5cd23
|
||||
#define CODE_messages_create_chat 0x419d9aee
|
||||
#define CODE_updates_get_state 0xedd4882a
|
||||
#define CODE_updates_get_difference 0xa041495
|
||||
#define CODE_photos_update_profile_photo 0xeef579a0
|
||||
#define CODE_photos_upload_profile_photo 0xd50f9c88
|
||||
#define CODE_upload_save_file_part 0xb304a621
|
||||
#define CODE_upload_get_file 0xe3a6cfb5
|
||||
#define CODE_help_get_config 0xc4f9186b
|
||||
#define CODE_help_get_nearest_dc 0x1fb33026
|
||||
#define CODE_help_get_app_update 0xc812ac7e
|
||||
#define CODE_help_save_app_log 0x6f02f748
|
||||
#define CODE_help_get_invite_text 0xa4a95186
|
||||
#define CODE_photos_get_user_photos 0xb7ee553c
|
||||
#define CODE_invoke_with_layer2 0x289dd1f6
|
||||
#define CODE_messages_forward_message 0x3f3f4f2
|
||||
#define CODE_messages_send_broadcast 0x41bb0972
|
||||
#define CODE_invoke_with_layer3 0xb7475268
|
||||
#define CODE_geochats_get_located 0x7f192d8f
|
||||
#define CODE_geochats_get_recents 0xe1427e6f
|
||||
#define CODE_geochats_checkin 0x55b3e8fb
|
||||
#define CODE_geochats_get_full_chat 0x6722dd6f
|
||||
#define CODE_geochats_edit_chat_title 0x4c8e2273
|
||||
#define CODE_geochats_edit_chat_photo 0x35d81a95
|
||||
#define CODE_geochats_search 0xcfcdc44d
|
||||
#define CODE_geochats_get_history 0xb53f7a68
|
||||
#define CODE_geochats_set_typing 0x8b8a729
|
||||
#define CODE_geochats_send_message 0x61b0044
|
||||
#define CODE_geochats_send_media 0xb8f0deff
|
||||
#define CODE_geochats_create_geo_chat 0xe092e16
|
||||
#define CODE_invoke_with_layer4 0xdea0d430
|
||||
#define CODE_invoke_with_layer5 0x417a57ae
|
||||
#define CODE_invoke_with_layer6 0x3a64d54d
|
||||
#define CODE_invoke_with_layer7 0xa5be56d3
|
||||
#define CODE_messages_get_dh_config 0x26cf8950
|
||||
#define CODE_messages_request_encryption 0xf64daf43
|
||||
#define CODE_messages_accept_encryption 0x3dbc0415
|
||||
#define CODE_messages_discard_encryption 0xedd923c5
|
||||
#define CODE_messages_set_encrypted_typing 0x791451ed
|
||||
#define CODE_messages_read_encrypted_history 0x7f4b690a
|
||||
#define CODE_messages_send_encrypted 0xa9776773
|
||||
#define CODE_messages_send_encrypted_file 0x9a901b66
|
||||
#define CODE_messages_send_encrypted_service 0x32d439a4
|
||||
#define CODE_messages_received_queue 0x55a5bb66
|
||||
#define CODE_invoke_with_layer8 0xe9abd9fd
|
||||
#define CODE_upload_save_big_file_part 0xde7b673d
|
||||
#define CODE_init_connection 0x69796de9
|
||||
#define CODE_invoke_with_layer9 0x76715a63
|
||||
#define CODE_invoke_with_layer10 0x39620c41
|
||||
#define CODE_invoke_with_layer11 0xa6b88fdf
|
||||
#define CODE_invoke_with_layer12 0xdda60d3c
|
||||
#endif
|
668
crc32.c
Normal file
668
crc32.c
Normal file
|
@ -0,0 +1,668 @@
|
|||
/*
|
||||
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 <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright 2009-2012 Vkontakte Ltd
|
||||
2009-2012 Nikolai Durov
|
||||
2009-2012 Andrei Lopatin
|
||||
2012 Anton Maydell
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <math.h>
|
||||
#include <assert.h>
|
||||
#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;
|
||||
}
|
59
crc32.h
Normal file
59
crc32.h
Normal file
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
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 <http://www.gnu.org/licenses/>.
|
||||
|
||||
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
|
1
encrypted_scheme.tl
Symbolic link
1
encrypted_scheme.tl
Symbolic link
|
@ -0,0 +1 @@
|
|||
encrypted_scheme16.tl
|
22
encrypted_scheme16.tl
Normal file
22
encrypted_scheme16.tl
Normal file
|
@ -0,0 +1,22 @@
|
|||
---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<long> = DecryptedMessageAction;
|
||||
decryptedMessageActionDeleteMessages#65614304 random_ids:Vector<long> = DecryptedMessageAction;
|
||||
decryptedMessageActionScreenshotMessages#8ac1f475 random_ids:Vector<long> = DecryptedMessageAction;
|
||||
decryptedMessageActionFlushHistory#6719e45c = DecryptedMessageAction;
|
||||
decryptedMessageActionNotifyLayer#f3048883 layer:int = DecryptedMessageAction;
|
||||
---functions---
|
43
event-old.h
Normal file
43
event-old.h
Normal file
|
@ -0,0 +1,43 @@
|
|||
#ifndef __EVENT_OLD_H__
|
||||
#define __EVENT_OLD_H__
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
#define BEV_EVENT_READ EVBUFFER_READ
|
||||
#define BEV_EVENT_WRITE EVBUFFER_WRITE
|
||||
#define BEV_EVENT_EOF EVBUFFER_EOF
|
||||
#define BEV_EVENT_ERROR EVBUFFER_ERROR
|
||||
#define BEV_EVENT_TIMEOUT EVBUFFER_TIMEOUT
|
||||
|
||||
typedef int evutil_socket_t;
|
||||
|
||||
static inline struct event *event_new (struct event_base *base, int fd, int what, void(*callback)(int, short, void *), void *arg) __attribute__ ((unused));
|
||||
static inline struct event *event_new (struct event_base *base, int fd, int what, void(*callback)(int, short, void *), void *arg) {
|
||||
struct event *ev = malloc (sizeof (*ev));
|
||||
event_set (ev, fd, what, callback, arg);
|
||||
event_base_set (base, ev);
|
||||
return ev;
|
||||
}
|
||||
|
||||
static inline struct event *evtimer_new (struct event_base *base, void(*callback)(int, short, void *), void *arg) __attribute__ ((unused));
|
||||
static inline struct event *evtimer_new (struct event_base *base, void(*callback)(int, short, void *), void *arg) {
|
||||
struct event *ev = malloc (sizeof (*ev));
|
||||
event_set (ev, -1, 0, callback, arg);
|
||||
event_base_set (base, ev);
|
||||
return ev;
|
||||
}
|
||||
|
||||
static void event_free (struct event *ev) __attribute__ ((unused));
|
||||
static void event_free (struct event *ev) {
|
||||
event_del (ev);
|
||||
free (ev);
|
||||
}
|
||||
|
||||
static struct bufferevent *bufferevent_socket_new (struct event_base *base, int fd, int flags) __attribute__ ((unused));
|
||||
static struct bufferevent *bufferevent_socket_new (struct event_base *base, int fd, int flags) {
|
||||
assert (!flags);
|
||||
struct bufferevent *bev = bufferevent_new(fd, 0, 0, 0, 0);
|
||||
bufferevent_base_set (base, bev);
|
||||
return bev;
|
||||
}
|
||||
#endif
|
|
@ -22,7 +22,7 @@ BEGIN {
|
|||
}
|
||||
// {
|
||||
if (split ($1, a, "#") == 2) {
|
||||
gsub (/[A-Z]/, "_&", a[1]);
|
||||
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/"
|
||||
|
|
1812
generate.c
Normal file
1812
generate.c
Normal file
File diff suppressed because it is too large
Load diff
171
generate.h
Normal file
171
generate.h
Normal file
|
@ -0,0 +1,171 @@
|
|||
/*
|
||||
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 <http://www.gnu.org/licenses/>.
|
||||
|
||||
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
|
1
gentoo/net-im/telegram-cli/Manifest
Normal file
1
gentoo/net-im/telegram-cli/Manifest
Normal file
|
@ -0,0 +1 @@
|
|||
EBUILD telegram-cli-9999.ebuild 665 SHA256 446cf5cd54f60485dda2f47e5c027b78f182053ef88cd09d7327603e2d5f3d86 SHA512 8a3673de91ec60e89391956523a4b61872161a23a7e0babdbd90cbdd8602104ba1855d09bd0af1d2092890eb202f498750610bf71e3bd0562e37ec984deb333e WHIRLPOOL e943b8870f461c62e3dc7f061dcad264c25758d1d50a0c34f5232d3be6ae26e9dd2ca1289e65b6153ff5b8800194969f1c53e3adc81aa4e47bf25c2f7e6aab7c
|
|
@ -5,6 +5,7 @@
|
|||
EAPI=5
|
||||
|
||||
EGIT_REPO_URI="https://github.com/vysheng/tg.git"
|
||||
EGIT_BRANCH="test"
|
||||
inherit git-2
|
||||
IUSE="lua"
|
||||
DESCRIPTION="Command line interface client for Telegram"
|
||||
|
@ -17,14 +18,15 @@ DEPEND="sys-libs/zlib
|
|||
sys-libs/readline
|
||||
dev-libs/libconfig
|
||||
dev-libs/openssl
|
||||
dev-libs/libevent
|
||||
lua? ( dev-lang/lua )"
|
||||
|
||||
src_configure() {
|
||||
econf $(use_enable lua liblua ) --with-progname=telegram-cli
|
||||
econf $(use_enable lua liblua )
|
||||
}
|
||||
|
||||
src_install() {
|
||||
newbin telegram telegram-cli
|
||||
newbin bin/telegram-cli telegram-cli
|
||||
|
||||
insinto /etc/telegram-cli/
|
||||
newins tg-server.pub server.pub
|
|
@ -1 +0,0 @@
|
|||
EBUILD telegram-cli-9999.ebuild 641 SHA256 4597e2f84c36b1ee02ecc415c399408bb8536b456e94370e996d57477db621be SHA512 287da263c9a4ba2058bf2f5844599432619053abc9249fd5725ed7b5e920c5c02e2493ad7b07f89177933b2c15394d939e7dc7dbf05d5873c32e55c9ec614d4c WHIRLPOOL 73dee37f91f1d4b747afc35c0a0cb2efb141d37702c71a7a9d188d2e1d727375c0ee3e7a1192e6c4c34f17ba1303f3a0be47b24272b5378ff255bce1a4a281be
|
2975
interface.c
2975
interface.c
File diff suppressed because it is too large
Load diff
55
interface.h
55
interface.h
|
@ -1,24 +1,25 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
This file is part of telegram-cli.
|
||||
|
||||
Telegram-client is free software: you can redistribute it and/or modify
|
||||
Telegram-cli 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,
|
||||
Telegram-cli 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 <http://www.gnu.org/licenses/>.
|
||||
along with this telegram-cli. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __INTERFACE_H__
|
||||
#define __INTERFACE_H__
|
||||
#include "structures.h"
|
||||
#include "tgl-layout.h"
|
||||
|
||||
#define COLOR_RED "\033[0;31m"
|
||||
#define COLOR_REDB "\033[1;31m"
|
||||
|
@ -37,25 +38,47 @@ char *get_default_prompt (void);
|
|||
char *complete_none (const char *text, int state);
|
||||
char **complete_text (char *text, int start, int end);
|
||||
void interpreter (char *line);
|
||||
void interpreter_ex (char *line, void *ex);
|
||||
|
||||
void rprintf (const char *format, ...) __attribute__ ((format (printf, 1, 2)));
|
||||
void logprintf (const char *format, ...) __attribute__ ((format (printf, 1, 2)));
|
||||
void hexdump (int *in_ptr, int *in_end);
|
||||
|
||||
struct message;
|
||||
union peer;
|
||||
void print_message (struct message *M);
|
||||
void print_chat_name (peer_id_t id, union peer *C);
|
||||
void print_user_name (peer_id_t id, union peer *U);
|
||||
void print_encr_chat_name_full (peer_id_t id, peer_t *C);
|
||||
void print_encr_chat_name (peer_id_t id, peer_t *C);
|
||||
//void print_media (struct message_media *M);
|
||||
#define vlogprintf(v,...) \
|
||||
do { \
|
||||
if (tgl_state.verbosity >= (v)) {\
|
||||
logprintf (__VA_ARGS__);\
|
||||
}\
|
||||
} while (0);\
|
||||
|
||||
|
||||
//void hexdump (int *in_ptr, int *in_end);
|
||||
|
||||
struct bufferevent;
|
||||
struct in_ev {
|
||||
struct bufferevent *bev;
|
||||
char in_buf[4096];
|
||||
int in_buf_pos;
|
||||
int refcnt;
|
||||
int error;
|
||||
int fd;
|
||||
};
|
||||
|
||||
|
||||
struct tgl_message;
|
||||
struct in_ev;
|
||||
void print_message (struct in_ev *ev, struct tgl_message *M);
|
||||
void print_chat_name (struct in_ev *ev, tgl_peer_id_t id, tgl_peer_t *C);
|
||||
void print_user_name (struct in_ev *ev, tgl_peer_id_t id, tgl_peer_t *U);
|
||||
void print_encr_chat_name_full (struct in_ev *ev, tgl_peer_id_t id, tgl_peer_t *C);
|
||||
void print_encr_chat_name (struct in_ev *ev, tgl_peer_id_t id, tgl_peer_t *C);
|
||||
//void print_media (struct tgl_message_media *M);
|
||||
//
|
||||
void pop_color (void);
|
||||
void push_color (const char *color);
|
||||
void print_start (void);
|
||||
void print_end (void);
|
||||
void print_date_full (long t);
|
||||
void print_date (long t);
|
||||
void print_date_full (struct in_ev *ev, long t);
|
||||
void print_date (struct in_ev *ev, long t);
|
||||
|
||||
void play_sound (void);
|
||||
void update_prompt (void);
|
||||
|
|
11
loop.h
11
loop.h
|
@ -1,24 +1,25 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
This file is part of telegram-cli.
|
||||
|
||||
Telegram-client is free software: you can redistribute it and/or modify
|
||||
Telegram-cli 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,
|
||||
Telegram-cli 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 <http://www.gnu.org/licenses/>.
|
||||
along with this telegram-cli. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __LOOP_H__
|
||||
#define __LOOP_H__
|
||||
int loop (void);
|
||||
void do_halt (int error);
|
||||
void net_loop (int flags, int (*end)(void));
|
||||
void write_auth_file (void);
|
||||
void write_state_file (void);
|
||||
|
|
29
lua-tg.h
29
lua-tg.h
|
@ -1,15 +1,34 @@
|
|||
/*
|
||||
This file is part of telegram-cli.
|
||||
|
||||
Telegram-cli 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-cli 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-cli. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __LUA_TG_H__
|
||||
#define __LUA_TG_H__
|
||||
|
||||
#include <string.h>
|
||||
#include "structures.h"
|
||||
#include "lua-tg.h"
|
||||
#include "tgl.h"
|
||||
|
||||
void lua_init (const char *file);
|
||||
void lua_new_msg (struct message *M);
|
||||
void lua_new_msg (struct tgl_message *M);
|
||||
void lua_our_id (int id);
|
||||
void lua_secret_chat_created (struct secret_chat *U);
|
||||
void lua_user_update (struct user *U);
|
||||
void lua_chat_update (struct chat *C);
|
||||
void lua_secret_chat_update (struct tgl_secret_chat *U, unsigned flags);
|
||||
void lua_user_update (struct tgl_user *U, unsigned flags);
|
||||
void lua_chat_update (struct tgl_chat *C, unsigned flags);
|
||||
void lua_binlog_end (void);
|
||||
void lua_diff_end (void);
|
||||
void lua_do_all (void);
|
||||
|
|
168
m4-ax_gcc_builtin.m4
Normal file
168
m4-ax_gcc_builtin.m4
Normal file
|
@ -0,0 +1,168 @@
|
|||
# ===========================================================================
|
||||
# http://www.gnu.org/software/autoconf-archive/ax_gcc_builtin.html
|
||||
# ===========================================================================
|
||||
#
|
||||
# SYNOPSIS
|
||||
#
|
||||
# AX_GCC_BUILTIN(BUILTIN)
|
||||
#
|
||||
# DESCRIPTION
|
||||
#
|
||||
# This macro checks if the compiler supports one of GCC's built-in
|
||||
# functions; many other compilers also provide those same built-ins.
|
||||
#
|
||||
# The BUILTIN parameter is the name of the built-in function.
|
||||
#
|
||||
# If BUILTIN is supported define HAVE_<BUILTIN>. Keep in mind that since
|
||||
# builtins usually start with two underscores they will be copied over
|
||||
# into the HAVE_<BUILTIN> definition (e.g. HAVE___BUILTIN_EXPECT for
|
||||
# __builtin_expect()).
|
||||
#
|
||||
# The macro caches its result in the ax_cv_have_<BUILTIN> variable (e.g.
|
||||
# ax_cv_have___builtin_expect).
|
||||
#
|
||||
# The macro currently supports the following built-in functions:
|
||||
#
|
||||
# __builtin_assume_aligned
|
||||
# __builtin_bswap32
|
||||
# __builtin_bswap64
|
||||
# __builtin_choose_expr
|
||||
# __builtin___clear_cache
|
||||
# __builtin_clrsb
|
||||
# __builtin_clrsbl
|
||||
# __builtin_clrsbll
|
||||
# __builtin_clz
|
||||
# __builtin_clzl
|
||||
# __builtin_clzll
|
||||
# __builtin_complex
|
||||
# __builtin_constant_p
|
||||
# __builtin_ctz
|
||||
# __builtin_ctzl
|
||||
# __builtin_ctzll
|
||||
# __builtin_expect
|
||||
# __builtin_ffs
|
||||
# __builtin_ffsl
|
||||
# __builtin_ffsll
|
||||
# __builtin_fpclassify
|
||||
# __builtin_huge_val
|
||||
# __builtin_huge_valf
|
||||
# __builtin_huge_vall
|
||||
# __builtin_inf
|
||||
# __builtin_infd128
|
||||
# __builtin_infd32
|
||||
# __builtin_infd64
|
||||
# __builtin_inff
|
||||
# __builtin_infl
|
||||
# __builtin_isinf_sign
|
||||
# __builtin_nan
|
||||
# __builtin_nand128
|
||||
# __builtin_nand32
|
||||
# __builtin_nand64
|
||||
# __builtin_nanf
|
||||
# __builtin_nanl
|
||||
# __builtin_nans
|
||||
# __builtin_nansf
|
||||
# __builtin_nansl
|
||||
# __builtin_object_size
|
||||
# __builtin_parity
|
||||
# __builtin_parityl
|
||||
# __builtin_parityll
|
||||
# __builtin_popcount
|
||||
# __builtin_popcountl
|
||||
# __builtin_popcountll
|
||||
# __builtin_powi
|
||||
# __builtin_powif
|
||||
# __builtin_powil
|
||||
# __builtin_prefetch
|
||||
# __builtin_trap
|
||||
# __builtin_types_compatible_p
|
||||
# __builtin_unreachable
|
||||
#
|
||||
# Unsuppored built-ins will be tested with an empty parameter set and the
|
||||
# result of the check might be wrong or meaningless so use with care.
|
||||
#
|
||||
# LICENSE
|
||||
#
|
||||
# Copyright (c) 2013 Gabriele Svelto <gabriele.svelto@gmail.com>
|
||||
#
|
||||
# Copying and distribution of this file, with or without modification, are
|
||||
# permitted in any medium without royalty provided the copyright notice
|
||||
# and this notice are preserved. This file is offered as-is, without any
|
||||
# warranty.
|
||||
|
||||
#serial 2
|
||||
|
||||
AC_DEFUN([AX_GCC_BUILTIN], [
|
||||
AS_VAR_PUSHDEF([ac_var], [ax_cv_have_$1])
|
||||
|
||||
AC_CACHE_CHECK([for $1], [ac_var], [
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM([], [
|
||||
m4_case([$1],
|
||||
[__builtin_assume_aligned], [$1("", 0)],
|
||||
[__builtin_bswap32], [$1(0)],
|
||||
[__builtin_bswap64], [$1(0)],
|
||||
[__builtin_choose_expr], [$1(0, 0, 0)],
|
||||
[__builtin___clear_cache], [$1("", "")],
|
||||
[__builtin_clrsb], [$1(0)],
|
||||
[__builtin_clrsbl], [$1(0)],
|
||||
[__builtin_clrsbll], [$1(0)],
|
||||
[__builtin_clz], [$1(0)],
|
||||
[__builtin_clzl], [$1(0)],
|
||||
[__builtin_clzll], [$1(0)],
|
||||
[__builtin_complex], [$1(0.0, 0.0)],
|
||||
[__builtin_constant_p], [$1(0)],
|
||||
[__builtin_ctz], [$1(0)],
|
||||
[__builtin_ctzl], [$1(0)],
|
||||
[__builtin_ctzll], [$1(0)],
|
||||
[__builtin_expect], [$1(0, 0)],
|
||||
[__builtin_ffs], [$1(0)],
|
||||
[__builtin_ffsl], [$1(0)],
|
||||
[__builtin_ffsll], [$1(0)],
|
||||
[__builtin_fpclassify], [$1(0, 1, 2, 3, 4, 0.0)],
|
||||
[__builtin_huge_val], [$1()],
|
||||
[__builtin_huge_valf], [$1()],
|
||||
[__builtin_huge_vall], [$1()],
|
||||
[__builtin_inf], [$1()],
|
||||
[__builtin_infd128], [$1()],
|
||||
[__builtin_infd32], [$1()],
|
||||
[__builtin_infd64], [$1()],
|
||||
[__builtin_inff], [$1()],
|
||||
[__builtin_infl], [$1()],
|
||||
[__builtin_isinf_sign], [$1(0.0)],
|
||||
[__builtin_nan], [$1("")],
|
||||
[__builtin_nand128], [$1("")],
|
||||
[__builtin_nand32], [$1("")],
|
||||
[__builtin_nand64], [$1("")],
|
||||
[__builtin_nanf], [$1("")],
|
||||
[__builtin_nanl], [$1("")],
|
||||
[__builtin_nans], [$1("")],
|
||||
[__builtin_nansf], [$1("")],
|
||||
[__builtin_nansl], [$1("")],
|
||||
[__builtin_object_size], [$1("", 0)],
|
||||
[__builtin_parity], [$1(0)],
|
||||
[__builtin_parityl], [$1(0)],
|
||||
[__builtin_parityll], [$1(0)],
|
||||
[__builtin_popcount], [$1(0)],
|
||||
[__builtin_popcountl], [$1(0)],
|
||||
[__builtin_popcountll], [$1(0)],
|
||||
[__builtin_powi], [$1(0, 0)],
|
||||
[__builtin_powif], [$1(0, 0)],
|
||||
[__builtin_powil], [$1(0, 0)],
|
||||
[__builtin_prefetch], [$1("")],
|
||||
[__builtin_trap], [$1()],
|
||||
[__builtin_types_compatible_p], [$1(int, int)],
|
||||
[__builtin_unreachable], [$1()],
|
||||
[m4_warn([syntax], [Unsupported built-in $1, the test may fail])
|
||||
$1()]
|
||||
)
|
||||
])],
|
||||
[AS_VAR_SET([ac_var], [yes])],
|
||||
[AS_VAR_SET([ac_var], [no])])
|
||||
])
|
||||
|
||||
AS_IF([test yes = AS_VAR_GET([ac_var])],
|
||||
[AC_DEFINE_UNQUOTED(AS_TR_CPP(HAVE_$1), 1,
|
||||
[Define to 1 if the system has the `$1' built-in function])], [])
|
||||
|
||||
AS_VAR_POPDEF([ac_var])
|
||||
])
|
124
m4_ax_check_openssl.m4
Normal file
124
m4_ax_check_openssl.m4
Normal file
|
@ -0,0 +1,124 @@
|
|||
# ===========================================================================
|
||||
# http://www.gnu.org/software/autoconf-archive/ax_check_openssl.html
|
||||
# ===========================================================================
|
||||
#
|
||||
# SYNOPSIS
|
||||
#
|
||||
# AX_CHECK_OPENSSL([action-if-found[, action-if-not-found]])
|
||||
#
|
||||
# DESCRIPTION
|
||||
#
|
||||
# Look for OpenSSL in a number of default spots, or in a user-selected
|
||||
# spot (via --with-openssl). Sets
|
||||
#
|
||||
# OPENSSL_INCLUDES to the include directives required
|
||||
# OPENSSL_LIBS to the -l directives required
|
||||
# OPENSSL_LDFLAGS to the -L or -R flags required
|
||||
#
|
||||
# and calls ACTION-IF-FOUND or ACTION-IF-NOT-FOUND appropriately
|
||||
#
|
||||
# This macro sets OPENSSL_INCLUDES such that source files should use the
|
||||
# openssl/ directory in include directives:
|
||||
#
|
||||
# #include <openssl/hmac.h>
|
||||
#
|
||||
# LICENSE
|
||||
#
|
||||
# Copyright (c) 2009,2010 Zmanda Inc. <http://www.zmanda.com/>
|
||||
# Copyright (c) 2009,2010 Dustin J. Mitchell <dustin@zmanda.com>
|
||||
#
|
||||
# Copying and distribution of this file, with or without modification, are
|
||||
# permitted in any medium without royalty provided the copyright notice
|
||||
# and this notice are preserved. This file is offered as-is, without any
|
||||
# warranty.
|
||||
|
||||
#serial 8
|
||||
|
||||
AU_ALIAS([CHECK_SSL], [AX_CHECK_OPENSSL])
|
||||
AC_DEFUN([AX_CHECK_OPENSSL], [
|
||||
found=false
|
||||
AC_ARG_WITH([openssl],
|
||||
[AS_HELP_STRING([--with-openssl=DIR],
|
||||
[root of the OpenSSL directory])],
|
||||
[
|
||||
case "$withval" in
|
||||
"" | y | ye | yes | n | no)
|
||||
AC_MSG_ERROR([Invalid --with-openssl value])
|
||||
;;
|
||||
*) ssldirs="$withval"
|
||||
;;
|
||||
esac
|
||||
], [
|
||||
# if pkg-config is installed and openssl has installed a .pc file,
|
||||
# then use that information and don't search ssldirs
|
||||
AC_PATH_PROG([PKG_CONFIG], [pkg-config])
|
||||
if test x"$PKG_CONFIG" != x""; then
|
||||
OPENSSL_LDFLAGS=`$PKG_CONFIG openssl --libs-only-L 2>/dev/null`
|
||||
if test $? = 0; then
|
||||
OPENSSL_LIBS=`$PKG_CONFIG openssl --libs-only-l 2>/dev/null`
|
||||
OPENSSL_INCLUDES=`$PKG_CONFIG openssl --cflags-only-I 2>/dev/null`
|
||||
found=true
|
||||
fi
|
||||
fi
|
||||
|
||||
# no such luck; use some default ssldirs
|
||||
if ! $found; then
|
||||
ssldirs="/usr/local/ssl /usr/lib/ssl /usr/ssl /usr/pkg /usr/local /usr"
|
||||
fi
|
||||
]
|
||||
)
|
||||
|
||||
|
||||
# note that we #include <openssl/foo.h>, so the OpenSSL headers have to be in
|
||||
# an 'openssl' subdirectory
|
||||
|
||||
if ! $found; then
|
||||
OPENSSL_INCLUDES=
|
||||
for ssldir in $ssldirs; do
|
||||
AC_MSG_CHECKING([for openssl/ssl.h in $ssldir])
|
||||
if test -f "$ssldir/include/openssl/ssl.h"; then
|
||||
OPENSSL_INCLUDES="-I$ssldir/include"
|
||||
OPENSSL_LDFLAGS="-L$ssldir/lib"
|
||||
OPENSSL_LIBS="-lssl -lcrypto"
|
||||
found=true
|
||||
AC_MSG_RESULT([yes])
|
||||
break
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
done
|
||||
|
||||
# if the file wasn't found, well, go ahead and try the link anyway -- maybe
|
||||
# it will just work!
|
||||
fi
|
||||
|
||||
# try the preprocessor and linker with our new flags,
|
||||
# being careful not to pollute the global LIBS, LDFLAGS, and CPPFLAGS
|
||||
|
||||
AC_MSG_CHECKING([whether compiling and linking against OpenSSL works])
|
||||
echo "Trying link with OPENSSL_LDFLAGS=$OPENSSL_LDFLAGS;" \
|
||||
"OPENSSL_LIBS=$OPENSSL_LIBS; OPENSSL_INCLUDES=$OPENSSL_INCLUDES" >&AS_MESSAGE_LOG_FD
|
||||
|
||||
save_LIBS="$LIBS"
|
||||
save_LDFLAGS="$LDFLAGS"
|
||||
save_CPPFLAGS="$CPPFLAGS"
|
||||
LDFLAGS="$LDFLAGS $OPENSSL_LDFLAGS"
|
||||
LIBS="$OPENSSL_LIBS $LIBS"
|
||||
CPPFLAGS="$OPENSSL_INCLUDES $CPPFLAGS"
|
||||
AC_LINK_IFELSE(
|
||||
[AC_LANG_PROGRAM([#include <openssl/ssl.h>], [SSL_new(NULL)])],
|
||||
[
|
||||
AC_MSG_RESULT([yes])
|
||||
$1
|
||||
], [
|
||||
AC_MSG_RESULT([no])
|
||||
$2
|
||||
])
|
||||
CPPFLAGS="$save_CPPFLAGS"
|
||||
LDFLAGS="$save_LDFLAGS"
|
||||
LIBS="$save_LIBS"
|
||||
|
||||
AC_SUBST([OPENSSL_INCLUDES])
|
||||
AC_SUBST([OPENSSL_LIBS])
|
||||
AC_SUBST([OPENSSL_LDFLAGS])
|
||||
])
|
142
m4_ax_check_zlib.m4
Normal file
142
m4_ax_check_zlib.m4
Normal file
|
@ -0,0 +1,142 @@
|
|||
# ===========================================================================
|
||||
# http://www.gnu.org/software/autoconf-archive/ax_check_zlib.html
|
||||
# ===========================================================================
|
||||
#
|
||||
# SYNOPSIS
|
||||
#
|
||||
# AX_CHECK_ZLIB([action-if-found], [action-if-not-found])
|
||||
#
|
||||
# DESCRIPTION
|
||||
#
|
||||
# This macro searches for an installed zlib library. If nothing was
|
||||
# specified when calling configure, it searches first in /usr/local and
|
||||
# then in /usr, /opt/local and /sw. If the --with-zlib=DIR is specified,
|
||||
# it will try to find it in DIR/include/zlib.h and DIR/lib/libz.a. If
|
||||
# --without-zlib is specified, the library is not searched at all.
|
||||
#
|
||||
# If either the header file (zlib.h) or the library (libz) is not found,
|
||||
# shell commands 'action-if-not-found' is run. If 'action-if-not-found' is
|
||||
# not specified, the configuration exits on error, asking for a valid zlib
|
||||
# installation directory or --without-zlib.
|
||||
#
|
||||
# If both header file and library are found, shell commands
|
||||
# 'action-if-found' is run. If 'action-if-found' is not specified, the
|
||||
# default action appends '-I${ZLIB_HOME}/include' to CPFLAGS, appends
|
||||
# '-L$ZLIB_HOME}/lib' to LDFLAGS, prepends '-lz' to LIBS, and calls
|
||||
# AC_DEFINE(HAVE_LIBZ). You should use autoheader to include a definition
|
||||
# for this symbol in a config.h file. Sample usage in a C/C++ source is as
|
||||
# follows:
|
||||
#
|
||||
# #ifdef HAVE_LIBZ
|
||||
# #include <zlib.h>
|
||||
# #endif /* HAVE_LIBZ */
|
||||
#
|
||||
# LICENSE
|
||||
#
|
||||
# Copyright (c) 2008 Loic Dachary <loic@senga.org>
|
||||
# Copyright (c) 2010 Bastien Chevreux <bach@chevreux.org>
|
||||
#
|
||||
# This program 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.
|
||||
#
|
||||
# This program 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 program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
# As a special exception, the respective Autoconf Macro's copyright owner
|
||||
# gives unlimited permission to copy, distribute and modify the configure
|
||||
# scripts that are the output of Autoconf when processing the Macro. You
|
||||
# need not follow the terms of the GNU General Public License when using
|
||||
# or distributing such scripts, even though portions of the text of the
|
||||
# Macro appear in them. The GNU General Public License (GPL) does govern
|
||||
# all other use of the material that constitutes the Autoconf Macro.
|
||||
#
|
||||
# This special exception to the GPL applies to versions of the Autoconf
|
||||
# Macro released by the Autoconf Archive. When you make and distribute a
|
||||
# modified version of the Autoconf Macro, you may extend this special
|
||||
# exception to the GPL to apply to your modified version as well.
|
||||
|
||||
#serial 14
|
||||
|
||||
AU_ALIAS([CHECK_ZLIB], [AX_CHECK_ZLIB])
|
||||
AC_DEFUN([AX_CHECK_ZLIB],
|
||||
#
|
||||
# Handle user hints
|
||||
#
|
||||
[AC_MSG_CHECKING(if zlib is wanted)
|
||||
zlib_places="/usr/local /usr /opt/local /sw"
|
||||
AC_ARG_WITH([zlib],
|
||||
[ --with-zlib=DIR root directory path of zlib installation @<:@defaults to
|
||||
/usr/local or /usr if not found in /usr/local@:>@
|
||||
--without-zlib to disable zlib usage completely],
|
||||
[if test "$withval" != no ; then
|
||||
AC_MSG_RESULT(yes)
|
||||
if test -d "$withval"
|
||||
then
|
||||
zlib_places="$withval $zlib_places"
|
||||
else
|
||||
AC_MSG_WARN([Sorry, $withval does not exist, checking usual places])
|
||||
fi
|
||||
else
|
||||
zlib_places=
|
||||
AC_MSG_RESULT(no)
|
||||
fi],
|
||||
[AC_MSG_RESULT(yes)])
|
||||
|
||||
#
|
||||
# Locate zlib, if wanted
|
||||
#
|
||||
if test -n "${zlib_places}"
|
||||
then
|
||||
# check the user supplied or any other more or less 'standard' place:
|
||||
# Most UNIX systems : /usr/local and /usr
|
||||
# MacPorts / Fink on OSX : /opt/local respectively /sw
|
||||
for ZLIB_HOME in ${zlib_places} ; do
|
||||
if test -f "${ZLIB_HOME}/include/zlib.h"; then break; fi
|
||||
ZLIB_HOME=""
|
||||
done
|
||||
|
||||
ZLIB_OLD_LDFLAGS=$LDFLAGS
|
||||
ZLIB_OLD_CPPFLAGS=$CPPFLAGS
|
||||
if test -n "${ZLIB_HOME}"; then
|
||||
LDFLAGS="$LDFLAGS -L${ZLIB_HOME}/lib"
|
||||
CPPFLAGS="$CPPFLAGS -I${ZLIB_HOME}/include"
|
||||
fi
|
||||
AC_LANG_SAVE
|
||||
AC_LANG_C
|
||||
AC_CHECK_LIB([z], [inflateEnd], [zlib_cv_libz=yes], [zlib_cv_libz=no])
|
||||
AC_CHECK_HEADER([zlib.h], [zlib_cv_zlib_h=yes], [zlib_cv_zlib_h=no])
|
||||
AC_LANG_RESTORE
|
||||
if test "$zlib_cv_libz" = "yes" && test "$zlib_cv_zlib_h" = "yes"
|
||||
then
|
||||
#
|
||||
# If both library and header were found, action-if-found
|
||||
#
|
||||
m4_ifblank([$1],[
|
||||
CPPFLAGS="$CPPFLAGS -I${ZLIB_HOME}/include"
|
||||
LDFLAGS="$LDFLAGS -L${ZLIB_HOME}/lib"
|
||||
LIBS="-lz $LIBS"
|
||||
AC_DEFINE([HAVE_LIBZ], [1],
|
||||
[Define to 1 if you have `z' library (-lz)])
|
||||
],[
|
||||
# Restore variables
|
||||
LDFLAGS="$ZLIB_OLD_LDFLAGS"
|
||||
CPPFLAGS="$ZLIB_OLD_CPPFLAGS"
|
||||
$1
|
||||
])
|
||||
else
|
||||
#
|
||||
# If either header or library was not found, action-if-not-found
|
||||
#
|
||||
m4_default([$2],[
|
||||
AC_MSG_ERROR([either specify a valid zlib installation with --with-zlib=DIR or disable zlib usage with --without-zlib])
|
||||
])
|
||||
fi
|
||||
fi
|
||||
])
|
482
main.c
482
main.c
|
@ -1,20 +1,20 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
This file is part of telegram-cli.
|
||||
|
||||
Telegram-client is free software: you can redistribute it and/or modify
|
||||
Telegram-cli 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,
|
||||
Telegram-cli 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 <http://www.gnu.org/licenses/>.
|
||||
along with this telegram-cli. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
|
@ -34,8 +34,18 @@
|
|||
#else
|
||||
#include <editline/readline.h>
|
||||
#endif
|
||||
#ifdef EVENT_V2
|
||||
#include <event2/event.h>
|
||||
#include <event2/bufferevent.h>
|
||||
#include <event2/buffer.h>
|
||||
#else
|
||||
#include <event.h>
|
||||
#include "event-old.h"
|
||||
#endif
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/un.h>
|
||||
#include <time.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
|
@ -47,9 +57,11 @@
|
|||
#include <libconfig.h>
|
||||
#endif
|
||||
|
||||
#include <grp.h>
|
||||
#include <arpa/inet.h>
|
||||
|
||||
#include "telegram.h"
|
||||
#include "loop.h"
|
||||
#include "mtproto-client.h"
|
||||
#include "interface.h"
|
||||
#include "tools.h"
|
||||
|
||||
|
@ -57,8 +69,10 @@
|
|||
# include "lua-tg.h"
|
||||
#endif
|
||||
|
||||
#define PROGNAME "telegram-client"
|
||||
#define VERSION "0.01"
|
||||
#include "tgl.h"
|
||||
|
||||
#define PROGNAME "telegram-cli"
|
||||
#define VERSION "0.07"
|
||||
|
||||
#define CONFIG_DIRECTORY "." PROG_NAME
|
||||
#define CONFIG_FILE "config"
|
||||
|
@ -68,28 +82,34 @@
|
|||
#define DOWNLOADS_DIRECTORY "downloads"
|
||||
#define BINLOG_FILE "binlog"
|
||||
|
||||
|
||||
#define CONFIG_DIRECTORY_MODE 0700
|
||||
|
||||
#define DEFAULT_CONFIG_CONTENTS \
|
||||
"# This is an empty config file\n" \
|
||||
"# Feel free to put something here\n"
|
||||
|
||||
char *default_username;
|
||||
char *auth_token;
|
||||
int verbosity;
|
||||
int msg_num_mode;
|
||||
char *default_username;
|
||||
char *config_filename;
|
||||
char *prefix;
|
||||
int test_dc;
|
||||
char *auth_file_name;
|
||||
char *state_file_name;
|
||||
char *secret_chat_file_name;
|
||||
char *downloads_directory;
|
||||
char *config_directory;
|
||||
char *binlog_file_name;
|
||||
char *lua_file;
|
||||
int binlog_enabled;
|
||||
extern int log_level;
|
||||
int sync_from_start;
|
||||
int allow_weak_random;
|
||||
int disable_colors;
|
||||
int readline_disabled;
|
||||
int disable_output;
|
||||
int reset_authorization;
|
||||
int port;
|
||||
|
||||
void set_default_username (const char *s) {
|
||||
if (default_username) {
|
||||
|
@ -214,7 +234,9 @@ void running_for_first_time (void) {
|
|||
//char *downloads_directory = get_downloads_directory ();
|
||||
|
||||
if (!mkdir (config_directory, CONFIG_DIRECTORY_MODE)) {
|
||||
printf ("[%s] created\n", config_directory);
|
||||
if (!disable_output) {
|
||||
printf ("[%s] created\n", config_directory);
|
||||
}
|
||||
}
|
||||
|
||||
tfree_str (config_directory);
|
||||
|
@ -267,16 +289,16 @@ void parse_config_val (config_t *conf, char **s, char *param_name, const char *d
|
|||
*s = tstrdup (r);
|
||||
}
|
||||
} else {
|
||||
if (path) {
|
||||
if (path && default_name) {
|
||||
tasprintf (s, "%s/%s", path, default_name);
|
||||
} else {
|
||||
*s = tstrdup (default_name);
|
||||
*s = default_name ? tstrdup (default_name) : 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void parse_config (void) {
|
||||
config_filename = make_full_path (config_filename);
|
||||
//config_filename = make_full_path (config_filename);
|
||||
|
||||
config_t conf;
|
||||
config_init (&conf);
|
||||
|
@ -296,9 +318,13 @@ void parse_config (void) {
|
|||
memcpy (buf, prefix, l);
|
||||
buf[l ++] = '.';
|
||||
}
|
||||
test_dc = 0;
|
||||
|
||||
int test_mode = 0;
|
||||
strcpy (buf + l, "test");
|
||||
config_lookup_bool (&conf, buf, &test_dc);
|
||||
config_lookup_bool (&conf, buf, &test_mode);
|
||||
if (test_mode) {
|
||||
tgl_set_test_mode ();
|
||||
}
|
||||
|
||||
strcpy (buf + l, "log_level");
|
||||
long long t = log_level;
|
||||
|
@ -314,29 +340,65 @@ void parse_config (void) {
|
|||
config_directory = make_full_path (config_directory);
|
||||
|
||||
parse_config_val (&conf, &auth_file_name, "auth_file", AUTH_KEY_FILE, config_directory);
|
||||
parse_config_val (&conf, &state_file_name, "state_file", STATE_FILE, config_directory);
|
||||
parse_config_val (&conf, &secret_chat_file_name, "secret", SECRET_CHAT_FILE, config_directory);
|
||||
parse_config_val (&conf, &downloads_directory, "downloads", DOWNLOADS_DIRECTORY, config_directory);
|
||||
parse_config_val (&conf, &binlog_file_name, "binlog", BINLOG_FILE, config_directory);
|
||||
|
||||
if (!lua_file) {
|
||||
parse_config_val (&conf, &lua_file, "lua_script", 0, config_directory);
|
||||
}
|
||||
|
||||
strcpy (buf + l, "binlog_enabled");
|
||||
config_lookup_bool (&conf, buf, &binlog_enabled);
|
||||
|
||||
int pfs_enabled = 0;
|
||||
strcpy (buf + l, "pfs_enabled");
|
||||
config_lookup_bool (&conf, buf, &pfs_enabled);
|
||||
if (pfs_enabled) {
|
||||
tgl_enable_pfs ();
|
||||
}
|
||||
|
||||
if (binlog_enabled) {
|
||||
parse_config_val (&conf, &binlog_file_name, "binlog", BINLOG_FILE, config_directory);
|
||||
tgl_set_binlog_mode (1);
|
||||
tgl_set_binlog_path (binlog_file_name);
|
||||
} else {
|
||||
tgl_set_binlog_mode (0);
|
||||
parse_config_val (&conf, &state_file_name, "state_file", STATE_FILE, config_directory);
|
||||
parse_config_val (&conf, &secret_chat_file_name, "secret", SECRET_CHAT_FILE, config_directory);
|
||||
//tgl_set_auth_file_path (auth_file_name);
|
||||
}
|
||||
tgl_set_download_directory (downloads_directory);
|
||||
|
||||
if (!mkdir (config_directory, CONFIG_DIRECTORY_MODE)) {
|
||||
printf ("[%s] created\n", config_directory);
|
||||
if (!disable_output) {
|
||||
printf ("[%s] created\n", config_directory);
|
||||
}
|
||||
}
|
||||
if (!mkdir (downloads_directory, CONFIG_DIRECTORY_MODE)) {
|
||||
printf ("[%s] created\n", downloads_directory);
|
||||
if (!disable_output) {
|
||||
printf ("[%s] created\n", downloads_directory);
|
||||
}
|
||||
}
|
||||
config_destroy (&conf);
|
||||
}
|
||||
#else
|
||||
void parse_config (void) {
|
||||
printf ("libconfig not enabled\n");
|
||||
tasprintf (&auth_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, AUTH_KEY_FILE);
|
||||
tasprintf (&state_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, STATE_FILE);
|
||||
tasprintf (&secret_chat_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, SECRET_CHAT_FILE);
|
||||
if (!disable_output) {
|
||||
printf ("libconfig not enabled\n");
|
||||
}
|
||||
tasprintf (&downloads_directory, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, DOWNLOADS_DIRECTORY);
|
||||
tasprintf (&binlog_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, BINLOG_FILE);
|
||||
|
||||
if (binlog_enabled) {
|
||||
tasprintf (&binlog_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, BINLOG_FILE);
|
||||
tgl_set_binlog_mode (1);
|
||||
tgl_set_binlog_path (binlog_file_name);
|
||||
} else {
|
||||
tgl_set_binlog_mode (0);
|
||||
//tgl_set_auth_file_path (auth_file_name;
|
||||
tasprintf (&auth_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, AUTH_KEY_FILE);
|
||||
tasprintf (&state_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, STATE_FILE);
|
||||
tasprintf (&secret_chat_file_name, "%s/%s/%s", get_home_directory (), CONFIG_DIRECTORY, SECRET_CHAT_FILE);
|
||||
}
|
||||
tgl_set_download_directory (downloads_directory);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -346,31 +408,42 @@ void inner_main (void) {
|
|||
|
||||
void usage (void) {
|
||||
printf ("%s Usage\n", PROGNAME);
|
||||
|
||||
printf (" -h this help list\n");
|
||||
printf (" -u username specify username\n");
|
||||
printf (" -k public-key specify server public key\n");
|
||||
printf (" -v verbose\n");
|
||||
printf (" -l [1-3] log level\n");
|
||||
printf (" -L log-file log net file\n");
|
||||
printf (" -N message num mode\n");
|
||||
printf (" -c config-file specify config file\n");
|
||||
printf (" -p prefix specify prefix\n");
|
||||
printf (" -R register mode\n");
|
||||
printf (" -f sync from start\n");
|
||||
printf (" -B enable binlog\n");
|
||||
printf (" -E disable auto accept\n");
|
||||
printf (" -w allow weak random\n");
|
||||
printf (" -s specify lua script\n");
|
||||
printf (" -W wait dialog list\n");
|
||||
printf ("\n");
|
||||
|
||||
printf (" -u specify username (would not be asked during authorization)\n");
|
||||
printf (" -k specify location of public key (possible multiple entries)\n");
|
||||
printf (" -v increase verbosity (0-ERROR 1-WARNIN 2-NOTICE 3+-DEBUG-levels)\n");
|
||||
printf (" -N message num mode\n");
|
||||
#ifdef HAVE_LIBCONFIG
|
||||
printf (" -c config file name\n");
|
||||
printf (" -p use specified profile\n");
|
||||
#else
|
||||
printf (" -B enable binlog\n");
|
||||
#endif
|
||||
printf (" -l log level\n");
|
||||
printf (" -f during authorization fetch all messages since registration\n");
|
||||
printf (" -E diable auto accept of encrypted chats\n");
|
||||
#ifdef USE_LUA
|
||||
printf (" -s lua script file\n");
|
||||
#endif
|
||||
printf (" -W send dialog_list query and wait for answer before reading input\n");
|
||||
printf (" -C disable color output\n");
|
||||
printf (" -R disable readline\n");
|
||||
printf (" -d daemon mode\n");
|
||||
printf (" -L <log-name> log file name\n");
|
||||
printf (" -U <user-name> change uid after start\n");
|
||||
printf (" -G <group-name> change gid after start\n");
|
||||
printf (" -D disable output\n");
|
||||
printf (" -P <port> port to listen for input commands\n");
|
||||
printf (" -S <socket-name> unix socket to create\n");
|
||||
|
||||
exit (1);
|
||||
}
|
||||
|
||||
extern char *rsa_public_key_name;
|
||||
extern int verbosity;
|
||||
extern int default_dc_num;
|
||||
//extern char *rsa_public_key_name;
|
||||
//extern int default_dc_num;
|
||||
|
||||
|
||||
|
||||
|
||||
char *log_net_file;
|
||||
FILE *log_net_f;
|
||||
|
@ -379,24 +452,118 @@ int register_mode;
|
|||
int disable_auto_accept;
|
||||
int wait_dialog_list;
|
||||
|
||||
char *lua_file;
|
||||
char *logname;
|
||||
int daemonize;
|
||||
|
||||
|
||||
void reopen_logs (void) {
|
||||
int fd;
|
||||
fflush (stdout);
|
||||
fflush (stderr);
|
||||
if ((fd = open ("/dev/null", O_RDWR, 0)) != -1) {
|
||||
dup2 (fd, 0);
|
||||
dup2 (fd, 1);
|
||||
dup2 (fd, 2);
|
||||
if (fd > 2) {
|
||||
close (fd);
|
||||
}
|
||||
}
|
||||
if (logname && (fd = open (logname, O_WRONLY|O_APPEND|O_CREAT, 0640)) != -1) {
|
||||
dup2 (fd, 1);
|
||||
dup2 (fd, 2);
|
||||
if (fd > 2) {
|
||||
close (fd);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void sigusr1_handler (const int sig) {
|
||||
fprintf(stderr, "got SIGUSR1, rotate logs.\n");
|
||||
reopen_logs ();
|
||||
signal (SIGUSR1, sigusr1_handler);
|
||||
}
|
||||
|
||||
static void sighup_handler (const int sig) {
|
||||
fprintf(stderr, "got SIGHUP.\n");
|
||||
signal (SIGHUP, sighup_handler);
|
||||
}
|
||||
|
||||
char *set_user_name;
|
||||
char *set_group_name;
|
||||
|
||||
int change_user_group () {
|
||||
char *username = set_user_name;
|
||||
char *groupname = set_group_name;
|
||||
struct passwd *pw;
|
||||
/* lose root privileges if we have them */
|
||||
if (getuid() == 0 || geteuid() == 0) {
|
||||
if (username == 0 || *username == '\0') {
|
||||
username = "telegramd";
|
||||
}
|
||||
if ((pw = getpwnam (username)) == 0) {
|
||||
fprintf (stderr, "change_user_group: can't find the user %s to switch to\n", username);
|
||||
return -1;
|
||||
}
|
||||
gid_t gid = pw->pw_gid;
|
||||
if (setgroups (1, &gid) < 0) {
|
||||
fprintf (stderr, "change_user_group: failed to clear supplementary groups list: %m\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (groupname) {
|
||||
struct group *g = getgrnam (groupname);
|
||||
if (g == NULL) {
|
||||
fprintf (stderr, "change_user_group: can't find the group %s to switch to\n", groupname);
|
||||
return -1;
|
||||
}
|
||||
gid = g->gr_gid;
|
||||
}
|
||||
|
||||
if (setgid (gid) < 0) {
|
||||
fprintf (stderr, "change_user_group: setgid (%d) failed. %m\n", (int) gid);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (setuid (pw->pw_uid) < 0) {
|
||||
fprintf (stderr, "change_user_group: failed to assume identity of user %s\n", username);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *unix_socket;
|
||||
|
||||
void args_parse (int argc, char **argv) {
|
||||
int opt = 0;
|
||||
while ((opt = getopt (argc, argv, "u:hk:vn:Nc:p:l:RfBL:Es:wW")) != -1) {
|
||||
while ((opt = getopt (argc, argv, "u:hk:vNl:fEwWCRdL:DU:G:qP:S:"
|
||||
#ifdef HAVE_LIBCONFIG
|
||||
"c:p:"
|
||||
#else
|
||||
"B"
|
||||
#endif
|
||||
#ifdef USE_LUA
|
||||
"s:"
|
||||
#endif
|
||||
|
||||
)) != -1) {
|
||||
switch (opt) {
|
||||
case 'u':
|
||||
set_default_username (optarg);
|
||||
break;
|
||||
case 'k':
|
||||
rsa_public_key_name = tstrdup (optarg);
|
||||
//rsa_public_key_name = tstrdup (optarg);
|
||||
tgl_set_rsa_key (optarg);
|
||||
break;
|
||||
case 'v':
|
||||
tgl_incr_verbosity ();
|
||||
verbosity ++;
|
||||
break;
|
||||
case 'N':
|
||||
msg_num_mode ++;
|
||||
break;
|
||||
#ifdef HAVE_LIBCONFIG
|
||||
case 'c':
|
||||
config_filename = tstrdup (optarg);
|
||||
break;
|
||||
|
@ -404,25 +571,16 @@ void args_parse (int argc, char **argv) {
|
|||
prefix = tstrdup (optarg);
|
||||
assert (strlen (prefix) <= 100);
|
||||
break;
|
||||
case 'l':
|
||||
log_level = atoi (optarg);
|
||||
break;
|
||||
case 'R':
|
||||
register_mode = 1;
|
||||
break;
|
||||
case 'f':
|
||||
sync_from_start = 1;
|
||||
break;
|
||||
#else
|
||||
case 'B':
|
||||
binlog_enabled = 1;
|
||||
break;
|
||||
case 'L':
|
||||
if (log_net_file) {
|
||||
usage ();
|
||||
}
|
||||
log_net_file = tstrdup (optarg);
|
||||
log_net_f = fopen (log_net_file, "a");
|
||||
assert (log_net_f);
|
||||
#endif
|
||||
case 'l':
|
||||
log_level = atoi (optarg);
|
||||
break;
|
||||
case 'f':
|
||||
sync_from_start = 1;
|
||||
break;
|
||||
case 'E':
|
||||
disable_auto_accept = 1;
|
||||
|
@ -430,12 +588,44 @@ void args_parse (int argc, char **argv) {
|
|||
case 'w':
|
||||
allow_weak_random = 1;
|
||||
break;
|
||||
#ifdef USE_LUA
|
||||
case 's':
|
||||
lua_file = tstrdup (optarg);
|
||||
lua_file = strdup (optarg);
|
||||
break;
|
||||
#endif
|
||||
case 'W':
|
||||
wait_dialog_list = 1;
|
||||
break;
|
||||
case 'C':
|
||||
disable_colors ++;
|
||||
break;
|
||||
case 'R':
|
||||
readline_disabled ++;
|
||||
break;
|
||||
case 'd':
|
||||
daemonize ++;
|
||||
break;
|
||||
case 'L':
|
||||
logname = optarg;
|
||||
break;
|
||||
case 'U':
|
||||
set_user_name = optarg;
|
||||
break;
|
||||
case 'G':
|
||||
set_group_name = optarg;
|
||||
break;
|
||||
case 'D':
|
||||
disable_output ++;
|
||||
break;
|
||||
case 'q':
|
||||
reset_authorization ++;
|
||||
break;
|
||||
case 'P':
|
||||
port = atoi (optarg);
|
||||
break;
|
||||
case 'S':
|
||||
unix_socket = optarg;
|
||||
break;
|
||||
case 'h':
|
||||
default:
|
||||
usage ();
|
||||
|
@ -458,40 +648,164 @@ void print_backtrace (void) {
|
|||
}
|
||||
#endif
|
||||
|
||||
void sig_segv_handler (int signum __attribute__ ((unused))) {
|
||||
set_terminal_attributes ();
|
||||
if (write (1, "SIGSEGV received\n", 18) < 0) {
|
||||
int sfd;
|
||||
int usfd;
|
||||
|
||||
void termination_signal_handler (int signum) {
|
||||
if (!readline_disabled) {
|
||||
rl_free_line_state ();
|
||||
rl_cleanup_after_signal ();
|
||||
}
|
||||
|
||||
if (write (1, "SIGNAL received\n", 18) < 0) {
|
||||
// Sad thing
|
||||
}
|
||||
|
||||
if (unix_socket) {
|
||||
unlink (unix_socket);
|
||||
}
|
||||
|
||||
if (usfd > 0) {
|
||||
close (usfd);
|
||||
}
|
||||
if (sfd > 0) {
|
||||
close (sfd);
|
||||
}
|
||||
print_backtrace ();
|
||||
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
void sig_abrt_handler (int signum __attribute__ ((unused))) {
|
||||
set_terminal_attributes ();
|
||||
if (write (1, "SIGABRT received\n", 18) < 0) {
|
||||
volatile int sigterm_cnt;
|
||||
|
||||
void sig_term_handler (int signum __attribute__ ((unused))) {
|
||||
signal (signum, termination_signal_handler);
|
||||
//set_terminal_attributes ();
|
||||
if (write (1, "SIGTERM/SIGINT received\n", 25) < 0) {
|
||||
// Sad thing
|
||||
}
|
||||
print_backtrace ();
|
||||
exit (EXIT_FAILURE);
|
||||
if (tgl_state.ev_base) {
|
||||
event_base_loopbreak(tgl_state.ev_base);
|
||||
}
|
||||
sigterm_cnt ++;
|
||||
}
|
||||
|
||||
void do_halt (int error) {
|
||||
if (!readline_disabled) {
|
||||
rl_free_line_state ();
|
||||
rl_cleanup_after_signal ();
|
||||
}
|
||||
|
||||
if (write (1, "halt\n", 5) < 0) {
|
||||
// Sad thing
|
||||
}
|
||||
|
||||
if (unix_socket) {
|
||||
unlink (unix_socket);
|
||||
}
|
||||
|
||||
if (usfd > 0) {
|
||||
close (usfd);
|
||||
}
|
||||
if (sfd > 0) {
|
||||
close (sfd);
|
||||
}
|
||||
|
||||
exit (error ? EXIT_FAILURE : EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
int main (int argc, char **argv) {
|
||||
signal (SIGSEGV, sig_segv_handler);
|
||||
signal (SIGABRT, sig_abrt_handler);
|
||||
signal (SIGSEGV, termination_signal_handler);
|
||||
signal (SIGABRT, termination_signal_handler);
|
||||
signal (SIGBUS, termination_signal_handler);
|
||||
signal (SIGQUIT, termination_signal_handler);
|
||||
signal (SIGFPE, termination_signal_handler);
|
||||
|
||||
signal (SIGPIPE, SIG_IGN);
|
||||
|
||||
signal (SIGTERM, sig_term_handler);
|
||||
signal (SIGINT, sig_term_handler);
|
||||
|
||||
rl_catch_signals = 0;
|
||||
|
||||
|
||||
log_level = 10;
|
||||
|
||||
args_parse (argc, argv);
|
||||
printf (
|
||||
"Telegram-client version " TG_VERSION ", Copyright (C) 2013 Vitaly Valtman\n"
|
||||
"Telegram-client comes with ABSOLUTELY NO WARRANTY; for details type `show_license'.\n"
|
||||
"This is free software, and you are welcome to redistribute it\n"
|
||||
"under certain conditions; type `show_license' for details.\n"
|
||||
);
|
||||
|
||||
change_user_group ();
|
||||
|
||||
if (port > 0) {
|
||||
struct sockaddr_in serv_addr;
|
||||
|
||||
sfd = socket (AF_INET, SOCK_STREAM, 0);
|
||||
if (sfd < 0) {
|
||||
perror ("socket");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
memset (&serv_addr, 0, sizeof (serv_addr));
|
||||
|
||||
serv_addr.sin_family = AF_INET;
|
||||
serv_addr.sin_addr.s_addr = htonl (0x7f000001);
|
||||
serv_addr.sin_port = htons (port);
|
||||
|
||||
if (bind (sfd, (struct sockaddr *) &serv_addr, sizeof (serv_addr)) < 0) {
|
||||
perror ("bind");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
listen (sfd, 5);
|
||||
} else {
|
||||
sfd = -1;
|
||||
}
|
||||
|
||||
if (unix_socket) {
|
||||
assert (strlen (unix_socket) < 100);
|
||||
struct sockaddr_un serv_addr;
|
||||
|
||||
usfd = socket (AF_UNIX, SOCK_STREAM, 0);
|
||||
if (usfd < 0) {
|
||||
perror ("socket");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
memset (&serv_addr, 0, sizeof (serv_addr));
|
||||
|
||||
serv_addr.sun_family = AF_UNIX;
|
||||
|
||||
snprintf (serv_addr.sun_path, 108, "%s", unix_socket);
|
||||
|
||||
if (bind (usfd, (struct sockaddr *) &serv_addr, sizeof (serv_addr)) < 0) {
|
||||
perror ("bind");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
listen (usfd, 5);
|
||||
} else {
|
||||
usfd = -1;
|
||||
}
|
||||
|
||||
if (daemonize) {
|
||||
signal (SIGHUP, sighup_handler);
|
||||
reopen_logs ();
|
||||
}
|
||||
signal (SIGUSR1, sigusr1_handler);
|
||||
|
||||
if (!disable_output) {
|
||||
printf (
|
||||
"Telegram-cli version " TGL_VERSION ", Copyright (C) 2013-2014 Vitaly Valtman\n"
|
||||
"Telegram-cli comes with ABSOLUTELY NO WARRANTY; for details type `show_license'.\n"
|
||||
"This is free software, and you are welcome to redistribute it\n"
|
||||
"under certain conditions; type `show_license' for details.\n"
|
||||
);
|
||||
}
|
||||
running_for_first_time ();
|
||||
parse_config ();
|
||||
|
||||
tgl_set_rsa_key ("/etc/" PROG_NAME "/server.pub");
|
||||
tgl_set_rsa_key ("tg-server.pub");
|
||||
|
||||
|
||||
get_terminal_attributes ();
|
||||
|
||||
|
|
1650
mtproto-client.c
1650
mtproto-client.c
File diff suppressed because it is too large
Load diff
|
@ -1,33 +1,60 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013
|
||||
Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __MTPROTO_CLIENT_H__
|
||||
#define __MTPROTO_CLIENT_H__
|
||||
#include "net.h"
|
||||
//#include "net.h"
|
||||
#include <openssl/bn.h>
|
||||
void on_start (void);
|
||||
long long encrypt_send_message (struct connection *c, int *msg, int msg_ints, int useful);
|
||||
void dc_authorize (struct 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);
|
||||
//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 connection *c, int *msg, int msg_ints, int flags);
|
||||
void tglmp_dc_create_session (struct tgl_dc *DC);
|
||||
int tglmp_check_g (unsigned char p[256], BIGNUM *g);
|
||||
int tglmp_check_DH_params (BIGNUM *p, int g);
|
||||
struct tgl_dc *tglmp_alloc_dc (int id, char *ip, int port);
|
||||
void tglmp_regenerate_temp_auth_key (struct tgl_dc *D);
|
||||
|
||||
void tgln_insert_msg_id (struct tgl_session *S, long long id);
|
||||
void tglmp_on_start (void);
|
||||
void tgl_dc_authorize (struct tgl_dc *DC);
|
||||
void tgls_free_dc (struct tgl_dc *DC);
|
||||
void tgls_free_pubkey (void);
|
||||
#endif
|
||||
|
|
111
mtproto-common.c
111
mtproto-common.c
|
@ -1,21 +1,22 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013
|
||||
Vitaly Valtman 2013-2014
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
|
@ -39,8 +40,8 @@
|
|||
#include <openssl/sha.h>
|
||||
|
||||
#include "mtproto-common.h"
|
||||
#include "interface.h"
|
||||
#include "include.h"
|
||||
#include "tools.h"
|
||||
|
||||
#ifdef __MACH__
|
||||
#include <mach/clock.h>
|
||||
|
@ -48,22 +49,20 @@
|
|||
#endif
|
||||
|
||||
|
||||
int __packet_buffer[PACKET_BUFFER_SIZE], *packet_ptr;
|
||||
int *packet_buffer = __packet_buffer + 16;
|
||||
static int __packet_buffer[PACKET_BUFFER_SIZE + 16];
|
||||
int *tgl_packet_ptr;
|
||||
int *tgl_packet_buffer = __packet_buffer + 16;
|
||||
|
||||
long long rsa_encrypted_chunks, rsa_decrypted_chunks;
|
||||
static long long rsa_encrypted_chunks, rsa_decrypted_chunks;
|
||||
|
||||
BN_CTX *BN_ctx;
|
||||
int verbosity;
|
||||
//int verbosity;
|
||||
|
||||
int get_random_bytes (unsigned char *buf, int n) {
|
||||
static int get_random_bytes (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) {
|
||||
if (verbosity >= 3) {
|
||||
logprintf ( "added %d bytes of real entropy to secure random numbers seed\n", r);
|
||||
}
|
||||
vlogprintf (E_DEBUG, "added %d bytes of real entropy to secure random numbers seed\n", r);
|
||||
} else {
|
||||
r = 0;
|
||||
}
|
||||
|
@ -90,20 +89,6 @@ int get_random_bytes (unsigned char *buf, int n) {
|
|||
return r;
|
||||
}
|
||||
|
||||
void my_clock_gettime (int clock_id UU, struct timespec *T) {
|
||||
#ifdef __MACH__
|
||||
// We are ignoring MONOTONIC and hope time doesn't go back to 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
|
||||
}
|
||||
|
||||
/* RDTSC */
|
||||
#if defined(__i386__)
|
||||
|
@ -122,9 +107,9 @@ static __inline__ unsigned long long rdtsc (void) {
|
|||
}
|
||||
#endif
|
||||
|
||||
void prng_seed (const char *password_filename, int password_length) {
|
||||
void tgl_prng_seed (const char *password_filename, int password_length) {
|
||||
struct timespec T;
|
||||
my_clock_gettime (CLOCK_REALTIME, &T);
|
||||
tgl_my_clock_gettime (CLOCK_REALTIME, &T);
|
||||
RAND_add (&T, sizeof (T), 4.0);
|
||||
#ifdef HAVE_RDTSC
|
||||
unsigned long long r = rdtsc ();
|
||||
|
@ -143,27 +128,25 @@ void prng_seed (const char *password_filename, int password_length) {
|
|||
if (password_filename && password_length > 0) {
|
||||
int fd = open (password_filename, O_RDONLY);
|
||||
if (fd < 0) {
|
||||
logprintf ( "Warning: fail to open password file - \"%s\", %m.\n", password_filename);
|
||||
vlogprintf (E_WARNING, "Warning: fail to open password file - \"%s\", %m.\n", password_filename);
|
||||
} else {
|
||||
unsigned char *a = talloc0 (password_length);
|
||||
int l = read (fd, a, password_length);
|
||||
if (l < 0) {
|
||||
logprintf ( "Warning: fail to read password file - \"%s\", %m.\n", password_filename);
|
||||
vlogprintf (E_WARNING, "Warning: fail to read password file - \"%s\", %m.\n", password_filename);
|
||||
} else {
|
||||
if (verbosity > 0) {
|
||||
logprintf ( "read %d bytes from password file.\n", l);
|
||||
}
|
||||
vlogprintf (E_DEBUG, "read %d bytes from password file.\n", l);
|
||||
RAND_add (a, l, l);
|
||||
}
|
||||
close (fd);
|
||||
tfree_secure (a, password_length);
|
||||
}
|
||||
}
|
||||
BN_ctx = BN_CTX_new ();
|
||||
ensure_ptr (BN_ctx);
|
||||
tgl_state.BN_ctx = BN_CTX_new ();
|
||||
ensure_ptr (tgl_state.BN_ctx);
|
||||
}
|
||||
|
||||
int serialize_bignum (BIGNUM *b, char *buffer, int maxlen) {
|
||||
int tgl_serialize_bignum (BIGNUM *b, char *buffer, int maxlen) {
|
||||
int itslen = BN_num_bytes (b);
|
||||
int reqlen;
|
||||
if (itslen < 254) {
|
||||
|
@ -193,19 +176,19 @@ int serialize_bignum (BIGNUM *b, char *buffer, int maxlen) {
|
|||
}
|
||||
|
||||
|
||||
long long compute_rsa_key_fingerprint (RSA *key) {
|
||||
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 = serialize_bignum (key->n, tempbuff, 4096);
|
||||
int l1 = tgl_serialize_bignum (key->n, tempbuff, 4096);
|
||||
assert (l1 > 0);
|
||||
int l2 = serialize_bignum (key->e, tempbuff + l1, 4096 - l1);
|
||||
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 out_cstring (const char *str, long len) {
|
||||
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;
|
||||
|
@ -223,7 +206,7 @@ void out_cstring (const char *str, long len) {
|
|||
packet_ptr = (int *) dest;
|
||||
}
|
||||
|
||||
void out_cstring_careful (const char *str, long len) {
|
||||
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;
|
||||
|
@ -248,16 +231,16 @@ void out_cstring_careful (const char *str, long len) {
|
|||
}
|
||||
|
||||
|
||||
void out_data (const void *data, long len) {
|
||||
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 *in_ptr, *in_end;
|
||||
int *tgl_in_ptr, *tgl_in_end;
|
||||
|
||||
int fetch_bignum (BIGNUM *x) {
|
||||
int tgl_fetch_bignum (BIGNUM *x) {
|
||||
int l = prefetch_strlen ();
|
||||
if (l < 0) {
|
||||
return l;
|
||||
|
@ -267,7 +250,7 @@ int fetch_bignum (BIGNUM *x) {
|
|||
return l;
|
||||
}
|
||||
|
||||
int pad_rsa_encrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *E) {
|
||||
int tgl_pad_rsa_encrypt (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);
|
||||
|
@ -282,7 +265,7 @@ int pad_rsa_encrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BI
|
|||
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, BN_ctx) == 1);
|
||||
assert (BN_mod_exp (&y, &x, E, N, tgl_state.BN_ctx) == 1);
|
||||
unsigned l = 256 - BN_num_bytes (&y);
|
||||
assert (l <= 256);
|
||||
memset (to, 0, l);
|
||||
|
@ -294,7 +277,7 @@ int pad_rsa_encrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BI
|
|||
return chunks * 256;
|
||||
}
|
||||
|
||||
int pad_rsa_decrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *D) {
|
||||
int tgl_pad_rsa_decrypt (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;
|
||||
}
|
||||
|
@ -309,7 +292,7 @@ int pad_rsa_decrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BI
|
|||
for (i = 0; i < chunks; i++) {
|
||||
++rsa_decrypted_chunks;
|
||||
BN_bin2bn ((unsigned char *) from, 256, &x);
|
||||
assert (BN_mod_exp (&y, &x, D, N, BN_ctx) == 1);
|
||||
assert (BN_mod_exp (&y, &x, D, N, tgl_state.BN_ctx) == 1);
|
||||
int l = BN_num_bytes (&y);
|
||||
if (l > 255) {
|
||||
BN_free (&x);
|
||||
|
@ -326,10 +309,10 @@ int pad_rsa_decrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BI
|
|||
return chunks * 255;
|
||||
}
|
||||
|
||||
unsigned char aes_key_raw[32], aes_iv[32];
|
||||
AES_KEY aes_key;
|
||||
static unsigned char aes_key_raw[32], aes_iv[32];
|
||||
static AES_KEY aes_key;
|
||||
|
||||
void init_aes_unauth (const char server_nonce[16], const char hidden_client_nonce[32], int encrypt) {
|
||||
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);
|
||||
|
@ -350,7 +333,7 @@ void init_aes_unauth (const char server_nonce[16], const char hidden_client_nonc
|
|||
memset (aes_key_raw, 0, sizeof (aes_key_raw));
|
||||
}
|
||||
|
||||
void init_aes_auth (char auth_key[192], char msg_key[16], int encrypt) {
|
||||
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));
|
||||
|
@ -390,7 +373,7 @@ void init_aes_auth (char auth_key[192], char msg_key[16], int encrypt) {
|
|||
memset (aes_key_raw, 0, sizeof (aes_key_raw));
|
||||
}
|
||||
|
||||
int pad_aes_encrypt (char *from, int from_len, char *to, int size) {
|
||||
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) {
|
||||
|
@ -400,7 +383,7 @@ int pad_aes_encrypt (char *from, int from_len, char *to, int size) {
|
|||
return padded_size;
|
||||
}
|
||||
|
||||
int pad_aes_decrypt (char *from, int from_len, char *to, int 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;
|
||||
}
|
||||
|
|
136
mtproto-common.h
136
mtproto-common.h
|
@ -1,21 +1,22 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013
|
||||
Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __MTPROTO_COMMON_H__
|
||||
#define __MTPROTO_COMMON_H__
|
||||
|
@ -25,15 +26,20 @@
|
|||
#include <openssl/bn.h>
|
||||
#include <openssl/aes.h>
|
||||
#include <stdio.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "interface.h"
|
||||
//#include "interface.h"
|
||||
#include "tools.h"
|
||||
#include "constants.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
|
||||
|
@ -43,6 +49,8 @@
|
|||
#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
|
||||
|
@ -107,14 +115,17 @@ struct encrypted_message {
|
|||
|
||||
#pragma pack(pop)
|
||||
|
||||
BN_CTX *BN_ctx;
|
||||
//BN_CTX *BN_ctx;
|
||||
|
||||
void prng_seed (const char *password_filename, int password_length);
|
||||
int serialize_bignum (BIGNUM *b, char *buffer, int maxlen);
|
||||
long long compute_rsa_key_fingerprint (RSA *key);
|
||||
void tgl_prng_seed (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);
|
||||
|
||||
extern int *packet_buffer;
|
||||
extern int *packet_ptr;
|
||||
#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);
|
||||
|
@ -135,30 +146,43 @@ static inline void out_long (long long 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 out_cstring (const char *str, long len);
|
||||
void out_cstring_careful (const char *str, long len);
|
||||
void out_data (const void *data, long len);
|
||||
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 = serialize_bignum (n, (char *)packet_ptr, (PACKET_BUFFER_SIZE - (packet_ptr - packet_buffer)) * 4);
|
||||
int l = tgl_serialize_bignum (n, (char *)packet_ptr, (PACKET_BUFFER_SIZE - (packet_ptr - packet_buffer)) * 4);
|
||||
assert (l > 0);
|
||||
packet_ptr += l >> 2;
|
||||
}
|
||||
|
||||
extern int *in_ptr, *in_end;
|
||||
#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);
|
||||
|
||||
//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;
|
||||
|
@ -175,12 +199,9 @@ static inline int prefetch_strlen (void) {
|
|||
}
|
||||
}
|
||||
|
||||
extern int verbosity;
|
||||
static inline char *fetch_str (int len) {
|
||||
assert (len >= 0);
|
||||
if (verbosity > 6) {
|
||||
logprintf ("fetch_string: len = %d\n", len);
|
||||
}
|
||||
vlogprintf (E_DEBUG + 3, "fetch_string: len = %d\n", len);
|
||||
if (len < 254) {
|
||||
char *str = (char *) in_ptr + 1;
|
||||
in_ptr += 1 + (len >> 2);
|
||||
|
@ -268,20 +289,17 @@ static inline long have_prefetch_ints (void) {
|
|||
return in_end - in_ptr;
|
||||
}
|
||||
|
||||
int fetch_bignum (BIGNUM *x);
|
||||
int tgl_fetch_bignum (BIGNUM *x);
|
||||
#define fetch_bignum tgl_fetch_bignum
|
||||
|
||||
static inline int fetch_int (void) {
|
||||
assert (in_ptr + 1 <= in_end);
|
||||
if (verbosity > 6) {
|
||||
logprintf ("fetch_int: 0x%08x (%d)\n", *in_ptr, *in_ptr);
|
||||
}
|
||||
vlogprintf (E_DEBUG + 3, "fetch_int: 0x%08x (%d)\n", *in_ptr, *in_ptr);
|
||||
return *(in_ptr ++);
|
||||
}
|
||||
|
||||
static inline int fetch_bool (void) {
|
||||
if (verbosity > 6) {
|
||||
logprintf ("fetch_bool: 0x%08x (%d)\n", *in_ptr, *in_ptr);
|
||||
}
|
||||
vlogprintf (E_DEBUG + 3, "fetch_bool: 0x%08x (%d)\n", *in_ptr, *in_ptr);
|
||||
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;
|
||||
|
@ -323,33 +341,47 @@ static inline void fetch_ints (void *data, int count) {
|
|||
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);
|
||||
}
|
||||
}
|
||||
|
||||
int get_random_bytes (unsigned char *buf, int n);
|
||||
static inline int in_remaining (void) {
|
||||
return 4 * (in_end - in_ptr);
|
||||
}
|
||||
|
||||
int pad_rsa_encrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *E);
|
||||
int pad_rsa_decrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *D);
|
||||
//int get_random_bytes (unsigned char *buf, int n);
|
||||
|
||||
extern long long rsa_encrypted_chunks, rsa_decrypted_chunks;
|
||||
int tgl_pad_rsa_encrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *E);
|
||||
int tgl_pad_rsa_decrypt (char *from, int from_len, char *to, int size, BIGNUM *N, BIGNUM *D);
|
||||
|
||||
extern unsigned char aes_key_raw[32], aes_iv[32];
|
||||
extern AES_KEY aes_key;
|
||||
//extern long long rsa_encrypted_chunks, rsa_decrypted_chunks;
|
||||
|
||||
void init_aes_unauth (const char server_nonce[16], const char hidden_client_nonce[32], int encrypt);
|
||||
void init_aes_auth (char auth_key[192], char msg_key[16], int encrypt);
|
||||
int pad_aes_encrypt (char *from, int from_len, char *to, int size);
|
||||
int pad_aes_decrypt (char *from, int from_len, char *to, int size);
|
||||
//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
|
||||
void my_clock_gettime (int clock_id, struct timespec *T);
|
||||
#endif
|
||||
|
|
422
net.c
422
net.c
|
@ -1,20 +1,21 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
|
@ -37,81 +38,79 @@
|
|||
#include <poll.h>
|
||||
#include <openssl/rand.h>
|
||||
#include <arpa/inet.h>
|
||||
#ifdef EVENT_V2
|
||||
#include <event2/event.h>
|
||||
#else
|
||||
#include <event.h>
|
||||
#include "event-old.h"
|
||||
#endif
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "net.h"
|
||||
#include "include.h"
|
||||
#include "mtproto-client.h"
|
||||
#include "mtproto-common.h"
|
||||
#include "tgl.h"
|
||||
#include "tgl-inner.h"
|
||||
//#include "mtproto-client.h"
|
||||
//#include "mtproto-common.h"
|
||||
#include "tree.h"
|
||||
#include "interface.h"
|
||||
#include "tools.h"
|
||||
|
||||
#ifndef POLLRDHUP
|
||||
#define POLLRDHUP 0
|
||||
#endif
|
||||
|
||||
#define long_cmp(a,b) ((a) > (b) ? 1 : (a) == (b) ? 0 : -1)
|
||||
DEFINE_TREE(long,long long,long_cmp,0)
|
||||
double get_utime (int clock_id);
|
||||
//double get_utime (int clock_id);
|
||||
|
||||
int verbosity;
|
||||
extern struct connection_methods auth_methods;
|
||||
extern FILE *log_net_f;
|
||||
//extern struct mtproto_methods auth_methods;
|
||||
|
||||
void fail_connection (struct connection *c);
|
||||
static void fail_connection (struct connection *c);
|
||||
|
||||
#define PING_TIMEOUT 10
|
||||
|
||||
void start_ping_timer (struct connection *c);
|
||||
int ping_alarm (struct connection *c) {
|
||||
if (verbosity > 2) {
|
||||
logprintf ("ping alarm\n");
|
||||
}
|
||||
static void start_ping_timer (struct connection *c);
|
||||
static void ping_alarm (evutil_socket_t fd, short what, void *arg) {
|
||||
struct connection *c = arg;
|
||||
vlogprintf (E_DEBUG + 2,"ping alarm\n");
|
||||
assert (c->state == conn_ready || c->state == conn_connecting);
|
||||
if (get_double_time () - c->last_receive_time > 20 * PING_TIMEOUT) {
|
||||
if (verbosity) {
|
||||
logprintf ( "fail connection: reason: ping timeout\n");
|
||||
}
|
||||
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 (get_double_time () - c->last_receive_time > 5 * PING_TIMEOUT && c->state == conn_ready) {
|
||||
int x[3];
|
||||
x[0] = CODE_ping;
|
||||
*(long long *)(x + 1) = lrand48 () * (1ll << 32) + lrand48 ();
|
||||
encrypt_send_message (c, x, 3, 0);
|
||||
} else if (tglt_get_double_time () - c->last_receive_time > 3 * PING_TIMEOUT && c->state == conn_ready) {
|
||||
tgl_do_send_ping (c);
|
||||
start_ping_timer (c);
|
||||
} else {
|
||||
start_ping_timer (c);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void stop_ping_timer (struct connection *c) {
|
||||
remove_event_timer (&c->ev);
|
||||
static void stop_ping_timer (struct connection *c) {
|
||||
event_del (c->ping_ev);
|
||||
}
|
||||
|
||||
void start_ping_timer (struct connection *c) {
|
||||
c->ev.timeout = get_double_time () + PING_TIMEOUT;
|
||||
c->ev.alarm = (void *)ping_alarm;
|
||||
c->ev.self = c;
|
||||
insert_event_timer (&c->ev);
|
||||
static void start_ping_timer (struct connection *c) {
|
||||
static struct timeval ptimeout = { PING_TIMEOUT, 0};
|
||||
event_add (c->ping_ev, &ptimeout);
|
||||
}
|
||||
|
||||
void restart_connection (struct connection *c);
|
||||
int fail_alarm (void *ev) {
|
||||
((struct connection *)ev)->in_fail_timer = 0;
|
||||
restart_connection (ev);
|
||||
return 0;
|
||||
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);
|
||||
}
|
||||
void start_fail_timer (struct connection *c) {
|
||||
|
||||
static void start_fail_timer (struct connection *c) {
|
||||
if (c->in_fail_timer) { return; }
|
||||
c->in_fail_timer = 1;
|
||||
c->ev.timeout = get_double_time () + 10;
|
||||
c->ev.alarm = (void *)fail_alarm;
|
||||
c->ev.self = c;
|
||||
insert_event_timer (&c->ev);
|
||||
|
||||
static struct timeval ptimeout = { 10, 0};
|
||||
event_add (c->fail_ev, &ptimeout);
|
||||
}
|
||||
|
||||
struct connection_buffer *new_connection_buffer (int size) {
|
||||
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;
|
||||
|
@ -119,16 +118,20 @@ struct connection_buffer *new_connection_buffer (int size) {
|
|||
return b;
|
||||
}
|
||||
|
||||
void delete_connection_buffer (struct connection_buffer *b) {
|
||||
static void delete_connection_buffer (struct connection_buffer *b) {
|
||||
tfree (b->start, b->end - b->start);
|
||||
tfree (b, sizeof (*b));
|
||||
}
|
||||
|
||||
int write_out (struct connection *c, const void *_data, int len) {
|
||||
int tgln_write_out (struct connection *c, const void *_data, int len) {
|
||||
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;
|
||||
|
@ -156,7 +159,7 @@ int write_out (struct connection *c, const void *_data, int len) {
|
|||
return x;
|
||||
}
|
||||
|
||||
int read_in (struct connection *c, void *_data, int len) {
|
||||
int tgln_read_in (struct connection *c, void *_data, int len) {
|
||||
unsigned char *data = _data;
|
||||
if (!len) { return 0; }
|
||||
assert (len > 0);
|
||||
|
@ -188,7 +191,7 @@ int read_in (struct connection *c, void *_data, int len) {
|
|||
return x;
|
||||
}
|
||||
|
||||
int read_in_lookup (struct connection *c, void *_data, int len) {
|
||||
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);
|
||||
|
@ -213,14 +216,14 @@ int read_in_lookup (struct connection *c, void *_data, int len) {
|
|||
return x;
|
||||
}
|
||||
|
||||
void flush_out (struct connection *c UU) {
|
||||
void tgln_flush_out (struct connection *c UU) {
|
||||
}
|
||||
|
||||
#define MAX_CONNECTIONS 100
|
||||
struct connection *Connections[MAX_CONNECTIONS];
|
||||
int max_connection_fd;
|
||||
static struct connection *Connections[MAX_CONNECTIONS];
|
||||
static int max_connection_fd;
|
||||
|
||||
void rotate_port (struct connection *c) {
|
||||
static void rotate_port (struct connection *c) {
|
||||
switch (c->port) {
|
||||
case 443:
|
||||
c->port = 80;
|
||||
|
@ -234,11 +237,31 @@ void rotate_port (struct connection *c) {
|
|||
}
|
||||
}
|
||||
|
||||
struct connection *create_connection (const char *host, int port, struct session *session, struct connection_methods *methods) {
|
||||
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;
|
||||
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;
|
||||
if (c->state == conn_connecting) {
|
||||
c->state = conn_ready;
|
||||
c->methods->ready (c);
|
||||
}
|
||||
try_write (c);
|
||||
if (c->out_bytes) {
|
||||
event_add (c->write_ev, 0);
|
||||
}
|
||||
}
|
||||
|
||||
struct connection *tgln_create_connection (const char *host, int port, struct tgl_session *session, struct tgl_dc *dc, struct mtproto_methods *methods) {
|
||||
struct connection *c = talloc0 (sizeof (*c));
|
||||
int fd = socket (AF_INET, SOCK_STREAM, 0);
|
||||
if (fd == -1) {
|
||||
logprintf ("Can not create socket: %m\n");
|
||||
vlogprintf (E_ERROR, "Can not create socket: %m\n");
|
||||
exit (1);
|
||||
}
|
||||
assert (fd >= 0 && fd < MAX_CONNECTIONS);
|
||||
|
@ -259,52 +282,46 @@ struct connection *create_connection (const char *host, int port, struct session
|
|||
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) {
|
||||
logprintf ( "Can not connect to %s:%d %m\n", host, port);
|
||||
vlogprintf (E_ERROR, "Can not connect to %s:%d %m\n", host, port);
|
||||
close (fd);
|
||||
tfree (c, sizeof (*c));
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
struct pollfd s;
|
||||
s.fd = fd;
|
||||
s.events = POLLOUT | POLLERR | POLLRDHUP | POLLHUP;
|
||||
errno = 0;
|
||||
|
||||
while (poll (&s, 1, 10000) <= 0 || !(s.revents & POLLOUT)) {
|
||||
if (errno == EINTR) { continue; }
|
||||
if (errno) {
|
||||
logprintf ("Problems in poll: %m\n");
|
||||
exit (1);
|
||||
}
|
||||
logprintf ("Connect with %s:%d timeout\n", host, port);
|
||||
close (fd);
|
||||
tfree (c, sizeof (*c));
|
||||
return 0;
|
||||
}
|
||||
|
||||
c->session = session;
|
||||
c->fd = fd;
|
||||
c->fd = fd;
|
||||
c->state = conn_connecting;
|
||||
c->last_receive_time = tglt_get_double_time ();
|
||||
c->ip = tstrdup (host);
|
||||
c->flags = 0;
|
||||
c->state = conn_ready;
|
||||
c->methods = methods;
|
||||
c->port = port;
|
||||
assert (!Connections[fd]);
|
||||
Connections[fd] = c;
|
||||
if (verbosity) {
|
||||
logprintf ( "connect to %s:%d successful\n", host, port);
|
||||
}
|
||||
if (c->methods->ready) {
|
||||
c->methods->ready (c);
|
||||
}
|
||||
c->last_receive_time = get_double_time ();
|
||||
|
||||
c->ping_ev = evtimer_new (tgl_state.ev_base, ping_alarm, c);
|
||||
c->fail_ev = evtimer_new (tgl_state.ev_base, fail_alarm, c);
|
||||
c->write_ev = event_new (tgl_state.ev_base, c->fd, EV_WRITE, conn_try_write, c);
|
||||
|
||||
struct timeval tv = {5, 0};
|
||||
c->read_ev = event_new (tgl_state.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;
|
||||
}
|
||||
|
||||
void restart_connection (struct connection *c) {
|
||||
static void restart_connection (struct connection *c) {
|
||||
if (c->last_connect_time == time (0)) {
|
||||
start_fail_timer (c);
|
||||
return;
|
||||
|
@ -313,7 +330,7 @@ void restart_connection (struct connection *c) {
|
|||
c->last_connect_time = time (0);
|
||||
int fd = socket (AF_INET, SOCK_STREAM, 0);
|
||||
if (fd == -1) {
|
||||
logprintf ("Can not create socket: %m\n");
|
||||
vlogprintf (E_ERROR, "Can not create socket: %m\n");
|
||||
exit (1);
|
||||
}
|
||||
assert (fd >= 0 && fd < MAX_CONNECTIONS);
|
||||
|
@ -335,7 +352,7 @@ void restart_connection (struct connection *c) {
|
|||
|
||||
if (connect (fd, (struct sockaddr *) &addr, sizeof (addr)) == -1) {
|
||||
if (errno != EINPROGRESS) {
|
||||
logprintf ( "Can not connect to %s:%d %m\n", c->ip, c->port);
|
||||
vlogprintf (E_WARNING, "Can not connect to %s:%d %m\n", c->ip, c->port);
|
||||
start_fail_timer (c);
|
||||
close (fd);
|
||||
return;
|
||||
|
@ -344,19 +361,28 @@ void restart_connection (struct connection *c) {
|
|||
|
||||
c->fd = fd;
|
||||
c->state = conn_connecting;
|
||||
c->last_receive_time = get_double_time ();
|
||||
c->last_receive_time = tglt_get_double_time ();
|
||||
start_ping_timer (c);
|
||||
Connections[fd] = c;
|
||||
|
||||
c->write_ev = event_new (tgl_state.ev_base, c->fd, EV_WRITE, conn_try_write, c);
|
||||
|
||||
struct timeval tv = {5, 0};
|
||||
c->read_ev = event_new (tgl_state.ev_base, c->fd, EV_READ | EV_PERSIST, conn_try_read, c);
|
||||
event_add (c->read_ev, &tv);
|
||||
|
||||
char byte = 0xef;
|
||||
assert (write_out (c, &byte, 1) == 1);
|
||||
flush_out (c);
|
||||
assert (tgln_write_out (c, &byte, 1) == 1);
|
||||
tgln_flush_out (c);
|
||||
}
|
||||
|
||||
void fail_connection (struct connection *c) {
|
||||
static void fail_connection (struct connection *c) {
|
||||
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) {
|
||||
|
@ -375,27 +401,16 @@ void fail_connection (struct connection *c) {
|
|||
c->out_bytes = c->in_bytes = 0;
|
||||
close (c->fd);
|
||||
Connections[c->fd] = 0;
|
||||
logprintf ("Lost connection to server... %s:%d\n", c->ip, c->port);
|
||||
vlogprintf (E_NOTICE, "Lost connection to server... %s:%d\n", c->ip, c->port);
|
||||
restart_connection (c);
|
||||
}
|
||||
|
||||
extern FILE *log_net_f;
|
||||
void try_write (struct connection *c) {
|
||||
if (verbosity) {
|
||||
logprintf ( "try write: fd = %d\n", c->fd);
|
||||
}
|
||||
//extern FILE *log_net_f;
|
||||
static void try_write (struct connection *c) {
|
||||
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 && log_net_f) {
|
||||
fprintf (log_net_f, "%.02lf %d OUT %s:%d", get_utime (CLOCK_REALTIME), r, c->ip, c->port);
|
||||
int i;
|
||||
for (i = 0; i < r; i++) {
|
||||
fprintf (log_net_f, " %02x", *(unsigned char *)(c->out_head->rptr + i));
|
||||
}
|
||||
fprintf (log_net_f, "\n");
|
||||
fflush (log_net_f);
|
||||
}
|
||||
if (r >= 0) {
|
||||
x += r;
|
||||
c->out_head->rptr += r;
|
||||
|
@ -410,9 +425,7 @@ void try_write (struct connection *c) {
|
|||
delete_connection_buffer (b);
|
||||
} else {
|
||||
if (errno != EAGAIN && errno != EWOULDBLOCK) {
|
||||
if (verbosity) {
|
||||
logprintf ("fail_connection: write_error %m\n");
|
||||
}
|
||||
vlogprintf (E_NOTICE, "fail_connection: write_error %m\n");
|
||||
fail_connection (c);
|
||||
return;
|
||||
} else {
|
||||
|
@ -420,95 +433,59 @@ void try_write (struct connection *c) {
|
|||
}
|
||||
}
|
||||
}
|
||||
if (verbosity) {
|
||||
logprintf ( "Sent %d bytes to %d\n", x, c->fd);
|
||||
}
|
||||
vlogprintf (E_DEBUG, "Sent %d bytes to %d\n", x, c->fd);
|
||||
c->out_bytes -= x;
|
||||
}
|
||||
|
||||
void hexdump_buf (struct connection_buffer *b) {
|
||||
int pos = 0;
|
||||
int rem = 8;
|
||||
while (b) {
|
||||
unsigned char *c = b->rptr;
|
||||
while (c != b->wptr) {
|
||||
if (rem == 8) {
|
||||
if (pos) { printf ("\n"); }
|
||||
printf ("%04d", pos);
|
||||
}
|
||||
printf (" %02x", (int)*c);
|
||||
rem --;
|
||||
pos ++;
|
||||
if (!rem) {
|
||||
rem = 8;
|
||||
}
|
||||
c ++;
|
||||
}
|
||||
b = b->next;
|
||||
}
|
||||
printf ("\n");
|
||||
|
||||
}
|
||||
|
||||
void try_rpc_read (struct connection *c) {
|
||||
static void try_rpc_read (struct connection *c) {
|
||||
assert (c->in_head);
|
||||
if (verbosity >= 3) {
|
||||
hexdump_buf (c->in_head);
|
||||
}
|
||||
|
||||
while (1) {
|
||||
if (c->in_bytes < 1) { return; }
|
||||
unsigned len = 0;
|
||||
unsigned t = 0;
|
||||
assert (read_in_lookup (c, &len, 1) == 1);
|
||||
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 (read_in_lookup (c, &len, 4) == 4);
|
||||
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 (read_in (c, &t, 1) == 1);
|
||||
assert (tgln_read_in (c, &t, 1) == 1);
|
||||
assert (t == len);
|
||||
assert (len >= 1);
|
||||
} else {
|
||||
assert (len == 0x7f);
|
||||
assert (read_in (c, &len, 4) == 4);
|
||||
assert (tgln_read_in (c, &len, 4) == 4);
|
||||
len = (len >> 8);
|
||||
assert (len >= 1);
|
||||
}
|
||||
len *= 4;
|
||||
int op;
|
||||
assert (read_in_lookup (c, &op, 4) == 4);
|
||||
assert (tgln_read_in_lookup (c, &op, 4) == 4);
|
||||
c->methods->execute (c, op, len);
|
||||
}
|
||||
}
|
||||
|
||||
void try_read (struct connection *c) {
|
||||
if (verbosity) {
|
||||
logprintf ( "try read: fd = %d\n", c->fd);
|
||||
}
|
||||
static void try_read (struct connection *c) {
|
||||
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 && log_net_f) {
|
||||
fprintf (log_net_f, "%.02lf %d IN %s:%d", get_utime (CLOCK_REALTIME), r, c->ip, c->port);
|
||||
int i;
|
||||
for (i = 0; i < r; i++) {
|
||||
fprintf (log_net_f, " %02x", *(unsigned char *)(c->in_tail->wptr + i));
|
||||
}
|
||||
fprintf (log_net_f, "\n");
|
||||
fflush (log_net_f);
|
||||
}
|
||||
if (r > 0) {
|
||||
c->last_receive_time = get_double_time ();
|
||||
c->last_receive_time = tglt_get_double_time ();
|
||||
stop_ping_timer (c);
|
||||
start_ping_timer (c);
|
||||
}
|
||||
|
@ -523,9 +500,7 @@ void try_read (struct connection *c) {
|
|||
c->in_tail = b;
|
||||
} else {
|
||||
if (errno != EAGAIN && errno != EWOULDBLOCK) {
|
||||
if (verbosity) {
|
||||
logprintf ("fail_connection: read_error %m\n");
|
||||
}
|
||||
vlogprintf (E_NOTICE, "fail_connection: read_error %m\n");
|
||||
fail_connection (c);
|
||||
return;
|
||||
} else {
|
||||
|
@ -533,16 +508,14 @@ void try_read (struct connection *c) {
|
|||
}
|
||||
}
|
||||
}
|
||||
if (verbosity) {
|
||||
logprintf ( "Received %d bytes from %d\n", x, c->fd);
|
||||
}
|
||||
vlogprintf (E_DEBUG, "Received %d bytes from %d\n", x, c->fd);
|
||||
c->in_bytes += x;
|
||||
if (x) {
|
||||
try_rpc_read (c);
|
||||
}
|
||||
}
|
||||
|
||||
int connections_make_poll_array (struct pollfd *fds, int max) {
|
||||
int tgl_connections_make_poll_array (struct pollfd *fds, int max) {
|
||||
int _max = max;
|
||||
int i;
|
||||
for (i = 0; i <= max_connection_fd; i++) {
|
||||
|
@ -561,16 +534,10 @@ int connections_make_poll_array (struct pollfd *fds, int max) {
|
|||
max --;
|
||||
}
|
||||
}
|
||||
if (verbosity >= 10) {
|
||||
logprintf ( "%d connections in poll\n", _max - max);
|
||||
}
|
||||
return _max - max;
|
||||
}
|
||||
|
||||
void connections_poll_result (struct pollfd *fds, int max) {
|
||||
if (verbosity >= 10) {
|
||||
logprintf ( "connections_poll_result: max = %d\n", 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];
|
||||
|
@ -578,15 +545,13 @@ void connections_poll_result (struct pollfd *fds, int max) {
|
|||
try_read (c);
|
||||
}
|
||||
if (fds[i].revents & (POLLHUP | POLLERR | POLLRDHUP)) {
|
||||
if (verbosity) {
|
||||
logprintf ("fail_connection: events_mask=0x%08x\n", fds[i].revents);
|
||||
}
|
||||
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) {
|
||||
logprintf ("connection ready\n");
|
||||
vlogprintf (E_DEBUG, "connection ready\n");
|
||||
c->state = conn_ready;
|
||||
c->last_receive_time = get_double_time ();
|
||||
c->last_receive_time = tglt_get_double_time ();
|
||||
}
|
||||
if (c->out_bytes) {
|
||||
try_write (c);
|
||||
|
@ -595,53 +560,50 @@ void connections_poll_result (struct pollfd *fds, int max) {
|
|||
}
|
||||
}
|
||||
|
||||
int send_all_acks (struct 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);
|
||||
}
|
||||
encrypt_send_message (S->c, packet_buffer, packet_ptr - packet_buffer, 0);
|
||||
return 0;
|
||||
static void incr_out_packet_num (struct connection *c) {
|
||||
c->out_packet_num ++;
|
||||
}
|
||||
|
||||
void insert_msg_id (struct session *S, long long id) {
|
||||
if (!S->ack_tree) {
|
||||
S->ev.alarm = (void *)send_all_acks;
|
||||
S->ev.self = (void *)S;
|
||||
S->ev.timeout = get_double_time () + ACK_TIMEOUT;
|
||||
insert_event_timer (&S->ev);
|
||||
}
|
||||
if (!tree_lookup_long (S->ack_tree, id)) {
|
||||
S->ack_tree = tree_insert_long (S->ack_tree, id, lrand48 ());
|
||||
}
|
||||
static struct tgl_dc *get_dc (struct connection *c) {
|
||||
return c->dc;
|
||||
}
|
||||
|
||||
extern struct dc *DC_list[];
|
||||
|
||||
struct dc *alloc_dc (int id, char *ip, int port UU) {
|
||||
assert (!DC_list[id]);
|
||||
struct dc *DC = talloc0 (sizeof (*DC));
|
||||
DC->id = id;
|
||||
DC->ip = ip;
|
||||
DC->port = port;
|
||||
DC_list[id] = DC;
|
||||
return DC;
|
||||
static struct tgl_session *get_session (struct connection *c) {
|
||||
return c->session;
|
||||
}
|
||||
|
||||
void dc_create_session (struct dc *DC) {
|
||||
struct session *S = talloc0 (sizeof (*S));
|
||||
assert (RAND_pseudo_bytes ((unsigned char *) &S->session_id, 8) >= 0);
|
||||
S->dc = DC;
|
||||
S->c = create_connection (DC->ip, DC->port, S, &auth_methods);
|
||||
if (!S->c) {
|
||||
logprintf ("Can not create connection to DC. Is network down?\n");
|
||||
exit (1);
|
||||
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);
|
||||
}
|
||||
assert (!DC->sessions[0]);
|
||||
DC->sessions[0] = S;
|
||||
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
|
||||
};
|
||||
|
|
118
net.h
118
net.h
|
@ -1,88 +1,33 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __NET_H__
|
||||
#define __NET_H__
|
||||
|
||||
#include <poll.h>
|
||||
struct dc;
|
||||
#include "queries.h"
|
||||
#define TG_SERVER "173.240.5.1"
|
||||
#define TG_SERVER_TEST "173.240.5.253"
|
||||
#define TG_APP_HASH "36722c72256a24c1225de00eb6a1ca74"
|
||||
#define TG_APP_ID 2899
|
||||
#define TG_BUILD "209"
|
||||
|
||||
#define TG_VERSION "0.01-beta"
|
||||
|
||||
#define ACK_TIMEOUT 1
|
||||
#define MAX_DC_ID 10
|
||||
|
||||
enum dc_state {
|
||||
st_init,
|
||||
st_reqpq_sent,
|
||||
st_reqdh_sent,
|
||||
st_client_dh_sent,
|
||||
st_authorized,
|
||||
st_error
|
||||
} ;
|
||||
|
||||
struct connection;
|
||||
struct connection_methods {
|
||||
int (*ready) (struct connection *c);
|
||||
int (*close) (struct connection *c);
|
||||
int (*execute) (struct connection *c, int op, int len);
|
||||
};
|
||||
|
||||
|
||||
#define MAX_DC_SESSIONS 3
|
||||
|
||||
struct session {
|
||||
struct dc *dc;
|
||||
long long session_id;
|
||||
int seq_no;
|
||||
struct connection *c;
|
||||
struct tree_long *ack_tree;
|
||||
struct event_timer ev;
|
||||
};
|
||||
|
||||
struct dc {
|
||||
int id;
|
||||
int port;
|
||||
int flags;
|
||||
char *ip;
|
||||
char *user;
|
||||
struct session *sessions[MAX_DC_SESSIONS];
|
||||
char auth_key[256];
|
||||
long long auth_key_id;
|
||||
long long server_salt;
|
||||
|
||||
int server_time_delta;
|
||||
double server_time_udelta;
|
||||
int has_auth;
|
||||
};
|
||||
|
||||
#define DC_SERIALIZED_MAGIC 0x64582faa
|
||||
#define DC_SERIALIZED_MAGIC_V2 0x94032abb
|
||||
#define STATE_FILE_MAGIC 0x84217a0d
|
||||
#define SECRET_CHAT_FILE_MAGIC 0xa9840add
|
||||
|
||||
struct dc_serialized {
|
||||
struct tgl_dc_serialized {
|
||||
int magic;
|
||||
int port;
|
||||
char ip[64];
|
||||
|
@ -125,27 +70,34 @@ struct connection {
|
|||
int out_packet_num;
|
||||
int last_connect_time;
|
||||
int in_fail_timer;
|
||||
struct connection_methods *methods;
|
||||
struct session *session;
|
||||
struct mtproto_methods *methods;
|
||||
struct tgl_session *session;
|
||||
struct tgl_dc *dc;
|
||||
void *extra;
|
||||
struct event_timer ev;
|
||||
struct event *ping_ev;
|
||||
struct event *fail_ev;
|
||||
struct event *read_ev;
|
||||
struct event *write_ev;
|
||||
double last_receive_time;
|
||||
};
|
||||
|
||||
extern struct connection *Connections[];
|
||||
//extern struct connection *Connections[];
|
||||
|
||||
int write_out (struct connection *c, const void *data, int len);
|
||||
void flush_out (struct connection *c);
|
||||
int read_in (struct connection *c, void *data, int len);
|
||||
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 create_all_outbound_connections (void);
|
||||
void tgln_insert_msg_id (struct tgl_session *S, long long id);
|
||||
|
||||
struct connection *create_connection (const char *host, int port, struct session *session, struct connection_methods *methods);
|
||||
int connections_make_poll_array (struct pollfd *fds, int max);
|
||||
void connections_poll_result (struct pollfd *fds, int max);
|
||||
void dc_create_session (struct dc *DC);
|
||||
void insert_msg_id (struct session *S, long long id);
|
||||
struct dc *alloc_dc (int id, char *ip, int port);
|
||||
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 (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
|
||||
|
|
25
no-preview.h
25
no-preview.h
|
@ -1,20 +1,21 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
|
||||
// Just sample jpg file 90x90
|
||||
|
|
118
queries.h
118
queries.h
|
@ -1,39 +1,40 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#include "net.h"
|
||||
//#include "net.h"
|
||||
#ifndef __QUERIES_H__
|
||||
#define __QUERIES_H__
|
||||
#include "structures.h"
|
||||
#include "auto.h"
|
||||
#include "tgl-layout.h"
|
||||
|
||||
struct event;
|
||||
|
||||
#define QUERY_ACK_RECEIVED 1
|
||||
#define QUERY_FORCE_SEND 2
|
||||
|
||||
struct query;
|
||||
struct query_methods {
|
||||
int (*on_answer)(struct query *q);
|
||||
int (*on_error)(struct query *q, int error_code, int len, char *error);
|
||||
int (*on_timeout)(struct query *q);
|
||||
};
|
||||
|
||||
struct event_timer {
|
||||
double timeout;
|
||||
int (*alarm)(void *self);
|
||||
void *self;
|
||||
struct paramed_type *type;
|
||||
};
|
||||
|
||||
struct query {
|
||||
|
@ -41,83 +42,36 @@ struct query {
|
|||
int data_len;
|
||||
int flags;
|
||||
int seq_no;
|
||||
long long session_id;
|
||||
void *data;
|
||||
struct query_methods *methods;
|
||||
struct event_timer ev;
|
||||
struct dc *DC;
|
||||
struct session *session;
|
||||
struct event *ev;
|
||||
struct tgl_dc *DC;
|
||||
struct tgl_session *session;
|
||||
struct paramed_type *type;
|
||||
void *extra;
|
||||
void *callback;
|
||||
void *callback_extra;
|
||||
};
|
||||
|
||||
|
||||
struct query *send_query (struct dc *DC, int len, void *data, struct query_methods *methods, void *extra);
|
||||
void query_ack (long long id);
|
||||
void query_error (long long id);
|
||||
void query_result (long long id);
|
||||
void query_restart (long long id);
|
||||
struct query *tglq_send_query (struct tgl_dc *DC, int len, void *data, struct query_methods *methods, void *extra, void *callback, void *callback_extra);
|
||||
void tglq_query_ack (long long id);
|
||||
void tglq_query_error (long long id);
|
||||
void tglq_query_result (long long id);
|
||||
void tglq_query_restart (long long id);
|
||||
|
||||
void insert_event_timer (struct event_timer *ev);
|
||||
void remove_event_timer (struct event_timer *ev);
|
||||
double next_timer_in (void);
|
||||
void work_timers (void);
|
||||
|
||||
extern struct query_methods help_get_config_methods;
|
||||
//extern struct query_methods help_get_config_methods;
|
||||
|
||||
void do_send_code (const char *user);
|
||||
void do_phone_call (const char *user);
|
||||
int do_send_code_result (const char *code);
|
||||
double get_double_time (void);
|
||||
|
||||
void do_update_contact_list (void);
|
||||
union user_chat;
|
||||
void do_send_message (peer_id_t id, const char *msg, int len);
|
||||
void do_send_text (peer_id_t id, char *file);
|
||||
void do_get_history (peer_id_t id, int limit);
|
||||
void do_get_dialog_list (void);
|
||||
void do_get_dialog_list_ex (void);
|
||||
void do_send_photo (int type, peer_id_t to_id, char *file_name);
|
||||
void do_get_chat_info (peer_id_t id);
|
||||
void do_get_user_list_info_silent (int num, int *list);
|
||||
void do_get_user_info (peer_id_t id);
|
||||
void do_forward_message (peer_id_t id, int n);
|
||||
void do_rename_chat (peer_id_t id, char *name);
|
||||
void do_load_encr_video (struct encr_video *V, int next);
|
||||
void do_create_encr_chat_request (int user_id);
|
||||
void do_create_secret_chat (peer_id_t id);
|
||||
void do_create_group_chat (peer_id_t id, char *chat_topic);
|
||||
void do_get_suggested (void);
|
||||
|
||||
struct photo;
|
||||
struct video;
|
||||
void do_load_photo (struct photo *photo, int next);
|
||||
void do_load_video_thumb (struct video *video, int next);
|
||||
void do_load_audio (struct video *V, int next);
|
||||
void do_load_video (struct video *V, int next);
|
||||
void do_load_document (struct document *V, int next);
|
||||
void do_load_document_thumb (struct document *video, int next);
|
||||
void do_help_get_config (void);
|
||||
int do_auth_check_phone (const char *user);
|
||||
int do_get_nearest_dc (void);
|
||||
int do_send_code_result_auth (const char *code, const char *first_name, const char *last_name);
|
||||
void do_import_auth (int num);
|
||||
void do_export_auth (int num);
|
||||
void do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force);
|
||||
void do_msg_search (peer_id_t id, int from, int to, int limit, const char *s);
|
||||
void do_accept_encr_chat_request (struct secret_chat *E);
|
||||
void do_get_difference (void);
|
||||
void do_mark_read (peer_id_t id);
|
||||
void do_visualize_key (peer_id_t id);
|
||||
void do_create_keys_end (struct secret_chat *U);
|
||||
void do_add_user_to_chat (peer_id_t chat_id, peer_id_t id, int limit);
|
||||
void do_del_user_from_chat (peer_id_t chat_id, peer_id_t id);
|
||||
void do_update_status (int online);
|
||||
void do_contacts_search (int limit, const char *s);
|
||||
void do_send_msg (struct message *M);
|
||||
void do_delete_msg (long long id);
|
||||
void do_restore_msg (long long id);
|
||||
void tgl_do_send_bind_temp_key (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);
|
||||
//int get_dh_config_on_answer (struct query *q);
|
||||
//void fetch_dc_option (void);
|
||||
#endif
|
||||
|
|
1
scheme.tl
Symbolic link
1
scheme.tl
Symbolic link
|
@ -0,0 +1 @@
|
|||
scheme16.tl
|
505
scheme12.tl
Normal file
505
scheme12.tl
Normal file
|
@ -0,0 +1,505 @@
|
|||
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<ChatParticipant> 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<int> = 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<PhotoSize> = 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<PhotoSize> 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<Contact> users:Vector<User> = contacts.Contacts;
|
||||
contacts.contactsNotModified#b74ba9d2 = contacts.Contacts;
|
||||
|
||||
contacts.importedContacts#d1cd0a4c imported:Vector<ImportedContact> users:Vector<User> = contacts.ImportedContacts;
|
||||
|
||||
contacts.blocked#1c138d15 blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
contacts.blockedSlice#900802a1 count:int blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
|
||||
contacts.found#566000e results:Vector<ContactFound> users:Vector<User> = contacts.Found;
|
||||
|
||||
contacts.suggested#5649dcc5 results:Vector<ContactSuggested> users:Vector<User> = contacts.Suggested;
|
||||
|
||||
messages.dialogs#15ba6c40 dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
messages.dialogsSlice#71e094f3 count:int dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
|
||||
messages.messages#8c718e87 messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
messages.messagesSlice#b446ae3 count:int messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
|
||||
messages.messageEmpty#3f4e0648 = messages.Message;
|
||||
messages.message#ff90c417 message:Message chats:Vector<Chat> users:Vector<User> = messages.Message;
|
||||
|
||||
messages.statedMessages#969478bb messages:Vector<Message> chats:Vector<Chat> users:Vector<User> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessage#d07ae726 message:Message chats:Vector<Chat> users:Vector<User> 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<User> = messages.Chat;
|
||||
|
||||
messages.chats#8150cbd8 chats:Vector<Chat> users:Vector<User> = messages.Chats;
|
||||
|
||||
messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector<Chat> users:Vector<User> = 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<int> pts:int = Update;
|
||||
updateDeleteMessages#a92bfe26 messages:Vector<int> pts:int = Update;
|
||||
updateRestoreMessages#d15de04d messages:Vector<int> 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<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> state:updates.State = updates.Difference;
|
||||
updates.differenceSlice#a8fb1981 new_messages:Vector<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> 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<Update> users:Vector<User> chats:Vector<Chat> date:int seq_start:int seq:int = Updates;
|
||||
updates#74ae4240 updates:Vector<Update> users:Vector<User> chats:Vector<Chat> date:int seq:int = Updates;
|
||||
|
||||
photos.photos#8dca6aa5 photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
photos.photosSlice#15051f54 count:int photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
|
||||
photos.photo#20212ca8 photo:Photo users:Vector<User> = 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<DcOption> 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<Message> chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessageLink#a9af2881 message:Message chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessage;
|
||||
|
||||
messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector<contacts.Link> = 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<Chat> users:Vector<User> seq:int = geochats.StatedMessage;
|
||||
|
||||
geochats.located#48feb267 results:Vector<ChatLocated> messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Located;
|
||||
|
||||
geochats.messages#d1526db1 messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Messages;
|
||||
geochats.messagesSlice#bc5863e8 count:int messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = 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<DcOption> = 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<long> 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<string> 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<WallPaper>;
|
||||
|
||||
users.getUsers#d91a548 id:Vector<InputUser> = Vector<User>;
|
||||
users.getFullUser#ca30a5b1 id:InputUser = UserFull;
|
||||
|
||||
contacts.getStatuses#c4a353ee = Vector<ContactStatus>;
|
||||
contacts.getContacts#22c6aa08 hash:string = contacts.Contacts;
|
||||
contacts.importContacts#da30b32d contacts:Vector<InputContact> 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<InputUser> = 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<int> = 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<int> = Vector<int>;
|
||||
messages.restoreMessages#395f9d7e id:Vector<int> = Vector<int>;
|
||||
messages.receivedMessages#28abcb68 max_id:int = Vector<int>;
|
||||
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<int> = messages.StatedMessages;
|
||||
messages.getChats#3c6aa187 id:Vector<int> = 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<InputUser> 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<InputAppEvent> = 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<InputUser> 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<long>;
|
||||
|
||||
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;
|
522
scheme15.tl
Normal file
522
scheme15.tl
Normal file
|
@ -0,0 +1,522 @@
|
|||
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<ChatParticipant> 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<int> = 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<PhotoSize> = 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<PhotoSize> 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<Contact> users:Vector<User> = contacts.Contacts;
|
||||
contacts.contactsNotModified#b74ba9d2 = contacts.Contacts;
|
||||
|
||||
contacts.importedContacts#ad524315 imported:Vector<ImportedContact> retry_contacts:Vector<long> users:Vector<User> = contacts.ImportedContacts;
|
||||
|
||||
contacts.blocked#1c138d15 blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
contacts.blockedSlice#900802a1 count:int blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
|
||||
contacts.found#0566000e results:Vector<ContactFound> users:Vector<User> = contacts.Found;
|
||||
|
||||
contacts.suggested#5649dcc5 results:Vector<ContactSuggested> users:Vector<User> = contacts.Suggested;
|
||||
|
||||
messages.dialogs#15ba6c40 dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
messages.dialogsSlice#71e094f3 count:int dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
|
||||
messages.messages#8c718e87 messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
messages.messagesSlice#0b446ae3 count:int messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
|
||||
messages.messageEmpty#3f4e0648 = messages.Message;
|
||||
messages.message#ff90c417 message:Message chats:Vector<Chat> users:Vector<User> = messages.Message;
|
||||
|
||||
messages.statedMessages#969478bb messages:Vector<Message> chats:Vector<Chat> users:Vector<User> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessage#d07ae726 message:Message chats:Vector<Chat> users:Vector<User> 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<User> = messages.Chat;
|
||||
|
||||
messages.chats#8150cbd8 chats:Vector<Chat> users:Vector<User> = messages.Chats;
|
||||
|
||||
messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector<Chat> users:Vector<User> = 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<int> pts:int = Update;
|
||||
updateDeleteMessages#a92bfe26 messages:Vector<int> pts:int = Update;
|
||||
updateRestoreMessages#d15de04d messages:Vector<int> 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<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> state:updates.State = updates.Difference;
|
||||
updates.differenceSlice#a8fb1981 new_messages:Vector<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> 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<Update> users:Vector<User> chats:Vector<Chat> date:int seq_start:int seq:int = Updates;
|
||||
updates#74ae4240 updates:Vector<Update> users:Vector<User> chats:Vector<Chat> date:int seq:int = Updates;
|
||||
|
||||
photos.photos#8dca6aa5 photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
photos.photosSlice#15051f54 count:int photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
|
||||
photos.photo#20212ca8 photo:Photo users:Vector<User> = 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<DcOption> 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<Message> chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessageLink#a9af2881 message:Message chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessage;
|
||||
|
||||
messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector<contacts.Link> = 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<Chat> users:Vector<User> seq:int = geochats.StatedMessage;
|
||||
|
||||
geochats.located#48feb267 results:Vector<ChatLocated> messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Located;
|
||||
|
||||
geochats.messages#d1526db1 messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Messages;
|
||||
geochats.messagesSlice#bc5863e8 count:int messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = 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<DcOption> = 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<long> = DecryptedMessageAction;
|
||||
decryptedMessageActionDeleteMessages#65614304 random_ids:Vector<long> = DecryptedMessageAction;
|
||||
decryptedMessageActionScreenshotMessages#8ac1f475 random_ids:Vector<long> = 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<long> 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<string> 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<WallPaper>;
|
||||
|
||||
users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User>;
|
||||
users.getFullUser#ca30a5b1 id:InputUser = UserFull;
|
||||
|
||||
contacts.getStatuses#c4a353ee = Vector<ContactStatus>;
|
||||
contacts.getContacts#22c6aa08 hash:string = contacts.Contacts;
|
||||
contacts.importContacts#da30b32d contacts:Vector<InputContact> 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<InputUser> = 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<int> = 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<int> = Vector<int>;
|
||||
messages.restoreMessages#395f9d7e id:Vector<int> = Vector<int>;
|
||||
messages.receivedMessages#28abcb68 max_id:int = Vector<int>;
|
||||
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<int> = messages.StatedMessages;
|
||||
messages.getChats#3c6aa187 id:Vector<int> = 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<InputUser> 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<InputAppEvent> = 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<InputUser> 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<long>;
|
||||
|
||||
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;
|
504
scheme16.tl
Normal file
504
scheme16.tl
Normal file
|
@ -0,0 +1,504 @@
|
|||
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<ChatParticipant> 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<int> = 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<PhotoSize> = 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<PhotoSize> 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<Contact> users:Vector<User> = contacts.Contacts;
|
||||
contacts.contactsNotModified#b74ba9d2 = contacts.Contacts;
|
||||
|
||||
contacts.importedContacts#ad524315 imported:Vector<ImportedContact> retry_contacts:Vector<long> users:Vector<User> = contacts.ImportedContacts;
|
||||
|
||||
contacts.blocked#1c138d15 blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
contacts.blockedSlice#900802a1 count:int blocked:Vector<ContactBlocked> users:Vector<User> = contacts.Blocked;
|
||||
|
||||
contacts.found#566000e results:Vector<ContactFound> users:Vector<User> = contacts.Found;
|
||||
|
||||
contacts.suggested#5649dcc5 results:Vector<ContactSuggested> users:Vector<User> = contacts.Suggested;
|
||||
|
||||
messages.dialogs#15ba6c40 dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
messages.dialogsSlice#71e094f3 count:int dialogs:Vector<Dialog> messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Dialogs;
|
||||
|
||||
messages.messages#8c718e87 messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
messages.messagesSlice#b446ae3 count:int messages:Vector<Message> chats:Vector<Chat> users:Vector<User> = messages.Messages;
|
||||
|
||||
messages.messageEmpty#3f4e0648 = messages.Message;
|
||||
messages.message#ff90c417 message:Message chats:Vector<Chat> users:Vector<User> = messages.Message;
|
||||
|
||||
messages.statedMessages#969478bb messages:Vector<Message> chats:Vector<Chat> users:Vector<User> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessage#d07ae726 message:Message chats:Vector<Chat> users:Vector<User> 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<User> = messages.Chat;
|
||||
|
||||
messages.chats#8150cbd8 chats:Vector<Chat> users:Vector<User> = messages.Chats;
|
||||
|
||||
messages.chatFull#e5d7d19c full_chat:ChatFull chats:Vector<Chat> users:Vector<User> = 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<int> pts:int = Update;
|
||||
updateDeleteMessages#a92bfe26 messages:Vector<int> pts:int = Update;
|
||||
updateRestoreMessages#d15de04d messages:Vector<int> 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<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> state:updates.State = updates.Difference;
|
||||
updates.differenceSlice#a8fb1981 new_messages:Vector<Message> new_encrypted_messages:Vector<EncryptedMessage> other_updates:Vector<Update> chats:Vector<Chat> users:Vector<User> 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<Update> users:Vector<User> chats:Vector<Chat> date:int seq_start:int seq:int = Updates;
|
||||
updates#74ae4240 updates:Vector<Update> users:Vector<User> chats:Vector<Chat> date:int seq:int = Updates;
|
||||
|
||||
photos.photos#8dca6aa5 photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
photos.photosSlice#15051f54 count:int photos:Vector<Photo> users:Vector<User> = photos.Photos;
|
||||
|
||||
photos.photo#20212ca8 photo:Photo users:Vector<User> = 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<DcOption> 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<Message> chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessages;
|
||||
|
||||
messages.statedMessageLink#a9af2881 message:Message chats:Vector<Chat> users:Vector<User> links:Vector<contacts.Link> pts:int seq:int = messages.StatedMessage;
|
||||
|
||||
messages.sentMessageLink#e9db4a3f id:int date:int pts:int seq:int links:Vector<contacts.Link> = 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<Chat> users:Vector<User> seq:int = geochats.StatedMessage;
|
||||
|
||||
geochats.located#48feb267 results:Vector<ChatLocated> messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Located;
|
||||
|
||||
geochats.messages#d1526db1 messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = geochats.Messages;
|
||||
geochats.messagesSlice#bc5863e8 count:int messages:Vector<GeoChatMessage> chats:Vector<Chat> users:Vector<User> = 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<DcOption> = 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<long> 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<string> 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<WallPaper>;
|
||||
|
||||
users.getUsers#d91a548 id:Vector<InputUser> = Vector<User>;
|
||||
users.getFullUser#ca30a5b1 id:InputUser = UserFull;
|
||||
|
||||
contacts.getStatuses#c4a353ee = Vector<ContactStatus>;
|
||||
contacts.getContacts#22c6aa08 hash:string = contacts.Contacts;
|
||||
contacts.importContacts#da30b32d contacts:Vector<InputContact> 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<InputUser> = 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<int>;
|
||||
contacts.importCard#4fe196fe export_card:Vector<int> = User;
|
||||
|
||||
messages.getMessages#4222fa74 id:Vector<int> = 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<int> = Vector<int>;
|
||||
messages.restoreMessages#395f9d7e id:Vector<int> = Vector<int>;
|
||||
messages.receivedMessages#28abcb68 max_id:int = Vector<int>;
|
||||
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<int> = messages.StatedMessages;
|
||||
messages.getChats#3c6aa187 id:Vector<int> = 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<InputUser> 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<InputAppEvent> = 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<InputUser> 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<long>;
|
||||
|
||||
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;
|
206
start-telegram-daemon
Executable file
206
start-telegram-daemon
Executable file
|
@ -0,0 +1,206 @@
|
|||
#!/usr/bin/perl -w
|
||||
|
||||
# start-engine
|
||||
# derived from start-memcached
|
||||
# 2003/2004 - Jay Bonci <jaybonci@debian.org>
|
||||
# This script handles the parsing of the /etc/memcached.conf file
|
||||
# and was originally created for the Debian distribution.
|
||||
# Anyone may use this little script under the same terms as
|
||||
# memcached itself.
|
||||
|
||||
# a bit changed it for telegram-daemon to generate config before start (Vitaly Valtman)
|
||||
|
||||
use POSIX qw(strftime);
|
||||
use strict;
|
||||
|
||||
my $id = defined($ARGV[0]) ? $ARGV[0] : '';
|
||||
my $idx = $id eq '' ? '' : " '$id'";
|
||||
my $idl = ($id =~ /^\.(.*)$/ ? "-$1" : $id);
|
||||
|
||||
my $root = "";
|
||||
|
||||
my $params; my $etchandle; my $etcfile = "$root/etc/telegram-daemon/telegram-daemon$id.conf";
|
||||
|
||||
# This script assumes that engine is located at /usr/bin/engine, and
|
||||
# that the pidfile is writable at /var/run/engine.pid
|
||||
|
||||
my $engine_pfx = "$root/usr/share/telegram-daemon/bin/";
|
||||
my $pidfile = "$root/var/run/telegram-daemon$id.pid";
|
||||
|
||||
# If we don't get a valid logfile parameter in the /etc/engine.conf file,
|
||||
# we'll just throw away all of our in-daemon output. We need to re-tie it so
|
||||
# that non-bash shells will not hang on logout. Thanks to Michael Renner for
|
||||
# the tip
|
||||
my $fd_reopened = "/dev/null";
|
||||
$fd_reopened = "$root/var/log/telegram-daemon/telegram-daemon$idl.log" if -d "$root/var/log/telegram-daemon/";
|
||||
|
||||
sub handle_logfile
|
||||
{
|
||||
my ($logfile) = @_;
|
||||
$logfile = "$root/var/log/telegram-daemon/$logfile" unless $logfile =~ /\//;
|
||||
$fd_reopened = $logfile;
|
||||
}
|
||||
|
||||
sub reopen_logfile
|
||||
{
|
||||
my ($logfile) = @_;
|
||||
|
||||
open *STDERR, ">>$logfile";
|
||||
open *STDOUT, ">>$logfile";
|
||||
open *STDIN, ">>/dev/null";
|
||||
chown 239, 239, $logfile;
|
||||
$fd_reopened = $logfile;
|
||||
}
|
||||
|
||||
sub adjust_arg
|
||||
{
|
||||
my ($arg) = @_;
|
||||
if ($arg =~ /^newest:(.*)$/) {
|
||||
my @L = split /:/, $1;
|
||||
my $x = $arg;
|
||||
my $xt = 0;
|
||||
for my $y (@L) {
|
||||
my @S = stat($y);
|
||||
if (scalar @S && $S[9] > $xt) {
|
||||
$x = $y;
|
||||
$xt = $S[9];
|
||||
}
|
||||
}
|
||||
return $x;
|
||||
}
|
||||
return $arg;
|
||||
}
|
||||
|
||||
# This is set up in place here to support other non -[a-z] directives
|
||||
|
||||
my $conf_directives = {
|
||||
"logfile" => \&handle_logfile,
|
||||
};
|
||||
|
||||
my %Vars = (
|
||||
"execute" => "msg-search-engine",
|
||||
"work_dir" => "$root/var/lib/telegram-daemon"
|
||||
);
|
||||
|
||||
my $have_c = 0;
|
||||
my $have_l = 0;
|
||||
my $have_u = 0;
|
||||
my $have_aes = 0;
|
||||
|
||||
if(open $etchandle, $etcfile)
|
||||
{
|
||||
foreach my $line (<$etchandle>)
|
||||
{
|
||||
$line ||= "";
|
||||
$line =~ s/\#.*//g;
|
||||
$line =~ s/\s+$//g;
|
||||
$line =~ s/^\s+//g;
|
||||
next unless $line;
|
||||
next if $line =~ /^\-[dh]/;
|
||||
|
||||
if($line =~ /^[^\-]/)
|
||||
{
|
||||
my ($directive, $int, $arg) = $line =~ /^(.*?)(\s+|\s*=\s*)(.*)/;
|
||||
next unless $directive;
|
||||
if (exists $conf_directives->{$directive}) {
|
||||
$conf_directives->{$directive}->($arg);
|
||||
} else {
|
||||
$Vars{$directive} = $arg;
|
||||
}
|
||||
next;
|
||||
}
|
||||
|
||||
$have_l = 1 if $line =~ /^-L\s/;
|
||||
$have_c = 1 if $line =~ /^-c\s/;
|
||||
$have_u = 1 if $line =~ /^-u\s/;
|
||||
push @$params, $line;
|
||||
}
|
||||
|
||||
}else{
|
||||
$params = [];
|
||||
}
|
||||
|
||||
push @$params, "-u telegramd" unless($have_u);
|
||||
push @$params, "-L $fd_reopened" unless($have_l);
|
||||
push @$params, "-c config$idl" unless($have_c);
|
||||
$params = join " ", @$params;
|
||||
|
||||
if(-e $pidfile)
|
||||
{
|
||||
open PIDHANDLE, "$pidfile";
|
||||
my $localpid = <PIDHANDLE>;
|
||||
close PIDHANDLE;
|
||||
|
||||
if ($localpid && $localpid =~ /(\d+)/) { $localpid = $1; } else { $localpid = -1; }
|
||||
if (-d "/proc/$localpid")
|
||||
{
|
||||
print STDERR "telegram-daemon$idl is already running.\n";
|
||||
exit;
|
||||
} else {
|
||||
print STDERR "removing stale $pidfile.\n";
|
||||
`rm -f $pidfile`;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (exists $Vars{'quit'}) {
|
||||
print STDERR "telegram-daemon$idl disabled\n";
|
||||
exit(0);
|
||||
}
|
||||
|
||||
my $engine = $engine_pfx.$Vars{'execute'};
|
||||
my $wdir = $Vars{'work_dir'};
|
||||
chdir $wdir if -d $wdir;
|
||||
|
||||
unless (-x $engine) {
|
||||
print STDERR "executable $engine not found\n";
|
||||
exit(1);
|
||||
}
|
||||
|
||||
unless (-d $wdir) {
|
||||
print STDERR "work directory $wdir not found\n";
|
||||
exit(1);
|
||||
}
|
||||
|
||||
for my $x ('s', 0 .. 9) {
|
||||
if (defined($Vars{"arg$x"})) {
|
||||
$params .= " ".adjust_arg($Vars{"arg$x"});
|
||||
}
|
||||
}
|
||||
|
||||
my $pid = fork();
|
||||
|
||||
|
||||
|
||||
if (!$pid) {
|
||||
reopen_logfile ($fd_reopened);
|
||||
chdir $wdir;
|
||||
open(my $fh, '>', "config$idl");
|
||||
|
||||
my $text = <<"END_MSG"
|
||||
config_directory="$wdir";
|
||||
test=false;
|
||||
msg_num=true;
|
||||
binlog_enabled=true;
|
||||
binlog="binlog$idl.bin";
|
||||
pfs_enabled=true;
|
||||
log_level = 0;
|
||||
lua_script="script$idl.lua";
|
||||
END_MSG
|
||||
;
|
||||
print $fh $text;
|
||||
close $fh;
|
||||
my $t;
|
||||
$t = strftime ("%Y-%m-%d %H:%M:%S %Z", localtime);
|
||||
print STDERR "[$t] invoking telegram-daemon$idl: $engine $params\n";
|
||||
exec "$engine $params";
|
||||
exit (0);
|
||||
} else {
|
||||
if (open PIDHANDLE,">$pidfile") {
|
||||
print PIDHANDLE $pid;
|
||||
close PIDHANDLE;
|
||||
} else {
|
||||
print STDERR "Can't write pidfile to $pidfile.\n";
|
||||
}
|
||||
}
|
||||
|
1754
structures.c
1754
structures.c
File diff suppressed because it is too large
Load diff
434
structures.h
434
structures.h
|
@ -1,413 +1,55 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __STRUCTURES_H__
|
||||
#define __STRUCTURES_H__
|
||||
|
||||
#include <assert.h>
|
||||
typedef struct { int type; int id; } peer_id_t;
|
||||
#include "tgl-layout.h"
|
||||
#include "tgl-fetch.h"
|
||||
|
||||
//#define FLAG_EMPTY 1
|
||||
#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
|
||||
|
||||
struct file_location {
|
||||
int dc;
|
||||
long long volume;
|
||||
int local_id;
|
||||
long long secret;
|
||||
};
|
||||
|
||||
struct photo_size {
|
||||
char *type;
|
||||
struct file_location loc;
|
||||
int w;
|
||||
int h;
|
||||
int size;
|
||||
char *data;
|
||||
};
|
||||
|
||||
struct geo {
|
||||
double longitude;
|
||||
double latitude;
|
||||
};
|
||||
|
||||
struct photo {
|
||||
long long id;
|
||||
long long access_hash;
|
||||
int user_id;
|
||||
int date;
|
||||
char *caption;
|
||||
struct geo geo;
|
||||
int sizes_num;
|
||||
struct photo_size *sizes;
|
||||
};
|
||||
|
||||
struct 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 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;
|
||||
};
|
||||
|
||||
struct 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;
|
||||
};
|
||||
|
||||
struct 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 encr_file {
|
||||
char *filename;
|
||||
unsigned char *key;
|
||||
unsigned char *iv;
|
||||
};
|
||||
char *tgls_default_create_print_name (tgl_peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4);
|
||||
|
||||
|
||||
struct user_status {
|
||||
int online;
|
||||
int when;
|
||||
};
|
||||
void tgls_free_user (struct tgl_user *U);
|
||||
void tgls_free_chat (struct tgl_chat *U);
|
||||
void tgls_free_photo (struct tgl_photo *P);
|
||||
void tgls_free_message (struct tgl_message *M);
|
||||
void tgls_clear_message (struct tgl_message *M);
|
||||
|
||||
struct user {
|
||||
peer_id_t id;
|
||||
int flags;
|
||||
struct message *last;
|
||||
char *print_name;
|
||||
int structure_version;
|
||||
struct file_location photo_big;
|
||||
struct file_location photo_small;
|
||||
long long photo_id;
|
||||
struct photo photo;
|
||||
char *first_name;
|
||||
char *last_name;
|
||||
char *phone;
|
||||
long long access_hash;
|
||||
struct user_status status;
|
||||
int blocked;
|
||||
char *real_first_name;
|
||||
char *real_last_name;
|
||||
};
|
||||
struct tgl_message *tglm_message_alloc (long long id);
|
||||
void tglm_message_insert_tree (struct tgl_message *M);
|
||||
void tglm_update_message_id (struct tgl_message *M, long long id);
|
||||
void tglm_message_insert (struct tgl_message *M);
|
||||
void tglm_message_insert_unsent (struct tgl_message *M);
|
||||
void tglm_message_remove_unsent (struct tgl_message *M);
|
||||
void tglm_send_all_unsent (void);
|
||||
void tglm_message_remove_tree (struct tgl_message *M);
|
||||
void tglm_message_add_peer (struct tgl_message *M);
|
||||
void tglm_message_del_peer (struct tgl_message *M);
|
||||
void tglm_message_del_use (struct tgl_message *M);
|
||||
void tglm_message_add_use (struct tgl_message *M);
|
||||
|
||||
struct chat_user {
|
||||
int user_id;
|
||||
int inviter_id;
|
||||
int date;
|
||||
};
|
||||
|
||||
struct chat {
|
||||
peer_id_t id;
|
||||
int flags;
|
||||
struct message *last;
|
||||
char *print_title;
|
||||
int structure_version;
|
||||
struct file_location photo_big;
|
||||
struct file_location photo_small;
|
||||
struct photo photo;
|
||||
char *title;
|
||||
int users_num;
|
||||
int user_list_size;
|
||||
int user_list_version;
|
||||
struct chat_user *user_list;
|
||||
int date;
|
||||
int version;
|
||||
int admin_id;
|
||||
};
|
||||
|
||||
enum secret_chat_state {
|
||||
sc_none,
|
||||
sc_waiting,
|
||||
sc_request,
|
||||
sc_ok,
|
||||
sc_deleted
|
||||
};
|
||||
|
||||
struct secret_chat {
|
||||
peer_id_t id;
|
||||
int flags;
|
||||
struct message *last;
|
||||
char *print_name;
|
||||
int structure_version;
|
||||
struct file_location photo_big;
|
||||
struct file_location photo_small;
|
||||
struct photo photo;
|
||||
int user_id;
|
||||
int admin_id;
|
||||
int date;
|
||||
int ttl;
|
||||
long long access_hash;
|
||||
unsigned char *g_key;
|
||||
unsigned char *nonce;
|
||||
|
||||
enum secret_chat_state state;
|
||||
int key[64];
|
||||
long long key_fingerprint;
|
||||
};
|
||||
|
||||
typedef union peer {
|
||||
struct {
|
||||
peer_id_t id;
|
||||
int flags;
|
||||
struct message *last;
|
||||
char *print_name;
|
||||
int structure_version;
|
||||
struct file_location photo_big;
|
||||
struct file_location photo_small;
|
||||
struct photo photo;
|
||||
};
|
||||
struct user user;
|
||||
struct chat chat;
|
||||
struct secret_chat encr_chat;
|
||||
} peer_t;
|
||||
|
||||
struct video {
|
||||
long long id;
|
||||
long long access_hash;
|
||||
int user_id;
|
||||
int date;
|
||||
int size;
|
||||
int dc_id;
|
||||
struct photo_size thumb;
|
||||
char *caption;
|
||||
int duration;
|
||||
int w;
|
||||
int h;
|
||||
};
|
||||
|
||||
struct audio {
|
||||
long long id;
|
||||
long long access_hash;
|
||||
int user_id;
|
||||
int date;
|
||||
int size;
|
||||
int dc_id;
|
||||
int duration;
|
||||
};
|
||||
|
||||
struct document {
|
||||
long long id;
|
||||
long long access_hash;
|
||||
int user_id;
|
||||
int date;
|
||||
int size;
|
||||
int dc_id;
|
||||
struct photo_size thumb;
|
||||
char *caption;
|
||||
char *mime_type;
|
||||
};
|
||||
|
||||
struct message_action {
|
||||
unsigned type;
|
||||
union {
|
||||
struct {
|
||||
char *title;
|
||||
int user_num;
|
||||
int *users;
|
||||
};
|
||||
char *new_title;
|
||||
struct photo photo;
|
||||
int user;
|
||||
int ttl;
|
||||
};
|
||||
};
|
||||
|
||||
struct message_media {
|
||||
unsigned type;
|
||||
union {
|
||||
struct photo photo;
|
||||
struct video video;
|
||||
struct audio audio;
|
||||
struct document document;
|
||||
struct geo geo;
|
||||
struct {
|
||||
char *phone;
|
||||
char *first_name;
|
||||
char *last_name;
|
||||
int user_id;
|
||||
};
|
||||
struct encr_photo encr_photo;
|
||||
struct encr_video encr_video;
|
||||
struct encr_audio encr_audio;
|
||||
struct encr_document encr_document;
|
||||
struct encr_file encr_file;
|
||||
struct {
|
||||
void *data;
|
||||
int data_size;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
struct message {
|
||||
struct message *next_use, *prev_use;
|
||||
struct message *next, *prev;
|
||||
long long id;
|
||||
int flags;
|
||||
peer_id_t fwd_from_id;
|
||||
int fwd_date;
|
||||
peer_id_t from_id;
|
||||
peer_id_t to_id;
|
||||
int out;
|
||||
int unread;
|
||||
int date;
|
||||
int service;
|
||||
union {
|
||||
struct message_action action;
|
||||
struct {
|
||||
char *message;
|
||||
int message_len;
|
||||
struct message_media media;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
int fetch_file_location (struct file_location *loc);
|
||||
int fetch_user_status (struct user_status *S);
|
||||
int fetch_user (struct user *U);
|
||||
struct user *fetch_alloc_user (void);
|
||||
struct user *fetch_alloc_user_full (void);
|
||||
struct chat *fetch_alloc_chat (void);
|
||||
struct chat *fetch_alloc_chat_full (void);
|
||||
struct secret_chat *fetch_alloc_encrypted_chat (void);
|
||||
struct message *fetch_alloc_message (void);
|
||||
struct message *fetch_alloc_geo_message (void);
|
||||
struct message *fetch_alloc_message_short (void);
|
||||
struct message *fetch_alloc_message_short_chat (void);
|
||||
struct message *fetch_alloc_encrypted_message (void);
|
||||
void fetch_encrypted_message_file (struct message_media *M);
|
||||
void fetch_skip_encrypted_message_file (void);
|
||||
void fetch_encrypted_message_file (struct message_media *M);
|
||||
void fetch_message_action_encrypted (struct message_action *M);
|
||||
peer_id_t fetch_peer_id (void);
|
||||
|
||||
void fetch_message_media (struct message_media *M);
|
||||
void fetch_message_media_encrypted (struct message_media *M);
|
||||
void fetch_message_action (struct message_action *M);
|
||||
void message_insert_tree (struct message *M);
|
||||
|
||||
void free_user (struct user *U);
|
||||
void free_chat (struct chat *U);
|
||||
|
||||
char *create_print_name (peer_id_t id, const char *a1, const char *a2, const char *a3, const char *a4);
|
||||
|
||||
int print_stat (char *s, int len);
|
||||
peer_t *user_chat_get (peer_id_t id);
|
||||
struct message *message_get (long long id);
|
||||
void update_message_id (struct message *M, long long id);
|
||||
void message_insert (struct message *M);
|
||||
void free_photo (struct photo *P);
|
||||
void fetch_photo (struct photo *P);
|
||||
void insert_encrypted_chat (peer_t *P);
|
||||
void insert_user (peer_t *P);
|
||||
void insert_chat (peer_t *P);
|
||||
void fetch_photo (struct photo *P);
|
||||
void free_photo (struct photo *P);
|
||||
void message_insert_unsent (struct message *M);
|
||||
void message_remove_unsent (struct message *M);
|
||||
void send_all_unsent (void);
|
||||
void message_remove_tree (struct message *M);
|
||||
void message_add_peer (struct message *M);
|
||||
void message_del_peer (struct message *M);
|
||||
void free_message (struct message *M);
|
||||
void message_del_use (struct message *M);
|
||||
void peer_insert_name (peer_t *P);
|
||||
void peer_delete_name (peer_t *P);
|
||||
peer_t *peer_lookup_name (const char *s);
|
||||
|
||||
#define PEER_USER 1
|
||||
#define PEER_CHAT 2
|
||||
#define PEER_GEO_CHAT 3
|
||||
#define PEER_ENCR_CHAT 4
|
||||
#define PEER_UNKNOWN 0
|
||||
|
||||
#define MK_USER(id) set_peer_id (PEER_USER,id)
|
||||
#define MK_CHAT(id) set_peer_id (PEER_CHAT,id)
|
||||
#define MK_GEO_CHAT(id) set_peer_id (PEER_GEO_CHAT,id)
|
||||
#define MK_ENCR_CHAT(id) set_peer_id (PEER_ENCR_CHAT,id)
|
||||
|
||||
static inline int get_peer_type (peer_id_t id) {
|
||||
return id.type;
|
||||
}
|
||||
|
||||
static inline int get_peer_id (peer_id_t id) {
|
||||
return id.id;
|
||||
}
|
||||
|
||||
static inline peer_id_t set_peer_id (int type, int id) {
|
||||
peer_id_t ID;
|
||||
ID.id = id;
|
||||
ID.type = type;
|
||||
return ID;
|
||||
}
|
||||
|
||||
static inline int cmp_peer_id (peer_id_t a, peer_id_t b) {
|
||||
return memcmp (&a, &b, sizeof (a));
|
||||
}
|
||||
void tglp_peer_insert_name (tgl_peer_t *P);
|
||||
void tglp_peer_delete_name (tgl_peer_t *P);
|
||||
void tglp_insert_encrypted_chat (tgl_peer_t *P);
|
||||
void tglp_insert_user (tgl_peer_t *P);
|
||||
void tglp_insert_chat (tgl_peer_t *P);
|
||||
|
||||
#endif
|
||||
|
|
332
telegram-daemon
Executable file
332
telegram-daemon
Executable file
|
@ -0,0 +1,332 @@
|
|||
#!/bin/bash
|
||||
|
||||
### BEGIN INIT INFO
|
||||
# Provides: engine
|
||||
# Required-Start: $local_fs $syslog
|
||||
# Required-Stop: $local_fs $syslog
|
||||
# Default-Start: 2 3 4 5
|
||||
# Default-Stop: 0 1 6
|
||||
# Short-Description: KittenDB Meta Engine
|
||||
### END INIT INFO
|
||||
|
||||
#
|
||||
# run script for KittenDB Engine
|
||||
# author: kot
|
||||
# author: burunduk
|
||||
# author: burunduk
|
||||
#
|
||||
# Version: 2013-06-06
|
||||
#
|
||||
|
||||
# Features added:
|
||||
# -- flock to avoid parallel execution
|
||||
# -- checks to avoid creating empty engine configuration files
|
||||
|
||||
|
||||
# a bit changed it for telegram-daemon to use different folders
|
||||
# and to have posiiblilities to have fake root
|
||||
# Vitaly Valtman
|
||||
|
||||
ROOT=""
|
||||
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
|
||||
DAEMONDIR=$ROOT/usr/share/telegram-daemon/bin
|
||||
DAEMONBOOTSTRAP=$ROOT/usr/share/telegram-daemon/bin/start-telegram-daemon
|
||||
NAME=telegram-daemon
|
||||
DESC="KOT's meta engine"
|
||||
PIDFILE=$ROOT/var/run/$NAME
|
||||
LOCKFILE=$ROOT/var/lock/$NAME
|
||||
CONFFILE=$ROOT/etc/telegram-daemon/$NAME
|
||||
LOCK_WAIT=5
|
||||
STOP_TIMEOUT=5
|
||||
KILL_TIMEOUT=5
|
||||
|
||||
test -x $DAEMONDIR || exit 0
|
||||
test -x $DAEMONBOOTSTRAP || exit 0
|
||||
|
||||
set -e
|
||||
|
||||
## Utilitary functions
|
||||
|
||||
# Send information to stderr
|
||||
function echo_stderr() {
|
||||
echo "$*" 1>&2
|
||||
}
|
||||
|
||||
# Get engine status. Returns 0 on running engine, 1 otherwise.
|
||||
function engine_status() {
|
||||
local id="$1"
|
||||
local pif="$PIDFILE.$id.pid"
|
||||
if ! [ -f "$pif" ] ; then
|
||||
echo "stopped"
|
||||
return 1
|
||||
fi
|
||||
local pid="$(<$pif)"
|
||||
if [ -z "$pid" ]; then
|
||||
echo "corrupt pid file"
|
||||
return 1
|
||||
fi
|
||||
if [ -d "/proc/$pid/" ]; then
|
||||
echo "$pid"
|
||||
return 0
|
||||
else
|
||||
echo "failed (pid $pid)"
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
# Start engine. Usage: engine_start <eid>
|
||||
function engine_start() {
|
||||
local eid="$1"
|
||||
local r=''
|
||||
local pid=''
|
||||
pid="$(engine_status "$eid")" && r='ok' || r='fail'
|
||||
if [ "$r" == 'ok' ] ; then
|
||||
echo_stderr "telegram-daemon-$eid: already running ($pid)"
|
||||
else
|
||||
start-stop-daemon --start --quiet --exec $DAEMONBOOTSTRAP -- .$eid 100> /dev/null
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# Stop engine. Usage: engine_stop <eid>
|
||||
function engine_stop() {
|
||||
local eid="$1"
|
||||
local r=''
|
||||
local status="$(engine_status "$eid")" && r='ok' || r='fail'
|
||||
local pif="$PIDFILE.$eid.pid"
|
||||
if [ "$r" == 'ok' ] ; then
|
||||
start-stop-daemon --stop --quiet --oknodo --pidfile "$pif"
|
||||
local ti=0
|
||||
while [ $ti -lt $((10 * $STOP_TIMEOUT)) ] ; do
|
||||
status="$(engine_status "$eid")" && r='ok' || r='fail'
|
||||
if [ "$r" == 'fail' ]; then
|
||||
break
|
||||
fi
|
||||
sleep 0.1
|
||||
ti=$(($ti + 1))
|
||||
done
|
||||
if [ "$r" == 'ok' ] ; then
|
||||
echo_stderr "telegram-daemon-$eid: not stopped, sending SIGKILL..."
|
||||
start-stop-daemon --stop --quiet --oknodo --pidfile "$pif" --signal KILL
|
||||
ti=0
|
||||
while [ $ti -lt $((10 * $KILL_TIMEOUT)) ] ; do
|
||||
status="$(engine_status "$eid")" && r='ok' || r='fail'
|
||||
if [ "$r" == 'fail' ]; then
|
||||
break
|
||||
fi
|
||||
sleep 0.1
|
||||
ti=$(($ti + 1))
|
||||
done
|
||||
fi
|
||||
if [ "$r" == 'ok' ] ; then
|
||||
echo_stderr "telegram-daemon-$eid: not stopped with SIGKILL, giving up"
|
||||
return 1
|
||||
else
|
||||
if [ -f "$pif" ] ; then
|
||||
rm "$pif"
|
||||
fi
|
||||
echo "telegram-daemon-$eid: stopped"
|
||||
fi
|
||||
else
|
||||
echo_stderr "telegram-daemon-$eid: not running: $status"
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# usage: engine_disable <id>
|
||||
function engine_disable() {
|
||||
local eid="$1"
|
||||
local conf="$CONFFILE.$eid.conf"
|
||||
[ -e "$conf" ] || return 1 # work only with existing engines
|
||||
if grep -E '^quit 1$' "$conf" > /dev/null ; then
|
||||
echo_stderr "telegram-daemon-$eid: already disabled"
|
||||
else
|
||||
echo 'quit 1' >> "$conf"
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# usage: engine_enable <id>
|
||||
function engine_enable() {
|
||||
local eid="$1"
|
||||
local conf="$CONFFILE.$eid.conf"
|
||||
[ -e "$conf" ] || return 1 # work only with existing engines
|
||||
if ! grep -E '^quit' "$conf" > /dev/null ; then
|
||||
echo_stderr "telegram-daemon-$eid: already enabled"
|
||||
else
|
||||
sed -i~ -e '/^quit/d' -- "$conf"
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# Wait for engine's command to be completed
|
||||
function engine_wait() {
|
||||
local eid="$1"
|
||||
(
|
||||
flock -x -w $(($LOCK_WAIT + $STOP_TIMEOUT + $KILL_TIMEOUT)) 100 || exit 1
|
||||
) 100> $LOCKFILE.$eid.lock || echo "Unable to wait for $eid"
|
||||
return 0
|
||||
}
|
||||
|
||||
# Run a single command
|
||||
# Only one instance of this command per engine is supposed to work
|
||||
function run_one() {
|
||||
local eid="$1"
|
||||
shift
|
||||
local command="$*"
|
||||
[ "${#eid}" -gt 5 ] && return 0 # avoid long engine ids
|
||||
(
|
||||
flock -x -w $LOCK_WAIT 100 || exit 1
|
||||
$command "$eid"
|
||||
) 100> $LOCKFILE.$eid.lock
|
||||
return 0
|
||||
}
|
||||
|
||||
# Run commands
|
||||
function run() {
|
||||
local mode="$1"
|
||||
shift
|
||||
local command="$*"
|
||||
local eid=''
|
||||
if [ "$mode" == 'parallel' ] ; then
|
||||
for eid in $arguments ; do
|
||||
run_one "$eid" "$command" &
|
||||
done
|
||||
sleep 0.1
|
||||
for eid in $arguments ; do
|
||||
engine_wait "$eid"
|
||||
done
|
||||
else
|
||||
for eid in $arguments ; do
|
||||
run_one "$eid" "$command"
|
||||
done
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# Get all actual engine ids
|
||||
function arguments_all() {
|
||||
local file=''
|
||||
local id=''
|
||||
local list=''
|
||||
for file in $(ls $CONFFILE.?*.conf 2> /dev/null) ; do
|
||||
id=${file#$CONFFILE.}
|
||||
id=${id%.conf}
|
||||
list="$list $id"
|
||||
done
|
||||
for file in $(ls $PIDFILE.?*.pid 2> /dev/null) ; do
|
||||
id=${file#$PIDFILE.}
|
||||
id=${id%.pid}
|
||||
list="$list $id"
|
||||
done
|
||||
local f=''
|
||||
for f in $list ; do echo "$f" ; done | sort -u
|
||||
return 0
|
||||
}
|
||||
|
||||
## Commands
|
||||
|
||||
# Start engine.
|
||||
function engine_command_start() {
|
||||
local eid="$1"
|
||||
engine_start "$eid"
|
||||
}
|
||||
|
||||
# Stop engine.
|
||||
function engine_command_stop() {
|
||||
local eid="$1"
|
||||
engine_stop "$eid"
|
||||
}
|
||||
|
||||
# Enable engine.
|
||||
function engine_command_enable() {
|
||||
local eid="$1"
|
||||
engine_enable "$eid"
|
||||
engine_start "$eid"
|
||||
}
|
||||
|
||||
# Disable engine.
|
||||
function engine_command_disable() {
|
||||
local eid="$1"
|
||||
engine_disable "$eid"
|
||||
engine_stop "$eid"
|
||||
}
|
||||
|
||||
# Restart engine.
|
||||
function engine_command_restart() {
|
||||
local eid="$1"
|
||||
engine_stop "$eid"
|
||||
echo "restarting telegram-daemon-$eid..."
|
||||
engine_start "$eid"
|
||||
}
|
||||
|
||||
# Send signal to engine. Usage: engine_command_signal <signal> <id>
|
||||
function engine_command_signal() {
|
||||
local id="$2"
|
||||
local signal="$1"
|
||||
local r=''
|
||||
local comment="$(engine_status "$id")" && r='ok' || r='fail'
|
||||
local res=''
|
||||
if [ "$r" == 'ok' ]; then
|
||||
start-stop-daemon --stop --quiet --oknodo --pidfile $PIDFILE.$id.pid --signal "$signal"
|
||||
else
|
||||
echo_stderr "telegram-daemon-$id: not running: $comment"
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# Get engine status
|
||||
function engine_command_status() {
|
||||
local id="$1"
|
||||
local res="telegram-daemon-$id: "
|
||||
local r=''
|
||||
local pid=''
|
||||
pid="$(engine_status "$id")" && r='ok' || r='fail'
|
||||
if [ "$r" == 'ok' ]; then
|
||||
res="$res $(COLUMNS=10000 ps -o pid,c,stime,time,cmd --no-header --pid $pid | sed -e 's/\/usr\/share\/telegram-daemon\/bin\///')"
|
||||
else
|
||||
res="$res $pid"
|
||||
fi
|
||||
echo "$res"
|
||||
return 0
|
||||
}
|
||||
|
||||
## Entry point
|
||||
|
||||
command="$1"
|
||||
shift
|
||||
|
||||
arguments="$*"
|
||||
if [ -z "$arguments" ] ; then
|
||||
if [ "$command" == "status" -o "$command" == "start" -o "$command" == "rotate-logs" -o "$command" == "stop" ] ; then
|
||||
arguments="$(arguments_all)"
|
||||
fi
|
||||
elif [ "$arguments" == "all" ] ; then
|
||||
arguments="$(arguments_all)"
|
||||
fi
|
||||
if [ -z "$arguments" ] ; then
|
||||
echo "nothing to do"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
case "$command" in
|
||||
('disable') run parallel engine_command_disable ;;
|
||||
('enable') run parallel engine_command_enable ;;
|
||||
#
|
||||
('start') run parallel engine_command_start ;;
|
||||
('status') run normal engine_command_status ;;
|
||||
('stop') run parallel engine_command_stop ;;
|
||||
#
|
||||
('rotate-logs') run parallel engine_command_signal USR1 ;;
|
||||
#
|
||||
('restart'|'force-reload') run parallel engine_command_restart ;;
|
||||
(*)
|
||||
N=/etc/init.d/$NAME
|
||||
echo "Usage: $N {start|stop|restart|rotate-logs|status} [<ids...>|all]" >&2
|
||||
echo " additional commands: disable <ids...>, enable <ids...>, reindex <ids...> (use with caution)" >&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
|
||||
exit 0
|
||||
|
14
telegram.h
14
telegram.h
|
@ -1,24 +1,22 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
This file is part of telegram-cli.
|
||||
|
||||
Telegram-client is free software: you can redistribute it and/or modify
|
||||
Telegram-cli 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,
|
||||
Telegram-cli 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 <http://www.gnu.org/licenses/>.
|
||||
along with this telegram-cli. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Copyright Vitaly Valtman 2013
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#define MAX_DC_NUM 9
|
||||
#define MAX_PEER_NUM 100000
|
||||
|
||||
#ifndef PROG_NAME
|
||||
#define PROG_NAME "telegram"
|
||||
#define PROG_NAME "telegram-cli"
|
||||
#endif
|
||||
|
|
57
test.lua
57
test.lua
|
@ -40,7 +40,34 @@ end
|
|||
|
||||
print ("HI, this is lua script")
|
||||
|
||||
function ok_cb(extra, success, result)
|
||||
end
|
||||
|
||||
-- Notification code {{{
|
||||
|
||||
function get_title (P, Q)
|
||||
if (Q.type == 'user') then
|
||||
return P.first_name .. " " .. P.last_name
|
||||
elseif (Q.type == 'chat') then
|
||||
return Q.title
|
||||
elseif (Q.type == 'encr_chat') then
|
||||
return 'Secret chat with ' .. P.first_name .. ' ' .. P.last_name
|
||||
else
|
||||
return ''
|
||||
end
|
||||
end
|
||||
|
||||
local lgi = require ('lgi')
|
||||
local notify = lgi.require('Notify')
|
||||
notify.init ("Telegram updates")
|
||||
local icon = os.getenv("HOME") .. "/.telegram-cli/telegram-pics/telegram_64.png"
|
||||
|
||||
function do_notify (user, msg)
|
||||
local n = notify.Notification.new(user, msg, icon)
|
||||
n:show ()
|
||||
end
|
||||
|
||||
-- }}}
|
||||
|
||||
function on_msg_receive (msg)
|
||||
if started == 0 then
|
||||
|
@ -49,13 +76,13 @@ function on_msg_receive (msg)
|
|||
if msg.out then
|
||||
return
|
||||
end
|
||||
do_notify (get_title (msg.from, msg.to), msg.text)
|
||||
|
||||
if (msg.text == 'ping') then
|
||||
if (msg.to.id == our_id) then
|
||||
print ('sending pong to ' .. tostring (msg.from.print_name))
|
||||
send_msg (msg.from.print_name, 'pong')
|
||||
send_msg (msg.from.print_name, 'pong', ok_cb, false)
|
||||
else
|
||||
print ('sending pong to ' .. tostring (msg.to.print_name))
|
||||
send_msg (msg.to.print_name, 'pong')
|
||||
send_msg (msg.to.print_name, 'pong', ok_cb, false)
|
||||
end
|
||||
return
|
||||
end
|
||||
|
@ -67,29 +94,33 @@ function on_msg_receive (msg)
|
|||
end
|
||||
return
|
||||
end
|
||||
--vardump (msg)
|
||||
--print ( "Message # " .. msg.id .. " (flags " .. msg.flags .. ")")
|
||||
end
|
||||
|
||||
function on_our_id (id)
|
||||
our_id = id
|
||||
end
|
||||
|
||||
function on_secret_chat_created (peer)
|
||||
--vardump (peer)
|
||||
end
|
||||
|
||||
function on_user_update (user)
|
||||
function on_user_update (user, what)
|
||||
--vardump (user)
|
||||
end
|
||||
|
||||
function on_chat_update (user)
|
||||
--vardump (user)
|
||||
function on_chat_update (chat, what)
|
||||
--vardump (chat)
|
||||
end
|
||||
|
||||
function on_secret_chat_update (schat, what)
|
||||
--vardump (schat)
|
||||
end
|
||||
|
||||
function on_get_difference_end ()
|
||||
end
|
||||
|
||||
function cron()
|
||||
-- do something
|
||||
postpone (cron, false, 1.0)
|
||||
end
|
||||
|
||||
function on_binlog_replay_end ()
|
||||
started = 1
|
||||
postpone (cron, false, 1.0)
|
||||
end
|
||||
|
|
53
tgl-fetch.h
Normal file
53
tgl-fetch.h
Normal file
|
@ -0,0 +1,53 @@
|
|||
/*
|
||||
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__
|
||||
|
||||
int tglf_fetch_file_location (struct tgl_file_location *loc);
|
||||
int tglf_fetch_user_status (struct tgl_user_status *S);
|
||||
int tglf_fetch_user (struct tgl_user *U);
|
||||
struct tgl_user *tglf_fetch_alloc_user (void);
|
||||
struct tgl_user *tglf_fetch_alloc_user_full (void);
|
||||
struct tgl_chat *tglf_fetch_alloc_chat (void);
|
||||
struct tgl_chat *tglf_fetch_alloc_chat_full (void);
|
||||
struct tgl_secret_chat *tglf_fetch_alloc_encrypted_chat (void);
|
||||
struct tgl_message *tglf_fetch_alloc_message (void);
|
||||
struct tgl_message *tglf_fetch_alloc_geo_message (void);
|
||||
struct tgl_message *tglf_fetch_alloc_message_short (void);
|
||||
struct tgl_message *tglf_fetch_alloc_message_short_chat (void);
|
||||
struct tgl_message *tglf_fetch_alloc_encrypted_message (void);
|
||||
void tglf_fetch_encrypted_message_file (struct tgl_message_media *M);
|
||||
tgl_peer_id_t tglf_fetch_peer_id (void);
|
||||
|
||||
void tglf_fetch_message_media (struct tgl_message_media *M);
|
||||
void tglf_fetch_message_media_encrypted (struct tgl_message_media *M);
|
||||
void tglf_fetch_message_action (struct tgl_message_action *M);
|
||||
void tglf_fetch_message_action_encrypted (struct tgl_message_action *M);
|
||||
void tglf_fetch_photo (struct tgl_photo *P);
|
||||
|
||||
void tglf_fetch_chat (struct tgl_chat *C);
|
||||
void tglf_fetch_chat_full (struct tgl_chat *C);
|
||||
|
||||
void tglf_fetch_audio (struct tgl_audio *V);
|
||||
void tglf_fetch_video (struct tgl_video *V);
|
||||
void tglf_fetch_document (struct tgl_document *V);
|
||||
void tglf_fetch_message (struct tgl_message *M);
|
||||
void tglf_fetch_geo_message (struct tgl_message *M);
|
||||
#endif
|
31
tgl-inner.h
Normal file
31
tgl-inner.h
Normal file
|
@ -0,0 +1,31 @@
|
|||
/*
|
||||
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 (tgl_state.verbosity >= verbosity_level) { \
|
||||
tgl_state.callback.logprintf (__VA_ARGS__); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#endif
|
422
tgl-layout.h
Normal file
422
tgl-layout.h
Normal file
|
@ -0,0 +1,422 @@
|
|||
/*
|
||||
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 event *ev;
|
||||
//struct event_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 event *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_notify_layer
|
||||
};
|
||||
|
||||
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_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;
|
||||
};
|
||||
|
||||
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;
|
||||
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;
|
||||
};
|
||||
};
|
||||
|
||||
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
|
93
tgl.c
Normal file
93
tgl.c
Normal file
|
@ -0,0 +1,93 @@
|
|||
/*
|
||||
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"
|
||||
|
||||
#ifdef EVENT_V2
|
||||
#include <event2/event.h>
|
||||
#else
|
||||
#include <event.h>
|
||||
#include "event-old.h"
|
||||
#endif
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
struct tgl_state tgl_state;
|
||||
|
||||
|
||||
void tgl_set_binlog_mode (int mode) {
|
||||
tgl_state.binlog_enabled = mode;
|
||||
}
|
||||
|
||||
void tgl_set_binlog_path (const char *path) {
|
||||
tgl_state.binlog_name = tstrdup (path);
|
||||
}
|
||||
|
||||
void tgl_set_auth_file_path (const char *path) {
|
||||
tgl_state.auth_file = tstrdup (path);
|
||||
}
|
||||
|
||||
void tgl_set_download_directory (const char *path) {
|
||||
tgl_state.downloads_directory = tstrdup (path);
|
||||
}
|
||||
|
||||
void tgl_set_callback (struct tgl_update_callback *cb) {
|
||||
tgl_state.callback = *cb;
|
||||
}
|
||||
|
||||
void tgl_set_rsa_key (const char *key) {
|
||||
assert (tgl_state.rsa_key_num < TGL_MAX_RSA_KEYS_NUM);
|
||||
tgl_state.rsa_key_list[tgl_state.rsa_key_num ++] = tstrdup (key);
|
||||
}
|
||||
|
||||
void tgl_init (void) {
|
||||
tgl_state.ev_base = event_base_new ();
|
||||
|
||||
if (!tgl_state.net_methods) {
|
||||
tgl_state.net_methods = &tgl_conn_methods;
|
||||
}
|
||||
if (!tgl_state.callback.create_print_name) {
|
||||
tgl_state.callback.create_print_name = tgls_default_create_print_name;
|
||||
}
|
||||
if (!tgl_state.temp_key_expire_time) {
|
||||
tgl_state.temp_key_expire_time = 100000;
|
||||
}
|
||||
|
||||
tglmp_on_start ();
|
||||
}
|
||||
|
||||
int tgl_authorized_dc (struct tgl_dc *DC) {
|
||||
assert (DC);
|
||||
return (DC->flags & 4) != 0;//DC->auth_key_id;
|
||||
}
|
||||
|
||||
int tgl_signed_dc (struct tgl_dc *DC) {
|
||||
assert (DC);
|
||||
return DC->has_auth;
|
||||
}
|
||||
|
330
tgl.h
Normal file
330
tgl.h
Normal file
|
@ -0,0 +1,330 @@
|
|||
/*
|
||||
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 <tgl-layout.h>
|
||||
#include <string.h>
|
||||
|
||||
#define TGL_MAX_DC_NUM 100
|
||||
#define TG_SERVER "149.154.167.50"
|
||||
#define TG_SERVER_TEST "149.154.167.40"
|
||||
#define TG_SERVER_DC 2
|
||||
#define TG_SERVER_TEST_DC 2
|
||||
|
||||
// JUST RANDOM STRING
|
||||
#define TGL_BUILD "2014"
|
||||
#define TGL_VERSION "1.0.5"
|
||||
|
||||
#define TGL_ENCRYPTED_LAYER 16
|
||||
|
||||
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
|
||||
|
||||
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_update_callback {
|
||||
void (*new_msg)(struct tgl_message *M);
|
||||
void (*marked_read)(int num, struct tgl_message *list[]);
|
||||
void (*logprintf)(const char *format, ...) __attribute__ ((format (printf, 1, 2)));
|
||||
void (*type_notification)(struct tgl_user *U);
|
||||
void (*type_in_chat_notification)(struct tgl_user *U, struct tgl_chat *C);
|
||||
void (*type_in_secret_chat_notification)(struct tgl_secret_chat *E);
|
||||
void (*status_notification)(struct tgl_user *U);
|
||||
void (*user_registered)(struct tgl_user *U);
|
||||
void (*user_activated)(struct tgl_user *U);
|
||||
void (*new_authorization)(const char *device, const char *location);
|
||||
//void (*secret_chat_created)(struct tgl_secret_chat *E);
|
||||
//void (*secret_chat_request)(struct tgl_secret_chat *E);
|
||||
//void (*secret_chat_established)(struct tgl_secret_chat *E);
|
||||
//void (*secret_chat_deleted)(struct tgl_secret_chat *E);
|
||||
//void (*secret_chat_accepted)(struct tgl_secret_chat *E);
|
||||
//void (*new_user)(struct tgl_user *U);
|
||||
//void (*delete_user)(struct tgl_user *U);
|
||||
//void (*update_user_info)(struct tgl_user *U);
|
||||
//void (*secret_chat_delete)(struct tgl_secret_chat *U);
|
||||
//void (*secret_chat_requested)(struct tgl_secret_chat *U);
|
||||
//void (*secret_chat_accepted)(struct tgl_secret_chat *U);
|
||||
//void (*secret_chat_created)(struct tgl_secret_chat *U);
|
||||
void (*chat_update)(struct tgl_chat *C, unsigned flags);
|
||||
void (*user_update)(struct tgl_user *C, unsigned flags);
|
||||
void (*secret_chat_update)(struct tgl_secret_chat *C, unsigned flags);
|
||||
void (*msg_receive)(struct tgl_message *M);
|
||||
void (*our_id)(int id);
|
||||
char *(*create_print_name) (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) (const char *host, int port, struct tgl_session *session, struct tgl_dc *dc, struct mtproto_methods *methods);
|
||||
};
|
||||
|
||||
|
||||
#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
|
||||
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;
|
||||
struct event_base *ev_base;
|
||||
|
||||
char *rsa_key_list[TGL_MAX_RSA_KEYS_NUM];
|
||||
int rsa_key_num;
|
||||
struct bignum_ctx *BN_ctx;
|
||||
|
||||
struct tgl_allocator allocator;
|
||||
};
|
||||
extern struct tgl_state tgl_state;
|
||||
|
||||
void tgl_reopen_binlog_for_writing (void);
|
||||
void tgl_replay_log (void);
|
||||
|
||||
int tgl_print_stat (char *s, int len);
|
||||
tgl_peer_t *tgl_peer_get (tgl_peer_id_t id);
|
||||
tgl_peer_t *tgl_peer_get_by_name (const char *s);
|
||||
|
||||
struct tgl_message *tgl_message_get (long long id);
|
||||
void tgl_peer_iterator_ex (void (*it)(tgl_peer_t *P, void *extra), void *extra);
|
||||
|
||||
int tgl_complete_user_list (int index, const char *text, int len, char **R);
|
||||
int tgl_complete_chat_list (int index, const char *text, int len, char **R);
|
||||
int tgl_complete_encr_chat_list (int index, const char *text, int len, char **R);
|
||||
int tgl_complete_peer_list (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 (int mode);
|
||||
void tgl_set_binlog_path (const char *path);
|
||||
void tgl_set_auth_file_path (const char *path);
|
||||
void tgl_set_download_directory (const char *path);
|
||||
void tgl_set_callback (struct tgl_update_callback *cb);
|
||||
void tgl_set_rsa_key (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 (void) {
|
||||
tgl_state.verbosity ++;
|
||||
}
|
||||
|
||||
static inline void tgl_set_verbosity (int val) {
|
||||
tgl_state.verbosity = val;
|
||||
}
|
||||
|
||||
static inline void tgl_enable_pfs (void) {
|
||||
tgl_state.enable_pfs = 1;
|
||||
}
|
||||
|
||||
static inline void tgl_set_test_mode (void) {
|
||||
tgl_state.test_mode ++;
|
||||
}
|
||||
|
||||
struct pollfd;
|
||||
int tgl_connections_make_poll_array (struct pollfd *fds, int max);
|
||||
void tgl_connections_poll_result (struct pollfd *fds, int max);
|
||||
|
||||
void tgl_do_help_get_config (void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_send_code (const char *user, void (*callback)(void *callback_extra, int success, int registered, const char *hash), void *callback_extra);
|
||||
void tgl_do_phone_call (const char *user, const char *hash, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
int tgl_do_send_code_result (const char *user, const char *hash, const char *code, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra) ;
|
||||
int tgl_do_send_code_result_auth (const char *user, const char *hash, const char *code, const char *first_name, const char *last_name, void (*callback)(void *callback_extra, int success, struct tgl_user *Self), void *callback_extra);
|
||||
void tgl_do_update_contact_list (void (*callback) (void *callback_extra, int success, int size, struct tgl_user *contacts[]), void *callback_extra);
|
||||
void tgl_do_send_message (tgl_peer_id_t id, const char *msg, int len, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_send_msg (struct tgl_message *M, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_send_text (tgl_peer_id_t id, char *file, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_mark_read (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_get_history (tgl_peer_id_t id, int limit, int offline_mode, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra);
|
||||
void tgl_do_get_history_ext (tgl_peer_id_t id, int offset, int limit, int offline_mode, void (*callback)(void *callback_extra, int success, int size, struct tgl_message *list[]), void *callback_extra);
|
||||
void tgl_do_get_dialog_list (void (*callback)(void *callback_extra, int success, int size, tgl_peer_id_t peers[], int last_msg_id[], int unread_count[]), void *callback_extra);
|
||||
void tgl_do_send_photo (enum tgl_message_media_type type, tgl_peer_id_t to_id, char *file_name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_set_chat_photo (tgl_peer_id_t chat_id, char *file_name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_set_profile_photo (char *file_name, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_forward_message (tgl_peer_id_t id, int n, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_rename_chat (tgl_peer_id_t id, char *name, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_get_chat_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_chat *C), void *callback_extra);
|
||||
void tgl_do_get_user_info (tgl_peer_id_t id, int offline_mode, void (*callback)(void *callback_extra, int success, struct tgl_user *U), void *callback_extra);
|
||||
void tgl_do_load_photo (struct tgl_photo *photo, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_video_thumb (struct tgl_video *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_audio (struct tgl_audio *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_video (struct tgl_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_document (struct tgl_document *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_document_thumb (struct tgl_document *video, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_load_encr_video (struct tgl_encr_video *V, void (*callback)(void *callback_extra, int success, char *filename), void *callback_extra);
|
||||
void tgl_do_export_auth (int num, void (*callback) (void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_add_contact (const char *phone, int phone_len, const char *first_name, int first_name_len, const char *last_name, int last_name_len, int force, void (*callback)(void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra);
|
||||
void tgl_do_msg_search (tgl_peer_id_t id, int from, int to, int limit, int offset, const char *s, void (*callback)(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) (void *callback_extra, int success, int size, struct tgl_user *users[]), void *callback_extra);
|
||||
void tgl_do_create_encr_chat_request (int user_id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
|
||||
void tgl_do_create_secret_chat (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
|
||||
void tgl_do_accept_encr_chat_request (struct tgl_secret_chat *E, void (*callback)(void *callback_extra, int success, struct tgl_secret_chat *E), void *callback_extra);
|
||||
void tgl_do_get_difference (int sync_from_start, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_lookup_state (void);
|
||||
void tgl_do_add_user_to_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, int limit, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_del_user_from_chat (tgl_peer_id_t chat_id, tgl_peer_id_t id, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_create_group_chat (tgl_peer_id_t id, char *chat_topic, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_create_group_chat_ex (int users_num, tgl_peer_id_t ids[], char *chat_topic, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_delete_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_restore_msg (long long id, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_update_status (int online, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_help_get_config_dc (struct tgl_dc *D, void (*callback)(void *, int), void *callback_extra);
|
||||
void tgl_do_export_card (void (*callback)(void *callback_extra, int success, int size, int *card), void *callback_extra);
|
||||
void tgl_do_import_card (int size, int *card, void (*callback)(void *callback_extra, int success, struct tgl_user *U), void *callback_extra);
|
||||
void tgl_do_send_contact (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)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_forward_media (tgl_peer_id_t id, int n, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
void tgl_do_del_contact (tgl_peer_id_t id, void (*callback)(void *callback_extra, int success), void *callback_extra);
|
||||
void tgl_do_set_encr_chat_ttl (struct tgl_secret_chat *E, int ttl, void (*callback)(void *callback_extra, int success, struct tgl_message *M), void *callback_extra);
|
||||
|
||||
|
||||
void tgl_do_visualize_key (tgl_peer_id_t id, unsigned char buf[16]);
|
||||
|
||||
void tgl_do_send_ping (struct connection *c);
|
||||
|
||||
int tgl_authorized_dc (struct tgl_dc *DC);
|
||||
int tgl_signed_dc (struct tgl_dc *DC);
|
||||
|
||||
//void tgl_do_get_suggested (void);
|
||||
|
||||
void tgl_do_create_keys_end (struct tgl_secret_chat *U);
|
||||
void tgl_do_send_encr_chat_layer (struct tgl_secret_chat *E);
|
||||
|
||||
struct mtproto_methods {
|
||||
int (*ready) (struct connection *c);
|
||||
int (*close) (struct connection *c);
|
||||
int (*execute) (struct connection *c, int op, int len);
|
||||
};
|
||||
|
||||
void tgl_init (void);
|
||||
void tgl_dc_authorize (struct tgl_dc *DC);
|
||||
|
||||
void tgl_dc_iterator (void (*iterator)(struct tgl_dc *DC));
|
||||
void tgl_dc_iterator_ex (void (*iterator)(struct tgl_dc *DC, void *extra), void *extra);
|
||||
|
||||
double tglt_get_double_time (void);
|
||||
|
||||
void tgl_insert_empty_user (int id);
|
||||
void tgl_insert_empty_chat (int id);
|
||||
|
||||
int tglf_extf_autocomplete (const char *text, int text_len, int index, char **R, char *data, int data_len);
|
||||
struct paramed_type *tglf_extf_store (const char *data, int data_len);
|
||||
void tgl_do_send_extf (char *data, int data_len, void (*callback)(void *callback_extra, int success, char *data), void *callback_extra);
|
||||
char *tglf_extf_fetch (struct paramed_type *T);
|
||||
|
||||
void tgl_free_all (void);
|
||||
|
||||
#endif
|
3077
tl-parser.c
Normal file
3077
tl-parser.c
Normal file
File diff suppressed because it is too large
Load diff
206
tl-parser.h
Normal file
206
tl-parser.h
Normal file
|
@ -0,0 +1,206 @@
|
|||
/*
|
||||
This file is part of tgl-libary/tlc
|
||||
|
||||
Tgl-library/tlc 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/tlc 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/tlc. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
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 __TL_PARSER_NEW_H__
|
||||
#define __TL_PARSER_NEW_H__
|
||||
enum lex_type {
|
||||
lex_error,
|
||||
lex_char,
|
||||
lex_triple_minus,
|
||||
lex_uc_ident,
|
||||
lex_lc_ident,
|
||||
lex_eof,
|
||||
lex_final,
|
||||
lex_new,
|
||||
lex_none,
|
||||
lex_num,
|
||||
lex_empty
|
||||
};
|
||||
|
||||
|
||||
struct curlex {
|
||||
char *ptr;
|
||||
int len;
|
||||
enum lex_type type;
|
||||
int flags;
|
||||
};
|
||||
|
||||
struct parse {
|
||||
char *text;
|
||||
int pos;
|
||||
int len;
|
||||
int line;
|
||||
int line_pos;
|
||||
struct curlex lex;
|
||||
};
|
||||
|
||||
|
||||
enum tree_type {
|
||||
type_tl_program,
|
||||
type_fun_declarations,
|
||||
type_constr_declarations,
|
||||
type_declaration,
|
||||
type_combinator_decl,
|
||||
type_equals,
|
||||
type_partial_app_decl,
|
||||
type_final_decl,
|
||||
type_full_combinator_id,
|
||||
type_opt_args,
|
||||
type_args,
|
||||
type_args1,
|
||||
type_args2,
|
||||
type_args3,
|
||||
type_args4,
|
||||
type_boxed_type_ident,
|
||||
type_subexpr,
|
||||
type_partial_comb_app_decl,
|
||||
type_partial_type_app_decl,
|
||||
type_final_new,
|
||||
type_final_final,
|
||||
type_final_empty,
|
||||
// type_type,
|
||||
type_var_ident,
|
||||
type_var_ident_opt,
|
||||
type_multiplicity,
|
||||
type_type_term,
|
||||
type_term,
|
||||
type_percent,
|
||||
type_result_type,
|
||||
type_expr,
|
||||
type_nat_term,
|
||||
type_combinator_id,
|
||||
type_nat_const,
|
||||
type_type_ident,
|
||||
type_builtin_combinator_decl,
|
||||
type_exclam,
|
||||
type_optional_arg_def
|
||||
};
|
||||
|
||||
struct tree {
|
||||
char *text;
|
||||
int len;
|
||||
enum tree_type type;
|
||||
int lex_line;
|
||||
int lex_line_pos;
|
||||
int flags;
|
||||
int size;
|
||||
int nc;
|
||||
struct tree **c;
|
||||
};
|
||||
|
||||
|
||||
#define TL_ACT(x) (x == act_var ? "act_var" : x == act_field ? "act_field" : x == act_plus ? "act_plus" : x == act_type ? "act_type" : x == act_nat_const ? "act_nat_const" : x == act_array ? "act_array" : x == act_question_mark ? "act_question_mark" : \
|
||||
x == act_union ? "act_union" : x == act_arg ? "act_arg" : x == act_opt_field ? "act_opt_field" : "act_unknown")
|
||||
|
||||
#define TL_TYPE(x) (x == type_num ? "type_num" : x == type_type ? "type_type" : x == type_list_item ? "type_list_item" : x == type_list ? "type_list" : x == type_num_value ? "type_num_value" : "type_unknown")
|
||||
enum combinator_tree_action {
|
||||
act_var,
|
||||
act_field,
|
||||
act_plus,
|
||||
act_type,
|
||||
act_nat_const,
|
||||
act_array,
|
||||
act_question_mark,
|
||||
act_union,
|
||||
act_arg,
|
||||
act_opt_field
|
||||
};
|
||||
|
||||
enum combinator_tree_type {
|
||||
type_num,
|
||||
type_num_value,
|
||||
type_type,
|
||||
type_list_item,
|
||||
type_list
|
||||
};
|
||||
|
||||
struct tl_combinator_tree {
|
||||
enum combinator_tree_action act;
|
||||
struct tl_combinator_tree *left, *right;
|
||||
char *name;
|
||||
void *data;
|
||||
long long flags;
|
||||
enum combinator_tree_type type;
|
||||
int type_len;
|
||||
long long type_flags;
|
||||
};
|
||||
|
||||
|
||||
struct tl_program {
|
||||
int types_num;
|
||||
int functions_num;
|
||||
int constructors_num;
|
||||
struct tl_type **types;
|
||||
struct tl_function **functions;
|
||||
// struct tl_constuctor **constructors;
|
||||
};
|
||||
|
||||
struct tl_type {
|
||||
char *id;
|
||||
char *print_id;
|
||||
char *real_id;
|
||||
unsigned name;
|
||||
int flags;
|
||||
|
||||
int params_num;
|
||||
long long params_types;
|
||||
|
||||
int constructors_num;
|
||||
struct tl_constructor **constructors;
|
||||
};
|
||||
|
||||
struct tl_constructor {
|
||||
char *id;
|
||||
char *print_id;
|
||||
char *real_id;
|
||||
unsigned name;
|
||||
struct tl_type *type;
|
||||
|
||||
struct tl_combinator_tree *left;
|
||||
struct tl_combinator_tree *right;
|
||||
};
|
||||
|
||||
struct tl_var {
|
||||
char *id;
|
||||
struct tl_combinator_tree *ptr;
|
||||
int type;
|
||||
int flags;
|
||||
};
|
||||
|
||||
struct parse *tl_init_parse_file (const char *fname);
|
||||
struct tree *tl_parse_lex (struct parse *P);
|
||||
void tl_print_parse_error (void);
|
||||
struct tl_program *tl_parse (struct tree *T);
|
||||
|
||||
void write_types (int f);
|
||||
|
||||
#define FLAG_BARE 1
|
||||
#define FLAG_OPT_VAR (1 << 17)
|
||||
#define FLAG_EXCL (1 << 18)
|
||||
#define FLAG_OPT_FIELD (1 << 20)
|
||||
#define FLAG_IS_VAR (1 << 21)
|
||||
#define FLAG_DEFAULT_CONSTRUCTOR (1 << 25)
|
||||
#define FLAG_EMPTY (1 << 10)
|
||||
|
||||
#endif
|
52
tl-tl.h
Normal file
52
tl-tl.h
Normal file
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
This file is part of VK/KittenPHP-DB-Engine.
|
||||
|
||||
VK/KittenPHP-DB-Engine 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.
|
||||
|
||||
VK/KittenPHP-DB-Engine 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 VK/KittenPHP-DB-Engine. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
This program is released under the GPL with the additional exemption
|
||||
that compiling, linking, and/or using OpenSSL is allowed.
|
||||
You are free to remove this exemption from derived works.
|
||||
|
||||
Copyright 2012-2013 Vkontakte Ltd
|
||||
2012-2013 Vitaliy Valtman
|
||||
*/
|
||||
|
||||
#ifndef __TL_TL_H__
|
||||
#define __TL_TL_H__
|
||||
|
||||
#define TLS_SCHEMA 0xf19d9e38
|
||||
#define TLS_TYPE 0x12eb4386
|
||||
#define TLS_COMBINATOR 0x5c0a1ed5
|
||||
#define TLS_COMBINATOR_LEFT_BUILTIN 0xcd211f63
|
||||
#define TLS_COMBINATOR_LEFT 0x4c12c6d9
|
||||
#define TLS_COMBINATOR_RIGHT 0xd325b367
|
||||
#define TLS_ARG 0x46afe232
|
||||
#define TLS_TREE_NAT_CONST 0xc09f07d7
|
||||
#define TLS_TREE_NAT_VAR 0x90ea6f58
|
||||
#define TLS_TREE_TYPE_VAR 0x1caa237a
|
||||
#define TLS_TREE_ARRAY 0x80479360
|
||||
#define TLS_TREE_TYPE 0x10f32190
|
||||
|
||||
#define TLS_SCHEMA_V2 0x3a2f9be2
|
||||
#define TLS_COMBINATOR_RIGHT_V2 0x2c064372
|
||||
#define TLS_ARG_V2 0x29dfe61b
|
||||
#define TLS_EXPR_TYPE 0xecc9da78
|
||||
#define TLS_EXPR_NAT 0xdcb49bd8
|
||||
|
||||
#define TLS_NAT_CONST 0xdcb49bd8
|
||||
#define TLS_NAT_VAR 0x4e8a14f0
|
||||
#define TLS_TYPE_VAR 0x0142ceae
|
||||
#define TLS_ARRAY 0xd9fb20de
|
||||
#define TLS_TYPE_EXPR 0xc1863d08
|
||||
#endif
|
165
tlc.c
Normal file
165
tlc.c
Normal file
|
@ -0,0 +1,165 @@
|
|||
/*
|
||||
This file is part of tgl-libary/tlc
|
||||
|
||||
Tgl-library/tlc 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/tlc 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/tlc. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
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
|
||||
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "tl-parser.h"
|
||||
|
||||
#include <unistd.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#include <signal.h>
|
||||
#include "config.h"
|
||||
#include <execinfo.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
int verbosity;
|
||||
int output_expressions;
|
||||
int schema_version = 2;
|
||||
void usage (void) {
|
||||
printf ("usage: tlc [-v] [-h] <TL-schema-file>\n"
|
||||
"\tTL compiler\n"
|
||||
"\t-v\toutput statistical and debug information into stderr\n"
|
||||
"\t-E\twhenever is possible output to stdout expressions\n"
|
||||
"\t-e <file>\texport serialized schema to file\n"
|
||||
"\t-w\t custom version of serialized schema (0 - very old, 1 - old, 2 - current (default))\n"
|
||||
);
|
||||
exit (2);
|
||||
}
|
||||
|
||||
int vkext_write (const char *filename) {
|
||||
int f = open (filename, O_CREAT | O_WRONLY | O_TRUNC, 0640);
|
||||
assert (f >= 0);
|
||||
write_types (f);
|
||||
close (f);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void logprintf (const char *format, ...) __attribute__ ((format (printf, 1, 2)));
|
||||
void logprintf (const char *format __attribute__ ((unused)), ...) {
|
||||
va_list ap;
|
||||
va_start (ap, format);
|
||||
vfprintf (stderr, format, ap);
|
||||
va_end (ap);
|
||||
}
|
||||
|
||||
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;
|
||||
char *vkext_file = 0;
|
||||
while ((i = getopt (argc, argv, "Ehve:w:")) != -1) {
|
||||
switch (i) {
|
||||
case 'E':
|
||||
output_expressions++;
|
||||
break;
|
||||
case 'h':
|
||||
usage ();
|
||||
return 2;
|
||||
case 'e':
|
||||
vkext_file = optarg;
|
||||
break;
|
||||
case 'w':
|
||||
schema_version = atoi (optarg);
|
||||
break;
|
||||
case 'v':
|
||||
verbosity++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (argc != optind + 1) {
|
||||
usage ();
|
||||
}
|
||||
|
||||
|
||||
struct parse *P = tl_init_parse_file (argv[optind]);
|
||||
if (!P) {
|
||||
return 0;
|
||||
}
|
||||
struct tree *T;
|
||||
if (!(T = tl_parse_lex (P))) {
|
||||
fprintf (stderr, "Error in parse:\n");
|
||||
tl_print_parse_error ();
|
||||
return 0;
|
||||
} else {
|
||||
if (verbosity) {
|
||||
fprintf (stderr, "Parse ok\n");
|
||||
}
|
||||
if (!tl_parse (T)) {
|
||||
if (verbosity) {
|
||||
fprintf (stderr, "Fail\n");
|
||||
}
|
||||
return 1;
|
||||
} else {
|
||||
if (verbosity) {
|
||||
fprintf (stderr, "Ok\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
if (vkext_file) {
|
||||
vkext_write (vkext_file);
|
||||
}
|
||||
return 0;
|
||||
}
|
226
tools.c
226
tools.c
|
@ -1,20 +1,21 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
|
@ -28,31 +29,47 @@
|
|||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/rand.h>
|
||||
#include <zlib.h>
|
||||
#include <time.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include "interface.h"
|
||||
//#include "interface.h"
|
||||
#include "tools.h"
|
||||
|
||||
#ifdef DEBUG
|
||||
#ifdef __MACH__
|
||||
#include <mach/clock.h>
|
||||
#include <mach/mach.h>
|
||||
#endif
|
||||
|
||||
#ifdef __MACH__
|
||||
#define CLOCK_REALTIME 0
|
||||
#define CLOCK_MONOTONIC 1
|
||||
#endif
|
||||
|
||||
#define RES_PRE 8
|
||||
#define RES_AFTER 8
|
||||
#define MAX_BLOCKS 1000000
|
||||
void *blocks[MAX_BLOCKS];
|
||||
void *free_blocks[MAX_BLOCKS];
|
||||
int used_blocks;
|
||||
int free_blocks_cnt;
|
||||
#endif
|
||||
static void *blocks[MAX_BLOCKS];
|
||||
static void *free_blocks[MAX_BLOCKS];
|
||||
static int used_blocks;
|
||||
static int free_blocks_cnt;
|
||||
|
||||
extern int verbosity;
|
||||
static long long total_allocated_bytes;
|
||||
|
||||
long long total_allocated_bytes;
|
||||
|
||||
static void out_of_memory (void) {
|
||||
fprintf (stderr, "Out of memory\n");
|
||||
exit (1);
|
||||
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);
|
||||
}
|
||||
|
||||
int tsnprintf (char *buf, int len, const char *format, ...) {
|
||||
//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);
|
||||
|
@ -61,7 +78,7 @@ int tsnprintf (char *buf, int len, const char *format, ...) {
|
|||
return r;
|
||||
}
|
||||
|
||||
int tasprintf (char **res, const char *format, ...) {
|
||||
int tgl_asprintf (char **res, const char *format, ...) {
|
||||
va_list ap;
|
||||
va_start (ap, format);
|
||||
int r = vasprintf (res, format, ap);
|
||||
|
@ -74,9 +91,7 @@ int tasprintf (char **res, const char *format, ...) {
|
|||
return r;
|
||||
}
|
||||
|
||||
void print_backtrace (void);
|
||||
void tfree (void *ptr, int size __attribute__ ((unused))) {
|
||||
#ifdef DEBUG
|
||||
void tgl_free_debug (void *ptr, int size __attribute__ ((unused))) {
|
||||
total_allocated_bytes -= size;
|
||||
ptr -= RES_PRE;
|
||||
if (size != (int)((*(int *)ptr) ^ 0xbedabeda)) {
|
||||
|
@ -100,36 +115,28 @@ void tfree (void *ptr, int size __attribute__ ((unused))) {
|
|||
memset (ptr, 0, size + RES_PRE + RES_AFTER);
|
||||
*(int *)ptr = size + 12;
|
||||
free_blocks[free_blocks_cnt ++] = ptr;
|
||||
#else
|
||||
}
|
||||
|
||||
void tgl_free_release (void *ptr, int size) {
|
||||
free (ptr);
|
||||
#endif
|
||||
}
|
||||
|
||||
void tfree_str (void *ptr) {
|
||||
if (!ptr) { return; }
|
||||
tfree (ptr, strlen (ptr) + 1);
|
||||
}
|
||||
|
||||
void tfree_secure (void *ptr, int size) {
|
||||
memset (ptr, 0, size);
|
||||
tfree (ptr, size);
|
||||
}
|
||||
|
||||
void *trealloc (void *ptr, size_t old_size __attribute__ ((unused)), size_t size) {
|
||||
#ifdef DEBUG
|
||||
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;
|
||||
#else
|
||||
}
|
||||
|
||||
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;
|
||||
#endif
|
||||
}
|
||||
|
||||
void *talloc (size_t size) {
|
||||
#ifdef DEBUG
|
||||
void *tgl_alloc_debug (size_t size) {
|
||||
total_allocated_bytes += size;
|
||||
void *p = malloc (size + RES_PRE + RES_AFTER);
|
||||
ensure_ptr (p);
|
||||
|
@ -138,67 +145,44 @@ void *talloc (size_t 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;
|
||||
#else
|
||||
}
|
||||
|
||||
void *tgl_alloc_release (size_t size) {
|
||||
void *p = malloc (size);
|
||||
ensure_ptr (p);
|
||||
return p;
|
||||
#endif
|
||||
}
|
||||
|
||||
void *talloc0 (size_t size) {
|
||||
void *tgl_alloc0 (size_t size) {
|
||||
void *p = talloc (size);
|
||||
memset (p, 0, size);
|
||||
return p;
|
||||
}
|
||||
|
||||
char *tstrdup (const char *s) {
|
||||
#ifdef DEBUG
|
||||
char *tgl_strdup (const char *s) {
|
||||
int l = strlen (s);
|
||||
char *p = talloc (l + 1);
|
||||
memcpy (p, s, l + 1);
|
||||
return p;
|
||||
#else
|
||||
char *p = strdup (s);
|
||||
if (p == NULL) {
|
||||
out_of_memory ();
|
||||
}
|
||||
return p;
|
||||
#endif
|
||||
}
|
||||
|
||||
char *tstrndup (const char *s, size_t n) {
|
||||
#ifdef DEBUG
|
||||
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;
|
||||
#else
|
||||
char *p = strndup (s, n);
|
||||
if (p == NULL) {
|
||||
out_of_memory ();
|
||||
}
|
||||
return p;
|
||||
#endif
|
||||
}
|
||||
|
||||
void ensure (int r) {
|
||||
if (!r) {
|
||||
logprintf ("Open SSL error\n");
|
||||
ERR_print_errors_fp (stderr);
|
||||
assert (0);
|
||||
}
|
||||
}
|
||||
|
||||
void ensure_ptr (void *p) {
|
||||
if (p == NULL) {
|
||||
out_of_memory ();
|
||||
}
|
||||
}
|
||||
|
||||
int tinflate (void *input, int ilen, void *output, int olen) {
|
||||
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);
|
||||
|
@ -206,30 +190,29 @@ int tinflate (void *input, int ilen, void *output, int olen) {
|
|||
strm.next_in = input;
|
||||
strm.avail_out = olen ;
|
||||
strm.next_out = output;
|
||||
int err = inflate (&strm, Z_FINISH), total_out = 0;
|
||||
if (err == Z_OK || err == Z_STREAM_END) {
|
||||
total_out = (int) strm.total_out;
|
||||
if (err == Z_STREAM_END && verbosity >= 2) {
|
||||
logprintf ( "inflated %d bytes\n", (int) strm.total_out);
|
||||
}
|
||||
}
|
||||
if (verbosity && err != Z_STREAM_END) {
|
||||
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;
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
void tcheck (void) {
|
||||
void tgl_check_debug (void) {
|
||||
int i;
|
||||
for (i = 0; i < used_blocks; i++) {
|
||||
void *ptr = blocks[i];
|
||||
int size = (*(int *)ptr) ^ 0xbedabeda;
|
||||
assert (*(int *)(ptr + 4) == size);
|
||||
assert (*(int *)(ptr + RES_PRE + size) == (size ^ 0x7bed7bed));
|
||||
assert (*(int *)(ptr + RES_PRE + 4 + size) == i);
|
||||
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];
|
||||
|
@ -243,10 +226,10 @@ void tcheck (void) {
|
|||
}
|
||||
}
|
||||
}
|
||||
logprintf ("ok. Used_blocks = %d. Free blocks = %d\n", used_blocks, free_blocks_cnt);
|
||||
//logprintf ("ok. Used_blocks = %d. Free blocks = %d\n", used_blocks, free_blocks_cnt);
|
||||
}
|
||||
|
||||
void texists (void *ptr, int size) {
|
||||
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);
|
||||
|
@ -260,4 +243,55 @@ void texists (void *ptr, int size) {
|
|||
}
|
||||
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;
|
||||
|
|
111
tools.h
111
tools.h
|
@ -19,26 +19,101 @@
|
|||
|
||||
#ifndef __TOOLS_H__
|
||||
#define __TOOLS_H__
|
||||
#include <time.h>
|
||||
#include <openssl/err.h>
|
||||
#include <assert.h>
|
||||
#include "tgl.h"
|
||||
|
||||
void *talloc (size_t size);
|
||||
void *trealloc (void *ptr, size_t old_size, size_t size);
|
||||
void *talloc0 (size_t size);
|
||||
char *tstrdup (const char *s);
|
||||
char *tstrndup (const char *s, size_t n);
|
||||
int tinflate (void *input, int ilen, void *output, int olen);
|
||||
void ensure (int r);
|
||||
void ensure_ptr (void *p);
|
||||
|
||||
void tfree (void *ptr, int size);
|
||||
void tfree_str (void *ptr);
|
||||
void tfree_secure (void *ptr, int size);
|
||||
#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
|
||||
|
||||
|
||||
int tsnprintf (char *buf, int len, const char *format, ...) __attribute__ ((format (printf, 3, 4)));
|
||||
int tasprintf (char **res, const char *format, ...) __attribute__ ((format (printf, 2, 3)));
|
||||
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"); }
|
||||
}
|
||||
|
||||
|
||||
#ifdef DEBUG
|
||||
void tcheck (void);
|
||||
void texists (void *ptr, int size);
|
||||
#endif
|
||||
#endif
|
||||
|
|
74
tree.h
74
tree.h
|
@ -1,28 +1,29 @@
|
|||
/*
|
||||
This file is part of telegram-client.
|
||||
/*
|
||||
This file is part of tgl-library
|
||||
|
||||
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.
|
||||
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.
|
||||
|
||||
Telegram-client is distributed in the hope that it will be useful,
|
||||
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 General Public License for more details.
|
||||
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 General Public License
|
||||
along with this telegram-client. If not, see <http://www.gnu.org/licenses/>.
|
||||
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
|
||||
Copyright Vitaly Valtman 2013-2014
|
||||
*/
|
||||
#ifndef __TREE_H__
|
||||
#define __TREE_H__
|
||||
#include <stdio.h>
|
||||
|
||||
#include <memory.h>
|
||||
#include <tools.h>
|
||||
#include <assert.h>
|
||||
#include "tools.h"
|
||||
|
||||
#pragma pack(push,4)
|
||||
#define DEFINE_TREE(X_NAME, X_TYPE, X_CMP, X_UNSET) \
|
||||
|
@ -32,7 +33,7 @@ struct tree_ ## X_NAME { \
|
|||
int y;\
|
||||
};\
|
||||
\
|
||||
struct tree_ ## X_NAME *new_tree_node_ ## X_NAME (X_TYPE x, int y) {\
|
||||
static struct tree_ ## X_NAME *new_tree_node_ ## X_NAME (X_TYPE x, int y) {\
|
||||
struct tree_ ## X_NAME *T = talloc (sizeof (*T));\
|
||||
T->x = x;\
|
||||
T->y = y;\
|
||||
|
@ -40,11 +41,11 @@ struct tree_ ## X_NAME *new_tree_node_ ## X_NAME (X_TYPE x, int y) {\
|
|||
return T;\
|
||||
}\
|
||||
\
|
||||
void delete_tree_node_ ## X_NAME (struct tree_ ## X_NAME *T) {\
|
||||
static void delete_tree_node_ ## X_NAME (struct tree_ ## X_NAME *T) {\
|
||||
tfree (T, sizeof (*T));\
|
||||
}\
|
||||
\
|
||||
void tree_split_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, struct tree_ ## X_NAME **L, struct tree_ ## X_NAME **R) {\
|
||||
static void tree_split_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, struct tree_ ## X_NAME **L, struct tree_ ## X_NAME **R) {\
|
||||
if (!T) {\
|
||||
*L = *R = 0;\
|
||||
} else {\
|
||||
|
@ -59,8 +60,8 @@ void tree_split_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, struct tree_ ##
|
|||
}\
|
||||
}\
|
||||
\
|
||||
struct tree_ ## X_NAME *tree_insert_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, int y) __attribute__ ((warn_unused_result));\
|
||||
struct tree_ ## X_NAME *tree_insert_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, int y) {\
|
||||
static struct tree_ ## X_NAME *tree_insert_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, int y) __attribute__ ((warn_unused_result,unused));\
|
||||
static struct tree_ ## X_NAME *tree_insert_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x, int y) {\
|
||||
if (!T) {\
|
||||
return new_tree_node_ ## X_NAME (x, y);\
|
||||
} else {\
|
||||
|
@ -81,7 +82,7 @@ struct tree_ ## X_NAME *tree_insert_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYP
|
|||
}\
|
||||
}\
|
||||
\
|
||||
struct tree_ ## X_NAME *tree_merge_ ## X_NAME (struct tree_ ## X_NAME *L, struct tree_ ## X_NAME *R) {\
|
||||
static struct tree_ ## X_NAME *tree_merge_ ## X_NAME (struct tree_ ## X_NAME *L, struct tree_ ## X_NAME *R) {\
|
||||
if (!L || !R) {\
|
||||
return L ? L : R;\
|
||||
} else {\
|
||||
|
@ -95,8 +96,8 @@ struct tree_ ## X_NAME *tree_merge_ ## X_NAME (struct tree_ ## X_NAME *L, struct
|
|||
}\
|
||||
}\
|
||||
\
|
||||
struct tree_ ## X_NAME *tree_delete_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) __attribute__ ((warn_unused_result));\
|
||||
struct tree_ ## X_NAME *tree_delete_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) {\
|
||||
static struct tree_ ## X_NAME *tree_delete_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) __attribute__ ((warn_unused_result,unused));\
|
||||
static struct tree_ ## X_NAME *tree_delete_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) {\
|
||||
assert (T);\
|
||||
int c = X_CMP (x, T->x);\
|
||||
if (!c) {\
|
||||
|
@ -113,13 +114,15 @@ struct tree_ ## X_NAME *tree_delete_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYP
|
|||
}\
|
||||
}\
|
||||
\
|
||||
X_TYPE tree_get_min_ ## X_NAME (struct tree_ ## X_NAME *T) {\
|
||||
static X_TYPE tree_get_min_ ## X_NAME (struct tree_ ## X_NAME *t) __attribute__ ((unused));\
|
||||
static X_TYPE tree_get_min_ ## X_NAME (struct tree_ ## X_NAME *T) {\
|
||||
if (!T) { return X_UNSET; } \
|
||||
while (T->left) { T = T->left; }\
|
||||
return T->x; \
|
||||
} \
|
||||
\
|
||||
X_TYPE tree_lookup_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) {\
|
||||
static X_TYPE tree_lookup_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) __attribute__ ((unused));\
|
||||
static X_TYPE tree_lookup_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) {\
|
||||
int c;\
|
||||
while (T && (c = X_CMP (x, T->x))) {\
|
||||
T = (c < 0 ? T->left : T->right);\
|
||||
|
@ -127,18 +130,29 @@ X_TYPE tree_lookup_ ## X_NAME (struct tree_ ## X_NAME *T, X_TYPE x) {\
|
|||
return T ? T->x : X_UNSET;\
|
||||
}\
|
||||
\
|
||||
void tree_act_ ## X_NAME (struct tree_ ## X_NAME *T, void (*act)(X_TYPE)) {\
|
||||
static void tree_act_ ## X_NAME (struct tree_ ## X_NAME *T, void (*act)(X_TYPE)) __attribute__ ((unused));\
|
||||
static void tree_act_ ## X_NAME (struct tree_ ## X_NAME *T, void (*act)(X_TYPE)) {\
|
||||
if (!T) { return; } \
|
||||
tree_act_ ## X_NAME (T->left, act); \
|
||||
act (T->x); \
|
||||
tree_act_ ## X_NAME (T->right, act); \
|
||||
}\
|
||||
\
|
||||
int tree_count_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
||||
static void tree_act_ex_ ## X_NAME (struct tree_ ## X_NAME *T, void (*act)(X_TYPE, void *), void *extra) __attribute__ ((unused));\
|
||||
static void tree_act_ex_ ## X_NAME (struct tree_ ## X_NAME *T, void (*act)(X_TYPE, void *), void *extra) {\
|
||||
if (!T) { return; } \
|
||||
tree_act_ex_ ## X_NAME (T->left, act, extra); \
|
||||
act (T->x, extra); \
|
||||
tree_act_ex_ ## X_NAME (T->right, act, extra); \
|
||||
}\
|
||||
\
|
||||
static int tree_count_ ## X_NAME (struct tree_ ## X_NAME *T) __attribute__ ((unused));\
|
||||
static int tree_count_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
||||
if (!T) { return 0; }\
|
||||
return 1 + tree_count_ ## X_NAME (T->left) + tree_count_ ## X_NAME (T->right); \
|
||||
}\
|
||||
void tree_check_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
||||
static void tree_check_ ## X_NAME (struct tree_ ## X_NAME *T) __attribute__ ((unused));\
|
||||
static void tree_check_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
||||
if (!T) { return; }\
|
||||
if (T->left) { \
|
||||
assert (T->left->y <= T->y);\
|
||||
|
@ -151,6 +165,14 @@ void tree_check_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
|||
tree_check_ ## X_NAME (T->left); \
|
||||
tree_check_ ## X_NAME (T->right); \
|
||||
}\
|
||||
static struct tree_ ## X_NAME *tree_clear_ ## X_NAME (struct tree_ ## X_NAME *T) __attribute__ ((unused));\
|
||||
static struct tree_ ## X_NAME *tree_clear_ ## X_NAME (struct tree_ ## X_NAME *T) { \
|
||||
if (!T) { return 0; }\
|
||||
tree_clear_ ## X_NAME (T->left); \
|
||||
tree_clear_ ## X_NAME (T->right); \
|
||||
delete_tree_node_ ## X_NAME (T); \
|
||||
return 0; \
|
||||
} \
|
||||
|
||||
#define int_cmp(a,b) ((a) - (b))
|
||||
#pragma pack(pop)
|
||||
|
|
520
updates.c
Normal file
520
updates.c
Normal file
|
@ -0,0 +1,520 @@
|
|||
/*
|
||||
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 <assert.h>
|
||||
|
||||
void tglu_fetch_pts (void) {
|
||||
int p = fetch_int ();
|
||||
if (p <= tgl_state.pts) { return; }
|
||||
bl_do_set_pts (p);
|
||||
}
|
||||
|
||||
void tglu_fetch_qts (void) {
|
||||
int p = fetch_int ();
|
||||
if (p <= tgl_state.qts) { return; }
|
||||
bl_do_set_qts (p);
|
||||
}
|
||||
|
||||
void tglu_fetch_date (void) {
|
||||
int p = fetch_int ();
|
||||
if (p > tgl_state.date) {
|
||||
//tgl_state.date = p;
|
||||
bl_do_set_date (tgl_state.date);
|
||||
}
|
||||
}
|
||||
|
||||
static void fetch_dc_option (void) {
|
||||
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 (id, l1, name, l2, ip, port);
|
||||
}
|
||||
|
||||
void tglu_work_update (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 ();
|
||||
assert (M);
|
||||
tglu_fetch_pts ();
|
||||
bl_do_msg_update (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 (new);
|
||||
if (M) {
|
||||
bl_do_set_msg_id (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 (id);
|
||||
if (M) {
|
||||
bl_do_set_unread (M, 0);
|
||||
}
|
||||
}
|
||||
tglu_fetch_pts ();
|
||||
}
|
||||
break;
|
||||
case CODE_update_user_typing:
|
||||
{
|
||||
tgl_peer_id_t id = TGL_MK_USER (fetch_int ());
|
||||
tgl_peer_t *U = tgl_peer_get (id);
|
||||
|
||||
if (tgl_state.callback.type_notification && U) {
|
||||
tgl_state.callback.type_notification ((void *)U);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CODE_update_chat_user_typing:
|
||||
{
|
||||
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 (chat_id);
|
||||
tgl_peer_t *U = tgl_peer_get (id);
|
||||
|
||||
if (U && C) {
|
||||
if (tgl_state.callback.type_in_chat_notification) {
|
||||
tgl_state.callback.type_in_chat_notification ((void *)U, (void *)C);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CODE_update_user_status:
|
||||
{
|
||||
tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ());
|
||||
tgl_peer_t *U = tgl_peer_get (user_id);
|
||||
if (U) {
|
||||
tglf_fetch_user_status (&U->user.status);
|
||||
|
||||
if (tgl_state.callback.status_notification) {
|
||||
tgl_state.callback.status_notification ((void *)U);
|
||||
}
|
||||
} else {
|
||||
struct tgl_user_status t;
|
||||
tglf_fetch_user_status (&t);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CODE_update_user_name:
|
||||
{
|
||||
tgl_peer_id_t user_id = TGL_MK_USER (fetch_int ());
|
||||
tgl_peer_t *UC = tgl_peer_get (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 (U, f, l1, l, l2);
|
||||
} else {
|
||||
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 (user_id);
|
||||
tglu_fetch_date ();
|
||||
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 (&small);
|
||||
tglf_fetch_file_location (&big);
|
||||
}
|
||||
bl_do_set_user_profile_photo (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 (&t);
|
||||
tglf_fetch_file_location (&t);
|
||||
}
|
||||
}
|
||||
fetch_bool ();
|
||||
}
|
||||
break;
|
||||
case CODE_update_restore_messages:
|
||||
{
|
||||
assert (fetch_int () == CODE_vector);
|
||||
int n = fetch_int ();
|
||||
fetch_skip (n);
|
||||
tglu_fetch_pts ();
|
||||
}
|
||||
break;
|
||||
case CODE_update_delete_messages:
|
||||
{
|
||||
assert (fetch_int () == CODE_vector);
|
||||
int n = fetch_int ();
|
||||
fetch_skip (n);
|
||||
tglu_fetch_pts ();
|
||||
}
|
||||
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 (chat_id);
|
||||
if (C && (C->flags & FLAG_CREATED)) {
|
||||
if (x == CODE_chat_participants) {
|
||||
bl_do_chat_set_admin (&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 (&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 (user_id);
|
||||
fetch_int (); // date
|
||||
if (tgl_state.callback.user_registered && U) {
|
||||
tgl_state.callback.user_registered ((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 (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 (user_id);
|
||||
|
||||
if (tgl_state.callback.user_activated && U) {
|
||||
tgl_state.callback.user_activated ((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 (tgl_state.callback.new_authorization) {
|
||||
tgl_state.callback.new_authorization (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 ();
|
||||
assert (M);
|
||||
bl_do_msg_update (M->id);
|
||||
}
|
||||
break;
|
||||
case CODE_update_new_encrypted_message:
|
||||
{
|
||||
struct tgl_message *M = tglf_fetch_alloc_encrypted_message ();
|
||||
assert (M);
|
||||
tglu_fetch_qts ();
|
||||
bl_do_msg_update (M->id);
|
||||
}
|
||||
break;
|
||||
case CODE_update_encryption:
|
||||
{
|
||||
struct tgl_secret_chat *E = tglf_fetch_alloc_encrypted_chat ();
|
||||
vlogprintf (E_DEBUG, "Secret chat state = %d\n", E->state);
|
||||
if (E->state == sc_ok) {
|
||||
tgl_do_send_encr_chat_layer (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 (id);
|
||||
|
||||
if (P) {
|
||||
if (tgl_state.callback.type_in_secret_chat_notification) {
|
||||
tgl_state.callback.type_in_secret_chat_notification ((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 (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 (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 (chat_id);
|
||||
if (C && (C->flags & FLAG_CREATED)) {
|
||||
bl_do_chat_add_user (&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 (chat_id);
|
||||
if (C && (C->flags & FLAG_CREATED)) {
|
||||
bl_do_chat_del_user (&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 ();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CODE_update_user_blocked:
|
||||
{
|
||||
int id = fetch_int ();
|
||||
int blocked = fetch_bool ();
|
||||
tgl_peer_t *P = tgl_peer_get (TGL_MK_USER (id));
|
||||
if (P && (P->flags & FLAG_CREATED)) {
|
||||
bl_do_user_set_blocked (&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;
|
||||
default:
|
||||
vlogprintf (E_ERROR, "Unknown update type %08x\n", op);
|
||||
;
|
||||
}
|
||||
}
|
||||
|
||||
void tglu_work_update_short (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 (c, msg_id);
|
||||
tglu_fetch_date ();
|
||||
|
||||
assert (save_end == in_ptr);
|
||||
}
|
||||
|
||||
static int do_skip_seq (int seq) {
|
||||
if (tgl_state.seq) {
|
||||
if (seq <= tgl_state.seq) {
|
||||
vlogprintf (E_NOTICE, "Duplicate message with seq=%d\n", seq);
|
||||
return -1;
|
||||
}
|
||||
if (seq > tgl_state.seq + 1) {
|
||||
vlogprintf (E_NOTICE, "Hole in seq (seq = %d, cur_seq = %d)\n", seq, tgl_state.seq);
|
||||
//vlogprintf (E_NOTICE, "lock_diff = %s\n", (tgl_state.locks & TGL_LOCK_DIFF) ? "true" : "false");
|
||||
tgl_do_get_difference (0, 0, 0);
|
||||
return -1;
|
||||
}
|
||||
if (tgl_state.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 connection *c, long long msg_id) {
|
||||
int *save = in_ptr;
|
||||
assert (!skip_type_any (TYPE_TO_PARAM (updates)));
|
||||
if (do_skip_seq (*(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 (c, msg_id);
|
||||
}
|
||||
assert (fetch_int () == CODE_vector);
|
||||
n = fetch_int ();
|
||||
for (i = 0; i < n; i++) {
|
||||
tglf_fetch_alloc_user ();
|
||||
}
|
||||
assert (fetch_int () == CODE_vector);
|
||||
n = fetch_int ();
|
||||
for (i = 0; i < n; i++) {
|
||||
tglf_fetch_alloc_chat ();
|
||||
}
|
||||
bl_do_set_date (fetch_int ());
|
||||
//bl_do_set_seq (fetch_int ());
|
||||
int seq = fetch_int ();
|
||||
assert (seq == tgl_state.seq + 1);
|
||||
bl_do_set_seq (seq);
|
||||
assert (save_end == in_ptr);
|
||||
}
|
||||
|
||||
void tglu_work_update_short_message (struct connection *c, long long msg_id) {
|
||||
int *save = in_ptr;
|
||||
assert (!skip_type_any (TYPE_TO_PARAM (updates)));
|
||||
if (do_skip_seq (*(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 ();
|
||||
assert (M);
|
||||
|
||||
assert (save_end == in_ptr);
|
||||
if (!(tgl_state.locks & TGL_LOCK_DIFF)) {
|
||||
bl_do_msg_seq_update (M->id);
|
||||
}
|
||||
}
|
||||
|
||||
void tglu_work_update_short_chat_message (struct connection *c, long long msg_id) {
|
||||
int *save = in_ptr;
|
||||
assert (!skip_type_any (TYPE_TO_PARAM (updates)));
|
||||
if (do_skip_seq (*(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 ();
|
||||
assert (M);
|
||||
assert (save_end == in_ptr);
|
||||
|
||||
if (!(tgl_state.locks & TGL_LOCK_DIFF)) {
|
||||
bl_do_msg_seq_update (M->id);
|
||||
}
|
||||
}
|
||||
|
||||
void tglu_work_updates_to_long (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 (0, 0, 0);
|
||||
}
|
35
updates.h
Normal file
35
updates.h
Normal file
|
@ -0,0 +1,35 @@
|
|||
/*
|
||||
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 connection *c, long long msg_id);
|
||||
void tglu_work_updates_to_long (struct connection *c, long long msg_id);
|
||||
void tglu_work_update_short_chat_message (struct connection *c, long long msg_id);
|
||||
void tglu_work_update_short_message (struct connection *c, long long msg_id);
|
||||
void tglu_work_update_short (struct connection *c, long long msg_id);
|
||||
void tglu_work_updates (struct connection *c, long long msg_id);
|
||||
|
||||
void tglu_fetch_pts (void);
|
||||
void tglu_fetch_qts (void);
|
||||
void tglu_fetch_seq (void);
|
||||
void tglu_fetch_date (void);
|
||||
#endif
|
Loading…
Add table
Reference in a new issue