diff options
author | Markus Friedl <markus@cvs.openbsd.org> | 2001-04-30 11:18:53 +0000 |
---|---|---|
committer | Markus Friedl <markus@cvs.openbsd.org> | 2001-04-30 11:18:53 +0000 |
commit | 3dcc04883104af8c3a320b19c2871353d158608f (patch) | |
tree | b61f7a84142437e4afa44a3876cc46255e2e0d99 | |
parent | 18595b28d6594317f453f679cad3b0bf7cb6a644 (diff) |
implement 'ssh -b bind_address' like 'telnet -b'
-rw-r--r-- | usr.bin/ssh/readconf.c | 10 | ||||
-rw-r--r-- | usr.bin/ssh/readconf.h | 3 | ||||
-rw-r--r-- | usr.bin/ssh/ssh.1 | 13 | ||||
-rw-r--r-- | usr.bin/ssh/ssh.c | 8 | ||||
-rw-r--r-- | usr.bin/ssh/sshconnect.c | 48 |
5 files changed, 64 insertions, 18 deletions
diff --git a/usr.bin/ssh/readconf.c b/usr.bin/ssh/readconf.c index cbb93b7b061..7c7a4ebab4c 100644 --- a/usr.bin/ssh/readconf.c +++ b/usr.bin/ssh/readconf.c @@ -12,7 +12,7 @@ */ #include "includes.h" -RCSID("$OpenBSD: readconf.c,v 1.76 2001/04/17 10:53:25 markus Exp $"); +RCSID("$OpenBSD: readconf.c,v 1.77 2001/04/30 11:18:51 markus Exp $"); #include "ssh.h" #include "xmalloc.h" @@ -111,7 +111,7 @@ typedef enum { oGlobalKnownHostsFile2, oUserKnownHostsFile2, oPubkeyAuthentication, oKbdInteractiveAuthentication, oKbdInteractiveDevices, oHostKeyAlias, oDynamicForward, oPreferredAuthentications, oHostbasedAuthentication, - oHostKeyAlgorithms + oHostKeyAlgorithms, oBindAddress } OpCodes; /* Textual representations of the tokens. */ @@ -177,6 +177,7 @@ static struct { { "dynamicforward", oDynamicForward }, { "preferredauthentications", oPreferredAuthentications }, { "hostkeyalgorithms", oHostKeyAlgorithms }, + { "bindaddress", oBindAddress }, { NULL, 0 } }; @@ -457,6 +458,10 @@ parse_string: charptr = &options->preferred_authentications; goto parse_string; + case oBindAddress: + charptr = &options->bind_address; + goto parse_string; + case oProxyCommand: charptr = &options->proxy_command; string = xstrdup(""); @@ -759,6 +764,7 @@ initialize_options(Options * options) options->num_remote_forwards = 0; options->log_level = (LogLevel) - 1; options->preferred_authentications = NULL; + options->bind_address = NULL; } /* diff --git a/usr.bin/ssh/readconf.h b/usr.bin/ssh/readconf.h index 9e943f905c5..4b20c93bf5d 100644 --- a/usr.bin/ssh/readconf.h +++ b/usr.bin/ssh/readconf.h @@ -11,7 +11,7 @@ * called by a name other than "ssh" or "Secure Shell". */ -/* RCSID("$OpenBSD: readconf.h,v 1.30 2001/04/17 10:53:25 markus Exp $"); */ +/* RCSID("$OpenBSD: readconf.h,v 1.31 2001/04/30 11:18:52 markus Exp $"); */ #ifndef READCONF_H #define READCONF_H @@ -85,6 +85,7 @@ typedef struct { char *system_hostfile2; char *user_hostfile2; char *preferred_authentications; + char *bind_address; /* local socket address for connection to sshd */ int num_identity_files; /* Number of files for RSA/DSA identities. */ char *identity_files[SSH_MAX_IDENTITY_FILES]; diff --git a/usr.bin/ssh/ssh.1 b/usr.bin/ssh/ssh.1 index 0d26197b693..6f4110e4189 100644 --- a/usr.bin/ssh/ssh.1 +++ b/usr.bin/ssh/ssh.1 @@ -34,7 +34,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.\" $OpenBSD: ssh.1,v 1.107 2001/04/22 23:58:36 markus Exp $ +.\" $OpenBSD: ssh.1,v 1.108 2001/04/30 11:18:52 markus Exp $ .Dd September 25, 1999 .Dt SSH 1 .Os @@ -49,6 +49,7 @@ .Pp .Nm ssh .Op Fl afgknqstvxACNPTX1246 +.Op Fl b Ar bind_address .Op Fl c Ar cipher_spec .Op Fl e Ar escape_char .Op Fl i Ar identity_file @@ -383,6 +384,9 @@ Disables forwarding of the authentication agent connection. .It Fl A Enables forwarding of the authentication agent connection. This can also be specified on a per-host basis in a configuration file. +.It Fl b Ar bind_address +Specify the interface to transmit from on machines with multiple +interfaces or aliased addresses. .It Fl c Ar blowfish|3des Selects the cipher to use for encrypting the session. .Ar 3des @@ -667,6 +671,13 @@ or .Dq no . The default is .Dq no . +.It Cm BindAddress +Specify the interface to transmit from on machines with multiple +interfaces or aliased addresses. +Note that this option does not work if +.Cm UsePrivilegedPort +is set to +.Dq yes . .It Cm CheckHostIP If this flag is set to .Dq yes , diff --git a/usr.bin/ssh/ssh.c b/usr.bin/ssh/ssh.c index b9a56c938bc..32092b888b6 100644 --- a/usr.bin/ssh/ssh.c +++ b/usr.bin/ssh/ssh.c @@ -39,7 +39,7 @@ */ #include "includes.h" -RCSID("$OpenBSD: ssh.c,v 1.116 2001/04/17 12:55:04 markus Exp $"); +RCSID("$OpenBSD: ssh.c,v 1.117 2001/04/30 11:18:52 markus Exp $"); #include <openssl/evp.h> #include <openssl/err.h> @@ -183,6 +183,7 @@ usage(void) fprintf(stderr, " -6 Use IPv6 only.\n"); fprintf(stderr, " -o 'option' Process the option as if it was read from a configuration file.\n"); fprintf(stderr, " -s Invoke command (mandatory) as SSH2 subsystem.\n"); + fprintf(stderr, " -b Local IP address.\n"); exit(1); } @@ -305,7 +306,7 @@ main(int ac, char **av) opt = av[optind][1]; if (!opt) usage(); - if (strchr("eilcmpLRDo", opt)) { /* options with arguments */ + if (strchr("eilcmpbLRDo", opt)) { /* options with arguments */ optarg = av[optind] + 2; if (strcmp(optarg, "") == 0) { if (optind >= ac - 1) @@ -504,6 +505,9 @@ main(int ac, char **av) case 's': subsystem_flag = 1; break; + case 'b': + options.bind_address = optarg; + break; default: usage(); } diff --git a/usr.bin/ssh/sshconnect.c b/usr.bin/ssh/sshconnect.c index 31d06964bb0..39a661a6602 100644 --- a/usr.bin/ssh/sshconnect.c +++ b/usr.bin/ssh/sshconnect.c @@ -13,7 +13,7 @@ */ #include "includes.h" -RCSID("$OpenBSD: sshconnect.c,v 1.104 2001/04/12 19:15:25 markus Exp $"); +RCSID("$OpenBSD: sshconnect.c,v 1.105 2001/04/30 11:18:52 markus Exp $"); #include <openssl/bn.h> @@ -147,7 +147,8 @@ ssh_proxy_connect(const char *host, u_short port, struct passwd *pw, int ssh_create_socket(struct passwd *pw, int privileged, int family) { - int sock; + int sock, gaierr; + struct addrinfo hints, *res; /* * If we are running as root and want to connect to a privileged @@ -160,17 +161,40 @@ ssh_create_socket(struct passwd *pw, int privileged, int family) error("rresvport: af=%d %.100s", family, strerror(errno)); else debug("Allocated local port %d.", p); - } else { - /* - * Just create an ordinary socket on arbitrary port. We use - * the user's uid to create the socket. - */ - temporarily_use_uid(pw); - sock = socket(family, SOCK_STREAM, 0); - if (sock < 0) - error("socket: %.100s", strerror(errno)); - restore_uid(); + return sock; + } + /* + * Just create an ordinary socket on arbitrary port. We use + * the user's uid to create the socket. + */ + temporarily_use_uid(pw); + sock = socket(family, SOCK_STREAM, 0); + if (sock < 0) + error("socket: %.100s", strerror(errno)); + restore_uid(); + + /* Bind the socket to an alternative local IP address */ + if (options.bind_address == NULL) + return sock; + + memset(&hints, 0, sizeof(hints)); + hints.ai_family = IPv4or6; + hints.ai_socktype = SOCK_STREAM; + hints.ai_flags = AI_PASSIVE; + gaierr = getaddrinfo(options.bind_address, "0", &hints, &res); + if (gaierr) { + error("getaddrinfo: %s: %s", options.bind_address, + gai_strerror(gaierr)); + close(sock); + return -1; + } + if (bind(sock, res->ai_addr, res->ai_addrlen) < 0) { + error("bind: %s: %s", options.bind_address, strerror(errno)); + close(sock); + freeaddrinfo(res); + return -1; } + freeaddrinfo(res); return sock; } |