From b6ee7e3ea810064b33ffa0c12ab555e4ec399360 Mon Sep 17 00:00:00 2001 From: momo5502 Date: Mon, 28 Dec 2015 14:53:20 +0100 Subject: [PATCH] Correct server parsing. --- iw4/Components/ServerList.cpp | 43 ++++++++++++----------------------- iw4/Components/ServerList.hpp | 23 +++++++++++++++++++ 2 files changed, 38 insertions(+), 28 deletions(-) diff --git a/iw4/Components/ServerList.cpp b/iw4/Components/ServerList.cpp index 928391f5..b3cb3c4a 100644 --- a/iw4/Components/ServerList.cpp +++ b/iw4/Components/ServerList.cpp @@ -139,41 +139,28 @@ namespace Components ServerList::RefreshContainer.Mutex.lock(); - // Is this safe? If server ip/port is encoded as '\', it might fail - // TODO: Rather parse six bytes and skip the seventh - auto servers = Utils::Explode(data, '\\'); + ServerList::MasterEntry* entry = (ServerList::MasterEntry*)data.data(); - if (servers.size()) + for (int i = 0; !entry[i].IsEndToken() && entry[i].HasSeparator(); i++) { - if (servers[servers.size() - 1] == "EOT") - { - Logger::Print("We got an invalid response from the master. Trying to parse it anyways...\n"); - } + Network::Address serverAddr = address; + serverAddr.SetIP(entry[i].IP); + serverAddr.SetPort(entry[i].Port); + serverAddr.Get()->type = Game::NA_IP; - for (unsigned int i = 0; i < servers.size() - 1; i++) - { - const char* server = servers[i].data(); + ServerList::Container::ServerContainer container; + container.SendTime = Game::Com_Milliseconds(); + container.Challenge = Utils::VA("%d", container.SendTime); + container.Sent = true; + container.Target = serverAddr; - DWORD ip = *(DWORD*)server; - uint16_t port = *(uint16_t*)(server + 4); + ServerList::RefreshContainer.Servers.push_back(container); - Network::Address serverAddr = address; - serverAddr.SetIP(ip); - serverAddr.SetPort(port); - serverAddr.Get()->type = Game::NA_IP; - - ServerList::Container::ServerContainer container; - container.SendTime = Game::Com_Milliseconds(); - container.Challenge = Utils::VA("%d", container.SendTime); - container.Sent = true; - container.Target = serverAddr; - - ServerList::RefreshContainer.Servers.push_back(container); - - Network::Send(container.Target, Utils::VA("getinfo %s\n", container.Challenge.data())); - } + Network::Send(container.Target, Utils::VA("getinfo %s\n", container.Challenge.data())); } + Logger::Print("Parsed %d servers from master\n", ServerList::RefreshContainer.Servers.size()); + ServerList::RefreshContainer.Mutex.unlock(); }); diff --git a/iw4/Components/ServerList.hpp b/iw4/Components/ServerList.hpp index fdc249ce..e8a883c7 100644 --- a/iw4/Components/ServerList.hpp +++ b/iw4/Components/ServerList.hpp @@ -37,6 +37,29 @@ namespace Components Ping, }; +#pragma pack(push, 1) + union MasterEntry + { + char Token[7]; + struct + { + uint32_t IP; + uint16_t Port; + }; + + bool IsEndToken() + { + // End of transmission token + return (Token[0] == 'E' && Token[1] == 'O' && Token[2] == 'T'); + } + + bool HasSeparator() + { + return (Token[6] == '\\'); + } + }; +#pragma pack(pop) + struct Container { struct ServerContainer