[英]reachability with std::launder
我试图从CPP 参考中理解以下片段。 有人可以更详细地解释为什么x2[1]
无法从source
访问吗? 例如,我们不能通过&x2[0][0] + 10
到达它吗?
int x2[2][10];
auto p2 = std::launder(reinterpret_cast<int(*)[10]>(&x2[0][0]));
// Undefined behavior: x2[1] would be reachable through the resulting pointer to x2[0]
// but is not reachable from the source
可达性条件基本上询问是否可以通过指针算法访问给定字节 memory 并从给定指针reinterpret_cast
_cast。 在链接的 cppreference 页面上给出了实际上相同的技术定义:
(字节可以通过指向 object Y 的指针访问,如果这些字节在 object Z 的存储中,该 Z 可以与 Y 进行指针互换,或者在 Z 是其元素的紧邻数组中)
x2
是 2 arrays 的10
arrays 的数组int
。 假设我们将两个 arrays 称为a
和b
。
&x2[0][0]
是一个指向a
的第一个元素的int*
。
&x2[0][0] + 10
是一个指向最后一个元素a
的int*
指针。 这个指针值的地址也是b
开始的地址。 但是,无法通过reinterpret_cast
获得指向b
或其元素之一的指针,因为&x2[0][0] + 10
不指向任何 object 可与b
或其元素之一进行指针互换。
就技术定义而言,唯一可与a
的第一个元素相互转换的 object 指针是 object 本身。 因此,从指向 a 的第一个元素的指针的可到达字节只是a
a
字节,它是立即包含此 object 的数组。
因此,通过&x2[0][0]
的可达字节只是数组a
的字节,不包括b
。 例如*(&x2[0][0] + 10) = 123;
有未定义的行为。
但是,如果std::launder
返回指向a
(类型为int(*)[10]
)的指针,则(p2+1)[i]
将是访问b
的所有元素的一种方式。 或者根据技术定义,紧邻object p2
指向的数组将是x2
,因此x2
的所有字节都是可达的。
这意味着之前不可访问的std::launder
字节将变得可访问。 因此,调用具有未定义的行为。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.