diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index e773aad..938dfde 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -11,6 +11,9 @@ FetchContent_MakeAvailable(Catch2) list(APPEND CMAKE_MODULE_PATH ${catch2_SOURCE_DIR}/extras) include(Catch) +# source helper functions and library +add_subdirectory(test_utils) + add_subdirectory(app_handshake) -add_subdirectory(DIN) -add_subdirectory(ISO20) +add_subdirectory(din) +add_subdirectory(iso20) diff --git a/tests/DIN/CMakeLists.txt b/tests/DIN/CMakeLists.txt deleted file mode 100644 index 4428776..0000000 --- a/tests/DIN/CMakeLists.txt +++ /dev/null @@ -1,20 +0,0 @@ -add_executable(test_session_setup session_setup.cpp) - -target_link_libraries(test_session_setup - PRIVATE - cbv2g::din - Catch2::Catch2WithMain -) - -catch_discover_tests(test_session_setup) - - -add_executable(test_service_discovery service_discovery.cpp) - -target_link_libraries(test_service_discovery - PRIVATE - cbv2g::din - Catch2::Catch2WithMain -) - -catch_discover_tests(test_service_discovery) diff --git a/tests/ISO20/CMakeLists.txt b/tests/ISO20/CMakeLists.txt deleted file mode 100644 index dc6d8ff..0000000 --- a/tests/ISO20/CMakeLists.txt +++ /dev/null @@ -1,29 +0,0 @@ -add_executable(test_ac_charge_loop ac_charge_loop.cpp) -target_sources(test_ac_charge_loop - PRIVATE - codec_helper.cpp -) - -target_link_libraries(test_ac_charge_loop - PRIVATE - cbv2g::iso20 - Catch2::Catch2WithMain -) - -catch_discover_tests(test_ac_charge_loop) - - -add_executable(test_dc_charge_loop dc_charge_loop.cpp) -target_sources(test_dc_charge_loop - PRIVATE - codec_helper.cpp -) - - -target_link_libraries(test_dc_charge_loop - PRIVATE - cbv2g::iso20 - Catch2::Catch2WithMain -) - -catch_discover_tests(test_dc_charge_loop) diff --git a/tests/app_handshake/CMakeLists.txt b/tests/app_handshake/CMakeLists.txt index b69b556..b97d4e1 100644 --- a/tests/app_handshake/CMakeLists.txt +++ b/tests/app_handshake/CMakeLists.txt @@ -1,9 +1 @@ -add_executable(test_app_handshake app_handshake.cpp) - -target_link_libraries(test_app_handshake - PRIVATE - cbv2g::din - Catch2::Catch2WithMain -) - -catch_discover_tests(test_app_handshake) \ No newline at end of file +add_codec_test(app_handshake) diff --git a/tests/app_handshake/app_handshake.cpp b/tests/app_handshake/app_handshake.cpp index 2c63aba..5b113d9 100644 --- a/tests/app_handshake/app_handshake.cpp +++ b/tests/app_handshake/app_handshake.cpp @@ -5,6 +5,8 @@ #include #include +#include "test_utils/codec.hpp" + SCENARIO("Encode and decode app protocol request messages") { GIVEN("Decode an AppProtocolReq document") { @@ -14,16 +16,12 @@ SCENARIO("Encode and decode app protocol request messages") { "\xd1\x89\xa9\x89\x89\xc1\xd1\x69\x91\x81\xd2\x0a\x18\x01\x00\x00\x04" "\x00\x40"; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, reinterpret_cast(doc_raw), sizeof(doc_raw), pos1, nullptr); - THEN("It should be decoded succussfully") { - appHand_exiDocument request; + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); + REQUIRE(result.decoding_successful); + + const auto& request = result.value; - REQUIRE(decode_appHand_exiDocument(&exi_stream_in, &request) == 0); REQUIRE(request.supportedAppProtocolReq_isUsed == 1); REQUIRE(request.supportedAppProtocolReq.AppProtocol.arrayLen == 1); @@ -47,16 +45,12 @@ SCENARIO("Encode and decode app protocol response messages") { uint8_t doc_raw[] = "\x80\x40\x00\x40"; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, reinterpret_cast(doc_raw), sizeof(doc_raw), pos1, nullptr); - THEN("It should be decoded succussfully") { - appHand_exiDocument response; + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); + REQUIRE(result.decoding_successful); + + const auto& response = result.value; - REQUIRE(decode_appHand_exiDocument(&exi_stream_in, &response) == 0); REQUIRE(response.supportedAppProtocolRes_isUsed == 1); REQUIRE(response.supportedAppProtocolRes.ResponseCode == appHand_responseCodeType_OK_SuccessfulNegotiation); diff --git a/tests/din/CMakeLists.txt b/tests/din/CMakeLists.txt new file mode 100644 index 0000000..c5d5a52 --- /dev/null +++ b/tests/din/CMakeLists.txt @@ -0,0 +1,2 @@ +add_codec_test(session_setup) +add_codec_test(service_discovery) diff --git a/tests/DIN/service_discovery.cpp b/tests/din/service_discovery.cpp similarity index 81% rename from tests/DIN/service_discovery.cpp rename to tests/din/service_discovery.cpp index 22190b3..f6d01ad 100644 --- a/tests/DIN/service_discovery.cpp +++ b/tests/din/service_discovery.cpp @@ -1,14 +1,16 @@ #include +#include #include #include #include #include -#include #include #include +#include "test_utils/codec.hpp" + SCENARIO("Encode and decode a DIN service discovery message") { // Exi Stream: 809a0211d63f74d2297ac9119400 @@ -52,23 +54,11 @@ SCENARIO("Encode and decode a DIN service discovery message") { body.ServiceDiscoveryReq.ServiceCategory_isUsed = true; body.ServiceDiscoveryReq.ServiceCategory = din_serviceCategoryType_EVCharging; - uint8_t stream[256] = {}; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, stream, sizeof(stream), pos1, nullptr); - THEN("It should be encoded succussfully") { + const auto result = test_utils::encode_and_compare(request, doc_raw, sizeof(doc_raw)); - REQUIRE(encode_din_exiDocument(&exi_stream_in, &request) == 0); - - const auto encoded_stream = - std::vector(stream, stream + exi_bitstream_get_length(&exi_stream_in) + 1); - - const auto expected_exi_stream = std::vector(std::begin(doc_raw), std::end(doc_raw)); - - REQUIRE(encoded_stream == expected_exi_stream); + REQUIRE(result.encoding_successful); + REQUIRE(result.bitstream_match); } } @@ -76,16 +66,12 @@ SCENARIO("Encode and decode a DIN service discovery message") { auto expected_session_id = std::vector{0x47, 0x58, 0xFD, 0xD3, 0x48, 0xA5, 0xEB, 0x24}; uint8_t doc_raw[] = "\x80\x9a\x02\x11\xd6\x3f\x74\xd2\x29\x7a\xc9\x11\x94\x00"; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, reinterpret_cast(doc_raw), sizeof(doc_raw), pos1, nullptr); THEN("It should be decoded succussfully") { - din_exiDocument request; + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); + REQUIRE(result.decoding_successful); - REQUIRE(decode_din_exiDocument(&exi_stream_in, &request) == 0); + const auto& request = result.value; // Check Header const auto& header = request.V2G_Message.Header; @@ -169,39 +155,23 @@ SCENARIO("Encode and decode a DIN service discovery message") { chargeService.FreeService = false; chargeService.EnergyTransferType = din_EVSESupportedEnergyTransferType_DC_extended; - uint8_t stream[256] = {}; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, stream, sizeof(stream), pos1, nullptr); - THEN("It should be encoded succussfully") { + const auto result = test_utils::encode_and_compare(request, doc_raw, sizeof(doc_raw)); - REQUIRE(encode_din_exiDocument(&exi_stream_in, &request) == 0); - - const auto encoded_stream = - std::vector(stream, stream + exi_bitstream_get_length(&exi_stream_in) + 1); - - const auto expected_exi_stream = std::vector(std::begin(doc_raw), std::end(doc_raw)); - - REQUIRE(encoded_stream == expected_exi_stream); + REQUIRE(result.encoding_successful); + REQUIRE(result.bitstream_match); } } GIVEN("Good case - Decode an ServiceDiscoveryRes document") { auto expected_session_id = std::vector{0x47, 0x58, 0xFD, 0xD3, 0x48, 0xA5, 0xEB, 0x24}; uint8_t doc_raw[] = "\x80\x9a\x02\x11\xd6\x3f\x74\xd2\x29\x7a\xc9\x11\xa0\x01\x20\x02\x41\x00\xc4"; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, reinterpret_cast(doc_raw), sizeof(doc_raw), pos1, nullptr); THEN("It should be decoded succussfully") { - din_exiDocument request; + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); + REQUIRE(result.decoding_successful); - REQUIRE(decode_din_exiDocument(&exi_stream_in, &request) == 0); + const auto& request = result.value; // Check Header const auto& header = request.V2G_Message.Header; diff --git a/tests/DIN/session_setup.cpp b/tests/din/session_setup.cpp similarity index 90% rename from tests/DIN/session_setup.cpp rename to tests/din/session_setup.cpp index 80720ac..983bfa8 100644 --- a/tests/DIN/session_setup.cpp +++ b/tests/din/session_setup.cpp @@ -1,14 +1,16 @@ #include +#include #include #include #include #include -#include #include #include +#include "test_utils/codec.hpp" + SCENARIO("Encode and decode DIN session setup message") { // Exi Stream: 809a02000000000000000011d01a121dc983cd6000 @@ -48,23 +50,11 @@ SCENARIO("Encode and decode DIN session setup message") { std::copy(evccid.begin(), evccid.end(), body.SessionSetupReq.EVCCID.bytes); body.SessionSetupReq.EVCCID.bytesLen = 6; - uint8_t stream[256] = {}; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, stream, sizeof(stream), pos1, nullptr); - THEN("It should be encoded succussfully") { + const auto result = test_utils::encode_and_compare(request, doc_raw, sizeof(doc_raw)); - REQUIRE(encode_din_exiDocument(&exi_stream_in, &request) == 0); - - const auto encoded_stream = - std::vector(stream, stream + exi_bitstream_get_length(&exi_stream_in) + 1); - - const auto expected_exi_stream = std::vector(std::begin(doc_raw), std::end(doc_raw)); - - REQUIRE(encoded_stream == expected_exi_stream); + REQUIRE(result.encoding_successful); + REQUIRE(result.bitstream_match); } } @@ -73,16 +63,12 @@ SCENARIO("Encode and decode DIN session setup message") { uint8_t doc_raw[] = "\x80" "\x9a\x02\x00\x00\x00\x00\x00\x00\x00\x00" "\x11\xd0\x1a\x12\x1d\xc9\x83\xcd\x60\x00"; - exi_bitstream_t exi_stream_in; - size_t pos1 = 0; - int errn = 0; - - exi_bitstream_init(&exi_stream_in, reinterpret_cast(doc_raw), sizeof(doc_raw), pos1, nullptr); THEN("It should be decoded succussfully") { - din_exiDocument request; + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); + REQUIRE(result.decoding_successful); - REQUIRE(decode_din_exiDocument(&exi_stream_in, &request) == 0); + const auto& request = result.value; // Check Header auto& header = request.V2G_Message.Header; @@ -222,4 +208,4 @@ SCENARIO("Encode and decode DIN session setup message") { // REQUIRE(session_setup_res.DateTimeNow == 1675074582); // } // } -} +} \ No newline at end of file diff --git a/tests/iso20/CMakeLists.txt b/tests/iso20/CMakeLists.txt new file mode 100644 index 0000000..59b1f44 --- /dev/null +++ b/tests/iso20/CMakeLists.txt @@ -0,0 +1,2 @@ +add_codec_test(ac_charge_loop) +add_codec_test(dc_charge_loop) diff --git a/tests/ISO20/ac_charge_loop.cpp b/tests/iso20/ac_charge_loop.cpp similarity index 93% rename from tests/ISO20/ac_charge_loop.cpp rename to tests/iso20/ac_charge_loop.cpp index 85be017..00c1612 100644 --- a/tests/ISO20/ac_charge_loop.cpp +++ b/tests/iso20/ac_charge_loop.cpp @@ -6,7 +6,7 @@ #include #include -#include "codec_helper.hpp" +#include "test_utils/codec.hpp" // Exi Stream: 8008041e9869d6a61dc1ef895b9b4a8062832418640096 // XML: @@ -69,7 +69,7 @@ SCENARIO("Encode and decode AC charge loop message") { charge_loop.BPT_Scheduled_AC_CLReqControlMode.EVPresentActivePower = {3, 200}; THEN("It should be encoded succussfully") { - const auto result = encode_iso20_and_compare(request, doc_raw, sizeof(doc_raw)); + const auto result = test_utils::encode_and_compare(request, doc_raw, sizeof(doc_raw)); REQUIRE(result.encoding_successful); REQUIRE(result.bitstream_match); @@ -98,7 +98,7 @@ SCENARIO("Encode and decode AC charge loop message") { charge_loop.BPT_Scheduled_AC_CLResControlMode = {}; THEN("It should be encoded succussfully") { - const auto result = encode_iso20_and_compare(response, doc_raw, sizeof(doc_raw)); + const auto result = test_utils::encode_and_compare(response, doc_raw, sizeof(doc_raw)); REQUIRE(result.encoding_successful); REQUIRE(result.bitstream_match); @@ -112,7 +112,7 @@ SCENARIO("Encode and decode AC charge loop message") { "\x9b\x4a\x80\x62\x83\x24\x18\x64\x00\x96"; THEN("It should be decoded succussfully") { - const auto result = decode_iso20(doc_raw, sizeof(doc_raw)); + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); REQUIRE(result.decoding_successful); const auto& request = result.value; @@ -144,7 +144,7 @@ SCENARIO("Encode and decode AC charge loop message") { "\x89\x5b\x9b\x4a\x80\x62\x00\x59\x00"; THEN("It should be decoded succussfully") { - const auto result = decode_iso20(doc_raw, sizeof(doc_raw)); + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); REQUIRE(result.decoding_successful); const auto& request = result.value; diff --git a/tests/ISO20/dc_charge_loop.cpp b/tests/iso20/dc_charge_loop.cpp similarity index 95% rename from tests/ISO20/dc_charge_loop.cpp rename to tests/iso20/dc_charge_loop.cpp index 7bcf4ab..5519def 100644 --- a/tests/ISO20/dc_charge_loop.cpp +++ b/tests/iso20/dc_charge_loop.cpp @@ -6,7 +6,7 @@ #include #include -#include "codec_helper.hpp" +#include "test_utils/codec.hpp" // Exi Stream: 8034042d166f29fb80ea560aebdbfb3062810012006164000a02002400c800 // XML: @@ -91,7 +91,7 @@ SCENARIO("Encode and decode DC charge loop message") { charge_loop.BPT_Scheduled_DC_CLReqControlMode.EVTargetVoltage = {0, 400}; THEN("It should be encoded succussfully") { - const auto result = encode_iso20_and_compare(request, doc_raw, sizeof(doc_raw)); + const auto result = test_utils::encode_and_compare(request, doc_raw, sizeof(doc_raw)); REQUIRE(result.encoding_successful); REQUIRE(result.bitstream_match); @@ -127,7 +127,7 @@ SCENARIO("Encode and decode DC charge loop message") { charge_loop.BPT_Scheduled_DC_CLResControlMode = {}; THEN("It should be encoded succussfully") { - const auto result = encode_iso20_and_compare(response, doc_raw, sizeof(doc_raw)); + const auto result = test_utils::encode_and_compare(response, doc_raw, sizeof(doc_raw)); REQUIRE(result.encoding_successful); REQUIRE(result.bitstream_match); @@ -142,7 +142,7 @@ SCENARIO("Encode and decode DC charge loop message") { "\x0a\x02\x00\x24\x00\xc8\x00"; THEN("It should be decoded succussfully") { - const auto result = decode_iso20(doc_raw, sizeof(doc_raw)); + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); REQUIRE(result.decoding_successful); const auto& request = result.value; @@ -178,7 +178,7 @@ SCENARIO("Encode and decode DC charge loop message") { "\x30\x62\x00\x63\xf0\x68\x07\x81\xfc\x28\x07\xc2\x22\x30"; THEN("It should be decoded succussfully") { - const auto result = decode_iso20(doc_raw, sizeof(doc_raw)); + const auto result = test_utils::decode(doc_raw, sizeof(doc_raw)); REQUIRE(result.decoding_successful); const auto& request = result.value; diff --git a/tests/test_utils/CMakeLists.txt b/tests/test_utils/CMakeLists.txt new file mode 100644 index 0000000..868a3f2 --- /dev/null +++ b/tests/test_utils/CMakeLists.txt @@ -0,0 +1,25 @@ +add_library(test_utilities OBJECT codec.cpp) +target_link_libraries(test_utilities + PUBLIC + cbv2g::din + cbv2g::iso2 + cbv2g::iso20 +) + +target_include_directories(test_utilities + PUBLIC + include +) + +function(add_codec_test CPP_FILE) + set(TEST_TARGET_NAME test_${CPP_FILE}) + add_executable(${TEST_TARGET_NAME} ${CPP_FILE}.cpp) + + target_link_libraries(${TEST_TARGET_NAME} + PRIVATE + test_utilities + Catch2::Catch2WithMain + ) + + catch_discover_tests(${TEST_TARGET_NAME}) +endfunction() diff --git a/tests/ISO20/codec_helper.cpp b/tests/test_utils/codec.cpp similarity index 53% rename from tests/ISO20/codec_helper.cpp rename to tests/test_utils/codec.cpp index f84de7c..ecde98a 100644 --- a/tests/ISO20/codec_helper.cpp +++ b/tests/test_utils/codec.cpp @@ -1,12 +1,20 @@ -#include "codec_helper.hpp" +#include "test_utils/codec.hpp" #include +#include +#include + +#include +#include + #include #include #include #include +namespace test_utils { + template static EncodingResult encode(int (*encode_func)(exi_bitstream_t*, DocType*), const DocType& request, const uint8_t* compare_data, std::size_t length) { @@ -29,18 +37,6 @@ static EncodingResult encode(int (*encode_func)(exi_bitstream_t*, DocType*), con return {true, encoded_stream == expected_exi_stream}; } -template <> -EncodingResult encode_iso20_and_compare(const iso20_ac_exiDocument& request, const uint8_t* compare_data, - std::size_t length) { - return encode(&encode_iso20_ac_exiDocument, request, compare_data, length); -} - -template <> -EncodingResult encode_iso20_and_compare(const iso20_dc_exiDocument& request, const uint8_t* compare_data, - std::size_t length) { - return encode(&encode_iso20_dc_exiDocument, request, compare_data, length); -} - template DecodingResult decode(int (*decode_func)(exi_bitstream_t*, DocType*), const uint8_t* raw_data, std::size_t length) { @@ -54,10 +50,54 @@ DecodingResult decode(int (*decode_func)(exi_bitstream_t*, DocType*), c return result; } -template <> DecodingResult decode_iso20(const uint8_t* raw_data, std::size_t length) { +// +// app handshake +// +template <> +EncodingResult encode_and_compare(const appHand_exiDocument& request, const uint8_t* compare_data, std::size_t length) { + return encode(&encode_appHand_exiDocument, request, compare_data, length); +} + +template <> DecodingResult decode(const uint8_t* raw_data, std::size_t length) { + return decode(&decode_appHand_exiDocument, raw_data, length); +} + +// +// din +// +template <> +EncodingResult encode_and_compare(const din_exiDocument& request, const uint8_t* compare_data, std::size_t length) { + return encode(&encode_din_exiDocument, request, compare_data, length); +} + +template <> DecodingResult decode(const uint8_t* raw_data, std::size_t length) { + return decode(&decode_din_exiDocument, raw_data, length); +} + +// +// iso20 ac +// +template <> +EncodingResult encode_and_compare(const iso20_ac_exiDocument& request, const uint8_t* compare_data, + std::size_t length) { + return encode(&encode_iso20_ac_exiDocument, request, compare_data, length); +} + +template <> DecodingResult decode(const uint8_t* raw_data, std::size_t length) { return decode(&decode_iso20_ac_exiDocument, raw_data, length); } -template <> DecodingResult decode_iso20(const uint8_t* raw_data, std::size_t length) { +// +// iso20 dc +// +template <> +EncodingResult encode_and_compare(const iso20_dc_exiDocument& request, const uint8_t* compare_data, + std::size_t length) { + return encode(&encode_iso20_dc_exiDocument, request, compare_data, length); +} + +template <> DecodingResult decode(const uint8_t* raw_data, std::size_t length) { return decode(&decode_iso20_dc_exiDocument, raw_data, length); } + +} // namespace test_utils diff --git a/tests/ISO20/codec_helper.hpp b/tests/test_utils/include/test_utils/codec.hpp similarity index 51% rename from tests/ISO20/codec_helper.hpp rename to tests/test_utils/include/test_utils/codec.hpp index 20712e7..7e3178b 100644 --- a/tests/ISO20/codec_helper.hpp +++ b/tests/test_utils/include/test_utils/codec.hpp @@ -3,17 +3,21 @@ #include #include +namespace test_utils { + struct EncodingResult { bool encoding_successful; bool bitstream_match; }; template -EncodingResult encode_iso20_and_compare(const DocType&, const uint8_t* compare_data, std::size_t length); +EncodingResult encode_and_compare(const DocType&, const uint8_t* compare_data, std::size_t length); template struct DecodingResult { bool decoding_successful; DocType value; }; -template DecodingResult decode_iso20(const uint8_t* raw_data, std::size_t length); +template DecodingResult decode(const uint8_t* raw_data, std::size_t length); + +} // namespace test_utils