SerialPorts_GD32F450/SerialPorts.c

229 lines
7.2 KiB
C
Executable File
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

//
// Created by cfif on 15.11.22.
//
#include "SerialPorts.h"
#include "gd32f4xx.h"
tSerialPorts SERIAL_PORTS;
uint8_t buf_UART0_DMA[2048];
void USART0_IRQHandler() {
// Смотрим idle прерывание
if (usart_flag_get(SERIAL_PORTS.GONEC0.uart, USART_FLAG_IDLE)) {
// Сброс прерывания
usart_data_receive(SERIAL_PORTS.GONEC0.uart);
vSerialPortIrqProcessingDMAloop(&SERIAL_PORTS.GONEC0, SERIAL_PORTS.GONEC0.dma_init_struct.number -
dma_transfer_number_get(DMA1, DMA_CH2));
}
}
void DMA1_Channel2_IRQHandler(void) {
if (dma_flag_get(DMA1,DMA_CH2,DMA_FLAG_FTF)) {
vSerialPortIrqProcessingDMAloop(&SERIAL_PORTS.GONEC0,
SERIAL_PORTS.GONEC0.dma_init_struct.number);
SERIAL_PORTS.GONEC0.offset = 0;
dma_flag_clear(DMA1, DMA_CH2, DMA_FLAG_FTF);
}
}
#define USART0_RDATA_ADDRESS ((uint32_t)&USART_DATA(USART0))
// Настройка порта
static void vSerialPort_InitUSART0(tSerialPortGiga *env) {
env->dma_buf = buf_UART0_DMA;
rcu_periph_clock_enable(RCU_DMA1);
env->dma_channel = DMA_CH2;
dma_deinit(DMA1, DMA_CH2);
env->dma_init_struct.direction = DMA_PERIPH_TO_MEMORY;
env->dma_init_struct.memory0_addr = (uint32_t)buf_UART0_DMA;
env->dma_init_struct.memory_inc = DMA_MEMORY_INCREASE_ENABLE;
env->dma_init_struct.number = sizeof(buf_UART0_DMA);
env->dma_init_struct.periph_addr = USART0_RDATA_ADDRESS;
env->dma_init_struct.periph_inc = DMA_PERIPH_INCREASE_DISABLE;
env->dma_init_struct.periph_memory_width = DMA_PERIPH_WIDTH_8BIT;
env->dma_init_struct.priority = DMA_PRIORITY_ULTRA_HIGH;
// env->dma_init_struct.circular_mode = DMA_CIRCULAR_MODE_ENABLE;
dma_single_data_mode_init(DMA1, DMA_CH2, &env->dma_init_struct);
/* configure DMA mode */
dma_circulation_enable(DMA1, DMA_CH2);
dma_channel_subperipheral_select(DMA1, DMA_CH2, DMA_SUBPERI4);
/* enable DMA1 channel7 transfer complete interrupt */
dma_interrupt_enable(DMA1, DMA_CH2, DMA_CHXCTL_FTFIE);
/* enable DMA1 channel2 */
dma_channel_enable(DMA1, DMA_CH2);
/* enable GPIO clock */
rcu_periph_clock_enable(RCU_GPIOA);
/* enable USART clock */
rcu_periph_clock_enable(RCU_USART0);
/* connect port to USARTx_Tx */
gpio_af_set(GPIOA, GPIO_AF_7, GPIO_PIN_9);
/* connect port to USARTx_Rx */
gpio_af_set(GPIOA, GPIO_AF_7, GPIO_PIN_10);
/* configure USART Tx as alternate function push-pull */
gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_9);
gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_9);
/* configure USART Rx as alternate function push-pull */
gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_10);
gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_10);
/* configure USART */
usart_deinit(USART0);
usart_baudrate_set(USART0, 921600);
// usart_halfduplex_enable(USART1);
usart_receive_config(USART0, USART_RECEIVE_ENABLE);
usart_transmit_config(USART0, USART_TRANSMIT_ENABLE);
usart_dma_receive_config(USART0, USART_RECEIVE_DMA_ENABLE);
usart_enable(USART0);
/* clear the USART1 data register */
usart_data_receive(USART0);
usart_interrupt_enable(USART0, USART_INT_IDLE);
NVIC_EnableIRQ(USART0_IRQn);
NVIC_SetPriority(USART0_IRQn, 0xFF);
NVIC_EnableIRQ(DMA1_Channel2_IRQn);
NVIC_SetPriority(DMA1_Channel2_IRQn, 0xFF);
vSerialPortInit(env, USART0, 3200);
}
uint8_t buf_UART1_DMA[2048];
void USART1_IRQHandler() {
// Смотрим idle прерывание
if (usart_flag_get(SERIAL_PORTS.GONEC1.uart, USART_FLAG_IDLE)) {
// Сброс прерывания
usart_data_receive(SERIAL_PORTS.GONEC1.uart);
vSerialPortIrqProcessingDMAloop(&SERIAL_PORTS.GONEC1, SERIAL_PORTS.GONEC1.dma_init_struct.number -
dma_transfer_number_get(DMA0, DMA_CH5));
}
}
void DMA0_Channel5_IRQHandler(void) {
if (dma_flag_get(DMA0,DMA_CH5,DMA_FLAG_FTF)) {
vSerialPortIrqProcessingDMAloop(&SERIAL_PORTS.GONEC1,
SERIAL_PORTS.GONEC1.dma_init_struct.number);
SERIAL_PORTS.GONEC1.offset = 0;
dma_flag_clear(DMA0, DMA_CH5, DMA_FLAG_FTF);
}
}
#define USART1_RDATA_ADDRESS ((uint32_t)&USART_DATA(USART1))
// Настройка порта
static void vSerialPort_InitUSART1(tSerialPortGiga *env) {
env->dma_buf = buf_UART1_DMA;
rcu_periph_clock_enable(RCU_DMA0);
env->dma_channel = DMA_CH5;
dma_deinit(DMA0, DMA_CH5);
env->dma_init_struct.direction = DMA_PERIPH_TO_MEMORY;
env->dma_init_struct.memory0_addr = (uint32_t)buf_UART1_DMA;
env->dma_init_struct.memory_inc = DMA_MEMORY_INCREASE_ENABLE;
env->dma_init_struct.number = sizeof(buf_UART1_DMA);
env->dma_init_struct.periph_addr = USART1_RDATA_ADDRESS;
env->dma_init_struct.periph_inc = DMA_PERIPH_INCREASE_DISABLE;
env->dma_init_struct.periph_memory_width = DMA_PERIPH_WIDTH_8BIT;
env->dma_init_struct.priority = DMA_PRIORITY_ULTRA_HIGH;
// env->dma_init_struct.circular_mode = DMA_CIRCULAR_MODE_ENABLE;
dma_single_data_mode_init(DMA0, DMA_CH5, &env->dma_init_struct);
/* configure DMA mode */
dma_circulation_enable(DMA0, DMA_CH5);
dma_channel_subperipheral_select(DMA0, DMA_CH5, DMA_SUBPERI4);
/* enable DMA1 channel7 transfer complete interrupt */
dma_interrupt_enable(DMA0, DMA_CH5, DMA_CHXCTL_FTFIE);
/* enable DMA1 channel2 */
dma_channel_enable(DMA0, DMA_CH5);
/* enable GPIO clock */
rcu_periph_clock_enable(RCU_GPIOD);
/* enable USART clock */
rcu_periph_clock_enable(RCU_USART1);
/* connect port to USARTx_Tx */
gpio_af_set(GPIOD, GPIO_AF_7, GPIO_PIN_5);
/* connect port to USARTx_Rx */
gpio_af_set(GPIOD, GPIO_AF_7, GPIO_PIN_6);
/* configure USART Tx as alternate function push-pull */
gpio_mode_set(GPIOD, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_5);
gpio_output_options_set(GPIOD, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_5);
/* configure USART Rx as alternate function push-pull */
gpio_mode_set(GPIOD, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_6);
gpio_output_options_set(GPIOD, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_6);
/* configure USART */
usart_deinit(USART1);
usart_baudrate_set(USART1, 921600);
// usart_halfduplex_enable(USART1);
usart_receive_config(USART1, USART_RECEIVE_ENABLE);
usart_transmit_config(USART1, USART_TRANSMIT_ENABLE);
usart_dma_receive_config(USART1, USART_RECEIVE_DMA_ENABLE);
usart_enable(USART1);
/* clear the USART1 data register */
usart_data_receive(USART1);
usart_interrupt_enable(USART1, USART_INT_IDLE);
NVIC_EnableIRQ(USART1_IRQn);
NVIC_SetPriority(USART1_IRQn, 0xFF);
NVIC_EnableIRQ(DMA0_Channel5_IRQn);
NVIC_SetPriority(DMA0_Channel5_IRQn, 0xFF);
vSerialPortInit(env, USART1, 3200);
}
void SerialPorts_Init() {
tSerialPorts *env = &SERIAL_PORTS;
vSerialPort_InitUSART0(&env->GONEC0);
SERIAL_PORTS.GONEC0IO = vSerialPortGetIo(&SERIAL_PORTS.GONEC0);
vSerialPort_InitUSART1(&env->GONEC1);
SERIAL_PORTS.GONEC1IO = vSerialPortGetIo(&SERIAL_PORTS.GONEC1);
}