mirror of
https://github.com/cloudnativelabs/kube-router.git
synced 2025-10-11 18:01:05 +02:00
Ipv6; BGP peering (#545)
* Use ip6tables for ipv6 and handle ipv6 for egress rules * Make the temp ipset's fit into 31 characters This should be improved. Some hash string should be used for temp names.
This commit is contained in:
parent
a47e0f4541
commit
077ff86bcc
@ -60,6 +60,7 @@ type NetworkRoutingController struct {
|
|||||||
nodeName string
|
nodeName string
|
||||||
nodeSubnet net.IPNet
|
nodeSubnet net.IPNet
|
||||||
nodeInterface string
|
nodeInterface string
|
||||||
|
isIpv6 bool
|
||||||
activeNodes map[string]bool
|
activeNodes map[string]bool
|
||||||
mu sync.Mutex
|
mu sync.Mutex
|
||||||
clientset kubernetes.Interface
|
clientset kubernetes.Interface
|
||||||
@ -151,7 +152,7 @@ func (nrc *NetworkRoutingController) Run(healthChan chan<- *healthcheck.Controll
|
|||||||
}
|
}
|
||||||
|
|
||||||
glog.V(1).Info("Performing cleanup of depreciated rules/ipsets (if needed).")
|
glog.V(1).Info("Performing cleanup of depreciated rules/ipsets (if needed).")
|
||||||
err = deleteBadPodEgressRules()
|
err = nrc.deleteBadPodEgressRules()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("Error cleaning up old/bad Pod egress rules: %s", err.Error())
|
glog.Errorf("Error cleaning up old/bad Pod egress rules: %s", err.Error())
|
||||||
}
|
}
|
||||||
@ -160,14 +161,14 @@ func (nrc *NetworkRoutingController) Run(healthChan chan<- *healthcheck.Controll
|
|||||||
if nrc.enablePodEgress {
|
if nrc.enablePodEgress {
|
||||||
glog.V(1).Infoln("Enabling Pod egress.")
|
glog.V(1).Infoln("Enabling Pod egress.")
|
||||||
|
|
||||||
err = createPodEgressRule()
|
err = nrc.createPodEgressRule()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("Error enabling Pod egress: %s", err.Error())
|
glog.Errorf("Error enabling Pod egress: %s", err.Error())
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
glog.V(1).Infoln("Disabling Pod egress.")
|
glog.V(1).Infoln("Disabling Pod egress.")
|
||||||
|
|
||||||
err = deletePodEgressRule()
|
err = nrc.deletePodEgressRule()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Warningf("Error cleaning up Pod Egress related networking: %s", err)
|
glog.Warningf("Error cleaning up Pod Egress related networking: %s", err)
|
||||||
}
|
}
|
||||||
@ -458,18 +459,18 @@ func (nrc *NetworkRoutingController) injectRoute(path *table.Path) error {
|
|||||||
// Cleanup performs the cleanup of configurations done
|
// Cleanup performs the cleanup of configurations done
|
||||||
func (nrc *NetworkRoutingController) Cleanup() {
|
func (nrc *NetworkRoutingController) Cleanup() {
|
||||||
// Pod egress cleanup
|
// Pod egress cleanup
|
||||||
err := deletePodEgressRule()
|
err := nrc.deletePodEgressRule()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Warningf("Error deleting Pod egress iptable rule: %s", err.Error())
|
glog.Warningf("Error deleting Pod egress iptable rule: %s", err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
err = deleteBadPodEgressRules()
|
err = nrc.deleteBadPodEgressRules()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Warningf("Error deleting Pod egress iptable rule: %s", err.Error())
|
glog.Warningf("Error deleting Pod egress iptable rule: %s", err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
// delete all ipsets created by kube-router
|
// delete all ipsets created by kube-router
|
||||||
ipset, err := utils.NewIPSet(false)
|
ipset, err := utils.NewIPSet(nrc.isIpv6)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("Failed to clean up ipsets: " + err.Error())
|
glog.Errorf("Failed to clean up ipsets: " + err.Error())
|
||||||
}
|
}
|
||||||
@ -535,12 +536,20 @@ func (nrc *NetworkRoutingController) syncNodeIPSets() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (nrc *NetworkRoutingController) newIptablesCmdHandler() (*iptables.IPTables, error) {
|
||||||
|
if nrc.isIpv6 {
|
||||||
|
return iptables.NewWithProtocol(iptables.ProtocolIPv6)
|
||||||
|
} else {
|
||||||
|
return iptables.NewWithProtocol(iptables.ProtocolIPv4)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// ensure there is rule in filter table and FORWARD chain to permit in/out traffic from pods
|
// ensure there is rule in filter table and FORWARD chain to permit in/out traffic from pods
|
||||||
// this rules will be appended so that any iptable rules for network policies will take
|
// this rules will be appended so that any iptable rules for network policies will take
|
||||||
// precedence
|
// precedence
|
||||||
func (nrc *NetworkRoutingController) enableForwarding() error {
|
func (nrc *NetworkRoutingController) enableForwarding() error {
|
||||||
|
|
||||||
iptablesCmdHandler, err := iptables.New()
|
iptablesCmdHandler, _ := nrc.newIptablesCmdHandler()
|
||||||
|
|
||||||
comment := "allow outbound traffic from pods"
|
comment := "allow outbound traffic from pods"
|
||||||
args := []string{"-m", "comment", "--comment", comment, "-i", "kube-bridge", "-j", "ACCEPT"}
|
args := []string{"-m", "comment", "--comment", comment, "-i", "kube-bridge", "-j", "ACCEPT"}
|
||||||
@ -661,7 +670,7 @@ func (nrc *NetworkRoutingController) startBgpServer() error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if ipv6IsEnabled() {
|
if ipv6IsEnabled() {
|
||||||
localAddressList = append(localAddressList, "::")
|
localAddressList = append(localAddressList, "::1")
|
||||||
}
|
}
|
||||||
|
|
||||||
global := &config.Global{
|
global := &config.Global{
|
||||||
@ -795,6 +804,21 @@ func NewNetworkRoutingController(clientset kubernetes.Interface,
|
|||||||
nrc.disableSrcDstCheck = kubeRouterConfig.DisableSrcDstCheck
|
nrc.disableSrcDstCheck = kubeRouterConfig.DisableSrcDstCheck
|
||||||
nrc.initSrcDstCheckDone = false
|
nrc.initSrcDstCheckDone = false
|
||||||
|
|
||||||
|
nrc.hostnameOverride = kubeRouterConfig.HostnameOverride
|
||||||
|
node, err := utils.GetNodeObject(clientset, nrc.hostnameOverride)
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.New("Failed getting node object from API server: " + err.Error())
|
||||||
|
}
|
||||||
|
|
||||||
|
nrc.nodeName = node.Name
|
||||||
|
|
||||||
|
nodeIP, err := utils.GetNodeIP(node)
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.New("Failed getting IP address from node object: " + err.Error())
|
||||||
|
}
|
||||||
|
nrc.nodeIP = nodeIP
|
||||||
|
nrc.isIpv6 = nodeIP.To4() == nil
|
||||||
|
|
||||||
// lets start with assumption we hace necessary IAM creds to access EC2 api
|
// lets start with assumption we hace necessary IAM creds to access EC2 api
|
||||||
nrc.ec2IamAuthorized = true
|
nrc.ec2IamAuthorized = true
|
||||||
|
|
||||||
@ -808,7 +832,7 @@ func NewNetworkRoutingController(clientset kubernetes.Interface,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
nrc.ipSetHandler, err = utils.NewIPSet(false)
|
nrc.ipSetHandler, err = utils.NewIPSet(nrc.isIpv6)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@ -872,20 +896,6 @@ func NewNetworkRoutingController(clientset kubernetes.Interface,
|
|||||||
return nil, fmt.Errorf("Error processing Global Peer Router configs: %s", err)
|
return nil, fmt.Errorf("Error processing Global Peer Router configs: %s", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
nrc.hostnameOverride = kubeRouterConfig.HostnameOverride
|
|
||||||
node, err := utils.GetNodeObject(clientset, nrc.hostnameOverride)
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.New("Failed getting node object from API server: " + err.Error())
|
|
||||||
}
|
|
||||||
|
|
||||||
nrc.nodeName = node.Name
|
|
||||||
|
|
||||||
nodeIP, err := utils.GetNodeIP(node)
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.New("Failed getting IP address from node object: " + err.Error())
|
|
||||||
}
|
|
||||||
nrc.nodeIP = nodeIP
|
|
||||||
|
|
||||||
nrc.nodeSubnet, nrc.nodeInterface, err = getNodeSubnet(nodeIP)
|
nrc.nodeSubnet, nrc.nodeInterface, err = getNodeSubnet(nodeIP)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, errors.New("Failed find the subnet of the node IP and interface on" +
|
return nil, errors.New("Failed find the subnet of the node IP and interface on" +
|
||||||
|
@ -4,28 +4,38 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
"github.com/coreos/go-iptables/iptables"
|
|
||||||
"github.com/golang/glog"
|
"github.com/golang/glog"
|
||||||
)
|
)
|
||||||
|
|
||||||
// set up MASQUERADE rule so that egress traffic from the pods gets masquraded to node's IP
|
// set up MASQUERADE rule so that egress traffic from the pods gets masquraded to node's IP
|
||||||
|
|
||||||
var (
|
var (
|
||||||
podEgressArgs = []string{"-m", "set", "--match-set", podSubnetsIPSetName, "src",
|
podEgressArgs4 = []string{"-m", "set", "--match-set", podSubnetsIPSetName, "src",
|
||||||
"-m", "set", "!", "--match-set", podSubnetsIPSetName, "dst",
|
"-m", "set", "!", "--match-set", podSubnetsIPSetName, "dst",
|
||||||
"-m", "set", "!", "--match-set", nodeAddrsIPSetName, "dst",
|
"-m", "set", "!", "--match-set", nodeAddrsIPSetName, "dst",
|
||||||
"-j", "MASQUERADE"}
|
"-j", "MASQUERADE"}
|
||||||
podEgressArgsBad = [][]string{{"-m", "set", "--match-set", podSubnetsIPSetName, "src",
|
podEgressArgs6 = []string{"-m", "set", "--match-set", "inet6:" + podSubnetsIPSetName, "src",
|
||||||
|
"-m", "set", "!", "--match-set", "inet6:" + podSubnetsIPSetName, "dst",
|
||||||
|
"-m", "set", "!", "--match-set", "inet6:" + nodeAddrsIPSetName, "dst",
|
||||||
|
"-j", "MASQUERADE"}
|
||||||
|
podEgressArgsBad4 = [][]string{{"-m", "set", "--match-set", podSubnetsIPSetName, "src",
|
||||||
"-m", "set", "!", "--match-set", podSubnetsIPSetName, "dst",
|
"-m", "set", "!", "--match-set", podSubnetsIPSetName, "dst",
|
||||||
"-j", "MASQUERADE"}}
|
"-j", "MASQUERADE"}}
|
||||||
|
podEgressArgsBad6 = [][]string{{"-m", "set", "--match-set", "inet6:" + podSubnetsIPSetName, "src",
|
||||||
|
"-m", "set", "!", "--match-set", "inet6:" + podSubnetsIPSetName, "dst",
|
||||||
|
"-j", "MASQUERADE"}}
|
||||||
)
|
)
|
||||||
|
|
||||||
func createPodEgressRule() error {
|
func (nrc *NetworkRoutingController) createPodEgressRule() error {
|
||||||
iptablesCmdHandler, err := iptables.New()
|
iptablesCmdHandler, err := nrc.newIptablesCmdHandler()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("Failed create iptables handler:" + err.Error())
|
return errors.New("Failed create iptables handler:" + err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
podEgressArgs := podEgressArgs4
|
||||||
|
if nrc.isIpv6 {
|
||||||
|
podEgressArgs = podEgressArgs6
|
||||||
|
}
|
||||||
err = iptablesCmdHandler.AppendUnique("nat", "POSTROUTING", podEgressArgs...)
|
err = iptablesCmdHandler.AppendUnique("nat", "POSTROUTING", podEgressArgs...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("Failed to add iptable rule to masqurade outbound traffic from pods: " +
|
return errors.New("Failed to add iptable rule to masqurade outbound traffic from pods: " +
|
||||||
@ -37,12 +47,16 @@ func createPodEgressRule() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func deletePodEgressRule() error {
|
func (nrc *NetworkRoutingController) deletePodEgressRule() error {
|
||||||
iptablesCmdHandler, err := iptables.New()
|
iptablesCmdHandler, err := nrc.newIptablesCmdHandler()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("Failed create iptables handler:" + err.Error())
|
return errors.New("Failed create iptables handler:" + err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
podEgressArgs := podEgressArgs4
|
||||||
|
if nrc.isIpv6 {
|
||||||
|
podEgressArgs = podEgressArgs6
|
||||||
|
}
|
||||||
exists, err := iptablesCmdHandler.Exists("nat", "POSTROUTING", podEgressArgs...)
|
exists, err := iptablesCmdHandler.Exists("nat", "POSTROUTING", podEgressArgs...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("Failed to lookup iptable rule to masqurade outbound traffic from pods: " + err.Error())
|
return errors.New("Failed to lookup iptable rule to masqurade outbound traffic from pods: " + err.Error())
|
||||||
@ -60,12 +74,15 @@ func deletePodEgressRule() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func deleteBadPodEgressRules() error {
|
func (nrc *NetworkRoutingController) deleteBadPodEgressRules() error {
|
||||||
iptablesCmdHandler, err := iptables.New()
|
iptablesCmdHandler, err := nrc.newIptablesCmdHandler()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("Failed create iptables handler:" + err.Error())
|
return errors.New("Failed create iptables handler:" + err.Error())
|
||||||
}
|
}
|
||||||
|
podEgressArgsBad := podEgressArgsBad4
|
||||||
|
if nrc.isIpv6 {
|
||||||
|
podEgressArgsBad = podEgressArgsBad6
|
||||||
|
}
|
||||||
for _, args := range podEgressArgsBad {
|
for _, args := range podEgressArgsBad {
|
||||||
exists, err := iptablesCmdHandler.Exists("nat", "POSTROUTING", args...)
|
exists, err := iptablesCmdHandler.Exists("nat", "POSTROUTING", args...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -98,7 +98,7 @@ func getNodeSubnet(nodeIp net.IP) (net.IPNet, string, error) {
|
|||||||
return net.IPNet{}, "", errors.New("Failed to get list of links")
|
return net.IPNet{}, "", errors.New("Failed to get list of links")
|
||||||
}
|
}
|
||||||
for _, link := range links {
|
for _, link := range links {
|
||||||
addresses, err := netlink.AddrList(link, netlink.FAMILY_V4)
|
addresses, err := netlink.AddrList(link, netlink.FAMILY_ALL)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return net.IPNet{}, "", errors.New("Failed to get list of addr")
|
return net.IPNet{}, "", errors.New("Failed to get list of addr")
|
||||||
}
|
}
|
||||||
|
@ -440,7 +440,8 @@ func (set *Set) Swap(setTo *Set) error {
|
|||||||
// Refresh a Set with new entries.
|
// Refresh a Set with new entries.
|
||||||
func (set *Set) Refresh(entries []string, extraOptions ...string) error {
|
func (set *Set) Refresh(entries []string, extraOptions ...string) error {
|
||||||
var err error
|
var err error
|
||||||
tempName := set.Name + "-temp"
|
// The set-name must be < 32 characters!
|
||||||
|
tempName := set.Name + "-"
|
||||||
|
|
||||||
newSet := &Set{
|
newSet := &Set{
|
||||||
Parent: set.Parent,
|
Parent: set.Parent,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user