Bugzilla – Attachment 1251 Details for
Bug 1295
[PATCH] Transparent proxy support on Linux
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Move Linux code to port-linux.c, add OpenBSD pf rdr support
openssh-tranparent-proxy.patch (text/plain), 9.70 KB, created by
Darren Tucker
on 2007-03-12 23:39:15 AEDT
(
hide
)
Description:
Move Linux code to port-linux.c, add OpenBSD pf rdr support
Filename:
MIME Type:
Creator:
Darren Tucker
Created:
2007-03-12 23:39:15 AEDT
Size:
9.70 KB
patch
obsolete
>Index: channels.c >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh/channels.c,v >retrieving revision 1.251 >diff -u -p -r1.251 channels.c >--- channels.c 28 Jan 2007 23:16:28 -0000 1.251 >+++ channels.c 12 Mar 2007 11:51:33 -0000 >@@ -1131,6 +1131,45 @@ channel_decode_socks5(Channel *c, fd_set > return 1; > } > >+/* ARGSUSED */ >+static int >+channel_decode_transparent(Channel *c, fd_set *readset, fd_set *writeset) >+{ >+ int ret; >+ struct sockaddr *sa; >+ >+ if ((sa = lookup_transparent_sock(c->sock)) == NULL) >+ return -1; >+ >+ switch (sa->sa_family) { >+ case AF_INET: >+ c->host_port = ntohs(((struct sockaddr_in *)sa)->sin_port); >+ break; >+ case AF_INET6: >+ c->host_port = ntohs(((struct sockaddr_in6 *)sa)->sin6_port); >+ break; >+ default: >+ debug("channel %d: transparent proxy of address family %d " >+ "not supported", c->self, sa->sa_family); >+ return -1; >+ } >+ >+ ret = getnameinfo(sa, sizeof(*sa), c->path, sizeof(c->path), NULL, 0, >+ NI_NUMERICHOST|NI_NUMERICSERV); >+ if (ret == -1) { >+ error("channel_decode_transparent: getnameinfo: %s", >+ (ret != EAI_SYSTEM) ? gai_strerror(ret) : strerror(errno)); >+ return -1; >+ } >+ >+ debug2("channel %d: dynamic request: transparent host %s port %u", >+ c->self, c->path, c->host_port); >+ c->delayed = 0; >+ c->type = SSH_CHANNEL_OPENING; >+ port_open_helper(c, "direct-tcpip"); >+ return 0; >+} >+ > /* dynamic port forwarding */ > static void > channel_pre_dynamic(Channel *c, fd_set *readset, fd_set *writeset) >@@ -1139,6 +1178,9 @@ channel_pre_dynamic(Channel *c, fd_set * > u_int have; > int ret; > >+ if (channel_decode_transparent(c, readset, writeset) == 0) >+ return; >+ > have = buffer_len(&c->input); > c->delayed = 0; > debug2("channel %d: pre_dynamic: have %d", c->self, have); >Index: configure.ac >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh/configure.ac,v >retrieving revision 1.372 >diff -u -p -r1.372 configure.ac >--- configure.ac 5 Mar 2007 00:51:27 -0000 1.372 >+++ configure.ac 12 Mar 2007 11:59:55 -0000 >@@ -518,6 +518,19 @@ main() { if (NSVersionOfRunTimeLibrary(" > AC_DEFINE(SSH_TUN_PREPEND_AF, 1, > [Prepend the address family to IP tunnel traffic]) > fi >+ # transparent dynamic port forwarding >+ AC_CHECK_HEADERS([linux/netfilter_ipv4.h], [], [], >+ [ #include <limits.h> ]) >+ AC_CHECK_DECL(SO_ORIGINAL_DST, >+ [ >+ TRANSPROXY=netfilter >+ AC_DEFINE(TRANSPARENT_PROXY_NETFILTER, 1, >+ [Transparent redirection support via netfilter]) >+ ], [], >+ [AC_LANG_SOURCE([[ >+#include <limits.h> >+#include <linux/netfilter_ipv4.h> >+ ]])]) > ;; > mips-sony-bsd|mips-sony-newsos4) > AC_DEFINE(NEED_SETPGRP, 1, [Need setpgrp to acquire controlling tty]) >@@ -562,6 +575,19 @@ mips-sony-bsd|mips-sony-newsos4) > AC_DEFINE(SSH_TUN_OPENBSD, 1, [Open tunnel devices the OpenBSD way]) > AC_DEFINE(SYSLOG_R_SAFE_IN_SIGHAND, 1, > [syslog_r function is safe to use in in a signal handler]) >+ AC_CHECK_HEADERS([net/pfvar.h], [ >+ TRANSPROXY=pf >+ AC_DEFINE(TRANSPARENT_PROXY_PF, 1, >+ [Transparent redirection support via pf]) >+ ], [], [AC_LANG_SOURCE([[ >+#include <sys/types.h> >+#include <sys/socket.h> >+#include <sys/ioctl.h> >+#include <sys/fcntl.h> >+#include <net/if.h> >+#include <netinet/in.h> >+#include <net/pfvar.h> >+ ]])]) > ;; > *-*-solaris*) > if test "x$withval" != "xno" ; then >@@ -3989,6 +4015,9 @@ echo " TCP Wrappers support > echo " MD5 password support: $MD5_MSG" > echo " libedit support: $LIBEDIT_MSG" > echo " Solaris process contract support: $SPC_MSG" >+if test ! -z "$TRANSPROXY" ; then >+echo " Transparent proxy support: $TRANSPROXY" >+fi > echo " IP address in \$DISPLAY hack: $DISPLAY_HACK_MSG" > echo " Translate v4 in v6 hack: $IPV4_IN6_HACK_MSG" > echo " BSD Auth support: $BSD_AUTH_MSG" >Index: misc.c >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh/misc.c,v >retrieving revision 1.83 >diff -u -p -r1.83 misc.c >--- misc.c 5 Jan 2007 05:24:48 -0000 1.83 >+++ misc.c 12 Mar 2007 11:26:12 -0000 >@@ -27,6 +27,7 @@ > #include "includes.h" > > #include <sys/types.h> >+#include <sys/fcntl.h> > #include <sys/ioctl.h> > #include <sys/socket.h> > #include <sys/param.h> >@@ -39,6 +40,10 @@ > > #include <netinet/in.h> > #include <netinet/tcp.h> >+#ifdef TRANSPARENT_PROXY_PF >+# include <net/if.h> >+# include <net/pfvar.h> >+#endif > > #include <errno.h> > #include <fcntl.h> >@@ -262,6 +267,81 @@ a2tun(const char *s, int *remote) > return (tun); > } > >+/* >+ * Look up a transparently redirected socket's original address. >+ * Returns sockaddr pointer representing original address or NULL if >+ * if not redirected. >+ */ >+struct sockaddr * >+lookup_transparent_sock(int fd) >+{ >+#if defined(TRANSPARENT_PROXY_NETFILTER) >+ return netfilter_lookup_transparent_sock(fd); >+#elif defined(TRANSPARENT_PROXY_PF) >+ int devfd, ret; >+ struct pfioc_natlook nl; >+ static struct sockaddr la; >+ struct sockaddr sa; >+ struct sockaddr_in *sa_in, *la_in; >+ socklen_t slen = sizeof(sa), llen = sizeof(la); >+ >+ /* get local addrinfo */ >+ if (getsockname(fd, &la, &llen) == -1) { >+ error("lookup_transparent_sock: getsockname: %s", >+ strerror(errno)); >+ return NULL; >+ } >+ >+ /* get remote addrinfo */ >+ if (getpeername(fd, &sa, &slen) == -1) { >+ error("lookup_transparent_sock: getpeername: %s", >+ strerror(errno)); >+ return NULL; >+ } >+ >+ memset(&nl, 0, sizeof(nl)); >+ nl.direction = PF_OUT; >+ nl.af = sa.sa_family; >+ nl.proto = IPPROTO_TCP; >+ switch (sa.sa_family) { >+ case AF_INET: >+ la_in = (struct sockaddr_in *)&la; >+ sa_in = (struct sockaddr_in *)&sa; >+ nl.saddr.v4.s_addr = sa_in->sin_addr.s_addr; >+ nl.sport = sa_in->sin_port; >+ nl.daddr.v4.s_addr = la_in->sin_addr.s_addr; >+ nl.dport = la_in->sin_port; >+ break; >+ case AF_INET6: >+ return NULL; /* TODO */ >+ default: >+ return NULL; >+ } >+ >+ /* lookup redirected connection */ >+ if ((devfd = open("/dev/pf", O_RDWR)) == -1) { >+ debug("lookup_transparent_sock: could not open /dev/pf: %s", >+ strerror(errno)); >+ return NULL; >+ } >+ ret = ioctl(devfd, DIOCNATLOOK, &nl); >+ close(devfd); >+ if (ret == -1) { >+ if (errno != ENOENT) >+ error("lookup_transparent_sock: pf lookup failed: %s", >+ strerror(errno)); >+ return NULL; >+ } >+ >+ /* copy translated values and return */ >+ la_in->sin_addr.s_addr = nl.rdaddr.v4.s_addr; >+ la_in->sin_port = nl.rdport; >+ return &la; >+#else >+ return NULL; >+#endif >+} >+ > #define SECONDS 1 > #define MINUTES (SECONDS * 60) > #define HOURS (MINUTES * 60) >Index: misc.h >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh/misc.h,v >retrieving revision 1.39 >diff -u -p -r1.39 misc.h >--- misc.h 18 Aug 2006 14:33:06 -0000 1.39 >+++ misc.h 12 Mar 2007 11:23:21 -0000 >@@ -87,4 +87,6 @@ char *read_passphrase(const char *, int) > int ask_permission(const char *, ...) __attribute__((format(printf, 1, 2))); > int read_keyfile_line(FILE *, const char *, char *, size_t, u_long *); > >+struct sockaddr *lookup_transparent_sock(int); >+ > #endif /* _MISC_H */ >Index: openbsd-compat/port-linux.c >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh_cvs/openbsd-compat/port-linux.c,v >retrieving revision 1.3 >diff -u -p -r1.3 port-linux.c >--- openbsd-compat/port-linux.c 1 Sep 2006 05:38:41 -0000 1.3 >+++ openbsd-compat/port-linux.c 12 Mar 2007 11:25:21 -0000 >@@ -18,7 +18,7 @@ > */ > > /* >- * Linux-specific portability code - just SELinux support at present >+ * Linux-specific portability code. > */ > > #include "includes.h" >@@ -27,9 +27,15 @@ > #include <stdarg.h> > #include <string.h> > >+#include "port-linux.h" >+ >+#ifdef TRANSPARENT_PROXY_NETFILTER >+# include <limits.h> >+# include <linux/netfilter_ipv4.h> >+#endif >+ > #ifdef WITH_SELINUX > #include "log.h" >-#include "port-linux.h" > > #include <selinux/selinux.h> > #include <selinux/flask.h> >@@ -167,3 +173,40 @@ ssh_selinux_setup_pty(char *pwname, cons > debug3("%s: done", __func__); > } > #endif /* WITH_SELINUX */ >+ >+#if defined(TRANSPARENT_PROXY_NETFILTER) >+/* >+ * Look up a transparently redirected socket's original address. >+ * Returns sockaddr pointer representing original address or NULL if >+ * if not redirected. >+ */ >+struct sockaddr * >+netfilter_lookup_transparent_sock(int fd) >+{ >+ static struct sockaddr oa; /* original destination address */ >+ struct sockaddr sa; /* redirected destination address */ >+ struct sockaddr_in *oa_in, *sa_in; >+ socklen_t olen, slen; >+ >+ slen = olen = sizeof(struct sockaddr); >+ if (getsockopt(fd, SOL_IP, SO_ORIGINAL_DST, &oa, &olen) == -1 || >+ getsockname(fd, &sa, &slen) == -1 || oa.sa_family != sa.sa_family) >+ return NULL; >+ >+ switch (oa.sa_family) { >+ case AF_INET: >+ oa_in = (struct sockaddr_in *)&oa; >+ sa_in = (struct sockaddr_in *)&sa; >+ if (oa_in->sin_addr.s_addr == INADDR_ANY || >+ oa_in->sin_addr.s_addr == INADDR_NONE || >+ (oa_in->sin_family == sa_in->sin_family && >+ oa_in->sin_addr.s_addr == sa_in->sin_addr.s_addr && >+ oa_in->sin_port == sa_in->sin_port)) >+ return NULL; >+ return &oa; >+ case AF_INET6: >+ return NULL; /* XXX */ >+ } >+ return NULL; >+} >+#endif >Index: openbsd-compat/port-linux.h >=================================================================== >RCS file: /usr/local/src/security/openssh/cvs/openssh_cvs/openbsd-compat/port-linux.h,v >retrieving revision 1.1 >diff -u -p -r1.1 port-linux.h >--- openbsd-compat/port-linux.h 22 Apr 2006 11:26:08 -0000 1.1 >+++ openbsd-compat/port-linux.h 12 Mar 2007 11:21:02 -0000 >@@ -24,4 +24,8 @@ void ssh_selinux_setup_pty(char *, const > void ssh_selinux_setup_exec_context(char *); > #endif > >+#ifdef TRANSPARENT_PROXY_NETFILTER >+struct sockaddr *netfilter_lookup_transparent_sock(int); >+#endif >+ > #endif /* ! _PORT_LINUX_H */
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 1295
:
1249
|
1250
| 1251