端口扫描
本次实验主要对主机扫描和端口扫描原理的理解。使用python(scapy库)编写端口扫描程序,对目标IP(包含IP地址段)进行扫描,完成以下功能:
1)使用icmp协议探测主机是否开启;
2)对本机(关闭防火墙)的开放端口和非开放端口完成半连接、ACK、FIN、Null、Xmas、windows扫描,并与nmap扫描结果进行比较。
3)对远程(有防火墙)主机的开放端口和非开放端口完成半连接、ACK、FIN、Null、Xmas、windows扫描,并与2)进行比较,分析结果。
4)回答问题:样例程序中“conf.L3socket=L3RawSocket”的作用是什么?
2 实验步骤及结果
多图预警
1. 使用icmp协议探测主机是否开启;
这里通过引入scapy包中包含的IP和ICMP包完成基于icmp协议的主机探测。
大概思路就是首先讲输入的ip地址转为IPY中的对象,这个类能够将输入的字符串ip转为ip地址列表,从而挨个进行探测。然后构造IP层,并将IP地址放到该IP层中,接着将ICMP协议搭载到上面构造的IP层上,接着将需要传输的探测数据一起构造完成包组装。最后咱们需要把封装的包发送出去并接收目的主机返回的数据从而判断该主机是否开启。scapy提供了接收内容的函数,分别是sr、sr1、srp,其中sr、sr1主要用于第三层,srp用于第二层。这里我们使用sr1方法。
具体代码如下:
测试结果如下:
a) 探测局域网主机
b) 探测公网主机(www.baidu.com[110.242.68.3])
2. 对本机(关闭防火墙)的开放端口和非开放端口完成半连接、ACK、FIN、Null、Xmas、windows扫描,并与nmap扫描结果进行比较。
启动主机(worker2)并关闭防火墙,如下:
a) 半连接
半连接扫描又称SYN扫描,该过程不会和服务端建立完整的连接,首先客户端会发送一个带有SYN标识和端口号的TCP数据包给服务器,如果服务器这个端口是开放的,则会接受这个连接并返回一个带有SYN和ACK标识的数据包给客户端,随后客户端会返回带有RST标识的数据包而不是返回一个带有ACK和RST标识的数据包。
i. 代码
代码主要原理也是基于上述过程,通过发送一个TCP试探包给目的主机的目的端口,如果返回的flags是SA,则该口是开放的,否则该端口是关闭的。代码具体如下:
ii. 代码扫描结果:
- 开放端口(22)
- 非开放端口(80)
iii. Nmap扫描结果
- 开放端口(22)
- 非开放端口(80)
b) ACK
TCP ACK 扫描能说明端口是否被过滤。如果使用nmap -sA就会发现他只会返回两种结果unfiltered和filtered,因为nmap -sA就是ACK扫描的。判断端口是否被过滤,分为两种情况:
a) 发送一个flags为ACK报文,open(开放的)和closed(关闭的) 端口 都会返回RST报文,至于他们是open还是closed状态我们无法确定。不响应的端口,或者发送特定的ICMP错误消息(类型3,代号1,2,3,9,10, 或者13)的端口,标记为 filtered(被过滤的)。
b) 上面那种情况下是服务器REJECT掉数据包,所以客户端会有个ICMP包返回,如果是直接DROP掉的话,就会什么也不会返回,所以我们要判断该主机是否存在,因为如果一个主机存在的话,向它发送一个flags为ACK包的话,无论端口是否关闭都会有返回一个flags为RST包,如果是DROP是话就会一个数据包都不会返回,所以我们可以利用这一点去判断端口是否被过滤了。
ii. 代码
根据ACK访问原理,我们这里没有办法判断该端口是开放还是关闭,因此我们的代码也只能返回时有没有被过滤,代码如下:
iii. 代码扫描结果
- 开放端口(22)
- 非开放端口(80)
iv. Nmap扫描结果
- 开放端口(3306)
- 非开放端口(80)
c) FIN
FIN 扫描会向服务器发送带有 FIN 标识和端口号的 TCP 数据包。如果没有服务器端回应则说明端口开放。如果服务器返回一个 RST 数据包,则说明目标端口是关闭的。如果服务器返回了一个 ICMP 数据包,其中包含 ICMP 目标不可达错误类型3以及 ICMP 代码为1,2,3,9,10或13,则说明目标端口被过滤了无法确定端口状态。
i. 代码
FIN扫描很多时候也能够被对方服务器给过滤掉,所以使用FIN扫描的时候会有三种状态,open、close和filtered,代码如下:
ii. 代码扫描结果
- 开放端口(22)
- 非开放端口(80)
iii. Nmap扫描结果
- 开放端口(22)
- 非开放端口(80)
d) Null
TCP Null扫描在空扫描中,客户端发出的 TCP 数据包仅仅只会包含端口号而不会有其他任何的标识信息。如果目标端口是开放的则不会回复任何信息。如果服务器返回了一个 RST(或者RST+ACK) 数据包,则说明目标端口是关闭的。如果返回 ICMP 错误类型3且代码为1,2,3,9,10或13的数据包,则说明端口被服务器过滤了。
i. 代码
和上述原理一致,代码同样编写的时候需要检测RST和ICMP返回的错误类型。代码如下:
ii. 代码扫描结果
- 开放端口(22)
- 非开放端口(80)
iii. Nmap扫描结果
- 开放端口(22)
- 非开放端口(80)
e) Xmas
在发送的数据包中设置PSH,FIN,URG标志位,如果目标端口是开放的则不会回复任何信息。如果目标端口关闭则会返回一个RST+ACK的数据包。但如果服务器返回了一个 ICMP 数据包,其中包含 ICMP 目标不可达错误类型3以及 ICMP 状态码为1,2,3,9,10或13,则说明目标端口被过滤了无法确定是否处于开放状态。
i. 代码
在发送的数据包中设置FPU代码,通过返回的RA还是ICMP数据包来判断是否开放。代码如下:
ii. 代码扫描结果
- 开放端口(22)
- 非开放端口(80)
iii. Nmap扫描结果
- 开放端口(22)
- 非开放端口(80)
f) Windows
TCP 窗口扫描的流程同 ACK 扫描类似,同样是客户端向服务器发送一个带有 ACK 标识和端口号的 TCP 数据包,但是这种扫描能够用于发现目标服务器端口的状态。在 ACK 扫描中返回 RST 表明没有被过滤,但在窗口扫描中,当收到返回的 RST 数据包后,它会检查窗口大小的值。如果窗口大小的值是个非零值,则说明目标端口是开放的。如果返回的 RST 数据包中的窗口大小为0,则说明目标端口是关闭的。
i. 代码
通过发送带有ACK的包到目标主机,如果目标主机的tcp返回结果window等于0,则是关闭的,如果大于0,则是开放的。代码如下:
ii. 代码扫描结果
- 开放端口(22)
- 非开放端口(80)
iii. Nmap扫描结果
- 开放端口(22)
- 非开放端口(80)
结果分析:
从nmap的角度来看一个被扫描的端口可能处于3种状态:开放,关闭和被过滤。 半开放扫描器发送一个SYN数据给TCP端口,希望获得一个SYN/ACK数据包或者RST/ACK 。收到前者表示目标端口是开着的,收到后者表示是关着的。当然还存在第三种情况,那就是什么都没获得,这种情况只能说明数据包被过滤了,这个端口到底开着或者没开,nmap也不知道。但是这种扫描方式不会完成3次握手,也就是它故意不返回ACK给已经响应了SYN/ACK数据包的开放端口。因此SYN扫描也称为半开放扫描; FIN,XMAS,NULL 扫描的操作是基于同一个原理,就是当某个关闭端口突然收到一个没有设置SYN,ACK或RST控制位的TCP数据包时,通常是一个RST去响应这个令人诧异的数据包,但如果是一个开放的端口,TCP将不做任何响应;TCP ACK扫描向每个被扫描的端口发送一个TCP ACK数据包。如果目标数据包发送出去有接收到RST(不是RST/ACK数据包)说明端口是开放或者关闭的,没有回信表示被过滤了。ACK扫描的目的并不是确定某个端口是开着的还是关着的,它是为了确定一个端口是否被一个有状态的防火墙过滤了。
3. 对远程(有防火墙)主机的开放端口和非开放端口完成半连接、ACK、FIN、Null、Xmas、windows扫描,并与2)进行比较,分析结果。
启动另外一台主机(worker2)并开启防火墙,如下:
a) 半连接
i. 开放端口(22)
ii. 非开放端口(80) 报错
b) ACK
i. 开放端口(22)
ii. 非开放端口(80)
c) FIN
i. 开放端口(22)
ii. 非开放端口(80)
d) Null
i. 开放端口(22)
ii. 非开放端口(80)
e) Xmas
i. 开放端口(22)
ii. 非开放端口(80)
f) Window
i. 开放端口(22)
ii. 非开放端口(80)
g) 结果分析
通过上述多个图的实验,可以比较明显的看出来,开了防火墙的主机,会对包进行过滤,这点从ACK、NULL、FIN、Xmaxs这几个都提示端口可能开了或者是包可能被过滤了。由于80端口确实没有开,可以明显的知道,那肯定是包被过滤了。甚至于,使用示例程序完成的半连接SYN扫描来扫描未开放的端口是直接报错了,说明防火墙把要返回来的包筛选掉之后才反过来,导致报错。
总结来说,开了防火墙能够极大增强网络保护,降低被扫描检测端口的风险,生活中推荐开启。
4. 回答问题:样例程序中“conf.L3socket=L3RawSocket”的作用是什么?
Raw Socket,即原始套接字,它工作在网络层或数据链路层,而不是和其他Socket一样工作在传输层,它可以接收本机网卡上的数据帧或者数据包,对与监听网络的流量和分析是很有作用的。这句代码能够将当前Scapy配置中的发包参数L3socket参数改为L3RawSocket,从而能够监听本机流量,如果是在本机进行测试的话,添加这句代码,能够正常监听到流量并正常返回,否则由于由于src和dst是一个地址,会出现无法收到包的情况。经过实际测试,在本机做测试的时候,如果将这句代码注释,不开放的端口也将返回与开放端口一样的结果,经过wireshark抓包分析,是因为未收到数据。如果扫描的是另一台主机,则可以不用该句代码。
5. 总结
经过大量实验,可以证明windows平台和linux/unix平台确实有许多不同点,在端口扫描这部分来说,能够检测到linux平台的可能检测不到windows平台的。比如ack探测中,如果仅凭ttl的跳数来判断的话,windows是128,linux是64,这个跟系统有关系。
另外,本次实验也从网络包底层程序来实验了关于nmap的端口探测程序原理,比较实用,对于攻击情报收集也具有较大作用。但是,经过后续防火墙实验,感觉最大的敌人已经不是探测了,如何绕过防火墙完成真正的探测才是更应该继续深入研究的一部分问题。
6. 参考文献
无
评论区