]> asedeno.scripts.mit.edu Git - PuTTY.git/commitdiff
New option to allow use of the local OS username for login to the remote side
authorJacob Nevins <jacobn@chiark.greenend.org.uk>
Mon, 24 Nov 2008 17:51:42 +0000 (17:51 +0000)
committerJacob Nevins <jacobn@chiark.greenend.org.uk>
Mon, 24 Nov 2008 17:51:42 +0000 (17:51 +0000)
if we have no better ideas, with UI shamelessly stolen from Quest PuTTY.

Off by default, which effectively reverts the change to using the local
username by default that came in with GSSAPI support in r8138. Anyone wanting
seamless single sign-on will need to set the new option. (The previous
default behaviour was getting in the way in ad-hoc scenarios.)

Note that the PSCP and Unix-Plink behaviour of using the local username by
default have remained unchanged throughout; they are not affected by the new
option. Not sure if that's the Right Thing.

[originally from svn r8324]
[r8138 == de5dd9d65c0e2ffa9bc9cab038bf0be77efbf820]

config.c
doc/config.but
putty.h
rlogin.c
settings.c
ssh.c
telnet.c
windows/winhelp.h

index 67a018fe51590165a8c8d820122f814be7f793ca..09c77d57083c7ccdaec996cd14e1e8f6ecf5afc5 100644 (file)
--- a/config.c
+++ b/config.c
@@ -1751,6 +1751,21 @@ void setup_config_box(struct controlbox *b, int midsession,
                         HELPCTX(connection_username),
                         dlg_stdeditbox_handler, I(offsetof(Config,username)),
                         I(sizeof(((Config *)0)->username)));
+           {
+               /* We assume the local username is sufficiently stable
+                * to include on the dialog box. */
+               char *user = get_username();
+               char *userlabel = dupprintf("Use system username (%s)", user);
+               sfree(user);
+               ctrl_radiobuttons(s, "When username is not specified:", 'n', 4,
+                                 HELPCTX(connection_username_from_env),
+                                 dlg_stdradiobutton_handler,
+                                 I(offsetof(Config, username_from_env)),
+                                 "Prompt", I(FALSE),
+                                 userlabel, I(TRUE),
+                                 NULL);
+               sfree(userlabel);
+           }
 
            s = ctrl_getset(b, "Connection/Data", "term",
                            "Terminal details");
