summaryrefslogtreecommitdiff
path: root/modules/security
diff options
context:
space:
mode:
authorDaiderd Jordan <daiderd@gmail.com>2019-02-16 16:18:52 +0100
committerDaiderd Jordan <daiderd@gmail.com>2019-02-16 16:55:07 +0100
commit1e67f6a2bc496cb5014915a71e323603e4b41662 (patch)
tree9d7aba2c7dcd8c289279713345173acac920d8b5 /modules/security
parent10c34f12775dd941ecb796f426272f891bde5ec7 (diff)
sandbox: add module for sandbox profiles
This could be used outside of nix-darwin, but this is mainly useful for services since all of the inputs are known there. { # $ /usr/bin/sandbox-exec -f $profile $coreutils/bin/ls / # ls: cannot access '/': Operation not permitted security.sandbox.profiles.example.closure = [ pkgs.coreutils ]; }
Diffstat (limited to 'modules/security')
-rw-r--r--modules/security/sandbox/default.nix131
1 files changed, 131 insertions, 0 deletions
diff --git a/modules/security/sandbox/default.nix b/modules/security/sandbox/default.nix
new file mode 100644
index 0000000..4ad453a
--- /dev/null
+++ b/modules/security/sandbox/default.nix
@@ -0,0 +1,131 @@
+{ config, lib, pkgs, ... }:
+
+with lib;
+
+let
+ cfg = config.security.sandbox;
+
+ profile =
+ { config, name, ... }:
+ {
+ options = {
+ profile = mkOption {
+ type = types.lines;
+ apply = text: pkgs.runCommandNoCC "sandbox.sb" {} ''
+ for f in $(< ${config.closure}/store-paths); do
+ storePaths+="(subpath \"$f\")"
+ done
+
+ cat <<-EOF > $out
+ ${text}
+ EOF
+ '';
+ };
+
+ closure = mkOption {
+ type = types.listOf types.package;
+ default = [];
+ apply = paths: pkgs.closureInfo { rootPaths = paths; };
+ description = "List of store paths to make accessible.";
+ };
+
+ readablePaths = mkOption {
+ type = types.listOf types.path;
+ default = [];
+ description = "List of paths that should be read-only inside the sandbox.";
+ };
+
+ writablePaths = mkOption {
+ type = types.listOf types.path;
+ default = [];
+ description = "List of paths that should be read/write inside the sandbox.";
+ };
+
+ allowSystemPaths = mkOption {
+ type = types.bool;
+ default = false;
+ };
+
+ allowLocalNetworking = mkOption {
+ type = types.bool;
+ default = false;
+ description = "Whether to allow localhost network access inside the sandbox.";
+ };
+
+ allowNetworking = mkOption {
+ type = types.bool;
+ default = false;
+ description = "Whether to allow network access inside the sandbox.";
+ };
+ };
+
+ config = {
+
+ profile = mkOrder 0 ''
+ (version 1)
+ (deny default)
+
+ (allow file-read*
+ (subpath "/usr/lib")
+ (subpath "/System/Library/Frameworks")
+ (subpath "/System/Library/PrivateFrameworks"))
+
+ (allow file-read-metadata
+ (literal "/dev"))
+ (allow file*
+ (literal "/dev/null")
+ (literal "/dev/random")
+ (literal "/dev/stdin")
+ (literal "/dev/stdout")
+ (literal "/dev/tty")
+ (literal "/dev/urandom")
+ (literal "/dev/zero")
+ (subpath "/dev/fd"))
+
+ (allow process-fork)
+ (allow signal (target same-sandbox))
+ (deny file-write* (subpath "/nix/store"))
+ (allow file-read* process-exec
+ $storePaths)
+
+ ${optionalString (config.readablePaths != []) ''
+ (allow file-read*
+ ${concatMapStrings (x: ''(subpath "${x}")'') config.readablePaths})
+ ''}
+ ${optionalString (config.writablePaths != []) ''
+ (allow file*
+ ${concatMapStrings (x: ''(subpath "${x}")'') config.writablePaths})
+ ''}
+ ${optionalString config.allowSystemPaths ''
+ (allow file-read* process-exec
+ (subpath "/bin")
+ (subpath "/usr/bin"))
+ ''}
+ ${optionalString config.allowLocalNetworking ''
+ (allow network* (local ip) (local tcp) (local udp))
+ ''}
+ ${optionalString config.allowNetworking ''
+ (allow network*
+ (local ip)
+ (remote ip))
+ (allow network-outbound
+ (remote unix-socket (path-literal "/private/var/run/mDNSResponder")))
+ ''}
+ '';
+
+ };
+ };
+in
+
+{
+ options = {
+ security.sandbox.profiles = mkOption {
+ type = types.attrsOf (types.submodule profile);
+ default = {};
+ description = "Definition of sandbox profiles.";
+ };
+ };
+
+ config = {
+ };
+}