程序打开特定文件时 gdb 中断 [英] gdb break when program opens specific file

查看:22
本文介绍了程序打开特定文件时 gdb 中断的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

背景故事:在 strace 下运行程序时,我注意到 '/dev/urandom' 正在被 open'ed.我想知道这个调用来自哪里(它不是程序本身的一部分,它是系统的一部分).

Back story: While running a program under strace I notice that '/dev/urandom' is being open'ed. I would like to know where this call is coming from (it is not part of the program itself, it is part of the system).

所以,使用 gdb,我试图在发出 open 调用时中断(使用 catch syscall open)程序执行,因此我可以看到回溯.问题是 open 被调用了 alot,大概有几百次,所以我无法缩小打开/dev/urandom 的具体调用范围.我应该如何缩小特定呼叫的范围?有没有办法按参数过滤,如果是这样,我该如何为系统调用进行过滤?

So, using gdb, I am trying to break (using catch syscall open) program execution when the open call is issued, so I can see a backtrace. The problem is that open is being called alot, like several hundred times so I can't narrow down the specific call that is opening /dev/urandom. How should I go about narrowing down the specific call? Is there a way to filter by arguments, and if so how do I do it for a syscall?

任何建议都会有所帮助——也许我做错了.

Any advice would be helpful -- maybe I am going about this all wrong.

推荐答案

GDB 是一个非常强大的工具,但有一点学习曲线.

GDB is a pretty powerful tool, but has a bit of a learning curve.

基本上,你想设置一个条件断点.

Basically, you want to set up a conditional breakpoint.

首先使用 -i 标志来 strace 或 objdump -d 来查找打开函数的地址,或者更实际地在到达那里的链中找到某个地址,例如在 plt 中.

First use the -i flag to strace or objdump -d to find the address of the open function or more realistically something in the chain of getting there, such as in the plt.

在该地址设置一个断点(如果你有调试符号,你可以使用它们,省略 *,但我假设你没有 - 尽管如果没有别的,你很可能将它们用于库函数.

set a breakpoint at that address (if you have debug symbols, you can use those instead, omitting the *, but I'm assuming you don't - though you may well have them for library functions if nothing else.

break * 0x080482c8 

接下来你需要让它有条件

Next you need to make it conditional

(理想情况下,您可以将字符串参数与所需的字符串进行比较.我在尝试的最初几分钟内没有让它工作)

(Ideally you could compare a string argument to a desired string. I wasn't getting this to work within the first few minutes of trying)

希望我们可以假设字符串是程序中某处的常量或它加载的库之一.您可以查看/proc/pid/maps 以了解加载的内容和位置,然后使用 grep 验证字符串实际上是否在文件中,使用 objdump -s 找到它的地址,并使用 gdb 验证您已经实际上是通过将映射中地址的高部分与文件中的低部分结合起来在内存中找到它的.(在可执行文件上使用 ldd 可能比查看/proc/pid/maps 更容易)

Let's hope we can assume the string is a constant somewhere in the program or one of the libraries it loads. You could look in /proc/pid/maps to get an idea of what is loaded and where, then use grep to verify the string is actually in a file, objdump -s to find it's address, and gdb to verify that you've actually found it in memory by combining the high part of the address from maps with the low part from the file. ( it's probably easier to use ldd on the executable than look in /proc/pid/maps)

接下来,您需要了解您正在开发的平台的 abi,​​特别是如何传递参数.我最近一直在研究 arm,这非常好,因为前几个参数只进入寄存器 r0、r1、r2 等.x86 不太方便 - 似乎它们进入堆栈,即*($esp+4)、*($esp+8)、*($esp+12).

Next you will need to know something about the abi of the platform you are working on, specifically how arguments are passed. I've been working on arm's lately, and that's very nice as the first few arguments just go in registers r0, r1, r2... etc. x86 is a bit less convenient - it seems they go on the stack, ie, *($esp+4), *($esp+8), *($esp+12).

假设我们在 x86 上,我们想检查 esp+4 中的第一个参数是否等于我们为试图捕捉它传递的常量找到的地址.只是,esp+4 是一个 指向 char 指针的指针.所以我们需要取消引用它以进行比较.

So let's assume we are on an x86, and we want to check that the first argument in esp+4 equals the address we found for the constant we are trying to catch it passing. Only, esp+4 is a pointer to a char pointer. So we need to dereference it for comparison.

cond 1 *(char **)($esp+4)==0x8048514

然后你可以输入 run 并希望最好

Then you can type run and hope for the best

如果您捕捉到断点条件,并使用 info 寄存器环顾四周,并且 x 命令检查内存似乎是正确的,那么您可以使用 return 命令过滤备份调用堆栈,直到找到您识别的内容.

If you catch your breakpoint condition, and looking around with info registers and the x command to examine memory seems right, then you can use the return command to percolate back up the call stack until you find something you recognize.

这篇关于程序打开特定文件时 gdb 中断的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