aboutsummaryrefslogtreecommitdiff
path: root/src/libexpr/eval.cc
AgeCommit message (Collapse)Author
2022-05-06debugError()Ben Burdette
2022-05-05rename valmapBen Burdette
2022-05-05Style fixesEelco Dolstra
In particular, use std::make_shared and enumerate(). Also renamed some fields to fit naming conventions.
2022-04-29line endingsBen Burdette
2022-04-29fix 'suggestions' errorBen Burdette
2022-04-29incorporate PosIdx changes, symbol changes.Ben Burdette
2022-04-28Merge branch 'master' into debug-merge-masterBen Burdette
2022-04-25rename SymbolIdx -> Symbol, Symbol -> SymbolStrpennae
after #6218 `Symbol` no longer confers a uniqueness invariant on the string it wraps, it is now possible to create multiple symbols that compare equal but whose string contents have different addresses. this guarantee is now only provided by `SymbolIdx`, leaving `Symbol` only as a string wrapper that knows about the intricacies of how symbols need to be formatted for output. this change renames `SymbolIdx` to `Symbol` to restore the previous semantics of `Symbol` to that name. we also keep the wrapper type and rename it to `SymbolStr` instead of returning plain strings from lookups into the symbol table because symbols are formatted for output in many places. theoretically we do not need `SymbolStr`, only a function that formats a string for output as a symbol, but having to wrap every symbol that appears in a message into eg `formatSymbol()` is error-prone and inconvient.
2022-04-21store Symbols in a table as well, like positionspennae
this slightly increases the amount of memory used for any given symbol, but this increase is more than made up for if the symbol is referenced more than once in the EvalState that holds it. on average every symbol should be referenced at least twice (once to introduce a binding, once to use it), so we expect no increase in memory on average. symbol tables are limited to 2³² entries like position tables, and similar arguments apply to why overflow is not likely: 2³² symbols would require as many string instances (at 24 bytes each) and map entries (at 24 bytes or more each, assuming that the map holds on average at most one item per bucket as the docs say). a full symbol table would require at least 192GB of memory just for symbols, which is well out of reach. (an ofborg eval of nixpks today creates less than a million symbols!)
2022-04-21don't use Symbol in Pos to represent a pathpennae
PosTable deduplicates origin information, so using symbols for paths is no longer necessary. moving away from path Symbols also reduces the usage of symbols for things that are not keys in attribute sets, which will become important in the future when we turn symbols into indices as well.
2022-04-21replace most Pos objects/ptrs with indexes into a position tablepennae
Pos objects are somewhat wasteful as they duplicate the origin file name and input type for each object. on files that produce more than one Pos when parsed this a sizeable waste of memory (one pointer per Pos). the same goes for ptr<Pos> on 64 bit machines: parsing enough source to require 8 bytes to locate a position would need at least 8GB of input and 64GB of expression memory. it's not likely that we'll hit that any time soon, so we can use a uint32_t index to locate positions instead.
2022-04-21make throw*Error member functions of EvalStatepennae
when we introduce position and symbol tables we'll need to do lookups to turn indices into those tables into actual positions/symbols. having the error functions as members of EvalState will avoid a lot of churn for adding lookups into the tables for each caller.
2022-04-21remove Symbol::emptypennae
the only use of this function is to determine whether a lambda has a non-set formal, but this use is arguably better served by Symbol::set and using a non-Symbol instead of an empty symbol in the parser when no such formal is present.
2022-04-21turn primop names into stringspennae
we don't *need* symbols here. the only advantage they have over strings is making call-counting slightly faster, but that's a diagnostic feature and thus needn't be optimized. this also fixes a move bug that previously didn't show up: PrimOp structs were accessed after being moved from, which technically invalidates them. previously the names remained valid because Symbol copies on move, but strings are invalidated. we now copy the entire primop struct instead of moving since primop registration happen once and are not performance-sensitive.
2022-04-09remove commaBen Burdette
2022-04-09don't use std::map mergeBen Burdette
2022-04-08minor cleanupBen Burdette
2022-04-08move throw to preverve Error type; turn off debugger for tryEvalBen Burdette
2022-04-07Merge remote-tracking branch 'upstream/master' into upstream-mergeBen Burdette
2022-04-07remove debug codeBen Burdette
2022-03-31commentsBen Burdette
2022-03-31show 'with' bindings as well as staticBen Burdette
2022-03-31Add support for impure derivationsEelco Dolstra
Impure derivations are derivations that can produce a different result every time they're built. Example: stdenv.mkDerivation { name = "impure"; __impure = true; # marks this derivation as impure outputHashAlgo = "sha256"; outputHashMode = "recursive"; buildCommand = "date > $out"; }; Some important characteristics: * This requires the 'impure-derivations' experimental feature. * Impure derivations are not "cached". Thus, running "nix-build" on the example above multiple times will cause a rebuild every time. * They are implemented similar to CA derivations, i.e. the output is moved to a content-addressed path in the store. The difference is that we don't register a realisation in the Nix database. * Pure derivations are not allowed to depend on impure derivations. In the future fixed-output derivations will be allowed to depend on impure derivations, thus forming an "impurity barrier" in the dependency graph. * When sandboxing is enabled, impure derivations can access the network in the same way as fixed-output derivations. In relaxed sandboxing mode, they can access the local filesystem.
2022-03-29remove const_castBen Burdette
2022-03-25add DebugTrace for errorBen Burdette
2022-03-25Only provide builtin.{getFlake,fetchClosure} is the corresponding ↵Eelco Dolstra
experimental feature is enabled This allows writing fallback code like if builtins ? fetchClosure then builtins.fetchClose { ... } else builtins.storePath ...
2022-03-22Don't hide repeated values while generating manifest.nixEelco Dolstra
Fixes #6243.
2022-03-22printValue(): <REPEAT> -> «repeated»Eelco Dolstra
This ensures that it doesn't get parsed as a valid Nix expression.
2022-03-18Decode string context straight to using `StorePath`sJohn Ericson
I gather decoding happens on demand, so I hope don't think this should have any perf implications one way or the other.
2022-03-14have only one debuggerHook declarationBen Burdette
2022-03-11Create some type aliases for string ContextsJohn Ericson
2022-03-11Merge remote-tracking branch 'origin/eval-suggestions'Eelco Dolstra
2022-03-11Merge pull request #5865 from pennae/memory-friendlinessEelco Dolstra
be more memory friendly
2022-03-08force-inline a few much-used functionspennae
these functions are called a whole lot, and they're all comparatively small. always inlining them gives ~0.7% performance boost on eval. before: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.935 s ± 0.052 s [User: 5.852 s, System: 0.853 s] Range (min … max): 6.808 s … 7.026 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 329.8 ms ± 2.7 ms [User: 299.0 ms, System: 30.8 ms] Range (min … max): 326.6 ms … 336.5 ms 20 runs Benchmark 3: nix flakes eval --raw --impure --file expr.nix Time (mean ± σ): 2.655 s ± 0.038 s [User: 2.364 s, System: 0.220 s] Range (min … max): 2.574 s … 2.737 s 20 runs after: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.912 s ± 0.036 s [User: 5.823 s, System: 0.856 s] Range (min … max): 6.849 s … 6.980 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 325.1 ms ± 2.5 ms [User: 293.2 ms, System: 31.8 ms] Range (min … max): 322.2 ms … 332.8 ms 20 runs Benchmark 3: nix flakes eval --raw --impure --file expr.nix Time (mean ± σ): 2.636 s ± 0.024 s [User: 2.352 s, System: 0.226 s] Range (min … max): 2.574 s … 2.681 s 20 runs
2022-03-08cache singleton Envs just like Valuespennae
vast majority of envs is this size. before: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.946 s ± 0.041 s [User: 5.875 s, System: 0.835 s] Range (min … max): 6.834 s … 7.005 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 330.3 ms ± 2.5 ms [User: 299.2 ms, System: 30.9 ms] Range (min … max): 327.5 ms … 337.7 ms 20 runs Benchmark 3: nix eval --raw --impure --expr 'with import <nixpkgs/nixos> {}; system' Time (mean ± σ): 2.671 s ± 0.035 s [User: 2.370 s, System: 0.232 s] Range (min … max): 2.597 s … 2.749 s 20 runs after: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.935 s ± 0.052 s [User: 5.852 s, System: 0.853 s] Range (min … max): 6.808 s … 7.026 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 329.8 ms ± 2.7 ms [User: 299.0 ms, System: 30.8 ms] Range (min … max): 326.6 ms … 336.5 ms 20 runs Benchmark 3: nix flakes eval --raw --impure --file expr.nix Time (mean ± σ): 2.655 s ± 0.038 s [User: 2.364 s, System: 0.220 s] Range (min … max): 2.574 s … 2.737 s 20 runs
2022-03-08remove GC_PTR_STORE_AND_DIRTYpennae
turns out it's only necessary for MANUAL_VDB, which nix doesn't use. omitting them gives a slight performance improvement on eval. before: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.988 s ± 0.061 s [User: 5.935 s, System: 0.845 s] Range (min … max): 6.865 s … 7.075 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 332.6 ms ± 3.9 ms [User: 299.6 ms, System: 32.9 ms] Range (min … max): 328.1 ms … 339.1 ms 20 runs Benchmark 3: nix eval --raw --impure --expr 'with import <nixpkgs/nixos> {}; system' Time (mean ± σ): 2.681 s ± 0.049 s [User: 2.382 s, System: 0.228 s] Range (min … max): 2.607 s … 2.776 s 20 runs after: Benchmark 1: nix flakes search --no-eval-cache --offline ../nixpkgs hello Time (mean ± σ): 6.946 s ± 0.041 s [User: 5.875 s, System: 0.835 s] Range (min … max): 6.834 s … 7.005 s 20 runs Benchmark 2: nix flakes eval -f ../nixpkgs/pkgs/development/haskell-modules/hackage-packages.nix Time (mean ± σ): 330.3 ms ± 2.5 ms [User: 299.2 ms, System: 30.9 ms] Range (min … max): 327.5 ms … 337.7 ms 20 runs Benchmark 3: nix eval --raw --impure --expr 'with import <nixpkgs/nixos> {}; system' Time (mean ± σ): 2.671 s ± 0.035 s [User: 2.370 s, System: 0.232 s] Range (min … max): 2.597 s … 2.749 s 20 runs
2022-03-08Also display some suggestions for invalid formal argumentsregnat
```console $ nix eval --expr '({ foo ? 1 }: foo) { fob = 2; }' error: anonymous function at (string):1:2 called with unexpected argument 'fob' at «string»:1:1: 1| ({ foo ? 1 }: foo) { fob = 2; } | ^ Did you mean foo? ``` Not that because Nix will first check for _missing_ arguments before checking for extra arguments, `({ foo }: foo) { fob = 1; }` will complain about the missing `foo` argument (rather than extra `fob`) and so won’t display a suggestion.
2022-03-08Try and make the darwin build happyregnat
2022-03-08Add some suggestions to the evaluatorregnat
Make the evaluator show some suggestions when trying to access an invalid field from an attrset. ```console $ nix eval --expr '{ foo = 1; }.foa' error: attribute 'foa' missing at «string»:1:1: 1| { foo = 1; }.foa | ^ Did you mean foo? ```
2022-03-07dupStringWithLen -> makeImmutableStringRobert Hensing
Refactor the `size == 0` logic into a new helper function that replaces dupStringWithLen. The name had to change, because unlike a `dup`-function, it does not always allocate a new string.
2022-03-07Value::mkPath: Avoid potential crash from null string_viewRobert Hensing
2022-03-07Value::mkString: Avoid crash from null string_viewRobert Hensing
2022-03-03Be more aggressive in hiding repeated valuesEelco Dolstra
We now memoize on Bindings / list element vectors rather than Values, so that e.g. two Values that point to the same Bindings will be printed only once.
2022-03-03printValue(): Don't show repeated valuesEelco Dolstra
Fixes #6157.
2022-03-02Add EvalState::coerceToStorePath() helperEelco Dolstra
This is useful whenever we want to evaluate something to a store path (e.g. in get-drvs.cc). Extracted from the lazy-trees branch (where we can require that a store path must come from a store source tree accessor).
2022-03-01fetch{url,Tarball}: Remove 'narHash' attributeEelco Dolstra
This was introduced in #6174. However fetch{url,Tarball} are legacy and we shouldn't have an undocumented attribute that does the same thing as one that already exists ('sha256').
2022-02-28Add EvalState::allowAndSetStorePathString helperRobert Hensing
This switches addPath from `printStorePath` to `toRealPath`.
2022-02-25Remove std::string alias (for real this time)Eelco Dolstra
Also use std::string_view in a few more places.
2022-02-15Expr refs instead of pointersBen Burdette
2022-02-15quit repl from step modeBen Burdette