Centralise calls to fcntl into functions that carefully check the
[sgt/putty] / unix / uxplink.c
index 61b9426..898f27c 100644 (file)
@@ -63,6 +63,22 @@ void modalfatalbox(char *p, ...)
     }
     cleanup_exit(1);
 }
+void nonfatal(char *p, ...)
+{
+    struct termios cf;
+    va_list ap;
+    premsg(&cf);
+    fprintf(stderr, "ERROR: ");
+    va_start(ap, p);
+    vfprintf(stderr, p, ap);
+    va_end(ap);
+    fputc('\n', stderr);
+    postmsg(&cf);
+    if (logctx) {
+        log_free(logctx);
+        logctx = NULL;
+    }
+}
 void connection_fatal(void *frontend, char *p, ...)
 {
     struct termios cf;
@@ -380,20 +396,18 @@ int try_output(int is_stderr)
     bufchain *chain = (is_stderr ? &stderr_data : &stdout_data);
     int fd = (is_stderr ? STDERR_FILENO : STDOUT_FILENO);
     void *senddata;
-    int sendlen, ret, fl;
+    int sendlen, ret;
 
     if (bufchain_size(chain) > 0) {
-        fl = fcntl(fd, F_GETFL);
-        if (fl != -1 && !(fl & O_NONBLOCK))
-            fcntl(fd, F_SETFL, fl | O_NONBLOCK);
+        int prev_nonblock = nonblock(fd);
         do {
             bufchain_prefix(chain, &senddata, &sendlen);
             ret = write(fd, senddata, sendlen);
             if (ret > 0)
                 bufchain_consume(chain, ret);
         } while (ret == sendlen && bufchain_size(chain) != 0);
-        if (fl != -1 && !(fl & O_NONBLOCK))
-            fcntl(fd, F_SETFL, fl);
+        if (!prev_nonblock)
+            no_nonblock(fd);
         if (ret < 0 && errno != EAGAIN) {
             perror(is_stderr ? "stderr: write" : "stdout: write");
             exit(1);
@@ -593,7 +607,7 @@ int main(int argc, char **argv)
     int errors;
     int use_subsystem = 0;
     int got_host = FALSE;
-    long now;
+    unsigned long now;
     struct winsize size;
 
     fdlist = NULL;
@@ -654,8 +668,11 @@ int main(int argc, char **argv)
            } else if (!strcmp(p, "-s")) {
                 /* Save status to write to conf later. */
                use_subsystem = 1;
-           } else if (!strcmp(p, "-V")) {
+           } else if (!strcmp(p, "-V") || !strcmp(p, "--version")) {
                 version();
+           } else if (!strcmp(p, "--help")) {
+                usage();
+                exit(0);
             } else if (!strcmp(p, "-pgpfp")) {
                 pgp_fingerprints();
                 exit(1);
@@ -1016,12 +1033,17 @@ int main(int argc, char **argv)
        }
 
        do {
-           long next, ticks;
+           unsigned long next, then;
+           long ticks;
            struct timeval tv, *ptv;
 
            if (run_timers(now, &next)) {
-               ticks = next - GETTICKCOUNT();
-               if (ticks < 0) ticks = 0;   /* just in case */
+               then = now;
+               now = GETTICKCOUNT();
+               if (now - then > next - then)
+                   ticks = 0;
+               else
+                   ticks = next - now;
                tv.tv_sec = ticks / 1000;
                tv.tv_usec = ticks % 1000 * 1000;
                ptv = &tv;