mirror of
https://github.com/golang/go.git
synced 2025-12-08 06:10:04 +00:00
syscall: call setgroups for no groups on GNU/Linux
Skip setgroups only for one particular case: GidMappings != nil and GidMappingsEnableSetgroup == false and list of supplementary groups is empty. This patch returns pre-1.5 behavior for simple exec and still allows to use GidMappings with non-empty Credential. Change-Id: Ia91c77e76ec5efab7a7f78134ffb529910108fc1 Reviewed-on: https://go-review.googlesource.com/23524 Reviewed-by: Ian Lance Taylor <iant@golang.org> Run-TryBot: Ian Lance Taylor <iant@golang.org> TryBot-Result: Gobot Gobot <gobot@golang.org>
This commit is contained in:
parent
e90a49a0f5
commit
853cd1f4a6
2 changed files with 68 additions and 3 deletions
|
|
@ -26,7 +26,7 @@ func isChrooted(t *testing.T) bool {
|
|||
return root.Sys().(*syscall.Stat_t).Ino != 2
|
||||
}
|
||||
|
||||
func whoamiCmd(t *testing.T, uid, gid int, setgroups bool) *exec.Cmd {
|
||||
func checkUserNS(t *testing.T) {
|
||||
if _, err := os.Stat("/proc/self/ns/user"); err != nil {
|
||||
if os.IsNotExist(err) {
|
||||
t.Skip("kernel doesn't support user namespaces")
|
||||
|
|
@ -56,6 +56,10 @@ func whoamiCmd(t *testing.T, uid, gid int, setgroups bool) *exec.Cmd {
|
|||
if os.Getenv("GO_BUILDER_NAME") != "" && os.Getenv("IN_KUBERNETES") == "1" {
|
||||
t.Skip("skipping test on Kubernetes-based builders; see Issue 12815")
|
||||
}
|
||||
}
|
||||
|
||||
func whoamiCmd(t *testing.T, uid, gid int, setgroups bool) *exec.Cmd {
|
||||
checkUserNS(t)
|
||||
cmd := exec.Command("whoami")
|
||||
cmd.SysProcAttr = &syscall.SysProcAttr{
|
||||
Cloneflags: syscall.CLONE_NEWUSER,
|
||||
|
|
@ -161,3 +165,58 @@ func TestUnshare(t *testing.T) {
|
|||
t.Fatalf("Expected 3 lines of output, got %d", len(lines))
|
||||
}
|
||||
}
|
||||
|
||||
func TestGroupCleanup(t *testing.T) {
|
||||
if os.Getuid() != 0 {
|
||||
t.Skip("we need root for credential")
|
||||
}
|
||||
cmd := exec.Command("id")
|
||||
cmd.SysProcAttr = &syscall.SysProcAttr{
|
||||
Credential: &syscall.Credential{
|
||||
Uid: 0,
|
||||
Gid: 0,
|
||||
},
|
||||
}
|
||||
out, err := cmd.CombinedOutput()
|
||||
if err != nil {
|
||||
t.Fatalf("Cmd failed with err %v, output: %s", err, out)
|
||||
}
|
||||
strOut := strings.TrimSpace(string(out))
|
||||
expected := "uid=0(root) gid=0(root) groups=0(root)"
|
||||
if strOut != expected {
|
||||
t.Fatalf("id command output: %s, expected: %s", strOut, expected)
|
||||
}
|
||||
}
|
||||
|
||||
func TestGroupCleanupUserNamespace(t *testing.T) {
|
||||
if os.Getuid() != 0 {
|
||||
t.Skip("we need root for credential")
|
||||
}
|
||||
checkUserNS(t)
|
||||
cmd := exec.Command("id")
|
||||
uid, gid := os.Getuid(), os.Getgid()
|
||||
cmd.SysProcAttr = &syscall.SysProcAttr{
|
||||
Cloneflags: syscall.CLONE_NEWUSER,
|
||||
Credential: &syscall.Credential{
|
||||
Uid: uint32(uid),
|
||||
Gid: uint32(gid),
|
||||
},
|
||||
UidMappings: []syscall.SysProcIDMap{
|
||||
{ContainerID: 0, HostID: uid, Size: 1},
|
||||
},
|
||||
GidMappings: []syscall.SysProcIDMap{
|
||||
{ContainerID: 0, HostID: gid, Size: 1},
|
||||
},
|
||||
}
|
||||
out, err := cmd.CombinedOutput()
|
||||
if err != nil {
|
||||
t.Fatalf("Cmd failed with err %v, output: %s", err, out)
|
||||
}
|
||||
strOut := strings.TrimSpace(string(out))
|
||||
// there are two possible outs
|
||||
expected1 := "uid=0(root) gid=0(root) groups=0(root)"
|
||||
expected2 := "uid=0(root) gid=0(root) groups=0(root),65534(nobody)"
|
||||
if strOut != expected1 && strOut != expected2 {
|
||||
t.Fatalf("id command output: %s, expected: %s or %s", strOut, expected1, expected2)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue