summaryrefslogtreecommitdiffstats
path: root/nixos/modules/hardware/video/bumblebee.nix
blob: 3aebc4a800f56905a8fca0805da42a6d1df1a0a8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
{
  config,
  lib,
  pkgs,
  ...
}:
let
  cfg = config.hardware.bumblebee;

  kernel = config.boot.kernelPackages;

  useNvidia = cfg.driver == "nvidia";

  bumblebee = pkgs.bumblebee.override {
    inherit useNvidia;
    useDisplayDevice = cfg.connectDisplay;
  };

  useBbswitch = cfg.pmMethod == "bbswitch" || cfg.pmMethod == "auto" && useNvidia;

  primus = pkgs.primus.override {
    inherit useNvidia;
  };

in

{

  options = {
    hardware.bumblebee = {

      enable = lib.mkOption {
        default = false;
        type = lib.types.bool;
        description = ''
          Enable the bumblebee daemon to manage Optimus hybrid video cards.
          This should power off secondary GPU until its use is requested
          by running an application with optirun.
        '';
      };

      group = lib.mkOption {
        default = "wheel";
        example = "video";
        type = lib.types.str;
        description = "Group for bumblebee socket";
      };

      connectDisplay = lib.mkOption {
        default = false;
        type = lib.types.bool;
        description = ''
          Set to true if you intend to connect your discrete card to a
          monitor. This option will set up your Nvidia card for EDID
          discovery and to turn on the monitor signal.

          Only nvidia driver is supported so far.
        '';
      };

      driver = lib.mkOption {
        default = "nvidia";
        type = lib.types.enum [
          "nvidia"
          "nouveau"
        ];
        description = ''
          Set driver used by bumblebeed. Supported are nouveau and nvidia.
        '';
      };

      pmMethod = lib.mkOption {
        default = "auto";
        type = lib.types.enum [
          "auto"
          "bbswitch"
          "switcheroo"
          "none"
        ];
        description = ''
          Set preferred power management method for unused card.
        '';
      };

    };
  };

  config = lib.mkIf cfg.enable {
    boot.blacklistedKernelModules = [
      "nvidia-drm"
      "nvidia"
      "nouveau"
    ];
    boot.kernelModules = lib.optional useBbswitch "bbswitch";
    boot.extraModulePackages =
      lib.optional useBbswitch kernel.bbswitch
      ++ lib.optional useNvidia (
        if config.hardware.nvidia.open == true then kernel.nvidia_x11.open else kernel.nvidia_x11.mod
      );

    environment.systemPackages = [
      bumblebee
      primus
    ];

    systemd.services.bumblebeed = {
      description = "Bumblebee Hybrid Graphics Switcher";
      wantedBy = [ "multi-user.target" ];
      before = [ "display-manager.service" ];
      serviceConfig = {
        ExecStart = "${bumblebee}/bin/bumblebeed --use-syslog -g ${cfg.group} --driver ${cfg.driver} --pm-method ${cfg.pmMethod}";
      };
    };
  };
}