Mat*_* M. 72 c memcpy null-pointer language-lawyer
我不太熟悉C标准,所以请耐心等待.
我想知道,按标准保证memcpy(0,0,0)是否安全.
我能找到的唯一限制是,如果内存区域重叠,那么行为是未定义的......
但我们可以认为这里的内存区域重叠吗?
tem*_*def 67
我有一个C标准的草案版本(ISO/IEC 9899:1999),它有一些有趣的事情可以说.首先,它在关于提到(§7.21.1/ 2)memcpy是
如果声明为
size_tn 的参数指定了函数数组的长度,则在调用该函数时,n的值可以为零.除非在本子条款中对特定函数的描述中另有明确说明,否则此类调用上的指针参数仍应具有有效值,如7.1.4中所述.在这样的调用中,定位字符的函数不会发生,比较两个字符序列的函数返回零,复制字符的函数复制零个字符.
此处指出的参考指向:
如果函数的参数具有无效值(例如函数域外的值,或程序地址空间外的 指针,或空指针,或指向不可修改存储的指针,则相应参数不具有const限定条件)或具有可变数量参数的函数不期望的类型(提升后),行为未定义.
所以看起来根据C规范,调用
memcpy(0, 0, 0)
Run Code Online (Sandbox Code Playgroud)
导致未定义的行为,因为空指针被视为"无效值".
也就是说,memcpy如果您执行此操作,如果任何实际执行中断,我会感到非常惊讶,因为如果您说要复制零字节,我能想到的大多数直观实现都不会做任何事情.
use*_*586 21
只是为了好玩,gcc-4.9的发行说明表明它的优化器使用了这些规则,例如可以删除条件
int copy (int* dest, int* src, size_t nbytes) {
memmove (dest, src, nbytes);
if (src != NULL)
return *src;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
然后在copy(0,0,0)调用时给出意想不到的结果(参见https://gcc.gnu.org/gcc-4.9/porting_to.html).
我对gcc-4.9的行为有些矛盾; 行为可能符合标准,但能够调用memmove(0,0,0)有时是对这些标准的有用扩展.
| 归档时间: |
|
| 查看次数: |
20796 次 |
| 最近记录: |