Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Secure random documentation #32957

Closed
wants to merge 1 commit into from
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions stdlib/Random/docs/src/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,11 @@ unbounded integers, the interval must be specified (e.g. `rand(big.(1:6))`).
Additionally, normal and exponential distributions are implemented for some `AbstractFloat` and
`Complex` types, see [`randn`](@ref) and [`randexp`](@ref) for details.

!!! note
The `MersenneTwister` used by unqualified `rand` or `randstring` calls is not suitable for
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It may be not clear for everyone what is meant by "unqualified" here, what about:

The MersenneTwister object used implicitly by unqualified rand or randstring calls is ...

applications where cryptographically secure random numbers are required, as for example
session keys in web applications or nonces in network protocols.

## Random numbers module
```@docs
Random.Random
Expand Down Expand Up @@ -66,6 +71,18 @@ Random.MersenneTwister
Random.RandomDevice
```

## Cryptographically secure random numbers

The Julia standard library does not provide a native cryptographically secure random number generator. For most applications,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

By "native", you mean written in Julia? I find it's easy to interpret this sentence as "you can't get CSPRNG" from the Random module, which seems to be contradicted in the next sentence...

we recommend to use the operating system `RandomDevice()`. This should be initialized via a module-level
`const SECURE_RANDOM = Random.RandomDevice()` and subsequently used via e.g. `gen_nonce() = rand(SECURE_RANDOM, UInt128)`.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only by the name SECURE_RANDOM we can infer that indeed RandomDevice is secure, it should be stated explicitly.


It is important to initialize the `RandomDevice()` on the module level, and not use e.g.
`bad_gen_nonce() = rand(Random.RandomDevice(), UInt128)`, in order to not cause performance degradation and an eventual
`ERROR: SystemError: opening file "/dev/urandom": Too many open files`.

The `RandomDevice` reads and caches `/dev/urandom` on Unix-derived systems, and uses appropriate `Ntsecapi.h` calls on Windows.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will trust you on this fact concerning Windows, but I infer from the name of the file that it's a CSPRNG?


## Hooking into the `Random` API

There are two mostly orthogonal ways to extend `Random` functionalities:
Expand Down