pub const fn build_size2class<const N: usize, const L: usize>(
table: &[usize; N],
min_block: usize,
) -> [u8; L]Expand description
Build the O(1) size→class lookup from a table at compile time — so the
lookup and the table cannot drift. The caller indexes it as
size2class[(size - 1) >> log2(min_block)], so bucket k covers every size
in (k * min_block, (k + 1) * min_block]; size2class[k] is the smallest
class whose block_size >= (k + 1) * min_block – EXCEPT the top bucket
L - 1, whose ideal need (L * min_block mathematically – NOT
guaranteed to fit usize even for a valid scheme, e.g. min_block = 1 << 62, L = 4; the builder computes it as (k + 1).checked_mul(min_block)
and folds that same overflow into the clamp below, never evaluating the
unrepresentable product) exceeds table[N - 1] (the
largest class), so no such class exists; that bucket is clamped to
table[N - 1] itself instead. For SizeClasses::class_for specifically
this is harmless: it never queries bucket L - 1 for any in-range size
(its own early-rejection guard catches every size that would land there),
so THERE the clamped entry is an unreachable sentinel, not
an observable answer. A caller driving this array directly (bypassing
class_for) can still observe it – and for a hand-built table whose
small_max is not a multiple of min_block, bucket L - 1 need not even
be a sentinel: it can be the correct, reachable answer for sizes in
((L - 1) * min_block, small_max].
L must equal size2class_len(max_class, min_block), where max_class
is table[N - 1].
table need not come from build_table – this function is a
standalone building block, callable with any hand-built strictly
increasing array. Note, though, that build_table’s own output always
has every entry a multiple of min_block; a hand-built table that
violates that (while still passing every check below) can produce an
entry the documented bucket lookup never selects – e.g. min_block = 16, table = [16, 24, 32]: bucket (16, 32] resolves straight to 32,
leaving 24 monotonicity-valid but permanently unreachable through the
public lookup path. (There is no public constructor that feeds a
hand-built table into SizeClasses::class_for – SizeClasses::build
always derives its table from build_table – so this is a property of
the derived LUT itself, not of class_for.)
§Panics
Panics – identically in const evaluation and at runtime, since this is
a pub const fn callable either way – if the table is empty, if L is
wrong (including if computing the expected L via
size2class_len(table[N - 1], min_block) itself overflows usize),
if min_block is not a power of two, if table.len() > 256 (entries are
u8 CLASS INDICES, so the largest representable table has 256 classes,
indices 0..=255; a 257th class would silently truncate), or if table
is not strictly increasing.