0xeb/libghidra
GitHub: 0xeb/libghidra
一个面向 Ghidra 的多语言自动化 SDK,提供 Python、Rust 和 C++ 的强类型 API,支持远程连接 Ghidra 实例和完全离线的嵌入式反编译后端,让逆向分析可以像基础设施一样被程序化调用。
Stars: 66 | Forks: 4
# libghidra
用于 Ghidra 程序数据库的强类型 API。从 C++、Python 或 Rust 查询函数、类型、内存、反编译器输出等内容——无需接触 Java。
当前版本:`0.0.2` alpha。API 已可用,但仍在不断演进中。
## 使用 AI 智能体安装(推荐)
搭建 libghidra 端到端环境最快的方法是将 AI
编码智能体(Claude Code、Cursor、Codex、Aider 等)指向捆绑的
安装器提示词:
它是一个自包含的运行手册,在每个步骤都设有明确的验证关卡——
预检、Ghidra 安装、主机扩展安装、
Python wheel 安装,以及首次实时反编译。将其交给您的
智能体并让其驱动安装;仅在关卡报告
失败时才进行干预。
如果您更愿意自己驱动安装,请参阅下面的**开始运行**。
## 开始运行
### 快速入门
如果您正在评估此版本,最简的成功路径是:
1. 将 `LibGhidraHost` 扩展安装到 Ghidra 12.0.4+ 发行版中。
2. 启动 Ghidra,打开一个程序,然后启动 `Tools > libghidra Host > Start Server...`。
3. 首先使用 Python 客户端验证连接性。
4. 然后在相同的主机 URL 之上叠加 C++/Rust SDK 或您自己的工具。
此路径演练了当前版本的重点:实时类型化访问、反编译器支持的读取,
以及结构化注释写入。
### 前置条件
- [Ghidra](https://ghidra-sre.org/) 发行版 (12.0.4+)
- 用于构建 Java 扩展的 JDK 21(例如 [Eclipse Adoptium](https://adoptium.net/))
- 用于构建 Java 扩展的 [Gradle](https://gradle.org/)
- `libghidra/ghidra-extension` 中没有检入独立的 Gradle wrapper
- 如果您拥有本地的 Ghidra 源码树,您也可以使用 `ghidra/gradlew.bat` 驱动扩展构建
- `protoc` 对于常规扩展构建是可选的;预生成的 Java protobuf 存根已包含在源码树中
- C++20 编译器 (Visual Studio 2022, GCC 12+, 或 Clang 15+) —— 仅在使用 C++ SDK 时需要
- CMake 3.20+ —— 仅在使用 C++ SDK 时需要
### 1. 安装 libghidra 主机扩展
此步骤将安装通过 HTTP 提供强类型 libghidra RPC API 的 Ghidra 插件:
`GHIDRA_INSTALL_DIR` 必须指向 Ghidra 发行版的根目录,即包含 `support/buildExtension.gradle` 的目录。
例如,如果您将 Ghidra 解压到 `C:\ghidra_dist\ghidra_12.1_DEV`,请使用该完整的内部路径作为安装目录。
常规扩展构建不需要 `protoc`;如果缺少它,构建将使用自带的生成存根。
```
cd ghidra-extension
gradle installExtension -PGHIDRA_INSTALL_DIR=/path/to/ghidra_dist
```
如果您已经检出本地的 Ghidra 源码树,此基于 wrapper 的变体也可以工作:
```
C:\path\to\ghidra\gradlew.bat -p libghidra\ghidra-extension installExtension -PGHIDRA_INSTALL_DIR=C:\ghidra_dist\ghidra_12.1_DEV
```
安装后,扩展将被解压到:
```
/path/to/ghidra_dist/Ghidra/Extensions/LibGhidraHost
```
### 2. 启动 API 服务器
**选项 A —— 从 Ghidra GUI 启动:**
从您安装了扩展的同一发行版启动 Ghidra 并打开一个程序。然后:
1. 转到 `File > Configure` 并启用 `LibGhidraHost`(如果尚未启用)。
2. 使用 `Tools > libghidra Host > Start Server...`,然后接受默认 URL 或输入完整的 `http://host:port` URL 或纯 `host:port`。
3. 可选地检查 `Tools > libghidra Host > Status` 以确认绑定的 URL 和活动程序。
默认情况下,启动对话框预填充为 `http://127.0.0.1:18080`。
要覆盖 GUI 绑定/端口,请通过 Ghidra 的启动器环境变量使用 JVM 属性启动 Ghidra:
```
set GHIDRA_GUI_JAVA_OPTIONS=-Dlibghidra.host.bind=127.0.0.1 -Dlibghidra.host.port=19090
C:\ghidra_dist\ghidra_12.1_DEV\ghidraRun.bat
```
**选项 B —— Headless 模式(无 GUI):**
```
/path/to/ghidra_dist/support/analyzeHeadless \
./myproject MyProject -import target.exe \
-postScript LibGhidraHeadlessServer.java port=18080
```
headless 命令也必须使用包含 `support/analyzeHeadless` 的 Ghidra 发行版根目录。
### 3. 查询 API
**Python**(最简单):
预构建的 wheel 包(Python 3.12+)附在每次[发布](https://github.com/0xeb/libghidra/releases)中。每个原生 wheel 都捆绑了 HTTP/RPC 客户端和离线本地后端—— Ghidra 的 Sleigh 反编译引擎已被编译在内,并嵌入了 Sleigh 处理器规格,因此在运行时不需要安装 Ghidra 或 Java。
```
# Linux x86_64 (RHEL 8+, Ubuntu 20.04+, Debian 11+, Fedora 29+)
pip install https://github.com/0xeb/libghidra/releases/download/v0.0.2/libghidra-0.0.2-cp312-abi3-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl
# Linux aarch64 (Raspberry Pi 4/5 on 64-bit OS, Ubuntu aarch64, Debian arm64)
pip install https://github.com/0xeb/libghidra/releases/download/v0.0.2/libghidra-0.0.2-cp312-abi3-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl
# macOS Apple Silicon (M1/M2/M3/M4)
pip install https://github.com/0xeb/libghidra/releases/download/v0.0.2/libghidra-0.0.2-cp312-abi3-macosx_15_0_arm64.whl
# Windows x64
pip install https://github.com/0xeb/libghidra/releases/download/v0.0.2/libghidra-0.0.2-cp312-abi3-win_amd64.whl
```
没有适合您平台的 wheel(Intel Mac、Windows on Arm 等)?请使用发布页上 `libghidra-python-v0.0.2.zip` 中的纯 Python 备用 `libghidra-0.0.2-py3-none-any.whl`——它仅提供 HTTP/RPC 客户端;本地离线后端不可用。
对于从克隆仓库进行的贡献者/可编辑安装:
```
pip install -e python # HTTP/RPC client only
pip install -e "python[async]" # adds aiohttp for AsyncGhidraClient
pip install -e "python[cli]" # adds pefile/capstone for CLI offline helpers
pip install -e "python[local]" # adds local ELF/PE/Mach-O detection helpers
```
从源代码构建离线本地后端还需要 CMake 3.24+、C++20 编译器和本地 Ghidra 源码树——请参阅[构建 C++ SDK](#building-the-c-sdk)。
在 Python 中使用原生本地后端时,请安装 `libghidra[local]`。
`LocalClient` 会自动检测 ELF、PE、Mach-O 和原始数据输入,并将匹配的 Ghidra `language_id` 传递给后端。高级用户仍然可以在 `OpenProgramRequest` 上传递显式的 `language_id`。
```
import libghidra as ghidra
client = ghidra.connect("http://127.0.0.1:18080")
status = client.get_status()
print(f"Connected: {status.service_name}")
funcs = client.list_functions()
for f in funcs.functions[:10]:
print(f" 0x{f.entry_address:x} {f.name}")
```
Python 包还安装了 `libghidra` 命令,用于快速状态检查、函数列表、反编译和小型离线二进制辅助工具:
```
libghidra status --url http://127.0.0.1:18080
libghidra functions --url http://127.0.0.1:18080 --limit 20
libghidra decompile --url http://127.0.0.1:18080 0x140001000
```
**C++:**
```
#include "libghidra/ghidra.hpp"
auto client = ghidra::connect("http://127.0.0.1:18080");
auto funcs = client->ListFunctions(/*min_addr=*/0, /*max_addr=*/UINT64_MAX,
/*limit=*/10, /*offset=*/0);
if (funcs.ok())
for (auto& f : funcs.value->functions)
printf("0x%llx %s\n", f.entry_address, f.name.c_str());
```
**Rust:**
就像 Python wheel 一样,Rust crate 在一个包中发布了两个后端——并且也像 Python wheel 一样,它**是从 GitHub Releases 页面分发的,而不是 crates.io**:
```
[dependencies]
# Live (HTTP) only — pure Rust, no system deps
libghidra = { git = "https://github.com/0xeb/libghidra" }
# Live + offline (cxx → C++ engine, prebuilt archive needed)
libghidra = { git = "https://github.com/0xeb/libghidra", features = ["local"] }
```
```
# Or grab a prebuilt local archive from the Releases page:
cargo binstall libghidra
```
完整说明请参见 [`rust/README.md`](rust/README.md)。
```
use libghidra as ghidra;
// Live (HTTP) — needs a Ghidra Desktop with the LibGhidraHost extension
let client = ghidra::connect("http://127.0.0.1:18080");
let funcs = client.list_functions(0, u64::MAX, 10, 0)?;
for f in &funcs.functions {
println!("0x{:x} {}", f.entry_address, f.name);
}
// Offline — no Ghidra install required at runtime (feature = "local")
# #[cfg(feature = "local")] {
let local = ghidra::local()?;
let _ = libghidra::format_detect::detect_and_open(&local, "/usr/bin/ls", None)?;
let dec = local.get_decompilation(0xa000, 30_000)?;
println!("{}", dec.decompilation.unwrap().pseudocode);
# }
# Ok::<(), libghidra::Error>(())
```
## 构建 C++ SDK
```
cmake -B build -G "Visual Studio 17 2022"
cmake --build build --config Release
```
在 Windows 上,推荐使用 Visual Studio 生成器。MinGW 可能在构建 HTTP 客户端时有效,但本地/离线后端已使用 MSVC 进行了验证。
这会构建 `libghidra_client`(HTTP 客户端)。离线本地后端是可选的,因为它还需要本地的 Ghidra 源码检出。
要同时构建离线本地后端:
```
# 1) Apply libghidra's patches to Ghidra's C++ decompiler source. CI does
# this automatically before every release build; if you skip it, ELF
# binaries on non-x86 architectures (aarch64, ARM, RISC-V, …) will load
# as x86 and disassemble as nonsense.
cd /path/to/ghidra-source
for p in /path/to/libghidra/cpp/patches/*.patch; do patch -p1 < "$p"; done
cd -
# 2) Overlay compiled Sleigh `.sla` grammars from the Ghidra release ZIP.
# The git source tree only ships `.slaspec` (grammar source) — without
# the compiled `.sla` files, the embedded-spec generator finds the
# architecture metadata but the decompiler has no grammar to use, so
# every disassembly returns `halt_baddata()`. Download the matching
# Ghidra release ZIP, extract, and copy:
# cp -R ghidra_*_PUBLIC/Ghidra/Processors/*/data/languages/*.sla \
# /path/to/ghidra-source/Ghidra/Processors//data/languages/
# (one .sla per processor; the ci.yml `Overlay compiled Sleigh .sla`
# step has the exact rsync invocation.)
# 3) Configure + build.
cmake -B build -G "Visual Studio 17 2022" \
-DLIBGHIDRA_WITH_LOCAL=ON \
-DGHIDRA_SOURCE_DIR=/path/to/ghidra-source
cmake --build build --config Release
```
**仅限源码构建 —— `cargo binstall` / `pip install` 用户请跳过
所有这些。** 发布的 wheel 和 Rust 预构建存档由
CI 生成,已应用了补丁步骤和 `.sla` 覆盖层。
如果在 `.sla` 更新后重新同步相同的 Ghidra 源码树,请先删除
`build/cpp/embedded_specs.{cpp,h}`——`embed_specs.py` 的 mtime
过期检查信任源码的 mtime,而 rsync/cp 会保留来自
发布 ZIP 的原始时间戳,因此重新覆盖可能看起来比缓存输出“更旧”。
### CMake 目标
| 目标 | 别名 | 说明 |
|--------|-------|------|
| `libghidra_client` | `libghidra::client` | IClient + HTTP 后端 + protobuf 存根 |
| `libghidra_local` | `libghidra::local` | 添加离线反编译器后端(运行时无需 Java) |
```
target_link_libraries(app PRIVATE libghidra::client) # HTTP only
target_link_libraries(app PRIVATE libghidra::local) # HTTP + offline
```
也支持已安装包的使用:
```
find_package(libghidra CONFIG REQUIRED)
target_link_libraries(app PRIVATE libghidra::client)
```
安装将导出 `libghidra::client` 和 `libghidra::local`,以及当前公共 C++ API 所使用的生成
`libghidra/*.h` protobuf 头文件。
依赖项(通过 FetchContent 自动获取):protobuf v29.3、cpp-httplib v0.16.3。
## 离线 / 本地后端
本地后端直接嵌入了 Ghidra 的 Sleigh 反编译引擎——无需 Java、无需网络、无需运行 Ghidra 实例。处理器规格在构建时嵌入;在运行时它是完全自包含的。
```
#include "libghidra/ghidra.hpp"
ghidra::LocalOptions opts;
opts.pool_size = 4; // parallel decompilation (default: 1)
auto client = ghidra::local(opts);
ghidra::OpenRequest req;
req.program_path = "/path/to/binary.exe";
req.language_id = "x86:LE:64:default"; // optional; Python LocalClient can auto-detect
client->OpenProgram(req);
auto decomp = client->GetDecompilation(0x140001000, 30000);
if (decomp.ok())
printf("%s\n", decomp.value->decompilation->pseudocode.c_str());
```
涵盖 HTTP、headless 和本地后端(内存、反汇编、注释、数据项、符号、类型、结构体、枚举、签名、CFG、会话管理、并行 headless 分析以及完整的 headless 实战手册)的完整示例,请参见 [`cpp/examples/`](cpp/examples/)。
有关逐个方法的完整参考,请参见 [C++ LocalClient API 参考](cpp/README.md)。
## 架构
```
IClient (composite interface, 88 domain methods)
|-- HttpClient --> POST /rpc (protobuf) --> libghidra host (Java, live Ghidra)
|-- LocalClient --> standalone C++ decompiler engine (offline, no Java)
```
两个后端,一个接口。每次调用都返回 `StatusOr` —— 检查 `.ok()`,然后使用 `.value`。
| | **远程** (HttpClient) | **本地** (LocalClient) |
|---|---|---|
| 运行时 | Ghidra JVM + 扩展 | 无 |
| 功能 | 实时主机 API(读写) | 离线子集:反编译器、函数、符号、类型、内存、列表、xref |
| 用例 | GUI 自动化、实时分析、写入 | 离线批量反编译、CI、工具集成 |
## 目录结构
```
libghidra/
proto/ Protobuf service contracts (source of truth)
cpp/ C++ SDK (two CMake targets from one directory)
include/libghidra/ Public headers
src/ HTTP + local backend + decompiler engine
generated/ Pre-generated protobuf stubs
examples/ Complete examples (HTTP + local)
python/ Python SDK
rust/ Rust SDK
ghidra-extension/ Java extension project (installed as `LibGhidraHost`)
```
## SDK 状态
| SDK | 状态 | 说明 |
|-----|--------|-------|
| **C++ (HttpClient)** | 可用 | 广泛的实时主机 API 覆盖 |
| **C++ (LocalClient)** | 可用 | 离线子集;有关支持和不支持的方法,请参见 [cpp/](cpp/) |
| **Python** | 可用 | 同步 + 异步 HTTP、类型化模型和 CLI 工具。请参见 [python/](python/) 和 [API 参考](python/docs/api_reference.md) |
| **Rust** | 可用 | 同步 HTTP 客户端、类型化模型和分页辅助工具。请参见 [rust/](rust/) 和 [API 参考](rust/docs/api_reference.md) |
## 已知限制
- 在做出兼容性承诺之前,方法名和数据模型可能仍会更改。
- 当前的公共 C++ API 仍会在 `libghidra/*` 下暴露生成的 protobuf 头文件。
- 支持结构化的局部变量修改,但调用者应使用 API 返回的规范 `local_id`,而不是猜测显示样式的名称。
- 主要验证路径是实时主机加 headless 集成覆盖;更广泛的
干净打包和安装程序覆盖仍是发布强化工作的一部分。
### 本地后端(`LocalClient`)注意事项
- **枚举方法在本地模式下超出了范围。** `IClient` 是跨
两个后端的共享 API。`HttpClient` 与运行中的 Ghidra 实例通信,该实例的分析过程会填充一个
完整的函数/xref/字符串数据库—— `list_functions()`、`list_basic_blocks(addr)`、
`list_cfg_edges(addr)`、`list_xrefs(start, end)` 和 `list_defined_strings()` 在
那里会如您预期般工作。`LocalClient` 包装了独立的 C++ 反编译引擎,它不
运行分析过程;这些相同的枚举方法在设计上总是返回空。本地
模式用于**地址驱动**的查询—— `get_decompilation(addr)`、
`list_instructions(start, end)`、`read_bytes(addr, n)`、`rename_function(addr, name)` 以及
其余的按地址 API 都会按文档所述工作。如果您需要枚举已分析程序中的所有内容,请通过 `HttpClient` 路由到 Ghidra 主机。
- **矩阵中没有 macOS x86_64 / Windows arm64 wheel** —— 两者都因 GitHub Actions
运行器可用性(macos-13 饱和)和 `actions/setup-python` 尚未为 `windows-11-arm` 提供_arm64_ Python 而被放弃。这两个空白都将在日后重新评估;同时,这些
平台上的用户可以从发布 ZIP 中 `pip install` 纯 Python wheel 以使用 HTTP 客户端。
- **升级 wheel 后,请清除一次规格缓存。** 原生模块在
首次使用时将 Ghidra 的 Sleigh 数据解压到 `~/.ghidracpp/cache/sleigh//` 中;该 key 现在是
嵌入规格的内容哈希(rc8+),因此升级会自动获取新数据。
较旧的 rc wheel(rc1–rc7)哈希的是宿主进程二进制文件的 mtime,可能会留下
过期的缓存。如果您是从其中一个版本升级的,请运行一次 `rm -rf ~/.ghidracpp`。
## Proto 契约
跨越 9 个领域服务区域的类型化 RPC,定义在 [`proto/libghid/`](proto/libghidra/) 中。当前的契约定义了 88 个领域 RPC 加上一个传输 RPC。传输是在 `POST /rpc` 上的二进制 protobuf(不是 gRPC)。请参见 [proto/README.md](proto/README.md)。
## 许可证
本项目根据 [Mozilla Public License 2.0](LICENSE) 授权。
标签:AI编程助手, API, Bash脚本, C++, Claude, CMake, Cursor, CVE检测, Ghidra, Gradle, JARM, JS文件枚举, Protobuf, Python, Rust, TLS抓取, 二进制分析, 云安全运维, 云资产清单, 交叉引用, 代码注释, 内存分析, 反编译器, 可视化界面, 可配置连接, 后台面板检测, 基础设施化, 多语言绑定, 开发库, 数据擦除, 无后门, 漏洞测试, 程序分析, 符号检查, 类型查询, 网络流量审计, 网络调试, 自动化, 软件安全, 逆向工具, 逆向工程