diff --git a/generate.bat b/generate.bat index 782e5e3c..b6d22cc3 100644 --- a/generate.bat +++ b/generate.bat @@ -1,2 +1,3 @@ @echo off +call tools\protogen.bat premake5 %* vs2015 \ No newline at end of file diff --git a/premake5.lua b/premake5.lua index 1e52785e..3b9b72c6 100644 --- a/premake5.lua +++ b/premake5.lua @@ -1,4 +1,3 @@ - -- Option to allow copying the DLL file to a custom folder after build newoption { trigger = "copy-to", @@ -36,7 +35,7 @@ newaction { -- get old version number from version.hpp if any local oldRevNumber = "(none)" - local oldVersionHeader = io.open(wks.location .. "/version.hpp", "r") + local oldVersionHeader = io.open(wks.location .. "/src/version.hpp", "r") if oldVersionHeader ~=nil then local oldVersionHeaderContent = assert(oldVersionHeader:read('*a')) oldRevNumber = string.match(oldVersionHeaderContent, "#define REVISION (%d+)") @@ -49,7 +48,7 @@ newaction { -- generate version.hpp with a revision number if not equal if oldRevNumber ~= revNumber then print ("Update " .. oldRevNumber .. " -> " .. revNumber) - local versionHeader = assert(io.open(wks.location .. "/version.hpp", "w")) + local versionHeader = assert(io.open(wks.location .. "/src/version.hpp", "w")) versionHeader:write("/*\n") versionHeader:write(" * Automatically generated by premake5.\n") versionHeader:write(" * Do not touch, you fucking moron!\n") @@ -92,38 +91,38 @@ workspace "iw4x" kind "SharedLib" language "C++" files { "./src/**.hpp", "./src/**.cpp" } - includedirs { "%{prj.location}", "./src" } + includedirs { "%{prj.location}/src", "./src" } -- Pre-compiled header pchheader "STDInclude.hpp" -- must be exactly same as used in #include directives pchsource "src/STDInclude.cpp" -- real path - buildoptions { "-Zm88" } + buildoptions { "/Zm100" } -- Dependency on zlib, json11 and asio links { "zlib", "json11", "pdcurses", "libtomcrypt", "libtommath", "protobuf" } includedirs - { + { "./deps/zlib", "./deps/json11", "./deps/pdcurses", "./deps/asio/asio/include", "./deps/libtomcrypt/src/headers", "./deps/libtommath", - "./deps/protobuf/src", + "./deps/protobuf/src", } -- Virtual paths if not _OPTIONS["no-new-structure"] then vpaths { - ["Headers/*"] = "./src/**.hpp", - ["Sources/*"] = {"./src/**.cpp"} + ["Headers/*"] = { "./src/**.hpp" }, + ["Sources/*"] = { "./src/**.cpp" } } end vpaths { - ["Docs/*"] = {"**.txt","**.md"} + ["Docs/*"] = { "**.txt","**.md" }, } - + -- Pre-build prebuildcommands { "cd %{_MAIN_SCRIPT_DIR}", @@ -259,8 +258,12 @@ workspace "iw4x" "./deps/protobuf/src", } + -- default protobuf sources files { "./deps/protobuf/src/**.cc" } + -- our generated sources + files { "./%{prj.location}/src/proto/**.cc" } + -- remove unnecessary sources removefiles { diff --git a/src/Components/Modules/Node.cpp b/src/Components/Modules/Node.cpp index 746a3628..654c41f5 100644 --- a/src/Components/Modules/Node.cpp +++ b/src/Components/Modules/Node.cpp @@ -229,7 +229,9 @@ namespace Components node.challenge = Utils::VA("%X", Utils::Cryptography::Rand::GenerateInt()); std::string data; - Utils::Message::WriteBuffer(data, node.challenge); + Proto::NodePacket packet; + packet.set_challenge(node.challenge); + packet.SerializePartialToString(&data); Logger::Print("Sending registration request to %s\n", node.address.GetString()); Network::SendRaw(node.address, "nodeRegisterRequest\n" + data); @@ -311,8 +313,11 @@ namespace Components { std::string data, challenge; challenge = Utils::VA("X", Utils::Cryptography::Rand::GenerateInt()); - Utils::Message::WriteBuffer(data, challenge); - Utils::Message::WriteBuffer(data, Utils::Cryptography::ECDSA::SignMessage(Node::SignatureKey, challenge)); + + Proto::NodePacket packet; + packet.set_challenge(challenge); + packet.set_signature(Utils::Cryptography::ECDSA::SignMessage(Node::SignatureKey, challenge)); + packet.SerializePartialToString(&data); for (auto node : Node::Nodes) { @@ -336,16 +341,19 @@ namespace Components Logger::Print("Received registration request from %s\n", address.GetString()); - std::string response, challenge; - if (!Utils::Message::ReadBuffer(data, challenge)) return; + Proto::NodePacket packet; + if (!packet.ParseFromString(data)) return; + if (!packet.has_challenge()) return; - std::string publicKey = Node::SignatureKey.GetPublicKey(); - std::string signature = Utils::Cryptography::ECDSA::SignMessage(Node::SignatureKey, challenge); - challenge = Utils::VA("%X", Utils::Cryptography::Rand::GenerateInt()); + std::string response; + std::string signature = Utils::Cryptography::ECDSA::SignMessage(Node::SignatureKey, packet.challenge()); + std::string challenge = Utils::VA("%X", Utils::Cryptography::Rand::GenerateInt()); - Utils::Message::WriteBuffer(response, signature); - Utils::Message::WriteBuffer(response, publicKey); - Utils::Message::WriteBuffer(response, challenge); + packet.Clear(); + packet.set_challenge(challenge); + packet.set_signature(signature); + packet.set_publickey(Node::SignatureKey.GetPublicKey()); + packet.SerializeToString(&response); entry->lastTime = Game::Com_Milliseconds(); entry->challenge = challenge; @@ -361,10 +369,15 @@ namespace Components Logger::Print("Received synchronization data for registration from %s!\n", address.GetString()); - std::string challenge, publicKey, signature; - if (!Utils::Message::ReadBuffer(data, signature)) return; - if (!Utils::Message::ReadBuffer(data, publicKey)) return; - if (!Utils::Message::ReadBuffer(data, challenge)) return; + Proto::NodePacket packet; + if (!packet.ParseFromString(data)) return; + if (!packet.has_challenge()) return; + if (!packet.has_publickey()) return; + if (!packet.has_signature()) return; + + std::string challenge = packet.challenge(); + std::string publicKey = packet.publickey(); + std::string signature = packet.signature(); // Verify signature entry->publicKey.Set(publicKey); @@ -388,8 +401,10 @@ namespace Components publicKey = Node::SignatureKey.GetPublicKey(); signature = Utils::Cryptography::ECDSA::SignMessage(Node::SignatureKey, challenge); - Utils::Message::WriteBuffer(data, signature); - Utils::Message::WriteBuffer(data, publicKey); + packet.Clear(); + packet.set_signature(signature); + packet.set_publickey(publicKey); + packet.SerializePartialToString(&data); Network::SendRaw(address, "nodeRegisterAcknowledge\n" + data); }); @@ -402,9 +417,13 @@ namespace Components Logger::Print("Received acknowledgment from %s\n", address.GetString()); - std::string publicKey, signature; - if (!Utils::Message::ReadBuffer(data, signature)) return; - if (!Utils::Message::ReadBuffer(data, publicKey)) return; + Proto::NodePacket packet; + if (!packet.ParseFromString(data)) return; + if (!packet.has_signature()) return; + if (!packet.has_publickey()) return; + + std::string publicKey = packet.publickey(); + std::string signature = packet.signature(); entry->publicKey.Set(publicKey); @@ -464,9 +483,13 @@ namespace Components Node::NodeEntry* entry = Node::FindNode(address); if (!entry || !entry->registered) return; - std::string challenge, signature; - if (!Utils::Message::ReadBuffer(data, challenge)) return; - if (!Utils::Message::ReadBuffer(data, signature)) return; + Proto::NodePacket packet; + if (!packet.ParseFromString(data)) return; + if (!packet.has_challenge()) return; + if (!packet.has_signature()) return; + + std::string challenge = packet.challenge(); + std::string signature = packet.signature(); if (Utils::Cryptography::ECDSA::VerifyMessage(entry->publicKey, challenge, signature)) { diff --git a/src/STDInclude.hpp b/src/STDInclude.hpp index ffc3505d..74877e0b 100644 --- a/src/STDInclude.hpp +++ b/src/STDInclude.hpp @@ -60,6 +60,9 @@ #include #include +// Protobuf +#include + #pragma warning(pop) // Version number diff --git a/src/Utils/CSV.cpp b/src/Utils/CSV.cpp index 233ac9ee..2870a5ce 100644 --- a/src/Utils/CSV.cpp +++ b/src/Utils/CSV.cpp @@ -43,7 +43,7 @@ namespace Utils for (int i = 0; i < CSV::GetRows(); ++i) { - count = max(CSV::GetColumns(i), count); + count = std::max(CSV::GetColumns(i), count); } return count; diff --git a/src/Utils/Utils.cpp b/src/Utils/Utils.cpp index f092525b..d3e0cf67 100644 --- a/src/Utils/Utils.cpp +++ b/src/Utils/Utils.cpp @@ -246,31 +246,4 @@ namespace Utils this->KeyValuePairs[KeyValues[i]] = KeyValues[i + 1]; } } - - namespace Message - { - void WriteBuffer(std::string& message, std::string buffer) - { - DWORD length = buffer.size(); - message.append(reinterpret_cast(&length), 4); - message.append(buffer); - } - - bool ReadBuffer(std::string& message, std::string& buffer) - { - if (message.size() < 4) return false; - - char* messagePtr = const_cast(message.data()); - - DWORD length = *reinterpret_cast(messagePtr); - - if (message.size() < (length + 4)) return false; - - buffer.clear(); - buffer.append(messagePtr + 4, length); - - message = std::string(messagePtr + 4 + length, message.size() - (4 + length)); - return true; - } - } } \ No newline at end of file diff --git a/src/Utils/Utils.hpp b/src/Utils/Utils.hpp index 0fb3b9c1..95725575 100644 --- a/src/Utils/Utils.hpp +++ b/src/Utils/Utils.hpp @@ -59,12 +59,4 @@ namespace Utils target->push_back(entry); } } - - // TODO: Implement a bytebuffer class - // Maybe convery's or protobuf - namespace Message - { - void WriteBuffer(std::string& message, std::string buffer); - bool ReadBuffer(std::string& message, std::string& buffer); - } } diff --git a/tools/proto/node.proto b/tools/proto/node.proto new file mode 100644 index 00000000..4937d5ba --- /dev/null +++ b/tools/proto/node.proto @@ -0,0 +1,9 @@ +syntax = "proto3"; + +package Proto; + +message NodePacket { + string challenge = 1; + string signature = 2; + string publicKey = 3; +} \ No newline at end of file diff --git a/tools/protoc.exe b/tools/protoc.exe new file mode 100644 index 00000000..fd7de52b Binary files /dev/null and b/tools/protoc.exe differ diff --git a/tools/protogen.bat b/tools/protogen.bat new file mode 100644 index 00000000..fd6f0c1a --- /dev/null +++ b/tools/protogen.bat @@ -0,0 +1,4 @@ +pushd "%~dp0" +mkdir "..\build\src\proto" 2>NUL +protoc.exe -I=proto --cpp_out=../build/src/proto/ proto/node.proto +popd \ No newline at end of file