From 16d25c972c7d66e8f788c853519788f6bffc1bd2 Mon Sep 17 00:00:00 2001 From: "Zyad A. Ali" Date: Mon, 31 May 2021 21:15:28 +0200 Subject: Use syserror.ENOSPC for system-wide semaphore limits. semget(2) man page specifies that ENOSPC should be used if "the system limit for the maximum number of semaphore sets (SEMMNI), or the system wide maximum number of semaphores (SEMMNS), would be exceeded." --- pkg/sentry/kernel/semaphore/semaphore.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pkg/sentry/kernel/semaphore/semaphore.go b/pkg/sentry/kernel/semaphore/semaphore.go index 1d9edf118..47bb66b42 100644 --- a/pkg/sentry/kernel/semaphore/semaphore.go +++ b/pkg/sentry/kernel/semaphore/semaphore.go @@ -171,10 +171,10 @@ func (r *Registry) FindOrCreate(ctx context.Context, key, nsems int32, mode linu // Map semaphores and map indexes in a registry are of the same size, // check map semaphores only here for the system limit. if len(r.semaphores) >= setsMax { - return nil, syserror.EINVAL + return nil, syserror.ENOSPC } if r.totalSems() > int(semsTotalMax-nsems) { - return nil, syserror.EINVAL + return nil, syserror.ENOSPC } // Finally create a new set. -- cgit v1.2.3 From 69e3476ad5247a11f4b93e29607bb7c1513d3cc4 Mon Sep 17 00:00:00 2001 From: "Zyad A. Ali" Date: Tue, 1 Jun 2021 20:17:06 +0200 Subject: Test system-wide semaphore limits. --- test/syscalls/linux/semaphore.cc | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/test/syscalls/linux/semaphore.cc b/test/syscalls/linux/semaphore.cc index 2ce8f836c..54cbda19d 100644 --- a/test/syscalls/linux/semaphore.cc +++ b/test/syscalls/linux/semaphore.cc @@ -22,12 +22,12 @@ #include #include -#include "gmock/gmock.h" -#include "gtest/gtest.h" #include "absl/base/macros.h" #include "absl/memory/memory.h" #include "absl/synchronization/mutex.h" #include "absl/time/clock.h" +#include "gmock/gmock.h" +#include "gtest/gtest.h" #include "test/util/capability_util.h" #include "test/util/test_util.h" #include "test/util/thread_util.h" @@ -49,6 +49,9 @@ constexpr int kSemAem = 32767; class AutoSem { public: + // Creates a new private semaphore. + AutoSem() : id_(semget(IPC_PRIVATE, 1, 0)) {} + explicit AutoSem(int id) : id_(id) {} ~AutoSem() { if (id_ >= 0) { @@ -101,6 +104,17 @@ TEST(SemaphoreTest, SemGet) { EXPECT_NE(sem3.get(), sem2.get()); } +// Tests system-wide limits for semget. +TEST(SemaphoreTest, SemGetSystemLimits) { + // Exceed number of semaphores per set. + EXPECT_THAT(semget(IPC_PRIVATE, kSemMsl + 1, 0), + SyscallFailsWithErrno(EINVAL)); + + // Exceed system-wide limit for semaphore sets by 1. + AutoSem sems[kSemMni]; + EXPECT_THAT(semget(IPC_PRIVATE, 1, 0), SyscallFailsWithErrno(ENOSPC)); +} + // Tests simple operations that shouldn't block in a single-thread. TEST(SemaphoreTest, SemOpSingleNoBlock) { AutoSem sem(semget(IPC_PRIVATE, 1, 0600 | IPC_CREAT)); -- cgit v1.2.3