gpt4 book ai didi

c - 在 C 中使用 (char *) 0 有什么特殊方法吗?

转载 作者:行者123 更新时间:2023-11-30 17:03:23 25 4
gpt4 key购买 nike

我知道(char *) 0是一个char指针,它指向0处的地址。因此没有内存地址,超出范围。我经常看到人们使用它而不是 NULL,那么为什么他们不直接使用 NULL 呢?或者,我想知道是否有什么特殊的方法。

最佳答案

一个null pointer严格来说没有有效的地址编码:

An integer constant expression with the value 0, or such an expression cast to type void *, is called a null pointer constant.66) If a null pointer constant is converted to a pointer type, the resulting pointer, called a null pointer, is guaranteed to compare unequal to a pointer to any object or function.

因此,当涉及到空指针时,我会尽量避免使用短语“地址0”,因为这是编码,空指针不需要所有位都为零。例如,架构可以使用指针变量中未使用的位将其标记为无效。用于比较,例如将使用 bitops 代替比较。

最常见的编码是“所有位为零”,因此我将主要关注这一点。使用这种编码是因为大多数 CPU 都有特殊(更短/更快)的指令来将 0x0 位值存储到存储单元中,并与 0x0 进行比较/测试。使用特殊的位模式还可以使用单个比较直接比较两个指针。设置专用位的版本需要额外的说明。

位于地址范围边缘的值也可以避免出现间隙。对于“所有位 1”也是如此,但 CPU 支持和地址宽度依赖性较少。

<小时/>

请注意,大多数架构确实有一个有效的物理地址0,因此实际上对于空指针的这种编码存在问题 没有地址转换。幸运的是,这通常是一个特殊地址,正常应用程序代码不使用。使用虚拟内存寻址,很容易使地址0x0无效,因此不予讨论。

在某些系统上,地址0x0用于代码(PC引导代码/BIOS、嵌入式系统)或数据访问(RAM/外围硬件寄存器)。严格来说,如果不调用到空指针的隐式转换,则无法将整数常量 0 转换为指针。因此,如果您的系统不使用 0x0 编码,则仅使用标准 C 语法访问地址 0x0 时会出现问题。 (仅供引用:这是其他语言为空指针常量使用特殊关键字的原因之一,例如 pascal NIL、Python None、C++ nullptr。)

整数到指针的转换无论如何都是由实现定义的,空指针编码也是如此。因此,0 到指针的转换与常见的仅复制整数->指针编码非常一致,无需修改表示形式。

取消引用此类指针时会出现问题。取消引用空指针是未定义行为 (UB)。由于两种编码相同,CPU 无法检测这是否是有效访问或空指针取消引用。更糟糕的是:如果编译器检测到诸如 char c = *((char *)0); 之类的内容,则它可以自由地利用此 UB 并生成任意代码(或根本不生成任何代码)。

对于真正的变量(即非 const 限定)指针,这通常不是什么大问题,因为这需要动态代码分析,并且在 C 中,不会生成用于运行时检查的代码编译器,但对于上面的常量表达式,它可能很可能会导致问题。

关于c - 在 C 中使用 (char *) 0 有什么特殊方法吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36223261/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com