(define-module (epistemia systems demiurge) #:use-module (gnu) #:use-module (gnu packages bash) #:use-module (gnu packages emacs) #:use-module (gnu packages golang-crypto) #:use-module (gnu packages linux) #:use-module (gnu packages music) #:use-module (gnu packages version-control) #:use-module (gnu packages vpn) #:use-module (gnu services dbus) ; temp #:use-module (gnu services desktop) #:use-module (gnu services dns) #:use-module (gnu services containers) ; temp #:use-module (gnu services linux) #:use-module (gnu services networking) #:use-module (gnu services shepherd) #:use-module (gnu services sound) #:use-module (gnu services ssh) #:use-module (gnu services sysctl) #:use-module (gnu services vpn) #:use-module (gnu services web) #:use-module (gnu system accounts) #:use-module (guix) #:use-module (guix gexp) #:use-module (guix transformations) #:use-module (guix utils) #:use-module (nongnu packages linux) #:use-module (nongnu system linux-initrd) #:use-module (epistemia bootloader) #:use-module (epistemia systems base-system) #:use-module (epistemia systems linux-initrd) #:use-module (epistemia services age-secret) #:use-module (epistemia services machine-learning) #:use-module (epistemia services zfs) #:use-module (epistemia packages machine-learning) #:use-module (epistemia packages zfs)) (define (nginx-reverse-proxy domain proxy-port) (nginx-server-configuration (server-name (list domain)) (listen '("10.0.13.2:443" "[fd00:b0ba:cafe:babe::2]:443" "10.0.13.2:80" "[fd00:b0ba:cafe:babe::2]:80")) (ssl-certificate "/var/demiurge.epistemia.crt") (ssl-certificate-key "/var/demiurge.epistemia.key") (locations (list (nginx-location-configuration (uri "/") (body `(,(string-append "proxy_pass http://127.0.0.1:" (number->string proxy-port) ";") "proxy_set_header Upgrade $http_upgrade;" "proxy_set_header Connection \"upgrade\";" "proxy_read_timeout 3600s;" "proxy_send_timeout 3600s;" "client_max_body_size 10M;"))))))) (operating-system (inherit base-system) (host-name "demiurge.epistemia") (users (cons (user-account (name "vin") (comment "Vineet") (shell (file-append bash "/bin/bash")) (group "users") (supplementary-groups '("wheel" "audio" "video" "input" "seat" "tty" "cgroup" "kvm"))) ;; TODO remove docker %base-user-accounts)) (kernel linux-6.18) (kernel-arguments '("net.ifnames=0" "modprobe.blacklist=snd_hda_intel" "amdgpu.gfxoff=0" "amdgpu.aspm=0" "amdgpu.runpm=0")) (kernel-loadable-modules (list (list zfs-linux "module"))) (initrd (lambda (file-systems . args) (apply microcode-initrd file-systems #:initrd epistemia-zfs-initrd #:zfs-package zfs-linux args))) (firmware (cons* amdgpu-firmware %base-firmware)) (bootloader (bootloader-configuration (bootloader grub-zfs) (targets '("/boot/efi")))) (file-systems (append (list (file-system (device "zroot/root") (mount-point "/") (type "zfs") (check? #f) (needed-for-boot? #t)) (file-system (device "zroot/gnu") (mount-point "/gnu") (type "zfs") (check? #f) (needed-for-boot? #t)) (file-system (device "zroot/var") (mount-point "/var") (type "zfs") (check? #f) (needed-for-boot? #t)) (file-system (device "zroot/home") (mount-point "/home") (type "zfs") (check? #f) (needed-for-boot? #t)) (file-system (device (uuid "F618-FA9F" 'fat)) (mount-point "/boot/efi") (type "vfat")) (file-system (device "none") (mount-point "/home/vin/.local/state/runtime") (type "tmpfs") (options "uid=1000"))) %base-file-systems)) (packages (append (list emacs-no-x git zfs-linux) %base-packages)) (services (modify-services (append (list (service age-secret-service-type (age-secret-configuration (secrets (list (age-secret (name "wg0_demiurge") (file (local-file "../secrets/wg0_demiurge.age"))) (age-secret (name "wg1_demiurge") (file (local-file "../secrets/wg1_demiurge.age"))))))) (simple-service 'zfs-loader kernel-module-loader-service-type '("zfs")) (simple-service 'zfs-shepherd-services shepherd-root-service-type zfs-shepherd-services) (simple-service 'zfs-shepherd-services-user-processes user-processes-service-type '(zfs-automount)) (simple-service 'gpu-power-cap shepherd-root-service-type (list (shepherd-service (provision '(gpu-power-cap)) (requirement '(udev)) (one-shot? #t) (documentation "Set GPU power cap on boot") (start #~(make-forkexec-constructor (list #$(file-append bash "/bin/bash") "-c" (string-append "echo 294000000 > /sys/class/drm/card0/device/hwmon/hwmon*/power1_cap; " "echo 294000000 > /sys/class/drm/card1/device/hwmon/hwmon*/power1_cap")))) (stop #~(make-kill-destructor))))) (service seatd-service-type) (service iptables-service-type) (service static-networking-service-type (list (static-networking (addresses (list (network-address (device "eth0") (value "192.168.1.2/24")))) (routes (list (network-route (destination "default") (gateway "192.168.1.1"))))))) (simple-service 'resolv-configuration etc-service-type `(("resolv.conf" ,(plain-file "epistemia_resolv.conf" (string-append "nameserver ::1\n" "search epistemia\n"))))) (service openssh-service-type (openssh-configuration (permit-root-login #f) (authorized-keys `(("vin" ,(local-file "/data/ssh/id_ed25519.pub")) ("root" ,(local-file "/data/ssh/id_ed25519.pub")))))) (service unbound-service-type (unbound-configuration (server (unbound-server (interface '("::1")) (hide-version #t) (hide-identity #t) (extra-options '((ip-freebind . "yes" ) (aggressive-nsec . "no"))))) (forward-zone (list (unbound-zone (name ".") (forward-addr '("10.0.13.1"))))))) (service wireguard-service-type (wireguard-configuration (interface "wg0") (addresses '("172.26.55.213/32" "fd00:0000:1337:cafe:1111:1111:4975:4c1d/128")) (port 51821) (bootstrap-private-key? #f) (private-key "/run/secrets/wg0_demiurge") (pre-up '("while [ ! -f /run/secrets/wg0_demiurge ]; do sleep 1; done" "ip route replace 185.157.162.7 via 192.168.1.1 dev eth0")) (post-up `("ip rule add fwmark 0x1 table 100 priority 100" "ip rule add fwmark 51820 table 100 priority 100" "ip route replace default via 192.168.1.1 dev eth0 table 100" ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -A PREROUTING -i eth0 -d 192.168.1.2 -m conntrack --ctstate NEW -j CONNMARK --set-mark 0x1") ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -A PREROUTING -i eth0 -j CONNMARK --restore-mark") ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -A OUTPUT -m conntrack --ctstate ESTABLISHED,RELATED -j CONNMARK --restore-mark"))) (post-down `("ip route del 185.157.162.7 via 192.168.1.1 dev eth0" "ip rule del fwmark 0x1 table 100" "ip rule del fwmark 51820 table 100" "ip route flush table 100" ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -D PREROUTING -i eth0 -d 192.168.1.2 -m conntrack --ctstate NEW -j CONNMARK --set-mark 0x1") ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -D PREROUTING -i eth0 -j CONNMARK --restore-mark") ,#~(string-append #$(file-append iptables "/sbin/iptables") " -t mangle -D OUTPUT -m conntrack --ctstate ESTABLISHED,RELATED -j CONNMARK --restore-mark"))) (peers (list (wireguard-peer (name "ovpn-ams-29") (public-key "wTlz3u1egzUrx4Ho02cL7Ht1BBa/C8bULzXStn5f+zk=") (allowed-ips '("0.0.0.0/0" "::0/0")) (endpoint "185.157.162.7:9929")))))) (service wireguard-service-type (wireguard-configuration (interface "wg1") (addresses '("10.0.13.2/24" "fd00:b0ba:cafe:babe::2/64 ")) (port 51820) (bootstrap-private-key? #f) (private-key "/run/secrets/wg1_demiurge") (table #f) (shepherd-requirement '(age-secret ;; to prevent iptables lock issues wireguard-wg0)) (pre-up '("while [ ! -f /run/secrets/wg1_demiurge ]; do sleep 1; done")) (post-up ;; IPv4 and IPv6 NAT (list #~(string-append #$(file-append iptables "/sbin/iptables") " -t nat -I POSTROUTING 1 -s 10.0.13.4/32 -o wg0 -j MASQUERADE") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -t nat -I POSTROUTING 1 -s fd00:b0ba:cafe:babe::4/128 -o wg0 -j MASQUERADE") #~(string-append #$(file-append iptables "/sbin/iptables") " -N WG1-FWD") ;; IPv4 Forwarding Chain #~(string-append #$(file-append iptables "/sbin/iptables") " -I FORWARD 1 -j WG1-FWD") #~(string-append #$(file-append iptables "/sbin/iptables") " -A WG1-FWD -i wg1 -o wg1 -j ACCEPT") #~(string-append #$(file-append iptables "/sbin/iptables") " -A WG1-FWD -i wg1 -o wg0 -j ACCEPT") #~(string-append #$(file-append iptables "/sbin/iptables") " -A WG1-FWD -i wg0 -o wg1 -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT") ;; IPv6 Forwarding Chain #~(string-append #$(file-append iptables "/sbin/ip6tables") " -N WG1-FWD") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -I FORWARD 1 -j WG1-FWD") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -A WG1-FWD -i wg1 -o wg1 -j ACCEPT") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -A WG1-FWD -i wg1 -o wg0 -j ACCEPT") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -A WG1-FWD -i wg0 -o wg1 -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT"))) (pre-down ;; IPv4 and IPv6 NAT (list #~(string-append #$(file-append iptables "/sbin/iptables") " -t nat -D POSTROUTING -s 10.0.13.4/32 -o wg0 -j MASQUERADE") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -t nat -D POSTROUTING -s fd00:b0ba:cafe:babe::4/128 -o wg0 -j MASQUERADE") ;; IPv4 Forwarding Chain #~(string-append #$(file-append iptables "/sbin/iptables") " -D FORWARD -j WG1-FWD") #~(string-append #$(file-append iptables "/sbin/iptables") " -F WG1-FWD") #~(string-append #$(file-append iptables "/sbin/iptables") " -X WG1-FWD") ;; IPv6 Forwarding Chain #~(string-append #$(file-append iptables "/sbin/ip6tables") " -D FORWARD -j WG1-FWD") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -F WG1-FWD") #~(string-append #$(file-append iptables "/sbin/ip6tables") " -X WG1-FWD"))) (peers (list (wireguard-peer (name "saklas.epistemia") (public-key "XvRailvccuc7LJIF4aaYM/MLkU4upiprwFlCfBllhl0=") (allowed-ips '("10.0.13.1/32" "fd00:b0ba:cafe:babe::1/128")) (endpoint "141.95.52.111:51820") (keep-alive 25)) (wireguard-peer (name "hastur.epistemia") (public-key "1ketYziRhoUmpbrj/60O5DYbcPacvmEoFQqa/NntSnc=") (allowed-ips '("10.0.13.3/32" "fd00:b0ba:cafe:babe::3/128")) (keep-alive 25)) (wireguard-peer (name "iphonebob.epistemia") (public-key "Xn0EmeRZdpMejBgzr98mYtb/2f5O58GAzQLNZV/SS30=") (allowed-ips '("10.0.13.4/32" "fd00:b0ba:cafe:babe::4/128")) (keep-alive 25)) (wireguard-peer (name "lab.epistemia") (public-key "iMDEwvXjPAlQH8ZCmP63FM5ICYIFIX5XIyGxjnXoNVE=") (allowed-ips '("10.0.13.5/32" "fd00:b0ba:cafe:babe::5/128")) (keep-alive 25)))))) (simple-service 'wireguard-route-timer shepherd-root-service-type (list (shepherd-timer '(wg1-route-updater) "* * * * *" #~("/data_hdd/wireguard-endpoint-route") #:requirement '(wireguard-wg1) #:documentation "Update Wireguard routes every minute."))) (service nginx-service-type (nginx-configuration (server-blocks (list (nginx-reverse-proxy "llm.demiurge.epistemia" 8080) (nginx-reverse-proxy "searx.demiurge.epistemia" 8081) (nginx-reverse-proxy "redlib.demiurge.epistemia" 8085) (nginx-reverse-proxy "navidrome.demiurge.epistemia" 4533) (nginx-reverse-proxy "sdui.demiurge.epistemia" 5000) (nginx-reverse-proxy "home.demiurge.epistemia" 8123))))) (service pam-limits-service-type (list (pam-limits-entry "@audio" 'both 'rtprio 99) (pam-limits-entry "@audio" 'both 'memlock 'unlimited))) (simple-service 'llm-router shepherd-root-service-type (list (shepherd-service (provision '(llm-router)) (requirement '(user-processes networking guix-daemon)) (documentation "llm-router service") (start #~(make-forkexec-constructor '("/home/vin/.config/guix/current/bin/guix" "shell" "-m" "/data/src/public/llm-router/manifest.scm" "--" "python3" "app.py") #:user "vin" #:directory "/data/src/public/llm-router" #:log-file "/var/log/llm-router.log" #:environment-variables (append (default-environment-variables) ;; for vulkan (list "XDG_DATA_DIRS=/home/vin/.guix-home/profile/share")))) (stop #~(make-kill-destructor))))) (simple-service 'sdui shepherd-root-service-type (list (shepherd-service (provision '(sdui)) (requirement '(user-processes networking guix-daemon)) (documentation "sdui service") (start #~(make-forkexec-constructor '("/home/vin/.config/guix/current/bin/guix" "shell" "-m" "/data/src/public/sdui/manifest.scm" "--" "python3" "app.py") #:user "vin" #:directory "/data/src/public/sdui" #:log-file "/var/log/sdui.log")) (stop #~(make-kill-destructor))))) ;; netx three temporary (service dbus-root-service-type) (service rootless-podman-service-type (rootless-podman-configuration (subgids (list (subid-range (name "vin")))) (subuids (list (subid-range (name "vin")))))) (service oci-service-type (oci-configuration (runtime 'podman) (containers (list (oci-container-configuration (image "deluan/navidrome:latest") (user "vin") (ports '(("4533" . "4533"))) (environment '("ND_ENABLEINSIGHTCOLLECTOR=false")) (volumes '("/data_hdd/music_navidrome:/data" "/data_hdd/music:/music:ro")))))))) %base-services) (sysctl-service-type config => (sysctl-configuration (settings (append '(("net.ipv4.ip_forward" . "1") ("net.ipv6.conf.all.forwarding" . "1") ;; for nginx since shepherd-requirement cannot be set ("net.ipv4.ip_nonlocal_bind" . "1") ("net.ipv6.ip_nonlocal_bind" . "1")) %default-sysctl-settings)))))))