凌晨三点收到负载告警,登进服务器发现多了几个不认识的进程和定时任务,很多站长的第一反应是直接重启或者干脆重装系统——这恰恰是新手最容易犯的错误:重启和重装会抹掉攻击者留下的大部分痕迹,让你事后连发生了什么都查不清楚。这篇文章教你如何在不破坏现场的前提下,只用系统自带的 last、lastb、auth.log 和 history 这四类工具,判断你的 VPS(虚拟专用服务器)或独服(独立服务器)是否真的被入侵,以及入侵者登录进来之后到底做了什么。全程不需要额外安装任何软件,一台跑着主流 Linux 发行版的机器就能直接操作。
动手之前:先保住现场,再谈排查
在敲第一条命令之前,先明确一个原则:此时这台机器上的每一份日志都是证据,你的目标是”取证”,不是”杀毒”。如果在排查前就急着重启服务、删文件或者重装面板,攻击者的登录记录、提权痕迹和历史命令会被一并清空,后面所有结论都只能靠猜。正确的做法是先做最小化的保全动作,再逐项核查。
具体来说,排查前的保全动作只需要三步。第一步,如果条件允许,用云控制台的快照功能对整台机器做一次快照,云服务器(Cloud Server)和 VPS(虚拟专用服务器)一般都支持在线快照,几 GB 的系统盘几分钟就能完成。第二步,立即把关键日志目录打包备份到本机之外,例如执行 tar czf /root/forensics-$(date +%F).tar.gz /var/log,并把压缩包下载到你自己的电脑上,防止攻击者后续清理日志。更多关于主机层面数据安全与备份策略的思路,可以参考这篇美国虚拟主机安全与备份实战指南。第三步,在排查期间尽量不要再登录无关的业务系统,避免你自己的正常操作混进证据里干扰判断。这三步做完,就可以放心开始核对登录记录了。
第一现场:用 last 和 lastb 核对登录记录
last:谁登录过、什么时候、从哪里来
last 命令读取 /var/log/wtmp 这个二进制文件,列出所有成功的登录记录,包括登录用户、来源 IP(互联网协议地址)、登录时间和退出时间。排查时先看最近 50 条:
last -n 50
last -n 50 -F # 显示完整年份和秒级时间
last root # 只看 root 账户
重点看三类异常:一是不该出现的来源地区,比如你的业务只面向国内用户,日志里却出现了大量海外 IP 的成功登录;二是不该出现的时段,比如凌晨两点到五点之间出现了交互式登录;三是不该出现的账户,比如你平时只用某个普通用户加密钥登录,日志里却出现了 root 的密码登录记录。发现可疑条目后,把对应的 IP 和时间点记下来,这两样东西是后面所有交叉验证的锚点。

lastb:被拒绝的登录里藏着多少攻击
lastb 读取 /var/log/btmp,记录的是所有失败的登录尝试。暴力破解(攻击者用密码字典反复试登录)的机器,这个文件往往大得惊人:
lastb -n 30
lastb | awk '{print $3}' | sort | uniq -c | sort -rn | head -20
第二条命令会统计失败登录中出现的来源 IP 并按次数倒序排列,快速暴露攻击最集中的几个地址。如果某个 IP 在失败记录里出现了成千上万次,说明它正在跑字典;如果它偶尔还成功登录过一次(在 last 里出现),那基本可以确认这就是攻击入口。
核心证据:逐行解读 auth.log 与 secure
Debian/Ubuntu 系的认证日志在 /var/log/auth.log,RHEL/CentOS 系在 /var/log/secure,两者内容结构一致,都是明文文本,可以直接用 grep 过滤。相比 last 只给结论,auth.log 会记录每一次认证尝试的完整过程,是判断”密码破解还是密钥泄露”的关键。
grep 'Accepted' /var/log/auth.log # 所有成功登录
grep 'Failed password' /var/log/auth.log # 所有失败尝试
grep 'session opened' /var/log/auth.log # 会话与提权记录
拿到成功登录列表后,重点核对认证方式:日志里 Accepted password for root 说明对方是用密码登进来的,配合 lastb 里的海量失败记录,可以判定为暴力破解;如果显示的是 Accepted publickey,但authorized_keys 里并没有你添加过的那把密钥,那说明攻击者早就写入了后门公钥,这就不是改密码能解决的了,必须清理 ~/.ssh/authorized_keys。另外别忘了用 journalctl -u ssh --since "2026-10-01" 这类命令查 systemd 日志,有些发行版轮转后 auth.log 只保留最近几周,journalctl 里能翻到更早的记录。

