[m-rev.] time additions (was Re: for review: Add random.init/3)

Julien Fischer jfischer at opturion.com
Thu May 26 13:56:02 AEST 2016


Hi Sebastian,

On Thu, 26 May 2016, Sebastian Godelet wrote:

> Note that .NET and Delphi's System.DateTime record are also using
> double precision floating point numbers to represent time, I also
> don't see anything wrong with this. As long as the precision is the
> same for every platform.  I wish that Mercury would expose true 32-bit
> and 64-bit integers (from C99 for example)

I've written a library that does this (<https://github.com/juliensf/mercury-inttypes>)
for the C, C# and Java backends.  However, the lack of literals for each
type of integer does make using it a bit fiddly.

> and double and single precision floating point number types, at least
> expose it to the C foreign interface.  The former would make the hash
> calculation functions platform independent for one thing.

...

>>> 4. Seed the PRNG using something other than time, for example:
>>>
>>>     :- pred generate_random_int(int::out, io::di, io::uo) is det.
>>>
>>> and generate the int using /dev/random (on Unix) or CryptGenRandom (on
>>> Windows), or whatever the appropriate OS / platform specific source of
>>> randomness is.  (Most OSs -- and certainly the ones that Mercury
>>> actually runs on -- will provide something along those lines.)
>>
>> That would be useful, too.
>
> A cryptographically secure random number generator would be really useful.
> I would prefer a more fine-grained interface though,
>
> acquire_random_source(source::uo, io::di, io::uo) is det.
>  Windows: CryptAcquireContext(*Source, nil, MS_ENHANCED_PROV,
>                             PROV_RSA_FULL, CRYPT_VERIFYCONTEXT);
>  POSIX: Source = fopen("/dev/urandom", "r");
>
> generate_random_int(source::in?, int::out, io::di, io::uo) is det.
>
> release_random_source(source::uo, io::di, io::uo) is det.
>  Windows: CryptReleaseContext(Source, 0);
>  POSIX: fclose(Source);

The ultimate problem here is that Mercury's current random and time
modules are simply not very good.  For random, what the standard library
*should* be providing is a generic interface to random number generators
in general (e.g. something along the lines of Boost.Random, but using
type classes), along with some actual instances of generators.  I find
the current time module a bit too C-like, also it's not terribly well
integrated with the calander module.

> Not sure about the IO threading though

You'll need it if you want to maintain purity -- on my system
(OS X) /dev/random is backed by an entropy pool that is refreshed
every so often by the OS, that's very much an I/O operation.
(See 'man 4 random' on OS X for details.)

Julien.


More information about the reviews mailing list