Skip to content

[cuda] Score autotune picks with one event tick of tolerance, on longer kernels - #23635

Merged
Gasoonjia merged 1 commit into
mainfrom
gasoonjia/autotune-regret-timer-resolution
Oct 13, 2026
Merged

Gasoonjia merged 1 commit into
mainfrom
gasoonjia/autotune-regret-timer-resolution

Conversation

@Gasoonjia

@Gasoonjia Gasoonjia commented Oct 9, 2026 •

Copy link
Copy Markdown
Contributor

SaturatedCpuExportTest (test_cuda_graph_timing.py) and Int4AutotunePickTest score each autotune decision by its regret: the pick's reference time divided by the best candidate's. Event timing is quantized: cudaEventElapsedTime steps by 0.512 µs on the A10G CI GPU, and hipEventElapsedTime by about 1 µs. A reading is the difference of two quantized timestamps, so it can fall on either side of the true time by about a tick. On a kernel of a few microseconds, that is a large ratio. The A10G job failed on (https://github.com/pytorch/executorch/actions/runs/37835437673/job/113511485001):

AssertionError: 1.2000000727595779 not less than or equal to 1.2 :
Pick(kind='inductor', name='triton_poi_fused__unsafe_view_add_transpose_copy_view_copy_9', candidates=2, regret=1.2000000727595779)

That is exactly fp32(6 × 0.512 µs) / fp32(5 × 0.512 µs).

Changes

  1. One tick of tolerance: _regret() credits the best candidate one tick, pick / (best + 1 tick), floored at 1.0, with margins for the float32 event times.
    • A difference the timer can't resolve no longer counts as a worse pick.
    • Anything larger is charged in proportion, so there's no jump at one tick and the limits stay meaningful at every scale.
    • No thresholds change.
  2. Longer kernels, so one tick is a small fraction of them:
    • SaturatedCpuExportTest's model now uses widths (512, 1536, 3072) and 4096 tokens (was (256, 768, 1536) and 64).
    • Int4AutotunePickTest's smallest weight is now 8192×2048 (was 2048×2048).
    • summarize() now also prints the fastest kernel's reference time, so CI shows how far above one tick the shortest kernel runs.

Tests

RegretTest runs on CPU and covers both the CUDA and the HIP tick:

  • one tick apart scores 1.0, checked up to 31250-tick kernels;
  • two ticks apart is charged, checked up to ~1 s;
  • larger gaps score pick / (best + 1).

Test plan

CI: unittest-cuda / unittest-cuda-quantized-gemm should show RegretTest, SaturatedCpuExportTest and Int4AutotunePickTest passing, the "fastest kernel" line in their output, and how long the two pick tests now take.

@pytorch-bot

pytorch-bot Bot commented Oct 9, 2026 •

Copy link
Copy Markdown

🔗 Helpful Links

🧪 See artifacts and rendered test results at hud.pytorch.org/pr/pytorch/executorch/23635

Note: Links to docs will display an error until the docs builds have been completed.

✅ No Failures

As of commit 0dadcb0 with merge base 7f4dac6 (image):
💚 Looks good so far! There are no failures yet. 💚

This comment was automatically generated by Dr. CI and updates every 15 minutes.

@meta-cla meta-cla Bot added the CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. label Oct 9, 2026
@github-actions

github-actions Bot commented Oct 9, 2026

Copy link
Copy Markdown

This PR needs a release notes: label

If your change should be included in the release notes (i.e. would users of this library care about this change?), please use a label starting with release notes:. This helps us keep track and include your important work in the next release notes.

To add a label, you can comment to pytorchbot, for example
@pytorchbot label "release notes: none"

For more information, see
https://github.com/pytorch/pytorch/wiki/PyTorch-AutoLabel-Bot#why-categorize-for-release-notes-and-how-does-it-work.

@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 9, 2026 11:46 — with GitHub Actions Active
@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 9, 2026 23:08 — with GitHub Actions Active
@Gasoonjia
Gasoonjia force-pushed the gasoonjia/autotune-regret-timer-resolution branch from 95031ed to 6d128a8 Compare October 9, 2026 23:48
@Gasoonjia Gasoonjia changed the title [cuda] Count autotune candidates one event tick apart as a tie in the pick tests [cuda] Score autotune picks with one event tick of tolerance, on longer kernels Oct 9, 2026
@Gasoonjia
Gasoonjia force-pushed the gasoonjia/autotune-regret-timer-resolution branch from 6d128a8 to febf90e Compare October 9, 2026 23:50
@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 10, 2026 01:21 — with GitHub Actions Active
Gasoonjia added a commit that referenced this pull request Oct 12, 2026
unittest-cuda is cancelled at its 90-minute timeout on every recent main
commit. #23605 moved the quantized GEMM kernel suites into
unittest-cuda-quantized-gemm, but the same push added
test_int4_large_quantized_gemm.py (~7.7 min on the A10G) and
test_int6_large_quantized_gemm.py (~5.1 min), which still run in
unittest-cuda. On #23635 its backends/cuda/tests pytest alone took 62 min and
the job was cancelled during the Gemma 4 tests that follow.

Run both in the second quantized-GEMM shard, renamed
large-int5-int6-int8-graph-timing (that shard took 44 min; the int4 shard
already takes ~60). unittest-cuda ignores them. No test is dropped.
@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 12, 2026 02:37 — with GitHub Actions Active
Gasoonjia added a commit that referenced this pull request Oct 12, 2026
#23676)

`unittest-cuda` is cancelled at its 90-minute timeout on every recent
main commit (e.g.
https://github.com/pytorch/executorch/actions/runs/37991426749/job/114026586806).
#23605 moved the quantized GEMM kernel suites into
`unittest-cuda-quantized-gemm`, but the same push also added two new
suites that still run in `unittest-cuda`:
- `test_int4_large_quantized_gemm.py` (`711dd81e23`, ~7.7 min on the
A10G)
- `test_int6_large_quantized_gemm.py` (`f19360763f`, ~5.1 min)

On #23635
(https://github.com/pytorch/executorch/actions/runs/38006402026/job/114076255669),
`unittest-cuda`'s `backends/cuda/tests` pytest alone took 62 min, and
the job was cancelled during the Gemma 4 tests that follow.

### Change
- Run both large suites in the second quantized-GEMM shard, renamed
`large-int5-int6-int8-graph-timing`. That shard took 44 min on #23635;
the int4 shard already takes ~60 min, so they don't go there.
- `unittest-cuda` ignores them.
- No test is dropped.

### Test plan
CI:
- `unittest-cuda` finishes within 90 min.
- `unittest-cuda-quantized-gemm (large-int5-int6-int8-graph-timing)`
runs both large suites and also stays within 90 min.
@Gasoonjia
Gasoonjia marked this pull request as ready for review October 13, 2026 00:58
@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 13, 2026 02:22 — with GitHub Actions Active
…er kernels

SaturatedCpuExportTest and Int4AutotunePickTest score each autotune decision
by the regret of the pick: its reference time over the best candidate's.
Event timing is quantized (cudaEventElapsedTime steps by 0.512 us on the A10G
CI GPU, hipEventElapsedTime by about 1 us), and a reading is the difference
of two quantized timestamps, so it can fall either side of the true time by
about a tick. On a kernel of a few microseconds that is a large ratio. The
A10G unittest-cuda job failed on

  AssertionError: 1.2000000727595779 not less than or equal to 1.2 :
  Pick(kind='inductor', name='triton_poi_fused__unsafe_view_add_transpose_
  copy_view_copy_9', candidates=2, regret=1.2000000727595779)

which is exactly fp32(6 * 0.512 us) / fp32(5 * 0.512 us).

Two changes:

- _regret() credits the best candidate one tick: pick / (best + 1 tick),
  floored at 1.0, with margins for the float32 event times. A difference the
  timer cannot resolve no longer counts as a worse pick; anything larger is
  charged in proportion, so the limits stay meaningful at every scale.
- The tests' kernels run longer, so a tick is a small fraction of them:
  SaturatedCpuExportTest's model uses widths (512, 1536, 3072) and 4096
  tokens (was (256, 768, 1536) and 64), and Int4AutotunePickTest's smallest
  weight is 8192x2048 (was 2048x2048). summarize() now also prints the
  fastest kernel's reference time, so CI shows how far above a tick it is.

RegretTest checks, on CPU, for both the CUDA and the HIP tick: one tick apart
is 1.0 (up to 31250-tick kernels), two ticks apart is charged (up to ~1 s),
and pick / (best + 1) beyond that.
@Gasoonjia
Gasoonjia force-pushed the gasoonjia/autotune-regret-timer-resolution branch from e290977 to 0dadcb0 Compare October 13, 2026 05:26
@Gasoonjia
Gasoonjia deployed to upload-benchmark-results October 13, 2026 08:48 — with GitHub Actions Active
@Gasoonjia
Gasoonjia merged commit 6c110e5 into main Oct 13, 2026
424 of 426 checks passed
@Gasoonjia
Gasoonjia deleted the gasoonjia/autotune-regret-timer-resolution branch October 13, 2026 11:21

This branch was successfully deployed

2 active deployments
upload-benchmark-results — 0dadcb09 Deployed Oct 13, 2026 by Gasoonjia via upload-benchmark-results #20750
cadence — 0dadcb09 Deployed Oct 13, 2026 by Gasoonjia via hifi-op-test / hifi4 #33041
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants