Valgrind:故意造成段错误

时间:2009-10-20 06:35:05

标签: c segmentation-fault valgrind

这是 mad-hack ,但我试图故意在执行的某个特定点引起段错误,所以valgrind会给我一个堆栈跟踪。

如果有更好的方法可以告诉我,但我仍然很想知道如何故意导致段错误,以及为什么我的尝试不起作用。

这是我失败的尝试:

long* ptr = (long *)0xF0000000;
ptr = 10;

我认为valgrind至少应该将其视为无效写入,即使它不是分段违规。 Valgrind对此一无所知。

任何想法为什么?

修改

接受了答案,但我仍然有一些建议可以获得更合理的方法来获得堆栈跟踪......

6 个答案:

答案 0 :(得分:7)

只需致电abort()即可。这不是一个段错误,但它应该产生一个核心转储。

答案 1 :(得分:5)

您是否遗漏了*中的*ptr = 10?你有什么不会编译。

如果确实如此,那当然不会导致seg-fault,因为你只是分配一个数字。解除引用可能。

假设您的操作系统上取消引用null会导致段错误,以下应该可以解决这个问题:

inline void seg_fault(void)
{
    volatile int *p = reinterpret_cast<volatile int*>(0);
    *p = 0x1337D00D;
}

答案 2 :(得分:5)

很抱歉提到明显但为什么不使用带有断点的gdb然后使用backtrace?

(gdb) b somewhere
(gdb) r
(gdb) bt

答案 3 :(得分:3)

如其他答案中所述,如果您想完全异常终止程序,可以致电abort(),如果必须是分段错误,则可以kill(getpid(), SIGSEGV)。这将生成一个核心文件,即使您没有在valgrind下运行,也可以使用gdb来获取堆栈跟踪或调试。

使用valgrind client request你也可以让valgrind使用你自己的自定义消息转储堆栈跟踪,然后继续执行。当程序未在valgrind下运行时,客户端请求不执行任何操作。

#include <valgrind/valgrind.h>
...
VALGRIND_PRINTF_BACKTRACE("Encountered the foobar problem, x=%d, y=%d\n", x, y);

答案 4 :(得分:2)

你是x86吗?如果是这样,那么CPU中实际上存在一个操作码,意味着“调用可能附加的调试器”。这是操作码CC,或更常见的称为int 3。触发它的最简单方法是使用内联汇编:

inline void debugger_halt(void)
{
#ifdef MSVC
   __asm int 3;
#elif defined(GCC)
   asm("int 3");
#else
#pragma error Well, you'll have to figure out how to do inline assembly 
              in your compiler
#endif
}

MSVC还支持__debugbreak(),这是非托管代码中的硬件中断和托管代码中的MSIL“中断”。

答案 5 :(得分:2)

将SIGV(11)发送到强制核心转储的进程不是更好吗?