2016-01-13 873 views
1

我正在分析一个外设驱动程序的文件并发现一些寄存器映射代码。我有关于指针的基本知识,但无法理解下面的代码。指向易失性数据的指针(*((volatile volatile uint32_t *)0x40000000))

#define WATCHDOG0_LOAD_R  (*((volatile uint32_t *)0x40000000)) 

我知道它将标识符WATCHDOG0_LOAD_R定义为寄存器的内存地址。但我无法理解右侧的语法。任何人都可以详细解释我为什么这个指针是以这种方式写的吗?

+1

你不明白'0x40000000'或什么'volatile uint32_t *'的含义? –

+4

请选择其中一个'C'和'C++'标记,除非您特意询问这两种语言之间的交互。 – Quentin

+0

您可能还会从阅读[此问题](http://stackoverflow.com/q/4166201/212858)中受益,该代码以类似的代码结束。 – Useless

回答

9

让我们一步一步的时候:

0x40000000 

是你的内存地址。

(uint32_t *)0x40000000 

投射这一个指针,指向存储器地址,uint32_t型的,这意味着32位的无符号。

(volatile uint32_t *)0x40000000 

volatile手段,基本上,“哎编译器,不要做任何优化,我真的想每次都去那个内存地址并获取它,而没有任何预取或任何特定的”。

*((volatile uint32_t *)0x40000000) 

装置:取包含在由该指针标识的地址的值,所以在开始的0x40000000四个字节。

+0

@DombleMaza引用您的评论:哪个“以下语法”? –

+0

非常感谢。但我仍然无法理解将这整体作为指针的目的。 '(volatile uint32_t *)0x40000000'本身不是指针吗? 我可以写一个与'volatile uint32_t * ptr = 0x40000000; #define WATCHDOG0_LOAD_R * ptr'? – DombleMaza

4

判断(*((volatile uint32_t *)0x40000000))

  • 0x40000000是寄存器的地址在微存储器映射
  • 寄存器为32个位宽,这意味着必须uint32_t *
  • volatile加到告诉编译,以避免对优化该变量是因为可能会改变,例如,在中断程序中。
  • last:*取消引用指针:使您能够访问该特定寄存器的内容。
+2

还要注意取消引用。将此定义分配给一个整数将加载地址处的值。 – 2016-01-13 13:52:05

+0

@TruthSerum真的,我编辑过。我希望OP至少明白他/她自己。 – LPs