pub struct RuntimeConfig {Show 16 fields
pub limits: Limits,
pub max_connections: usize,
pub max_connections_per_peer: usize,
pub endpoint_queue: usize,
pub max_resolved_addresses: usize,
pub worker_threads: usize,
pub shutdown_timeout: Duration,
pub guarantees: GuaranteeSet,
pub discovery: Discovery,
pub resolver: SharedResolver,
pub connect_attempt_timeout: Duration,
pub reconnect: ReconnectPolicy,
pub send_timeout: Option<Duration>,
pub outbox_messages: usize,
pub outbox_bytes: usize,
pub outbox_full: OutboxFull,
}Expand description
Configuration for one crate::Runtime.
Fields§
§limits: LimitsResource limits applied to every connection this runtime owns or accepts.
One profile, not yet one per connection tier: the control tier of
docs/decisions/0002-control-and-bulk-separation.md §6.3 does not
exist in the code yet, and a second profile nothing reads would be
worse than none.
max_connections: usizeConcurrently accepted connections per binding. Excess connections are
closed immediately with LIMIT_EXCEEDED.
Per binding rather than per connection, which is why it is here and
not in Limits.
max_connections_per_peer: usizeConnections one peer may hold on one binding at once, counted by the fingerprint it proved.
One connection per dialled endpoint path means the dialling side
chooses how many connections it opens, so max_connections alone
would let a single peer fill a binding: 64 connections to one peer
measured about 50 MiB of transport state on the pair
(docs/IMPLEMENTATION.md §4, B-011), and the default of 64 is that
measured number — enough for a control connection plus 63 dialled
paths, and a sixteenth of the default max_connections.
Counted per proved fingerprint. Connections that proved no
identity are each their own peer and are bounded only by
max_connections, because two anonymous connections cannot be shown
to be one peer (PROTOCOL.md §2.5,
docs/decisions/0008-session-identity.md §4.2). A binding that wants
this bound therefore requires a client identity.
endpoint_queue: usizeDepth of an endpoint’s accept queue. Senders await a free slot, so QUIC flow control carries the backpressure to the peer.
max_resolved_addresses: usizeAddresses a dialling endpoint will try for one hostname, in the order the resolver returned them.
More than one is necessary because the first is not necessarily
reachable — localhost commonly resolves to both ::1 and
127.0.0.1 — and a ceiling is necessary because a resolver answer is
remote input.
worker_threads: usizeWorker threads of the Tokio runtime crate::Runtime::owned creates.
Ignored by crate::Runtime::new and crate::Runtime::with_handle,
which run on a reactor somebody else sized. One is the default because
a messaging runtime is I/O bound and every extra worker is a thread a
library takes from its host process without being asked; 0 is
rejected rather than silently corrected.
shutdown_timeout: DurationHow long crate::Runtime::shutdown waits for closed sockets to go
idle before it returns anyway.
The wait exists so peers see a clean SHUTDOWN rather than a timeout,
and it is bounded because otherwise a peer’s behaviour decides when
this process may exit — the failure ZeroMQ’s infinite ZMQ_LINGER
default is known for
(docs/decisions/0009-drain.md §4.4). QUIC’s own closing and draining
periods last about three times the path’s probe timeout, so the default
of one second is generous on any network where a clean close was
possible at all, and it is not a deadline anything waits for twice:
every endpoint is closed first, and only the idle wait is capped.
guarantees: GuaranteeSetGuarantee set this runtime offers and requires of its peers
(docs/PROTOCOL.md §6.1, §6.5).
Offered and required are one setting in v0 on purpose: a set is a
statement of what this side runs, and a peer that cannot match it
fails the handshake rather than quietly giving less
(docs/decisions/0006-guarantee-sets.md §4.4). The default is core,
which is what every v0 peer declares by declaring nothing.
discovery: DiscoveryWhether an authority may name a set of nodes (Discovery).
resolver: SharedResolverWhat a name means.
The system resolver by default — A and AAAA, one port for the whole
set. Replace it to answer from DNS SRV, a service registry or a table:
a cloud load balancer that forwards several ports from one address is
the deployment the system resolver cannot express, and
weida_runtime::Resolver is how it brings its own answer
(decisions/0020
§4.2).
connect_attempt_timeout: DurationHow long a dial waits on one resolved address before trying the next.
Only the addresses before the last one are bounded by it: a name
that resolves to one address, and every IP literal, keeps the full
handshake budget. The default of 250 ms is RFC 8305’s Connection
Attempt Delay, which exists for exactly this case — localhost
resolving to ::1 before 127.0.0.1, where the first address answers
nothing at all and QUIC has no refusal to observe, so without a bound
the second address is reached only after a handshake timeout.
reconnect: ReconnectPolicyHow a dialling endpoint redials an address whose connection it lost
(decisions/0031
§4.5). The default doubles from 100 ms to 30 s with jitter and never
gives up; ReconnectPolicy::never is the behaviour before 0031.
send_timeout: Option<Duration>How long an open on a dialling endpoint waits for a peer to come
back before it fails with the loss cause; None waits as long as the
redial does (0031 §4.4). ZeroMQ’s ZMQ_SNDTIMEO, with its default.
outbox_messages: usizeBodies a dialling endpoint’s outbox holds while no peer is live, and
the bytes they may sum to (0031 §4.2). At either bound
RuntimeConfig::outbox_full decides. ZeroMQ’s ZMQ_SNDHWM of 1000
for the count; the byte bound is what ZeroMQ lacks and
docs/INVARIANTS.md needs.
outbox_bytes: usize§outbox_full: OutboxFullWhat a send does at the outbox bound: wait, drop and count, or
fail. Local to the sender, unlike the negotiated
GuaranteeSet::backpressure, because a puller has no say in how
its pusher waits.