Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/64.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 除了调用free()之外,还有什么方法可以确定指针是否可以传递到free()?_C_Debugging_Heap - Fatal编程技术网

C 除了调用free()之外,还有什么方法可以确定指针是否可以传递到free()?

C 除了调用free()之外,还有什么方法可以确定指针是否可以传递到free()?,c,debugging,heap,C,Debugging,Heap,首先,一点背景知识,这样你就不会认为我在试图做一些疯狂的事情: 我正试图调试由其他人编写的C库中的崩溃。坠机情况如下所示: TheProgram(44365,0x7fff75996310) malloc: *** error for object 0x7fb8d4b9d440: pointer being freed was not allocated 崩溃发生在我无法运行valgrind的系统上,唉。我做的第一件事是围绕库对malloc()、calloc()、realloc()和free()

首先,一点背景知识,这样你就不会认为我在试图做一些疯狂的事情:

我正试图调试由其他人编写的C库中的崩溃。坠机情况如下所示:

TheProgram(44365,0x7fff75996310) malloc: *** error for object 0x7fb8d4b9d440: pointer being freed was not allocated
崩溃发生在我无法运行valgrind的系统上,唉。我做的第一件事是围绕库对malloc()、calloc()、realloc()和free()的所有调用包装调试打印宏,以便在库分配/重新分配/释放内存时看到printf()输出。从该调试输出中可以看出,导致free()崩溃的指针确实是先前在程序中分配的,并且在调用problem free()之前它没有被释放:

因此,可能发生的情况是,在调用malloc()之后和调用free()之前的某个地方,堆必须以某种方式损坏,free()不再认为该指针是有效的

那么,我需要做的是跟踪导致堆损坏的例程。我可以这样做的一种方法是在执行路径的不同位置查询指针的有效性,并缩小其状态从“有效堆指针”更改为“堆管理器不知道该指针是什么”的范围。但我所知道的确定堆管理器认为指针是否可用的唯一方法是调用free(),当程序仍然想使用指针时,我显然不能这样做。是否有某种方法可以调用检查指针是否在free()使用的堆函数中,而不实际释放数据?

一般来说:否


有一些“调试堆”,它们用附加的“围栏”信息围绕分配的块,以帮助检测错误的指针错误。如果你试图释放一些没有通过它们分配的东西,它们会非常可靠地抱怨,因为围栏将丢失。(当然,如果您覆盖了缓冲区的结尾并损坏了围栏,他们也会抱怨。)在代码频繁更改的环境中,我有时会永久启用这些堆,尽管性能成本很高。。。但人们希望,在代码发送给客户之前,它们通常可以关闭。

您无法判断指针是否可以有效地传递到
免费
。运行valgrind以查明内存错误。[Hack]您可能可以查看
malloc
'd指针指向的缓冲区之前存在的。通常情况下,不会。在某些系统上,可能会在分配的第一个字节或类似字节之前存在堆簿记数据,但这将高度依赖于系统。不过,大多数开发环境都有某种(缓慢的)堆错误检测模式可供使用。释放指针后,可能有助于将指针设置为
NULL
。事实上,我怀疑是这样一个系统产生了我看到的错误消息——但我需要知道的不仅仅是堆损坏发生的事实,还有发生的时间/地点。调试堆可以与调试器或核心转储一起使用——或者在代码中记录调用,如果你不能得到更好的结果——在失败点确定程序状态。在那里,做到了这一点,有助于说服IBM,在C编译器产品中包含调试堆是值得的。。。
JJ_CHECK_MALLOC at [fastgr.c : 265] malloc() returned 0x7fb8d4b9d440
[...]
JJ_CHECK_FREE at [dotinit.c : 204] about to call free(0x7fb8d4b9d440)
TheProgram(44365,0x7fff75996310) malloc: *** error for object 0x7fb8d4b9d440: pointer being freed was not allocated