summary refs log tree commit diff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/attrsets.nix9
-rw-r--r--lib/default.nix4
-rw-r--r--lib/fixed-points.nix10
3 files changed, 21 insertions, 2 deletions
diff --git a/lib/attrsets.nix b/lib/attrsets.nix
index 2a1b866dbc5..d374d229f59 100644
--- a/lib/attrsets.nix
+++ b/lib/attrsets.nix
@@ -94,6 +94,15 @@ rec {
   attrValues = builtins.attrValues or (attrs: attrVals (attrNames attrs) attrs);
 
 
+  /* Given a set of attribute names, return the set of the corresponding
+     attributes from the given set.
+
+     Example:
+       getAttrs [ "a" "b" ] { a = 1; b = 2; c = 3; }
+       => { a = 1; b = 2; }
+  */
+  getAttrs = names: attrs: genAttrs names (name: attrs.${name});
+
   /* Collect each attribute named `attr' from a list of attribute
      sets.  Sets that don't contain the named attribute are ignored.
 
diff --git a/lib/default.nix b/lib/default.nix
index d7a05fec833..e4e3e7d325a 100644
--- a/lib/default.nix
+++ b/lib/default.nix
@@ -61,10 +61,10 @@ let
       boolToString mergeAttrs flip mapNullable inNixShell min max
       importJSON warn info nixpkgsVersion version mod compare
       splitByAndCompare functionArgs setFunctionArgs isFunction;
-    inherit (fixedPoints) fix fix' extends composeExtensions
+    inherit (fixedPoints) fix fix' converge extends composeExtensions
       makeExtensible makeExtensibleWithCustomName;
     inherit (attrsets) attrByPath hasAttrByPath setAttrByPath
-      getAttrFromPath attrVals attrValues catAttrs filterAttrs
+      getAttrFromPath attrVals attrValues getAttrs catAttrs filterAttrs
       filterAttrsRecursive foldAttrs collect nameValuePair mapAttrs
       mapAttrs' mapAttrsToList mapAttrsRecursive mapAttrsRecursiveCond
       genAttrs isDerivation toDerivation optionalAttrs
diff --git a/lib/fixed-points.nix b/lib/fixed-points.nix
index 7169c46fcbb..2f818c88de5 100644
--- a/lib/fixed-points.nix
+++ b/lib/fixed-points.nix
@@ -24,6 +24,16 @@ rec {
   # for a concrete example.
   fix' = f: let x = f x // { __unfix__ = f; }; in x;
 
+  # Return the fixpoint that `f` converges to when called recursively, starting
+  # with the input `x`.
+  #
+  #     nix-repl> converge (x: x / 2) 16
+  #     0
+  converge = f: x:
+    if (f x) == x
+    then x
+    else converge f (f x);
+
   # Modify the contents of an explicitly recursive attribute set in a way that
   # honors `self`-references. This is accomplished with a function
   #