ngx_module_names仅用于调试和错误提示,不参与模块加载或索引分配;其与ngx_modules顺序一致是为便于日志可读和调试映射,属工程约定而非运行时依赖。

在 Nginx 源码中,ngx_module_names 数组并不直接参与模块加载或运行时索引分配,它仅用于调试和错误提示,与模块的索引(如 ctx_index、index)没有运行时关联。
ngx_module_names 是纯字符串表,不参与模块管理
ngx_module_names 定义在 src/core/ngx_module.c 中,是一个静态的 const char * 数组,按编译时链接顺序存放所有模块的名称字符串(如 "ngx_core_module"、"ngx_http_module" 等)。它的唯一用途是:
- 在启动失败时打印可读的模块名(例如配置解析出错时显示 “module ‘ngx_http_core_module’ is not loaded”);
- 配合
ngx_modules数组下标,供调试器或日志辅助定位——但该对应关系是人工维护的,非代码逻辑保证。
真正的模块索引由 ngx_modules 数组顺序决定
Nginx 运行时识别模块依赖的是 ngx_modules 全局数组(类型为 ngx_module_t *),其元素顺序决定了两类关键索引:
-
index:每个模块在ngx_modules中的下标(从 0 开始),用于核心数据结构(如 cycle->modules)索引,不可变; -
ctx_index:同类模块(如所有 HTTP 模块)内部的相对序号,由初始化阶段(ngx_http_add_module等)动态分配,用于 HTTP 框架回调调度。
这两个索引均来自 ngx_modules 的遍历过程,与 ngx_module_names 内容无关。即使删掉 ngx_module_names 或打乱其顺序,只要 ngx_modules 不变,Nginx 仍能正常工作。
为什么名字数组要和模块数组保持顺序一致?
虽然无运行时依赖,但构建系统(auto/modules)在生成 objs/ngx_modules.c 时,会强制让 ngx_modules 和 ngx_module_names 一一对应。这是为了:
- 使
ngx_module_t.name字段(指向模块自己的名字字符串)与全局名字表下标可互查,便于开发调试; - 在
ngx_get_module_name()这类辅助函数中,通过模块指针快速映射到名称字符串(利用module - ngx_modules[0]计算下标,再查ngx_module_names); - 避免人工维护错位导致日志输出名字错误——属于工程便利性约定,不是机制要求。
实际验证方式
可在 ngx_init_cycle() 中加日志,打印:
-
ngx_modules[i]->name与ngx_module_names[i]是否相等; -
ngx_modules[i]->index是否恒等于i; - 修改
ngx_module_names某项内容后,观察错误日志是否显示对应新字符串。
你会发现:索引逻辑不受名字数组影响,但错误提示会变——这正说明二者分工明确:一个管运行,一个管可读性。










