From: Vincent Bernat Date: Wed, 10 Dec 2014 09:31:37 +0000 (+0100) Subject: BUG/MEDIUM: sample: fix random number upper-bound X-Git-Tag: v1.6-dev1~246 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=1228dc0e7ae4a6b16c0c7f74a28f8e84601b526c;p=thirdparty%2Fhaproxy.git BUG/MEDIUM: sample: fix random number upper-bound random() will generate a number between 0 and RAND_MAX. POSIX mandates RAND_MAX to be at least 32767. GNU libc uses (1<<31 - 1) as RAND_MAX. In smp_fetch_rand(), a reduction is done with a multiply and shift to avoid skewing the results. However, the shift was always 32 and hence the numbers were not distributed uniformly in the specified range. We fix that by dividing by RAND_MAX+1. gcc is smart enough to turn that into a shift: 0x000000000046ecc8 <+40>: shr $0x1f,%rax --- diff --git a/src/sample.c b/src/sample.c index 0ffc76daf3..00345a8940 100644 --- a/src/sample.c +++ b/src/sample.c @@ -1824,7 +1824,7 @@ smp_fetch_rand(struct proxy *px, struct session *s, void *l7, unsigned int opt, /* reduce if needed. Don't do a modulo, use all bits! */ if (args && args[0].type == ARGT_UINT) - smp->data.uint = ((uint64_t)smp->data.uint * args[0].data.uint) >> 32; + smp->data.uint = ((uint64_t)smp->data.uint * args[0].data.uint) / ((u64)RAND_MAX+1); smp->type = SMP_T_UINT; smp->flags |= SMP_F_VOL_TEST | SMP_F_MAY_CHANGE;