- djm@cvs.openbsd.org 2011/05/06 21:34:32

[clientloop.c mux.c readconf.c readconf.h ssh.c ssh_config.5]
     Add a RequestTTY ssh_config option to allow configuration-based
     control over tty allocation (like -t/-T); ok markus@
This commit is contained in:
Damien Miller 2011-05-15 08:45:50 +10:00
parent fe92421772
commit 21771e22d3
7 changed files with 91 additions and 40 deletions

View File

@ -32,6 +32,10 @@
Will match "a.example.org", "b.example.org", but not "c.example.org" Will match "a.example.org", "b.example.org", but not "c.example.org"
ok markus@ ok markus@
- djm@cvs.openbsd.org 2011/05/06 21:34:32
[clientloop.c mux.c readconf.c readconf.h ssh.c ssh_config.5]
Add a RequestTTY ssh_config option to allow configuration-based
control over tty allocation (like -t/-T); ok markus@
20110510 20110510
- (dtucker) [openbsd-compat/openssl-compat.{c,h}] Bug #1882: fix - (dtucker) [openbsd-compat/openssl-compat.{c,h}] Bug #1882: fix

View File

@ -1,4 +1,4 @@
/* $OpenBSD: clientloop.c,v 1.232 2011/04/17 22:42:41 djm Exp $ */ /* $OpenBSD: clientloop.c,v 1.233 2011/05/06 21:34:32 djm Exp $ */
/* /*
* Author: Tatu Ylonen <ylo@cs.hut.fi> * Author: Tatu Ylonen <ylo@cs.hut.fi>
* Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@ -130,9 +130,6 @@ extern int muxserver_sock; /* XXX use mux_client_cleanup() instead */
*/ */
extern char *host; extern char *host;
/* Force TTY allocation */
extern int force_tty_flag;
/* /*
* Flag to indicate that we have received a window change signal which has * Flag to indicate that we have received a window change signal which has
* not yet been processed. This will cause a message indicating the new * not yet been processed. This will cause a message indicating the new
@ -662,7 +659,7 @@ client_suspend_self(Buffer *bin, Buffer *bout, Buffer *berr)
atomicio(vwrite, fileno(stderr), buffer_ptr(berr), atomicio(vwrite, fileno(stderr), buffer_ptr(berr),
buffer_len(berr)); buffer_len(berr));
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
/* /*
* Free (and clear) the buffer to reduce the amount of data that gets * Free (and clear) the buffer to reduce the amount of data that gets
@ -683,7 +680,7 @@ client_suspend_self(Buffer *bin, Buffer *bout, Buffer *berr)
buffer_init(bout); buffer_init(bout);
buffer_init(berr); buffer_init(berr);
enter_raw_mode(force_tty_flag); enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
} }
static void static void
@ -826,7 +823,7 @@ process_cmdline(void)
bzero(&fwd, sizeof(fwd)); bzero(&fwd, sizeof(fwd));
fwd.listen_host = fwd.connect_host = NULL; fwd.listen_host = fwd.connect_host = NULL;
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
handler = signal(SIGINT, SIG_IGN); handler = signal(SIGINT, SIG_IGN);
cmd = s = read_passphrase("\r\nssh> ", RP_ECHO); cmd = s = read_passphrase("\r\nssh> ", RP_ECHO);
if (s == NULL) if (s == NULL)
@ -930,7 +927,7 @@ process_cmdline(void)
out: out:
signal(SIGINT, handler); signal(SIGINT, handler);
enter_raw_mode(force_tty_flag); enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
if (cmd) if (cmd)
xfree(cmd); xfree(cmd);
if (fwd.listen_host != NULL) if (fwd.listen_host != NULL)
@ -1049,7 +1046,8 @@ process_escapes(Channel *c, Buffer *bin, Buffer *bout, Buffer *berr,
* more new connections). * more new connections).
*/ */
/* Restore tty modes. */ /* Restore tty modes. */
leave_raw_mode(force_tty_flag); leave_raw_mode(
options.request_tty == REQUEST_TTY_FORCE);
/* Stop listening for new connections. */ /* Stop listening for new connections. */
channel_stop_listening(); channel_stop_listening();
@ -1344,7 +1342,7 @@ client_channel_closed(int id, void *arg)
{ {
channel_cancel_cleanup(id); channel_cancel_cleanup(id);
session_closed = 1; session_closed = 1;
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
} }
/* /*
@ -1415,7 +1413,7 @@ client_loop(int have_pty, int escape_char_arg, int ssh2_chan_id)
signal(SIGWINCH, window_change_handler); signal(SIGWINCH, window_change_handler);
if (have_pty) if (have_pty)
enter_raw_mode(force_tty_flag); enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
if (compat20) { if (compat20) {
session_ident = ssh2_chan_id; session_ident = ssh2_chan_id;
@ -1559,7 +1557,7 @@ client_loop(int have_pty, int escape_char_arg, int ssh2_chan_id)
channel_free_all(); channel_free_all();
if (have_pty) if (have_pty)
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
/* restore blocking io */ /* restore blocking io */
if (!isatty(fileno(stdin))) if (!isatty(fileno(stdin)))
@ -2142,7 +2140,7 @@ client_stop_mux(void)
void void
cleanup_exit(int i) cleanup_exit(int i)
{ {
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
leave_non_blocking(); leave_non_blocking();
if (options.control_path != NULL && muxserver_sock != -1) if (options.control_path != NULL && muxserver_sock != -1)
unlink(options.control_path); unlink(options.control_path);

7
mux.c
View File

@ -1,4 +1,4 @@
/* $OpenBSD: mux.c,v 1.26 2011/05/05 05:12:08 djm Exp $ */ /* $OpenBSD: mux.c,v 1.27 2011/05/06 21:34:32 djm Exp $ */
/* /*
* Copyright (c) 2002-2008 Damien Miller <djm@openbsd.org> * Copyright (c) 2002-2008 Damien Miller <djm@openbsd.org>
* *
@ -87,7 +87,6 @@
/* from ssh.c */ /* from ssh.c */
extern int tty_flag; extern int tty_flag;
extern int force_tty_flag;
extern Options options; extern Options options;
extern int stdin_null_flag; extern int stdin_null_flag;
extern char *host; extern char *host;
@ -1710,7 +1709,7 @@ mux_client_request_session(int fd)
signal(SIGWINCH, control_client_sigrelay); signal(SIGWINCH, control_client_sigrelay);
if (tty_flag) if (tty_flag)
enter_raw_mode(force_tty_flag); enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
/* /*
* Stick around until the controlee closes the client_fd. * Stick around until the controlee closes the client_fd.
@ -1739,7 +1738,7 @@ mux_client_request_session(int fd)
} }
close(fd); close(fd);
leave_raw_mode(force_tty_flag); leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
if (muxclient_terminate) { if (muxclient_terminate) {
debug2("Exiting on signal %d", muxclient_terminate); debug2("Exiting on signal %d", muxclient_terminate);

View File

@ -1,4 +1,4 @@
/* $OpenBSD: readconf.c,v 1.191 2011/05/06 21:31:38 djm Exp $ */ /* $OpenBSD: readconf.c,v 1.192 2011/05/06 21:34:32 djm Exp $ */
/* /*
* Author: Tatu Ylonen <ylo@cs.hut.fi> * Author: Tatu Ylonen <ylo@cs.hut.fi>
* Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@ -134,7 +134,7 @@ typedef enum {
oHashKnownHosts, oHashKnownHosts,
oTunnel, oTunnelDevice, oLocalCommand, oPermitLocalCommand, oTunnel, oTunnelDevice, oLocalCommand, oPermitLocalCommand,
oVisualHostKey, oUseRoaming, oZeroKnowledgePasswordAuthentication, oVisualHostKey, oUseRoaming, oZeroKnowledgePasswordAuthentication,
oKexAlgorithms, oIPQoS, oKexAlgorithms, oIPQoS, oRequestTTY,
oDeprecated, oUnsupported oDeprecated, oUnsupported
} OpCodes; } OpCodes;
@ -245,6 +245,7 @@ static struct {
#endif #endif
{ "kexalgorithms", oKexAlgorithms }, { "kexalgorithms", oKexAlgorithms },
{ "ipqos", oIPQoS }, { "ipqos", oIPQoS },
{ "requesttty", oRequestTTY },
{ NULL, oBadOption } { NULL, oBadOption }
}; };
@ -1013,6 +1014,26 @@ parse_int:
intptr = &options->use_roaming; intptr = &options->use_roaming;
goto parse_flag; goto parse_flag;
case oRequestTTY:
arg = strdelim(&s);
if (!arg || *arg == '\0')
fatal("%s line %d: missing argument.",
filename, linenum);
intptr = &options->request_tty;
if (strcasecmp(arg, "yes") == 0)
value = REQUEST_TTY_YES;
else if (strcasecmp(arg, "no") == 0)
value = REQUEST_TTY_NO;
else if (strcasecmp(arg, "force") == 0)
value = REQUEST_TTY_FORCE;
else if (strcasecmp(arg, "auto") == 0)
value = REQUEST_TTY_AUTO;
else
fatal("Unsupported RequestTTY \"%s\"", arg);
if (*activep && *intptr == -1)
*intptr = value;
break;
case oDeprecated: case oDeprecated:
debug("%s line %d: Deprecated option \"%s\"", debug("%s line %d: Deprecated option \"%s\"",
filename, linenum, keyword); filename, linenum, keyword);
@ -1173,6 +1194,7 @@ initialize_options(Options * options)
options->zero_knowledge_password_authentication = -1; options->zero_knowledge_password_authentication = -1;
options->ip_qos_interactive = -1; options->ip_qos_interactive = -1;
options->ip_qos_bulk = -1; options->ip_qos_bulk = -1;
options->request_tty = -1;
} }
/* /*
@ -1331,6 +1353,8 @@ fill_default_options(Options * options)
options->ip_qos_interactive = IPTOS_LOWDELAY; options->ip_qos_interactive = IPTOS_LOWDELAY;
if (options->ip_qos_bulk == -1) if (options->ip_qos_bulk == -1)
options->ip_qos_bulk = IPTOS_THROUGHPUT; options->ip_qos_bulk = IPTOS_THROUGHPUT;
if (options->request_tty == -1)
options->request_tty = REQUEST_TTY_AUTO;
/* options->local_command should not be set by default */ /* options->local_command should not be set by default */
/* options->proxy_command should not be set by default */ /* options->proxy_command should not be set by default */
/* options->user will be set in the main program if appropriate */ /* options->user will be set in the main program if appropriate */

View File

@ -1,4 +1,4 @@
/* $OpenBSD: readconf.h,v 1.88 2010/11/13 23:27:50 djm Exp $ */ /* $OpenBSD: readconf.h,v 1.89 2011/05/06 21:34:32 djm Exp $ */
/* /*
* Author: Tatu Ylonen <ylo@cs.hut.fi> * Author: Tatu Ylonen <ylo@cs.hut.fi>
@ -132,6 +132,7 @@ typedef struct {
int use_roaming; int use_roaming;
int request_tty;
} Options; } Options;
#define SSHCTL_MASTER_NO 0 #define SSHCTL_MASTER_NO 0
@ -140,6 +141,11 @@ typedef struct {
#define SSHCTL_MASTER_ASK 3 #define SSHCTL_MASTER_ASK 3
#define SSHCTL_MASTER_AUTO_ASK 4 #define SSHCTL_MASTER_AUTO_ASK 4
#define REQUEST_TTY_AUTO 0
#define REQUEST_TTY_NO 1
#define REQUEST_TTY_YES 2
#define REQUEST_TTY_FORCE 3
void initialize_options(Options *); void initialize_options(Options *);
void fill_default_options(Options *); void fill_default_options(Options *);
int read_config_file(const char *, const char *, Options *, int); int read_config_file(const char *, const char *, Options *, int);

41
ssh.c
View File

@ -1,4 +1,4 @@
/* $OpenBSD: ssh.c,v 1.358 2011/05/06 21:18:02 djm Exp $ */ /* $OpenBSD: ssh.c,v 1.359 2011/05/06 21:34:32 djm Exp $ */
/* /*
* Author: Tatu Ylonen <ylo@cs.hut.fi> * Author: Tatu Ylonen <ylo@cs.hut.fi>
* Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@ -114,10 +114,8 @@ extern char *__progname;
/* Flag indicating whether debug mode is on. May be set on the command line. */ /* Flag indicating whether debug mode is on. May be set on the command line. */
int debug_flag = 0; int debug_flag = 0;
/* Flag indicating whether a tty should be allocated */ /* Flag indicating whether a tty should be requested */
int tty_flag = 0; int tty_flag = 0;
int no_tty_flag = 0;
int force_tty_flag = 0;
/* don't exec a shell */ /* don't exec a shell */
int no_shell_flag = 0; int no_shell_flag = 0;
@ -135,7 +133,7 @@ int stdin_null_flag = 0;
int need_controlpersist_detach = 0; int need_controlpersist_detach = 0;
/* Copies of flags for ControlPersist foreground slave */ /* Copies of flags for ControlPersist foreground slave */
int ostdin_null_flag, ono_shell_flag, ono_tty_flag, otty_flag; int ostdin_null_flag, ono_shell_flag, otty_flag, orequest_tty;
/* /*
* Flag indicating that ssh should fork after authentication. This is useful * Flag indicating that ssh should fork after authentication. This is useful
@ -389,9 +387,10 @@ main(int ac, char **av)
#endif #endif
break; break;
case 't': case 't':
if (tty_flag) if (options.request_tty == REQUEST_TTY_YES)
force_tty_flag = 1; options.request_tty = REQUEST_TTY_FORCE;
tty_flag = 1; else
options.request_tty = REQUEST_TTY_YES;
break; break;
case 'v': case 'v':
if (debug_flag == 0) { if (debug_flag == 0) {
@ -434,7 +433,7 @@ main(int ac, char **av)
optarg); optarg);
exit(255); exit(255);
} }
no_tty_flag = 1; options.request_tty = REQUEST_TTY_NO;
no_shell_flag = 1; no_shell_flag = 1;
options.clear_forwardings = 1; options.clear_forwardings = 1;
options.exit_on_forward_failure = 1; options.exit_on_forward_failure = 1;
@ -543,10 +542,10 @@ main(int ac, char **av)
break; break;
case 'N': case 'N':
no_shell_flag = 1; no_shell_flag = 1;
no_tty_flag = 1; options.request_tty = REQUEST_TTY_NO;
break; break;
case 'T': case 'T':
no_tty_flag = 1; options.request_tty = REQUEST_TTY_NO;
break; break;
case 'o': case 'o':
dummy = 1; dummy = 1;
@ -606,6 +605,10 @@ main(int ac, char **av)
/* Initialize the command to execute on remote host. */ /* Initialize the command to execute on remote host. */
buffer_init(&command); buffer_init(&command);
if (options.request_tty == REQUEST_TTY_YES ||
options.request_tty == REQUEST_TTY_FORCE)
tty_flag = 1;
/* /*
* Save the command to execute on the remote host in a buffer. There * Save the command to execute on the remote host in a buffer. There
* is no limit on the length of the command, except by the maximum * is no limit on the length of the command, except by the maximum
@ -613,7 +616,7 @@ main(int ac, char **av)
*/ */
if (!ac) { if (!ac) {
/* No command specified - execute shell on a tty. */ /* No command specified - execute shell on a tty. */
tty_flag = 1; tty_flag = options.request_tty != REQUEST_TTY_NO;
if (subsystem_flag) { if (subsystem_flag) {
fprintf(stderr, fprintf(stderr,
"You must specify a subsystem to invoke.\n"); "You must specify a subsystem to invoke.\n");
@ -636,13 +639,14 @@ main(int ac, char **av)
/* Allocate a tty by default if no command specified. */ /* Allocate a tty by default if no command specified. */
if (buffer_len(&command) == 0) if (buffer_len(&command) == 0)
tty_flag = 1; tty_flag = options.request_tty != REQUEST_TTY_NO;
/* Force no tty */ /* Force no tty */
if (no_tty_flag || muxclient_command != 0) if (options.request_tty == REQUEST_TTY_NO || muxclient_command != 0)
tty_flag = 0; tty_flag = 0;
/* Do not allocate a tty if stdin is not a tty. */ /* Do not allocate a tty if stdin is not a tty. */
if ((!isatty(fileno(stdin)) || stdin_null_flag) && !force_tty_flag) { if ((!isatty(fileno(stdin)) || stdin_null_flag) &&
options.request_tty != REQUEST_TTY_FORCE) {
if (tty_flag) if (tty_flag)
logit("Pseudo-terminal will not be allocated because " logit("Pseudo-terminal will not be allocated because "
"stdin is not a terminal."); "stdin is not a terminal.");
@ -946,8 +950,7 @@ control_persist_detach(void)
/* Parent: set up mux slave to connect to backgrounded master */ /* Parent: set up mux slave to connect to backgrounded master */
debug2("%s: background process is %ld", __func__, (long)pid); debug2("%s: background process is %ld", __func__, (long)pid);
stdin_null_flag = ostdin_null_flag; stdin_null_flag = ostdin_null_flag;
no_shell_flag = ono_shell_flag; options.request_tty = orequest_tty;
no_tty_flag = ono_tty_flag;
tty_flag = otty_flag; tty_flag = otty_flag;
close(muxserver_sock); close(muxserver_sock);
muxserver_sock = -1; muxserver_sock = -1;
@ -1394,11 +1397,11 @@ ssh_session2(void)
if (options.control_persist && muxserver_sock != -1) { if (options.control_persist && muxserver_sock != -1) {
ostdin_null_flag = stdin_null_flag; ostdin_null_flag = stdin_null_flag;
ono_shell_flag = no_shell_flag; ono_shell_flag = no_shell_flag;
ono_tty_flag = no_tty_flag; orequest_tty = options.request_tty;
otty_flag = tty_flag; otty_flag = tty_flag;
stdin_null_flag = 1; stdin_null_flag = 1;
no_shell_flag = 1; no_shell_flag = 1;
no_tty_flag = 1; options.request_tty == REQUEST_TTY_NO;
tty_flag = 0; tty_flag = 0;
if (!fork_after_authentication_flag) if (!fork_after_authentication_flag)
need_controlpersist_detach = 1; need_controlpersist_detach = 1;

View File

@ -33,7 +33,7 @@
.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
.\" .\"
.\" $OpenBSD: ssh_config.5,v 1.148 2011/05/06 21:31:38 djm Exp $ .\" $OpenBSD: ssh_config.5,v 1.149 2011/05/06 21:34:32 djm Exp $
.Dd $Mdocdate: May 6 2011 $ .Dd $Mdocdate: May 6 2011 $
.Dt SSH_CONFIG 5 .Dt SSH_CONFIG 5
.Os .Os
@ -959,6 +959,23 @@ will only succeed if the server's
.Cm GatewayPorts .Cm GatewayPorts
option is enabled (see option is enabled (see
.Xr sshd_config 5 ) . .Xr sshd_config 5 ) .
.It Cm RequestTTY
Specifies whether to request a pseudo-tty for the session.
The argument may be one of:
.Dq no
(never request a TTY),
.Dq yes
(always request a TTY when standard input is a TTY),
.Dq force
(always request a TTY) or
.Dq auto
(request a TTY when opening a login session).
This option mirrors the
.Fl t
and
.Fl T
flags for
.Xr ssh 1 .
.It Cm RhostsRSAAuthentication .It Cm RhostsRSAAuthentication
Specifies whether to try rhosts based authentication with RSA host Specifies whether to try rhosts based authentication with RSA host
authentication. authentication.