是编译器可循环释放的指针变量? [英] Is the compiler allowed to recycle freed pointer variables?

查看:93
本文介绍了是编译器可循环释放的指针变量?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

据声称,

一个编译器是免费后重新用于其他目的的指针变量的realloc的线被释放的,所以你不能保证它具有相同的值,因为它没有前

a compiler is free to reuse the pointer variable for some other purpose after the realloc being freed, so you have no guarantee that it has the same value as it did before

void *p = malloc(42);
uintptr_t address = (uintptr_t)p;
free(p);

// [...] stuff unrelated to p or address

assert((uintptr_t)p == address);

可能会失败。

C11附件J.2读

指针指向通过调用释放的自由和空间的价值
  realloc函数时(7.22.3)的未定义的]

The value of a pointer that refers to space deallocated by a call to the free or realloc function is used (7.22.3) [is undefined]

但附件当然不是规范。

附件L.3(这是规范的,但可选)告诉我们,如果

Annex L.3 (which is normative, but optional) tells us that if

指针指向通过调用释放到免费或realloc的价值空间
  使用功能(7.22.3)。

The value of a pointer that refers to space deallocated by a call to the free or realloc function is used (7.22.3).

结果被允许是至关重要的未定义的行为。

the result is permitted to be critical undefined behaviour.

这证实了这一说法,但我想看到从标准的正确,而不是附件合适的报价。

This confirms the claim, but I'd like to see an appropriate quote from the standard proper instead of the annex.

推荐答案

当一个物体达到其生命周期结束后,所有指向它成为的不确定的。这适用于块范围变量和malloc内存一样。适用的条款,在C11,6.2.4:2

Upon an object reaching the end of its lifetime, all pointers to it become indeterminate. This applies to block-scope variables and to malloced memory just the same. The applicable clause is, in C11, 6.2.4:2.

的对象的生存期是在此期间,存储是保证预留它执行程序的一部分。一个对象存在,具有恒定的地址,并保留在其整个生命周期的最后存储的值。如果一个对象被称为其生命周期以外,其行为是不确定的。指针的值变为不确定时,它指向的对象(或刚刚过去的)达到其生命周期结束。

The lifetime of an object is the portion of program execution during which storage is guaranteed to be reserved for it. An object exists, has a constant address, and retains its last-stored value throughout its lifetime. If an object is referred to outside of its lifetime, the behavior is undefined. The value of a pointer becomes indeterminate when the object it points to (or just past) reaches the end of its lifetime.

使用不确定的记忆任何东西,包括明显无害比较或算术,是不确定的行为(在C90;后来标准此事非常复杂,但是编译器继续把不确定的内存作为未定义行为的使用)。

Using indeterminate memory for anything, including apparently harmless comparison or arithmetic, is undefined behavior (in C90; later standards complicate the matter terribly but compilers continue to treat usage of indeterminate memory as undefined behavior).

作为一个例子,怎么样 P以下程序打印都是不同的,相同的?与各种编译器执行的结果是这里显示

As an example, how about the following program printing that p and q are both different and the same? The results of execution with various compilers are shown here.

#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <inttypes.h>

int main(int argc, char *argv[]) {
  char *p, *q;
  uintptr_t pv, qv;
  {
    char a = 3;
    p = &a;
    pv = (uintptr_t)p;
  }
  {
    char b = 4;
    q = &b;
    qv = (uintptr_t)q;
  }
  printf("Roses are red,\nViolets are blue,\n");
  if (p == q)
    printf ("This poem is lame,\nIt doesn't even rhyme.\n");
  else {
    printf("%p is different from %p\n", (void*)p, (void*)q);
    printf("%"PRIxPTR" is not the same as %"PRIxPTR"\n", pv, qv);
  }
}

这篇关于是编译器可循环释放的指针变量?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