An immutable replay window for connectionless transports.
Applications own this value and store it alongside their session. Check an
incoming nonce before authentication with check/2, then replace the stored
window with the result of commit/2 only after Decibel.decrypt/3 succeeds.
The module holds no process, ETS, or hidden session state.
A window of size size retains exactly size nonce positions. After the
first commit, those positions run from highest down to
highest - size + 1; highest - size is the first stale value. Internally,
bit i in the bitmap records nonce highest - i.
Applications must serialize session operations with updates to their replay
window. Sharing an old value between concurrent operations can allow both to
pass check/2 before either commits.
Summary
Functions
Checks whether nonce is eligible for authentication.
Commits a nonce after successful authentication.
Creates an empty replay window.
Types
Functions
@spec check(t(), Decibel.usable_nonce()) :: :ok | {:error, :duplicate | :stale}
Checks whether nonce is eligible for authentication.
Returns :ok for a new nonce, {:error, :duplicate} for an already
committed nonce still inside the window, or {:error, :stale} for a nonce
below the window. The window is not changed.
A value outside Decibel.usable_nonce/0 raises ArgumentError.
@spec commit(t(), Decibel.usable_nonce()) :: t()
Commits a nonce after successful authentication.
Returns a new window. A nonce that check/2 classifies as duplicate or stale
raises ArgumentError, because committing it indicates a caller error. A
value outside Decibel.usable_nonce/0 also raises ArgumentError.
@spec new(pos_integer()) :: t()
Creates an empty replay window.
The default window size is 64. An explicit size must be a positive integer;
invalid sizes raise ArgumentError.