于是乎,理所当然,我临时将这个事宜定性为 Node.js 的一个 Bug。
Node.js 源码排查
http.js -> _http_server.js -> _http_common.js
源码以 Node.js 8.9.2 为准。
这里先预留一下我们能立时想到的 node_http_parser.cc,而先讲这几个文件,是有原因的——这涉及到最后的一个应对方法。
认定了它是个 Bug 之后,我就开端了一贯的看源码环节——因为这个 Bug 的复现前提比脚绫趋显,我临时将其定性为“Node.js HTTP 办事端模块在接到请求后解析 HTTP 数据包的时刻解析 URI 时出了问题”。
起首看看 lib/http.js 的响应源码:
在扫描的时刻,如不雅当缁ご态是 URI 相干的(如 s_req_path、s_req_query_string 等),则履行一个子 switch,琅绫擎的处理如下:
- 若当缁ぶ符是空格,则将状况改变为 s_req_http_start 并认为 URI 已经解析好了,经由过程宏 CALLBACK_DATA() 触发 URI 解析好的事宜;
- 若当缁ぶ符是换行符,则解释还在解析 URI 的时刻就被换行了,后面就弗成能跟着 HTTP 协定版本的申清楚明了,所以设置默认的 HTTP 版本为 0.9,并修改当缁ご态,最后认为 URI 已经解析好了,经由过程宏 CALLBACK_DATA() 触发 URI 解析好的事宜;
- 其余情况(所有其它字符)下,经由过程调用 parse_url_char() 函数来解析一些器械并更新当缁ご态。(因为哪怕是在解析 URI 状况中,也还有各类不合的细分,如 s_req_path、s_req_query_string )
- ...
- const server = require('_http_server');
- const { Server } = server;
- function createServer(requestListener) {
- return new Server(requestListener);
- }
那么,立时进入 lib/_http_server.js 看吧。
起首是创建一个 HttpParser 并绑上监听获取到 HTTP 数据包后解析结不雅的回调函数的代码:
- const {
- parsers,
- ...
- } = require('_http_common');
- function connectionListener(socket) {
- ...
- var parser = parsers.alloc();
- parser.reinitialize(HTTPParser.REQUEST);
- parser.socket = socket;
- socket.parser = parser;
- parser.incoming = null;
- ...
- state.onData = socketOnData.bind(undefined, this, socket, parser, state);
- ...
- socket.on('data', state.onData);
- ...
- }
- function socketOnData(server, socket, parser, state, d) {
- assert(!socket._paused);
- debug('SERVER socketOnData %d', d.length);
- var ret = parser.execute(d);
- onParserExecuteCommon(server, socket, parser, state, ret, d);
- }
大年夜源码中文我们能看到,当一个 HTTP 请求过来的时刻,监听函数 connectionListener() 会拿着 Socket 对象加上一个 data 事宜监听——一旦有请求连接过来,就去履行 socketOnData() 函数。
而在 socketOnData() 函数中,做的重要工作就是 parser.execute(d) 来解析 HTTP 数据包,在解析完成后履行一下回调函数>
推荐阅读
黑客在渗入渗出一个网站时,受制于本身的黑客才能以及小我思维宽度,在想尽了一切办法后,却一无所得,最终就不得不走上了暴力破解这一条陆辜暴力破解的道理就是穷举法,其根本思惟是根据标题标部分前提>>>详细阅读
本文标题:Node.js中遇到含空格URL的神奇“Bug”——小范围深入HTTP协议
地址:http://www.17bianji.com/lsqh/39781.html
1/2 1

网友点评
精彩导读
科技快报
品牌展示