It looks like Furey wrote a random-number generator for Merc based on an algorithm from Knuth. When Alander wrote ROM, he said he noticed streakiness in the Furey-written RNG and reverted to the POSIX system function random() while seeding it using srandom() with a seed of a bitwise XOR of the time_t long and the program's PID. The relevant bits are below:
/*
* I've gotten too many bad reports on OS-supplied random number generators.
* This is the Mitchell-Moore algorithm from Knuth Volume II.
* Best to leave the constants alone unless you've read Knuth.
* -- Furey
*/
/* I noticed streaking with this random number generator, so I switched
back to the system srandom call. If this doesn't work for you,
define OLD_RAND to use the old system -- Alander */
#if defined (OLD_RAND)
static int rgiState[2 + 55];
#endif
void init_mm ()
{
#if defined (OLD_RAND)
int *piState;
int iState;
piState = &rgiState[2];
piState[-2] = 55 - 55;
piState[-1] = 55 - 24;
piState[0] = ((int) current_time) & ((1 << 30) - 1);
piState[1] = 1;
for (iState = 2; iState < 55; iState++)
{
piState[iState] = (piState[iState - 1] + piState[iState - 2])
& ((1 << 30) - 1);
}
#else
srandom (time (NULL) ^ getpid ());
#endif
return;
}
long number_mm (void)
{
#if defined (OLD_RAND)
int *piState;
int iState1;
int iState2;
int iRand;
piState = &rgiState[2];
iState1 = piState[-2];
iState2 = piState[-1];
iRand = (piState[iState1] + piState[iState2]) & ((1 << 30) - 1);
piState[iState1] = iRand;
if (++iState1 == 55)
iState1 = 0;
if (++iState2 == 55)
iState2 = 0;
piState[-2] = iState1;
piState[-1] = iState2;
return iRand >> 6;
#else
return random () >> 6;
#endif
}
/*
* Generate a random number.
*/
int number_range (int from, int to)
{
int power;
int number;
if (from == 0 && to == 0)
return 0;
if ((to = to - from + 1) <= 1)
return from;
for (power = 2; power < to; power <<= 1);
while ((number = number_mm () & (power - 1)) >= to);
return from + number;
}