Created attachment 191279 [details] Proposed patch to correct IPv6 vs IPv4 check in receive path Since bug 221385's been closed, with net.inet6.ip6.v6only=0, a socket listening on an IPv6 address accepts a connection from another IPv6 host, the accepted socket shows type "tcp46" and has its address truncated to the lower 32 bits: USER COMMAND PID FD PROTO LOCAL ADDRESS FOREIGN ADDRESS dan sshd 711 3 tcp46 254.11.122.185:22 0.0.0.2:47615 root sshd 708 3 tcp46 254.11.122.185:22 0.0.0.2:47615 The addresses are the lower 32 bits of the IPv6 addresses in question, 2001:470:1f17:273:2a0:98ff:fe0b:7ab9 and 2001:470:1c:4df::2. The expected result would be: USER COMMAND PID FD PROTO LOCAL ADDRESS FOREIGN ADDRESS dan sshd 40475 3 tcp6 2001:470:30f3:1:ca60:ff:fe5f:c1f3:22 2001:470:30f3:1:922b:34ff:fe5d:d4b3:33558 root sshd 35424 3 tcp6 2001:470:30f3:1:ca60:ff:fe5f:c1f3:22 2001:470:30f3:1:922b:34ff:fe5d:d4b3:33558 This appears to be due to the kernel assuming any socket whose inp_vflag includes IPv4 is an IPv4 socket. The accepted socket inherits that value from the parent socket. It should only have tcp46 for listening sockets, and in accept check that only INP_IPV4 is set.
Michael, CCing you as you addressed the previous issue in a similar area and probably have some experience with this code.
Hi Conrad, thanks for adding me. I'm aware of the problem and have a fix under review D13514. Can you test the patch under reiew D13514? Best regards Michael
Dan, can you test Michael's patch? I'm afraid I don't have any ipv6 networking on any of my FreeBSD machines (nor time to test).
(In reply to Conrad Meyer from comment #3) Yes, it looks like Michael's review D13514 fixes the issue for me too.
A commit references this bug: Author: tuexen Date: Fri Mar 16 15:26:08 UTC 2018 New revision: 331061 URL: https://svnweb.freebsd.org/changeset/base/331061 Log: Set the inp_vflag consistently for accepted TCP/IPv6 connections when net.inet6.ip6.v6only=0. Without this patch, the inp_vflag would have INP_IPV4 and the INP_IPV6 flags for accepted TCP/IPv6 connections if the sysctl variable net.inet6.ip6.v6only is 0. This resulted in netstat to report the source and destination addresses as IPv4 addresses, even they are IPv6 addresses. PR: 226421 Reviewed by: bz, hiren, kib MFC after: 3 days Sponsored by: Netflix, Inc. Differential Revision: https://reviews.freebsd.org/D13514 Changes: head/sys/netinet/tcp_syncache.c
A commit references this bug: Author: tuexen Date: Sat Apr 7 20:47:25 UTC 2018 New revision: 332238 URL: https://svnweb.freebsd.org/changeset/base/332238 Log: MFC r331061: Set the inp_vflag consistently for accepted TCP/IPv6 connections when net.inet6.ip6.v6only=0. Without this patch, the inp_vflag would have INP_IPV4 and the INP_IPV6 flags for accepted TCP/IPv6 connections if the sysctl variable net.inet6.ip6.v6only is 0. This resulted in netstat to report the source and destination addresses as IPv4 addresses, even they are IPv6 addresses. PR: 226421 Reviewed by: bz, hiren, kib Sponsored by: Netflix, Inc. Differential Revision: https://reviews.freebsd.org/D13514 Changes: _U stable/11/ stable/11/sys/netinet/tcp_syncache.c
This is now fixed in head and stable/11. So I'm closing this bug.