Skip to content
KitploitKITPLOIT
工具漏洞利用博客
Log in
提交
工具漏洞利用博客
提交

黑客、渗透测试和网络安全工具,武装您的安全武器库!

Kitploit 是一个黑客、网络安全和渗透测试工具的目录。发现最新的项目更新,查找漏洞、分析系统、自动化测试并加强你的安全。

订阅源联系隐私© 2026 Kitploit

工具目录

分类

查看所有分类
Loading categories
ghidra_svr_bridge — Binary Ninja 插件,通过 Java 桥接子进程与 Ghidra Server 仓库进行双向分析同步。 | Kitploit
工具/GitHubGitHub/gmh5225/ghidra_svr_bridge
静态分析代码分析逆向工程脚本与自动化实用工具与框架二进制分析
GitHubgmh5225/ghidra_svr_bridge

ghidra_svr_bridge

Binary Ninja 插件,通过 Java 桥接子进程与 Ghidra Server 仓库进行双向分析同步。

查看仓库
252个月前尚未审核

最受欢迎

查看全部 →

发现我们社区最常用的工具。

探索所有工具

浏览我们的工具集合

查看所有工具 →
分享

binja-ghidra

一个 Binary Ninja 插件,可连接到 Ghidra Server 仓库,并将其分析结果——符号、函数名和注释——直接导入到已打开的 Binary Ninja 二进制视图中。

功能说明

Ghidra 和 Binary Ninja 各有优势。本插件让你可以在同一个二进制文件上同时使用两者,而无需手动在它们之间复制名称或注释。连接到正在运行的 Ghidra Server,浏览其仓库,双击任意项目文件即可将其分析结果拉取到当前打开的 BN 视图中。

同步是双向的。

BN ← Ghidra(导入)BN → Ghidra(检入)
符号(标签、函数名)✓✓
注释(EOL/PRE/POST/PLATE/REP)✓✓
函数签名(返回类型、调用约定)✓✓
函数参数(重命名、重设类型、添加)✓✓
数据类型(struct/union/enum/typedef + 指针/数组)✓✓
等价常量(常量名 + 引用)✓✓
书签✓✓
类型化数据项✓✓
函数标志(thunk、no-return、inline)✓ 作为 BN 标签—
局部变量(存储感知)✓部分——寄存器存储映射尚未实现

架构

Binary Ninja (C++ plugin)
    │  TCP / newline-delimited JSON
    ▼
ghidra-bridge-*.jar  (Java, runs as a subprocess)
    │  Java RMI / SSL
    ▼
Ghidra Server  (ghidraSvr, running on the network)

插件在加载时会启动一个 Java 子进程(即“bridge”)。bridge 持有与 Ghidra Server 的 RMI 连接,并通过本地 TCP 套接字与插件之间使用简单的 JSON 协议通信。这样可以将所有 Java/RMI 代码排除在 C++ 进程之外,并让 JVM 在 BN 完成加载的同时在后台启动。

bridge JVM 还会在启动时初始化 Ghidra 的 Application 框架,以便写入路径可以使用 Ghidra 的高层程序模型 API(ProgramDB、DataTypeManager、SymbolTable、FunctionManager),而不是原始的 db.Table.putRecord() 写入——请参阅下方的检入写入路径。

组件

路径语言角色
plugin/C++ / Qt6Binary Ninja 侧边栏插件
bridge/Java 17Ghidra RMI 客户端 + JSON 桥接服务器

插件(C++):

  • plugin.cpp — 注册设置和侧边栏控件;在加载时立即启动 bridge JVM
  • GhidraConnection.cpp — 单例;管理 bridge 生命周期及所有基于 RMI 的操作
  • BridgeProcess.cpp — 将 bridge JAR 作为子进程启动,带有 stdout/stderr 管道;读取 READY port=N 握手行
  • BridgeClient.cpp — TCP 客户端;发送 JSON 请求、接收响应、分发异步事件
  • SyncEngine.cpp — 将 GhidraDbExport 应用到 BinaryView(符号、注释、标志)
  • ui/ProjectPanel.cpp — 侧边栏控件:仓库树、连接对话框、活动日志
  • ui/ConnectDialog.cpp — 主机/端口/用户/密码对话框

