Skip to content

Commit

Permalink
feat(diagnosis): add host interface detection for flannel & calico pl…
Browse files Browse the repository at this point in the history
…ugin

Signed-off-by: xiayu.lyt <xiayu.lyt@alibaba-inc.com>
  • Loading branch information
Lyt99 committed Aug 9, 2023
1 parent 0a56cf9 commit 71e18f2
Show file tree
Hide file tree
Showing 4 changed files with 87 additions and 2 deletions.
28 changes: 28 additions & 0 deletions pkg/skoop/netstack/link.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,13 @@ package netstack

import (
"net"
"regexp"

"github.com/samber/lo"
)

var defaultInterfaceNames = []string{"eth0", "eno0"}

type Addr struct {
*net.IPNet
}
Expand Down Expand Up @@ -55,3 +60,26 @@ func GetDefaultIPv4(iface *Interface) (net.IP, net.IPMask) {
}
return defaultIP, net.CIDRMask(32, 32)
}

func LookupDefaultIfaceName(ifaces []Interface) string {
// find interfaces in default names
for _, n := range defaultInterfaceNames {
if lo.ContainsBy(ifaces, func(i Interface) bool {
return i.Name == n
}) {
return n
}
}

// find first interfaces matched enp[0-9]+s[0-9]+.*
regex := regexp.MustCompile("^enp[0-9]+s[0-9]+.*$")
filtered := lo.Filter(ifaces, func(i Interface, _ int) bool {
return regex.MatchString(i.Name)
})

if len(filtered) != 0 {
return filtered[0].Name
}

return ""
}
40 changes: 40 additions & 0 deletions pkg/skoop/netstack/link_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package netstack

import "testing"

func TestLookupDefaultIfaceName(t *testing.T) {
testcases := []struct {
ifaces []string
expected string
}{
{
ifaces: []string{"eth0", "eno0", "ipvs0", "cali123456"},
expected: "eth0",
},
{
ifaces: []string{"enp1s2", "eno0", "ipvs0", "cali123456"},
expected: "eno0",
},
{
ifaces: []string{"enp1s1", "ipvs0", "cali123456"},
expected: "enp1s1",
},
{
ifaces: []string{"wg0", "ipvs0", "cni0"},
expected: "",
},
}

for _, c := range testcases {
var ifs []Interface
for _, i := range c.ifaces {
ifs = append(ifs, Interface{Name: i})
}

result := LookupDefaultIfaceName(ifs)
if result != c.expected {
t.Errorf("excepted testcase %v to be %s, but %s", c.ifaces, c.expected, result)
t.FailNow()
}
}
}
11 changes: 10 additions & 1 deletion pkg/skoop/plugin/calico.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import (
"net"
"strings"

"k8s.io/klog/v2"

"github.com/spf13/pflag"

"github.com/alibaba/kubeskoop/pkg/skoop/assertions"
Expand All @@ -33,7 +35,7 @@ type CalicoConfig struct {
}

func (c *CalicoConfig) BindFlags(fs *pflag.FlagSet) {
fs.StringVarP(&c.Interface, "calico-host-interface", "", "eth0",
fs.StringVarP(&c.Interface, "calico-host-interface", "", "",
"Host interface for calico plugin.")
fs.IntVarP(&c.PodMTU, "calico-pod-mtu", "", 1500,
"Pod MTU for calico plugin. Pod interface MTU in BGP mode.")
Expand Down Expand Up @@ -331,6 +333,13 @@ func newCalicoHost(ipCache *k8s.IPCache, nodeInfo *k8s.NodeInfo, infraShim netwo
k8s: k8sAssertion,
infraShim: infraShim,
}
if host.iface == "" {
host.iface = netstack.LookupDefaultIfaceName(nodeInfo.NetNSInfo.Interfaces)
if host.iface == "" {
return nil, fmt.Errorf("cannot lookup default host interface, please manually specify it via --calico-host-interface")
}
klog.V(5).Infof("detected host interface %s on node %s", host.iface, host.nodeInfo.NodeName)
}

err := host.initRoute()
if err != nil {
Expand Down
10 changes: 9 additions & 1 deletion pkg/skoop/plugin/flannel.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ func (f *FlannelConfig) BindFlags(fs *pflag.FlagSet) {
"Pod MTU for flannel plugin. If not set, it will auto detect from flannel cni mode (1450 for vxlan, 1500 for others).")
fs.BoolVarP(&f.IPMasq, "flannel-ip-masq", "", true,
"Should do IP masquerade for flannel plugin.")
fs.StringVarP(&f.Interface, "flannel-host-interface", "", "eth0",
fs.StringVarP(&f.Interface, "flannel-host-interface", "", "",
"Host interface for flannel plugin.")
}

Expand Down Expand Up @@ -474,6 +474,14 @@ func newFlannelHost(ipCache *k8s.IPCache, nodeInfo *k8s.NodeInfo, infraShim netw
serviceProcessor: serviceProcessor,
}

if host.iface == "" {
host.iface = netstack.LookupDefaultIfaceName(nodeInfo.NetNSInfo.Interfaces)
if host.iface == "" {
return nil, fmt.Errorf("cannot lookup default host interface, please manually specify it via --flannel-host-interface")
}
klog.V(5).Infof("detected host interface %s on node %s", host.iface, host.nodeInfo.NodeName)
}

err = host.initRoute()
if err != nil {
return nil, err
Expand Down

0 comments on commit 71e18f2

Please sign in to comment.