diff --git a/openvpn/ssl/customcontrolchannel.hpp b/openvpn/ssl/customcontrolchannel.hpp index 4f8278b3..2b4e9d66 100644 --- a/openvpn/ssl/customcontrolchannel.hpp +++ b/openvpn/ssl/customcontrolchannel.hpp @@ -32,6 +32,7 @@ #include #include #include +#include namespace openvpn { @@ -177,8 +178,9 @@ class AppControlMessageReceiver throw parse_acc_message{"Discarding malformed custom app control message"}; } + auto protocol = std::move(parts[1]); - auto length = std::move(parts[2]); + auto length_str = std::move(parts[2]); auto flags = std::move(parts[3]); auto message = std::move(parts[4]); @@ -186,6 +188,12 @@ class AppControlMessageReceiver bool textEncoding = false; bool fragment = false; + size_t length = 0; + if (!parse_number(length_str, length) || length != message.length()) + { + throw parse_acc_message{"Discarding malformed custom app control message"}; + } + for (char const &c : flags) { switch (c) diff --git a/test/unittests/test_acc.cpp b/test/unittests/test_acc.cpp index b009f5be..7b8a1cff 100644 --- a/test/unittests/test_acc.cpp +++ b/test/unittests/test_acc.cpp @@ -168,4 +168,48 @@ TEST(customcontrolchannel, send_with_nul) EXPECT_EQ(cmsgs.size(), 1); EXPECT_EQ(cmsgs[0], expected_control_msg); +} + +TEST(customcontrolchannel, test_incorrect_len) +{ + std::string control_msg{"ACC,fortune,62,6,InsgIm1lIjogImZyb2ciLCAAeGZm/SJtc2ciOiAiSSBhbSAAS2VybWl0IiB9Ig=="}; + + AppControlMessageReceiver accrecv{}; + + EXPECT_THROW( + accrecv.receive_message(control_msg), + parse_acc_message); +} + +TEST(customcontrolchannel, test_wrong_header) +{ + std::string control_msg{"ABC,fortune,64,6,InsgIm1lIjogImZyb2ciLCAAeGZm/SJtc2ciOiAiSSBhbSAAS2VybWl0IiB9Ig=="}; + + AppControlMessageReceiver accrecv{}; + + EXPECT_THROW( + accrecv.receive_message(control_msg), + parse_acc_message); +} + +TEST(customcontrolchannel, test_unsupported_encoding) +{ + std::string control_msg{"ACC,fortune,64,Q,InsgIm1lIjogImZyb2ciLCAAeGZm/SJtc2ciOiAiSSBhbSAAS2VybWl0IiB9Ig=="}; + + AppControlMessageReceiver accrecv{}; + + EXPECT_THROW( + accrecv.receive_message(control_msg), + parse_acc_message); +} + +TEST(customcontrolchannel, test_missing_message) +{ + std::string control_msg{"ABC,fortune,64,6"}; + + AppControlMessageReceiver accrecv{}; + + EXPECT_THROW( + accrecv.receive_message(control_msg), + parse_acc_message); } \ No newline at end of file