- Joined
- Sep 10, 2007
- Messages
- 970
- Reaction score
- 815
The new packet structure is quite unique now. The header is is 12 bytes instead of 6, where the size is stored in a DWORD in the first 4 bytes, and the command id is now offset 16 and the data length is stored at offset 12.
Blobs are now 4 bytes long instead of 12 (size, count)
Packet layout (not yet complete)
Size and encryption checking:
Quick analysis of the initial connect packet (data section only):
Decryption/Encryption is still the same, just changed SHL & SHLMASK
CryptKey generation is even easier to use now, just extract the CryptKeySeed from the initial packet 0x1D:
Example:
Blobs are now 4 bytes long instead of 12 (size, count)
Packet layout (not yet complete)
Code:
// [COLOR=#DD1144]C2UF::REQ_SUPPLY_BOX_OPEN[/COLOR]
byte[] packet = new byte[]
{
0x69, 0x02, 0x00, 0x00, // flags
0xBB, 0x00, // packet counter.
0x00, 0x00, // unknown
0x18, 0x06, // unknown
0x64, 0x05, // checksum
0x07, 0x00, // data size
0x00, 0x00, // unknown
0x18, 0x06, // command id
0x00 // data?
};
Size and encryption checking:
Code:
var temp = BitConverter.ToUInt32(packet, 0);
var size = (uint)(0x7FFFFF & (temp >> 5));
var encrypted = (byte)((temp >> 3) & 1) == 1;
// how to check if it it's encrypted.
if (encrypted)
Decrypt(packet, 12, (int)size - 12, CryptKey);
Quick analysis of the initial connect packet (data section only):
Code:
/*
* 1D 00 -- data size 12
* 00 00 -- unknown 14
* 1C 0C -- command id 16
* 00 00 -- error code 18
* 00 10 -- blob size 20
* 00 01 -- blob count 22
* 00 // ???? 23
* 7D CD 9D 06 00 00 00 00 // gsid 24
* 73 0C 00 00 // crypt 33
* 4C 11 00 00 // session 37
*/
Decryption/Encryption is still the same, just changed SHL & SHLMASK
Code:
static void Decrypt(byte[] buf, int index, int length, byte[] key)
{
for (var i = 0; i < length; ++i)
{
var a = buf[index + i];
a ^= 0x0F0;
var b = (byte)(a & 3);
a >>= 2;
b <<= 6;
b = (byte)(a | b);
buf[index + i] = (byte)(b ^ key[i % 32]);
}
}
CryptKey generation is even easier to use now, just extract the CryptKeySeed from the initial packet 0x1D:
Code:
static void MakeCryptKey(uint num)
{
byte[] XOR = new byte[] { 87, 2, 91, 4, 52, 6, 1, 8, 55, 10, 18, 105, 65, 56, 15, 120 };
byte[] IV = new byte[] { 27, 4, 36, 34, 67, 1, 73, 83, 80, 5, 19, 53, 79, 2, 77, 5 };
Buffer.BlockCopy(BitConverter.GetBytes(num), 0, CryptKey, 4, 4);
for (int i = 0; i < 16; ++i)
CryptKey[i] ^= XOR[i];
Buffer.BlockCopy(IV, 0, CryptKey, 16, 16);
}
Example:
Code:
if (commandId == 0xC1C)
{
var index = 25;
var gsId = BitConverter.ToUInt64(packet, index);
index += 8;
var cryptKeySeed = BitConverter.ToUInt32(packet, index);
Console.WriteLine("GSId: {0} - Crypt Key Seed: {1}", gsId, cryptKeySeed);
MakeCryptKey(cryptKeySeed);
}
Last edited: