Rebuild the World: Nix Ecosystem
This talk provides an overview of the Nix package manager, its ecosystem, and its role in reproducible software builds. The speakers discuss the fundamental components of Nix, including the package manager, package sets, and the NixOS operating system. They highlight the benefits of using Nix for managing build recipes and ensuring consistent, reproducible environments across different systems. The discussion also touches on the integration of Nix with containerization technologies like Docker and the potential for Nix to improve supply chain security.
Why Your Build Pipeline is a Security Black Box
TLDR: Most build pipelines treat dependencies as opaque blobs, creating a massive blind spot for supply chain attacks. By moving to a declarative, reproducible build system like Nix, you can cryptographically verify every single dependency and build step. This talk breaks down how to move from "it works on my machine" to a verifiable, immutable build process that eliminates entire classes of supply chain vulnerabilities.
Software supply chain security is currently a mess of "hope-based" security. We pull down thousands of lines of code from public repositories, run a few scripts, and hope that the resulting binary is what we intended to ship. When a build environment is non-deterministic, you cannot audit what you are actually deploying. If your build process relies on mutable state, local environment variables, or unpinned dependencies, you are essentially running a blind trust exercise every time you push to production.
The Problem with Imperative Builds
Traditional build systems are imperative. They tell the machine how to build software: "install this package, then run this command, then move this file." This approach is inherently fragile. If the underlying system packages change, or if a developer has a different version of a library installed locally, the build output changes. This is the root cause of "works on my machine" syndrome, but from a security perspective, it is a nightmare.
If you cannot reproduce a build bit-for-bit, you cannot verify it. If you cannot verify it, you cannot trust it. This is where the Nix package manager changes the game. Nix treats software builds as pure functions. Given the same input—the source code and the dependency graph—Nix will always produce the exact same output. It does this by isolating builds in a sandbox where they have no access to the global system state.
Declarative Security and Reproducibility
When you define your build environment in a Nix expression, you are creating a cryptographic manifest of your entire dependency tree. Every library, compiler, and build tool is identified by a hash. If a single bit in a dependency changes, the hash changes, and the build fails. This is not just a convenience; it is a security control.
For a pentester, this is a goldmine. If you are auditing a target's build pipeline, you no longer have to guess what environment they are using. You can look at their flake.nix or default.nix files and see exactly what is being pulled in. If you are a developer, you can use nix-packages-review to audit changes in your dependency set before they ever hit your CI/CD pipeline.
Consider the difference between a standard Docker build and a Nix build. In a Dockerfile, you might see:
RUN apt-get update && apt-get install -y python3
This command is non-deterministic. It pulls whatever version of python3 is currently in the repository. A week later, that same command could pull a version with a different set of vulnerabilities. In Nix, you specify the exact version and hash:
{ pkgs ? import <nixpkgs> {} }:
pkgs.python3.overrideAttrs (old: {
src = pkgs.fetchurl {
url = "...";
sha256 = "0abc123...";
};
})
This ensures that the build is pinned to a specific, known-good state.
Real-World Impact for Researchers
During an engagement, you often find yourself trying to understand how a target's application is compiled. If they are using Nix, you have a clear, auditable trail. If they are not, you are often left reverse-engineering binaries to figure out what dependencies were linked in. The shift toward declarative builds is making it harder for attackers to hide malicious code in build-time dependencies, but it also provides a structured way for researchers to perform supply chain analysis.
The NixOS ecosystem takes this further by applying the same principles to the entire operating system. The configuration of the OS is defined in a single, version-controlled file. This means you can roll back an entire system to a known-good state with a single command if you detect a compromise. For a red teamer, this makes persistence significantly harder. For a defender, it makes recovery trivial.
Moving Beyond the "Black Box"
We need to stop treating build pipelines as black boxes. If you are still relying on npm install or pip install without strict pinning and hash verification, you are leaving the door open for dependency confusion and typosquatting attacks. These are not theoretical risks; they are the primary vectors for modern supply chain compromises.
Start by auditing your current build process. Can you reproduce your production binary from scratch, in a clean environment, and get the exact same hash? If the answer is no, you have a security vulnerability. Start small. Use Nix to manage your development environment or your local tooling. Once you see the power of reproducible builds, the transition to using them for your production artifacts becomes the only logical path forward. The goal is not to make builds "easier"—it is to make them verifiable. When you can prove exactly what went into your binary, you can finally start to trust what you are running.
Up Next From This Conference
Similar Talks

Unmasking the Snitch Puck: The Creepy IoT Surveillance Tech in the School Bathroom

Google First-Party Secrets Disclosure




