PERFORCE change 196390 for review

Catalin Nicutar cnicutar at FreeBSD.org
Tue Jul 19 10:40:59 UTC 2011


http://p4web.freebsd.org/@@196390?ac=10

Change 196390 by cnicutar at cnicutar_cronos on 2011/07/19 10:40:36

	Add TCP UTO support to ssh and sshd.

Affected files ...

.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/readconf.c#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/readconf.h#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/servconf.c#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/servconf.h#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh.1#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh.c#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh_config.5#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshconnect.c#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshd.c#2 edit
.. //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshd_config.5#2 edit

Differences ...

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/readconf.c#2 (text+ko) ====

@@ -134,7 +134,7 @@
 	oSendEnv, oControlPath, oControlMaster, oHashKnownHosts,
 	oTunnel, oTunnelDevice, oLocalCommand, oPermitLocalCommand,
 	oVisualHostKey, oUseRoaming, oZeroKnowledgePasswordAuthentication,
-	oVersionAddendum,
+	oVersionAddendum, oUserTimeout,
 	oDeprecated, oUnsupported
 } OpCodes;
 
@@ -222,6 +222,7 @@
 	{ "nohostauthenticationforlocalhost", oNoHostAuthenticationForLocalhost },
 	{ "rekeylimit", oRekeyLimit },
 	{ "connecttimeout", oConnectTimeout },
+	{ "usertimeout", oUserTimeout },
 	{ "addressfamily", oAddressFamily },
 	{ "serveraliveinterval", oServerAliveInterval },
 	{ "serveralivecountmax", oServerAliveCountMax },
@@ -396,6 +397,10 @@
 			*intptr = value;
 		break;
 
+	case oUserTimeout:
+		intptr = &options->user_timeout;
+		goto parse_time;
+
 	case oForwardAgent:
 		intptr = &options->forward_agent;
 parse_flag:
@@ -1055,6 +1060,7 @@
 	options->address_family = -1;
 	options->connection_attempts = -1;
 	options->connection_timeout = -1;
+	options->user_timeout = -1;
 	options->number_of_password_prompts = -1;
 	options->cipher = -1;
 	options->ciphers = NULL;

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/readconf.h#2 (text+ko) ====

@@ -65,6 +65,7 @@
 					 * giving up */
 	int     connection_timeout;	/* Max time (seconds) before
 					 * aborting connection attempt */
+	int	user_timeout;	/* Timeout value (seconds) sent to server. */
 	int     number_of_password_prompts;	/* Max number of password
 						 * prompts. */
 	int     cipher;		/* Cipher to use. */

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/servconf.c#2 (text+ko) ====

@@ -105,6 +105,7 @@
 	options->compression = -1;
 	options->allow_tcp_forwarding = -1;
 	options->allow_agent_forwarding = -1;
+	options->allow_user_timeout = -1;
 	options->num_allow_users = 0;
 	options->num_deny_users = 0;
 	options->num_allow_groups = 0;
@@ -310,7 +311,7 @@
 	sClientAliveCountMax, sAuthorizedKeysFile, sAuthorizedKeysFile2,
 	sGssAuthentication, sGssCleanupCreds, sAcceptEnv, sPermitTunnel,
 	sMatch, sPermitOpen, sForceCommand, sChrootDirectory,
-	sUsePrivilegeSeparation, sAllowAgentForwarding,
+	sUsePrivilegeSeparation, sAllowAgentForwarding, sAllowUserTimeout,
 	sZeroKnowledgePasswordAuthentication, sHostCertificate,
 	sRevokedKeys, sTrustedUserCAKeys,
 	sVersionAddendum,
@@ -405,6 +406,7 @@
 	{ "keepalive", sTCPKeepAlive, SSHCFG_GLOBAL },	/* obsolete alias */
 	{ "allowtcpforwarding", sAllowTcpForwarding, SSHCFG_ALL },
 	{ "allowagentforwarding", sAllowAgentForwarding, SSHCFG_ALL },
+	{ "allowusertimeout", sAllowUserTimeout, SSHCFG_ALL },
 	{ "allowusers", sAllowUsers, SSHCFG_GLOBAL },
 	{ "denyusers", sDenyUsers, SSHCFG_GLOBAL },
 	{ "allowgroups", sAllowGroups, SSHCFG_GLOBAL },
@@ -1066,6 +1068,10 @@
 	case sAllowAgentForwarding:
 		intptr = &options->allow_agent_forwarding;
 		goto parse_flag;
+	
+	case sAllowUserTimeout:
+		intptr = &options->allow_user_timeout;
+		goto parse_flag;
 
 	case sUsePrivilegeSeparation:
 		intptr = &use_privsep;

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/servconf.h#2 (text+ko) ====

