From 6f1b1aefde5a06d3317e1350d61a33b263cfc3e7 Mon Sep 17 00:00:00 2001 From: Eelco Dolstra Date: Wed, 26 Aug 2009 16:52:38 +0000 Subject: [PATCH] * Added an option `nixpkgs.config' that allows the Nixpkgs options to be set from the NixOS configuration. For instance, you can say nixpkgs.config.firefox.enableGeckoMediaPlayer = true; environment.systemPackages = [ pkgs.firefox ]; but the more interesting application is to apply global overrides to Nixpkgs throughout NixOS, e.g. nixpkgs.config.packageOverrides = pkgs: { glibc = pkgs.glibc27; gcc = pkgs.gcc42; }; would build the whole system with Glibc 2.7 and GCC 4.2. (There are some issues with "useFromStdenv" in all-packages.nix that need to be fixed for packages in the stdenv bootstrap though.) The implementation of this option is kind of evil though due to the need to prevent a circularity between the evaluation of nixpkgs.config and the "pkgs" module argument. svn path=/nixos/trunk/; revision=16866 --- lib/eval-config.nix | 54 +++++++++++++++++++------- {lib => modules/misc}/check-config.nix | 0 modules/misc/nixpkgs.nix | 17 ++++++++ modules/module-list.nix | 2 + 4 files changed, 60 insertions(+), 13 deletions(-) rename {lib => modules/misc}/check-config.nix (100%) create mode 100644 modules/misc/nixpkgs.nix diff --git a/lib/eval-config.nix b/lib/eval-config.nix index 8befb75408b..653a260fb9b 100644 --- a/lib/eval-config.nix +++ b/lib/eval-config.nix @@ -5,41 +5,69 @@ { configuration , system ? builtins.currentSystem , nixpkgs ? import ./from-env.nix "NIXPKGS" /etc/nixos/nixpkgs -, pkgs ? import nixpkgs {inherit system;} +, pkgs ? null +, baseModules ? import ../modules/module-list.nix , extraArgs ? {} , extraModules ? [] }: -let extraArgs_ = extraArgs; in +let extraArgs_ = extraArgs; pkgs_ = pkgs; in rec { - inherit nixpkgs pkgs; + # These are the NixOS modules that constitute the system configuration. configComponents = - [ configuration - ./check-config.nix - ] + [ configuration ] ++ extraModules - ++ (import ../modules/module-list.nix); + ++ baseModules; + # Merge the option definitions in all modules, forming the full + # system configuration. This is called "configFast" because it's + # not checked for undeclared options. + configFast = + pkgs.lib.definitionsOf configComponents extraArgs; + + # These are the extra arguments passed to every module. In + # particular, Nixpkgs is passed through the "pkgs" argument. extraArgs = extraArgs_ // { inherit pkgs optionDeclarations; modulesPath = ../modules; }; - config_ = - pkgs.lib.definitionsOf configComponents extraArgs; + # Import Nixpkgs, allowing the NixOS option nixpkgs.config to + # specify the Nixpkgs configuration (e.g., to set package options + # such as firefox.enableGeckoMediaPlayer, or to apply global + # overrides such as changing GCC throughout the system). This is + # tricky, because we have to prevent an infinite recursion: "pkgs" + # is passed as an argument to NixOS modules, but the value of "pkgs" + # depends on config.nixpkgs.config, which we get from the modules. + # So we call ourselves here with "pkgs" explicitly set to an + # instance that doesn't depend on nixpkgs.config. + pkgs = + if pkgs_ != null + then pkgs_ + else import nixpkgs { + inherit system; + config = + (import ./eval-config.nix { + inherit configuration system nixpkgs extraArgs extraModules; + # For efficiency, leave out most NixOS modules; they don't + # define nixpkgs.config, so it's pointless to evaluate them. + baseModules = [ ../modules/misc/nixpkgs.nix ]; + pkgs = import nixpkgs { inherit system; config = {}; }; + }).configFast.nixpkgs.config; + }; # "fixableDeclarationsOf" is used instead of "declarationsOf" because some # option default values may depends on the definition of other options. # !!! This seems inefficent. Didn't definitionsOf already compute # the option declarations? optionDeclarations = - pkgs.lib.fixableDeclarationsOf configComponents extraArgs config_; + pkgs.lib.fixableDeclarationsOf configComponents extraArgs configFast; # Optionally check wether all config values have corresponding # option declarations. - config = pkgs.checker config_ - config_.environment.checkConfigurationOptions - optionDeclarations config_; + config = pkgs.checker configFast + configFast.environment.checkConfigurationOptions + optionDeclarations configFast; } diff --git a/lib/check-config.nix b/modules/misc/check-config.nix similarity index 100% rename from lib/check-config.nix rename to modules/misc/check-config.nix diff --git a/modules/misc/nixpkgs.nix b/modules/misc/nixpkgs.nix new file mode 100644 index 00000000000..68e7e2517f9 --- /dev/null +++ b/modules/misc/nixpkgs.nix @@ -0,0 +1,17 @@ +{ config, pkgs, ... }: + +{ + options = { + + nixpkgs.config = pkgs.lib.mkOption { + default = {}; + example = { + firefox.enableGeckoMediaPlayer = true; + }; + description = '' + The configuration of the Nix Packages collection. + ''; + }; + + }; +} \ No newline at end of file diff --git a/modules/module-list.nix b/modules/module-list.nix index ec30539df84..02268df64bb 100644 --- a/modules/module-list.nix +++ b/modules/module-list.nix @@ -15,8 +15,10 @@ ./installer/tools/nixos-checkout.nix ./installer/tools/tools.nix ./misc/assertions.nix + ./misc/check-config.nix ./misc/ids.nix ./misc/locate.nix + ./misc/nixpkgs.nix ./misc/passthru.nix ./programs/bash/bash.nix ./programs/info.nix