diff options
Diffstat (limited to 'test/syscalls/linux')
27 files changed, 184 insertions, 147 deletions
diff --git a/test/syscalls/linux/BUILD b/test/syscalls/linux/BUILD index 94a582256..b07f556de 100644 --- a/test/syscalls/linux/BUILD +++ b/test/syscalls/linux/BUILD @@ -3710,6 +3710,7 @@ cc_binary( deps = [ ":socket_test_util", "//test/util:file_descriptor", + "@com_google_absl//absl/strings", "@com_google_absl//absl/time", gtest, "//test/util:posix_error", diff --git a/test/syscalls/linux/chdir.cc b/test/syscalls/linux/chdir.cc index 3182c228b..3c64b9eab 100644 --- a/test/syscalls/linux/chdir.cc +++ b/test/syscalls/linux/chdir.cc @@ -41,8 +41,8 @@ TEST(ChdirTest, Success) { TEST(ChdirTest, PermissionDenied) { // Drop capabilities that allow us to override directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto temp_dir = ASSERT_NO_ERRNO_AND_VALUE( TempPath::CreateDirWith(GetAbsoluteTestTmpdir(), 0666 /* mode */)); diff --git a/test/syscalls/linux/chmod.cc b/test/syscalls/linux/chmod.cc index 4a5ea84d4..dd82c5fb1 100644 --- a/test/syscalls/linux/chmod.cc +++ b/test/syscalls/linux/chmod.cc @@ -33,7 +33,7 @@ namespace { TEST(ChmodTest, ChmodFileSucceeds) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFile()); @@ -43,8 +43,8 @@ TEST(ChmodTest, ChmodFileSucceeds) { TEST(ChmodTest, ChmodDirSucceeds) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); const std::string fileInDir = NewTempAbsPathInDir(dir.path()); @@ -55,7 +55,7 @@ TEST(ChmodTest, ChmodDirSucceeds) { TEST(ChmodTest, FchmodFileSucceeds) { // Drop capabilities that allow us to file directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileMode(0666)); int fd; @@ -72,8 +72,8 @@ TEST(ChmodTest, FchmodFileSucceeds) { TEST(ChmodTest, FchmodDirSucceeds) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); int fd; @@ -118,7 +118,7 @@ TEST(ChmodTest, FchmodDirWithOpath) { TEST(ChmodTest, FchmodatWithOpath) { SKIP_IF(IsRunningWithVFS1()); // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto temp_file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFile()); @@ -140,7 +140,7 @@ TEST(ChmodTest, FchmodatNotDir) { TEST(ChmodTest, FchmodatFileAbsolutePath) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFile()); @@ -150,8 +150,8 @@ TEST(ChmodTest, FchmodatFileAbsolutePath) { TEST(ChmodTest, FchmodatDirAbsolutePath) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); @@ -167,7 +167,7 @@ TEST(ChmodTest, FchmodatDirAbsolutePath) { TEST(ChmodTest, FchmodatFile) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto temp_file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFile()); @@ -188,8 +188,8 @@ TEST(ChmodTest, FchmodatFile) { TEST(ChmodTest, FchmodatDir) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); @@ -227,8 +227,8 @@ TEST(ChmodTest, ChmodDowngradeWritability) { TEST(ChmodTest, ChmodFileToNoPermissionsSucceeds) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileMode(0666)); @@ -254,8 +254,8 @@ TEST(ChmodTest, FchmodDowngradeWritability) { TEST(ChmodTest, FchmodFileToNoPermissionsSucceeds) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileMode(0666)); diff --git a/test/syscalls/linux/chown.cc b/test/syscalls/linux/chown.cc index ff0d39343..b0c1b6f4a 100644 --- a/test/syscalls/linux/chown.cc +++ b/test/syscalls/linux/chown.cc @@ -91,9 +91,7 @@ using Chown = class ChownParamTest : public ::testing::TestWithParam<Chown> {}; TEST_P(ChownParamTest, ChownFileSucceeds) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_CHOWN))) { - ASSERT_NO_ERRNO(SetCapability(CAP_CHOWN, false)); - } + AutoCapability cap(CAP_CHOWN, false); const auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFile()); @@ -135,9 +133,7 @@ TEST_P(ChownParamTest, ChownFilePermissionDenied) { // thread won't be able to open some log files after the test ends. ScopedThread([&] { // Drop privileges. - if (HaveCapability(CAP_CHOWN).ValueOrDie()) { - EXPECT_NO_ERRNO(SetCapability(CAP_CHOWN, false)); - } + AutoCapability cap(CAP_CHOWN, false); // Change EUID and EGID. // diff --git a/test/syscalls/linux/epoll.cc b/test/syscalls/linux/epoll.cc index b180f633c..af3d27894 100644 --- a/test/syscalls/linux/epoll.cc +++ b/test/syscalls/linux/epoll.cc @@ -39,6 +39,15 @@ namespace { constexpr int kFDsPerEpoll = 3; constexpr uint64_t kMagicConstant = 0x0102030405060708; +#ifndef SYS_epoll_pwait2 +#define SYS_epoll_pwait2 441 +#endif + +int epoll_pwait2(int fd, struct epoll_event* events, int maxevents, + const struct timespec* timeout, const sigset_t* sigset) { + return syscall(SYS_epoll_pwait2, fd, events, maxevents, timeout, sigset); +} + TEST(EpollTest, AllWritable) { auto epollfd = ASSERT_NO_ERRNO_AND_VALUE(NewEpollFD()); std::vector<FileDescriptor> eventfds; @@ -144,6 +153,50 @@ TEST(EpollTest, Timeout) { EXPECT_GT(ms_elapsed(begin, end), kTimeoutMs - 1); } +TEST(EpollTest, EpollPwait2Timeout) { + auto epollfd = ASSERT_NO_ERRNO_AND_VALUE(NewEpollFD()); + // 200 milliseconds. + constexpr int kTimeoutNs = 200000000; + struct timespec timeout; + timeout.tv_sec = 0; + timeout.tv_nsec = 0; + struct timespec begin; + struct timespec end; + struct epoll_event result[kFDsPerEpoll]; + + std::vector<FileDescriptor> eventfds; + for (int i = 0; i < kFDsPerEpoll; i++) { + eventfds.push_back(ASSERT_NO_ERRNO_AND_VALUE(NewEventFD())); + ASSERT_NO_ERRNO(RegisterEpollFD(epollfd.get(), eventfds[i].get(), EPOLLIN, + kMagicConstant + i)); + } + + // Pass valid arguments so that the syscall won't be blocked indefinitely + // nor return errno EINVAL. + // + // The syscall returns immediately when timeout is zero, + // even if no events are available. + SKIP_IF(!IsRunningOnGvisor() && + epoll_pwait2(epollfd.get(), result, kFDsPerEpoll, &timeout, nullptr) < + 0 && + errno == ENOSYS); + + { + const DisableSave ds; // Timing-related. + EXPECT_THAT(clock_gettime(CLOCK_MONOTONIC, &begin), SyscallSucceeds()); + + timeout.tv_nsec = kTimeoutNs; + ASSERT_THAT(RetryEINTR(epoll_pwait2)(epollfd.get(), result, kFDsPerEpoll, + &timeout, nullptr), + SyscallSucceedsWithValue(0)); + EXPECT_THAT(clock_gettime(CLOCK_MONOTONIC, &end), SyscallSucceeds()); + } + + // Check the lower bound on the timeout. Checking for an upper bound is + // fragile because Linux can overrun the timeout due to scheduling delays. + EXPECT_GT(ns_elapsed(begin, end), kTimeoutNs - 1); +} + void* writer(void* arg) { int fd = *reinterpret_cast<int*>(arg); uint64_t tmp = 1; diff --git a/test/syscalls/linux/fchdir.cc b/test/syscalls/linux/fchdir.cc index c6675802d..0383f3f85 100644 --- a/test/syscalls/linux/fchdir.cc +++ b/test/syscalls/linux/fchdir.cc @@ -46,8 +46,8 @@ TEST(FchdirTest, InvalidFD) { TEST(FchdirTest, PermissionDenied) { // Drop capabilities that allow us to override directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto temp_dir = ASSERT_NO_ERRNO_AND_VALUE( TempPath::CreateDirWith(GetAbsoluteTestTmpdir(), 0666 /* mode */)); diff --git a/test/syscalls/linux/mkdir.cc b/test/syscalls/linux/mkdir.cc index 11fbfa5c5..36504fe6d 100644 --- a/test/syscalls/linux/mkdir.cc +++ b/test/syscalls/linux/mkdir.cc @@ -72,8 +72,8 @@ TEST_F(MkdirTest, HonorsUmask2) { TEST_F(MkdirTest, FailsOnDirWithoutWritePerms) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); ASSERT_THAT(mkdir(dirname_.c_str(), 0555), SyscallSucceeds()); auto dir = JoinPath(dirname_.c_str(), "foo"); @@ -84,8 +84,8 @@ TEST_F(MkdirTest, FailsOnDirWithoutWritePerms) { TEST_F(MkdirTest, DirAlreadyExists) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); ASSERT_THAT(mkdir(dirname_.c_str(), 0777), SyscallSucceeds()); auto dir = JoinPath(dirname_.c_str(), "foo"); diff --git a/test/syscalls/linux/mlock.cc b/test/syscalls/linux/mlock.cc index 78ac96bed..dfa5b7133 100644 --- a/test/syscalls/linux/mlock.cc +++ b/test/syscalls/linux/mlock.cc @@ -114,9 +114,7 @@ TEST(MlockTest, Fork) { } TEST(MlockTest, RlimitMemlockZero) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE(ScopedSetSoftRlimit(RLIMIT_MEMLOCK, 0)); auto const mapping = ASSERT_NO_ERRNO_AND_VALUE( @@ -127,9 +125,7 @@ TEST(MlockTest, RlimitMemlockZero) { } TEST(MlockTest, RlimitMemlockInsufficient) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE(ScopedSetSoftRlimit(RLIMIT_MEMLOCK, kPageSize)); auto const mapping = ASSERT_NO_ERRNO_AND_VALUE( @@ -255,9 +251,7 @@ TEST(MapLockedTest, Basic) { } TEST(MapLockedTest, RlimitMemlockZero) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE(ScopedSetSoftRlimit(RLIMIT_MEMLOCK, 0)); EXPECT_THAT( @@ -266,9 +260,7 @@ TEST(MapLockedTest, RlimitMemlockZero) { } TEST(MapLockedTest, RlimitMemlockInsufficient) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE(ScopedSetSoftRlimit(RLIMIT_MEMLOCK, kPageSize)); EXPECT_THAT( @@ -298,9 +290,7 @@ TEST(MremapLockedTest, RlimitMemlockZero) { MmapAnon(kPageSize, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_LOCKED)); EXPECT_TRUE(IsPageMlocked(mapping.addr())); - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE(ScopedSetSoftRlimit(RLIMIT_MEMLOCK, 0)); void* addr = mremap(mapping.ptr(), mapping.len(), 2 * mapping.len(), @@ -315,9 +305,7 @@ TEST(MremapLockedTest, RlimitMemlockInsufficient) { MmapAnon(kPageSize, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_LOCKED)); EXPECT_TRUE(IsPageMlocked(mapping.addr())); - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_IPC_LOCK))) { - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_LOCK, false)); - } + AutoCapability cap(CAP_IPC_LOCK, false); Cleanup reset_rlimit = ASSERT_NO_ERRNO_AND_VALUE( ScopedSetSoftRlimit(RLIMIT_MEMLOCK, mapping.len())); void* addr = mremap(mapping.ptr(), mapping.len(), 2 * mapping.len(), diff --git a/test/syscalls/linux/open.cc b/test/syscalls/linux/open.cc index 4697c404c..ab9d19fef 100644 --- a/test/syscalls/linux/open.cc +++ b/test/syscalls/linux/open.cc @@ -433,7 +433,7 @@ TEST_F(OpenTest, CanTruncateReadOnly) { // O_TRUNC should fail. TEST_F(OpenTest, CanTruncateReadOnlyNoWritePermission) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); const DisableSave ds; // Permissions are dropped. ASSERT_THAT(chmod(test_file_name_.c_str(), S_IRUSR | S_IRGRP), @@ -473,8 +473,8 @@ TEST_F(OpenTest, CanTruncateWriteOnlyNoReadPermission) { } TEST_F(OpenTest, CanTruncateWithStrangePermissions) { - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); const DisableSave ds; // Permissions are dropped. std::string path = NewTempAbsPath(); // Create a file without user permissions. @@ -510,8 +510,8 @@ TEST_F(OpenTest, OpenWithStrangeFlags) { TEST_F(OpenTest, OpenWithOpath) { SKIP_IF(IsRunningWithVFS1()); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); const DisableSave ds; // Permissions are dropped. std::string path = NewTempAbsPath(); diff --git a/test/syscalls/linux/open_create.cc b/test/syscalls/linux/open_create.cc index 43d446926..177bda54d 100644 --- a/test/syscalls/linux/open_create.cc +++ b/test/syscalls/linux/open_create.cc @@ -93,7 +93,8 @@ TEST(CreateTest, CreatFileWithOTruncAndReadOnly) { TEST(CreateTest, CreateFailsOnDirWithoutWritePerms) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // always override directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); + auto parent = ASSERT_NO_ERRNO_AND_VALUE( TempPath::CreateDirWith(GetAbsoluteTestTmpdir(), 0555)); auto file = JoinPath(parent.path(), "foo"); @@ -123,8 +124,8 @@ TEST(CreateTest, ChmodReadToWriteBetweenOpens) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // override file read/write permissions. CAP_DAC_READ_SEARCH needs to be // cleared for the same reason. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); const TempPath file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileMode(0400)); @@ -152,7 +153,7 @@ TEST(CreateTest, ChmodReadToWriteBetweenOpens) { TEST(CreateTest, ChmodWriteToReadBetweenOpens) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // override file read/write permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); const TempPath file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileMode(0200)); @@ -186,8 +187,8 @@ TEST(CreateTest, CreateWithReadFlagNotAllowedByMode) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // override file read/write permissions. CAP_DAC_READ_SEARCH needs to be // cleared for the same reason. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); // Create and open a file with read flag but without read permissions. const std::string path = NewTempAbsPath(); @@ -212,7 +213,7 @@ TEST(CreateTest, CreateWithWriteFlagNotAllowedByMode) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // override file read/write permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); // Create and open a file with write flag but without write permissions. const std::string path = NewTempAbsPath(); diff --git a/test/syscalls/linux/prctl.cc b/test/syscalls/linux/prctl.cc index f675dc430..19a57d353 100644 --- a/test/syscalls/linux/prctl.cc +++ b/test/syscalls/linux/prctl.cc @@ -184,10 +184,8 @@ TEST(PrctlTest, PDeathSig) { // This test is to validate that calling prctl with PR_SET_MM without the // CAP_SYS_RESOURCE returns EPERM. TEST(PrctlTest, InvalidPrSetMM) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_SYS_RESOURCE))) { - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_RESOURCE, - false)); // Drop capability to test below. - } + // Drop capability to test below. + AutoCapability cap(CAP_SYS_RESOURCE, false); ASSERT_THAT(prctl(PR_SET_MM, 0, 0, 0, 0), SyscallFailsWithErrno(EPERM)); } diff --git a/test/syscalls/linux/proc.cc b/test/syscalls/linux/proc.cc index 9e48fbca5..143075e2d 100644 --- a/test/syscalls/linux/proc.cc +++ b/test/syscalls/linux/proc.cc @@ -1849,8 +1849,8 @@ TEST(ProcPidSymlink, SubprocessRunning) { } TEST(ProcPidSymlink, SubprocessZombied) { - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); char buf[1]; @@ -2252,7 +2252,7 @@ TEST(ProcTask, VerifyTaskDir) { TEST(ProcTask, TaskDirCannotBeDeleted) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); EXPECT_THAT(rmdir("/proc/self/task"), SyscallFails()); EXPECT_THAT(rmdir(absl::StrCat("/proc/self/task/", getpid()).c_str()), @@ -2698,6 +2698,14 @@ TEST(Proc, Statfs) { EXPECT_EQ(st.f_namelen, NAME_MAX); } +// Tests that /proc/[pid]/fd/[num] can resolve to a path inside /proc. +TEST(Proc, ResolveSymlinkToProc) { + const auto proc = ASSERT_NO_ERRNO_AND_VALUE(Open("/proc/self/cmdline", 0)); + const auto path = JoinPath("/proc/self/fd/", absl::StrCat(proc.get())); + const auto target = ASSERT_NO_ERRNO_AND_VALUE(ReadLink(path)); + EXPECT_EQ(target, JoinPath("/proc/", absl::StrCat(getpid()), "/cmdline")); +} + } // namespace } // namespace testing } // namespace gvisor diff --git a/test/syscalls/linux/ptrace.cc b/test/syscalls/linux/ptrace.cc index 2d9fec371..d519b65e6 100644 --- a/test/syscalls/linux/ptrace.cc +++ b/test/syscalls/linux/ptrace.cc @@ -175,7 +175,7 @@ TEST(PtraceTest, AttachSameThreadGroup) { TEST(PtraceTest, TraceParentNotAllowed) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) < 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); pid_t const child_pid = fork(); if (child_pid == 0) { @@ -193,7 +193,7 @@ TEST(PtraceTest, TraceParentNotAllowed) { TEST(PtraceTest, TraceNonDescendantNotAllowed) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) < 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); pid_t const tracee_pid = fork(); if (tracee_pid == 0) { @@ -259,7 +259,7 @@ TEST(PtraceTest, TraceNonDescendantWithCapabilityAllowed) { TEST(PtraceTest, TraceDescendantsAllowed) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) > 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use socket pair to communicate tids to this process from its grandchild. int sockets[2]; @@ -346,7 +346,7 @@ TEST(PtraceTest, PrctlSetPtracerInvalidPID) { TEST(PtraceTest, PrctlSetPtracerPID) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -410,7 +410,7 @@ TEST(PtraceTest, PrctlSetPtracerPID) { TEST(PtraceTest, PrctlSetPtracerAny) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -475,7 +475,7 @@ TEST(PtraceTest, PrctlSetPtracerAny) { TEST(PtraceTest, PrctlClearPtracer) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -543,7 +543,7 @@ TEST(PtraceTest, PrctlClearPtracer) { TEST(PtraceTest, PrctlReplacePtracer) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); pid_t const unused_pid = fork(); if (unused_pid == 0) { @@ -633,7 +633,7 @@ TEST(PtraceTest, PrctlReplacePtracer) { // thread group leader is still around. TEST(PtraceTest, PrctlSetPtracerPersistsPastTraceeThreadExit) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -703,7 +703,7 @@ TEST(PtraceTest, PrctlSetPtracerPersistsPastTraceeThreadExit) { // even if the tracee thread is terminated. TEST(PtraceTest, PrctlSetPtracerPersistsPastLeaderExec) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -770,7 +770,7 @@ TEST(PtraceTest, PrctlSetPtracerPersistsPastLeaderExec) { // exec. TEST(PtraceTest, PrctlSetPtracerDoesNotPersistPastNonLeaderExec) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -904,7 +904,7 @@ TEST(PtraceTest, PrctlSetPtracerDoesNotPersistPastTracerThreadExit) { [[noreturn]] void RunPrctlSetPtracerDoesNotPersistPastTracerThreadExit( int tracee_tid, int fd) { - TEST_PCHECK(SetCapability(CAP_SYS_PTRACE, false).ok()); + AutoCapability cap(CAP_SYS_PTRACE, false); ScopedThread t([fd] { pid_t const tracer_tid = gettid(); @@ -1033,7 +1033,7 @@ TEST(PtraceTest, PrctlSetPtracerRespectsTracerThreadID) { // attached. TEST(PtraceTest, PrctlClearPtracerDoesNotAffectCurrentTracer) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Use sockets to synchronize between tracer and tracee. int sockets[2]; @@ -1118,7 +1118,7 @@ TEST(PtraceTest, PrctlClearPtracerDoesNotAffectCurrentTracer) { TEST(PtraceTest, PrctlNotInherited) { SKIP_IF(ASSERT_NO_ERRNO_AND_VALUE(YamaPtraceScope()) != 1); - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); // Allow any ptracer. This should not affect the child processes. ASSERT_THAT(prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY), SyscallSucceeds()); @@ -2302,7 +2302,7 @@ TEST(PtraceTest, SetYAMAPtraceScope) { EXPECT_STREQ(buf.data(), "0\n"); // Test that a child can attach to its parent when ptrace_scope is 0. - ASSERT_NO_ERRNO(SetCapability(CAP_SYS_PTRACE, false)); + AutoCapability cap(CAP_SYS_PTRACE, false); pid_t const child_pid = fork(); if (child_pid == 0) { TEST_PCHECK(CheckPtraceAttach(getppid()) == 0); diff --git a/test/syscalls/linux/raw_socket_hdrincl.cc b/test/syscalls/linux/raw_socket_hdrincl.cc index 2f25aceb2..8b3d02d97 100644 --- a/test/syscalls/linux/raw_socket_hdrincl.cc +++ b/test/syscalls/linux/raw_socket_hdrincl.cc @@ -177,10 +177,8 @@ TEST_F(RawHDRINCL, ConnectToLoopback) { SyscallSucceeds()); } -TEST_F(RawHDRINCL, SendWithoutConnectSucceeds) { - // FIXME(gvisor.dev/issue/3159): Test currently flaky. - SKIP_IF(true); - +// FIXME(gvisor.dev/issue/3159): Test currently flaky. +TEST_F(RawHDRINCL, DISABLED_SendWithoutConnectSucceeds) { struct iphdr hdr = LoopbackHeader(); ASSERT_THAT(send(socket_, &hdr, sizeof(hdr), 0), SyscallSucceedsWithValue(sizeof(hdr))); diff --git a/test/syscalls/linux/rename.cc b/test/syscalls/linux/rename.cc index b1a813de0..76a8da65f 100644 --- a/test/syscalls/linux/rename.cc +++ b/test/syscalls/linux/rename.cc @@ -259,8 +259,8 @@ TEST(RenameTest, DirectoryDoesNotOverwriteNonemptyDirectory) { TEST(RenameTest, FailsWhenOldParentNotWritable) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); auto f1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileIn(dir1.path())); @@ -275,8 +275,8 @@ TEST(RenameTest, FailsWhenOldParentNotWritable) { TEST(RenameTest, FailsWhenNewParentNotWritable) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); auto f1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileIn(dir1.path())); @@ -293,8 +293,8 @@ TEST(RenameTest, FailsWhenNewParentNotWritable) { // to overwrite. TEST(RenameTest, OverwriteFailsWhenNewParentNotWritable) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); auto f1 = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileIn(dir1.path())); @@ -312,8 +312,8 @@ TEST(RenameTest, OverwriteFailsWhenNewParentNotWritable) { // because the user cannot determine if source exists. TEST(RenameTest, FileDoesNotExistWhenNewParentNotExecutable) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); // No execute permission. auto dir = ASSERT_NO_ERRNO_AND_VALUE( diff --git a/test/syscalls/linux/rlimits.cc b/test/syscalls/linux/rlimits.cc index 860f0f688..d31a2a880 100644 --- a/test/syscalls/linux/rlimits.cc +++ b/test/syscalls/linux/rlimits.cc @@ -41,9 +41,7 @@ TEST(RlimitTest, SetRlimitHigher) { TEST(RlimitTest, UnprivilegedSetRlimit) { // Drop privileges if necessary. - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_SYS_RESOURCE))) { - EXPECT_NO_ERRNO(SetCapability(CAP_SYS_RESOURCE, false)); - } + AutoCapability cap(CAP_SYS_RESOURCE, false); struct rlimit rl = {}; rl.rlim_cur = 1000; diff --git a/test/syscalls/linux/semaphore.cc b/test/syscalls/linux/semaphore.cc index 207377efb..2ce8f836c 100644 --- a/test/syscalls/linux/semaphore.cc +++ b/test/syscalls/linux/semaphore.cc @@ -535,7 +535,7 @@ TEST(SemaphoreTest, SemCtlGetPidFork) { TEST(SemaphoreTest, SemIpcSet) { // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); AutoSem sem(semget(IPC_PRIVATE, 1, 0600 | IPC_CREAT)); ASSERT_THAT(sem.get(), SyscallSucceeds()); @@ -560,7 +560,7 @@ TEST(SemaphoreTest, SemIpcSet) { TEST(SemaphoreTest, SemCtlIpcStat) { // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); const uid_t kUid = getuid(); const gid_t kGid = getgid(); time_t start_time = time(nullptr); @@ -635,7 +635,7 @@ PosixErrorOr<int> WaitSemctl(int semid, int target, int cmd) { TEST(SemaphoreTest, SemopGetzcnt) { // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); // Create a write only semaphore set. AutoSem sem(semget(IPC_PRIVATE, 1, 0200 | IPC_CREAT)); ASSERT_THAT(sem.get(), SyscallSucceeds()); @@ -743,7 +743,7 @@ TEST(SemaphoreTest, SemopGetzcntOnSignal) { TEST(SemaphoreTest, SemopGetncnt) { // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); // Create a write only semaphore set. AutoSem sem(semget(IPC_PRIVATE, 1, 0200 | IPC_CREAT)); ASSERT_THAT(sem.get(), SyscallSucceeds()); @@ -853,7 +853,7 @@ TEST(SemaphoreTest, IpcInfo) { std::set<int> sem_ids; struct seminfo info; // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); for (int i = 0; i < kLoops; i++) { AutoSem sem(semget(IPC_PRIVATE, 1, 0600 | IPC_CREAT)); ASSERT_THAT(sem.get(), SyscallSucceeds()); @@ -923,7 +923,7 @@ TEST(SemaphoreTest, SemInfo) { std::set<int> sem_ids; struct seminfo info; // Drop CAP_IPC_OWNER which allows us to bypass semaphore permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_IPC_OWNER, false)); + AutoCapability cap(CAP_IPC_OWNER, false); for (int i = 0; i < kLoops; i++) { AutoSem sem(semget(IPC_PRIVATE, kSemSetSize, 0600 | IPC_CREAT)); ASSERT_THAT(sem.get(), SyscallSucceeds()); diff --git a/test/syscalls/linux/socket_capability.cc b/test/syscalls/linux/socket_capability.cc index 84b5b2b21..f75482aba 100644 --- a/test/syscalls/linux/socket_capability.cc +++ b/test/syscalls/linux/socket_capability.cc @@ -40,7 +40,7 @@ TEST(SocketTest, UnixConnectNeedsWritePerm) { // Drop capabilites that allow us to override permision checks. Otherwise if // the test is run as root, the connect below will bypass permission checks // and succeed unexpectedly. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); // Connect should fail without write perms. ASSERT_THAT(chmod(addr.sun_path, 0500), SyscallSucceeds()); diff --git a/test/syscalls/linux/sticky.cc b/test/syscalls/linux/sticky.cc index 4afed6d08..5a2841899 100644 --- a/test/syscalls/linux/sticky.cc +++ b/test/syscalls/linux/sticky.cc @@ -56,9 +56,7 @@ TEST(StickyTest, StickyBitPermDenied) { // thread won't be able to open some log files after the test ends. ScopedThread([&] { // Drop privileges. - if (HaveCapability(CAP_FOWNER).ValueOrDie()) { - EXPECT_NO_ERRNO(SetCapability(CAP_FOWNER, false)); - } + AutoCapability cap(CAP_FOWNER, false); // Change EUID and EGID. EXPECT_THAT( @@ -98,9 +96,7 @@ TEST(StickyTest, StickyBitSameUID) { // thread won't be able to open some log files after the test ends. ScopedThread([&] { // Drop privileges. - if (HaveCapability(CAP_FOWNER).ValueOrDie()) { - EXPECT_NO_ERRNO(SetCapability(CAP_FOWNER, false)); - } + AutoCapability cap(CAP_FOWNER, false); // Change EGID. EXPECT_THAT( diff --git a/test/syscalls/linux/symlink.cc b/test/syscalls/linux/symlink.cc index 9f6c59446..fa6849f11 100644 --- a/test/syscalls/linux/symlink.cc +++ b/test/syscalls/linux/symlink.cc @@ -100,8 +100,8 @@ TEST(SymlinkTest, CanCreateSymlinkDir) { TEST(SymlinkTest, CannotCreateSymlinkInReadOnlyDir) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); const std::string olddir = NewTempAbsPath(); ASSERT_THAT(mkdir(olddir.c_str(), 0444), SyscallSucceeds()); @@ -250,8 +250,8 @@ TEST(SymlinkTest, PwriteToSymlink) { TEST(SymlinkTest, SymlinkAtDegradedPermissions) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileIn(dir.path())); @@ -301,8 +301,8 @@ TEST(SymlinkTest, ReadlinkAtDirWithOpath) { TEST(SymlinkTest, ReadlinkAtDegradedPermissions) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); const std::string oldpath = NewTempAbsPathInDir(dir.path()); diff --git a/test/syscalls/linux/tcp_socket.cc b/test/syscalls/linux/tcp_socket.cc index 011b60f0e..ef3452306 100644 --- a/test/syscalls/linux/tcp_socket.cc +++ b/test/syscalls/linux/tcp_socket.cc @@ -27,6 +27,7 @@ #include <vector> #include "gtest/gtest.h" +#include "absl/strings/str_split.h" #include "absl/time/clock.h" #include "absl/time/time.h" #include "test/syscalls/linux/socket_test_util.h" @@ -1144,6 +1145,17 @@ TEST_P(SimpleTcpSocketTest, SelfConnectSendRecv) { } TEST_P(SimpleTcpSocketTest, SelfConnectSend) { + // Ensure the write size is not larger than the write buffer. + size_t write_size = 512 << 10; // 512 KiB. + constexpr char kWMem[] = "/proc/sys/net/ipv4/tcp_wmem"; + std::string wmem = ASSERT_NO_ERRNO_AND_VALUE(GetContents(kWMem)); + std::vector<std::string> vals = absl::StrSplit(wmem, absl::ByAnyChar("\t ")); + size_t max_wmem; + ASSERT_TRUE(absl::SimpleAtoi(vals.back(), &max_wmem)); + if (write_size > max_wmem) { + write_size = max_wmem; + } + // Initialize address to the loopback one. sockaddr_storage addr = ASSERT_NO_ERRNO_AND_VALUE(InetLoopbackAddr(GetParam())); @@ -1164,7 +1176,7 @@ TEST_P(SimpleTcpSocketTest, SelfConnectSend) { ASSERT_THAT(RetryEINTR(connect)(s.get(), AsSockAddr(&addr), addrlen), SyscallSucceeds()); - std::vector<char> writebuf(512 << 10); // 512 KiB. + std::vector<char> writebuf(write_size); // Try to send the whole thing. int n; diff --git a/test/syscalls/linux/truncate.cc b/test/syscalls/linux/truncate.cc index 5db0b8276..0f08d9996 100644 --- a/test/syscalls/linux/truncate.cc +++ b/test/syscalls/linux/truncate.cc @@ -181,7 +181,7 @@ TEST(TruncateTest, FtruncateDir) { TEST(TruncateTest, TruncateNonWriteable) { // Make sure we don't have CAP_DAC_OVERRIDE, since that allows the user to // always override write permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); auto temp_file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileWith( GetAbsoluteTestTmpdir(), absl::string_view(), 0555 /* mode */)); EXPECT_THAT(truncate(temp_file.path().c_str(), 0), @@ -210,7 +210,7 @@ TEST(TruncateTest, FtruncateWithOpath) { // regardless of whether the file permissions allow writing. TEST(TruncateTest, FtruncateWithoutWritePermission) { // Drop capabilities that allow us to override file permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); + AutoCapability cap(CAP_DAC_OVERRIDE, false); // The only time we can open a file with flags forbidden by its permissions // is when we are creating the file. We cannot re-open with the same flags, diff --git a/test/syscalls/linux/tuntap.cc b/test/syscalls/linux/tuntap.cc index 6e3a00d2c..279fe342c 100644 --- a/test/syscalls/linux/tuntap.cc +++ b/test/syscalls/linux/tuntap.cc @@ -170,10 +170,10 @@ TEST(TuntapStaticTest, NetTunExists) { class TuntapTest : public ::testing::Test { protected: void SetUp() override { - have_net_admin_cap_ = + const bool have_net_admin_cap = ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_NET_ADMIN)); - if (have_net_admin_cap_ && !IsRunningOnGvisor()) { + if (have_net_admin_cap && !IsRunningOnGvisor()) { // gVisor always creates enabled/up'd interfaces, while Linux does not (as // observed in b/110961832). Some of the tests require the Linux stack to // notify the socket of any link-address-resolution failures. Those @@ -183,21 +183,12 @@ class TuntapTest : public ::testing::Test { ASSERT_NO_ERRNO(LinkChangeFlags(link.index, IFF_UP, IFF_UP)); } } - - void TearDown() override { - if (have_net_admin_cap_) { - // Bring back capability if we had dropped it in test case. - ASSERT_NO_ERRNO(SetCapability(CAP_NET_ADMIN, true)); - } - } - - bool have_net_admin_cap_; }; TEST_F(TuntapTest, CreateInterfaceNoCap) { SKIP_IF(!ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_NET_ADMIN))); - ASSERT_NO_ERRNO(SetCapability(CAP_NET_ADMIN, false)); + AutoCapability cap(CAP_NET_ADMIN, false); FileDescriptor fd = ASSERT_NO_ERRNO_AND_VALUE(Open(kDevNetTun, O_RDWR)); diff --git a/test/syscalls/linux/uname.cc b/test/syscalls/linux/uname.cc index d8824b171..759ea4f53 100644 --- a/test/syscalls/linux/uname.cc +++ b/test/syscalls/linux/uname.cc @@ -76,9 +76,7 @@ TEST(UnameTest, SetNames) { } TEST(UnameTest, UnprivilegedSetNames) { - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_SYS_ADMIN))) { - EXPECT_NO_ERRNO(SetCapability(CAP_SYS_ADMIN, false)); - } + AutoCapability cap(CAP_SYS_ADMIN, false); EXPECT_THAT(sethostname("", 0), SyscallFailsWithErrno(EPERM)); EXPECT_THAT(setdomainname("", 0), SyscallFailsWithErrno(EPERM)); diff --git a/test/syscalls/linux/unlink.cc b/test/syscalls/linux/unlink.cc index 7c301c305..75dcf4465 100644 --- a/test/syscalls/linux/unlink.cc +++ b/test/syscalls/linux/unlink.cc @@ -66,8 +66,8 @@ TEST(UnlinkTest, AtDir) { TEST(UnlinkTest, AtDirDegradedPermissions) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); @@ -86,8 +86,8 @@ TEST(UnlinkTest, AtDirDegradedPermissions) { // Files cannot be unlinked if the parent is not writable and executable. TEST(UnlinkTest, ParentDegradedPermissions) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); auto dir = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateDir()); auto file = ASSERT_NO_ERRNO_AND_VALUE(TempPath::CreateFileIn(dir.path())); diff --git a/test/syscalls/linux/utimes.cc b/test/syscalls/linux/utimes.cc index e647d2896..e711d6657 100644 --- a/test/syscalls/linux/utimes.cc +++ b/test/syscalls/linux/utimes.cc @@ -225,7 +225,8 @@ void TestUtimensat(int dirFd, std::string const& path) { EXPECT_GE(mtime3, before); EXPECT_LE(mtime3, after); - EXPECT_EQ(atime3, mtime3); + // TODO(b/187074006): atime/mtime may differ with local_gofer_uncached. + // EXPECT_EQ(atime3, mtime3); } TEST(UtimensatTest, OnAbsPath) { diff --git a/test/syscalls/linux/xattr.cc b/test/syscalls/linux/xattr.cc index dd8067807..c8a97df6b 100644 --- a/test/syscalls/linux/xattr.cc +++ b/test/syscalls/linux/xattr.cc @@ -109,8 +109,8 @@ TEST_F(XattrTest, XattrInvalidPrefix) { // the restore will fail to open it with r/w permissions. TEST_F(XattrTest, XattrReadOnly) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); const char* path = test_file_name_.c_str(); const char name[] = "user.test"; @@ -140,8 +140,8 @@ TEST_F(XattrTest, XattrReadOnly) { // the restore will fail to open it with r/w permissions. TEST_F(XattrTest, XattrWriteOnly) { // Drop capabilities that allow us to override file and directory permissions. - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_OVERRIDE, false)); - ASSERT_NO_ERRNO(SetCapability(CAP_DAC_READ_SEARCH, false)); + AutoCapability cap1(CAP_DAC_OVERRIDE, false); + AutoCapability cap2(CAP_DAC_READ_SEARCH, false); DisableSave ds; ASSERT_NO_ERRNO(testing::Chmod(test_file_name_, S_IWUSR)); @@ -632,7 +632,7 @@ TEST_F(XattrTest, TrustedNamespaceWithCapSysAdmin) { // Trusted namespace not supported in VFS1. SKIP_IF(IsRunningWithVFS1()); - // TODO(b/66162845): Only gVisor tmpfs currently supports trusted namespace. + // TODO(b/166162845): Only gVisor tmpfs currently supports trusted namespace. SKIP_IF(IsRunningOnGvisor() && !ASSERT_NO_ERRNO_AND_VALUE(IsTmpfs(test_file_name_))); @@ -680,9 +680,7 @@ TEST_F(XattrTest, TrustedNamespaceWithoutCapSysAdmin) { !ASSERT_NO_ERRNO_AND_VALUE(IsTmpfs(test_file_name_))); // Drop CAP_SYS_ADMIN if we have it. - if (ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_SYS_ADMIN))) { - EXPECT_NO_ERRNO(SetCapability(CAP_SYS_ADMIN, false)); - } + AutoCapability cap(CAP_SYS_ADMIN, false); const char* path = test_file_name_.c_str(); const char name[] = "trusted.test"; |