Pyhon網(wǎng)絡(luò)編程10-實(shí)現(xiàn)TCP端口掃描與UDP端口掃描

一、端口掃描原理

?? 連接網(wǎng)絡(luò)設(shè)備時(shí),一般都會(huì)在網(wǎng)絡(luò)設(shè)備端選取0-65535之間的一個(gè)端口進(jìn)行連接,端口掃描是指:檢查網(wǎng)絡(luò)設(shè)備上0-65535號(hào)端口哪些端口是開(kāi)啟狀態(tài)。
TCP端口掃描
??TCP端口掃描過(guò)程如下:
?? 1、掃描端向目標(biāo)端發(fā)送SYN請(qǐng)求建立連接
?? 2、目標(biāo)端收到請(qǐng)求后,回復(fù)ACK同意連接并同意發(fā)送SYN請(qǐng)求建立連接
?? 3、掃描端收到后,以此來(lái)判斷端口是否存活
UDP端口掃描
??UDP掃描發(fā)送空的(沒(méi)有數(shù)據(jù))UDP報(bào)頭到每個(gè)目標(biāo)端口。 如果返回ICMP端口不可到達(dá)錯(cuò)誤(類(lèi)型3,代碼3), 該端口是closed(關(guān)閉的)。 其它ICMP不可到達(dá)錯(cuò)誤(類(lèi)型3, 代碼1,2,9,10,或者13)表明該端口是filtered(被過(guò)濾的)。 偶爾地,某服務(wù)會(huì)響應(yīng)一個(gè)UDP報(bào)文,證明該端口是open(開(kāi)放的)。

二、Python實(shí)現(xiàn)

2.1 Python腳本

??以下python腳本通過(guò)Scapy實(shí)現(xiàn)網(wǎng)絡(luò)主機(jī)發(fā)現(xiàn)、主機(jī)TCP端口掃描與主機(jī)UDP端口掃描

#!/usr/bin/python3.4
# -*- coding=utf-8 -*-

from kamene.all import *
import ipaddress

def host_scan(net):
    net = ipaddress.ip_network(net)
    ip_list = []
    for ip in net.hosts():  # 迭代可用的主機(jī)地址
        id_no = random.randint(1, 65535)
        pkt = IP(dst=str(ip))/ICMP(id=id_no,seq=1)
        #print(pkt.summary())
        result_raw=sr1(pkt,timeout=0.2, verbose=False)
        if result_raw == None:
            print(str(ip)+"不在線(xiàn)")
        elif result_raw != None:
            ip_list.append(str(ip))# ip默認(rèn)類(lèi)型未IPv4adress,需轉(zhuǎn)換為str類(lèi)型
            print(str(ip)+"在線(xiàn)")
    print("在線(xiàn)主機(jī)如下:\n%s"%ip_list)

def syn_scan_final(dstip,lport,hport):
    #發(fā)送SYN包,并且等待回應(yīng)##############目的端口可以為元組(lport,hport)##flag為SYN(S)#########
    port_list = []
    for p in range(int(lport), int(hport) + 1):
        source_port = random.randint(1024, 65535)
        pkt = IP(dst=dstip)/TCP(sport=source_port, dport=p,flags="S")
        print(pkt.summary())
        result_raw = sr1(pkt, verbose=False, timeout=0.3)  # 發(fā)送三層包,等待接收一個(gè)回應(yīng)
        if result_raw != None:
            if result_raw.getlayer(TCP).fields["flags"] == 18:
                port_list.append(str(p))
                print("TCP " + str(p) + "端口可達(dá),open")
        elif result_raw == None:
            print("TCP " + str(p) + "端口無(wú)響應(yīng)")
    print("%s 開(kāi)放的TCP端口為:%s\n" % (dstip,port_list))

def udp_port_scan(dstip,lport,hport):
    port_list=[]
    for p in range(int(lport),int(hport)+1):
        source_port = random.randint(1024, 65535)
        pkt=IP(dst=dstip)/UDP(sport=source_port,dport=p)
        print(pkt.summary())
        result_raw=sr1(pkt,verbose = False,timeout=0.3)#發(fā)送三層包,等待接收一個(gè)回應(yīng)
        if result_raw != None:
            if result_raw.haslayer(ICMP):
                icmpfields=result_raw.getlayer(ICMP).fields
                if icmpfields["type"] == 3 and icmpfields["code"] == 3:
                    print("UDP "+str(p)+"端口不可達(dá),close")
                else:
                    print("UDP " + str(p) + "端口被過(guò)濾,filtered")
            if result_raw.haslayer(UDP):
                print("UDP " + str(p) + "端口open")
                port_list.append(str(p))
        elif result_raw == None:
            print("UDP "+str(p)+"端口無(wú)響應(yīng)")
    print("%s 開(kāi)放的UDP端口為:%s\n" % (dstip, port_list))

if __name__ == '__main__':
    while True:
        print('''
        -----選擇功能-----
        1.主機(jī)掃描
        2.TCP端口掃描
        3.UDP端口掃描
        q.退出
        ''')
        choice = input("選擇功能>>>")
        try:
            if choice == '1':
                net = input("Net/mask>>>")
                host_scan(net)
            elif choice == '2':
                host = input('請(qǐng)你輸入掃描主機(jī)的IP地址: ')
                port_low =input('請(qǐng)你輸入掃描端口的最低端口號(hào): ')
                port_high = input('請(qǐng)你輸入掃描端口的最高端口號(hào): ')
                syn_scan_final(host,port_low,port_high)
            elif choice == '3':
                host = input('請(qǐng)你輸入掃描主機(jī)的IP地址: ')
                port_low = input('請(qǐng)你輸入掃描端口的最低端口號(hào): ')
                port_high = input('請(qǐng)你輸入掃描端口的最高端口號(hào): ')
                udp_port_scan(host, port_low, port_high)
            elif choice == 'q':
                break
            else:
                print("輸入錯(cuò)誤?。?)
        except Exception:
            pass

2.2 主機(jī)掃描

??執(zhí)行腳本選擇主機(jī)掃描,輸入需要掃描的網(wǎng)段后,會(huì)發(fā)送ICMP包來(lái)探測(cè)主機(jī)是否在線(xiàn)。



主機(jī)掃描

2.3 TCP端口掃描

??執(zhí)行腳本選擇TCP端口掃描,輸入目標(biāo)IP,與端口范圍后開(kāi)始進(jìn)行探測(cè)。



TCP端口掃描

2.4 UDP端口掃描

??執(zhí)行腳本選擇UDP端口掃描,輸入目標(biāo)IP,與端口范圍后開(kāi)始進(jìn)行探測(cè)。



UDP端口掃描
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容