diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index dd479fb0..1e396be6 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -53,15 +53,29 @@ jobs: name: 'integration on ${{ matrix.image }}' runs-on: ${{ matrix.image }} timeout-minutes: 5 + defaults: + run: + shell: ${{ contains(matrix.image, 'windows') && 'msys2 {0}' || 'bash' }} env: - CC: clang - CMAKE_GENERATOR: Ninja + CC: ${{ !contains(matrix.image, 'windows') && 'clang' || '' }} strategy: fail-fast: false matrix: - image: [ubuntu-latest, macos-latest] + image: [ubuntu-latest, macos-latest, windows-latest] steps: + - uses: msys2/setup-msys2@d44ca8e88d8b43d56cf5670f91747359d5537f97 # v2 + if: ${{ contains(matrix.image, 'windows') }} + with: + msystem: mingw64 + release: false + update: false + cache: false + path-type: inherit + install: >- + mingw-w64-x86_64-zlib mingw-w64-x86_64-libgcrypt mingw-w64-x86_64-openssl mingw-w64-x86_64-mbedtls + - name: 'install packages' + if: ${{ !contains(matrix.image, 'windows') }} run: | if [[ '${{ matrix.image }}' = *'ubuntu'* ]]; then sudo rm -f /var/lib/man-db/auto-update @@ -75,16 +89,19 @@ jobs: persist-credentials: false - name: 'via FetchContent' run: ./tests/cmake/test.sh FetchContent - - name: 'via add_subdirectory' - run: ./tests/cmake/test.sh add_subdirectory + - name: 'via add_subdirectory OpenSSL' + run: ./tests/cmake/test.sh add_subdirectory -DCRYPTO_BACKEND=OpenSSL + - name: 'via add_subdirectory Libgcrypt' + run: ./tests/cmake/test.sh add_subdirectory -DCRYPTO_BACKEND=Libgcrypt - name: 'via find_package OpenSSL' - run: ./tests/cmake/test.sh find_package OpenSSL + run: ./tests/cmake/test.sh find_package -DCRYPTO_BACKEND=OpenSSL - name: 'via find_package Libgcrypt' - run: ./tests/cmake/test.sh find_package Libgcrypt + run: ./tests/cmake/test.sh find_package -DCRYPTO_BACKEND=Libgcrypt - name: 'via find_package mbedTLS' - run: ./tests/cmake/test.sh find_package mbedTLS + run: ./tests/cmake/test.sh find_package -DCRYPTO_BACKEND=mbedTLS - name: 'via find_package wolfSSL' - run: ./tests/cmake/test.sh find_package wolfSSL + if: ${{ !contains(matrix.image, 'windows') }} # MSYS2 wolfSSL package not built with the OpenSSL compatibility option + run: ./tests/cmake/test.sh find_package -DCRYPTO_BACKEND=wolfSSL build_linux: name: 'linux' diff --git a/tests/cmake/CMakeLists.txt b/tests/cmake/CMakeLists.txt index 850c450b..ea9345d8 100644 --- a/tests/cmake/CMakeLists.txt +++ b/tests/cmake/CMakeLists.txt @@ -4,7 +4,7 @@ cmake_minimum_required(VERSION 3.7...3.16 FATAL_ERROR) message(STATUS "Using CMake version ${CMAKE_VERSION}") -project(test-dependent C) +project(test-consumer C) option(TEST_INTEGRATION_MODE "Integration mode" "find_package") @@ -14,7 +14,16 @@ if(TEST_INTEGRATION_MODE STREQUAL "FetchContent" AND CMAKE_VERSION VERSION_LESS message(FATAL_ERROR "This test requires CMake 3.14 or upper") endif() -if(TEST_INTEGRATION_MODE STREQUAL "find_package") +if(TEST_INTEGRATION_MODE STREQUAL "ExternalProject") # Broken + include(ExternalProject) + ExternalProject_Add(libssh2 + URL "${FROM_ARCHIVE}" URL_HASH "SHA256=${FROM_HASH}" + INSTALL_COMMAND "" + DOWNLOAD_EXTRACT_TIMESTAMP ON) +endif() + +if(TEST_INTEGRATION_MODE STREQUAL "find_package" OR + TEST_INTEGRATION_MODE STREQUAL "ExternalProject") find_package(libssh2 REQUIRED CONFIG) find_package(libssh2 REQUIRED CONFIG) # Double-inclusion test foreach(result_var IN ITEMS @@ -50,31 +59,32 @@ elseif(TEST_INTEGRATION_MODE STREQUAL "FetchContent") FetchContent_MakeAvailable(libssh2) # Requires CMake 3.14 endif() -add_executable(test-dependent-static-ns "test.c") -target_link_libraries(test-dependent-static-ns PRIVATE "libssh2::libssh2_static") +add_executable(test-consumer-static-ns "test.c") +target_link_libraries(test-consumer-static-ns PRIVATE "libssh2::libssh2_static") -add_executable(test-dependent-shared-ns "test.c") -target_link_libraries(test-dependent-shared-ns PRIVATE "libssh2::libssh2_shared") +add_executable(test-consumer-shared-ns "test.c") +target_link_libraries(test-consumer-shared-ns PRIVATE "libssh2::libssh2_shared") # Alias for either shared or static library -add_executable(test-dependent-selected-ns "test.c") -target_link_libraries(test-dependent-selected-ns PRIVATE "libssh2::libssh2") +add_executable(test-consumer-selected-ns "test.c") +target_link_libraries(test-consumer-selected-ns PRIVATE "libssh2::libssh2") -if(TEST_INTEGRATION_MODE STREQUAL "find_package") +if(TEST_INTEGRATION_MODE STREQUAL "find_package" OR + TEST_INTEGRATION_MODE STREQUAL "ExternalProject") # Compatibility alias - add_executable(test-dependent-compat "test.c") - target_link_libraries(test-dependent-compat PRIVATE "Libssh2::libssh2") + add_executable(test-consumer-compat "test.c") + target_link_libraries(test-consumer-compat PRIVATE "Libssh2::libssh2") elseif(TEST_INTEGRATION_MODE STREQUAL "add_subdirectory" OR TEST_INTEGRATION_MODE STREQUAL "FetchContent") - add_executable(test-dependent-static-bare "test.c") - target_link_libraries(test-dependent-static-bare PRIVATE "libssh2_static") + add_executable(test-consumer-static-bare "test.c") + target_link_libraries(test-consumer-static-bare PRIVATE "libssh2_static") - add_executable(test-dependent-shared-bare "test.c") - target_link_libraries(test-dependent-shared-bare PRIVATE "libssh2_shared") + add_executable(test-consumer-shared-bare "test.c") + target_link_libraries(test-consumer-shared-bare PRIVATE "libssh2_shared") - add_executable(test-dependent-selected-bare "test.c") - target_link_libraries(test-dependent-selected-bare PRIVATE "libssh2") + add_executable(test-consumer-selected-bare "test.c") + target_link_libraries(test-consumer-selected-bare PRIVATE "libssh2") endif() diff --git a/tests/cmake/test.c b/tests/cmake/test.c index 029c84d8..b00dcc3d 100644 --- a/tests/cmake/test.c +++ b/tests/cmake/test.c @@ -6,8 +6,34 @@ #include "libssh2.h" #include -int main(void) +int main(int argc, char **argv) { - printf("libssh2_version(0): |%s|\n", libssh2_version(0)); + const char *crypto_str; + + (void)argc; + + switch(libssh2_crypto_engine()) { + case libssh2_gcrypt: + crypto_str = "libgcrypt"; + break; + case libssh2_mbedtls: + crypto_str = "mbedTLS"; + break; + case libssh2_openssl: + crypto_str = "openssl compatible"; + break; + case libssh2_os400qc3: + crypto_str = "OS400QC3"; + break; + case libssh2_wincng: + crypto_str = "WinCNG"; + break; + default: + crypto_str = "(unrecognized)"; + } + + printf("libssh2 test: |%s|%s|%s|\n", argv[0], + libssh2_version(0), crypto_str); + return 0; } diff --git a/tests/cmake/test.sh b/tests/cmake/test.sh index 2474db48..7efe1d01 100755 --- a/tests/cmake/test.sh +++ b/tests/cmake/test.sh @@ -1,44 +1,130 @@ -#!/bin/sh +#!/bin/sh -x # # Copyright (C) Viktor Szakats # SPDX-License-Identifier: BSD-3-Clause +# shellcheck disable=SC2086 + set -eu cd "$(dirname "$0")" -mode="${1:-all}" +command -v ninja >/dev/null && export CMAKE_GENERATOR=Ninja # 3.17+ -if [ "${mode}" = 'all' ] || [ "${mode}" = 'FetchContent' ]; then - rm -rf bld-fetchcontent - cmake -B bld-fetchcontent \ +mode="${1:-all}"; shift + +cmake_consumer="${CMAKE_CONSUMER:-cmake}" +cmake_provider="${CMAKE_PROVIDER:-${cmake_consumer}}" + +# 'modern': supports -S/-B (3.13+), --install (3.15+) +"${cmake_consumer}" --help | grep -q -- '--install' && cmake_consumer_modern=1 +"${cmake_provider}" --help | grep -q -- '--install' && cmake_provider_modern=1 + +cmake_opts='-DBUILD_EXAMPLES=OFF -DBUILD_TESTING=OFF -DENABLE_ZLIB_COMPRESSION=ON' + +src='../..' + +runresults() { + set +x + for bin in "$1"/test-consumer*; do + file "${bin}" || true + ${LIBSSH2_TEST_EXE_RUNNER:-} "${bin}" || true + done + set -x +} + +if [ "${mode}" = 'ExternalProject' ]; then # Broken + (cd "${src}"; git archive --format=tar HEAD) | gzip > source.tar.gz + src="${PWD}/source.tar.gz" + sha="$(openssl dgst -sha256 "${src}" | grep -a -i -o -E '[0-9a-f]{64}$')" + bldc='bld-externalproject' + rm -rf "${bldc}" + if [ -n "${cmake_consumer_modern:-}" ]; then # 3.15+ + "${cmake_consumer}" -B "${bldc}" ${cmake_opts} -DCMAKE_UNITY_BUILD=ON "$@" \ + -DTEST_INTEGRATION_MODE=ExternalProject \ + -DFROM_ARCHIVE="${src}" -DFROM_HASH="${sha}" + "${cmake_consumer}" --build "${bldc}" --verbose + else + mkdir "${bldc}"; cd "${bldc}" + "${cmake_consumer}" .. ${cmake_opts} "$@" \ + -DTEST_INTEGRATION_MODE=ExternalProject \ + -DFROM_ARCHIVE="${src}" -DFROM_HASH="${sha}" + VERBOSE=1 "${cmake_consumer}" --build . + cd .. + fi + runresults "${bldc}" +fi + +if [ "${mode}" = 'all' ] || [ "${mode}" = 'FetchContent' ]; then # 3.14+ + src="${PWD}/${src}" + bldc='bld-fetchcontent' + rm -rf "${bldc}" + "${cmake_consumer}" -B "${bldc}" ${cmake_opts} -DCMAKE_UNITY_BUILD=ON "$@" \ -DTEST_INTEGRATION_MODE=FetchContent \ - -DFROM_GIT_REPO="${PWD}/../.." \ + -DFROM_GIT_REPO="${src}" \ -DFROM_GIT_TAG="$(git rev-parse HEAD)" - cmake --build bld-fetchcontent + "${cmake_consumer}" --build "${bldc}" --verbose + PATH="${bldc}/_deps/libssh2-build/lib:${PATH}" + runresults "${bldc}" fi if [ "${mode}" = 'all' ] || [ "${mode}" = 'add_subdirectory' ]; then - rm -rf libssh2; ln -s ../.. libssh2 - rm -rf bld-add_subdirectory - cmake -B bld-add_subdirectory \ - -DTEST_INTEGRATION_MODE=add_subdirectory - cmake --build bld-add_subdirectory + rm -rf libssh2 + if ! ln -s "${src}" libssh2; then + rm -rf libssh2; mkdir libssh2; (cd "${src}"; git archive --format=tar HEAD) | tar -x --directory=libssh2 # for MSYS2/Cygwin + fi + bldc='bld-add_subdirectory' + rm -rf "${bldc}" + if [ -n "${cmake_consumer_modern:-}" ]; then # 3.15+ + "${cmake_consumer}" -B "${bldc}" ${cmake_opts} -DCMAKE_UNITY_BUILD=ON "$@" \ + -DTEST_INTEGRATION_MODE=add_subdirectory + "${cmake_consumer}" --build "${bldc}" --verbose + else + mkdir "${bldc}"; cd "${bldc}" + # Disable `pkg-config` for CMake <= 3.12. These versions cannot propagate + # library directories to the consumer project. + "${cmake_consumer}" .. ${cmake_opts} -DCURL_USE_PKGCONFIG=OFF "$@" \ + -DTEST_INTEGRATION_MODE=add_subdirectory + VERBOSE=1 "${cmake_consumer}" --build . + cd .. + fi + PATH="${bldc}/libssh2/src:${PATH}" + runresults "${bldc}" fi if [ "${mode}" = 'all' ] || [ "${mode}" = 'find_package' ]; then - crypto="${2:-OpenSSL}" - bld="bld-libssh2-${crypto}" - rm -rf "${bld}" - cmake ../.. -B "${bld}" -DCMAKE_INSTALL_PREFIX="${PWD}/${bld}/_pkg" \ - -DBUILD_EXAMPLES=OFF -DBUILD_TESTING=OFF \ - -DENABLE_ZLIB_COMPRESSION=ON \ - -DCRYPTO_BACKEND="${crypto}" - cmake --build "${bld}" - cmake --install "${bld}" - rm -rf bld-find_package - cmake -B bld-find_package \ - -DTEST_INTEGRATION_MODE=find_package \ - -DCMAKE_PREFIX_PATH="${PWD}/${bld}/_pkg/lib/cmake/libssh2" - cmake --build bld-find_package --verbose + src="${PWD}/${src}" + bldp='bld-libssh2' + prefix="${PWD}/${bldp}/_pkg" + rm -rf "${bldp}" + if [ -n "${cmake_provider_modern:-}" ]; then # 3.15+ + "${cmake_provider}" -B "${bldp}" -S "${src}" ${cmake_opts} -DCMAKE_UNITY_BUILD=ON "$@" \ + -DCMAKE_INSTALL_PREFIX="${prefix}" + "${cmake_provider}" --build "${bldp}" + "${cmake_provider}" --install "${bldp}" + else + mkdir "${bldp}"; cd "${bldp}" + "${cmake_provider}" "${src}" ${cmake_opts} "$@" \ + -DCMAKE_INSTALL_PREFIX="${prefix}" + "${cmake_provider}" --build . + make install + cd .. + fi + bldc='bld-find_package' + rm -rf "${bldc}" + if [ -n "${cmake_consumer_modern:-}" ]; then # 3.15+ + "${cmake_consumer}" -B "${bldc}" \ + -DTEST_INTEGRATION_MODE=find_package \ + -DCMAKE_PREFIX_PATH="${prefix}/lib/cmake/libssh2" + "${cmake_consumer}" --build "${bldc}" --verbose + else + mkdir "${bldc}"; cd "${bldc}" + "${cmake_consumer}" .. \ + -DTEST_INTEGRATION_MODE=find_package \ + -DCMAKE_PREFIX_PATH="${prefix}/lib/cmake/libssh2" + VERBOSE=1 "${cmake_consumer}" --build . + cd .. + fi + PATH="${prefix}/bin:${PATH}" + runresults "${bldc}" fi