feat(sysctl): add reapply_sysctl_exclude option
When reapply_sysctl=1 (default), TuneD re-applies all system sysctl settings after profile switches. This breaks Kubernetes overlay networking because CNI plugins set net.ipv4.ip_forward=1 at runtime, which gets overwritten by static /etc/sysctl.d/ files. Add reapply_sysctl_exclude config option to protect specific sysctls from reapplication while maintaining backward compatibility. Supports shell-style wildcards via fnmatch. Example config for Kubernetes: reapply_sysctl_exclude = net.ipv4.ip_forward, net.ipv6.conf.*.forwarding Fixes: #816 Signed-off-by: Matthew Mattox <mmattox@support.tools>
This commit is contained in:
parent
181472a0be
commit
4e300529c9
4 changed files with 44 additions and 0 deletions
|
|
@ -70,6 +70,21 @@ will not override user-provided system sysctl settings. If set to \fBFalse\fR or
|
||||||
\fB0\fR, TuneD sysctl settings will override system sysctl settings. By default
|
\fB0\fR, TuneD sysctl settings will override system sysctl settings. By default
|
||||||
it's set to \fBTrue\fR.
|
it's set to \fBTrue\fR.
|
||||||
|
|
||||||
|
.TP
|
||||||
|
.BI reapply_sysctl_exclude= LIST
|
||||||
|
A comma or semicolon separated list of sysctl parameter patterns to exclude
|
||||||
|
from reapplication when \fBreapply_sysctl\fR is enabled. This is useful for
|
||||||
|
protecting runtime sysctl changes made by Kubernetes CNI plugins or other
|
||||||
|
services that set sysctls dynamically. Supports shell-style wildcards
|
||||||
|
(\fB*\fR, \fB?\fR, \fB[seq]\fR). By default the list is empty.
|
||||||
|
.PP
|
||||||
|
.RS
|
||||||
|
.B Example:
|
||||||
|
.nf
|
||||||
|
reapply_sysctl_exclude = net.ipv4.ip_forward, net.ipv6.conf.*.forwarding
|
||||||
|
.fi
|
||||||
|
.RE
|
||||||
|
|
||||||
.TP
|
.TP
|
||||||
.BI default_instance_priority= INT
|
.BI default_instance_priority= INT
|
||||||
Default instance (unit) priority. By default it's \fB0\fR. Each unit has a
|
Default instance (unit) priority. By default it's \fB0\fR. Each unit has a
|
||||||
|
|
@ -86,6 +101,7 @@ processed as the first.
|
||||||
update_interval = 10
|
update_interval = 10
|
||||||
recommend_command = 0
|
recommend_command = 0
|
||||||
reapply_sysctl = 1
|
reapply_sysctl = 1
|
||||||
|
reapply_sysctl_exclude = net.ipv4.ip_forward, net.bridge.bridge-nf-call-iptables
|
||||||
default_instance_priority = 0
|
default_instance_priority = 0
|
||||||
.fi
|
.fi
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -28,6 +28,14 @@ recommend_command = 1
|
||||||
# override user-provided system sysctls.
|
# override user-provided system sysctls.
|
||||||
reapply_sysctl = 1
|
reapply_sysctl = 1
|
||||||
|
|
||||||
|
# Sysctl parameters matching these patterns will be excluded from
|
||||||
|
# reapplication even when reapply_sysctl is enabled. Useful for
|
||||||
|
# protecting runtime sysctl changes made by Kubernetes CNI plugins
|
||||||
|
# or other services that set sysctls dynamically.
|
||||||
|
# Supports shell-style wildcards (*, ?, [seq]). Separated by , or ;
|
||||||
|
# Example: net.ipv4.ip_forward, net.ipv6.conf.*.forwarding
|
||||||
|
# reapply_sysctl_exclude =
|
||||||
|
|
||||||
# Default priority assigned to instances
|
# Default priority assigned to instances
|
||||||
default_instance_priority = 0
|
default_instance_priority = 0
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -130,6 +130,7 @@ CFG_SLEEP_INTERVAL = "sleep_interval"
|
||||||
CFG_UPDATE_INTERVAL = "update_interval"
|
CFG_UPDATE_INTERVAL = "update_interval"
|
||||||
CFG_RECOMMEND_COMMAND = "recommend_command"
|
CFG_RECOMMEND_COMMAND = "recommend_command"
|
||||||
CFG_REAPPLY_SYSCTL = "reapply_sysctl"
|
CFG_REAPPLY_SYSCTL = "reapply_sysctl"
|
||||||
|
CFG_REAPPLY_SYSCTL_EXCLUDE = "reapply_sysctl_exclude"
|
||||||
CFG_DEFAULT_INSTANCE_PRIORITY = "default_instance_priority"
|
CFG_DEFAULT_INSTANCE_PRIORITY = "default_instance_priority"
|
||||||
CFG_UDEV_BUFFER_SIZE = "udev_buffer_size"
|
CFG_UDEV_BUFFER_SIZE = "udev_buffer_size"
|
||||||
CFG_LOG_FILE_COUNT = "log_file_count"
|
CFG_LOG_FILE_COUNT = "log_file_count"
|
||||||
|
|
@ -166,6 +167,8 @@ CFG_FUNC_RECOMMEND_COMMAND = "getboolean"
|
||||||
# reapply system sysctl
|
# reapply system sysctl
|
||||||
CFG_DEF_REAPPLY_SYSCTL = True
|
CFG_DEF_REAPPLY_SYSCTL = True
|
||||||
CFG_FUNC_REAPPLY_SYSCTL = "getboolean"
|
CFG_FUNC_REAPPLY_SYSCTL = "getboolean"
|
||||||
|
# sysctl parameters to exclude from reapplication
|
||||||
|
CFG_DEF_REAPPLY_SYSCTL_EXCLUDE = []
|
||||||
# default instance priority
|
# default instance priority
|
||||||
CFG_DEF_DEFAULT_INSTANCE_PRIORITY = 0
|
CFG_DEF_DEFAULT_INSTANCE_PRIORITY = 0
|
||||||
CFG_FUNC_DEFAULT_INSTANCE_PRIORITY = "getint"
|
CFG_FUNC_DEFAULT_INSTANCE_PRIORITY = "getint"
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,4 @@
|
||||||
|
import fnmatch
|
||||||
import re
|
import re
|
||||||
from . import base
|
from . import base
|
||||||
from .decorators import *
|
from .decorators import *
|
||||||
|
|
@ -100,6 +101,17 @@ class SysctlPlugin(base.Plugin):
|
||||||
for option, value in list(instance._sysctl_original.items()):
|
for option, value in list(instance._sysctl_original.items()):
|
||||||
self._write_sysctl(option, value)
|
self._write_sysctl(option, value)
|
||||||
|
|
||||||
|
def _is_sysctl_excluded(self, option):
|
||||||
|
"""Check if a sysctl option matches any exclusion pattern."""
|
||||||
|
exclude_list = self._global_cfg.get_list(
|
||||||
|
consts.CFG_REAPPLY_SYSCTL_EXCLUDE,
|
||||||
|
consts.CFG_DEF_REAPPLY_SYSCTL_EXCLUDE
|
||||||
|
)
|
||||||
|
for pattern in exclude_list:
|
||||||
|
if fnmatch.fnmatch(option, pattern):
|
||||||
|
return True
|
||||||
|
return False
|
||||||
|
|
||||||
def _apply_system_sysctl(self, instance_sysctl):
|
def _apply_system_sysctl(self, instance_sysctl):
|
||||||
files = {}
|
files = {}
|
||||||
for d in SYSCTL_CONFIG_DIRS:
|
for d in SYSCTL_CONFIG_DIRS:
|
||||||
|
|
@ -148,6 +160,11 @@ class SysctlPlugin(base.Plugin):
|
||||||
% (path, lineno))
|
% (path, lineno))
|
||||||
return
|
return
|
||||||
value = value.strip()
|
value = value.strip()
|
||||||
|
# Check if this sysctl is excluded from reapplication
|
||||||
|
if self._is_sysctl_excluded(option):
|
||||||
|
log.debug("Skipping excluded sysctl parameter '%s' from '%s'"
|
||||||
|
% (option, path))
|
||||||
|
return
|
||||||
if option in instance_sysctl:
|
if option in instance_sysctl:
|
||||||
instance_value = self._variables.expand(instance_sysctl[option])
|
instance_value = self._variables.expand(instance_sysctl[option])
|
||||||
if instance_value != value:
|
if instance_value != value:
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue