From b67957f9dced698a5326f1ad57bcee34eb3a0641 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?G=C3=BCnther=20Noack?= Date: Sun, 2 Jun 2024 17:47:09 +0200 Subject: [PATCH] WIP: Support for composite rules Fixes issue #25 --- landlock/composite_opt.go | 46 ++++++++++++++++++++++++++++++++ landlock/llrules/experimental.go | 35 ++++++++++++++++++++++++ 2 files changed, 81 insertions(+) create mode 100644 landlock/composite_opt.go create mode 100644 landlock/llrules/experimental.go diff --git a/landlock/composite_opt.go b/landlock/composite_opt.go new file mode 100644 index 0000000..c5b5491 --- /dev/null +++ b/landlock/composite_opt.go @@ -0,0 +1,46 @@ +package landlock + +type compositeRule struct { + rules []Rule +} + +func (c *compositeRule) compatibleWithConfig(cfg Config) bool { + for _, r := range c.rules { + if !r.compatibleWithConfig(cfg) { + return false + } + } + return true +} + +func (c *compositeRule) downgrade(cfg Config) (out Rule, ok bool) { + cr := new(compositeRule) + for _, r := range c.rules { + r, ok := r.downgrade(cfg) + if !ok { + return nil, false + } + cr.rules = append(cr.rules, r) + } + return cr, true +} + +func (c *compositeRule) addToRuleset(rulesetFD int, cfg Config) error { + for _, r := range c.rules { + err := r.addToRuleset(rulesetFD, cfg) + if err != nil { + return err + } + } + return nil +} + +// CompositeRule returns a rule composed of sub-rules. +// +// A composite rule passed to [Restrict] behaves the same as passing +// all sub-rules individually. Composite rules are not strictly +// necessary in Go-Landlock, but useful for building libraries of +// re-usable Landlock rules. +func CompositeRule(rules ...Rule) Rule { + return &compositeRule{rules: rules} +} diff --git a/landlock/llrules/experimental.go b/landlock/llrules/experimental.go new file mode 100644 index 0000000..96ca7cb --- /dev/null +++ b/landlock/llrules/experimental.go @@ -0,0 +1,35 @@ +// Package llrules experimentally implements commonly used groups of +// Landlock rules. +package llrules + +import "github.com/landlock-lsm/go-landlock/landlock" + +func DNSOverTCP() landlock.Rule { + return landlock.CompositeRule(landlock.ConnectTCP(53), dnsFiles()) +} + +func DNSOverUDP() landlock.Rule { + // UDP is not restrictable yet, but it can be added here once + // Landlock can do that. + return dnsFiles() +} + +func dnsFiles() landlock.Rule { + return landlock.ROFiles( + "/etc/hosts", + "/etc/resolv.conf", + ).IgnoreIfMissing() +} + +func SharedLibraries() landlock.Rule { + // XXX: How does the linker look up this list of paths? + // XXX: Use more specific rulesets. + return landlock.RODirs( + "/lib", + "/lib32", + "/lib64", + "/usr/lib", + "/usr/lib32", + "/usr/lib64", + ).IgnoreIfMissing() +}