index 96f5dbe4cf2958380e0a8d899a69f0ba1b995439..27704ee97aedc03506aaf8a6db7fa2102de68cae 100644 (file)
@@ -1788,6 +1788,22 @@ it explicitly every time. (Some Telnet servers don't support this.)
 
 In this box you can type that user name.
 
+\S{config-username-from-env} \q{Use of system username}
+
+\cfg{winhelp-topic}{connection.usernamefromenv}
+
+When the previous box (\k{config-username}) is left blank, by default,
+PuTTY will prompt for a username at the time you make a connection.
+
+In some environments, such as large corporate networks with \i{single
+sign-on}, a more sensible default may be to use the name of the user
+logged in to the local operating system (if any). This control allows
+you to change the default behaviour.
+
+The current system username is displayed in the dialog as a
+convenience. It is not saved in the configuration; if a saved session
+is later used by a different user, that user's name will be used.
+
 \S{config-termtype} \q{\ii{Terminal-type} string}
 
 \cfg{winhelp-topic}{connection.termtype}
diff --git a/putty.h b/putty.h
index 20cff54369815f1503b555958f9bdc4a0345eaed..b372d4a3d5a558335574d166f604138b8dc5aced 100644 (file)
--- a/putty.h
+++ b/putty.h
@@ -472,6 +472,7 @@ struct config_tag {
     char ttymodes[768];                       /* MODE\tVvalue\0MODE\tA\0\0 */
     char environmt[1024];             /* VAR\tvalue\0VAR\tvalue\0\0 */
     char username[100];
+    int username_from_env;
     char localusername[100];
     int rfc_environ;
     int passive_telnet;
@@ -790,6 +791,7 @@ void random_destroy_seed(void);
  */
 Backend *backend_from_name(const char *name);
 Backend *backend_from_proto(int proto);
+int get_remote_username(Config *cfg, char *user, size_t len);
 char *save_settings(char *section, Config * cfg);
 void save_open_settings(void *sesskey, Config *cfg);
 void load_settings(char *section, Config * cfg);
index c9e7c5ec955df5d41d27f677b11a39fcad40a506..c392fa0a983178318687ebc1cfe5fc9fffd3255b 100644 (file)
--- a/rlogin.c
+++ b/rlogin.c
@@ -182,12 +182,14 @@ static const char *rlogin_init(void *frontend_handle, void **backend_handle,
     {
        char z = 0;
        char *p;
+       char ruser[sizeof(cfg->username)];
+       (void) get_remote_username(cfg, ruser, sizeof(ruser));
        sk_write(rlogin->s, &z, 1);
        sk_write(rlogin->s, cfg->localusername,
                 strlen(cfg->localusername));
        sk_write(rlogin->s, &z, 1);
-       sk_write(rlogin->s, cfg->username,
-                strlen(cfg->username));
+       sk_write(rlogin->s, ruser,
+                strlen(ruser));
        sk_write(rlogin->s, &z, 1);
        sk_write(rlogin->s, cfg->termtype,
                 strlen(cfg->termtype));
index 269267699275c8b0684b03b403788a5343a51f9f..7ecd56108b3731efc409e3cc298b97ce5ca476a9 100644 (file)
@@ -75,6 +75,25 @@ Backend *backend_from_proto(int proto)
     return NULL;
 }
 
+int get_remote_username(Config *cfg, char *user, size_t len)
+{
+    if (*cfg->username) {
+       strncpy(user, cfg->username, len);
+       user[len-1] = '\0';
+    } else {
+       if (cfg->username_from_env) {
+           /* Use local username. */
+           char *luser = get_username();
+           strncpy(user, luser, len);
+           user[len-1] = '\0';
+           sfree(luser);
+       } else {
+           *user = '\0';
+       }
+    }
+    return (*user != '\0');
+}
+
 static void gpps(void *handle, const char *name, const char *def,
                 char *val, int len)
 {
@@ -316,6 +335,7 @@ void save_open_settings(void *sesskey, Config *cfg)
     write_setting_s(sesskey, "ProxyTelnetCommand", cfg->proxy_telnet_command);
     wmap(sesskey, "Environment", cfg->environmt, lenof(cfg->environmt));
     write_setting_s(sesskey, "UserName", cfg->username);
+    write_setting_i(sesskey, "UserNameFromEnvironment", cfg->username_from_env);
     write_setting_s(sesskey, "LocalUserName", cfg->localusername);
     write_setting_i(sesskey, "NoPTY", cfg->nopty);
     write_setting_i(sesskey, "Compression", cfg->compression);
@@ -584,7 +604,8 @@ void load_open_settings(void *sesskey, Config *cfg)
     gpps(sesskey, "ProxyTelnetCommand", "connect %host %port\\n",
         cfg->proxy_telnet_command, sizeof(cfg->proxy_telnet_command));
     gppmap(sesskey, "Environment", "", cfg->environmt, lenof(cfg->environmt));
-    gpps(sesskey, "UserName", get_username(), cfg->username, sizeof(cfg->username));
+    gpps(sesskey, "UserName", "", cfg->username, sizeof(cfg->username));
+    gppi(sesskey, "UserNameFromEnvironment", 0, &cfg->username_from_env);
     gpps(sesskey, "LocalUserName", "", cfg->localusername,
         sizeof(cfg->localusername));
     gppi(sesskey, "NoPTY", 0, &cfg->nopty);
diff --git a/ssh.c b/ssh.c
index d30626dc31b3e5535ad9025a80192ca77a7d2b51..9f2d011150afb0ccade3ae7973091f339ed173c5 100644 (file)
--- a/ssh.c
+++ b/ssh.c
@@ -3361,7 +3361,8 @@ static int do_ssh1_login(Ssh ssh, unsigned char *in, int inlen,
 
     fflush(stdout); /* FIXME eh? */
     {
-       if (!*ssh->cfg.username) {
+       if (!get_remote_username(&ssh->cfg, s->username,
+                                sizeof(s->username))) {
            int ret; /* need not be kept over crReturn */
            s->cur_prompt = new_prompts(ssh->frontend);
            s->cur_prompt->to_server = TRUE;
@@ -3386,9 +3387,6 @@ static int do_ssh1_login(Ssh ssh, unsigned char *in, int inlen,
            memcpy(s->username, s->cur_prompt->prompts[0]->result,
                   lenof(s->username));
            free_prompts(s->cur_prompt);
-       } else {
-           strncpy(s->username, ssh->cfg.username, sizeof(s->username));
-           s->username[sizeof(s->username)-1] = '\0';
        }
 
        send_packet(ssh, SSH1_CMSG_USER, PKT_STR, s->username, PKT_END);
@@ -7295,7 +7293,8 @@ static void do_ssh2_authconn(Ssh ssh, unsigned char *in, int inlen,
             * with change_username turned off we don't try to get
             * it again.
             */
-       } else if (!*ssh->cfg.username) {
+       } else if (!get_remote_username(&ssh->cfg, s->username,
+                                       sizeof(s->username))) {
            int ret; /* need not be kept over crReturn */
            s->cur_prompt = new_prompts(ssh->frontend);
            s->cur_prompt->to_server = TRUE;
@@ -7323,8 +7322,6 @@ static void do_ssh2_authconn(Ssh ssh, unsigned char *in, int inlen,
            free_prompts(s->cur_prompt);
        } else {
            char *stuff;
-           strncpy(s->username, ssh->cfg.username, sizeof(s->username));
-           s->username[sizeof(s->username)-1] = '\0';
            if ((flags & FLAG_VERBOSE) || (flags & FLAG_INTERACTIVE)) {
                stuff = dupprintf("Using username \"%s\".\r\n", s->username);
                c_write_str(ssh, stuff);
index 4f0a36fe54f396180c929d00e3d15250f19cde98..20ccc83e2ab49f84ad4337254815851773edc5e8 100644 (file)
--- a/telnet.c
+++ b/telnet.c
@@ -466,29 +466,33 @@ static void process_subneg(Telnet telnet)
                    b[n++] = *e++;
                e++;
            }
-           if (*telnet->cfg.username) {
-               b[n++] = var;
-               b[n++] = 'U';
-               b[n++] = 'S';
-               b[n++] = 'E';
-               b[n++] = 'R';
-               b[n++] = value;
-               e = telnet->cfg.username;
-               while (*e)
-                   b[n++] = *e++;
+           {
+               char user[sizeof(telnet->cfg.username)];
+               (void) get_remote_username(&telnet->cfg, user, sizeof(user));
+               if (*user) {
+                   b[n++] = var;
+                   b[n++] = 'U';
+                   b[n++] = 'S';
+                   b[n++] = 'E';
+                   b[n++] = 'R';
+                   b[n++] = value;
+                   e = user;
+                   while (*e)
+                       b[n++] = *e++;
+               }
+               b[n++] = IAC;
+               b[n++] = SE;
+               telnet->bufsize = sk_write(telnet->s, (char *)b, n);
+               logbuf = dupprintf("client:\tSB %s IS %s%s%s%s",
+                                  telopt(telnet->sb_opt),
+                                  *user ? "USER=" : "",
+                                  user,
+                                  *user ? " " : "",
+                                  n == 6 ? "<nothing>" :
+                                  (*telnet->cfg.environmt ? "<stuff>" : ""));
+               logevent(telnet->frontend, logbuf);
+               sfree(logbuf);
            }
-           b[n++] = IAC;
-           b[n++] = SE;
-           telnet->bufsize = sk_write(telnet->s, (char *)b, n);
-           logbuf = dupprintf("client:\tSB %s IS %s%s%s%s",
-                              telopt(telnet->sb_opt),
-                              *telnet->cfg.username ? "USER=" : "",
-                              telnet->cfg.username,
-                              *telnet->cfg.username ? " " : "",
-                              n == 6 ? "<nothing>" :
-                              (*telnet->cfg.environmt ? "<stuff>" : ""));
-           logevent(telnet->frontend, logbuf);
-           sfree(logbuf);
        }
        break;
     }
index fc0b83701231a71317a9486f4974f7ffb2323247..4a3c6aaa05c6b166a76b6b305f8dcb01e107062d 100644 (file)
@@ -1,6 +1,10 @@
 /*
- * winhelp.h - define Windows Help context names. These match up with
- * the \cfg{winhelp-topic} directives in the Halibut source.
+ * winhelp.h - define Windows Help context names.
+ * Each definition has the form "winhelp-topic:halibut-topic", where:
+ *  - "winhelp-topic" matches up with the \cfg{winhelp-topic} directives
+ *    in the Halibut source, and is used for WinHelp;
+ *  - "halibut-topic" matches up with the Halibut keywords in the source,
+ *    and is used for HTML Help.
  */
 
 /* Maximum length for WINHELP_CTX_foo strings */
@@ -70,6 +74,7 @@
 #define WINHELP_CTX_connection_termtype "connection.termtype:config-termtype"
 #define WINHELP_CTX_connection_termspeed "connection.termspeed:config-termspeed"
 #define WINHELP_CTX_connection_username "connection.username:config-username"
+#define WINHELP_CTX_connection_username_from_env "connection.usernamefromenv:config-username-from-env"
 #define WINHELP_CTX_connection_keepalive "connection.keepalive:config-keepalive"
 #define WINHELP_CTX_connection_nodelay "connection.nodelay:config-nodelay"
 #define WINHELP_CTX_connection_ipversion "connection.ipversion:config-address-family"