以下示例:
void foo(void)
{
uint8* ptr_data8;
uint32* ptr_data32;
uint32 data32 = 255;
ptr_data32 = &data32;
ptr_data8 = (uint8*)ptr_data32;
}
因此,根据 Endianess,内存可能看起来有所不同:
小尾数:
Address: [ 0| 1| 2| 3]
-------------------
Value: [255| 0| 0| 0]
大尾数:
Address: [ 0| 1| 2| 3]
-------------------
Value: [ 0| 0| 0| 255]
所以问题是,每个架构的指针指向哪个地址?
指针是否指向整个数据元素的最低地址?
[Little Endian]
ptr_data8 --> 0
ptr_data32 --> 0
[Big Endian]
ptr_data8 --> 0
ptr_data32 --> 0
或者它们是否指向数据元素的最低值/字节?
[Little Endian]
ptr_data8 --> 0
ptr_data32 --> 0
[Big Endian]
ptr_data8 --> 0
ptr_data32 --> 3
此外,指针指向平台/编译器/架构的地址是否依赖于平台/编译器/体系结构,并且在某处是否有此行为的定义?
最佳答案
您的猜测无法证明或反驳,因为标准没有要求指针指向某个数字位置。
该标准要求您的 uint32_t*
指针可转换为 void*
,它与 char*
具有相同的表示形式(并且通过扩展, uint8_t*
) 指针。编译器必须能够像这样“往返”指针:
uint32_t *ptr32orig = ... // Assign some valid value
void *tmp1 = (void*)ptr32orig;
char *cptr = (char*)tmp1;
// cptr has the same representation as tmp1
void *tmp2 = (void*)cptr;
// At this point, tmp1 must be equal to tmp2
uint32_t *ptr32back = (uint32_t*)tmp2;
// At this point ptr32back must be equal to ptr32orig
这似乎意味着 cptr
必须指向与 ptr32orig
相同的位置,但这是不对的:编译器可以做任何它想做的“魔术”将 ptr32orig
转换为 tmp1
,然后撤消其对将 tmp2
转换回 uint32_t*
的影响。
关于c - 指针转换是否依赖于平台?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47179443/