openwall / john

John the Ripper jumbo - advanced offline password cracker, which supports hundreds of hash and cipher types, and runs on many operating systems, CPUs, GPUs, and even some FPGAs
https://www.openwall.com/john/
Other
10.37k stars 2.11k forks source link

Telegram Desktop 2.1.14+ support #4387

Open madeonukraine opened 4 years ago

madeonukraine commented 4 years ago

Hello, I can't get a hash from the telegrams of the desktop version, please tell me how to do it correctly, described in more detail here

claudioandre-br commented 4 years ago

The GitHub issues are primarily to keep track of bugs or other shortcomings of our software, and fix those. It is not to help individual users with their specific tasks. To receive user support from the community, please use the john-users mailing list instead.

solardiz commented 4 years ago

@madeonukraine I checked out your referenced hashcat forum postings. First you reported what might be a problem with telegram2john.py, but you were using Python 2.7. Then you wrote "use python3 and have the same problem", but I expect it's not literally the same output from the script. So can you please post in here the actual output from your latest attempts at using the script with Python 3? Thanks!

solardiz commented 4 years ago

@madeonukraine Can you show us what files are inside your "Telegram Desktop" directory? What version of Telegram Desktop are you using?

The "Permission denied" error is a result of trying to process the directory as an XML file, which the script falls back to after its call to process_tdfs_file() on the directory fails. So apparently whatever is in that directory on your system is not recognized by our script. Perhaps it's a newer version of "Telegram Desktop", which we need to add support for.

solardiz commented 4 years ago

@madeonukraine Can you show what's inside the "tdata" directory?

BTW, please don't quote your translated versions of my questions. (Edit: I've just removed that from your comments.)

madeonukraine commented 4 years ago

@solardiz can help how do it?

solardiz commented 4 years ago

@madeonukraine dir tdata

philsmd commented 4 years ago

