mirror of
https://git.haproxy.org/git/haproxy.git/
synced 2025-11-29 14:50:59 +01:00
MINOR: IPv6 support for transparent proxy
Set socket option IPV6_TRANSPARENT on binding to enable transparent proxy on IPv6. This option is available from Linux 2.6.37.
This commit is contained in:
parent
5b88da269c
commit
65c1796c4a
@ -88,6 +88,9 @@
|
|||||||
#if !defined(IP_TRANSPARENT)
|
#if !defined(IP_TRANSPARENT)
|
||||||
#define IP_TRANSPARENT 19
|
#define IP_TRANSPARENT 19
|
||||||
#endif /* !IP_TRANSPARENT */
|
#endif /* !IP_TRANSPARENT */
|
||||||
|
#if !defined(IPV6_TRANSPARENT)
|
||||||
|
#define IPV6_TRANSPARENT 75
|
||||||
|
#endif /* !IPV6_TRANSPARENT */
|
||||||
#endif /* CONFIG_HAP_LINUX_TPROXY */
|
#endif /* CONFIG_HAP_LINUX_TPROXY */
|
||||||
|
|
||||||
/* We'll try to enable SO_REUSEPORT on Linux 2.4 and 2.6 if not defined.
|
/* We'll try to enable SO_REUSEPORT on Linux 2.4 and 2.6 if not defined.
|
||||||
|
|||||||
@ -128,6 +128,9 @@ int tcp_bind_socket(int fd, int flags, struct sockaddr_storage *local, struct so
|
|||||||
|
|
||||||
#ifdef CONFIG_HAP_LINUX_TPROXY
|
#ifdef CONFIG_HAP_LINUX_TPROXY
|
||||||
static int ip_transp_working = 1;
|
static int ip_transp_working = 1;
|
||||||
|
static int ip6_transp_working = 1;
|
||||||
|
switch (local->ss_family) {
|
||||||
|
case AF_INET:
|
||||||
if (flags && ip_transp_working) {
|
if (flags && ip_transp_working) {
|
||||||
if (setsockopt(fd, SOL_IP, IP_TRANSPARENT, &one, sizeof(one)) == 0
|
if (setsockopt(fd, SOL_IP, IP_TRANSPARENT, &one, sizeof(one)) == 0
|
||||||
|| setsockopt(fd, SOL_IP, IP_FREEBIND, &one, sizeof(one)) == 0)
|
|| setsockopt(fd, SOL_IP, IP_FREEBIND, &one, sizeof(one)) == 0)
|
||||||
@ -135,6 +138,16 @@ int tcp_bind_socket(int fd, int flags, struct sockaddr_storage *local, struct so
|
|||||||
else
|
else
|
||||||
ip_transp_working = 0;
|
ip_transp_working = 0;
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
|
case AF_INET6:
|
||||||
|
if (flags && ip6_transp_working) {
|
||||||
|
if (setsockopt(fd, SOL_IPV6, IPV6_TRANSPARENT, &one, sizeof(one)) == 0)
|
||||||
|
foreign_ok = 1;
|
||||||
|
else
|
||||||
|
ip6_transp_working = 0;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
if (flags) {
|
if (flags) {
|
||||||
memset(&bind_addr, 0, sizeof(bind_addr));
|
memset(&bind_addr, 0, sizeof(bind_addr));
|
||||||
@ -736,12 +749,23 @@ int tcp_bind_listener(struct listener *listener, char *errmsg, int errlen)
|
|||||||
setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &one, sizeof(one));
|
setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &one, sizeof(one));
|
||||||
#endif
|
#endif
|
||||||
#ifdef CONFIG_HAP_LINUX_TPROXY
|
#ifdef CONFIG_HAP_LINUX_TPROXY
|
||||||
if ((listener->options & LI_O_FOREIGN)
|
if (listener->options & LI_O_FOREIGN) {
|
||||||
&& (setsockopt(fd, SOL_IP, IP_TRANSPARENT, &one, sizeof(one)) == -1)
|
switch (listener->addr.ss_family) {
|
||||||
|
case AF_INET:
|
||||||
|
if ((setsockopt(fd, SOL_IP, IP_TRANSPARENT, &one, sizeof(one)) == -1)
|
||||||
&& (setsockopt(fd, SOL_IP, IP_FREEBIND, &one, sizeof(one)) == -1)) {
|
&& (setsockopt(fd, SOL_IP, IP_FREEBIND, &one, sizeof(one)) == -1)) {
|
||||||
msg = "cannot make listening socket transparent";
|
msg = "cannot make listening socket transparent";
|
||||||
err |= ERR_ALERT;
|
err |= ERR_ALERT;
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
|
case AF_INET6:
|
||||||
|
if (setsockopt(fd, SOL_IPV6, IPV6_TRANSPARENT, &one, sizeof(one)) == -1) {
|
||||||
|
msg = "cannot make listening socket transparent";
|
||||||
|
err |= ERR_ALERT;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
#ifdef SO_BINDTODEVICE
|
#ifdef SO_BINDTODEVICE
|
||||||
/* Note: this might fail if not CAP_NET_RAW */
|
/* Note: this might fail if not CAP_NET_RAW */
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user