背景与问题
Linux 提权(Privilege Escalation)是指攻击者或恶意用户从低权限账号获取更高权限的过程。在实际的安全事件中,攻击者很少能直接获得 root 权限,更多的情况是首先通过某个漏洞或配置错误获得普通用户权限,然后通过各种提权技术获得 root 权限。
对于运维工程师来说,了解提权风险是至关重要的。一方面,服务器可能被攻击者入侵,攻击者会尝试提权;另一方面,公司内部的普通用户也可能尝试提权到 root 权限,执行未授权的操作。运维人员有责任确保系统配置安全,防止提权发生。
本文详细介绍 Linux 系统中常见的提权风险点:危险的 SUID 程序、内核漏洞利用、sudo 配置错误、计划任务(cron)漏洞、密码和密钥管理、容器逃逸风险等。通过了解这些风险点,运维人员可以有针对性地进行安全加固。
1 SUID 程序提权
1.1 SUID 机制原理
SUID(Set User ID)是 Linux 的一种特殊权限机制。当可执行文件设置了 SUID 位时,任何用户执行该文件都会以文件所有者的身份运行,而不是执行者的身份。
例如,/usr/bin/passwd 文件设置了 SUID 位且所有者是 root,所以任何用户执行 passwd 命令时,都会以 root 身份运行,从而能够修改 /etc/shadow 文件。
# 查看设置了 SUID 位的文件
find / -perm -4000 -type f 2>/dev/null
# 查看具体的 SUID 程序及其权限
ls -la /usr/bin/passwd
# -rwsr-xr-x 1 root root 23272 Jan ... /usr/bin/passwd
# ^
# 注意 s 代替了 x,表示 SUID 位已设置
# 查看所有 SUID 程序
find /usr -perm -4000 -type f -exec ls -la {} \;
1.2 危险的 SUID 程序
并非所有 SUID 程序都是必需的,也不是所有 SUID 程序都是安全的。以下是常见的潜在危险 SUID 程序:
# nmap(旧版本可以执行任意命令)
find / -perm -4000 -type f -name "nmap" 2>/dev/null
# bash(如果设置了 SUID,可以直接获得 root shell)
find / -perm -4000 -type f -name "bash" 2>/dev/null
# python/perl/ruby 等脚本解释器(如果设置了 SUID)
find / -perm -4000 \( -name "python*" -o -name "perl*" -o -name "ruby*" \) 2>/dev/null
# find 命令(-exec 选项可以执行任意命令)
find / -perm -4000 -type f -name "find" 2>/dev/null
# vim/vi(可以读取和修改任意文件)
find / -perm -4000 -type f \( -name "vim" -o -name "vi" -o -name "nano" \) 2>/dev/null
1.3 SUID 提权示例
了解攻击者如何利用 SUID 程序提权,有助于我们更好地防御:
# bash SUID 提权
# 如果 bash 设置了 SUID,可以直接获得 root shell
bash -p
# nmap 提权(旧版本 interactive 模式)
nmap --interactive
!sh
# find 命令提权
find . -exec /bin/sh -p \; -quit
# vim 提权
vim -c ':!/bin/sh'
# perl 提权
perl -e 'exec "/bin/sh";'
# python 提权
python -c 'import os; os.system("/bin/sh")'
1.4 SUID 安全加固
原则:尽量减少 SUID 程序的数量;定期检查新出现的 SUID 程序;移除不必要的 SUID 位。
# 查找系统上所有的 SUID 程序,评估每个是否必要
find / -perm -4000 -type f 2>/dev/null > /tmp/suid_files.txt
cat /tmp/suid_files.txt
# 移除不必要的 SUID 位
chmod u-s /usr/bin/nmap # 移除 nmap 的 SUID
chmod u-s /usr/bin/bash # 移除 bash 的 SUID(如果设置了)
# 只对必要的程序保留 SUID
# 常见的必要 SUID 程序:passwd, su, sudo, pkexec, crontab, at, gpasswd, mount, umount, suidmanager
2 Sudo 配置错误提权
2.1 sudo 权限配置错误
sudo 配置不当是另一种常见的提权途径。运维人员有时为了"方便",会给用户分配过宽的 sudo 权限。
# 查看当前用户的 sudo 权限
sudo -l
# 查看所有用户的 sudo 权限(需要 root)
cat /etc/sudoers
cat /etc/sudoers.d/*
# 常见的危险 sudo 配置:
# 允许执行任意命令
username ALL=(ALL) ALL
%groupname ALL=(ALL) ALL
# 允许执行任意 shell 命令
username ALL=(root) /bin/bash
# 允许无密码 sudo(自动化脚本常用,但风险很高)
username ALL=(ALL) NOPASSWD: ALL
# 允许用户修改 sudoers 文件
username ALL=(ALL) /usr/sbin/visudo
username ALL=(ALL) /bin/chmod 777 /etc/sudoers
# 允许用户以 root 身份执行任何命令(可以用 vim 提权)
username ALL=(root) /usr/bin/vim
2.2 利用 sudo 权限提权
# 如果 vim 可以 sudo 执行
sudo vim
# 在 vim 中
:!/bin/sh
# 如果 less 可以 sudo 执行(less 可以调用 shell)
sudo less /etc/passwd
# 在 less 中
!sh
# 如果 find 可以 sudo 执行
sudo find . -exec /bin/sh -p \; -quit
# 如果 wget 可以 sudo 执行(可以覆盖 /etc/shadow 或 /etc/sudoers)
sudo wget -F /etc/shadow
# 但这个例子不完整,实际操作很复杂
# 如果 python 可以 sudo 执行
sudo python -c 'import os; os.system("/bin/sh")'
2.3 sudo 安全配置
# /etc/sudoers 配置示例
# 遵循最小权限原则
username ALL=(root) /usr/bin/systemctl restart nginx, /usr/bin/systemctl restart php-fpm
# 禁止危险命令
username ALL=(root) ALL, !/bin/bash, !/usr/bin/vim, !/usr/bin/less
# 使用 sudoers.d 目录管理
# /etc/sudoers.d/custom
# 每行一个配置,避免修改主配置文件
# 记录所有 sudo 操作
Defaults logfile="/var/log/sudo.log"
3 计划任务(Cron)提权
3.1 Cron 任务配置错误
系统或用户的 cron 任务如果配置不当,可能被攻击者利用提权。
# 查看系统 cron 任务
ls -la /etc/cron.d/
ls -la /etc/cron.daily/
ls -la /etc/cron.hourly/
cat /etc/crontab
# 查看当前用户的 cron 任务
crontab -l
# 查看其他用户的 cron 任务(需要 root)
crontab -u username -l
# 检查 cron 任务的权限
ls -la /etc/cron.d/
3.2 Cron 提权风险点
风险一:cron 任务执行的脚本可以被普通用户修改。
# 如果 cron 任务执行的是一个普通用户有写权限的脚本
# 该用户可以修改脚本内容,以 root 身份执行任意命令
# 检查 cron 脚本的权限
ls -la /etc/cron.daily/mybackup.sh
# -rwxrwxrwx 1 root root ... /etc/cron.daily/mybackup.sh
# 如果普通用户对此脚本有写权限,就存在风险
风险二:cron 任务使用的脚本路径没有使用绝对路径。
# 不安全的 cron 任务
@hourly /home/user/backup.sh # 如果 /home/user 在 PATH 中
# 安全的 cron 任务
@hourly /usr/local/bin/backup.sh # 使用绝对路径
风险三:环境变量问题导致的安全漏洞。
# cron 任务可能继承不安全的 PATH
# 如果 PATH 包含用户可写的目录
# 查看 cron 的环境
cat /etc/pam.d/cron
3.3 Cron 安全加固
# 确保 cron 任务脚本权限正确
chmod 755 /etc/cron.daily/myscript.sh
chown root:root /etc/cron.daily/myscript.sh
# 使用绝对路径
*/5 * * * * /usr/local/bin/check_service.sh
# 限制可写的环境变量
CRON_TZ=UTC
PATH=/usr/bin:/bin
# 记录 cron 执行日志
# /etc/rsyslog.conf 或 /etc/rsyslog.d/50-default.conf
cron.* /var/log/cron.log
systemctl restart rsyslog
4 密码和密钥提权
4.1 密码哈希提取
如果攻击者能够读取 /etc/shadow 文件(需要 root 权限才能写入,但可能有读取权限配置错误),可以尝试离线破解密码哈希。
# 检查 /etc/shadow 权限
ls -la /etc/shadow
# -rw-r----- 1 root shadow ... /etc/shadow
# 如果普通用户可以读取 /etc/shadow,就是严重漏洞
# 检查权限配置
grep shadow /etc/group
# 检查是否有文件意外设置了读取权限
find / -perm -004 -name "shadow" 2>/dev/null
4.2 SSH 密钥提权
如果攻击者能够读取用户的 SSH 私钥,可以利用该私钥访问其他服务器。
# 查找 SSH 私钥
find / -name "*.pem" -o -name "id_rsa" -o -name "id_ed25519" -o -name "id_ecdsa" 2>/dev/null
# 检查私钥权限
ls -la ~/.ssh/id_rsa
# 私钥应该是 600 权限
# 检查是否有密钥被错误地设置了过宽的权限
find /home -name "*.pem" -perm 0777 2>/dev/null
4.3 密码安全加固
# 设置强密码策略
# /etc/pam.d/common-password 或 /etc/pam.d/system-auth
password requisite pam_pwquality.so retry=3 minlen=12 dcredit=-1 ucredit=-1 lcredit=-1 ocredit=-1
# 参数说明:
# minlen=12 - 最小长度 12 字符
# dcredit=-1 - 至少 1 个数字
# ucredit=-1 - 至少 1 个大写字母
# lcredit=-1 - 至少 1 个小写字母
# ocredit=-1 - 至少 1 个特殊字符
# 限制密码历史(防止重复使用)
password sufficient pam_unix.so sha512 shadow nullok try_first_pass use_authtok remember=5
# 设置密码过期策略
# /etc/login.defs
PASS_MAX_DAYS 90
PASS_MIN_DAYS 7
PASS_WARN_DAYS 14
# 对已有用户设置密码过期
chage -M 90 -m 7 -W 14 username
5 内核和软件漏洞提权
5.1 内核漏洞
内核漏洞是提权最直接的途径。著名的 Dirty COW(CVE-2016-5195)、Spectre/Meltdown 等都允许普通用户提权到 root。
# 查看内核版本
uname -a
cat /proc/version
# 检查已知内核漏洞
# 使用 linux-exploit-suggester 工具
wget https://raw.githubusercontent.com/mzet-/linux-exploit-suggester/master/linux-exploit-suggester.sh
chmod +x linux-exploit-suggester.sh
./linux-exploit-suggester.sh
# 或者使用 ike
wget https://raw.githubusercontent.com/InteliSecure/Linux_Exploit_Suggester/master/les.pl
perl les.pl
5.2 Sudo 和其他软件漏洞
# 检查 sudo 版本是否有已知漏洞
sudo -V | head -3
# 检查其他常用软件版本
openssl version
nginx -v
apache2 -v
mysql --version
php -v
# 使用包管理器检查安全更新
apt list --upgradable 2>/dev/null | grep -i security
yum updateinfo list security 2>/dev/null
5.3 安全更新流程
# Debian/Ubuntu
apt update
apt list --upgradable
apt-get upgrade
apt-get dist-upgrade # 包含内核更新
# RHEL/CentOS
yum check-update
yum update
yum update --security # 只安装安全更新
# 定期执行安全更新
# 添加到 cron 或使用 unattended-upgrades 包
apt-get install unattended-upgrades
dpkg-reconfigure unattended-upgrades
6 容器逃逸提权
6.1 Docker 容器提权风险
在容器化环境中,容器逃逸是一种特殊的提权方式。如果容器配置不当,容器内的用户可能获得宿主机的 root 权限。
# 检查当前是否在容器中
cat /proc/1/cgroup | grep -i docker
ls /.dockerenv 2>/dev/null
# 检查 Docker socket 是否挂载到容器中
ls -la /var/run/docker.sock 2>/dev/null
# 如果存在,说明容器配置不安全
6.2 容器提权方式
如果 Docker socket 被挂载到容器中,容器内的用户可以控制宿主机上的 Docker,进而获得宿主机 root 权限:
# 在容器中如果能访问 /var/run/docker.sock
docker -H unix:///var/run/docker.sock run -v /:/host ubuntu chroot /host bash
# 这会以 root 身份在宿主机上执行命令
6.3 容器安全加固
# 不要在容器中挂载 Docker socket
# Kubernetes 中使用安全上下文
securityContext:
privileged: false
readOnlyRootFilesystem: true
# Docker 运行参数
docker run --rm --cap-drop ALL --read-only nginx
# 不要使用 --privileged 标志
docker run --privileged nginx # 危险
# 使用 AppArmor 或 SELinux 限制容器
apparmor=unconfined
selinux enabled
# 定期更新容器基础镜像
docker pull ubuntu:22.04
7 文件权限提权
7.1 NFS 和文件共享提权
通过网络文件系统共享的文件,如果权限配置不当,可能导致提权。
# 检查 NFS 导出
cat /etc/exports
showmount -e localhost
# 检查 NFS 挂载
mount | grep nfs
# 检查可写的 NFS 导出(no_root_squash)
# 如果某个导出是 no_root_squash,在客户端的 root 可以变成服务端的 root
7.2 敏感文件权限
# 检查关键系统文件的权限
ls -la /etc/passwd /etc/shadow /etc/group /etc/gshadow
# /etc/passwd 应该可读但不可写
chmod 644 /etc/passwd
# /etc/shadow 应该只能被 root 读取
chmod 600 /etc/shadow
chown root:shadow /etc/shadow
# /etc/sudoers 应该只能被 root 修改
chmod 440 /etc/sudoers
chown root:root /etc/sudoers
# 检查是否存在任何可写的 /etc/cron.d
find /etc/cron.d -type f -perm -002 2>/dev/null
7.3 计划任务目录权限
# cron 目录应该是 root 所有且不可被其他用户写入
ls -la /etc/cron.d/
# 应该是 dr-xr-xr-x root root
# /etc/cron.deny 和 /etc/at.deny
# 应该只有 root 可写
chmod 600 /etc/cron.deny /etc/at.deny
8 通用的提权防御策略
8.1 最小权限原则
所有账号和服务都应该只拥有完成任务所需的最小权限。
# 定期审查用户和组
cat /etc/passwd
cat /etc/group
# 删除不必要的账号
userdel username
# 删除不必要的组
groupdel groupname
# 审查 sudo 权限
visudo
# 移除所有不必要的 sudo 权限
8.2 定期安全审计
# 使用 Lynis 进行安全审计
apt-get install lynis
lynis audit system
# 使用 chkrootkit 检查 rootkit
apt-get install chkrootkit
chkrootkit
# 使用 rkhunter 检查 rootkit
apt-get install rkhunter
rkhunter --check
8.3 文件完整性监控
# 使用 AIDE 进行文件完整性监控
apt-get install aide
aideinit
aide --check
# 配置 AIDE 定期检查
# /etc/cron.daily/aide
#!/bin/bash
/usr/bin/aide --check
8.4 入侵检测
# 安装 OSSEC 或类似的主机入侵检测系统
# 监控文件修改、用户添加、权限变更等
# 使用 auditd 监控关键目录
auditctl -w /etc/passwd -p wa -k passwd_changes
auditctl -w /etc/shadow -p wa -k shadow_changes
auditctl -w /etc/sudoers -p wa -k sudoers_changes
auditctl -w /usr/bin -p x -k execution
# 查询审计日志
ausearch -k passwd_changes | tail -20
9 快速安全检查脚本
#!/bin/bash
# privilege_escalation_check.sh - Linux 提权风险快速检查脚本
echo"=== Linux Privilege Escalation Check ==="
echo""
# 1. 检查 SUID 程序
echo"[1] SUID Programs:"
find / -perm -4000 -type f 2>/dev/null | head -20
# 2. 检查 sudo 权限
echo""
echo"[2] Current User Sudo Permissions:"
sudo -l 2>/dev/null
# 3. 检查 cron 任务
echo""
echo"[3] Cron Tasks:"
ls -la /etc/cron.d/ /etc/cron.daily/ /etc/cron.hourly/ 2>/dev/null | grep -v "^total"
# 4. 检查 /etc/passwd 可写性
echo""
echo"[4] /etc/passwd Writable:"
ls -la /etc/passwd
if [ -w /etc/passwd ]; thenecho"WARNING: /etc/passwd is world-writable!"; fi
# 5. 检查 /etc/shadow 权限
echo""
echo"[5] /etc/shadow Permissions:"
ls -la /etc/shadow
if [ -r /etc/shadow ]; thenecho"NOTE: /etc/shadow is readable by all"; fi
# 6. 检查 Docker socket
echo""
echo"[6] Docker Socket:"
ls -la /var/run/docker.sock 2>/dev/null || echo"Docker socket not found"
# 7. 检查内核版本
echo""
echo"[7] Kernel Version:"
uname -a
# 8. 检查可写的 /etc 文件
echo""
echo"[8] Writable /etc files:"
find /etc -type f -perm -002 2>/dev/null | head -10
# 9. 检查 SSH 密钥权限
echo""
echo"[9] SSH Keys:"
find /home -name "*.pem" -o -name "id_*" 2>/dev/null | xargs ls -la 2>/dev/null
# 10. 检查服务配置
echo""
echo"[10] Running Services:"
systemctl list-units --type=service --state=running | head -20
echo""
echo"=== Check Complete ==="
10 结论
Linux 提权是运维安全的重要组成部分。了解常见的提权途径和防御方法,是每个运维工程师的必修课。
本文介绍的主要提权风险点:SUID 程序提权;sudo 配置错误提权;cron 任务配置错误提权;密码和 SSH 密钥泄露;内核和软件漏洞;容器逃逸;文件权限配置错误。
防御的核心原则:最小权限原则——不给用户或服务分配超过需要的权限;纵深防御——多层安全防护,单点失效不会导致全面沦陷;持续监控——记录和监控关键操作,及时发现异常。
运维工程师应该定期进行安全审计,检查系统配置是否仍然安全,及时修补发现的漏洞和错误配置。
参考资料:
- Linux Privilege Escalation - PayloadsAllTheThings
- GTFOBins - https://gtfobins.github.io/
man chmod、man chown、man visudo- NSA/CISA Linux Hardening Guide