예제 #1
0
/*
 * Starts a dialog with the server, and authenticates the current user on the
 * server.  This does not need any extra privileges.  The basic connection
 * to the server must already have been established before this is called.
 * If login fails, this function prints an error and never returns.
 * This function does not require super-user privileges.
 */
void
ssh_login(Sensitive *sensitive, const char *orighost,
    struct sockaddr *hostaddr, u_short port, struct passwd *pw, int timeout_ms)
{
	char *host;
	char *server_user, *local_user;

	local_user = xstrdup(pw->pw_name);
	server_user = options.user ? options.user : local_user;

	/* Convert the user-supplied hostname into all lowercase. */
	host = xstrdup(orighost);
	lowercase(host);

	/* Exchange protocol version identification strings with the server. */
	ssh_exchange_identification(timeout_ms);

	/* Put the connection into non-blocking mode. */
	packet_set_nonblocking();

	/* key exchange */
	/* authenticate user */
	debug("Authenticating to %s:%d as '%s'", host, port, server_user);
	ssh_kex2(host, hostaddr, port);
	ssh_userauth2(local_user, server_user, host, sensitive);
	free(local_user);
}
예제 #2
0
/*
 * Starts a dialog with the server, and authenticates the current user on the
 * server.  This does not need any extra privileges.  The basic connection
 * to the server must already have been established before this is called.
 * If login fails, this function prints an error and never returns.
 * This function does not require super-user privileges.
 */
void
ssh_login(Sensitive *sensitive, const char *orighost,
    struct sockaddr *hostaddr, u_short port, struct passwd *pw, int timeout_ms)
{
	char *host, *cp;
	char *server_user, *local_user;

	local_user = xstrdup(pw->pw_name);
	server_user = options.user ? options.user : local_user;

	/* Convert the user-supplied hostname into all lowercase. */
	host = xstrdup(orighost);
	for (cp = host; *cp; cp++)
		if (isupper(*cp))
			*cp = (char)tolower(*cp);

	/* Exchange protocol version identification strings with the server. */
	ssh_exchange_identification(timeout_ms);

	/* Put the connection into non-blocking mode. */
	packet_set_nonblocking();

	/* key exchange */
	/* authenticate user */
	if (compat20) {
		ssh_kex2(host, hostaddr, port);
		ssh_userauth2(local_user, server_user, host, sensitive);
	} else {
		ssh_kex(host, hostaddr);
		ssh_userauth1(local_user, server_user, host, sensitive);
	}
	xfree(local_user);
}
예제 #3
0
/*
 * Starts a dialog with the server, and authenticates the current user on the
 * server.  This does not need any extra privileges.  The basic connection
 * to the server must already have been established before this is called.
 * If login fails, this function prints an error and never returns.
 * This function does not require super-user privileges.
 */
void
ssh_login(Sensitive *sensitive, const char *orighost,
    struct sockaddr *hostaddr, u_short port, struct passwd *pw, int timeout_ms)
{
	char *host;
	char *server_user, *local_user;

	local_user = xstrdup(pw->pw_name);
	server_user = options.user ? options.user : local_user;

	/* Convert the user-supplied hostname into all lowercase. */
	host = xstrdup(orighost);
	lowercase(host);

	/* Exchange protocol version identification strings with the server. */
	ssh_exchange_identification(timeout_ms);

	/* Put the connection into non-blocking mode. */
	packet_set_nonblocking();

	/* key exchange */
	/* authenticate user */
	if (compat20) {
		ssh_kex2(host, hostaddr, port);
		ssh_userauth2(local_user, server_user, host, sensitive);
	} else {
#ifdef WITH_SSH1
		ssh_kex(host, hostaddr);
		ssh_userauth1(local_user, server_user, host, sensitive);
#else
		fatal("ssh1 is not unsupported");
#endif
	}
	free(local_user);
}
예제 #4
0
static int
roaming_resume(void)
{
	u_int64_t recv_bytes;
	char *str = NULL, *kexlist = NULL, *c;
	int i, type;
	int timeout_ms = options.connection_timeout * 1000;
	u_int len;
	u_int32_t rnd = 0;

	resume_in_progress = 1;

	/* Exchange banners */
	ssh_exchange_identification(timeout_ms);
	packet_set_nonblocking();

	/* Send a kexinit message with [email protected] as only kex algo */
	packet_start(SSH2_MSG_KEXINIT);
	for (i = 0; i < KEX_COOKIE_LEN; i++) {
		if (i % 4 == 0)
			rnd = arc4random();
		packet_put_char(rnd & 0xff);
		rnd >>= 8;
	}
	packet_put_cstring(KEX_RESUME);
	for (i = 1; i < PROPOSAL_MAX; i++) {
		/* kex algorithm added so start with i=1 and not 0 */
		packet_put_cstring(""); /* Not used when we resume */
	}
	packet_put_char(1); /* first kex_packet follows */
	packet_put_int(0); /* reserved */
	packet_send();

	/* Assume that [email protected] will be accepted */
	packet_start(SSH2_MSG_KEX_ROAMING_RESUME);
	packet_put_int(roaming_id);
	packet_send();

	/* Read the server's kexinit and check for [email protected] */
	if ((type = packet_read()) != SSH2_MSG_KEXINIT) {
		debug("expected kexinit on resume, got %d", type);
		goto fail;
	}
	for (i = 0; i < KEX_COOKIE_LEN; i++)
		(void)packet_get_char();
	kexlist = packet_get_string(&len);
	if (!kexlist
	    || (str = match_list(KEX_RESUME, kexlist, NULL)) == NULL) {
		debug("server doesn't allow resume");
		goto fail;
	}
	free(str);
	for (i = 1; i < PROPOSAL_MAX; i++) {
		/* kex algorithm taken care of so start with i=1 and not 0 */
		free(packet_get_string(&len));
	}
	i = packet_get_char(); /* first_kex_packet_follows */
	if (i && (c = strchr(kexlist, ',')))
		*c = 0;
	if (i && strcmp(kexlist, KEX_RESUME)) {
		debug("server's kex guess (%s) was wrong, skipping", kexlist);
		(void)packet_read(); /* Wrong guess - discard packet */
	}

	/*
	 * Read the ROAMING_AUTH_REQUIRED challenge from the server and
	 * send ROAMING_AUTH
	 */
	if ((type = packet_read()) != SSH2_MSG_KEX_ROAMING_AUTH_REQUIRED) {
		debug("expected roaming_auth_required, got %d", type);
		goto fail;
	}
	roaming_auth_required();

	/* Read ROAMING_AUTH_OK from the server */
	if ((type = packet_read()) != SSH2_MSG_KEX_ROAMING_AUTH_OK) {
		debug("expected roaming_auth_ok, got %d", type);
		goto fail;
	}
	recv_bytes = packet_get_int64() ^ oldkey2;
	debug("Peer received %llu bytes", (unsigned long long)recv_bytes);
	resend_bytes(packet_get_connection_out(), &recv_bytes);

	resume_in_progress = 0;

	session_resumed = 1; /* Tell clientloop */

	return 0;

fail:
	free(kexlist);
	if (packet_get_connection_in() == packet_get_connection_out())
		close(packet_get_connection_in());
	else {
		close(packet_get_connection_in());
		close(packet_get_connection_out());
	}
	return 1;
}