Historical record · 131 daily runs
The same measurement, every day since May.
A single benchmark is a snapshot; a run every day on the same hardware is a record. This is that record — 131 runs from 2026-05-11 to 2026-09-21, with every point linking to the GitHub Actions run that produced it.
Runs
131
First
2026-05-11
Latest
2026-09-21
Host
Xeon Platinum 8488C
Instance
c7i.large
liboqs
0.15.0
Over time
Pick a metric and watch it move — or not.
Up to four algorithms at once, so no colour is ever reused for two lines. Breaks in a line are runs with no measurement.
Mean latency · µs · keygen · 131 runs
Measured points only. A break in a line is a run with no measurement — it is not smoothed over, and there is no value between two runs.
Summary
First measurement, latest, and everything between.
The default selection. Change is first-to-last; read it against the observed range in the next column, not on its own.
| Algorithm | First | Latest | Change | Observed range | Points | Gaps |
|---|---|---|---|---|---|---|
| ML-KEM-512ML-KEM | 13.7 µs · 2026-05-11 | 7.7 µs · 2026-09-21 | -43.5% | 6.8 µs – 47.8 µs | 131 | 0 |
| ML-KEM-768ML-KEM | 18.8 µs · 2026-05-11 | 17.1 µs · 2026-09-21 | -8.9% | 9.6 µs – 69.6 µs | 131 | 0 |
| ML-DSA-44ML-DSA | 32.3 µs · 2026-05-11 | 21.9 µs · 2026-09-21 | -32.4% | 17.5 µs – 63.2 µs | 131 | 0 |
| ML-DSA-65ML-DSA | 52.3 µs · 2026-05-11 | 30.3 µs · 2026-09-21 | -42.1% | 28.6 µs – 93.0 µs | 131 | 0 |
Why the line breaksOther benchmark publishers interpolate: they fit a curve through measured points and read a value off it at whatever operating point you ask for. We do not, and the gaps in these lines are the visible consequence. A run that did not happen produces no point, and the line breaks rather than being drawn through a value nobody measured. If you need a figure for a date between two runs, the honest answer is that we do not have one — and the API says the same thing in its own payload.
Why none of this is called a trendAcross these 131 runs the observed range on a single algorithm’s keygen mean is 226–628% of its own minimum. Every first-to-last change in the table above sits inside that band. So does the largest of them: ML-KEM-512 reads -44% end to end, but it alternates between roughly 6.8 µs and 47.8 µs from one run to the next rather than drifting — the endpoints only say which mode each happened to land in.
The cause is the host, not the algorithms. c7i.large is a fixed-performance instance class, which removes burst-credit throttling as a cause but does not by itself make a day-to-day trend readable. CPU steal across this hardware era has ranged from <0.01% to <0.01%. We publish this rather than smooth it, and it is the honest reason not to read a trend line here as a performance change. Comparisons between algorithms measured in the same run are sound — that is what compare is for. Detecting real change over time would need a dedicated instance, and until there is one this page is a record of what we measured, not a claim about what changed.
The cause is the host, not the algorithms. c7i.large is a fixed-performance instance class, which removes burst-credit throttling as a cause but does not by itself make a day-to-day trend readable. CPU steal across this hardware era has ranged from <0.01% to <0.01%. We publish this rather than smooth it, and it is the honest reason not to read a trend line here as a performance change. Comparisons between algorithms measured in the same run are sound — that is what compare is for. Detecting real change over time would need a dedicated instance, and until there is one this page is a record of what we measured, not a claim about what changed.
Take the data
The whole series, as JSON.
This page reads the same public endpoint you can — no privileged access to its own data.