summaryrefslogtreecommitdiffhomepage
path: root/pkg/sentry/syscalls
diff options
context:
space:
mode:
authorgVisor bot <gvisor-bot@google.com>2021-07-22 14:33:18 -0700
committergVisor bot <gvisor-bot@google.com>2021-07-22 14:33:18 -0700
commit8daeda207205f9c66083846e6ba231ab04e09163 (patch)
treed1ab40a29ca612f64396b4ce34a04fe163587032 /pkg/sentry/syscalls
parent70626b3da217373eb74420e2c3426cc9283265fa (diff)
parent4a874557f5846ec9cb2e5b2515921e37a4ca4f07 (diff)
Merge pull request #6108 from sudo-sturbia:msgqueue/syscalls
PiperOrigin-RevId: 386323389
Diffstat (limited to 'pkg/sentry/syscalls')
-rw-r--r--pkg/sentry/syscalls/linux/BUILD2
-rw-r--r--pkg/sentry/syscalls/linux/linux64.go16
-rw-r--r--pkg/sentry/syscalls/linux/sys_msgqueue.go57
-rw-r--r--pkg/sentry/syscalls/linux/sys_sem.go43
-rw-r--r--pkg/sentry/syscalls/linux/sys_shm.go11
5 files changed, 95 insertions, 34 deletions
diff --git a/pkg/sentry/syscalls/linux/BUILD b/pkg/sentry/syscalls/linux/BUILD
index a2f612f45..ccccce6a9 100644
--- a/pkg/sentry/syscalls/linux/BUILD
+++ b/pkg/sentry/syscalls/linux/BUILD
@@ -25,6 +25,7 @@ go_library(
"sys_mempolicy.go",
"sys_mmap.go",
"sys_mount.go",
+ "sys_msgqueue.go",
"sys_pipe.go",
"sys_poll.go",
"sys_prctl.go",
@@ -84,6 +85,7 @@ go_library(
"//pkg/sentry/kernel/epoll",
"//pkg/sentry/kernel/eventfd",
"//pkg/sentry/kernel/fasync",
+ "//pkg/sentry/kernel/ipc",
"//pkg/sentry/kernel/pipe",
"//pkg/sentry/kernel/sched",
"//pkg/sentry/kernel/shm",
diff --git a/pkg/sentry/syscalls/linux/linux64.go b/pkg/sentry/syscalls/linux/linux64.go
index f1cb5a2c8..6f44d767b 100644
--- a/pkg/sentry/syscalls/linux/linux64.go
+++ b/pkg/sentry/syscalls/linux/linux64.go
@@ -121,10 +121,10 @@ var AMD64 = &kernel.SyscallTable{
65: syscalls.PartiallySupported("semop", Semop, "Option SEM_UNDO not supported.", nil),
66: syscalls.Supported("semctl", Semctl),
67: syscalls.Supported("shmdt", Shmdt),
- 68: syscalls.ErrorWithEvent("msgget", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 69: syscalls.ErrorWithEvent("msgsnd", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 70: syscalls.ErrorWithEvent("msgrcv", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 71: syscalls.ErrorWithEvent("msgctl", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
+ 68: syscalls.Supported("msgget", Msgget),
+ 69: syscalls.ErrorWithEvent("msgsnd", linuxerr.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
+ 70: syscalls.ErrorWithEvent("msgrcv", linuxerr.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
+ 71: syscalls.PartiallySupported("msgctl", Msgctl, "Only supports IPC_RMID option.", []string{"gvisor.dev/issue/135"}),
72: syscalls.PartiallySupported("fcntl", Fcntl, "Not all options are supported.", nil),
73: syscalls.PartiallySupported("flock", Flock, "Locks are held within the sandbox only.", nil),
74: syscalls.PartiallySupported("fsync", Fsync, "Full data flush is not guaranteed at this time.", nil),
@@ -616,10 +616,10 @@ var ARM64 = &kernel.SyscallTable{
183: syscalls.ErrorWithEvent("mq_timedreceive", syserror.ENOSYS, "", []string{"gvisor.dev/issue/136"}), // TODO(b/29354921)
184: syscalls.ErrorWithEvent("mq_notify", syserror.ENOSYS, "", []string{"gvisor.dev/issue/136"}), // TODO(b/29354921)
185: syscalls.ErrorWithEvent("mq_getsetattr", syserror.ENOSYS, "", []string{"gvisor.dev/issue/136"}), // TODO(b/29354921)
- 186: syscalls.ErrorWithEvent("msgget", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 187: syscalls.ErrorWithEvent("msgctl", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 188: syscalls.ErrorWithEvent("msgrcv", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
- 189: syscalls.ErrorWithEvent("msgsnd", syserror.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
+ 186: syscalls.Supported("msgget", Msgget),
+ 187: syscalls.PartiallySupported("msgctl", Msgctl, "Only supports IPC_RMID option.", []string{"gvisor.dev/issue/135"}),
+ 188: syscalls.ErrorWithEvent("msgrcv", linuxerr.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
+ 189: syscalls.ErrorWithEvent("msgsnd", linuxerr.ENOSYS, "", []string{"gvisor.dev/issue/135"}), // TODO(b/29354921)
190: syscalls.Supported("semget", Semget),
191: syscalls.Supported("semctl", Semctl),
192: syscalls.Supported("semtimedop", Semtimedop),
diff --git a/pkg/sentry/syscalls/linux/sys_msgqueue.go b/pkg/sentry/syscalls/linux/sys_msgqueue.go
new file mode 100644
index 000000000..3476e218d
--- /dev/null
+++ b/pkg/sentry/syscalls/linux/sys_msgqueue.go
@@ -0,0 +1,57 @@
+// Copyright 2021 The gVisor Authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package linux
+
+import (
+ "gvisor.dev/gvisor/pkg/abi/linux"
+ "gvisor.dev/gvisor/pkg/errors/linuxerr"
+ "gvisor.dev/gvisor/pkg/sentry/arch"
+ "gvisor.dev/gvisor/pkg/sentry/kernel"
+ "gvisor.dev/gvisor/pkg/sentry/kernel/auth"
+ "gvisor.dev/gvisor/pkg/sentry/kernel/ipc"
+)
+
+// Msgget implements msgget(2).
+func Msgget(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
+ key := ipc.Key(args[0].Int())
+ flag := args[1].Int()
+
+ private := key == linux.IPC_PRIVATE
+ create := flag&linux.IPC_CREAT == linux.IPC_CREAT
+ exclusive := flag&linux.IPC_EXCL == linux.IPC_EXCL
+ mode := linux.FileMode(flag & 0777)
+
+ r := t.IPCNamespace().MsgqueueRegistry()
+ queue, err := r.FindOrCreate(t, key, mode, private, create, exclusive)
+ if err != nil {
+ return 0, nil, err
+ }
+ return uintptr(queue.ID()), nil, nil
+}
+
+// Msgctl implements msgctl(2).
+func Msgctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
+ id := ipc.ID(args[0].Int())
+ cmd := args[1].Int()
+
+ creds := auth.CredentialsFromContext(t)
+
+ switch cmd {
+ case linux.IPC_RMID:
+ return 0, nil, t.IPCNamespace().MsgqueueRegistry().Remove(id, creds)
+ default:
+ return 0, nil, linuxerr.EINVAL
+ }
+}
diff --git a/pkg/sentry/syscalls/linux/sys_sem.go b/pkg/sentry/syscalls/linux/sys_sem.go
index 30919eb2f..f61cc466c 100644
--- a/pkg/sentry/syscalls/linux/sys_sem.go
+++ b/pkg/sentry/syscalls/linux/sys_sem.go
@@ -26,13 +26,14 @@ import (
"gvisor.dev/gvisor/pkg/sentry/fs"
"gvisor.dev/gvisor/pkg/sentry/kernel"
"gvisor.dev/gvisor/pkg/sentry/kernel/auth"
+ "gvisor.dev/gvisor/pkg/sentry/kernel/ipc"
)
const opsMax = 500 // SEMOPM
// Semget handles: semget(key_t key, int nsems, int semflg)
func Semget(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- key := args[0].Int()
+ key := ipc.Key(args[0].Int())
nsems := args[1].Int()
flag := args[2].Int()
@@ -46,7 +47,7 @@ func Semget(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscal
if err != nil {
return 0, nil, err
}
- return uintptr(set.ID), nil, nil
+ return uintptr(set.ID()), nil, nil
}
// Semtimedop handles: semop(int semid, struct sembuf *sops, size_t nsops, const struct timespec *timeout)
@@ -56,7 +57,7 @@ func Semtimedop(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Sy
return Semop(t, args)
}
- id := args[0].Int()
+ id := ipc.ID(args[0].Int())
sembufAddr := args[1].Pointer()
nsops := args[2].SizeT()
timespecAddr := args[3].Pointer()
@@ -91,7 +92,7 @@ func Semtimedop(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Sy
// Semop handles: semop(int semid, struct sembuf *sops, size_t nsops)
func Semop(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- id := args[0].Int()
+ id := ipc.ID(args[0].Int())
sembufAddr := args[1].Pointer()
nsops := args[2].SizeT()
@@ -109,7 +110,7 @@ func Semop(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscall
return 0, nil, semTimedOp(t, id, ops, false, time.Second)
}
-func semTimedOp(t *kernel.Task, id int32, ops []linux.Sembuf, haveTimeout bool, timeout time.Duration) error {
+func semTimedOp(t *kernel.Task, id ipc.ID, ops []linux.Sembuf, haveTimeout bool, timeout time.Duration) error {
set := t.IPCNamespace().SemaphoreRegistry().FindByID(id)
if set == nil {
@@ -131,7 +132,7 @@ func semTimedOp(t *kernel.Task, id int32, ops []linux.Sembuf, haveTimeout bool,
// Semctl handles: semctl(int semid, int semnum, int cmd, ...)
func Semctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- id := args[0].Int()
+ id := ipc.ID(args[0].Int())
num := args[1].Int()
cmd := args[2].Int()
@@ -210,7 +211,7 @@ func Semctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscal
case linux.SEM_STAT:
arg := args[3].Pointer()
// id is an index in SEM_STAT.
- semid, ds, err := semStat(t, id)
+ semid, ds, err := semStat(t, int32(id))
if err != nil {
return 0, nil, err
}
@@ -222,7 +223,7 @@ func Semctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscal
case linux.SEM_STAT_ANY:
arg := args[3].Pointer()
// id is an index in SEM_STAT.
- semid, ds, err := semStatAny(t, id)
+ semid, ds, err := semStatAny(t, int32(id))
if err != nil {
return 0, nil, err
}
@@ -236,13 +237,13 @@ func Semctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscal
}
}
-func remove(t *kernel.Task, id int32) error {
+func remove(t *kernel.Task, id ipc.ID) error {
r := t.IPCNamespace().SemaphoreRegistry()
creds := auth.CredentialsFromContext(t)
- return r.RemoveID(id, creds)
+ return r.Remove(id, creds)
}
-func ipcSet(t *kernel.Task, id int32, uid auth.UID, gid auth.GID, perms fs.FilePermissions) error {
+func ipcSet(t *kernel.Task, id ipc.ID, uid auth.UID, gid auth.GID, perms fs.FilePermissions) error {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -262,7 +263,7 @@ func ipcSet(t *kernel.Task, id int32, uid auth.UID, gid auth.GID, perms fs.FileP
return set.Change(t, creds, owner, perms)
}
-func ipcStat(t *kernel.Task, id int32) (*linux.SemidDS, error) {
+func ipcStat(t *kernel.Task, id ipc.ID) (*linux.SemidDS, error) {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -283,7 +284,7 @@ func semStat(t *kernel.Task, index int32) (int32, *linux.SemidDS, error) {
if err != nil {
return 0, ds, err
}
- return set.ID, ds, nil
+ return int32(set.ID()), ds, nil
}
func semStatAny(t *kernel.Task, index int32) (int32, *linux.SemidDS, error) {
@@ -296,10 +297,10 @@ func semStatAny(t *kernel.Task, index int32) (int32, *linux.SemidDS, error) {
if err != nil {
return 0, ds, err
}
- return set.ID, ds, nil
+ return int32(set.ID()), ds, nil
}
-func setVal(t *kernel.Task, id int32, num int32, val int16) error {
+func setVal(t *kernel.Task, id ipc.ID, num int32, val int16) error {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -310,7 +311,7 @@ func setVal(t *kernel.Task, id int32, num int32, val int16) error {
return set.SetVal(t, num, val, creds, int32(pid))
}
-func setValAll(t *kernel.Task, id int32, array hostarch.Addr) error {
+func setValAll(t *kernel.Task, id ipc.ID, array hostarch.Addr) error {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -325,7 +326,7 @@ func setValAll(t *kernel.Task, id int32, array hostarch.Addr) error {
return set.SetValAll(t, vals, creds, int32(pid))
}
-func getVal(t *kernel.Task, id int32, num int32) (int16, error) {
+func getVal(t *kernel.Task, id ipc.ID, num int32) (int16, error) {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -335,7 +336,7 @@ func getVal(t *kernel.Task, id int32, num int32) (int16, error) {
return set.GetVal(num, creds)
}
-func getValAll(t *kernel.Task, id int32, array hostarch.Addr) error {
+func getValAll(t *kernel.Task, id ipc.ID, array hostarch.Addr) error {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -350,7 +351,7 @@ func getValAll(t *kernel.Task, id int32, array hostarch.Addr) error {
return err
}
-func getPID(t *kernel.Task, id int32, num int32) (int32, error) {
+func getPID(t *kernel.Task, id ipc.ID, num int32) (int32, error) {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -369,7 +370,7 @@ func getPID(t *kernel.Task, id int32, num int32) (int32, error) {
return int32(tg.ID()), nil
}
-func getZCnt(t *kernel.Task, id int32, num int32) (uint16, error) {
+func getZCnt(t *kernel.Task, id ipc.ID, num int32) (uint16, error) {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
@@ -379,7 +380,7 @@ func getZCnt(t *kernel.Task, id int32, num int32) (uint16, error) {
return set.CountZeroWaiters(num, creds)
}
-func getNCnt(t *kernel.Task, id int32, num int32) (uint16, error) {
+func getNCnt(t *kernel.Task, id ipc.ID, num int32) (uint16, error) {
r := t.IPCNamespace().SemaphoreRegistry()
set := r.FindByID(id)
if set == nil {
diff --git a/pkg/sentry/syscalls/linux/sys_shm.go b/pkg/sentry/syscalls/linux/sys_shm.go
index 3e3a952ce..840540506 100644
--- a/pkg/sentry/syscalls/linux/sys_shm.go
+++ b/pkg/sentry/syscalls/linux/sys_shm.go
@@ -19,12 +19,13 @@ import (
"gvisor.dev/gvisor/pkg/errors/linuxerr"
"gvisor.dev/gvisor/pkg/sentry/arch"
"gvisor.dev/gvisor/pkg/sentry/kernel"
+ "gvisor.dev/gvisor/pkg/sentry/kernel/ipc"
"gvisor.dev/gvisor/pkg/sentry/kernel/shm"
)
// Shmget implements shmget(2).
func Shmget(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- key := shm.Key(args[0].Int())
+ key := ipc.Key(args[0].Int())
size := uint64(args[1].SizeT())
flag := args[2].Int()
@@ -40,13 +41,13 @@ func Shmget(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscal
return 0, nil, err
}
defer segment.DecRef(t)
- return uintptr(segment.ID), nil, nil
+ return uintptr(segment.ID()), nil, nil
}
// findSegment retrives a shm segment by the given id.
//
// findSegment returns a reference on Shm.
-func findSegment(t *kernel.Task, id shm.ID) (*shm.Shm, error) {
+func findSegment(t *kernel.Task, id ipc.ID) (*shm.Shm, error) {
r := t.IPCNamespace().ShmRegistry()
segment := r.FindByID(id)
if segment == nil {
@@ -58,7 +59,7 @@ func findSegment(t *kernel.Task, id shm.ID) (*shm.Shm, error) {
// Shmat implements shmat(2).
func Shmat(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- id := shm.ID(args[0].Int())
+ id := ipc.ID(args[0].Int())
addr := args[1].Pointer()
flag := args[2].Int()
@@ -89,7 +90,7 @@ func Shmdt(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.Syscall
// Shmctl implements shmctl(2).
func Shmctl(t *kernel.Task, args arch.SyscallArguments) (uintptr, *kernel.SyscallControl, error) {
- id := shm.ID(args[0].Int())
+ id := ipc.ID(args[0].Int())
cmd := args[1].Int()
buf := args[2].Pointer()