Apache HTTP Server 版本 2.4
这是我在尝试将 mod_mmap_static
模块转换为 Apache 2.0 时学到的经验教训的首次尝试。它绝不是最终的,甚至可能在某些方面不正确,但这是一个开始。
这些现在需要是 apr_status_t
类型并返回该类型的值。通常,返回值将是 APR_SUCCESS
,除非需要在清理中发出错误信号。请注意,即使您发出错误信号,也不是所有代码都会检查并处理错误。
这些现在应该重命名以更好地表明它们在整个过程中的位置。因此,名称从 mmap_init
变成了 mmap_post_config
。传递的参数已经发生了根本性的变化,现在看起来像
apr_pool_t *p
apr_pool_t *plog
apr_pool_t *ptemp
server_rec *s
许多数据类型已移至 APR。这意味着有些名称已更改,例如上面显示的名称。以下是您可能需要进行的一些更改的简要列表。
pool
变成 apr_pool_t
table
变成 apr_table_t
新架构使用一系列钩子来提供调用您的函数的功能。您需要通过一个新函数 static void register_hooks(void)
将这些添加到您的模块中。一旦您了解了需要做什么,该函数实际上非常简单。每个需要在请求处理的某个阶段调用的函数都需要注册,处理程序不需要注册。有许多阶段可以添加函数,并且对于每个阶段,您可以高度控制函数调用的相对顺序。
这是添加到 mod_mmap_static
的代码
static void register_hooks(void) { static const char * const aszPre[]={ "http_core.c",NULL }; ap_hook_post_config(mmap_post_config,NULL,NULL,HOOK_MIDDLE); ap_hook_translate_name(mmap_static_xlat,aszPre,NULL,HOOK_LAST); };
这注册了 2 个需要调用的函数,一个在 post_config
阶段(几乎每个模块都需要这个函数),另一个在 translate_name
阶段。请注意,虽然函数名称不同,但每个函数的格式都相同。那么格式是什么呢?
ap_hook_phase_name(function_name, predecessors, successors, position);
定义了 3 个钩子位置...
HOOK_FIRST
HOOK_MIDDLE
HOOK_LAST
要定义位置,请使用位置,然后使用前驱和后继对其进行修改。每个修饰符都可以是应该调用的函数列表,这些函数可以在运行函数之前(前驱)或运行函数之后(后继)调用。
在 mod_mmap_static
案例中,我不关心 post_config
阶段,但 mmap_static_xlat
**必须**在核心模块完成其名称转换后调用,因此使用 aszPre 来定义对位置 HOOK_LAST
的修饰符。
现在在创建模块定义时要考虑的阶段少了很多。旧的定义看起来像
module MODULE_VAR_EXPORT module_name_module = { STANDARD_MODULE_STUFF, /* initializer */ /* dir config creater */ /* dir merger --- default is to override */ /* server config */ /* merge server config */ /* command handlers */ /* handlers */ /* filename translation */ /* check_user_id */ /* check auth */ /* check access */ /* type_checker */ /* fixups */ /* logger */ /* header parser */ /* child_init */ /* child_exit */ /* post read-request */ };
新的结构简单得多...
module MODULE_VAR_EXPORT module_name_module = { STANDARD20_MODULE_STUFF, /* create per-directory config structures */ /* merge per-directory config structures */ /* create per-server config structures */ /* merge per-server config structures */ /* command handlers */ /* handlers */ /* register hooks */ };
其中一些直接读取,一些则没有。我将尝试总结一下下面应该做什么。
直接读取的阶段
/* 目录配置创建器 */
/* 创建每个目录配置结构 */
/* 服务器配置 */
/* 创建每个服务器配置结构 */
/* 目录合并器 */
/* 合并每个目录配置结构 */
/* 合并服务器配置 */
/* 合并每个服务器配置结构 */
/* 命令表 */
/* 命令 apr_table_t */
/* 处理程序 */
/* 处理程序 */
旧函数的其余部分应注册为钩子。到目前为止,定义了以下钩子阶段...
ap_hook_pre_config
ap_hook_check_config
ap_hook_test_config
-t
选项时执行ap_hook_open_logs
ap_hook_post_config
_init
例程注册的地方ap_hook_http_method
ap_hook_auth_checker
ap_hook_access_checker
ap_hook_check_user_id
ap_hook_default_port
ap_hook_pre_connection
ap_hook_process_connection
ap_hook_child_init
ap_hook_create_request
ap_hook_fixups
ap_hook_handler
ap_hook_header_parser
post_read_request
ap_hook_insert_filter
ap_hook_log_transaction
ap_hook_optional_fn_retrieve
ap_hook_post_read_request
ap_hook_quick_handler
ap_hook_translate_name
ap_hook_type_checker