Skip to content

Commit 2fca704

Browse files
authored
Merge branch 'main' into amd/agentx_dsv4_sgl_mtp_0717
2 parents a11a377 + b6abf19 commit 2fca704

99 files changed

Lines changed: 7468 additions & 522 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/workflows/README.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,14 @@ they run all evals only. The primary label still controls canary/fail-fast.
157157
with both modifiers, are not. Default full sweeps, including default evals,
158158
are also reusable.
159159

160+
## AgentX Fast Mode
161+
162+
Add `agentx-fast` alongside one primary sweep label to run the 5-minute cache
163+
warmup and 20-minute profiling preset for single- and multi-node AgentX
164+
throughput jobs. Fixed-sequence throughput and eval jobs retain their canonical
165+
settings. Adding or removing the modifier restarts the active sweep. Fast-mode
166+
runs are not eligible for artifact reuse after merge.
167+
160168
## Reusing an Approved PR Full Sweep
161169

162170
`[skip-sweep]` skips PR benchmark setup only; changelog and reuse checks still

.github/workflows/benchmark-multinode-tmpl.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -274,8 +274,8 @@ jobs:
274274
timeout-minutes: 480
275275
name: >-
276276
p${{ inputs.priority }} | ${{ inputs.model-prefix }} ${{ inputs.precision }} ${{ inputs.runner }} ${{ inputs.framework == 'sglang' && 'sgl' || inputs.framework == 'dynamo-sglang' && 'dyn-sgl' || inputs.framework == 'sglang-disagg' && 'sgl-disagg' || inputs.framework }}
277-
${{ inputs.prefill-num-worker }}P (TP${{ inputs.prefill-tp }}${{ inputs.prefill-pp != '' && inputs.prefill-pp != '1' && format('/PP{0}', inputs.prefill-pp) || '' }}${{ inputs.prefill-dcp-size != '' && inputs.prefill-dcp-size != '1' && format('/DCP{0}', inputs.prefill-dcp-size) || '' }}${{ inputs.prefill-pcp-size != '' && inputs.prefill-pcp-size != '1' && format('/PCP{0}', inputs.prefill-pcp-size) || '' }}${{ inputs.prefill-ep != '' && inputs.prefill-ep != '1' && format('/EP{0}', inputs.prefill-ep) || '' }}${{ inputs.prefill-dp-attn == 'true' && '/DPA' || '' }})
278-
x ${{ inputs.decode-num-worker }}D (TP${{ inputs.decode-tp }}${{ inputs.decode-pp != '' && inputs.decode-pp != '1' && format('/PP{0}', inputs.decode-pp) || '' }}${{ inputs.decode-dcp-size != '' && inputs.decode-dcp-size != '1' && format('/DCP{0}', inputs.decode-dcp-size) || '' }}${{ inputs.decode-pcp-size != '' && inputs.decode-pcp-size != '1' && format('/PCP{0}', inputs.decode-pcp-size) || '' }}${{ inputs.decode-ep != '' && inputs.decode-ep != '1' && format('/EP{0}', inputs.decode-ep) || '' }}${{ inputs.decode-dp-attn == 'true' && '/DPA' || '' }})
277+
${{ inputs.disagg == 'true' && format('{0}P ', inputs.prefill-num-worker) || '' }}(TP${{ inputs.prefill-tp }}${{ inputs.prefill-pp != '' && inputs.prefill-pp != '1' && format('/PP{0}', inputs.prefill-pp) || '' }}${{ inputs.prefill-dcp-size != '' && inputs.prefill-dcp-size != '1' && format('/DCP{0}', inputs.prefill-dcp-size) || '' }}${{ inputs.prefill-pcp-size != '' && inputs.prefill-pcp-size != '1' && format('/PCP{0}', inputs.prefill-pcp-size) || '' }}${{ inputs.prefill-ep != '' && inputs.prefill-ep != '1' && format('/EP{0}', inputs.prefill-ep) || '' }}${{ inputs.prefill-dp-attn == 'true' && '/DPA' || '' }})
278+
${{ inputs.disagg == 'true' && format('x {0}D (TP{1}{2}{3}{4}{5}{6})', inputs.decode-num-worker, inputs.decode-tp, inputs.decode-pp != '' && inputs.decode-pp != '1' && format('/PP{0}', inputs.decode-pp) || '', inputs.decode-dcp-size != '' && inputs.decode-dcp-size != '1' && format('/DCP{0}', inputs.decode-dcp-size) || '', inputs.decode-pcp-size != '' && inputs.decode-pcp-size != '1' && format('/PCP{0}', inputs.decode-pcp-size) || '', inputs.decode-ep != '' && inputs.decode-ep != '1' && format('/EP{0}', inputs.decode-ep) || '', inputs.decode-dp-attn == 'true' && '/DPA' || '') || '' }}
279279
${{ inputs.spec-decoding != 'none' && inputs.spec-decoding || '' }}
280280
${{ inputs.kv-offloading != '' && inputs.kv-offloading != 'none' && format('{0} KV offload', inputs.kv-offloading) || '' }}
281281
${{ inputs.kv-offload-backend != '' && inputs.kv-offload-backend != 'none' && inputs.kv-offload-backend != 'default' && inputs.kv-offload-backend || '' }}

