NixOS / nix

Nix, the purely functional package manager
https://nixos.org/
GNU Lesser General Public License v2.1
12.73k stars 1.52k forks source link

libexpr: serialize ASTs to avoid parsing many files each time per evaluation #9102

Closed inclyc closed 1 year ago

inclyc commented 1 year ago

Is your feature request related to a problem? Please describe.

This is the profiling data for eval my nixos configuration. And there are actually 3450 calls to nix::EvalState::parseExprFromFile, which means we will read the filesystem 3450 times, parse the file using a GLR parser, on each evaluation (e.g. the user types nixos-switch rebuild ...).

image

Describe the solution you'd like

Serialize ASTs into some files (for example, module files in nixpkgs, we are parsing these files each time, for nixos config), and get ASTs directly from that file, instead of parsing files again. Similar things like pre-compiled headers, or modules, in C++ language.

Maybe we can explicitly make serialized ASTs at first, and introduce caches to libexpr, for backward compatibility.

Describe alternatives you've considered

Additional context

callgrind.out.1466508.zip

Priorities

Add :+1: to issues you find important.

edolstra commented 1 year ago

IIRC, parsing is a relatively small part of the total evaluation time, so caching ASTs probably isn't worth the complexity. An eval cache hit also avoids parsing, so it's probably better to improve the eval cache.