name: Check example code

on:
  push:
    branches:
      - master
  pull_request:
    branches:
      - master

jobs:
  correctness:
    name: OI-wiki Offline Test
    runs-on: ubuntu-latest
    outputs:
      any_changed: ${{ steps.changed-files.outputs.any_changed }}
      files_to_test: ${{ steps.GetFiles.outputs.files_to_test }}
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Get changed code files
        id: changed-files
        uses: tj-actions/changed-files@v46
        with:
          files: |
            docs/**/*.cpp
            docs/**/*.in
            docs/**/*.ans
      - uses: actions/setup-python@v5
        if: steps.changed-files.outputs.any_changed == 'true'
        with:
          python-version: '3.10'
      - name: Install uv
        if: steps.changed-files.outputs.any_changed == 'true'
        uses: astral-sh/setup-uv@v6
        with:
          version: "latest"
      - name: Install Python dependencies
        if: steps.changed-files.outputs.any_changed == 'true'
        run: uv sync
      - name: Install C++
        if: steps.changed-files.outputs.any_changed == 'true'
        run: |
          sudo apt-get update
          sudo apt-get install -y g++
      - name: Make the File list
        if: steps.changed-files.outputs.any_changed == 'true'
        run: echo "${{ steps.changed-files.outputs.all_changed_files }}" > res.txt
      - name: Get Files to Test
        if: steps.changed-files.outputs.any_changed == 'true'
        id: GetFiles
        run: uv run python scripts/get_files_to_test.py
      - name: Correctness Check
        if: steps.changed-files.outputs.any_changed == 'true'
        env: 
          FILES_TO_TEST: ${{ steps.GetFiles.outputs.files_to_test }}
        run: uv run python scripts/correctness_check.py

  undefinedbehaviors-ubuntu:
    name: UB Check - x86_64 Ubuntu
    needs: correctness
    if: ${{ needs.correctness.outputs.any_changed == 'true' }}
    runs-on: ubuntu-latest
    container: ghcr.io/trickeye/ubuntu_gcc1x:clang
    outputs:
      output: ${{ steps.set-output.outputs.output }}
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Install g++-9
        run: |
          apt-get update
          apt-get install -y g++-9
      - name: Undefined Behaviors Check
        env: 
          FILES_TO_TEST: ${{ needs.correctness.outputs.files_to_test }}
          RUNS_ON: x86_64 Ubuntu
          PYTHONIOENCODING: UTF-8
        run: python3 scripts/ub-check.py

  undefinedbehaviors-macos:
    name: UB Check - Arm64 MacOS
    needs: correctness
    if: ${{ needs.correctness.outputs.any_changed == 'true' }}
    runs-on: macos-latest
    outputs:
      output: ${{ steps.set-output.outputs.output }}
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Check Compiler Version
        run: |
          echo "::group::Check G++ Version"
          g++-14 --version
          echo "::endgroup::"
          echo "::group::Check Clang Version"
          clang --version
          echo "::endgroup::"
      - name: Undefined Behaviors Check
        env: 
          FILES_TO_TEST: ${{ needs.correctness.outputs.files_to_test }}
          RUNS_ON: arm64 MacOS
          PYTHONIOENCODING: UTF-8
        run: python3 scripts/ub-check.py

  undefinedbehaviors-rv:
    name: UB Check - RISC-V Ubuntu
    needs: correctness
    if: ${{ needs.correctness.outputs.any_changed == 'true' }}
    runs-on: ubuntu-latest
    outputs:
      output: ${{ steps.set-output.outputs.output }}
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Launch Risc-V Docker
        run: |
          docker pull --platform riscv64 ghcr.io/trickeye/ubtest:latest
          docker run --rm --privileged multiarch/qemu-user-static --reset -p yes
          docker run -d --name ubtest --platform riscv64 \
            --volume $PWD:$PWD \
            --volume $GITHUB_STEP_SUMMARY:$GITHUB_STEP_SUMMARY \
            --workdir $PWD \
            --env FILES_TO_TEST="${{ needs.correctness.outputs.files_to_test }}" \
            --env RUNS_ON="riscv64 Ubuntu" \
            --env PYTHONIOENCODING="UTF-8" \
            --env GITHUB_STEP_SUMMARY=$GITHUB_STEP_SUMMARY \
            ghcr.io/trickeye/ubtest:latest sleep infinity
          docker exec ubtest uname -a
      - name: Check Compiler Version
        run: |
          echo "::group::gcc --version"
          docker exec ubtest gcc --version
          echo "::endgroup::"
          echo "::group::g++ --version"
          docker exec ubtest g++ --version
          echo "::endgroup::"
          echo "::group::clang --version"
          docker exec ubtest clang++ --version
          echo "::endgroup::"
      - name: Undefined Behaviors Check
        # The environment variables are set in Launch Risc-V Docker step
        run: docker exec ubtest python3 scripts/ub-check.py

  undefinedbehaviors-windows:
    name: UB Check - x86_64 Windows
    needs: correctness
    if: ${{ needs.correctness.outputs.any_changed == 'true' }}
    runs-on: windows-2025
    outputs:
      output: ${{ steps.set-output.outputs.output }}
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Check Compiler Version
        shell: cmd
        run: |
          echo ::group::Install Clang, MinGW
          choco install -y llvm mingw
          echo ::endgroup::
          echo ::group::Check Clang Version
          clang --version
          echo ::endgroup::
          echo ::group::Check G++ Version
          g++ --version
          echo ::endgroup::
          echo ::group::Check MSVC Version
          call "C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Auxiliary\Build\vcvars64.bat"
          cl.exe
          echo ::endgroup::
      - name: Undefined Behaviors Check
        env: 
          FILES_TO_TEST: ${{ needs.correctness.outputs.files_to_test }}
          RUNS_ON: x86_64 Windows
          PYTHONIOENCODING: UTF-8
        run: |
          chcp 65001
          python scripts/ub-check.py


  undefinedbehaviors-alpine:
    name: UB Check - x86_64 Alpine
    needs: correctness
    if: ${{ needs.correctness.outputs.any_changed == 'true' }}
    runs-on: ubuntu-latest
    outputs:
      output: ${{ steps.set-output.outputs.output }}
    container: alpine:latest
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0
      - name: Check Compiler Version
        run: |
          echo "::group::Install Python, GCC, Clang"
          apk add build-base python3 llvm clang
          echo "::endgroup::"
          echo "::group::Check G++ Version"
          g++ --version
          echo "::endgroup::"
          echo "::group::Check Clang Version"
          clang --version
          echo "::endgroup::"
      - name: Undefined Behaviors Check
        env: 
          FILES_TO_TEST: ${{ needs.correctness.outputs.files_to_test }}
          RUNS_ON: x86_64 Alpine
          PYTHONIOENCODING: UTF-8
        run: python3 scripts/ub-check.py