还原动作:用 history 看攻击者进来之后干了什么
确认了”谁在什么时候登进来”,下一步是还原”他做了什么”。bash 的历史命令记录在用户主目录的 .bash_history 文件里,直接执行 history 就能看当前用户的记录,配合时间戳食用效果更好:
HISTTIMEFORMAT="%F %T " history | tail -100
cat /root/.bash_history | tail -200
stat /root/.bash_history # 看文件最后修改时间
排查历史命令时,优先搜索这几类高危操作:grep -E 'wget|curl' .bash_history 找下载行为(攻击者常用它拉取挖矿或后门程序);grep -E 'useradd|passwd|chmod|chattr' .bash_history 找账户和权限改动;grep -E 'crontab|systemctl' .bash_history 找持久化痕迹——攻击者最喜欢把恶意脚本写进定时任务实现开机自启。如果 .bash_history 是空的,或者文件的修改时间明显晚于最后一次可疑登录,大概率是攻击者执行过 history -c 清空了记录,这本身就是一个强入侵信号,此时应转而从 /var/log/audit/、进程启动时间(ps -eo pid,lstart,cmd)等旁证继续还原时间线。如果你手上这台是海外 VPS(虚拟专用服务器),日志轮转策略和发行版差异可以对照这篇美国 VPS 服务器优化指南里的环境说明先行确认。
交叉验证:把三类证据拼成完整时间线
单一日志都存在被篡改的可能,可信的结论来自多源印证。实操中推荐按”登录入口 → 停留时长 → 落地动作”三段式拼时间线:先用 last 确定可疑登录的时间点和来源 IP;再用 auth.log 里同一时段的记录确认认证方式是密码还是密钥;最后用 history 和定时任务目录(/var/spool/cron、/etc/cron.d)核对该时段之后的文件改动。三个来源指向同一个 IP、同一串时间,结论才站得住。需要提醒的是,last 读取的 wtmp 是二进制格式,攻击者拿到 root 后可以删除整个文件来抹掉记录——如果你发现 /var/log/wtmp 文件不存在或者修改时间很奇怪,不要直接认定”没被入侵”,反而要提高警惕。

排查完之后:堵住入口比查明真相更急
时间线拼出来之后,处置顺序有讲究:先堵入口,再清后门,最后才是复盘。堵入口的常见组合是改用密钥登录并关闭密码认证(sshd_config 里把 PasswordAuthentication 设为 no)、用防火墙把 22 端口限制到固定出口 IP、清理 authorized_keys 里的陌生公钥。清后门则顺着 history 的线索,删掉恶意定时任务、陌生 systemd 服务和被替换的二进制。如果攻击者已经取得过 root,最稳妥的方案仍然是迁移重装:把确认干净的网站数据导出,重装系统后再恢复,比在已经被污染的系统上”打补丁”可靠得多。
写在最后
总结一下整套排查思路:last 和 lastb 回答”谁进来了”,auth.log 回答”怎么进来的”,history 回答”进来之后干了什么”,三者交叉印证才能下结论。如果你需要一台方便做这类安全演练的环境,Hostease 美国 VPS 方案支持快照和重装,配合中文工单响应,排查期间需要临时重置系统时比较省事。日常运营中,建议每月固定做一次登录记录巡检,把 last 输出和自己的运维日历对一遍;对暴露在公网的机器,可以考虑叠加 fail2ban 这类自动封禁工具,把暴力破解扼杀在字典跑完之前。




