gpt4 book ai didi

c - sleep 必须在 tcdrain() 之后吗?

转载 作者:行者123 更新时间:2023-11-30 19:26:44 25 4
gpt4 key购买 nike

我正在测试我的串口库的写入功能。首先,我将串口文件描述符安排为非阻塞文件描述符。然后我在自定义写入函数的末尾调用 tcdrain(fd) 。但是,如果我在这个自定义写入函数之后不等待 sleep() 并立即从应用程序返回,则实际上不会通过串行端口写入字节。

所以,我有两个问题。

  1. tcdrain() 不保证发送字节吗?
  2. 如何在不调用 sleep() 函数的情况下实现自定义写入功能。

我尝试使用阻塞文件描述符来执行相同的功能。但一切都没有改变。

首先,我使用以下代码初始化串行端口:

struct termios stermios;
tcgetattr ( fd, &stermios );
cfsetispeed ( &stermios, handle->baudrate );
cfsetospeed ( &stermios, handle->baudrate );

stermios.c_cflag &= ~(PARENB | CSTOPB | CRTSCTS );
stermios.c_cflag |= ( CLOCAL | CREAD );
stermios.c_cflag &= ~CSIZE;
stermios.c_cflag |= CS8;

stermios.c_iflag &= (IXON | IXOFF );
stermios.c_oflag &= ~OPOST;
stermios.c_lflag &= ~(ICANON | ECHO | ECHOE );

tcflush ( fd, TCIOFLUSH );
tcsetattr ( fd, TCSANOW, termios_p );

这是我定制的写入功能:


static int32_t surely_tcdrain ( SerialPortHandle_t const * handle_p )
{
int32_t retval = -1;
int32_t try_cnt = 0;

while ( ( ++try_cnt < MAX_TCDRAIN_TRY_CNT ) &&\
( -1 == (retval = tcdrain ( fd ) ) ) )
{
if ( EINTR == errno )
{
usleep ( TCDRAIN_DELAY );
}
else
{
fprintf (stderr, "tcdrain() FAILED, %d, %s\n",\
errno, strerror ( errno ) );
try_cnt = MAX_TCDRAIN_TRY_CNT; // Dont try again, break the loop. //
}
}

return retval;
}
int32_t write_to_serial_port( int32_t fd, void * buff, size_t size )
{
uint8_t try_cnt = 0;
size_t total_write_size = 0;

while ( ( total_write_size < size ) && ( ++try_cnt < 10 ) )
{
ssize_t w_size = -1;
w_size = write (fd, ( ( uint8_t * ) buff + total_write_size ),\
( size - total_write_size ) );

if ( w_size == -1 )
{
if ( ( errno != EINTR ) && ( errno != EAGAIN ) &&\
( errno != EWOULDBLOCK ) )
{
try_cnt = MAX_WRITE_TRY_CNT;
}
else
{
usleep ( WRITE_DELAY );
}
}
else
{
total_write_size += ( ( size_t ) w_size );
}
}

return ( ( surely_tcdrain ( fd ) == 0 ) &&\
( ( total_write_size == size ) ) ) ? 0 : -1;
}

最后,我使用以下函数关闭了串行端口文件描述符。

static void deinit_fd ( int32_t fd )
{
if ( FD_INVALID != fd )
{
if ( 1 == isatty ( fd ) )
{
tcdrain ( fd ); // Wait for write all output process. //
}
else
{
// fd not referring terminal. So no need to call tcdrain(). //
}

close ( fd );
}
else
{
// fd is invalid. //
}
}

我在 main 中调用此写入函数,然后关闭我的文件描述符并立即从应用程序返回。

我希望所有字节都必须使用我的写入函数通过串行端口写入。但我的功能不能那样工作。

最佳答案

听起来您在进程退出之前没有关闭文件。我知道你说过你这样做,但不显示该代码。您的那部分代码是否可能存在错误?

关于c - sleep 必须在 tcdrain() 之后吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56709594/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com