Bugzilla – Attachment 3080 Details for
Bug 2784
Add native support for routing domains / VRF
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
rdomain support for ssh client connect socket
0001-ssh-add-routing-domain-support.patch (text/plain), 9.06 KB, created by
Luca Boccassi
on 2017-10-28 03:23:35 AEDT
(
hide
)
Description:
rdomain support for ssh client connect socket
Filename:
MIME Type:
Creator:
Luca Boccassi
Created:
2017-10-28 03:23:35 AEDT
Size:
9.06 KB
patch
obsolete
>From 7c74a6654e3194c68e606d0f4885c7acc683fec4 Mon Sep 17 00:00:00 2001 >From: Luca Boccassi <luca.boccassi@gmail.com> >Date: Mon, 23 Oct 2017 17:41:50 +0100 >Subject: [PATCH 1/3] ssh: add routing domain support > >Add support for BSD routing domains to ssh via a new -r command line >option and a RDomain ssh_config file option like for sshd. >This will apply to the connecting socket. >--- > misc.c | 36 ++++++++++++++++++++++++++++++++++++ > misc.h | 1 + > openbsd-compat/port-net.c | 7 ++++++- > readconf.c | 9 ++++++++- > readconf.h | 2 ++ > servconf.c | 36 ------------------------------------ > ssh.1 | 6 ++++++ > ssh.c | 12 ++++++++++-- > ssh_config.5 | 4 ++++ > sshconnect.c | 6 ++++++ > 10 files changed, 79 insertions(+), 40 deletions(-) > >diff --git a/misc.c b/misc.c >index 2369361b..16845b70 100644 >--- a/misc.c >+++ b/misc.c >@@ -234,6 +234,42 @@ set_rdomain(int fd, const char *name) > #endif > } > >+/* Returns nonzero if the routing domain name is valid */ >+int >+valid_rdomain(const char *name) >+{ >+#if defined(HAVE_SYS_VALID_RDOMAIN) >+ return sys_valid_rdomain(name); >+#elif defined(__OpenBSD__) >+ const char *errstr; >+ long long num; >+ struct rt_tableinfo info; >+ int mib[6]; >+ size_t miblen = sizeof(mib); >+ >+ if (name == NULL) >+ return 1; >+ >+ num = strtonum(name, 0, 255, &errstr); >+ if (errstr != NULL) >+ return 0; >+ >+ /* Check whether the table actually exists */ >+ memset(mib, 0, sizeof(mib)); >+ mib[0] = CTL_NET; >+ mib[1] = PF_ROUTE; >+ mib[4] = NET_RT_TABLE; >+ mib[5] = (int)num; >+ if (sysctl(mib, 6, &info, &miblen, NULL, 0) == -1) >+ return 0; >+ >+ return 1; >+#else /* defined(__OpenBSD__) */ >+ error("Routing domains are not supported on this platform"); >+ return 0; >+#endif >+} >+ > /* Characters considered whitespace in strsep calls. */ > #define WHITESPACE " \t\r\n" > #define QUOTE "\"" >diff --git a/misc.h b/misc.h >index 5ad30ce3..e2f7fb69 100644 >--- a/misc.h >+++ b/misc.h >@@ -51,6 +51,7 @@ void set_nodelay(int); > int set_reuseaddr(int); > char *get_rdomain(int); > int set_rdomain(int, const char *); >+int valid_rdomain(const char *name); > int a2port(const char *); > int a2tun(const char *, int *); > char *put_host_port(const char *, u_short); >diff --git a/openbsd-compat/port-net.c b/openbsd-compat/port-net.c >index 7050629c..d0fceb8b 100644 >--- a/openbsd-compat/port-net.c >+++ b/openbsd-compat/port-net.c >@@ -78,6 +78,9 @@ sys_valid_rdomain(const char *name) > { > int fd; > >+ if (!strlen(name)) >+ return 0; >+ > /* > * This is a pretty crappy way to test. It would be better to > * check whether "name" represents a VRF device, but apparently >@@ -87,6 +90,8 @@ sys_valid_rdomain(const char *name) > return 0; > if (setsockopt(fd, SOL_SOCKET, SO_BINDTODEVICE, > name, strlen(name)) == -1) { >+ error("%s: setsockopt(%d, SO_BINDTODEVICE, %s): %s", >+ __func__, fd, name, strerror(errno)); > close(fd); > return 0; > } >@@ -108,7 +113,7 @@ sys_set_rdomain(int fd, const char *name) > } > > int >-valid_rdomain(const char *name) >+sys_valid_rdomain(const char *name) > { > return 0; > } >diff --git a/readconf.c b/readconf.c >index 63baa7d7..0421aa2d 100644 >--- a/readconf.c >+++ b/readconf.c >@@ -156,7 +156,7 @@ typedef enum { > oPubkeyAuthentication, > oKbdInteractiveAuthentication, oKbdInteractiveDevices, oHostKeyAlias, > oDynamicForward, oPreferredAuthentications, oHostbasedAuthentication, >- oHostKeyAlgorithms, oBindAddress, oPKCS11Provider, >+ oHostKeyAlgorithms, oBindAddress, oPKCS11Provider, oRDomain, > oClearAllForwardings, oNoHostAuthenticationForLocalhost, > oEnableSSHKeysign, oRekeyLimit, oVerifyHostKeyDNS, oConnectTimeout, > oAddressFamily, oGssAuthentication, oGssDelegateCreds, >@@ -305,6 +305,7 @@ static struct { > { "pubkeyacceptedkeytypes", oPubkeyAcceptedKeyTypes }, > { "ignoreunknown", oIgnoreUnknown }, > { "proxyjump", oProxyJump }, >+ { "rdomain", oRDomain }, > > { NULL, oBadOption } > }; >@@ -1645,6 +1646,10 @@ parse_keytypes: > charptr = &options->identity_agent; > goto parse_string; > >+ case oRDomain: >+ charptr = &options->rdomain; >+ goto parse_string; >+ > case oDeprecated: > debug("%s line %d: Deprecated option \"%s\"", > filename, linenum, keyword); >@@ -1845,6 +1850,7 @@ initialize_options(Options * options) > options->update_hostkeys = -1; > options->hostbased_key_types = NULL; > options->pubkey_key_types = NULL; >+ options->rdomain = NULL; > } > > /* >@@ -2534,6 +2540,7 @@ dump_client_config(Options *o, const char *host) > dump_cfg_string(oPubkeyAcceptedKeyTypes, o->pubkey_key_types); > dump_cfg_string(oRevokedHostKeys, o->revoked_host_keys); > dump_cfg_string(oXAuthLocation, o->xauth_location); >+ dump_cfg_string(oRDomain, o->rdomain); > > /* Forwards */ > dump_cfg_forwards(oDynamicForward, o->num_local_forwards, o->local_forwards); >diff --git a/readconf.h b/readconf.h >index 34aad83c..a46f871f 100644 >--- a/readconf.h >+++ b/readconf.h >@@ -163,6 +163,8 @@ typedef struct { > int jump_port; > char *jump_extra; > >+ char *rdomain; /* routing domain to bind to */ >+ > char *ignored_unknown; /* Pattern list of unknown tokens to ignore */ > } Options; > >diff --git a/servconf.c b/servconf.c >index 53d81fb3..c849689d 100644 >--- a/servconf.c >+++ b/servconf.c >@@ -731,42 +731,6 @@ add_one_listen_addr(ServerOptions *options, const char *addr, > options->listen_addrs[i].addrs = aitop; > } > >-/* Returns nonzero if the routing domain name is valid */ >-static int >-valid_rdomain(const char *name) >-{ >-#if defined(HAVE_SYS_VALID_RDOMAIN) >- return sys_valid_rdomain(name); >-#elif defined(__OpenBSD__) >- const char *errstr; >- long long num; >- struct rt_tableinfo info; >- int mib[6]; >- size_t miblen = sizeof(mib); >- >- if (name == NULL) >- return 1; >- >- num = strtonum(name, 0, 255, &errstr); >- if (errstr != NULL) >- return 0; >- >- /* Check whether the table actually exists */ >- memset(mib, 0, sizeof(mib)); >- mib[0] = CTL_NET; >- mib[1] = PF_ROUTE; >- mib[4] = NET_RT_TABLE; >- mib[5] = (int)num; >- if (sysctl(mib, 6, &info, &miblen, NULL, 0) == -1) >- return 0; >- >- return 1; >-#else /* defined(__OpenBSD__) */ >- error("Routing domains are not supported on this platform"); >- return 0; >-#endif >-} >- > /* > * Queue a ListenAddress to be processed once we have all of the Ports > * and AddressFamily options. >diff --git a/ssh.1 b/ssh.1 >index 093f1770..76683364 100644 >--- a/ssh.1 >+++ b/ssh.1 >@@ -45,6 +45,7 @@ > .Bk -words > .Op Fl 46AaCfGgKkMNnqsTtVvXxYy > .Op Fl b Ar bind_address >+.Op Fl r Ar routing_domain > .Op Fl c Ar cipher_spec > .Op Fl D Oo Ar bind_address : Oc Ns Ar port > .Op Fl E Ar log_file >@@ -650,6 +651,11 @@ When used together with > .Ic -O forward > the allocated port will be printed to the standard output. > .Pp >+.It Fl r Ar routing_domain >+Specifies an explicit routing domain (BSD) or VRF (Linux - NOTE: requires cap_net_raw) that is applied to the connection. >+The user session will be bound to this >+.Xr rdomain 4 . >+.Pp > .It Fl S Ar ctl_path > Specifies the location of a control socket for connection sharing, > or the string >diff --git a/ssh.c b/ssh.c >index ae468d28..2c0ee674 100644 >--- a/ssh.c >+++ b/ssh.c >@@ -201,7 +201,7 @@ static void > usage(void) > { > fprintf(stderr, >-"usage: ssh [-46AaCfGgKkMNnqsTtVvXxYy] [-b bind_address] [-c cipher_spec]\n" >+"usage: ssh [-46AaCfGgKkMNnqsTtVvXxYy] [-b bind_address] [-r routing_domain] [-c cipher_spec]\n" > " [-D [bind_address:]port] [-E log_file] [-e escape_char]\n" > " [-F configfile] [-I pkcs11] [-i identity_file]\n" > " [-J [user@]host[:port]] [-L address] [-l login_name] [-m mac_spec]\n" >@@ -614,7 +614,7 @@ main(int ac, char **av) > 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:qr:stvx" > "ACD:E:F:GI:J:KL:MNO:PQ:R:S:TVw:W:XYy")) != -1) { > switch (opt) { > case '1': >@@ -925,6 +925,14 @@ main(int ac, char **av) > case 'b': > options.bind_address = optarg; > break; >+ case 'r': >+ if (!valid_rdomain(optarg)) { >+ fprintf(stderr, "Bad remote routing domain " >+ "'%s'\n", optarg); >+ exit(255); >+ } >+ options.rdomain = optarg; >+ break; > case 'F': > config = optarg; > break; >diff --git a/ssh_config.5 b/ssh_config.5 >index c1bd7df4..cdfcd707 100644 >--- a/ssh_config.5 >+++ b/ssh_config.5 >@@ -1261,6 +1261,10 @@ The argument to this keyword must be > (the default) > or > .Cm no . >+.It Cm RDomain >+Specifies an explicit routing domain (BSD) or VRF (Linux - NOTE: requires cap_net_raw) that is applied to the connection. >+The user session will be bound to this >+.Xr rdomain 4 . > .It Cm RekeyLimit > Specifies the maximum amount of data that may be transmitted before the > session key is renegotiated, optionally followed a maximum amount of >diff --git a/sshconnect.c b/sshconnect.c >index dc7a704d..7578ef17 100644 >--- a/sshconnect.c >+++ b/sshconnect.c >@@ -286,6 +286,12 @@ ssh_create_socket(int privileged, struct addrinfo *ai) > } > fcntl(sock, F_SETFD, FD_CLOEXEC); > >+ if (options.rdomain != NULL && >+ set_rdomain(sock, options.rdomain) == -1) { >+ close(sock); >+ return -1; >+ } >+ > /* Bind the socket to an alternative local IP address */ > if (options.bind_address == NULL && !privileged) > return sock; >-- >2.11.0 >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 2784
:
3061
|
3064
|
3070
|
3071
|
3072
|
3075
|
3076
|
3077
|
3078
|
3079
| 3080 |
3081
|
3082