ESP8266学习笔记(9)——UART串口使用(NONOS SDK)

一、简介

ESP8266 有两个UART。UART0有TX、RX作为 系统的打印信息输出接口数据收发口,而UART1只有TX,作为 打印信息输出接口(调试用)。

二、UART0接收

2.1 相关函数

/driver/uart.c 中,

2.1.1 uart0_rx_intr_handler

用于UART0中断处理,用户可在该函数内添加对接收到数据包的处理。

LOCAL void
uart0_rx_intr_handler(void *para)
{
    /* uart0 and uart1 intr combine togther, when interrupt occur, see reg 0x3ff20020, bit2, bit0 represents
    * uart1 and uart0 respectively
    */
    uint8 RcvChar;
    uint8 uart_no = UART0;//UartDev.buff_uart_no;
    uint8 fifo_len = 0;
    uint8 buf_idx = 0;
    uint8 temp,cnt;
    //RcvMsgBuff *pRxBuff = (RcvMsgBuff *)para;

    /* 注意: */
    // 不要在中断处理函数中调用带有 "ICACHE_FLASH_ATTR" 宏的函数,否则将引起异常。
    /*ALL THE FUNCTIONS CALLED IN INTERRUPT HANDLER MUST BE DECLARED IN RAM */
    /*IF NOT , POST AN EVENT AND PROCESS IN SYSTEM TASK */

    // 接收帧错误中断
    if(UART_FRM_ERR_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_FRM_ERR_INT_ST))
    {
        WRITE_PERI_REG(UART_INT_CLR(uart_no), UART_FRM_ERR_INT_CLR);    // 清除中断寄存器的 帧错误位
    }
    // 接收满中断 FULL
    else if(UART_RXFIFO_FULL_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_RXFIFO_FULL_INT_ST))
    {
        uart_rx_intr_disable(UART0);                                    // 1. 接收中断禁用,用于不再接受数据,因为现在处于处理数据中
        WRITE_PERI_REG(UART_INT_CLR(UART0), UART_RXFIFO_FULL_INT_CLR);  // 2.清除中断寄存器的 接收 FULL 位
        system_os_post(uart_recvTaskPrio, 0, 0);                        // 3.向任务函数发送消息
    }
    // 接收超时中断 TOUT
    else if(UART_RXFIFO_TOUT_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_RXFIFO_TOUT_INT_ST))
    {
        uart_rx_intr_disable(UART0);                                    // 1. 接收中断禁用,用于不再接受数据,因为现在处于处理数据中
        WRITE_PERI_REG(UART_INT_CLR(UART0), UART_RXFIFO_TOUT_INT_CLR);  // 2.清除中断寄存器的 接收超时中断位
        system_os_post(uart_recvTaskPrio, 0, 0);                        // 3.向任务函数发送消息
    }
    // 发送 FIFO 空中断
    else if(UART_TXFIFO_EMPTY_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_TXFIFO_EMPTY_INT_ST))
    {
        /* to output uart data from uart buffer directly in empty interrupt handler*/
        /*instead of processing in system event, in order not to wait for current task/function to quit */
        /*ATTENTION:*/
        /*IN NON-OS VERSION SDK, DO NOT USE "ICACHE_FLASH_ATTR" FUNCTIONS IN THE WHOLE HANDLER PROCESS*/
        /*ALL THE FUNCTIONS CALLED IN INTERRUPT HANDLER MUST BE DECLARED IN RAM */
        CLEAR_PERI_REG_MASK(UART_INT_ENA(UART0), UART_TXFIFO_EMPTY_INT_ENA);// 清楚中断标志
        //system_os_post(uart_recvTaskPrio, 1, 0);
        WRITE_PERI_REG(UART_INT_CLR(uart_no), UART_TXFIFO_EMPTY_INT_CLR);  // 清除中断寄存器的 发送 FIFO 空中断位
    }
    // 接收溢出中断
    else if(UART_RXFIFO_OVF_INT_ST  == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_RXFIFO_OVF_INT_ST))
    {
        WRITE_PERI_REG(UART_INT_CLR(uart_no), UART_RXFIFO_OVF_INT_CLR); // 清除中断寄存器的 接收溢出中断位
    }
}

