diff --git a/.github/actions/setup-zkc-measurement/action.yml b/.github/actions/setup-zkc-measurement/action.yml index 85d68b7928..b078fa8c1f 100644 --- a/.github/actions/setup-zkc-measurement/action.yml +++ b/.github/actions/setup-zkc-measurement/action.yml @@ -52,8 +52,23 @@ runs: echo "RUN=${RUNNER_TEMP}/wzm" >> "$GITHUB_ENV" mkdir -p "${RUNNER_TEMP}/wzm" - # Only Go is needed here: building zkc and, in the report job, running the renderer. The guest ELF - # needs Zig and the riscv toolchain, which is why only `prepare` uses setup-arithmetization-riscv. + # GNU time is NOT on the runner image: setup-arithmetization-riscv apt-installs it (its line 53), + # and these jobs deliberately skip that heavy action. Every measurement wraps its command in + # `/usr/bin/time -v` to capture peak RSS, so without this the step dies with exit 127. + - name: Install GNU time + shell: bash + run: | + set -euo pipefail + if [ -x /usr/bin/time ]; then + echo "/usr/bin/time already present" + else + sudo apt-get update && sudo apt-get install -y time + fi + /usr/bin/time -v true 2>&1 | tail -1 + + # Only Go is needed beyond that: building zkc and, in the report job, running the renderer. The + # guest ELF needs Zig and the riscv toolchain, which is why only `prepare` uses + # setup-arithmetization-riscv. - name: Install Go uses: actions/setup-go@924ae3a1cded613372ab5595356fb5720e22ba16 # v6.5.0 with: diff --git a/.github/workflows/arithmetization-weekly-zkc-metrics.yml b/.github/workflows/arithmetization-weekly-zkc-metrics.yml index 5d07ffefe4..7d46301614 100644 --- a/.github/workflows/arithmetization-weekly-zkc-metrics.yml +++ b/.github/workflows/arithmetization-weekly-zkc-metrics.yml @@ -136,7 +136,10 @@ jobs: id: guest if: ${{ github.event_name != 'workflow_dispatch' || inputs.run-heavy }} run: | - set -uo pipefail + # GitHub's default shell is `bash -e`; `set -uo pipefail` does NOT clear errexit, so + # without `set +e` the rc/wall_s/timedout capture below never runs on a failure or + # timeout — which is precisely the outcome this workflow exists to record. + set +e -uo pipefail d="$RUN/guest"; mkdir -p "$d" t0=$(date +%s) # Both halves timed as one task. No `make linker-script`: linker_script.ld is tracked @@ -244,7 +247,10 @@ jobs: # wall_s were written and leave the table unable to name the failure. - name: zkc compile --stats run: | - set -uo pipefail + # GitHub's default shell is `bash -e`; `set -uo pipefail` does NOT clear errexit, so + # without `set +e` the rc/wall_s/timedout capture below never runs on a failure or + # timeout — which is precisely the outcome this workflow exists to record. + set +e -uo pipefail d="$RUN/compile"; mkdir -p "$d" t0=$(date +%s) # --order name (not zkc's default --order total) keeps the table diffable week to week. @@ -300,7 +306,10 @@ jobs: # lost in exactly the case worth recording. timeout exits 124. - name: zkc trace --stats run: | - set -uo pipefail + # GitHub's default shell is `bash -e`; `set -uo pipefail` does NOT clear errexit, so + # without `set +e` the rc/wall_s/timedout capture below never runs on a failure or + # timeout — which is precisely the outcome this workflow exists to record. + set +e -uo pipefail # Clamped below the job's timeout-minutes so the cap fires here and the measurement is # recorded, instead of the job being killed with nothing to show. [ -s "$RUN/guest.json" ] || { echo "::warning::no guest JSON; recording nothing"; exit 0; } @@ -363,7 +372,10 @@ jobs: - name: zkc trace --stats --check run: | - set -uo pipefail + # GitHub's default shell is `bash -e`; `set -uo pipefail` does NOT clear errexit, so + # without `set +e` the rc/wall_s/timedout capture below never runs on a failure or + # timeout — which is precisely the outcome this workflow exists to record. + set +e -uo pipefail [ -s "$RUN/guest.json" ] || { echo "::warning::no guest JSON; recording nothing"; exit 0; } cap=${{ inputs.check-timeout-min || 90 }} if [ "$cap" -gt 110 ]; then cap=110; fi @@ -404,10 +416,25 @@ jobs: runs-on: gha-lfdt-lineth-ss-ubuntu-24-amd64-xxl timeout-minutes: 20 steps: + # Generated before the checkout, not after it: actions/checkout persists whatever token it used + # into .git/config as an http..extraheader, and that header takes precedence over + # credentials embedded in a remote URL. Handing the App token to checkout is therefore the only + # way to make the later push authenticate as the App, and mirrors component-changelog-commit.yml. + - name: Generate release bot App token + if: ${{ github.event_name != 'workflow_dispatch' || inputs.commit-results }} + id: app-token + uses: actions/create-github-app-token@bcd2ba49218906704ab6c1aa796996da409d3eb1 # v3.2.0 + with: + app-id: ${{ secrets.RELEASE_BOT_APP_ID }} + private-key: ${{ secrets.RELEASE_BOT_PRIVATE_KEY }} + # fetch-depth: 0 because the commit step rebases onto origin/; a shallow clone cannot. - name: Checkout tooling uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 # v7.0.0 with: + # Falls back to the default token on a dispatch that is not committing results, where the + # step above is skipped and its output is the empty string. + token: ${{ steps.app-token.outputs.token || github.token }} submodules: false fetch-depth: 0 @@ -433,7 +460,10 @@ jobs: name: zkc-metrics-meta path: ${{ env.RUN }} + # Only attempted when the heavy path ran: prepare skips the guest build otherwise, and a + # download for a non-existent artifact leaves a red annotation on an otherwise green run. - name: Download guest build measurement + if: ${{ github.event_name == 'schedule' || inputs.run-heavy }} continue-on-error: true uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1 with: @@ -497,16 +527,8 @@ jobs: ${{ env.RUN }}/meta.env retention-days: 7 - # App token so the push is not blocked by branch protection, mirroring - # component-changelog-commit.yml. [skip ci] keeps it from re-triggering. - - name: Generate release bot App token - if: ${{ github.event_name != 'workflow_dispatch' || inputs.commit-results }} - id: app-token - uses: actions/create-github-app-token@bcd2ba49218906704ab6c1aa796996da409d3eb1 # v3.2.0 - with: - app-id: ${{ secrets.RELEASE_BOT_APP_ID }} - private-key: ${{ secrets.RELEASE_BOT_PRIVATE_KEY }} - + # Pushes as the App so branch protection does not block it; the credentials come from the + # checkout above. [skip ci] keeps the commit from re-triggering the workflow. - name: Commit and push metrics if: ${{ github.event_name != 'workflow_dispatch' || inputs.commit-results }} env: @@ -520,8 +542,6 @@ jobs: fi git config user.name "${APP_SLUG}[bot]" git config user.email "$(gh api "/users/${APP_SLUG}[bot]" -q .id)+${APP_SLUG}[bot]@users.noreply.github.com" - git remote set-url origin \ - "https://x-access-token:${GITHUB_TOKEN}@github.com/${GITHUB_REPOSITORY}.git" git add "$METRICS_FILE" git commit -m "chore(arithmetization): weekly zkc metrics $(date -u +%G-W%V) [skip ci]" for attempt in 1 2 3; do diff --git a/arithmetization/docs/metrics/zkc-weekly-metrics.md b/arithmetization/docs/metrics/zkc-weekly-metrics.md index 8b3d513ffa..fcfd595669 100644 --- a/arithmetization/docs/metrics/zkc-weekly-metrics.md +++ b/arithmetization/docs/metrics/zkc-weekly-metrics.md @@ -24,6 +24,7 @@ comes from the fixed CI tier. | week | started (UTC) | trigger | runner | arithmetization | zkc | run | |---|---|---|---|---|---|---| +| 2026-W32 | 2026-08-05 09:32 | manual (@OlivierBBB) | `xxl` 384 cores, 1488 GiB | `33b459e2e` (3698-weekly-metrics-runner-fixes, requested) | main@`9d844de0f` | [#7](https://github.com/LFDT-Lineth/lineth-monorepo/actions/runs/30993600507) | | 2026-W32 | 2026-08-03 14:55 | local (first harvest) | laptop arm64 12 cores, 36 GiB | `a2f9d079d` (3693-feat-weekly-zkc-metrics) | main@`49737ebb2275` | – | ## Cost per task — outcome, wall clock, peak RSS @@ -31,6 +32,7 @@ comes from the fixed CI tier. | week | compile | guest build | trace | trace + check | trace cells | |---|---|---|---|---|---| +| 2026-W32 | ok 1s / 111.08 MiB | ok 20s / 277.99 MiB | ok 6m21s / 42.10 GiB | skipped | 8 828 822 732 | | 2026-W32 | ok 2s / 118.73 MiB | ok 1m10s | ok 3m42s / 7.70 GiB | **TIMEOUT** 1h00m / 12.14 GiB | 7 908 271 799 | ## Constraint system (`zkc compile --stats`, `Total | function` row) @@ -38,6 +40,7 @@ comes from the fixed CI tier. | week | max degree | constraints | d1 | d2 | d3 | d4 | d5 | d6 | d7 | d8+ | lookups | complexity | static cells | |---|---|---|---|---|---|---|---|---|---|---|---|---|---| +| 2026-W32 | 8 | 13 061 | 17 | 6 974 | 4 620 | 1 064 | 277 | 106 | 2 | 1 | 6 840 | 97 420 | 722 684 | | 2026-W32 | 8 | 12 627 | 10 | 7 422 | 3 954 | 875 | 257 | 106 | 2 | 1 | 6 387 | 89 687 | 721 628 | ## Most expensive modules by constraint complexity (Σ d²) @@ -45,6 +48,7 @@ comes from the fixed CI tier. | week | 1 | 2 | 3 | 4 | 5 | |---|---|---|---|---|---| +| 2026-W32 | `kec_absorbing_phase` 19 987 | `main` 9 181 | `kec_theta` 9 032 | `rem64_ss` 6 034 | `kec_chi` 4 431 | | 2026-W32 | `absorbing_phase` 24 695 | `theta` 8 991 | `main` 8 674 | `rem64_ss` 6 034 | `process_I_type_instruction` 4 447 | ## Most expensive modules by trace cells @@ -52,4 +56,5 @@ comes from the fixed CI tier. | week | 1 | 2 | 3 | 4 | 5 | |---|---|---|---|---|---| +| 2026-W32 | `main` 2 459 123 849 | `process_I_type_instruction` 1 318 463 432 | `interpreter` 1 027 928 880 | `process_R_type_instruction` 856 086 132 | `registers` 673 691 160 | | 2026-W32 | `main` 2 339 652 245 | `process_I_type_instruction` 1 429 103 720 | `interpreter` 1 037 273 688 | `process_R_type_instruction` 919 761 960 | `$bit_shl_u64` 512 115 600 |