Measure genuine CPU query startup first input and warm latency

This commit is contained in:
karl committed 2026-10-13 13:53:03 +02:00
1 parent 6e7616b6d3
commit d568bdb2b1
2 files changed
+43 -1

No files matched your search

@@ -8,6 +8,7 @@ import argparse
import ctypes
import hashlib
import json
import math
import os
from pathlib import Path
import platform
@@ -53,6 +54,8 @@ def main():
parser.add_argument("--output", type=Path, required=True)
parser.add_argument("--repeats", type=int, default=3)
args = parser.parse_args()
if args.output.exists():
parser.error("output must be new; preserve previous evidence")
if not 1 <= args.repeats <= 20:
parser.error("repeats must be 1..20")
manifest = json.loads((ROOT / "tools/embeddinggemma2/model-manifest.json").read_text())
@@ -77,6 +80,15 @@ def main():
response, first_ms = session.worker({"op": "query", "text": "cancel the supplier partnership", "debug_performance": True})
vectors(response, 1)
sample.update(first_query_ms=first_ms, worker=response["performance"], after_query_memory=memory(session.process.pid))
warm = []
# Distinct inputs exercise native query inference without a Rust
# query cache. Keep first input separate from these warmed calls.
for index in range(20):
response, duration = session.worker({"op": "query", "text": f"supplier cancellation notice example {index}", "debug_performance": True})
vectors(response, 1)
warm.append({"round_trip_ms": duration, "worker": response["performance"]})
ordered = sorted(item["round_trip_ms"] for item in warm)
sample["warm_queries"] = {"samples": warm, "p95_ms": ordered[math.ceil(len(ordered) * .95) - 1]}
if role == "query":
session.send({"op": "documents", "texts": ["test"], "title": "none"})
rejected = session.next()
@@ -88,7 +100,8 @@ def main():
session.close()
report = {"platform": platform.platform(), "cpu_count": os.cpu_count(), "verification_ms": verification_ms, "cache_note": "Cached model bytes; startup excludes Rust verification and desktop preparation. No GPU executed. Repeated fresh processes, not cold disk.", "worker_sha256": hashlib.sha256(args.worker.read_bytes()).hexdigest(), "samples": samples}
args.output.parent.mkdir(parents=True, exist_ok=True)
args.output.write_text(json.dumps(report, indent=2) + "\n", encoding="utf-8")
with args.output.open("x", encoding="utf-8") as output:
output.write(json.dumps(report, indent=2) + "\n")
for role in ["indexing", "query"]:
rows = [s for s in samples if s["role"] == role]
print(role, "startup median ms", statistics.median(s["startup_ms"] for s in rows), "ready memory", rows[0]["ready_memory"], "after query", rows[0]["after_query_memory"])