Sysinternals 文件工具学习笔记(12.12):常见踩坑场景、排障套路与面试问题
-
- 一、为什么还要多写这一篇?
- 二、常见踩坑场景合集:这些坑很常见,也很好躲
-
- [1. Strings / Streams:当杀毒软件用,翻车](#1. Strings / Streams:当杀毒软件用,翻车)
- [2. Junction / FindLinks:删错"入口",不是删错"内容"](#2. Junction / FindLinks:删错“入口”,不是删错“内容”)
- [3. DU:一言不合扫全盘,搞成"自带压测"](#3. DU:一言不合扫全盘,搞成“自带压测”)
- [4. PendMoves / MoveFile:路径写错 = "重启后惊喜"](#4. PendMoves / MoveFile:路径写错 = “重启后惊喜”)
- [三、典型故障场景 → 该用哪一套 Sysinternals 组合拳?](#三、典型故障场景 → 该用哪一套 Sysinternals 组合拳?)
-
- [场景 1:某盘突然 99%,谁吃的?](#场景 1:某盘突然 99%,谁吃的?)
- [场景 2:目录删不掉,说"被占用/访问拒绝"](#场景 2:目录删不掉,说“被占用/访问拒绝”)
- [场景 3:明明更新了 DLL / EXE,程序还是"读旧的"](#场景 3:明明更新了 DLL / EXE,程序还是“读旧的”)
- 四、几段值得收藏的"小脚本模式"
-
- [1. 扫描日志目录并列出 Top N 目录](#1. 扫描日志目录并列出 Top N 目录)
- [2. 按扩展名找大文件 + 预留清理名单](#2. 按扩展名找大文件 + 预留清理名单)
- [五、面试 / 复盘里可以用到的问答点](#五、面试 / 复盘里可以用到的问答点)
-
- [Q1:NTFS 里的 Junction、软链接、硬链接,有什么区别?](#Q1:NTFS 里的 Junction、软链接、硬链接,有什么区别?)
- [Q2:为什么有时要用 PendMoves / MoveFile,而不是直接覆盖文件?](#Q2:为什么有时要用 PendMoves / MoveFile,而不是直接覆盖文件?)
- [Q3:如果你怀疑有人用 ADS 藏数据,你会怎么做?](#Q3:如果你怀疑有人用 ADS 藏数据,你会怎么做?)
- [六、第 12 章快速回顾:你现在应该会什么?](#六、第 12 章快速回顾:你现在应该会什么?)
本篇是第 12 章的「番外总结篇」:不再逐个讲命令,而是帮你把 Strings / Streams / Junction / FindLinks / DU / PendMoves / MoveFile 串成一套"文件世界作战手册"。
一、为什么还要多写这一篇?
你前面已经学了:
- 怎么用 Strings 挖可执行文件里的文本
- 怎么用 Streams 找 NTFS 隐藏数据流
- 怎么用 Junction / FindLinks 玩转 NTFS 链接
- 怎么用 DU 查谁在吃磁盘
- 怎么用 PendMoves / MoveFile 在重启后悄悄动文件
但真正在线上环境,你遇到的不是"命令行参数选择题",而是:
- "某盘突然爆满"
- "某目录怎么删都删不掉"
- "我明明删了,但程序还是读到旧的 DLL"
- "要替换系统文件,还怕一脚踢死机器"
这一篇就是:
把这些工具从「百科」变成「战术包」------告诉你 常见误区、几类典型故障的套路、以及一些面试/复盘时好用的问题与答法。
二、常见踩坑场景合集:这些坑很常见,也很好躲
1. Strings / Streams:当杀毒软件用,翻车
典型误区
- 看到文件里有一段"奇怪的 URL / shellcode 样式字符串",就认定这是"木马"
- 把所有带 ADS(替代数据流)的文件统统干掉
更稳的做法
-
Strings 只是"有字符串",不是"有罪证"
- 很多库文件会内置调试路径、内部接口名,看起来都很"邪门"
- 正确姿势:结合 ProcMon / 签名 / 时间线,看是否真的被加载、被调用
-
Streams 删除前先确认:
bashstreams -s C:\Path\To\Folder- 注意有些软件(备份、加密、标签)会用 ADS 存元数据
- 删之前至少:
- 只删不认识的、自建目录里的 ADS
- 系统目录(Windows、Program Files)里的,先查清是哪个软件写的
2. Junction / FindLinks:删错"入口",不是删错"内容"
典型翻车:
- 某人对着一个 junction / 硬链接目录来了一发
robocopy /MIR或rmdir /s - 结果发现:真正的源数据被洗了,哭着去找备份
几点硬记:
- 先认清它是不是链接:
bash
junction C:\Some\Path
findlinks C:\Some\File
- Junction 输出里会有
Substitute Name/Print Name - FindLinks 会列出同一个 MFT 记录的所有路径
- 操作建议:
- 删除目录前多花 5 秒跑一下
junction - 搬运大量数据时,prefer robocopy 的
/SL(按链接本身处理)或清晰区分"入口 vs 真实存储"
3. DU:一言不合扫全盘,搞成"自带压测"
典型现象:
-
运维在生产机直接来一句:
bashdu C:\ -
然后磁盘灯红到飞起,业务开始哀嚎。
更温柔的姿势:
-
优先锁定「怀疑区域」再扫描:
bashdu -q -l 1 C:\inetpub\logs du -q -l 2 D:\Data -
结合 最近变更 与 应用路径,按目录深度逐层下钻
-
对于大盘(>1TB),建议:
- 先用系统自带
Storage Sense / WinDirStat做初筛 - 再用 DU 精细扫重点目录
- 先用系统自带
4. PendMoves / MoveFile:路径写错 = "重启后惊喜"
典型事故:
- 计划重启后删一个老版 DLL,结果:
- 打错路径,删了现用 DLL
- 或者路径写成了
C:\Windows\System32\下的其他东西
- 重启之后:服务起不来,甚至蓝屏
使用这两个工具的三条红线:
-
一定要先 dry run & 记录:
bashpendmoves- 看当前排队里已有啥,不要误删别人的"待执行操作"
-
对要删除/替换的文件:
- 跑一遍
sigcheck/ hash 校验 - 确认确实是你要动的那一个版本
- 跑一遍
-
尽量锁到"明确路径 + 明确文件名",避免用模糊路径或变量不明的脚本
三、典型故障场景 → 该用哪一套 Sysinternals 组合拳?
场景 1:某盘突然 99%,谁吃的?
推荐流程:
-
粗定位:
bashdu -q -l 1 D:\- 找出前 3--5 个最大目录
-
深挖具体目录:
bashdu -q -l 2 D:\BigApp -
怀疑日志/缓存不断增长?
- 配合 ProcMon 看对这些目录的写入
- 若是"每日轮转没删旧日志",提方案改轮转策略
场景 2:目录删不掉,说"被占用/访问拒绝"
推荐组合:Handle + PsTools + Streams
-
找谁在占:
bashhandle C:\Problem\Dir -
如果是某服务/进程:
pslist看活性- 合理情况下
pskill,或psservice停服务
-
若目录无句柄仍删不掉:
- 用
streams -s看有没有奇怪 ADS - 检查是不是 junction 指向了你没权限的地方
- 用
场景 3:明明更新了 DLL / EXE,程序还是"读旧的"
推荐组合:FindLinks + PendMoves / MoveFile
-
看文件是否有硬链接 / 多路径:
bashfindlinks C:\Path\NewLib.dll- 如果同一个物理文件挂了多个逻辑路径,你以为更新了 A,程序实际上加载的是 B
-
需要在重启后原子替换系统文件:
bashmovefile C:\New\Good.dll !C:\Windows\System32\Target.dll- 或先安排删除旧版本,再安排移动新版本
- 全程记录执行计划(存一份脚本/工单),方便回滚和追责
四、几段值得收藏的"小脚本模式"
1. 扫描日志目录并列出 Top N 目录
bat
@echo off
set LOGROOT=D:\Logs
echo === 目录磁盘占用(Top 10) ===
du -q -l 2 "%LOGROOT%" | sort /R /+15 | head -n 10
思路:用
du递归统计,再交给排序工具处理。发布到公司内部"磁盘告警 Runbook"里非常合适。
2. 按扩展名找大文件 + 预留清理名单
bat
@echo off
set ROOT=D:\Data
set EXT=*.log
echo 扫描 %ROOT%,查找扩展名为 %EXT% 的前 50 个大文件:
dir "%ROOT%\%EXT%" /S /O:-S /B > bigfiles.log
echo 结果已写入 bigfiles.log,请人工审核后再删除。
重点是"人工审核"四个字------永远给自己留一步"人脑确认"。
五、面试 / 复盘里可以用到的问答点
这些不是让你背,而是给你一个"能说得明白"的结构。
Q1:NTFS 里的 Junction、软链接、硬链接,有什么区别?
- 硬链接(hard link) :多条目录项指向同一底层文件记录(MFT Record),删除任意一条并不会立即删数据,直到最后一个被删
- 目录联接(junction)/ reparse point:目录级别的"指向别处的入口",更像"内核级的快捷方式"
- 符号链接(symlink):可指向文件/目录,可以跨卷,类似 Unix 下的 symlink
Sysinternals 的 Junction / FindLinks 就是这块的"放大镜"。
Q2:为什么有时要用 PendMoves / MoveFile,而不是直接覆盖文件?
- 很多系统文件、正在被服务加载的 DLL 都处于"锁定使用"状态
- 直接覆盖会失败、或在某些情况下产生"文件半旧半新"这种极难复盘的状态
- PendMoves / MoveFile 通过 在注册表里安排"重启后执行的文件操作队列" 来保证:
- 操作在系统启动早期、文件尚未被占用时执行
- 多步操作(删旧、移新)可以原子化串在一起,降低"中间态"
Q3:如果你怀疑有人用 ADS 藏数据,你会怎么做?
大致回答思路:
- 用
streams -s扫描重点目录(用户目录、上传目录、临时目录等) - 关注:
- 不常见的 ADS 名称
- ADS 大小异常、创建时间与主文件不一致
- 可结合:
sigcheck校验主文件是否被篡改ProcMon看是否有进程读写该 ADS
- 高风险环境下:先隔离样本,再用安全产品/沙箱分析,不直接在线上机器上打开
六、第 12 章快速回顾:你现在应该会什么?
不按原书目录,而按"能力地图"来复盘:
- 可见/不可见内容分析
- Strings:找文件里的文本线索
- Streams:发现 NTFS 隐藏数据流
- 路径与链接结构分析
- Junction:识别目录联接
- FindLinks:识别硬链接、多路径共用同一文件
- 磁盘空间与大文件定位
- DU:从盘 → 目录 → 子目录,逐层找"胖子"
- 受锁文件与重启后操作
- PendMoves / MoveFile:安排重启后删除/替换,做"外科手术型操作"
再叠加你前面学过的 ProcMon / PsTools / SigCheck / AccessChk,其实已经可以搭一套很不错的 Windows 故障排查工具栈 了。
结尾就留一句:
遇到"文件相关的怪事",先思考它属于哪一类(内容/链接/空间/锁定/时机),再从工具箱里挑一个合适的 Sysinternals 组合,而不是条件反射打开资源管理器瞎点。
这就是整本书想给你的思维升级。