STM32F10x GPIO_Init() 库函数简化

来源:互联网 发布:创世写作 mac 编辑:程序博客网 时间:2024/06/05 05:38

ST提供的库函数对开发stm32很有帮助,但是方便的同时,库函数就是个黑箱,总让人不够放心

(以前用了个读ms5611的库,居然等传感器读数的时候用的是延时函数!这要是上天了岂不是要掉下来)

这次对最常用的GPIO_Init() 做个简单的探究并简化

原库函数内容就不贴了,在stm32f10x_gpio.c中可以找到,以下是库自带的帮助文件相关内容

其主要作用就是对GPIOx用GPIO_InitStruct这个初始化结构体去初始化,很傻瓜得填进去就可以初始化GPIO了



接下来

初始化结构体主要内容就是,IO脚,IO模式,IO速度,这里我们自己定义一个初始化结构体

typedef struct {    uint16_t pin;    GPIO_Mode mode;    GPIO_Speed speed;} gpio_config_t;

以下是简化的初始化函数:(相关寄存器请自行查阅参考手册,对,就是七百多页那个)

void gpioInit(GPIO_TypeDef *gpio, gpio_config_t *config){    uint32_t pinpos;    for (pinpos = 0; pinpos < 16; pinpos++)     {        //选定设置IO口        if (config->pin & (0x1 << pinpos)) {            // 根据引脚选择CRL还是CRH            __IO uint32_t *cr = &gpio->CRL + (pinpos / 8);            // 留下最后4位            uint32_t currentmode = config->mode & 0x0F;            // 计算配置该IO口的4位在CRx中的位置            uint32_t shift = (pinpos % 8) * 4;            // 读出CRx的值            uint32_t tmp = *cr;            // 若为输出模式,设置速度            if (config->mode & 0x10)                currentmode |= config->speed;            // 清零要设置的4位            tmp &= ~(0xF << shift);            // 设置            tmp |= currentmode << shift;            *cr = tmp;            // 上拉输出和下拉输出的设置            if (config->mode == Mode_IPD) {                gpio->ODR &= ~(1U << pinpos);            } else if (config->mode == Mode_IPU) {                gpio->ODR |= (1U << pinpos);            }        }    }}

参考资料:https://github.com/multiwii/baseflight

0 0