diff --git a/tests/unit/plugins/test_base.py b/tests/unit/plugins/test_base.py index 7f59624..af01205 100644 --- a/tests/unit/plugins/test_base.py +++ b/tests/unit/plugins/test_base.py @@ -139,7 +139,7 @@ class PluginBaseTestCase(unittest.TestCase): command = [com for com in self._commands_plugin._commands.values()\ if com['name'] == 'size'][0] - self.assertEqual(self._commands_plugin._get_current_value(command),'S') + self.assertEqual(self._commands_plugin._get_current_value(instance, command),'S') def test_norm_value(self): self.assertEqual(self._plugin._norm_value('"000000021"'),'21') @@ -211,25 +211,25 @@ class CommandsPlugin(Plugin): return {'size':'S','device_setting':'101'} @decorators.command_set('size') - def _set_size(self, new_size, sim, remove): + def _set_size(self, new_size, instance, sim, remove): self._size = new_size return new_size @decorators.command_get('size') - def _get_size(self): + def _get_size(self, instance): return self._size - @decorators.command_set('device_setting',per_device = True) - def _set_device_setting(self,value,device,sim,remove): + @decorators.command_set('device_setting', per_device = True) + def _set_device_setting(self, value, device, instance, sim, remove): device.setting = value return device.setting @decorators.command_get('device_setting') - def _get_device_setting(self,device,ignore_missing = False): + def _get_device_setting(self, device, instance, ignore_missing = False): return device.setting @decorators.command_custom('custom_name') - def the_most_custom_command(self): + def the_most_custom_command(self, instance): return True class BadCommandsPlugin(Plugin): diff --git a/tuned/hardware/inventory.py b/tuned/hardware/inventory.py index 359cfab..5867a4a 100644 --- a/tuned/hardware/inventory.py +++ b/tuned/hardware/inventory.py @@ -41,10 +41,17 @@ class Inventory(object): def get_device(self, subsystem, sys_name): """Get a pyudev.Device object for the sys_name (e.g. 'sda').""" try: - return pyudev.Devices.from_name(self._udev_context, subsystem, sys_name) + try: + d = pyudev.Devices.from_name(self._udev_context, subsystem, sys_name) + except pyudev.DeviceNotFoundByNameError: + d = None # workaround for pyudev < 0.18 except AttributeError: - return pyudev.Device.from_name(self._udev_context, subsystem, sys_name) + try: + d = pyudev.Device.from_name(self._udev_context, subsystem, sys_name) + except pyudev.DeviceNotFoundByNameError: + d = None + return d def get_devices(self, subsystem): """Get list of devices on a given subsystem.""" diff --git a/tuned/monitors/monitor_net.py b/tuned/monitors/monitor_net.py index 2a43520..9dc247f 100644 --- a/tuned/monitors/monitor_net.py +++ b/tuned/monitors/monitor_net.py @@ -30,10 +30,20 @@ class NetMonitor(tuned.monitors.Monitor): return (int) (0.6 * 1024 * 1024 * speed / 8) @classmethod + def _set_dev_map(cls, map_fce): + cls.map_fce = map_fce + + @classmethod + def _dev_map(cls, dev): + try: + return cls.map_fce(dev) + except AttributeError: + return dev + @classmethod def _updateStat(cls, dev): files = ["rx_bytes", "rx_packets", "tx_bytes", "tx_packets"] for i,f in enumerate(files): - cls._load[dev][i] = cmd.read_file("/sys/class/net/" + dev + "/statistics/" + f, err_ret = "0").strip() + cls._load[dev][i] = cmd.read_file("/sys/class/net/" + cls._dev_map(dev) + "/statistics/" + f, err_ret = "0").strip() @classmethod def update(cls): diff --git a/tuned/plugins/base.py b/tuned/plugins/base.py index 501fcff..b6ac8dd 100644 --- a/tuned/plugins/base.py +++ b/tuned/plugins/base.py @@ -504,14 +504,14 @@ class Plugin(object): log.warning("cannot compare new value '%s' with current value '%s' by operator '%s', using '%s' directly as new value" % (val, current_value, op, new_value)) return new_value - def _get_current_value(self, command, device = None, ignore_missing=False): + def _get_current_value(self, instance, command, device = None, ignore_missing=False): if device is not None: - return command["get"](device, ignore_missing=ignore_missing) + return command["get"](device, instance, ignore_missing=ignore_missing) else: - return command["get"]() + return command["get"](instance) def _check_and_save_value(self, instance, command, device = None, new_value = None): - current_value = self._get_current_value(command, device) + current_value = self._get_current_value(instance, command, device) new_value = self._process_assignment_modifiers(new_value, current_value) if new_value is not None and current_value is not None: self._storage_set(instance, command, current_value, device) @@ -519,19 +519,19 @@ class Plugin(object): def _execute_device_command(self, instance, command, device, new_value): if command["custom"] is not None: - command["custom"](True, new_value, device, False, False) + command["custom"](True, new_value, device, False, False, instance) else: new_value = self._check_and_save_value(instance, command, device, new_value) if new_value is not None: - command["set"](new_value, device, sim = False, remove = False) + command["set"](new_value, device, instance, sim = False, remove = False) def _execute_non_device_command(self, instance, command, new_value): if command["custom"] is not None: - command["custom"](True, new_value, False, False) + command["custom"](True, new_value, False, False, instance) else: new_value = self._check_and_save_value(instance, command, None, new_value) if new_value is not None: - command["set"](new_value, sim = False, remove = False) + command["set"](new_value, instance, sim = False, remove = False) def _norm_value(self, value): v = self._cmd.unquote(str(value)) @@ -588,22 +588,22 @@ class Plugin(object): def _verify_device_command(self, instance, command, device, new_value, ignore_missing): if command["custom"] is not None: - return command["custom"](True, new_value, device, True, ignore_missing) - current_value = self._get_current_value(command, device, ignore_missing=ignore_missing) + return command["custom"](True, new_value, device, True, ignore_missing, instance) + current_value = self._get_current_value(instance, command, device, ignore_missing=ignore_missing) new_value = self._process_assignment_modifiers(new_value, current_value) if new_value is None: return None - new_value = command["set"](new_value, device, True, False) + new_value = command["set"](new_value, device, instance, True, False) return self._verify_value(command["name"], new_value, current_value, ignore_missing, device) def _verify_non_device_command(self, instance, command, new_value, ignore_missing): if command["custom"] is not None: - return command["custom"](True, new_value, True, ignore_missing) - current_value = self._get_current_value(command) + return command["custom"](True, new_value, True, ignore_missing, instance) + current_value = self._get_current_value(instance, command) new_value = self._process_assignment_modifiers(new_value, current_value) if new_value is None: return None - new_value = command["set"](new_value, True, False) + new_value = command["set"](new_value, instance, True, False) return self._verify_value(command["name"], new_value, current_value, ignore_missing) def _cleanup_all_non_device_commands(self, instance): @@ -619,18 +619,18 @@ class Plugin(object): def _cleanup_device_command(self, instance, command, device, remove = False): if command["custom"] is not None: - command["custom"](False, None, device, False, False) + command["custom"](False, None, device, False, False, instance) else: old_value = self._storage_get(instance, command, device) if old_value is not None: - command["set"](old_value, device, sim = False, remove = remove) + command["set"](old_value, device, instance, sim = False, remove = remove) self._storage_unset(instance, command, device) def _cleanup_non_device_command(self, instance, command): if command["custom"] is not None: - command["custom"](False, None, False, False) + command["custom"](False, None, False, False, instance) else: old_value = self._storage_get(instance, command) if old_value is not None: - command["set"](old_value, sim = False, remove = False) + command["set"](old_value, instance, sim = False, remove = False) self._storage_unset(instance, command) diff --git a/tuned/plugins/hotplug.py b/tuned/plugins/hotplug.py index 9e392a7..9ce8aab 100644 --- a/tuned/plugins/hotplug.py +++ b/tuned/plugins/hotplug.py @@ -27,11 +27,14 @@ class Plugin(base.Plugin): def _hardware_events_callback(self, event, device): if event == "add": - log.info("device '%s' added" % device.sys_name) + log.info("device '%s', add event" % device.sys_name) self._add_device(device.sys_name) elif event == "remove": - log.info("device '%s' removed" % device.sys_name) + log.info("device '%s', remove event" % device.sys_name) self._remove_device(device.sys_name) + elif event == "move": + log.info("device: '%s', rename event, reported new name" % device.sys_name) + self._move_device(device.sys_name) def _add_device_process(self, instance, device_name): log.info("instance %s: adding new device %s" % (instance.name, device_name)) @@ -78,6 +81,19 @@ class Plugin(base.Plugin): return True return False + def _move_device(self, device_name): + """Rename device in the instance, this probably applies only + to network interfaces. The udev device environment is + mostly unchanged (except the name) and the old device name + isn't announced, thus the rename functionality is plugin + dependant and has to be implemented in the child plugin class. + + Parameters: + device_name -- new name of the device + + """ + pass + def _remove_device(self, device_name): """Remove device from the instance diff --git a/tuned/plugins/plugin_acpi.py b/tuned/plugins/plugin_acpi.py index 04d44d0..61193cc 100644 --- a/tuned/plugins/plugin_acpi.py +++ b/tuned/plugins/plugin_acpi.py @@ -52,7 +52,7 @@ class ACPIPlugin(base.Plugin): return os.path.join(ACPI_DIR, "platform_profile") @command_set("platform_profile") - def _set_platform_profile(self, profiles, sim, remove): + def _set_platform_profile(self, profiles, instance, sim, remove): if not os.path.isfile(self._platform_profile_path()): log.debug("ACPI platform_profile is not supported on this system") return None @@ -70,7 +70,7 @@ class ACPIPlugin(base.Plugin): return None @command_get("platform_profile") - def _get_platform_profile(self, ignore_missing=False): + def _get_platform_profile(self, instance, ignore_missing=False): if not os.path.isfile(self._platform_profile_path()): log.debug("ACPI platform_profile is not supported on this system") return None diff --git a/tuned/plugins/plugin_audio.py b/tuned/plugins/plugin_audio.py index 6f44fe1..e43d420 100644 --- a/tuned/plugins/plugin_audio.py +++ b/tuned/plugins/plugin_audio.py @@ -72,7 +72,7 @@ class AudioPlugin(hotplug.Plugin): return "/sys/module/%s/parameters/power_save_controller" % device @command_set("timeout", per_device = True) - def _set_timeout(self, value, device, sim, remove): + def _set_timeout(self, value, device, instance, sim, remove): try: timeout = int(value) except ValueError: @@ -88,7 +88,7 @@ class AudioPlugin(hotplug.Plugin): return None @command_get("timeout") - def _get_timeout(self, device, ignore_missing=False): + def _get_timeout(self, device, instance, ignore_missing=False): sys_file = self._timeout_path(device) value = cmd.read_file(sys_file, no_error=ignore_missing) if len(value) > 0: @@ -96,7 +96,7 @@ class AudioPlugin(hotplug.Plugin): return None @command_set("reset_controller", per_device = True) - def _set_reset_controller(self, value, device, sim, remove): + def _set_reset_controller(self, value, device, instance, sim, remove): v = cmd.get_bool(value) sys_file = self._reset_controller_path(device) if os.path.exists(sys_file): @@ -107,7 +107,7 @@ class AudioPlugin(hotplug.Plugin): return None @command_get("reset_controller") - def _get_reset_controller(self, device, ignore_missing=False): + def _get_reset_controller(self, device, instance, ignore_missing=False): sys_file = self._reset_controller_path(device) if os.path.exists(sys_file): value = cmd.read_file(sys_file) diff --git a/tuned/plugins/plugin_bootloader.py b/tuned/plugins/plugin_bootloader.py index 99cbb13..86efb42 100644 --- a/tuned/plugins/plugin_bootloader.py +++ b/tuned/plugins/plugin_bootloader.py @@ -562,7 +562,7 @@ class BootloaderPlugin(base.Plugin): return True @command_custom("grub2_cfg_file") - def _grub2_cfg_file(self, enabling, value, verify, ignore_missing): + def _grub2_cfg_file(self, enabling, value, verify, ignore_missing, instance): # nothing to verify if verify: return None @@ -570,7 +570,7 @@ class BootloaderPlugin(base.Plugin): self._grub2_cfg_file_names = [str(value)] @command_custom("initrd_dst_img") - def _initrd_dst_img(self, enabling, value, verify, ignore_missing): + def _initrd_dst_img(self, enabling, value, verify, ignore_missing, instance): # nothing to verify if verify: return None @@ -578,19 +578,24 @@ class BootloaderPlugin(base.Plugin): self._initrd_dst_img_val = str(value) if self._initrd_dst_img_val == "": return False - if self._initrd_dst_img_val[0] != "/": - self._initrd_dst_img_val = os.path.join(consts.BOOT_DIR, self._initrd_dst_img_val) + if self._initrd_dst_img_val[0] == "/": + return False + self._initrd_dst_img_val = os.path.join(consts.BOOT_DIR, self._initrd_dst_img_val) + return True + return None @command_custom("initrd_remove_dir") - def _initrd_remove_dir(self, enabling, value, verify, ignore_missing): + def _initrd_remove_dir(self, enabling, value, verify, ignore_missing, instance): # nothing to verify if verify: return None if enabling and value is not None: self._initrd_remove_dir = self._cmd.get_bool(value) == "1" + return True + return None @command_custom("initrd_add_img", per_device = False, priority = 10) - def _initrd_add_img(self, enabling, value, verify, ignore_missing): + def _initrd_add_img(self, enabling, value, verify, ignore_missing, instance): # nothing to verify if verify: return None @@ -601,9 +606,11 @@ class BootloaderPlugin(base.Plugin): return False if not self._install_initrd(src_img): return False + return True + return None @command_custom("initrd_add_dir", per_device = False, priority = 10) - def _initrd_add_dir(self, enabling, value, verify, ignore_missing): + def _initrd_add_dir(self, enabling, value, verify, ignore_missing, instance): # nothing to verify if verify: return None @@ -631,9 +638,11 @@ class BootloaderPlugin(base.Plugin): if self._initrd_remove_dir: log.info("removing directory '%s'" % src_dir) self._cmd.rmtree(src_dir) + return True + return None @command_custom("cmdline", per_device = False, priority = 10) - def _cmdline(self, enabling, value, verify, ignore_missing): + def _cmdline(self, enabling, value, verify, ignore_missing, instance): v = self._variables.expand(self._cmd.unquote(value)) if verify: if self._rpm_ostree: @@ -664,15 +673,19 @@ class BootloaderPlugin(base.Plugin): log.info("installing additional boot command line parameters to grub2") self.update_grub2_cfg = True self._cmdline_val = v + return True + return None @command_custom("skip_grub_config", per_device = False, priority = 10) - def _skip_grub_config(self, enabling, value, verify, ignore_missing): + def _skip_grub_config(self, enabling, value, verify, ignore_missing, instance): if verify: return None if enabling and value is not None: if self._cmd.get_bool(value) == "1": log.info("skipping any modification of grub config") self._skip_grub_config_val = True + return True + return None def _instance_post_static(self, instance, enabling): if enabling and self._skip_grub_config_val: diff --git a/tuned/plugins/plugin_cpu.py b/tuned/plugins/plugin_cpu.py index b119cd6..53806f4 100644 --- a/tuned/plugins/plugin_cpu.py +++ b/tuned/plugins/plugin_cpu.py @@ -526,7 +526,7 @@ class CPULatencyPlugin(hotplug.Plugin): return self._cmd.read_file("/sys/devices/system/cpu/%s/cpufreq/scaling_available_governors" % device).strip().split() @command_set("governor", per_device=True) - def _set_governor(self, governors, device, sim, remove): + def _set_governor(self, governors, device, instance, sim, remove): if not self._check_cpu_can_change_governor(device): return None governors = str(governors) @@ -555,7 +555,7 @@ class CPULatencyPlugin(hotplug.Plugin): return governor @command_get("governor") - def _get_governor(self, device, ignore_missing=False): + def _get_governor(self, device, instance, ignore_missing=False): governor = None if not self._check_cpu_can_change_governor(device): return None @@ -572,7 +572,7 @@ class CPULatencyPlugin(hotplug.Plugin): return "/sys/devices/system/cpu/cpufreq/%s/sampling_down_factor" % governor @command_set("sampling_down_factor", per_device = True, priority = 10) - def _set_sampling_down_factor(self, sampling_down_factor, device, sim, remove): + def _set_sampling_down_factor(self, sampling_down_factor, device, instance, sim, remove): val = None # hack to clear governors map when the profile starts unloading @@ -599,7 +599,7 @@ class CPULatencyPlugin(hotplug.Plugin): return val @command_get("sampling_down_factor") - def _get_sampling_down_factor(self, device, ignore_missing=False): + def _get_sampling_down_factor(self, device, instance, ignore_missing=False): governor = self._get_governor(device, ignore_missing=ignore_missing) if governor is None: return None @@ -627,7 +627,7 @@ class CPULatencyPlugin(hotplug.Plugin): return "/sys/devices/system/cpu/cpu%s/power/energy_perf_bias" % cpu_id @command_set("energy_perf_bias", per_device=True) - def _set_energy_perf_bias(self, energy_perf_bias, device, sim, remove): + def _set_energy_perf_bias(self, energy_perf_bias, device, instance, sim, remove): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -706,7 +706,7 @@ class CPULatencyPlugin(hotplug.Plugin): }.get(self._try_parse_num(s), s) @command_get("energy_perf_bias") - def _get_energy_perf_bias(self, device, ignore_missing=False): + def _get_energy_perf_bias(self, device, instance, ignore_missing=False): energy_perf_bias = None if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) @@ -741,7 +741,7 @@ class CPULatencyPlugin(hotplug.Plugin): return self._has_pm_qos_resume_latency_us @command_set("pm_qos_resume_latency_us", per_device=True) - def _set_pm_qos_resume_latency_us(self, pm_qos_resume_latency_us, device, sim, remove): + def _set_pm_qos_resume_latency_us(self, pm_qos_resume_latency_us, device, instance, sim, remove): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -757,7 +757,7 @@ class CPULatencyPlugin(hotplug.Plugin): return latency @command_get("pm_qos_resume_latency_us") - def _get_pm_qos_resume_latency_us(self, device, ignore_missing=False): + def _get_pm_qos_resume_latency_us(self, device, instance, ignore_missing=False): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -766,7 +766,7 @@ class CPULatencyPlugin(hotplug.Plugin): return self._cmd.read_file(self._pm_qos_resume_latency_us_path(device), no_error=ignore_missing).strip() @command_set("boost", per_device=True) - def _set_boost(self, boost, device, sim, remove): + def _set_boost(self, boost, device, instance, sim, remove): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -785,7 +785,7 @@ class CPULatencyPlugin(hotplug.Plugin): return None @command_get("boost") - def _get_boost(self, device, ignore_missing=False): + def _get_boost(self, device, instance, ignore_missing=False): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -797,7 +797,7 @@ class CPULatencyPlugin(hotplug.Plugin): return None @command_set("energy_performance_preference", per_device=True) - def _set_energy_performance_preference(self, energy_performance_preference, device, sim, remove): + def _set_energy_performance_preference(self, energy_performance_preference, device, instance, sim, remove): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None @@ -823,7 +823,7 @@ class CPULatencyPlugin(hotplug.Plugin): return None @command_get("energy_performance_preference") - def _get_energy_performance_preference(self, device, ignore_missing=False): + def _get_energy_performance_preference(self, device, instance, ignore_missing=False): if not self._is_cpu_online(device): log.debug("%s is not online, skipping" % device) return None diff --git a/tuned/plugins/plugin_disk.py b/tuned/plugins/plugin_disk.py index 99a2eb4..f4d94d9 100644 --- a/tuned/plugins/plugin_disk.py +++ b/tuned/plugins/plugin_disk.py @@ -335,7 +335,7 @@ class DiskPlugin(hotplug.Plugin): return self._sysfs_path(device, "queue/scheduler") @command_set("elevator", per_device=True) - def _set_elevator(self, value, device, sim, remove): + def _set_elevator(self, value, device, instance, sim, remove): sys_file = self._elevator_file(device) if not sim: self._cmd.write_to_file(sys_file, value, \ @@ -343,14 +343,14 @@ class DiskPlugin(hotplug.Plugin): return value @command_get("elevator") - def _get_elevator(self, device, ignore_missing=False): + def _get_elevator(self, device, instance, ignore_missing=False): sys_file = self._elevator_file(device) # example of scheduler file content: # noop deadline [cfq] return self._cmd.get_active_option(self._cmd.read_file(sys_file, no_error=ignore_missing)) @command_set("apm", per_device=True) - def _set_apm(self, value, device, sim, remove): + def _set_apm(self, value, device, instance, sim, remove): if not self._is_hdparm_apm_supported(device): if not sim: log.info("apm option is not supported for device '%s'" % device) @@ -366,7 +366,7 @@ class DiskPlugin(hotplug.Plugin): return None @command_get("apm") - def _get_apm(self, device, ignore_missing=False): + def _get_apm(self, device, instance, ignore_missing=False): if not self._is_hdparm_apm_supported(device): if not ignore_missing: log.info("apm option is not supported for device '%s'" % device) @@ -390,7 +390,7 @@ class DiskPlugin(hotplug.Plugin): return value @command_set("spindown", per_device=True) - def _set_spindown(self, value, device, sim, remove): + def _set_spindown(self, value, device, instance, sim, remove): if not self._is_hdparm_apm_supported(device): if not sim: log.info("spindown option is not supported for device '%s'" % device) @@ -406,7 +406,7 @@ class DiskPlugin(hotplug.Plugin): return None @command_get("spindown") - def _get_spindown(self, device, ignore_missing=False): + def _get_spindown(self, device, instance, ignore_missing=False): if not self._is_hdparm_apm_supported(device): if not ignore_missing: log.info("spindown option is not supported for device '%s'" % device) @@ -429,7 +429,7 @@ class DiskPlugin(hotplug.Plugin): return v @command_set("readahead", per_device=True) - def _set_readahead(self, value, device, sim, remove): + def _set_readahead(self, value, device, instance, sim, remove): sys_file = self._readahead_file(device) val = self._parse_ra(value) if val is None: @@ -441,7 +441,7 @@ class DiskPlugin(hotplug.Plugin): return val @command_get("readahead") - def _get_readahead(self, device, ignore_missing=False): + def _get_readahead(self, device, instance, ignore_missing=False): sys_file = self._readahead_file(device) value = self._cmd.read_file(sys_file, no_error=ignore_missing).strip() if len(value) == 0: @@ -449,7 +449,7 @@ class DiskPlugin(hotplug.Plugin): return int(value) @command_custom("readahead_multiply", per_device=True) - def _multiply_readahead(self, enabling, multiplier, device, verify, ignore_missing): + def _multiply_readahead(self, enabling, multiplier, device, verify, ignore_missing, instance): if verify: return None storage_key = self._storage_key( @@ -473,7 +473,7 @@ class DiskPlugin(hotplug.Plugin): return self._sysfs_path(device, "queue/iosched/quantum") @command_set("scheduler_quantum", per_device=True) - def _set_scheduler_quantum(self, value, device, sim, remove): + def _set_scheduler_quantum(self, value, device, instance, sim, remove): sys_file = self._scheduler_quantum_file(device) if not sim: self._cmd.write_to_file(sys_file, "%d" % int(value), \ @@ -481,7 +481,7 @@ class DiskPlugin(hotplug.Plugin): return value @command_get("scheduler_quantum") - def _get_scheduler_quantum(self, device, ignore_missing=False): + def _get_scheduler_quantum(self, device, instance, ignore_missing=False): sys_file = self._scheduler_quantum_file(device) value = self._cmd.read_file(sys_file, no_error=ignore_missing).strip() if len(value) == 0: diff --git a/tuned/plugins/plugin_irq.py b/tuned/plugins/plugin_irq.py index 0a6ec3d..7ffdea5 100644 --- a/tuned/plugins/plugin_irq.py +++ b/tuned/plugins/plugin_irq.py @@ -248,7 +248,7 @@ class IrqPlugin(hotplug.Plugin): # command definitions: entry to device-specific tuning # @command_custom("mode", per_device=False, priority=-10) - def _mode(self, enabling, value, verify, ignore_missing): + def _mode(self, enabling, value, verify, ignore_missing, instance): if (enabling or verify) and value is not None: # Store the operating mode of the current instance in the plugin # object, from where it is read by the "affinity" command. @@ -256,7 +256,7 @@ class IrqPlugin(hotplug.Plugin): self._mode_val = value @command_custom("affinity", per_device=True) - def _affinity(self, enabling, value, device, verify, ignore_missing): + def _affinity(self, enabling, value, device, verify, ignore_missing, instance): irq = "DEFAULT" if device == "DEFAULT" else device[len("irq"):] if irq not in self._irqs: log.error("Unknown device: %s" % device) diff --git a/tuned/plugins/plugin_irqbalance.py b/tuned/plugins/plugin_irqbalance.py index e9225e1..afd5524 100644 --- a/tuned/plugins/plugin_irqbalance.py +++ b/tuned/plugins/plugin_irqbalance.py @@ -101,7 +101,7 @@ class IrqbalancePlugin(base.Plugin): self._restart_irqbalance() @command_custom("banned_cpus", per_device=False) - def _banned_cpus(self, enabling, value, verify, ignore_missing): + def _banned_cpus(self, enabling, value, verify, ignore_missing, instance): banned_cpulist_string = None if value is not None: banned = set(self._cmd.cpulist_unpack(value)) diff --git a/tuned/plugins/plugin_mounts.py b/tuned/plugins/plugin_mounts.py index 2361d6f..62c8e2c 100644 --- a/tuned/plugins/plugin_mounts.py +++ b/tuned/plugins/plugin_mounts.py @@ -129,7 +129,7 @@ class MountsPlugin(base.Plugin): cmd.execute(remount_command) @command_custom("disable_barriers", per_device=True) - def _disable_barriers(self, start, value, mountpoint, verify, ignore_missing): + def _disable_barriers(self, start, value, mountpoint, verify, ignore_missing, instance): storage_key = self._storage_key( command_name = "disable_barriers", device_name = mountpoint) diff --git a/tuned/plugins/plugin_net.py b/tuned/plugins/plugin_net.py index e3480df..bbcd8a3 100644 --- a/tuned/plugins/plugin_net.py +++ b/tuned/plugins/plugin_net.py @@ -6,6 +6,7 @@ from tuned.utils.nettool import ethcard from tuned.utils.commands import commands import os import re +import pyudev log = tuned.logs.get() @@ -167,15 +168,21 @@ class NetTuningPlugin(hotplug.Plugin): self._cmd = commands() self._re_ip_link_show = {} self._use_ip = True + self.re_not_virtual = re.compile('(?!.*/virtual/.*)') + # pyudev >= 0.21 check + if hasattr(pyudev.Device, "properties"): + self._get_device_property = self._get_device_property_1 + else: + self._get_device_property = self._get_device_property_2 def _init_devices(self): + super(NetTuningPlugin, self)._init_devices() self._devices_supported = True self._free_devices = set() self._assigned_devices = set() - re_not_virtual = re.compile('(?!.*/virtual/.*)') for device in self._hardware_inventory.get_devices("net"): - if re_not_virtual.match(device.device_path): + if self._device_is_supported(device): self._free_devices.add(device.sys_name) log.debug("devices: %s" % str(self._free_devices)); @@ -183,13 +190,83 @@ class NetTuningPlugin(hotplug.Plugin): def _get_device_objects(self, devices): return [self._hardware_inventory.get_device("net", x) for x in devices] + def _device_is_supported(self, device): + return self.re_not_virtual.match(device.device_path) + + def _hardware_events_init(self): + self._hardware_inventory.subscribe(self, "net", self._hardware_events_callback) + + def _hardware_events_cleanup(self): + self._hardware_inventory.unsubscribe(self) + + def _hardware_events_callback(self, event, device): + if self._device_is_supported(device): + super(NetTuningPlugin, self)._hardware_events_callback(event, device) + + def _added_device_apply_tuning(self, instance, device_name): + if instance._load_monitor is not None: + instance._load_monitor.add_device(device_name) + super(NetTuningPlugin, self)._added_device_apply_tuning(instance, device_name) + + def _removed_device_unapply_tuning(self, instance, device_name): + if instance._load_monitor is not None: + instance._load_monitor.remove_device(device_name) + super(NetTuningPlugin, self)._removed_device_unapply_tuning(instance, device_name) + + # pyudev >= 0.21 + def _get_device_property_1(self, pyudev_dev, prop): + return pyudev_dev.properties.get(prop) + + # pyudev < 0.21 + def _get_device_property_2(self, pyudev_dev, prop): + try: + p = pyudev_dev.__getitem__(prop) + except KeyError: + p = None + return p + + # handle device rename + def _move_device(self, device_name): + d = self._hardware_inventory.get_device("net", device_name) + if d: + i = self._get_device_property(d, "IFINDEX") + if i: + for instance_name, instance in list(self._instances.items()): + device_name_old = instance._ifmap_orig.get(i) + if device_name_old: + log.debug("Rename device, ifindex: '%s', original name '%s', new name '%s'" % \ + (i, device_name_old, device_name)) + instance._ifnamemap[device_name_old] = device_name + break + + def _get_curr_device_wrapper(self, instance): + # get new device name after rename + def _get_curr_device(device): + d = instance._ifnamemap.get(device) + return d if d else device + + return _get_curr_device + def _instance_init(self, instance): instance._has_static_tuning = True instance._load_monitor = None instance._idle = None instance._stats = None + instance._ifnamemap = {} + instance._get_curr_device = self._get_curr_device_wrapper(instance) instance._has_dynamic_tuning = self._option_bool(instance.options["dynamic"]) + def assign_free_devices(self, instance): + super(NetTuningPlugin, self).assign_free_devices(instance) + instance._ifmap_orig = {} + devices = instance.assigned_devices + for device in devices: + d = self._hardware_inventory.get_device("net", device) + if d: + i = self._get_device_property(d, "IFINDEX") + if i: + instance._ifmap_orig[i] = device + def _instance_cleanup(self, instance): if instance._load_monitor is not None: self._monitors_repository.delete(instance._load_monitor) @@ -200,6 +277,7 @@ class NetTuningPlugin(hotplug.Plugin): instance._idle = {} instance._stats = {} instance._load_monitor = self._monitors_repository.create("net", instance.assigned_devices) + instance._load_monitor._set_dev_map(instance._get_curr_device) def _instance_apply_dynamic(self, instance, device): self._instance_update_dynamic(instance, device) @@ -292,7 +370,7 @@ class NetTuningPlugin(hotplug.Plugin): } def _init_stats_and_idle(self, instance, device): - max_speed = self._calc_speed(ethcard(device).get_max_speed()) + max_speed = self._calc_speed(ethcard(instance._get_curr_device(device)).get_max_speed()) instance._stats[device] = { "new": 4 * [0], "max": 2 * [max_speed, 1] } instance._idle[device] = { "level": 0, "read": 0, "write": 0 } @@ -326,7 +404,7 @@ class NetTuningPlugin(hotplug.Plugin): if device in instance._idle and instance._idle[device]["level"] > 0: instance._idle[device]["level"] = 0 log.info("%s: setting max speed" % device) - ethcard(device).set_max_speed() + ethcard(instance._get_curr_device(device)).set_max_speed() def _calc_speed(self, speed): # 0.6 is just a magical constant (empirical value): Typical workload on netcard won't exceed @@ -389,7 +467,7 @@ class NetTuningPlugin(hotplug.Plugin): return "/sys/module/nf_conntrack/parameters/hashsize" @command_set("wake_on_lan", per_device=True) - def _set_wake_on_lan(self, value, device, sim, remove): + def _set_wake_on_lan(self, value, device, instance, sim, remove): if value is None: return None @@ -400,14 +478,15 @@ class NetTuningPlugin(hotplug.Plugin): return None if not sim: - self._cmd.execute(["ethtool", "-s", device, "wol", value]) + self._cmd.execute(["ethtool", "-s", instance._get_curr_device(device), "wol", value]) return value @command_get("wake_on_lan") - def _get_wake_on_lan(self, device, ignore_missing=False): + def _get_wake_on_lan(self, device, instance, ignore_missing=False): value = None try: - m = re.match(r".*Wake-on:\s*([" + WOL_VALUES + "]+).*", self._cmd.execute(["ethtool", device])[1], re.S) + m = re.match(r".*Wake-on:\s*([" + WOL_VALUES + "]+).*", + self._cmd.execute(["ethtool", instance._get_curr_device(device)])[1], re.S) if m: value = m.group(1) except IOError: @@ -415,7 +494,7 @@ class NetTuningPlugin(hotplug.Plugin): return value @command_set("nf_conntrack_hashsize") - def _set_nf_conntrack_hashsize(self, value, sim, remove): + def _set_nf_conntrack_hashsize(self, value, instance, sim, remove): if value is None: return None @@ -429,7 +508,7 @@ class NetTuningPlugin(hotplug.Plugin): return None @command_get("nf_conntrack_hashsize") - def _get_nf_conntrack_hashsize(self): + def _get_nf_conntrack_hashsize(self, instance): value = self._cmd.read_file(self._nf_conntrack_hashsize_path()) if len(value) > 0: return int(value) @@ -457,7 +536,7 @@ class NetTuningPlugin(hotplug.Plugin): return self._call_ip_link(args) @command_set("txqueuelen", per_device=True) - def _set_txqueuelen(self, value, device, sim, remove): + def _set_txqueuelen(self, value, device, instance, sim, remove): if value is None: return None try: @@ -467,9 +546,9 @@ class NetTuningPlugin(hotplug.Plugin): return None if not sim: # there is inconsistency in "ip", where "txqueuelen" is set as it, but is shown as "qlen" - res = self._call_ip_link(["set", "dev", device, "txqueuelen", value]) + res = self._call_ip_link(["set", "dev", instance._get_curr_device(device), "txqueuelen", value]) if res is None: - log.warning("Cannot set txqueuelen for device '%s'" % device) + log.warning("Cannot set txqueuelen for device '%s'" % instance._get_curr_device(device)) return None return value @@ -482,22 +561,24 @@ class NetTuningPlugin(hotplug.Plugin): return self._re_ip_link_show[arg] @command_get("txqueuelen") - def _get_txqueuelen(self, device, ignore_missing=False): - out = self._ip_link_show(device) + def _get_txqueuelen(self, device, instance, ignore_missing=False): + out = self._ip_link_show(instance._get_curr_device(device)) if out is None: if not ignore_missing: - log.info("Cannot get 'ip link show' result for txqueuelen value for device '%s'" % device) + log.info("Cannot get 'ip link show' result for txqueuelen value for device '%s'" % \ + instance._get_curr_device(device)) return None res = self._get_re_ip_link_show("qlen").search(out) if res is None: # We can theoretically get device without qlen (http://linux-ip.net/gl/ip-cref/ip-cref-node17.html) if not ignore_missing: - log.info("Cannot get txqueuelen value from 'ip link show' result for device '%s'" % device) + log.info("Cannot get txqueuelen value from 'ip link show' result for device '%s'" % \ + instance._get_curr_device(device)) return None return res.group(1) @command_set("mtu", per_device=True) - def _set_mtu(self, value, device, sim, remove): + def _set_mtu(self, value, device, instance, sim, remove): if value is None: return None try: @@ -506,24 +587,26 @@ class NetTuningPlugin(hotplug.Plugin): log.warning("mtu value '%s' is not integer" % value) return None if not sim: - res = self._call_ip_link(["set", "dev", device, "mtu", value]) + res = self._call_ip_link(["set", "dev", instance._get_curr_device(device), "mtu", value]) if res is None: - log.warning("Cannot set mtu for device '%s'" % device) + log.warning("Cannot set mtu for device '%s'" % instance._get_curr_device(device)) return None return value @command_get("mtu") - def _get_mtu(self, device, ignore_missing=False): - out = self._ip_link_show(device) + def _get_mtu(self, device, instance, ignore_missing=False): + out = self._ip_link_show(instance._get_curr_device(device)) if out is None: if not ignore_missing: - log.info("Cannot get 'ip link show' result for mtu value for device '%s'" % device) + log.info("Cannot get 'ip link show' result for mtu value for device '%s'" % \ + instance._get_curr_device(device)) return None res = self._get_re_ip_link_show("mtu").search(out) if res is None: # mtu value should be always present, but it's better to have a test if not ignore_missing: - log.info("Cannot get mtu value from 'ip link show' result for device '%s'" % device) + log.info("Cannot get mtu value from 'ip link show' result for device '%s'" % \ + instance._get_curr_device(device)) return None return res.group(1) @@ -589,10 +672,11 @@ class NetTuningPlugin(hotplug.Plugin): mod_params_list.extend(["combined", cnt]) return dict(list(zip(mod_params_list[::2], mod_params_list[1::2]))) - def _check_device_support(self, context, parameters, device, dev_params): + def _check_device_support(self, instance, context, parameters, device, dev_params): """Filter unsupported parameters and log warnings about it Positional parameters: + instance -- instance calling it context -- context of change parameters -- parameters to change device -- name of device on which should be parameters set @@ -608,15 +692,15 @@ class NetTuningPlugin(hotplug.Plugin): log.warning("%s parameter %s is not supported by device %s" % ( context, param, - device, + instance._get_curr_device(device), )) parameters.pop(param, None) - def _get_device_parameters(self, context, device): + def _get_device_parameters(self, instance, context, device): context2opt = { "coalesce": "-c", "features": "-k", "pause": "-a", "ring": "-g", \ "channels": "-l"} opt = context2opt[context] - ret, value = self._cmd.execute(["ethtool", opt, device]) + ret, value = self._cmd.execute(["ethtool", opt, instance._get_curr_device(device)]) if ret != 0 or len(value) == 0: return None context2parser = { "coalesce": self._parse_device_parameters, \ @@ -630,7 +714,7 @@ class NetTuningPlugin(hotplug.Plugin): return None return d - def _set_device_parameters(self, context, value, device, sim, + def _set_device_parameters(self, instance, context, value, device, sim, dev_params = None): if value is None or len(value) == 0: return None @@ -639,7 +723,7 @@ class NetTuningPlugin(hotplug.Plugin): return {} # check if device supports parameters and filter out unsupported ones if dev_params: - self._check_device_support(context, d, device, dev_params) + self._check_device_support(instance, context, d, device, dev_params) # replace the channel parameters based on the device support if context == "channels" and str(dev_params[next(iter(d))]) in ["n/a", "0"]: d = self._replace_channels_parameters(context, self._cmd.dict2list(d), dev_params) @@ -650,19 +734,19 @@ class NetTuningPlugin(hotplug.Plugin): "channels": "-L"} opt = context2opt[context] # ignore ethtool return code 80, it means parameter is already set - self._cmd.execute(["ethtool", opt, device] + self._cmd.dict2list(d), no_errors = [80]) + self._cmd.execute(["ethtool", opt, instance._get_curr_device(device)] + \ + self._cmd.dict2list(d), no_errors = [80]) return d - def _custom_parameters(self, context, start, value, device, verify): + def _custom_parameters(self, context, start, value, device, verify, instance): storage_key = self._storage_key( command_name = context, device_name = device) if start: - params_current = self._get_device_parameters(context, - device) + params_current = self._get_device_parameters(instance, context, device) if params_current is None or len(params_current) == 0: return False - params_set = self._set_device_parameters(context, + params_set = self._set_device_parameters(instance, context, value, device, verify, dev_params = params_current) # if none of parameters passed checks then the command completely @@ -679,7 +763,7 @@ class NetTuningPlugin(hotplug.Plugin): self._log_verification_result(context, res, params_set, relevant_params_current, - device = device) + device = instance._get_curr_device(device)) return res # saved are only those parameters which passed checks self._storage.set(storage_key, " ".join( @@ -688,25 +772,25 @@ class NetTuningPlugin(hotplug.Plugin): original_value = self._storage.get(storage_key) # in storage are only those parameters which were already tested # so skip check for supported parameters - self._set_device_parameters(context, original_value, device, False) + self._set_device_parameters(instance, context, original_value, device, False) return None @command_custom("features", per_device = True) - def _features(self, start, value, device, verify, ignore_missing): - return self._custom_parameters("features", start, value, device, verify) + def _features(self, start, value, device, verify, ignore_missing, instance): + return self._custom_parameters("features", start, value, device, verify, instance) @command_custom("coalesce", per_device = True) - def _coalesce(self, start, value, device, verify, ignore_missing): - return self._custom_parameters("coalesce", start, value, device, verify) + def _coalesce(self, start, value, device, verify, ignore_missing, instance): + return self._custom_parameters("coalesce", start, value, device, verify, instance) @command_custom("pause", per_device = True) - def _pause(self, start, value, device, verify, ignore_missing): - return self._custom_parameters("pause", start, value, device, verify) + def _pause(self, start, value, device, verify, ignore_missing, instance): + return self._custom_parameters("pause", start, value, device, verify, instance) @command_custom("ring", per_device = True) - def _ring(self, start, value, device, verify, ignore_missing): - return self._custom_parameters("ring", start, value, device, verify) + def _ring(self, start, value, device, verify, ignore_missing, instance): + return self._custom_parameters("ring", start, value, device, verify, instance) @command_custom("channels", per_device = True) - def _channels(self, start, value, device, verify, ignore_missing): - return self._custom_parameters("channels", start, value, device, verify) + def _channels(self, start, value, device, verify, ignore_missing, instance): + return self._custom_parameters("channels", start, value, device, verify, instance) diff --git a/tuned/plugins/plugin_scheduler.py b/tuned/plugins/plugin_scheduler.py index e5dc3d5..05ac85f 100644 --- a/tuned/plugins/plugin_scheduler.py +++ b/tuned/plugins/plugin_scheduler.py @@ -1110,7 +1110,7 @@ class SchedulerPlugin(base.Plugin): self._remove_pid(instance, int(event.tid)) @command_custom("cgroup_ps_blacklist", per_device = False) - def _cgroup_ps_blacklist(self, enabling, value, verify, ignore_missing): + def _cgroup_ps_blacklist(self, enabling, value, verify, ignore_missing, instance): # currently unsupported if verify: return None @@ -1118,7 +1118,7 @@ class SchedulerPlugin(base.Plugin): self._cgroup_ps_blacklist_re = "|".join(["(%s)" % v for v in re.split(r"(? 0: return int(value) diff --git a/tuned/plugins/plugin_systemd.py b/tuned/plugins/plugin_systemd.py index cbc4855..5583588 100644 --- a/tuned/plugins/plugin_systemd.py +++ b/tuned/plugins/plugin_systemd.py @@ -122,7 +122,7 @@ class SystemdPlugin(base.Plugin): return " ".join(str(v) for v in self._cmd.cpulist_unpack(re.sub(r"\s+", r",", re.sub(r",\s+", r",", cpulist)))) @command_custom("cpu_affinity", per_device = False) - def _cmdline(self, enabling, value, verify, ignore_missing): + def _cmdline(self, enabling, value, verify, ignore_missing, instance): conf_affinity = None conf_affinity_unpacked = None v = self._cmd.unescape(self._variables.expand(self._cmd.unquote(value))) @@ -141,3 +141,6 @@ class SystemdPlugin(base.Plugin): log.info("setting '%s' to '%s' in the '%s'" % (consts.SYSTEMD_CPUAFFINITY_VAR, v_unpacked, consts.SYSTEMD_SYSTEM_CONF_FILE)) self._write_systemd_system_conf(self._add_keyval(conf, consts.SYSTEMD_CPUAFFINITY_VAR, v_unpacked)) + return True + return None + diff --git a/tuned/plugins/plugin_uncore.py b/tuned/plugins/plugin_uncore.py index fe18762..ac8be72 100644 --- a/tuned/plugins/plugin_uncore.py +++ b/tuned/plugins/plugin_uncore.py @@ -166,7 +166,7 @@ class UncorePlugin(hotplug.Plugin): return self._validate_khz_value(device, min_or_max, khz) @command_set("max_freq_khz", per_device = True) - def _set_max_freq_khz(self, value, device, sim, remove): + def _set_max_freq_khz(self, value, device, instance, sim, remove): max_freq_khz = self._validate_value(device, IS_MAX, value) if max_freq_khz is None: return None @@ -178,7 +178,7 @@ class UncorePlugin(hotplug.Plugin): return self._set(device, "max_freq_khz", max_freq_khz) @command_get("max_freq_khz") - def _get_max_freq_khz(self, device, ignore_missing=False): + def _get_max_freq_khz(self, device, instance, ignore_missing=False): if ignore_missing and not os.path.isdir(SYSFS_DIR): return None @@ -192,7 +192,7 @@ class UncorePlugin(hotplug.Plugin): return max_freq_khz @command_set("min_freq_khz", per_device = True) - def _set_min_freq_khz(self, value, device, sim, remove): + def _set_min_freq_khz(self, value, device, instance, sim, remove): min_freq_khz = self._validate_value(device, IS_MIN, value) if min_freq_khz is None: return None @@ -204,7 +204,7 @@ class UncorePlugin(hotplug.Plugin): return self._set(device, "min_freq_khz", min_freq_khz) @command_get("min_freq_khz") - def _get_min_freq_khz(self, device, ignore_missing=False): + def _get_min_freq_khz(self, device, instance, ignore_missing=False): if ignore_missing and not os.path.isdir(SYSFS_DIR): return None diff --git a/tuned/plugins/plugin_usb.py b/tuned/plugins/plugin_usb.py index 9107126..8e5c2d2 100644 --- a/tuned/plugins/plugin_usb.py +++ b/tuned/plugins/plugin_usb.py @@ -56,7 +56,7 @@ class USBPlugin(base.Plugin): return "/sys/bus/usb/devices/%s/power/autosuspend" % device @command_set("autosuspend", per_device=True) - def _set_autosuspend(self, value, device, sim, remove): + def _set_autosuspend(self, value, device, instance, sim, remove): enable = self._option_bool(value) if enable is None: return None @@ -69,6 +69,6 @@ class USBPlugin(base.Plugin): return val @command_get("autosuspend") - def _get_autosuspend(self, device, ignore_missing=False): + def _get_autosuspend(self, device, instance, ignore_missing=False): sys_file = self._autosuspend_sysfile(device) return self._cmd.read_file(sys_file, no_error=ignore_missing).strip() diff --git a/tuned/plugins/plugin_video.py b/tuned/plugins/plugin_video.py index 751b479..b71097a 100644 --- a/tuned/plugins/plugin_video.py +++ b/tuned/plugins/plugin_video.py @@ -107,7 +107,7 @@ class VideoPlugin(base.Plugin): return None @command_set("radeon_powersave", per_device=True) - def _set_radeon_powersave(self, value, device, sim, remove): + def _set_radeon_powersave(self, value, device, instance, sim, remove): sys_files = self._files(device) va = str(re.sub(r"(\s*:\s*)|(\s+)|(\s*;\s*)|(\s*,\s*)", " ", value)).split() if not os.path.exists(sys_files["method"]): @@ -143,7 +143,7 @@ class VideoPlugin(base.Plugin): return None @command_get("radeon_powersave") - def _get_radeon_powersave(self, device, ignore_missing = False): + def _get_radeon_powersave(self, device, instance, ignore_missing = False): sys_files = self._files(device) if not os.path.exists(sys_files["method"]): log.debug("radeon_powersave is not supported on '%s'" % device) @@ -159,7 +159,7 @@ class VideoPlugin(base.Plugin): return None @command_set("panel_power_savings", per_device=True) - def _set_panel_power_savings(self, value, device, sim, remove): + def _set_panel_power_savings(self, value, device, instance, sim, remove): """Set the panel_power_savings value""" try: value = int(value, 10) @@ -173,7 +173,7 @@ class VideoPlugin(base.Plugin): return None @command_get("panel_power_savings") - def _get_panel_power_savings(self, device, ignore_missing=False): + def _get_panel_power_savings(self, device, instance, ignore_missing=False): """Get the current panel_power_savings value""" if not os.path.exists(self._files(device)["panel_power_savings"]): log.debug("panel_power_savings is not supported on '%s'" % device) diff --git a/tuned/plugins/plugin_vm.py b/tuned/plugins/plugin_vm.py index a671e17..c4b50f3 100644 --- a/tuned/plugins/plugin_vm.py +++ b/tuned/plugins/plugin_vm.py @@ -77,7 +77,7 @@ class VMPlugin(base.Plugin): return path @command_set("transparent_hugepages") - def _set_transparent_hugepages(self, value, sim, remove): + def _set_transparent_hugepages(self, value, instance, sim, remove): if value not in ["always", "never", "madvise"]: if not sim: log.warning("Incorrect 'transparent_hugepages' value '%s'." % str(value)) @@ -102,11 +102,11 @@ class VMPlugin(base.Plugin): # just an alias to transparent_hugepages @command_set("transparent_hugepage") - def _set_transparent_hugepage(self, value, sim, remove): + def _set_transparent_hugepage(self, value, instance, sim, remove): self._set_transparent_hugepages(value, sim, remove) @command_get("transparent_hugepages") - def _get_transparent_hugepages(self): + def _get_transparent_hugepages(self, instance): sys_file = os.path.join(self._thp_path(), "enabled") if os.path.exists(sys_file): return cmd.get_active_option(cmd.read_file(sys_file)) @@ -115,11 +115,11 @@ class VMPlugin(base.Plugin): # just an alias to transparent_hugepages @command_get("transparent_hugepage") - def _get_transparent_hugepage(self): + def _get_transparent_hugepage(self, instance): return self._get_transparent_hugepages() @command_set("transparent_hugepage.defrag") - def _set_transparent_hugepage_defrag(self, value, sim, remove): + def _set_transparent_hugepage_defrag(self, value, instance, sim, remove): sys_file = os.path.join(self._thp_path(), "defrag") if os.path.exists(sys_file): if not sim: @@ -132,7 +132,7 @@ class VMPlugin(base.Plugin): return None @command_get("transparent_hugepage.defrag") - def _get_transparent_hugepage_defrag(self): + def _get_transparent_hugepage_defrag(self, instance): sys_file = os.path.join(self._thp_path(), "defrag") if os.path.exists(sys_file): return cmd.get_active_option(cmd.read_file(sys_file)) @@ -159,19 +159,19 @@ class VMPlugin(base.Plugin): return True @command_custom("dirty_bytes") - def _dirty_bytes(self, enabling, value, verify, ignore_missing): + def _dirty_bytes(self, enabling, value, verify, ignore_missing, instance): return self._dirty_option("dirty_bytes", "dirty_ratio", self._check_twice_pagesize, enabling, value, verify) @command_custom("dirty_ratio") - def _dirty_ratio(self, enabling, value, verify, ignore_missing): + def _dirty_ratio(self, enabling, value, verify, ignore_missing, instance): return self._dirty_option("dirty_ratio", "dirty_bytes", self._check_ratio, enabling, value, verify) @command_custom("dirty_background_bytes") - def _dirty_background_bytes(self, enabling, value, verify, ignore_missing): + def _dirty_background_bytes(self, enabling, value, verify, ignore_missing, instance): return self._dirty_option("dirty_background_bytes", "dirty_background_ratio", self._check_positive, enabling, value, verify) @command_custom("dirty_background_ratio") - def _dirty_background_ratio(self, enabling, value, verify, ignore_missing): + def _dirty_background_ratio(self, enabling, value, verify, ignore_missing, instance): return self._dirty_option("dirty_background_ratio", "dirty_background_bytes", self._check_ratio, enabling, value, verify) def _dirty_option(self, option, counterpart, check_fun, enabling, value, verify):