Secrets v0.1.0

Source
Comparing secrets in constant time and wiping them so the compiler cannot skip it.

Equal

pub func Equal(left: char8[..], right: char8[..]) -> bool

Whether two byte sequences are equal, in time that does not depend on where they differ. The ordinary comparison returns at the first difference, so its duration reveals the length of the matching prefix. Against a message authentication tag that is enough to find the correct tag one byte at a time -- a few thousand attempts rather than the number the tag's length suggests. This reads every byte of both sequences whatever it finds, accumulating differences rather than branching on them. Sequences of different lengths are unequal, and that answer is immediate: a length is not a secret, and pretending otherwise would mean reading past one of them.

Source

Parameters

NameTypeDescription
leftchar8[..]one of the two byte runs
rightchar8[..]the other

Returns: whether the two runs match, compared in time that does not depend on where they differ

Wipe

pub func Wipe(bytes: var char8[..])

Overwrites bytes with zeros in a way the compiler may not remove. A plain loop clearing a buffer nothing reads afterwards is dead code, and an optimizer is entitled to delete it — which is how a key a program believed it had erased stays in memory, in a core dump, or in a page written to swap. The barrier below is handed the buffer's address and its body is opaque, so the writes must have happened before it runs and the call cannot be dropped.

Source

Parameters

NameTypeDescription
bytesvar char8[..]the bytes to clear