.github/workflows/run-sweep.yml

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ concurrency:
1313
github.event.label.name != 'full-sweep-fail-fast-no-canary' &&
1414
github.event.label.name != 'all-evals' &&
1515
github.event.label.name != 'evals-only' &&
16+
github.event.label.name != 'agentx-fast' &&
1617
github.event.label.name != 'skip_queue' &&
1718
github.event.label.name != 'ci-patchwork' &&
1819
github.event.label.name != 'engine-patch' &&
@@ -55,6 +56,7 @@ jobs:
5556
github.event.label.name == 'full-sweep-fail-fast-no-canary' ||
5657
github.event.label.name == 'all-evals' ||
5758
github.event.label.name == 'evals-only' ||
59+
github.event.label.name == 'agentx-fast' ||
5860
github.event.label.name == 'skip_queue' ||
5961
github.event.label.name == 'ci-patchwork' ||
6062
github.event.label.name == 'engine-patch' ||
@@ -136,6 +138,7 @@ jobs:
136138
github.event.action == 'synchronize' &&
137139
!github.event.pull_request.draft &&
138140
!contains(github.event.pull_request.labels.*.name, 'evals-only') &&
141+
!contains(github.event.pull_request.labels.*.name, 'agentx-fast') &&
139142
(
140143
contains(github.event.pull_request.labels.*.name, 'full-sweep-enabled') ||
141144
contains(github.event.pull_request.labels.*.name, 'non-canary-full-sweep-enabled') ||
@@ -204,6 +207,7 @@ jobs:
204207
github.event.label.name == 'full-sweep-fail-fast-no-canary' ||
205208
github.event.label.name == 'all-evals' ||
206209
github.event.label.name == 'evals-only' ||
210+
github.event.label.name == 'agentx-fast' ||
207211
github.event.label.name == 'skip_queue' ||
208212
github.event.label.name == 'ci-patchwork' ||
209213
github.event.label.name == 'engine-patch' ||
@@ -622,6 +626,7 @@ jobs:
622626
disagg: ${{ 'false' }}
623627
run-eval: false
624628
scenario-type: agentic-coding
629+
agentx-fast: ${{ contains(github.event.pull_request.labels.*.name, 'agentx-fast') }}
625630

626631
sweep-multi-node-agentic:
627632
needs: [setup, canary-select, canary-sweep]
@@ -685,6 +690,7 @@ jobs:
685690
duration: ${{ matrix.config.duration }}
686691
run-eval: false
687692
scenario-type: agentic-coding
693+
agentx-fast: ${{ contains(github.event.pull_request.labels.*.name, 'agentx-fast') }}
688694

689695
sweep-evals:
690696
needs: [setup, canary-select, canary-sweep]
@@ -1097,7 +1103,8 @@ jobs:
10971103
github.event.label.name == 'full-sweep-fail-fast' ||
10981104
github.event.label.name == 'full-sweep-fail-fast-no-canary' ||
10991105
github.event.label.name == 'all-evals' ||
1100-
github.event.label.name == 'evals-only'
1106+
github.event.label.name == 'evals-only' ||
1107+
github.event.label.name == 'agentx-fast'
11011108
)
11021109
runs-on: ubuntu-latest
11031110
permissions:

