CMSIS 寄存器值

CMSIS register values

我刚刚开始研究用于 ARM 控制器的 CMSIS。使用它似乎很方便,但是我想知道实际的寄存器值在哪里定义。让我们以 GPIO 为例。

有一个结构 GPIOA_AHB_Type 定义了各种成员。然后,对于 GPIOB,定义了一个内存(或寄存器?)地址,比方说 GPIOB_AHB_BASE。之后,一个指针被设置为 GPIOB_AHB_BASE,像这样:

#define GPIOB_AHB        ((GPIOA_AHB_Type*) GPIOB_AHB_BASE)
例如

GPIOB_AHB的成员变量为GPIOB_AHB->DIR,设置为输入或输出。我的问题是,这些成员变量究竟在哪里被初始化?我想寄存器的实际地址是特定于设备的,所以我试图在特定于设备的 header 中找到它们,但我找到的只是 GPIOB_AHB_BASE 定义和成员变量的声明。编译器如何知道当我键入 GPIOB_AHB->DIR 时,我想写入设置该端口 I/O 方向的寄存器?

如果您查看 CMSIS header,您将看到所有结构定义。这是我当前项目的示例:

typedef struct
{
  __IO uint32_t DATA;              /*!< Port A Data Register                         */
  __IO uint32_t CR;                /*!< Port A Output Control Register               */
  __IO uint32_t FR1;               /*!< Port A Function Register 1                   */
  __IO uint32_t FR2;               /*!< Port A Function Register 2                   */
       uint32_t RESERVED0[6];
  __IO uint32_t OD;                /*!< Port A Open Drain Control Register           */
  __IO uint32_t PUP;               /*!< Port A Pull-up Control Register              */
       uint32_t RESERVED1[2];
  __IO uint32_t IE;                /*!< Port A Input Control Register                */
} TSB_PA_TypeDef;

稍后,定义了指向该类型结构的指针:

#define PERI_BASE                  (0x40000000UL)
#define TSB_PA_BASE                (PERI_BASE  + 0x00C0000UL)
#define TSB_PA                     ((     TSB_PA_TypeDef *)    TSB_PA_BASE)

以便您可以像这样使用它:

TSB_PA->CR |= (1U << 2);          // make Port A, bit 2 an output
value = TSB_PA->DATA & (1U << 5); // read Port A, bit 5.