pub struct ShapeProfile { /* private fields */ }Expand description
A complete egress shaping configuration for one session.
Constructed only through ShapeProfile::try_new, which validates the
combination — an invalid profile cannot reach a session, so there is no
runtime your config was rejected path to miss.
Not #[non_exhaustive]: the fields are private, so the attribute would
add nothing a caller could observe.
§Reading one from a file
Under the non-default serde feature this type serializes and
deserializes, and the two directions are not symmetric. Serializing is
a derive over the private fields, which is safe because writing a profile
out cannot make an invalid one. Deserializing goes
#[serde(try_from = "ShapeProfileSpec")], through a public-field mirror
whose TryFrom calls ShapeProfile::try_new.
The detour is the whole point. A derived Deserialize would reach these
private fields directly and bypass every one of the seven validations below
— including ShapeError::UnknownBucket, where a file naming a bucket
that does not exist would parse, arm, report shaping and shape nothing.
Routing through the mirror means there is no deserialization path that
skips the constructor, and no consumer has to remember to convert.
Implementations§
Source§impl ShapeProfile
impl ShapeProfile
Sourcepub fn try_new(
buckets: Vec<BucketConfig>,
classes: Vec<ClassRule>,
queue: QueueConfig,
discipline: Discipline,
) -> Result<Self, ShapeError>
pub fn try_new( buckets: Vec<BucketConfig>, classes: Vec<ClassRule>, queue: QueueConfig, discipline: Discipline, ) -> Result<Self, ShapeError>
Validate a profile and build it, or say exactly what is wrong.
The seven rejections, in the order they are checked:
ShapeError::EmptyQueue— a queue that can hold nothing.ShapeError::NoClasses— a profile with no class rules at all, which is a shaping profile that shapes nothing.ShapeError::DuplicateClassName— class names index the statistics, so duplicates make them unattributable.ShapeError::UnknownBucket— a class naming a bucket that is not inbuckets; the silently-inert class this constructor exists to prevent.ShapeError::EgressSideInMatcher— a matcher keyed on an egress side, which no hook site ever sees.ShapeError::ZeroWeight— a zero weight underDiscipline::WeightedRoundRobin, which is a class that can never be scheduled.ShapeError::InertMatcher— a matcher key naming an empty set of values, which is a class that can never claim a unit.
The second is checked outside the loop below, and that is the
point of it: every other class rule is checked inside a
for class in &classes, and a loop over nothing runs no checks at
all. A profile with no classes was therefore the one shape that could
pass every rule here by not being subject to any of them.
Duplicate bucket names are not an error: two identical entries resolve to the same bucket and the first one wins, which is what a caller who wrote the name twice meant. Only class names index anything.
§What this constructor cannot see, and why the line is there
Every check above is a property of the configuration alone. What it deliberately does not attempt is anything that depends on the draft or on the traffic, and there are two such faults; both are reported during the run instead, because a rejection here has to be right for every session the profile could be used in.
A key the wire does not carry on this draft is
Impairment{ShapeRuleUnmatchable} — try_new has no draft. And a
BucketConfig::burst_bytes smaller than the objects a class
actually sees is
Impairment{ShapeBurstBelowUnit} — try_new has the burst but not
the object sizes, and the sizes are what decide. The second is worth
the attention because its silent form is so plausible: a burst below
one object makes every unit leave at its max_hold clamp, at a
throughput with no relation to the rate that was configured, and
before the report existed the only signal was the one an ordinary
rate-limited class produces.
Sourcepub fn buckets(&self) -> &[BucketConfig]
pub fn buckets(&self) -> &[BucketConfig]
The configured buckets, in the order they were given.
Sourcepub fn classes(&self) -> &[ClassRule]
pub fn classes(&self) -> &[ClassRule]
The configured class rules, in the order they were given — which is
also the order the statistics snapshot reports them in, and the
order Discipline::Fifo tie-breaks on.
Sourcepub fn queue(&self) -> &QueueConfig
pub fn queue(&self) -> &QueueConfig
The per-stream queue policy.
Sourcepub fn discipline(&self) -> Discipline
pub fn discipline(&self) -> Discipline
How classes competing for one bucket are arbitrated.
Trait Implementations§
Source§impl Clone for ShapeProfile
impl Clone for ShapeProfile
Source§fn clone(&self) -> ShapeProfile
fn clone(&self) -> ShapeProfile
1.0.0 (const: unstable) · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source. Read more