lib: add xor

This gets clumsily reimplemented in various places, to no useful end.
This commit is contained in:
edef 2024-04-04 14:05:18 +00:00
parent d03a448222
commit 725bb4e48c
12 changed files with 49 additions and 38 deletions

View file

@ -69,7 +69,7 @@ let
hasAttr head isAttrs isBool isInt isList isPath isString length hasAttr head isAttrs isBool isInt isList isPath isString length
lessThan listToAttrs pathExists readFile replaceStrings seq lessThan listToAttrs pathExists readFile replaceStrings seq
stringLength sub substring tail trace; stringLength sub substring tail trace;
inherit (self.trivial) id const pipe concat or and bitAnd bitOr bitXor inherit (self.trivial) id const pipe concat or and xor bitAnd bitOr bitXor
bitNot boolToString mergeAttrs flip mapNullable inNixShell isFloat min max bitNot boolToString mergeAttrs flip mapNullable inNixShell isFloat min max
importJSON importTOML warn warnIf warnIfNot throwIf throwIfNot checkListOfEnum importJSON importTOML warn warnIf warnIfNot throwIf throwIfNot checkListOfEnum
info showWarnings nixpkgsVersion version isInOldestRelease info showWarnings nixpkgsVersion version isInOldestRelease

View file

@ -102,6 +102,7 @@ let
types types
updateManyAttrsByPath updateManyAttrsByPath
versions versions
xor
; ;
testingThrow = expr: { testingThrow = expr: {
@ -210,6 +211,21 @@ runTests {
expected = false; expected = false;
}; };
testXor = {
expr = [
(xor true false)
(xor true true)
(xor false false)
(xor false true)
];
expected = [
true
false
false
true
];
};
testFix = { testFix = {
expr = fix (x: {a = if x ? a then "a" else "b";}); expr = fix (x: {a = if x ? a then "a" else "b";});
expected = {a = "a";}; expected = {a = "a";};

View file

@ -199,6 +199,24 @@ in {
*/ */
and = x: y: x && y; and = x: y: x && y;
/**
boolean exclusive or
# Inputs
`x`
: 1\. Function argument
`y`
: 2\. Function argument
*/
# We explicitly invert the arguments purely as a type assertion.
# This is invariant under XOR, so it does not affect the result.
xor = x: y: (!x) != (!y);
/** /**
bitwise not bitwise not
*/ */

View file

@ -871,7 +871,6 @@ in {
} }
{ {
assertion = let assertion = let
xor = a: b: a && !b || b && !a;
isEffectivelySystemUser = user.isSystemUser || (user.uid != null && user.uid < 1000); isEffectivelySystemUser = user.isSystemUser || (user.uid != null && user.uid < 1000);
in xor isEffectivelySystemUser user.isNormalUser; in xor isEffectivelySystemUser user.isNormalUser;
message = '' message = ''

View file

@ -9,7 +9,6 @@ with lib;
let let
cfg = config.services.kea; cfg = config.services.kea;
xor = x: y: (!x && y) || (x && !y);
format = pkgs.formats.json {}; format = pkgs.formats.json {};
chooseNotNull = x: y: if x != null then x else y; chooseNotNull = x: y: if x != null then x else y;

View file

@ -42,12 +42,9 @@
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -41,12 +41,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -41,12 +41,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -41,12 +41,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -41,12 +41,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -41,12 +41,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +

View file

@ -46,12 +46,9 @@
, monorepoSrc ? null , monorepoSrc ? null
}: }:
assert let assert
int = a: if a then 1 else 0;
xor = a: b: ((builtins.bitXor (int a) (int b)) == 1);
in
lib.assertMsg lib.assertMsg
(xor (lib.xor
(gitRelease != null) (gitRelease != null)
(officialRelease != null)) (officialRelease != null))
("must specify `gitRelease` or `officialRelease`" + ("must specify `gitRelease` or `officialRelease`" +