Added
- The Substrate WorkerPool’s CPU generation pin —
karpenter.k8s.aws/instance-generationnext to the vendor inkagent.substrateWorkerPool.template.nodeSelector— is documented, render-guarded and verified (giantswarm/agent-platform#457, the caveat #430 recorded). One pool runs one CPU feature set: an actor’s golden snapshot is a gVisor checkpoint that restores only on a host whose CPU offers every feature it recorded, and #429’s vendor pin left the generation open — on gazelle (2026-09-14) Karpenter put two workers on anm7a.2xlarge(generation 7, AVX-512) and two onc5ad.xlarge(generation 5), the goldens were taken on the m7a workers, and every cold turn placed on a c5ad worker failedincompatible FeatureSet: missing features: … avx512f …twice (30 s each), thenSendStreamingMessage Internal, “the turn failed” in Slack; the next morning’s pool (c6a, c5a ×2, m6a) restored everywhere only because the goldens had been re-taken on a gen-5 worker. The pin is a second label in the same map, set per installation (the fleet template renders it from the installation’s values the way it renders the vendor): pick a generation that is one CPU model across its families — for AMD on AWS 6 (c6a/m6a/r6a, EPYC Milan) or 7 (c7a/m7a/r7a, Genoa); 5 mixes Naples (m5a/r5a) with Rome (c5a/c5ad) and is no feature-set pin — and one the goldens restore on (an older generation’s golden restores on a newer one, never the reverse), and check the spot pool it leaves (the generation’s families × the NodePool’s sizes; three families is the floor). The meta chart now refuses a nodeSelector value that is not a string naming the key (agent-platform.validateWorkerPool): the label is"6", and a bare6rendered, passed the open kagent schema and would have failed only when helm-controller applied the kagent release on every installation carrying it.make verify-workerpool(in CI) asserts the default forwards the architecture alone, an installation’s three-label pin reaches the kagent release verbatim with every value a string, the unquoted generation fails the render, and the kagent chart the range resolves to renders the pin unchanged into the one WorkerPool’sspec.template.nodeSelector— the lab has no Karpenter labels, so this render is where the pin is proven. Docs: values.yaml, the chart README, the root README’s Substrate section and UPGRADE.md name the generation next to the vendor. A restore that fails withincompatible FeatureSetis retried on the same worker; placing it on another worker is Substrate’s (giantswarm/giantswarm#37742 row 12), not this chart’s. No rendered object changes for an installation that sets no generation.