2026-10-15 20:33:59 -04:00
|
|
|
{
|
|
|
|
|
inputs.nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
|
|
|
|
|
|
|
|
|
|
outputs = { self, nixpkgs }:
|
|
|
|
|
let
|
|
|
|
|
pkgs = nixpkgs.legacyPackages.x86_64-linux;
|
|
|
|
|
|
2026-10-16 01:43:15 -04:00
|
|
|
# toolchain is an environment with the specified packages
|
|
|
|
|
# rootfs will contain all binaries given by toolchain
|
2026-10-15 20:33:59 -04:00
|
|
|
toolchain = pkgs.buildEnv {
|
|
|
|
|
name = "pigeon-toolchain";
|
|
|
|
|
paths = with pkgs; [ bash coreutils gcc gnumake util-linux ];
|
|
|
|
|
};
|
|
|
|
|
closure = pkgs.closureInfo {
|
|
|
|
|
rootPaths = [ toolchain ];
|
|
|
|
|
};
|
|
|
|
|
rootfs = pkgs.runCommand "pigeon-rootfs" {
|
|
|
|
|
nativeBuildInputs = with pkgs; [ e2fsprogs ];
|
|
|
|
|
} ''
|
|
|
|
|
mkdir -p rootfs && cd rootfs
|
|
|
|
|
umask 022
|
|
|
|
|
mkdir -p dev proc sys tmp usr nix/store root/student root/project root/results
|
|
|
|
|
chmod 777 tmp
|
|
|
|
|
|
|
|
|
|
for FILE in $(cat ${closure}/store-paths) ; do
|
|
|
|
|
cp -a "$FILE" nix/store
|
|
|
|
|
done
|
|
|
|
|
ln -s ${toolchain}/bin bin
|
|
|
|
|
ln -s ${toolchain}/bin usr/bin
|
|
|
|
|
cp ${./init.sh} init
|
|
|
|
|
|
|
|
|
|
cd ..
|
|
|
|
|
mkfs.ext4 -q -F -d rootfs $out "1G"
|
|
|
|
|
'';
|
|
|
|
|
|
2026-10-16 01:43:15 -04:00
|
|
|
# minimal kernel build, see firecracker documentation for needed params
|
2026-10-15 20:33:59 -04:00
|
|
|
kernel-params = [
|
|
|
|
|
"64BIT" "TTY" "SERIAL_8250" "SERIAL_8250_CONSOLE" "PRINTK"
|
|
|
|
|
"HYPERVISOR_GUEST" "PARAVIRT" "KVM_GUEST"
|
|
|
|
|
"BLOCK" "VIRTIO_MENU" "VIRTIO" "VIRTIO_PCI" "VIRTIO_MMIO" "VIRTIO_BLK"
|
|
|
|
|
"EXT4_FS" "SHMEM" "TMPFS" "PROC_FS" "PROC_SYSCTL" "SYSFS" "DEVTMPFS"
|
|
|
|
|
"ACPI" "PCI" "MAGIC_SYSRQ"
|
|
|
|
|
"BINFMT_ELF" "BINFMT_SCRIPT" "MULTIUSER" "FUTEX" "EPOLL" "EVENTFD"
|
|
|
|
|
"SIGNALFD" "TIMERFD" "POSIX_TIMERS" "FILE_LOCKING" "ADVISE_SYSCALLS"
|
|
|
|
|
"NET" "UNIX"
|
|
|
|
|
];
|
|
|
|
|
kernel = pkgs.stdenv.mkDerivation {
|
|
|
|
|
inherit (pkgs.linux_6_1) src version;
|
|
|
|
|
pname = "pigeon-kernel";
|
|
|
|
|
|
|
|
|
|
nativeBuildInputs = with pkgs; [ bc bison elfutils flex perl ];
|
|
|
|
|
hardeningDisable = [ "all" ];
|
|
|
|
|
enableParallelBuilding = true;
|
|
|
|
|
|
|
|
|
|
configurePhase = ''
|
|
|
|
|
runHook preConfigure
|
|
|
|
|
patchShebangs scripts tools
|
|
|
|
|
make tinyconfig
|
|
|
|
|
for OPTION in ${toString kernel-params} ; do
|
|
|
|
|
scripts/config --enable "$OPTION"
|
|
|
|
|
done
|
|
|
|
|
make olddefconfig
|
|
|
|
|
for OPTION in ${toString kernel-params} ; do
|
|
|
|
|
grep -qx "CONFIG_$OPTION=y" .config || exit 1
|
|
|
|
|
done
|
|
|
|
|
runHook postConfigure
|
|
|
|
|
'';
|
|
|
|
|
|
|
|
|
|
buildFlags = [ "vmlinux" ];
|
|
|
|
|
|
|
|
|
|
installPhase = ''
|
|
|
|
|
runHook preInstall
|
|
|
|
|
cp vmlinux "$out"
|
|
|
|
|
runHook postInstall
|
|
|
|
|
'';
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
pigeon = pkgs.writeShellApplication {
|
|
|
|
|
name = "pigeon";
|
|
|
|
|
runtimeInputs = with pkgs; [ coreutils curl e2fsprogs firecracker git ];
|
|
|
|
|
text = builtins.replaceStrings
|
|
|
|
|
[ "@kernel@" "@rootfs@" ] [ "${kernel}" "${rootfs}"]
|
|
|
|
|
(builtins.readFile ./pigeon.sh);
|
|
|
|
|
};
|
|
|
|
|
|
2026-10-16 01:43:15 -04:00
|
|
|
# see webhook documentation for hooks
|
2026-10-16 00:10:59 -04:00
|
|
|
hooks = pkgs.writeText "pigeon-hooks.json" (builtins.toJSON [
|
|
|
|
|
{
|
|
|
|
|
id = "release";
|
|
|
|
|
execute-command = "${pkgs.nq}/bin/nq";
|
|
|
|
|
include-command-output-in-response = false;
|
|
|
|
|
pass-arguments-to-command = [
|
|
|
|
|
{ source = "string"; name = "${pigeon}/bin/pigeon"; }
|
|
|
|
|
{ source = "payload"; name = "project.id"; }
|
|
|
|
|
{ source = "payload"; name = "project.namespace"; }
|
|
|
|
|
{ source = "payload"; name = "project.name"; }
|
|
|
|
|
{ source = "payload"; name = "commit.id"; }
|
|
|
|
|
{ source = "payload"; name = "tag"; }
|
|
|
|
|
{ source = "payload"; name = "created_at"; }
|
|
|
|
|
];
|
|
|
|
|
trigger-rule.and = [
|
|
|
|
|
{
|
|
|
|
|
match = {
|
|
|
|
|
type = "value";
|
|
|
|
|
parameter = { source = "header"; name = "X-Gitlab-Event"; };
|
|
|
|
|
value = "Release Hook";
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
{
|
|
|
|
|
match = {
|
|
|
|
|
type = "value";
|
|
|
|
|
parameter = { source = "payload"; name = "action"; };
|
|
|
|
|
value = "create";
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
{
|
|
|
|
|
match = {
|
|
|
|
|
type = "value";
|
|
|
|
|
parameter = { source = "header"; name = "X-Gitlab-Token"; };
|
|
|
|
|
value = "{{ getenv `PIGEON_GITLAB_SECRET` | js }}";
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
];
|
|
|
|
|
}
|
|
|
|
|
]);
|
2026-10-15 20:33:59 -04:00
|
|
|
pigeon-webhook = pkgs.writeShellApplication {
|
|
|
|
|
name = "pigeon-webhook";
|
2026-10-16 01:18:37 -04:00
|
|
|
runtimeInputs = with pkgs; [ coreutils jq nq sqlite webhook ];
|
2026-10-15 20:33:59 -04:00
|
|
|
text = ''
|
|
|
|
|
: "''${PIGEON_GITLAB_SECRET:?}"
|
|
|
|
|
: "''${PIGEON_GITLAB_TOKEN:?}"
|
|
|
|
|
: "''${PIGEON_PROJECTS:?}"
|
2026-10-16 01:18:37 -04:00
|
|
|
: "''${PIGEON_STATE}"
|
2026-10-15 23:45:11 -04:00
|
|
|
|
2026-10-16 01:18:37 -04:00
|
|
|
mkdir -p "$PIGEON_STATE"
|
|
|
|
|
export NQDIR="$PIGEON_STATE/nqdir"
|
2026-10-15 21:33:32 -04:00
|
|
|
exec webhook -hooks ${hooks} -template -port 3000 -verbose -debug
|
2026-10-15 20:33:59 -04:00
|
|
|
'';
|
|
|
|
|
};
|
|
|
|
|
in {
|
|
|
|
|
packages.x86_64-linux.default = pigeon-webhook;
|
|
|
|
|
};
|
|
|
|
|
}
|