指针定义中的双星
double stars in pointer definition
我在嵌入式代码中遇到了以下定义:
#define REG_ADD 0x20081004
#define pREG ((void * volatile *)REG_ADD)
为什么pREG
定义中有2个*
?这是什么意思?
void**
是指向空指针的指针。
void * volatile *
是指向 volatile-qualified-pointer-to-void 的指针。 (几乎从右到左阅读声明。See this。)
用简单的英语来说,这意味着 pREG
可能是指向某种硬件变址寄存器的指针,它又包含一个地址。为了告诉编译器这个索引寄存器可以随时更新,寄存器本身应该被视为 volatile
.
一种更易读的写法是:
typedef void* volatile reg_add_t;
reg_add_t* pREG = (reg_add_t)0x20081004u;
请注意,将 void*
用于此目的是有问题的。该寄存器将有明确的用途,可能它应该是 uint32_t * volatile
或 uint8_t * volatile
。
我在嵌入式代码中遇到了以下定义:
#define REG_ADD 0x20081004
#define pREG ((void * volatile *)REG_ADD)
为什么pREG
定义中有2个*
?这是什么意思?
void**
是指向空指针的指针。
void * volatile *
是指向 volatile-qualified-pointer-to-void 的指针。 (几乎从右到左阅读声明。See this。)
用简单的英语来说,这意味着 pREG
可能是指向某种硬件变址寄存器的指针,它又包含一个地址。为了告诉编译器这个索引寄存器可以随时更新,寄存器本身应该被视为 volatile
.
一种更易读的写法是:
typedef void* volatile reg_add_t;
reg_add_t* pREG = (reg_add_t)0x20081004u;
请注意,将 void*
用于此目的是有问题的。该寄存器将有明确的用途,可能它应该是 uint32_t * volatile
或 uint8_t * volatile
。