
zone_statistics()是页面分配路径上用于更新 NUMA 命中/未命中统计的辅助函数。它追踪分配请求的“首选 zone”与实际分配到的 zone 之间的关系为/proc/vmstat提供numa_hit、numa_miss、numa_foreign等计数。核心作用它的职责是当一次分配发生在zzone而调用者“期望”的是preferred_zone时根据两者是否一致来更新统计一致z preferred_zoneNUMA_HIT递增表示分配成功落在期望节点。不一致z ! preferred_zonez上NUMA_MISS递增preferred_zone上NUMA_FOREIGN递增。这三个计数器共同反映了 NUMA 本地性策略的效果。典型实现static inline void zone_statistics(struct zone *preferred_zone, struct zone *z, long nr_account) { #ifdef CONFIG_NUMA enum numa_stat_item local_stat NUMA_LOCAL; /* 如果启用了 NUMA 统计 */ if (!static_branch_unlikely(vm_numa_stat_key)) return; if (z preferred_zone) local_stat NUMA_HIT; else local_stat NUMA_MISS; __count_numa_event(z, local_stat); if (local_stat NUMA_MISS) __count_numa_event(preferred_zone, NUMA_FOREIGN); #endif }具体实现随版本早期版本还区分NUMA_LOCAL/NUMA_OTHER。关键点解析1.static_branch_unlikely(vm_numa_stat_key)静态键控制 NUMA 统计是否启用。未启用时函数直接返回零开销——这是热路径上的关键优化。只有启用统计默认开启可通过 sysfs 关闭时才走真实逻辑。2.preferred_zone与zpreferred_zone调用者期望的 zone通常由numa_node_id()决定本地节点。z实际分配到的 zone。分配可能因本地内存不足而“降级”到其他节点的 zone此时产生 miss/foreign。3. 三种计数事件含义NUMA_HIT分配落在首选 zone本地性好NUMA_MISS分配落在非首选 zone本节点“错过”NUMA_FOREIGN本节点被其他节点“借用”了内存4.nr_account传入的页数1 order供按页数加权统计的版本使用。在分配路径中的位置它被buffered_rmqueue()调用位于页面从 PCP 或伙伴系统取出之后buffered_rmqueue(preferred_zone, zone, order, gfp_flags, ...) ├── 从 PCP 或伙伴系统取页 └── zone_statistics(preferred_zone, zone, 1 order) // ← 这里历史演进zone_statistics()在 2025 年经历了一次重构。旧实现使用enum numa_stat_item local_stat并区分NUMA_LOCAL/NUMA_OTHER逻辑较复杂。新实现在启用统计时直接用NUMA_HIT初始化并简化了分支/* old */ enum numa_stat_item local_stat NUMA_LOCAL; if (z preferred_zone) local_stat NUMA_HIT; else if (z-node ! preferred_zone-node) local_stat NUMA_OTHER; else goto out; /* 同一节点无需统计 */ __count_numa_event(z, local_stat); /* new */ if (z preferred_zone) __count_numa_event(z, NUMA_HIT); else { __count_numa_event(z, NUMA_MISS); __count_numa_event(preferred_zone, NUMA_FOREIGN); }新逻辑更直观且移除了对NUMA_LOCAL/NUMA_OTHER的依赖这两个计数器在早期版本中用于区分“同节点不同 zone”与“不同节点”的情况。总结zone_statistics()是 NUMA 分配路径上的统计记录器它通过静态键vm_numa_stat_key实现零开销开关在启用时根据“实际分配 zone”与“首选 zone”是否一致分别递增NUMA_HIT或NUMA_MISSNUMA_FOREIGN为/proc/vmstat提供 NUMA 本地性数据。它由buffered_rmqueue()在每次成功分配后调用。