Merge pull request #1595 from brucechousz/master
[Bsp][STM32F10x-HAL]优化GPIO驱动减小Flash占用
This commit is contained in:
commit
06789333f4
|
@ -18,76 +18,142 @@
|
|||
#include <board.h>
|
||||
#include <rtthread.h>
|
||||
#ifdef RT_USING_PIN
|
||||
#define __STM32_PIN(index, gpio, gpio_index) {index, GPIO##gpio##_CLK_ENABLE, GPIO##gpio, GPIO_PIN_##gpio_index}
|
||||
#define __STM32_PIN_DEFAULT {-1, 0, 0, 0}
|
||||
#define __STM32_PIN(index, gpio, gpio_index) (gpio | gpio_index)
|
||||
#define __STM32_PIN_DEFAULT 0
|
||||
|
||||
static void GPIOA_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOA_CLK_ENABLE
|
||||
__HAL_RCC_GPIOA_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
static void GPIOB_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOB_CLK_ENABLE
|
||||
__HAL_RCC_GPIOB_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
#if (STM32F10X_PIN_NUMBERS >36)
|
||||
static void GPIOC_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOC_CLK_ENABLE
|
||||
__HAL_RCC_GPIOC_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
#if (STM32F10X_PIN_NUMBERS >48)
|
||||
#define A (1U << 8)
|
||||
#define B (2U << 8)
|
||||
#define C (3U << 8)
|
||||
#define D (4U << 8)
|
||||
#define E (5U << 8)
|
||||
#define F (6U << 8)
|
||||
#define G (7U << 8)
|
||||
#define H (8U << 8)
|
||||
#define I (9U << 8)
|
||||
#define J (10U << 8)
|
||||
#define K (11U << 8)
|
||||
|
||||
static void GPIOD_CLK_ENABLE(void)
|
||||
static GPIO_TypeDef * get_st_gpio(rt_uint16_t gpio_pin)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOD_CLK_ENABLE
|
||||
__HAL_RCC_GPIOD_CLK_ENABLE();
|
||||
#endif
|
||||
switch(gpio_pin & 0xFF00)
|
||||
{
|
||||
case A:
|
||||
#ifdef GPIOA
|
||||
return GPIOA;
|
||||
#endif
|
||||
case B:
|
||||
#ifdef GPIOB
|
||||
return GPIOB;
|
||||
#endif
|
||||
case C:
|
||||
#ifdef GPIOC
|
||||
return GPIOC;
|
||||
#endif
|
||||
case D:
|
||||
#ifdef GPIOD
|
||||
return GPIOD;
|
||||
#endif
|
||||
case E:
|
||||
#ifdef GPIOE
|
||||
return GPIOE;
|
||||
#endif
|
||||
case F:
|
||||
#ifdef GPIOF
|
||||
return GPIOF;
|
||||
#endif
|
||||
case G:
|
||||
#ifdef GPIOG
|
||||
return GPIOG;
|
||||
#endif
|
||||
case H:
|
||||
#ifdef GPIOH
|
||||
return GPIOH;
|
||||
#endif
|
||||
case I:
|
||||
#ifdef GPIOI
|
||||
return GPIOI;
|
||||
#endif
|
||||
case J:
|
||||
#ifdef GPIOJ
|
||||
return GPIOJ;
|
||||
#endif
|
||||
case K:
|
||||
#ifdef GPIOK
|
||||
return GPIOK;
|
||||
#endif
|
||||
default:
|
||||
return RT_NULL;
|
||||
}
|
||||
}
|
||||
#if (STM32F10X_PIN_NUMBERS >64)
|
||||
static void GPIOE_CLK_ENABLE(void)
|
||||
|
||||
#define get_st_pin(gpio_pin) (0x01 << (gpio_pin&0xFF))
|
||||
|
||||
static void drv_clock_enable(rt_uint16_t gpio_pin)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOE_CLK_ENABLE
|
||||
__HAL_RCC_GPIOE_CLK_ENABLE();
|
||||
#endif
|
||||
switch(gpio_pin & 0xFF00)
|
||||
{
|
||||
case A:
|
||||
#ifdef __HAL_RCC_GPIOA_CLK_ENABLE
|
||||
__HAL_RCC_GPIOA_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case B:
|
||||
#ifdef __HAL_RCC_GPIOB_CLK_ENABLE
|
||||
__HAL_RCC_GPIOB_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case C:
|
||||
#ifdef __HAL_RCC_GPIOC_CLK_ENABLE
|
||||
__HAL_RCC_GPIOC_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case D:
|
||||
#ifdef __HAL_RCC_GPIOD_CLK_ENABLE
|
||||
__HAL_RCC_GPIOD_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case E:
|
||||
#ifdef __HAL_RCC_GPIOE_CLK_ENABLE
|
||||
__HAL_RCC_GPIOE_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case F:
|
||||
#ifdef __HAL_RCC_GPIOF_CLK_ENABLE
|
||||
__HAL_RCC_GPIOF_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case G:
|
||||
#ifdef __HAL_RCC_GPIOG_CLK_ENABLE
|
||||
__HAL_RCC_GPIOG_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case H:
|
||||
#ifdef __HAL_RCC_GPIOH_CLK_ENABLE
|
||||
__HAL_RCC_GPIOH_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case I:
|
||||
#ifdef __HAL_RCC_GPIOI_CLK_ENABLE
|
||||
__HAL_RCC_GPIOI_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case J:
|
||||
#ifdef __HAL_RCC_GPIOJ_CLK_ENABLE
|
||||
__HAL_RCC_GPIOJ_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
case K:
|
||||
#ifdef __HAL_RCC_GPIOK_CLK_ENABLE
|
||||
__HAL_RCC_GPIOK_CLK_ENABLE();
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
#if (STM32F10X_PIN_NUMBERS >100)
|
||||
static void GPIOF_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOF_CLK_ENABLE
|
||||
__HAL_RCC_GPIOF_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
static void GPIOG_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOG_CLK_ENABLE
|
||||
__HAL_RCC_GPIOG_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
static void GPIOH_CLK_ENABLE(void)
|
||||
{
|
||||
#ifdef __HAL_RCC_GPIOH_CLK_ENABLE
|
||||
__HAL_RCC_GPIOH_CLK_ENABLE();
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* STM32 GPIO driver */
|
||||
struct pin_index
|
||||
{
|
||||
int index;
|
||||
void (*rcc)(void);
|
||||
GPIO_TypeDef *gpio;
|
||||
uint32_t pin;
|
||||
};
|
||||
|
||||
static const struct pin_index pins[] =
|
||||
static const rt_uint16_t pins[] =
|
||||
{
|
||||
#if (STM32F10X_PIN_NUMBERS == 36)
|
||||
__STM32_PIN_DEFAULT,
|
||||
|
@ -361,7 +427,6 @@ static const struct pin_index pins[] =
|
|||
__STM32_PIN(7, C, 13),
|
||||
__STM32_PIN(8, C, 14),
|
||||
__STM32_PIN(9, C, 15),
|
||||
|
||||
__STM32_PIN(10, F, 0),
|
||||
__STM32_PIN(11, F, 1),
|
||||
__STM32_PIN(12, F, 2),
|
||||
|
@ -545,74 +610,58 @@ struct rt_pin_irq_hdr pin_irq_hdr_tab[] =
|
|||
};
|
||||
|
||||
#define ITEM_NUM(items) sizeof(items) / sizeof(items[0])
|
||||
const struct pin_index *get_pin(uint8_t pin)
|
||||
static rt_uint16_t get_pin(uint8_t pin)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
rt_uint16_t gpio_pin = __STM32_PIN_DEFAULT;
|
||||
if (pin < ITEM_NUM(pins))
|
||||
{
|
||||
index = &pins[pin];
|
||||
if (index->index == -1)
|
||||
index = RT_NULL;
|
||||
gpio_pin = pins[pin];
|
||||
}
|
||||
else
|
||||
{
|
||||
index = RT_NULL;
|
||||
}
|
||||
return index;
|
||||
return gpio_pin;
|
||||
};
|
||||
|
||||
void stm32_pin_write(rt_device_t dev, rt_base_t pin, rt_base_t value)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
rt_uint16_t gpio_pin;
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return;
|
||||
}
|
||||
HAL_GPIO_WritePin(index->gpio, index->pin, (GPIO_PinState)value);
|
||||
HAL_GPIO_WritePin(get_st_gpio(gpio_pin), get_st_pin(gpio_pin), (GPIO_PinState)value);
|
||||
}
|
||||
|
||||
int stm32_pin_read(rt_device_t dev, rt_base_t pin)
|
||||
{
|
||||
int value;
|
||||
const struct pin_index *index;
|
||||
value = PIN_LOW;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
rt_uint16_t gpio_pin;
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return value;
|
||||
return PIN_LOW;
|
||||
}
|
||||
value = HAL_GPIO_ReadPin(index->gpio, index->pin);
|
||||
return value;
|
||||
return HAL_GPIO_ReadPin(get_st_gpio(gpio_pin), get_st_pin(gpio_pin));
|
||||
}
|
||||
|
||||
void stm32_pin_mode(rt_device_t dev, rt_base_t pin, rt_base_t mode)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
rt_uint16_t gpio_pin;
|
||||
GPIO_InitTypeDef GPIO_InitStruct;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return;
|
||||
}
|
||||
/* GPIO Periph clock enable */
|
||||
index->rcc();
|
||||
drv_clock_enable(gpio_pin);
|
||||
/* Configure GPIO_InitStructure */
|
||||
GPIO_InitStruct.Pin = index->pin;
|
||||
GPIO_InitStruct.Pin = get_st_pin(gpio_pin);
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
|
||||
if (mode == PIN_MODE_OUTPUT)
|
||||
{
|
||||
/* output setting */
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
}
|
||||
else if (mode == PIN_MODE_INPUT)
|
||||
if (mode == PIN_MODE_INPUT)
|
||||
{
|
||||
/* input setting: not pull. */
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_INPUT;
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
}
|
||||
else if (mode == PIN_MODE_INPUT_PULLUP)
|
||||
{
|
||||
|
@ -630,54 +679,41 @@ void stm32_pin_mode(rt_device_t dev, rt_base_t pin, rt_base_t mode)
|
|||
{
|
||||
/* output setting: od. */
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_OD;
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
}
|
||||
HAL_GPIO_Init(index->gpio, &GPIO_InitStruct);
|
||||
HAL_GPIO_Init(get_st_gpio(gpio_pin), &GPIO_InitStruct);
|
||||
}
|
||||
|
||||
rt_inline rt_int32_t bit2bitno(rt_uint32_t bit)
|
||||
rt_inline const struct pin_irq_map *get_pin_irq_map(rt_uint16_t gpio_pin)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < 32; i++)
|
||||
{
|
||||
if ((0x01 << i) == bit)
|
||||
{
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
rt_inline const struct pin_irq_map *get_pin_irq_map(uint32_t pinbit)
|
||||
{
|
||||
rt_int32_t mapindex = bit2bitno(pinbit);
|
||||
rt_int32_t mapindex = gpio_pin & 0x00FF;
|
||||
if (mapindex < 0 || mapindex >= ITEM_NUM(pin_irq_map))
|
||||
{
|
||||
return RT_NULL;
|
||||
}
|
||||
return &pin_irq_map[mapindex];
|
||||
};
|
||||
|
||||
rt_err_t stm32_pin_attach_irq(struct rt_device *device, rt_int32_t pin,
|
||||
rt_uint32_t mode, void (*hdr)(void *args), void *args)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
rt_uint16_t gpio_pin;
|
||||
rt_base_t level;
|
||||
rt_int32_t irqindex = -1;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
}
|
||||
irqindex = bit2bitno(index->pin);
|
||||
irqindex = gpio_pin & 0x00FF;
|
||||
if (irqindex < 0 || irqindex >= ITEM_NUM(pin_irq_map))
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
}
|
||||
level = rt_hw_interrupt_disable();
|
||||
if (pin_irq_hdr_tab[irqindex].pin == pin &&
|
||||
pin_irq_hdr_tab[irqindex].hdr == hdr &&
|
||||
pin_irq_hdr_tab[irqindex].mode == mode &&
|
||||
pin_irq_hdr_tab[irqindex].args == args)
|
||||
pin_irq_hdr_tab[irqindex].hdr == hdr &&
|
||||
pin_irq_hdr_tab[irqindex].mode == mode &&
|
||||
pin_irq_hdr_tab[irqindex].args == args)
|
||||
{
|
||||
rt_hw_interrupt_enable(level);
|
||||
return RT_EOK;
|
||||
|
@ -697,15 +733,15 @@ rt_err_t stm32_pin_attach_irq(struct rt_device *device, rt_int32_t pin,
|
|||
|
||||
rt_err_t stm32_pin_detach_irq(struct rt_device *device, rt_int32_t pin)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
rt_uint16_t gpio_pin;
|
||||
rt_base_t level;
|
||||
rt_int32_t irqindex = -1;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
}
|
||||
irqindex = bit2bitno(index->pin);
|
||||
irqindex = gpio_pin & 0x00FF;
|
||||
if (irqindex < 0 || irqindex >= ITEM_NUM(pin_irq_map))
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
|
@ -727,19 +763,19 @@ rt_err_t stm32_pin_detach_irq(struct rt_device *device, rt_int32_t pin)
|
|||
rt_err_t stm32_pin_irq_enable(struct rt_device *device, rt_base_t pin,
|
||||
rt_uint32_t enabled)
|
||||
{
|
||||
const struct pin_index *index;
|
||||
rt_uint16_t gpio_pin;
|
||||
const struct pin_irq_map *irqmap;
|
||||
rt_base_t level;
|
||||
rt_int32_t irqindex = -1;
|
||||
GPIO_InitTypeDef GPIO_InitStruct;
|
||||
index = get_pin(pin);
|
||||
if (index == RT_NULL)
|
||||
gpio_pin = get_pin(pin);
|
||||
if (get_st_gpio(gpio_pin) == RT_NULL)
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
}
|
||||
if (enabled == PIN_IRQ_ENABLE)
|
||||
{
|
||||
irqindex = bit2bitno(index->pin);
|
||||
irqindex = gpio_pin & 0x00FF;
|
||||
if (irqindex < 0 || irqindex >= ITEM_NUM(pin_irq_map))
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
|
@ -752,33 +788,31 @@ rt_err_t stm32_pin_irq_enable(struct rt_device *device, rt_base_t pin,
|
|||
}
|
||||
irqmap = &pin_irq_map[irqindex];
|
||||
/* GPIO Periph clock enable */
|
||||
index->rcc();
|
||||
drv_clock_enable(gpio_pin);
|
||||
/* Configure GPIO_InitStructure */
|
||||
GPIO_InitStruct.Pin = index->pin;
|
||||
GPIO_InitStruct.Pin = get_st_pin(gpio_pin);
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
|
||||
switch (pin_irq_hdr_tab[irqindex].mode)
|
||||
{
|
||||
case PIN_IRQ_MODE_RISING:
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING;
|
||||
GPIO_InitStruct.Pull = GPIO_PULLDOWN;
|
||||
break;
|
||||
case PIN_IRQ_MODE_FALLING:
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
|
||||
GPIO_InitStruct.Pull = GPIO_PULLUP;
|
||||
break;
|
||||
case PIN_IRQ_MODE_RISING_FALLING:
|
||||
GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING_FALLING;
|
||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||
break;
|
||||
}
|
||||
HAL_GPIO_Init(index->gpio, &GPIO_InitStruct);
|
||||
HAL_GPIO_Init(get_st_gpio(gpio_pin), &GPIO_InitStruct);
|
||||
HAL_NVIC_SetPriority(irqmap->irqno, 5, 0);
|
||||
HAL_NVIC_EnableIRQ(irqmap->irqno);
|
||||
rt_hw_interrupt_enable(level);
|
||||
}
|
||||
else if (enabled == PIN_IRQ_DISABLE)
|
||||
{
|
||||
irqmap = get_pin_irq_map(index->pin);
|
||||
irqmap = get_pin_irq_map(gpio_pin);
|
||||
if (irqmap == RT_NULL)
|
||||
{
|
||||
return RT_ENOSYS;
|
||||
|
@ -810,8 +844,18 @@ int rt_hw_pin_init(void)
|
|||
}
|
||||
INIT_BOARD_EXPORT(rt_hw_pin_init);
|
||||
|
||||
rt_inline void pin_irq_hdr(int irqno)
|
||||
rt_inline void pin_irq_hdr(uint16_t GPIO_Pin)
|
||||
{
|
||||
uint16_t irqno;
|
||||
for (irqno = 0; irqno < 16; irqno++)
|
||||
{
|
||||
if ((0x01 << irqno) == GPIO_Pin)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (irqno == 16)
|
||||
return;
|
||||
if (pin_irq_hdr_tab[irqno].hdr)
|
||||
{
|
||||
pin_irq_hdr_tab[irqno].hdr(pin_irq_hdr_tab[irqno].args);
|
||||
|
@ -820,7 +864,7 @@ rt_inline void pin_irq_hdr(int irqno)
|
|||
|
||||
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
|
||||
{
|
||||
pin_irq_hdr(bit2bitno(GPIO_Pin));
|
||||
pin_irq_hdr(GPIO_Pin);
|
||||
}
|
||||
|
||||
void EXTI0_IRQHandler(void)
|
||||
|
|
|
@ -12,14 +12,7 @@
|
|||
* 2015-01-05 Bernard the first version
|
||||
* 2017-11-35 ZYH update to 3.0.0
|
||||
*/
|
||||
#ifndef GPIO_H__
|
||||
#define GPIO_H__
|
||||
struct stm32_hw_pin_userdata
|
||||
{
|
||||
int pin;
|
||||
uint32_t mode;
|
||||
};
|
||||
#define PIN_USERDATA_END {-1,0}
|
||||
extern struct stm32_hw_pin_userdata stm32_pins[];
|
||||
int rt_hw_pin_init(void);
|
||||
#ifndef __DRV_GPIO_H__
|
||||
#define __DRV_GPIO_H__
|
||||
extern int rt_hw_pin_init(void);
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue