Enable better build-time flexibility over which WinSock to include
[u/mdw/putty] / plink.c
diff --git a/plink.c b/plink.c
index 5022761..0a74062 100644 (file)
--- a/plink.c
+++ b/plink.c
@@ -2,7 +2,9 @@
  * PLink - a command-line (stdin/stdout) variant of PuTTY.
  */
 
+#ifndef AUTO_WINSOCK
 #include <winsock2.h>
+#endif
 #include <windows.h>
 #include <stdio.h>
 #include <stdarg.h>
@@ -20,14 +22,31 @@ void fatalbox (char *p, ...) {
     WSACleanup();
     exit(1);
 }
+void connection_fatal (char *p, ...) {
+    va_list ap;
+    fprintf(stderr, "FATAL ERROR: ", p);
+    va_start(ap, p);
+    vfprintf(stderr, p, ap);
+    va_end(ap);
+    fputc('\n', stderr);
+    WSACleanup();
+    exit(1);
+}
 
 HANDLE outhandle;
+DWORD orig_console_mode;
+
+void begin_session(void) {
+    if (!cfg.ldisc_term)
+        SetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), ENABLE_PROCESSED_INPUT);
+    else
+        SetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), orig_console_mode);
+}
 
 void term_out(void)
 {
     int reap;
     DWORD ret;
-
     reap = 0;
     while (reap < inbuf_head) {
         if (!WriteFile(outhandle, inbuf+reap, inbuf_head-reap, &ret, NULL))
@@ -43,6 +62,50 @@ struct input_data {
     HANDLE event;
 };
 
+static int get_password(const char *prompt, char *str, int maxlen)
+{
+    HANDLE hin, hout;
+    DWORD savemode, i;
+
+#if 0 /* this allows specifying a password some other way */
+    if (password) {
+        static int tried_once = 0;
+
+        if (tried_once) {
+            return 0;
+        } else {
+            strncpy(str, password, maxlen);
+            str[maxlen-1] = '\0';
+            tried_once = 1;
+            return 1;
+        }
+    }
+#endif
+
+    hin = GetStdHandle(STD_INPUT_HANDLE);
+    hout = GetStdHandle(STD_OUTPUT_HANDLE);
+    if (hin == INVALID_HANDLE_VALUE || hout == INVALID_HANDLE_VALUE) {
+        fprintf(stderr, "Cannot get standard input/output handles");
+        return 0;
+    }
+
+    GetConsoleMode(hin, &savemode);
+    SetConsoleMode(hin, (savemode & (~ENABLE_ECHO_INPUT)) |
+                   ENABLE_PROCESSED_INPUT | ENABLE_LINE_INPUT);
+
+    WriteFile(hout, prompt, strlen(prompt), &i, NULL);
+    ReadFile(hin, str, maxlen-1, &i, NULL);
+
+    SetConsoleMode(hin, savemode);
+
+    if ((int)i > maxlen) i = maxlen-1; else i = i - 2;
+    str[i] = '\0';
+
+    WriteFile(hout, "\r\n", 2, &i, NULL);
+
+    return 1;
+}
+
 int WINAPI stdin_read_thread(void *param) {
     struct input_data *idata = (struct input_data *)param;
     HANDLE inhandle;
@@ -70,7 +133,9 @@ int main(int argc, char **argv) {
     struct input_data idata;
     int sending;
 
-    flags = FLAG_CONNECTION;
+    ssh_get_password = get_password;
+
+    flags = FLAG_STDERR;
     /*
      * Process the command line.
      */
@@ -83,6 +148,8 @@ int main(int argc, char **argv) {
             if (!strcmp(p, "-ssh")) {
                default_protocol = cfg.protocol = PROT_SSH;
                default_port = cfg.port = 22;
+           } else if (!strcmp(p, "-v")) {
+                flags |= FLAG_VERBOSE;
            } else if (!strcmp(p, "-log")) {
                 logfile = "putty.log";
            }
@@ -165,6 +232,9 @@ int main(int argc, char **argv) {
        }
     }
 
+    if (!*cfg.remote_cmd)
+        flags |= FLAG_INTERACTIVE;
+
     /*
      * Select protocol. This is farmed out into a table in a
      * separate file to enable an ssh-free variant.
@@ -216,8 +286,8 @@ int main(int argc, char **argv) {
     netevent = CreateEvent(NULL, FALSE, FALSE, NULL);
     stdinevent = CreateEvent(NULL, FALSE, FALSE, NULL);
 
-    if (!cfg.ldisc_term)
-        SetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), ENABLE_PROCESSED_INPUT);
+    GetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), &orig_console_mode);
+    SetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), ENABLE_PROCESSED_INPUT);
     outhandle = GetStdHandle(STD_OUTPUT_HANDLE);
 
     /*