Skip to content

Latest commit

 

History

History
110 lines (91 loc) · 3.25 KB

200901071528.txt.md

File metadata and controls

110 lines (91 loc) · 3.25 KB

2.15 GDB断点后处理commands中finish/until/tb带来的问题

http://scz.617.cn/unix/200901071528.txt

Q:

我现在拦截recvmsg(),有几个目的:

  1. 获取UDP报文的源IP、源PORT
  2. 观察接收到的数据

由于recvmsg()被频繁调用,我需要设置条件断点,比如当源IP、源PORT、接收到的 数据满足一定条件时再命中断点。对于recvmsg()来说,这些信息都是函数返回之后 才能获取的,因此我设想了这样一种断点设置方式:


b recvmsg commands silent set $x=(struct msghdr )((unsigned int *)($esp+8)) finish if ($x->msg_name!=0&&$x->msg_namelen==16) set $y=(struct sockaddr_in *)$x->msg_name if ( ntohl( $y->sin_addr.s_addr )==<...>) else c end else c end end

但这个断点不能达到预期效果,commands中finish之后的脚本未被执行,可能是BUG, 也可能是GDB就是这样实现的。将finish换成until ((unsigned int *)$esp),情 况依旧。后来我试图将finish换成tb ((unsigned int *)$esp),并针对tb设置后 处理commands,但GDB不允许这样做:

Can't use the "commands" command among a breakpoint's commands.

用define也无法绕过上述限制。

A: coolq@nsfocus 2009-01-07 14:20

用如下办法变通满足原始需求:


define finish_recvmsg finish if ($x->msg_name!=0&&$x->msg_namelen==16) set $y=(struct sockaddr_in *)$x->msg_name if ( ntohl( $y->sin_addr.s_addr )==<...>) else c end else c end end

b recvmsg commands silent set $x=(struct msghdr )((unsigned int *)($esp+8)) finish_recvmsg end

A: emacsen@SMTH 2009-01-07 12:33:14

emacsen建议用hook试试,用Google搜"gdb hook"找到类似资料:


define hook-echo // 定义echo命令的"前处理" echo [ end

define hookpost-echo // 定义echo命令的"后处理" echo ]\n end

(gdb) echo Hello World [Hello World]

据此测试了hookpost-finish,也能满足原始需求:


define hookpost-finish if ($x->msg_name!=0&&$x->msg_namelen==16) set $y=(struct sockaddr_in *)$x->msg_name if ( ntohl( $y->sin_addr.s_addr )==<...>) else c end else c end end

b recvmsg commands silent set $x=(struct msghdr )((unsigned int *)($esp+8)) finish end