Running `mawk 'BEGIN {print rand()}'` on Debian Trixie on arm64,
produces the same results. It is expected (and documented) that srand()
is called implicitly. And on Bookworm or on amd64, this works as
expected. Easy to reproduce using docker:
```
$ docker run -it --rm --platform linux/arm64 debian:trixie sh -c 'for i in 1 2 3 4; do mawk "BEGIN {print rand()}"; sleep 1; done'
0.118709
0.118709
0.118709
0.118709
```
```
$ docker run -it --rm --platform linux/amd64 debian:trixie sh -c 'for i in 1 2 3 4; do mawk "BEGIN {print rand()}"; sleep 1; done'
0.301452
0.968917
0.975551
0.0758413
```
```
$ docker run -it --rm --platform linux/amd64 debian:bookworm sh -c 'for i in 1 2 3 4; do mawk "BEGIN {print rand()}"; sleep 1; done'
0.133928
0.991352
0.852069
0.211199
```
```
$ docker run -it --rm --platform linux/arm64 debian:bookworm sh -c 'for i in 1 2 3 4; do mawk "BEGIN {print rand()}"; sleep 1; done'
0.5202
0.878447
0.73942
0.956202
```
I see the problem.
Initially I assumed that the initial_seed function is returning
values that are much less than Max_UInt, and since they're close
together, the fmod gives the same result:
(with inactive ifdef's removed):
static double
initial_seed(void)
{
double result;
struct timespec data;
if (clock_gettime(CLOCK_REALTIME, &data) == 0)
result = (((double) data.tv_sec * 1e9) + (double) data.tv_nsec);
else
result = 0.0;
return result;
}
double seed32;
...
cseed.dval = initial_seed();
...
seed32 = fmod(cseed.dval, (double) Max_UInt);
srandom((unsigned) seed32);
Max_UInt is a 64-bit number, while unsigned is not.
However, the actual problem is this:
With my aarch64 machine, the unsigned cast on seed32 gives 0xffffffff,
(in the call to srandom) while it does not with x86_64
Changing that to a 32-bit value, e.g., UINT_MAX
seed32 = fmod(cseed.dval, (double) 0xffffffff);
makes it work.
I see the problem.
Initially I assumed that the initial_seed function is returning
values that are much less than Max_UInt, and since they're close
together, the fmod gives the same result:
(with inactive ifdef's removed):
static double
initial_seed(void)
{
double result;
struct timespec data;
if (clock_gettime(CLOCK_REALTIME, &data) == 0)
result = (((double) data.tv_sec * 1e9) + (double) data.tv_nsec);
else
result = 0.0;
return result;
}
double seed32;
...
cseed.dval = initial_seed();
...
seed32 = fmod(cseed.dval, (double) Max_UInt);
srandom((unsigned) seed32);
Max_UInt is a 64-bit number, while unsigned is not.
However, the actual problem is this:
With my aarch64 machine, the unsigned cast on seed32 gives 0xffffffff,
(in the call to srandom) while it does not with x86_64
Changing that to a 32-bit value, e.g., UINT_MAX
seed32 = fmod(cseed.dval, (double) 0xffffffff);
makes it work.