打印
[新唐博主]

m451串口问题

[复制链接]
1508|8
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
powerwang921|  楼主 | 2019-9-17 17:03 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
大家好,现在有个问题向想大家请教下,大概是这样的情况:
由于新项目使用了新唐的M451,由于对款MCU不熟悉,今天碰到一个串口接收的问题,弄了很久没有搞定,可否麻烦大家说下串口接收的用法,就以串口0为例,我不是很明白这个串口中断函数里会有一个UART_INTSTS_RDAINT_Msk和一个UART_INTSTS_RXTOINT_Msk,一个数据接收中断和一个接收超时中断,怎么样区分,为什么两个一起用?还有个问题,我老是一次只能收到16个字节的数据,反复测试了都不行,麻烦大家帮忙详细说明M451串口的使用方法和配置代码,比如,我现在要接收长度大于16字节的数据,该如何配置,总这对个串口实在头大,之前使用STM32的串口简单明了,在此先谢谢大家了!

我的串口0初始配置代码如下,也不是很懂:
void UART0_Init(void)//visual data process
{
         memset(Uart0_rx_buf,0,sizeof(Uart0_rx_buf));
         memset(Uart0_tx_buf,0,sizeof(Uart0_tx_buf));
         Uart0_rx_Count = 0;                        //接收字节个数        
       Uart0_tx_Count = 0;                        //发送字节个数
        Uart0_rx_P = 0;                                //接收指针
        Uart0_tx_P = 0;                                //发送指针
        Uart0_rx_Finish = 0;                //接收完成标志
        Uart0_tx_Finish = 0;                //发送完成标志
        
         SYS->GPD_MFPL = SYS_GPD_MFPL_PD1MFP_UART0_TXD | SYS_GPD_MFPL_PD0MFP_UART0_RXD;
         
     SYS_ResetModule(UART0_RST);
     UART_Open(UART0, 115200);
         
         UART0->FIFO &= ~UART_FIFO_RFITL_Msk;
         UART0->FIFO |= UART_FIFO_RFITL_14BYTES;
     //UART0->FIFO|=UART_FIFO_RFITL_1BYTE;
         
         UART_SetTimeoutCnt(UART0, 40);
         
     UART_EnableInt(UART0, (UART_INTEN_RDAIEN_Msk | UART_INTEN_RXTOIEN_Msk));
//        NVIC_EnableIRQ(UART0_IRQn);
}