@@ -108,6 +108,7 @@
 	int     compression;	/* If true, compression is allowed */
 	int	allow_tcp_forwarding;
 	int	allow_agent_forwarding;
+	int	allow_user_timeout;	/* Accept the client timeout if true. */
 	u_int num_allow_users;
 	char   *allow_users[MAX_ALLOW_USERS];
 	u_int num_deny_users;

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh.1#2 (text+ko) ====

@@ -36,7 +36,7 @@
 .\"
 .\" $OpenBSD: ssh.1,v 1.302 2010/03/05 10:28:21 djm Exp $
 .\" $FreeBSD: src/crypto/openssh/ssh.1,v 1.38.2.3 2010/06/02 10:28:26 des Exp $
-.Dd March 5, 2010
+.Dd July 19, 2011
 .Dt SSH 1
 .Os
 .Sh NAME
@@ -79,6 +79,7 @@
 .Sm on
 .Oc
 .Op Fl S Ar ctl_path
+.Op Fl u Ar timeout
 .Op Fl W Ar host : Ns Ar port
 .Oo Fl w Ar local_tun Ns
 .Op : Ns Ar remote_tun Oc
@@ -493,6 +494,7 @@
 .It TunnelDevice
 .It UsePrivilegedPort
 .It User
+.It UserTimeout
 .It UserKnownHostsFile
 .It VerifyHostKeyDNS
 .It VersionAddendum
@@ -586,6 +588,14 @@
 options force tty allocation, even if
 .Nm
 has no local tty.
+.It Fl u Ar timeout
+Sets the requested timeout (UTO) for the connection.
+If the option is accepted by the server, the connection will be kept for
+the specified time in the absence of network connectivity.
+.Pp
+This option can also be enabled using the UserTimeout directive as described
+in
+.Xr ssh_config 5 .
 .It Fl V
 Display the version number and exit.
 .It Fl v

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh.c#2 (text+ko) ====

@@ -69,6 +69,7 @@
 #include <unistd.h>
 
 #include <netinet/in.h>
+#include <netinet/tcp.h>
 #include <arpa/inet.h>
 
 #include <openssl/evp.h>
@@ -192,7 +193,7 @@
 "           [-L [bind_address:]port:host:hostport]\n"
 "           [-l login_name] [-m mac_spec] [-O ctl_cmd] [-o option] [-p port]\n"
 "           [-R [bind_address:]port:host:hostport] [-S ctl_path]\n"
-"           [-W host:port] [-w local_tun[:remote_tun]]\n"
+"           [-u timeout] [-W host:port] [-w local_tun[:remote_tun]]\n"
 "           [user@]hostname [command]\n"
 	);
 	exit(255);
@@ -282,7 +283,7 @@
 	argv0 = av[0];
 
  again:
