Files
CCSDS_study/test/Tianwen-1-frame-analysis-v2.md
2026-05-05 21:54:35 +08:00

6.7 KiB
Raw Permalink Blame History

Tianwen-1-frame-analysis-v2.py 新手说明

这个文件是一个“天问一号遥测帧分析脚本”。如果用新手的话说,它做的事情就是:

读取一大包二进制遥测数据,把它拆成一帧一帧,再按航天器 ID、虚拟信道和 APID 分类,最后把不同数据字段画成图片保存下来,方便人工观察这些遥测字段怎么变化。

输入数据

脚本读取的数据文件是:

/home/zjz/CCSDS_study/Tianwen/tianwen1_frames_20200730.u8

这个文件是一串连续的原始字节。脚本认为每 220 个字节是一帧 AOS frame所以会把它整理成

帧数 x 220字节

也就是一个二维数组,每一行代表一帧。

依赖的本地模块

脚本主要依赖两个本地文件:

Tianwen/ccsds.py
Tianwen/tianwen1_tm.py

ccsds.py 负责解析 CCSDS AOS 帧和 Space Packet。

tianwen1_tm.py 负责把天问一号的原始时间戳转换成 numpy.datetime64,这样 matplotlib 才能按时间画图。

为什么要设置 matplotlib 的 Agg 后端

WSL 下直接调用 plt.show() 经常会因为没有图形界面而报错。

所以脚本使用:

matplotlib.use("Agg")

意思是:不要弹出图形窗口,只把图保存成 PNG 文件。

所有图片最后会保存到:

/home/zjz/CCSDS_study/Tianwen/frame_analysis_figures

脚本整体流程

脚本主要分成以下几步:

  1. 设置路径和 matplotlib 环境。
  2. 读取 tianwen1_frames_20200730.u8
  3. 把原始字节按 220 字节切成 AOS 帧。
  4. ccsds.AOSFrame.parse(...) 解析每一帧。
  5. 统计 AOS 主头中的版本号、航天器 ID、虚拟信道 ID。
  6. 分别分析 Spacecraft 82 / VC 1Spacecraft 245 / VC 3Spacecraft 245 / VC 1
  7. 从 AOS 帧中重组 Space Packet。
  8. 按 APID 把 Space Packet 分类。
  9. 对多个 APID 的载荷字段按 uint8int16float64 解释。
  10. 绘制时间序列图、帧丢失图、APID 热力图。
  11. savefig(...) 保存所有图片。

关键概念解释

AOS Frame

AOS Frame 可以理解为“航天器遥测传输的一帧”。每一帧里有头部字段,也有承载的数据。

本脚本中每帧固定 220 字节。

Spacecraft ID

spacecraft_id 用来区分数据属于哪个航天器或数据源。

脚本主要关注:

82
245

Virtual Channel

virtual_channel_id 是虚拟信道编号。同一个航天器 ID 下可以有多个虚拟信道。

脚本重点分析:

Spacecraft 82, Virtual channel 1
Spacecraft 245, Virtual channel 3
Spacecraft 245, Virtual channel 1

其中 Spacecraft 245 / VC 1 是后面 APID 分析的主要数据来源。

Space Packet

AOS 帧中承载的是 Space Packet 数据流。一个 Space Packet 可能跨越多个 AOS 帧,所以脚本调用:

ccsds.extract_space_packets(...)

把它们重新拼接出来。

APID

APID 是 Space Packet 里的应用标识。新手可以先把它理解成“数据类型编号”。

不同 APID 里的载荷含义可能不同,所以脚本会按 APID 分组分析。

图片保存逻辑

脚本新增了 save_all_figures(output_dir) 函数。

它会做这些事:

  1. 找出当前 matplotlib 里所有还打开的 figure。
  2. 从每张图的标题中生成文件名。
  3. 调用:
fig.savefig(path, dpi=150, bbox_inches="tight")
  1. 保存成 PNG。
  2. 保存后关闭 figure释放内存。

文件名类似:

figure_001_spacecraft_82_virtual_channel_1_frame_loss.png
figure_002_apid_1_spacecraft_82_virtual_channel_1.png

各分析段落在做什么

Spacecraft 82 Virtual channel 1

这一段会:

  • 筛选出 SC 82 / VC 1 的 AOS 帧。
  • 检查帧计数是否连续。
  • 打印插入区时间戳。
  • 重组 Space Packet。
  • 按 APID 分类。
  • 为每个 APID 画载荷热力图。

Spacecraft 245 Virtual channel 3

这一段主要检查 VC 3 是否像固定填充数据。

它会查看某些字节区间的唯一值,比如是否一直是 0xaa

Spacecraft 245 Virtual channel 1

这是主要遥测数据通道。

这一段会:

  • 检查帧计数。
  • 提取时间戳。
  • 重组 Space Packet。
  • 统计所有 APID。
  • 按 APID 分组并画热力图。

APID 1280 / 1281

这些 APID 的载荷被按大端 int16 解释。

也就是说,每两个字节被看成一个 16 位整数,然后画出这些整数随时间的变化。

APID 1288 / 1287

这些 APID 的部分载荷被按大端 float64 解释。

脚本还对这些浮点序列做了 1 阶和 2 阶多项式拟合,并画出“原始值减拟合值”的残差。

新手可以理解为:

先把整体趋势去掉,再看剩下的小变化。

APID 2 / 3

原 notebook 这里变量名写了 APID 2 和 APID 3但代码实际两边都取了 APID 2。

脚本保留了原逻辑,并在代码注释里特别说明了这一点。

APID 454 / 462 / 1536

这些段落分别按 uint8int16 查看指定字节位置的变化。

目的不是完全解码每个遥测字段,而是先通过画图观察哪些字节像计数器、哪些字节像连续变化的遥测量。

运行方式

在项目根目录下可以运行:

/home/zjz/CCSDS_study/ccsds/bin/python /home/zjz/CCSDS_study/test/Tianwen-1-frame-analysis-v2.py

运行结束后,查看图片目录:

/home/zjz/CCSDS_study/Tianwen/frame_analysis_figures

常见提示

运行时可能看到类似:

Broken stream. Last frame count ..., current frame count ...

这是 ccsds.py 发出的 warning意思是帧计数中间不连续可能有丢帧或数据中断。

这不是 Python 程序崩溃,也不影响脚本继续保存图片。

新手视角总结

这个脚本不是一个“完整解码所有遥测含义”的程序,而是一个“探索和观察遥测数据结构”的分析脚本。

它先把原始二进制文件拆成 AOS 帧,再把 AOS 帧里的 Space Packet 拼出来,然后按照 APID 分组。分组之后,它把某些字节当成整数或浮点数画出来,让我们通过图片观察这些字段是否有规律。

简单说:

原始二进制数据
  -> AOS 帧
  -> Space Packet
  -> APID 分组
  -> 字节/整数/浮点数曲线
  -> PNG 图片

如果你是新手,建议先从这几个变量看起:

  • frames:原始帧字节数组。
  • aos:解析后的 AOS 帧对象。
  • sc245_vc1:筛选出的主要遥测虚拟信道。
  • sc245_vc1_packets:从 AOS 帧中重组出来的 Space Packet。
  • sc245_vc1_by_apid:按 APID 分类后的 packet 字典。
  • channels:某个 APID 的载荷被解释成数值后的矩阵。
  • timestamps:每个 packet 对应的时间戳。

理解这些变量后,整个脚本的结构就比较清楚了。