From 059164d4fa80047fc50bffc1582424d00cf4c139 Mon Sep 17 00:00:00 2001 From: Ophestra Date: Mon, 25 Aug 2025 17:44:12 +0900 Subject: [PATCH] hst/fsbind: optional autoroot behaviour This allows autoroot to be configured via Filesystem. Signed-off-by: Ophestra --- hst/fsbind.go | 49 ++++++++++++++++++++++++++++++++++++---------- hst/fsbind_test.go | 31 +++++++++++++++++++++++++++++ 2 files changed, 70 insertions(+), 10 deletions(-) diff --git a/hst/fsbind.go b/hst/fsbind.go index c6f4a7e..50e8da5 100644 --- a/hst/fsbind.go +++ b/hst/fsbind.go @@ -24,9 +24,21 @@ type FSBind struct { Device bool `json:"dev,omitempty"` // skip this mount point if the host path does not exist Optional bool `json:"optional,omitempty"` + + // enable autoroot behaviour; + // this requires Target to be [container.AbsFHSRoot]. + AutoRoot bool `json:"autoroot,omitempty"` } -func (b *FSBind) Valid() bool { return b != nil && b.Source != nil } +func (b *FSBind) Valid() bool { + if b == nil || b.Source == nil { + return false + } + if b.AutoRoot && (b.Target == nil || b.Target.String() != container.FHSRoot) { + return false + } + return true +} func (b *FSBind) Path() *container.Absolute { if !b.Valid() { @@ -64,28 +76,45 @@ func (b *FSBind) Apply(ops *container.Ops) { if b.Optional { flags |= container.BindOptional } - ops.Bind(b.Source, target, flags) + + if !b.AutoRoot { + ops.Bind(b.Source, target, flags) + } else { + ops.Root(b.Source, flags) + } } func (b *FSBind) String() string { - g := 4 if !b.Valid() { return "" } - g += len(b.Source.String()) + var flagSym string + if b.Device { + flagSym = "d" + } else if b.Write { + flagSym = "w" + } + + if b.AutoRoot { + prefix := "autoroot" + if flagSym != "" { + prefix += ":" + flagSym + } + if b.Source.String() != container.FHSRoot { + return prefix + ":" + b.Source.String() + } + return prefix + } + + g := 4 + len(b.Source.String()) if b.Target != nil { g += len(b.Target.String()) } expr := new(strings.Builder) expr.Grow(g) - - if b.Device { - expr.WriteString("d") - } else if b.Write { - expr.WriteString("w") - } + expr.WriteString(flagSym) if !b.Optional { expr.WriteString("*") diff --git a/hst/fsbind_test.go b/hst/fsbind_test.go index 21d3640..750dd93 100644 --- a/hst/fsbind_test.go +++ b/hst/fsbind_test.go @@ -62,5 +62,36 @@ func TestFSBind(t *testing.T) { Target: m("/"), }}, m("/"), ms("/"), "*/"}, + + {"autoroot nil target", &hst.FSBind{ + Source: m("/"), + AutoRoot: true, + }, false, nil, nil, nil, ""}, + + {"autoroot bad target", &hst.FSBind{ + Source: m("/"), + Target: m("/etc/"), + AutoRoot: true, + }, false, nil, nil, nil, ""}, + + {"autoroot pd", &hst.FSBind{ + Target: m("/"), + Source: m("/"), + Write: true, + AutoRoot: true, + }, true, container.Ops{&container.AutoRootOp{ + Host: m("/"), + Flags: container.BindWritable, + }}, m("/"), ms("/"), "autoroot:w"}, + + {"autoroot silly", &hst.FSBind{ + Target: m("/"), + Source: m("/etc"), + Write: true, + AutoRoot: true, + }, true, container.Ops{&container.AutoRootOp{ + Host: m("/etc"), + Flags: container.BindWritable, + }}, m("/"), ms("/etc"), "autoroot:w:/etc"}, }) }