nagashibot+ theory

2009-05-01

nagashibot+ is a series of nagashibot, a family of Tenhou robots (actually just rushed perl scripts), that exploited a critical bug to become more or less unbeatable; in about 30 games it never placed 4th in a single one. The bug is now resolved, so it is fine to talk about how nagashibot+ worked.

Tenhou's protocol controls calls by prompting with arguments to tile discard commands. For example, <F117/> is a regular xia discard (cut, throw, etc.) by the opposite player (all draw/discard commands are relative to the player's position on the table, not the player winds). However, if you have two more xia in your hand, the command would instead be <F117 t="1"/>. The t argument I refer to as the prompt, since the server expects applicable players to respond with their own action when it is present. If a player could pon or (for example) ron on a particular tile, the two prompt IDs are then ORed together (i.e. a|b) and counted as one value. Note that not all players will get the exact same prompt ID (if any), since the server gives the prompt ID for the player it is sending it to and not generally. (In fact, they never will anyway because of the relativity of the draw/discard command names.)

With that in mind, consider the following table:

PromptTypeResponse
allpass 0
1 pon 1
2 kan 2, 4 (closed), 5 (extended)
4 chii 3
8 ron 6
16 tsumo 7
32 riichi <REACH .../> (never actually prompted)
64 ryuukyoku 9 (yao9 only)
128nuki 10 (never actually prompted)

The responses above were the ones actually observed. The critical thing here, however, is how calls (including passing and stuff) are actually made. Those with actual numbers for the response are sent as <N type="x"/>, x being the number seen in the table (response ID? sure). All the types of calls are made this way as you can see from the table, except for riichi, which uses the REACH command instead, because there are two phases/steps to it technically. On its own that is not very interesting, but note the trend of response IDs; 0, 1, 2, ..., 10, except 8, which would logically go where REACH is used instead. Given how the other commands go, you would assume <N type="8"/> for so called riichi actions, except that this is never actually observed.

Now, I wanted to try this rather eagerly for some reason, so rather than fiddling around trying to get a 32 prompt from the server, I just modified nagashibot's code to send it rather than discarding a tile to see what would happen. I assumed the server would kick the player immediately as it does if you send it other illegal response IDs (>10), but instead, the bot just kept the tile and the turn shifted to the next player. That is, it ended its first turn with 14 tiles in its hand. Next round 15, then 16, 17, and so on until the tiles just go off the screen. Already this meant that the bot could not be ronned or called from (because it throws no tiles), but the best part came at the end of the round when no other players had made any hands: the bot got a nagashi mangan, living up to the filename I didn't put any thought into at the time, nagashibot+.pl.

So, I promptly emailed Tenhou about the bug because it was such a big one and I wanted to be the first to tell them or something. I then set up a bot that would constantly join games and just do that, to run in L0000. I ran it in total probably only about 10-15 hours, in which time it completed about 30 games on a freshly registered ID (無双ロイド, or musou roido to be misleading). In about that many games, it had achieved 3kyuu and R1900 (thereabouts). Such a simple exploit led to be indeed very critical.

But then I got a reply from Tenhou, and now I regret ever emailing them about the exploit in the first place, because seeing the results was just too fun.


From: C-EGG Support <support@c-egg.com>
To: <>

Thank you point out the bug.
We just fixed!
______________________________________________
有限会社シー・エッグ
C-EGG Software ( http://www.c-egg.com/ )
角田 真吾 / Shingo Tsunoda


----- Original Message ----- From: <>
To: <support@c-egg.com>
Sent: Saturday, March 14, 2009 3:46 PM
Subject: Tenhou Bug (<N type="8"/>)


> Greetings!
>
> I'm just mailing you to point out a little bug; if you send a
> <N type="8"/> command then you will skip your turn and keep the tile,
> like in this image: http://arcturus.su/~alvin/img/misc/tenhouwhat.png
>
> Alvin

They fixed it, and nagashibot+ was then kicked whenever an <N type="8"/> command was sent.

nagashibot+ RIP
2009-03-14 ~ 2009-03-17


Index Top
Last updated: 2009-05-01