找回密码
 立即注册

扫一扫,访问微社区

QQ登录

只需一步,快速开始

查看: 4379|回复: 1

[求助] dpkt解析http长连接包

1

主题

2

帖子

2

积分

贫民

积分
2
python_for7 发表于 2017-7-26 10:26:55 | 显示全部楼层 |阅读模式
本帖最后由 python_for7 于 2017-7-26 10:41 编辑

因为dpkt解析长连接包会报错,所以修改了http.py里的一行代码:
  1. <div class="blockcode"><blockquote>def parse_body(f, headers):
  2.     ...
  3.     elif 'content-length' in headers:
  4.     n = int(headers['content-length'])
  5.     body = f.read(n)
  6.     if len(body) != n:
  7.         <b>if 'expect' not in headers:</b>
  8.             raise dpkt.NeedData('short body (missing %d bytes)' % (n - len(body)))
复制代码

现在长连接的http包能解析出来了,但解析的包里的内容好像有重复,导致在拼接body的时候,长度和预期的content-length不符合,不知道怎么改了,谁有类似的经历吗?或者解析http长包有其它方法可以用?

以下是我解析httpbody的代码:

  1. # coding:utf-8

  2. from mydpkt import Request
  3. from mydpkt import Reader, Ethernet

  4. rh_log = open('e:\\rh.pcap','rb')
  5. rh_file = Reader(rh_log)
  6. # p.setfilter('tcp port 80')
  7. expect_request_switch = False
  8. expect_respone_switch = False
  9. body_lenth = 0
  10. keep_alive_index = 0
  11. body_persistent = ''
  12. body_all = []
  13. index = 0
  14. for index, (ptime, pdata) in enumerate(rh_file).__iter__():
  15.     p = Ethernet(pdata)
  16.     ip = p.data
  17.     if ip.__class__.__name__ == 'IP':
  18.         dst_ip = '%d.%d.%d.%d' % tuple(map(ord, list(ip.dst)))
  19.         src_ip = '%d.%d.%d.%d' % tuple(map(ord, list(ip.src)))
  20.         tcp = ip.data
  21.         # dport = tcp.dport
  22.         if tcp.__class__.__name__ == 'TCP' and len(tcp.data) > 1:
  23.             dport = tcp.dport
  24.             sport = tcp.sport
  25.             received_string = str(tcp.data)
  26.             if expect_request_switch:
  27.                 if 'HTTP/1.1 100 Continue' in tcp.data:
  28.                     keep_alive_index = index
  29.                     expect_respone_switch = True
  30.                 if (index >= (keep_alive_index + 1)) and expect_respone_switch and dport == 80:
  31.                     body_persistent += received_string
  32.                     body_persistent_lenth = len(body_persistent)
  33.                     if body_persistent_lenth >= body_lenth:
  34.                         print 'body:\n{}'.format(body_persistent)
  35.                         body_all.append(body_persistent)
  36.                         expect_request_switch = False
  37.                         expect_respone_switch = False
  38.                         body_persistent = ''
  39.             if dport == 80 and expect_respone_switch is False:
  40.                 try:
  41.                     rq = Request(received_string)
  42.                     Request_body = rq.body
  43.                     Request_headers = rq.headers
  44.                     Request_method = rq.method
  45.                     Request_uri = rq.uri
  46.                     # print 'headers:{}'.format(Request_headers)
  47.                     if 'expect' in Request_headers.keys():
  48.                        expect_request_switch = True
  49.                        body_lenth = int(Request_headers.get('content-length'))
  50.                except Exception as e:
  51.                    # print tcp.data
  52.     pass
复制代码



回复

使用道具 举报

1

主题

2

帖子

2

积分

贫民

积分
2
python_for7  楼主| 发表于 2017-7-26 10:35:48 | 显示全部楼层
主要逻辑是请求和响应两个长连接开关,都满足长连接获取条件后,开关打开并获得‘content-length’长度,body变量开始直接存储http数据,当长度≥‘content-length’,两个开关同时关闭,继续解析剩下的包
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表