From 2e43b87c62a2c2f179293ec3645a3688fc1e34a0 Mon Sep 17 00:00:00 2001 From: Wolfgang Walther Date: Sat, 8 Feb 2025 11:11:42 +0100 Subject: [PATCH] replaceVars: fail when exemption can't be found This also changes stdenv's substitute --replace-fail to error out when the replacement is the same as the search pattern, but can't be found. This should not cause any problems in existing code, from what I can tell from grepping nixpkgs. The exception for pattern==replacement was previously introduced all the way back in 5ff872aa24983cf3e1cf28bb990042846c1a97ee, but this was apparently only used to make the check for the warning "simpler". --- .../replace-vars/replace-vars-with.nix | 12 ++++------ pkgs/stdenv/generic/setup.sh | 18 ++++++-------- pkgs/test/replace-vars/default.nix | 24 +++++++++++++++++++ 3 files changed, 36 insertions(+), 18 deletions(-) diff --git a/pkgs/build-support/replace-vars/replace-vars-with.nix b/pkgs/build-support/replace-vars/replace-vars-with.nix index 14a1e6a8e1e3..42be45b6dcf1 100644 --- a/pkgs/build-support/replace-vars/replace-vars-with.nix +++ b/pkgs/build-support/replace-vars/replace-vars-with.nix @@ -58,13 +58,11 @@ let # We use `--replace-fail` instead of `--subst-var-by` so that if the thing isn't there, we fail. - subst-var-by = - name: value: - lib.optionals (value != null) [ - "--replace-fail" - (lib.escapeShellArg "@${name}@") - (lib.escapeShellArg value) - ]; + subst-var-by = name: value: [ + "--replace-fail" + (lib.escapeShellArg "@${name}@") + (lib.escapeShellArg (lib.defaultTo "@${name}@" value)) + ]; substitutions = lib.concatLists (lib.mapAttrsToList subst-var-by replacements); diff --git a/pkgs/stdenv/generic/setup.sh b/pkgs/stdenv/generic/setup.sh index 4198f41aadde..958fc54f277f 100644 --- a/pkgs/stdenv/generic/setup.sh +++ b/pkgs/stdenv/generic/setup.sh @@ -1042,19 +1042,15 @@ substituteStream() { pattern="$2" replacement="$3" shift 3 - local savedvar - savedvar="${!var}" - eval "$var"'=${'"$var"'//"$pattern"/"$replacement"}' - if [ "$pattern" != "$replacement" ]; then - if [ "${!var}" == "$savedvar" ]; then - if [ "$replace_mode" == --replace-warn ]; then - printf "substituteStream() in derivation $name: WARNING: pattern %q doesn't match anything in %s\n" "$pattern" "$description" >&2 - elif [ "$replace_mode" == --replace-fail ]; then - printf "substituteStream() in derivation $name: ERROR: pattern %q doesn't match anything in %s\n" "$pattern" "$description" >&2 - return 1 - fi + if ! [[ "${!var}" == *"$pattern"* ]]; then + if [ "$replace_mode" == --replace-warn ]; then + printf "substituteStream() in derivation $name: WARNING: pattern %q doesn't match anything in %s\n" "$pattern" "$description" >&2 + elif [ "$replace_mode" == --replace-fail ]; then + printf "substituteStream() in derivation $name: ERROR: pattern %q doesn't match anything in %s\n" "$pattern" "$description" >&2 + return 1 fi fi + eval "$var"'=${'"$var"'//"$pattern"/"$replacement"}' ;; --subst-var) diff --git a/pkgs/test/replace-vars/default.nix b/pkgs/test/replace-vars/default.nix index 7d9200a2cf08..e1cc2bf1c13d 100644 --- a/pkgs/test/replace-vars/default.nix +++ b/pkgs/test/replace-vars/default.nix @@ -119,6 +119,30 @@ let grep -F "@c@" $failed/testBuildFailure.log ! grep -F "@b@" $failed/testBuildFailure.log + touch $out + ''; + + fails-in-check-phase-with-bad-exemption = + runCommand "replaceVars-fails" + { + failed = + let + src = builtins.toFile "source.txt" '' + @a@ + @b@ + ''; + in + testBuildFailure ( + callReplaceVars src { + a = "a"; + b = null; + c = null; + } + ); + } + '' + grep -e "ERROR: pattern @c@ doesn't match anything in file.*source.txt" $failed/testBuildFailure.log + touch $out ''; };