我有这两个结构和4个常数:
#define MAX_BLK 16
#define MAX_STR 32
#define C_TRUE 1
#define C_FALSE 0
typedef struct {
int rsv;
void *addr;
int size;
char tag[MAX_STR];
} BlockType;
typedef struct {
int numBlocks;
BlockType *blocks;
} HeapType;
这是我初始化堆结构的函数:
void mh_init(HeapType *heap) {
heap->numBlocks = 0;
heap->blocks = (BlockType *) malloc(sizeof(BlockType[MAX_BLK]));
}
这是我分配新块的函数(创建一个n字节块,将新块和信息添加到heap-> blocks数组,然后返回新内存块的指针):
void *mh_alloc(HeapType *heap, int n, char *label) {
void *newAddr = (void*) malloc(n);
heap->blocks[heap->numBlocks].addr = newAddr;
heap->blocks[heap->numBlocks].rsv = C_TRUE;
heap->blocks[heap->numBlocks].size = n;
strcpy(heap->blocks[heap->numBlocks].tag, label);
heap->numBlocks += 1;
return newAddr;
}
最后,释放每个块和堆结构:
void mh_cleanup(HeapType *heap) {
for (int i = 0; i < heap->numBlocks; i++) {
printf("block %d\n", i);
free_block(&heap->blocks[i]);
}
free(&heap->numBlocks);
free(heap->blocks);
}
void free_block(BlockType *block) {
free(&(block->rsv));
printf(" freed: rsv,");
if (block->addr != NULL) { free(block->addr); }
printf("adr, ");
free(&(block->size));
printf("size, ");
free(block->tag);
printf("tag\n");
}
所有内容编译都很好,但是当我运行时,我一直收到一个glibc错误:“ *检测到glibc * ./a3:free():指针无效:0x002b6470 ***”
我做了一个小时左右的研究,并认为这个错误意味着我将无效地址传递给free()。基本上它打印出块0,释放rsv,但没有别的。谁能告诉我我的方法出错了?
***注意我的程序还有其他部分,但不认为它们对此问题有重要意义
答案 0 :(得分:2)
这看起来很可疑:
free(&(block->rsv));
您应该只是将指向free
的指针传递给malloc
。在这种情况下,您将指针传递给您分配的结构中的int
。如果您正在操作您分配的数组中的第二个结构,那么这肯定不是您从malloc获得的指针。如果它是第一个元素,如果这与指向数组的指针相同,则可能会释放整个数组(不确定是否保证),在这种情况下,函数的其余部分正在运行free
内存,非常糟糕。