-	while ((opt = getopt(ac, av, "1246ab:c:e:fgi:kl:m:no:p:qstvx"
+	while ((opt = getopt(ac, av, "1246ab:c:e:fgi:kl:m:no:p:qstu:vx"
 	    "ACD:F:I:KL:MNO:PR:S:TVw:W:XYy")) != -1) {
 		switch (opt) {
 		case '1':
@@ -375,6 +376,11 @@
 				force_tty_flag = 1;
 			tty_flag = 1;
 			break;
+		case 'u':
+			options.user_timeout = convtime(optarg);
+			if (options.user_timeout == -1)
+				fatal("Invalid User Timeout value");
+			break;
 		case 'v':
 			if (debug_flag == 0) {
 				debug_flag = 1;
@@ -844,6 +850,15 @@
 	/* Log into the remote system.  Never returns if the login fails. */
 	ssh_login(&sensitive_data, host, (struct sockaddr *)&hostaddr,
 	    pw, timeout_ms);
+	
+	/*
+	 * Attempt to send the option after authenticating. If the server
+	 * didn't record it at SYN, it should now.
+	 */
+	if (options.user_timeout && setsockopt(packet_get_connection_in(),
+	    IPPROTO_TCP, TCP_SNDUTO_TIMEOUT, &options.user_timeout,
+	    sizeof(options.user_timeout)))
+		error("setsockopt TCP_SNDUTO_TIMEOUT: %.100s", strerror(errno));
 
 	/* We no longer need the private host keys.  Clear them now. */
 	if (sensitive_data.nkeys != 0) {

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/ssh_config.5#2 (text+ko) ====

@@ -36,7 +36,7 @@
 .\"
 .\" $OpenBSD: ssh_config.5,v 1.129 2010/03/05 10:28:21 djm Exp $
 .\" $FreeBSD: src/crypto/openssh/ssh_config.5,v 1.26.2.3 2010/06/02 10:28:26 des Exp $
-.Dd March 5, 2010
+.Dd July 19, 2011
 .Dt SSH_CONFIG 5
 .Os
 .Sh NAME
@@ -1051,6 +1051,20 @@
 This can be useful when a different user name is used on different machines.
 This saves the trouble of
 having to remember to give the user name on the command line.
+.It Cm UserTimeout
+Specifies the UserTimeout (TCP UTO) for this connection.
+If the server accepts this option, the connection will be kept for the
+specified time in the absence of network connectivity.
+.Pp
+Usually a server will only allow certain users to use this option, due to
+the security risks involved.
+.Pp
+The values that can be specified are subject to
+.Dv net.inet.tcp.uto.min_timeout
+and 
+.Dv net.inet.tcp.uto.max_timeout .
+.Pp
+By default no timeout is used.
 .It Cm UserKnownHostsFile
 Specifies a file to use for the user
 host key database instead of

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshconnect.c#2 (text+ko) ====

@@ -25,6 +25,7 @@
 #endif
 
 #include <netinet/in.h>
+#include <netinet/tcp.h>
 #include <arpa/inet.h>
 
 #include <ctype.h>
@@ -375,6 +376,17 @@
 				/* Any error is already output */
 				continue;
 
+			/*
+			 * Attempt to set the UTO value before connecting.
+			 * Some hosts might not accept it if we send it later.
+			 */
+			if (options.user_timeout > 0 &&
+			    setsockopt(sock, IPPROTO_TCP, TCP_SNDUTO_TIMEOUT,
+			    &options.user_timeout,
+			    sizeof(options.user_timeout)) < 0)
+				error("setsockopt TCP_SNDUTO_TIMEOUT: %.100s",
+				    strerror(errno));
+
 			if (timeout_connect(sock, ai->ai_addr, ai->ai_addrlen,
 			    timeout_ms) >= 0) {
 				/* Successful connection. */

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshd.c#2 (text+ko) ====

@@ -59,6 +59,8 @@
 #include "openbsd-compat/sys-queue.h"
 #include <sys/wait.h>
 
+#include <netinet/tcp.h>
+
 #include <errno.h>
 #include <fcntl.h>
 #include <netdb.h>
@@ -2015,6 +2017,17 @@
 		startup_pipe = -1;
 	}
 
+	/*
+	 * After authentication it's safe to enable User Timeout. The
+	 * connection will not be dropped for this period of time even if
+	 * the client stays silent (doesn't ACK our data).
+	 */
+	if (options.allow_user_timeout && packet_connection_is_on_socket() &&
+	    setsockopt(sock_in, IPPROTO_TCP, TCP_RCVUTO_TIMEOUT, &on,
+	    sizeof(on)) < 0)
+		error("setsockopt TCP_RCVUTO_TIMEOUT: %.100s", strerror(errno));
+
+
 #ifdef SSH_AUDIT_EVENTS
 	audit_event(SSH_AUTH_SUCCESS);
 #endif

==== //depot/projects/soc2011/cnicutar_tcputo_8/src/crypto/openssh/sshd_config.5#2 (text+ko) ====

@@ -36,7 +36,7 @@
 .\"
 .\" $OpenBSD: sshd_config.5,v 1.120 2010/03/04 23:17:25 djm Exp $
 .\" $FreeBSD: src/crypto/openssh/sshd_config.5,v 1.32.2.3 2010/06/02 10:28:26 des Exp $
-.Dd March 4, 2010
+.Dd July 19, 2011
 .Dt SSHD_CONFIG 5
 .Os
 .Sh NAME
@@ -153,6 +153,22 @@
 in
 .Xr ssh_config 5
 for more information on patterns.
+.It Cm AllowUserTimeout
+This directive specifies that the UserTimeout requested by the client will
+be accepted after authentication.
+When a UserTimeout is accepted TCP will not drop the connection for the
+specified time even if the client remains silent (doesn't ACK data).
+.Pp
+The values that can be accepted are subject to the system-wide
+.Dv net.inet.tcp.uto.min_timeout
+and 
+.Dv net.inet.tcp.uto.max_timeout .
+.Pp
+A server should only allow trusted users to use this option, due to
+the security risks involved.
+.Pp
+The default value is
+.Dq no .
 .It Cm AuthorizedKeysFile
 Specifies the file that contains the public keys that can be used
 for user authentication.


More information about the p4-projects mailing list