From ee9bb597da0f3f5631b39e83bcc762e46061ba4d Mon Sep 17 00:00:00 2001 From: Gray Liang Date: Mon, 8 Jan 2024 15:33:41 +0800 Subject: [PATCH] setupNetns can retry on errors --- control/netns_utils.go | 75 ++++++++++++++++++++++-------------------- control/udp.go | 2 +- 2 files changed, 40 insertions(+), 37 deletions(-) diff --git a/control/netns_utils.go b/control/netns_utils.go index bc0e338587..a519866409 100644 --- a/control/netns_utils.go +++ b/control/netns_utils.go @@ -14,11 +14,11 @@ import ( ) var ( - indieNetns netns.NsHandle - once sync.Once + daeNetns netns.NsHandle + once sync.Once ) -func WithIndieNetns(f func() error) (err error) { +func WithDaeNetns(f func() error) (err error) { runtime.LockOSThread() defer runtime.UnlockOSThread() @@ -28,7 +28,7 @@ func WithIndieNetns(f func() error) (err error) { } defer netns.Set(hostNetns) - ns, err := GetIndieNetns() + ns, err := GetDaeNetns() if err != nil { return } @@ -39,35 +39,38 @@ func WithIndieNetns(f func() error) (err error) { return f() } -func GetIndieNetns() (_ netns.NsHandle, err error) { - if indieNetns != 0 { - return indieNetns, nil +func GetDaeNetns() (_ netns.NsHandle, err error) { + if daeNetns != 0 { + return daeNetns, nil } once.Do(func() { - err = setupIndieNetns() + daeNetns, err = setupDaeNetns() + if err != nil { + once = sync.Once{} + } }) - return indieNetns, err + return daeNetns, err } -func setupIndieNetns() (err error) { +func setupDaeNetns() (ns netns.NsHandle, err error) { runtime.LockOSThread() defer runtime.UnlockOSThread() hostNetns, err := netns.Get() if err != nil { - return fmt.Errorf("Failed to get host netns: %v", err) + return 0, fmt.Errorf("Failed to get host netns: %v", err) } defer netns.Set(hostNetns) // ip netns a daens DeleteNamedNetns("daens") - indieNetns, err = netns.NewNamed("daens") + ns, err = netns.NewNamed("daens") if err != nil { - return fmt.Errorf("Failed to create netns: %v", err) + return 0, fmt.Errorf("Failed to create netns: %v", err) } if err = netns.Set(hostNetns); err != nil { - return fmt.Errorf("Failed to switch to host netns: %v", err) + return 0, fmt.Errorf("Failed to switch to host netns: %v", err) } // ip l a dae0 type veth peer name dae0peer DeleteLink("dae0") @@ -77,43 +80,43 @@ func setupIndieNetns() (err error) { }, PeerName: "dae0peer", }); err != nil { - return fmt.Errorf("Failed to add veth pair: %v", err) + return 0, fmt.Errorf("Failed to add veth pair: %v", err) } dae0, err := netlink.LinkByName("dae0") if err != nil { - return fmt.Errorf("Failed to get link dae0: %v", err) + return 0, fmt.Errorf("Failed to get link dae0: %v", err) } dae0peer, err := netlink.LinkByName("dae0peer") if err != nil { - return fmt.Errorf("Failed to get link dae0peer: %v", err) + return 0, fmt.Errorf("Failed to get link dae0peer: %v", err) } // ip l s dae0 up if err = netlink.LinkSetUp(dae0); err != nil { - return fmt.Errorf("Failed to set link dae0 up: %v", err) + return 0, fmt.Errorf("Failed to set link dae0 up: %v", err) } // sysctl net.ipv4.conf.dae0.rp_filter=0 if err = SetRpFilter("dae0", "0"); err != nil { - return fmt.Errorf("Failed to set rp_filter for dae0: %v", err) + return 0, fmt.Errorf("Failed to set rp_filter for dae0: %v", err) } // sysctl net.ipv4.conf.all.rp_filter=0 if err = SetRpFilter("all", "0"); err != nil { - return fmt.Errorf("Failed to set rp_filter for all: %v", err) + return 0, fmt.Errorf("Failed to set rp_filter for all: %v", err) } // sysctl net.ipv4.conf.dae0.arp_filter=0 if err = SetArpFilter("dae0", "0"); err != nil { - return fmt.Errorf("Failed to set arp_filter for dae0: %v", err) + return 0, fmt.Errorf("Failed to set arp_filter for dae0: %v", err) } // sysctl net.ipv4.conf.all.arp_filter=0 if err = SetArpFilter("all", "0"); err != nil { - return fmt.Errorf("Failed to set arp_filter for all: %v", err) + return 0, fmt.Errorf("Failed to set arp_filter for all: %v", err) } // sysctl net.ipv4.conf.dae0.accept_local=1 if err = SetAcceptLocal("dae0", "1"); err != nil { - return fmt.Errorf("Failed to set accept_local for dae0: %v", err) + return 0, fmt.Errorf("Failed to set accept_local for dae0: %v", err) } // sysctl net.ipv6.conf.dae0.disable_ipv6=0 if err = SetDisableIpv6("dae0", "0"); err != nil { - return fmt.Errorf("Failed to set disable_ipv6 for dae0: %v", err) + return 0, fmt.Errorf("Failed to set disable_ipv6 for dae0: %v", err) } // sysctl net.ipv6.conf.dae0.forwarding=1 SetForwarding("dae0", "1") @@ -126,28 +129,28 @@ func setupIndieNetns() (err error) { Mask: net.CIDRMask(128, 128), }, }); err != nil { - return fmt.Errorf("Failed to add v6 addr to dae0: %v", err) + return 0, fmt.Errorf("Failed to add v6 addr to dae0: %v", err) } // ip l s dae0peer netns daens - if err = netlink.LinkSetNsFd(dae0peer, int(indieNetns)); err != nil { - return fmt.Errorf("Failed to move dae0peer to daens: %v", err) + if err = netlink.LinkSetNsFd(dae0peer, int(ns)); err != nil { + return 0, fmt.Errorf("Failed to move dae0peer to daens: %v", err) } // ip net e daens - if err = netns.Set(indieNetns); err != nil { - return fmt.Errorf("Failed to switch to daens: %v", err) + if err = netns.Set(ns); err != nil { + return 0, fmt.Errorf("Failed to switch to daens: %v", err) } // (ip net e daens) ip l s dae0peer up if err = netlink.LinkSetUp(dae0peer); err != nil { - return fmt.Errorf("Failed to set link dae0peer up: %v", err) + return 0, fmt.Errorf("Failed to set link dae0peer up: %v", err) } // (ip net e daens) ip a a 169.254.0.11 dev dae0peer ip, ipNet, err := net.ParseCIDR("169.254.0.11/32") ipNet.IP = ip if err != nil { - return fmt.Errorf("Failed to parse ip: %v", err) + return 0, fmt.Errorf("Failed to parse ip: %v", err) } if err = netlink.AddrAdd(dae0peer, &netlink.Addr{IPNet: ipNet}); err != nil { - return fmt.Errorf("Failed to add v4 addr to dae0peer: %v", err) + return 0, fmt.Errorf("Failed to add v4 addr to dae0peer: %v", err) } // (ip net e daens) ip r a 169.254.0.1 dev dae0peer if err = netlink.RouteAdd(&netlink.Route{ @@ -156,7 +159,7 @@ func setupIndieNetns() (err error) { Gw: nil, Scope: netlink.SCOPE_LINK, }); err != nil { - return fmt.Errorf("Failed to add v4 route1 to dae0peer: %v", err) + return 0, fmt.Errorf("Failed to add v4 route1 to dae0peer: %v", err) } // (ip net e daens) ip r a default via 169.254.0.1 dev dae0peer if err = netlink.RouteAdd(&netlink.Route{ @@ -164,7 +167,7 @@ func setupIndieNetns() (err error) { Dst: &net.IPNet{IP: net.IPv4(0, 0, 0, 0), Mask: net.CIDRMask(0, 32)}, Gw: net.ParseIP("169.254.0.1"), }); err != nil { - return fmt.Errorf("Failed to add v4 route2 to dae0peer: %v", err) + return 0, fmt.Errorf("Failed to add v4 route2 to dae0peer: %v", err) } // (ip net e daens) ip n r 169.254.0.1 dev dae0peer lladdr $mac_dae0 nud permanent if err = netlink.NeighAdd(&netlink.Neigh{ @@ -173,7 +176,7 @@ func setupIndieNetns() (err error) { LinkIndex: dae0peer.Attrs().Index, State: netlink.NUD_PERMANENT, }); err != nil { - return fmt.Errorf("Failed to add neigh to dae0peer: %v", err) + return 0, fmt.Errorf("Failed to add neigh to dae0peer: %v", err) } // (ip net e daens) ip -6 r a default via fe80::ecee:eeff:feee:eeee dev dae0peer if err = netlink.RouteAdd(&netlink.Route{ @@ -181,7 +184,7 @@ func setupIndieNetns() (err error) { Dst: &net.IPNet{IP: net.IPv6zero, Mask: net.CIDRMask(0, 128)}, Gw: net.ParseIP("fe80::ecee:eeff:feee:eeee"), }); err != nil { - return fmt.Errorf("Failed to add v6 route to dae0peer: %v", err) + return 0, fmt.Errorf("Failed to add v6 route to dae0peer: %v", err) } return diff --git a/control/udp.go b/control/udp.go index 0eee005a8c..44073c0d67 100644 --- a/control/udp.go +++ b/control/udp.go @@ -95,7 +95,7 @@ func sendPkt(data []byte, from netip.AddrPort, realTo, to netip.AddrPort, lConn WithField("to", to). WithField("realTo", realTo). Trace("Port in use, fallback to use netns.") - err = WithIndieNetns(func() (err error) { + err = WithDaeNetns(func() (err error) { uConn, _, err = DefaultAnyfromPool.GetOrCreate(from.String(), AnyfromTimeout) return err })