Skip to content

Commit

Permalink
Encryption update
Browse files Browse the repository at this point in the history
Small fixes
Remove of encryption def files
Implementation of the calculateKeys method
added a few debug info to encryption methods
  • Loading branch information
joaoescribano committed Nov 2, 2019
1 parent 243b9b6 commit af3ce5e
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 147 deletions.
126 changes: 0 additions & 126 deletions core/defs/encryption.def.php

This file was deleted.

33 changes: 24 additions & 9 deletions core/encrypt.core.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ class Encrypt {
/**
* Decrypts the packets received from the client on the first connection
*/
public static function decryptLoginPacket($data, $version = null) {
public static function decryptPacket($data, $version = null) {
if ($version === null || !is_array($version) || $version['major'] <= 0) {
return $data;
}
Expand All @@ -34,13 +34,28 @@ public static function decryptLoginPacket($data, $version = null) {
return $data;
}

public static function gameDecrypt($data, $version = null) {
if ($version === null || !is_array($version) || $version['major'] <= 0) {
return $data;
}

$seed = $version['seed'];
$key1 = $version['key1'];
$key2 = $version['key2'];
/**
* Retrive the client key based on the version
* Converted from: https://github.com/gokaygurcan/poc/blob/develop/index.js#L79-L98
*/
public static function calculateKeys($major, $minor, $revision, $prototype) {
$key1 = ($major << 23) | ($minor << 14) | ($revision << 4);
$key1 ^= ($revision * $revision) << 9;
$key1 ^= $minor * $minor;
$key1 ^= ($minor * 11) << 24;
$key1 ^= ($revision * 7) << 19;
$key1 ^= 0x2c13a5fd;

$key2 = ($major << 22) | ($revision << 13) | ($minor << 3);
$key2 ^= ($revision * $revision * 3) << 10;
$key2 ^= $minor * $minor;
$key2 ^= ($minor * 13) << 23;
$key2 ^= ($revision * 7) << 18;
$key2 ^= 0xa31d527f;

return [
$key1,
$key2
];
}
}
5 changes: 3 additions & 2 deletions core/packets/0xEF.packet.php
Original file line number Diff line number Diff line change
Expand Up @@ -41,15 +41,16 @@ public function receive($data) {
return false;
}

$keys = Encrypt::calculateKeys($major, $minor, $revision, $prototype);
UltimaPHP::$socketClients[$this->client]['version'] = [
'encrypted' => null,
'seed' => $seed,
'major' => $major,
'minor' => $minor,
'revision' => $revision,
'prototype' => $prototype,
'key1' => (isset(EncryptionDefs::VERSION[$major . $minor . $revision]) ? EncryptionDefs::VERSION[$major . $minor . $revision][0] : false),
'key2' => (isset(EncryptionDefs::VERSION[$major . $minor . $revision]) ? EncryptionDefs::VERSION[$major . $minor . $revision][1] : false),
'key1' => $keys[0],
'key2' => $keys[1]
];

return true;
Expand Down
43 changes: 33 additions & 10 deletions core/sockets.core.php
Original file line number Diff line number Diff line change
Expand Up @@ -118,9 +118,20 @@ public static function monitor() {
}

// If player isn't relayed and not tested for encryption
if ($socket['version'] !== null && is_array($socket['version']) && isset($socket['version']['encrypted'])) {
if ($socket['version']['encrypted'] === null && hexdec($buffer[0]) != 0x80 && $length == 62) {
$converted = Encrypt::decryptLoginPacket($buffer, $socket['version']);
if ($socket['version'] !== null && is_array($socket['version'])) {
if (UltimaPHP::$conf['logs']['debug'] === true) {
echo "Handling encryption\n";
print_r($socket['version']);
}

if ($socket['version']['encrypted'] === null) {
$converted = Encrypt::decryptPacket($buffer, $socket['version']);

if (UltimaPHP::$conf['logs']['debug'] === true) {
echo "converted 1:\n\n";
echo "Buffer:" . implode("", $buffer) . "\n";
echo "Decrypted:" . implode("", $converted) . "\n";
}

if (hexdec($converted[0]) != 0x80) {
UltimaPHP::log("Client tries to connect using unknow client version.", UltimaPHP::LOG_WARNING);
Expand All @@ -129,7 +140,6 @@ public static function monitor() {
}

$buffer = $converted;
$length = count($buffer);
UltimaPHP::$socketClients[$client]['version']['encrypted'] = true;
}

Expand All @@ -138,6 +148,17 @@ public static function monitor() {
}
}

if (UltimaPHP::$socketClients[$client]['version']['encrypted'] === true) {
if (UltimaPHP::$conf['logs']['debug'] === true) {
echo "converted 2:\n\n";
echo "Buffer:" . implode("", $buffer) . "\n";
}
$buffer = Encrypt::decryptPacket($buffer, $socket['version']);
if (UltimaPHP::$conf['logs']['debug'] === true) {
echo "Decrypted:" . implode("", $buffer) . "\n";
}
}

$validation = self::validatePacket($buffer);

if ($validation !== false) {
Expand Down Expand Up @@ -319,13 +340,15 @@ public static function validatePacket($inputArray = array()) {
}
} elseif (-1 == $expectedLength) {
// The packet have the information of lenth
$length = hexdec($inputArray[1] . $inputArray[2]);
if (isset($inputArray[1]) && isset($inputArray[2])) {
$length = hexdec($inputArray[1] . $inputArray[2]);

$return[] = array_slice($inputArray, 0, $length);
$next = self::validatePacket(array_slice($inputArray, $length));
if (false !== $next) {
foreach ($next as $key => $value) {
$return[] = $value;
$return[] = array_slice($inputArray, 0, $length);
$next = self::validatePacket(array_slice($inputArray, $length));
if (false !== $next) {
foreach ($next as $key => $value) {
$return[] = $value;
}
}
}
} elseif (false === $expectedLength) {
Expand Down

0 comments on commit af3ce5e

Please sign in to comment.