为什么strace在Docker容器中无法工作

技术为什么strace在Docker容器中无法工作本篇内容主要讲解“ 为什么strace在Docker容器中无法工作”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“ 为什么st

本文主要解释“为什么strace不能在Docker容器中工作”。感兴趣的朋友不妨看看。本文介绍的方法简单、快速、实用。让边肖带你了解为什么strace不能在Docker容器中工作。

这里的问题是mdashmdash如果我在笔记本的Docker容器中运行strace,就会出现这种情况:

$ dockerrun-itubuntu :18.04/bin/bash $ #.安装策略.[email protected]:/# stracelsstrace : pt race(PTRACE _ TRACEME,): operationnotpermitted place通过ptrace系统调用工作,所以如果不允许ptrace,那肯定不行!这个问题很容易解决;mdash在我的机器上,是这样解决的:

docker run-cap-add=sys _ pt race-it Ubuntu :18.04/bin/bash但我对如何修复不感兴趣,我想知道为什么会出现这种情况。为什么strace不能工作,为什么-cap-add=sys _ ptrace可以解决这个问题?

假设 1:容器进程缺少 CAP_SYS_PTRACE 能力。

我一直认为原因是Docker容器进程默认不具备CAP_SYS_PTRACE的能力。也是可以通过-cap-add=sys _ ptrace修复的东西,对吧?

但这实际上是不合理的,原因有二。

原因一:在实验中,作为一个普通用户,我可以截取用户运行的任何进程。但是,如果我检查我的当前进程是否具有CAP_SYS_PTRACE功能,它不会:

