Skip to content

Commit

Permalink
getDefaultNixPath: actually respect {restrict,pure}-eval
Browse files Browse the repository at this point in the history
Previously, getDefaultNixPath was called too early: at initialisation
time, before CLI and config have been processed, when `restrictEval` and
`pureEval` both have their default value `false`. Call it when
initialising the EvalState instead, and use `setDefault`.
  • Loading branch information
ncfavier committed Jan 25, 2023
1 parent f233fd4 commit b60f41d
Show file tree
Hide file tree
Showing 4 changed files with 37 additions and 18 deletions.
43 changes: 27 additions & 16 deletions src/libexpr/eval.cc
Original file line number Diff line number Diff line change
Expand Up @@ -519,6 +519,7 @@ EvalState::EvalState(
static_assert(sizeof(Env) <= 16, "environment must be <= 16 bytes");

/* Initialise the Nix expression search path. */
evalSettings.nixPath.setDefault(evalSettings.getDefaultNixPath());
if (!evalSettings.pureEval) {
for (auto & i : _searchPath) addToSearchPath(i);
for (auto & i : evalSettings.nixPath.get()) addToSearchPath(i);
Expand Down Expand Up @@ -2472,30 +2473,40 @@ std::ostream & operator << (std::ostream & str, const ExternalValueBase & v) {

EvalSettings::EvalSettings()
{
auto var = getEnv("NIX_PATH");
if (var) nixPath = parseNixPath(*var);
}

/* impure => NIX_PATH or a default path
* restrict-eval => NIX_PATH
* pure-eval => empty
*/
Strings EvalSettings::getDefaultNixPath()
{
Strings res;
auto add = [&](const Path & p, const std::string & s = std::string()) {
if (pathExists(p)) {
if (s.empty()) {
res.push_back(p);
} else {
res.push_back(s + "=" + p);
if (pureEval)
return {};

auto var = getEnv("NIX_PATH");
if (var) {
return parseNixPath(*var);
} else {
Strings res;
auto add = [&](const Path & p, const std::string & s = std::string()) {
if (pathExists(p)) {
if (s.empty()) {
res.push_back(p);
} else {
res.push_back(s + "=" + p);
}
}
};

if (!restrictEval && !pureEval) {
add(getHome() + "/.nix-defexpr/channels");
add(settings.nixStateDir + "/profiles/per-user/root/channels/nixpkgs", "nixpkgs");
add(settings.nixStateDir + "/profiles/per-user/root/channels");
}
};

if (!evalSettings.restrictEval && !evalSettings.pureEval) {
add(getHome() + "/.nix-defexpr/channels");
add(settings.nixStateDir + "/profiles/per-user/root/channels/nixpkgs", "nixpkgs");
add(settings.nixStateDir + "/profiles/per-user/root/channels");
return res;
}

return res;
}

bool EvalSettings::isPseudoUrl(std::string_view s)
Expand Down
4 changes: 2 additions & 2 deletions src/libexpr/eval.hh
Original file line number Diff line number Diff line change
Expand Up @@ -570,7 +570,7 @@ struct EvalSettings : Config
{
EvalSettings();

static Strings getDefaultNixPath();
Strings getDefaultNixPath();

static bool isPseudoUrl(std::string_view s);

Expand All @@ -580,7 +580,7 @@ struct EvalSettings : Config
"Whether builtin functions that allow executing native code should be enabled."};

Setting<Strings> nixPath{
this, getDefaultNixPath(), "nix-path",
this, {}, "nix-path",
"List of directories to be searched for `<...>` file references."};

Setting<bool> restrictEval{
Expand Down
5 changes: 5 additions & 0 deletions tests/nix_path.sh
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,8 @@ nix-instantiate --eval -E '<by-relative-path/simple.nix>' --restrict-eval

[[ $(nix-instantiate --find-file by-absolute-path/simple.nix) = $PWD/simple.nix ]]
[[ $(nix-instantiate --find-file by-relative-path/simple.nix) = $PWD/simple.nix ]]

unset NIX_PATH

[[ $(nix-instantiate --option nix-path by-relative-path=. --find-file by-relative-path/simple.nix) = "$PWD/simple.nix" ]]
[[ $(NIX_PATH= nix-instantiate --option nix-path by-relative-path=. --find-file by-relative-path/simple.nix) = "$PWD/simple.nix" ]]
3 changes: 3 additions & 0 deletions tests/restricted.sh
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,9 @@ nix-instantiate --restrict-eval --eval -E 'builtins.readDir ../src/nix-channel'
(! nix-instantiate --restrict-eval --eval -E 'let __nixPath = [ { prefix = "foo"; path = ./.; } ]; in <foo>')
nix-instantiate --restrict-eval --eval -E 'let __nixPath = [ { prefix = "foo"; path = ./.; } ]; in <foo>' -I src=.

# no default NIX_PATH
(unset NIX_PATH; ! nix-instantiate --restrict-eval --find-file .)

p=$(nix eval --raw --expr "builtins.fetchurl file://$(pwd)/restricted.sh" --impure --restrict-eval --allowed-uris "file://$(pwd)")
cmp $p restricted.sh

Expand Down

0 comments on commit b60f41d

Please sign in to comment.