Skip to content

Commit ab29593

Browse files
committed
libcontainer/system: move userns utilities to separate package
Moving these utilities to a separate package, so that consumers of this package don't have to pull in the whole "system" package. Looking at uses of these utilities (outside of runc itself); `RunningInUserNS()` is used by [various external consumers][1], so adding a "Deprecated" alias for this. [1]: https://grep.app/search?current=2&q=.RunningInUserNS Signed-off-by: Sebastiaan van Stijn <[email protected]>
0 parents  commit ab29593

5 files changed

Lines changed: 119 additions & 0 deletions

File tree

user/userns/userns.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
package userns
2+
3+
// RunningInUserNS detects whether we are currently running in a user namespace.
4+
// Originally copied from github.com/lxc/lxd/shared/util.go
5+
var RunningInUserNS = runningInUserNS

user/userns/userns_fuzzer.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
// +build gofuzz
2+
3+
package userns
4+
5+
import (
6+
"strings"
7+
8+
"github.com/opencontainers/runc/libcontainer/user"
9+
)
10+
11+
func FuzzUIDMap(data []byte) int {
12+
uidmap, _ := user.ParseIDMap(strings.NewReader(string(data)))
13+
_ = uidMapInUserNS(uidmap)
14+
return 1
15+
}

user/userns/userns_linux.go

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
package userns
2+
3+
import (
4+
"sync"
5+
6+
"github.com/opencontainers/runc/libcontainer/user"
7+
)
8+
9+
var (
10+
inUserNS bool
11+
nsOnce sync.Once
12+
)
13+
14+
// runningInUserNS detects whether we are currently running in a user namespace.
15+
// Originally copied from github.com/lxc/lxd/shared/util.go
16+
func runningInUserNS() bool {
17+
nsOnce.Do(func() {
18+
uidmap, err := user.CurrentProcessUIDMap()
19+
if err != nil {
20+
// This kernel-provided file only exists if user namespaces are supported
21+
return
22+
}
23+
inUserNS = uidMapInUserNS(uidmap)
24+
})
25+
return inUserNS
26+
}
27+
28+
func uidMapInUserNS(uidmap []user.IDMap) bool {
29+
/*
30+
* We assume we are in the initial user namespace if we have a full
31+
* range - 4294967295 uids starting at uid 0.
32+
*/
33+
if len(uidmap) == 1 && uidmap[0].ID == 0 && uidmap[0].ParentID == 0 && uidmap[0].Count == 4294967295 {
34+
return false
35+
}
36+
return true
37+
}

user/userns/userns_linux_test.go

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// +build linux
2+
3+
package userns
4+
5+
import (
6+
"strings"
7+
"testing"
8+
9+
"github.com/opencontainers/runc/libcontainer/user"
10+
)
11+
12+
func TestUIDMapInUserNS(t *testing.T) {
13+
cases := []struct {
14+
s string
15+
expected bool
16+
}{
17+
{
18+
s: " 0 0 4294967295\n",
19+
expected: false,
20+
},
21+
{
22+
s: " 0 0 1\n",
23+
expected: true,
24+
},
25+
{
26+
s: " 0 1001 1\n 1 231072 65536\n",
27+
expected: true,
28+
},
29+
{
30+
// file exist but empty (the initial state when userns is created. see man 7 user_namespaces)
31+
s: "",
32+
expected: true,
33+
},
34+
}
35+
for _, c := range cases {
36+
uidmap, err := user.ParseIDMap(strings.NewReader(c.s))
37+
if err != nil {
38+
t.Fatal(err)
39+
}
40+
actual := uidMapInUserNS(uidmap)
41+
if c.expected != actual {
42+
t.Fatalf("expected %v, got %v for %q", c.expected, actual, c.s)
43+
}
44+
}
45+
}

user/userns/userns_unsupported.go

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// +build !linux
2+
3+
package userns
4+
5+
import "github.com/opencontainers/runc/libcontainer/user"
6+
7+
// runningInUserNS is a stub for non-Linux systems
8+
// Always returns false
9+
func runningInUserNS() bool {
10+
return false
11+
}
12+
13+
// uidMapInUserNS is a stub for non-Linux systems
14+
// Always returns false
15+
func uidMapInUserNS(uidmap []user.IDMap) bool {
16+
return false
17+
}

0 commit comments

Comments
 (0)