Clarify kubelet/kube-proxy iptables rule skew constraints

This commit is contained in:
Dan Winship 2023-04-13 13:54:52 -04:00
parent 139a2c54a2
commit 2bb35e08f4
3 changed files with 31 additions and 7 deletions

View File

@ -87,6 +87,12 @@ func (kl *Kubelet) syncIPTablesRules(iptClient utiliptables.Interface) bool {
if !iptClient.IsIPv6() { // ipv6 doesn't have this issue if !iptClient.IsIPv6() { // ipv6 doesn't have this issue
// Set up the KUBE-FIREWALL chain and martian packet protection rule. // Set up the KUBE-FIREWALL chain and martian packet protection rule.
// (See below.) // (See below.)
// NOTE: kube-proxy (in iptables mode) creates an identical copy of this
// rule. If you want to change this rule in the future, you MUST do so in
// a way that will interoperate correctly with skewed versions of the rule
// created by kube-proxy.
if _, err := iptClient.EnsureChain(utiliptables.TableFilter, KubeFirewallChain); err != nil { if _, err := iptClient.EnsureChain(utiliptables.TableFilter, KubeFirewallChain); err != nil {
klog.ErrorS(err, "Failed to ensure that filter table KUBE-FIREWALL chain exists") klog.ErrorS(err, "Failed to ensure that filter table KUBE-FIREWALL chain exists")
return false return false
@ -178,8 +184,12 @@ func (kl *Kubelet) syncIPTablesRulesDeprecated(iptClient utiliptables.Interface)
} }
// Set up KUBE-POSTROUTING to unmark and masquerade marked packets // Set up KUBE-POSTROUTING to unmark and masquerade marked packets
// NB: THIS MUST MATCH the corresponding code in the iptables and ipvs
// modes of kube-proxy // NOTE: kube-proxy (in iptables and ipvs modes) creates identical copies of these
// rules. If you want to change these rules in the future, you MUST do so in a way
// that will interoperate correctly with skewed versions of the rules created by
// kube-proxy.
if _, err := iptClient.EnsureRule(utiliptables.Append, utiliptables.TableNAT, KubePostroutingChain, if _, err := iptClient.EnsureRule(utiliptables.Append, utiliptables.TableNAT, KubePostroutingChain,
"-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", masqueradeMark, masqueradeMark), "-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", masqueradeMark, masqueradeMark),
"-j", "RETURN"); err != nil { "-j", "RETURN"); err != nil {

View File

@ -922,7 +922,12 @@ func (proxier *Proxier) syncProxyRules() {
// Install the kubernetes-specific postrouting rules. We use a whole chain for // Install the kubernetes-specific postrouting rules. We use a whole chain for
// this so that it is easier to flush and change, for example if the mark // this so that it is easier to flush and change, for example if the mark
// value should ever change. // value should ever change.
// NB: THIS MUST MATCH the corresponding code in the kubelet
// NOTE: kubelet creates identical copies of these rules. If you want to change
// these rules in the future, you MUST do so in a way that will interoperate
// correctly with skewed versions of the rules created by kubelet. (Remove this
// comment once IPTablesOwnershipCleanup is GA.)
proxier.natRules.Write( proxier.natRules.Write(
"-A", string(kubePostroutingChain), "-A", string(kubePostroutingChain),
"-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", proxier.masqueradeMark, proxier.masqueradeMark), "-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", proxier.masqueradeMark, proxier.masqueradeMark),
@ -956,9 +961,13 @@ func (proxier *Proxier) syncProxyRules() {
// Kube-proxy's use of `route_localnet` to enable NodePorts on localhost // Kube-proxy's use of `route_localnet` to enable NodePorts on localhost
// creates a security hole (https://issue.k8s.io/90259) which this // creates a security hole (https://issue.k8s.io/90259) which this
// iptables rule mitigates. // iptables rule mitigates.
// NB: THIS MUST MATCH the corresponding code in the kubelet. (Actually,
// kubelet uses "--dst"/"--src" rather than "-d"/"-s" but that's just a // NOTE: kubelet creates an identical copy of this rule. If you want to
// command-line thing and results in the same rule being created.) // change this rule in the future, you MUST do so in a way that will
// interoperate correctly with skewed versions of the rule created by
// kubelet. (Actually, kubelet uses "--dst"/"--src" rather than "-d"/"-s"
// but that's just a command-line thing and results in the same rule being
// created in the kernel.)
proxier.filterChains.Write(utiliptables.MakeChainLine(kubeletFirewallChain)) proxier.filterChains.Write(utiliptables.MakeChainLine(kubeletFirewallChain))
proxier.filterRules.Write( proxier.filterRules.Write(
"-A", string(kubeletFirewallChain), "-A", string(kubeletFirewallChain),

View File

@ -1734,7 +1734,12 @@ func (proxier *Proxier) writeIptablesRules() {
// Install the kubernetes-specific postrouting rules. We use a whole chain for // Install the kubernetes-specific postrouting rules. We use a whole chain for
// this so that it is easier to flush and change, for example if the mark // this so that it is easier to flush and change, for example if the mark
// value should ever change. // value should ever change.
// NB: THIS MUST MATCH the corresponding code in the kubelet
// NOTE: kubelet creates identical copies of these rules. If you want to change
// these rules in the future, you MUST do so in a way that will interoperate
// correctly with skewed versions of the rules created by kubelet. (Remove this
// comment once IPTablesOwnershipCleanup is GA.)
proxier.natRules.Write( proxier.natRules.Write(
"-A", string(kubePostroutingChain), "-A", string(kubePostroutingChain),
"-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", proxier.masqueradeMark, proxier.masqueradeMark), "-m", "mark", "!", "--mark", fmt.Sprintf("%s/%s", proxier.masqueradeMark, proxier.masqueradeMark),