编写自己的漏扫—Web漏洞扫描技巧篇

首先我们要了解到漏洞扫描器的扫描原理怎样的
网络漏洞扫描器对目标系统进行漏洞检测时 , 首先探测目标系统的存活主机 , 对存活主机进行端口扫描 , 确定系统听开放的端口 , 同时根据协议指纹技术识别出主机的操作系统类型 。
然后扫描器对开放的端口进行网络服务类型的识别 , 确定其提供的网络服务 。
漏洞扫描器根据目标系统的操作系统平台和提供的网络服务 , 调用漏洞资料库中已知的各种漏洞进行逐一检测 , 通过对探测响应数据包的分析判断是否存在漏洞 。
 
一.编码/解码/协议在很久以前有人提问 AMF 格式的请求怎么进行检测 , 或者有什么工具可以检测?
既然我们要讲解的是 Web 漏洞扫描器 , 那么就先假设是 AMF over HTTP
假设我们需要测试一个 AMF 格式数据的 SQL 注入问题 , 那么按照通常的思路就是在 SQL 注入模块中

  1. 先解析 HTTP 中 AMF 格式数据
  2. 然后在测试参数中填写 payload
  3. 重新封装 AMF 格式数据
  4. 发送 HTTP 请求
 
伪代码如下:
req = {"method": "POST", "url": "http://fatezero.org", "body": "encoded data"}data = https://www.isolves.com/it/aq/wl/2019-12-10/decode_amf(req["body"])for key, value in data.items(): d = copy.deepcopy(data) d[key] = generate_payload(value) body = encode_amf(d) requests.request(method=req["method"], url=req["url"], body=body)整个流程下来没什么问题 , 但是如果又来了一个 X 协议(X over HTTP) , 那么我们就得继续修改 SQL 注入模块以便支持这种 X 协议
但是扫描器中可不是只有 SQL 注入检测模块 , 还有其他同类模块 , 难道每加一个新协议我还得把所有检测模块都改一遍?
所以我们需要把这些协议解析和封装单独抽出来放在一个模块中 。
 
伪代码如下:
# utils.pydef decode(data): if is_amf(data): data = decode_amf(data) if is_X(data): data = decode_X(data) # 递归 decode for i in data: data[i] = decode(data[i]) return data# detect_module.pyreq = {"method": "POST", "url": "http://fatezero.org", "body": "encoded data"}data = decode(req["body"])for key, value in data.items(): d = copy.deepcopy(data) d[key] = generate_payload(value) body = encode(d) requests.request(method=req["method"], url=req["url"], body=body)上面的递归 decode 主要是为了解码某种格式的数据里面还有另外一种格式的数据 , 虽然看起来这种场景比较少见
但是仔细想一下 multipart 带着 json , json 里的字符串是另外一个 json 字符串 , 是不是又觉得这种情况也并不少见 。
那 encode/decode 剥离出来就可以了吗?请注意到上面伪代码使用了 requests.request 发送请求
那如果某天需要我们去测试 websocket 协议 , 那是不是又得在检测模块中多加一套 websocket client 发送请求?
所以我们也需要将具体的网络操作给剥离出来 , 具体的协议类型直接由上面来处理 , 检测模块只需要关注具体填写的 payload 。
 
伪代码如下:
for key, value in x.items(): data.reset() x[key] = generate_payload(value) x.do() # 负责将数据重新组装成原来的格式 , 并按照原始协议发送 # check因为每个检测模块的检测依据大致就几种:
  • 返回内容
  • 消耗时间 (time based)
  • 另外一条信道的数据 (比方说 DNSlog)
所以即便是我们将网络操作剥离出来也不会影响检测的效果 。
 
在编写检测模块的时候 , 编写者可以不用关心基础协议是什么 , 怎么对数据编码解码 , 只用关心根据 value 生成 payload 并填写到相对应的 key 中 , 
假如某天出现了这么一种流行编码格式 http://www.a.com/key1,value1,key2,value2 , 那我们所有的检测模块也无需修改
仅仅需要在上一层再添加一套 encode/decode 操作即可 。假如某天出现了一种比较流行的协议 , 我们也仅需要在上一层提供一套 client 即可 。
检测模块的工作就仅仅剩下生成并填写 payload
 
二.分类在 2014 年的时候 , 我做了大量的竞品分析 , 包括使用逆向工程逆向商业的 Acunetix WVS, HP Webinspect, IBM AppScan, Netsparker 扫描逻辑 , 也包括阅读开源的 w3af, arachni 代码 。


推荐阅读