Small, experimental operating system designed for embedded and containerized situations. MicrOS is based heavily on NixOS, but compiles down to a microscopic kernel1, an initrd, a ~50mb squashfs,
This is also our experiment in init-agnostic NixOS. Runit is the default init backend, with a small init-agnostic service interface layered over it. This is not as robust as the NixOS systemd module, but it results in a small and fast image for low-resource scenarios, e.g., embedded development and service containers.
NixOS is great, it fits under most use-cases and it is extremely flexible on what you might use it for. Unfortunately for us, it is quite large even after you go out of your way to "debloat" it by applying various overlays that create a butterfly effect in the module system, breaking things you did not even know were called by your system. This is not unexpected, as Nixpkgs is quite large, but it is also very annoying.
MicrOS aims to be a robust solution to building small, minimal, and functional systems for various use cases. More specifically, embedded Linux and containerization.
Micros is a build system more so than it is a collection of hardware modules. It should be utilized primarily as a module system to reduce friction in building images for embedded systems.
Construct your own system with lib.microsSystem. This functions almost
identical to lib.nixosSystem that you might be familiar with.
lib.microsSystem {
modules = [
{
not-os.rpi1 = true;
not-os.rpi2 = true;
system.build.rpi-firmware = raspi-firmware;
nixpkgs.hostPlatform = {system = "armv7l-linux";};
nixpkgs.buildPlatform = {system = "x86_64-linux";};
}
];
};Above configuration enough to construct a basic system. You may build different
components of the configuration, available under config.system.build to create
different build artifacts for different workflows. Please see
our documentation for more details and
module system options.
MicrOS hands PID 1 off to the selected init backend after stage 2 activation.
runit is the default backend. Service modules should use micros.services;
the backend translates those services into whatever layout it needs.
Contributions are always welcome. If you have anything you'd like to see implemented, and would like to work on implementing it then please create an issue so that we may figure out next. Please remember to write comments in particularly complex areas if adding new modules, or refactoring existing modules.
You may visit runit/runscripts for additional services that could be upstreamed to MicrOS.
MicrOS is MIT licensed as a result of its status as a hard-fork of not-os and our tendency to borrow modules from Nixpkgs, both of which are MIT licensed. Any and all work here is available under the MIT license, following upstream. Please support the original author and contributors.
Note
Work here is based heavily on the awesome not-os. I (@notashelf) worked on something similar until I realized I was duplicating effort for no reason. This repository diverges (and will continue to diverge from not-os) in terms of module structure, coding conventions and goals on what should and should not be provided. In addition to the aggressive repository restructure, I will be working to provide more idiomatic Nix code that follows best practices and focuses on purity.
The nature of MicrOS does not quite allow for a direct dependency on Nixpkgs due to its tight integration with Systemd. Although, we borrow modules from nixpkgs at times to avoid duplicating work, or to avoid reinventing the wheel as as square. A copyright notice is hereby provided that some modules in MicrOS are directly copied from nixpkgs, also available under the MIT license.
Please see LICENSE for details.
Footnotes
-
For the time being MicrOS attempts to boot the mainline kernel as development is most steadily pacing on
x86_64-linuxand we would like minimum amount of rebuilds possible. In the future, likely after there is some CI infrastructure, alternative kernels aiming at achieving smaller kernels might become a priority. ↩