Debugging gdb如何在共享库函数中设置软件断点?

Debugging gdb如何在共享库函数中设置软件断点?,debugging,gdb,shared-libraries,breakpoints,internals,Debugging,Gdb,Shared Libraries,Breakpoints,Internals,我知道,在一个可执行文件中,可以通过将所需位置的某些汇编指令替换为另一条指令来工作,这会导致中断。所以调试器可以在这个地方停止执行,用原来的指令替换这个指令,并询问用户下一步要做什么,或者调用一些命令等等 但这种可执行文件的代码不被其他程序使用,并且在内存中只有一个副本。软件断点如何与共享库一起工作?例如,如果我在C-library的某个内部函数上设置了一个断点,那么软件断点是如何工作的(据我所知,所有应用程序只有一个断点,所以我们不能只替换其中的一些指令)?是否有任何“软件断点”技术用于此目的

我知道,在一个可执行文件中,可以通过将所需位置的某些汇编指令替换为另一条指令来工作,这会导致中断。所以调试器可以在这个地方停止执行,用原来的指令替换这个指令,并询问用户下一步要做什么,或者调用一些命令等等


但这种可执行文件的代码不被其他程序使用,并且在内存中只有一个副本。软件断点如何与共享库一起工作?例如,如果我在C-library的某个内部函数上设置了一个断点,那么软件断点是如何工作的(据我所知,所有应用程序只有一个断点,所以我们不能只替换其中的一些指令)?是否有任何“软件断点”技术用于此目的?

Linux的答案是Linux内核实现COW(写时复制):如果将共享库的代码写入,内核将首先创建共享页的私有副本,然后在内部将该进程的虚拟内存重新映射到副本,并允许应用程序继续。这对于userland应用程序来说是完全不可见的,并且完全在内核中完成

因此,在第一次将软件断点放入共享库之前,它的代码确实是共享的;但是后来,不是。此后,该过程将使用脏但私有的副本进行操作

这种内核魔法使调试器不会导致其他应用程序突然停止

但是,在VxWorks等操作系统上,这是不可能的。根据个人经验,当我为VxWorks实现GDB远程调试服务器时,我必须禁止我的用户在
semTake()
semGive()
(操作系统信号量功能)内单步执行,由于a)GDB在其源代码级单步实现中使用软件断点,b)VxWorks使用信号量来保护其断点列表


令人不快的结果是一个中断风暴,其中一个断点会导致一个中断,在这个中断中会有另一个中断,一个接一个地出现在一条无法逃脱的链条中,甚至对Ctrl-Z都有抵抗力。唯一的解决办法是关闭机器电源。

这是VWorks 5或更早版本?@osgx它是VWorks 5.4的一个高度定制的变体。