diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b310b27..13d7d8c 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -22,8 +22,8 @@ jobs: # older libzmq and without draft - os: "ubuntu-22.04" cppstd: "11" - cc: "gcc-9" - cxx: "g++-9" + cc: "gcc-12" + cxx: "g++-12" drafts: "OFF" libzmq: "4.2.0" libzmqbuild: "pkgconfig" @@ -38,8 +38,8 @@ jobs: # coverage (gcc version should match gcov version) - os: "ubuntu-22.04" cppstd: "17" - cc: "gcc-9" - cxx: "g++-9" + cc: "gcc-12" + cxx: "g++-12" drafts: "ON" libzmq: "4.3.5" libzmqbuild: "cmake" @@ -71,14 +71,14 @@ jobs: # libzmq: "4.3.5" # libzmqbuild: "cmake" # platform: "-Ax64" - - os: "windows-2022" - cppstd: "20" - cc: "msbuild" - cxx: "msbuild" - drafts: "ON" - libzmq: "4.3.5" - libzmqbuild: "cmake" - platform: "-Ax64" + # - os: "windows-2022" + # cppstd: "20" + # cc: "msbuild" + # cxx: "msbuild" + # drafts: "ON" + # libzmq: "4.3.5" + # libzmqbuild: "cmake" + # platform: "-Ax64" env: CC: ${{ matrix.cc }} @@ -108,9 +108,16 @@ jobs: - name: build_libzmq_cmake if: ${{ matrix.libzmqbuild == 'cmake' }} run: | + if [ ! "${{ matrix.os }}" = 'windows-2022' ]; then + export CXXFLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" + export CFLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" + fi cmake -Hlibzmq-${{ matrix.libzmq }} -Blibzmq-build ${{ matrix.platform}} \ -DWITH_PERF_TOOL=OFF \ -DZMQ_BUILD_TESTS=OFF \ + -DLIBZMQ_WERROR=OFF \ + -DCMAKE_CXX_FLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" \ + -DCMAKE_C_FLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" \ -DCMAKE_BUILD_TYPE=Release \ -DENABLE_DRAFTS=${{ matrix.drafts }} cmake --build libzmq-build --config ${BUILDTYPE} -j ${THREADS} @@ -126,6 +133,8 @@ jobs: if: ${{ matrix.libzmqbuild == 'pkgconfig' }} working-directory: libzmq-${{ matrix.libzmq }} run: | + export CXXFLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" + export CFLAGS="-Wno-error=stringop-truncation -Wno-stringop-overflow" ./autogen.sh && ./configure --prefix=${PWD}/libzmq-build && make -j ${THREADS} diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index 3821c5c..3adfcc4 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -31,6 +31,7 @@ add_executable( monitor.cpp utilities.cpp timers.cpp + curve.cpp ) target_include_directories(unit_tests PUBLIC ${CATCH_MODULE_PATH}) diff --git a/tests/curve.cpp b/tests/curve.cpp new file mode 100644 index 0000000..9ad8a02 --- /dev/null +++ b/tests/curve.cpp @@ -0,0 +1,36 @@ +#include +#include + +#ifdef ZMQ_HAVE_CURVE + +TEST_CASE("curve_keypair", "[curve]") +{ + auto keys = zmq::curve_keypair(); + auto public_key = keys.first; + auto secret_key = keys.second; + CHECK(!public_key.empty()); + CHECK(!secret_key.empty()); +} + +TEST_CASE("curve_public", "[curve]") +{ + auto secret_key = "D:)Q[IlAW!ahhC2ac:9*A}h:p?([4%wOTJ%JR%cs"; + auto public_key = zmq::curve_public(secret_key); + CHECK(public_key == "Yne@$w-vo data{1,2,3,4,5,6,7,8}; + auto encoded = zmq::z85_encode(data); + CHECK(encoded.size() == std::string("0rJua1Qkhq").size()); + CHECK(encoded == "0rJua1Qkhq"); +} + +TEST_CASE("z85_decode", "[curve]") +{ + auto decoded = zmq::z85_decode("0rJua1Qkhq"); + CHECK(decoded == std::vector{1,2,3,4,5,6,7,8}); +} diff --git a/zmq.hpp b/zmq.hpp index ad0509e..2f4d0e0 100644 --- a/zmq.hpp +++ b/zmq.hpp @@ -107,6 +107,7 @@ #include #include +#include #include #include @@ -539,7 +540,7 @@ class message_t throw error_t(); memcpy(data(), data_, size_); } - + void rebuild(const std::string &str) { rebuild(str.data(), str.size()); @@ -2492,7 +2493,7 @@ class monitor_t (void) addr_; } - protected: + protected: bool process_event(short events) { zmq::message_t eventMsg; @@ -2874,6 +2875,53 @@ class timers #endif // defined(ZMQ_CPP11) && defined(ZMQ_HAVE_TIMERS) +#ifdef ZMQ_HAVE_CURVE + +inline std::pair curve_keypair() +{ + char public_key_buffer[41]; + char secret_key_buffer[41]; + int rc = zmq_curve_keypair(public_key_buffer, secret_key_buffer); + if (rc == -1) + throw zmq::error_t(); + return {public_key_buffer, secret_key_buffer}; +} + +inline std::string curve_public(const std::string& secret) +{ + if (secret.size() != 40) + throw std::runtime_error("Invalid secret string size"); + char public_key_buffer[41]; + int rc = zmq_curve_public(public_key_buffer, secret.c_str()); + if (rc == -1) + throw zmq::error_t(); + return public_key_buffer; +} + +#endif + +inline std::string z85_encode(const std::vector& data) +{ + size_t buffer_size = data.size() * size_t{6} / size_t{5} + 1; + std::string buffer(buffer_size, '\0'); + auto *result = zmq_z85_encode(&buffer[0], data.data(), data.size()); + if (result == nullptr) + throw zmq::error_t(); + while (buffer.back() == '\0') + buffer.pop_back(); + return buffer; +} + +inline std::vector z85_decode(const std::string& encoded) +{ + size_t dest_size = encoded.size() * size_t{4} / size_t{5}; + std::vector dest(dest_size); + auto *result = zmq_z85_decode(dest.data(), encoded.c_str()); + if (result == nullptr) + throw zmq::error_t(); + return dest; +} + } // namespace zmq #endif // __ZMQ_HPP_INCLUDED__