使用Scapy发送tcp有效负载:为什么会吃掉一个字节?

使用Scapy发送tcp有效负载:为什么会吃掉一个字节?,tcp,scapy,payload,Tcp,Scapy,Payload,我的问题如下:我想用scapy实现一个监听服务来刺激一个蜜罐(因为蜜罐使用一个假的ip,所以我不能使用OS套接字),我选择了scapy 我实现了一个非常简单的TCP握手过程,但有一件事让我很沮丧:我使用PSH发送的数据包的一个字节被吃掉了 例如,我向客户机发送“abc”,但客户机的套接字(例如netcat或wget)只接收“bc”。另一个例子是“HTTP/1.1200ok”变为“TTP/1.1200ok”。我捕获了数据包,wireshark可以正确地将我手工制作的数据包识别为HTTP,但客户端套

我的问题如下:我想用scapy实现一个监听服务来刺激一个蜜罐(因为蜜罐使用一个假的ip,所以我不能使用OS套接字),我选择了scapy

我实现了一个非常简单的TCP握手过程,但有一件事让我很沮丧:我使用PSH发送的数据包的一个字节被吃掉了

例如,我向客户机发送“abc”,但客户机的套接字(例如netcat或wget)只接收“bc”。另一个例子是“HTTP/1.1200ok”变为“TTP/1.1200ok”。我捕获了数据包,wireshark可以正确地将我手工制作的数据包识别为HTTP,但客户端套接字只缺少1个字节。我不知道为什么

代码如下: 192.168.1.100代表服务器(my)ip地址,9999是端口。例如,我在192.168.1.100上运行这个python脚本,然后使用“nc192.168.1.1009999”。我希望得到“abc”,但我只能得到“bc”,但数据包在Wireshark中似乎没有问题。真奇怪

“”
创建于2012年6月2日
@作者:根
'''
从scapy导入所有
从scapy.layers.inet导入IP、ICMP、TCP
从scapy.packet导入ls,原始
从scapy.sendrecv导入嗅探,发送
从scipy.signal.signaltools导入lfilter
全部导入
HOSTADDR=“192.168.1.100”
TCPPORT=9999“要侦听的端口”
序号=100
添加_TEST=“abc”
def tcp_监视器_回调(pkt):
全局序号
全球技术支持
如果(pkt.payload.payload.flags==2):
'一个syn情况,2代表syn'
打印(“tcp传入连接”)
ACK=TCP(sport=TCPPORT,dport=pkt.payload.payload.sport,flags=“SA”,ACK=pkt.payload.payload.seq+1,seq=0)
发送(IP(src=pkt.payload.dst,dst=pkt.payload.src)/ACK)
如果(pkt.payload.payload.flags&8!=0):
'接受来自客户端的推送,8表示PSH标志'
打印(“tcp推送连接”)
pushLen=len(包装有效载荷。有效载荷。载荷)
httpPart=TCP(sport=TCPPORT,dport=pkt.payload.payload.sport,flags=“PA”,ack=pkt.payload.payload.seq+pushLen)/Raw(加载=添加测试)
“这里有问题!!!!”!!!!如果我发送abc,客户端套接字只接收bc,一个字节消失!!!但客户端接收的数据包是正确的'
发送(IP(src=pkt.payload.dst,dst=pkt.payload.src)/httpPart)
如果(pkt.payload.payload.flags&1!=0):
“接受来自cilent的fin”
打印(“tcp fin连接”)
FIN=TCP(sport=TCPPORT,dport=pkt.payload.payload.sport,flags=“FA”,ack=pkt.payload.payload.seq+1,seq=pkt.payload.ack)
发送(IP(src=pkt.payload.dst,dst=pkt.payload.src)/FIN)
def调度程序回调(pkt):
打印“数据包传入”
全球主机地址
全球技术支持
如果(pkt.haslayer(TCP)和(pkt.payload.dst==HOSTADDR)和(pkt.payload.dport==TCPPORT)):
tcp_监视器_回调(pkt)
其他:
返回
如果uuuu name uuuuuu='\uuuuuuu main\uuuuuuu':
打印“蜜罐侦听模块测试”
scapy.all.conf.iface=“eth0”
嗅探(筛选器=(“(tcp dst端口%s)和dst主机%s”)%(TCPPORT,HOSTADDR),prn=调度程序_回调)
一些建议:

  • Sniff可能会将一些有效负载附加到数据包的末尾,因此
    len(pkt.payload.payload.load)
    可能不是实际的有效负载长度。您可以使用
    pkt[IP].len-40
    (40是IP+TCP的公共头长度)。您还可以使用
    -len(pkt[IP].options)-len(pkt[TCP].options)
    获得更准确的结果
  • 通常TCP上面的应用程序层使用换行符(\r\n)来分隔命令,因此您最好将
    ADD\u TEST
    更改为
    “abc\r\n”

  • 如果以上方法都不起作用,您可以升级到最新的netcat并重试。

    我测试了您的代码,您缺少发送正确的tcp序列

    httpPart=TCP(sport=TCPPORT,dport=pkt.payload.payload.sport,flags=“PA”,ack=pkt.payload.payload.seq+pushLen,seq=pkt.payload.ack)/Raw(load=ADD\u测试)


    如果要解决这个问题,您可能会遇到其他数据包长度问题,但被吃掉的1字节是由于缺少正确的tcp序列造成的

    ,尽管5天过去了,从那时起我就没有做过这方面的工作,但还是要感谢您的回答:)