[Auth] Use all 64 bits of the guid for fingerprints

This commit is contained in:
momo5502 2017-01-13 13:58:16 +01:00
parent e1aab7905b
commit 5c43859044
3 changed files with 30 additions and 13 deletions

View File

@ -165,7 +165,6 @@ namespace Components
// Parse the id
unsigned __int64 xuid = strtoull(steamId.data(), nullptr, 16);
unsigned int id = static_cast<unsigned int>(~0x110000100000000 & xuid);
SteamID guid;
guid.Bits = xuid;
@ -176,7 +175,7 @@ namespace Components
return;
}
if ((xuid & 0xFFFFFFFF00000000) != 0x110000100000000 || id != (Utils::Cryptography::JenkinsOneAtATime::Compute(connectData.publickey()) & ~0x80000000))
if (xuid != Auth::GetKeyHash(connectData.publickey()))
{
Network::Send(address, "error\nXUID doesn't match the certificate!");
return;
@ -220,10 +219,22 @@ namespace Components
}
}
unsigned int Auth::GetKeyHash()
unsigned __int64 Auth::GetKeyHash(std::string key)
{
std::string hash = Utils::Cryptography::SHA1::Compute(key);
if (hash.size() >= 8)
{
return *reinterpret_cast<unsigned __int64*>(const_cast<char*>(hash.data()));
}
return 0;
}
unsigned __int64 Auth::GetKeyHash()
{
Auth::LoadKey();
return (Utils::Cryptography::JenkinsOneAtATime::Compute(Auth::GuidKey.getPublicKey()));
return Auth::GetKeyHash(Auth::GuidKey.getPublicKey());
}
void Auth::StoreKey()
@ -385,6 +396,13 @@ namespace Components
Utils::Hook(0x6265F9, Auth::DirectConnectStub, HOOK_JUMP).install()->quick();
Utils::Hook(0x41D3E3, Auth::SendConnectDataStub, HOOK_CALL).install()->quick();
// SteamIDs can only contain 31 bits of actual 'id' data.
// The other 33 bits are steam internal data like universe and so on.
// Using only 31 bits for fingerprints is pretty insecure.
// The function below verifies the integrity steam's part of the SteamID.
// Patching that check allows us to use 64 bit for fingerprints.
Utils::Hook::Set<DWORD>(0x4D0D60, 0xC301B0);
// Guid command
Command::Add("guid", [] (Command::Params*)
{

View File

@ -14,7 +14,8 @@ namespace Components
static void StoreKey();
static void LoadKey(bool force = false);
static unsigned int GetKeyHash();
static unsigned __int64 GetKeyHash();
static unsigned __int64 GetKeyHash(std::string key);
static uint32_t GetSecurityLevel();
static void IncreaseSecurityLevel(uint32_t level, std::string command = "");

View File

@ -16,29 +16,27 @@ namespace Steam
SteamID User::GetSteamID()
{
static unsigned int subId = 0;
static unsigned __int64 idBits = 0;
SteamID id;
if (!subId)
if (!idBits)
{
if (Components::Dedicated::IsEnabled() || Components::ZoneBuilder::IsEnabled()) // Dedi guid
{
subId = ~0xDED1CA7E;
idBits = *reinterpret_cast<unsigned __int64*>("DEDICATE");
}
else if (Components::Singleton::IsFirstInstance()) // ECDSA guid
{
subId = Components::Auth::GetKeyHash();
idBits = Components::Auth::GetKeyHash();
}
else // Random guid
{
subId = (Game::Sys_Milliseconds() + timeGetTime());
idBits = (static_cast<unsigned __int64>(Game::Sys_Milliseconds()) << 32) | timeGetTime();
}
subId &= ~0x80000000; // Ensure it's positive
}
id.Bits = 0x110000100000000 | subId;
id.Bits = idBits;
return id;
}