apps/system/zmodem: Call tcflush() before closing the serial port. This is necessary because that close operation may hang if hardware flow control is enabled. Consider this scenario: After the host sz runs on the host, it exits and leaves CTS high. The target rz completes, and tries to close the serial port. But if there is buffered Tx data, then the close will hang when it tries to drain the buffered Tx data since there is no where it can go. tcflush() discards the buffered data and permits the close to continue. There additional logic in nuttx/drivers/serial needed tow work with this.

This commit is contained in:
Gregory Nutt 2018-05-27 11:44:43 -06:00
parent 22e5af9320
commit b84f5841d5
3 changed files with 21 additions and 0 deletions

View File

@ -127,6 +127,7 @@ Using NuttX Zmodem with a Linux Host
$ sudo stty -F /dev/ttyS0 9600 # Select 9600 (or other) BAUD
$ sudo stty -F /dev/ttyS0 crtscts # Enables CTS/RTS handshaking *
$ sudo stty -F /dev/ttyS0 raw # Puts the TTY in raw mode
$ sudo stty -F /dev/ttyS0 # Show the TTY configuration
* Only is hardware flow control is enabled.

View File

@ -45,11 +45,13 @@
#include <string.h>
#include <signal.h>
#include <fcntl.h>
#include <termios.h>
#include <libgen.h>
#include <time.h>
#include <errno.h>
#include "system/zmodem.h"
#include "zm.h"
/****************************************************************************
* Private Functions
@ -155,8 +157,16 @@ int rz_main(int argc, FAR char **argv)
errout_with_zmodem:
(void)zmr_release(handle);
errout_with_device:
#ifdef CONFIG_SYSTEM_ZMODEM_FLOWC
/* Flush the serial output to assure do not hang trying to drain it */
tcflush(fd, TCIOFLUSH);
#endif
(void)close(fd);
errout:
return exitcode;
}

View File

@ -45,11 +45,13 @@
#include <string.h>
#include <signal.h>
#include <fcntl.h>
#include <termios.h>
#include <libgen.h>
#include <time.h>
#include <errno.h>
#include "system/zmodem.h"
#include "zm.h"
/****************************************************************************
* Private Functions
@ -261,8 +263,16 @@ int sz_main(int argc, FAR char **argv)
errout_with_zmodem:
(void)zms_release(handle);
errout_with_device:
#ifdef CONFIG_SYSTEM_ZMODEM_FLOWC
/* Flush the serial output to assure do not hang trying to drain it */
tcflush(fd, TCIOFLUSH);
#endif
(void)close(fd);
errout:
return exitcode;
}