Skip to main content
OpenBook a 1-on-1 review

Is Tenhou rigged? Rebuild any wall from its seed

Nicolas ProProOct 2026 · 7 min read
Is Tenhou rigged? Rebuild any wall from its seed
Contents6

on the fourth tile of a fold, for the third time tonight, and the thought arrives on its own: this thing is rigged. Tenhou's answer sits at the of every game log you've ever opened. It's a 3,328-character string, and it's the seed the wall was built from.

Tenhou published the recipe that turns that string into tiles: sample code in 2009, a worked example with every intermediate number in 2016. Anyone can copy the seed out of a log, run the recipe, and compare the result with the hands that were dealt. This post does it with the game Tenhou uses as its own example. The rebuilt wall matched the log, tile for tile.

What Tenhou published, and when

On 13 July 2009 Tenhou's blog announced that wall generation would go fully public. The two things to be published were "the generation method and the random seed", so that a player could check from the log that nobody chose their and nobody touched the wall at a specific point in a hand. The post came with sample code. Tenhou keeps a copy at tenhou.net/stat/rand/sample_code.txt.

On 25 February 2016 it followed up with validation data: one real game, log ID 2016022509gm-0009-0000-b327da61, with the seed from that log and every intermediate number printed out, so anyone writing their own version can check each stage. Both documents hang off Tenhou's 牌山乱数 page, which also hosts the hash lists below.

The recipe, in plain words

The seed label says it all: mt19937ar-sha512-n288-base64. Unpacked, in the order Tenhou's code runs it:

  1. The seed. 624 numbers of 32 bits each, written out in base64. That's the 3,328 characters. They initialise one MT19937 generator, the "ar" version of the Mersenne Twister that takes an array as its seed, for the whole game.
  2. 288 numbers per hand. For each new hand the generator produces 288 numbers. That's the "n288".
  3. Hashing. Those 288 numbers are hashed with SHA-512 in nine blocks, which yields 144 fresh numbers.
  4. The shuffle. The 136 tiles start sorted, 1-man through . A Fisher-Yates shuffle walks the array once, swapping each position with one picked by the matching number. A comment in the code owns the only bias in the process: the modulo step is allowed an error of at most one part in 2^32, about one in four billion.
  5. The deal. The wall is dealt from the top of the array down. The sixth tile from the bottom is the indicator, and numbers 136 and 137 of the 144 are the dice.

Why 624 numbers: the ways to order 136 tiles run to a 233-digit figure, and the code's comment says the seed was sized to be "sufficiently larger than 136!".

Rebuild one yourself

  1. Open the raw log and copy everything after the comma in seed=.
  2. Feed it to an implementation of the recipe. The tenhou-shuffle crate is a public Rust one. Tenhou's pseudocode is short enough to port to Python in an evening, and the validation file tells you whether each stage is right.
  3. Compare. The top 52 tiles of your wall are the four starting hands on the log's INIT line, hai0 to hai3, dealt four at a time from the top. The 53rd is the 's first draw. The last number in INIT's own seed attribute is the indicator.

For the 2016 example game, a straight port of the pseudocode puts tiles 127, 119, 104, and 120 on top of the wall. In Tenhou's numbering that's , and the log's hai0 begins 127, 119, 104, 120. The first draw was . The dora indicator was , sitting sixth from the bottom of the array. The dice were 5 and 1. All of it matched for the first hand, from a string copied out of a log.

Tenhou didn't ask you to trust a statement. It handed you the seed and the recipe.

The hash list closes the last gap

A public recipe shows that the wall follows from the seed. On its own it doesn't show that the seed was fixed before anyone knew who'd be at the table. Tenhou's answer is the hash list on the 牌山乱数 page. For each ranked room and rule, and for the 雀荘戦 shop rooms, Tenhou posts a SHA-512 hash of each upcoming seed, refreshed every minute, up to 20 games ahead, with the consumed ones marked USED. In Tenhou's words, the seeds are decided before the game starts, before the table is reserved, before you log in, and they're used in order. Private lobbies and tournament lobbies aren't listed.

The check: open the list for the rule you're about to play and leave it open. Play. Compute the hash from your log and seat order, then find it in the list you opened beforehand. A hash can't be reversed into a wall, so nobody can peek at the tiles, and a seed can't be swapped after the fact without the hash changing. Tenhou's FAQ says one successful check is enough, since the method is public and covers every future game. The same FAQ adds that anyone who doubts that is welcome to check every time.

One limit, stated by Tenhou itself: a strict check uses the log file your own client saved during the game, which the paid Windows version can do, and Tenhou's own CGI checker doesn't count as strict. The logic is plain. A file written on your machine during play is the one thing the server can't edit later.

Tenhou's walls are made trustworthy by the same methods that secure traffic on the internet.
— tenhou.net, 牌山乱数 page, my translationShare quote

What "rigged" usually is

You remember the fourth tile of the fold. You don't remember the forty folds that went through clean.

Then there are the other three seats. In Path of Houou's sample of 5,626 players with 100 or more Houou hanchan, the average rate is 16.9%, about one hand in six. Three opponents at that rate put up three riichis for every one of yours, and some opponent is in riichi in about four hands out of ten (1 minus 0.831 cubed). The table feels ready before you because the table is three people and you're one.

Streaks look the same from the inside. A player who takes 1st 30% of the time goes five games without one 16% of the time. An intermediate with a 20% 4th-place rate takes three 4ths in a row about 1% of the time, so every regular has lived through several. Those figures are worked out in the losing streaks post.

The one thing on Tenhou that is stacked against you is printed in the rules. Within a room, the reward for 1st is the same at every (+90 in ) while the penalty for 4th grows with each . That's a design choice made in the open, and it shapes play more than any wall could.

What a verified shuffle doesn't prove

It proves the wall. It leaves three things alone.

Matchmaking. Who sits down with you is a separate system, and nothing on the 牌山乱数 page covers it. The seed is fixed before the seats, but the seating itself isn't part of the proof.

Other servers. Mahjong Soul publishes nothing comparable that I could find, in Japanese or English: no algorithm, no seed in the log, no hash list. That's an absence of evidence, not evidence of anything, and the burden sits with the server.

Physical tables. An automatic table doesn't run a Fisher-Yates shuffle. It mixes tiles mechanically, and mechanical mixing is imperfect. That's machinery, not luck.

So open your last log. Scroll to the first line and look at the seed. Then close it, paste the same replay link into the Tenhou log stats tool, and read your placement, wins, deal-ins, and riichi rate. Once the wall is accounted for, those are the only numbers left to argue with, and every one of them is yours.

Share this

0 shares

Was this article helpful?

Discuss on Discord
Keep reading

Similar posts

Newsletterニュースレター

Mahjong Newsletter On Its Way!

Want to hear whenever there's new mahjong content? Pre-subscribe to the upcoming newsletter and I will email you what you always wanted to know about Japanese mahjong before anybody else!