.github/workflows/stage-results-callback.yml

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -66,9 +66,17 @@ jobs:
6666
? [
6767
`@${requestedBy} staged run ${runId}: ${chartUrl}`,
6868
'',
69-
`This shared staging slot remains available until the next \`/stage-results\` request. [Staging workflow](${appRunUrl})`,
69+
`This run remains available across future \`/stage-results\` requests. Staging the same run ID again updates its staged data. [Staging workflow](${appRunUrl})`,
70+
'',
71+
`@${requestedBy} 已将运行 ${runId} 发布到预发布环境:${chartUrl}`,
72+
'',
73+
`后续的 \`/stage-results\` 请求不会移除此运行;再次发布相同的运行 ID 会更新其预发布数据。[预发布工作流](${appRunUrl})`,
7074
].join('\n')
71-
: `@${requestedBy} staging run ${runId} failed. [Inspect the staging workflow](${appRunUrl}).`;
75+
: [
76+
`@${requestedBy} staging run ${runId} failed. [Inspect the staging workflow](${appRunUrl}).`,
77+
'',
78+
`@${requestedBy} 预发布运行 ${runId} 失败。[查看预发布工作流](${appRunUrl})。`,
79+
].join('\n');
7280
7381
if (commentId) {
7482
await github.rest.issues.updateComment({

.github/workflows/stage-results.yml

Lines changed: 22 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -153,14 +153,20 @@ jobs:
153153
name === 'eval_results_all' ||
154154
name.startsWith('bmk_agentic_'),
155155
);
156-
const validateRun = async (candidate) => {
156+
const validateRun = async (candidate, allowHistoricalAssociation = false) => {
157157
if (
158158
candidate.path !== '.github/workflows/run-sweep.yml' ||
159159
candidate.event !== 'pull_request'
160160
) {
161161
return { valid: false, reason: 'not a pull-request run of run-sweep.yml' };
162162
}
163-
if (!pullCommitShas.has(candidate.head_sha)) {
163+
const isAssociatedWithPull = candidate.pull_requests?.some(
164+
(candidatePull) => candidatePull.number === context.issue.number,
165+
);
166+
if (
167+
!pullCommitShas.has(candidate.head_sha) &&
168+
!(allowHistoricalAssociation && isAssociatedWithPull)
169+
) {
164170
return { valid: false, reason: 'its head commit is not in the PR commit list' };
165171
}
166172
if (fullSweepLabelsAt(candidate.created_at).length === 0) {
@@ -169,13 +175,19 @@ jobs:
169175
reason: 'it was not created while a full-sweep label was applied',
170176
};
171177
}
172-
if (candidate.status !== 'completed' || candidate.conclusion !== 'success') {
178+
const stageableConclusions = new Set(['success', 'cancelled', 'failure']);
179+
if (
180+
candidate.status !== 'completed' ||
181+
!stageableConclusions.has(candidate.conclusion)
182+
) {
173183
return {
174184
valid: false,
175185
reason: `it is ${candidate.status}/${candidate.conclusion}`,
176186
};
177187
}
178188
189+
// Cancelled or failed sweeps may still contain useful partial results. The
190+
// artifact checks below keep empty or metadata-only runs ineligible.
179191
const artifactNames = await usableArtifactNames(candidate.id);
180192
if (!artifactNames.includes('changelog-metadata')) {
181193
return { valid: false, reason: 'it has no unexpired changelog-metadata artifact' };
@@ -195,7 +207,7 @@ jobs:
195207
run_id: Number(requestedRunId),
196208
});
197209
run = response.data;
198-
const validation = await validateRun(run);
210+
const validation = await validateRun(run, true);
199211
if (!validation.valid) {
200212
core.setFailed(`Run ${requestedRunId} cannot be staged because ${validation.reason}`);
201213
return;
@@ -222,7 +234,7 @@ jobs:
222234
}
223235
if (!run) {
224236
core.setFailed(
225-
`No successful completed run-sweep.yml run with unexpired staging artifacts was found for PR #${context.issue.number}`,
237+
`No stageable completed run-sweep.yml run with unexpired staging artifacts was found for PR #${context.issue.number}`,
226238
);
227239
return;
228240
}
@@ -244,7 +256,11 @@ jobs:
244256
with:
245257
github-token: ${{ github.token }}
246258
script: |
247-
const body = `@${process.env.REQUESTED_BY} staging [run ${process.env.RUN_ID}](${process.env.RUN_URL}). The shared staging slot is serialized; a completion link will be posted here.`;
259+
const body = [
260+
`@${process.env.REQUESTED_BY} staging [run ${process.env.RUN_ID}](${process.env.RUN_URL}). Existing staged runs will be preserved; a completion link will be posted here.`,
261+
'',
262+
`@${process.env.REQUESTED_BY} 正在将[运行 ${process.env.RUN_ID}](${process.env.RUN_URL})发布到预发布环境。已有的预发布运行会继续保留;完成后将在此处提供链接。`,
263+
].join('\n');
248264
const comment = await github.rest.issues.createComment({
249265
owner: context.repo.owner,
250266
repo: context.repo.repo,

AGENTS.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -95,7 +95,7 @@ PRs do not run the sweep automatically - `run-sweep.yml` is gated on a primary s
9595
- `full-sweep-fail-fast` - runs the full intermediate concurrency sweep behind the same sequential single-node canary gate as `full-sweep-enabled` (so a globally broken change burns one job, not the whole fan-out), and with `strategy.fail-fast` enabled on every matrix: the first failure in a matrix cancels that matrix's remaining jobs. Fail-fast is matrix-scoped, so the other matrices (1k1k vs 8k1k vs agentic vs evals) keep running and self-terminate on their own first failure; their completed results remain valid. The failing job keeps its red *failure* conclusion and the run concludes failed. **This is the strongly recommended default for full sweeps** (image bumps, recipe changes, bring-up) - a failure means the rest of that matrix is wasted GPU time. Caveat: one flaky job kills its matrix's in-flight results; if that repeatedly bites a specific config, fall back to `full-sweep-enabled` for that PR.
9696
- `full-sweep-fail-fast-no-canary` - same as `full-sweep-fail-fast` but without the canary gate: all matrices fan out immediately. Use when the canary is flaky or not representative of the affected configuration but you still want per-matrix fail-fast.
9797

98-
`all-evals` and `evals-only` are optional modifier labels. Combine either or both with one primary sweep label. `all-evals` expands eval selection to every generated fixed-sequence configuration without changing throughput. `evals-only` suppresses throughput while keeping the default eval subset; combining both runs every eval and no throughput. `all-evals` remains eligible for artifact reuse when paired with an eligible full-sweep label. Runs with `evals-only`, including runs with both modifiers, are not eligible.
98+
`all-evals`, `evals-only`, and `agentx-fast` are optional modifier labels. Combine them with one primary sweep label. `all-evals` expands eval selection to every generated fixed-sequence configuration without changing throughput. `evals-only` suppresses throughput while keeping the default eval subset; combining both eval modifiers runs every eval and no throughput. `agentx-fast` applies the 5-minute warmup and 20-minute profiling preset to single- and multi-node AgentX throughput jobs only; fixed-sequence and eval jobs are unchanged. `all-evals` remains eligible for artifact reuse when paired with an eligible full-sweep label. Runs with `evals-only` or `agentx-fast` are not eligible for artifact reuse.
9999

100100
**The sweep does not trigger while the PR has merge conflicts.** Even with a sweep label applied, the `run-sweep.yml` workflow will not start until the PR cleanly merges into main — a stale claude/* or update-* branch with a `perf-changelog.yaml` conflict (the common case) will sit in NO_SWEEP / NO_SUCCESS until rebased. Resolution recipe is documented in `KLAUD_DEBUG.md §1.1`: `git merge origin/main`, then `git checkout origin/main -- perf-changelog.yaml`, then re-append the PR's own changelog entry at the tail. Don't 3-way merge `perf-changelog.yaml`; whitespace edits silently re-trigger the deletion check.
101101

0 commit comments

Comments
 (0)