@doc `~rac@1.0' (Ratcheting Authenticated Channels) provides ordered,
exactly-once, replay-resistant messaging between AO processes.

It is often necessary for an AO process to consume a stream of authenticated
messages -- events, or state updates -- from another process, applying each
at most once and in a well-defined order. `~rac@1.0' addresses this by
numbering messages rather than identifying them. A sender assigns each
message a monotonic `slot' on a named `channel'; a recipient maintains a
per-sender `ratchet' and admits a message only when its slot satisfies the
channel's ingest rule, rejecting replays and mis-ordered delivery.

== Channels, slots, and the ratchet ==

A `channel' is a named, unidirectional stream from a sending process to a
receiving process. Channels are independent and their slots begin at `0'.
The sender records the highest slot it has emitted on each channel and
stamps the next slot onto each outbound message. The recipient records the
highest slot it has admitted from each sender on each channel -- the
`ratchet' -- and advances it as messages are admitted.

== State ==

```
base/rac-outbound/<address>/<channel>:  Highest slot this process has sent
    to <address> on <channel>. Absent => -1; the next slot emitted is 0.
base/rac-inbound/<address>/<channel>:   Highest slot this process has
    admitted from <address> on <channel> (the ratchet). Absent => -1.
message/rac-slot:     The channel slot this message occupies.
message/rac-channel:  The channel name. Absent => `default'.
message/rac-ratchet:  The ingest rule (see `compute'). Absent => `false'.
'''

`<address>' is the counterparty's process identifier: on the sending side,
the recipient's address; on the receiving side, the sender's address, taken
from the inbound message's `from-process' field (established by `~push@1.0',
and not settable by the sending process's own logic). `rac-outbound' and
`rac-inbound' are the only state this device introduces.

== Keys ==

`send': Emit `body' to `recipient' on a channel, stamping it with the
channel's next slot and appending it to the process outbox for delivery.

```
send:
    recipient:  Address    (required) destination process.
    body:       Message    (required) the message to send.
    channel?:   Binary     channel name (default `default').
    ratchet?:   false | true | Integer  ingest rule to stamp on the message
                                         (default `false'); see `compute'.
'''

`send' sets `rac-slot' to `rac-outbound/<recipient>/<channel> + 1' (a
missing counter is `-1', so the first slot is `0'), stamps the outbound
message with `rac-slot' and `target = recipient' (plus `rac-channel' /
`rac-ratchet' when non-default), appends it to `results/outbox', and
advances the outbound counter. Delivery, provenance (`from-process'), and
re-signing to the recipient's policy are performed by `~push@1.0';
`~rac@1.0' only stamps and enqueues.

`compute': Admit or reject one inbound message according to its channel's
ingest rule, advancing the ratchet on admission. Intended to run once per
assigned message, ahead of application logic. It is `~multipass@1.0'-aware,
mirroring `~dedup@1.0': it acts only on the first pass and returns the base
unchanged on later passes. The inbound message is the request's `body', from
which `compute' reads `rac-slot', `rac-channel' (default `default'),
`rac-ratchet' (default `false'), and the sender (`from-process', or the
message's first committer if absent). Untagged traffic (no `rac-slot')
passes through unmodified. With `Ratchet = rac-inbound/<sender>/<channel>'
(absent => -1) and `Slot = rac-slot', the message is admitted iff:

```
rac-ratchet     Admit when                    Semantics
false (default) Slot == Ratchet + 1           strict, in-order, exactly-once
true            Slot > Ratchet                ratchet forward to any later slot
integer N       Slot > Ratchet and Ratchet >= N   ratchet forward once at N
'''

On admission `compute' sets `rac-inbound/<sender>/<channel> = Slot' and
returns `{ok, Base}'; on rejection it returns `{skip, Base}' -- state is
unchanged and, in a stack, no subsequent device runs for the message.

== Usage ==

`~rac@1.0' may be placed in a process's execution stack ahead of the
application device (a `{skip, ...}' from `compute' halts the stack for that
message), or a custom execution device may resolve `compute' against
`{as, ~rac@1.0, Base}' before its own logic, treating `skip' as rejection.
Senders resolve `send' against `{as, ~rac@1.0, Base}' from within compute.
`rac-ratchet = false' gives ordered, exactly-once event ingest; `true' or an
integer gives last-writer-wins state synchronization that tolerates gaps.