Bridge(Java):

  • BridgeMain.java — 参数解析;初始化 UniversalIdGenerator 和 Ghidra Application 框架;启动 TCP 服务器;向 stdout 打印 READY port=N
  • BridgeServer.java — 接受一个 TCP 客户端连接,并为其分配一个 BridgeConnection
  • BridgeConnection.java — JSON 请求分发器;将 Ghidra API 响应序列化为 JSON;处理 opCheckin(在服务器上创建新的程序版本)
  • GhidraSession.java — 已认证的 RMI 会话;封装 RemoteRepositoryServerHandle
  • EventStreamer.java — 每个已打开仓库的后台线程;将 RepositoryChangeEvent 作为异步 JSON 事件推送到插件
  • DatabaseExporter.java — 读取路径:通过原始 db.jar 访问,从 ManagedBufferFileHandle(Ghidra 的远程数据库缓冲区)中提取符号/注释/函数标志/数据类型/等价常量/书签表
  • ProgramApplier.java — 写入路径:将缓冲区文件作为真正的 ProgramDB 打开,并通过 Ghidra 的高层 API 应用所有 BN 侧的更改(请参阅下方的检入写入路径)
  • DatabaseImporter.java — 仅作为测试接缝保留的旧式原始写入辅助工具;生产环境的 apply(...) 委托给 ProgramApplier

检入写入路径

opCheckin 以写入模式打开程序的管理缓冲区文件,在其上构造一个 ProgramDB,并通过 Ghidra 的程序模型 API 应用 BN 侧的更改。避免使用原始的 db.Table.putRecord() 写入——它们是我们遇到过的所有检入损坏 bug 的根源:

错误层级的写入失败模式
在 Function Data 表上调用 setIntValue(col, longTypeId)IntField.setLongValue 会静默地 l2i 截断 → 每次签名更新时 StackPurge 损坏
在 V5V6 Composite Data Types 上调用 setByteValue(col, isUnion)在 Ghidra 12.x 中该列是 BooleanField → IllegalFieldAccessException(“Illegal field access”)
在 V2 Typedef Flags 列上调用 setIntValue(col, 0)该列是 ShortField → 同样的崩溃,不同的 schema
写入复合头但没有组件设置行在 Ghidra 中打开结构体时,CompositeEditorModel.cloneAllComponentSettings 抛出 ArrayIndexOutOfBoundsException
写入 PARAMETER 符号时 SYM_ADDR_COL = RAM 地址任何函数访问时,FunctionDB.loadSymbolBasedVariables 抛出 Address is not a VariableAddress
向 DBHandle.save() 传递 null DBChangeSet服务器写入 0 字节的变更数据文件 → 下次检出时在 ProgramContentHandler.loadProgramChangeSet 中因 EOFException 失败

ProgramApplier 没有这些陷阱,因为它通过 DataTypeManager.addDataType、SymbolTable.createLabel、Listing.setComment、Function.setReturnType 等 API 进行路由——这些 API 会自动维护 Ghidra 相互关联表的不变量。它还会在每次检入开始时运行 cleanupBadVariableSymbols 过程,以清除旧版 bridge 在数据库中留下的损坏。

server-package/CleanupBadVariableSymbols.java 是一个独立的 GhidraScript,它通过 analyzeHeadless 运行相同的清理——当文件损坏严重到无法在 Ghidra GUI 中打开时非常有用。

测试

./test.sh          # macOS / Linux: tiers 0-3 (C++ unit + BN-headless + Java)
test.bat           # Windows equivalent
test.bat --parity  # cross-DB parity tier only (C++ BN tests + gradlew parityTest)
test.bat --e2e     # live Ghidra-server E2E (starts a local ghidraSvr)

测试套件分为五个层级。第 2–4 层存在的目的是证明一个性质: 相同的兼容数据最终同时存储在 .bndb 和 Ghidra 程序数据库中(即本 README 顶部的兼容性矩阵)。

层级内容位置门槛
0纯单元测试plugin/test/*.cpp(binja-ghidra-tests)、bridge *Test.java始终运行
1Ghidra-DB 往返bridge *RoundTripTest.java(ProgramApplier 针对真实的 ProgramDB)需要 ghidra.home / GHIDRA_HOME
2BN BinaryView/.bndb 往返plugin/test/bn/(binja-ghidra-bn-tests;headless binaryninjacore)在没有支持 headless 的 BN 许可证时干净地 SKIP(遵循 BN_LICENSE 环境变量)
3跨数据库一致性CanonicalParityTest(C++ 和 Java)针对 testdata/parity/fixtures/ 中的共享黄金文件与第 1+2 层一起
4实时服务器 E2Ebridge LiveServerE2ETest — 在临时目录中启动真实的 ghidraSvr,通过 analyzeHeadless 播种,通过 RMI 驱动检出 → 导出 → 检入 → 重新导出test.bat --e2e(设置 GHIDRA_E2E=1)

一致性判据(第 3 层)。 双方独立地针对相同的已检入规范 JSON(bridge DatabaseExporter 形状)进行验证。导入方向:黄金文件加载到 ProgramDB(Java)中,并通过 SyncEngine(C++)加载到 BinaryView 中,每次重新导出都必须等于黄金文件。检入方向:脚本化的 BN 编辑必须精确产生 fixtures/checkin/*/expected-preview.json(C++),并且通过 ProgramApplier 应用该预览后必须重新导出为 expected-after.json(Java)。如果双方都与共享黄金文件匹配,则两个数据库通过传递性达成一致。字段比较模式和类型名规范化表位于 testdata/parity/RULES.md;测试二进制文件是 testdata/bin/parity_x64.bin(布局在 parity_x64.md 中)。