$ getpcaps $ $ capabilities for ` 11589 ' :=原因2:capabilities的手册页介绍了CAP_SYS_PTRACE如下:

CAP _ SYS _ PTRACE * tracaryaryprocessingptrace(2);因此,CAP_SYS_PTRACE的功能是使您能够像root一样对任何用户拥有的任何进程进行PTRACE。您不需要使用它来跟踪一个只由您的用户拥有的普通进程。

我用第三种方式测试了一下(LCTT翻译:原文在这里可能有误)mdashmdash我用Docker run-CAP-add=SYS _ PTRACE-it Ubuntu :18.04/bin/bash运行了一个Docker容器,并移除了CAP_SYS_PTRACE的能力,但我仍然可以跟踪进程,虽然我不再拥有这个能力。什么事?为什么呢?

假设 2:关于用户命名空间的事情?

我的下一个(不太有根据的)假设是“好吧,也许这个过程在不同的用户命名空间中,但是strace不能工作,并且由于某种原因不起作用?”这个问题其实无关紧要,但是我观察的时候就想到了。

容器进程是否在不同的用户名称空间中?在容器里:

root @ e27f 594 da 870:/# ls/proc/$ $/ns/user-l./proc/1/ns/user-' user 3360[4026531837]'在主机上:

bork @ kiwi : ~ $ ls/proc/$ $/ns/user-l./proc/12177/ns/user-' user 3360[4026531837]'因为用户命名空间ID(4026531837)是相同的,容器中的根用户。因此,它创造的过程绝对没有理由不能偏离!

这个假设是没有意义的,但是我没有意识到Docker容器中的root用户和主机上的root用户是一样的,所以我觉得很有意思。

00-1010.我也知道Do。

cker 使用 seccomp-bpf 来阻止容器进程运行许多系统调用。而 ptrace 在被 Docker 默认的 seccomp  配置文件阻止的系统调用列表中!(实际上,允许的系统调用列表是一个白名单,所以只是ptrace 不在默认的白名单中。但得出的结果是一样的。)

这很容易解释为什么 strace 在 Docker 容器中不能工作 —— 如果 ptrace 系统调用完全被屏蔽了,那么你当然不能调用它,strace  就会失败。

让我们来验证一下这个假设 —— 如果我们禁用了所有的 seccomp 规则,strace 能在 Docker 容器中工作吗?

$ docker run --security-opt seccomp=unconfined -it ubuntu:18.04  /bin/bash $ strace ls execve("/bin/ls", ["ls"], 0x7ffc69a65580 /* 8 vars */) = 0 ... it works fine ...

是的,很好用!很好。谜底解开了,除了…..

为什么 --cap-add=SYS_PTRACE 能解决问题?

我们还没有解释的是:为什么 --cap-add=SYS_PTRACE 可以解决这个问题?

docker run 的手册页是这样解释 --cap-add 参数的。

--cap-add=[]    Add Linux capabilities

这跟 seccomp 规则没有任何关系! 怎么回事?

我们来看看 Docker 源码

当文档没有帮助的时候,唯一要做的就是去看源码。

Go 语言的好处是,因为依赖关系通常是在一个 Go 仓库里,你可以通过 grep 来找出做某件事的代码在哪里。所以我克隆了  github.com/moby/moby,然后对一些东西进行 grep,比如 rg CAP_SYS_PTRACE。

我认为是这样的。在 containerd 的 seccomp 实现中,在  contrib/seccomp/seccomp/seccomp_default.go 中,有一堆代码来确保如果一个进程有一个能力,那么它也会(通过  seccomp 规则)获得访问权限,以使用与该能力相关的系统调用。

case "CAP_SYS_PTRACE":        s.Syscalls = append(s.Syscalls, specs.LinuxSyscall{            Names: []string{                "kcmp",                "process_vm_readv",                "process_vm_writev",                "ptrace",            },            Action: specs.ActAllow,            Args:   []specs.LinuxSeccompArg{},        })

在 moby 中的 profile/seccomp/seccomp.go 和 默认的 seccomp  配置文件中,也有一些其他的代码似乎做了一些非常类似的事情,所以有可能就是这个代码在做这个事情。

所以我想我们有答案了!

Docker 中的 --cap-add 做的事情比它说的要多

结果似乎是,--cap-add 并不像手册页里说的那样,它更像是  --cap-add-and-also-whiteelist-some-extra-system-calls-if-required。这很有意义!  如果你具有一个像 --CAP_SYS_PTRACE 这样的能力,可以让你使用 process_vm_readv 系统调用,但是该系统调用被 seccomp  配置文件阻止了,那对你没有什么帮助!

所以当你给容器 CAP_SYS_PTRACE 能力时,允许使用 process_vm_readv 和 ptrace 系统调用似乎是一个合理的选择。

到此,相信大家对“ 为什么strace在Docker容器中无法工作”有了更深的了解,不妨来实际操作一番吧!这里是网站,更多相关内容可以进入相关频道进行查询,关注我们,继续学习!

内容来源网络,如有侵权,联系删除,本文地址:https://www.230890.com/zhan/65482.html

(0)

相关推荐

  • 怎样看出仓鼠喜欢主人,仓鼠信任主人的表现有哪些

    技术怎样看出仓鼠喜欢主人,仓鼠信任主人的表现有哪些1怎样看出仓鼠喜欢主人、主人开笼子的时候,仓鼠只是抬头看看不会躲藏。 2、打开笼子手伸过去也没有躲闪。
    3、用手抓仓鼠,它没有明显的反抗,甚至很舒适的躺在手里。
    4、在

    生活 2021年10月30日
  • 如何深度剖析Python语言特点

    技术如何深度剖析Python语言特点这期内容当中小编将会给大家带来有关如何深度剖析Python语言特点,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。这里并不涉及python的特殊规则和

    攻略 2021年10月28日
  • vxworks如何获取任务运行状态(vxworksapi文档)

    技术vxworks中如何实现BroadCast这篇文章主要介绍了vxworks中如何实现BroadCast,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。有

    攻略 2021年12月22日
  • CentOS 6.5中如何搭建MySQL集群7.4

    技术CentOS 6.5中如何搭建MySQL集群7.4小编给大家分享一下CentOS 6.5中如何搭建MySQL集群7.4,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!各节点信息如下:管理节点:192.

    攻略 2021年11月15日
  • C++怎么正确使用线程

    技术C++怎么正确使用线程这篇文章主要介绍“C++怎么正确使用线程”,在日常操作中,相信很多人在C++怎么正确使用线程问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”C++怎么正确使用线程”

    攻略 2021年11月25日
  • redis缓存出现异常怎么处理(redis缓存遇到的问题及解决方法)

    技术如何解决Redis缓存异常的问题这篇文章将为大家详细讲解有关如何解决Redis缓存异常的问题,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。缓存雪崩缓存雪崩是指缓存同一时间大面积的失

    攻略 2021年12月17日