Quick Post for Intel Quartus on NixOS


Didn’t know where else to write this where it would be indexable by a search engine, so if you’re another electrical engineering student like me and need to get Quartus working with ModelSim for class, just switch to the 22.05 branch of nixpkgs and install Quartus from there. Just thought I’d save you the 3 hours of downloading previous versions to see which ones work.

I don’t feel like setting up tags or anything for SEO, so I’m just gonna write that if you’re in Digital Systems II at Rochester Institute of Technology (RIT), this will be helpful.

The following is a little specific to my config, but I think still useful. If you know how to pull packages from other nixpkgs versions, just ignore this. If you’re new to nix, this will kind of refactor your config, but I think it’s better.

If you’re using flakes and don’t want to build your entire system against 22.05, first import it as an input to your flake.nix.

inputs = {
  nixpkgs.url = "github:nixos/nixpkgs/nixos-23.11";   
  nixpkgs-quartus.url = "github:nixos/nixpkgs/nixos-22.05";   
  nixpkgs-unstable.url = "github:nixos/nixpkgs/nixos-unstable";

  #rest of your inputs

Then, in your system config, instead of inheriting the output explicitly, we can just pass in all the inputs and outputs with specialArgs.

nixosConfigurations = {
  YOURPCNAME =  nixpkgs.lib.nixosSystem {
    specialArgs = { inherit inputs outputs; };
    modules = [

This lets you access your inputs directly from your system config. For examples, instead of inputs.module.package, you can just do module.package.

The last thing that we need to do before we can head to your config file is add an overlay for this Quartus Nixpkgs.

outputs = {self, nixpkgs, #rest of inputs here}@inputs: {
  overlays = import ./overlays.nix {inherit inputs;};

Here, we take inputs as an argument, since we need to get inputs to get access to the different version of nixpkgs that reside there. Then, in unstable-packages, we make an overlay on nixpkgs-unstable. If you want to think about it in objects, we have an object called unstable-packages that contains the object unstable, which is defined to be inputs.nixpkgs-unstable. That way, if we import the top level unstable-packages, we have access to the child unstable.

The overlay syntax might be a little confusing, but I think that the graph on the wiki is very useful. Essentially, final is the final iteration of whatever you’re overlaying, not just the next step (see how final points to all blocks), whereas _prev is only the previous version of the thing you’re overlaying. That’s why we can say system = final.system, since we just care about whatever the host system architecture is after this is used and evaluated.

You can see how we did the same thing to quartus, with different variable names.


{ inputs, ... }:
  unstable-packages = final: _prev: {
    unstable = import inputs.nixpkgs-unstable {
      system = final.system;
      config.allowUnfree = true;
  quartus = final: _prev: {
    real = import inputs.nixpkgs-quartus {
      system = final.system;
      config.allowUnfree = true;

Now, to actually use these overlays. In your configuration.nix (or in your home-manager config), import the module:

nixpkgs = {
  overlays = [

This now lets us install what we need. Now we can add (I use home-manager for my package config):

{pkgs, ...}: {
  home = {
    packages = with pkgs; [
      unstable.amberol #random package that I want from the unstable branch

sudo nixos-rebuild switch --flake .# and “enjoy” doing your homework!

My config is based on Mistero77’s starter config, so if you want to take a shortcut, just use that. I was extra verbose here because a lot of their config was confusing to me when I started out, so I wanted to try and explain some of the components of the config are.