SDR 两种方法可视化打飞机ADS-B 信号接收与航班追踪引言什么是ADS-B与SDRADS-BAutomatic Dependent Surveillance–Broadcast是一种飞机自动广播自身位置、速度、高度等信息的通信协议。每架现代飞机每隔几秒就会广播一条ADS-B消息包含经纬度、高度、航班号等关键数据。而SDRSoftware Defined Radio软件定义无线电是一种通过软件替代传统硬件电路来解调无线电信号的设备例如RTL-SDR这种廉价USB电视棒就能接收ADS-B信号。通过SDR接收飞机信号再配合Python进行数据分析我们可以轻松实现打飞机即追踪航班的可视化。本文将介绍两种方法方法一使用预编译工具dump1090快速搭建接收站方法二使用Python库pyModeS从底层解码ADS-B信号。两种方法各有优劣适合不同技术水平的读者。—## 基础概念ADS-B信号结构ADS-B信号位于1090 MHz频率采用脉冲位置调制PPM编码。一条完整的ADS-B消息包含-前导码8微秒用于同步-数据块112比特包含DF下行链路格式、ICAO地址、位置、速度、航班号等信息理解这些基础后我们可以开始动手实践。—## 方法一使用dump1090快速可视化### 1. 安装与配置dump1090是一个流行的开源工具支持RTL-SDR直接输出ADS-B数据。它可以将接收到的数据通过HTTP服务器实时展示在地图上。安装步骤以Ubuntu为例bash# 安装依赖sudo apt-get install librtlsdr-dev libusb-1.0-0-dev git cmake# 克隆源码git clone https://github.com/antirez/dump1090.gitcd dump1090make### 2. 运行并查看可视化界面插入RTL-SDR设备后运行bash./dump1090 --interactive --net参数说明---interactive在终端实时显示飞机列表---net启动网络服务器打开浏览器访问http://localhost:8080你将看到类似雷达的实时地图每架飞机显示为绿色图标点击可查看航班号、高度、速度等详细信息。### 3. 进阶导出JSON数据dump1090还支持通过--json参数输出结构化数据方便后续分析bash./dump1090 --json --net --quiet数据格式示例简化版json[ { icao: 780A1B, flight: CCA1234, lat: 39.9042, lon: 116.4074, altitude: 10000, speed: 450, track: 270 }]—## 方法二使用Python与pyModeS从零解码对于希望深入理解ADS-B协议或进行自定义分析的读者推荐使用Python库pyModeS。它提供了完整的ADS-B解码函数无需依赖外部工具。### 安装依赖bashpip install pyModeS numpy matplotlib### 完整代码示例从SDR原始数据到航班追踪以下代码演示如何使用Python接收并解码ADS-B信号最终可视化航班位置。python# 导入必要的库import pyModeS as pmsimport numpy as npimport matplotlib.pyplot as pltfrom mpl_toolkits.basemap import Basemap # 需要安装basemap或使用cartopy# 模拟接收到的原始ADS-B消息实际应用中来自SDR设备# 格式十六进制字符串共28个字符112比特raw_messages [ 8D4840D6202CC371C32CE0576098, 8D4840D6202CC371C32CE0576180, 8D4840D6202CC371C32CE0576210]def decode_and_visualize(messages): 解码ADS-B消息并可视化航班位置 flights {} # 存储航班信息{icao: {lat, lon, alt, flight}} for msg in messages: # 检查消息有效性前8个字符为DF类型 df pms.df(msg) if df ! 17: # DF17表示ADS-B消息 continue icao pms.icao(msg) # 提取ICAO地址 tc pms.typecode(msg) # 提取类型码 # 根据类型码解码不同信息 if tc 1 and tc 4: # 航班号 flight pms.adsb.flight(msg) if flight: flights[icao] flights.get(icao, {}) flights[icao][flight] flight.strip() elif tc 11: # 经纬度奇数/偶数帧 # 需要成对接收奇数偶数帧才能解码位置 if icao not in flights: continue # 简化处理这里仅做示意 flights[icao][lat] 40.0 # 实际需解码 flights[icao][lon] 116.0 elif tc 19: # 速度与高度 velocity pms.adsb.velocity(msg) if velocity: flights[icao][speed] velocity[speed] flights[icao][altitude] velocity[altitude] # 可视化在地图上绘制航班 plt.figure(figsize(12, 8)) m Basemap(projectionmerc, llcrnrlat30, urcrnrlat45, llcrnrlon110, urcrnrlon125, resolutionl) m.drawcoastlines() m.drawcountries() for icao, info in flights.items(): if lat in info and lon in info: x, y m(info[lon], info[lat]) m.scatter(x, y, s100, cred, markero) plt.text(x, y, info.get(flight, icao), fontsize8, hacenter) plt.title(ADS-B Flight Tracking Visualization) plt.show() print(fDecoded {len(flights)} aircraft)# 执行解码与可视化decode_and_visualize(raw_messages)代码说明-pyModeS.df()提取下行格式DF17是ADS-B消息特征-pyModeS.icao()获取飞机唯一标识-pyModeS.adsb.flight()解码航班号需类型码1-4- 实际应用中需结合SDR硬件如通过rtl-sdr库读取实时的IQ数据### 高级用法实时数据流处理对于需要长期运行的追踪系统可以使用如下架构pythonimport socketimport jsonfrom pyModeS import adsb# 连接dump1090的JSON数据流sock socket.socket(socket.AF_INET, socket.SOCK_STREAM)sock.connect((localhost, 30002)) # dump1090默认JSON端口def process_realtime_data(): 实时处理航班数据 buffer while True: data sock.recv(4096).decode() buffer data # 解析换行分隔的JSON行 while \n in buffer: line, buffer buffer.split(\n, 1) if line: try: plane json.loads(line) icao plane.get(icao) flight plane.get(flight, Unknown) lat plane.get(lat) lon plane.get(lon) alt plane.get(altitude) print(fICAO: {icao}, Flight: {flight}, fPosition: ({lat}, {lon}), Alt: {alt}m) except json.JSONDecodeError: pass# 启动实时追踪# process_realtime_data() # 取消注释以运行—## 两种方法对比与总结| 方法 | 优点 | 缺点 | 适用场景 ||------|------|------|----------|| dump1090 | 开箱即用、自带可视化、性能稳定 | 依赖外部工具、灵活性低 | 快速搭建观测站 || pyModeS Python | 完全可控、可自定义分析、适合教学 | 开发成本高、需处理底层细节 | 协议研究、定制化系统 |总结ADS-B信号接收与航班追踪是SDR技术最直观的应用之一。通过dump1090初学者可在5分钟内看到飞机实时位置而使用Python的pyModeS库则能深入理解协议细节实现从原始比特到可视化地图的完整链路。两种方法相辅相成前者适合快速验证后者适合深度学习。无论选择哪种方式这个过程都能让你真切体会到用软件定义无线电的魅力——原来我们身边的电磁波里正飞行着无数个数字飞机。