name: Build binaries on: push: pull_request: branches: [master] workflow_dispatch: permissions: contents: read env: CARGO_TERM_COLOR: always # Measure before stripping; the packaged copy is stripped below. CARGO_PROFILE_RELEASE_STRIP: none jobs: build: name: Build (${{ matrix.target }}) runs-on: ubuntu-latest timeout-minutes: 60 env: TARGET: ${{ matrix.target }} defaults: run: shell: bash strategy: fail-fast: false # Supported by Gitea 28; bound concurrent cross-build memory use. max-parallel: 2 matrix: target: - x86_64-musl - i686-musl - arm-musleabi - arm-musleabihf - armv7-musleabi - armv7-musleabihf - aarch64-musl - mips-musl - mipsel-musl - mips64-muslabi64 - mips64el-muslabi64 - riscv64gc-musl steps: - name: Checkout uses: builtin:checkout - name: Configure Rust directories # Cross remote's symlink traversal skips hidden directories under /root. run: | echo "CARGO_HOME=$RUNNER_TEMP/cargo" >> "$GITHUB_ENV" echo "RUSTUP_HOME=$RUNNER_TEMP/rustup" >> "$GITHUB_ENV" echo "$RUNNER_TEMP/cargo/bin" >> "$GITHUB_PATH" - name: Install Rust toolchain uses: actions-rust-lang/setup-rust-toolchain@ecabd13d1c56bd1345c230e542e9144811ad706f # v2 with: toolchain: ${{ startsWith(matrix.target, 'mips') && 'nightly' || 'stable' }} cache: false build-warnings: warn - name: Install cross and binary tools run: | sudo apt-get update sudo apt-get install -y --no-install-recommends binutils llvm cargo install --git https://github.com/cross-rs/cross --locked cross echo "RUST_TARGET=${TARGET%-*}-unknown-linux-${TARGET#*-}" >> "$GITHUB_ENV" - name: Build release binary env: # MIPS build-std lacks Rust's bundled CRT objects; use the cross GCC copies. RUSTFLAGS: ${{ startsWith(matrix.target, 'mips') && '-C target-feature=+crt-static -C link-self-contained=no' || '-C target-feature=+crt-static' }} # Copy toolchains and sources instead of translating nested bind mounts. CROSS_REMOTE: "true" # Cross's per-artifact JSON capture hides compiler diagnostics. CROSS_REMOTE_COPY_FULL_TARGET_DIR: ${{ startsWith(matrix.target, 'mips') && 'true' || 'false' }} run: | cross build --release --locked --target "$RUST_TARGET" - name: Verify, package, and summarize binary run: | binary="target/${RUST_TARGET}/release/sqm-autorate-rust" readelf --program-headers "$binary" > /tmp/program-headers.txt readelf --dynamic "$binary" > /tmp/dynamic-section.txt if grep -q INTERP /tmp/program-headers.txt || grep -q NEEDED /tmp/dynamic-section.txt; then echo "Binary is not statically linked" >&2 exit 1 fi mkdir -p dist stripped="dist/sqm-autorate-rust-${TARGET}" artifact="${stripped}.tar.gz" cp "$binary" "$stripped" llvm-strip --strip-all "$stripped" # Tar preserves executable permissions when downloading the artifact. tar -czf "$artifact" -C dist "sqm-autorate-rust-${TARGET}" size() { stat -c %s "$1" | numfmt --to=iec-i --suffix=B --format='%.1f' } { echo '| Target | Unstripped | Stripped | Compressed |' echo '|:--|--:|--:|--:|' printf '| %s | %s | %s | %s |\n' \ "$TARGET" "$(size "$binary")" "$(size "$stripped")" "$(size "$artifact")" } >> "$GITHUB_STEP_SUMMARY" - name: Upload binary # Use the v3 artifact protocol supported by Gitea. uses: actions/upload-artifact@cf430e030ddbb5b0abf93d22962f4752f3646cd9 # v7.0.2 with: name: sqm-autorate-rust-${{ matrix.target }} path: dist/sqm-autorate-rust-${{ matrix.target }}.tar.gz if-no-files-found: error