Skip to main content

Module segment

Module segment 

Source
Expand description

Segments and spans — where a pointer’s identity comes from.

A segment is a 4 MiB region mapped at a 4 MiB-aligned address. It is cut into 64 spans of 64 KiB; span 0 holds the segment header and the other 63 serve allocations, one size class each.

That geometry is the whole reason there are no per-allocation headers. Masking a pointer with !(SEGMENT_BYTES - 1) gives the segment, the offset gives the span index, and the span’s metadata gives the class — so dealloc recovers everything it needs from the address itself. glibc has to store a size beside every chunk because C’s free is not told one; we are, and even when we were not, the address would answer.

Reference: mimalloc’s segment/page split (segment.c), and Go’s mheap arena indexing. The divergence from both is that a segment here is owned by exactly one shard for its whole life — kevy pins a shard per core, so ownership never has to be negotiated.

Re-exports§

pub use crate::pagemap::NO_CLASS;
pub use crate::pagemap::SpanMeta;

Structs§

Segment
The header at the base of every segment.

Constants§

FIRST_DATA_SPAN
Span index 0 is the header; allocation spans start at 1.
FOREIGN_SIZE_OFFSET
Where [push_foreign] stores the requested size inside a free slot, clear of the link that occupies the first word.
SEGMENT_BYTES
Bytes per segment. Power of two: the mask is the lookup.
SPANS_PER_SEGMENT
Spans in a segment, including the header span.

Functions§

foreign_requested
Read back the requested size a foreign free recorded.
segment_of
Recover the segment owning ptr.
slot_index_of
The slot index within its span holding ptr, for a given class.
span_index_of
The span index within a segment holding ptr.
splice_foreign
Push a slot onto a segment’s foreign-free stack.
take_foreign
Take the whole foreign-free list, leaving it empty. Only the owning shard may call this — that exclusivity is what makes the structure ABA-free (see [push_foreign]).