La cuarta entrada
Toda explicación del juego provably fair, incluida la nuestra, nombra tres entradas: un server seed que la casa se compromete a revelar por adelantado, un client seed que puedes establecer tú mismo, y un nonce que sube en uno con cada apuesta. Alimenta estos a un hash con clave y sale la aleatoriedad de la ronda. Esa descripción es completa para un volado. Es incompleta para casi todo lo demás, porque un hash produce un número y la mayoría de juegos necesitan varios.
La cuarta entrada es el cursor. En este sitio el mensaje que se hashea no es "client seed-nonce" sino "client seed-nonce-cursor", y el cursor es un contador dentro de la ronda: 0 para el primer número aleatorio que el juego necesita, 1 para el segundo, y así sucesivamente. Cada valor de cursor da un digest de 256 bits nuevo, sin relación con sus vecinos de ninguna forma que puedas explotar, y el motor lee los primeros ocho bytes de cada digest como un número entre 0 y 1.
ENGINE-VERIFIED_shared/demoLocal.ts: uAt(pair, cursor) devuelve u64(HMAC-SHA256(serverSeed, `${clientSeed}-${nonce}-${cursor}`)), descrito como coincidente con el RandomUtils.generateHash("clientSeed-nonce-cursor") del servidor. _shared/rng.ts: u64 lee los primeros ocho bytes del digest como hi/2^32 + lo/2^64, "la misma construcción de una sola ronda" que la conversión ULong→Double del servidor. El nonce es una secuencia por par de seeds en todos los juegos: cada apuesta consume el nonce actual y almacena nonce + 1.
Así que una ronda no es un número aleatorio sino una lista numerada de ellos, tan larga como el juego necesite, y cada entrada en la lista se fija en el instante en que el par de seeds y el nonce son. El juego no extrae mientras avanza. Lee una lista que ya existe.
Qué lee cada juego
La parte interesante es que la lista es diferente para cada juego, y cada módulo de derivación indica su disposición en su encabezado. Aquí está la secuencia de cursor de cada original que extrae del par de seeds, tomado del código fuente del motor.
| JUEGO | CURSORES LEÍDOS | EN QUÉ SE CONVIERTEN |
|---|---|---|
| Limbo | 0 | Un número a través de la curva 0.99 ÷ (1 − u) |
| Ruleta | 0 | El bolsillo: floor(u × 37) |
| Fukubukuro | 0 | El artículo, contra la tabla de pesos de la bolsa |
| Sic Bo | 0, 1, 2 | Los tres dados |
| Chinchiro | lado × 9 + intento × 3 + dado | Hasta 18: distribuidor luego jugador, hasta tres tiradas de tres dados cada una; una tirada que forma una mano termina el lado |
| Koban Flip | uno por volteada | La volteada i lee el cursor i; cada cara del viaje se fija cuando se compra la primera moneda |
| Omikuji | 0, luego 1–3, luego 4 en adelante | Nivel de fortuna; las tres celdas ganadoras en una victoria; glifos de relleno para el resto |
| Pagoda | uno por piso | La casilla trampa en cada piso: floor(u × fichas) |
| Video Poker | 5, más uno por carta reemplazada | Una secuencia sin reemplazo sobre 52 cartas; mantener todo y no se lee ningún cursor adicional |
| Casino Hold'em | hasta 9 | jugador 1, jugador 2, crupier 1, crupier 2, flop 1–3, turn, river; el turn y river solo se leen en CALL |
| Blackjack | uno por carta | Zapata infinita, carta = floor(u × 52), en orden de reparto: jugador, crupier visible, jugador, crupier oculta, luego cada extracción posterior |
| Andar Bahar | 0–4, luego uno por carta enfrentada | Dos cubetas potenciadas, sus magnitudes, el comodín, luego la carrera hasta que se repite el rango |
| Hanabi | 15 por giro | Celda = carrete × 3 + fila; giro gratis j lee 15 + 15j en adelante |
| Bingo | 0–24, luego 25–62 | La carta, cinco extracciones por columna; luego las 38 bolas |
Keno y Crash son las excepciones: sus rondas demo usan una cadena hash por boleto en lugar del nonce de par de semillas, descrito abajo. Mines y Plinko se resuelven por el servicio de la casa; la API de mines señala que toda la disposición surge de un único nonce.
ENGINE-VERIFIEDHeader comments in bingo/derive.ts (“Cursor stream: 0..24 — the card … 25..62 — the 38 balls”), hanabi/engine.ts (“base spin = cells 0..14 … free spin j = cells 15+15j .. 29+15j”), blackjack/derive.ts (“card i = floor(u × 52) at cursor i … Deal order (cursor): player1, dealer-up, player2, dealer-hole”), vpoker/derive.ts (“the first five are the deal, replacements continue the same sequence … Hold everything and no further cursor is read”), holdem/derive.ts (“player1, player2, dealer1, dealer2, flop1, flop2, flop3, turn, river. The turn/river cursors are only consumed on CALL”), andar/derive.ts (cursors 0–4 then “5.. one cursor per raced card”), koban/derive.ts (“flip i reads cursor i”), sicbo/derive.ts (“cursors 0/1/2 are the three dice”), roulette/derive.ts (“cursor 0 alone decides the pocket: floor(u × 37)”), fuku/derive.ts (“cursor 0 alone draws the item”), omikuji/derive.ts (cursor 0 tier, 1..3 winning cells, 4.. fillers); demoLocal.ts rollSide (chinchiro cursor = side*9 + attempt*3 + d), trapAt (pagoda: the floor number is the cursor), demoLimboBet (uAt(p, 0)); mines/minesApi.ts (“the whole mine layout comes off this one nonce”).
Tres cosas destacan en esa tabla. Primero, los juegos que reparten cartas leen un cursor por carta en un orden fijo, por eso una mano de blackjack puede replicarse desde su lista de acciones: tu decisión de pedir carta no crea una carta, revela la siguiente en una lista que estaba completa antes del reparto. Segundo, varios juegos dejan de leer antes. Una mano de video póker donde mantienes las cinco cartas nunca toca el cursor 5; un fold en Hold'em nunca lee el turn o river. Los números estaban ahí; el juego no los necesitaba. Tercero, las dos cubetas potenciadas en Andar Bahar y el tier de fortuna en Omikuji se extraen antes que las cartas y celdas, al inicio del flujo, así que las características especiales de la ronda se fijan por el mismo compromiso que las ordinarias.
Extracción sin reemplazo
Un número uniforme entre 0 y 1 es fácil de convertir en una casilla de ruleta: multiplica por 37 y redondea hacia abajo. Una baraja es más difícil, porque la segunda carta no debe ser la primera carta de nuevo. El motor lo maneja con lo que sus comentarios llaman un pool hop: mantén una lista de las cartas aún en el pool, usa el número del cursor para elegir una posición en ella, e intercambia la carta elegida al final de la lista para que la siguiente extracción elija de una menos. Video Poker, Casino Hold'em, Andar Bahar y la carta de Bingo se extraen de esta forma, así que ninguna carta o número se repite dentro de una ronda.
Blackjack es la excepción deliberada. Su zapata es infinita: cada carta es floor(u × 52) desde su propio cursor, y la misma carta puede aparecer dos veces en una mano. Es una decisión de diseño con un costo publicado, discutido en el artículo de payout de blackjack, y es exactamente el tipo de cosa que la disposición de cursores te dice que una página de marketing no haría.
ENGINE-VERIFIEDvpoker/derive.ts: “Cards come from ONE without-replacement sequence over the 52-card deck (pool-hop, cursor per draw)”. holdem/derive.ts: “ONE without-replacement pool-hop sequence (cursor per draw)”. bingo/derive.ts: “five pool-hop draws per column” and “the 38 balls, pool-hops over 1..75”. blackjack/derive.ts: “Infinite shoe: card i = floor(u × 52) at cursor i”.
Las dos excepciones
Keno y Crash no leen el nonce del par de semillas en absoluto en el motor demo. Keno utiliza un esquema por ticket: cada ticket obtiene su propio hash aleatorio y una salt, y cada una de las diez bolas se extrae hasheando el hash anterior nuevamente, tomando los bits iniciales como un número y eligiendo del pool menguante de cuarenta. El panel de fairness verifica un ticket de keno a partir de esas dos cadenas en lugar del par de semillas. Crash sigue la convención bustabit, una cadena de hashes donde el crash point de cada ronda se calcula a partir de su propio enlace con aritmética entera exacta.
ENGINE-VERIFIEDdemoLocal.ts kenoDraws: “per-bet randomHash chain + salt (verifiable per ticket via the fairness modal) … Does not touch the seed-pair nonce”; the loop hashes HMAC-SHA256(salt, previous hash) ten times, reads the leading 52 bits and picks index floor(norm × remaining) from a 40-number pool with a swap to the end. rng.ts h52 and the crash comment: “bustabit crash point in hundredths: floor((n·e − h)/(e − h)), e = 2^52, n = 100 … Exact BigInt math to match the server”.
Ninguna excepción es más débil que el esquema del cursor; ambas son más antiguas y más conocidas. Lo que importa para un jugador es solo que el panel muestre qué esquema utilizó una ronda, y que cada uno pueda recomputarse a partir de las cadenas que muestra.
Qué significa en la mesa
- La ronda existe antes de que actúes. Cada carta, bola y símbolo de carrete de una ronda es una función del par de semillas, el nonce y su posición de cursor. Golpear, cantar o mantener elige qué entradas se leen, no lo que contienen.
- Tus elecciones no pueden cambiar la lista, y tampoco la casa. Una vez que la semilla del servidor está comprometida y el nonce está fijo, nadie de ninguno de los lados puede alterar la entrada 7 sin alterar la semilla, lo que rompería la huella digital que te mostraron.
- Un verificador tiene que leer la misma lista de la misma manera. Recomputar una ronda de bingo significa derivar los 63 cursores en el orden publicado; recomputar un fold de Hold'em significa derivar 7. El panel de semilla hace esto en tu navegador, y los layouts en la tabla anterior son los que sigue.
- Una racha es una lista, no un sentimiento. Dos rondas no comparten nada excepto el par de semillas; sus nonces difieren y así cada digest difiere. Este es el mismo punto que el artículo de hot hand plantea desde la otra dirección.
Tres inputs deciden la ronda. El cuarto decide cuánto tiempo dura la ronda.el cursor, en una línea
Los layouts del cursor anterior se leen de los módulos de derivación del lado del cliente que comparten el verificador del navegador y el motor demo. El servicio de la casa es la autoridad pagadora; cuando un comentario en el código fuente dice que un módulo refleja el servidor, eso se cita tal como está escrito, no certificado por nosotros.
FAQ
¿Qué es el cursor en una ronda provably fair?
Un contador dentro de la ronda. El mensaje hasheado con la semilla del servidor es "client seed-nonce-cursor"; cursor 0 da el primer número aleatorio que necesita el juego, cursor 1 el segundo, y así sucesivamente. Un juego que necesita un número lee solo cursor 0.
¿En qué se diferencia el cursor del nonce?
El nonce cuenta rondas y sube de uno en uno con cada apuesta en cada original. El cursor cuenta extracciones dentro de una ronda y se reinicia en 0 cada ronda. Junto con el par de semillas identifican cada número aleatorio que el sitio produce.
¿Cuántos números aleatorios utiliza una ronda de bingo?
Sesenta y tres: cursores 0 a 24 distribuyen las 25 celdas de la tarjeta y cursores 25 a 62 extraen las 38 bolas, todo sin reemplazo dentro de sus pools.
¿Golpear en blackjack cambia la siguiente carta?
No. Cada carta se deriva de su propio cursor en el orden de reparto, y la lista completa existe una vez que se fijan el par de semillas y el nonce. Golpear lee la siguiente entrada; plantarse la deja sin leer.
¿Todos los juegos usan el esquema de cursor?
Keno y Crash usan cadenas hash en su lugar: keno hashea un hash aleatorio por ticket y salt diez veces, y crash sigue la cadena bustabit con aritmética de enteros exacta. El panel de imparcialidad verifica cada uno desde las cadenas que muestra.
FUENTES Y REFERENCIAS
- Código del motor Betkyo: _shared/demoLocal.ts (uAt, rollSide, trapAt, kenoDraws), _shared/rng.ts (u64, h52, crash point), y los módulos de derivación para bingo, hanabi, blackjack, vpoker, holdem, andar, koban, sicbo, roulette, fuku y omikuji
- RFC 2104 — HMAC: Keyed-Hashing for Message Authentication
- Esquema provably fair de Bustabit (la construcción crash-point que el motor replica)
LOS JUEGOS EN ESTE ARTÍCULO
Blackjack — reglas y juego gratis →Bingo — reglas y juego gratis →Sic Bo — reglas y juego gratis →