1{
2 config,
3 lib,
4 pkgs,
5 utils,
6 ...
7}:
8let
9
10 cfg = config.services.freefall;
11
12in
13{
14
15 options.services.freefall = {
16
17 enable = lib.mkOption {
18 type = lib.types.bool;
19 default = false;
20 description = ''
21 Whether to protect HP/Dell laptop hard drives (not SSDs) in free fall.
22 '';
23 };
24
25 package = lib.mkPackageOption pkgs "freefall" { };
26
27 devices = lib.mkOption {
28 type = lib.types.listOf lib.types.str;
29 default = [ "/dev/sda" ];
30 description = ''
31 Device paths to all internal spinning hard drives.
32 '';
33 };
34
35 };
36
37 config =
38 let
39
40 mkService =
41 dev:
42 assert dev != "";
43 let
44 dev' = utils.escapeSystemdPath dev;
45 in
46 lib.nameValuePair "freefall-${dev'}" {
47 description = "Free-fall protection for ${dev}";
48 after = [ "${dev'}.device" ];
49 wantedBy = [ "${dev'}.device" ];
50 serviceConfig = {
51 ExecStart = "${cfg.package}/bin/freefall ${dev}";
52 Restart = "on-failure";
53 Type = "forking";
54 };
55 };
56
57 in
58 lib.mkIf cfg.enable {
59
60 environment.systemPackages = [ cfg.package ];
61
62 systemd.services = builtins.listToAttrs (map mkService cfg.devices);
63
64 };
65
66}