rng.c (767B)
1 /* rng.c - PCG32 (O'Neill). Determinista y portable. */ 2 #include "rng.h" 3 4 uint32_t rng_next(Rng *r) 5 { 6 uint64_t old = r->state; 7 r->state = old * 6364136223846793005ULL + r->inc; 8 uint32_t xs = (uint32_t)(((old >> 18u) ^ old) >> 27u); 9 uint32_t rot = (uint32_t)(old >> 59u); 10 return (xs >> rot) | (xs << ((-rot) & 31)); 11 } 12 13 void rng_seed(Rng *r, uint64_t seed, uint64_t seq) 14 { 15 r->state = 0; 16 r->inc = (seq << 1u) | 1u; 17 rng_next(r); 18 r->state += seed; 19 rng_next(r); 20 } 21 22 /* Sin sesgo: descarta el rango que no divide parejo. */ 23 uint32_t rng_below(Rng *r, uint32_t n) 24 { 25 if (n <= 1) return 0; 26 uint32_t threshold = (uint32_t)(-n) % n; 27 for (;;) { 28 uint32_t x = rng_next(r); 29 if (x >= threshold) return x % n; 30 } 31 }