centralizing blog repo #567
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: CI | |
| on: | |
| push: | |
| branches: | |
| - '**' | |
| pull_request: | |
| branches: | |
| - '**' | |
| permissions: | |
| contents: read | |
| pull-requests: write | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| jobs: | |
| build-and-test: | |
| # Run on pushes for all branches, and only on PRs from forks to avoid double CI on same-repo PRs | |
| if: github.event_name == 'push' || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.fork == true) | |
| strategy: | |
| fail-fast: false | |
| max-parallel: 8 | |
| matrix: | |
| include: | |
| - runner: ["self-hosted", "linux", "gpu"] | |
| name: linux-x86_64 | |
| - runner: ["self-hosted", "windows", "gpu"] | |
| name: windows-x86_64 | |
| - runner: macos-latest | |
| name: macos-universal | |
| runs-on: ${{ matrix.runner }} | |
| env: | |
| # Ensure single-threaded tests for GC stability | |
| RUST_TEST_THREADS: 1 | |
| # Enable backtraces on CI to aid debugging of panics/segfaults | |
| RUST_BACKTRACE: 1 | |
| MATRIX_NAME: ${{ matrix.name }} | |
| steps: | |
| - uses: actions/checkout@v3 | |
| - name: Install Rust toolchain (Windows self-hosted) | |
| if: runner.os == 'Windows' | |
| shell: pwsh | |
| env: | |
| RUST_TOOLCHAIN: 1.90.0 | |
| RUST_COMPONENTS: rustfmt clippy | |
| run: | | |
| $toolchain = $env:RUST_TOOLCHAIN | |
| $components = $env:RUST_COMPONENTS.Split(' ') | |
| $cargoBin = Join-Path $env:USERPROFILE '.cargo\bin' | |
| $rustup = Join-Path $cargoBin 'rustup.exe' | |
| if (-not (Test-Path $cargoBin)) { | |
| New-Item -ItemType Directory -Path $cargoBin | Out-Null | |
| } | |
| if (-not (Test-Path $rustup)) { | |
| $tmp = Join-Path $env:USERPROFILE 'actions-runner\_work\_temp\rustup-init.exe' | |
| Invoke-WebRequest -Uri https://static.rust-lang.org/rustup/dist/x86_64-pc-windows-msvc/rustup-init.exe -OutFile $tmp | |
| & $tmp -y --default-host x86_64-pc-windows-msvc --default-toolchain $toolchain | |
| } else { | |
| & $rustup default $toolchain | |
| } | |
| foreach ($component in $components) { | |
| & $rustup component add --toolchain $toolchain $component | |
| } | |
| - uses: actions-rs/toolchain@v1 | |
| if: runner.os != 'Windows' | |
| with: | |
| toolchain: 1.90.0 | |
| components: rustfmt, clippy | |
| - uses: Swatinem/rust-cache@v2 | |
| - name: Install Linux system dependencies (BLAS/LAPACK, ZMQ, GUI, OpenSSL) | |
| if: runner.os == 'Linux' | |
| run: | | |
| # TEMP: include gdb while investigating Linux GPU segfaults (remove once resolved) | |
| sudo apt-get update | |
| sudo DEBIAN_FRONTEND=noninteractive apt-get install -y --no-install-recommends \ | |
| libopenblas-dev liblapack-dev libssl-dev \ | |
| libzmq3-dev pkg-config \ | |
| libx11-dev libxi-dev libxcursor-dev libxrandr-dev libxinerama-dev \ | |
| libxkbcommon-dev libxkbcommon-x11-0 libwayland-dev \ | |
| libegl1-mesa-dev libgl1-mesa-dev \ | |
| libudev-dev libdbus-1-dev ca-certificates \ | |
| gdb | |
| - name: Install macOS dependencies (ZMQ) | |
| if: runner.os == 'macOS' | |
| run: | | |
| brew update | |
| brew install zeromq | |
| - name: Install Windows dependencies (ZMQ, vcpkg + OpenBLAS) | |
| if: runner.os == 'Windows' | |
| shell: pwsh | |
| run: | | |
| choco install -y pkgconfiglite | |
| Write-Host "Fetching prebuilt ZeroMQ for Windows (MSVC)" | |
| curl -L -o libzmq.zip https://github.com/zeromq/libzmq/releases/download/v4.3.5/zeromq-4.3.5.zip | |
| Expand-Archive -Path libzmq.zip -DestinationPath zmq | |
| # Set env vars for ZMQ include/lib | |
| $zmq = Join-Path $pwd "zmq" | |
| Add-Content -Path $env:GITHUB_ENV -Value "INCLUDE=$($zmq)\include;$env:INCLUDE" | |
| Add-Content -Path $env:GITHUB_ENV -Value "LIB=$($zmq)\lib;$env:LIB" | |
| Add-Content -Path $env:GITHUB_ENV -Value "ZMQ_PATH=$($zmq)" | |
| Add-Content -Path $env:GITHUB_ENV -Value "PKG_CONFIG_PATH=$($zmq)\lib\pkgconfig" | |
| Write-Host "Cloning vcpkg and installing OpenBLAS/LAPACK" | |
| $vcpkgRoot = Join-Path $pwd "vcpkg" | |
| git clone https://github.com/microsoft/vcpkg.git $vcpkgRoot | |
| & "$vcpkgRoot\bootstrap-vcpkg.bat" | |
| # Ensure x64 triplet | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKG_ROOT=$vcpkgRoot" | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKG_DEFAULT_TRIPLET=x64-windows" | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKGRS_TRIPLET=x64-windows" | |
| # Install OpenBLAS with LAPACK symbols and ensure DLLs are on PATH | |
| & "$vcpkgRoot\vcpkg.exe" install openblas:x64-windows | |
| # Install LAPACK provider (use lapack-reference on Windows) | |
| & "$vcpkgRoot\vcpkg.exe" install lapack-reference:x64-windows | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKGRS_DYNAMIC=1" | |
| Add-Content -Path $env:GITHUB_PATH -Value "$vcpkgRoot\installed\x64-windows\bin" | |
| # Hint BLAS/LAPACK discovery for blas-sys/lapack-sys | |
| Add-Content -Path $env:GITHUB_ENV -Value "BLAS_LIB_DIR=$vcpkgRoot\installed\x64-windows\lib" | |
| Add-Content -Path $env:GITHUB_ENV -Value "BLAS_LIBS=openblas" | |
| Add-Content -Path $env:GITHUB_ENV -Value "LAPACK_LIB_DIR=$vcpkgRoot\installed\x64-windows\lib" | |
| # Prefer lapack if present; keep openblas as fallback | |
| Add-Content -Path $env:GITHUB_ENV -Value "LAPACK_LIBS=lapack;openblas" | |
| Add-Content -Path $env:GITHUB_ENV -Value "OPENBLAS_DIR=$vcpkgRoot\installed\x64-windows" | |
| - name: Format | |
| run: cargo fmt -- --check | |
| - name: Clippy (Unix) | |
| if: runner.os != 'Windows' | |
| run: cargo clippy --all-targets --all-features -- -D warnings | |
| - name: Clippy (Windows) | |
| if: runner.os == 'Windows' | |
| shell: pwsh | |
| run: cargo clippy --all-targets --all-features -- -D warnings | |
| - name: Check (Unix) | |
| if: runner.os != 'Windows' | |
| run: cargo check --all-targets --all-features | |
| - name: Check (Windows) | |
| if: runner.os == 'Windows' | |
| shell: pwsh | |
| run: cargo check --all-targets --all-features | |
| - name: Test (Unix) | |
| if: runner.os != 'Windows' | |
| env: | |
| RUST_TEST_THREADS: 1 | |
| RUST_BACKTRACE: 1 | |
| run: | | |
| set -o pipefail | |
| cargo test --all-targets --all-features 2>&1 -- --test-threads=1 | tee test.log | |
| - name: Test (Windows) | |
| if: runner.os == 'Windows' | |
| shell: pwsh | |
| env: | |
| RUST_TEST_THREADS: 1 | |
| RUST_BACKTRACE: 1 | |
| run: | | |
| $ErrorActionPreference = 'Stop' | |
| cargo test --all-targets --all-features -- --test-threads=1 2>&1 | Tee-Object -FilePath test.log | |
| if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } | |
| - name: Test Summary | |
| if: always() && github.event_name == 'pull_request' | |
| uses: actions/github-script@v7 | |
| with: | |
| github-token: ${{ github.token }} | |
| script: | | |
| const fs = require('fs'); | |
| const log = fs.readFileSync('test.log', 'utf8'); | |
| const matrixName = process.env.MATRIX_NAME || 'matrix'; | |
| let totalPassed = 0; | |
| let totalFailed = 0; | |
| let current = ''; | |
| const details = []; | |
| for (const line of log.split('\n')) { | |
| const run = line.match(/Running .*deps\/(.+?)-[a-f0-9]+\)/); | |
| if (run) current = run[1]; | |
| const m = line.match(/test result: .*?(\d+) passed; (\d+) failed.*finished in ([0-9.]+)s/); | |
| if (m) { | |
| const passed = parseInt(m[1], 10); | |
| const failed = parseInt(m[2], 10); | |
| totalPassed += passed; | |
| totalFailed += failed; | |
| details.push(`- ${matrixName} / ${current || 'crate'}: ${passed} passed, ${failed} failed (${m[3]}s)`); | |
| current = ''; | |
| } | |
| } | |
| let body = '**Test Summary**\n'; | |
| body += details.join('\n'); | |
| body += `\n**Totals**: ${totalPassed} passed, ${totalFailed} failed`; | |
| if (context.payload.pull_request) { | |
| await github.rest.issues.createComment({ | |
| owner: context.repo.owner, | |
| repo: context.repo.repo, | |
| issue_number: context.issue.number, | |
| body | |
| }); | |
| } else { | |
| console.log(body); | |
| } | |
| cross-build: | |
| # Build all release targets so failures are caught before tagging | |
| if: github.event_name == 'push' || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.fork == true) | |
| name: Cross build ${{ matrix.platform.release_for }} | |
| strategy: | |
| fail-fast: false | |
| max-parallel: 12 | |
| matrix: | |
| platform: | |
| - release_for: windows-x86_64 | |
| os: windows-latest-l | |
| target: x86_64-pc-windows-msvc | |
| command: build | |
| - release_for: macos-x86_64 | |
| os: macOS-latest | |
| target: x86_64-apple-darwin | |
| command: build | |
| - release_for: macos-aarch64 | |
| os: macOS-latest | |
| target: aarch64-apple-darwin | |
| command: build | |
| - release_for: linux-x86_64 | |
| os: ubuntu-latest-gpu | |
| target: x86_64-unknown-linux-gnu | |
| command: build | |
| runs-on: ${{ matrix.platform.os }} | |
| steps: | |
| - name: Checkout | |
| uses: actions/checkout@v4 | |
| - name: Install BLAS/LAPACK dependencies (Linux x86_64) | |
| if: runner.os == 'Linux' && matrix.platform.os != 'ubuntu-latest-arm-l' | |
| run: | | |
| sudo apt-get update | |
| sudo apt-get install -y libopenblas-dev liblapack-dev libzmq3-dev pkg-config libssl-dev | |
| - name: Install macOS dependencies (ZMQ) | |
| if: runner.os == 'macOS' | |
| run: | | |
| brew update | |
| brew install zeromq | |
| - name: Install Windows MSVC dependencies (ZMQ, vcpkg + OpenBLAS/LAPACK) | |
| if: runner.os == 'Windows' && matrix.platform.target != 'aarch64-pc-windows-gnu' | |
| shell: pwsh | |
| run: | | |
| choco install -y pkgconfiglite | |
| Write-Host "Fetching prebuilt ZeroMQ for Windows (MSVC)" | |
| curl -L -o libzmq.zip https://github.com/zeromq/libzmq/releases/download/v4.3.5/zeromq-4.3.5.zip | |
| Expand-Archive -Path libzmq.zip -DestinationPath zmq | |
| # Set env vars for ZMQ include/lib | |
| $zmq = Join-Path $pwd "zmq" | |
| Add-Content -Path $env:GITHUB_ENV -Value "INCLUDE=$($zmq)\include;$env:INCLUDE" | |
| Add-Content -Path $env:GITHUB_ENV -Value "LIB=$($zmq)\lib;$env:LIB" | |
| Add-Content -Path $env:GITHUB_ENV -Value "ZMQ_PATH=$($zmq)" | |
| Add-Content -Path $env:GITHUB_ENV -Value "PKG_CONFIG_PATH=$($zmq)\lib\pkgconfig" | |
| Write-Host "Cloning vcpkg and installing OpenBLAS/LAPACK" | |
| $vcpkgRoot = Join-Path $pwd "vcpkg" | |
| git clone https://github.com/microsoft/vcpkg.git $vcpkgRoot | |
| & "$vcpkgRoot\bootstrap-vcpkg.bat" | |
| # Compute vcpkg triplet based on target | |
| if (Test-Path env:MatrixPlatformTarget) { Remove-Item env:MatrixPlatformTarget } | |
| $env:MatrixPlatformTarget = "${{ matrix.platform.target }}" | |
| if ($env:MatrixPlatformTarget -eq "aarch64-pc-windows-msvc") { $triplet = "arm64-windows" } else { $triplet = "x64-windows" } | |
| # Ensure triplet in env | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKG_ROOT=$vcpkgRoot" | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKG_DEFAULT_TRIPLET=$triplet" | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKGRS_TRIPLET=$triplet" | |
| # Install OpenBLAS and LAPACK provider; on arm64-windows use --allow-unsupported for gfortran | |
| & "$vcpkgRoot\vcpkg.exe" install "openblas:$triplet" | |
| if ($triplet -eq "arm64-windows") { | |
| & "$vcpkgRoot\vcpkg.exe" install "lapack-reference:$triplet" --allow-unsupported | |
| } else { | |
| & "$vcpkgRoot\vcpkg.exe" install "lapack-reference:$triplet" | |
| } | |
| Add-Content -Path $env:GITHUB_ENV -Value "VCPKGRS_DYNAMIC=1" | |
| Add-Content -Path $env:GITHUB_PATH -Value "$vcpkgRoot\installed\$triplet\bin" | |
| # Hint BLAS/LAPACK discovery for blas-sys/lapack-sys | |
| Add-Content -Path $env:GITHUB_ENV -Value "BLAS_LIB_DIR=$vcpkgRoot\installed\$triplet\lib" | |
| Add-Content -Path $env:GITHUB_ENV -Value "BLAS_LIBS=openblas" | |
| Add-Content -Path $env:GITHUB_ENV -Value "LAPACK_LIB_DIR=$vcpkgRoot\installed\$triplet\lib" | |
| Add-Content -Path $env:GITHUB_ENV -Value "LAPACK_LIBS=lapack;openblas" | |
| Add-Content -Path $env:GITHUB_ENV -Value "OPENBLAS_DIR=$vcpkgRoot\installed\$triplet" | |
| - name: Cross build (linux-x86_64) | |
| if: matrix.platform.target == 'x86_64-unknown-linux-gnu' | |
| uses: houseabsolute/actions-rust-cross@v0 | |
| with: | |
| command: ${{ matrix.platform.command }} | |
| target: ${{ matrix.platform.target }} | |
| # Build all targets with full BLAS+LAPACK | |
| args: "--locked --release --bin runmat --features blas-lapack" | |
| strip: false | |
| - name: Cross build (other targets) | |
| if: matrix.platform.target != 'x86_64-unknown-linux-gnu' | |
| uses: houseabsolute/actions-rust-cross@v0 | |
| env: | |
| OPENSSL_NO_PKG_CONFIG: '1' | |
| OPENSSL_STATIC: '1' | |
| with: | |
| command: ${{ matrix.platform.command }} | |
| target: ${{ matrix.platform.target }} | |
| # Build all targets with full BLAS+LAPACK | |
| args: "--locked --release --bin runmat --features blas-lapack,vendored-openssl" | |
| strip: false |