前言
在内网中,好的信息搜集能力能够帮助开发者更快地拿到权限及达成目标。内网里的数据多种多样,需要根据需求寻找任何能对下一步渗透行动有所帮助的信息。
ICMP主机发现
差错通知
当IP数据包在对方计算机处理过程中出现未知的发送错误时,ICMP会向发送者传送错误事实以及错误原因等
信息查询
信息查询由一个请求和一个应答构成。只需要向目标发送一个请求数据包,如果收到了来自目标的回应,就可以判断目标是活跃主机,否则亦然。
代码展示
先导入相关的函数库
from scapy.all import *
from random import randint
from optparse import OptionParser
对用户输入的参数进行接收和批量处理,并将处理后的IP地址传入Scan函数
def main():
parser = OptionParser("Usage:%prog -i <target host> ") #输出帮助信息
parser.add_option('-i',type='string',dest='IP',help='specify target host') #获取IP地址参数
options,args = parser.parse_args()
print("Scan report for " + options.IP + "\n")
#判断是单台主机还是多台主机
#IP中存在-,说明是要扫描多台主机
if '-' in options.IP:
#代码举例:192.168.101.1-120
#通过'-'进行分隔,把192.168.101.1和120分开
#把192.168.1.1通过","进行分隔,取最后一个数作为range函数的start,然后把120+1作为range函数的stop
#这样循环遍历出需要扫描的IP地址
for i in range(int(options.IP.split('-')[0].split('.')[3]),int(options.IP.split('-')[1])+1):
Scan(options.IP.split('.')[0] + '.' + options.IP.split('.')[1] + '.' + options.IP.split('.')[2] + '.' + str(i))
time.sleep(0.2)
else:
Scan(options.IP)
print("\Scan finished!...\n")
这里重点是理解optparse这个函数,参考链接在这,大佬写得非常详细
https://blog.csdn.net/qfikh/article/details/83338304
这个函数的作用主要是读取用户输入的参数,然后对输入的IP范围字符串进行切割然后拼接传入Scan函数中进行执行,options返回的是一个字典,字典的值为参数值。
Scan函数通过调用ICMP,将构造好的请求包发送到目的地址,并根据目的地址应答数据判断目标主机是否存活。
def Scan(ip):
ip_id = randint(1,65535)
icmp_id = randint(1,65535)
icmp_seq = randint(1,65535)
packet = IP(dst=ip,ttl=64,id=ip_id) / ICMP(id=icmp_id,seq=icmp_seq) /b'rootkit'
result = sr1(packet,timeout=1,verbose=False)
if result:
for rcv in result:
scan_ip = rcv[IP].src
print(scan_ip + '--->' 'Host is up')
else:
print(ip + '--->' 'Host is down')
这里我利用kali的scapy解析一下IP数据包和ICMP数据包的构造原理
上述代码的意思主要是:先构造一个ICMP数据包,去除坏字符,然后发送给指定的IP目标主机,sr1是只发送一个数据包,将sr1包的内容存进result这个变量中,如果有数据包返回,就遍历出IP段中的src字段中的值,并打印该主机存活,否则该主机不存活,为了更好地理解,我这里在kali中举个例子
最后定义主函数入口,调用所有函数
if __name__ == '__main__':
try:
main()
except KeyboardInterrupt:
print("interrupted by user, killing all threads...")
在linux上运行成功
导入nmap包加快速率
导入相应的函数库
import nmap
import optparse
定义NmapScan函数通过调用nm.scan()函数,传入-sn -PE
参数,发起ping扫描,并打印出扫描后的结果
def NmapScan(targetIP):
#实例化PortScanner对象
nm = nmap.PortScanner()
try:
#host为目标IP地址,arguments为Nmap的扫描参数
#-sn:使用ping进行扫描
#-PE:使用ICMP的echo请求包(-PP:使用timestamp请求包 -PM:network请求包)
result = nm.scan(hosts=targetIP,arguments='-sn -PE')
#对结果进行切片,提取主机状态信息
state = result['scan'][targetIP]['status']['state']
print("[{}] is [{}]".format(targetIP,state))
except Exception as e:
pass
最后利用optparse模块生成命令行参数化形式,对用户输入的参数进行接收和批量处理,最后将处理后的IP地址传入NmapScan函数
if __name__ == '__main__':
parse = optparse.OptionParser('Usage: python %prog -i ip \n\n'
'Example: python %prog -i 192.168.1.1[192.168.1.1-100]\n')
#添加目标IP参数-i
parse.add_option('-i','--ip',dest='targetIP',default='192.168.75.1',type='string',help='target ip address')
options,args = parse.parse_args()
#判断是单台主机还是多台主机
#IP中存在"-",说明是要扫描多台主机
if '-' in options.targetIP:
# 代码举例:192.168.101.1-120
# 通过'-'进行分隔,把192.168.101.1和120分开
# 把192.168.1.1通过","进行分隔,取最后一个数作为range函数的start,然后把120+1作为range函数的stop
# 这样循环遍历出需要扫描的IP地址
for i in range(int(options.targetIP.split('-')[0].split('.')[3]), int(options.targetIP.split('-')[1]) + 1):
NmapScan(options.targetIP.split('.')[0] + '.' + options.targetIP.split('.')[1] + '.' + options.targetIP.split('.')[2] + '.' + str(
i))
else:
NmapScan(options.targetIP)
print("\Scan finished!...\n")
运行效果