Skip to content

Instantly share code, notes, and snippets.

@Rulexec
Created October 17, 2014 18:31
Show Gist options
  • Save Rulexec/e0d707c490bcba426957 to your computer and use it in GitHub Desktop.
Save Rulexec/e0d707c490bcba426957 to your computer and use it in GitHub Desktop.
// by Rulexec
// http://com.muna.by/people/ruliov
var net = require('net'),
CRC32Stream = require('crc32-stream').CRC32Stream;
var client = net.connect(443, '149.154.167.50', function() {
console.log('connected');
var packet = createPacket();
console.log('sending', packet.toString('hex'));
client.write(packet, function() {
console.log('sent');
});
}).on('data', function(data) {
console.log('data', data.toString('hex'));
}).on('end', function() {
console.log('end', arguments);
}).on('close', function() {
console.log('closed');
});
function createPacket() {
var buffer = new Buffer(52); // 4 + 4 + 40 + 4
buffer.writeUInt32LE(52, 0); // TCP-обёртка, длина пакета
buffer.writeUInt32LE(0, 4); // TCP-обёртка, номер пакета
buffer.fill(0, 8, 16); // Нешифрованный пакет, нулевой authKeyId
var messageId = pollMessageId(); // js sucks без 64-битных чисел
// Нешифрованный пакет, 64-битный messageId
buffer.writeUInt32LE(messageId[1], 16);
buffer.writeUInt32LE(messageId[0], 20);
buffer.writeUInt32LE(20, 24); // Нешифрованный пакет, длина данных
buffer.writeUInt32LE(0x60469778, 28); // Данные пакета, идентификатор конструктора типа
new Buffer(16).copy(buffer, 32); // Данный пакета, nonce, должны быть случайными байтами
// Лучше генерировать из надёжного источника!
var crc32Stream = new CRC32Stream();
crc32Stream.write(buffer.slice(0, 48)); // Всё, кроме места под crc32
crc32Stream.end();
buffer.writeUInt32LE(crc32Stream.digest(), 48);
return buffer;
}
// Ну... когда-то это работало, может и сейчас выдаёт что-то похожее на правду
var lastMessageId = [0, 0];
function pollMessageId() {
var time = new Date().getTime();
var higher = (time / 1000) | 0;
var lower = ((((time % 1000) * 256 / 1000) << 24) >>> 0) + // Первые 8 бит
(Math.random() * 16777216) | 0; // [0; 2^24), остальные биты
lower = (lower & 0xfffffffc) >>> 0; // Обнуляем последние два бита
if (higher < lastMessageId[0] || (higher === lastMessageId[0] && lower <= lastMessageId[1])) {
higher = lastMessageId[0];
lower = lastMessageId[1] + 4;
}
lastMessageId = [higher, lower];
return lastMessageId;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment