1
void setup_crsf_serial_port(uint32_t baud,crsf_read_cb_t read_cb)
{
if(g_crsf_read_callback==0)
{
g_crsf_read_callback = read_cb;
//uart_single_init(bdrate,DEFAULT_SYSTEM_CLOCK,bdrate);//Set single wire mode.
SIM->SCGC4 |= SIM_SCGC4_UART2_MASK;// Enable the clock to the selected UART
/*
Make sure that the transmitter and receiver are disabled while we
* change settings.*/
UART2->C2 &= ~(UART_C2_TE_MASK|UART_C2_RE_MASK);
/* Configure single wire , 8-bit mode, no parity*/
UART2->C1 |= (UART_C1_LOOPS_MASK | UART_C1_RSRC_MASK);
/* Calculate baud settings */
uint16_t sbr = (uint16_t)(DEFAULT_SYSTEM_CLOCK/2/(baud *16));
/* Save off the current value of the UARTx_BDH except for the SBR field */
/* Save off the current value of the UARTx_BDH except for the SBR field */
uint8_t temp = UART2->BDH & (~UART_BDH_SBR(0x1F));
UART2->BDH= temp | UART_BDH_SBR(((sbr & 0x1F00) >> 8));
UART2->BDL = (uint8_t)(sbr & UART_BDL_SBR_MASK);
#if 0
/* Determine if a fractional divider is needed to get closer to the baud rate */
uint16_t brfa = (((DEFAULT_SYSTEM_CLOCK*32000)/(baud * 16)) - (sbr * 32));
/* Save off the current value of the UARTx_C4 register except for the BRFA field */
temp = UART2->C4 & ~(0x1F);
UART2->C4 = temp | brfa;
#endif
/* Enable receiver and transmitter, and enable receive */
UART2->C2 |= (UART_C2_TE_MASK|UART_C2_RE_MASK);
//uart inverted
UART2->C3 |= UART_C3_TXINV_MASK;
UART2->S2 |= UART_S2_RXINV_MASK;
NVIC_EnableIRQ(UART2_IRQn);
}
}
bool uart_clear_error()
{
bool has_error = false;
if(UART2->S1 & UART_S1_OR_MASK )
{
//To clear OR,write a logic 1 to the OR flag.
UART2->S1 |= UART_S1_OR_MASK;
has_error = true ;
}
//clear all
if( UART2->S1 & UART_S1_FE_MASK )
{
UART2->S1 |= UART_S1_FE_MASK;
has_error = true ;
}
if( UART2->S1 & UART_S1_PF_MASK )
{
UART2->S1 |= UART_S1_PF_MASK;
has_error = true ;
}
if( UART2->S1 & UART_S1_NF_MASK )
{
UART2->S1 |=UART_S1_NF_MASK;
has_error = true ;
}
return has_error;
}
uint8_t *g_crsf_send_buf= 0;
uint32_t g_crsf_send_len = 0;
uint32_t g_crsf_send_pos = 0;
void crsf_send_data(uint8_t *buf, uint32_t len)
{
uint8_t dat;
cli();
//while(!(UART2->S1&UART_S1_TDRE_MASK));
//while(!(UART2->S1 & UART_S1_TC_MASK));
// PTE->PDDR |= 1C2 &=~(UART_C2_RIE_MASK);
UART2->C3 &=~(UART_C3_ORIE_MASK);
UART2->C3 |= UART_C3_TXDIR_MASK;
#if USE_IE_UART_TX
g_crsf_send_buf = buf;
g_crsf_send_len = len;
g_crsf_send_pos =0;
UART2->C2 |= UART_C2_TIE_MASK;
#else
for(int i=0;iS1&UART_S1_TDRE_MASK));
UART2->D = buf[i];
}
while(!(UART2->S1 & UART_S1_TC_MASK))
{
}
UART2->C3 &= ~UART_C3_TXDIR_MASK;
/* Configure the module1 TXD pin as an input */
// PTE->PDDR &= ~(1C3 &= ~UART_C3_TXDIR_MASK;
UART2->C2 |=UART_C2_RIE_MASK;
#endif
// UART_EnableInterrupts(UART2, kUART_RxDataRegFullInterruptEnable| kUART_RxOverrunInterruptEnable);
sei();
}
#if 1
void UART2_IRQHandler(void )
{
#if USE_IE_UART_TX
if(!UART2->C3 & UART_C3_TXDIR_MASK)
#endif
{
uint8_t dat;
if(uart_clear_error())
{
dat = UART2->D;
return;
}
}
if(UART2->S1 & UART_S1_RDRF_MASK)
{
uint8_t dat = UART2->D;
if(g_crsf_read_callback)
{
(*g_crsf_read_callback)(dat);
}
}
#if USE_IE_UART_TX
else if(UART2->S1 & UART_S1_TDRE_MASK)
{
if(g_crsf_send_pos < g_crsf_send_len)
{
UART2->D = g_crsf_send_buf[g_crsf_send_pos++];
}
else{
while(!(UART2->S1 & UART_S1_TC_MASK))
{
}
UART2->C2 &= ~UART_C2_TIE_MASK;
UART2->C3 &= ~UART_C3_TXDIR_MASK;
UART2->C2 |=UART_C2_RIE_MASK;
}
}
#endif
}
#endif
void shutdown_crsf_serial_port()
{
if( g_crsf_read_callback != NULL)
{
g_crsf_read_callback = NULL;
UART2->C2 &= ~(UART_C2_RE_MASK|UART_C2_RIE_MASK|UART_C2_TE_MASK|UART_C2_TIE_MASK);
UART2->C3 &=~(UART_C3_ORIE_MASK);
NVIC_DisableIRQ(UART2_IRQn);
SIM->SCGC4 &=~SIM_SCGC4_UART2_MASK;
}
}
int crsf_is_sending()
{
if(UART2->C3 & UART_C3_TXDIR_MASK)
return 1;
return 0;
}
本文档介绍了如何使用CRSF库进行串口通信,包括设置波特率、配置CRSF读写回调、清除错误状态、发送数据以及关闭串口。涉及函数如`setup_crsf_serial_port`、`uart_clear_error`和`crsf_send_data`,展示了串口操作的关键步骤。
2861

被折叠的 条评论
为什么被折叠?