这个是中断处理函数,是之前的工程师做的
void UART0_TEST_HANDLE(void)//for visual data process
{
     uint8_t u8InChar = 0xFF;
         uint8_t i;
     
     uint32_t u32IntSts = UART0->INTSTS;
     //接收有效数据
    if(u32IntSts & UART_INTSTS_RDAINT_Msk)
     {      
         while(UART_GET_RX_EMPTY(UART0)==0)
         {
             //read data
             u8InChar = UART_READ(UART0);
             Uart0_rx_buf[Uart0_rx_P]=u8InChar;
                         Uart0_rx_P ++;
     }
     
         //接收超时中断
        if(u32IntSts & UART_INTSTS_RXTOINT_Msk)
     {
         //Uart0_tx_Finish = 0;
         //Uart0_rx_P = 0;
                 /*i=0;
         while(UART_GET_RX_EMPTY(UART0)==0)
         {
             u8InChar = UART_READ(UART0);
             Uart0_rx_buf[Uart0_rx_P]=u8InChar;
                         Uart0_rx_P ++;      
            
                 
                 If (Uart0_rx_P==32)      
                            {
                                 Uart0_rx_Finish = 1;
                 Uart0_rx_Count = Uart0_rx_P;
                 Uart0_rx_P = 0;
                              }

                 

         
     
         //发送完成中断
    if(u32IntSts & UART_INTSTS_THREINT_Msk)
     {
                 if(Uart0_tx_P<Uart0_tx_Count)
                 {
                         i=0;
                         while(UART_GET_TX_FULL(UART0)==0)
                         {
                                 u8InChar=Uart0_tx_buf[Uart0_tx_P];
                                 UART_WRITE(UART0,u8InChar);
                                 Uart0_tx_P ++;
                                 i++;
                                 if(Uart0_tx_P>=Uart0_tx_Count)
                                 {                                        UART_DISABLE_INT(UART0, UART_INTEN_THREIEN_Msk);
                                         Uart0_tx_Finish = 0;
                                         Uart0_tx_P = 0;
                                         break;
                                 }
                                 if(i>=16)break;
                         }
                 }
                 else
                 {
                         UART_DISABLE_INT(UART0, UART_INTEN_THREIEN_Msk);
                         Uart0_tx_Finish = 0;
                         Uart0_tx_P = 0;
                 }
     }
}

使用特权

评论回复
沙发
wahahaheihei| | 2019-9-17 23:05 | 只看该作者
另外楼主可以看看例子和库函数,库函数原型有介绍各个参数,另外配合手册上介绍看看。

使用特权

评论回复
板凳
dongnanxibei| | 2019-9-17 23:55 | 只看该作者
通过接收中断实现持续接收吧

使用特权

评论回复
地板
dongnanxibei| | 2019-9-17 23:55 | 只看该作者
另外那个缓存应该可以设置

使用特权

评论回复
5
dongnanxibei| | 2019-9-17 23:56 | 只看该作者
我没下载451的例子,但是我看051做的挺好的啊
/****************************************************************************
* [url=home.php?mod=space&uid=288409]@file[/url]     main.c
* [url=home.php?mod=space&uid=895143]@version[/url]  V1.00
* $Revision: 10 $
* $Date: 15/05/22 2:52p $
* [url=home.php?mod=space&uid=247401]@brief[/url]    Transmit and receive data with auto flow control.
*           This sample code needs to work with UART_Autoflow_Master.
*
* @note
* Copyright (C) 2011 Nuvoton Technology Corp. All rights reserved.
*
******************************************************************************/
#include <stdio.h>
#include "M051Series.h"


#define PLL_CLOCK           50000000


#define RXBUFSIZE 1024

/*---------------------------------------------------------------------------------------------------------*/
/* Global variables                                                                                        */
/*---------------------------------------------------------------------------------------------------------*/
uint8_t g_u8SendData[12] = {0};
uint8_t g_u8RecData[RXBUFSIZE]  = {0};
volatile int32_t g_i32pointer = 0;

/*---------------------------------------------------------------------------------------------------------*/
/* Define functions prototype                                                                              */
/*---------------------------------------------------------------------------------------------------------*/
extern char GetChar(void);
int32_t main(void);
void AutoFlow_FunctionRxTest(void);


void SYS_Init(void)
{
    /*---------------------------------------------------------------------------------------------------------*/
    /* Init System Clock                                                                                       */
    /*---------------------------------------------------------------------------------------------------------*/

    /* Enable Internal RC 22.1184MHz clock */
    CLK_EnableXtalRC(CLK_PWRCON_OSC22M_EN_Msk);

    /* Waiting for Internal RC clock ready */
    CLK_WaitClockReady(CLK_CLKSTATUS_OSC22M_STB_Msk);

    /* Switch HCLK clock source to Internal RC and HCLK source divide 1 */
    CLK_SetHCLK(CLK_CLKSEL0_HCLK_S_HIRC, CLK_CLKDIV_HCLK(1));

    /* Enable external XTAL 12MHz clock */
    CLK_EnableXtalRC(CLK_PWRCON_XTL12M_EN_Msk);

    /* Waiting for external XTAL clock ready */
    CLK_WaitClockReady(CLK_CLKSTATUS_XTL12M_STB_Msk);

    /* Set core clock as PLL_CLOCK from PLL */
    CLK_SetCoreClock(PLL_CLOCK);

    /* Enable UART module clock */
    CLK_EnableModuleClock(UART0_MODULE);
    CLK_EnableModuleClock(UART1_MODULE);

    /* Select UART module clock source */
    CLK_SetModuleClock(UART0_MODULE, CLK_CLKSEL1_UART_S_HXT, CLK_CLKDIV_UART(1));
    CLK_SetModuleClock(UART1_MODULE, CLK_CLKSEL1_UART_S_HXT, CLK_CLKDIV_UART(1));

    /*---------------------------------------------------------------------------------------------------------*/
    /* Init I/O Multi-function                                                                                 */
    /*---------------------------------------------------------------------------------------------------------*/

    /* Set P3 multi-function pins for UART0 RXD and TXD */
    SYS->P3_MFP &= ~(SYS_MFP_P30_Msk | SYS_MFP_P31_Msk);
    SYS->P3_MFP |= (SYS_MFP_P30_RXD0 | SYS_MFP_P31_TXD0);

    /* Set P1 multi-function pins for UART1 RXD and TXD */
    SYS->P1_MFP &= ~(SYS_MFP_P12_Msk | SYS_MFP_P13_Msk);
    SYS->P1_MFP |= (SYS_MFP_P12_RXD1 | SYS_MFP_P13_TXD1);

    /* Set P0 multi-function pins for UART1 RTS */
    SYS->P0_MFP = SYS->P0_MFP & (~SYS_MFP_P01_Msk) | SYS_MFP_P01_RTS1;

}

void UART0_Init()
{
    /*---------------------------------------------------------------------------------------------------------*/
    /* Init UART                                                                                               */
    /*---------------------------------------------------------------------------------------------------------*/
    /* Reset UART0 */
    SYS_ResetModule(UART0_RST);

    /* Configure UART0 and set UART0 Baudrate */
    UART_Open(UART0, 115200);
}

void UART1_Init()
{
    /*---------------------------------------------------------------------------------------------------------*/
    /* Init UART                                                                                               */
    /*---------------------------------------------------------------------------------------------------------*/
    /* Reset UART1 */
    SYS_ResetModule(UART1_RST);

    /* Configure UART1 and set UART1 Baudrate */
    UART_Open(UART1, 115200);
}

/*---------------------------------------------------------------------------------------------------------*/
/* MAIN function                                                                                           */
/*---------------------------------------------------------------------------------------------------------*/

int main(void)
{

    /* Unlock protected registers */
    SYS_UnlockReg();

    /* Init System, peripheral clock and multi-function I/O */
    SYS_Init();

    /* Lock protected registers */
    SYS_LockReg();

    /* Init UART0 for printf */
    UART0_Init();

    /* Init UART1 for testing */
    UART1_Init();

    /*---------------------------------------------------------------------------------------------------------*/
    /* SAMPLE CODE                                                                                             */
    /*---------------------------------------------------------------------------------------------------------*/

    printf("\n\nCPU [url=home.php?mod=space&uid=72445]@[/url] %dHz\n", SystemCoreClock);

    printf("\n\nUART Sample Program\n");

    /* UART auto flow sample slave function */
    AutoFlow_FunctionRxTest();

    while(1);

}

/*---------------------------------------------------------------------------------------------------------*/
/* ISR to handle UART Channel 1 interrupt event                                                            */
/*---------------------------------------------------------------------------------------------------------*/
void UART1_IRQHandler(void)
{
    volatile uint32_t u32IntSts = UART1->ISR;;

    /* Rx Ready or Time-out INT */
    if(UART_GET_INT_FLAG(UART1, UART_ISR_RDA_INT_Msk) ||  UART_GET_INT_FLAG(UART1, UART_ISR_TOUT_INT_Msk))
    {
        /* Handle received data */
        g_u8RecData[g_i32pointer] = UART_READ(UART1);
        g_i32pointer++;
    }
}
/*---------------------------------------------------------------------------------------------------------*/
/*  AutoFlow Function Test (Slave)                                                                         */
/*---------------------------------------------------------------------------------------------------------*/
void AutoFlow_FunctionRxTest()
{
    uint32_t u32i;

    printf("\n");
    printf("+-----------------------------------------------------------+\n");
    printf("|     Pin Configure                                         |\n");
    printf("+-----------------------------------------------------------+\n");
    printf("|    _______                                    _______     |\n");
    printf("|   |       |                                  |       |    |\n");
    printf("|   |Master |---TXD1(P1.3) <====> RXD1(P1.2)---| Slave |    |\n");
    printf("|   |       |---CTS1(P0.0) <====> RTS1(P0.1)---|       |    |\n");
    printf("|   |_______|                                  |_______|    |\n");
    printf("|                                                           |\n");
    printf("+-----------------------------------------------------------+\n");

    printf("\n");
    printf("+-----------------------------------------------------------+\n");
    printf("|       AutoFlow Function Test (Slave)                      |\n");
    printf("+-----------------------------------------------------------+\n");
    printf("|  Description :                                            |\n");
    printf("|    The sample code needs two boards. One is Master and    |\n");
    printf("|    the other is slave. Master will send 1k bytes data     |\n");
    printf("|    to slave.Slave will check if received data is correct  |\n");
    printf("|    after getting 1k bytes data.                           |\n");
    printf("|    Press any key to start...                              |\n");
    printf("+-----------------------------------------------------------+\n");
    GetChar();

    /* Enable RTS and CTS autoflow control */
    UART_EnableFlowCtrl(UART1);

    /* Set RTS Trigger Level as 8 bytes */
    UART1->FCR &= ~UART_FCR_RTS_TRI_LEV_Msk;
    UART1->FCR |= UART_FCR_RTS_TRI_LEV_8BYTES;

    /* Enable RDA\RLS\RTO Interrupt  */
    UART_ENABLE_INT(UART1, (UART_IER_RDA_IEN_Msk | UART_IER_RLS_IEN_Msk | UART_IER_RTO_IEN_Msk));

    /* Set RX Trigger Level as 8 bytes */
    UART1->FCR &= ~UART_FCR_RFITL_Msk;
    UART1->FCR |= UART_FCR_RFITL_8BYTES;

    /* Set Timeout time 0x3E bit-time and time-out counter enable */
    UART_SetTimeoutCnt(UART1, 0x3E);

    /* Enable UART1 IRQ */
    NVIC_EnableIRQ(UART1_IRQn);

    printf("\n Starting to receive data...\n");

    /* Wait for receive 1k bytes data */
    while(g_i32pointer < RXBUFSIZE);

    /* Compare Data */
    for(u32i = 0; u32i < RXBUFSIZE; u32i++)
    {
        if(g_u8RecData[u32i] != (u32i & 0xFF))
        {
            printf("Compare Data Failed\n");
            while(1);
        }
    }
    printf("\n Receive OK & Check OK\n");

    /* Disable UART1 IRQ */
    NVIC_DisableIRQ(UART1_IRQn);

    /* Disable RDA\RLS\RTO Interrupt */
    UART_DISABLE_INT(UART1, (UART_IER_RDA_IEN_Msk | UART_IER_RLS_IEN_Msk | UART_IER_RTO_IEN_Msk));

}

使用特权

评论回复
6
hawthorn| | 2021-1-22 09:44 | 只看该作者
难道不是发了16个就break了吗

使用特权

评论回复
7
coshi| | 2021-2-6 10:10 | 只看该作者
无论什么型号单片机的串口都差不多啊

使用特权

评论回复
8
zljiu| | 2021-2-6 10:16 | 只看该作者
先试试官方的原版例程吧

使用特权

评论回复
9
wiba| | 2021-2-6 10:18 | 只看该作者
串口配置无非就是那么几项  但是别忘了配置io口和时钟

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

6

主题

24

帖子

0

粉丝