jeamxn/cisco-pka-to-xml
GitHub: jeamxn/cisco-pka-to-xml
该工具将 Cisco Packet Tracer 的 .pka/.pkt 文件与 XML 互相转换,采用纯 Python 解析多层压缩与 Twofish 加密管线,兼容现代版本。
Stars: 0 | Forks: 1
# cisco-pka-to-xml
将 Cisco Packet Tracer 活动文件(`.pka`)和已保存的网络文件(`.pkt`)转换为可读的 XML,以及将其反向转换。
这是一个基于净室设计的、采用 MIT 许可证的 Python 实现,解析了最初由 [Mirco De Zorzi (`mircodz/pka2xml`)](https://github.com/mircodz/pka2xml) 记录的文件格式。它适用于现代的 Packet Tracer 版本(7.x、8.x、**9.x**),而在这些版本中,诸如 [`axcheron/ptexplorer`](https://github.com/axcheron/ptexplorer) 这类仅使用 XOR 的旧工具已经无法正常工作。
## 目录
- [工作原理](#how-it-works)
- [环境要求](#requirements)
- [安装说明](#installation)
- [用法](#usage)
- [将 `.pka` 解码为 XML](#decode-a-pka-to-xml)
- [将 XML 重新编码为 `.pka`](#encode-xml-back-into-a-pka)
- [作为 Python 库使用](#use-as-a-python-library)
- [XML 中的内容](#what-you-get-in-the-xml)
- [疑难解答](#troubleshooting)
- [项目结构](#project-layout)
- [贡献指南](#contributing)
- [许可证](#license)
- [致谢](#credits)
## 工作原理
一个 Packet Tracer 文件是经历了四个可逆阶段的 XML 文档:
1. **zlib 压缩**,带有 4 字节大端序的未压缩长度前缀。
2. **基于位置的 XOR**:每个字节 `b[i]` 与 `(length - i) & 0xff` 进行异或运算。
3. **Twofish-EAX 加密**:使用重复 16 次的常量密钥 `0x89` 和重复 16 次的 IV `0x10`。
4. **基于位置的 XOR 及反转**:每个字节 `out[length-1-i] = in[i] ^ ((length - i*length) & 0xff)`。
解码过程则是反转此流水线。Twofish 分组密码是唯一需要原生代码的部分;其他所有内容——包括 EAX 认证模式(CMAC + CTR)——都在本仓库中使用纯 Python 实现,因此唯一的构建依赖是一个 C 编译器。
由 Niels Ferguson 编写的 Twofish 参考实现作为第三方库包含在 [`vendor/twofish/`](./vendor/twofish/) 目录中(同样采用 MIT 许可证;详见 [`vendor/twofish/LICENSE`](./vendor/twofish/LICENSE))。
## 环境要求
- Python 3.8 或更新版本
- 一个 C 编译器(`cc`、`gcc`、`clang` 或 `tcc` 中的任意一个)
- `patchelf` —— 仅在 Linux 上*且仅在*您的编译器不输出 `.note.GNU-stack` 节时需要。现代的 `gcc`/`clang` 会输出该节;`tcc` 不会。如果可用,构建脚本将自动使用 `patchelf --clear-execstack`。
不需要任何第三方 Python 包。
## 安装说明
```
git clone https://github.com/jeamxn/cisco-pka-to-xml.git
cd cisco-pka-to-xml
# 构建 Twofish 共享库(一次性)
python build_libtwofish.py
```
这会在 Python 包旁边生成 `pka2xml/libtwofish.so`(Linux)、`libtwofish.dylib`(macOS)或 `libtwofish.dll`(Windows)。
如果您需要指向现有的构建版本,请设置 `LIBTWOFISH` 环境变量:
```
export LIBTWOFISH=/path/to/libtwofish.so
```
### 运行测试
```
python tests/test_roundtrip.py
```
往返测试会对一个微小的 XML 数据块进行编码然后再将其解码。KAT 测试会针对原生构建版本运行一个官方的 Twofish 128 位测试向量。
## 用法
### 将 `.pka` 解码为 XML
```
python -m pka2xml decode path/to/activity.pka activity.xml
```
输出是一个单一的 XML 文档。对于活动(`.pka`)文件,它被包裹在 `` 中,并且通常包含多个 `` 快照(初始网络、答案网络等)。已保存的网络(`.pkt`)包含一个单一的 `` 文档。
### 将 XML 重新编码为 `.pka`
```
python -m pka2xml encode activity.xml rebuilt.pka
```
输出在长度类别上是完全一致的,但与原始文件并非字节完全一致——zlib 的确定性压缩取决于压缩器具体的构建版本。Packet Tracer 仍然可以打开它。
### 作为 Python 库使用
```
from pathlib import Path
from pka2xml import decrypt_pka, encrypt_pka
xml_bytes = decrypt_pka(Path("activity.pka").read_bytes())
Path("activity.xml").write_bytes(xml_bytes)
# round-trip
rebuilt = encrypt_pka(xml_bytes)
Path("rebuilt.pka").write_bytes(rebuilt)
```
如果 EAX 标签不匹配或内部 zlib 流格式错误,`decrypt_pka` 将引发 `pka2xml.PkaError`。这几乎总是意味着该文件不是一个 Packet Tracer 文件,或者是由非常旧(6.0 之前)的版本生成的。
## XML 中的内容
以下是从解码后的路由活动中截取的一小段示例:
```
9.0.0.0810
Router
R1
...
interface FastEthernet0/0.10
encapsulation dot1Q 10
ip address 204.200.10.1 255.255.255.0
...
...
```
一旦您获得了 XML,可以使用 grep 搜索以下有用的标签:
| 标签 | 含义 |
| ----------------------- | ----------------------------------------------- |
| `` / `` | 一个带有显示名称的设备节点 |
| `` | 硬件型号(例如 `2811`、`PC-PT`) |
| `` | 设备的 IOS `show running-config` |
| `` / `` | 接口 IP 和子网掩码 |
| `` | 默认网关(在 PC/服务器上) |
| `` | 一条线缆:包含两个端点 |
| `` | 设备的十六进制编码 CLI 历史记录 |
## 疑难解答
| 症状 | 可能的原因 |
| ------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------- |
| `libtwofish shared library not found` | 请先运行 `python build_libtwofish.py`,或者设置 `LIBTWOFISH=/path/to/libtwofish.so`。 |
| 在 Linux 上加载库时出现 `cannot enable executable stack as shared object requires` | 安装 `patchelf` 并重新运行构建,或者使用现代的 `gcc` / `clang` 重新构建。 |
| `EAX authentication tag mismatch — file may be corrupt or wrong key` | 输入的不是由 6.0 或更高版本生成的 Packet Tracer 文件。 |
| `zlib decompression failed` | 同上,或者该文件是由 Packet Tracer 5.x 生成的(仅使用 XOR —— 请使用 `ptexplorer`)。 |
| 输出的 XML 可以在 PT 中打开但文本出现乱码 | XML 使用了非 UTF-8 编辑器进行编辑。请将其保存为不带 BOM 的 UTF-8 格式。 |
## 项目结构
```
.
├── pka2xml/ Python package
│ ├── __init__.py Public API: Twofish, decrypt_pka, encrypt_pka, PkaError
│ ├── __main__.py CLI entry point (`python -m pka2xml ...`)
│ ├── build.py Build script for the native Twofish library
│ └── libtwofish.so (Generated) Native Twofish blob cipher
├── vendor/
│ └── twofish/ Niels Ferguson's reference Twofish implementation
│ ├── twofish.c
│ ├── twofish.h
│ └── LICENSE MIT (vendored upstream license)
├── tests/
│ └── test_roundtrip.py KAT + encode/decode roundtrip
├── examples/
│ └── inspect_devices.py Walk the decoded XML and print device + IP info
├── CONTRIBUTING.md
├── LICENSE MIT (this project)
└── README.md
```
## 许可证
本项目采用 [MIT 许可证](./LICENSE) 发布。
包含在 [`vendor/twofish/`](./vendor/twofish/) 中的 Twofish 第三方库同样采用 MIT 许可证;详见 [`vendor/twofish/LICENSE`](./vendor/twofish/LICENSE)。
## 致谢
- Niels Ferguson —— 原始的 Twofish 参考实现。
- Mirco De Zorzi —— [`pka2xml`](https://github.com/mircodz/pka2xml) 以及记录了该文件格式的[相关文章](https://mircodezorzi.github.io/doc/reversing-packet-tracer/)。
- Arnaud Cheron —— [`ptexplorer`](https://github.com/axcheron/ptexplorer),该工具用于解码旧版仅使用 XOR 的 Packet Tracer 格式。
标签:Cisco Packet Tracer, Python, XML, 密码学, 手动系统调用, 文件格式转换, 无后门, 编解码, 逆向工具