From 2b2fa1bdbc3ed791ab2a3c06fcf42720360c3428 Mon Sep 17 00:00:00 2001 From: mjallen18 Date: Thu, 8 May 2025 15:40:47 -0500 Subject: [PATCH] merge --- flake.lock | 367 +++++++++++++----- flake.nix | 56 +-- hosts/pi4/adguard.nix | 10 - hosts/pi4/argononed.nix | 15 - hosts/pi4/boot.nix | 21 - hosts/pi4/ups-monitor.nix | 310 --------------- hosts/pi5/boot.nix | 18 + hosts/{pi4 => pi5}/configuration.nix | 17 +- hosts/{pi4 => pi5}/hardware-configuration.nix | 0 hosts/{pi4 => pi5}/home.nix | 0 hosts/{pi4 => pi5}/impermanence.nix | 0 hosts/{pi4 => pi5}/sops.nix | 0 12 files changed, 327 insertions(+), 487 deletions(-) delete mode 100755 hosts/pi4/adguard.nix delete mode 100644 hosts/pi4/argononed.nix delete mode 100755 hosts/pi4/boot.nix delete mode 100755 hosts/pi4/ups-monitor.nix create mode 100755 hosts/pi5/boot.nix rename hosts/{pi4 => pi5}/configuration.nix (92%) rename hosts/{pi4 => pi5}/hardware-configuration.nix (100%) rename hosts/{pi4 => pi5}/home.nix (100%) rename hosts/{pi4 => pi5}/impermanence.nix (100%) rename hosts/{pi4 => pi5}/sops.nix (100%) diff --git a/flake.lock b/flake.lock index e7466a0..99e53d5 100755 --- a/flake.lock +++ b/flake.lock @@ -1,5 +1,92 @@ { "nodes": { + "Pi5-home-manager": { + "inputs": { + "nixpkgs": [ + "Pi5-nixpkgs" + ] + }, + "locked": { + "lastModified": 1746632058, + "narHash": "sha256-Mp5Bbvb+YlFEZ76C/0wFS6C1lRfH3D60u465wFNlnS0=", + "owner": "nix-community", + "repo": "home-manager", + "rev": "708074ae6db9e0468e4f48477f856e8c2d059795", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "home-manager", + "type": "github" + } + }, + "Pi5-impermanence": { + "locked": { + "lastModified": 1737831083, + "narHash": "sha256-LJggUHbpyeDvNagTUrdhe/pRVp4pnS6wVKALS782gRI=", + "owner": "nix-community", + "repo": "impermanence", + "rev": "4b3e914cdf97a5b536a889e939fb2fd2b043a170", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "impermanence", + "type": "github" + } + }, + "Pi5-nixos-hardware": { + "locked": { + "lastModified": 1746621361, + "narHash": "sha256-T9vOxEqI1j1RYugV0b9dgy0AreiZ9yBDKZJYyclF0og=", + "owner": "NixOS", + "repo": "nixos-hardware", + "rev": "2ea3ad8a1f26a76f8a8e23fc4f7757c46ef30ee5", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "master", + "repo": "nixos-hardware", + "type": "github" + } + }, + "Pi5-nixpkgs": { + "locked": { + "lastModified": 1746461020, + "narHash": "sha256-7+pG1I9jvxNlmln4YgnlW4o+w0TZX24k688mibiFDUE=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "3730d8a308f94996a9ba7c7138ede69c1b9ac4ae", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "Pi5-sops-nix": { + "inputs": { + "nixpkgs": [ + "Pi5-nixpkgs" + ] + }, + "locked": { + "lastModified": 1746485181, + "narHash": "sha256-PxrrSFLaC7YuItShxmYbMgSuFFuwxBB+qsl9BZUnRvg=", + "owner": "Mic92", + "repo": "sops-nix", + "rev": "e93ee1d900ad264d65e9701a5c6f895683433386", + "type": "github" + }, + "original": { + "owner": "Mic92", + "repo": "sops-nix", + "type": "github" + } + }, "authentik-src": { "flake": false, "locked": { @@ -644,6 +731,40 @@ "type": "github" } }, + "libcamera-src": { + "flake": false, + "locked": { + "lastModified": 1725630279, + "narHash": "sha256-KH30jmHfxXq4j2CL7kv18DYECJRp9ECuWNPnqPZajPA=", + "owner": "raspberrypi", + "repo": "libcamera", + "rev": "69a894c4adad524d3063dd027f5c4774485cf9db", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "repo": "libcamera", + "rev": "69a894c4adad524d3063dd027f5c4774485cf9db", + "type": "github" + } + }, + "libpisp-src": { + "flake": false, + "locked": { + "lastModified": 1724944683, + "narHash": "sha256-Fo2UJmQHS855YSSKKmGrsQnJzXog1cdpkIOO72yYAM4=", + "owner": "raspberrypi", + "repo": "libpisp", + "rev": "28196ed6edcfeda88d23cc5f213d51aa6fa17bb3", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "v1.0.7", + "repo": "libpisp", + "type": "github" + } + }, "napalm": { "inputs": { "flake-utils": [ @@ -699,7 +820,7 @@ "inputs": { "flake-compat": "flake-compat_3", "nixpkgs": [ - "nas-nixpkgs" + "nas-nixpkgs-stable" ], "nixpkgs-stable": "nixpkgs-stable_2", "rust-overlay": "rust-overlay_2" @@ -1137,93 +1258,6 @@ "type": "github" } }, - "pi4-home-manager": { - "inputs": { - "nixpkgs": [ - "pi4-nixpkgs" - ] - }, - "locked": { - "lastModified": 1742416832, - "narHash": "sha256-ycok0eJJcoknqaibdv/TEEEOUqovC42XCqbfLDYmnoQ=", - "owner": "nix-community", - "repo": "home-manager", - "rev": "eb0f617aecbaf1eff5bacec789891e775af2f5a3", - "type": "github" - }, - "original": { - "owner": "nix-community", - "repo": "home-manager", - "type": "github" - } - }, - "pi4-impermanence": { - "locked": { - "lastModified": 1737831083, - "narHash": "sha256-LJggUHbpyeDvNagTUrdhe/pRVp4pnS6wVKALS782gRI=", - "owner": "nix-community", - "repo": "impermanence", - "rev": "4b3e914cdf97a5b536a889e939fb2fd2b043a170", - "type": "github" - }, - "original": { - "owner": "nix-community", - "repo": "impermanence", - "type": "github" - } - }, - "pi4-nixos-hardware": { - "locked": { - "lastModified": 1742376361, - "narHash": "sha256-VFMgJkp/COvkt5dnkZB4D2szVdmF6DGm5ZdVvTUy61c=", - "owner": "NixOS", - "repo": "nixos-hardware", - "rev": "daaae13dff0ecc692509a1332ff9003d9952d7a9", - "type": "github" - }, - "original": { - "owner": "NixOS", - "ref": "master", - "repo": "nixos-hardware", - "type": "github" - } - }, - "pi4-nixpkgs": { - "locked": { - "lastModified": 1742288794, - "narHash": "sha256-Txwa5uO+qpQXrNG4eumPSD+hHzzYi/CdaM80M9XRLCo=", - "owner": "NixOS", - "repo": "nixpkgs", - "rev": "b6eaf97c6960d97350c584de1b6dcff03c9daf42", - "type": "github" - }, - "original": { - "owner": "NixOS", - "ref": "nixos-unstable", - "repo": "nixpkgs", - "type": "github" - } - }, - "pi4-sops-nix": { - "inputs": { - "nixpkgs": [ - "pi4-nixpkgs" - ] - }, - "locked": { - "lastModified": 1742406979, - "narHash": "sha256-r0aq70/3bmfjTP+JZs4+XV5SgmCtk1BLU4CQPWGtA7o=", - "owner": "Mic92", - "repo": "sops-nix", - "rev": "1770be8ad89e41f1ed5a60ce628dd10877cb3609", - "type": "github" - }, - "original": { - "owner": "Mic92", - "repo": "sops-nix", - "type": "github" - } - }, "poetry2nix": { "inputs": { "flake-utils": [ @@ -1336,8 +1370,40 @@ "type": "github" } }, + "raspberry-pi-nix": { + "inputs": { + "libcamera-src": "libcamera-src", + "libpisp-src": "libpisp-src", + "nixpkgs": "nixpkgs_2", + "rpi-bluez-firmware-src": "rpi-bluez-firmware-src", + "rpi-firmware-nonfree-src": "rpi-firmware-nonfree-src", + "rpi-firmware-src": "rpi-firmware-src", + "rpi-linux-6_12_17-src": "rpi-linux-6_12_17-src", + "rpi-linux-6_6_78-src": "rpi-linux-6_6_78-src", + "rpi-linux-stable-src": "rpi-linux-stable-src", + "rpicam-apps-src": "rpicam-apps-src" + }, + "locked": { + "lastModified": 1742223591, + "narHash": "sha256-ZNTz8r5jlJ1jvpqf5+aUYgpnYJSVX0iP14doOc1Hm0E=", + "owner": "nix-community", + "repo": "raspberry-pi-nix", + "rev": "3e8100d5e976a6a2be363015cb33463af9ef441a", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "raspberry-pi-nix", + "type": "github" + } + }, "root": { "inputs": { + "Pi5-home-manager": "Pi5-home-manager", + "Pi5-impermanence": "Pi5-impermanence", + "Pi5-nixos-hardware": "Pi5-nixos-hardware", + "Pi5-nixpkgs": "Pi5-nixpkgs", + "Pi5-sops-nix": "Pi5-sops-nix", "desktop-chaotic": "desktop-chaotic", "desktop-home-manager": "desktop-home-manager", "desktop-impermanence": "desktop-impermanence", @@ -1359,11 +1425,7 @@ "nix-darwin": "nix-darwin", "nixpkgs-stable": "nixpkgs-stable_4", "nixpkgs-unstable": "nixpkgs-unstable", - "pi4-home-manager": "pi4-home-manager", - "pi4-impermanence": "pi4-impermanence", - "pi4-nixos-hardware": "pi4-nixos-hardware", - "pi4-nixpkgs": "pi4-nixpkgs", - "pi4-sops-nix": "pi4-sops-nix", + "raspberry-pi-nix": "raspberry-pi-nix", "steamdeck-chaotic": "steamdeck-chaotic", "steamdeck-home-manager": "steamdeck-home-manager", "steamdeck-impermanence": "steamdeck-impermanence", @@ -1375,6 +1437,125 @@ "steamdeck-steam-rom-manager": "steamdeck-steam-rom-manager" } }, + "rpi-bluez-firmware-src": { + "flake": false, + "locked": { + "lastModified": 1708969706, + "narHash": "sha256-KakKnOBeWxh0exu44beZ7cbr5ni4RA9vkWYb9sGMb8Q=", + "owner": "RPi-Distro", + "repo": "bluez-firmware", + "rev": "78d6a07730e2d20c035899521ab67726dc028e1c", + "type": "github" + }, + "original": { + "owner": "RPi-Distro", + "ref": "bookworm", + "repo": "bluez-firmware", + "type": "github" + } + }, + "rpi-firmware-nonfree-src": { + "flake": false, + "locked": { + "lastModified": 1723266537, + "narHash": "sha256-T7eTKXqY9cxEMdab8Snda4CEOrEihy5uOhA6Fy+Mhnw=", + "owner": "RPi-Distro", + "repo": "firmware-nonfree", + "rev": "4b356e134e8333d073bd3802d767a825adec3807", + "type": "github" + }, + "original": { + "owner": "RPi-Distro", + "ref": "bookworm", + "repo": "firmware-nonfree", + "type": "github" + } + }, + "rpi-firmware-src": { + "flake": false, + "locked": { + "lastModified": 1728405098, + "narHash": "sha256-4gnK0KbqFnjBmWia9Jt2gveVWftmHrprpwBqYVqE/k0=", + "owner": "raspberrypi", + "repo": "firmware", + "rev": "7bbb5f80d20a2335066a8781459c9f33e5eebc64", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "1.20241008", + "repo": "firmware", + "type": "github" + } + }, + "rpi-linux-6_12_17-src": { + "flake": false, + "locked": { + "lastModified": 1740765145, + "narHash": "sha256-hoCsGc4+RC/2LmxDtswLBL5ZhWlw4vSiL4Vkl39r2MU=", + "owner": "raspberrypi", + "repo": "linux", + "rev": "5985ce32e511f4e8279a841a1b06a8c7d972b386", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "rpi-6.12.y", + "repo": "linux", + "type": "github" + } + }, + "rpi-linux-6_6_78-src": { + "flake": false, + "locked": { + "lastModified": 1740503700, + "narHash": "sha256-Y8+ot4Yi3UKwlZK3ap15rZZ16VZDvmeFkD46+6Ku7bE=", + "owner": "raspberrypi", + "repo": "linux", + "rev": "2e071057fded90e789c0101498e45a1778be93fe", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "rpi-6.6.y", + "repo": "linux", + "type": "github" + } + }, + "rpi-linux-stable-src": { + "flake": false, + "locked": { + "lastModified": 1728403745, + "narHash": "sha256-phCxkuO+jUGZkfzSrBq6yErQeO2Td+inIGHxctXbD5U=", + "owner": "raspberrypi", + "repo": "linux", + "rev": "5aeecea9f4a45248bcf564dec924965e066a7bfd", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "stable_20241008", + "repo": "linux", + "type": "github" + } + }, + "rpicam-apps-src": { + "flake": false, + "locked": { + "lastModified": 1727515047, + "narHash": "sha256-qCYGrcibOeGztxf+sd44lD6VAOGoUNwRqZDdAmcTa/U=", + "owner": "raspberrypi", + "repo": "rpicam-apps", + "rev": "a8ccf9f3cd9df49875dfb834a2b490d41d226031", + "type": "github" + }, + "original": { + "owner": "raspberrypi", + "ref": "v1.5.2", + "repo": "rpicam-apps", + "type": "github" + } + }, "rust-analyzer-src": { "flake": false, "locked": { diff --git a/flake.nix b/flake.nix index 9046a65..1001615 100755 --- a/flake.nix +++ b/flake.nix @@ -69,12 +69,13 @@ # Authentik nas-authentik-nix = { url = "github:nix-community/authentik-nix"; + inputs.nixpkgs.follows = "nas-nixpkgs"; }; # cosmic launcher nas-cosmic = { url = "github:lilyinstarlight/nixos-cosmic"; - inputs.nixpkgs.follows = "nas-nixpkgs"; + inputs.nixpkgs.follows = "nas-nixpkgs-stable"; }; # crowdsec @@ -113,36 +114,38 @@ }; ##################################################### - # Pi4 # + # Pi5 # ##################################################### # nixpgs - pi4-nixpkgs = { - url = "github:NixOS/nixpkgs/nixos-unstable"; + Pi5-nixpkgs = { + url = "github:NixOS/nixpkgs/nixos-24.11"; }; # Home Manager - pi4-home-manager = { + Pi5-home-manager = { url = "github:nix-community/home-manager"; - inputs.nixpkgs.follows = "pi4-nixpkgs"; + inputs.nixpkgs.follows = "Pi5-nixpkgs"; }; # Impermenance - pi4-impermanence = { + Pi5-impermanence = { url = "github:nix-community/impermanence"; }; # Nix hardware - pi4-nixos-hardware = { + Pi5-nixos-hardware = { url = "github:NixOS/nixos-hardware/master"; }; # Sops-nix - pi4-sops-nix = { + Pi5-sops-nix = { url = "github:Mic92/sops-nix"; - inputs.nixpkgs.follows = "pi4-nixpkgs"; + inputs.nixpkgs.follows = "Pi5-nixpkgs"; }; + raspberry-pi-nix.url = "github:nix-community/raspberry-pi-nix"; + ##################################################### # Steamdeck # ##################################################### @@ -247,12 +250,13 @@ nas-nixos-hardware, nas-sops-nix, - # Pi4 - pi4-nixpkgs, - pi4-home-manager, - pi4-impermanence, - pi4-nixos-hardware, - pi4-sops-nix, + # Pi5 + Pi5-nixpkgs, + Pi5-home-manager, + Pi5-impermanence, + Pi5-nixos-hardware, + Pi5-sops-nix, + raspberry-pi-nix, # Steamdeck steamdeck-nixpkgs, @@ -379,16 +383,18 @@ ]; }; - # Pi4 - "pi4" = pi4-nixpkgs.lib.nixosSystem { + # Pi5 + "pi5" = Pi5-nixpkgs.lib.nixosSystem { system = "aarch64-linux"; modules = [ - pi4-nixos-hardware.nixosModules.raspberry-pi-4 - pi4-impermanence.nixosModules.impermanence - ./hosts/pi4/configuration.nix - pi4-sops-nix.nixosModules.sops + Pi5-nixos-hardware.nixosModules.raspberry-pi-4 + Pi5-impermanence.nixosModules.impermanence + ./hosts/pi5/configuration.nix + Pi5-sops-nix.nixosModules.sops + raspberry-pi-nix.nixosModules.raspberry-pi + raspberry-pi-nix.nixosModules.sd-image - pi4-home-manager.nixosModules.home-manager + Pi5-home-manager.nixosModules.home-manager { home-manager.useGlobalPkgs = true; home-manager.useUserPackages = true; @@ -396,8 +402,8 @@ { ... }: { imports = [ - ./hosts/pi4/home.nix - pi4-sops-nix.homeManagerModules.sops + ./hosts/pi5/home.nix + Pi5-sops-nix.homeManagerModules.sops ]; }; } diff --git a/hosts/pi4/adguard.nix b/hosts/pi4/adguard.nix deleted file mode 100755 index 72b4ff3..0000000 --- a/hosts/pi4/adguard.nix +++ /dev/null @@ -1,10 +0,0 @@ -{ ... }: -{ - services.adguardhome = { - enable = true; - allowDHCP = true; - port = 3000; - openFirewall = true; - mutableSettings = true; - }; -} diff --git a/hosts/pi4/argononed.nix b/hosts/pi4/argononed.nix deleted file mode 100644 index 95886ae..0000000 --- a/hosts/pi4/argononed.nix +++ /dev/null @@ -1,15 +0,0 @@ -{ argononed, ... }: -{ - imports = [ "${argononed}/OS/nixos" ]; - - services.argonone = { - enable = true; - logLevel = 4; - settings = { - fanTemp0 = 36; fanSpeed0 = 10; - fanTemp1 = 41; fanSpeed1 = 50; - fanTemp2 = 46; fanSpeed2 = 80; - hysteresis = 4; - }; - }; -} \ No newline at end of file diff --git a/hosts/pi4/boot.nix b/hosts/pi4/boot.nix deleted file mode 100755 index c0fc0db..0000000 --- a/hosts/pi4/boot.nix +++ /dev/null @@ -1,21 +0,0 @@ -{ pkgs, lib, ... }: -{ - boot = { - kernelPackages = pkgs.linuxPackages_latest; - initrd.availableKernelModules = [ - "xhci_pci" - "usbhid" - "usb_storage" - ]; - # We're using EFI so enable systemd-boot - loader = { - systemd-boot.enable = true; - generic-extlinux-compatible.enable = lib.mkForce false; - }; - kernelParams = [ - # "snd_bcm2835.enable_hdmi=1" - "brcmfmac.roamoff=1" - "brcmfmac.feature_disable=0x282000" - ]; - }; -} diff --git a/hosts/pi4/ups-monitor.nix b/hosts/pi4/ups-monitor.nix deleted file mode 100755 index 7a25430..0000000 --- a/hosts/pi4/ups-monitor.nix +++ /dev/null @@ -1,310 +0,0 @@ -# /etc/nixos/modules/ups-monitor/default.nix -{ config, lib, pkgs, ... }: - -with lib; - -let - cfg = config.services.ups-monitor; - - pythonScript = pkgs.writeText "ups_monitor.py" '' - import smbus - import time - import logging - import json - from datetime import datetime - import os - from pathlib import Path - import sqlite3 - import signal - import sys - - class INA219: - def __init__(self, i2c_bus=1, addr=0x40): - self.bus = smbus.SMBus(i2c_bus) - self.addr = addr - self._cal_value = 0 - self._current_lsb = 0 - self._power_lsb = 0 - self.set_calibration_32V_2A() - - def read(self,address): - data = self.bus.read_i2c_block_data(self.addr, address, 2) - return ((data[0] * 256 ) + data[1]) - - def write(self,address,data): - temp = [0,0] - temp[1] = data & 0xFF - temp[0] =(data & 0xFF00) >> 8 - self.bus.write_i2c_block_data(self.addr,address,temp) - - def set_calibration_32V_2A(self): - self._current_lsb = .1 - self._cal_value = 4096 - self._power_lsb = .002 - self.write(0x05, self._cal_value) - self.bus_voltage_range = 0x01 - self.gain = 0x03 - self.bus_adc_resolution = 0x0D - self.shunt_adc_resolution = 0x0D - self.mode = 0x07 - self.config = self.bus_voltage_range << 13 | \ - self.gain << 11 | \ - self.bus_adc_resolution << 7 | \ - self.shunt_adc_resolution << 3 | \ - self.mode - self.write(0x00, self.config) - - def getBusVoltage_V(self): - self.write(0x05, self._cal_value) - self.read(0x02) - return (self.read(0x02) >> 3) * 0.004 - - def getShuntVoltage_mV(self): - self.write(0x05, self._cal_value) - value = self.read(0x01) - if value > 32767: - value -= 65535 - return value * 0.01 - - def getCurrent_mA(self): - value = self.read(0x04) - if value > 32767: - value -= 65535 - return value * self._current_lsb - - def getPower_W(self): - self.write(0x05, self._cal_value) - value = self.read(0x03) - if value > 32767: - value -= 65535 - return value * self._power_lsb - - class UPSMonitor: - def __init__(self, i2c_address, log_interval, battery_warning_threshold, - voltage_warning_threshold, log_dir): - self.ina219 = INA219(addr=i2c_address) - self.log_interval = log_interval - self.battery_warning_threshold = battery_warning_threshold - self.voltage_warning_threshold = voltage_warning_threshold - self.log_dir = Path(log_dir) - self.running = True - - self.log_dir.mkdir(parents=True, exist_ok=True) - self._setup_logging() - self._setup_database() - - signal.signal(signal.SIGINT, self._signal_handler) - signal.signal(signal.SIGTERM, self._signal_handler) - - def _setup_logging(self): - self.logger = logging.getLogger('UPSMonitor') - self.logger.setLevel(logging.INFO) - - fh = logging.FileHandler(self.log_dir / 'ups_monitor.log') - fh.setLevel(logging.INFO) - - ch = logging.StreamHandler() - ch.setLevel(logging.INFO) - - formatter = logging.Formatter('%(asctime)s - %(levelname)s - %(message)s') - fh.setFormatter(formatter) - ch.setFormatter(formatter) - - self.logger.addHandler(fh) - self.logger.addHandler(ch) - - def _setup_database(self): - db_path = self.log_dir / 'ups_metrics.db' - self.conn = sqlite3.connect(str(db_path)) - cursor = self.conn.cursor() - - cursor.execute(''' - CREATE TABLE IF NOT EXISTS metrics ( - timestamp DATETIME DEFAULT CURRENT_TIMESTAMP, - bus_voltage REAL, - shunt_voltage REAL, - current REAL, - power REAL, - battery_percentage REAL - ) - ''') - self.conn.commit() - - def _signal_handler(self, signum, frame): - self.logger.info("Received shutdown signal, cleaning up...") - self.running = False - self.conn.close() - sys.exit(0) - - def _calculate_battery_percentage(self, voltage): - p = (voltage - 6) / 2.4 * 100 - return max(0, min(100, p)) - - def _check_thresholds(self, voltage, battery_percentage): - if battery_percentage <= self.battery_warning_threshold: - self.logger.warning( - f"Low battery warning: {battery_percentage:.1f}%") - - if voltage <= self.voltage_warning_threshold: - self.logger.warning( - f"Low voltage warning: {voltage:.2f}V") - - def _store_metrics(self, metrics): - cursor = self.conn.cursor() - cursor.execute(''' - INSERT INTO metrics ( - bus_voltage, shunt_voltage, current, power, battery_percentage - ) VALUES (?, ?, ?, ?, ?) - ''', ( - metrics['bus_voltage'], - metrics['shunt_voltage'], - metrics['current'], - metrics['power'], - metrics['battery_percentage'] - )) - self.conn.commit() - - def get_metrics(self): - bus_voltage = self.ina219.getBusVoltage_V() - shunt_voltage = self.ina219.getShuntVoltage_mV() / 1000 - current = self.ina219.getCurrent_mA() / 1000 - power = self.ina219.getPower_W() - battery_percentage = self._calculate_battery_percentage(bus_voltage) - - return { - 'timestamp': datetime.now().isoformat(), - 'bus_voltage': bus_voltage, - 'shunt_voltage': shunt_voltage, - 'current': current, - 'power': power, - 'battery_percentage': battery_percentage - } - - def run(self): - self.logger.info("Starting UPS monitoring service...") - - while self.running: - try: - metrics = self.get_metrics() - self._store_metrics(metrics) - self._check_thresholds( - metrics['bus_voltage'], - metrics['battery_percentage'] - ) - - self.logger.info( - f"Status: {metrics['battery_percentage']:.1f}% | " - f"Voltage: {metrics['bus_voltage']:.2f}V | " - f"Current: {metrics['current']:.3f}A | " - f"Power: {metrics['power']:.2f}W" - ) - - time.sleep(self.log_interval) - - except Exception as e: - self.logger.error(f"Error in monitoring loop: {str(e)}") - time.sleep(self.log_interval) - - if __name__ == '__main__': - monitor = UPSMonitor( - i2c_address=int(os.getenv('UPS_I2C_ADDRESS', '0x42'), 16), - log_interval=int(os.getenv('UPS_LOG_INTERVAL', '2')), - battery_warning_threshold=float(os.getenv('UPS_BATTERY_WARNING_THRESHOLD', '20')), - voltage_warning_threshold=float(os.getenv('UPS_VOLTAGE_WARNING_THRESHOLD', '6.5')), - log_dir=os.getenv('UPS_LOG_DIR', '/var/log/ups_monitor') - ) - monitor.run() - ''; - - pythonEnv = pkgs.python3.withPackages (ps: with ps; [ - smbus2 - ]); - -in { - options.services.ups-monitor = { - enable = mkEnableOption "UPS HAT monitoring service"; - - i2cAddress = mkOption { - type = types.str; - default = "0x42"; - description = "I2C address of the UPS HAT"; - }; - - logInterval = mkOption { - type = types.int; - default = 2; - description = "Interval between log entries in seconds"; - }; - - batteryWarningThreshold = mkOption { - type = types.float; - default = 20.0; - description = "Battery percentage threshold for warnings"; - }; - - voltageWarningThreshold = mkOption { - type = types.float; - default = 6.5; - description = "Voltage threshold for warnings"; - }; - - logDir = mkOption { - type = types.str; - default = "/var/log/ups_monitor"; - description = "Directory for storing logs and metrics"; - }; - - user = mkOption { - type = types.str; - default = "root"; - description = "User to run the service as"; - }; - - group = mkOption { - type = types.str; - default = "root"; - description = "Group to run the service as"; - }; - }; - - config = mkIf cfg.enable { - systemd.services.ups-monitor = { - description = "UPS HAT Monitoring Service"; - wantedBy = [ "multi-user.target" ]; - after = [ "network.target" ]; - - environment = { - UPS_I2C_ADDRESS = cfg.i2cAddress; - UPS_LOG_INTERVAL = toString cfg.logInterval; - UPS_BATTERY_WARNING_THRESHOLD = toString cfg.batteryWarningThreshold; - UPS_VOLTAGE_WARNING_THRESHOLD = toString cfg.voltageWarningThreshold; - UPS_LOG_DIR = cfg.logDir; - PYTHONPATH = "${pythonEnv}/${pythonEnv.python.sitePackages}"; - }; - - serviceConfig = { - ExecStart = "${pythonEnv}/bin/python3 ${pythonScript}"; - User = cfg.user; - Group = cfg.group; - Restart = "always"; - RestartSec = "10s"; - - # Hardening options - ProtectSystem = "strict"; - ProtectHome = true; - PrivateTmp = true; - ReadWritePaths = [ cfg.logDir ]; - CapabilityBoundingSet = [ "CAP_SYS_RAWIO" ]; - DeviceAllow = [ "/dev/i2c-1 rw" ]; - }; - }; - - # Ensure the log directory exists and has correct permissions - systemd.tmpfiles.rules = [ - "d '${cfg.logDir}' 0750 ${cfg.user} ${cfg.group} -" - ]; - - # Enable I2C - hardware.i2c.enable = true; - }; -} \ No newline at end of file diff --git a/hosts/pi5/boot.nix b/hosts/pi5/boot.nix new file mode 100755 index 0000000..b587735 --- /dev/null +++ b/hosts/pi5/boot.nix @@ -0,0 +1,18 @@ +{ pkgs, lib, ... }: +{ + boot = { + kernelPackages = lib.mkDefault pkgs.linuxKernel.packages.linux_rpi4; + initrd.availableKernelModules = [ + "usbhid" + "usb_storage" + "vc4" + "pcie_brcmstb" # required for the pcie bus to work + "reset-raspberrypi" # required for vl805 firmware to load + ]; + + loader = { + grub.enable = lib.mkDefault false; + generic-extlinux-compatible.enable = lib.mkForce true; + }; + }; +} diff --git a/hosts/pi4/configuration.nix b/hosts/pi5/configuration.nix similarity index 92% rename from hosts/pi4/configuration.nix rename to hosts/pi5/configuration.nix index dc14c20..5c76667 100755 --- a/hosts/pi4/configuration.nix +++ b/hosts/pi5/configuration.nix @@ -11,22 +11,19 @@ let wifiSecrets = config.sops.secrets."wifi-password".path; interface = "wlan0"; timezone = "America/Chicago"; - hostname = "pi4"; + hostname = "pi5"; in { imports = [ - # Include the results of the hardware scan. - ./adguard.nix - ./argononed.nix ./boot.nix - ./hardware-configuration.nix + # ./hardware-configuration.nix ./impermanence.nix # ./sops.nix - ./ups-monitor.nix ../default.nix ]; - + raspberry-pi-nix.board = lib.mkForce "bcm2712"; + # Enable nix flakes and nix-command tools nix = { settings = { @@ -62,12 +59,6 @@ in }; }; - services.hardware.argonone.enable = true; - - services.ups-monitor = { - enable = false; - }; - hardware = { raspberry-pi."4".fkms-3d.enable = false; raspberry-pi."4".apply-overlays-dtmerge.enable = false; diff --git a/hosts/pi4/hardware-configuration.nix b/hosts/pi5/hardware-configuration.nix similarity index 100% rename from hosts/pi4/hardware-configuration.nix rename to hosts/pi5/hardware-configuration.nix diff --git a/hosts/pi4/home.nix b/hosts/pi5/home.nix similarity index 100% rename from hosts/pi4/home.nix rename to hosts/pi5/home.nix diff --git a/hosts/pi4/impermanence.nix b/hosts/pi5/impermanence.nix similarity index 100% rename from hosts/pi4/impermanence.nix rename to hosts/pi5/impermanence.nix diff --git a/hosts/pi4/sops.nix b/hosts/pi5/sops.nix similarity index 100% rename from hosts/pi4/sops.nix rename to hosts/pi5/sops.nix