使用Masscan扫描器进行信息搜集

Masscan 是一款极为高效的端口扫描工具,以其卓越的扫描速度和大规模扫描能力而著称。该工具不仅支持 TCP 和 UDP 协议的扫描,还允许用户根据需求灵活指定多个目标和端口。Masscan 通过采用先进的网络性能优化技术,充分利用操作系统的资源和多核处理能力,实现了极高的扫描效率和吞吐量。其强大的性能使它能在短时间内扫便互联网的每个角落。使用 Masscan,用户可以迅速了解目标主机的服务状态和潜在漏洞,并且工具提供多种灵活的输出格式和报告,便于后续的分析和处理。

源代码编译

由于该扫描器的底层采用了 Npcap 接口实现,因此在使用扫描器之前,用户需要先下载并安装Npcap库。安装完成后,用户需要下载Masscan的源代码,可以点击masscan-1.3.2.zip下载版本。

我们以下载源代码为例,下载好以后将其解压缩至任意位置。其中masscan-1.3.2/vs10目录下为Windows平台下的解决方案,读者可以使用Visual Studio打开该项目。在打开后会让读者升级项目此时点击升级即可,当升级结束后若直接对项目进行编译则会出现错误提示。
在这里插入图片描述
此时,读者可打开微软针对编译器的说明网站,由于笔者使用的是Visual Studio 2013则其对应的_MSC_VER为1800,读者只需要记录下这个编号。

在这里插入图片描述

接着,读者可在解决方案管理器内找到misc目录,并打开string_s.h头文件,打开后定位到第58行并将其中的1900替换为1800并保存文件,至此再次点击编译生成即可。当生成结束后会在其bin目录下得到masscan.exe扫描器成品。

在这里插入图片描述

使用扫描器探测

使用Masscan扫描常见的TCPUDP端口,可以在命令中直接指定。但默认情况下只会扫描TCP端口,若要扫描UDP端口则需要额外的参数配置。不过,Masscan 对于UDP扫描的支持并不如TCP扫描那样全面,建议在需要进行深入的UDP扫描时使用Nmap等工具。

我们通过使用-p参数来执行扫描常见的TCP端口,此处进扫描的端口包括 FTP(21)、SSH(22)、Telnet(23)、SMTP(25)、DNS(53)、HTTP(80)、POP3(110)、NetBIOS(139)、IMAP(143)、HTTPS(443)、SMB(445)、RDP(3389)。使用U来指定扫描UDP端口,此处扫描的端口包括DNS(53)、NTP(123)、SNMP(161),在扫描时我们通过使用0.0.0.0/8来指定网段。使用-oJ指定将扫描结果生成为JSON格式的报告,当然也可使用-oX指定生成XML报告。

masscan -p21,22,23,25,53,80,110,139,143,443,445,3389,U:53,U:123,U:161 0.0.0.0/8 -oJ output.json

若要扫描整个互联网则需要通过--exclude 255.255.255.255来指明。如下命令所示,通过0.0.0.0/0指定扫描全网段,并通过-p参数指定仅扫描HTTP(80)及HTTPS(443),执行命令后则会对整个互联网中的所有Web服务器进行探测,并输出为output_all.json格式的报告。

masscan -p80,443 0.0.0.0/0 --exclude 255.255.255.255 -oJ output_all.json

运用GeoIP2数据库解析

GeoIP2 是由MaxMind提供的一套地理位置数据库和API,用于将IP地址映射到地理位置信息。GeoIP2 数据库可以提供关于IP地址的详细地理信息,如国家、城市、经纬度、时区、自治系统(AS)等。其被广泛应用于各类需要地理位置数据的场景,如内容定制、安全、广告投放和数据分析等。

GeoIP2数据包含两部分内容,首先读者需要使用pip install geoip2来安装Python版本的接口,其次读者还需要自行下载对应的GeoLite2 database 数据库文件。

解析扫描结果

在之前我们通过使用Masscan扫描器扫描了世界范围内的所有Web服务器存活状态,并将扫描结果存储为了output_all.json格式的JSON文件中,接下来我们将通过使用Python解析这个数据库文件,并输出解析到的结果。

