From 7ab7f4126ebdd5a8afbea62604c276e229d3637a Mon Sep 17 00:00:00 2001 From: Ben Wiederhake Date: Thu, 1 Oct 2015 17:11:33 +0200 Subject: [PATCH] Avoid the PEM issue. --- Makefile.in | 5 ++-- README.md | 21 +++++++++++++++- telegram-base.c | 63 ++++++++++++++++++++++++++++++++++++++++++++-- telegram-base.h | 10 +++++++- telegram-purple.c | 24 +++++++++++++++--- tg-server.pub | 8 ------ tg-server.tglpub | Bin 0 -> 264 bytes tgl | 2 +- 8 files changed, 114 insertions(+), 19 deletions(-) delete mode 100644 tg-server.pub create mode 100644 tg-server.tglpub diff --git a/Makefile.in b/Makefile.in index 1fedab8..abe83a6 100644 --- a/Makefile.in +++ b/Makefile.in @@ -73,7 +73,7 @@ install: $(PRPL_LIBNAME) mkdir -m $(DIR_PERM) -p $(DESTDIR)$(PLUGIN_DIR_PURPLE) install -m $(FILE_PERM) $(PRPL_LIBNAME) $(DESTDIR)$(PLUGIN_DIR_PURPLE)/$(PRPL_NAME) mkdir -m $(DIR_PERM) -p $(DESTDIR)/etc/telegram-purple - install -m $(FILE_PERM) tg-server.pub $(DESTDIR)/etc/telegram-purple/server.pub + install -m $(FILE_PERM) tg-server.tglpub $(DESTDIR)/etc/telegram-purple/server.tglpub mkdir -m $(DIR_PERM) -p $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/16 install -m $(FILE_PERM) imgs/telegram16.png $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/16/telegram.png mkdir -m $(DIR_PERM) -p $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/22 @@ -88,7 +88,8 @@ local_install: .PHONY: uninstall uninstall: rm -f $(DESTDIR)$(PLUGIN_DIR_PURPLE)/$(PRPL_NAME) - rm -f $(DESTDIR)/etc/telegram-purple/server.pub + rm -f $(DESTDIR)/etc/telegram-purple/server.pub # TODO: Remove this in later versions + rm -f $(DESTDIR)/etc/telegram-purple/server.tglpub rm -f $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/16/telegram.png rm -f $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/22/telegram.png rm -f $(DESTDIR)$(DATA_ROOT_DIR_PURPLE)/pixmaps/pidgin/protocols/48/telegram.png diff --git a/README.md b/README.md index d2f05f3..141857d 100644 --- a/README.md +++ b/README.md @@ -72,16 +72,19 @@ This repository has submodules, so you need to clone recursively. sudo dnf install gcc openssl-devel glib2-devel libpurple-devel libwebp-devel +And the development files for gcrypt, probably `gcrypt-devel` or something. + ###### Debian / Ubuntu sudo apt-get install libgcrypt20-dev libssl-dev libpurple-dev libwebp-dev - ###### OpenSUSE sudo zypper install gcc glib glib-devel libpurple libpurple-devel zlib-devel openssl libopenssl-devel libwebp-devel +And the development files for gcrypt, probably `gcrypt-devel` or something. + #### 3. Compile and install @@ -188,6 +191,22 @@ Compiling with XCode is a little bit problematic, since it requires you to compi Discussion / Help ----------------- +#### Custom pubkeys + +As we want to avoid OpenSSL, it has become necessary to replace the PEM file format. This means that if you use a custom pubkey (which you really REALLY shouldn't be doing), you have to adapt, sorry. + +We no longer ship `tg-server.pub` (old format), but instead `tg-server.tlgpub` (new format). If you have a `.pub` and want to continue using telegram-purple, please use this (hopefully highly portable) tool: [pem2bignum](https://github.com/BenWiederhake/pem2bignum) + +You can also write your own conversion tool if you prefer. The format is really simple: + +1. `e`, the public exponent, encoded as big endian 32 bit fixed length (e.g. `0x00 01 00 01` for 65537) +2. `n_len`, the length of `n` in bytes, encoded as big endian 32 bit fixed length (e.g. `0x00 00 01 00` for a 2048-bit = 256-byte key) +3. `n_raw`, the raw modulus, encoded as big endian, using the previously indicated length (e.g. `0xC1 50 02 3E [248 bytes omitted] 21 79 25 1F` in the case of telegram's public RSA key.) + +If you are interested in developing a non-OpenSSL-licensed converter, look into [insane-triangle-banana](https://github.com/BenWiederhake/insane-triangle-banana). + +#### Group chat + Telegram group chat for telegram-purple or libtgl related discussions or questions: - https://telegram.me/joinchat/01fb53f301b67d3c7a5532908dfa9a89 diff --git a/telegram-base.c b/telegram-base.c index 02990ce..15a7d8b 100644 --- a/telegram-base.c +++ b/telegram-base.c @@ -51,6 +51,64 @@ #define STATE_FILE_MAGIC 0x28949a93 #define SECRET_CHAT_FILE_MAGIC 0x37a1988a +static gboolean read_ui32 (int fd, unsigned int *ret) { + typedef char check_int_size[(sizeof (int) >= 4) ? 1 : -1]; + (void) sizeof (check_int_size); + + unsigned char buf[4]; + if (4 != read (fd, buf, 4)) { + return 0; + } + /* Ugly but works. */ + *ret = 0; + *ret |= buf[0]; + *ret <<= 8; + *ret |= buf[1]; + *ret <<= 8; + *ret |= buf[2]; + *ret <<= 8; + *ret |= buf[3]; + return 1; +} + +int read_pubkey_file (const char *name, struct rsa_pubkey *dst) { + /* Just to make sure nobody reads garbage. */ + dst->e = 0; + dst->n_len = 0; + dst->n_raw = NULL; + + int pubkey_fd = open (name, O_RDONLY); + if (pubkey_fd < 0) { + return 0; + } + + unsigned int e; + unsigned int n_len; + if (!read_ui32 (pubkey_fd, &e) || !read_ui32 (pubkey_fd, &n_len) // Ensure successful reads + || n_len < 128 || n_len > 1024 || e < 5) { // Ensure (at least remotely) sane parameters. + close (pubkey_fd); + return 0; + } + + unsigned char *n_raw = malloc (n_len); + if (!n_raw) { + close (pubkey_fd); + return 0; + } + + if (n_len != read (pubkey_fd, n_raw, n_len)) { + free (n_raw); + close (pubkey_fd); + return 0; + } + close (pubkey_fd); + + dst->e = e; + dst->n_len = n_len; + dst->n_raw = n_raw; + return 1; +} + void read_state_file (struct tgl_state *TLS) { char *name = 0; if (asprintf (&name, "%s/%s", TLS->base_path, "state") < 0) { @@ -406,13 +464,14 @@ gchar *get_download_dir (struct tgl_state *TLS) { return dir; } -void assert_file_exists (PurpleConnection *gc, const char *filepath, const char *format) { +gboolean assert_file_exists (PurpleConnection *gc, const char *filepath, const char *format) { if (!g_file_test (filepath, G_FILE_TEST_EXISTS)) { gchar *msg = g_strdup_printf (format, filepath); purple_connection_error_reason (gc, PURPLE_CONNECTION_ERROR_CERT_OTHER_ERROR, msg); g_free (msg); - return; + return 0; } + return 1; } void export_auth_callback (struct tgl_state *TLS, void *extra, int success) { diff --git a/telegram-base.h b/telegram-base.h index 4006895..ddf3740 100644 --- a/telegram-base.h +++ b/telegram-base.h @@ -22,6 +22,14 @@ #include "telegram-purple.h" +struct rsa_pubkey { + unsigned int e; + unsigned int n_len; + unsigned char *n_raw; +}; + +gboolean read_pubkey_file (const char *name, struct rsa_pubkey *dst); + void read_state_file (struct tgl_state *TLS); void read_auth_file (struct tgl_state *TLS); void write_auth_file (struct tgl_state *TLS); @@ -37,7 +45,7 @@ void telegram_export_authorization (struct tgl_state *TLS); gchar *get_config_dir (struct tgl_state *TLS, char const *username); gchar *get_download_dir (struct tgl_state *TLS); -void assert_file_exists (PurpleConnection *gc, const char *filepath, const char *format); +gboolean assert_file_exists (PurpleConnection *gc, const char *filepath, const char *format); int tgp_visualize_key (struct tgl_state *TLS, unsigned char* sha1_key); void tgp_create_group_chat_by_usernames (struct tgl_state *TLS, const char *title, diff --git a/telegram-purple.c b/telegram-purple.c index 980374a..4aa2303 100644 --- a/telegram-purple.c +++ b/telegram-purple.c @@ -89,7 +89,7 @@ void on_user_get_info (struct tgl_state *TLS, void *info_data, int success, stru PurpleGroup *tggroup; const char *config_dir = "telegram-purple"; -const char *pk_path = "/etc/telegram-purple/server.pub"; +const char *pk_path = "/etc/telegram-purple/server.tglpub"; struct tgl_update_callback tgp_callback = { .logprintf = debug, @@ -575,12 +575,28 @@ static void tgprpl_login (PurpleAccount * acct) { TLS->base_path = get_config_dir(TLS, purple_account_get_username (acct)); tgl_set_download_directory (TLS, get_download_dir(TLS)); - assert_file_exists (gc, pk_path, "Error, server public key not found at %s." - " Make sure that Telegram-Purple is installed properly."); + if (!assert_file_exists (gc, pk_path, "Error, server public key not found at %s." + " Make sure that Telegram-Purple is installed properly.")) { + /* Already reported. */ + return; + } + debug ("base configuration path: '%s'", TLS->base_path); + struct rsa_pubkey the_pubkey; + if (!read_pubkey_file (pk_path, &the_pubkey)) { + char *cause = g_strdup_printf ("Unable to sign on as %s: Missing file %s.", + purple_account_get_username (acct), pk_path); + purple_connection_error_reason (gc, PURPLE_CONNECTION_ERROR_INVALID_SETTINGS, cause); + purple_notify_message (_telegram_protocol, PURPLE_NOTIFY_MSG_ERROR, cause, + "Make sure telegram-purple is installed properly,\n" + "including the .tglpub file.", NULL, NULL, NULL); + g_free (cause); + return; + } + tgl_set_verbosity (TLS, 4); - tgl_set_rsa_key (TLS, pk_path); + tgl_set_rsa_key_direct (TLS, the_pubkey.e, the_pubkey.n_len, the_pubkey.n_raw); tgl_set_ev_base (TLS, conn); tgl_set_net_methods (TLS, &tgp_conn_methods); diff --git a/tg-server.pub b/tg-server.pub deleted file mode 100644 index 5e38bb0..0000000 --- a/tg-server.pub +++ /dev/null @@ -1,8 +0,0 @@ ------BEGIN RSA PUBLIC KEY----- -MIIBCgKCAQEAwVACPi9w23mF3tBkdZz+zwrzKOaaQdr01vAbU4E1pvkfj4sqDsm6 -lyDONS789sVoD/xCS9Y0hkkC3gtL1tSfTlgCMOOul9lcixlEKzwKENj1Yz/s7daS -an9tqw3bfUV/nqgbhGX81v/+7RFAEd+RwFnK7a+XYl9sluzHRyVVaTTveB2GazTw -Efzk2DWgkBluml8OREmvfraX3bkHZJTKX4EQSjBbbdJ2ZXIsRrYOXfaA+xayEGB+ -8hdlLmAjbCVfaigxX0CDqWeR1yFL9kwd9P0NsZRPsmoqVwMbMu7mStFai6aIhc3n -Slv8kg9qv1m6XHVQY3PnEw+QQtqSIXklHwIDAQAB ------END RSA PUBLIC KEY----- diff --git a/tg-server.tglpub b/tg-server.tglpub new file mode 100644 index 0000000000000000000000000000000000000000..2e42cf9f6bd9c42ed885685a957dd5da6c3e0ba9 GIT binary patch literal 264 zcmV+j0r&m@0RRC20098OPy#+LaNBu>-q2)qoc_-W^C;$;LE7}z@EcQsHKzF=kBce} z$-0*y&NVLl_Qhxq{6b6CG=@n6-V00C)SpgR0x;vQm)Ts48AK~Q3J}=!V?XTe){<&} zZL1C2eMNtss2hZ3{MP^e?GZo`-;uys%I&Y0Vqa{Q?8iqXRcSQucpZjoH1HAp8Q$&F4y6{E`o9zgfCmbx>n- O=MxW*LfVocc_km3zkF~2 literal 0 HcmV?d00001 diff --git a/tgl b/tgl index ed4e304..391806c 160000 --- a/tgl +++ b/tgl @@ -1 +1 @@ -Subproject commit ed4e304be425afecdf954e3d88fae98b80e6ff50 +Subproject commit 391806c60e36f60352abfccf05392f31fa0ba184