仓库迁移
This commit is contained in:
367
source/interface/if_uart.c
Normal file
367
source/interface/if_uart.c
Normal file
@@ -0,0 +1,367 @@
|
||||
|
||||
#include "rtthread.h"
|
||||
#include "stm32f4xx.h"
|
||||
#include "board.h"
|
||||
#include "if_uart.h"
|
||||
|
||||
|
||||
|
||||
#ifndef RT_THREAD
|
||||
|
||||
#define rt_interrupt_enter()
|
||||
#define rt_interrupt_leave()
|
||||
#define rt_mutex_create(...) 0
|
||||
#define rt_mutex_delete(...)
|
||||
#define rt_mutex_take(...)
|
||||
#define rt_mutex_release(...)
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#define GPIO_Initer() {.GPIO_Mode=GPIO_Mode_AF,\
|
||||
.GPIO_Speed=GPIO_Speed_50MHz,\
|
||||
.GPIO_OType=GPIO_OType_PP,\
|
||||
.GPIO_PuPd=GPIO_PuPd_UP \
|
||||
}
|
||||
|
||||
|
||||
#define UART_Initer() {.USART_WordLength=USART_WordLength_8b,\
|
||||
.USART_StopBits=USART_StopBits_1,\
|
||||
.USART_Parity=USART_Parity_No,\
|
||||
.USART_HardwareFlowControl=USART_HardwareFlowControl_None,\
|
||||
.USART_Mode=USART_Mode_Rx | USART_Mode_Tx,\
|
||||
}
|
||||
|
||||
#define NVIC_Initer() {0}
|
||||
|
||||
|
||||
|
||||
|
||||
typedef struct{
|
||||
char *name;
|
||||
USART_TypeDef *uart;
|
||||
void (*uart_clock_fun)(uint32_t,FunctionalState);
|
||||
uint32_t uart_rcc;
|
||||
int baudrate;
|
||||
|
||||
void (*gpio_tx_clock_fun)(uint32_t,FunctionalState);
|
||||
uint32_t gpio_tx_rcc;
|
||||
GPIO_TypeDef *gpio_tx_base;
|
||||
uint16_t gpio_tx_pin;
|
||||
uint8_t gpio_tx_af;
|
||||
void (*gpio_rx_clock_fun)(uint32_t,FunctionalState);
|
||||
uint32_t gpio_rx_rcc;
|
||||
GPIO_TypeDef *gpio_rx_base;
|
||||
uint16_t gpio_rx_pin;
|
||||
uint8_t gpio_rx_af;
|
||||
|
||||
int irq_channel;
|
||||
}uart_dtb;
|
||||
|
||||
|
||||
|
||||
static const uart_dtb g_uartdtb[]={
|
||||
{
|
||||
.name="uart1",
|
||||
.uart=USART1,
|
||||
.uart_clock_fun=RCC_APB2PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB2Periph_USART1,
|
||||
.baudrate=57600,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOA,
|
||||
.gpio_tx_base=GPIOA,
|
||||
.gpio_tx_pin=9,
|
||||
.gpio_tx_af=GPIO_AF_USART1,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOA,
|
||||
.gpio_rx_base=GPIOA,
|
||||
.gpio_rx_pin=10,
|
||||
.gpio_rx_af=GPIO_AF_USART1,
|
||||
|
||||
.irq_channel=USART1_IRQn,
|
||||
},
|
||||
{
|
||||
.name="uart2",
|
||||
.uart=USART2,
|
||||
.uart_clock_fun=RCC_APB1PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB1Periph_USART2,
|
||||
.baudrate=57600,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOD,
|
||||
.gpio_tx_base=GPIOD,
|
||||
.gpio_tx_pin=5,
|
||||
.gpio_tx_af=GPIO_AF_USART2,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOD,
|
||||
.gpio_rx_base=GPIOD,
|
||||
.gpio_rx_pin=6,
|
||||
.gpio_rx_af=GPIO_AF_USART2,
|
||||
|
||||
.irq_channel=USART2_IRQn,
|
||||
},
|
||||
{
|
||||
.name="uart3",
|
||||
.uart=USART3,
|
||||
.uart_clock_fun=RCC_APB1PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB1Periph_USART3,
|
||||
.baudrate=57600,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOD,
|
||||
.gpio_tx_base=GPIOD,
|
||||
.gpio_tx_pin=8,
|
||||
.gpio_tx_af=GPIO_AF_USART3,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOD,
|
||||
.gpio_rx_base=GPIOD,
|
||||
.gpio_rx_pin=9,
|
||||
.gpio_rx_af=GPIO_AF_USART3,
|
||||
|
||||
.irq_channel=USART3_IRQn,
|
||||
},
|
||||
{
|
||||
.name="uart4",
|
||||
.uart=UART4,
|
||||
.uart_clock_fun=RCC_APB1PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB1Periph_UART4,
|
||||
.baudrate=115200,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOC,
|
||||
.gpio_tx_base=GPIOC,
|
||||
.gpio_tx_pin=10,
|
||||
.gpio_tx_af=GPIO_AF_UART4,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOC,
|
||||
.gpio_rx_base=GPIOC,
|
||||
.gpio_rx_pin=11,
|
||||
.gpio_rx_af=GPIO_AF_UART4,
|
||||
|
||||
.irq_channel=UART4_IRQn,
|
||||
},
|
||||
{
|
||||
.name="uart5",
|
||||
.uart=UART5,
|
||||
.uart_clock_fun=RCC_APB1PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB1Periph_UART5,
|
||||
.baudrate=57600,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOC,
|
||||
.gpio_tx_base=GPIOC,
|
||||
.gpio_tx_pin=12,
|
||||
.gpio_tx_af=GPIO_AF_UART5,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOD,
|
||||
.gpio_rx_base=GPIOD,
|
||||
.gpio_rx_pin=2,
|
||||
.gpio_rx_af=GPIO_AF_UART5,
|
||||
|
||||
.irq_channel=UART5_IRQn,
|
||||
},
|
||||
{
|
||||
.name="uart6",
|
||||
.uart=USART6,
|
||||
.uart_clock_fun=RCC_APB2PeriphClockCmd,
|
||||
.uart_rcc=RCC_APB2Periph_USART6,
|
||||
.baudrate=57600,
|
||||
|
||||
.gpio_tx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_tx_rcc=RCC_AHB1Periph_GPIOC,
|
||||
.gpio_tx_base=GPIOC,
|
||||
.gpio_tx_pin=6,
|
||||
.gpio_tx_af=GPIO_AF_USART6,
|
||||
.gpio_rx_clock_fun=RCC_AHB1PeriphClockCmd,
|
||||
.gpio_rx_rcc=RCC_AHB1Periph_GPIOC,
|
||||
.gpio_rx_base=GPIOC,
|
||||
.gpio_rx_pin=7,
|
||||
.gpio_rx_af=GPIO_AF_USART6,
|
||||
|
||||
.irq_channel=USART6_IRQn,
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
|
||||
typedef struct{
|
||||
const uart_dtb *dtb;
|
||||
void (*irq_fun)(void *t,uint8_t d);
|
||||
void *t;
|
||||
void *mutex;
|
||||
}self_data;
|
||||
|
||||
|
||||
static self_data g_self[LENGTH(g_uartdtb)];
|
||||
|
||||
|
||||
def_find_fun(uart_dtb,g_uartdtb)
|
||||
|
||||
|
||||
|
||||
static int init(uart_def *u)
|
||||
{
|
||||
param_check(u);
|
||||
if(u->private_data) return 0;
|
||||
GPIO_InitTypeDef init=GPIO_Initer();
|
||||
USART_InitTypeDef init2=UART_Initer();
|
||||
NVIC_InitTypeDef init3=NVIC_Initer();
|
||||
int index;
|
||||
const uart_dtb *dtb=find(u->name,&index);
|
||||
self_data *self=&g_self[index];
|
||||
self->dtb=dtb;
|
||||
self->irq_fun=0;
|
||||
self->t=0;
|
||||
self->mutex=rt_mutex_create(u->name,RT_IPC_FLAG_FIFO);
|
||||
{
|
||||
u->private_data=self;
|
||||
dtb->uart_clock_fun(dtb->uart_rcc,ENABLE);
|
||||
init2.USART_BaudRate = dtb->baudrate;
|
||||
USART_Init(dtb->uart, &init2);
|
||||
USART_Cmd(dtb->uart, ENABLE);
|
||||
|
||||
dtb->gpio_tx_clock_fun(dtb->gpio_tx_rcc,ENABLE);
|
||||
GPIO_PinAFConfig(dtb->gpio_tx_base,dtb->gpio_tx_pin,dtb->gpio_tx_af);
|
||||
init.GPIO_Pin=1<<dtb->gpio_tx_pin;
|
||||
GPIO_Init(dtb->gpio_tx_base,&init);
|
||||
|
||||
dtb->gpio_rx_clock_fun(dtb->gpio_rx_rcc,ENABLE);
|
||||
GPIO_PinAFConfig(dtb->gpio_rx_base,dtb->gpio_rx_pin,dtb->gpio_rx_af);
|
||||
init.GPIO_Pin=1<<dtb->gpio_rx_pin;
|
||||
GPIO_Init(dtb->gpio_rx_base,&init);
|
||||
|
||||
init3.NVIC_IRQChannel = dtb->irq_channel;
|
||||
init3.NVIC_IRQChannelPreemptionPriority=3;
|
||||
init3.NVIC_IRQChannelSubPriority =3;
|
||||
init3.NVIC_IRQChannelCmd = ENABLE;
|
||||
NVIC_Init(&init3);
|
||||
USART_ITConfig(dtb->uart, USART_IT_RXNE, ENABLE);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static int deinit(uart_def *u)
|
||||
{
|
||||
param_check(u);
|
||||
if(u->private_data==0) return 0;
|
||||
NVIC_InitTypeDef init3=NVIC_Initer();
|
||||
const uart_dtb *dtb=find(u->name,0);
|
||||
{
|
||||
USART_Cmd(dtb->uart, DISABLE);
|
||||
dtb->uart_clock_fun(dtb->uart_rcc,DISABLE);
|
||||
dtb->gpio_tx_clock_fun(dtb->gpio_tx_rcc,DISABLE);
|
||||
dtb->gpio_rx_clock_fun(dtb->gpio_rx_rcc,DISABLE);
|
||||
init3.NVIC_IRQChannelCmd = DISABLE;
|
||||
NVIC_Init(&init3);
|
||||
USART_ITConfig(dtb->uart, USART_IT_RXNE, DISABLE);
|
||||
rt_mutex_delete(((self_data *)u->private_data)->mutex);
|
||||
u->private_data=0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static int set_irq(uart_def *u,void (*irq)(void *t,uint8_t d),void *t)
|
||||
{
|
||||
param_check(u);
|
||||
param_check(u->private_data);
|
||||
self_data *self=u->private_data;
|
||||
irq_disable();
|
||||
self->irq_fun=irq;
|
||||
self->t=t;
|
||||
irq_enable();
|
||||
return 0;
|
||||
}
|
||||
static int read(uart_def *u,uint8_t *b,int len)
|
||||
{
|
||||
param_check(u);
|
||||
param_check(u->private_data);
|
||||
return 0;
|
||||
}
|
||||
static int write(uart_def *u,const uint8_t *b,int len)
|
||||
{
|
||||
param_check(u);
|
||||
param_check(u->private_data);
|
||||
self_data *self=u->private_data;
|
||||
USART_TypeDef *uart=self->dtb->uart;
|
||||
rt_mutex_take(self->mutex,RT_WAITING_FOREVER);
|
||||
for(int i=0;i<len;i++)
|
||||
{
|
||||
while(!USART_GetFlagStatus(uart,USART_FLAG_TXE));
|
||||
uart->DR=b[i];
|
||||
}
|
||||
rt_mutex_release(self->mutex);
|
||||
return len;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static inline void self_irq(self_data *self)
|
||||
{
|
||||
rt_interrupt_enter();
|
||||
if(USART_GetFlagStatus(self->dtb->uart,USART_FLAG_RXNE))
|
||||
{
|
||||
if(self->irq_fun){
|
||||
self->irq_fun(self->t,self->dtb->uart->DR);
|
||||
}
|
||||
}
|
||||
else if(USART_GetFlagStatus(self->dtb->uart,USART_FLAG_TC))
|
||||
{
|
||||
USART_ClearFlag(self->dtb->uart,USART_FLAG_TC);
|
||||
}
|
||||
rt_interrupt_leave();
|
||||
}
|
||||
|
||||
|
||||
void USART1_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[0];
|
||||
self_irq(self);
|
||||
}
|
||||
void USART2_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[1];
|
||||
self_irq(self);
|
||||
}
|
||||
void USART3_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[2];
|
||||
self_irq(self);
|
||||
}
|
||||
void UART4_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[3];
|
||||
self_irq(self);
|
||||
}
|
||||
void UART5_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[4];
|
||||
self_irq(self);
|
||||
}
|
||||
void USART6_IRQHandler(void)
|
||||
{
|
||||
self_data *self=&g_self[5];
|
||||
self_irq(self);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
uart_init_export(uart1,init,deinit,set_irq,0,read,write,0)
|
||||
uart_init_export(uart2,init,deinit,set_irq,0,read,write,0)
|
||||
uart_init_export(uart3,init,deinit,set_irq,0,read,write,0)
|
||||
uart_init_export(uart4,init,deinit,set_irq,0,read,write,0)
|
||||
uart_init_export(uart5,init,deinit,set_irq,0,read,write,0)
|
||||
uart_init_export(uart6,init,deinit,set_irq,0,read,write,0)
|
||||
|
||||
|
Reference in New Issue
Block a user