封装parse_scan_results函数,该函数接收一个扫描结果,并将该扫描结果解析为一个列表嵌套字典的格式,其中包含了基本的扫描信息,例如主机IP地址、扫描时间、端口号、TTL值等,并返回这个列表给调用者。

import json
from datetime import datetime, timezone
import geoip2.database"""解析扫描结果文件,并返回一个包含字典的列表。:param filename: 包含扫描结果的 JSON 文件路径:return: 一个包含解析结果的列表,每个元素是一个字典
"""
def parse_scan_results(filename):results_list = []# 从文件中读取 JSON 数据with open(filename, 'r') as file:data = json.load(file)# 提取所需的信息并保存到列表中for result in data:ip = result['ip']timestamp = int(result['timestamp'])# 转换时间戳为具体时间readable_time = datetime.fromtimestamp(timestamp, timezone.utc).strftime('%Y-%m-%d %H:%M:%S')for port_info in result['ports']:port = port_info['port']ttl = port_info['ttl']# 将结果保存到字典中result_dict = {'IP地址': ip,'扫描时间': readable_time,'端口': port,'TTL': ttl}results_list.append(result_dict)return results_list

封装get_geo_info函数,该函数通过使用GeoIP2数据库,打开并查询IP地址的详细位置信息,并将该信息转换为一个字典格式返回给调用者。

"""通过 GeoIP2 数据库查询 IP 地址的地理信息。:param ip_address: 需要查询的 IP 地址:param db_path: GeoIP2 数据库文件的路径:return: 包含地理信息的字典
"""
def get_geo_info(ip_address, db_path):try:# 打开 GeoIP2 数据库reader = geoip2.database.Reader(db_path)# 查询 IP 地址的地理信息response = reader.city(ip_address)# 提取所需的地理信息geo_info = {'国家': response.country.name,'国家ISO代码': response.country.iso_code,'省份': response.subdivisions.most_specific.name,'省份ISO代码': response.subdivisions.most_specific.iso_code,'城市': response.city.name,'邮政编码': response.postal.code,'纬度': response.location.latitude,'经度': response.location.longitude,'时区': response.location.time_zone,'精度半径': response.location.accuracy_radius,'大洲': response.continent.name,'大洲代码': response.continent.code}# 关闭数据库reader.close()return geo_infoexcept FileNotFoundError:# print(f"数据库文件 {db_path} 未找到。")return {}except geoip2.errors.AddressNotFoundError:# print(f"IP 地址 {ip_address} 未找到地理信息。")return {}except Exception as e:# print(f"出现错误: {e}")return {}

封装combine_scan_geo_info函数,用于将结合扫描结果和地理信息,生成包含完整信息的列表嵌套字典。封装format_combined_results函数,用于 格式化解析后的扫描结果和地理信息,并返回一个包含字典的列表。

"""结合扫描结果和地理信息,生成包含完整信息的列表嵌套字典。:param scan_results: 扫描结果列表:param db_path: GeoIP2 数据库文件的路径:return: 包含完整信息的列表,每个元素是一个字典
"""
def combine_scan_geo_info(scan_results, db_path):combined_results = []for result in scan_results:ip = result['IP地址']geo_info = get_geo_info(ip, db_path)combined_result = {**result, **geo_info}combined_results.append(combined_result)return combined_results"""格式化解析后的扫描结果和地理信息,返回一个包含字典的列表。:param results_list: 包含扫描结果和地理信息的列表,每个元素是一个字典:return: 格式化后的结果列表
"""
def format_combined_results(results_list):formatted_results = []for result in results_list:formatted_result = {"IP地址": result.get("IP地址", ""),"扫描时间": result.get("扫描时间", ""),"端口": result.get("端口", ""),"TTL": result.get("TTL", ""),"国家": result.get("国家", ""),"国家ISO代码": result.get("国家ISO代码", ""),"省份": result.get("省份", ""),"省份ISO代码": result.get("省份ISO代码", ""),"城市": result.get("城市", ""),"邮政编码": result.get("邮政编码", ""),"纬度": result.get("纬度", ""),"经度": result.get("经度", ""),"时区": result.get("时区", ""),"精度半径": result.get("精度半径", ""),"大洲": result.get("大洲", ""),"大洲代码": result.get("大洲代码", "")}formatted_results.append(formatted_result)return formatted_results

封装analyze_ip_distribution函数,该函数用于分析IP地址的地理分布情况,统计每个国家的IP地址数量,并返回详细信息。

"""分析 IP 地址的地理分布情况,统计每个国家的 IP 地址数量,并返回详细信息。:param results_list: 包含扫描结果和地理信息的列表,每个元素是一个字典:return: 包含国家、IP 列表和 IP 数量的列表,每个元素是一个字典
"""
def analyze_ip_distribution(results_list):country_distribution = {}for result in results_list:country = result.get("国家", "未知")ip_address = result.get("IP地址", "")if country not in country_distribution:country_distribution[country] = {"国家": country, "IP列表": [], "数量": 0}country_distribution[country]["IP列表"].append(ip_address)country_distribution[country]["数量"] += 1# 将字典转换为列表country_distribution_list = list(country_distribution.values())return country_distribution_list
绘制全球IP数量分布

通过调用analyze_ip_distribution函数,我们还可以进一步分析这个扫描结果,获取到不同国家的IP地址信息,及所在国家的IP数量等,代码如下所示;

if __name__ == "__main__":# 文件名filename = './output_all.json'db_path = './GeoLite2-City.mmdb'# 解析扫描结果scan_results = parse_scan_results(filename)# 结合扫描结果和地理信息combined_results = combine_scan_geo_info(scan_results, db_path)# 格式化结果formatted_results = format_combined_results(combined_results)# 分析 IP 地址的地理分布情况ip_distribution = analyze_ip_distribution(formatted_results)# 打印分析结果for country_info in ip_distribution:print(f"国家: {country_info['国家']}, IP数量: {country_info['数量']}, IP列表: {country_info['IP列表']}")

运行上述代码,则可获取到不同国家的IP分布信息,如下图所示;因扫描仅进行了一小部分,则当前解析结果并不全面,仅用于研究代码案例。

在这里插入图片描述

接着通过使用pyecharts库,我们根据IP地址数量及国家分布,绘制一个数量分布柱状图,实现代码如下所示;

from pyecharts.charts import Bar
from pyecharts import options as optsif __name__ == "__main__":# 文件名filename = './output_all.json'db_path = './GeoLite2-City.mmdb'# 解析扫描结果scan_results = parse_scan_results(filename)# 结合扫描结果和地理信息combined_results = combine_scan_geo_info(scan_results, db_path)# 格式化结果formatted_results = format_combined_results(combined_results)# 分析 IP 地址的地理分布情况ip_distribution = analyze_ip_distribution(formatted_results)# 过滤掉国家为美国的数据filtered_ip_distribution = [country_info for country_info in ip_distribution if country_info["国家"] != "United States"]# 提取国家和IP数量countries = [country_info["国家"] for country_info in filtered_ip_distribution]ip_counts = [country_info["数量"] for country_info in filtered_ip_distribution]# 创建柱状图bar = Bar()bar.add_xaxis(countries)bar.add_yaxis("IP数量", ip_counts)bar.set_global_opts(title_opts=opts.TitleOpts(title="全球IP数量分布(不包括美国)"),xaxis_opts=opts.AxisOpts(axislabel_opts=opts.LabelOpts(rotate=45)),yaxis_opts=opts.AxisOpts(name="IP数量"))# 渲染图表为HTML文件bar.render("ip_distribution.html")

由于美国地区的IP地址过多,此处为了能展示柱状图效果则忽略美国地区的IP数量,这样能更好地展示柱状图分布,其运行效果如下图所示;

在这里插入图片描述

绘制全球IP位置分布

通过filename传入扫描后的记录信息,并调用GeoLite2-City.mmdb城市数据库文件,将IP地址解析并组合为一个新的扫描结果,通过循环输出给用户。

