Population, zone and aggregation tokens now carry definitions that render. _vocabulary_definitions reads the three vocabularies as well as the locus registry, the physical bases and the geometry carriers, and select_conventions emits an applied definition for a population, zone or aggregation token that carries one.

Shape chosen for the definition-only entry: a sibling shape, AppliedDefinition(token, segment, definition), carried on AppliedConventions.definitions beside concepts. AppliedConcept keeps its required phrase, equation and restates_equation; no phrase or equation was invented to fill a required field. The sibling also lets the two be told apart: a concept names a shared phrase or equation, a token definition states only what the token means.

The three files changed from lists to token-keyed entries in which each entry maps its token to that token's definition, so a token without a definition still loads. This is not the root-keyed shape the locus registry and physical bases use: the codegen token extractor recognises a root key only for loci, carriers, bases, operators and axes (grammar_codegen/spec.py), and the cross-segment uniqueness lint reads a bare mapping's keys as its token list (tests/grammar/test_vocab_uniqueness.py). A root key populations: is extracted as the single token populations, which would have broken the generated enums and the drift gate — measured by loading a scratch spec through IncludeLoader. The token-keyed shape satisfies both readers unchanged. Adopting the root-keyed shape is a one-line addition to that root-key tuple, in a file outside this node's write scope; it is recorded as a follow-on rather than made here.

Definitions moved from comments, not invented. Seven populations carry one (fast: Non-thermal / energetic population.), two aggregations (total: Summed over sub-populations, species or additive contributions.), and four zones whose comment states a position (upper, lower, inner, outer). The nine remaining zone tokens (core, edge, pedestal, separatrix, divertor, scrape_off_layer, front_surface, back_surface, wetted) record no meaning in a comment, so they were left undefined rather than filled in.

The level of the corpus these tokens are read from — the conventions accessor — emits the definition for a name carrying the token. Its output for lower_outer_squareness_of_flux_surface is:

token:      lower
segment:    zone
definition: Lower vertical position.

token:      outer
segment:    zone
definition: Outer radial position.

And for total_plasma_current, whose only defined token is the outer aggregation:

token:      total
segment:    aggregation
definition: Summed over sub-populations, species or additive contributions.

A token without a definition loads and contributes nothing: core_electron_temperature parses, and select_conventions returns an empty definitions tuple for it.

Measure. tests/grammar/test_token_definitions.py asserts the loaders against Population, Aggregation and Zone — the enums are the token record the plain lists held — so load_populations and load_aggregations return the same sets and load_zones the same ordered tuple. The gate (this file plus test_vocab_uniqueness, test_conventions, test_codegen_drift, test_segment_vocabulary_additions, test_model_grammar_sync) ran 71 passed, 7 xfailed (EXIT=0) at head against 66 passed, 7 xfailed (EXIT=0) at base — five added tests, zero added failures. The codegen gate passing is the direct check that the entries shape still yields the full token list.

Negative control, declared as removing the definition emission. With definitions=definitions_applied dropped from the AppliedConventions construction and everything else held fixed, tests/grammar/test_token_definitions.py ran 2 failed, 3 passed (EXIT=1), failing test_a_definition_renders_for_a_name_carrying_the_token and test_a_zone_definition_names_the_segment_the_token_was_used_in — both of which pass at head. The three that still pass are the loader identity tests, the definition-presence test and the contributes-nothing test, none of which routes through the emission. Log: negative-control.log in the run directory.

No figure accompanies this fragment: the change is a data shape and an accessor field, and the rendered definitions above carry it. The figure directory given to this node is left empty.