Java 侧长期存在的回归固定测试:

  • DataTypesRoundTripTest.struct_cloneSettings_doesNotThrow — 复合设置必须与头部保持一致(cloneAllComponentSettings 崩溃)
  • FunctionSignaturesRoundTripTest.returnType_doesNotCorruptStackPurge — IntField 截断
  • ParametersRoundTripTest.noParameterSymbol_endsUpAtRamAddress — VariableAddress 不变量

往返和一致性测试需要 Ghidra 安装(在运行时用于语言服务)。路径从 ghidra.home Gradle 系统属性或 GHIDRA_HOME 环境变量读取;build.gradle 默认传递 ghidraHome。第 2/3 层 C++ 测试还需要 binaryninjacore 可加载(脚本将 BN 安装目录添加到 PATH)。

先决条件

依赖项说明
Binary Ninja(商业版)针对与 BN 安装中 api_REVISION.txt 匹配的版本进行测试
Ghidra Server使用 Ghidra 12.0.4 测试。必须正在运行并可通过 RMI/SSL 访问
Java 17+ JDK推荐 Eclipse Adoptium JDK 21
CMake 3.24+
Ninja
C++ 编译器Windows 上为 MSVC 2022+;macOS 上为 clang;Linux 上为 gcc/clang
Qt 6.7+请参阅下方的 Qt 设置;构建时 qmake 必须在 PATH 上
Gradle(通过 wrapper)bridge 使用 Gradle wrapper——无需单独安装
Poetry (仅 Qt 构建)仅当从 qt-build 子模块构建 Qt 时需要。使用 pip install poetry 或 pipx install poetry 安装。
libclang 19 (仅 Qt 构建)Qt 构建系统需要。下载说明请参阅 qt-build/README.md。

Qt 设置

插件链接到与 Binary Ninja 使用的相同 Qt 6 构建。你有两个选项:

选项 A — 使用现有的 Qt 安装(如果你已有 Qt,这是最快的方式)

将 Qt6_DIR 指向你的 Qt CMake 目录:

Qt6_DIR=/path/to/Qt/6.x.y/clang_64/lib/cmake/Qt6 ./build.sh

在 macOS 上,如果 Qt 是通过 Qt 在线安装程序安装在 /usr/local/Qt* 下,构建脚本会自动检测 Qt。

选项 B — 从 qt-build 子模块构建 Qt(约 1-2 小时,每台机器一次)

qt-build 子模块(Vector35 的 Qt 构建脚本)使用 Binary Ninja 的补丁编译 Qt 6。它需要 Poetry 和 libclang 19(请参阅上方的先决条件和 qt-build/README.md)。

Qt 安装到仓库内的 qt/<version>/<compiler>/:

平台安装路径
macOSqt/6.10.1/clang_64/
Linux x86-64qt/6.10.1/gcc_64/
Windowsqt/6.10.1/msvc2022_64/
# First time on a new machine:
./build.sh qt          # compiles Qt — takes 1-2 hours

# All subsequent builds (Qt cached in qt/, reused automatically):
./build.sh

qt 步骤只需执行一次。CMake 和构建脚本在后续每次运行时都会检测 qt/ 中已构建的 Qt,并完全跳过子模块。qt/ 目录已被 gitignore。

构建

全新检出

git clone https://github.com/mutinylaboratories/ghidra_svr_bridge.git
cd ghidra_svr_bridge
git submodule update --init   # populates binaryninja-api and qt-build (~seconds)

然后按照上方的 Qt 设置(选项 A 或 B)操作,并运行:

./build.sh install

macOS / Linux

# Incremental build of both components
./build.sh

# Full clean rebuild + install into BN plugins folder
./build.sh clean install

# Build only the C++ plugin
./build.sh plugin
下载工具