From 21b388f0d0e694d7cfa36a0ffb3f072f456e4f6e Mon Sep 17 00:00:00 2001 From: Kurt Sassenrath Date: Sun, 8 Oct 2023 08:20:23 -0700 Subject: [PATCH] WIP: Message definitions. --- include/parselink/msgpack/token/reader.h | 4 ++ include/parselink/proto/message.h | 63 ++++++++++++++++++++---- tests/msgpack/test_speed.cpp | 43 +++++++++++++++- 3 files changed, 100 insertions(+), 10 deletions(-) diff --git a/include/parselink/msgpack/token/reader.h b/include/parselink/msgpack/token/reader.h index 5e5e395..7edd8d0 100644 --- a/include/parselink/msgpack/token/reader.h +++ b/include/parselink/msgpack/token/reader.h @@ -273,6 +273,10 @@ public: return token_buffer.subspan(0, parsed); } + template + constexpr tl::expected read() { + } + private: std::span data_; diff --git a/include/parselink/proto/message.h b/include/parselink/proto/message.h index 61bb25b..93e4b75 100644 --- a/include/parselink/proto/message.h +++ b/include/parselink/proto/message.h @@ -7,9 +7,9 @@ // //----------------------------------------------------------------------------- // Author: Kurt Sassenrath -// Module: Message +// Module: Proto // -// Message types. +// Message type definitions for the parselink protocol. // // Copyright (c) 2023 Kurt Sassenrath. // @@ -19,18 +19,14 @@ #define message_0c61530748b9f966 #include +#include #include #include +#include namespace parselink { -namespace message { - -enum class error { - bad_magic, // Did not get the message magic expected - too_large, // The message size was too large. - unknown_type, // The message type is not known -}; +namespace proto { // Parselink messages are encoded with MessagePack and take the form of: // | magic | size | content | @@ -38,6 +34,55 @@ enum class error { // - [size] is the size of the message, not including this header. // - [content] is [size] bytes of MessagePack data, including the // specific type of message presented. +// This may be revised in the future. The header could remain as msgpack, or +// switch to something hand-crafted for saving bits. + +struct error_message { + std::uint32_t code; // An error code + std::string_view what; // A string +}; + +// C->S: Request to (re)connect. +struct connect_message { + std::uint32_t user_id; // The user id. + std::uint32_t version; // The version of the client. + std::span session_token; // An optional existing session token. +}; + +// S->C: Challenge to authenticate client as user_id +struct challenge_message { + std::uint32_t version; + std::span challenge; +}; + +// C->S: Calculated response to a challenge. +struct response_message { + std::span response; +}; + +// S->C: Session token. +struct session_established_message { + std::span session_token; +}; + +struct parser_data_message { + std::string_view opts; + std::span payload; +}; + +using message = std::variant< + error_message, + connect_message, + challenge_message, + response_message, + session_established_message, + parser_data_message>; + +enum class error { + bad_magic, // Did not get the message magic expected + too_large, // The message size was too large. + unknown_type, // The message type is not known +}; // This class is responsible for consuming buffer data and yielding a message // instance when complete. Will throw an error if data is incorrect. diff --git a/tests/msgpack/test_speed.cpp b/tests/msgpack/test_speed.cpp index b8efc28..44fdf17 100644 --- a/tests/msgpack/test_speed.cpp +++ b/tests/msgpack/test_speed.cpp @@ -1,6 +1,9 @@ #include "parselink/msgpack/token.h" +//#include "parselink/proto/message.h" #include +#include +#include #include #include @@ -9,6 +12,11 @@ using namespace std::chrono_literals; +struct any { + template + operator T() {} +}; + auto read_file(char const* filename) { std::vector data; auto fd = open(filename, O_RDONLY); @@ -30,7 +38,7 @@ auto read_file(char const* filename) { int main(int argc, char** argv) { - std::array buf; + std::array buf; auto data = read_file(argc < 2 ? "output.bin" : argv[1]); @@ -41,6 +49,39 @@ int main(int argc, char** argv) { auto after = std::chrono::steady_clock::now(); test.map([&](auto sp){ fmt::print("Read {} tokens\n", sp.size()); + for (auto token : sp) { + fmt::print("token type: {} value: ", magic_enum::enum_name(token.type())); + switch (token.type()) { + case msgpack::format::type::unsigned_int: + fmt::print("{}", *(token.template get())); + break; + case msgpack::format::type::signed_int: + fmt::print("{}", *(token.template get())); + break; + case msgpack::format::type::boolean: + fmt::print("{}", *(token.template get())); + break; + case msgpack::format::type::string: + fmt::print("{}", *(token.template get())); + break; + case msgpack::format::type::binary: + fmt::print("{}", *(token.template get>())); + break; + case msgpack::format::type::map: + fmt::print("map ({} entries)", token.template get()->count); + break; + case msgpack::format::type::array: + fmt::print("array ({} entries)", token.template get()->count); + break; + case msgpack::format::type::nil: + fmt::print("(nil)"); + break; + case msgpack::format::type::invalid: + fmt::print("(invalid)"); + break; + } + fmt::print("\n"); + } }).map_error([&](auto err){ fmt::print("Failed to read tokens: {}\n", (int)err); });