Skip to main content

struct-layout-analysis

Measure and fix C struct layout in BIND 9 — pahole on the build's DWARF for sizes, padding holes, and cacheline boundaries, plus the house cacheline-padding idiom. Use when asked about struct size, padding, false sharing, or when adding/reordering members in hot structures.

Source facts

Repository
isc-projects/bind9
Last source activity
July 14, 2026 at 11:40
Detected SKILL.md language
English
Stars
780
Forks
187

Install options

The review-first prompt is selected by default. You can switch to a direct command or download a local copy.

Review the source files

Read SKILL.md and any companion files shown by SkillsMP before deciding whether to install.

Showing SKILL.md

SKILL.md
Source instructions · Read-only preview
name
struct-layout-analysis
description
Measure and fix C struct layout in BIND 9 — pahole on the build's DWARF for sizes, padding holes, and cacheline boundaries, plus the house cacheline-padding idiom. Use when asked about struct size, padding, false sharing, or when adding/reordering members in hot structures.
# Struct layout: measure with pahole, pad with a multiplier ## Measuring — pahole, never throwaway sizeof programs The developer build (`-Og -ggdb`) already carries DWARF; read it instead of compiling sizeof/offsetof snippets: ```sh pahole -C <struct_name> build/lib/dns/libdns*.so.p/<file>.c.o pahole --holes -C <struct_name> <object-or-binary> ``` pahole prints member offsets, padding holes, total size, and cacheline boundaries — complete layout information the compiler already computed, with no boilerplate to write. Any object file under `build/` or the final binary works as input. ## Padding to cachelines — union arm with a plain multiplier Pad a struct to a whole number of cache lines with a union arm sized by a plain multiplier, always paired with a static assert: ```c struct foo { union { struct { /* members */ }; uint8_t __padding[ISC_OS_CACHELINE_SIZE * 6]; }; }; STATIC_ASSERT(sizeof(struct foo) % ISC_OS_CACHELINE_SIZE == 0, "struct foo size must be a multiple of the cacheline size"); ``` Pick the smallest `n` that fits; when members outgrow the arm to a non-multiple size, the STATIC_ASSERT fires and prompts a bump of `n`. Do NOT use the enumerated-sizeof trailing formula `uint8_t __padding[CACHELINE - (sizeof(a) + sizeof(b) + ...) % CACHELINE]` (the historical qpzone style): it must enumerate every member's sizeof, so adding a member silently miscounts unless the formula is updated in lockstep. The multiplier form has no such coupling and is easier to read.
View on GitHub