什么malloc(0)回报?
malloc(0)
答案会一样realloc(malloc(0),0)吗?
realloc(malloc(0),0)
#include<stdio.h> #include<malloc.h> int main() { printf("%p\n", malloc(0)); printf("%p\n", realloc(malloc(0), 0)); return 0; }
Linux GCC的输出:
manav@manav-workstation:~$ gcc -Wall mal.c manav@manav-workstation:~$ ./a.out 0x9363008 (nil) manav@manav-workstation:~$
输出每次都会保持变化malloc(0)。这是标准答案吗?为什么除了学术研究之外,还有谁会对获得这样的指示感兴趣?
编辑:
如果malloc(0)返回伪指针,则以下内容如何工作:
int main() { void *ptr = malloc(0); printf("%p\n", realloc(ptr, 1024)); return 0; }
以下代码为每次迭代输出“可能”。为什么不失败?
#include<stdio.h> #include<malloc.h> int main() { int i; void *ptr; printf("Testing using BRUTE FORCE\n"); for (i=0; i<65000; i++) { ptr = malloc(0); if (ptr == realloc(ptr, 1024)) printf("Iteration %d: possible\n", i); else { printf("Failed for iteration %d\n", i); break; } } return 0; }
其他人已经回答了如何malloc(0)工作。我将回答您提出的尚未回答的问题之一(我认为)。问题是关于realloc(malloc(0), 0):
realloc(malloc(0), 0)
什么malloc(0)回报?答案会一样realloc(malloc(0),0)吗?
该标准规定realloc(ptr, size):
realloc(ptr, size)
ptr
NULL
malloc(size)
size
free(ptr)
因此,有两种情况:
realloc()
realloc(NULL, 0)
free(malloc(0))
请注意,这里有一个有趣的情况:在第二种情况下,如果成功malloc(0)返回非NULL成功,则它仍可能返回NULL以指示失败。这将导致类似于这样的调用:realloc(NULL, 0),它等效于malloc(0),可能会或可能不会返回NULL。
我不确定C99中的遗漏是不是疏忽大意,或者这意味着C99中realloc(ptr, 0)的非NULL ptr省略不等同于free(ptr)。我只是试过了gcc -std=c99,上面的内容等同于free(ptr)。
realloc(ptr, 0)
gcc -std=c99
编辑 :我想我理解您的困惑是什么:
让我们看一下示例代码中的一个片段:
ptr = malloc(0); if (ptr == realloc(ptr, 1024))
上面的内容与相同malloc(0) == realloc(malloc(0), 1024)。在第二个中,malloc()调用进行了两次,而在第一个中,您将先前分配的指针传递给realloc()。
malloc(0) == realloc(malloc(0), 1024)
malloc()
让我们首先分析第一个代码。假设成功malloc(0)不返回NULL,ptr则具有有效值。当您这样做时realloc(ptr, 1024),realloc()基本上会为您提供一个大小为1024的新缓冲区,并且ptr变为无效。符合条件的实现可能返回与已经存在的地址相同的地址ptr。因此,您的if条件可能会返回true。(但是请注意,查看ptrafter 的值realloc(ptr, 1024)可能是未定义的行为。)
realloc(ptr, 1024)
if
现在您问的问题是:malloc(0) == realloc(malloc(0), 1024)。在这种情况下,我们假设malloc(0)LHS和RHS上的都返回non- NULL。然后,保证它们是不同的。此外,从返回值malloc()的LHS一直没有free()d还,所以任何其他malloc(),calloc()或realloc()可能不会返回值。这意味着如果您将条件写为:
free()
calloc()
if (malloc(0) == realloc(malloc(0), 1024) puts("possible");
您将不会possible在输出中看到(除非malloc()和realloc()失败并返回NULL)。
possible
#include <stdio.h> #include <stdlib.h> int main(void) { void *p1; void *p2; p1 = malloc(0); p2 = realloc(p1, 1024); if (p1 == p2) puts("possible, OK"); /* Ignore the memory leaks */ if (malloc(0) == realloc(malloc(0), 1024)) puts("shouldn't happen, something is wrong"); return 0; }
在OS X上,我的代码在运行时没有输出任何内容。在Linux上,它将打印possible, OK。
possible, OK