Ant*_*yko 14 linux debugging permissions gdb docker
问题
如果我从主机编译并运行,我能够设置并达到断点,但如果我从docker容器中执行此操作,gdb不会触及已设置的断点.
重现的步骤(所有片段都准备好复制粘贴)
创建一个docker文件:
cat << EOF > Dockerfile
FROM ubuntu
RUN apt-get update
RUN apt-get install -y build-essential gdb
EOF
Run Code Online (Sandbox Code Playgroud)
构建映像并在其中运行交互式会话:
docker build -t gdb_problem_testing . && docker run --rm -it gdb_problem_testing bash
Run Code Online (Sandbox Code Playgroud)
从容器内部创建小main.cpp,编译并运行gdb:
cat <<EOF > main.cpp && g++ -g main.cpp && gdb -ex 'break 5' -ex 'run' ./a.out
#include <iostream>
int main(int argc, const char *argv[])
{
std::cout << "hi\n";
return 0;
}
EOF
Run Code Online (Sandbox Code Playgroud)
观察gdb输出:
GNU gdb (Ubuntu 7.7.1-0ubuntu5~14.04.2) 7.7.1
[Skipped gdb greeting]
Reading symbols from ./a.out...done.
Breakpoint 1 at 0x40078c: file main.cpp, line 5.
1 #include <iostream>
2
3 int main(int argc, const char *argv[])
4 {
5 std::cout << "hi\n";
6 return 0;
7 }
Starting program: /a.out
hi
During startup program exited normally.
(gdb)
Run Code Online (Sandbox Code Playgroud)
从输出可以看出断点未被击中,尽管程序已执行(打印为"hi")并成功退出.我想这里最重要的是该程序确实运行并且启动程序正常退出时的消息是一种异常行为(根据GDB忽略我的断点)
题
什么阻止gdb设置断点以及如何解决这个问题?
到目前为止我尝试了什么
正如这里建议的那样,我试图改变一条线/etc/apparmor.d/docker
(我在主机中做过):替换profile docker-default flags=(attach_disconnected,mediate_deleted) {
为profile docker-default flags=(attach_disconnected,mediate_deleted,complain) {
.然后运行docker容器,compile和gdb.结果是一样的:During startup program exited normally
.
正如在另一个答案中所建议的,从容器内部,我试图做strace -f -o syscall.txt gdb ./a.out
,但我得到以下错误:
strace: test_ptrace_setoptions_followfork: PTRACE_TRACEME doesn't work: Permission denied
strace: test_ptrace_setoptions_followfork: unexpected exit status 1
Run Code Online (Sandbox Code Playgroud)
但我不明白如何解决这个问题.我尝试以root身份启动容器:sudo docker run --rm -it gdb_problem_testing bash
然后尝试了strace - 这给了我同样的错误.我必须承认我不明白docker管理用户权限的方式,即容器内部root的用户权限以及继承权限的用户权限(来自docker守护程序?).由于我能够点击断点,当我在主机中运行gdb时,我怀疑我的问题会归结为用户权限,但我不知道如何处理它.
在主持人中,我试图echo 0 | sudo tee /proc/sys/kernel/yama/ptrace_scope
按照另一个答案的建议去做.
rub*_*cks 24
tldr; 使用
docker run --privileged
Run Code Online (Sandbox Code Playgroud)
更长时间:我在docker中遇到了一些gdb问题 ---它正在尝试(并且失败)禁用地址空间布局随机化 - 但仅限于docker-machine
,而不是在我的本机linux主机上.
当gdb无法禁用ASLR时,我的所有断点都将被忽略.使用--privileged
旗帜修复了我的问题.你的旅费可能会改变.
我没有提升整个容器,而是能够使用该选项
--security-opt seccomp=unconfined
Run Code Online (Sandbox Code Playgroud)
修复地址空间随机化问题。
有些人还建议启用该ptrace
功能
--cap-add=SYS_PTRACE
Run Code Online (Sandbox Code Playgroud)
但这似乎对我没有任何影响。
以下是 Docker compose 的相同设置:
security_opt:
- seccomp:unconfined
cap_add:
- SYS_PTRACE
Run Code Online (Sandbox Code Playgroud)
详细信息取自这篇 Stack Overflow 帖子。
归档时间: |
|
查看次数: |
4008 次 |
最近记录: |