2017-08-15 227 views
2

对于Scool中的Projekt,我需要嗅探新的tcp握手包的网络流量。我想自动为此tcp连接创建一个新的iptables规则,并将其放入docker容器中。iptables忽略pakage由scapy发送

#!/usr/bin/env python2 

import subprocess 
from scapy.all import * 

def find_tcp_handshake(port, docker_ip): 
    global SYN 
    global ACK 
    # sniff for new syn pakage and send the pakage to function process_handshake() 
    sniff(lfilter=lambda x: x.haslayer(TCP) and str(x[TCP].dport) == port and x[TCP].flags & SYN and not x[TCP].flags & ACK, prn = lambda x:  process_handshake(paket = x, port = port, docker_ip = docker_ip)) 

def process_handshake(paket, port, docker_ip): 
    # get the four tcp parameter (destination an source - port and ip) 
    destination_port = port 
    source_ip = str(paket[IP].src) 
    source_port = str(paket[TCP].sport) 
    # add the iptables rule 
    add_ipt_rule(destination_ip = docker_ip, destination_port = destination_port, source_ip = source_ip, source_port = source_port) 
    # remove the ethernet layer (make sometimes problems) 
    paket = paket[IP] 
    # remove checksums (make sometimes problems) 
    del paket[TCP].chksum 
    del paket[IP].chksum 
    # this pakage will not arrive the docker container 
    send(paket) 

# funktion to send commands to bash 
def command (c): 
    return subprocess.Popen(c.split(" "), stdout=subprocess.PIPE).stdout.read().rstrip() 

# this rules are created from docker by default with the argument -p 80:80. I've added the source_ip and source_port part 
def add_ipt_rule(destination_ip, destination_port, source_ip, source_port): 
    command("iptables -I DOCKER -d " + destination_ip + "/32 -s " + source_ip + " ! -i docker0 -o docker0 -p tcp -m tcp --dport " + destination_port + " -j  ACCEPT") 
    command("iptables -t nat -I POSTROUTING -s " + destination_ip + "/32 -d " + destination_ip + "/32 -p tcp -m tcp --dport " + destination_port + " -j  MASQUERADE") 
    command("iptables -t nat -I DOCKER ! -i docker0 -p tcp -m tcp -s " + source_ip + " --sport " + source_port + " --dport " + destination_port + " -j  DNAT --to-destination " + destination_ip + ":" + destination_port) 

# my original script creates docker container itself and manage these in a sqlite database 
def main(): 
    docker_ip = "127.17.0.2" 
    port = "80" 
    find_tcp_handshake(port = port, docker_ip = docker_ip) 


# TCP-Flags for sniff rule (not all in use) 
FIN = 0x01 
SYN = 0x02 
RST = 0x04 
PSH = 0x08 
ACK = 0x10 
URG = 0x20 
ECE = 0x40 
CWR = 0x80 

if __name__ == "__main__": 
    main() 

嗅探正在工作,iptables命令正在工作。

问题是当我用scapy重新发送pakage。它应该适合码头集装箱。但这个pakage永远不会达到iptables规则。当我从客户端重新发送包裹时,规则正在工作。

scapy上是否有方法将包发送到iptables?

感谢您的帮助

回答

1

Scapy的低水平发送数据包,它们不是由netfilter的看到。如果要发送由netfilter显示的数据包,可以将它们从另一台计算机发送出去,也可以使用常规的socket API让主机的IP堆栈为您发送数据包。