乐鑫技术交流
直播中

王飞云

8年用户 1579经验值
私信 关注
[问答]

如何获取FIFO中接收的字节数?

我正在尝试在 UART0 上接收一个字符串,并在最基本的步骤中获取 RX FIFO 缓冲区中可用的字节数。
我试着使用神奇的公式
fifo_len = (READ_PERI_REG(UART_STATUS(UART0)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;

在回调函数中,我从我的 PC 将 char 发送到 ESP 的 RX 引脚上。

但是fifo_len总是低于我实际发送的实际字符数,并且几乎总是 0,除非我以非常短的间隔调用我的回调函数,比如 10 毫秒。在这种情况下,计数开始是正确的,直到来自 SDK 的 11500 波特的某个神秘的 printf(以“n”结尾)刷新了 UART 缓冲区并重置了计数(因为似乎 printfed 或在 UART 上发送的任何“n”都会刷新缓冲区...... -_- UART 仍然让我感到困惑:https://bbs.espressif.com/viewtopic.php?f=7&t=9581).

您知道如何获取FIFO中接收的字节数吗?

.....
我正在使用使用 esp-open-sdk 构建的 NONOS-SDK 2.2.0。
The mysterious printf in question is like "tail 4rr chksum 0xr1c, rn csum 0x1c..."
我的测试代码是:

#include "ets_sys.h"
#include "osapi.h"
#include "os_type.h"   
#include "user_interface.h"                    // Provide init_done_cb()
#include "espconn.h"                              // Provides the UDP/TCP functions
#include "../esp-open-sdk/sdk/driver_lib/include/driver/uart.h"



静态os_timer_t readUartTimer_st;

/**
*   Callback called on each tick of the timer, for the moment just to print the number of bytes available...
*/
void ReadUartTimerCb(void)
{
    uint8 fifo_len;
    fifo_len = (READ_PERI_REG(UART_STATUS(UART0)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;   
    os_printf("UART0: len = %d n", fifo_len);  
}



/**
*   Callback called when the ESP is fully initialized.
*/
void PostInitCb(void)
{
    // Hello
    gpio_init();
    PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO0_U, FUNC_GPIO0);
    GPIO_OUTPUT_SET(GPIO_ID_PIN(0u), 0);
   
    // Setting up UART0
    uart_init(BIT_RATE_9600, BIT_RATE_9600);

    os_timer_disarm(&readUartTimer_st);
    os_timer_setfn(&readUartTimer_st, (os_timer_func_t *) ReadUartTimerCb, NULL);
    os_timer_arm(&readUartTimer_st, 100, true);
}


/**
*   Main entry point of our programm
*/
无效 user_init()
{
    system_init_done_cb(PostInitCb);
}



            

回帖(1)

李桂兰

2024-7-10 17:42:05
要获取FIFO中接收的字节数,您可以使用以下步骤:

1. 首先,确保您已经正确地初始化了UART接口。这包括设置波特率、数据位、停止位和奇偶校验位。

2. 使用`READ_PERI_REG(UART_STATUS(UART0))`宏读取UART0的状态寄存器。这个寄存器包含了UART接收FIFO的当前字节数。

3. 使用位运算符`>>`将状态寄存器中的RX FIFO计数器部分(从UART_RXFIFO_CNT_S开始的6位)右移,以便将其与寄存器中的其他位分离。

4. 使用位运算符`&`将分离出来的RX FIFO计数器部分与`UART_RXFIFO_CNT`(0x3F,即二进制的111111)相与,以获取实际的字节数。

5. 将结果存储在`fifo_len`变量中。

关于您提到的问题,有以下几点可能的原因:

1. 回调函数的调用间隔可能过长。如果回调函数调用的间隔过长,可能会导致接收到的数据在FIFO中被覆盖或丢失。尝试将回调函数的调用间隔缩短,以确保数据能够被正确接收。

2. 打印函数可能影响了FIFO。您提到的“神秘的printf”可能在某些时候刷新了UART缓冲区,导致FIFO中的计数被重置。尝试找出这个打印函数的来源,并在接收数据的过程中禁用或修改它。

3. 硬件或软件问题。检查您的硬件连接和软件配置,确保没有其他问题影响到UART接收。

4. 检查ESP8266的固件版本和使用的SDK版本,确保它们是最新的,以避免潜在的兼容性问题。

通过以上步骤和注意事项,您应该能够更准确地获取FIFO中接收的字节数。
举报

更多回帖

发帖
×
20
完善资料,
赚取积分