at 25.11-pre 8.0 kB view raw
1# Upower daemon. 2{ 3 config, 4 lib, 5 pkgs, 6 ... 7}: 8let 9 10 cfg = config.services.upower; 11 12in 13 14{ 15 16 ###### interface 17 18 options = { 19 20 services.upower = { 21 22 enable = lib.mkOption { 23 type = lib.types.bool; 24 default = false; 25 description = '' 26 Whether to enable Upower, a DBus service that provides power 27 management support to applications. 28 ''; 29 }; 30 31 package = lib.mkPackageOption pkgs "upower" { }; 32 33 enableWattsUpPro = lib.mkOption { 34 type = lib.types.bool; 35 default = false; 36 description = '' 37 Enable the Watts Up Pro device. 38 39 The Watts Up Pro contains a generic FTDI USB device without a specific 40 vendor and product ID. When we probe for WUP devices, we can cause 41 the user to get a perplexing "Device or resource busy" error when 42 attempting to use their non-WUP device. 43 44 The generic FTDI device is known to also be used on: 45 46 - Sparkfun FT232 breakout board 47 - Parallax Propeller 48 ''; 49 }; 50 51 noPollBatteries = lib.mkOption { 52 type = lib.types.bool; 53 default = false; 54 description = '' 55 Don't poll the kernel for battery level changes. 56 57 Some hardware will send us battery level changes through 58 events, rather than us having to poll for it. This option 59 allows disabling polling for hardware that sends out events. 60 ''; 61 }; 62 63 ignoreLid = lib.mkOption { 64 type = lib.types.bool; 65 default = false; 66 description = '' 67 Do we ignore the lid state 68 69 Some laptops are broken. The lid state is either inverted, or stuck 70 on or off. We can't do much to fix these problems, but this is a way 71 for users to make the laptop panel vanish, a state that might be used 72 by a couple of user-space daemons. On Linux systems, see also 73 {manpage}`logind.conf(5)`. 74 ''; 75 }; 76 77 usePercentageForPolicy = lib.mkOption { 78 type = lib.types.bool; 79 default = true; 80 description = '' 81 Policy for warnings and action based on battery levels 82 83 Whether battery percentage based policy should be used. The default 84 is to use the percentage, which 85 should work around broken firmwares. It is also more reliable than 86 the time left (frantically saving all your files is going to use more 87 battery than letting it rest for example). 88 ''; 89 }; 90 91 percentageLow = lib.mkOption { 92 type = lib.types.ints.unsigned; 93 default = 20; 94 description = '' 95 When `usePercentageForPolicy` is 96 `true`, the levels at which UPower will consider the 97 battery low. 98 99 This will also be used for batteries which don't have time information 100 such as that of peripherals. 101 102 If any value (of `percentageLow`, 103 `percentageCritical` and 104 `percentageAction`) is invalid, or not in descending 105 order, the defaults will be used. 106 ''; 107 }; 108 109 percentageCritical = lib.mkOption { 110 type = lib.types.ints.unsigned; 111 default = 5; 112 description = '' 113 When `usePercentageForPolicy` is 114 `true`, the levels at which UPower will consider the 115 battery critical. 116 117 This will also be used for batteries which don't have time information 118 such as that of peripherals. 119 120 If any value (of `percentageLow`, 121 `percentageCritical` and 122 `percentageAction`) is invalid, or not in descending 123 order, the defaults will be used. 124 ''; 125 }; 126 127 percentageAction = lib.mkOption { 128 type = lib.types.ints.unsigned; 129 default = 2; 130 description = '' 131 When `usePercentageForPolicy` is 132 `true`, the levels at which UPower will take action 133 for the critical battery level. 134 135 This will also be used for batteries which don't have time information 136 such as that of peripherals. 137 138 If any value (of `percentageLow`, 139 `percentageCritical` and 140 `percentageAction`) is invalid, or not in descending 141 order, the defaults will be used. 142 ''; 143 }; 144 145 timeLow = lib.mkOption { 146 type = lib.types.ints.unsigned; 147 default = 1200; 148 description = '' 149 When `usePercentageForPolicy` is 150 `false`, the time remaining in seconds at which 151 UPower will consider the battery low. 152 153 If any value (of `timeLow`, 154 `timeCritical` and `timeAction`) is 155 invalid, or not in descending order, the defaults will be used. 156 ''; 157 }; 158 159 timeCritical = lib.mkOption { 160 type = lib.types.ints.unsigned; 161 default = 300; 162 description = '' 163 When `usePercentageForPolicy` is 164 `false`, the time remaining in seconds at which 165 UPower will consider the battery critical. 166 167 If any value (of `timeLow`, 168 `timeCritical` and `timeAction`) is 169 invalid, or not in descending order, the defaults will be used. 170 ''; 171 }; 172 173 timeAction = lib.mkOption { 174 type = lib.types.ints.unsigned; 175 default = 120; 176 description = '' 177 When `usePercentageForPolicy` is 178 `false`, the time remaining in seconds at which 179 UPower will take action for the critical battery level. 180 181 If any value (of `timeLow`, 182 `timeCritical` and `timeAction`) is 183 invalid, or not in descending order, the defaults will be used. 184 ''; 185 }; 186 187 allowRiskyCriticalPowerAction = lib.mkOption { 188 type = lib.types.bool; 189 default = false; 190 description = '' 191 Enable the risky critical power actions "Suspend" and "Ignore". 192 ''; 193 }; 194 195 criticalPowerAction = lib.mkOption { 196 type = lib.types.enum [ 197 "PowerOff" 198 "Hibernate" 199 "HybridSleep" 200 "Suspend" 201 "Ignore" 202 ]; 203 default = "HybridSleep"; 204 description = '' 205 The action to take when `timeAction` or 206 `percentageAction` has been reached for the batteries 207 (UPS or laptop batteries) supplying the computer. 208 209 When set to `Suspend` or `Ignore`, 210 {option}`services.upower.allowRiskyCriticalPowerAction` must be set 211 to `true`. 212 ''; 213 }; 214 215 }; 216 217 }; 218 219 ###### implementation 220 221 config = lib.mkIf cfg.enable { 222 assertions = [ 223 { 224 assertion = 225 let 226 inherit (builtins) elem; 227 riskyActions = [ 228 "Suspend" 229 "Ignore" 230 ]; 231 riskyActionEnabled = elem cfg.criticalPowerAction riskyActions; 232 in 233 riskyActionEnabled -> cfg.allowRiskyCriticalPowerAction; 234 message = '' 235 services.upower.allowRiskyCriticalPowerAction must be true if 236 services.upower.criticalPowerAction is set to 237 '${cfg.criticalPowerAction}'. 238 ''; 239 } 240 ]; 241 242 environment.systemPackages = [ cfg.package ]; 243 244 services.dbus.packages = [ cfg.package ]; 245 246 services.udev.packages = [ cfg.package ]; 247 248 systemd.packages = [ cfg.package ]; 249 250 environment.etc."UPower/UPower.conf".text = lib.generators.toINI { } { 251 UPower = { 252 EnableWattsUpPro = cfg.enableWattsUpPro; 253 NoPollBatteries = cfg.noPollBatteries; 254 IgnoreLid = cfg.ignoreLid; 255 UsePercentageForPolicy = cfg.usePercentageForPolicy; 256 PercentageLow = cfg.percentageLow; 257 PercentageCritical = cfg.percentageCritical; 258 PercentageAction = cfg.percentageAction; 259 TimeLow = cfg.timeLow; 260 TimeCritical = cfg.timeCritical; 261 TimeAction = cfg.timeAction; 262 AllowRiskyCriticalPowerAction = cfg.allowRiskyCriticalPowerAction; 263 CriticalPowerAction = cfg.criticalPowerAction; 264 }; 265 }; 266 }; 267 268}