From 2aa82152a53e7aa6b28c6390d9369ee5a5b63584 Mon Sep 17 00:00:00 2001 From: Cuong Manh Le Date: Sun, 18 Dec 2022 01:15:58 +0700 Subject: [PATCH] nettest: use RoutedInterface for probing network stack capability The ipv4/ipv6 support capability is done by explicitly listening on loopback interface. However, it can lead to false positive, especially for ipv6 case. For example, ipv6 can be enabled, but explicitly disable for loopback interface (for security, policy ...). This CL changes probeStack to use another approach, by looking for any interface that can route IP traffic and in "UP" state. If there's one, then the platform can do ipv4/ipv6 networking functionality. Fixes golang/go#57386 Change-Id: If911bc223b52c5a4562d3f61b4ee1032bdbec47c Reviewed-on: https://go-review.googlesource.com/c/net/+/458096 TryBot-Result: Gopher Robot Auto-Submit: Cuong Manh Le Reviewed-by: Benny Siegert Reviewed-by: Matt Layher Run-TryBot: Cuong Manh Le Reviewed-by: David Chase --- ipv6/bpf_test.go | 4 ++-- ipv6/readwrite_test.go | 7 +++---- ipv6/sockopt_test.go | 9 +++++---- ipv6/unicast_test.go | 4 ++-- ipv6/unicastsockopt_test.go | 8 ++++---- nettest/nettest.go | 6 ++---- 6 files changed, 18 insertions(+), 20 deletions(-) diff --git a/ipv6/bpf_test.go b/ipv6/bpf_test.go index e249e1c923..c43ddd02ec 100644 --- a/ipv6/bpf_test.go +++ b/ipv6/bpf_test.go @@ -19,8 +19,8 @@ func TestBPF(t *testing.T) { if runtime.GOOS != "linux" { t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } l, err := net.ListenPacket("udp6", "[::1]:0") diff --git a/ipv6/readwrite_test.go b/ipv6/readwrite_test.go index e8db1199e1..131b1904c5 100644 --- a/ipv6/readwrite_test.go +++ b/ipv6/readwrite_test.go @@ -223,10 +223,10 @@ func TestPacketConnConcurrentReadWriteUnicastUDP(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + ifi, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback) + if err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } - c, err := nettest.NewLocalPacketListener("udp6") if err != nil { t.Fatal(err) @@ -236,7 +236,6 @@ func TestPacketConnConcurrentReadWriteUnicastUDP(t *testing.T) { defer p.Close() dst := c.LocalAddr() - ifi, _ := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback) cf := ipv6.FlagTrafficClass | ipv6.FlagHopLimit | ipv6.FlagSrc | ipv6.FlagDst | ipv6.FlagInterface | ipv6.FlagPathMTU wb := []byte("HELLO-R-U-THERE") diff --git a/ipv6/sockopt_test.go b/ipv6/sockopt_test.go index 3305cfc114..ab0d2e4e51 100644 --- a/ipv6/sockopt_test.go +++ b/ipv6/sockopt_test.go @@ -20,8 +20,9 @@ func TestConnInitiatorPathMTU(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows", "zos": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } ln, err := net.Listen("tcp6", "[::1]:0") @@ -53,8 +54,8 @@ func TestConnResponderPathMTU(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows", "zos": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } ln, err := net.Listen("tcp6", "[::1]:0") diff --git a/ipv6/unicast_test.go b/ipv6/unicast_test.go index fe1d44dfa7..e03c2cd336 100644 --- a/ipv6/unicast_test.go +++ b/ipv6/unicast_test.go @@ -23,8 +23,8 @@ func TestPacketConnReadWriteUnicastUDP(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } c, err := nettest.NewLocalPacketListener("udp6") diff --git a/ipv6/unicastsockopt_test.go b/ipv6/unicastsockopt_test.go index ac0daf2856..c3abe2d14d 100644 --- a/ipv6/unicastsockopt_test.go +++ b/ipv6/unicastsockopt_test.go @@ -19,8 +19,8 @@ func TestConnUnicastSocketOptions(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } ln, err := net.Listen("tcp6", "[::1]:0") @@ -64,8 +64,8 @@ func TestPacketConnUnicastSocketOptions(t *testing.T) { case "fuchsia", "hurd", "js", "nacl", "plan9", "windows": t.Skipf("not supported on %s", runtime.GOOS) } - if !nettest.SupportsIPv6() { - t.Skip("ipv6 is not supported") + if _, err := nettest.RoutedInterface("ip6", net.FlagUp|net.FlagLoopback); err != nil { + t.Skip("ipv6 is not enabled for loopback interface") } ok := nettest.SupportsRawSocket() diff --git a/nettest/nettest.go b/nettest/nettest.go index 6918f2c362..3d970bfc67 100644 --- a/nettest/nettest.go +++ b/nettest/nettest.go @@ -34,12 +34,10 @@ var ( ) func probeStack() { - if ln, err := net.Listen("tcp4", "127.0.0.1:0"); err == nil { - ln.Close() + if _, err := RoutedInterface("ip4", net.FlagUp); err == nil { ipv4Enabled = true } - if ln, err := net.Listen("tcp6", "[::1]:0"); err == nil { - ln.Close() + if _, err := RoutedInterface("ip6", net.FlagUp); err == nil { ipv6Enabled = true } rawSocketSess = supportsRawSocket()