From bd1438e4dbec0acc6f268805568449f347b535c8 Mon Sep 17 00:00:00 2001 From: ghangz <152254226+ghangz@users.noreply.github.com> Date: Wed, 1 Jul 2026 11:39:26 +0800 Subject: [PATCH 1/2] Add mxcc compile performance gate --- tools/mxcc_perf_gate.py | 58 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 58 insertions(+) create mode 100644 tools/mxcc_perf_gate.py diff --git a/tools/mxcc_perf_gate.py b/tools/mxcc_perf_gate.py new file mode 100644 index 000000000000..aed125a7d159 --- /dev/null +++ b/tools/mxcc_perf_gate.py @@ -0,0 +1,58 @@ +#!/usr/bin/env python3 +"""Compare baseline and current performance JSON and fail on regressions.""" + +from __future__ import annotations + +import argparse +import json +from pathlib import Path + +METRIC = 'compile_seconds' +TOLERANCE = 0.1 + + +def load(path: Path) -> dict[str, float]: + data = json.loads(path.read_text(encoding="utf-8")) + if isinstance(data, list): + return {str(item["name"]): float(item[METRIC]) for item in data} + return {str(k): float(v[METRIC] if isinstance(v, dict) else v) for k, v in data.items()} + + +def compare(baseline: dict[str, float], current: dict[str, float]) -> dict[str, object]: + rows: list[dict[str, object]] = [] + failed = False + for name, old in sorted(baseline.items()): + if name not in current: + rows.append({"name": name, "status": "missing-current"}) + failed = True + continue + new = current[name] + ratio = (new - old) / old if old else 0.0 + status = "regression" if ratio < -TOLERANCE else "ok" + failed = failed or status != "ok" + rows.append({"name": name, "baseline": old, "current": new, "delta_ratio": ratio, "status": status}) + return {"ok": not failed, "metric": METRIC, "rows": rows} + + +def self_test() -> None: + data = compare({"case": 100.0}, {"case": 99.0}) + assert data["ok"] + print(json.dumps({"ok": True, "rows": len(data["rows"])}, ensure_ascii=False)) + + +def main() -> int: + parser = argparse.ArgumentParser(description=__doc__) + parser.add_argument("baseline") + parser.add_argument("current") + parser.add_argument("--self-test", action="store_true") + args = parser.parse_args() + if args.self_test: + self_test() + return 0 + result = compare(load(Path(args.baseline)), load(Path(args.current))) + print(json.dumps(result, ensure_ascii=False, indent=2)) + return 0 if result["ok"] else 1 + + +if __name__ == "__main__": + raise SystemExit(main()) From 1ce3a7ff386a7cc83fdd02643b45dca3086fe9e1 Mon Sep 17 00:00:00 2001 From: ghangz <152254226+ghangz@users.noreply.github.com> Date: Wed, 1 Jul 2026 15:04:23 +0800 Subject: [PATCH 2/2] Fix mxcc compile time regression direction --- tools/mxcc_perf_gate.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/tools/mxcc_perf_gate.py b/tools/mxcc_perf_gate.py index aed125a7d159..19b1bbef54a5 100644 --- a/tools/mxcc_perf_gate.py +++ b/tools/mxcc_perf_gate.py @@ -28,7 +28,7 @@ def compare(baseline: dict[str, float], current: dict[str, float]) -> dict[str, continue new = current[name] ratio = (new - old) / old if old else 0.0 - status = "regression" if ratio < -TOLERANCE else "ok" + status = "regression" if ratio > TOLERANCE else "ok" failed = failed or status != "ok" rows.append({"name": name, "baseline": old, "current": new, "delta_ratio": ratio, "status": status}) return {"ok": not failed, "metric": METRIC, "rows": rows} @@ -36,7 +36,11 @@ def compare(baseline: dict[str, float], current: dict[str, float]) -> dict[str, def self_test() -> None: data = compare({"case": 100.0}, {"case": 99.0}) - assert data["ok"] + if not data["ok"]: + raise RuntimeError("self-test failed: faster compile time should pass") + regression = compare({"case": 100.0}, {"case": 120.0}) + if regression["ok"]: + raise RuntimeError("self-test failed: slower compile time should regress") print(json.dumps({"ok": True, "rows": len(data["rows"])}, ensure_ascii=False))