From 37d79fbb08aae5eaef1c3326164cd826956621a6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?ryan4yin=20=7C=20=E4=BA=8C=E8=8A=B1?= Date: Sat, 3 Oct 2026 17:11:51 +0800 Subject: [PATCH] chore(hardening): consolidate system hardening and fix stale docs (#368) --- README.md | 6 +++ SECURITY.md | 10 ++-- WORKAROUNDS.md | 3 +- hardening/README.md | 51 +++++++++---------- .../base => hardening}/kernel-hardening.nix | 0 hardening/profiles/default.nix | 10 ---- modules/README.md | 4 +- modules/nixos/base/default.nix | 5 +- modules/nixos/server/server-aarch64.nix | 2 +- modules/nixos/server/server-riscv64.nix | 2 +- .../aarch64-linux/src/12kingdoms-shoukei.nix | 1 - outputs/x86_64-linux/src/idols-ai.nix | 1 - 12 files changed, 47 insertions(+), 48 deletions(-) rename {modules/nixos/base => hardening}/kernel-hardening.nix (100%) delete mode 100644 hardening/profiles/default.nix diff --git a/README.md b/README.md index 9a032d60..9d48a62d 100644 --- a/README.md +++ b/README.md @@ -99,6 +99,12 @@ Wallpapers: https://github.com/ryan4yin/wallpapers See [./secrets](./secrets) for details. +## Security & Hardening + +See [./SECURITY.md](./SECURITY.md) for the threat model, security architecture, controls and audit +status, [./hardening/README.md](./hardening/README.md) for application sandboxing and Linux +hardening, and [./WORKAROUNDS.md](./WORKAROUNDS.md) for temporary exceptions and known gaps. + ## How to Deploy this Flake? diff --git a/SECURITY.md b/SECURITY.md index 7e199164..9dff73b0 100644 --- a/SECURITY.md +++ b/SECURITY.md @@ -4,6 +4,9 @@ This is a personal infrastructure repository, not a supported security product. describes the intended architecture, controls present in source, their limitations, and remaining work. A configured control is not evidence that it is active on a running machine. +Related documents: [application hardening](hardening/README.md) for sandbox wrappers and Linux +hardening notes, and [WORKAROUNDS.md](WORKAROUNDS.md) for temporary exceptions and known gaps. + ## Reporting problems For non-sensitive configuration bugs, open an issue with the affected host role and a redacted @@ -51,9 +54,10 @@ resources are maintained in the separate k8s-gitops repository. ## Kernel and process baseline The following explicit, overridable baseline is implemented in -[kernel-hardening.nix](modules/nixos/base/kernel-hardening.nix), with Linux eval coverage and -explicit ARM/RISC-V server imports. Source implementation is not runtime verification. Some values -are already kernel/systemd/NixOS defaults; Darwin does not receive Linux sysctls. +[kernel-hardening.nix](hardening/kernel-hardening.nix), which holds the values; the table below +summarizes them. It has Linux eval coverage and explicit ARM/RISC-V server imports. Source +implementation is not runtime verification. Some values are already kernel/systemd/NixOS defaults; +Darwin does not receive Linux sysctls. | Setting | Value | Effect and compatibility | | ------------------------------------------------- | ----- | ----------------------------------------------------------------------------------------------------------------------------------- | diff --git a/WORKAROUNDS.md b/WORKAROUNDS.md index 2c048e87..3469be5c 100644 --- a/WORKAROUNDS.md +++ b/WORKAROUNDS.md @@ -35,7 +35,7 @@ A setting that works around a bug or a hardware quirk. | WA-008 | Relaxed NVMe APST (`nvme_core.default_ps_max_latency_us=100000`) — `hosts/idols-ai/hardware-configuration.nix` | the KINGBANK KP260 (DRAM-less QLC) froze on slow APST wake-ups | Drop the override once kernel/firmware fixes or replacement hardware make default APST reliable | 2026-10-03 | watch NVMe timeout/reset/AER in the journal | active | | WA-009 | USB-SATA bridge mitigations (`usbcore.autosuspend=-1`, `usb-storage.delay_use=10`) — `hosts/12kingdoms-youko/default.nix` | flaky JMicron JMS567 resets with UDMA-CRC and I/O errors | Drop once the bridge/controller is replaced; the signal is smartctl CRC/media errors | 2026-09-21 | on hardware change or CRC errors | active | | WA-010 | Insta360 Link USB reset on S3 resume — `hosts/idols-ai/default.nix` | the camera stays enumerated with a stalled UVC endpoint after resume | Drop after the Insta360 firmware or the kernel `uvcvideo` fixes it | 2026-08-01 | on kernel or firmware change | active | -| WA-011 | Kernel module blacklist (`esp4`, `esp6`, `rxrpc`) — `modules/nixos/base/kernel-hardening.nix` | attack surface for the Dirty Frag LPE (CVE-2026-43284 / CVE-2026-43500) | Kept as defence in depth; drop only if something needs those modules | 2026-10-03 | rarely | active | +| WA-011 | Kernel module blacklist (`esp4`, `esp6`, `rxrpc`) — `hardening/kernel-hardening.nix` | attack surface for the Dirty Frag LPE (CVE-2026-43284 / CVE-2026-43500) | Kept as defence in depth; drop only if something needs those modules | 2026-10-03 | rarely | active | If WA-008 freezes recur, the fallback is to restore `nvme_core.default_ps_max_latency_us=0 nvme_core.io_timeout=4294967295 pcie_aspm=off`; this is a @@ -60,6 +60,7 @@ An unfinished feature or gap. ## Related +- Security architecture, threat model and audit status: [SECURITY.md](./SECURITY.md). - Unmerged **nixpkgs** PRs are carried via the `nixpkgs-patched` input and the [`.agents/skills/nixpkgs-patched`](./.agents/skills/nixpkgs-patched/SKILL.md) workflow (that input currently carries nothing; package-level carries are recorded under `Pins`). diff --git a/hardening/README.md b/hardening/README.md index 2d0d3130..aa34da74 100644 --- a/hardening/README.md +++ b/hardening/README.md @@ -2,6 +2,10 @@ > Work in progress. +Application sandboxing (nixpak/bubblewrap) and Linux hardening knowledge for this repository. For +the repository security policy, architecture and audit status, see [`SECURITY.md`](../SECURITY.md); +for temporary exceptions and known gaps, see [`WORKAROUNDS.md`](../WORKAROUNDS.md). + ## Goal - **System Level**: Protect critical files from being accessed by untrusted applications. @@ -17,7 +21,8 @@ ### 1. **System Level** - **AppArmor** (`apparmor/`): AppArmor profiles and configuration -- **Kernel & System Hardening** (`profiles/`): System-wide hardening profiles +- **Kernel & process hardening** (`kernel-hardening.nix`): sysctl baseline and unused-module deny + list; rationale and verification live in [`SECURITY.md`](../SECURITY.md). ### 2. **Per-App Level** @@ -26,53 +31,43 @@ - QQ (Chinese messaging app) configuration - Telegram Desktop configuration - Modular system with reusable components -- **Firejail** (legacy): SUID-based sandboxing (not used) - **Bubblewrap** (`bwraps/`): Direct bubblewrap configurations - WeChat sandboxing configuration ## Current Implementation Status -| Component | Status | Notes | -| ----------------- | --------- | ------------------------------ | -| AppArmor Profiles | 🚧 WIP | Basic structure in place | -| Nixpak Firefox | ✅ Active | Firefox sandboxing via nixpak | -| Nixpak QQ | ✅ Active | QQ application sandboxing | -| Nixpak Telegram | ✅ Active | Telegram Desktop sandboxing | -| Bubblewrap WeChat | ✅ Active | WeChat specific sandboxing | -| System Profiles | 🚧 WIP | Hardened system configurations | +| Component | Status | Notes | +| ----------------- | --------- | ----------------------------- | +| AppArmor Profiles | 🚧 WIP | Basic structure in place | +| Nixpak Firefox | ✅ Active | Firefox sandboxing via nixpak | +| Nixpak QQ | ✅ Active | QQ application sandboxing | +| Nixpak Telegram | ✅ Active | Telegram Desktop sandboxing | +| Bubblewrap WeChat | ✅ Active | WeChat specific sandboxing | ## Directory Structure ``` hardening/ ├── README.md +├── kernel-hardening.nix # sysctl baseline + unused-module deny list ├── apparmor/ # AppArmor security profiles │ └── default.nix ├── bwraps/ # Direct bubblewrap configurations │ ├── default.nix │ └── wechat.nix -├── nixpaks/ # Nixpak application sandboxing -│ ├── default.nix -│ ├── firefox.nix -│ ├── qq.nix -│ ├── telegram-desktop.nix -│ └── modules/ # Reusable nixpak modules -│ ├── custom-policy.nix -│ ├── gui-base.nix -│ └── network.nix -└── profiles/ # System hardening profiles - └── default.nix +└── nixpaks/ # Nixpak application sandboxing + ├── default.nix + ├── firefox.nix + ├── qq.nix + ├── telegram-desktop.nix + └── modules/ # Reusable nixpak modules + ├── custom-policy.nix + ├── gui-base.nix + └── network.nix ``` -## Kernel Hardening - -- NixOS Kernel Config: - https://github.com/NixOS/nixpkgs/blob/nixos-unstable/pkgs/os-specific/linux/kernel/hardened/config.nix - ## System Hardening -- NixOS Profile: - https://github.com/NixOS/nixpkgs/blob/nixos-unstable/nixos/modules/profiles/hardened.nix - Apparmor: [roddhjav/apparmor.d](https://github.com/roddhjav/apparmor.d) - https://gitlab.com/apparmor/apparmor/-/wikis/Documentation - AppArmor.d is a set of over 1500 AppArmor profiles whose aim is to confine most Linux based diff --git a/modules/nixos/base/kernel-hardening.nix b/hardening/kernel-hardening.nix similarity index 100% rename from modules/nixos/base/kernel-hardening.nix rename to hardening/kernel-hardening.nix diff --git a/hardening/profiles/default.nix b/hardening/profiles/default.nix deleted file mode 100644 index 8288f8a7..00000000 --- a/hardening/profiles/default.nix +++ /dev/null @@ -1,10 +0,0 @@ -{ modulesPath, ... }: -{ - imports = [ - (modulesPath + "/profiles/hardened.nix") - ]; - - # disable coredump that could be exploited later - # and also slow down the system when something crash - systemd.coredump.enable = false; -} diff --git a/modules/README.md b/modules/README.md index f13dbd13..990414e2 100644 --- a/modules/README.md +++ b/modules/README.md @@ -32,7 +32,6 @@ modules/ │ ├── core.nix # Core system settings │ ├── default.nix │ ├── i18n.nix # Internationalization - │ ├── kernel-hardening.nix # Kernel hardening (module blacklisting) │ ├── locate.nix # locate/updatedb file search │ ├── monitoring.nix # System monitoring │ ├── networking/ # Network configuration @@ -69,6 +68,9 @@ modules/ └── server.nix ``` +System hardening modules (kernel baseline, AppArmor, app sandboxes) live under +[`../hardening/`](../hardening/README.md). + ## Module Categories ### 1. **Base Modules** (`base/`) diff --git a/modules/nixos/base/default.nix b/modules/nixos/base/default.nix index 8b8274f3..201b717a 100644 --- a/modules/nixos/base/default.nix +++ b/modules/nixos/base/default.nix @@ -1,4 +1,7 @@ { mylib, ... }: { - imports = mylib.scanPaths ./. ++ [ (mylib.relativeToRoot "hardening/apparmor") ]; + imports = mylib.scanPaths ./. ++ [ + (mylib.relativeToRoot "hardening/apparmor") + (mylib.relativeToRoot "hardening/kernel-hardening.nix") + ]; } diff --git a/modules/nixos/server/server-aarch64.nix b/modules/nixos/server/server-aarch64.nix index cbc1aaf1..7fe04241 100644 --- a/modules/nixos/server/server-aarch64.nix +++ b/modules/nixos/server/server-aarch64.nix @@ -8,7 +8,7 @@ ../base/btop.nix ../base/core.nix ../base/i18n.nix - ../base/kernel-hardening.nix + (mylib.relativeToRoot "hardening/kernel-hardening.nix") ../base/monitoring.nix ../base/nix.nix ../base/packages.nix diff --git a/modules/nixos/server/server-riscv64.nix b/modules/nixos/server/server-riscv64.nix index 2e40b4f4..881a8d70 100644 --- a/modules/nixos/server/server-riscv64.nix +++ b/modules/nixos/server/server-riscv64.nix @@ -8,7 +8,7 @@ ../base/btop.nix ../base/core.nix ../base/i18n.nix - ../base/kernel-hardening.nix + ../../../hardening/kernel-hardening.nix ../base/monitoring.nix ../base/nix.nix ../base/packages.nix diff --git a/outputs/aarch64-linux/src/12kingdoms-shoukei.nix b/outputs/aarch64-linux/src/12kingdoms-shoukei.nix index bc927e1e..74c80f2a 100644 --- a/outputs/aarch64-linux/src/12kingdoms-shoukei.nix +++ b/outputs/aarch64-linux/src/12kingdoms-shoukei.nix @@ -22,7 +22,6 @@ let # host specific "hosts/12kingdoms-${name}" # nixos hardening - # "hardening/profiles/default.nix" "hardening/nixpaks" "hardening/bwraps" ]) diff --git a/outputs/x86_64-linux/src/idols-ai.nix b/outputs/x86_64-linux/src/idols-ai.nix index fc5e7101..614944a5 100644 --- a/outputs/x86_64-linux/src/idols-ai.nix +++ b/outputs/x86_64-linux/src/idols-ai.nix @@ -23,7 +23,6 @@ let # host specific "hosts/idols-${name}" # nixos hardening - # "hardening/profiles/default.nix" "hardening/nixpaks" "hardening/bwraps" ])