Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import { DataCenter } from './app';
- function log(message) {
- console.log(`[MT Proto]`, message);
- }
- interface AuthProcesor {
- next(decryptedData, authData?): AuthProcesor;
- }
- function getFromStorage(id: string) {
- return localStorage.getItem(id);
- }
- function setToStorage(id: string, data) {
- return localStorage.setItem(id, data);
- }
- function getAuthKeyIdData(dc_id) {
- return JSON.parse((getFromStorage(dc_id+'auth_key_data') || '{}'));
- }
- function setAuthKeyData(dc_id, data) {
- console.log('set');
- console.log(data);
- setToStorage(dc_id+'auth_key_data', JSON.stringify(data));
- }
- export class Authorization {
- authData = {
- ...getAuthKeyIdData(this.dataCenter.dcId),
- };
- authStep: any = new BeginAuthorization();
- isAuthorized;
- constructor(private dataCenter: DataCenter) {
- if (this.authData.authKeyID) {
- this.isAuthorized = true;
- }
- }
- start() {
- this.authStep = this.authStep.next(this.authData, this.dataCenter);
- }
- updateSalt(newSalt) {
- this.authData.serverSalt = longToBytes(newSalt);
- localStorage.setItem(this.dataCenter.dcId + 'auth_key_data', JSON.stringify(this.authData));
- }
- onMessage(decryptedData) {
- this.authStep = this.authStep.next(decryptedData, this.authData, this.dataCenter);
- if (!this.authStep) {
- this.isAuthorized = true
- }
- }
- }
- class BeginAuthorization implements AuthProcesor {
- next(auth, dc: DataCenter) {
- log('Begin authorization');
- auth.nonce = randomBytes(16);
- dc.sendPlainMessage('req_pq', { nonce: auth.nonce });
- return new RequestDhParams()
- }
- }
- class RequestDhParams {
- next(decryptedData, auth, dc: DataCenter) {
- log('Request dh params');
- const tlSerializator = new TLSerialization({ mtproto: true });
- const desearelizator = new Desearelizator(decryptedData, true);
- desearelizator.desearelization.fetchInt();
- desearelizator.desearelization.fetchLong();
- desearelizator.desearelization.fetchLong();
- let obj = desearelizator.deserealize();
- let pq = pqPrimeFactorization(obj.pq);
- auth.newNonce = randomBytes(32);
- auth.serverNonce = obj['server_nonce'];
- tlSerializator.storeObject({
- _: 'p_q_inner_data',
- pq: obj.pq,
- p: pq[0],
- q: pq[1],
- nonce: auth.nonce,
- server_nonce: auth.serverNonce,
- new_nonce: auth.newNonce,
- }, 'P_Q_inner_data');
- let dataWithHash = concat(sha1BytesSync(tlSerializator.getBytes()), tlSerializator.getBytes());
- let rsa = selectRsaKeyByFingerPrint(obj['server_public_key_fingerprints']);
- dc.sendPlainMessage('req_DH_params', {
- nonce: auth.nonce,
- server_nonce: auth.serverNonce,
- p: pq[0],
- q: pq[1],
- public_key_fingerprint: rsa.fingerprint,
- encrypted_data: rsaEncrypt(rsa, dataWithHash),
- });
- return new SetClientDhParams();
- }
- }
- class SetClientDhParams {
- next(decryptedData, auth, dc: DataCenter) {
- log('Set client dh params');
- const desearelizator = new Desearelizator(decryptedData, true);
- desearelizator.desearelization.fetchInt();
- desearelizator.desearelization.fetchLong();
- desearelizator.desearelization.fetchLong();
- let obj = desearelizator.deserealize();
- auth.tmpAesKey = tmpAesKey(auth.serverNonce, auth.newNonce);
- auth.tmpAesIv = tmpAesIv(auth.serverNonce, auth.newNonce);
- const answerWithHash = aesDecryptSync(obj['encrypted_answer'], auth.tmpAesKey, auth.tmpAesIv);
- const innerDesearelizator = new Desearelizator(new Uint8Array(answerWithHash), true);
- innerDesearelizator.desearelization.fetchLong();
- innerDesearelizator.desearelization.fetchLong();
- let deser = innerDesearelizator.deserealize();
- const gBytes = bytesFromHex(deser.g.toString(16));
- auth.gA = deser['g_a'];
- auth.dhPrime = deser['dh_prime'];
- auth.randomB = randomBytes(256);
- ;
- auth.serverTime = deser.server_time
- let modpow = bytesModPow(gBytes, auth.randomB, auth.dhPrime);
- let tsSer = new TLSerialization({ mtproto: true });
- let serialization = tsSer;
- tsSer.writeInt(1715713620);
- tsSer.storeObject({
- _: 'client_DH_inner_data',
- nonce: new Uint8Array(auth.nonce),
- server_nonce: new Uint8Array(auth.serverNonce),
- retry_id: [0, 0],
- g_b: modpow,
- }, 'client_DH_inner_data');
- const dataWithHash = concat(sha1BytesSync(new Uint8Array(serialization.getBytes()).buffer), new Uint8Array(serialization.getBytes()));
- const encryptedData = aesEncryptSync(dataWithHash, auth.tmpAesKey, auth.tmpAesIv);
- dc.sendPlainMessage('set_client_DH_params', {
- nonce: auth.nonce,
- server_nonce: auth.serverNonce,
- encrypted_data: encryptedData,
- });
- auth.localTime = tsNow();
- dc.applyServerTime(auth.serverTime, auth.localTime)
- return new AuthFinished();
- }
- }
- class AuthFinished {
- next(decryptedData, auth, dataCenter) {
- let desearelizator = new Desearelizator(decryptedData, true);
- desearelizator.desearelization.fetchInt();
- desearelizator.desearelization.fetchLong();
- desearelizator.desearelization.fetchLong();
- desearelizator.deserealize();
- let authKey = bytesModPow(auth.gA, auth.randomB, auth.dhPrime);
- const authKeyHash = sha1BytesSync(authKey),
- authKeyAux = authKeyHash.slice(0, 8),
- authKeyID = authKeyHash.slice(-8)
- if (desearelizator.constructorName == 'dh_gen_ok') {
- log('It`s okay');
- const serverSalt = bytesXor(auth.newNonce.slice(0, 8), auth.serverNonce.slice(0, 8))
- //
- auth.authKeyID = authKeyID;
- auth.authKey = authKey;
- auth.serverSalt = serverSalt;
- setAuthKeyData(dataCenter.dcId, { authKeyID, authKey, serverSalt });
- } else {
- console.warn('[MT Proto] ' + desearelizator.constructorName);
- }
- return undefined;
- }
- }
- const publicKeysHex: PublicKey[] = [{
- modulus:
- 'c150023e2f70db7985ded064759cfecf0af328e69a41daf4d6f01b538135a6f91f' +
- '8f8b2a0ec9ba9720ce352efcf6c5680ffc424bd634864902de0b4bd6d49f4e5802' +
- '30e3ae97d95c8b19442b3c0a10d8f5633fecedd6926a7f6dab0ddb7d457f9ea81b' +
- '8465fcd6fffeed114011df91c059caedaf97625f6c96ecc74725556934ef781d86' +
- '6b34f011fce4d835a090196e9a5f0e4449af7eb697ddb9076494ca5f81104a305b' +
- '6dd27665722c46b60e5df680fb16b210607ef217652e60236c255f6a28315f4083' +
- 'a96791d7214bf64c1df4fd0db1944fb26a2a57031b32eee64ad15a8ba68885cde7' +
- '4a5bfc920f6abf59ba5c75506373e7130f9042da922179251f',
- exponent: '010001',
- },
- {
- modulus: `00aeec36c8ffc109cb099624685b97
- 815415657bd76d8c9c3e398103d7ad
- 16c9bba6f525ed0412d7ae2c2de2b4
- 4e77d72cbf4b7438709a4e646a05c4
- 3427c7f184debf72947519680e6515
- 00890c6832796dd11f772c25ff8f57
- 6755afe055b0a3752c696eb7d8da0d
- 8be1faf38c9bdd97ce0a77d3916230
- c4032167100edd0f9e7a3a9b602d04
- 367b689536af0d64b613ccba796293
- 9d3b57682beb6dae5b608130b2e52a
- ca78ba023cf6ce806b1dc49c72cf92
- 8a7199d22e3d7ac84e47bc9427d023
- 6945d10dbd15177bab413fbf0edfda
- 09f014c7a7da088dde9759702ca760
- af2b8e4e97cc055c617bd74c3d9700
- 8635b98dc4d621b4891da9fb047304
- 7927`.split('\n').map((it) => it.trim()).join(''),
- exponent: '010001',
- },
- {
- modulus: `00bdf2c77d81f6afd47bd30f29ac76
- e55adfe70e487e5e48297e5a9055c9
- c07d2b93b4ed3994d3eca5098bf18d
- 978d54f8b7c713eb10247607e69af9
- ef44f38e28f8b439f257a11572945c
- c0406fe3f37bb92b79112db69eedf2
- dc71584a661638ea5becb9e2358507
- 4b80d57d9f5710dd30d2da940e0ada
- 2f1b878397dc1a72b5ce2531b6f7dd
- 158e09c828d03450ca0ff8a174deac
- ebcaa22dde84ef66ad370f259d18af
- 806638012da0ca4a70baa83d9c158f
- 3552bc9158e69bf332a45809e1c369
- 05a5caa12348dd57941a482131be7b
- 2355a5f4635374f3bd3ddf5ff925bf
- 4809ee27c1e67d9120c5fe08a9de45
- 8b1b4a3c5d0a428437f2beca81f4e2
- d5ff`.split('\n').map((it) => it.trim()).join(''),
- exponent: '010001',
- },
- {
- modulus: `00b3f762b739be98f343eb1921cf01
- 48cfa27ff7af02b6471213fed9daa0
- 098976e667750324f1abcea4c31e43
- b7d11f1579133f2b3d9fe27474e462
- 058884e5e1b123be9cbbc6a443b292
- 5c08520e7325e6f1a6d50e117eb61e
- a49d2534c8bb4d2ae4153fabe832b9
- edf4c5755fdd8b19940b81d1d96cf4
- 33d19e6a22968a85dc80f0312f596b
- d2530c1cfb28b5fe019ac9bc25cd9c
- 2a5d8a0f3a1c0c79bcca524d315b5e
- 21b5c26b46babe3d75d06d1cd33329
- ec782a0f22891ed1db42a1d6c0dea4
- 31428bc4d7aabdcf3e0eb6fda4e23e
- b7733e7727e9a1915580796c55188d
- 2596d2665ad1182ba7abf15aaa5a8b
- 779ea996317a20ae044b820bff35b6
- e8a`.split('\n').map((it) => it.trim()).join(''),
- exponent: '010001',
- },
- {
- modulus: `00be6a71558ee577ff03023cfa17aa
- b4e6c86383cff8a7ad38edb9fafe6f
- 323f2d5106cbc8cafb83b869cffd1c
- cf121cd743d509e589e68765c96601
- e813dc5b9dfc4be415c7a6526132d0
- 035ca33d6d6075d4f535122a1cdfe0
- 17041f1088d1419f65c8e5490ee613
- e16dbf662698c0f54870f0475fa893
- fc41eb55b08ff1ac211bc045ded31b
- e27d12c96d8d3cfc6a7ae8aa50bf2e
- e0f30ed507cc2581e3dec56de94f5d
- c0a7abee0be990b893f2887bd2c631
- 0a1e0a9e3e38bd34fded2541508dc1
- 02a9c9b4c95effd9dd2dfe96c29be6
- 47d6c69d66ca500843cfaed6e44019
- 6f1dbe0e2e22163c61ca48c79116fa
- 77216726749a976a1c4b0944b5121e
- 8c01`.split('\n').map((it) => it.trim()).join(''),
- exponent: '010001',
- },
- ];
- let prepared = false;
- const tmpAesKey = (serverNonce, newNonce) => {
- const arr1 = concat(newNonce, serverNonce)
- const arr2 = concat(serverNonce, newNonce)
- const key1 = sha1BytesSync(arr1)
- const key2 = sha1BytesSync(arr2).slice(0, 12)
- return concat(key1, key2);
- }
- const tmpAesIv = (serverNonce, newNonce) => {
- const arr1 = concat(serverNonce, newNonce)
- const arr2 = concat(newNonce, newNonce)
- const arr3 = newNonce.slice(0, 4)
- const key1 = sha1BytesSync(arr1)
- const key2 = sha1BytesSync(arr2)
- return concat(key1.slice(12), concat(key2, arr3));
- }
- function prepareRsaKeys() {
- if (prepared) return
- publicKeysHex.forEach((it) => mapPrepare(it));
- prepared = true
- }
- let publicKeysParsed = {};
- function selectRsaKeyByFingerPrint(fingerprints: string[]) {
- let fingerprintHex, foundKey
- for (const fingerprint of fingerprints) {
- fingerprintHex = strDecToHex(fingerprint);
- console.log(fingerprintHex);
- foundKey = publicKeysParsed[fingerprintHex]
- if (foundKey)
- return { fingerprint, ...foundKey }
- }
- return false
- }
- const mapPrepare = ({ modulus, exponent }) => {
- const serializatorTL = new TLSerialization({ mptroto: true });
- serializatorTL.storeBytes(bytesFromHex(modulus));
- serializatorTL.storeBytes(bytesFromHex(exponent));
- let fingerprintBytes = sha1BytesSync(serializatorTL.getBytes()).slice(-8);
- fingerprintBytes = fingerprintBytes.reverse();
- publicKeysParsed[bytesToHex(fingerprintBytes)] = {
- modulus,
- exponent,
- }
- console.log(publicKeysParsed);
- };
- prepareRsaKeys();
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement