我有一个程序,它有一个释放结构内存的函数。它通常工作正常,但有时它只是冻结。
这是我试图释放内存的结构:
struct Image {
unsigned int height;
unsigned int width;
unsigned int maxvalue;
unsigned int *imgdata[];
};
这是释放内存的函数(printfs仅用于检查冻结的位置)
void Image_Delete (Image *img)
{
printf("1");
free(img->imgdata);
printf("1");
free(img);
printf("1");
}
有时候这种方法很好,但程序通常会冻结free(img);
。我的Image_Delete
函数中是否有错误?
以下是img和img-> imgdata
的malloc行Image *img= (Image*)malloc(sizeof(Image*));
img->imgdata[height*width]= (unsigned int*)malloc(height*width*sizeof(unsigned int*));
答案 0 :(得分:2)
你的第一个malloc没有分配足够的空间:
Image *img= (Image*)malloc(sizeof(Image*));
为“指向图像的指针”分配足够的空间,但是您将要将其用作“图像”,即3个整数和一个指针。因此,当您开始修改新分配的“图像”时,您最终会覆盖任意内存。此外,您的free(img->imgdata)
调用使用的指针未包含在img
的已分配空间中,因此可能已被程序的其他部分修改;对free
未返回的值调用malloc
可能会导致malloc内部状态的任意损坏,所以一切皆有可能。
这是一个提示。最好的风格是总是这样编写malloc:
Image *img = malloc(sizeof *img);
使用*variable
而不是重复类型更不容易出错,尽管你仍然最终重复变量名,所以它并不完美。并且没有必要转换malloc返回的void *。
另外,要回答您在评论中提出的问题:在free
上调用NULL
始终是安全的,否则您只能在{{1}返回的指针上调用它}。因此,如果您不打算立即填写malloc
,则应将其清除为0.事实上,使用img->imgdata
代替calloc
会更好;对于像malloc
这样的小对象,开销可以忽略不计。