HeapFree Breakpoint on Free()

时间:2016-02-15 06:46:56

标签: c

我有一个非常大的(~1E9)对象数组,我可以在单个线程程序的迭代中使用malloc,realloc和free。

具体地,

//(Individual *ind)

//malloc, old implementation
ind->obj = (double *)malloc(sizeof(double)*acb->in.nobj); 

//new implementation
ind->obj = (double *)a_allocate(acb->in.nobj*sizeof(double));

void *a_allocate (int siz){
   void *buf;

   buf = calloc(1,siz);
   acb->totmemMalloc+=siz;

   if (buf==NULL){
      a_throw2("a_allocate...failed to allocate buf...<%d>",siz);
   }

   return buf;
}

...

//realloc
ind->obj = (double *)a_realloc(ind->obj, acb->in.nobj*sizeof(double));

void *a_realloc (void *bufIn,int siz)
{
   void *buf   = bufIn;

   if (buf==NULL){
      a_throw2("a_realloc called with null bufIn...");
   }

   buf = realloc(buf,siz);

   return buf;
}

...

//deallocate
free(ind->obj);

其他三十个属性的处理方式相似。

但是,每隔几次测试运行,代码就会在仅释放此对象属性(free()语句)时对堆验证失败。在失败时,ind->obj属性不为null并且具有一些有效值。

我正在做什么有明显的问题?

我对C很新,并不完全确定我是否正确执行了内存操作。

谢谢!

编辑:使用_CRTLDBG_REPORT_FLAG

HEAP[DEMO.exe]: Heap block at 010172B0 modified at 010172E4 past requested size of 2c

1 个答案:

答案 0 :(得分:2)

堆验证是延迟指标。可以使用Visual Studio调试堆(调试版本)进行更频繁的检查Microsoft : Debug Heap flags

替代使用应用程序验证程序并启用堆检查,将有助于找到导致此问题的点。

           +-----+----------+-----+  +----+-------------+-----+
           | chk | memory   |chk2 |  | chk| different m | chk2|
           +-----+----------+-----+  +----+-------------+-----+

当系统分配内存时,它会在返回指针之前(或之后)放置有关内存的元信息。当这些内存块被覆盖时,会导致堆失败。

这可能是你正在释放的记忆,也可能是直接存在的记忆。

编辑 - 发表评论

诸如“HEAP [DEMO.exe]:010172B0处的堆块在010172E4处修改过去请求的大小为2c”的消息

意味着01017280处的内存超出了已分配内存的末尾。

这可能是因为malloc ed / realloc ed的数量太小,或者循环中出现错误。

+---+-----------------+----+--------------------------+
|chk|d0|d1|d2|d3|d4|d5|chk2| memory                   |
+---+-----------------+----+--------------------------+

因此,如果您尝试写入上面的d6,那将导致'chk2'被覆盖,这被检测到。在这种情况下,差异很小 - 请求的大小是0x2c,差异= E4 - B0 = 0x34

启用这些调试检查应该会将代码更改为更具崩溃性和可预测性。如果数据中没有随机性,则关闭ASLR(仅用于调试)并且所使用的地址是可预测的,您可以在malloc / realloc中为给定的内存地址设置断点