stdenv: don't include drvs in disallowedRefs as build-time deps.#211783
stdenv: don't include drvs in disallowedRefs as build-time deps.#211783Artturin merged 1 commit intoNixOS:stagingfrom
Conversation
There was a problem hiding this comment.
how does this interact with CA derivations
There was a problem hiding this comment.
That should probably work (although a bit fragile) because drv.outPath will evaluate to a placeholder that will be rewritten just before the build if drv is part of the derivation closure. Which means that
- If
drvis part of the closure (because it's refered to somewhere else), then it will do the right thing (theunsafeDiscardStringContextwill morally be a no-op) - Otherwise, the placeholder won't be rewritten, but it's fine since because the derivation isn't part of the build-time closure we know that it can't be in the runtime closure either
|
should target staging https://github.com/NixOS/nixpkgs/blob/master/CONTRIBUTING.md#rebasing-between-branches-ie-from-master-to-staging and commit msg should follow the guide |
8db65db to
ece8640
Compare
ece8640 to
1e5c2bf
Compare
|
@Artturin: right, I didn't know about staging, that should be fixed now. |
1e5c2bf to
be21494
Compare
trofi
left a comment
There was a problem hiding this comment.
LGTM. I wonder if nix's derivation() builtin should already do the right thing. WDYT of filing a bug there? Sounds reasonable?
CA case is interesting. I think (hope) CA behaviour will not be changed by this context discard: our scanning operation does not need to pull in contents of checked derivations, but will still require building one to get the actual path for CA case. Thus I would guess this change will only help to non-CA builds. Which might be good enough. For CA-enabled builds such scans are probably already incorrect as there is no guarantee that build-CA has different store path from host-CA.
|
@trofi, agreed. Apparently there was an issue for nix already, but it got dismissed as not a bug, even though I think that the current behaviour is definitely surprising and unproductive and I don't think we should expect people to understand this intricacy and know about Regarding CA derivations, I must admit that I did not look into them enough to know how this would work in that case. |
Good find! Worth adding a link to to the comment around
I think it's OK to ignore it for now. We can always conditionally restore it back. |
|
@trofi sure! I updated the description to include the reference, I didn't know about the issue when I made the PR. |
be21494 to
bb2bc44
Compare
|
i added a link to the nix issue |
|
work for the future
outputChecks."out" = {
# The closure of 'out' must not be larger than 256 MiB.
maxClosureSize = 256 * 1024 * 1024;
# It must not refer to C compiler or to the 'dev' output.
disallowedRequisites = [ stdenv.cc "dev" ];
};
outputChecks."dev" = {
# The 'dev' output must not be larger than 128 KiB.
maxSize = 128 * 1024;
};perhaps this could even be fixed in nix because there's not many users of structuredAttrs outputChecks yet |
Introduces unnecessary attrs to all derivations
Would an opt-in flag into derivation() to enable new behaviour be an option? (like |
It would. It would be less useful though since the main issue here is that it's fairly unintuitive, so people will likely overlook it until it actually bites. |
bb2bc44 to
15655db
Compare
Derivations listed as disallowedReferences or disallowedRequisites, currently end up as build-time dependencies. This is problematic since the disallowed derivations will be built by nix as build-time dependencies, while those derivations might take a very long time to build, or might not even build successfully on the platform used. However, in order to scan for disallowed references in the final output, knowing the out path is sufficient, and the out path can be calculated from the derivation without needing to build it, saving time and resources. While the problem is less severe for allowedReferences and allowedRequisites, since we want the derivation to be built eventually, we would still like to get the error early and without having to wait while nix builds a derivation that might not be used (e.g. if we listed the wrong one).
15655db to
51acc62
Compare
|
I think this should really be fixed in Nix. With a proper deprecation strategy this should not be a problem. E.g. introduce a
If you want this to be more expressive you can also do something like We should be brave enough to deprecate problematic behavior, otherwise these problems will never be fixed. |
|
Noticed content-addressed failures on today's system build. Small reproducer against Did not look in detail yet. Will spend some time this evening to understand it unless someone gets earlier to it. |
No, that's an unnecessary breaking change.
Deprecate yes, remove no. A subtle difference until it punches you in the face while you're trying to get some old software to work.
I think it'd be ok for supposedly easy changes like this to be linearized into a single |
Fair enough. Instead then (and I think that's what you're implying), the default should be changed for just I think we should rethink this policy though, because not ever being able to deprecate old features really locks us in, requiring maintenance on code that may be only very rarely needed. What if instead we were to not only specify a minimum support Nix version for nixpkgs (backwards compat), but also a maximum (forwards compat, perhaps with a date). Nixpkgs CI should make sure that it works with the minimum supported Nix version, and Nix CI should make sure it works with the earliest nixpkgs that supports its own version. This could be something like supporting Nix versions released around a NixOS release ± 5 years. This does mean that we can't import arbitrary old nixpkgs versions anymore (there should be a check warning/erroring for that in nixpkgs), essentially limiting the time range of nixpkgs versions in a single Nix evaluation. But with a good error message we can present some workarounds:
This also very much relates to NixOS/rfcs#137, I'm abusing this issue as a scratch pad at this point 😅 |
Without the change build for packages that use `disallowedReferences`
fails in `contentAddressedByDefault = true` mode:
$ nix build -f. ruby_3_1 --arg config '{ contentAddressedByDefault = true; }'
...
error: derivation contains an illegal reference specifier '/0j3hif3ni7zl5zhlzzr5q2q23z66136mnzp75pyiqp5c72q14im2'
error: 1 dependencies of derivation '/nix/store/39ji7qp225pxvrm8cgvzmyjqsyis2n0h-ruby-3.1.2.drv' failed to build
Original intent of NixOS#211783 was to
avoid pulling in actual derivation for reference scanning purposes.
Unfortunately CA derivations's outputPath are placeholders until they
are instantiated.
Let's restore string context for CA derivations for now.
Proposed restore of context just for CA derivations as #214044. |
|
@infinisil I appreciate your care towards the Nix team, but "too much backcompat behavior" is not a problem I perceive in the Nix code. I can build a 2013 zlib (using $ nix-build -I nixpkgs=https://github.com/NixOS/nixpkgs/archive/release-13.10.tar.gz --expr 'with import <nixpkgs> {}; zlib.override(o: { static = true; })'This capability can be a lifesaver if you have to deal with a really bad legacy binary in some academic, corporate or government environment or whatever. It's even useful for running old binary linux games. Being able to do this (with care of course) is uniquely valuable.
This prevents installing anything old alongside anything new in a single expression.
That's a lot of effort for very little gain (removing a couple of lines of code from Nix). Furthermore, creating and implementing a policy for breaking stuff is also work. A bad kind of work that will make nobody happy. Let's not make new problems if we don't have to. We can revisit this when compatibility becomes a proper burden, but until then, enjoy a working Nix and Nixpkgs. |
…hecks This was added for non-structuredAttrs output checks in NixOS#211783. Here we extend the same concept to structuredAttrs-enabled outputChecks, too. The postgresql package worked around this with some conditionals. Those can now be removed - without causing LLVM to be built or substituted.
Without the change build for packages that use `disallowedReferences`
fails in `contentAddressedByDefault = true` mode:
$ nix build -f. ruby_3_1 --arg config '{ contentAddressedByDefault = true; }'
...
error: derivation contains an illegal reference specifier '/0j3hif3ni7zl5zhlzzr5q2q23z66136mnzp75pyiqp5c72q14im2'
error: 1 dependencies of derivation '/nix/store/39ji7qp225pxvrm8cgvzmyjqsyis2n0h-ruby-3.1.2.drv' failed to build
Original intent of NixOS#211783 was to
avoid pulling in actual derivation for reference scanning purposes.
Unfortunately CA derivations's outputPath are placeholders until they
are instantiated.
Let's restore string context for CA derivations for now.
Derivations listed as
disallowedReferencesordisallowedRequisites, currently end up as build-time dependencies.This is problematic since the disallowed derivations will be built by nix as build-time dependencies, while those derivations might take a very long time to build, or might not even build successfully on the platform used. However, in order to scan for disallowed references in the final output, knowing the out path is sufficient, and the out path can be calculated from the derivation without needing to build it, saving time and resources.
While the problem is less severe for
allowedReferencesandallowedRequisites, since we want the derivation to be built eventually, we would still like to get the error early and without having to wait while nix builds a derivation that might not be used (e.g. if we listed the wrong one).Before this PR:
After this PR:
Note how in the first case
busyboxends up as a build-time dependency, and will be built or substituted if it's not yet in the nix store. In the second case, with the changes in this PR, it no longer ends up as a build-time dependency and won't be built or substituted.There is also an issue for nix itself to fix this on a lower level, where the approach implemented in this PR was suggested.
I don't agree with the conclusion on that issue and I think that it is a perfectly sensible use case to disallow references so that they cannot be accidentally included in the future and that we should not expect from our users to have to use
unsafeDiscardStringContextto get the correct behaviour in that case.Description of changes
Things done
sandbox = trueset innix.conf? (See Nix manual)nix-shell -p nixpkgs-review --run "nixpkgs-review rev HEAD". Note: all changes have to be committed, also see nixpkgs-review usage./result/bin/)nixos/doc/manual/md-to-db.shto update generated release notes