UlricE / pen

Pen
Other
249 stars 41 forks source link

IPv6 UDP packets are not forwarded #45

Open tmueller64 opened 6 years ago

tmueller64 commented 6 years ago

Tried using pen to forward IPv6 UDP packets. Command line is:

pen -F /etc/pen/upstreams.cfg -U :::80

Content of upstreams.cfg is:

server 0 address 10.1.93.108 port 88

Here is an strace from when a packet is received:

epoll_wait(5, {{EPOLLIN, {u32=4, u64=4}}}, 1002, 3000) = 1 recvfrom(4, "X", 32768, 0, {sa_family=AF_INET6, sin6_port=htons(50290), inet_pton(AF_INET6, "2600:8804:900:440:e8f9:6e8:1c34:348b", &sin6_addr), sin6_flowinfo=0, sin6_scope_id=0}, [28]) = 1 socket(PF_INET6, SOCK_DGRAM|SOCK_NONBLOCK, IPPROTO_IP) = 6 setsockopt(6, SOLSOCKET, 0xf /* SO??? */, [1], 4) = 0 getsockname(4, {sa_family=AF_INET6, sin6_port=htons(80), inet_pton(AF_INET6, "::5800:0:0:0", &sin6_addr), sin6_flowinfo=0, sin6_scope_id=0}, [28]) = 0 bind(6, {sa_family=AF_INET6, sin6_port=htons(80), inet_pton(AF_INET6, "::5800:0:0:0", &sin6_addr), sin6_flowinfo=0, sin6_scope_id=0}, 28) = -1 EADDRNOTAVAIL (Cannot assign requested address) stat("/etc/localtime", {st_mode=S_IFREG|0644, st_size=118, ...}) = 0 socket(PF_LOCAL, SOCK_DGRAM|SOCK_CLOEXEC, 0) = 7 connect(7, {sa_family=AF_LOCAL, sun_path="/dev/log"}, 110) = 0 sendto(7, "<15>Aug 30 20:00:51 pen: bind re"..., 53, MSG_NOSIGNAL, NULL, 0) = 53 close(7) = 0 close(6) = 0

The bind call in the add_client method fails with an EADDRNOTAVAIL because the downfd is being bound to the same address as being used by the listenfd.

Assuming that the bind is fixed, I'm also wondering if a PF_INET6 socket will be able to send a packet to an IPv4 destination.

UlricE commented 5 years ago

Good catch. The root cause was actually that the buffer used to get the address from getsockname was only large enough for ipv4 addresses, so an ipv6 address would be truncated. The buffer is now a sockaddr_storage, big enough for ipv4 and ipv6 addresses.

With that bug out of the way, you can indeed "proxy" ipv6 packets to ipv4 destinations. You can try this e.g. by starting Pen like this:

pen -dfU :::53 8.8.8.8

And making a DNS query like this:

root@debtest:~# dig @::1 +short siag.nu 93.188.2.52