我正在尝试实现一个python traceroute,它发送UDP消息并通过原始套接字接收ICMP响应。我遇到了一个ICMP数据包似乎不惜一切代价避免捕获的问题。 ICMP响应在wireshark中显示为我所期望的,但套接字从不接收任何要读取的数据。另一个复杂因素是我在运行Ubuntu的VirtualBox上运行代码,因为sendto()不会在Windows 7中获取数据包。(我在windows中运行wireshark来捕获数据包)。奇怪的是,当我从虚拟机运行python脚本时,wireshark将捕获ICMP消息。但是,当我尝试在Windows上运行脚本时,ICMP消息不会显示在wireshark中。 (UDP数据包神奇地开始在Windows上工作)
我已经玩过各种不同版本的设置套接字的在线示例,并使用bind()而不使用它,但没有配置似乎产生一个读取的套接字。它只是等待读取ICMP消息的时间。
还应该注意,如果我尝试读取我的udp发送套接字,它会成功读取udp数据包。一旦我将IPPROTO_ICMP设置为读取超时。
receive_response方法:
def receive_response(rec_socket, packetid, tsend, timeout):
remain = timeout
print packetid
while remain > 0:
ready = select.select([rec_socket], [], [], remain)
if ready[0] == []:
return
print 'got something'
设置套接字:
rec_socket = socket.socket(socket.AF_INET, socket.SOCK_RAW, ICMP_CODE)
rec_socket.setsockopt(socket.SOL_IP, socket.IP_HDRINCL, 1)
rec_socket.bind(("",0)) #played with using this statement and skipping it
致电接收只是:
reached = receive_response(rec_socket, packetid, time.time(), timeout)
答案 0 :(得分:0)
看起来问题是VirtualBox默认使用NAT连接到网络。这意味着虚拟机将不会因ICMP消息而接收ICMP消息。似乎解决方案是将VirtualBox网络配置为使用“桥接网络”模式。不幸的是我无法确认这一点,因为我无法在桥接模式下在我大学的网络上设置虚拟机。至于他们没有在Windows中工作的原因,它必须与Windows缺乏对原始套接字的支持有关。