Since it seems we do not get much info from the user very quickly, I just decided to troubleshoot this myself a little bit (remember that the question was first asked in the hashcat forum and I kind of tought that the user has enough info and is convinced that it's a hash extraction problem with telegram2john, maybe I was wrong about the user info at least ... because there is little info about the files here for now).

So I've now investigated this a little bit and many interesting things came up from my little research:

The first interesting thing I've discovered quite quickly is that this D877F783D5D3EF8C directory (see https://github.com/openwall/john/blob/26cf9821e3868d5ee65754689b67446e6e723a38/run/telegram2john.py#L96) actually has a dir name that is derived by it's dataName and that there could be some alternatives D877F783D5D3EF8C0 and D877F783D5D3EF8C1 mainly (maybe also D877F783D5D3EF8Cs, see below). So telegram2john should probably also allow these alternatives.

But more interestingly, it turns out that D877F783D5D3EF8C stands for "data" and it it's the first 8 bytes of the md5 of the string "data" (without quotes), but the bytes are not in the "normal" order:

$ echo -n data | md5sum
8d777f385d3dfec8815d20f7496026dc

if we take the first half (first 8 bytes) of it 8d777f385d3dfec8 and change the order of the hex converted output, swapping the first byte (here I start counting with 1, not 0) with the second, byte 3 with 4, byte 5 with 6, ... (so basically just a different/unusual byte order for MD5 hashes) and therefore we get d877f783d5d3ef8c.

It's funny that this doesn't turn up with a simple google search and isn't documented anywhere (it seems). I would suggest having a comment also in the telegram2john source code, just in case.


back to the original problem. I've now tested with the Telegram Desktop (2.4.3) windows application (tsetup.2.4.3.exe) within a virtual machine without connection to the internet (maybe not the best test, but it is what it is).

It turns out that the application can't be really used without a mobile phone number etc... but after installation and first launch, it seems to create the %APPDATA%/Telegram Destkop/tdata/ directory.

The interesting thing is that within this directory I do not have the D877F783D5D3EF8C directory... but, surprisingly, I have a key_datas file. I'm pretty sure this file is now very important (for newer versions of Telegram Desktop).

This file (key_datas) contains the header TDF$ (but again, most other Telegram Desktop Files, is this what TDF stands for ?, have this file magic).

I tried to run telegram2john with this file and I got a hash. Yeah, this is not a joke ! so I tried to crack it with empty password (and other attempts too) and failed, it didn't crack.

I've also deleted the tdata folder and on new launch a new key_datas file was generated, with different content (different salt and different encryptedKey, was my assumption).

Later on I've checked the Telegram Desktop source code that can be found here: https://github.com/telegramdesktop/tdesktop

It seems that these 2 (actually very recent) commits did change a lot with the files and also encryption:

https://github.com/telegramdesktop/tdesktop/commit/ad4afe9 from Jun 9 2020
"Move session data localstorage -> storage_account."
(most interesting new function is CreateLocalKey)

https://github.com/telegramdesktop/tdesktop/commit/6fc5e22 from Jun 15 2020
"Allow several accounts in Core::App."

With this diffs I discovered that the new key_datas (or better said "key_" + dataName + "s") cracking works like this:

telegram_desktop_modern.pl ```perl #!/usr/bin/env perl # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # this version of Telegram uses the "key_datas" file (or "key_" + dataName + "s" file) # Telegram Desktop 2.1.14 (beta) / 2.2.0 (major release) or newer use strict; use warnings; use Digest::SHA qw (sha1 sha512); use Crypt::PBKDF2; use Crypt::Mode::ECB; # # Constants: # my $ITERATIONS_EMPTY_PASS = 1; my $ITERATIONS_STRONG = 100000; # kStrongIterationsCount my $AES256_IGE_BLOCK_SIZE = 16; # # Example: # # Example 1: my $pass = ""; my $iter = 1; # ITERATIONS_EMPTY_PASS my $salt = pack ("H*", "2370ac3bb4b8c7aa73f05a9e60fd2b0db5405fc78cb01b4a27dd190f03d6cf48"); my $data = pack ("H*", "84294a44ad833439b1ecaf56ca04fe15489525796041a2f6e809a82a8ce32abb75e04cd8b6e36532ac2ed8cc50a41c2aca5608a91de0c6f173e15e58027850683bf55da75662bfd12249c0ad52bdf4f434be42c6a71256da1b43e0a2fcb30145c4197977dea66bb6a2738984411f260b36700c974c81f4e0f3531e30560c25d50879c8f9b0d9109a67f15c97cb97a2958feef82098334537fdea116cc65aecac2e3859d2cc1332b1b9da653bc1f516c0a448816a7aa06b6150b3c7f4689ca3e05bd7b1c20ae20b59adf7ec379562d687f0393ce0029ae5295ed30e6e123c92a0b794789a79865ce47164d0d2e09878cb412ab8945b65c03df2ede6eab0c89be3bb60575d6cbd3a7ceeae565d5a9424fade2910373912878518c46191d19aa4ed"); # Example 2: # my $pass = ""; # my $iter = 1; # ITERATIONS_EMPTY_PASS # my $salt = pack ("H*", "16613898d763a5244bc97d5974ab65d18640562dd11d90b3626fc01fce1cb219"); # my $data = pack ("H*", "2a0f2a9f3548a223f1a93cac5618ea0c2fae859e98c3503da420b86682f5e3e3fc437ccfb9e2e324fc2664e23ad06d3109898ceee865eb46b9e5e913b76aca56eccc74457b0b4eac39737b99a8ad8bd95b0919e72fc09b9a28e659921d0a870fa40c31b74a3154ed5e5050326fd7abecef63eeb3a9d91b5684bca0b55551b2938fa68bb5be4b4c6741865de79376202d3bbb5ee900f521103e6229eca291b0844391e301eb66f503c5cbd17a9baf657aac6e6a764d0578f1f4a8ab6fe7d5b76c9df8e01ea627993f85ec659f8c6ca28ea4fb720dc488795d787cdd3c707558483ebdefcd0fb92955caae6d9472d3c1e97342dba67969b208c07a92b80ecb0f7cb8ad7143bff46d29d11e6bb185eec2acb138ddc2f6c28851dc0d8854be5b28cd"); # Example 3: # my $pass = ""; # my $iter = 1; # ITERATIONS_EMPTY_PASS # my $salt = pack ("H*", "060a3b87c406490576ef9620718e9accfa43565f71ab7e46476c53a36548fd1a"); # my $data = pack ("H*", "b7b3c7c746460eff72fc128cfd2b97b8faf54ece4b0eccc89ec6f903668b51378af8df2d573f87e862934a3fa96d8c187128f849921c437b851ca8108849e858dd08628151538fe8a05bca49f27af600668945fc28c793bd4bb023fe4d4b8ff0f27001688a9c98f740f544feba6905944c918dc016fad12e257e42d61e2c85fc2200a98f0548d4a5b33148d9ea6b017e33d7a6b9125a8d026148d07db0dacea7426012aeb18c9b1215acce87b8e247e9434dd4324beba3dace0510e64e686b76665ca46c06824e21d234d5914256e84fba3d15cd8fa881f3269d22ba525f14028f97cd8b21a4439c432bcd206f502718b919cf5dd934185a3ab3871987b9e8287716a903bed570923254fd2db85e711b4d9843ceeb222a739c72120c14369687"); # # Helper functions: # sub exclusive_or { my $in1 = shift; my $in2 = shift; # MIN () function (should always be 16 for us): # my $len = (length ($in1) <= length ($in2)) ? length ($in2) : length ($in1); # padding if input not multiple of block size: # $in1 .= "\x00" x ($AES256_IGE_BLOCK_SIZE - $len); # $in2 .= "\x00" x ($AES256_IGE_BLOCK_SIZE - $len); my $out = ""; for (my $i = 0; $i < $AES256_IGE_BLOCK_SIZE; $i++) # $i < $len { $out .= chr (ord (substr ($in1, $i, 1)) ^ ord (substr ($in2, $i, 1))); } return $out; } sub aes256_decrypt_ige { my $key = shift; my $iv = shift; my $in = shift; my $x_prev = substr ($iv, 0, $AES256_IGE_BLOCK_SIZE); my $y_prev = substr ($iv, $AES256_IGE_BLOCK_SIZE, $AES256_IGE_BLOCK_SIZE); my $m = Crypt::Mode::ECB->new ('AES', 0); my $out = ""; for (my $i = 0; $i < length ($in); $i += $AES256_IGE_BLOCK_SIZE) { my $x = substr ($in, $i, $AES256_IGE_BLOCK_SIZE); my $y_xor = exclusive_or ($x, $y_prev); my $y_final = $m->decrypt ($y_xor, $key); # $y_final .= "\x00" x ($AES256_IGE_BLOCK_SIZE - length ($y_final)); my $y = exclusive_or ($y_final, $x_prev); $x_prev = $x; $y_prev = $y; $out .= $y; } return $out; } # # Start: # my $sha512_hash = sha512 ($salt . $pass . $salt); # this is new in latest versions my $iterations = $iter; # the actual way how Telegram Desktop works: # my $iterations = $ITERATIONS_STRONG; # if (length ($pass) == 0) # { # $iterations = $ITERATIONS_EMPTY_PASS; # 1 iteration only if "no password" was set # } # PBKDF2-HMAC-SHA512 instead of PBKDF2-HMAC-SHA1 (from older versions): my $pbkdf = Crypt::PBKDF2->new ( hasher => Crypt::PBKDF2->hasher_from_algorithm ('HMACSHA2', 512), iterations => $iterations, output_len => 136 # or 256 would be the whole key length ); my $authkey = $pbkdf->PBKDF2 ($salt, $sha512_hash); my $data_a = "\x00" x 48; my $data_b = "\x00" x 48; my $data_c = "\x00" x 48; my $data_d = "\x00" x 48; my $message_key = substr ($data, 0, 16); my $message = substr ($data, 16); substr ($data_a, 0, 16) = $message_key; # memcpy () substr ($data_b, 16, 16) = $message_key; substr ($data_c, 32, 16) = $message_key; substr ($data_d, 0, 16) = $message_key; substr ($data_a, 16, 32) = substr ($authkey, 8, 32); substr ($data_b, 0, 16) = substr ($authkey, 40, 16); substr ($data_b, 32, 16) = substr ($authkey, 56, 16); substr ($data_c, 0, 32) = substr ($authkey, 72, 32); substr ($data_d, 16, 32) = substr ($authkey, 104, 32); my $sha1_a = sha1 ($data_a); my $sha1_b = sha1 ($data_b); my $sha1_c = sha1 ($data_c); my $sha1_d = sha1 ($data_d); my $aes_key = substr ($sha1_a, 0, 8) . # 8 + 12 + 12 = 32 substr ($sha1_b, 8, 12) . substr ($sha1_c, 4, 12); my $aes_iv = substr ($sha1_a, 8, 12) . # 12 + 8 + 4 + 8 = 32 substr ($sha1_b, 0, 8) . substr ($sha1_c, 16, 4) . substr ($sha1_d, 0, 8); # AES256 IGE decrypt: my $decrypted_data = aes256_decrypt_ige ($aes_key, $aes_iv, $message); # "checksum" of raw data: my $hash = sha1 ($decrypted_data); $hash = substr ($hash, 0, 16); # compare: if ($hash eq $message_key) { print "Password found: '$pass'\n"; exit (0); } exit (1); ```
solardiz commented 4 years ago

Thanks @philsmd. Somehow @madeonukraine deleted some of their comments. One of the comments contained this:

version 2.3.1
10/01/2020 12:03 PM <DIR>.
10/01/2020 12:03 <DIR> ..
07/27/2020 16:11 60 A44DFD4ADEDD1B82s
09/16/2020 08:56 <DIR> A7FDF864FBC10B77
09/16/2020 08:56 1 116 A7FDF864FBC10B77s
10/01/2020 12:03 <DIR> D877F783D5D3EF8C
11/22/2018 06:55 1 372 D877F783D5D3EF8C1
07/14/2020 01:28 PM <DIR> dumps
08/18/2020 10:44 10 748 E82C3665D6F18580s
07/14/2020 01:29 PM <DIR> emoji
09/30/2020 10:22 227 484 F9DF07E356484A5Bs
09/16/2020 08:56 388 key_datas
31.10.2018 14:42 2 679 log.txt
09/16/2020 09:36 28 prefix
10/01/2020 12:03 1 456 settingss
30.10.2018 21:12 390 shortcuts-custom.json
08/25/2020 17:37 2 838 shortcuts-default.json
07/14/2020 01:29 PM <DIR> tdata
07/14/2020 01:28 PM <DIR> tdummy
10/30/2018 09:12 PM 8 usertag
07/14/2020 01:28 PM <DIR> user_data
08/25/2020 05:38 PM <DIR> user_data # 2
10/01/2020 12:03 0 working
              13 files 248 567 bytes
              10 folders 115 040 845 824
madeonukraine commented 4 years ago

""""I've also deleted the tdata folder and on new launch a new key_datas file was generated, with different content (different salt and different encryptedKey, was my assumption).> """

it finds the hash successfully, but does not pick up the password, for the test I set the password to 123, but john or hashcat cannot find it by this hash

magnumripper commented 4 years ago

john or hashcat cannot find it by this hash

That's because the algorithm changed.

the most interesting thing is the PBKDF2-HMAC-SHA512 change (instead of PBKDF2-HMAC-SHA1), the default iteration count changes (I'm still pretty sure the iteration count isn't stored anywhere, it's actually determined by the password, if no password or 0-length password, only 1 iteration is used), and the initial sha512 ($salt . $pass . $salt) hashing of the password. The decryption seems to still work the same way.

We need to implement these changes.

magnumripper commented 4 years ago

@madeonukraine if you can supply that hash you got as a test vector for us, it would help!

philsmd commented 4 years ago

Thanks @solardiz for this file list.

For me it's not clear if this directory/file listing is recursive (i.e. including subdirs. I don't think so, there would probably be more files then). I just double-checked and my key_datas file is within the tdata directory (no such file outside tdata).

If this file listing is (only) the content of the tdata directory as you (@solardiz) have requested above from the user ... then @madeonukraine had a tdata subfolder within the tdata folder (not sure why, maybe a manual backup ? or is this always the case for a "normal"/used user account ?).

BTW for me it is like this (%APPDATA%\Telegram Desktop\):

DIR  tdata
FILE log.txt
FILE Telegram.exe
FILE unins000.dat
FILE unins000.exe
FILE Updater.exe

The %APPDATA%\Telegram Desktop\tdata\ folder instead looks like this:

DIR  dumps
DIR  emoji
FILE 237347D650DB09F3s
FILE key_datas
FILE settingss
FILE shortcuts-custom.json
FILE shortcuts-default.json
FILE usertag

(dumps dir is empty for me and the emoji folder contains cache_* files with a number after "cache_" e.g. cache_18_0)

237347D650DB09F3s is always a new random file it seems, if I delete the tdata folder (also see GenerateKey () from https://github.com/telegramdesktop/tdesktop/blob/744eccc51eb0705ae657dcd88ce4f15bd1a332f3/Telegram/SourceFiles/storage/details/storage_file_utilities.cpp#L55-L67 where 16 + 1 characters are generated randomly and added to the base folder name).

Again, I want to emphasize that this is not a Telegram Desktop profile that is used normally (or used at all), it's a new installation and without even completing the initial login/verification step. So a normal/used folder could look much different (and maybe even have a tdata subfolder, dunno).

This is also interesting, if we apply the byte swap explained above to A7FDF864FBC10B77 we get :

a7fdf864fbc10b77 -> 7adf8f46bf1cb077

and we can see that this matches with the data#2 dataName:

$ echo -n data#2 | md5sum
7adf8f46bf1cb07727da1a16eac309e0

You can also crack this with half MD5:

7adf8f46bf1cb077:data#2

This probably means that the A7FDF864FBC10B77 folder could in general maybe also contain a map* file (or only older versions of Telegram Desktop have map files ?), so telegram2john might need to be updated to test these folders too ? but we still need to confirm this.

It's also interesting that only two files, namely A7FDF864FBC10B77s has a corresponding A7FDF864FBC10B77 (dataName = "data#2") dir (probably associated to a different user account) and D877F783D5D3EF8C1 has a corresponding dir D877F783D5D3EF8C (dataName = "data"). All other random 17 (16 + 1) hex-char (random) files have no corresponding dir. So these other ones probably use random keys for the file name (see the GenerateKey () function explained above).

Just in case that this is needed or picked up by search engines etc, here are some other examples (data#n):

data    : D877F783D5D3EF8C -> 8d777f385d3dfec8 (substr (md5_hex ("data"),    0, 16))
data#2  : A7FDF864FBC10B77 -> 7adf8f46bf1cb077 (substr (md5_hex ("data#2"),  0, 16))
data#3  : F8806DD0C461824F -> 8f08d60d4c1628f4 (substr (md5_hex ("data#3"),  0, 16))
data#4  : C2B05980D9127787 -> 2c0b95089d217778 (substr (md5_hex ("data#4"),  0, 16))
data#5  : 0CA814316818D8F6 -> c08a411386818d6f (substr (md5_hex ("data#5"),  0, 16))
data#6  : 45D0FC5B5101406D -> 540dcfb5151004d6 (substr (md5_hex ("data#6"),  0, 16))
data#7  : 93987688214F8E69 -> 3989678812f4e896 (substr (md5_hex ("data#7"),  0, 16))
data#8  : FEC2F64A7E75EEE7 -> ef2c6fa4e757ee7e (substr (md5_hex ("data#8"),  0, 16))
data#9  : AE1FA186729C99BE -> eaf11a6827c999eb (substr (md5_hex ("data#9"),  0, 16))
data#10 : 70FA7BB980698B1B -> 07afb79b0896b8b1 (substr (md5_hex ("data#10"), 0, 16))

The file size of the key_datas file is also interesting, exactly the same size as mine ! so I guess this can be used for cracking with the modified algo expained above.

It would be interesting to know if there could/should be also key_data#2s or similar files... All this needs to be tested with an actual account and after the mobile phone number verification. Best would be if even several accounts (more than one phone number needed ?!) would be used to confirm which files are automatically generated etc (also see this: https://github.com/telegramdesktop/tdesktop/blob/744eccc51eb0705ae657dcd88ce4f15bd1a332f3/Telegram/SourceFiles/main/main_account.cpp#L38-L45 for the "#" + index appending).

It would also be great if @madeonukraine could tell us if this was an "upgraded" version/folder/account... maybe some files are kept as backup if you changed the Telegram Desktop version starting with older versions than 2.1.14 (or 2.2.0 release). All these details could help us a lot here to figure out which files are important and which files we can use to check/crack the password the user set.

BTW, I just found this by accident on github https://github.com/sergava/tg-session-chrome-stealer/blob/855c97258ea4615eb984934991d84c2c40fb667b/tgsend.py#L136-L146 when searching for key_datas, so maybe we are spot on that key_datas is an "important" file ;)

Thx

philsmd commented 4 years ago

@madeonukraine please share the hash that you got. It isn't sensitive information as far as we know. and could help a lot to confirm the 100000 iterations and algorithm details...

It's also good that you already set a non-zero password, i.e. 123. It would be great if you post the hash here. Thx

madeonukraine commented 4 years ago

@philsmd

$telegram$1*4000*f8a97519eda3a80b79a83fde2f7aa5bd453e0f148fc5995cf054c2e697a13816*aa6c7bccf4f32611974c61fdef63dcda85114a7fbdc6cc1184ae7793758f5f7c4f007382bccec17ad9e4af29c9adddae91dc1469550c8400903a8032dfb512053782f8203ca98de3ba02b253550dd91ab5da02940bf65f2a177ce36b2ab57f96ee108c397ce12f3fb5951468f6853e2628cc9b82250e9d8e28cd59b4a5692f856e06bda9ebc78a651916ce8700cfcd333d29f0ccc4fced374f773005460bc2b0e784d1c339c9d85135148f494c85708a990ab7e2720409a15900ad6d42b36e3244d507b67a17ee1a1547dce29dd5ef92b0e356ae9ad5696083c3591250996ab48bc59d64c6bda2cae1a5def57f299e24902af20adb9e8e986feb41edf13c2ad4fd04da97b33ee968c4b1f70fe8391405c14c791132627d49707da69567d3867e

Edit by @solardiz: added backticks around the hash so that it isn't mangled by GitHub's text formatting.

solardiz commented 4 years ago

If this file listing is (only) the content of the tdata directory as you (@solardiz) have requested above from the user

That request of mine is obviously irrelevant, because that listing I reposted was in a comment @madeonukraine had posted before my request for the tdata directory contents. It was posted in response to this request I made:

@madeonukraine Can you show us what files are inside your "Telegram Desktop" directory? What version of Telegram Desktop are you using?

And yes, that listing looks puzzling. Even the dates format is somehow inconsistent on different entries, so maybe @madeonukraine combined that listing from several pieces manually, or otherwise is it a feature of Windows (and of a filesystem used on Windows) that the date format could somehow depend on per-file properties? I don't know.

madeonukraine commented 4 years ago

Telegram version 2.4.3 . @magnumripper philsmd can take zip file in private messages my test telegram where i take this hash

philsmd commented 4 years ago

We probably should change the title of this issue to make it clear that already version 2.1.14 introduced this change.

Your example hash cracks for me with your pass/iter/salt/data configuration:

my $pass = "123";
my $iter = $ITERATIONS_STRONG; # 100000
my $salt = pack ("H*", "f8a97519eda3a80b79a83fde2f7aa5bd453e0f148fc5995cf054c2e697a13816");
my $data = pack ("H*", "aa6c7bccf4f32611974c61fdef63dcda85114a7fbdc6cc1184ae7793758f5f7c4f007382bccec17ad9e4af29c9adddae91dc1469550c8400903a8032dfb512053782f8203ca98de3ba02b253550dd91ab5da02940bf65f2a177ce36b2ab57f96ee108c397ce12f3fb5951468f6853e2628cc9b82250e9d8e28cd59b4a5692f856e06bda9ebc78a651916ce8700cfcd333d29f0ccc4fced374f773005460bc2b0e784d1c339c9d85135148f494c85708a990ab7e2720409a15900ad6d42b36e3244d507b67a17ee1a1547dce29dd5ef92b0e356ae9ad5696083c3591250996ab48bc59d64c6bda2cae1a5def57f299e24902af20adb9e8e986feb41edf13c2ad4fd04da97b33ee968c4b1f70fe8391405c14c791132627d49707da69567d3867e");

Full updated script (only example added):

telegram_desktop_modern_example123.pl ```perl #!/usr/bin/env perl # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # this version of Telegram uses the "key_datas" file (or "key_" + dataName + "s" file) # Telegram Desktop 2.1.14 (beta) / 2.2.0 (major release) or newer use strict; use warnings; use Digest::SHA qw (sha1 sha512); use Crypt::PBKDF2; use Crypt::Mode::ECB; # # Constants: # my $ITERATIONS_EMPTY_PASS = 1; my $ITERATIONS_STRONG = 100000; # kStrongIterationsCount my $AES256_IGE_BLOCK_SIZE = 16; # # Example: # # Example 1: # my $pass = ""; # my $iter = $ITERATIONS_EMPTY_PASS; # 1 # my $salt = pack ("H*", "2370ac3bb4b8c7aa73f05a9e60fd2b0db5405fc78cb01b4a27dd190f03d6cf48"); # my $data = pack ("H*", "84294a44ad833439b1ecaf56ca04fe15489525796041a2f6e809a82a8ce32abb75e04cd8b6e36532ac2ed8cc50a41c2aca5608a91de0c6f173e15e58027850683bf55da75662bfd12249c0ad52bdf4f434be42c6a71256da1b43e0a2fcb30145c4197977dea66bb6a2738984411f260b36700c974c81f4e0f3531e30560c25d50879c8f9b0d9109a67f15c97cb97a2958feef82098334537fdea116cc65aecac2e3859d2cc1332b1b9da653bc1f516c0a448816a7aa06b6150b3c7f4689ca3e05bd7b1c20ae20b59adf7ec379562d687f0393ce0029ae5295ed30e6e123c92a0b794789a79865ce47164d0d2e09878cb412ab8945b65c03df2ede6eab0c89be3bb60575d6cbd3a7ceeae565d5a9424fade2910373912878518c46191d19aa4ed"); # Example 2: # my $pass = ""; # my $iter = $ITERATIONS_EMPTY_PASS; # 1 # my $salt = pack ("H*", "16613898d763a5244bc97d5974ab65d18640562dd11d90b3626fc01fce1cb219"); # my $data = pack ("H*", "2a0f2a9f3548a223f1a93cac5618ea0c2fae859e98c3503da420b86682f5e3e3fc437ccfb9e2e324fc2664e23ad06d3109898ceee865eb46b9e5e913b76aca56eccc74457b0b4eac39737b99a8ad8bd95b0919e72fc09b9a28e659921d0a870fa40c31b74a3154ed5e5050326fd7abecef63eeb3a9d91b5684bca0b55551b2938fa68bb5be4b4c6741865de79376202d3bbb5ee900f521103e6229eca291b0844391e301eb66f503c5cbd17a9baf657aac6e6a764d0578f1f4a8ab6fe7d5b76c9df8e01ea627993f85ec659f8c6ca28ea4fb720dc488795d787cdd3c707558483ebdefcd0fb92955caae6d9472d3c1e97342dba67969b208c07a92b80ecb0f7cb8ad7143bff46d29d11e6bb185eec2acb138ddc2f6c28851dc0d8854be5b28cd"); # Example 3: # my $pass = ""; # my $iter = $ITERATIONS_EMPTY_PASS; # 1 # my $salt = pack ("H*", "060a3b87c406490576ef9620718e9accfa43565f71ab7e46476c53a36548fd1a"); # my $data = pack ("H*", "b7b3c7c746460eff72fc128cfd2b97b8faf54ece4b0eccc89ec6f903668b51378af8df2d573f87e862934a3fa96d8c187128f849921c437b851ca8108849e858dd08628151538fe8a05bca49f27af600668945fc28c793bd4bb023fe4d4b8ff0f27001688a9c98f740f544feba6905944c918dc016fad12e257e42d61e2c85fc2200a98f0548d4a5b33148d9ea6b017e33d7a6b9125a8d026148d07db0dacea7426012aeb18c9b1215acce87b8e247e9434dd4324beba3dace0510e64e686b76665ca46c06824e21d234d5914256e84fba3d15cd8fa881f3269d22ba525f14028f97cd8b21a4439c432bcd206f502718b919cf5dd934185a3ab3871987b9e8287716a903bed570923254fd2db85e711b4d9843ceeb222a739c72120c14369687"); # Example 4: my $pass = "123"; my $iter = $ITERATIONS_STRONG; # 100000 my $salt = pack ("H*", "f8a97519eda3a80b79a83fde2f7aa5bd453e0f148fc5995cf054c2e697a13816"); my $data = pack ("H*", "aa6c7bccf4f32611974c61fdef63dcda85114a7fbdc6cc1184ae7793758f5f7c4f007382bccec17ad9e4af29c9adddae91dc1469550c8400903a8032dfb512053782f8203ca98de3ba02b253550dd91ab5da02940bf65f2a177ce36b2ab57f96ee108c397ce12f3fb5951468f6853e2628cc9b82250e9d8e28cd59b4a5692f856e06bda9ebc78a651916ce8700cfcd333d29f0ccc4fced374f773005460bc2b0e784d1c339c9d85135148f494c85708a990ab7e2720409a15900ad6d42b36e3244d507b67a17ee1a1547dce29dd5ef92b0e356ae9ad5696083c3591250996ab48bc59d64c6bda2cae1a5def57f299e24902af20adb9e8e986feb41edf13c2ad4fd04da97b33ee968c4b1f70fe8391405c14c791132627d49707da69567d3867e"); # # Helper functions: # sub exclusive_or { my $in1 = shift; my $in2 = shift; # MIN () function (should always be 16 for us): # my $len = (length ($in1) <= length ($in2)) ? length ($in2) : length ($in1); # padding if input not multiple of block size: # $in1 .= "\x00" x ($AES256_IGE_BLOCK_SIZE - $len); # $in2 .= "\x00" x ($AES256_IGE_BLOCK_SIZE - $len); my $out = ""; for (my $i = 0; $i < $AES256_IGE_BLOCK_SIZE; $i++) # $i < $len { $out .= chr (ord (substr ($in1, $i, 1)) ^ ord (substr ($in2, $i, 1))); } return $out; } sub aes256_decrypt_ige { my $key = shift; my $iv = shift; my $in = shift; my $x_prev = substr ($iv, 0, $AES256_IGE_BLOCK_SIZE); my $y_prev = substr ($iv, $AES256_IGE_BLOCK_SIZE, $AES256_IGE_BLOCK_SIZE); my $m = Crypt::Mode::ECB->new ('AES', 0); my $out = ""; for (my $i = 0; $i < length ($in); $i += $AES256_IGE_BLOCK_SIZE) { my $x = substr ($in, $i, $AES256_IGE_BLOCK_SIZE); my $y_xor = exclusive_or ($x, $y_prev); my $y_final = $m->decrypt ($y_xor, $key); # $y_final .= "\x00" x ($AES256_IGE_BLOCK_SIZE - length ($y_final)); my $y = exclusive_or ($y_final, $x_prev); $x_prev = $x; $y_prev = $y; $out .= $y; } return $out; } # # Start: # my $sha512_hash = sha512 ($salt . $pass . $salt); # this is new in latest versions my $iterations = $iter; # the actual way how Telegram Desktop works: # my $iterations = $ITERATIONS_STRONG; # if (length ($pass) == 0) # { # $iterations = $ITERATIONS_EMPTY_PASS; # 1 iteration only if "no password" was set # } # PBKDF2-HMAC-SHA512 instead of PBKDF2-HMAC-SHA1 (from older versions): my $pbkdf = Crypt::PBKDF2->new ( hasher => Crypt::PBKDF2->hasher_from_algorithm ('HMACSHA2', 512), iterations => $iterations, output_len => 136 # or 256 would be the whole key length ); my $authkey = $pbkdf->PBKDF2 ($salt, $sha512_hash); my $data_a = "\x00" x 48; my $data_b = "\x00" x 48; my $data_c = "\x00" x 48; my $data_d = "\x00" x 48; my $message_key = substr ($data, 0, 16); my $message = substr ($data, 16); substr ($data_a, 0, 16) = $message_key; # memcpy () substr ($data_b, 16, 16) = $message_key; substr ($data_c, 32, 16) = $message_key; substr ($data_d, 0, 16) = $message_key; substr ($data_a, 16, 32) = substr ($authkey, 8, 32); substr ($data_b, 0, 16) = substr ($authkey, 40, 16); substr ($data_b, 32, 16) = substr ($authkey, 56, 16); substr ($data_c, 0, 32) = substr ($authkey, 72, 32); substr ($data_d, 16, 32) = substr ($authkey, 104, 32); my $sha1_a = sha1 ($data_a); my $sha1_b = sha1 ($data_b); my $sha1_c = sha1 ($data_c); my $sha1_d = sha1 ($data_d); my $aes_key = substr ($sha1_a, 0, 8) . # 8 + 12 + 12 = 32 substr ($sha1_b, 8, 12) . substr ($sha1_c, 4, 12); my $aes_iv = substr ($sha1_a, 8, 12) . # 12 + 8 + 4 + 8 = 32 substr ($sha1_b, 0, 8) . substr ($sha1_c, 16, 4) . substr ($sha1_d, 0, 8); # AES256 IGE decrypt: my $decrypted_data = aes256_decrypt_ige ($aes_key, $aes_iv, $message); # "checksum" of raw data: my $hash = sha1 ($decrypted_data); $hash = substr ($hash, 0, 16); # compare: if ($hash eq $message_key) { print "Password found: '$pass'\n"; exit (0); } exit (1); ```

Now we could think about what we should do with empty passwords. I think it makes little sense to run them normally with the hash cracker (JTR / hashcat). A dynamic switch to only 1 iteration would be needed based on the password length and only the special case (length 0) has this differing algo parameters. My suggestion here is that we could either let telegram2john already detect this empty password (but this could make the script a little bit slower and adds additional code, so there are some advantages and disadvantages to it) or just make an initial check for the empty password and only 1 iteration within the crackers themself when parsing these hashes (also extra code needed). We could also just ignore them because the user probably will notice that the Telegram Desktop application will start without asking for a password (but some users might still get a hash which is uncrackable if not the right - dynamic - iteration count is used within the cracker, therefore this solution isn't really user-friendly).

I tend for the solution where already the python extraction script checks for an empty password. But again, it has some drawbacks (little slower, extra code needed, especially AES-IGE decrypt could be annoying to implement in python maybe. tgcrypto or implement our own function like I did in the perl POC ?).

I think we should also decide what hash format we choose (my suggestion is $telegram$2*iter*hex_salt*hex_data to allow for iteration count changes in the future).

The other question is how we should update telegram2john to find/detect/check the different files ... maybe for now the best solution would be to force the user to specify the full path to the map* or key_* files. This way it's a little bit less user-friendly, but the user has the option to specify any file and telegram2john can do the file/magic/checksum verification.

One way could be to dermine the algo by only checking if the file starts with "key_" and then the 100000 iteration version (new one using PBKDF2-HMAC-SHA512) is used (so file name is kind of important, furthermore the Android .xml variant could be detected by the file extension or just if the file does not start with TDF$).

A maybe better way (or might this be a wrong assumption ? Is this safe ?) for detecting the new 100000 iterations variant could be to check the AppVersion in the header (it's the next 4 bytes after the "TDF$" magic), I guess: https://github.com/telegramdesktop/tdesktop/blob/dev/Telegram/SourceFiles/core/version.h#L25

This was the version when the change occurred 2.1.14 (=> Appversion = 2001014): https://github.com/telegramdesktop/tdesktop/blob/a8d0b80baa8a26438d5cba986e0e83423b4b4dc2/Telegram/SourceFiles/core/version.h#L25

All in all, the user has to specify either an userconfing.xml file (only for the Android App) or a new key_* file or an old map* file directly (no Telegram Desktop folder allowed anymore, because there are just too many possibilities !?).

I've now also double checked if Android still uses the same algo and I've found no changes there: https://github.com/TelegramOrg/Telegram-Android/blob/d3ad1316c4d13cc884d733b34ab3981b461df16f/TMessagesProj/src/main/java/org/telegram/messenger/SharedConfig.java#L370-L373 (even if there were several recent changes to the Android App).

Thx

@madeonukraine the only thing that would help us a lot here is that you answer the questions we asked above and that you try to resolve the doubts that we still have, e.g. why is your key_datas file not in tdata directory, what is the exact directory structure (which subfolders, which files are in which directory) for you ? Do you still have some map* (map0, map1, maps, map) files inside some directories (search for them please) that can be run with telegram2john ? Is this an upgraded account or is this installation a fresh installation after the key_datas change ? Is there a tdata directory within the tdata directory ? Why so different date formats ? Why are there sooo old files ? It's a very weird mix of files that have different date formats and should be inside different directories etc ? Do you have multiple accounts ? Can you create multiple accounts for testing ? Could you also please backup the whole directory and save it securely, delete the tdata folder after verifying that everything is correctly backed up and try to create a new account ? Does the directories and subfolders now look differently ? etc etc etc (all the questions we asked in the previous posts)

madeonukraine commented 4 years ago

1 - have key_datas file on C:\1\2\tdata\key_datas 2 - have C:\1\2\tdata\D877F783D5D3EF8C\maps map* files (map0, map1, maps, map) 3 - download last version Telegram Portable from official site 4 - its new test account 5 - yes i have another account but in test not have

DIR 15.10.2020 11:02

. 15.10.2020 11:02 .. 08.10.2020 16:53 108 64A4D2E7B96990B7s 08.10.2020 16:56 10 732 94055B2E91CC327Es 08.10.2020 16:54 108 C98F61FCD821C65Es 15.10.2020 10:58 D877F783D5D3EF8C 09.10.2020 14:27 604 D877F783D5D3EF8Cs 08.10.2020 16:53 dumps 08.10.2020 16:53 emoji 13.10.2020 12:08 227 516 FD9B6EA6BE739949s 15.10.2020 10:56 670 hashJTRforTelegram.txt 08.10.2020 16:56 388 key_datas 08.10.2020 17:44 28 prefix 15.10.2020 10:58 1 520 settingss 08.10.2020 16:53 404 shortcuts-custom.json 08.10.2020 16:53 2 908 shortcuts-default.json 08.10.2020 16:55 tdummy 14.05.2019 20:07 5 203 telegram2john.py 08.10.2020 16:53 8 usertag 08.10.2020 16:56 user_data

sergava commented 4 years ago

The "Permission denied" error is a result of trying to process the directory as an XML file, which the script falls back to after its call to process_tdfs_file() on the directory fails. So apparently whatever is in that directory on your system is not recognized by our script. Perhaps it's a newer version of "Telegram Desktop", which we need to add support for.

I have the same issue. Telegram version 2.4.3. Folder structure is default and has no anomalies. Using command "python telegram2john.py D:\Telegram Desktop" gives me this error:

Traceback (most recent call last): File "telegram2john.py", line 179, in process_xml_file(sys.argv[j]) File "telegram2john.py", line 142, in process_xml_file tree = ET.parse(filename) File "C:\Users\xsoi\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 1202, in parse tree.parse(source, parser) File "C:\Users\xsoi\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 584, in parse source = open(source, "rb") PermissionError: [Errno 13] Permission denied: 'D:\Telegram Desktop'

I'm sorry if this issue was resolved earlier, but I didn't find it. Could you, please, help me?

philsmd commented 4 years ago

@madeonukraine What happens if you run telegram2john with your C:\1\2\tdata\D877F783D5D3EF8C\maps file ? Does it produce a "hash" or does it not work with that file ? My guess is that we need to stick to the key_* files (which most likely replace the old map0/map1 files and this new maps is very different), but again we need to confirm this first if there are some alternative files that can be used (even from backups, old settings etc) or even a file that uses a different algo that can be cracked faster etc (not sure if such an alternative exists, my guess is that the Telegram devs made sure that you first and always need to decrypt the key_datas file, before other data can be decrypted, otherwise it would be a weakness).

I've now double-checked if the Python check for empty passwords (i.e. Telegram profiles that are not password protected, no password set) is feasible and easy to add and it turns out it's true: it's neither difficult nor slow at all:

With tgcrypto:

telegram_desktop_modern_tgcrypto.py ```python #!/usr/bin/env python3 from tgcrypto import ige256_decrypt from hashlib import sha1, sha512, pbkdf2_hmac from binascii import unhexlify # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # Goal of this little script is: # to test for encrypted Telegram Desktop v2.1.14+ encrypted data, # encrypted with an *empty password* # The data usually comes from key_datas (or "key_" + dataName + "s" files) # # Example: # # Example 1: path = "key_datas" # fake path (set this variable to the full file path) salt = unhexlify ("2370ac3bb4b8c7aa73f05a9e60fd2b0db5405fc78cb01b4a27dd190f03d6cf48") data = unhexlify ("84294a44ad833439b1ecaf56ca04fe15489525796041a2f6e809a82a8ce32abb75e04cd8b6e36532ac2ed8cc50a41c2aca5608a91de0c6f173e15e58027850683bf55da75662bfd12249c0ad52bdf4f434be42c6a71256da1b43e0a2fcb30145c4197977dea66bb6a2738984411f260b36700c974c81f4e0f3531e30560c25d50879c8f9b0d9109a67f15c97cb97a2958feef82098334537fdea116cc65aecac2e3859d2cc1332b1b9da653bc1f516c0a448816a7aa06b6150b3c7f4689ca3e05bd7b1c20ae20b59adf7ec379562d687f0393ce0029ae5295ed30e6e123c92a0b794789a79865ce47164d0d2e09878cb412ab8945b65c03df2ede6eab0c89be3bb60575d6cbd3a7ceeae565d5a9424fade2910373912878518c46191d19aa4ed") # Example 2: # path = "C:\\Users\\User\\AppData\\Telegram Desktop\\tdata\\key_datas" # salt = unhexlify ("16613898d763a5244bc97d5974ab65d18640562dd11d90b3626fc01fce1cb219") # data = unhexlify ("2a0f2a9f3548a223f1a93cac5618ea0c2fae859e98c3503da420b86682f5e3e3fc437ccfb9e2e324fc2664e23ad06d3109898ceee865eb46b9e5e913b76aca56eccc74457b0b4eac39737b99a8ad8bd95b0919e72fc09b9a28e659921d0a870fa40c31b74a3154ed5e5050326fd7abecef63eeb3a9d91b5684bca0b55551b2938fa68bb5be4b4c6741865de79376202d3bbb5ee900f521103e6229eca291b0844391e301eb66f503c5cbd17a9baf657aac6e6a764d0578f1f4a8ab6fe7d5b76c9df8e01ea627993f85ec659f8c6ca28ea4fb720dc488795d787cdd3c707558483ebdefcd0fb92955caae6d9472d3c1e97342dba67969b208c07a92b80ecb0f7cb8ad7143bff46d29d11e6bb185eec2acb138ddc2f6c28851dc0d8854be5b28cd") # Example 3: # path = "D:\\backups\\Telegram Backup\\tdata\\key_datas" # salt = unhexlify ("060a3b87c406490576ef9620718e9accfa43565f71ab7e46476c53a36548fd1a") # data = unhexlify ("b7b3c7c746460eff72fc128cfd2b97b8faf54ece4b0eccc89ec6f903668b51378af8df2d573f87e862934a3fa96d8c187128f849921c437b851ca8108849e858dd08628151538fe8a05bca49f27af600668945fc28c793bd4bb023fe4d4b8ff0f27001688a9c98f740f544feba6905944c918dc016fad12e257e42d61e2c85fc2200a98f0548d4a5b33148d9ea6b017e33d7a6b9125a8d026148d07db0dacea7426012aeb18c9b1215acce87b8e247e9434dd4324beba3dace0510e64e686b76665ca46c06824e21d234d5914256e84fba3d15cd8fa881f3269d22ba525f14028f97cd8b21a4439c432bcd206f502718b919cf5dd934185a3ab3871987b9e8287716a903bed570923254fd2db85e711b4d9843ceeb222a739c72120c14369687") # # Start: # sha512_hash = sha512 (salt + salt).digest () # password is empty in sha512 (s + p + s) auth_key = pbkdf2_hmac ('SHA512', sha512_hash, salt, iterations = 1, dklen = 136) # Setup buffer: data_key = data[ 0: 16] aes_data = data[16:288] # up to the end of the buffer data_a = data_key + auth_key[ 8: 40] data_b = auth_key[40: 56] + data_key + auth_key[56:72] data_c = auth_key[72:104] + data_key data_d = data_key + auth_key[104:136] sha1_a = sha1 (data_a).digest () sha1_b = sha1 (data_b).digest () sha1_c = sha1 (data_c).digest () sha1_d = sha1 (data_d).digest () # Setup decryption key and IV: aes_key = sha1_a[0: 8] + sha1_b[8:20] + sha1_c[ 4:16] aes_iv = sha1_a[8:20] + sha1_b[0: 8] + sha1_c[16:20] + sha1_d[0:8] # Decrypt: decrypted = ige256_decrypt (aes_data, aes_key, aes_iv) checksum = sha1 (decrypted).digest () checksum = checksum[0:16] # only first 16 bytes are used # Verify: if checksum == data_key: print ("'%s': ATTENTION: no password set for this file/account (empty password)" % path) ```

Same approach but using cryptg library instead:

telegram_desktop_modern_cryptg.py ```python #!/usr/bin/env python from cryptg import decrypt_ige from hashlib import sha1, sha512, pbkdf2_hmac from binascii import unhexlify # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # Goal of this little script is: # to test for encrypted Telegram Desktop v2.1.14+ encrypted data, # encrypted with an *empty password* # The data usually comes from key_datas (or "key_" + dataName + "s" files) # # Example: # # Example 1: path = "key_datas" # fake path (set this variable to the full file path) salt = unhexlify ("2370ac3bb4b8c7aa73f05a9e60fd2b0db5405fc78cb01b4a27dd190f03d6cf48") data = unhexlify ("84294a44ad833439b1ecaf56ca04fe15489525796041a2f6e809a82a8ce32abb75e04cd8b6e36532ac2ed8cc50a41c2aca5608a91de0c6f173e15e58027850683bf55da75662bfd12249c0ad52bdf4f434be42c6a71256da1b43e0a2fcb30145c4197977dea66bb6a2738984411f260b36700c974c81f4e0f3531e30560c25d50879c8f9b0d9109a67f15c97cb97a2958feef82098334537fdea116cc65aecac2e3859d2cc1332b1b9da653bc1f516c0a448816a7aa06b6150b3c7f4689ca3e05bd7b1c20ae20b59adf7ec379562d687f0393ce0029ae5295ed30e6e123c92a0b794789a79865ce47164d0d2e09878cb412ab8945b65c03df2ede6eab0c89be3bb60575d6cbd3a7ceeae565d5a9424fade2910373912878518c46191d19aa4ed") # Example 2: # path = "C:\\Users\\User\\AppData\\Telegram Desktop\\tdata\\key_datas" # salt = unhexlify ("16613898d763a5244bc97d5974ab65d18640562dd11d90b3626fc01fce1cb219") # data = unhexlify ("2a0f2a9f3548a223f1a93cac5618ea0c2fae859e98c3503da420b86682f5e3e3fc437ccfb9e2e324fc2664e23ad06d3109898ceee865eb46b9e5e913b76aca56eccc74457b0b4eac39737b99a8ad8bd95b0919e72fc09b9a28e659921d0a870fa40c31b74a3154ed5e5050326fd7abecef63eeb3a9d91b5684bca0b55551b2938fa68bb5be4b4c6741865de79376202d3bbb5ee900f521103e6229eca291b0844391e301eb66f503c5cbd17a9baf657aac6e6a764d0578f1f4a8ab6fe7d5b76c9df8e01ea627993f85ec659f8c6ca28ea4fb720dc488795d787cdd3c707558483ebdefcd0fb92955caae6d9472d3c1e97342dba67969b208c07a92b80ecb0f7cb8ad7143bff46d29d11e6bb185eec2acb138ddc2f6c28851dc0d8854be5b28cd") # Example 3: # path = "D:\\backups\\Telegram Backup\\tdata\\key_datas" # salt = unhexlify ("060a3b87c406490576ef9620718e9accfa43565f71ab7e46476c53a36548fd1a") # data = unhexlify ("b7b3c7c746460eff72fc128cfd2b97b8faf54ece4b0eccc89ec6f903668b51378af8df2d573f87e862934a3fa96d8c187128f849921c437b851ca8108849e858dd08628151538fe8a05bca49f27af600668945fc28c793bd4bb023fe4d4b8ff0f27001688a9c98f740f544feba6905944c918dc016fad12e257e42d61e2c85fc2200a98f0548d4a5b33148d9ea6b017e33d7a6b9125a8d026148d07db0dacea7426012aeb18c9b1215acce87b8e247e9434dd4324beba3dace0510e64e686b76665ca46c06824e21d234d5914256e84fba3d15cd8fa881f3269d22ba525f14028f97cd8b21a4439c432bcd206f502718b919cf5dd934185a3ab3871987b9e8287716a903bed570923254fd2db85e711b4d9843ceeb222a739c72120c14369687") # # Start: # sha512_hash = sha512 (salt + salt).digest () # password is empty in sha512 (s + p + s) auth_key = pbkdf2_hmac ('SHA512', sha512_hash, salt, iterations = 1, dklen = 136) # Setup buffer: data_key = data[ 0: 16] aes_data = data[16:288] # up to the end of the buffer data_a = data_key + auth_key[ 8: 40] data_b = auth_key[40: 56] + data_key + auth_key[56:72] data_c = auth_key[72:104] + data_key data_d = data_key + auth_key[104:136] sha1_a = sha1 (data_a).digest () sha1_b = sha1 (data_b).digest () sha1_c = sha1 (data_c).digest () sha1_d = sha1 (data_d).digest () # Setup decryption key and IV: aes_key = sha1_a[0: 8] + sha1_b[8:20] + sha1_c[ 4:16] aes_iv = sha1_a[8:20] + sha1_b[0: 8] + sha1_c[16:20] + sha1_d[0:8] # Decrypt: decrypted = decrypt_ige (aes_data, aes_key, aes_iv) checksum = sha1 (decrypted).digest () checksum = checksum[0:16] # only first 16 bytes are used # Verify: if checksum == data_key: print ("'%s': ATTENTION: no password set for this file/account (empty password)" % path) ```

And as another alternative we could also implement our own AES-IGE decrypt function (for instance using Crypto.Cipher with just plain AES-ECB decryption and a little extra code):

telegram_desktop_modern_AES_ECB.py ```python #!/usr/bin/env python from Crypto.Cipher import AES from hashlib import sha1, sha512, pbkdf2_hmac from binascii import unhexlify # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # Goal of this little script is: # to test for encrypted Telegram Desktop v2.1.14+ encrypted data, # encrypted with an *empty password* # The data usually comes from key_datas (or "key_" + dataName + "s" files) # # Example: # # Example 1: path = "key_datas" # fake path (set this variable to the full file path) salt = unhexlify ("2370ac3bb4b8c7aa73f05a9e60fd2b0db5405fc78cb01b4a27dd190f03d6cf48") data = unhexlify ("84294a44ad833439b1ecaf56ca04fe15489525796041a2f6e809a82a8ce32abb75e04cd8b6e36532ac2ed8cc50a41c2aca5608a91de0c6f173e15e58027850683bf55da75662bfd12249c0ad52bdf4f434be42c6a71256da1b43e0a2fcb30145c4197977dea66bb6a2738984411f260b36700c974c81f4e0f3531e30560c25d50879c8f9b0d9109a67f15c97cb97a2958feef82098334537fdea116cc65aecac2e3859d2cc1332b1b9da653bc1f516c0a448816a7aa06b6150b3c7f4689ca3e05bd7b1c20ae20b59adf7ec379562d687f0393ce0029ae5295ed30e6e123c92a0b794789a79865ce47164d0d2e09878cb412ab8945b65c03df2ede6eab0c89be3bb60575d6cbd3a7ceeae565d5a9424fade2910373912878518c46191d19aa4ed") # Example 2: # path = "C:\\Users\\User\\AppData\\Telegram Desktop\\tdata\\key_datas" # salt = unhexlify ("16613898d763a5244bc97d5974ab65d18640562dd11d90b3626fc01fce1cb219") # data = unhexlify ("2a0f2a9f3548a223f1a93cac5618ea0c2fae859e98c3503da420b86682f5e3e3fc437ccfb9e2e324fc2664e23ad06d3109898ceee865eb46b9e5e913b76aca56eccc74457b0b4eac39737b99a8ad8bd95b0919e72fc09b9a28e659921d0a870fa40c31b74a3154ed5e5050326fd7abecef63eeb3a9d91b5684bca0b55551b2938fa68bb5be4b4c6741865de79376202d3bbb5ee900f521103e6229eca291b0844391e301eb66f503c5cbd17a9baf657aac6e6a764d0578f1f4a8ab6fe7d5b76c9df8e01ea627993f85ec659f8c6ca28ea4fb720dc488795d787cdd3c707558483ebdefcd0fb92955caae6d9472d3c1e97342dba67969b208c07a92b80ecb0f7cb8ad7143bff46d29d11e6bb185eec2acb138ddc2f6c28851dc0d8854be5b28cd") # Example 3: # path = "D:\\backups\\Telegram Backup\\tdata\\key_datas" # salt = unhexlify ("060a3b87c406490576ef9620718e9accfa43565f71ab7e46476c53a36548fd1a") # data = unhexlify ("b7b3c7c746460eff72fc128cfd2b97b8faf54ece4b0eccc89ec6f903668b51378af8df2d573f87e862934a3fa96d8c187128f849921c437b851ca8108849e858dd08628151538fe8a05bca49f27af600668945fc28c793bd4bb023fe4d4b8ff0f27001688a9c98f740f544feba6905944c918dc016fad12e257e42d61e2c85fc2200a98f0548d4a5b33148d9ea6b017e33d7a6b9125a8d026148d07db0dacea7426012aeb18c9b1215acce87b8e247e9434dd4324beba3dace0510e64e686b76665ca46c06824e21d234d5914256e84fba3d15cd8fa881f3269d22ba525f14028f97cd8b21a4439c432bcd206f502718b919cf5dd934185a3ab3871987b9e8287716a903bed570923254fd2db85e711b4d9843ceeb222a739c72120c14369687") # # Helper functions: # def xor_buf (buf1, buf2): out = b'' for i in range (0, 16): n1 = ord (buf1[i:i + 1]) n2 = ord (buf2[i:i + 1]) out += bytes ([n1 ^ n2]) return out def aes_ige_decrypt (data, key, iv): out = b'' cipher = AES.new (key, AES.MODE_ECB) x = iv[ 0:16] y = iv[16:32] for i in range (0, len (data), 16): d = data[i:i + 16] y = xor_buf (d, y) y = cipher.decrypt (y) # main decrypt call: AES-256-ECB y = xor_buf (x, y) out += y x = d return out # # Start: # sha512_hash = sha512 (salt + salt).digest () # password is empty in sha512 (s + p + s) auth_key = pbkdf2_hmac ('SHA512', sha512_hash, salt, iterations = 1, dklen = 136) # Setup buffer: data_key = data[ 0: 16] aes_data = data[16:288] # up to the end of the buffer data_a = data_key + auth_key[ 8: 40] data_b = auth_key[40: 56] + data_key + auth_key[56:72] data_c = auth_key[72:104] + data_key data_d = data_key + auth_key[104:136] sha1_a = sha1 (data_a).digest () sha1_b = sha1 (data_b).digest () sha1_c = sha1 (data_c).digest () sha1_d = sha1 (data_d).digest () # Setup decryption key and IV: aes_key = sha1_a[0: 8] + sha1_b[8:20] + sha1_c[ 4:16] aes_iv = sha1_a[8:20] + sha1_b[0: 8] + sha1_c[16:20] + sha1_d[0:8] # Decrypt: decrypted = aes_ige_decrypt (aes_data, aes_key, aes_iv) checksum = sha1 (decrypted).digest () checksum = checksum[0:16] # only first 16 bytes are used # Verify: if checksum == data_key: print ("'%s': ATTENTION: no password set for this file/account (empty password)" % path) ```

Not sure which method you guys prefer, I think there are only minor differences, but they are not really important, I guess (e.g. differences for old python 2.7 support: does tgcrypto even support older python versions? It doesn't seem so, but we need/could/should double-check this, etc).

The other question is how we could detect the hash type and file type that the users specify. The following mechanism could be a good approach (but I'm open for suggestions/improvements and a general discussion here):

telegram_detect_hash_type.py ```python #!/usr/bin/env python import os import sys import struct import xml.etree.ElementTree as ET # Author: philsmd # Date: October 2020 # License: public domain, credits go to philsmd and hashcat # Goal of this little script is: # to check the type of Telegram hash depending on the file name and content # This code is intended to be incorporated directly into telegram2john.py # usage: # python telegram_detect_hash_type.py "C:\Users\User\AppData\Telegram Desktop\tdata\key_datas" def is_valid_xml (f): try: ET.parse (f) return True except: return False def is_valid_tdf (f): # TODO # check MD5 checksum of header etc return True def process_xml (f): # TODO if not is_valid_xml (f): # or just XML parse it and catch errors ! print ("ERROR: %s is not a valid .xml file" % f) return print ("Detected Telegram Mobile Android App .xml file") # => $telegram$0* / $dynamic_1528$ hashes def process_map (f): # TODO if not is_valid_tdf (f): return print ("Detected Telegram Desktop map* file") # => $telegram$1* hashes def process_key_datas (f): # TODO if not is_valid_tdf (f): return print ("Detected Telegram Desktop key_* file") # => $telegram$2* hashes # # Start: # if __name__ == "__main__": argc = len (sys.argv) if argc < 2: # TODO usage: # usage (sys.argv[0]) sys.exit (1) for i in range (1, argc): full_path = sys.argv[i] if not os.path.isfile (full_path): print ("ERROR: '%s' is not a valid file" % full_path) continue is_xml = False is_map = False is_key_datas = False file_name = os.path.basename (full_path) # checks based on file name: if len (file_name) >= 4: if ".xml" == file_name[-4:].lower (): is_xml = True elif "key_" == file_name[:4]: is_key_datas = True elif "map" == file_name[:3]: is_map = True # check if it is a valid TDF$ file (if it is for sure not an .xml file): if not is_xml: f = None try: f = open (full_path, "rb") except: print ("ERROR: Could not open '%s' for reading" % full_path) continue magic = f.read (4) if magic == b'TDF$': # determine the algorithm of the TDF file based on the AppVersion number if not is_key_datas: version = f.read (4) version = struct.unpack ("I", version)[0] if version >= 2001014: # Telegram Desktop 2.1.14+ is_key_datas = True else: is_map = True else: is_key_datas = False is_map = False # maybe detect XML validity here too: is_xml = is_valid_xml (full_path) f.close() if is_xml: process_xml (full_path) elif is_key_datas: process_key_datas (full_path) elif is_map: process_map (full_path) else: print ("ERROR: '%s' is not a known Telegram xml/map/key_ file" % full_path) ```

Of course this file is just a minimal python script that is intended (if we decide so to follow this approach) to be incorporated directly into telegram2john (not a standalone script).

I think we now need some decisions here to proceed with the telegram2john changes. For instance, I'm not sure if you still want to let the user specify the %APPDATA%\Telegram Desktop\ directory or if the user now should only be allowed to specify the files (xml/map0/key_datas) directly. As mentioned above, there are pros and cons. One additional disadvantage that came to my mind is that some users (but probably very few) already are used to specify a folder... so a change or removal of this "file searching feature" could confuse them (and they might want to have the "old approach" back).

Furthermore, a decision needs to be made about adding code for empty-password detection (if we want this at all or if the crackers, JTR/hc, should do this instead) and if we decide to support/do it within telegram2john, which library we should use for that feature.

Thx

madeonukraine commented 4 years ago

@philsmd What happens if you run telegram2john with your C:\1\2\tdata\D877F783D5D3EF8C\maps file ? Does it produce a "hash" or does it not work with that file ?

No have hash, have error

One additional disadvantage that came to my mind is that some users (but probably very few) already are used to specify a folder +

philsmd commented 4 years ago

I've now decided to try to modify telegram2john.py myself (even through unfortunately I didn't get much feedback above about changes / design decisions we want to have/implement).

The new telegram2john.py script * The changes/diff

* "new" at the time of this writing, if you read this in a couple of weeks it could be already older than bleeding-jumbo

The modified telegram2john.py should be able to work with any userconfing.xml, map*, key_* and Telegram Desktop profile folder now. It tries to find all the important/valid files if a folder is specified and also determines the type/algo automatically. It is able to detect empty passwords for both TDF$ variants too and adverts the user whenever there was no password set for a specific "key file".

Please test and give feedback (I've decided to not create a pull request for now, because of the "alpha" status of this new script and because John itself doesn't support the underlying algo yet, it would probably be an open pull request that can't be merged for weeks, without changes to the cracking code, i.e. new hash type support). Nevertheless, the data/hash/output should work with my POC test scripts above and/or with the new hash type -m 24500 for hashcat (not merged yet, no release version, nor beta version yet, compile it youself for the time being).

I'm open for any discussion and changes/improvements... but I think the general idea and user-friendliness is quite impressive now with this modified script.

Thx

magnumripper commented 4 years ago

I've now decided to try to modify telegram2john.py myself (even through unfortunately I didn't get much feedback above about changes / design decisions we want to have/implement).

Sorry for the lack of feedback. I reviewed your script now and it looks excellent but unfortunately I can't test it at all. Please submit a PR, IMHO we should merge it even if not yet supporting the new format - and I can probably whip up a format this week.

zloishax commented 4 years ago

The "Permission denied" error is a result of trying to process the directory as an XML file, which the script falls back to after its call to process_tdfs_file() on the directory fails. So apparently whatever is in that directory on your system is not recognized by our script. Perhaps it's a newer version of "Telegram Desktop", which we need to add support for.

I have the same issue. Telegram version 2.4.3. Folder structure is default and has no anomalies. Using command "python telegram2john.py D:\Telegram Desktop" gives me this error:

Traceback (most recent call last): File "telegram2john.py", line 179, in process_xml_file(sys.argv[j]) File "telegram2john.py", line 142, in process_xml_file tree = ET.parse(filename) File "C:\Users\xsoi\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 1202, in parse tree.parse(source, parser) File "C:\Users\xsoi\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 584, in parse source = open(source, "rb") PermissionError: [Errno 13] Permission denied: 'D:\Telegram Desktop'

I'm sorry if this issue was resolved earlier, but I didn't find it. Could you, please, help me?

Did you find a way?

solardiz commented 4 years ago

@zloishax Given the current state of this issue, it isn't helping for users to be asking one another for help here (especially given that this isn't a user support forum, and our focus is thus not user support but rather improving the software). Luckily for you and for others who reported the issue here, @philsmd already investigated it enough that you can proceed to help us test things, which should later result in a software revision that you can use to try recovering your passwords. Please test @philsmd's revision of the telegram2john.py script from his comment above against your Telegram install and let us know of your results. Thanks.

zloishax commented 4 years ago

@philsmd

I've now decided to try to modify telegram2john.py myself (even through unfortunately I didn't get much feedback above about changes / design decisions we want to have/implement).

The new telegram2john.py script * The changes/diff

  • "new" at the time of this writing, if you read this in a couple of weeks it could be already older than bleeding-jumbo

The modified telegram2john.py should be able to work with any userconfing.xml, map*, key_* and Telegram Desktop profile folder now. It tries to find all the important/valid files if a folder is specified and also determines the type/algo automatically. It is able to detect empty passwords for both TDF$ variants too and adverts the user whenever there was no password set for a specific "key file".

Please test and give feedback (I've decided to not create a pull request for now, because of the "alpha" status of this new script and because John itself doesn't support the underlying algo yet, it would probably be an open pull request that can't be merged for weeks, without changes to the cracking code, i.e. new hash type support). Nevertheless, the data/hash/output should work with my POC test scripts above and/or with the new hash type -m 24500 for hashcat (not merged yet, no release version, nor beta version yet, compile it youself for the time being).

I'm open for any discussion and changes/improvements... but I think the general idea and user-friendliness is quite impressive now with this modified script.

does not work

Traceback (most recent call last):
  File "telegram2john.py", line 53, in <module>
    from Crypto.Cipher import AES
ModuleNotFoundError: No module named 'Crypto'
C:\Game\Telegram Desktop
λ ls
log.txt  tdata/  Telegram.exe*  unins000.dat  unins000.exe*  Updater.exe*

C:\Game\Telegram Desktop
λ cd tdata\

C:\Game\Telegram Desktop\tdata
λ ls
3C76126DFB5E203Cs  913BB8499F1DC294s  D877F783D5D3EF8C/  dumps/             F8806DD0C461824Fs  prefix                 shortcuts-default.json  user_data#3/
42C6C46F120B98BCs  A7FDF864FBC10B77/  D877F783D5D3EF8Cs  emoji/             FEA94EECC3FFC1A5s  settingss              user_data/              usertag
74DA68CC2E641DD3s  A7FDF864FBC10B77s  dictionaries/      F8806DD0C461824F/  key_datas          shortcuts-custom.json  user_data#2/            working

C:\Game\Telegram Desktop\tdata

Telegram Desktop Version 2.4.4

philsmd commented 4 years ago

Thank you @zloishax for testing,

the problem is that this is not how you evaluate if a script works. For every python script you need to install the dependencies first: ModuleNotFoundError always means that you just didn't install the required python modules correctly.

This is a guide how you would install python modules: https://docs.python.org/3/installing/index.html#basic-usage

So basically just using python -m pip install NAME_OF_MODULE or pip install NAME_OF_MODULE:

python -m pip install pycrypto

pycrypto is the python module that you need to install and which is also used by several other *2john tools. The use of Crypto.Cipher is also something that I explained/discussed above (it seems you guys do not really bother to read the posts above, maybe they are just too long, I admit... but they would explain a lot of reasons and design decisions, also the tgcrypto vs cryptg vs Crypto.Cipher/pycrypto alternatives and pros/cons).

I've now opened a pull request for my telegram2john.py modifications, the script is: https://raw.githubusercontent.com/openwall/john/6c39f1266aefa7355dbff4f59992a9ff30f4af3f/run/telegram2john.py


update: I've decided to add a warning message if PyCrypto is not installed (see https://github.com/openwall/john/pull/4416/commits/8f923a4d943933508a58fa1f1fec04c5e42f1b24). The only reason why I did this and why I think it kind of makes sense here is because of the PyCrypto vs Crypto confusion (the module name vs the name you need to specify when importing), it's not exactly the same and therefore users could be confused which Crypto module to import, how to fix it and why it's still not working if you just install the Crypto package etc (the only correct module is PyCrypto here).

solardiz commented 4 years ago

@philsmd I greatly appreciate your work on this, and I'm sorry I didn't comment for real sooner (I'm not focused on JtR this month).

It's fine that we got the PR merged as-is, but FWIW I feel the empty password check isn't worth the extra dependency. Maybe we can make it a soft dependency, printing the warning/instructions and skipping the empty password check but proceeding to output the hash if the module isn't installed?

If we do that, we should probably implement an equivalent/redundant check in JtR and hashcat. We use AES in JtR anyway, but hashcat appears to only have it in OpenCL? So I guess the OpenCL kernel would know how to check for empty password, then. I admit that would be a bit unfortunate. So not sure which way is better now; I'm more like thinking out loud.

Other tools with the same dependency appear to be DPAPImk2john.py and zed2john.py. In the former, it appears to be a soft dependency (some functionality is lost without that module). In the latter, it's for real and not trivial to avoid now.

One final note: @philsmd, perhaps you should be credited for your contribution in the initial comment in telegram2john.py and in NEWS, so please send us another PR adding that. (Alternatively, I guess magnum can take care of NEWS, mentioning your contribution, when he adds support to john itself.) Also, since your changes to that script are non-trivial, please add yourself as a copyright holder. Thank you!

zloishax commented 4 years ago

Thank you @zloishax for testing,

the problem is that this is not how you evaluate if a script works. For every python script you need to install the dependencies first: ModuleNotFoundError always means that you just didn't install the required python modules correctly.

This is a guide how you would install python modules: https://docs.python.org/3/installing/index.html#basic-usage

So basically just using python -m pip install NAME_OF_MODULE or pip install NAME_OF_MODULE:

python -m pip install pycrypto

pycrypto is the python module that you need to install and which is also used by several other *2john tools. The use of Crypto.Cipher is also something that I explained/discussed above (it seems you guys do not really bother to read the posts above, maybe they are just too long, I admit... but they would explain a lot of reasons and design decisions, also the tgcrypto vs cryptg vs Crypto.Cipher/pycrypto alternatives and pros/cons).

I've now opened a pull request for my telegram2john.py modifications, the script is: https://raw.githubusercontent.com/openwall/john/6c39f1266aefa7355dbff4f59992a9ff30f4af3f/run/telegram2john.py


update: I've decided to add a warning message if PyCrypto is not installed (see https://github.com/openwall/john/pull/4416/commits/8f923a4d943933508a58fa1f1fec04c5e42f1b24). The only reason why I did this and why I think it kind of makes sense here is because of the PyCrypto vs Crypto confusion (the module name vs the name you need to specify when importing), it's not exactly the same and therefore users could be confused which Crypto module to import, how to fix it and why it's still not working if you just install the Crypto package etc (the only correct module is PyCrypto here).

"C:\Users\ALT AIR TRAVEL\Desktop\telegram2john.py" "C:\Users\ALT AIR TRAVEL\AppData\Roaming\telegram" Traceback (most recent call last): File "C:\Users\ALT AIR TRAVEL\Desktop\telegram2john.py", line 179, in <module> process_xml_file(sys.argv[j]) File "C:\Users\ALT AIR TRAVEL\Desktop\telegram2john.py", line 142, in process_xml_file tree = ET.parse(filename) File "C:\Users\ALT AIR TRAVEL\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 1202, in parse tree.parse(source, parser) File "C:\Users\ALT AIR TRAVEL\AppData\Local\Programs\Python\Python38-32\lib\xml\etree\ElementTree.py", line 584, in parse source = open(source, "rb") PermissionError: [Errno 13] Permission denied: 'C:\\Users\\ALT AIR TRAVEL\\AppData\\Roaming\\telegram'

magnumripper commented 4 years ago

It's fine that we got the PR merged as-is, but FWIW I feel the empty password check isn't worth the extra dependency. Maybe we can make it a soft dependency, printing the warning/instructions and skipping the empty password check but proceeding to output the hash if the module isn't installed?

If we do so, we must output an iteration count of (eg.) 100,000 which isn't correct for that "hash". That puts the format in limbo. I think we should just keep the dependency.

If we do that, we should probably implement an equivalent/redundant check in JtR and hashcat. We use AES in JtR anyway, but hashcat appears to only have it in OpenCL? So I guess the OpenCL kernel would know how to check for empty password, then. I admit that would be a bit unfortunate. So not sure which way is better now; I'm more like thinking out loud.

Admittedly this algo is so slow the extra checks wont matter. Still, I really don't like it.

Also, what if a user explicitly sets an empty password (as opposed to not setting any password at all). Is that even allowed? Do will still get an iteration count of 1 then?

solardiz commented 4 years ago

If we do so, we must output an iteration count of 100,000 which isn't correct for that "hash".

Technically not correct, but our code in john can know that when it's testing empty password that iteration count doesn't apply.

That puts the format in limbo. I think we should just keep the dependency.

OK, I don't mind.

Admittedly this algo is so slow the extra checks wont matter. Still, I really don't like it.

The "extra checks" wouldn't be per-candidate. Rather, we can check on loading in valid and output a message, or/and we can simply process empty candidate passwords differently (then in terms of user experience it'll work like with any other format, where we don't pre-check for empty password but we do crack such passwords when an empty string comes from a cracking mode).

Also, what if a user explicitly sets an empty password (as opposed to not setting any password at all). Is that even allowed? Do will still get an iteration count of 1 then?

Good point, and indeed we don't know yet.

solardiz commented 4 years ago

Here's another thought regarding the dependency: can we reasonably avoid it when processing older (pre-2.1.14) Telegram? Move the import (and the associated try/except logic) inside a code block that's only reached just before the module's functionality would actually be needed.

magnumripper commented 4 years ago

can we reasonably avoid it when processing older (pre-2.1.14) Telegram?

I take it this logic applied to the older version as well (so we always had a bug for that case until now).

magnumripper commented 4 years ago

I take it this logic applied to the older version as well (so we always had a bug for that case until now).

OTOH that is actually an argument for catching them in valid()...

magnumripper commented 4 years ago

I have the CPU format ready (~except for any~ now with special checks in valid()) but the OpenCL format gets hairy because our shared PBKDF2-SHA512 code for OpenCL is so very different from the one for PBKDF2-SHA1. Perhaps I should just make it a separate format. I'd love to unify the shared code (or this will hit us again) but that'd mean intrusive changes to many formats.

I'm taking a break now, pondering the alternatives.

@philsmd do you have any (or can you supply known-good) test-vector(s) for ~single-iteration~ low-iterations-count null password?

magnumripper commented 4 years ago

After re-reading Phil's script, here's the deal: Old version used 4 iterations (instead of 4,000) for no password (so yes, we had a bug all the time not handling this). New version use 1 iteration (instead of 100,000) for no password.

As far as I can tell, the script give no hint about whether it's possible to set a zero-length password and get a higher iterations count.

zloishax commented 4 years ago

@magnumripper hello i have such a problem. help me (telegram2john)

key_datas:$telegram$2*100000*0970f6c043d855aa895703b8a1cc086109cf081f72a77b6504f7f4bf3db06420*129294a5eac3196a4c9a88e556f7507b0957f6dd45d704db8abe607ec6d807270c02635289056256a6044a6408e7ef5d33f98c561f16f8aedd2b3ae33ddffddc63c8584dcb232c9f610953f461adb8d29da83f2b01e32db98101febffae4072703bfbfd492e1dd6abeb0926d3df2ed3b47dee4eb6c9f42ab657f89f19d7314c07e2ffc843e448c6d324e9f8d2c3e877a25b0b153736fddb35f5205737620ba2f96aa47f799366150b4de89a0c6e12caa4f03553d164ce9e2e975aadc83538e6ae3df93acb6026f97ac9f6f017a6bbc6607767e591b2c732e3c0ac844584c69dae89ca3272c996eb83b4e66976e3851cfc89be11dc602bb8c0cdf578d9a0a9dbc2296888fa5ee7e58d985a9bf9a1dbc75d2ddfd6ce222c5ee9f3bb40f6e25c2cd

key_datas:$telegram$2*100000*c87d4f7a65112524d6c6ba36957d7a1a6dabe3b74d21b44399862f531c7144c4*01f117f6d3eed44bbef06f367a2d30eaf2ca2147ab3a3f41beb92765e79472e5ee009b631406aaec6d6e5f6a723cc7527c66fd1cc8b1cf8af4c0f60bf370a7cf8a26260d904ea7728f2db61fbe44cd82b4e3f1716739b0f689370b801aa3dcb7cdd52eaa696fcb617431f43bcb0dbef0db72a9f9786c2b451efd52775077067cc86a0adf471f6907d024b6b3def90ed5cd974eb5528323192b99ef1fffb9988ade5cc53f671daab54a5b495d397ad0c5d199ccd438ff4a5af80bc554d96ad436096d628a14a9346a64c9a22ba6cc11ede546c6002d48a676822f7fd7f84bf21a94204703f3db9d67961a6d2474856c4cce909b38e66b0cc1540983d8f8b8e249347395f7f798bdc2f96b6c79b8cd676ce55bc1f264b4f450373993e4af05c846

this 2 hash telegram does not find the password

john --wordlist=/usr/share/wordlists/nmap.lst 1.txt
Using default input encoding: UTF-8
No password hashes loaded (see FAQ)
john 1.txt --mask=test
Using default input encoding: UTF-8
No password hashes loaded (see FAQ)
magnumripper commented 4 years ago

@zloishax it's not in the main repo yet (this issue will be closed once it is). You can try checking out the "telegram2" branch of https://github.com/magnumripper/john.git but there's no OpenCL support yet, just CPU - and it's a one of the very slowest algos due to the 100K iterations which ends up as 200K iterations due to key length - it's actually over 600K rounds of SHA-512.

philsmd commented 4 years ago

Hey @zloishax, from your output of telegram2john.py a few posts above it's very, very easy to see that you are using the wrong script. You are not using the new script, but an old version.

Why do we/I know that? Your output makes it very obvious (the traceback): it has process_xml_file() in it which isn't available anymore, your output says sys.argv[j] while the new script only has sys.argv[i], there is no filename variable in the updated/new script etc etc etc

You really need to test more carefully (this is the second time you report a problem which isn't a problem, just PEBCAK) and you need to test with the correct/updated script and double-check it, otherwise your feedback is just misleading and it is distracting/confusing us. That's very, very bad.

Fortunately, with these python tracebacks it's very easy to spot that you are doing it completely incorrectly, not even using the latest version of the script.

Also your newest post didn't mention the john version that you are using or how you got the code for the new Telegram Desktop algorithm support. We already mentioned it several times that the algorithm is not yet supported by the "normal" / old john binaries, nor by the master code. As @magnumripper mentioned above, there is already work in progress for JtR (the telegram2 branch) but nobody mentioned here that it's already supported by latest (at the time of this writing) john, instead we always made sure to emphasize that it's not supported yet for latest john. Please read carefully. This is not how you help developers testing something. You need to use your brain, patience and reading skills and explain exactly what you are trying and why you are doing it like this (when we mention that it's a new algo, it can't work with old john versions, right? there is currently no release version that supports it, only a new dev git branch)

... and of course your hashes work if you test correctly (proof of crack and can be used as a test vector): $telegram$2*100000*0970f6c043d855aa895703b8a1cc086109cf081f72a77b6504f7f4bf3db06420*129294a5eac3196a4c9a88e556f7507b0957f6dd45d704db8abe607ec6d807270c02635289056256a6044a6408e7ef5d33f98c561f16f8aedd2b3ae33ddffddc63c8584dcb232c9f610953f461adb8d29da83f2b01e32db98101febffae4072703bfbfd492e1dd6abeb0926d3df2ed3b47dee4eb6c9f42ab657f89f19d7314c07e2ffc843e448c6d324e9f8d2c3e877a25b0b153736fddb35f5205737620ba2f96aa47f799366150b4de89a0c6e12caa4f03553d164ce9e2e975aadc83538e6ae3df93acb6026f97ac9f6f017a6bbc6607767e591b2c732e3c0ac844584c69dae89ca3272c996eb83b4e66976e3851cfc89be11dc602bb8c0cdf578d9a0a9dbc2296888fa5ee7e58d985a9bf9a1dbc75d2ddfd6ce222c5ee9f3bb40f6e25c2cd:0404

password: 0404

Also this is not a "crack my hash" service. You are the one that needs to tell us what the password is and not the other way around. If anything, we are the ones that request samples and would need example hashes with known password, this is not a "I post my hashes and the devs waste their time/resources to crack the hash for me" game.


@magnumripper the Telegram Desktop application always uses passcode.isEmpty() to determine which iteration count should be used (both for new and old version, in the "GUI" there are also some sanity checks which forbit empty passwords, but it seems no additional password policies or restrictions in password length except for passcode.size() >= 1 (or not passcode.isEmpty()) etc).

So it's pretty clear that length 0 is the special case where the user didn't set any password and the user can't set an empty password themself (and therefore it's impossible that a higher iteration count is being used for empty passwords).

@magnumripper I'll attach all the example Telegram Desktop files I have generated myself (they all have no password set and therefore would all be identified as empty-pass hashes with telegram2john.py).

telegram_desktop_empty_pass_examples.zip


Yeah, I think we should/can do both... we can update the script to allow using it without PyCrypto package + noticable warnings (even though I still didn't understand what the problem installing PyCrypto is... I saw this post https://github.com/openwall/john/issues/4413#issuecomment-716679320 from @claudioandre-br , but I didn't really see what the problem is, from that output it seems to be very easy to install the package also on windows... maybe I'm missing something) and in addition to it the crackers could check for "empty password" as soon as loading/parsing the hashes.

Furthermore, the installation (really hard to do ? I guess not) of Python packages would also be a problem for many, many other extraction tools of JtR (I just had a glance at some import statements used in Python scripts within the run/ folder of JtR and I see a lot of "uncommon" packages that the user would need to install, not pre-installed ones, like scapy,zipfile,ldap3,pysap,asn1crypto,plistlib, etc etc etc ... and I think we shouldn't really limit the functionality and scope of an extraction tool just by the fact that users are struggling (a little bit !?) to install these additional python packages). Of course we could make it more user-friendly and give warnings etc and also mention how the user can install python packages i.e. some clear instructions (we've already added that error message), but I think it's still good that already the extraction tool does as much as makes sense and it's able to do, because not everything can normally be done in the extraction tool itself without knowing the correct password (and this "check for non-default iterations" and at the same time empty-pass check is in my opinion exactly one of these cases where we can "exploit" this).


I've now opened 2 new pull requests that (a) should make PyCrypto optional with a noticable warning message and (b) added myself to the "credits" list within telegram2john.py and a note about the date of change, basically what @solardiz suggested (I think that @kholia should still remain the original copyright holder, because my updated script actually just uses the ideas and also several portions of code from the original script and just refactors and updates it with the logic for the new algo and files). The changes for doc/NEWS are still missing, but I think it makes sense that @magnumripper could do this at the same time or just after the telegram2 branch from @magnumripper 's repo is merged.

Thx

zloishax commented 4 years ago

@philsmd excuse me for grammatical mistakes in writing, I don't know English that well. Therefore, I could not explain the situation, but now I will try to answer your questions that arose to me.

I just can't install the pcrypto because I have windows 7/64bit the problem is that when I install the pip install --user PyCrypto, such a mistake comes out

C:\john\run
λ pip install --user PyCrypto
Collecting PyCrypto
  Using cached pycrypto-2.6.1.tar.gz (446 kB)
Building wheels for collected packages: PyCrypto
  Building wheel for PyCrypto (setup.py) ... error
  ERROR: Command errored out with exit status 1:
   command: 'c:\users\pc\appdata\local\programs\python\python38-32\python.exe' -u -c 'import sys, setuptools, tokenize; sys.argv[0] =
 '"'"'C:\\Users\\pc\\AppData\\Local\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"'; __file__='"'"'C:\\Users\\pc\\AppData\\Local
\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'
\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' bdist_wheel -d 'C:\Users\pc\AppData\Local\Temp\pip-
wheel-ayie26x5'
       cwd: C:\Users\pc\AppData\Local\Temp\pip-install-w347e9vx\pycrypto\
  Complete output (153 lines):
  running bdist_wheel
  running build
  running build_py
  creating build
  creating build\lib.win32-3.8
  creating build\lib.win32-3.8\Crypto
  copying lib\Crypto\pct_warnings.py -> build\lib.win32-3.8\Crypto
  copying lib\Crypto\__init__.py -> build\lib.win32-3.8\Crypto
  creating build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\hashalgo.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\HMAC.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\MD2.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\MD4.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\MD5.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\RIPEMD.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\SHA.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\SHA224.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\SHA256.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\SHA384.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\SHA512.py -> build\lib.win32-3.8\Crypto\Hash
  copying lib\Crypto\Hash\__init__.py -> build\lib.win32-3.8\Crypto\Hash
  creating build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\AES.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\ARC2.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\ARC4.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\blockalgo.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\Blowfish.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\CAST.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\DES.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\DES3.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\PKCS1_OAEP.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\PKCS1_v1_5.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\XOR.py -> build\lib.win32-3.8\Crypto\Cipher
  copying lib\Crypto\Cipher\__init__.py -> build\lib.win32-3.8\Crypto\Cipher
  creating build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\asn1.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\Counter.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\number.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\py3compat.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\randpool.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\RFC1751.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\winrandom.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\_number_new.py -> build\lib.win32-3.8\Crypto\Util
  copying lib\Crypto\Util\__init__.py -> build\lib.win32-3.8\Crypto\Util
  creating build\lib.win32-3.8\Crypto\Random
  copying lib\Crypto\Random\random.py -> build\lib.win32-3.8\Crypto\Random
  copying lib\Crypto\Random\_UserFriendlyRNG.py -> build\lib.win32-3.8\Crypto\Random
  copying lib\Crypto\Random\__init__.py -> build\lib.win32-3.8\Crypto\Random
  creating build\lib.win32-3.8\Crypto\Random\Fortuna
  copying lib\Crypto\Random\Fortuna\FortunaAccumulator.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
  copying lib\Crypto\Random\Fortuna\FortunaGenerator.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
  copying lib\Crypto\Random\Fortuna\SHAd256.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
  copying lib\Crypto\Random\Fortuna\__init__.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
  creating build\lib.win32-3.8\Crypto\Random\OSRNG
  copying lib\Crypto\Random\OSRNG\fallback.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
  copying lib\Crypto\Random\OSRNG\nt.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
  copying lib\Crypto\Random\OSRNG\posix.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
  copying lib\Crypto\Random\OSRNG\rng_base.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
  copying lib\Crypto\Random\OSRNG\__init__.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
  creating build\lib.win32-3.8\Crypto\SelfTest
  copying lib\Crypto\SelfTest\st_common.py -> build\lib.win32-3.8\Crypto\SelfTest
  copying lib\Crypto\SelfTest\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest
  creating build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\common.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_AES.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_ARC2.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_ARC4.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_Blowfish.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_CAST.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_DES.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_DES3.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_pkcs1_15.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_pkcs1_oaep.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\test_XOR.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  copying lib\Crypto\SelfTest\Cipher\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
  creating build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\common.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_HMAC.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_MD2.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_MD4.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_MD5.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_RIPEMD.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_SHA.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_SHA224.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_SHA256.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_SHA384.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\test_SHA512.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  copying lib\Crypto\SelfTest\Hash\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
  creating build\lib.win32-3.8\Crypto\SelfTest\Protocol
  copying lib\Crypto\SelfTest\Protocol\test_AllOrNothing.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
  copying lib\Crypto\SelfTest\Protocol\test_chaffing.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
  copying lib\Crypto\SelfTest\Protocol\test_KDF.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
  copying lib\Crypto\SelfTest\Protocol\test_rfc1751.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
  copying lib\Crypto\SelfTest\Protocol\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
  creating build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  copying lib\Crypto\SelfTest\PublicKey\test_DSA.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  copying lib\Crypto\SelfTest\PublicKey\test_ElGamal.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  copying lib\Crypto\SelfTest\PublicKey\test_importKey.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  copying lib\Crypto\SelfTest\PublicKey\test_RSA.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  copying lib\Crypto\SelfTest\PublicKey\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
  creating build\lib.win32-3.8\Crypto\SelfTest\Random
  copying lib\Crypto\SelfTest\Random\test_random.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
  copying lib\Crypto\SelfTest\Random\test_rpoolcompat.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
  copying lib\Crypto\SelfTest\Random\test__UserFriendlyRNG.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
  copying lib\Crypto\SelfTest\Random\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
  creating build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
  copying lib\Crypto\SelfTest\Random\Fortuna\test_FortunaAccumulator.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
  copying lib\Crypto\SelfTest\Random\Fortuna\test_FortunaGenerator.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
  copying lib\Crypto\SelfTest\Random\Fortuna\test_SHAd256.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
  copying lib\Crypto\SelfTest\Random\Fortuna\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
  creating build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\test_fallback.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\test_generic.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\test_nt.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\test_posix.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\test_winrandom.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  copying lib\Crypto\SelfTest\Random\OSRNG\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
  creating build\lib.win32-3.8\Crypto\SelfTest\Util
  copying lib\Crypto\SelfTest\Util\test_asn1.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
  copying lib\Crypto\SelfTest\Util\test_Counter.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
  copying lib\Crypto\SelfTest\Util\test_number.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
  copying lib\Crypto\SelfTest\Util\test_winrandom.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
  copying lib\Crypto\SelfTest\Util\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
  creating build\lib.win32-3.8\Crypto\SelfTest\Signature
  copying lib\Crypto\SelfTest\Signature\test_pkcs1_15.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
  copying lib\Crypto\SelfTest\Signature\test_pkcs1_pss.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
  copying lib\Crypto\SelfTest\Signature\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
  creating build\lib.win32-3.8\Crypto\Protocol
  copying lib\Crypto\Protocol\AllOrNothing.py -> build\lib.win32-3.8\Crypto\Protocol
  copying lib\Crypto\Protocol\Chaffing.py -> build\lib.win32-3.8\Crypto\Protocol
  copying lib\Crypto\Protocol\KDF.py -> build\lib.win32-3.8\Crypto\Protocol
  copying lib\Crypto\Protocol\__init__.py -> build\lib.win32-3.8\Crypto\Protocol
  creating build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\DSA.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\ElGamal.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\pubkey.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\RSA.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\_DSA.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\_RSA.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\_slowmath.py -> build\lib.win32-3.8\Crypto\PublicKey
  copying lib\Crypto\PublicKey\__init__.py -> build\lib.win32-3.8\Crypto\PublicKey
  creating build\lib.win32-3.8\Crypto\Signature
  copying lib\Crypto\Signature\PKCS1_PSS.py -> build\lib.win32-3.8\Crypto\Signature
  copying lib\Crypto\Signature\PKCS1_v1_5.py -> build\lib.win32-3.8\Crypto\Signature
  copying lib\Crypto\Signature\__init__.py -> build\lib.win32-3.8\Crypto\Signature
  Skipping optional fixer: buffer
  Skipping optional fixer: idioms
  Skipping optional fixer: set_literal
  Skipping optional fixer: ws_comma
  running build_ext
  warning: GMP or MPIR library not found; Not building Crypto.PublicKey._fastmath.
  building 'Crypto.Random.OSRNG.winrandom' extension
  error: Microsoft Visual C++ 14.0 is required. Get it with "Build Tools for Visual Studio": https://visualstudio.microsoft.com/downl
oads/
  ----------------------------------------
  ERROR: Failed building wheel for PyCrypto
  Running setup.py clean for PyCrypto
Failed to build PyCrypto
Installing collected packages: PyCrypto
    Running setup.py install for PyCrypto ... error
    ERROR: Command errored out with exit status 1:
     command: 'c:\users\pc\appdata\local\programs\python\python38-32\python.exe' -u -c 'import sys, setuptools, tokenize; sys.argv[0]
 = '"'"'C:\\Users\\pc\\AppData\\Local\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"'; __file__='"'"'C:\\Users\\pc\\AppData\\Loc
al\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'
"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' install --record 'C:\Users\pc\AppData\Local\Temp\
pip-record-q1ktcfvu\install-record.txt' --single-version-externally-managed --user --prefix= --compile --install-headers 'C:\Users\pc
\AppData\Roaming\Python\Python38\Include\PyCrypto'
         cwd: C:\Users\pc\AppData\Local\Temp\pip-install-w347e9vx\pycrypto\
    Complete output (153 lines):
    running install
    running build
    running build_py
    creating build
    creating build\lib.win32-3.8
    creating build\lib.win32-3.8\Crypto
    copying lib\Crypto\pct_warnings.py -> build\lib.win32-3.8\Crypto
    copying lib\Crypto\__init__.py -> build\lib.win32-3.8\Crypto
    creating build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\hashalgo.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\HMAC.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\MD2.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\MD4.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\MD5.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\RIPEMD.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\SHA.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\SHA224.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\SHA256.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\SHA384.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\SHA512.py -> build\lib.win32-3.8\Crypto\Hash
    copying lib\Crypto\Hash\__init__.py -> build\lib.win32-3.8\Crypto\Hash
    creating build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\AES.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\ARC2.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\ARC4.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\blockalgo.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\Blowfish.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\CAST.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\DES.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\DES3.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\PKCS1_OAEP.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\PKCS1_v1_5.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\XOR.py -> build\lib.win32-3.8\Crypto\Cipher
    copying lib\Crypto\Cipher\__init__.py -> build\lib.win32-3.8\Crypto\Cipher
    creating build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\asn1.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\Counter.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\number.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\py3compat.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\randpool.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\RFC1751.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\winrandom.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\_number_new.py -> build\lib.win32-3.8\Crypto\Util
    copying lib\Crypto\Util\__init__.py -> build\lib.win32-3.8\Crypto\Util
    creating build\lib.win32-3.8\Crypto\Random
    copying lib\Crypto\Random\random.py -> build\lib.win32-3.8\Crypto\Random
    copying lib\Crypto\Random\_UserFriendlyRNG.py -> build\lib.win32-3.8\Crypto\Random
    copying lib\Crypto\Random\__init__.py -> build\lib.win32-3.8\Crypto\Random
    creating build\lib.win32-3.8\Crypto\Random\Fortuna
    copying lib\Crypto\Random\Fortuna\FortunaAccumulator.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
    copying lib\Crypto\Random\Fortuna\FortunaGenerator.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
    copying lib\Crypto\Random\Fortuna\SHAd256.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
    copying lib\Crypto\Random\Fortuna\__init__.py -> build\lib.win32-3.8\Crypto\Random\Fortuna
    creating build\lib.win32-3.8\Crypto\Random\OSRNG
    copying lib\Crypto\Random\OSRNG\fallback.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
    copying lib\Crypto\Random\OSRNG\nt.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
    copying lib\Crypto\Random\OSRNG\posix.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
    copying lib\Crypto\Random\OSRNG\rng_base.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
    copying lib\Crypto\Random\OSRNG\__init__.py -> build\lib.win32-3.8\Crypto\Random\OSRNG
    creating build\lib.win32-3.8\Crypto\SelfTest
    copying lib\Crypto\SelfTest\st_common.py -> build\lib.win32-3.8\Crypto\SelfTest
    copying lib\Crypto\SelfTest\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest
    creating build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\common.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_AES.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_ARC2.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_ARC4.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_Blowfish.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_CAST.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_DES.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_DES3.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_pkcs1_15.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_pkcs1_oaep.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\test_XOR.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    copying lib\Crypto\SelfTest\Cipher\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Cipher
    creating build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\common.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_HMAC.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_MD2.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_MD4.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_MD5.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_RIPEMD.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_SHA.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_SHA224.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_SHA256.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_SHA384.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\test_SHA512.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    copying lib\Crypto\SelfTest\Hash\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Hash
    creating build\lib.win32-3.8\Crypto\SelfTest\Protocol
    copying lib\Crypto\SelfTest\Protocol\test_AllOrNothing.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
    copying lib\Crypto\SelfTest\Protocol\test_chaffing.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
    copying lib\Crypto\SelfTest\Protocol\test_KDF.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
    copying lib\Crypto\SelfTest\Protocol\test_rfc1751.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
    copying lib\Crypto\SelfTest\Protocol\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Protocol
    creating build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    copying lib\Crypto\SelfTest\PublicKey\test_DSA.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    copying lib\Crypto\SelfTest\PublicKey\test_ElGamal.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    copying lib\Crypto\SelfTest\PublicKey\test_importKey.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    copying lib\Crypto\SelfTest\PublicKey\test_RSA.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    copying lib\Crypto\SelfTest\PublicKey\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\PublicKey
    creating build\lib.win32-3.8\Crypto\SelfTest\Random
    copying lib\Crypto\SelfTest\Random\test_random.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
    copying lib\Crypto\SelfTest\Random\test_rpoolcompat.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
    copying lib\Crypto\SelfTest\Random\test__UserFriendlyRNG.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
    copying lib\Crypto\SelfTest\Random\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random
    creating build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
    copying lib\Crypto\SelfTest\Random\Fortuna\test_FortunaAccumulator.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
    copying lib\Crypto\SelfTest\Random\Fortuna\test_FortunaGenerator.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
    copying lib\Crypto\SelfTest\Random\Fortuna\test_SHAd256.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
    copying lib\Crypto\SelfTest\Random\Fortuna\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\Fortuna
    creating build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\test_fallback.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\test_generic.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\test_nt.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\test_posix.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\test_winrandom.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    copying lib\Crypto\SelfTest\Random\OSRNG\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Random\OSRNG
    creating build\lib.win32-3.8\Crypto\SelfTest\Util
    copying lib\Crypto\SelfTest\Util\test_asn1.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
    copying lib\Crypto\SelfTest\Util\test_Counter.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
    copying lib\Crypto\SelfTest\Util\test_number.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
    copying lib\Crypto\SelfTest\Util\test_winrandom.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
    copying lib\Crypto\SelfTest\Util\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Util
    creating build\lib.win32-3.8\Crypto\SelfTest\Signature
    copying lib\Crypto\SelfTest\Signature\test_pkcs1_15.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
    copying lib\Crypto\SelfTest\Signature\test_pkcs1_pss.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
    copying lib\Crypto\SelfTest\Signature\__init__.py -> build\lib.win32-3.8\Crypto\SelfTest\Signature
    creating build\lib.win32-3.8\Crypto\Protocol
    copying lib\Crypto\Protocol\AllOrNothing.py -> build\lib.win32-3.8\Crypto\Protocol
    copying lib\Crypto\Protocol\Chaffing.py -> build\lib.win32-3.8\Crypto\Protocol
    copying lib\Crypto\Protocol\KDF.py -> build\lib.win32-3.8\Crypto\Protocol
    copying lib\Crypto\Protocol\__init__.py -> build\lib.win32-3.8\Crypto\Protocol
    creating build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\DSA.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\ElGamal.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\pubkey.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\RSA.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\_DSA.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\_RSA.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\_slowmath.py -> build\lib.win32-3.8\Crypto\PublicKey
    copying lib\Crypto\PublicKey\__init__.py -> build\lib.win32-3.8\Crypto\PublicKey
    creating build\lib.win32-3.8\Crypto\Signature
    copying lib\Crypto\Signature\PKCS1_PSS.py -> build\lib.win32-3.8\Crypto\Signature
    copying lib\Crypto\Signature\PKCS1_v1_5.py -> build\lib.win32-3.8\Crypto\Signature
    copying lib\Crypto\Signature\__init__.py -> build\lib.win32-3.8\Crypto\Signature
    Skipping optional fixer: buffer
    Skipping optional fixer: idioms
    Skipping optional fixer: set_literal
    Skipping optional fixer: ws_comma
    running build_ext
    warning: GMP or MPIR library not found; Not building Crypto.PublicKey._fastmath.
    building 'Crypto.Random.OSRNG.winrandom' extension
    error: Microsoft Visual C++ 14.0 is required. Get it with "Build Tools for Visual Studio": https://visualstudio.microsoft.com/dow
nloads/
    ----------------------------------------
ERROR: Command errored out with exit status 1: 'c:\users\pc\appdata\local\programs\python\python38-32\python.exe' -u -c 'import sys,
setuptools, tokenize; sys.argv[0] = '"'"'C:\\Users\\pc\\AppData\\Local\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"'; __file__
='"'"'C:\\Users\\pc\\AppData\\Local\\Temp\\pip-install-w347e9vx\\pycrypto\\setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__
file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' install --record
 'C:\Users\pc\AppData\Local\Temp\pip-record-q1ktcfvu\install-record.txt' --single-version-externally-managed --user --prefix= --compi
le --install-headers 'C:\Users\pc\AppData\Roaming\Python\Python38\Include\PyCrypto' Check the logs for full command output.

I don't want to blame you, but I think there are many like me... John the Ripper version 1.9.0-jumbo-1 OMP [cygwin 64-bit x86_64 SSE2 AC]

you write that you found the password from the first yes, you found it correctly, my goal is not what you think, I just do it for my safety $telegram$2*100000*0970f6c043d855aa895703b8a1cc086109cf081f72a77b6504f7f4bf3db06420*129294a5eac3196a4c9a88e556f7507b0957f6dd45d704db8abe607ec6d807270c02635289056256a6044a6408e7ef5d33f98c561f16f8aedd2b3ae33ddffddc63c8584dcb232c9f610953f461adb8d29da83f2b01e32db98101febffae4072703bfbfd492e1dd6abeb0926d3df2ed3b47dee4eb6c9f42ab657f89f19d7314c07e2ffc843e448c6d324e9f8d2c3e877a25b0b153736fddb35f5205737620ba2f96aa47f799366150b4de89a0c6e12caa4f03553d164ce9e2e975aadc83538e6ae3df93acb6026f97ac9f6f017a6bbc6607767e591b2c732e3c0ac844584c69dae89ca3272c996eb83b4e66976e3851cfc89be11dc602bb8c0cdf578d9a0a9dbc2296888fa5ee7e58d985a9bf9a1dbc75d2ddfd6ce222c5ee9f3bb40f6e25c2cd:0404

the first one was a simple password(0404) on this one I put a password for verification with a length of 7 digits and one dot at the end on the lower hash password (7227385.) I think that your John the Ripper program cannot crack passwords more than 4 digits I will mean it now key_datas:$telegram$2*100000*c87d4f7a65112524d6c6ba36957d7a1a6dabe3b74d21b44399862f531c7144c4*01f117f6d3eed44bbef06f367a2d30eaf2ca2147ab3a3f41beb92765e79472e5ee009b631406aaec6d6e5f6a723cc7527c66fd1cc8b1cf8af4c0f60bf370a7cf8a26260d904ea7728f2db61fbe44cd82b4e3f1716739b0f689370b801aa3dcb7cdd52eaa696fcb617431f43bcb0dbef0db72a9f9786c2b451efd52775077067cc86a0adf471f6907d024b6b3def90ed5cd974eb5528323192b99ef1fffb9988ade5cc53f671daab54a5b495d397ad0c5d199ccd438ff4a5af80bc554d96ad436096d628a14a9346a64c9a22ba6cc11ede546c6002d48a676822f7fd7f84bf21a94204703f3db9d67961a6d2474856c4cce909b38e66b0cc1540983d8f8b8e249347395f7f798bdc2f96b6c79b8cd676ce55bc1f264b4f450373993e4af05c846 this password 7227385.

sergava commented 4 years ago

@zloishax just try to install pycryptodome instead. Pycrypto has been already dead for a long time.

magnumripper commented 4 years ago

I put a password for verification with a length of 7 digits and one dot at the end on the lower hash password (7227385.) I think that your John the Ripper program cannot crack passwords more than 4 digits I will mean it now

@zloishax I can crack it just fine

$ ../run/john zloishax.in -mask=7227?d?d?d.
Warning: detected hash type "telegram", but the string is also recognized as "telegram-opencl"
Use the "--format=telegram-opencl" option to force loading these as that type instead
Using default input encoding: UTF-8
Loaded 1 password hash (telegram [PBKDF2-SHA1/SHA512 256/256 AVX2 8x AES])
Cost 1 (iteration count) is 100000 for all loaded hashes
Will run 16 OpenMP threads
Press 'q' or Ctrl-C to abort, almost any other key for status
7227385.         (key_datas)
1g 0:00:00:05 DONE (2020-10-30 13:19) 0.1675g/s 128.6p/s 128.6c/s 128.6C/s 7227195...7227454.
No remaining hashes
Use the "--show" option to display all of the cracked passwords reliably
Session completed. 
zloishax commented 4 years ago

@magnumripper This is after when I said the code. Having learned the code and at the same time hack it, forgive me not hacking. If you can hack without my prompt, how do you do it? Is there such a function other than brutus in john the ripper. Thanks.

magnumripper commented 4 years ago

If you mean I could crack it without your password hint, sure - it would just take much longer time, probably to the point I'd give up before cracking it (and this is the very idea with slow hashes like this). Basically all about JtR is brute-forcing, although we try to achieve really clever brute-force.

ghost commented 4 years ago

Hi, do you happen to know how you can get a .session file from the tdata folder (used by telethon)

magnumripper commented 4 years ago

I assume that refers to https://github.com/LonamiWebs/Telethon

solardiz commented 4 years ago

@zloishax I've just deleted your off-topic comment. This issue is only about Telegram, and our use of GitHub is about improving our software - it is not about providing user support, let alone cracking things for people. Please refrain from posting off-topic comments and making such requests. Thanks.