# 工具盘点与有界 CLI `scripts/tool_runner.py` 仅依赖 Python 3.10+ 标准库;实际工具、Binwalk 模块和 MediaInfo DLL 需本机单独配置。它收集可复核证据,不判定测试通过。所有公开命令返回都有 `execution_status` 和 `test_verdict: "not_evaluated"`。`completed` 只代表进程退出码为 0;端口状态、媒体指标和采集覆盖度仍需与用例标准比对。 ## 配置与盘点 从 Skill 根目录运行下面示例。全局选项放在子命令之前。执行网络、抓包或串口命令前,须已确定用户授权的目标、网卡/串口、端口、时长和证据目录;本适配器不自动发现设备、不推断路由器入口。 ```powershell python scripts/tool_runner.py list python scripts/tool_runner.py --tool-root 'D:\ApprovedTools' doctor python scripts/tool_runner.py --profile .\device-profile.json doctor --check-versions ``` `list` / `doctor` 默认只查文件;只有显式 `--check-versions` 才运行已定位的可执行程序的版本/帮助参数,每个进程最多 5 秒。`--dry-run doctor --check-versions` 不启动程序。`--tool-root` 可重复,扫描最多 4 层、每个根目录最多 20000 个文件名,不解压包。只将用户明确指定的可信已解压目录传给该参数。 原生可执行体发现顺序:`profile.tools` → `--tool-root` → `PATH`。Binwalk 的显式 Python 运行时优先于此顺序,MediaInfo DLL 只从显式 `libraries.mediainfo` 读取,详见下方配置。可执行文件名必须匹配工具 ID 的固定候选名;不接受 `cmd`、`wsl`、shell wrapper 或安装器代替工具。`powershell` 同时接受 `powershell.exe` / `pwsh.exe`。profile 中的相对路径按 profile 所在目录解析。 ```json { "tools": { "ffprobe": "D:/ApprovedTools/ffmpeg/bin/ffprobe.exe", "ffmpeg": "D:/ApprovedTools/ffmpeg/bin/ffmpeg.exe", "tshark": "D:/ApprovedTools/Wireshark/tshark.exe", "dumpcap": "D:/ApprovedTools/Wireshark/dumpcap.exe", "nmap": "D:/ApprovedTools/Nmap/nmap.exe" }, "runtimes": { "binwalk_python": "D:/ApprovedTools/binwalk-env/Scripts/python.exe" }, "libraries": { "mediainfo": "D:/ApprovedTools/MediaInfo/MediaInfo.dll" }, "auth": { "password_env": "DEVICE_PASSWORD" } } ``` 以上路径只是格式示例,按实际已安装位置填写;不必列出未安装工具。分发脚本不含开发机的安装路径。profile 不能保存明文密码、token、带认证信息的 URL 或 RTSP URL。`password_env` 等环境变量引用可以保留,但工具不会自动使用密码登录。 `runtimes` 只接受 `binwalk_python`;`libraries` 只接受 `mediainfo`。这两处只填本地文件路径,不接受对象、模块名、脚本路径、命令行或额外参数。相对路径同样以 profile 所在目录为基准。`binwalk_python` 配置优先于 `tools.binwalk`,固定执行 `python -I -m binwalk`;Python 文件名须为 `python.exe`、`python` 或相应 `python3[.N]` 名称。未配置时仍使用原来的 Binwalk 可执行体发现方式。MediaInfo 只接受显式配置的 `MediaInfo.dll`,不会运行 GUI 或安装器。 | availability | 含义 | | --- | --- | | `executable-found` | 找到名字匹配的文件;未证明驱动、依赖、权限、版本兼容或设备连通性 | | `python-module-configured` | 找到配置的 Python;须通过 `--check-versions` 确认 Binwalk 模块能加载 | | `library-found` | 找到配置的 MediaInfo DLL;须通过版本检查确认可加载,再用实际媒体验证解析 | | `package-only` | 在指定 root 中只看到对应 `.zip` / `.7z` 文件;没有可执行体 | | `missing` | 当前 profile/root/PATH 未定位工具;静态 `package_evidence` 仍可记录历史包证据 | | `manual-interface` | 原网页或 GUI;此适配器没有其专有 CLI,不表示程序缺失,也不阻止宿主原生 GUI/浏览器路由 | | `mcp-check-required` | 已确认的MCP路由;CLI不检查MCP连接、Android设备或任务就绪性,需使用相应MCP工具 | | `orchestrator-context` | Codex协作编排上下文;不作为独立PC工具安装状态 | 完整固定 ID 与证据见 `assets/tool-catalog.json`。Wireshark/Nmap ZIP 有相应 EXE 成员;Binwalk 外层 ZIP 有源码、教程及 Python 安装器,固定隔离模块入口已有本地样本验证;FFmpeg 7z 的包版本不能代替实际运行版本。mainThread 的真实程序和手册已取得,其专有能力仍按原生窗口路由。压缩包存在、已启动或版本检查通过均不等于登录及业务可用。内部配置、移动视联、客诉、联楹、路由器保留原入口;账号统计表未读取或复制。 ## 子命令 | 子命令 | 必填输入 | 固定行为与边界 | | --- | --- | --- | | `probe` | `--input FILE` 或 `--rtsp-env NAME` | FFprobe;输出选定编解码/分辨率/帧率/格式字段;本地输入只允许 `file` 协议 | | `media-info` | `--input FILE` | Windows MediaInfo DLL;拒绝直接URL/UNC输入,回读确认Internet选项关闭;每类最多100路,输出通用/视频/音频白名单字段 | | `analyze-pcap` | `--input PCAP` | TShark `-r -n -T fields`;默认1000、最多10000包;仅时间、长度、地址、端口、协议列 | | `capture` | `--interface ID --host IP --duration SEC --output PCAPNG` | Dumpcap;`host IP` 过滤;1..600秒;100MiB上限;snaplen=256 | | `scan` | `--host IP --ports 22,80,554` | Nmap TCP connect `-sT -n -Pn`,最多128个明确端口;无NSE、网段、主机名、服务版本探测 | | `firmware-scan` | `--input FILE` | `binwalk FILE` 或固定 Python 模块入口,默认签名分析;不自动解包、不执行提取物;本地实测版本为2.3.2,其他版本另核验 | | `serial` | `--port COMx --baud N --duration SEC --output LOG` | PowerShell串口脚本;1..600秒;原始字节与时间戳文本;不发登录或其他命令。可显式指定 `--dtr-enable` / `--rts-enable`,两者默认关闭 | 所有进程使用参数数组及 `shell=False`,没有 `--args` / 任意参数透传。默认进程时限60秒,串口/抓包为时长+10秒;`--timeout` 可设1..3600的整数,抓包/串口须至少比采集时长多5秒。输出目录须已存在,输出文件和串口 `.raw.bin` 必须不存在,防止追加或覆盖已有证据。 ```powershell python scripts/tool_runner.py --profile .\device-profile.json probe --input .\recording.mp4 python scripts/tool_runner.py --profile .\device-profile.json media-info --input .\recording.mp4 python scripts/tool_runner.py --profile .\device-profile.json analyze-pcap --input .\capture.pcapng --max-packets 500 python scripts/tool_runner.py --profile .\device-profile.json --dry-run capture --interface 1 --host 192.0.2.10 --duration 30 --output .\evidence\device.pcapng python scripts/tool_runner.py --profile .\device-profile.json --dry-run scan --host 192.0.2.10 --ports 22,80,554 python scripts/tool_runner.py --profile .\device-profile.json firmware-scan --input .\firmware.bin python scripts/tool_runner.py --dry-run serial --port COM9 --baud 115200 --duration 60 --output .\evidence\serial.log ``` 示例使用文档地址 `192.0.2.10`;必须替换为用户明确提供且授权的单个目标。`--dry-run` 仍检查输入和可执行体,输出脱敏后的参数计划,不启动进程。计划确认后移除 `--dry-run` 才执行。无需把整个工具目录提取或安装到 Skill;工具包和驱动安装属于独立的环境准备操作。 ### Binwalk 与 MediaInfo 运行条件 Binwalk 2.3.2 的 Python 源码依赖 `imp`,不兼容 Python 3.12+;本机已用 Python 3.11 的独立 venv 安装用户提供源码并验证签名扫描。团队部署时使用已验证的独立环境或相容的原生 Binwalk,不更换 Artemis 的 Python。`-I` 忽略用户 site/PYTHONPATH;每次调用另设空的临时 `XDG_CONFIG_HOME`,避免自动加载用户自定义插件。不会自动安装模块。`doctor --check-versions` 成功只能证明模块帮助可运行,扫描仍需本地文件验证。 MediaInfo 使用与当前 Python 位数匹配的 Windows DLL;32/64位不匹配、DLL 缺依赖或 API 缺失会返回失败。解析在运行器自己启动的固定子进程中执行,沿用 `--timeout`;内部 `_media-info-worker` 是实现细节,不用于直接调用或替换超时入口。它将 `Internet` 设为空字符串,并严格要求 `Internet_Get` 返回空字符串,否则拒绝解析;21.09 中 `No` 等非空值反而启用该选项。直接URL/UNC输入已拒绝,但此配置不是操作系统级网络隔离保证。输出不含 CompleteName、标题、标签或完整 Inform 文本。Duration 使用 MediaInfo 原生毫秒值,FrameRate 为帧/秒,FileSize 为字节;不要直接与 FFprobe 的秒制 Duration 相减。已用 MediaInfoLib 21.09 在 Python 3.14 及 Artemis 当前 Python 验证本地样本,不代表所有媒体格式或 GUI 功能均已验收。 ### RTSP 凭据 用户必须提供完整 URL,不能猜测通道路径。只从指定环境变量读取,不接受 `--url` 或 profile 中的 URL。交互式 PowerShell 可避免把完整 URL 写入命令历史: ```powershell $rtspInput = Read-Host '输入完整 RTSP URL' -AsSecureString $env:CAMERA_RTSP = [System.Net.NetworkCredential]::new('', $rtspInput).Password try { python scripts/tool_runner.py --profile .\device-profile.json probe --rtsp-env CAMERA_RTSP --transport tcp } finally { Remove-Item Env:CAMERA_RTSP -ErrorAction SilentlyContinue $rtspInput.Dispose() } ``` JSON输出、计划、异常不回显完整URL或其中的凭据;FFprobe只输出固定字段并对文本二次脱敏,合法的数值/帧率字段作为测量值保留,避免短查询值(如 `token=1`)误伤 `20/1`、`8000` 等指标。完整URL在计划中整体替换,stderr直接丢弃,子进程移除 `FFREPORT` 防止工具日志持久化完整命令行。FFprobe需要在其进程参数中接收URL,因此同一主机上有进程查看权限的程序仍可能看到它;不能声称环境变量消除了这一点。不要保存终端明文输入或环境快照。 ### 证据限制 抓包默认仅截取前256字节,适合连接/协议/时序分析,不能作为完整负载或码流内容证据。抓包文件和串口原始日志仍可能包含设备发送的敏感信息;命令不把其内容打印到JSON,分享前按项目规则脱敏。运行器抑制所有外部工具stderr;非零退出码、超时只给固定错误码,排错先核对工具、文件、权限和参数,不以打印含凭据命令替代诊断。 Nmap的主机时限可能让部分端口未完成;`execution_status=completed` 不等于所有请求端口都被覆盖。FFprobe元数据不等于持续码率、丢帧率或长期流稳定性;Binwalk签名结果不等于固件安全结论;本适配器不据此输出PASS/FAIL。 Nmap XML可能把同状态端口折叠到 ``。扫描结果保留 `requested_ports`、逐端口 `ports` 及 `aggregate_states`(state/count/reasons)。每个主机的 `ports_not_individually_reported` 列出缺少明确TCP端口状态的请求端口,`individual_port_coverage` 为 `complete` / `partial` / `none`,只描述逐端口结果覆盖度。聚合组即使计数与剩余端口数量相等,也不会被展开为各端口状态;多个聚合组之间更不能猜测端口归属。没有主机结果时 `host_results_present=false`。这些字段用于暴露证据缺口,不能把聚合计数、退出码0或缺失端口解释为全覆盖或测试通过。 ### 串口来源 `scripts/vendor/serial_monitor.ps1` 从用户给定参考包 `embedded-app-pc-debug/scripts/serial_monitor.ps1` 原样复制。SHA-256: `173584db05950b9842f2485eec5b33c0b16062f944216c283a18e038a9138a67` 包装器每次构造计划时校验该哈希。脚本独占打开COM口,默认8N1、无流控、DTR/RTS不启用,记录 `LOG` 和 `LOG.raw.bin`;包装器不暴露发送命令。`--dtr-enable` / `--rts-enable` 分别映射原脚本已有的 `-DtrEnable` / `-RtsEnable`,用于复现已确认且获授权的现场会话设置,JSON同时记录实际开关值。它们不启用RTS/CTS或DTR/DSR握手,不应仅因一次无数据就盲目组合切换。某些设备将控制线用于复位,已知会触发复位时不能把它当作一般只读采集。没有参数时行为保持不变。 下面仅演示一个已确认需要同时启用DTR/RTS的本机会话;不是所有设备的默认配置。`profile.serial` 当前只作为环境资料,本运行器不会从中读取控制线或其他串口参数;实际行为由命令行显式值决定。 ```powershell python scripts/tool_runner.py --profile .\device-profile.json serial --port COM9 --baud 115200 --duration 5 --output .\evidence\serial.log --dtr-enable --rts-enable ``` 打开串口仍依赖设备、驱动与操作系统权限,并可能改变端口占用;运行适配器允许在授权目标上做限定时长的现场验证。若用户终端占用端口,报告占用并等待释放,不关闭或抢占其会话。现场结果放到独立的运行报告,不作为其他机器可用性的保证。执行策略若阻止脚本,报告环境条件,不自动绕过策略。 ## 状态与退出码 | execution_status | CLI退出码 | 解释 | | --- | --- | --- | | `planned` / `completed` | 0 | 计划构造成功或进程结束;无测试结论 | | `failed` / `timed_out` / `launch_failed` / `output_invalid` | 1 | 工具失败、超时、无法启动或输出格式异常 | | `invalid_arguments` / `configuration_error` | 2 | 参数/本地文件配置错误;不回显原始参数 | | `tool_missing` | 3 | 缺少对应执行文件、已配置Python或DLL;按上文tools/runtimes/libraries配置,MediaInfo不查PATH | ## 官方参数来源 - [FFprobe 官方文档](https://ffmpeg.org/ffprobe.html):元数据、JSON writer、字段选择。 - [TShark 手册](https://www.wireshark.org/docs/man-pages/tshark.html):离线输入与 fields 输出。 - [Dumpcap 手册](https://www.wireshark.org/docs/man-pages/dumpcap.html):网卡、capture filter、停止条件与snaplen。 - [Nmap 参考指南](https://nmap.org/book/man.html):显式目标、TCP connect、端口与时限选项。 - [Binwalk 官方项目](https://github.com/ReFirmLabs/binwalk):默认固件签名分析,提取是单独选项。 - [MediaInfo DLL 官方接口](https://github.com/MediaArea/MediaInfoLib/blob/master/Source/MediaInfoDLL/MediaInfoDLL.h):固定 `New/Open/Get/Count_Get/Option/Close/Delete` API。 - [MediaInfo SDK Quick Start](https://mediaarea.net/en/MediaInfo/Support/SDK/Quick_Start):API 初始化及版本读取。 - [MediaInfo 21.09 配置实现](https://raw.githubusercontent.com/MediaArea/MediaInfoLib/v21.09/Source/MediaInfo/MediaInfo_Config.cpp):Internet 空字符串关闭及 Internet_Get 回读语义。 测试:`python -m unittest discover -s tests -p test_tool_runner.py -v`。单元测试只构造命令并模拟外部进程结果;不会连接设备、扫描或抓包。实际可用性由当前机器的doctor、限定本地样本及经授权的现场验证分别说明,不能从一次适配器执行成功推广成实机功能验收。