at 24.11-pre 6.6 kB view raw
1# D-Bus configuration and system bus daemon. 2 3{ config, lib, pkgs, ... }: 4 5let 6 7 cfg = config.services.dbus; 8 9 homeDir = "/run/dbus"; 10 11 configDir = pkgs.makeDBusConf { 12 inherit (cfg) apparmor; 13 suidHelper = "${config.security.wrapperDir}/dbus-daemon-launch-helper"; 14 serviceDirectories = cfg.packages; 15 }; 16 17 inherit (lib) mkOption mkEnableOption mkIf mkMerge types; 18 19in 20 21{ 22 options = { 23 24 boot.initrd.systemd.dbus = { 25 enable = mkEnableOption "dbus in stage 1"; 26 }; 27 28 services.dbus = { 29 30 enable = mkOption { 31 type = types.bool; 32 default = false; 33 internal = true; 34 description = '' 35 Whether to start the D-Bus message bus daemon, which is 36 required by many other system services and applications. 37 ''; 38 }; 39 40 implementation = mkOption { 41 type = types.enum [ "dbus" "broker" ]; 42 default = "dbus"; 43 description = '' 44 The implementation to use for the message bus defined by the D-Bus specification. 45 Can be either the classic dbus daemon or dbus-broker, which aims to provide high 46 performance and reliability, while keeping compatibility to the D-Bus 47 reference implementation. 48 ''; 49 50 }; 51 52 packages = mkOption { 53 type = types.listOf types.path; 54 default = [ ]; 55 description = '' 56 Packages whose D-Bus configuration files should be included in 57 the configuration of the D-Bus system-wide or session-wide 58 message bus. Specifically, files in the following directories 59 will be included into their respective DBus configuration paths: 60 {file}`«pkg»/etc/dbus-1/system.d` 61 {file}`«pkg»/share/dbus-1/system.d` 62 {file}`«pkg»/share/dbus-1/system-services` 63 {file}`«pkg»/etc/dbus-1/session.d` 64 {file}`«pkg»/share/dbus-1/session.d` 65 {file}`«pkg»/share/dbus-1/services` 66 ''; 67 }; 68 69 apparmor = mkOption { 70 type = types.enum [ "enabled" "disabled" "required" ]; 71 description = '' 72 AppArmor mode for dbus. 73 74 `enabled` enables mediation when it's 75 supported in the kernel, `disabled` 76 always disables AppArmor even with kernel support, and 77 `required` fails when AppArmor was not found 78 in the kernel. 79 ''; 80 default = "disabled"; 81 }; 82 }; 83 }; 84 85 config = mkIf cfg.enable (mkMerge [ 86 { 87 environment.etc."dbus-1".source = configDir; 88 89 environment.pathsToLink = [ 90 "/etc/dbus-1" 91 "/share/dbus-1" 92 ]; 93 94 users.users.messagebus = { 95 uid = config.ids.uids.messagebus; 96 description = "D-Bus system message bus daemon user"; 97 home = homeDir; 98 homeMode = "0755"; 99 group = "messagebus"; 100 }; 101 102 users.groups.messagebus.gid = config.ids.gids.messagebus; 103 104 # Install dbus for dbus tools even when using dbus-broker 105 environment.systemPackages = [ 106 pkgs.dbus 107 ]; 108 109 # You still need the dbus reference implementation installed to use dbus-broker 110 systemd.packages = [ 111 pkgs.dbus 112 ]; 113 114 services.dbus.packages = [ 115 pkgs.dbus 116 config.system.path 117 ]; 118 119 systemd.user.sockets.dbus.wantedBy = [ 120 "sockets.target" 121 ]; 122 } 123 124 (mkIf config.boot.initrd.systemd.dbus.enable { 125 boot.initrd.systemd = { 126 users.messagebus = { }; 127 groups.messagebus = { }; 128 contents."/etc/dbus-1".source = pkgs.makeDBusConf { 129 inherit (cfg) apparmor; 130 suidHelper = "/bin/false"; 131 serviceDirectories = [ pkgs.dbus ]; 132 }; 133 packages = [ pkgs.dbus ]; 134 storePaths = [ "${pkgs.dbus}/bin/dbus-daemon" ]; 135 targets.sockets.wants = [ "dbus.socket" ]; 136 }; 137 }) 138 139 (mkIf (cfg.implementation == "dbus") { 140 security.wrappers.dbus-daemon-launch-helper = { 141 source = "${pkgs.dbus}/libexec/dbus-daemon-launch-helper"; 142 owner = "root"; 143 group = "messagebus"; 144 setuid = true; 145 setgid = false; 146 permissions = "u+rx,g+rx,o-rx"; 147 }; 148 149 systemd.services.dbus = { 150 aliases = [ 151 # hack aiding to prevent dbus from restarting when switching from dbus-broker back to dbus 152 "dbus-broker.service" 153 ]; 154 # Don't restart dbus-daemon. Bad things tend to happen if we do. 155 reloadIfChanged = true; 156 restartTriggers = [ 157 configDir 158 ]; 159 environment = { 160 LD_LIBRARY_PATH = config.system.nssModules.path; 161 }; 162 }; 163 164 systemd.user.services.dbus = { 165 aliases = [ 166 # hack aiding to prevent dbus from restarting when switching from dbus-broker back to dbus 167 "dbus-broker.service" 168 ]; 169 # Don't restart dbus-daemon. Bad things tend to happen if we do. 170 reloadIfChanged = true; 171 restartTriggers = [ 172 configDir 173 ]; 174 }; 175 176 }) 177 178 (mkIf (cfg.implementation == "broker") { 179 environment.systemPackages = [ 180 pkgs.dbus-broker 181 ]; 182 183 systemd.packages = [ 184 pkgs.dbus-broker 185 ]; 186 187 # Just to be sure we don't restart through the unit alias 188 systemd.services.dbus.reloadIfChanged = true; 189 systemd.user.services.dbus.reloadIfChanged = true; 190 191 # NixOS Systemd Module doesn't respect 'Install' 192 # https://github.com/NixOS/nixpkgs/issues/108643 193 systemd.services.dbus-broker = { 194 aliases = [ 195 # allow other services to just depend on dbus, 196 # but also a hack aiding to prevent dbus from restarting when switching from dbus-broker back to dbus 197 "dbus.service" 198 ]; 199 unitConfig = { 200 # We get errors when reloading the dbus-broker service 201 # if /tmp got remounted after this service started 202 RequiresMountsFor = [ "/tmp" ]; 203 }; 204 # Don't restart dbus. Bad things tend to happen if we do. 205 reloadIfChanged = true; 206 restartTriggers = [ 207 configDir 208 ]; 209 environment = { 210 LD_LIBRARY_PATH = config.system.nssModules.path; 211 }; 212 }; 213 214 systemd.user.services.dbus-broker = { 215 aliases = [ 216 # allow other services to just depend on dbus, 217 # but also a hack aiding to prevent dbus from restarting when switching from dbus-broker back to dbus 218 "dbus.service" 219 ]; 220 # Don't restart dbus. Bad things tend to happen if we do. 221 reloadIfChanged = true; 222 restartTriggers = [ 223 configDir 224 ]; 225 }; 226 }) 227 228 ]); 229}