if __name__ == "__main__":# 文件名filename = './output_all.json'db_path = './GeoLite2-City.mmdb'# 解析扫描结果scan_results = parse_scan_results(filename)# 结合扫描结果和地理信息combined_results = combine_scan_geo_info(scan_results, db_path)# 格式化结果formatted_results = format_combined_results(combined_results)# 打印格式化后的结果for result in formatted_results:print(result)

通过循环的方式依次验证IP地址所对应的数据库信息,读者可以获取到包括IP地址、扫描时间、扫描端口、TTL值、国家、国家ISO代码、省份、省份ISO代码、城市、邮政编码、纬度、经度、时区、精度半径、大洲、大洲代码等信息,如下图所示;

在这里插入图片描述

KML(Keyhole Markup Language)是一种用于表示地理数据的 XML 格式文件。KML 文件通常用于在地理信息系统(GIS)和地理应用(如 Google Earth 和 Google Maps)中显示地理数据。我们可以将扫描到的数据进行归纳,并调用generate_kml_from_results函数提取出所需要的IP地址及经纬度信息,并将其生成为一个独立的KML文件。

def retKML(addr, longitude, latitude):# 确保 longitude 和 latitude 为浮点数,如果为 None 或无效值则设置为 0.0try:longitude = float(longitude)except (TypeError, ValueError):longitude = 0.0try:latitude = float(latitude)except (TypeError, ValueError):latitude = 0.0kml = ('<Placemark>\n''<name>{}</name>\n''<Point>\n''<coordinates>{:.6f},{:.6f}</coordinates>\n''</Point>\n''</Placemark>\n').format(addr, longitude, latitude)return kmldef generate_kml_from_results(results_list, output_file):kmlheader = '<?xml version="1.0" encoding="UTF-8"?>\n<kml xmlns="http://www.opengis.net/kml/2.2">\n<Document>\n'kmlfooter = '</Document>\n</kml>\n'with open(output_file, "w") as f:f.write(kmlheader)for result in results_list:ip = result.get("IP地址", "")longitude = result.get("经度", 0.0)latitude = result.get("纬度", 0.0)kml_placemark = retKML(ip, longitude, latitude)f.write(kml_placemark)f.write(kmlfooter)if __name__ == "__main__":# 文件名filename = './output_all.json'db_path = './GeoLite2-City.mmdb'# 解析扫描结果scan_results = parse_scan_results(filename)# 结合扫描结果和地理信息combined_results = combine_scan_geo_info(scan_results, db_path)# 格式化结果formatted_results = format_combined_results(combined_results)# 生成 KML 文件output_file = "GoogleEarth.kml"generate_kml_from_results(formatted_results, output_file)

通过将KML文件导入到谷歌地图中,我们可以很直观的在地图上进行打点操作,打点后每个国家的详细信息都将被呈现,如下图所示;

在这里插入图片描述

通过拉近一个国家,则可看到每一个打过标记的IP分布位置图,如下所示;

在这里插入图片描述

至此,本次的技术分享就到此结束了。事实上,在获取到IP地址的在线状态后,我们可以继续使用Nmap扫描器对其进行操作系统的鉴别。当鉴别到每一个IP地址的操作系统版本后,我们就可以推测出这个国家所使用的操作系统比例,并以此来衡量每个国家的操作系统普及程度及进一步评估其国家的系统安全系数。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/414583.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

基于北斗+自组网技术的光伏电场人员位置监控系统优化方案

一、方案背景 1.1 用户需求 随着我国经济的快速发展&#xff0c;光伏电场等新能源项目的建设日益增多。然而&#xff0c;这些项目往往位于偏远地区&#xff0c;通信基础设施不完善&#xff0c;导致施工人员在作业过程中难以与外界保持实时联系。特别是在无人区或信号弱的地区…

【Qt 事件】—— 详解Qt事件处理

