flash_eraseall: implement -N
[oweals/busybox.git] / miscutils / microcom.c
index 1608960e95ceee581ef8b359cf46c773127a05d6..5e29a1acdd483ba51e4382807c24685f8aa1b577 100644 (file)
@@ -5,17 +5,20 @@
  *
  * Copyright (C) 2008 by Vladimir Dronnikov <dronnikov@gmail.com>
  *
- * Licensed under GPLv2, see file LICENSE in this tarball for details.
+ * Licensed under GPLv2, see file LICENSE in this source tree.
  */
-#include "libbb.h"
 
-/* All known arches use small ints for signals */
-static volatile smallint signalled;
+//usage:#define microcom_trivial_usage
+//usage:       "[-d DELAY] [-t TIMEOUT] [-s SPEED] [-X] TTY"
+//usage:#define microcom_full_usage "\n\n"
+//usage:       "Copy bytes for stdin to TTY and from TTY to stdout\n"
+//usage:     "\n       -d      Wait up to DELAY ms for TTY output before sending every"
+//usage:     "\n               next byte to it"
+//usage:     "\n       -t      Exit if both stdin and TTY are silent for TIMEOUT ms"
+//usage:     "\n       -s      Set serial line to SPEED"
+//usage:     "\n       -X      Disable special meaning of NUL and Ctrl-X from stdin"
 
-static void signal_handler(int signo)
-{
-       signalled = signo;
-}
+#include "libbb.h"
 
 // set raw tty mode
 static void xget1(int fd, struct termios *t, struct termios *oldt)
@@ -41,7 +44,7 @@ static int xset1(int fd, struct termios *tio, const char *device)
 }
 
 int microcom_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
-int microcom_main(int argc ATTRIBUTE_UNUSED, char **argv)
+int microcom_main(int argc UNUSED_PARAM, char **argv)
 {
        int sfd;
        int nfd;
@@ -72,7 +75,7 @@ int microcom_main(int argc ATTRIBUTE_UNUSED, char **argv)
        if (sfd < 0) {
                // device already locked -> bail out
                if (errno == EEXIST)
-                       bb_perror_msg_and_die("can't create %s", device_lock_file);
+                       bb_perror_msg_and_die("can't create '%s'", device_lock_file);
                // can't create lock -> don't care
                if (ENABLE_FEATURE_CLEAN_UP)
                        free(device_lock_file);
@@ -91,16 +94,16 @@ int microcom_main(int argc ATTRIBUTE_UNUSED, char **argv)
                + (1 << SIGINT)
                + (1 << SIGTERM)
                + (1 << SIGPIPE)
-               , signal_handler);
+               , record_signo);
 
        // error exit code if we fail to open the device
-       signalled = 1;
+       bb_got_signal = 1;
 
        // open device
        sfd = open_or_warn(argv[0], O_RDWR | O_NOCTTY | O_NONBLOCK);
        if (sfd < 0)
                goto done;
-       fcntl(sfd, F_SETFL, 0);
+       fcntl(sfd, F_SETFL, O_RDWR);
 
        // put device to "raw mode"
        xget1(sfd, &tio, &tiosfd);
@@ -123,9 +126,10 @@ int microcom_main(int argc ATTRIBUTE_UNUSED, char **argv)
        pfd[1].fd = STDIN_FILENO;
        pfd[1].events = POLLIN;
 
-       signalled = 0;
+       bb_got_signal = 0;
        nfd = 2;
-       while (!signalled && safe_poll(pfd, nfd, timeout) > 0) {
+       // Not safe_poll: we want to exit on signal
+       while (!bb_got_signal && poll(pfd, nfd, timeout) > 0) {
                if (nfd > 1 && pfd[1].revents) {
                        char c;
                        // read from stdin -> write to device
@@ -159,7 +163,7 @@ skip_write: ;
                                full_write(STDOUT_FILENO, iobuf, len);
                        else {
                                // EOF/error -> bail out
-                               signalled = SIGHUP;
+                               bb_got_signal = SIGHUP;
                                break;
                        }
                }
@@ -175,5 +179,5 @@ done:
        if (device_lock_file)
                unlink(device_lock_file);
 
-       return signalled;
+       return bb_got_signal;
 }