name: Build

on: [push, pull_request]

#
# Some repeated stuff
#
env:
  sanitizer_autotools_flags: '
    CFLAGS="-fsanitize=address,leak"
    LDFLAGS="-fsanitize=address,leak"'

  cmake_sanitizer_flags: "
    -DCMAKE_C_FLAGS=-fsanitize=address,leak
    -DCMAKE_CXX_FLAGS=-fsanitize=address,leak
    -DCMAKE_SHARED_LINKER_FLAGS=-fsanitize=address,leak"

  cmake_extra_flags: "
    -DUPNP_ENABLE_UNSPECIFIED_SERVER=ON
    -DUPNP_ENABLE_BLOCKING_TCP_CONNECTIONS=ON"

jobs:
  # Linux builds
  linux:
    name: Build (${{ matrix.os }}) - ${{ matrix.conf }}
    runs-on: ${{ matrix.os }}
    strategy:
      matrix:
        os: [ubuntu-20.04, ubuntu-22.04]
        conf: [Debug, Release]
      fail-fast: false
    steps:
      - uses: actions/checkout@v2
      - name: Configure
        run: >
          cmake
          -S .
          -B build
          -DCMAKE_BUILD_TYPE=${{ matrix.conf }}
          -DBUILD_TESTING=ON
          -DDOWNLOAD_AND_BUILD_DEPS=ON
          -DUPNP_ENABLE_OPEN_SSL=ON
          -DCMAKE_C_FLAGS="-Wall -Wpedantic"
          -DCMAKE_INSTALL_PREFIX=${{ GITHUB.WORKSPACE }}/test-install
          ${{ env.cmake_extra_flags }}
      - name: Build
        run: cmake --build build --config ${{matrix.conf}}
      - name: Test
        run: |
          cd build
          ctest --output-on-failure
          cd ..
      - name: Debug output
        run: cmake -DBUILD_DIR=build -P cmake/post-test.cmake
      - name: install
        run: cmake --install build --config ${{matrix.conf}}
  # Windows Visual Studio builds
  windows-msvc:
    name: Build (${{ matrix.os }})  - ${{ matrix.conf }}
    runs-on: ${{ matrix.os }}
    strategy:
      matrix:
        os: [windows-2019, windows-latest, macos-latest]
        conf: [Debug, Release]
      fail-fast: false
    steps:
      - uses: actions/checkout@v2
      - name: Configure
        run: >
          cmake
          -S .
          -B build
          -DCMAKE_BUILD_TYPE=${{ matrix.conf }}
          -DBUILD_TESTING=ON
          -DDOWNLOAD_AND_BUILD_DEPS=ON
          -DCMAKE_INSTALL_PREFIX=${{ GITHUB.WORKSPACE }}/test-install
          ${{ env.cmake_extra_flags }}
      - name: Build
        run: cmake --build build --config ${{ matrix.conf }}
      - name: Test
        run: |
          cd build
          ctest --output-on-failure -C ${{ matrix.conf }}
          cd ..
      - name: Debug output
        run: cmake -DBUILD_DIR=build -P cmake/post-test.cmake
      - name: install
        run: cmake --install build --config ${{matrix.conf}}
  # Windows msys2 builds
  windows-msys2:
    name: Build MSys ${{matrix.sys}} - ${{matrix.conf}}
    runs-on: windows-latest
    strategy:
      matrix:
        sys: [mingw64, mingw32, ucrt64, clang64]
        conf: [Release, Debug]
    steps:
      - name: install sys (mingw64)
        uses: msys2/setup-msys2@v2
        if: ${{ matrix.sys == 'mingw64' }}
        with:
          msystem: ${{matrix.sys}}
          install: mingw-w64-x86_64-cmake mingw-w64-x86_64-make git mingw-w64-x86_64-gcc
      - name: install sys (mingw32)
        uses: msys2/setup-msys2@v2
        if: ${{ matrix.sys == 'mingw32' }}
        with:
          msystem: ${{matrix.sys}}
          install: mingw-w64-i686-cmake mingw-w64-i686-make git mingw-w64-i686-gcc
      - name: install sys (ucrt64)
        uses: msys2/setup-msys2@v2
        if: ${{ matrix.sys == 'ucrt64' }}
        with:
          msystem: ${{matrix.sys}}
          install: mingw-w64-ucrt-x86_64-cmake mingw-w64-ucrt-x86_64-make git mingw-w64-ucrt-x86_64-gcc
      - name: install sys (clang64)
        uses: msys2/setup-msys2@v2
        if: ${{ matrix.sys == 'clang64' }}
        with:
          msystem: ${{matrix.sys}}
          install: mingw-w64-clang-x86_64-cmake mingw-w64-clang-x86_64-make git mingw-w64-clang-x86_64-gcc
      - uses: actions/checkout@v2
      - name: Configure
        run: >
          cmake
          -S .
          -B build
          -DCMAKE_BUILD_TYPE=${{ matrix.conf }}
          -DBUILD_TESTING=ON
          -DDOWNLOAD_AND_BUILD_DEPS=ON
          -DCMAKE_INSTALL_PREFIX=${{ GITHUB.WORKSPACE }}/test-install
          ${{ env.cmake_extra_flags }}
      - name: Build
        run: cmake --build build --config ${{matrix.conf}}
      - name: Test
        run: |
          cd build
          ctest --output-on-failure -C ${{ matrix.conf }}
          cd ..
      - name: Debug output
        run: cmake -DBUILD_DIR=build -P cmake/post-test.cmake
      - name: install
        run: cmake --install build --config ${{matrix.conf}}
  # Linux sanitizer builds
  build_asan:
    name: Sanitizer build (ubuntu-20.04) - ${{ matrix.tool }}
    runs-on: ubuntu-20.04
    strategy:
      matrix:
        tool: [autotools, cmake]
        conf: [Debug]
    steps:
    - uses: actions/checkout@v1
    - name: bootstrap and configure (autotools)
      if: ${{ matrix.tool == 'autotools' }}
      run: >
        ./bootstrap &&
        ./configure
        --enable-debug
        ${{ env.sanitizer_autotools_flags }}
    - name: configure (cmake)
      if: ${{ matrix.tool == 'cmake' }}
      run: >
        cmake
        -S .
        -B build
        -DBUILD_TESTING=ON
        -DCMAKE_BUILD_TYPE=${{ matrix.conf }}
        -DDOWNLOAD_AND_BUILD_DEPS=ON
        -DUPNP_ENABLE_OPEN_SSL=ON
        ${{ env.cmake_sanitizer_flags }}
        ${{ env.cmake_extra_flags }}
    - name: build (autotools)
      if: ${{ matrix.tool == 'autotools' }}
      run: make
    - name: build (cmake)
      if: ${{ matrix.tool == 'cmake' }}
      run: cmake --build build
    - name: test ixml (autotools)
      if: ${{ matrix.tool == 'autotools' }}
      run: >
        cd ixml && make check ||
        (cat test-suite.log && exit 1)
    - name: test upnp (autotools)
      if: ${{ matrix.tool == 'autotools' }}
      run: >
        cd upnp && make check && cat test_init.log ||
        (cat test-suite.log test_init.log && exit 1)
    - name: ctest (cmake)
      if: ${{ matrix.tool == 'cmake' }}
      run: |
          cd build
          ctest --output-on-failure