目录 &#xff08;一&#xff09;事件介绍 &#xff08;二&#xff09;事件的处理 &#xff08;三&#xff09;按键事件 3.1 单个按键 3.2 组合按键 &#xff08;四&#xff09;鼠标事件 4.1 鼠标单击事件 4.2 鼠标释放事件 4.3 鼠标双击事件 4.4 鼠标移动事件 4.5…

101.SAP MII功能详解(15)Workbench-Transaction Logic(Iterator)

目录 1.Logic->Iterator 2.演示 配置连接 Iterator使用示例 1.Logic->Iterator 您可以使用此操作迭代循环浏览List&#xff0c;迭代是指遍历某个List数据结构&#xff0c;逐个访问其元素的过程。迭代使用的场景不多。 2.演示 配置连接 Iterator使用示例 数据源是Lis…

Qt:玩转QPainter序列九(文本,文本框,填充)

前言 继续承接序列八 正文 1. drawImage系列函数 绘制图像 inline void drawImage(const QPoint &p, const QImage &image); 作用: 在指定的点 p 上绘制 QImage 图像。图像的左上角将对齐到 p 点。 inline void drawImage(int x, int y, const QImage &image,…

[001-07-001].Redis7缓存双写一致性之更新策略探讨

1、面试题&#xff1a; 1.只要使用缓存&#xff0c;就可能会涉及到redis缓存与数据库双存储双写&#xff0c;只要是双写&#xff0c;就存在数据一致性问题&#xff0c;那么是如何解决数据一致性问题的2.双写一致性&#xff0c;你先动缓存redis还是数据库MySQL&#xff0c;哪一个…

新能源汽车超级电容和电池能量管理系统的simulink建模与仿真

目录 1.课题概述 2.系统仿真结果 3.核心程序与模型 4.系统原理简介 4.1 电池模型 4.2 电池荷电状态&#xff08;SOC&#xff09;估算 4.3 超级电容器模型 4.4 能量管理 5.完整工程文件 1.课题概述 新能源汽车的能量管理系统&#xff08;Energy Management System, EMS…

中国艺术孙溟㠭凿篆《无用之用》

孙溟㠭凿篆作品《无用之用》 这方作品是孙溟㠭先生用凿木的方式凿刻出来的&#xff0c;呈现出了凿痕的效果&#xff0c;与众不同。 孙溟㠭凿篆《无用之用》 孙溟㠭凿篆《无用之用》 万般皆有所用&#xff0c;取其长补余短&#xff0c;无用之用是为大用&#xff0…

JS实现高度不等的列表虚拟滚动加载

当我们拿到后台返回的1万条数据展示时&#xff0c;如果完全渲染不仅渲染的时间很长&#xff0c;也会导致浏览器性能变差&#xff0c;使用过程中还可能会导致卡顿&#xff0c;使用体验变差。 就需要我们想办法优化这种情况&#xff0c;这个时候使用虚拟滚动加载就能很好的避免这…

ESXi服务器无法安装Windows11:“不符合此版本的Windows所需最低系统要求“

目录 一、问题描述1.使用环境2.问题截图3.问题解析 二、解决方法Ⅰ1.按 ShiftF10 弹出命令提示符2.在弹出的Dos框中输入regedit&#xff0c;回车&#xff0c;进入注册表。3.打开HKEY_LOCAL_MACHINE\SYSTEM\Setup&#xff0c;并新建 LabConfig 的项&#xff0c;在 LabConfig 下创…

SAP 查询中间表

可以看到如下代码中&#xff0c;查询了底表zdbconn&#xff0c;又查了中间表ZTFI0072 DATA: gv_dbs(20) ,go_exc_ref TYPE REF TO cx_sy_native_sql_error,gv_error_text TYPE string,lv_count TYPE syst_index.SELECT SINGLE conntxtFROM zdbconn INTO gv_dbsWHERE sy…

RK3568 Android 11 蓝牙BluetoothA2dpSink 获取用于生成频谱的PCM

Android 中的 A2DP Sink A2DP Sink 在 Android 系统中主要用于 接收 其他蓝牙设备&#xff08;如手机、平板、电脑等&#xff09;发送过来的 高质量的立体声音频。简单来说&#xff0c;它让你的 Android 设备可以充当一个 蓝牙音箱 或 耳机 的角色。 核心功能&#xff1a; 接…

【Java】SpringBoot 单体项目创建 与 整合 Mybatis-Plus

文章目录 前言1. 创建项目与整合MP1.1 IDEA创建SpringBoot项目1.2 SpringBoot整合Mybatis-Plus 2. 远程仓库2.1 创建远程仓库/本地仓库2.2 Add/Commit/Push/Pull 3. 总结与补充3.1 解决refusing to merge unrelated histories3.2 总结3.3 结语 参考资料 SpringBoot 单体项目创建…

Hadoop环境搭建

一、Linux环境准备 Linux命令查询https://www.linuxcool.com/ http://linux.51yip.com/ 安装Linux虚拟机 安装 sudo apt install open-vm-tools 安装 sudo apt install open-vm-tools-desktop &#xff08;可选&#xff09;换国内源 ​​ sudo apt update 更新软件列表&…

火焰传感器详解(STM32)

目录 一、介绍 二、传感器原理 1.原理图 2.引脚描述 三、程序设计 main.c文件 IR.h文件 IR.c文件 四、实验效果 五、资料获取 项目分享 一、介绍 火焰传感器是一种常用于检测火焰或特定波长&#xff08;760nm-1100nm&#xff09;红外光的传感器。探测角度60左右&am…

Docker占用根目录/存储空间过多如何清理?

问题背景 使用df -h查看磁盘空间时发现根目录空间不多了&#xff0c;已使用96%&#xff0c;红色警告&#xff01;&#xff01;&#xff01; 于是使用df -h /* 一层一层定位&#xff0c;终于找到了一个大文件 9G多的文件夹&#xff0c;位置是&#xff1a; /var/lib/docker/o…

无线通信-WIFI通信

文章目录 1. 基础知识2. 工作模式3. AT指令4. 常用AT指令实例5. 连接原子云6. 使用usb转ttl模块测试ATK-MW8266D7. 使用STM32F103ZET6战舰开发板透传模式8. 使用STM32F103ZET6战舰板连接原子云 1. 基础知识 ATK-ESP-01 ATK-ESP-01模块支持标准的IEEE802.11b/g/n协议&#xff0c…

【Linux】文件魔法师:时间与日历的解密

欢迎来到 CILMY23 的博客 &#x1f3c6;本篇主题为&#xff1a;文件魔法师&#xff1a;时间与日历的解密 &#x1f3c6;个人主页&#xff1a;CILMY23-CSDN博客 &#x1f3c6;系列专栏&#xff1a;Python | C | C语言 | 数据结构与算法 | 贪心算法 | Linux | 算法专题 | 代码…

【uniapp重大bug】uni-data-select的localdata改变,也会触发@change方法

bug描述 uni-data-select的下拉列表值localdata是动态获取的&#xff0c;且绑定了change方法&#xff0c;在页面加载后&#xff0c;请求localdata的列表数据&#xff0c;给localdata重新赋值&#xff0c;此时发现自动触发了change方法 当前uni版本&#xff1a;^2.0.2-30709202…

Axure RP10安装教程(Pro版)

下载链接 https://ga90eobypbb.feishu.cn/docx/UyzSd4q8SoXySjxtrcac4QnVn3f Axure RP 是一款专业的快速原型设计工具。它能帮助用户高效地创建网页和移动应用的线框图、流程图、原型和规格说明文档。拥有丰富的交互组件&#xff0c;可模拟各种复杂交互效果&#xff0c;如点击…

【千帆AppBuilder】使用Python调用基于官方的API创建图片故事的应用,一起体验下全代码模式下是怎样的效果

欢迎来到《小5讲堂》 这是《千帆》系列文章&#xff0c;每篇文章将以博主理解的角度展开讲解。 温馨提示&#xff1a;博主能力有限&#xff0c;理解水平有限&#xff0c;若有不对之处望指正&#xff01; 目录 背景基本信息名称简介角色指令 能力扩展组件对话开场白推荐问 模型选…