Back to News & Insights
Web Development September 10, 2026 · 6 min read

400 rounds, and the bug never showed up. So I stopped rolling dice.

The most expensive bug in the game I just shipped could only fire on 1.01% of rounds. Here is the...

400 rounds, and the bug never showed up. So I stopped rolling dice.

The most expensive bug in the game I just shipped could only fire on 1.01% of rounds.

Here is the shape of it. Replay is a betting game where the final score is public before you bet — the game ended 8–5, and what you buy is which of the 1,287 orderings of those 13 points actually happened. It runs on a casino platform whose host contract caps what a game may pay out:

Zero slack. The game quotes its own numbers up front — quoteCaps declares how much profit to reserve, quoteRiskParams declares the maximum payout — and then at settlement it returns the payout it actually owes. Three call sites, one number. If any of them re-derives that number independently and lands one wei high, the transaction reverts.

Not "sometimes reverts". It reverts every single time a player hits the top ticket. Which is the 96.03× ticket. Which wins on 13 orderings out of 1,287 — 1.0101% of rounds.

Read the failure mode again, because that is the nasty part: the rarer the outcome, the better the bug hides. It survives casual testing perfectly. It survives a demo. It fails on the one round somebody actually remembers.

So I played 400 rounds against the platform's local simulator — its own chain, a real ECVRF node rather than a mock, the full contract lifecycle. The tail never landed.

That is not surprising, and it is also not evidence. At p = 1.0101%, the odds of 400 rounds all missing are 0.98989^400 ≈ 1.7%. Unlucky, not informative.

And the flip side is worse. Suppose the tail had landed once, and paid correctly. What would I have learned? That one rank out of 1,287 works. Either way I would have shipped a game whose most valuable outcome was checked by luck.

Two properties of the contract turned out to make the entire outcome space reachable.

It takes randomness as an argument and returns the result. Nothing is written, nothing is read from storage. So I can call it from a script, with randomness I choose, as often as I like, against the deployed contract — no VRF, no waiting, no state to reset between calls.

That is rejection sampling over the sixteen 16-bit windows of the word, because plain byte % n is biased — and a biased draw is not a rounding error when the draw is the odds.

The useful consequence is the first line. For total = 1287, limit = 64350, so a bytes32 whose leading two bytes are R yields rank R. The randomness is addressable. Every outcome on the board has a preimage I can write down.

The winner count becomes checkable against the mathematics. Because winning ranks are counted rather than observed, I can compare the total against a closed form: this ticket should win on exactly C(13, 5-4) = C(13,1) = 13 orderings. It wins on 13.

That check catches a class of bug sampling structurally cannot see. If the payout arithmetic is perfect but three extra ranks are classified as winners, every sampled test still passes — you saw a win, it paid the right amount. The set of winners was wrong, and the set of winners is the thing that costs money.

One wei becomes visible. cap and maxPayout printed on adjacent lines, compared as integers, at the exact multiplier where the cap binds hardest.

There was a second trap in the same family, incidentally, and it is the reason I now distrust anything that only misbehaves at the top of a distribution. The host applies a game's reservedProfitDelta before finalising the session — so a game that helpfully releases its reserved profit at settlement collapses its own cap to the wager and reverts every win above 1×. The correct value is a slightly uncomfortable-looking zero:

A 1.75× ticket wins often enough that you would catch this one by playing. A 96.03× ticket would have shipped broken.

None of the above is really about blockchains. The property that made the sweep possible is this:

Want to discuss this further?

Book a free strategy call with our team to see how these insights apply to your specific business goals.

Book a consultation