2014-11-05 65 views
9

我写和从存储器映射寄存器读取,像这样使用“无效*”的指针:警告:类型算术

//READ 
return *((volatile uint32_t *) (map + offset)); 

//WRITE 
*((volatile uint32_t *) (map + offset)) = value; 

但是编译器给了我这样的警告:

warning: pointer of type ‘void *’ used in arithmetic [-Wpointer-arith] 

如何更改我的代码以删除警告?我正在使用C++和Linux。

+3

转换为'char *' - 假设您需要* byte *偏移量。你做? – 2014-11-05 11:06:50

+0

是的,这是正确的地图是无效*,谢谢。 – user1876942 2014-11-05 11:09:54

+0

您需要将'map'强制转换为大小为1的指针。标准保证大小为1的唯一类型是'char',因此您需要将其转换为'char *'。 – 2014-11-05 11:17:38

回答

6

类型void为不完整类型。它的大小是未知的。所以指针指向void的指针算术没有任何意义。您必须将指针转换为将void类型指向某种其他类型的指针,例如指向char。 还要考虑到您可能不会分配使用限定符volatile声明的对象。

15

由于void*是一个指向未知类型的指针,因此无法对指针进行算术运算,因为编译器不知道指向的指针有多大。

最好的办法是将map转换为字节宽的类型,然后再进行算术运算。您可以使用uint8_t代替:

//READ 
return *((volatile uint32_t *) (((uint8_t*)map) + offset)); 

//WRITE 
*((volatile uint32_t *) (((uint8_t*)map)+ offset)) = value; 
+0

但无效*是一个众所周知的类型,它是一个地址类型,它可以指向任何地址类型......我想解决的办法是静态将其转换为uintptr_t *,然后 – Dmitry 2016-11-09 01:25:04

+1

这将是更习惯转换为char ',因为'sizeof(char)'被定义为1。 – Artyer 2017-07-09 19:59:15