2.1.2 uart_recvTask

上述uart0_rx_intr_handler函数中,在满中断和超时中断时,system_os_post发送了一个信号,于是进入uart_recvTask函数。

LOCAL void ICACHE_FLASH_ATTR
uart_recvTask(os_event_t *events)
{
    if(events->sig == 0)
    {
        // 1.从先进先出通道 FIFO 读取接收到的数据长度
        uint8 fifo_len = (READ_PERI_REG(UART_STATUS(UART0))>>UART_RXFIFO_CNT_S)&UART_RXFIFO_CNT;

        uint8 d_tmp = 0;
        uint8 idx = 0;
        // 2.定义一个临时接收的数据区
        uint8 uartRxBuffer[256] = {0};

        // 3. 赋值给临时数组
        for(idx = 0; idx < fifo_len; idx++) 
        {
            d_tmp = READ_PERI_REG(UART_FIFO(UART0)) & 0xFF;   // 根据数据长度一个一个读取数据
            uartRxBuffer[idx] = d_tmp;                        // 赋值
        }
              
        // 4.做你自己的事情,uartRxBuffer[]数组就是接收到的数据
        {
            ...
            ...
        }

        // 清除中断寄存器的 满中断位 或 超时中断位
        WRITE_PERI_REG(UART_INT_CLR(UART0), UART_RXFIFO_FULL_INT_CLR|UART_RXFIFO_TOUT_INT_CLR);  
        // 5.UART0接收中断使能
        uart_rx_intr_enable(UART0);
    }
    else if(events->sig == 1)
    {
    }
}

2.2 使用流程

①串口初始化
uart_init(115200, 115200); // 设置串口0和串口1的波特率
②串口中断处理
uart0_rx_intr_handler(void *para); // UART0 中断处理函数,在此用作中断触发类型的判断
主要修改下面这个函数
uart_recvTask(os_event_t *events) // UART0 中断处理函数,在此用作中断接收数据处理

三、UART0发送

3.1 相关函数

3.2 使用流程

①串口初始化
uart_init(115200, 115200); // 设置串口0和串口1的波特率
②串口发送数据
uart0_tx_buffer(void *buf, uint16 len); // UART0 发送数据函数

四、UART1发送

4.1 相关函数

/driver/uart.c 中,

4.1.1 UART_SetPrintPort

用于设置打印调试信息的串口

void ICACHE_FLASH_ATTR
UART_SetPrintPort(uint8 uart_no)
{
    if(uart_no==1){
        os_install_putc1(uart1_write_char);
    }else{
        /*option 1: do not wait if uart fifo is full,drop current character*/
        os_install_putc1(uart0_write_char_no_wait);
    /*option 2: wait for a while if uart fifo is full*/
    os_install_putc1(uart0_write_char);
    }
}

4.1.2 uart1_sendStr_no_wait

用于串口1输出一串字符

void uart1_sendStr_no_wait(const char *str)
{
    while(*str){
        uart_tx_one_char_no_wait(UART1, *str++);
    }
}

3.2 使用流程

①串口初始化
uart_init(115200, 115200); // 设置串口0和串口1的波特率
②设置调试串口
UART_SetPrintPort(UART1); // 使用串口1打印调试信息
③打印调试信息
os_printf()uart1_sendStr_no_wait()


• 由 Leung 写于 2019 年 2 月 16 日

• 参考:Esp8266 进阶之路25【高级篇】深聊下esp8266的串口 Uart 通讯中断编程
    ESP8266 Non-OS SDK API参考[7qq6]
    ESP8266 技术参考[zj5o]

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 216,402评论 6 499
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,377评论 3 392
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 162,483评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,165评论 1 292
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,176评论 6 388
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,146评论 1 297
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,032评论 3 417
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,896评论 0 274
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,311评论 1 310
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,536评论 2 332
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,696评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,413评论 5 343
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,008评论 3 325
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,659评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,815评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,698评论 2 368
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,592评论 2 353

推荐阅读更多精彩内容