mirror of
https://github.com/ryan4yin/nix-config.git
synced 2026-11-13 12:13:46 +01:00
fix(power): drop TuneD for native CPU scaling (#461)
This commit is contained in:
1 parent
643984e1ab
commit
3266aad4a2
12 files changed
+98
-46
No files matched your search
@@ -21,11 +21,6 @@ in
|
|||||||
|
|
||||||
# disable sunshine for security
|
# disable sunshine for security
|
||||||
services.sunshine.enable = lib.mkForce false;
|
services.sunshine.enable = lib.mkForce false;
|
||||||
# battery-first: pin the low-power profile. apple-cpufreq exposes no EPP or
|
|
||||||
# platform_profile, so the only thing this changes is cpufreq boost.
|
|
||||||
services.tuned.recommend = {
|
|
||||||
powersave = { };
|
|
||||||
};
|
|
||||||
|
|
||||||
# Laptop joins untrusted networks and is never scraped (see youko's
|
# Laptop joins untrusted networks and is never scraped (see youko's
|
||||||
# `offlineHosts`); don't expose :9100, and don't keep the smartctl exporter
|
# `offlineHosts`); don't expose :9100, and don't keep the smartctl exporter
|
||||||
|
|||||||
@@ -104,6 +104,18 @@ Copy the closest existing host and adapt it. The step-by-step procedure, includi
|
|||||||
networking wiring, secrets, and the eval tests a new host must pass, is in
|
networking wiring, secrets, and the eval tests a new host must pass, is in
|
||||||
[`.agents/skills/nix-config-new-host/SKILL.md`](../.agents/skills/nix-config-new-host/SKILL.md).
|
[`.agents/skills/nix-config-new-host/SKILL.md`](../.agents/skills/nix-config-new-host/SKILL.md).
|
||||||
|
|
||||||
|
## CPU Power Policy
|
||||||
|
|
||||||
|
Physical hosts get `powersave` from [`power.nix`](../modules/nixos/power.nix); Apple hosts keep
|
||||||
|
their own `schedutil`. On the active Intel/AMD P-state drivers `powersave` still scales with load,
|
||||||
|
so this is not a frequency cap.
|
||||||
|
|
||||||
|
TuneD is not enabled on any host. It tunes much more than CPU frequency and fits laptops, but our
|
||||||
|
laptop is a MacBook with its own native support, so it has no use here.
|
||||||
|
|
||||||
|
The desktops also run UPower for power-supply reporting: the laptop's battery, and peripheral
|
||||||
|
batteries on a desktop. It only reports state, and changes no CPU or device setting.
|
||||||
|
|
||||||
## Deploying VM Hosts
|
## Deploying VM Hosts
|
||||||
|
|
||||||
The three VM hosts (`shoryu`, `shushou`, `youko`) put their VMs on the Linux bridge `br0`, with the
|
The three VM hosts (`shoryu`, `shushou`, `youko`) put their VMs on the Linux bridge `br0`, with the
|
||||||
|
|||||||
@@ -58,10 +58,6 @@ in
|
|||||||
};
|
};
|
||||||
|
|
||||||
services.sunshine.enable = true;
|
services.sunshine.enable = true;
|
||||||
# desktop PC: keep the CPU pinned to the performance profile
|
|
||||||
services.tuned.recommend = {
|
|
||||||
throughput-performance = { };
|
|
||||||
};
|
|
||||||
|
|
||||||
modules.btrbk.enable = true;
|
modules.btrbk.enable = true;
|
||||||
|
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ in
|
|||||||
{
|
{
|
||||||
imports = [
|
imports = [
|
||||||
disko.nixosModules.default
|
disko.nixosModules.default
|
||||||
|
../../modules/nixos/power.nix
|
||||||
# disks
|
# disks
|
||||||
./disko-fs.nix
|
./disko-fs.nix
|
||||||
|
|
||||||
|
|||||||
@@ -10,13 +10,8 @@ let
|
|||||||
ipv4WithMask = "${ipv4}/24";
|
ipv4WithMask = "${ipv4}/24";
|
||||||
in
|
in
|
||||||
{
|
{
|
||||||
# Physical machines only: these three always-on mini PCs hold their CPU at
|
# CPU policy belongs to physical hosts; guests do not control hardware frequency.
|
||||||
# TuneD's power-saving profile (EPP biased to power, cpufreq boost off). A
|
|
||||||
# MicroVM guest has no EPP or boost of its own, so it never imports this module.
|
|
||||||
imports = [ ../modules/nixos/power.nix ];
|
imports = [ ../modules/nixos/power.nix ];
|
||||||
services.tuned.recommend = {
|
|
||||||
powersave = { };
|
|
||||||
};
|
|
||||||
|
|
||||||
# supported file systems, so we can mount any removable disks with these filesystems
|
# supported file systems, so we can mount any removable disks with these filesystems
|
||||||
boot.supportedFilesystems = [
|
boot.supportedFilesystems = [
|
||||||
|
|||||||
@@ -1,4 +1,9 @@
|
|||||||
{ mylib, ... }:
|
{ mylib, ... }:
|
||||||
{
|
{
|
||||||
imports = mylib.scanPaths ./. ++ [ ../power.nix ];
|
imports = mylib.scanPaths ./. ++ [ ../power.nix ];
|
||||||
|
|
||||||
|
# Power-supply reporting for the desktop shell: the laptop's battery, and
|
||||||
|
# peripheral batteries on a desktop. UPower only reports state; unlike TuneD it
|
||||||
|
# writes no CPU, network, or disk setting.
|
||||||
|
services.upower.enable = true;
|
||||||
}
|
}
|
||||||
+5
-27
@@ -1,29 +1,7 @@
|
|||||||
{ config, lib, ... }:
|
{ lib, pkgs, ... }:
|
||||||
{
|
{
|
||||||
# TuneD - Tuning Profile Delivery Mechanism for Linux
|
# These x86 hosts use active Intel/AMD P-state drivers: powersave permits
|
||||||
# A modern replacement for PPD(power-profiles-daemon), and the only power manager
|
# hardware-managed scaling. Apple Silicon keeps its native schedutil policy;
|
||||||
# here: nixpkgs' tuned module already disables power-profiles-daemon and fails
|
# generic cpufreq powersave would instead hold the CPU at its minimum.
|
||||||
# the build if TLP, auto-cpufreq or system76-power is enabled as well.
|
powerManagement.cpuFreqGovernor = lib.mkIf pkgs.stdenv.hostPlatform.isx86 "powersave";
|
||||||
services.tuned = {
|
|
||||||
enable = true;
|
|
||||||
settings.dynamic_tuning = true;
|
|
||||||
|
|
||||||
# Hosts pin their profile with `services.tuned.recommend` (an empty rule
|
|
||||||
# matches any host): TuneD reads /etc/tuned/recommend.conf in its automatic
|
|
||||||
# profile mode on every boot. `ppdSettings.main.default` looks like it does
|
|
||||||
# the same, but never wins -- tuned-ppd restores the base profile it saved in
|
|
||||||
# /etc/tuned/ppd_base_profile, or TuneD's own recommendation, first. Nothing
|
|
||||||
# here uses the PPD D-Bus API, so tuned-ppd stays off instead of overwriting
|
|
||||||
# the pinned profile at startup.
|
|
||||||
ppdSupport = false;
|
|
||||||
};
|
|
||||||
|
|
||||||
# Battery/AC state, used by the desktops; tuned-ppd was the other consumer.
|
|
||||||
services.upower.enable = true;
|
|
||||||
|
|
||||||
# ppdSupport = false drops /etc/tuned/ppd.conf, but the tuned package ships its
|
|
||||||
# own tuned-ppd.service (WantedBy=graphical.target) which systemd.packages links
|
|
||||||
# regardless, so activation starts it, it fails on the missing config file and
|
|
||||||
# switch-to-configuration exits 4. Mask it.
|
|
||||||
systemd.units."tuned-ppd.service".enable = lib.mkIf (!config.services.tuned.ppdSupport) false;
|
|
||||||
}
|
}
|
||||||
+4
-4
@@ -47,10 +47,10 @@ Some tests iterate over every configuration, so a new host is covered automatica
|
|||||||
them. Others name specific hosts — or a name prefix, like `k3s-api-endpoint`, which covers every
|
them. Others name specific hosts — or a name prefix, like `k3s-api-endpoint`, which covers every
|
||||||
`k3s-test-1-*` configuration — and only cover a new host if you add it.
|
`k3s-test-1-*` configuration — and only cover a new host if you add it.
|
||||||
|
|
||||||
| Kind | Tests |
|
| Kind | Tests |
|
||||||
| ------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
| ------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||||
| Every configuration | `hostname`, `kernel`, `nix-system-features`, `security-apparmor`, `security-container-groups`, `security-exporters`, `security-firewall`, `security-k3s-kubeconfig`, `security-k3s-pod-firewall`, `security-kernel`, `security-ssh-x11` |
|
| Every configuration | `hostname`, `kernel`, `nix-system-features`, `security-apparmor`, `security-container-groups`, `security-exporters`, `security-firewall`, `security-k3s-kubeconfig`, `security-k3s-pod-firewall`, `security-kernel`, `security-ssh-x11` |
|
||||||
| Named hosts only | `btrbk`, `home-manager`, `home-manager-xdg`, `computer-use-headless`, `k3s-api-endpoint`, `k3s-node-home-manager`, `idols-ai-gpu`, `idols-ai-net`, `idols-ai-voice-input`, `idols-aquamarine`, `security-postgres-auth`, `youko-metrics`, `ups-metrics`, `shoukei-logind` |
|
| Named hosts only | `btrbk`, `cpu-power`, `home-manager`, `home-manager-xdg`, `computer-use-headless`, `k3s-api-endpoint`, `k3s-node-home-manager`, `idols-ai-gpu`, `idols-ai-net`, `idols-ai-voice-input`, `idols-aquamarine`, `security-postgres-auth`, `youko-metrics`, `ups-metrics`, `shoukei-logind` |
|
||||||
|
|
||||||
`hostname` expects each configuration's `networking.hostName` to equal its name. Niri desktop
|
`hostname` expects each configuration's `networking.hostName` to equal its name. Niri desktop
|
||||||
configurations are the exception (`ai-niri` → `ai`, `shoukei-niri` → `shoukei`) and are listed in
|
configurations are the exception (`ai-niri` → `ai`, `shoukei-niri` → `shoukei`) and are listed in
|
||||||
|
|||||||
@@ -0,0 +1,6 @@
|
|||||||
|
{
|
||||||
|
governor = "schedutil";
|
||||||
|
noTuned = true;
|
||||||
|
noFrequencyCaps = true;
|
||||||
|
batteryReporting = true;
|
||||||
|
}
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
{
|
||||||
|
lib,
|
||||||
|
outputs,
|
||||||
|
...
|
||||||
|
}:
|
||||||
|
let
|
||||||
|
cfg = outputs.nixosConfigurations.shoukei-niri.config;
|
||||||
|
in
|
||||||
|
{
|
||||||
|
governor = cfg.powerManagement.cpuFreqGovernor;
|
||||||
|
noTuned = lib.all (host: !host.config.services.tuned.enable) (
|
||||||
|
builtins.attrValues outputs.nixosConfigurations
|
||||||
|
);
|
||||||
|
noFrequencyCaps =
|
||||||
|
cfg.powerManagement.cpufreq.min == null && cfg.powerManagement.cpufreq.max == null;
|
||||||
|
batteryReporting = cfg.services.upower.enable;
|
||||||
|
}
|
||||||
@@ -0,0 +1,12 @@
|
|||||||
|
{
|
||||||
|
lib,
|
||||||
|
...
|
||||||
|
}:
|
||||||
|
{
|
||||||
|
governors = lib.genAttrs [ "ai-niri" "aquamarine" "shoryu" "shushou" "youko" ] (_: "powersave");
|
||||||
|
noTuned = true;
|
||||||
|
noEeeWorkaround = true;
|
||||||
|
noFrequencyCaps = true;
|
||||||
|
guestsHaveNoCpuPolicy = true;
|
||||||
|
desktopBatteryReporting = true;
|
||||||
|
}
|
||||||
@@ -0,0 +1,35 @@
|
|||||||
|
{
|
||||||
|
lib,
|
||||||
|
outputs,
|
||||||
|
...
|
||||||
|
}:
|
||||||
|
let
|
||||||
|
configs = outputs.nixosConfigurations;
|
||||||
|
physicalHosts = [
|
||||||
|
"ai-niri"
|
||||||
|
"aquamarine"
|
||||||
|
"shoryu"
|
||||||
|
"shushou"
|
||||||
|
"youko"
|
||||||
|
];
|
||||||
|
in
|
||||||
|
{
|
||||||
|
governors = lib.genAttrs physicalHosts (
|
||||||
|
name: configs.${name}.config.powerManagement.cpuFreqGovernor
|
||||||
|
);
|
||||||
|
noTuned = lib.all (host: !host.config.services.tuned.enable) (builtins.attrValues configs);
|
||||||
|
noEeeWorkaround = lib.all (host: !(host.config.systemd.services ? disable-eee)) (
|
||||||
|
builtins.attrValues configs
|
||||||
|
);
|
||||||
|
noFrequencyCaps = lib.all (
|
||||||
|
name:
|
||||||
|
let
|
||||||
|
cfg = configs.${name}.config.powerManagement;
|
||||||
|
in
|
||||||
|
cfg.cpufreq.min == null && cfg.cpufreq.max == null
|
||||||
|
) physicalHosts;
|
||||||
|
guestsHaveNoCpuPolicy = lib.all (name: !(configs.${name}.config.systemd.services ? cpufreq)) (
|
||||||
|
lib.subtractLists physicalHosts (builtins.attrNames configs)
|
||||||
|
);
|
||||||
|
desktopBatteryReporting = configs.ai-niri.config.services.upower.enable;
|
||||||
|
}
|
||||||
Reference in new issue
Block a user