我正在尝试fgets
在 esp-idf 中使用从 UART 读取整行。
基本参考代码是选择示例。到目前为止,这是我的代码:
#define DLP_RFID2_BUF_SIZE 256
static char buffer[DLP_RFID2_BUF_SIZE];
uart_config_t uart_config =
{
.baud_rate = 115200,
.data_bits = UART_DATA_8_BITS,
.parity = UART_PARITY_DISABLE,
.stop_bits = UART_STOP_BITS_1,
.flow_ctrl = UART_HW_FLOWCTRL_DISABLE,
.source_clk = UART_SCLK_DEFAULT,
};
ESP_ERROR_CHECK(uart_driver_install(UART_NUM_1, DLP_RFID2_BUF_SIZE * 2, 0, 0, NULL, 0));
ESP_ERROR_CHECK(uart_param_config(UART_NUM_1, &uart_config));
ESP_ERROR_CHECK(uart_set_pin(UART_NUM_1, PIN_DLP_RFID2_TX, PIN_DLP_RFID2_RX, UART_PIN_NO_CHANGE, UART_PIN_NO_CHANGE));
if ((fd = open("/dev/uart/1", O_RDWR)) == -1)
{
ESP_LOGE(TAG, "Cannot open UART");
return fd;
}
uart_vfs_dev_use_driver(UART_NUM_1);
这里是循环函数:
int s;
fd_set rfds;
struct timeval tv = {
.tv_sec = 0,
.tv_usec = 20000,
};
FD_ZERO(&rfds);
FD_SET(fd, &rfds);
s = select(fd + 1, &rfds, NULL, NULL, &tv);
if (s < 0)
{
ESP_LOGE(TAG, "Select failed: errno %d (%s)", errno, strerror(errno));
}
else if (s == 0)
{
ESP_LOGI(TAG, "Timeout has been reached and nothing has been received");
}
else
{
if (FD_ISSET(fd, &rfds))
{
if (fgets(buffer, sizeof(buffer), ???))
{
// do something
}
}
else
{
ESP_LOGE(TAG, "No FD has been set in select()");
}
}
fgets函数需要一个FILE *
变量作为第三个参数。但我只有int
s ( fd
, s
) 和fd_set
( rfds
)。
我尝试更改代码以便使用FILE *
:
FILE *f = fopen("/dev/uart/1", "rw");
// ...
if (fgets(buffer, sizeof(buffer) - 1, f))
{
// do something
}
由于fgets
是阻塞的,我需要先检查是否有一些数据。但现在select
需要一个fd_set
而不是一个FILE *
:
int select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *errorfds, struct timeval *timeout);
我怎样才能“转换”FILE *
为fd_set
或?int
FILE *