1name: CI 2on: 3 # Run CI for PRs to `main` and to release branches. 4 # 5 # Note that PRs to `main` will run a subset of tests and PRs to the 6 # `release-*` branches will run full CI. 7 pull_request: 8 branches: 9 - main 10 - 'release-*' 11 12 # Run full CI on the `main` branch once a day to prime the GitHub Actions 13 # caches used by PRs and the merge queue. 14 schedule: 15 - cron: '13 4 * * *' 16 17 # This is the CI that runs for PRs-to-merge. 18 merge_group: 19 20 push: 21 branches: 22 # Right now merge queues can't be used with wildcards in branch protections 23 # so full CI runs both on PRs to release branches as well as merges to 24 # release branches. Note that the merge to a release branch may produce a 25 # tag at the end of CI if successful and the tag will trigger the artifact 26 # uploads as well as publication to crates.io. 27 - 'release-*' 28 29defaults: 30 run: 31 shell: bash 32 33# Cancel any in-flight jobs for the same PR/branch so there's only one active 34# at a time 35concurrency: 36 group: ${{ github.workflow }}-${{ github.ref }} 37 cancel-in-progress: true 38 39jobs: 40 # Check Code style quickly by running `rustfmt` over all code 41 rustfmt: 42 name: Rustfmt 43 runs-on: ubuntu-latest 44 steps: 45 - uses: actions/checkout@v3 46 with: 47 submodules: true 48 - uses: ./.github/actions/install-rust 49 - run: rustup component add rustfmt 50 - run: cargo fmt --all -- --check 51 52 # common logic to cancel the entire run if this job fails 53 - run: gh run cancel ${{ github.run_id }} 54 if: failure() && github.event_name != 'pull_request' 55 env: 56 GH_TOKEN: ${{ github.token }} 57 58 # Check Code style quickly by running `clang-format` over all the C/C++ code 59 clangformat: 60 name: Clang format 61 runs-on: ubuntu-latest 62 steps: 63 - uses: actions/checkout@v3 64 with: 65 submodules: true 66 - run: git ls-files '*.h' '*.c' '*.cpp' | xargs clang-format-15 --dry-run --Werror --verbose 67 68 # common logic to cancel the entire run if this job fails 69 - run: gh run cancel ${{ github.run_id }} 70 if: failure() && github.event_name != 'pull_request' 71 env: 72 GH_TOKEN: ${{ github.token }} 73 74 # Lint dependency graph for security advisories, duplicate versions, and 75 # incompatible licences 76 cargo_deny: 77 name: Cargo deny 78 needs: determine 79 if: needs.determine.outputs.audit 80 runs-on: ubuntu-latest 81 steps: 82 - uses: actions/checkout@v3 83 with: 84 submodules: true 85 - uses: ./.github/actions/install-rust 86 - run: | 87 set -e 88 curl -L https://github.com/EmbarkStudios/cargo-deny/releases/download/0.8.5/cargo-deny-0.8.5-x86_64-unknown-linux-musl.tar.gz | tar xzf - 89 mv cargo-deny-*-x86_64-unknown-linux-musl/cargo-deny cargo-deny 90 echo `pwd` >> $GITHUB_PATH 91 - run: cargo deny check bans licenses 92 93 # common logic to cancel the entire run if this job fails 94 - run: gh run cancel ${{ github.run_id }} 95 if: failure() && github.event_name != 'pull_request' 96 env: 97 GH_TOKEN: ${{ github.token }} 98 99 # Ensure dependencies are vetted. See https://mozilla.github.io/cargo-vet/ 100 cargo_vet: 101 name: Cargo vet 102 needs: determine 103 if: needs.determine.outputs.audit 104 runs-on: ubuntu-latest 105 steps: 106 - uses: actions/checkout@v3 107 with: 108 submodules: true 109 - uses: ./.github/actions/install-rust 110 - uses: ./.github/actions/install-cargo-vet 111 - run: cargo vet --locked 112 113 # common logic to cancel the entire run if this job fails 114 - run: gh run cancel ${{ github.run_id }} 115 if: failure() && github.event_name != 'pull_request' 116 env: 117 GH_TOKEN: ${{ github.token }} 118 119 # This job is a dependency of many of the jobs below. This calculates what's 120 # actually being run for this workflow. For example: 121 # 122 # * Pushes to branches, which is currently both pushes to merge queue branches 123 # as well as release branches, perform full CI. 124 # * PRs to release branches (not `main`) run full CI. 125 # * PRs to `main` will only run a few smoke tests above plus some elements of 126 # the test matrix. The test matrix here is determined dynamically by the 127 # `./ci/build-test-matrix.js` script given the commits that happened and 128 # the files modified. 129 determine: 130 name: Determine CI jobs to run 131 runs-on: ubuntu-latest 132 outputs: 133 run-full: ${{ steps.calculate.outputs.run-full }} 134 test-matrix: ${{ steps.calculate.outputs.test-matrix }} 135 build-matrix: ${{ steps.calculate.outputs.build-matrix }} 136 test-capi: ${{ steps.calculate.outputs.test-capi }} 137 build-fuzz: ${{ steps.calculate.outputs.build-fuzz }} 138 audit: ${{ steps.calculate.outputs.audit }} 139 preview1-adapter: ${{ steps.calculate.outputs.preview1-adapter }} 140 steps: 141 - uses: actions/checkout@v3 142 - id: calculate 143 env: 144 GH_TOKEN: ${{ github.token }} 145 run: | 146 touch commits.log names.log 147 # Note that CI doesn't run on pushes to `main`, only pushes to merge 148 # queue branches and release branches, so this only runs full CI in 149 # those locations. 150 if [ "${{ github.event_name }}" != "pull_request" ]; then 151 run_full=true 152 else 153 pr=${{ github.event.number }} 154 gh pr view $pr --json commits | tee commits.log 155 gh pr diff $pr --name-only | tee names.log 156 if [ "${{ github.base_ref }}" != "main" ]; then 157 run_full=true 158 elif grep -q 'prtest:full' commits.log; then 159 run_full=true 160 fi 161 if grep -q crates.c-api names.log; then 162 echo test-capi=true >> $GITHUB_OUTPUT 163 fi 164 if grep -q fuzz names.log; then 165 echo build-fuzz=true >> $GITHUB_OUTPUT 166 fi 167 if grep -q Cargo.lock names.log; then 168 echo audit=true >> $GITHUB_OUTPUT 169 fi 170 if grep -q supply-chain names.log; then 171 echo audit=true >> $GITHUB_OUTPUT 172 fi 173 if grep -q component-adapter names.log; then 174 echo preview1-adapter=true >> $GITHUB_OUTPUT 175 fi 176 fi 177 matrix="$(node ./ci/build-test-matrix.js ./commits.log ./names.log $run_full)" 178 echo "test-matrix={\"include\":$(echo $matrix)}" >> $GITHUB_OUTPUT 179 echo "$matrix" 180 181 matrix="$(node ./ci/build-build-matrix.js)" 182 echo "build-matrix={\"include\":$(echo $matrix)}" >> $GITHUB_OUTPUT 183 184 if [ "$run_full" = "true" ]; then 185 echo run-full=true >> $GITHUB_OUTPUT 186 echo test-capi=true >> $GITHUB_OUTPUT 187 echo build-fuzz=true >> $GITHUB_OUTPUT 188 echo audit=true >> $GITHUB_OUTPUT 189 echo preview1-adapter=true >> $GITHUB_OUTPUT 190 fi 191 192 # Build all documentation of Wasmtime, including the C API documentation, 193 # mdbook documentation, etc. This produces a `gh-pages` artifact which is what 194 # gets uploaded to the `gh-pages` branch later on. 195 doc: 196 needs: determine 197 if: needs.determine.outputs.run-full 198 name: Doc build 199 runs-on: ubuntu-latest 200 env: 201 CARGO_MDBOOK_VERSION: 0.4.21 202 RUSTDOCFLAGS: -Dbroken_intra_doc_links --cfg nightlydoc 203 OPENVINO_SKIP_LINKING: 1 204 steps: 205 - uses: actions/checkout@v3 206 with: 207 submodules: true 208 - uses: ./.github/actions/install-rust 209 with: 210 toolchain: nightly-2023-10-10 211 212 # Build C API documentation 213 - run: curl -L https://sourceforge.net/projects/doxygen/files/rel-1.9.3/doxygen-1.9.3.linux.bin.tar.gz/download | tar xzf - 214 - run: echo "`pwd`/doxygen-1.9.3/bin" >> $GITHUB_PATH 215 - run: cd crates/c-api && doxygen doxygen.conf 216 217 # install mdbook, build the docs, and test the docs 218 - uses: actions/cache@v3 219 with: 220 path: ${{ runner.tool_cache }}/mdbook 221 key: cargo-mdbook-bin-${{ env.CARGO_MDBOOK_VERSION }} 222 - run: | 223 echo "${{ runner.tool_cache }}/mdbook/bin" >> $GITHUB_PATH 224 cargo install --root ${{ runner.tool_cache }}/mdbook --version ${{ env.CARGO_MDBOOK_VERSION }} mdbook 225 - run: (cd docs && mdbook build) 226 - run: cargo build -p wasmtime-wasi --features wasmtime/wat,wasmtime/cranelift 227 - run: (cd docs/rust_wasi_markdown_parser && cargo build) 228 - run: (cd docs && mdbook test -L ../target/debug/deps) 229 230 # Build Rust API documentation. 231 # We pass in the `component-model` feature 232 # to match the docs.rs metadata in 233 # crates/wasmtime/Cargo.toml. 234 - run: | 235 cargo doc --no-deps --workspace \ 236 --exclude wasmtime-cli \ 237 --exclude test-programs \ 238 --exclude wasi-http-tests \ 239 --exclude cranelift-codegen-meta \ 240 --features component-model 241 - run: cargo doc --package cranelift-codegen-meta --document-private-items 242 243 # Assemble the documentation, and always upload it as an artifact for 244 # inspection on PRs and such. 245 - run: | 246 mv docs/book gh-pages 247 mv crates/c-api/html gh-pages/c-api 248 mv target/doc gh-pages/api 249 tar czf gh-pages.tar.gz gh-pages 250 - uses: actions/upload-artifact@v3 251 with: 252 name: gh-pages 253 path: gh-pages.tar.gz 254 255 # common logic to cancel the entire run if this job fails 256 - run: gh run cancel ${{ github.run_id }} 257 if: failure() && github.event_name != 'pull_request' 258 env: 259 GH_TOKEN: ${{ github.token }} 260 261 # Checks of various feature combinations and whether things 262 # compile. The goal here isn't to run tests, mostly just serve as a 263 # double-check that Rust code compiles and is likely to work everywhere else. 264 checks: 265 needs: determine 266 if: needs.determine.outputs.run-full 267 name: Check 268 runs-on: ubuntu-latest 269 env: 270 CARGO_NDK_VERSION: 2.12.2 271 steps: 272 - uses: actions/checkout@v3 273 with: 274 submodules: true 275 - uses: ./.github/actions/install-rust 276 277 # Check some feature combinations of the `wasmtime` crate 278 - run: cargo check -p wasmtime --no-default-features 279 - run: cargo check -p wasmtime --no-default-features --features wat 280 - run: cargo check -p wasmtime --no-default-features --features profiling 281 - run: cargo check -p wasmtime --no-default-features --features cache 282 - run: cargo check -p wasmtime --no-default-features --features async 283 - run: cargo check -p wasmtime --no-default-features --features pooling-allocator 284 - run: cargo check -p wasmtime --no-default-features --features cranelift 285 - run: cargo check -p wasmtime --no-default-features --features component-model 286 - run: cargo check -p wasmtime --no-default-features --features cranelift,wat,async,cache 287 - run: cargo check -p wasmtime --no-default-features --features winch 288 - run: cargo check -p wasmtime --no-default-features --features wmemcheck 289 - run: cargo check -p wasmtime --no-default-features --features demangle 290 - run: cargo check -p wasmtime --no-default-features --features addr2line 291 - run: cargo check --features component-model 292 - run: cargo check -p wasmtime --features incremental-cache 293 294 # Feature combinations of the `wasmtime-cli` 295 - run: cargo check -p wasmtime-cli --no-default-features 296 297 # Check that benchmarks of the cranelift project build 298 - run: cargo check --benches -p cranelift-codegen 299 300 # Check that the bench-api compiles 301 - run: cargo check -p wasmtime-bench-api 302 303 # Check some feature combinations of the `wasmtime-c-api` crate 304 - run: cargo check -p wasmtime-c-api --no-default-features 305 - run: cargo check -p wasmtime-c-api --no-default-features --features wat 306 - run: cargo check -p wasmtime-c-api --no-default-features --features wasi 307 308 # Check a few builds of the cranelift backend 309 # - only x86 backend support, 310 # - only arm64 backend support, 311 # - no debug_assertions. 312 - run: cargo check --manifest-path=./cranelift/Cargo.toml --bin clif-util --no-default-features --features=cranelift-codegen/arm64 313 - run: cargo check --manifest-path=./cranelift/Cargo.toml --bin clif-util --no-default-features --features=cranelift-codegen/x86 314 - run: cargo check --manifest-path=./cranelift/Cargo.toml --bin clif-util 315 env: 316 CARGO_PROFILE_DEV_DEBUG_ASSERTIONS: false 317 318 # Check whether `wasmtime` cross-compiles to x86_64-unknown-freebsd 319 # TODO: We aren't building with default features since the `ittapi` crate fails to compile on freebsd. 320 - run: rustup target add x86_64-unknown-freebsd 321 - run: cargo check -p wasmtime --no-default-features --features cranelift,wat,async,cache --target x86_64-unknown-freebsd 322 323 # Check whether `wasmtime` cross-compiles to aarch64-linux-android 324 - run: rustup target add aarch64-linux-android 325 - name: Setup Android SDK 326 uses: android-actions/setup-android@v2 327 - uses: actions/cache@v3 328 with: 329 path: ${{ runner.tool_cache }}/cargo-ndk 330 key: cargo-ndk-bin-${{ env.CARGO_NDK_VERSION }} 331 - run: echo "${{ runner.tool_cache }}/cargo-ndk/bin" >> $GITHUB_PATH 332 - run: cargo install --root ${{ runner.tool_cache }}/cargo-ndk --version ${{ env.CARGO_NDK_VERSION }} cargo-ndk 333 - run: cargo ndk -t arm64-v8a check -p wasmtime 334 335 # Run clippy configuration 336 - run: rustup component add clippy 337 - run: cargo clippy --workspace 338 339 # common logic to cancel the entire run if this job fails 340 - run: gh run cancel ${{ github.run_id }} 341 if: failure() && github.event_name != 'pull_request' 342 env: 343 GH_TOKEN: ${{ github.token }} 344 345 # Check whether `wasmtime` cross-compiles to aarch64-pc-windows-msvc 346 # We don't build nor test it because it lacks trap handling. 347 # Tracking issue: https://github.com/bytecodealliance/wasmtime/issues/4992 348 checks_winarm64: 349 needs: determine 350 if: needs.determine.outputs.run-full 351 name: Check Windows ARM64 352 runs-on: windows-latest 353 steps: 354 - uses: actions/checkout@v3 355 with: 356 submodules: true 357 - uses: ./.github/actions/install-rust 358 - run: rustup target add aarch64-pc-windows-msvc 359 - run: cargo check -p wasmtime --target aarch64-pc-windows-msvc 360 361 # common logic to cancel the entire run if this job fails 362 - run: gh run cancel ${{ github.run_id }} 363 if: failure() && github.event_name != 'pull_request' 364 env: 365 GH_TOKEN: ${{ github.token }} 366 367 # Verify all fuzz targets compile successfully 368 fuzz_targets: 369 needs: determine 370 if: needs.determine.outputs.build-fuzz 371 name: Fuzz Targets 372 runs-on: ubuntu-latest 373 steps: 374 - uses: actions/checkout@v3 375 with: 376 submodules: true 377 # Note that building with fuzzers requires nightly since it uses unstable 378 # flags to rustc. 379 - uses: ./.github/actions/install-rust 380 with: 381 toolchain: nightly-2023-10-10 382 - run: cargo install cargo-fuzz --vers "^0.11" 383 # Install the OCaml packages necessary for fuzz targets that use the 384 # `wasm-spec-interpreter`. 385 - run: sudo apt-get update && sudo apt install -y ocaml-nox ocamlbuild ocaml-findlib libzarith-ocaml-dev 386 - run: cargo fetch 387 working-directory: ./fuzz 388 - run: cargo fuzz build --dev -s none 389 # Check that the ISLE fuzz targets build too. 390 - run: cargo fuzz build --dev -s none --fuzz-dir ./cranelift/isle/fuzz 391 392 # common logic to cancel the entire run if this job fails 393 - run: gh run cancel ${{ github.run_id }} 394 if: failure() && github.event_name != 'pull_request' 395 env: 396 GH_TOKEN: ${{ github.token }} 397 398 # Perform all tests (debug mode) for `wasmtime`. 399 # 400 # Note that the full matrix for what may run here is defined within 401 # `./ci/build-test-matrix.js` and the execution of the `determine` step will 402 # calculate whether the tests are actually run as part of PRs and such. 403 test: 404 needs: determine 405 name: ${{ matrix.name }} 406 runs-on: ${{ matrix.os }} 407 env: 408 QEMU_BUILD_VERSION: 8.1.1 409 strategy: 410 fail-fast: ${{ github.event_name != 'pull_request' }} 411 matrix: ${{ fromJson(needs.determine.outputs.test-matrix) }} 412 steps: 413 - uses: actions/checkout@v3 414 with: 415 submodules: true 416 - uses: ./.github/actions/install-rust 417 with: 418 toolchain: ${{ matrix.rust }} 419 420 # Install targets in order to build various tests throughout the repo 421 - run: rustup target add wasm32-wasi wasm32-unknown-unknown ${{ matrix.target }} 422 - run: echo CARGO_BUILD_TARGET=${{ matrix.target }} >> $GITHUB_ENV 423 if: matrix.target != '' 424 425 # Fix an ICE for now in gcc when compiling zstd with debuginfo (??) 426 - run: echo CFLAGS=-g0 >> $GITHUB_ENV 427 if: matrix.target == 'x86_64-pc-windows-gnu' 428 429 - run: cargo fetch --locked 430 431 - uses: actions/cache@v3 432 with: 433 path: ${{ runner.tool_cache }}/qemu 434 key: qemu-${{ matrix.target }}-${{ env.QEMU_BUILD_VERSION }}-patchcpuinfo 435 if: matrix.target != '' && matrix.os == 'ubuntu-latest' 436 - name: Install cross-compilation tools 437 run: | 438 set -ex 439 sudo apt-get update 440 sudo apt-get install -y ${{ matrix.gcc_package }} ninja-build 441 442 # Configure Cargo for cross compilation and tell it how it can run 443 # cross executables 444 upcase=$(echo ${{ matrix.target }} | awk '{ print toupper($0) }' | sed 's/-/_/g') 445 echo CARGO_TARGET_${upcase}_RUNNER=${{ runner.tool_cache }}/qemu/bin/${{ matrix.qemu }} >> $GITHUB_ENV 446 echo CARGO_TARGET_${upcase}_LINKER=${{ matrix.gcc }} >> $GITHUB_ENV 447 448 # QEMU emulation is not always the speediest, so total testing time 449 # goes down if we build the libs in release mode when running tests. 450 echo CARGO_PROFILE_DEV_OPT_LEVEL=2 >> $GITHUB_ENV 451 452 # See comments in the source for why we enable this during QEMU 453 # emulation. 454 echo WASMTIME_TEST_NO_HOG_MEMORY=1 >> $GITHUB_ENV 455 456 # See if qemu is already in the cache 457 if [ -f ${{ runner.tool_cache }}/qemu/built ]; then 458 exit 0 459 fi 460 461 # Download and build qemu from source since the most recent release is 462 # way faster at arm emulation than the current version github actions' 463 # ubuntu image uses. Disable as much as we can to get it to build 464 # quickly. 465 curl https://download.qemu.org/qemu-$QEMU_BUILD_VERSION.tar.xz | tar xJf - 466 cd qemu-$QEMU_BUILD_VERSION 467 ./configure --target-list=${{ matrix.qemu_target }} --prefix=${{ runner.tool_cache}}/qemu --disable-tools --disable-slirp --disable-fdt --disable-capstone --disable-docs 468 ninja -C build install 469 touch ${{ runner.tool_cache }}/qemu/built 470 if: matrix.gcc != '' 471 472 # Build and test the C API with example C programs along with the example 473 # Rust programs. Note that this only executes if the `determine` step told 474 # us to test the capi which is off-by-default for PRs. 475 - run: cmake -Sexamples -Bexamples/build -DBUILD_SHARED_LIBS=OFF 476 if: matrix.target == '' && needs.determine.outputs.test-capi 477 - run: cmake --build examples/build --config Debug 478 if: matrix.target == '' && needs.determine.outputs.test-capi 479 - run: cmake -E env CTEST_OUTPUT_ON_FAILURE=1 cmake --build examples/build --config Debug --target RUN_TESTS 480 env: 481 RUST_BACKTRACE: 1 482 if: matrix.target == '' && matrix.os == 'windows-latest' && needs.determine.outputs.test-capi 483 - run: cmake -E env CTEST_OUTPUT_ON_FAILURE=1 cmake --build examples/build --config Debug --target test 484 env: 485 RUST_BACKTRACE: 1 486 if: matrix.target == '' && matrix.os != 'windows-latest' && needs.determine.outputs.test-capi 487 488 # Ensure wit definitions are in sync: both wasmtime-wasi and wasmtime-wasi-http need their own 489 # copy of the wit definitions so publishing works, but we need to ensure they are identical copies. 490 - name: Check that the wasi and wasi-http wit directories agree 491 run: | 492 diff -ru crates/wasi/wit crates/wasi-http/wit 493 494 # Record some CPU details; this is helpful information if tests fail due 495 # to CPU-specific features. 496 - name: CPU information 497 run: lscpu 498 if: matrix.os == 'ubuntu-latest' 499 - name: CPU information 500 run: sysctl hw 501 if: matrix.os == 'macos-latest' 502 - name: CPU information 503 run: wmic cpu list /format:list 504 shell: pwsh 505 if: matrix.os == 'windows-latest' 506 507 # Build and test all features 508 - run: ./ci/run-tests.sh --locked 509 env: 510 RUST_BACKTRACE: 1 511 512 # Test debug (DWARF) related functionality. 513 - run: | 514 sudo apt-get update && sudo apt-get install -y gdb lldb llvm 515 cargo test test_debug_dwarf -- --ignored --test-threads 1 516 if: matrix.os == 'ubuntu-latest' && matrix.target == ''&& needs.determine.outputs.run-full 517 env: 518 RUST_BACKTRACE: 1 519 520 # NB: the test job here is explicitly lacking in cancellation of this run if 521 # something goes wrong. These take the longest anyway and otherwise if 522 # Windows fails GitHub Actions will confusingly mark the failed Windows job 523 # as cancelled instead of failed. 524 525 # Build and test the wasi-nn module. 526 test_wasi_nn: 527 needs: determine 528 if: needs.determine.outputs.run-full 529 name: Test wasi-nn module 530 runs-on: ubuntu-latest 531 steps: 532 - uses: actions/checkout@v3 533 with: 534 submodules: true 535 - uses: ./.github/actions/install-rust 536 - run: rustup target add wasm32-wasi 537 - uses: abrown/install-openvino-action@v7 538 with: 539 version: 2022.3.0 540 apt: true 541 - run: ./ci/run-wasi-nn-example.sh 542 env: 543 RUST_BACKTRACE: 1 544 545 # common logic to cancel the entire run if this job fails 546 - run: gh run cancel ${{ github.run_id }} 547 if: failure() && github.event_name != 'pull_request' 548 env: 549 GH_TOKEN: ${{ github.token }} 550 551 build-preview1-component-adapter: 552 name: Build wasi-preview1-component-adapter 553 needs: determine 554 if: needs.determine.outputs.preview1-adapter 555 runs-on: ubuntu-latest 556 permissions: 557 deployments: write 558 contents: write 559 steps: 560 - uses: actions/checkout@v3 561 with: 562 submodules: true 563 - run: rustup update stable && rustup default stable 564 - run: rustup target add wasm32-wasi wasm32-unknown-unknown 565 566 - name: Install wasm-tools 567 run: | 568 curl -L https://github.com/bytecodealliance/wasm-tools/releases/download/wasm-tools-1.0.27/wasm-tools-1.0.27-x86_64-linux.tar.gz | tar xfz - 569 echo `pwd`/wasm-tools-1.0.27-x86_64-linux >> $GITHUB_PATH 570 571 - run: ./ci/build-wasi-preview1-component-adapter.sh 572 env: 573 VERSION: ${{ github.sha }} 574 575 - uses: actions/upload-artifact@v3 576 with: 577 name: bins-wasi-preview1-component-adapter 578 path: target/wasm32-unknown-unknown/release/wasi_snapshot_preview1.*.wasm 579 580 581 # common logic to cancel the entire run if this job fails 582 - run: gh run cancel ${{ github.run_id }} 583 if: failure() && github.event_name != 'pull_request' 584 env: 585 GH_TOKEN: ${{ github.token }} 586 587 588 bench: 589 needs: determine 590 if: needs.determine.outputs.run-full 591 name: Run benchmarks 592 runs-on: ubuntu-latest 593 steps: 594 - uses: actions/checkout@v3 595 with: 596 submodules: true 597 - uses: ./.github/actions/install-rust 598 - run: rustup target add wasm32-wasi 599 - run: cargo test --benches --release 600 601 # common logic to cancel the entire run if this job fails 602 - run: gh run cancel ${{ github.run_id }} 603 if: failure() && github.event_name != 'pull_request' 604 env: 605 GH_TOKEN: ${{ github.token }} 606 607 # Verify that cranelift's code generation is deterministic 608 meta_deterministic_check: 609 needs: determine 610 if: needs.determine.outputs.run-full 611 name: Meta deterministic check 612 runs-on: ubuntu-latest 613 steps: 614 - uses: actions/checkout@v3 615 with: 616 submodules: true 617 - uses: ./.github/actions/install-rust 618 - run: cd cranelift/codegen && cargo build --features all-arch 619 - run: ci/ensure_deterministic_build.sh 620 621 # common logic to cancel the entire run if this job fails 622 - run: gh run cancel ${{ github.run_id }} 623 if: failure() && github.event_name != 'pull_request' 624 env: 625 GH_TOKEN: ${{ github.token }} 626 627 verify-publish: 628 needs: determine 629 if: github.repository == 'bytecodealliance/wasmtime' && needs.determine.outputs.run-full 630 runs-on: ubuntu-latest 631 steps: 632 - uses: actions/checkout@v3 633 with: 634 submodules: true 635 - run: rustup update stable && rustup default stable 636 - run: | 637 cd ${{ runner.tool_cache }} 638 curl -L https://github.com/mozilla/sccache/releases/download/0.2.13/sccache-0.2.13-x86_64-unknown-linux-musl.tar.gz | tar xzf - 639 echo "`pwd`/sccache-0.2.13-x86_64-unknown-linux-musl" >> $GITHUB_PATH 640 echo RUSTC_WRAPPER=sccache >> $GITHUB_ENV 641 - run: rustc scripts/publish.rs 642 # Make sure the tree is publish-able as-is 643 - run: ./publish verify 644 # Make sure we can bump version numbers for the next release 645 - run: ./publish bump 646 647 # common logic to cancel the entire run if this job fails 648 - run: gh run cancel ${{ github.run_id }} 649 if: failure() && github.event_name != 'pull_request' 650 env: 651 GH_TOKEN: ${{ github.token }} 652 653 # Run a subset of tests under MIRI on CI to help check the `unsafe` code in 654 # Wasmtime to make sure it's at least not obviously incorrect for basic usage. 655 # Note that this doesn't run the full test suite since MIRI can't actually run 656 # WebAssembly itself at this time (aka it doesn't support a JIT). There are a 657 # number of annotations throughout the code which gates some tests on MIRI not 658 # being run. 659 # 660 # Note that `cargo nextest` is used here additionally to get parallel test 661 # execution by default to help cut down on the time in CI. 662 miri: 663 needs: determine 664 if: needs.determine.outputs.run-full && github.repository == 'bytecodealliance/wasmtime' 665 name: Miri 666 runs-on: ubuntu-latest 667 env: 668 CARGO_NEXTEST_VERSION: 0.9.51 669 steps: 670 - uses: actions/checkout@v3 671 with: 672 submodules: true 673 - uses: ./.github/actions/install-rust 674 with: 675 toolchain: nightly-2023-10-10 676 - run: rustup component add rust-src miri 677 - uses: actions/cache@v3 678 with: 679 path: ${{ runner.tool_cache }}/cargo-nextest 680 key: cargo-nextest-bin-${{ env.CARGO_NEXTEST_VERSION }} 681 - run: echo "${{ runner.tool_cache }}/cargo-nextest/bin" >> $GITHUB_PATH 682 - run: cargo install --root ${{ runner.tool_cache }}/cargo-nextest --version ${{ env.CARGO_NEXTEST_VERSION }} cargo-nextest 683 - run: | 684 cargo miri nextest run -j4 --no-fail-fast \ 685 -p wasmtime \ 686 -p wasmtime-cli \ 687 -p wasmtime-runtime \ 688 -p wasmtime-environ 689 env: 690 MIRIFLAGS: -Zmiri-strict-provenance 691 692 # common logic to cancel the entire run if this job fails 693 - run: gh run cancel ${{ github.run_id }} 694 if: failure() && github.event_name != 'pull_request' 695 env: 696 GH_TOKEN: ${{ github.token }} 697 698 # Perform release builds of `wasmtime` and `libwasmtime.so`. Builds a variety 699 # of platforms and architectures and then uploads the release artifacts to 700 # this workflow run's list of artifacts. 701 # 702 # Note that the full matrix is computed by `ci/build-build-matrix.js`. 703 build: 704 needs: determine 705 if: needs.determine.outputs.run-full 706 name: Release build for ${{ matrix.build }} 707 runs-on: ${{ matrix.os }} 708 strategy: 709 fail-fast: ${{ github.event_name != 'pull_request' }} 710 matrix: ${{ fromJson(needs.determine.outputs.build-matrix) }} 711 steps: 712 - uses: actions/checkout@v3 713 with: 714 submodules: true 715 716 - uses: ./.github/actions/install-rust 717 with: 718 toolchain: ${{ matrix.rust }} 719 - run: | 720 rustup component add rust-src 721 rustup target add ${{ matrix.target }} 722 723 # On one builder produce the source tarball since there's no need to produce 724 # it everywhere 725 - run: ./ci/build-src-tarball.sh 726 if: matrix.build == 'x86_64-linux' 727 - uses: ./.github/actions/binary-compatible-builds 728 with: 729 name: ${{ matrix.build }} 730 731 - run: $CENTOS ./ci/build-release-artifacts.sh "${{ matrix.build }}" "${{ matrix.target }}" 732 733 # Assemble release artifacts appropriate for this platform, then upload them 734 # unconditionally to this workflow's files so we have a copy of them. 735 - run: ./ci/build-tarballs.sh "${{ matrix.build }}" "${{ matrix.target }}" 736 737 - uses: actions/upload-artifact@v3 738 with: 739 name: bins-${{ matrix.build }} 740 path: dist 741 742 # common logic to cancel the entire run if this job fails 743 - run: gh run cancel ${{ github.run_id }} 744 if: failure() && github.event_name != 'pull_request' 745 env: 746 GH_TOKEN: ${{ github.token }} 747 748 # This is a "join node" which depends on all prior workflows. The merge queue, 749 # for example, gates on this to ensure that everything has executed 750 # successfully. 751 # 752 # Note that this is required currently for odd reasons with github. Notably 753 # the set of checks to enter the merge queue and leave the merge queue must 754 # be the same which means that the "build" step for example shows as skipped 755 # for PRs but expands to many different steps for merge-queue-based PRs. That 756 # means that for that step there's no single name to gate on, so it's required 757 # to have a "join" node here which joins everything. 758 # 759 # Note that this currently always runs to always report a status, even on 760 # cancellation and even if dependency steps fail. Each dependency tries to 761 # cancel the whole run if it fails, so if a test matrix entry fails, for 762 # example, it cancels the build matrix entries too. This step then tries to 763 # fail on cancellation to ensure that the dependency failures are propagated 764 # correctly. 765 ci-status: 766 name: Record the result of testing and building steps 767 runs-on: ubuntu-latest 768 needs: 769 - test 770 - build 771 - rustfmt 772 - cargo_deny 773 - cargo_vet 774 - doc 775 - checks 776 - checks_winarm64 777 - fuzz_targets 778 - test_wasi_nn 779 - bench 780 - meta_deterministic_check 781 - verify-publish 782 - determine 783 - miri 784 - build-preview1-component-adapter 785 if: always() 786 steps: 787 - name: Dump needs context 788 env: 789 CONTEXT: ${{ toJson(needs) }} 790 run: | 791 echo -e "\033[33;1;4mDump context\033[0m" 792 echo -e "$CONTEXT\n" 793 - name: Successful test and build 794 if: ${{ !(contains(needs.*.result, 'failure')) }} 795 run: exit 0 796 - name: Failing test and build 797 if: ${{ contains(needs.*.result, 'failure') }} 798 run: exit 1 799 - name: Report failure on cancellation 800 if: ${{ contains(needs.*.result, 'cancelled') || cancelled() }} 801 run: exit 1 802 803 # The purpose of this jobs is to watch for changes on the `release-*` 804 # branches of this repository and look for the term 805 # "automatically-tag-and-release-this-commit" within merged PRs/commits. Once 806 # that term is found the current version of `Cargo.toml`, the `wasmtime-cli` 807 # Cargo.toml, is created as a tag and the tag is pushed to the repo. 808 # Currently the tag is created through the GitHub API with an access token to 809 # ensure that CI is further triggered for the tag itself which performs the 810 # full release process. 811 # 812 # Note that this depends on the `ci-status` step above which is the "join" 813 # point of this workflow for when everything succeeds. the purpose of that is 814 # so that the tag is only created after the aftifacts have been uploaded for 815 # this workflow as the `publish-artifacts.yml` workflow will download these 816 # artifacts and then publish them to the tag. 817 push-tag: 818 runs-on: ubuntu-latest 819 needs: ci-status 820 if: | 821 always() 822 && needs.ci-status.result == 'success' 823 && github.event_name == 'push' 824 && startsWith(github.ref, 'refs/heads/release-') 825 && github.repository == 'bytecodealliance/wasmtime' 826 steps: 827 - uses: actions/checkout@v3 828 with: 829 submodules: true 830 fetch-depth: 0 831 - name: Test if tag is needed 832 run: | 833 git log ${{ github.event.before }}...${{ github.event.after }} | tee main.log 834 version=$(grep '^version =' Cargo.toml | head -n 1 | sed 's/.*"\(.*\)"/\1/') 835 echo "version: $version" 836 echo "version=$version" >> $GITHUB_OUTPUT 837 echo "sha=$(git rev-parse HEAD)" >> $GITHUB_OUTPUT 838 if grep -q "automatically-tag-and-release-this-commit" main.log; then 839 echo push-tag 840 echo "push_tag=yes" >> $GITHUB_OUTPUT 841 else 842 echo no-push-tag 843 echo "push_tag=no" >> $GITHUB_OUTPUT 844 fi 845 id: tag 846 - name: Push the tag 847 run: | 848 git_refs_url=$(jq .repository.git_refs_url $GITHUB_EVENT_PATH | tr -d '"' | sed 's/{\/sha}//g') 849 curl -iX POST $git_refs_url \ 850 -H "Authorization: token ${{ secrets.PERSONAL_ACCESS_TOKEN }}" \ 851 -d @- << EOF 852 { 853 "ref": "refs/tags/v${{ steps.tag.outputs.version }}", 854 "sha": "${{ steps.tag.outputs.sha }}" 855 } 856 EOF 857 if: steps.tag.outputs.push_tag == 'yes' 858