m10ust/machscope
GitHub: m10ust/machscope
machscope 是一款终端原生的 macOS 溯源工具,它将进程、launchd 任务、Mach 服务、Bundle、代码签名和 Mach-O 链接整合成可查询的图谱,解决安全分析师需要在多个系统工具间手动关联信息的痛点。
Stars: 0 | Forks: 0
# machscope
**machscope** 是一款终端原生的 macOS 探索工具,它将进程、launchd 任务、Mach 服务、Bundle、签名、授权信息和 Mach-O 链接整合成一个可供查询的图谱。
它的存在是为了彻底回答一个简单的问题:
它将**进程**、**可执行文件**、**launchd 任务**、**Mach 服务**、**Bundle**、**内嵌的 XPC 服务**、**代码签名**、**授权信息**、**Mach-O 链接**以及**信任/异常发现**关联到一个视图中。
如果 `Activity Monitor`、`ps`、`lsof`、`launchctl`、`codesign` 和 `otool` 生了一个偏执但易于操作的孩子,那就是它。
## 为什么存在
macOS 内部机制很优雅,但真相是分散的。
要理解一个可疑的进程,你常常需要在以下工具之间来回切换:
- `ps`
- `lsof`
- `launchctl`
- `codesign`
- `otool`
- Bundle 的 `Info.plist`
- launchd 的 plist 文件
- 你自己的笔记和猜测
`machscope` 将这一工作流程压缩成一个单一的终端工具。
它专为以下场景构建:
- 安全分类排查
- 恶意软件狩猎
- 持久化机制调查
- launchd 和 Mach 服务探索
- 调试奇怪的 macOS 行为
- 理解一个应用是如何真正组合起来的
## 它能做什么
给定一个 **PID**、**路径**、**launchd 标签** 或 **Mach 服务名称**,`machscope` 可以关联以下信息:
- 来自 `ps` 的进程元数据
- 来自 `lsof` 的可执行文件路径和打开文件上下文
- 来自 `launchctl` 的 launchd 状态和标签提示
- launchd plist 元数据和声明的 `MachServices`
- Bundle 标识和内嵌的 `.xpc` 服务
- 来自 `codesign` 的代码签名标识符、Team ID、授权链和运行时提示
- 来自 `codesign` 的授权数据
- 来自 `otool` 的 Mach-O 头部、链接动态库、加载命令和 rpath
- 用于下游导出的图节点/边
- 带证据的信任发现
它**不会**假装观察每一个实时的 XPC 关系。某些关系是**声明的**,而非**观察到的**。这种坦诚是有意为之。
## 为什么选择 machscope 而非原始 macOS 工具?
- `ps` 显示进程,但不显示归属链
- `launchctl` 显示任务,但不显示完整的二进制/bundle/信任上下文
- `codesign` 显示身份,但不显示运行时关系
- `otool` 显示链接关系,但不显示 launchd 或 Mach 服务的暴露情况
- `machscope` 在一次执行中关联所有这些信息
## 功能
- **无外部依赖的 Python**
- 仅使用 Python 标准库
- **终端原生**
- 优先输出可读的人类文本,需要时也支持 JSON
- **灵活的目标解析**
- 检查 PID、可执行文件、应用 Bundle、launchd 标签或 Mach 服务
- **`--follow` 解析器跳转**
- Bundle 目标解析为其可执行文件
- Mach 服务解析为声明它的 launchd 任务和可执行文件
- launchd 标签在有活跃 PID 时跳转到对应的 PID
- **信任/异常评分**
- 在不假装所有异常都是恶意软件的前提下,暴露异常
- **简单的图模型**
- `graph.nodes` 和 `graph.edges` 专为未来的 TUI、渲染或差异对比工作流设计
## 命令
```
./machscope.py inspect
./machscope.py inspect --follow
./machscope.py inspect --json
./machscope.py scan --limit 40 --min-score 1
./machscope.py services [filter]
```
## 示例
### 检查一个正在运行的进程
```
./machscope.py inspect 1
./machscope.py inspect 57382
```
### 检查一个应用或二进制文件
```
./machscope.py inspect /System/Applications/Calculator.app --follow
./machscope.py inspect /usr/libexec/remoted
```
### 检查一个 launchd 任务
```
./machscope.py inspect com.apple.WindowServer --follow
./machscope.py inspect ai.openclaw.gateway --follow
```
### 检查一个 Mach 服务
```
./machscope.py inspect com.apple.dnssd.service --follow
```
### 扫描异常
```
./machscope.py scan --limit 40 --min-score 1
./machscope.py scan --limit 10 --min-score 6
```
### 浏览已声明的服务
```
./machscope.py services
./machscope.py services mDNS
./machscope.py services com.apple
```
## 输出示例
```
Target: com.apple.dnssd.service [mach-service follow]
Resolved via: mach-service-launchd
Executable: /usr/sbin/mDNSResponder
Launchd: com.apple.mDNSResponder.reloaded
Plist: /System/Library/LaunchDaemons/com.apple.mDNSResponder.plist
Signature: apple-platform team=not set id=com.apple.mDNSResponder
Mach services: com.apple.dnssd.service, com.apple.mDNSResponder.control, com.apple.mDNSResponder.log_utility
Entitlements: 0
Linked dylibs: 25 RPATHs: 0
Trust: score=1 verdict=ordinary
Findings:
- [LOW] T012 Odd launchd label suffix
```
## JSON 输出
`inspect --json` 返回一个结构化对象,用于脚本和未来的 UI 工作。
顶层结构:
- `target`
- `target_resolution`
- `process`
- `binary`
- `bundle`
- `launchd`
- `trust`
- `graph.nodes`
- `graph.edges`
图结构刻意保持简单,以便它能服务于:
- 未来的 TUI
- 渲染器
- 差异对比模式
- 其他工具
## `--follow` 的工作原理
`--follow` 是 `machscope` 感觉不再只是元数据转储器,而更像一个探索者的关键所在。
它增加了解析器跳转,例如:
- **Bundle 目标** → 可执行文件
- **Mach 服务** → 声明它的 launchd 任务 → 可执行文件
- **launchd 标签** → `launchctl print` 状态 → 如果存在,则跳到活跃 PID
这一点很重要,因为 macOS 中最有趣的人工制品往往不是你输入的字面量,而是它背后的东西。
## 信任发现
`machscope` 包含一个简单的信任/异常检测层。
它能暴露的示例包括:
- 持久化条目背后的缺失二进制文件
- 用户可写的执行目标
- 非 Apple 代码上的敏感授权
- launchd 标签 / Bundle 标识不匹配
- 奇怪的 launchd 后缀,如 `.reloaded`
- 看起来像系统路径但验证结果不符合预期的路径
这**不是**一个恶意软件裁决引擎。
它是一种发现线索、减少盲点、使可疑链条更容易被审查的方法。
## 设计选择
### 刻意无依赖
第一个版本有意使用:
- Python 标准库
- 仅限 macOS 原生工具
包含的被包装工具:
- `ps`
- `lsof`
- `launchctl`
- `codesign`
- `otool`
- `file`
这使得该工具易于克隆、审查并在一个近乎原生的系统上运行。
### 诚实面对可见性
某些关系是声明的,而非观察到的。
例如:
- launchd plist 可以声明 Mach 服务
- Bundle 可以暴露内嵌的 XPC 服务
- 但公开的工具并不总能清楚地暴露实时的 XPC 客户端/服务端关系
`machscope` 宁愿明确表态,也不假装确定。
## 系统要求
- macOS
- Python 3
- 可访问原生工具,如 `ps`、`lsof`、`launchctl`、`codesign`、`otool` 和 `file`
## 权限
首先以普通用户身份运行。
这对于获得有用的答案通常已经足够。
某些细节在高权限下可能仍不完整,特别是在以下方面:
- `lsof`
- `launchctl`
- 某些目标上的代码签名详细信息
如果需要提升权限,请有意识地操作。
## 好的使用场景
- “这个 Mach 服务到底归谁所有?”
- “这个 launchd 任务是正常、过时还是损坏的?”
- “为什么这个的父进程是 launchd,但位置却不在我期望的地方?”
- “这个助手程序实际上拥有哪些授权?”
- “这个应用 Bundle 是否隐藏了内嵌的 XPC 服务?”
- “为什么这个进程看起来可疑?”
## 非目标
`machscope` 不打算成为:
- 完整的 EDR 系统
- 实时的内核遥测系统
- 完美的 XPC 观察器
- GUI 应用
- 庞大的框架
它是一个锋利的本地区工具,用于让 macOS 内部机制变得清晰可读。
## 状态
早期阶段,但已经有用。
当前的输出和图模型是刻意设计的,以便未来版本可以添加:
- TUI 探索
- 差异对比模式
- 导出/渲染集成
- 更丰富的信任规则
- 更好的跨目标图遍历
标签:DAST, launchd, Mach-O, Mach服务, macOS内部机制, macOS安全, 二进制发布, 代码签名, 信任关系, 关联图, 动态分析, 子域名枚举, 开源工具, 异常检测, 恶意软件分析, 持久性分析, 授权分析, 数字取证, 系统安全, 终端工具, 自动化脚本, 进程分析, 逆向工具, 零依赖