医学--modsecurity调研工作汇报_第1页
医学--modsecurity调研工作汇报_第2页
医学--modsecurity调研工作汇报_第3页
医学--modsecurity调研工作汇报_第4页
医学--modsecurity调研工作汇报_第5页
已阅读5页,还剩67页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

Modsecurity调研报告 郭川 2012年2月13日 调研目的 分析Modsecurity模块作为Apache框架 下的一个规则引擎的执行流程,以期 在Nginx下实现具有类似功能的规则引 擎模块 内容 n Modsecurity执行流程 n Modsecurity移植问题 n 重要函数流程图 Modsecurity执行流程 读取规则、翻译规则、规则生效简介 规则格式、指令哈希表、规则引擎介绍 读取规则、翻译规则、规则生效详解 读取规则 时间:Apache启动阶段 位置:配置文件,例如 httpd.conf 中 存储数据结构:配置树,数据结构选择树 是由配置文件中的配置信息结构决定的 翻译规则 时间:Apache启动阶段,读取配置文件后 方法:利用规则引擎(规则引擎是 Modsecurity 模 块添加的一个钩子函数建立的) 存储结构:Modsecurity 模块中定义了存储 一条及多条规则的结构体 结果:构建了存储多条可使用的规则的结 构体 规则生效 时间:Apache 读取、处理以及响应请求过 程中的某一点(Modsecurity 模块注册了钩子函数的地方) 过程:根据翻译好的规则,进行匹配检查 结果:若匹配,则执行规则中的相应动作 规则格式 一条规则实例: SecRule REMOTE_ADDR “05$“ “redirect:“ 其中SecRule是指令名称,其后所跟是该指令的参数。Modsecurity 定义的指令有60多条,并且各条指令的参数格式不同。 指令(Directives)举例: SecAction;SecDefaultAction;SecMarker; SecRuleEngine;SecRule;SecRuleInheritance; SecRequestBodyAccess 规则格式 SecRule 的参数格式如下: SecRule VARIABLES OPERATOR TRANSFORMATION_FUNCTIONS, ACTIONS VARIABLES举例: QUERY_STRING; REMOTE_ADDR; REQUEST_BODY OPERATOR举例: rx; eq; ge; gt; le; lt TRANSFORMATION_FUNCTIONS举例: lowercase; urlDecode; removeWhitespace ACTIONS举例: allow; msg; id; deny; phase; skip; chain 指令哈希表 Apache 的每一个模块都有自己定义的指令 数组 指令数组在模块被添加的时候被 Apache 保 存 所有的指令被 Apache 保存在指令哈希表 中。利用这个哈希表,由指令名字可以快 速获取到Apache中保存的关于该条指令的 一个结构体 指令哈希表 指令哈希表是在 Apache 启动阶段加载模块的过程中通 过读取模块定义的指令数组建立的存储指令的哈希表 Modsecurity模块的定义: module AP_MODULE_DECLARE_DATA security2_module = STANDARD20_MODULE_STUFF, create_directory_config, merge_directory_configs, NULL, /* create_server_config */ NULL, /* merge_server_configs */ module_directives, register_hooks ; 其中,moduel_directives 是 Modsecurity 模块定义的指令数组。 哈希表结构体 哈希表元素结构体 模块链结构体 模块结构体 指令哈希表 ap_conf_hash 指令存储结构体 建立规则引擎 时间:读取规则之后,解析规则之前使用 Modsecurity的钩子函数hook_pre_config SecRule的语法也即其参数格式如下: SecRule VARIABLES OPERATOR TRANSFORMATION_FUNCTIONS, ACTIONS 将VARIABLES OPERATOR TRANSFORMATION_FUNCTIONS ACTIONS 四个域对应的所有可选值存储到一个类型为 msc_egine的结构体中,这个结构体就称为规 则引擎。 规则规则 引擎 modsecurity 模块引擎结构体 规则引擎结构体 规则变换函数结构体 规则变量结构体 规则操作符结构体 规则动作结构体 读取规则 读取配置文件中的每条配置信息,形成一 颗配置树结构。配置树中结点结构如下: 配置树中指令结点结构体 读取规则 配置树: 配置树树 ap_conftre e 配置树中指令结点结构体 遍历配置树并执行每个结点中的指令的过程 读取规则 翻译规则 遍历配置树中的每一条规则 根据规则名称查找指令哈希表 执行指令结构中的相应函数 指令哈希表中的 指令存储结构 SecRule指令的存储结构,相应的函数即cmd_rule() 翻译规则 cmd_rule() 函数 利用规则引擎翻译规则,并保存翻译后的规则 规则解释好以后,被存储到Modsecurity模块定义 的规则结构体(msre_rule)中,所有的规则都存储 到规则集结构体中(msre_ruleset)中 cmd_rule()函数是Modsecurity模块中最重要的两个 函数之一,另一个是modsecurity_process_phase() 翻译规则 规则举例: SecRule REMOTE_ADDR “05$“ “redirect: “ 使用REMOTE_ADDR从规则库中取出相应的 msre_var_metadata 类型的变量结构体: 规则变量结构体的定义 存储变量REMOTE_ADDR的结构体 翻译规则 使用“05$” 从规则库中取出类型为 msre_op_metadata类型的操作符结构体: 使用“redirect: ” 从规则库中取出 类型为msre_action_metadata类型的动作结构体: 规则操作符结构体 规则操作符结构体实例 规则动作 结构体规则动作结构体实例 翻译规则 规则翻译的步骤: 规则库中存储msre_var | op | tfn | action_metadata 类型的结构体 根据规则中的具体变量名从规则库中取到对应 的结构体 将一条规则的相关信息存储到一个规则结构体 中 将所有规则按照执行阶段的不同存储到一个规 则集结构体中 规则规则 集和规则规则 *规则规则 存储储* 规则集 动作 规则 变量 动作集 动动作和动动作集 规则生效 时间:在Apache处理请求的过程中,添加 钩子函数,Modsecurity 的钩子函数中使用 规则对请求进行处理 过程: 变量决定数据 操作符决定匹配 动作决定去向 首先生成具体变量,其次根据操作符进行匹配 , 若匹配成功,则完成相应动作。 规则生效 规则被解释后得到的规则结构体中存储着 各个域对应的结构体,结构体中存储相应 的函数指针 使用如下规则详细解释 SecRule REMOTE_ADDR “05$“ “redirect: “ SecRule REMOTE_ADDR “05$“ “redirect: “ 变量REMOTE_ADDR对应的结构体,其中函数 var_romote_addr_generate的作用是获得访问端ip地址并保 存。 函数将modsec_rec类型结构体中remote_addr的 值保存到mare_var类型的结构体中。 例子中变变量域为为 ”REMOTE_ADDR” SecRule REMOTE_ADDR “05$“ “redirect: “ 例子中操作符域为为 “05$“ 默认操作符为“rx”,及正则表达式匹配方式,函数msre_op_rx_execute将操作符 的参数(此例中参数为05 )与已获得的变量相匹配,并返回匹配结 果标识。 SecRule REMOTE_ADDR “05$“ “redirect: “ 规则动作结构体实例,函数msre_action_redirect_validate检验参数是否合法; msre_action_redirect_execute函数将从定向地址赋给rule-actionset-intercept_uri 例子中动动作域为为 “redirect:http:/www.modsecurit “ 重要结构体总结 规则引擎: msc_engine; msre_engine; msre_var_metadata; msre_op_metadata; msre_tfn_metadata; msre_action_metadata; 规则使用: modsec_rec; directory_rec; msre_ruleset; msre_rule; msre_var; msre_actionset; msre_action; 执行流程总结 加载模块,读取指令数组,建立指令哈希 表 读取配置文件中的规则,建立配置树 一个挂钩函数,建立规则库 处理配置树,查询指令哈希表,使用规则 库翻译规则 处理请求,执行钩子函数,匹配规则 移植问题 modsecurity规则集的维护独立作为另外一个 项目,网址如下: /index.php/Category:OWASP_ModSecurity_Core_Rule_Set_Project 移植的modsecurity应至少能翻译最小规则集 (Rules Language Porting Spec)中的规则。 实现nginx下的规则引擎主要参考apache下 modsecurity的实现。 移植问题 将modsecurity模块从apache下移植到nginx 下需要注意的问题是modsecurity中与apache 有联系的部分,modsecurity独立实现部分直 接复制就行。 modsecurity apache apache+modsecurity 中间相互关联的一部 分是移植过程中应该 重点考虑的地方 在apache框架下实现的规则引擎 移植问题 模块定义: apache通过加载模块来使用modsecurity实现的 规则解释功能,定义模块结构体可以看做是定 义apache核心和modsecurity所实现功能的一个 接口,加载模块的过程就是apache了解模块实 现哪些功能的过程 Apache中定义模块的结构体 Nginx中定义模块的结构体 Apache和nginx中 模块结块结 构体比较较 移植问题 读取、处理配置信息: 需要将apache和nginx读取、处理配置信息的方 式作比较 规则存储在配置文件中,apache读取配置文件 过程中,将每一条规则作为一条独立的配置信 息 Apache 配置信息的存储数据结构图解 Structure of the perrequest configuration processor: The walk procedures 移植问题 规则生效: 各个域对应的结构体中有相应的函数,在函数的执 行过程中会用到apache中的一些数据,此时就需要 使用保存的apache数据。 规则操作符结构体实例 规则动作结构体实例 规则变量结构体实例 移植问题 规则生效: modsecurity首先获取将会用到的apache中的数据, 存储到类型为modsec_rec类型的结构体中,等到 modsecurity中的函数需要时直接从此结构体中取到 此结构体是modsecurity中最重要的两个结构体之一 ;另一个之一类型为directory_config,用于apache 处理配置信息的过程中 request_rec modsec_rec msre_ruleset directory_configserver_rec notes lookup_default Apache和Modsecurity交互 过过程中的主要结结构体 Apache结构体 *规则规则 存储储* 规则集 动作 规则 变量 动作集 重要函数流程图 规则添加函数(规则翻译函数)及规则生 效函数流程图 hook_request_early 、hook_request_late 、 output_filter 三个函数的流程图 规则添加函数(规则翻译函数) 及规则生效函数流程图 Apache2_config.c, Line 615; add_rule; Line 629; dcfg-ruleset = msre_ruleset_create(modsecurity-msre, cmd-pool); /*Create a ruleset if one does not exist.*/ Line 653; dcfg-tmp_default_actionset = msre_actionset_create_default(modsecurity-msre); /*Create default actionset if one does not already exist.*/ Line 660; if (rule-actionset != NULL) /*Check syntax for chained rules.*/ Line 702; rule-actionset = msre_actionset_merge(modsecurity-msre, dcfg- tmp_default_actionset, rule-actionset, 1); /*Check syntax for chained rules.*/ Line 720; if (dcfg-tmp_chain_starter != NULL); /*如果规则 属于某规则链 ,则设 置链头 .*/ 规则规则 添加流程图图 Apache2_config.c, Line 615; add_rule; Line 725; if (rule-actionset-is_chained != 1); /*检查规则链 中的一条规则 是否还要继续连 接此规则链 .*/ Line 748; if (dcfg-tmp_rule_placeholders = NULL); dcfg-tmp_rule_placeholders = apr_table_make(cmd-pool, 10); /*Create skip table if one does not already exist.*/ Line 753; if (rule-actionset-skip_after != NOT_SET_P); apr_table_setn(dcfg-tmp_rule_placeholders, tmp_id, tmp_id); /*Keep track of any rule IDs we need to skip after.*/ Line 776; if (rule-actionset-id != NULL) modsecurity_process_phase; Line 661; if (msr-was_intercepted) /*Check if we should run.*/ Line 670; if (msr-phase = phase); /*Do not process the same phase twice.*/ Line 682; if (msr-txcfg-cache_trans = MODSEC_CACHE_ENABLED); /*Clear out the transformation cache at the start of each phase.*/ Line 743; switch(phase); /*这这一步是重点。根据当前所处的阶段phase,选择调 用哪一个 处理函数.*/ 规则规则 生效流程图图1 modsecurity.c, Line 459; modsecurity_process_phase_request_headers; Line 463;if (msr-txcfg-debuglog_level = 4); /*检查 是否需要记录 日志.*/ Line 467;time_before = apr_time_now(); /*记录 开始时间 .*/ Line 469;if (msr-txcfg-ruleset != NULL); /*这这一步是重点。 检查规则 集是否为空,若不为空,调用规 则集处理函数msre_ruleset_process_phase.*/ Line 473; msr-time_phase1 = apr_time_now() - time_before; /*计算此阶段规则 集处理所花费时间 ,结束时间 减去开始时 间.*/ 规则规则 生效流程图图2 re.c, Line 1078; msre_ruleset_process_phase; Line 1089; switch (msr-phase); /*获取当前阶段的规则 集.*/ Line 1122; for (i = 0; i nelts; i+); /*循环遍历当前阶段规则 集中的所有规则 .*/ Line 1134; if (mode = SKIP_RULES); /*是否有skipAfter动作.*/ Line 1189; if (mode = NEXT_CHAIN) /*规则链 中有规则 不匹配,则跳出此 链.*/ Line 1203; if (mode = NEXT_RULE) /*/ Line 1223; if(apr_is_empty_array(msr-removed_rules_tag)=0); /*Check if this rule was removed at runtime.*/ Line 1300; if(msr-txcfg-is_enabled = MODSEC_DISABLED); Line 1336; rc = msre_rule_process(rule, msr); /*重点。 经过 一系列的检查 ,最终 调用规则处 理函数.*/ Line 1346; if (rc = RULE_NO_MATCH); /*后续处 理.*/ 规则规则 生效流程图图3 re.c, Line 2849; msre_rule_process; Line 2851; if (msr-msc_rule_mptmp = NULL); /*处理每条规则时 使用新的内存地址空间(新的子内存池), 在这里创建新内存 Use a fresh memory sub-pool for processing each rule.*/ Line 2865; msre_rule_process_normal(rule, msr); /*重点。 调用真正的规则处 理函数. Executes rule against the given transaction.*/ 规则规则 生效流程图图4 re.c, Line 2271; msre_rule_process_normal; Line 2303; for (i = 0; i targets-nelts; i+); /*处理变量域并保存其值。Expand variables to create a list of targets.*/ Line 2371; if (msr-txcfg-cache_trans != MODSEC_CACHE_DISABLED) ; /*Is this var cacheable?*/ Line 2337; if (msr-txcfg-debuglog_level = 4); /*记录变 量处理的日志。Log the target variable expansion.*/ Line 2360; for (i = 0; i nelts; i+); /*遍历前面已经保存的生成的变量,针对 每一次遍历:执行变换 操作;并调用操作 符函数execute_operator。 Loop through targets on the final target list, perform transformations as necessary, and invoke the operator.*/ Line 2784; rc = execute_operator(var, rule, msr, acting_actionset, mptmp); /*重点。Execute operator.*/ Line 2469; /*Transform target.*/ 规则规则 生效流程图图5 re.c, Line 2120; execute_operator; Line 2136; if (var-param != NULL) /*确定完整变量名称*/ Line 2167; rc = rule-op_metadata-execute(msr, rule, var, /*Detect whether variable and operator matches?*/ Line 2255; msre_perform_nondisruptive_actions(msr, rule, rule-actionset, mptmp); /*根据操作符函数匹配的结果执行非中断性的动作.*/ Line 2261; msre_perform_disruptive_actions(msr, rule, acting_actionset, mptmp, my_error_msg); /*执行中断性动作,但要求该规则 不属于规则链 */ 规则规则 生效流程图图6 hook_request_early 、hook_request_late、 output_filter 三个函数的流程图 mod_security2.c, Line 638; hook_request_early; /*初始化请求处理,在apache接收到请求头后马上执行。这 个函数会创建新的modsec_rec类型结构体。*/ Line 639; modsec_rec *msr = NULL; /*定义空的类型为modsec_rec的结构体变量。*/ Line 651; msr = create_tx_context(r); /*初始化交易上下文并建立初始配置信息。 这这里是重点。初始化结构体msr。见下一页。*/ hook_request_early1 mod_security2.c, Line 350; create_tx_context; Line 367; msr-dcfg1 = (directory_config *)ap_get_module_config(r-per_dir_config, /*获取apache中保存的关于此模块的配置信息*/ Line 388; msr-txcfg = merge_directory_configs(msr-mp, msr-txcfg, msr-dcfg1); /*合并配置信息结构体*/ Line 391; init_directory_config(msr-txcfg); /*设置配置结构体的初始默认值 */ Line 426; if (modsecurity_tx_init(msr) txid = get_env_var(r, “UNIQUE_ID”); /*获取命名的环境变量*/ Line 431; store_tx_context(msr, r); /*保存交易上下文到r-notes字段中: Line 344; apr_table_setn(r-notes, NOTE_MSR, (void *)msr);*/ modsecurity.c, Line 267; modsecurity_tx_init; hook_request_early3 Line 277-281; /* 设置C-L(Content-Length) */ Line 284-296; /* 检查 此请求是否存在请求体*/ Line 299-301; /* 设置C-T (Content-Type) */ Line 337-340; /* 检查 是否必须缓 冲,若是则只是用内存。*/ Line 304-334; /* 确定针对请 求体的操作。挺重要的。*/ Line 380-390; /* 找到cookie headers 并解析*/ Line 343-359; /* 设置参数。在ARGS变量处理函数中会用到。*/ Line 348; 函数parse_arguments(); /*解析参数并存储*/ mod_security2.c, Line 676; hook_request_late; Line 738-746; /* REQUEST_HEADERS处理阶段 */ hook_request_late1 Line 691; msr = retrieve_tx_context(r); /* 取得交易上下文*/ Line 709; msr-dcfg2 = (directory_config *)ap_get_module_config(r-per_dir_config, /* 取得第二个配置信息*/ Line 713; msr-txcfg = create_directory_config(msr-mp, NULL); /* 创建交易上下文*/ Line 721; msr-txcfg = merge_directory_configs(msr-mp, msr-txcfg, msr-usercfg); /* 更新默认的用户设 置*/ Line 723; init_directory_config(msr-txcfg); /* 初始化配置结构体 */ Line 765-789; /* 检查请 求体是否过长 */ Line 799-843; /* 调用读取请求体的函数read_request_body(),并检查 返回结果 */ Line 792-797; /* 确定是否提取多重文件*/ Line 854; msr-request_headers = apr_table_copy(msr-mp, r-headers_in); /* 更新请求头*/ Line 857-867; /* REQUEST_BODY处理阶段 */ Line 872-875; /* 只有当后台需要时才移除客户端设置的压缩标识 。*/ Line 749-755; /* 检查 在阶段一中是否有禁用规则 引擎*/ mod_security2.c, Line 676; hook_request_late; hook_request_late2 Line 189; bb_in = apr_brigade_create(msr-mp, r-connection-bucket_alloc); /* */ Line 194; rc = ap_get_brigade(r-input_filters, bb_in, AP_MODE_READBYTES, APR_BLOCK_READ, HUGE_STRING_LEN); /*使用注册的input_filter中的处理函数 ,如ap_http_filter。*/ apache2_io.c, Line 157; read_request_body; hook_request_late3.1 Line 166; if (msr-reqbody_should_exist != 1) ; /*检查 是否存在请求体*/ Line 173; if (msr-txcfg-reqbody_access != 1) ; /*检查 是否允许访问请 求体*/ Line 184; if (modsecurity_request_body_start(msr, error_msg) reqbody_length + buflen (apr_size_t)msr-txcfg-reqbody_limit) ; /* 检查请 求体大小限制(should only trigger on chunked requests) */ Line 266; modsecurity_request_body_to_stream(msr, buf, buflen, error_msg); /* */ Line 309; modsecurity_request_body_end(msr, error_msg); /* */ apache2_io.c, Line 157; read_request_body; hook_request_late3.2 Line 272; int rcbs = modsecurity_request_body_store(msr, buf, buflen, error_msg); /* 重点。将从请求体中取到的数据存储到modsec_rec结构体的相关字段中。 */ Line 305; apr_brigade_cleanup(bb_in); /* */ Line 228; rc = apr_bucket_read(bucket, /* */ Line 97; msre_reqbody_processor_metadata *metadata =; /*获取请求体处理器的元数据结构体*/ Line 100-137; /*确定请求体处理器是否为空及其种类*/ msc_reqbody.c, Line 82; modsecurity_request_body_start; /* Prepare to accept the request body (part 1). */ hook_request_late3.3 Line 91; apr_pool_create( /*另外建立一个新的内存池用以分配新的数据结构(not data, which is allocated via malloc).*/ Line 95-138; if (msr-msc_reqbody_processor != NULL) ; /*初始化请求体处理器*/ Line 140; return modsecurity_request_body_start_init(msr, error_msg); /*调用请求体处理的第二部分*/ Line 56-74; /*为将请求体保存到磁盘中做准备*/ Line 58; msr-msc_reqbody_filename = apr_psprintf(msr-mp, “%s/%s-%s- request_body-XXXXXX”, msr-txcfg-tmp_dir, current_filetime(msr-mp), msr- txid); /*确定磁盘上存储请 求体的临时 文件名*/ msc_reqbody.c, Line 43; modsecurity_request_body_start_init; /* Prepare to accept the request body (part 2). */ hook_request_late3.4 Line 46-55; if(msr-msc_reqbody_storage = MSC_REQBODY_MEMORY) /* 为将请求体保存到内存中做准备*/ Line 49; msr-msc_reqbody_chunks = apr_array_make(msr-msc_reqbody_mp, 32, sizeof(msc_data_chunk *); /*创建准备存储请 求体数据的内存空间*/ Line 65; msr-msc_reqbody_fd = msc_mkstemp(char *)msr- msc_reqbody_filename); /* 在磁盘上创建保存请求体的临时 文件*/ Line 653; msr-msc_reqbody_fd = open(msr-msc_reqbody_filename, O_RDONLY | O_BINARY); /*打开磁盘上将要存储请 求体数据的文件*/ msc_reqbody.c, Line 621; modsecurity_request_body_retrieve_start; /*Prepares to forward the request body.*/ hook_request_late3.5 Line 628; msr-msc_reqbody_disk_chunk = apr_pcalloc(msr- msc_reqbody_mp, sizeof(msc_data_chunk); /*/ Line 646; msr-msc_reqbody_disk_chunk-data = apr_palloc(msr- msc_reqbody_mp, CHUNK_CAPACITY); /*/ Line 624; if (msr-msc_reqbody_storage = MSC_REQBODY_MEMORY) ; /*判 断请求体是否将存储在内存中*/ Line 637; if (msr-msc_reqbody_storage = MSC_REQBODY_DISK) ; /*判断请 求体是否将存储在磁盘中*/ Line 638; msr-msc_reqbody_disk_chunk = apr_pcalloc(msr- msc_reqbody_mp, sizeof(msc_data_chunk); /*/ msc_reqbody.c, Line 687; modsecurity_request_body_retrieve; /*Returns one chunk of request body data. It stores a NULL in the chunk pointer when there is no data to return. The return code is 1 if more calls can be made to retrieve more data, 0 if there is no more data to retrieve, or -1 on error. The caller can limit the amount of data returned by providing a non-negative value in nbytes. */ hook_request_late3.6 Line 653; if (msr-msc_reqbody_storage = MSC_REQBODY_DISK) ; Line 713-743; /*Advance to the current chunk and position on the next byte we need to send.*/ Line 700; if (msr-msc_reqbody_storage = MSC_REQBODY_MEMORY) ; Line 708; *chunk = msr-msc_reqbody_disk_chunk; /*/ Line 765; i = read(msr-msc_reqbody_fd, msr-msc_reqbody_disk_chunk-data, my_nbytes); Line 772; *chunk = msr-msc_reqbody_disk_chunk; Line 373; return modsecurity_request_body_store_disk(msr, data, length, error_msg); /*将请求体数据块存储到磁盘上*/ msc_reqbody.c, Line 293; modsecurity_request_body_store; /* Stores one chunk of request body data. */ hook_request_late3.7 Line 302-360; if (msr-msc_reqbody_processor != NULL) return modsecurity_request_body_store_memory(msr, data, length, error_msg); /*将请求体数据块存储在内存中*/ Line 236-257; /*分配新的存储请 求体数据的数据结构。*/ msc_reqbody.c, Line 166; modsecurity_request_body_store_memory; /* Stores one chunk of request body data in memory. */ hook_request_late3.9 Line 172-215; /* 检查 需要存储的请求体数据块是否超出规定的限制大小.*/ Line 234-282; /*while循环将请求体数据块中的数据转存储在相关的数据结构中 */ Line 259-265; /*当前数据结构的剩余空间足够存储请 求体数据*/ Line 266-280; /*当前数据结构空间有限,则填充满以后修改相关指针,并等待 下次循环新建一个结构体*/ Line 626-637; /* Put back the Accept-Encoding and TE request headers if they were removed from the request. */ Line 640-729; if (msr-of_status = OF_STATUS_NOT_STARTED) ; /* Initialise on first invocation */ Line 650; rc = modsecurity_process_phase(msr, PHASE_RESPONSE_HEADERS); /* RESPONSE_HEADERS处理阶段*/ Line 610-615; /* 检查 上下文内容是否为空*/ apache2_io.c, Line 602; output_filter; output_filter1 Line 668-689; ap_add_output_filter(“MODSECURITY_OUT”, msr, r, r- connection);/* 确定是否需要检查 response body. */ Line 692-711; /*

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论