We're sorry but this page doesn't work properly without JavaScript enabled. Please enable it to continue.
Feedback

Running the Nix daemon (nearly) rootless

00:00

Formal Metadata

Title
Running the Nix daemon (nearly) rootless
Title of Series
Number of Parts
28
Author
License
CC Attribution 3.0 Unported:
You are free to use, adapt and copy, distribute and transmit the work or content in adapted or unchanged form for any legal purpose as long as the work is attributed to the author in the manner specified by the author or licensor.
Identifiers
Publisher
Release Date
Language

Content Metadata

Subject Area
Genre
Abstract
Making Nix follow the principle of least privilege by removing as much as possible the need to it to run as root In multi-user mode, the Nix daemon is expected to run as root. This is quite annoying from a security point of view as the Nix codebase is (somewhat) large and not properly audited. Because of that it is also an adoption blocker in some places. I turns out that there's very few places where Nix actually needs to be root, and we can remove or isolate these, as done in https://github.com/NixOS/nix/pull/5380.
Roundness (object)Profil (magazine)Client (computing)Computer programmingFilm editingLevel (video gaming)Data managementCategory of beingLine (geometry)RootSet (mathematics)40 (number)Cartesian coordinate systemCommunications protocolBinary codePhysical systemWave packetEmailLaptopCASE <Informatik>Multiplication signTheory of relativityControl flowReading (process)Goodness of fitSpeicherbereinigungResultantRoutingMehrplatzsystemVolumenvisualisierungError messageDirection (geometry)Arrow of timeRight angleWordSpeciesDemonData storage deviceDirected graphSuite (music)Local ringVarianceFile systemLink (knot theory)SimulationBitCodeProper mapBuildingSoftwareCodeVirtual machineDerivation (linguistics)Enterprise architectureSurface
Transcript: English(auto-generated)
OK, so hey, everyone. I'm sorry you're going to have to rewrite your brain a little because we're going to get down from Ron's very high-level talk on the future of the community to a very mundane technical problem that we've been solving.
So what I'm going to talk to you about today is how we can make the Nix daemon run as much as possible without being rude. So well, let's first try and understand why we want to do that. So for a security-minded person, running Nix like in multi-user mode, essentially it's running this big C++ code base.
I've just checked. It's around 60,000 line of codes. That has never been properly audited. That's doing some very dangerous things. It's accessing the network. It's running its own custom binary protocol. It's essentially running untrusted code because the daemon is just running the derivations builders. And so that's the kind of things that,
well, I don't mind running it as root on my laptop. It's a single-user machine. But if you're running it in a big enterprise context, you definitely don't want to run this as root. So it turns out that Nix fundamentally doesn't require to be root. You can do a single-user installation. You don't need to be root. Just need to have slash Nix,
well, even that you don't really need. But that doesn't work when you're using the daemon. We can try it. If, like, the slash things are not coming in the right order, but if you try to run the Nix daemon and then as another user you run a Nix command that tries to talk to the daemon, you're gonna be greeted by some nice errors
with a, you can see the red errors popping up in the middle of the error message. And it turns out that there's two more or less bad reasons for why the daemon requires to be root. They were good originally, but now hopefully we can get rid of them.
So the first one is that the daemon is trying to do some profile management for the client, trying to be helpful, but too helpful for its own good. And the other thing is the garbage collection, where for some reason that we're gonna see right after, currently the daemon wants to have root access to the system.
So, well, can we fix this? Well, let's see about that. So the first issue about the daemon trying to help the client a bit too much, turns out that that's mostly an historical artifact and we can just let the client, all the profile management by itself.
That works, that even makes the code nicer in a lot of ways. A small problem that's kind of breaking the backwards compatibility in a small cases, which is why it's still there. We need to figure out how to migrate things properly. So that's not too much of a problem. The other problem is the garbage collection.
Why does the garbage collection needs to run as roots? Well, it works if you're not roots. It works even very, very well in that if you build something, well, you have this nice result sim link, you can run it. Now you run the garbage collection and the thing just disappeared,
which shouldn't be the case. Like you have a root, a GC root, so it shouldn't be garbage collected. But if your daemon is not root, that's not working properly. So let's look quickly at how the garbage collection works to understand why it is so. So what happens when you run nix build something is that nix will create what's called an indirect root.
So it's gonna create something under nix var nix, it's on internal magic. And that's gonna be a sim link pointing to the result path that you have. And that result is itself a sim link pointing to something somewhere in the store.
And so nix will inspect this nix var nix GC roots thing, follow the sim links and see that, oh yeah, okay, hello is something that can be reachable. I don't wanna delete it. Now, if you remove this result sim link, then great, then you'll remove the sim link path to the store. So nix, well, the thing is no longer alive
as far as nix is concerned. So it can be garbage collected. That's great because then you can just, you don't have to bother about what's in the GC roots things. You just have your local sim links. You can delete them to remove the roots and you're happy. But now what happens if, what happens if now the daemon doesn't have access
to this result sim link? The sim link is there, but the daemon doesn't have the rights to read it. Well, as far as it's concerned, it's like if the sim link didn't exist, the thing is no longer a GC roots. And so it can be garbage collected, which is exactly what we had before. And that's problematic. So can we get rid of that?
Yes, well, we can just add some layers of stuff on top of that. And the best solution we found so far is that let's just make the next daemon run as a normal user, but another daemon that's gonna run as roots and just do that, which is a bit silly, but it turns out that it's nicer in many ways
because only that new daemon will need to be root. And because it's a very small self-contained thing that just has to traverse the file system in many ways. First, it's smaller, easier to edit. And also because it has a very restricted set of feature that it's only doing a very small set of things.
It just needs read-only access to the system. It doesn't need to do any network access or anything. So now you can sandbox it properly. And that reduces the attack surface of Nix a lot. So that was all I've already exceeded in my five minutes, sorry about that. And I'm letting the next speaker come in.
Thank you.