1824 lines · cpp
1//===--- rtsan_test_interceptors.cpp - Realtime Sanitizer -------*- C++ -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9//===----------------------------------------------------------------------===//10 11#include "sanitizer_common/sanitizer_platform.h"12#if SANITIZER_POSIX13 14#include "gtest/gtest.h"15 16#include "sanitizer_common/sanitizer_platform_interceptors.h"17 18#include "rtsan_test_utilities.h"19 20#if SANITIZER_APPLE21#include <libkern/OSAtomic.h>22#include <os/lock.h>23#include <unistd.h>24#endif25 26#if SANITIZER_INTERCEPT_MEMALIGN || SANITIZER_INTERCEPT_PVALLOC27#include <malloc.h>28#endif29 30#if SANITIZER_INTERCEPT_EPOLL31#include <sys/epoll.h>32#endif33 34#if SANITIZER_INTERCEPT_KQUEUE35#include <sys/event.h>36#include <sys/time.h>37#endif38 39#include <fcntl.h>40#include <ifaddrs.h>41#include <net/if.h>42#include <netdb.h>43#include <poll.h>44#include <pthread.h>45#include <stdio.h>46#if SANITIZER_LINUX47#include <sys/eventfd.h>48#include <sys/inotify.h>49#include <sys/timerfd.h>50#endif51#include <sys/ioctl.h>52#include <sys/mman.h>53#include <sys/socket.h>54#include <sys/stat.h>55#include <sys/syscall.h>56#include <sys/types.h>57#include <sys/uio.h>58 59#if _FILE_OFFSET_BITS == 64 && SANITIZER_GLIBC60// Under these conditions, some system calls are `foo64` instead of `foo`61#define MAYBE_APPEND_64(func) func "64"62#else63#define MAYBE_APPEND_64(func) func64#endif65 66#if SANITIZER_INTERCEPT_FREE_SIZED67extern "C" void free_sized(void *ptr, size_t size);68#endif69 70#if SANITIZER_INTERCEPT_FREE_ALIGNED_SIZED71extern "C" void free_aligned_sized(void *ptr, size_t alignment, size_t size);72#endif73 74using namespace testing;75using namespace rtsan_testing;76using namespace std::chrono_literals;77 78// NOTE: In the socket tests we pass in bad info to the calls to ensure they79// fail which is why we EXPECT_NE 0 for their return codes.80// We just care that the call is intercepted81const int kNotASocketFd = 0;82 83void *FakeThreadEntryPoint(void *) { return nullptr; }84 85class RtsanFileTest : public ::testing::Test {86protected:87 void SetUp() override {88 const ::testing::TestInfo *const test_info =89 ::testing::UnitTest::GetInstance()->current_test_info();90 file_path_ = std::string("/tmp/rtsan_temporary_test_file_") +91 test_info->name() + ".txt";92 RemoveTemporaryFile();93 }94 95 // Gets a file path with the test's name in it96 // This file will be removed if it exists at the end of the test97 const char *GetTemporaryFilePath() const { return file_path_.c_str(); }98 99 void TearDown() override { RemoveTemporaryFile(); }100 101private:102 void RemoveTemporaryFile() const { std::remove(GetTemporaryFilePath()); }103 std::string file_path_;104};105 106/*107 Allocation and deallocation108*/109 110TEST(TestRtsanInterceptors, MallocDiesWhenRealtime) {111 auto Func = []() { EXPECT_NE(nullptr, malloc(1)); };112 ExpectRealtimeDeath(Func, "malloc");113 ExpectNonRealtimeSurvival(Func);114}115 116TEST(TestRtsanInterceptors, CallocDiesWhenRealtime) {117 auto Func = []() { EXPECT_NE(nullptr, calloc(2, 4)); };118 ExpectRealtimeDeath(Func, "calloc");119 ExpectNonRealtimeSurvival(Func);120}121 122TEST(TestRtsanInterceptors, ReallocDiesWhenRealtime) {123 void *ptr_1 = malloc(1);124 auto Func = [ptr_1]() { EXPECT_NE(nullptr, realloc(ptr_1, 8)); };125 ExpectRealtimeDeath(Func, "realloc");126 ExpectNonRealtimeSurvival(Func);127}128 129#if SANITIZER_APPLE130TEST(TestRtsanInterceptors, ReallocfDiesWhenRealtime) {131 void *ptr_1 = malloc(1);132 auto Func = [ptr_1]() { EXPECT_NE(nullptr, reallocf(ptr_1, 8)); };133 ExpectRealtimeDeath(Func, "reallocf");134 ExpectNonRealtimeSurvival(Func);135}136#endif137 138TEST(TestRtsanInterceptors, VallocDiesWhenRealtime) {139 auto Func = []() { EXPECT_NE(nullptr, valloc(4)); };140 ExpectRealtimeDeath(Func, "valloc");141 ExpectNonRealtimeSurvival(Func);142}143 144#if __has_builtin(__builtin_available) && SANITIZER_APPLE145#define ALIGNED_ALLOC_AVAILABLE() (__builtin_available(macOS 10.15, *))146#else147// We are going to assume this is true until we hit systems where it isn't148#define ALIGNED_ALLOC_AVAILABLE() (true)149#endif150 151TEST(TestRtsanInterceptors, AlignedAllocDiesWhenRealtime) {152 if (ALIGNED_ALLOC_AVAILABLE()) {153 auto Func = []() { EXPECT_NE(nullptr, aligned_alloc(16, 32)); };154 ExpectRealtimeDeath(Func, "aligned_alloc");155 ExpectNonRealtimeSurvival(Func);156 }157}158 159TEST(TestRtsanInterceptors, FreeDiesWhenRealtime) {160 void *ptr_1 = malloc(1);161 void *ptr_2 = malloc(1);162 ExpectRealtimeDeath([ptr_1]() { free(ptr_1); }, "free");163 ExpectNonRealtimeSurvival([ptr_2]() { free(ptr_2); });164 165 // Prevent malloc/free pair being optimised out166 ASSERT_NE(nullptr, ptr_1);167 ASSERT_NE(nullptr, ptr_2);168}169 170#if SANITIZER_INTERCEPT_FREE_SIZED171TEST(TestRtsanInterceptors, FreeSizedDiesWhenRealtime) {172 void *ptr_1 = malloc(1);173 void *ptr_2 = malloc(1);174 ExpectRealtimeDeath([ptr_1]() { free_sized(ptr_1, 1); }, "free_sized");175 ExpectNonRealtimeSurvival([ptr_2]() { free_sized(ptr_2, 1); });176 177 // Prevent malloc/free pair being optimised out178 ASSERT_NE(nullptr, ptr_1);179 ASSERT_NE(nullptr, ptr_2);180}181#endif182 183#if SANITIZER_INTERCEPT_FREE_ALIGNED_SIZED184TEST(TestRtsanInterceptors, FreeAlignedSizedDiesWhenRealtime) {185 if (ALIGNED_ALLOC_AVAILABLE()) {186 void *ptr_1 = aligned_alloc(16, 32);187 void *ptr_2 = aligned_alloc(16, 32);188 ExpectRealtimeDeath([ptr_1]() { free_aligned_sized(ptr_1, 16, 32); },189 "free_aligned_sized");190 ExpectNonRealtimeSurvival([ptr_2]() { free_aligned_sized(ptr_2, 16, 32); });191 192 // Prevent malloc/free pair being optimised out193 ASSERT_NE(nullptr, ptr_1);194 ASSERT_NE(nullptr, ptr_2);195 }196}197#endif198 199TEST(TestRtsanInterceptors, FreeSurvivesWhenRealtimeIfArgumentIsNull) {200 RealtimeInvoke([]() { free(NULL); });201 ExpectNonRealtimeSurvival([]() { free(NULL); });202}203 204#if SANITIZER_INTERCEPT_FREE_SIZED205TEST(TestRtsanInterceptors, FreeSizedSurvivesWhenRealtimeIfArgumentIsNull) {206 RealtimeInvoke([]() { free_sized(NULL, 0); });207 ExpectNonRealtimeSurvival([]() { free_sized(NULL, 0); });208}209#endif210 211#if SANITIZER_INTERCEPT_FREE_ALIGNED_SIZED212TEST(TestRtsanInterceptors,213 FreeAlignedSizedSurvivesWhenRealtimeIfArgumentIsNull) {214 RealtimeInvoke([]() { free_aligned_sized(NULL, 0, 0); });215 ExpectNonRealtimeSurvival([]() { free_aligned_sized(NULL, 0, 0); });216}217#endif218 219TEST(TestRtsanInterceptors, PosixMemalignDiesWhenRealtime) {220 auto Func = []() {221 void *ptr;222 posix_memalign(&ptr, 4, 4);223 };224 ExpectRealtimeDeath(Func, "posix_memalign");225 ExpectNonRealtimeSurvival(Func);226}227 228#if SANITIZER_INTERCEPT_MEMALIGN229TEST(TestRtsanInterceptors, MemalignDiesWhenRealtime) {230 auto Func = []() { EXPECT_NE(memalign(2, 2048), nullptr); };231 ExpectRealtimeDeath(Func, "memalign");232 ExpectNonRealtimeSurvival(Func);233}234#endif235 236#if SANITIZER_INTERCEPT_PVALLOC237TEST(TestRtsanInterceptors, PvallocDiesWhenRealtime) {238 auto Func = []() { EXPECT_NE(pvalloc(2048), nullptr); };239 ExpectRealtimeDeath(Func, "pvalloc");240 ExpectNonRealtimeSurvival(Func);241}242#endif243 244TEST(TestRtsanInterceptors, MmapDiesWhenRealtime) {245 auto Func = []() {246 void *_ = mmap(nullptr, 8, PROT_READ | PROT_WRITE,247 MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);248 };249 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("mmap"));250 ExpectNonRealtimeSurvival(Func);251}252 253#if SANITIZER_LINUX254TEST(TestRtsanInterceptors, MremapDiesWhenRealtime) {255 void *addr = mmap(nullptr, 8, PROT_READ | PROT_WRITE,256 MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);257 auto Func = [addr]() { void *_ = mremap(addr, 8, 16, 0); };258 ExpectRealtimeDeath(Func, "mremap");259 ExpectNonRealtimeSurvival(Func);260}261#endif262 263TEST(TestRtsanInterceptors, MunmapDiesWhenRealtime) {264 void *ptr = mmap(nullptr, 8, PROT_READ | PROT_WRITE,265 MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);266 EXPECT_NE(ptr, nullptr);267 auto Func = [ptr]() { munmap(ptr, 8); };268 printf("Right before death munmap\n");269 ExpectRealtimeDeath(Func, "munmap");270 ExpectNonRealtimeSurvival(Func);271}272 273class RtsanOpenedMmapTest : public RtsanFileTest {274protected:275 void SetUp() override {276 RtsanFileTest::SetUp();277 file = fopen(GetTemporaryFilePath(), "w+");278 ASSERT_THAT(file, Ne(nullptr));279 fd = fileno(file);280 ASSERT_THAT(fd, Ne(-1));281 int ret = ftruncate(GetOpenFd(), size);282 ASSERT_THAT(ret, Ne(-1));283 addr =284 mmap(nullptr, size, PROT_READ | PROT_WRITE, MAP_SHARED, GetOpenFd(), 0);285 ASSERT_THAT(addr, Ne(MAP_FAILED));286 ASSERT_THAT(addr, Ne(nullptr));287 }288 289 void TearDown() override {290 if (addr != nullptr && addr != MAP_FAILED)291 munmap(addr, size);292 RtsanFileTest::TearDown();293 }294 295 void *GetAddr() { return addr; }296 static constexpr size_t GetSize() { return size; }297 298 int GetOpenFd() { return fd; }299 300private:301 void *addr = nullptr;302 static constexpr size_t size = 4096;303 FILE *file = nullptr;304 int fd = -1;305};306 307#if !SANITIZER_APPLE308TEST_F(RtsanOpenedMmapTest, MadviseDiesWhenRealtime) {309 auto Func = [this]() { madvise(GetAddr(), GetSize(), MADV_NORMAL); };310 ExpectRealtimeDeath(Func, "madvise");311 ExpectNonRealtimeSurvival(Func);312}313 314TEST_F(RtsanOpenedMmapTest, PosixMadviseDiesWhenRealtime) {315 auto Func = [this]() {316 posix_madvise(GetAddr(), GetSize(), POSIX_MADV_NORMAL);317 };318 ExpectRealtimeDeath(Func, "posix_madvise");319 ExpectNonRealtimeSurvival(Func);320}321#endif322 323TEST_F(RtsanOpenedMmapTest, MprotectDiesWhenRealtime) {324 auto Func = [this]() { mprotect(GetAddr(), GetSize(), PROT_READ); };325 ExpectRealtimeDeath(Func, "mprotect");326 ExpectNonRealtimeSurvival(Func);327}328 329TEST_F(RtsanOpenedMmapTest, MsyncDiesWhenRealtime) {330 auto Func = [this]() { msync(GetAddr(), GetSize(), MS_INVALIDATE); };331 ExpectRealtimeDeath(Func, "msync");332 ExpectNonRealtimeSurvival(Func);333}334 335TEST_F(RtsanOpenedMmapTest, MincoreDiesWhenRealtime) {336#if SANITIZER_APPLE337 std::vector<char> vec(GetSize() / 1024);338#else339 std::vector<unsigned char> vec(GetSize() / 1024);340#endif341 auto Func = [this, &vec]() { mincore(GetAddr(), GetSize(), vec.data()); };342 ExpectRealtimeDeath(Func, "mincore");343 ExpectNonRealtimeSurvival(Func);344}345 346TEST(TestRtsanInterceptors, ShmOpenDiesWhenRealtime) {347 auto Func = []() { shm_open("/rtsan_test_shm", O_CREAT | O_RDWR, 0); };348 ExpectRealtimeDeath(Func, "shm_open");349 ExpectNonRealtimeSurvival(Func);350}351 352TEST(TestRtsanInterceptors, ShmUnlinkDiesWhenRealtime) {353 auto Func = []() { shm_unlink("/rtsan_test_shm"); };354 ExpectRealtimeDeath(Func, "shm_unlink");355 ExpectNonRealtimeSurvival(Func);356}357 358#if !SANITIZER_APPLE359TEST(TestRtsanInterceptors, MemfdCreateDiesWhenRealtime) {360 auto Func = []() { memfd_create("/rtsan_test_memfd_create", MFD_CLOEXEC); };361 ExpectRealtimeDeath(Func, "memfd_create");362 ExpectNonRealtimeSurvival(Func);363}364#endif365 366/*367 Sleeping368*/369 370TEST(TestRtsanInterceptors, SleepDiesWhenRealtime) {371 auto Func = []() { sleep(0u); };372 ExpectRealtimeDeath(Func, "sleep");373 ExpectNonRealtimeSurvival(Func);374}375 376TEST(TestRtsanInterceptors, UsleepDiesWhenRealtime) {377 auto Func = []() { usleep(1u); };378 ExpectRealtimeDeath(Func, "usleep");379 ExpectNonRealtimeSurvival(Func);380}381 382TEST(TestRtsanInterceptors, NanosleepDiesWhenRealtime) {383 auto Func = []() {384 timespec T{};385 nanosleep(&T, &T);386 };387 ExpectRealtimeDeath(Func, "nanosleep");388 ExpectNonRealtimeSurvival(Func);389}390 391TEST(TestRtsanInterceptors, SchedYieldDiesWhenRealtime) {392 auto Func = []() { sched_yield(); };393 ExpectRealtimeDeath(Func, "sched_yield");394 ExpectNonRealtimeSurvival(Func);395}396 397#if SANITIZER_LINUX398TEST(TestRtsanInterceptors, SchedGetaffinityDiesWhenRealtime) {399 cpu_set_t set{};400 auto Func = [&set]() { sched_getaffinity(0, sizeof(set), &set); };401 ExpectRealtimeDeath(Func, "sched_getaffinity");402 ExpectNonRealtimeSurvival(Func);403}404 405TEST(TestRtsanInterceptors, SchedSetaffinityDiesWhenRealtime) {406 cpu_set_t set{};407 auto Func = [&set]() { sched_setaffinity(0, sizeof(set), &set); };408 ExpectRealtimeDeath(Func, "sched_setaffinity");409 ExpectNonRealtimeSurvival(Func);410}411#endif412 413/*414 Filesystem415*/416 417TEST_F(RtsanFileTest, OpenDiesWhenRealtime) {418 auto Func = [this]() { open(GetTemporaryFilePath(), O_RDONLY); };419 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("open"));420 ExpectNonRealtimeSurvival(Func);421}422 423TEST_F(RtsanFileTest, OpenatDiesWhenRealtime) {424 auto Func = [this]() { openat(0, GetTemporaryFilePath(), O_RDONLY); };425 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("openat"));426 ExpectNonRealtimeSurvival(Func);427}428 429TEST_F(RtsanFileTest, OpenCreatesFileWithProperMode) {430 const mode_t existing_umask = umask(0);431 umask(existing_umask);432 433 const int mode = S_IRGRP | S_IROTH | S_IRUSR | S_IWUSR;434 435 const int fd = open(GetTemporaryFilePath(), O_CREAT | O_WRONLY, mode);436 ASSERT_THAT(fd, Ne(-1));437 close(fd);438 439 struct stat st;440 ASSERT_THAT(stat(GetTemporaryFilePath(), &st), Eq(0));441 442 // Mask st_mode to get permission bits only443 const mode_t actual_mode = st.st_mode & 0777;444 const mode_t expected_mode = mode & ~existing_umask;445 ASSERT_THAT(actual_mode, Eq(expected_mode));446}447 448TEST_F(RtsanFileTest, CreatDiesWhenRealtime) {449 auto Func = [this]() { creat(GetTemporaryFilePath(), S_IWOTH | S_IROTH); };450 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("creat"));451 ExpectNonRealtimeSurvival(Func);452}453 454TEST(TestRtsanInterceptors, FcntlDiesWhenRealtime) {455 auto Func = []() { fcntl(0, F_GETFL); };456 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fcntl"));457 ExpectNonRealtimeSurvival(Func);458}459 460TEST_F(RtsanFileTest, FcntlFlockDiesWhenRealtime) {461 int fd = creat(GetTemporaryFilePath(), S_IRUSR | S_IWUSR);462 ASSERT_THAT(fd, Ne(-1));463 464 auto Func = [fd]() {465 struct flock lock{};466 lock.l_type = F_RDLCK;467 lock.l_whence = SEEK_SET;468 lock.l_start = 0;469 lock.l_len = 0;470 lock.l_pid = ::getpid();471 472 ASSERT_THAT(fcntl(fd, F_GETLK, &lock), Eq(0));473 ASSERT_THAT(lock.l_type, F_UNLCK);474 };475 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fcntl"));476 ExpectNonRealtimeSurvival(Func);477 478 close(fd);479}480 481TEST_F(RtsanFileTest, FcntlSetFdDiesWhenRealtime) {482 int fd = creat(GetTemporaryFilePath(), S_IRUSR | S_IWUSR);483 ASSERT_THAT(fd, Ne(-1));484 485 auto Func = [fd]() {486 int old_flags = fcntl(fd, F_GETFD);487 ASSERT_THAT(fcntl(fd, F_SETFD, FD_CLOEXEC), Eq(0));488 489 int flags = fcntl(fd, F_GETFD);490 ASSERT_THAT(flags, Ne(-1));491 ASSERT_THAT(flags & FD_CLOEXEC, Eq(FD_CLOEXEC));492 493 ASSERT_THAT(fcntl(fd, F_SETFD, old_flags), Eq(0));494 ASSERT_THAT(fcntl(fd, F_GETFD), Eq(old_flags));495 };496 497 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fcntl"));498 ExpectNonRealtimeSurvival(Func);499 500 close(fd);501}502 503TEST(TestRtsanInterceptors, ChdirDiesWhenRealtime) {504 auto Func = []() { chdir("."); };505 ExpectRealtimeDeath(Func, "chdir");506 ExpectNonRealtimeSurvival(Func);507}508 509TEST(TestRtsanInterceptors, FchdirDiesWhenRealtime) {510 auto Func = []() { fchdir(0); };511 ExpectRealtimeDeath(Func, "fchdir");512 ExpectNonRealtimeSurvival(Func);513}514 515#if SANITIZER_INTERCEPT_READLINK516TEST(TestRtsanInterceptors, ReadlinkDiesWhenRealtime) {517 char buf[1024];518 auto Func = [&buf]() { readlink("/proc/self", buf, sizeof(buf)); };519 ExpectRealtimeDeath(Func, "readlink");520 ExpectNonRealtimeSurvival(Func);521}522#endif523 524#if SANITIZER_INTERCEPT_READLINKAT525TEST(TestRtsanInterceptors, ReadlinkatDiesWhenRealtime) {526 char buf[1024];527 auto Func = [&buf]() { readlinkat(0, "/proc/self", buf, sizeof(buf)); };528 ExpectRealtimeDeath(Func, "readlinkat");529 ExpectNonRealtimeSurvival(Func);530}531#endif532 533TEST_F(RtsanFileTest, FopenDiesWhenRealtime) {534 auto Func = [this]() {535 FILE *f = fopen(GetTemporaryFilePath(), "w");536 EXPECT_THAT(f, Ne(nullptr));537 };538 539 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fopen"));540 ExpectNonRealtimeSurvival(Func);541}542 543#if SANITIZER_INTERCEPT_FOPENCOOKIE544TEST_F(RtsanFileTest, FopenCookieDieWhenRealtime) {545 FILE *f = fopen(GetTemporaryFilePath(), "w");546 EXPECT_THAT(f, Ne(nullptr));547 struct fholder {548 FILE *fp;549 size_t read;550 } fh = {f, 0};551 auto CookieRead = [](void *cookie, char *buf, size_t size) {552 fholder *p = reinterpret_cast<fholder *>(cookie);553 p->read = fread(static_cast<void *>(buf), 1, size, p->fp);554 EXPECT_NE(0u, p->read);555 };556 cookie_io_functions_t funcs = {(cookie_read_function_t *)&CookieRead, nullptr,557 nullptr, nullptr};558 auto Func = [&fh, &funcs]() {559 FILE *f = fopencookie(&fh, "w", funcs);560 EXPECT_THAT(f, Ne(nullptr));561 };562 563 ExpectRealtimeDeath(Func, "fopencookie");564 ExpectNonRealtimeSurvival(Func);565}566#endif567 568#if SANITIZER_INTERCEPT_OPEN_MEMSTREAM569TEST_F(RtsanFileTest, OpenMemstreamDiesWhenRealtime) {570 char *buffer;571 size_t size;572 auto Func = [&buffer, &size]() {573 FILE *f = open_memstream(&buffer, &size);574 EXPECT_THAT(f, Ne(nullptr));575 };576 577 ExpectRealtimeDeath(Func, "open_memstream");578 ExpectNonRealtimeSurvival(Func);579}580 581TEST_F(RtsanFileTest, FmemOpenDiesWhenRealtime) {582 char buffer[1024];583 auto Func = [&buffer]() {584 FILE *f = fmemopen(&buffer, sizeof(buffer), "w");585 EXPECT_THAT(f, Ne(nullptr));586 };587 588 ExpectRealtimeDeath(Func, "fmemopen");589 ExpectNonRealtimeSurvival(Func);590}591#endif592 593#if SANITIZER_INTERCEPT_SETVBUF594TEST_F(RtsanFileTest, SetbufDieWhenRealtime) {595 char buffer[BUFSIZ];596 FILE *f = fopen(GetTemporaryFilePath(), "w");597 EXPECT_THAT(f, Ne(nullptr));598 599 auto Func = [f, &buffer]() { setbuf(f, buffer); };600 601 ExpectRealtimeDeath(Func, "setbuf");602 ExpectNonRealtimeSurvival(Func);603}604 605TEST_F(RtsanFileTest, SetvbufDieWhenRealtime) {606 char buffer[1024];607 size_t size = sizeof(buffer);608 FILE *f = fopen(GetTemporaryFilePath(), "w");609 EXPECT_THAT(f, Ne(nullptr));610 611 auto Func = [f, &buffer, size]() {612 int r = setvbuf(f, buffer, _IOFBF, size);613 EXPECT_THAT(r, Eq(0));614 };615 616 ExpectRealtimeDeath(Func, "setvbuf");617 ExpectNonRealtimeSurvival(Func);618}619 620TEST_F(RtsanFileTest, SetlinebufDieWhenRealtime) {621 FILE *f = fopen(GetTemporaryFilePath(), "w");622 EXPECT_THAT(f, Ne(nullptr));623 624 auto Func = [f]() { setlinebuf(f); };625 626 ExpectRealtimeDeath(Func, "setlinebuf");627 ExpectNonRealtimeSurvival(Func);628}629 630TEST_F(RtsanFileTest, SetbufferDieWhenRealtime) {631 char buffer[1024];632 size_t size = sizeof(buffer);633 FILE *f = fopen(GetTemporaryFilePath(), "w");634 EXPECT_THAT(f, Ne(nullptr));635 636 auto Func = [f, &buffer, size]() { setbuffer(f, buffer, size); };637 638 ExpectRealtimeDeath(Func, "setbuffer");639 ExpectNonRealtimeSurvival(Func);640}641#endif642 643class RtsanOpenedFileTest : public RtsanFileTest {644protected:645 void SetUp() override {646 RtsanFileTest::SetUp();647 file = fopen(GetTemporaryFilePath(), "w");648 ASSERT_THAT(file, Ne(nullptr));649 fd = fileno(file);650 ASSERT_THAT(fd, Ne(-1));651 }652 653 void TearDown() override {654 const bool is_open = fcntl(fd, F_GETFD) != -1;655 if (is_open && file != nullptr)656 fclose(file);657 658 RtsanFileTest::TearDown();659 }660 661 FILE *GetOpenFile() { return file; }662 663 int GetOpenFd() { return fd; }664 665private:666 FILE *file = nullptr;667 int fd = -1;668};669 670TEST_F(RtsanOpenedFileTest, CloseDiesWhenRealtime) {671 auto Func = [this]() { close(GetOpenFd()); };672 ExpectRealtimeDeath(Func, "close");673}674 675TEST_F(RtsanOpenedFileTest, CloseSurvivesWhenNotRealtime) {676 auto Func = [this]() { close(GetOpenFd()); };677 ExpectNonRealtimeSurvival(Func);678}679 680#if SANITIZER_INTERCEPT_FSEEK681TEST_F(RtsanOpenedFileTest, FgetposDieWhenRealtime) {682 auto Func = [this]() {683 fpos_t pos;684 int ret = fgetpos(GetOpenFile(), &pos);685 ASSERT_THAT(ret, Eq(0));686 };687 688 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fgetpos"));689 ExpectNonRealtimeSurvival(Func);690}691 692TEST_F(RtsanOpenedFileTest, FsetposDieWhenRealtime) {693 fpos_t pos;694 int ret = fgetpos(GetOpenFile(), &pos);695 ASSERT_THAT(ret, Eq(0));696 auto Func = [this, pos]() {697 int ret = fsetpos(GetOpenFile(), &pos);698 ASSERT_THAT(ret, Eq(0));699 };700 701 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fsetpos"));702 ExpectNonRealtimeSurvival(Func);703}704 705TEST_F(RtsanOpenedFileTest, FseekDieWhenRealtime) {706 auto Func = [this]() {707 int ret = fseek(GetOpenFile(), 0, SEEK_CUR);708 ASSERT_THAT(ret, Eq(0));709 };710 711 ExpectRealtimeDeath(Func, "fseek");712 ExpectNonRealtimeSurvival(Func);713}714 715TEST_F(RtsanOpenedFileTest, FseekoDieWhenRealtime) {716 auto Func = [this]() {717 int ret = fseeko(GetOpenFile(), 0, SEEK_CUR);718 ASSERT_THAT(ret, Eq(0));719 };720 721 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("fseeko"));722 ExpectNonRealtimeSurvival(Func);723}724 725TEST_F(RtsanOpenedFileTest, FtellDieWhenRealtime) {726 auto Func = [this]() {727 long ret = ftell(GetOpenFile());728 ASSERT_THAT(ret, Eq(0));729 };730 731 ExpectRealtimeDeath(Func, "ftell");732 ExpectNonRealtimeSurvival(Func);733}734 735TEST_F(RtsanOpenedFileTest, FtelloDieWhenRealtime) {736 auto Func = [this]() {737 off_t ret = ftello(GetOpenFile());738 ASSERT_THAT(ret, Eq(0));739 };740 741 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("ftello"));742 ExpectNonRealtimeSurvival(Func);743}744 745TEST_F(RtsanOpenedFileTest, RewindDieWhenRealtime) {746 int end = fseek(GetOpenFile(), 0, SEEK_END);747 EXPECT_THAT(end, Eq(0));748 auto Func = [this]() { rewind(GetOpenFile()); };749 750 ExpectRealtimeDeath(Func, "rewind");751 ExpectNonRealtimeSurvival(Func);752}753#endif754 755TEST_F(RtsanOpenedFileTest, IoctlDiesWhenRealtime) {756 auto Func = [this]() {757 int arg{};758 ioctl(GetOpenFd(), FIONREAD, &arg);759 EXPECT_THAT(arg, Ge(0));760 };761 ExpectRealtimeDeath(Func, "ioctl");762 ExpectNonRealtimeSurvival(Func);763}764 765TEST_F(RtsanOpenedFileTest, IoctlBehavesWithoutOutputArg) {766 const int result = ioctl(GetOpenFd(), FIONCLEX);767 EXPECT_THAT(result, Ne(-1));768}769 770TEST_F(RtsanOpenedFileTest, IoctlBehavesWithOutputArg) {771 int arg{};772 const int result = ioctl(GetOpenFd(), FIONREAD, &arg);773 ASSERT_THAT(result, Ne(-1));774 EXPECT_THAT(arg, Ge(0));775}776 777TEST_F(RtsanOpenedFileTest, FdopenDiesWhenRealtime) {778 auto Func = [&]() {779 FILE *f = fdopen(GetOpenFd(), "w");780 EXPECT_THAT(f, Ne(nullptr));781 };782 783 ExpectRealtimeDeath(Func, "fdopen");784 ExpectNonRealtimeSurvival(Func);785}786 787TEST_F(RtsanOpenedFileTest, FreopenDiesWhenRealtime) {788 auto Func = [&]() {789 FILE *newfile = freopen(GetTemporaryFilePath(), "w", GetOpenFile());790 EXPECT_THAT(newfile, Ne(nullptr));791 };792 793 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("freopen"));794 ExpectNonRealtimeSurvival(Func);795}796 797TEST(TestRtsanInterceptors, IoctlBehavesWithOutputPointer) {798 // These initial checks just see if we CAN run these tests.799 // If we can't (can't open a socket, or can't find an interface, just800 // gracefully skip.801 int sock = socket(AF_INET, SOCK_STREAM, 0);802 if (sock == -1) {803 perror("socket");804 GTEST_SKIP();805 }806 807 struct ifaddrs *ifaddr = nullptr;808 if (getifaddrs(&ifaddr) == -1 || ifaddr == nullptr) {809 perror("getifaddrs");810 close(sock);811 GTEST_SKIP();812 }813 814 struct ifreq ifr{};815 strncpy(ifr.ifr_name, ifaddr->ifa_name, IFNAMSIZ - 1);816 817 int retval = ioctl(sock, SIOCGIFADDR, &ifr);818 if (retval == -1) {819 perror("ioctl");820 close(sock);821 freeifaddrs(ifaddr);822 FAIL();823 }824 825 freeifaddrs(ifaddr);826 close(sock);827 828 ASSERT_THAT(ifr.ifr_addr.sa_data, NotNull());829 ASSERT_THAT(ifr.ifr_addr.sa_family, Eq(AF_INET));830}831 832TEST_F(RtsanOpenedFileTest, LseekDiesWhenRealtime) {833 auto Func = [this]() { lseek(GetOpenFd(), 0, SEEK_SET); };834 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("lseek"));835 ExpectNonRealtimeSurvival(Func);836}837 838TEST_F(RtsanOpenedFileTest, DupDiesWhenRealtime) {839 auto Func = [this]() { dup(GetOpenFd()); };840 ExpectRealtimeDeath(Func, "dup");841 ExpectNonRealtimeSurvival(Func);842}843 844TEST_F(RtsanOpenedFileTest, Dup2DiesWhenRealtime) {845 auto Func = [this]() { dup2(GetOpenFd(), 0); };846 ExpectRealtimeDeath(Func, "dup2");847 ExpectNonRealtimeSurvival(Func);848}849 850TEST_F(RtsanFileTest, ChmodDiesWhenRealtime) {851 auto Func = [this]() { chmod(GetTemporaryFilePath(), 0777); };852 ExpectRealtimeDeath(Func, "chmod");853 ExpectNonRealtimeSurvival(Func);854}855 856TEST_F(RtsanOpenedFileTest, FchmodDiesWhenRealtime) {857 auto Func = [this]() { fchmod(GetOpenFd(), 0777); };858 ExpectRealtimeDeath(Func, "fchmod");859 ExpectNonRealtimeSurvival(Func);860}861 862TEST(TestRtsanInterceptors, UmaskDiesWhenRealtime) {863 auto Func = []() { umask(0); };864 ExpectRealtimeDeath(Func, "umask");865 ExpectNonRealtimeSurvival(Func);866}867 868#if SANITIZER_INTERCEPT_PROCESS_VM_READV869TEST(TestRtsanInterceptors, ProcessVmReadvDiesWhenRealtime) {870 char stack[1024];871 int p;872 iovec lcl{&stack, sizeof(stack)};873 iovec rmt{&p, sizeof(p)};874 auto Func = [&lcl, &rmt]() { process_vm_readv(0, &lcl, 1, &rmt, 1, 0); };875 ExpectRealtimeDeath(Func, "process_vm_readv");876 ExpectNonRealtimeSurvival(Func);877}878 879TEST(TestRtsanInterceptors, ProcessVmWritevDiesWhenRealtime) {880 char stack[1024];881 int p;882 iovec lcl{&p, sizeof(p)};883 iovec rmt{&stack, sizeof(stack)};884 auto Func = [&lcl, &rmt]() { process_vm_writev(0, &lcl, 1, &rmt, 1, 0); };885 ExpectRealtimeDeath(Func, "process_vm_writev");886 ExpectNonRealtimeSurvival(Func);887}888#endif889 890class RtsanDirectoryTest : public ::testing::Test {891protected:892 void SetUp() override {893 const ::testing::TestInfo *const test_info =894 ::testing::UnitTest::GetInstance()->current_test_info();895 directory_path_ = std::string("/tmp/rtsan_temp_dir_") + test_info->name();896 RemoveTemporaryDirectory();897 }898 899 const char *GetTemporaryDirectoryPath() const {900 return directory_path_.c_str();901 }902 903 void TearDown() override { RemoveTemporaryDirectory(); }904 905private:906 void RemoveTemporaryDirectory() const {907 std::remove(GetTemporaryDirectoryPath());908 }909 std::string directory_path_;910};911 912TEST_F(RtsanDirectoryTest, MkdirDiesWhenRealtime) {913 auto Func = [this]() { mkdir(GetTemporaryDirectoryPath(), 0777); };914 ExpectRealtimeDeath(Func, "mkdir");915 ExpectNonRealtimeSurvival(Func);916}917 918TEST_F(RtsanDirectoryTest, RmdirDiesWhenRealtime) {919 // We don't actually create this directory before we try to remove it920 // Thats OK - we are just making sure the call gets intercepted921 auto Func = [this]() { rmdir(GetTemporaryDirectoryPath()); };922 ExpectRealtimeDeath(Func, "rmdir");923 ExpectNonRealtimeSurvival(Func);924}925 926TEST_F(RtsanOpenedFileTest, FreadDiesWhenRealtime) {927 auto Func = [this]() {928 char c{};929 fread(&c, 1, 1, GetOpenFile());930 };931 ExpectRealtimeDeath(Func, "fread");932 ExpectNonRealtimeSurvival(Func);933}934 935TEST_F(RtsanOpenedFileTest, FwriteDiesWhenRealtime) {936 const char *message = "Hello, world!";937 auto Func = [&]() { fwrite(&message, 1, 4, GetOpenFile()); };938 ExpectRealtimeDeath(Func, "fwrite");939 ExpectNonRealtimeSurvival(Func);940}941 942TEST_F(RtsanOpenedFileTest, UnlinkDiesWhenRealtime) {943 auto Func = [&]() { unlink(GetTemporaryFilePath()); };944 ExpectRealtimeDeath(Func, "unlink");945 ExpectNonRealtimeSurvival(Func);946}947 948TEST_F(RtsanOpenedFileTest, UnlinkatDiesWhenRealtime) {949 auto Func = [&]() { unlinkat(0, GetTemporaryFilePath(), 0); };950 ExpectRealtimeDeath(Func, "unlinkat");951 ExpectNonRealtimeSurvival(Func);952}953 954TEST_F(RtsanOpenedFileTest, TruncateDiesWhenRealtime) {955 auto Func = [&]() { truncate(GetTemporaryFilePath(), 16); };956 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("truncate"));957 ExpectNonRealtimeSurvival(Func);958}959 960TEST_F(RtsanOpenedFileTest, FtruncateDiesWhenRealtime) {961 auto Func = [&]() { ftruncate(GetOpenFd(), 16); };962 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("ftruncate"));963 ExpectNonRealtimeSurvival(Func);964}965 966TEST_F(RtsanOpenedFileTest, SymlinkDiesWhenRealtime) {967 auto Func = [&]() {968 symlink("/tmp/rtsan_symlink_test", GetTemporaryFilePath());969 };970 ExpectRealtimeDeath(Func, "symlink");971 ExpectNonRealtimeSurvival(Func);972}973 974TEST_F(RtsanOpenedFileTest, SymlinkatDiesWhenRealtime) {975 auto Func = [&]() {976 symlinkat("/tmp/rtsan_symlinkat_test", AT_FDCWD, GetTemporaryFilePath());977 };978 ExpectRealtimeDeath(Func, "symlinkat");979 ExpectNonRealtimeSurvival(Func);980}981 982TEST_F(RtsanFileTest, FcloseDiesWhenRealtime) {983 FILE *f = fopen(GetTemporaryFilePath(), "w");984 EXPECT_THAT(f, Ne(nullptr));985 auto Func = [f]() { fclose(f); };986 ExpectRealtimeDeath(Func, "fclose");987 ExpectNonRealtimeSurvival(Func);988}989 990TEST(TestRtsanInterceptors, PutsDiesWhenRealtime) {991 auto Func = []() { puts("Hello, world!\n"); };992 ExpectRealtimeDeath(Func);993 ExpectNonRealtimeSurvival(Func);994}995 996TEST_F(RtsanOpenedFileTest, FputsDiesWhenRealtime) {997 auto Func = [this]() { fputs("Hello, world!\n", GetOpenFile()); };998 ExpectRealtimeDeath(Func);999 ExpectNonRealtimeSurvival(Func);1000}1001 1002TEST_F(RtsanFileTest, FflushDiesWhenRealtime) {1003 FILE *f = fopen(GetTemporaryFilePath(), "w");1004 EXPECT_THAT(f, Ne(nullptr));1005 int written = fwrite("abc", 1, 3, f);1006 EXPECT_THAT(written, Eq(3));1007 auto Func = [&f]() {1008 int res = fflush(f);1009 EXPECT_THAT(res, Eq(0));1010 };1011 ExpectRealtimeDeath(Func, "fflush");1012 ExpectNonRealtimeSurvival(Func);1013}1014 1015#if SANITIZER_APPLE1016TEST_F(RtsanFileTest, FpurgeDiesWhenRealtime) {1017 FILE *f = fopen(GetTemporaryFilePath(), "w");1018 EXPECT_THAT(f, Ne(nullptr));1019 int written = fwrite("abc", 1, 3, f);1020 EXPECT_THAT(written, Eq(3));1021 auto Func = [&f]() {1022 int res = fpurge(f);1023 EXPECT_THAT(res, Eq(0));1024 };1025 ExpectRealtimeDeath(Func, "fpurge");1026 ExpectNonRealtimeSurvival(Func);1027}1028#endif1029 1030TEST_F(RtsanOpenedFileTest, ReadDiesWhenRealtime) {1031 auto Func = [this]() {1032 char c{};1033 read(GetOpenFd(), &c, 1);1034 };1035 ExpectRealtimeDeath(Func, "read");1036 ExpectNonRealtimeSurvival(Func);1037}1038 1039TEST_F(RtsanOpenedFileTest, WriteDiesWhenRealtime) {1040 auto Func = [this]() {1041 char c = 'a';1042 write(GetOpenFd(), &c, 1);1043 };1044 ExpectRealtimeDeath(Func, "write");1045 ExpectNonRealtimeSurvival(Func);1046}1047 1048TEST_F(RtsanOpenedFileTest, PreadDiesWhenRealtime) {1049 auto Func = [this]() {1050 char c{};1051 pread(GetOpenFd(), &c, 1, 0);1052 };1053 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("pread"));1054 ExpectNonRealtimeSurvival(Func);1055}1056 1057#if SANITIZER_INTERCEPT_PREADV1058TEST_F(RtsanOpenedFileTest, PreadvDiesWhenRealtime) {1059 auto Func = [this]() {1060 char c{};1061 iovec iov{&c, sizeof(c)};1062 preadv(GetOpenFd(), &iov, 1, 0);1063 };1064 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("preadv"));1065 ExpectNonRealtimeSurvival(Func);1066}1067#endif1068 1069#if SANITIZER_INTERCEPT_PWRITEV1070TEST_F(RtsanOpenedFileTest, PwritevDiesWhenRealtime) {1071 auto Func = [this]() {1072 char c{};1073 iovec iov{&c, sizeof(c)};1074 pwritev(GetOpenFd(), &iov, 1, 0);1075 };1076 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("pwritev"));1077 ExpectNonRealtimeSurvival(Func);1078}1079#endif1080 1081TEST_F(RtsanOpenedFileTest, ReadvDiesWhenRealtime) {1082 auto Func = [this]() {1083 char c{};1084 iovec iov{&c, 1};1085 readv(GetOpenFd(), &iov, 1);1086 };1087 ExpectRealtimeDeath(Func, "readv");1088 ExpectNonRealtimeSurvival(Func);1089}1090 1091TEST_F(RtsanOpenedFileTest, PwriteDiesWhenRealtime) {1092 auto Func = [this]() {1093 char c = 'a';1094 pwrite(GetOpenFd(), &c, 1, 0);1095 };1096 ExpectRealtimeDeath(Func, MAYBE_APPEND_64("pwrite"));1097 ExpectNonRealtimeSurvival(Func);1098}1099 1100TEST_F(RtsanOpenedFileTest, WritevDiesWhenRealtime) {1101 auto Func = [this]() {1102 char c = 'a';1103 iovec iov{&c, 1};1104 writev(GetOpenFd(), &iov, 1);1105 };1106 ExpectRealtimeDeath(Func, "writev");1107 ExpectNonRealtimeSurvival(Func);1108}1109 1110/*1111 Concurrency1112*/1113 1114TEST(TestRtsanInterceptors, PthreadCreateDiesWhenRealtime) {1115 auto Func = []() {1116 pthread_t thread{};1117 const pthread_attr_t attr{};1118 struct thread_info *thread_info{};1119 pthread_create(&thread, &attr, &FakeThreadEntryPoint, thread_info);1120 };1121 ExpectRealtimeDeath(Func, "pthread_create");1122 ExpectNonRealtimeSurvival(Func);1123}1124 1125class PthreadMutexLockTest : public ::testing::Test {1126protected:1127 void SetUp() override {1128 pthread_mutex_init(&mutex, nullptr);1129 is_locked = false;1130 }1131 1132 void TearDown() override {1133 if (is_locked)1134 Unlock();1135 1136 pthread_mutex_destroy(&mutex);1137 }1138 1139 void Lock() {1140 ASSERT_TRUE(!is_locked);1141 pthread_mutex_lock(&mutex);1142 is_locked = true;1143 }1144 1145 void Unlock() {1146 ASSERT_TRUE(is_locked);1147 pthread_mutex_unlock(&mutex);1148 is_locked = false;1149 }1150 1151private:1152 pthread_mutex_t mutex;1153 bool is_locked;1154};1155 1156TEST_F(PthreadMutexLockTest, PthreadMutexLockDiesWhenRealtime) {1157 auto Func = [this]() { Lock(); };1158 1159 ExpectRealtimeDeath(Func, "pthread_mutex_lock");1160}1161 1162TEST_F(PthreadMutexLockTest, PthreadMutexLockSurvivesWhenNotRealtime) {1163 auto Func = [this]() { Lock(); };1164 1165 ExpectNonRealtimeSurvival(Func);1166}1167 1168TEST_F(PthreadMutexLockTest, PthreadMutexUnlockDiesWhenRealtime) {1169 Lock();1170 auto Func = [this]() { Unlock(); };1171 1172 ExpectRealtimeDeath(Func, "pthread_mutex_unlock");1173 ExpectNonRealtimeSurvival(Func);1174}1175 1176TEST_F(PthreadMutexLockTest, PthreadMutexUnlockSurvivesWhenNotRealtime) {1177 Lock();1178 auto Func = [this]() { Unlock(); };1179 1180 ExpectNonRealtimeSurvival(Func);1181}1182 1183TEST(TestRtsanInterceptors, PthreadJoinDiesWhenRealtime) {1184 pthread_t thread{};1185 ASSERT_EQ(0,1186 pthread_create(&thread, nullptr, &FakeThreadEntryPoint, nullptr));1187 1188 auto Func = [&thread]() { pthread_join(thread, nullptr); };1189 1190 ExpectRealtimeDeath(Func, "pthread_join");1191 ExpectNonRealtimeSurvival(Func);1192}1193 1194#if SANITIZER_APPLE1195#pragma clang diagnostic push1196// OSSpinLockLock is deprecated, but still in use in libc++1197#pragma clang diagnostic ignored "-Wdeprecated-declarations"1198#undef OSSpinLockLock1199extern "C" {1200typedef int32_t OSSpinLock;1201void OSSpinLockLock(volatile OSSpinLock *__lock);1202// _os_nospin_lock_lock may replace OSSpinLockLock due to deprecation macro.1203typedef volatile OSSpinLock *_os_nospin_lock_t;1204void _os_nospin_lock_lock(_os_nospin_lock_t lock);1205}1206 1207TEST(TestRtsanInterceptors, OsSpinLockLockDiesWhenRealtime) {1208 auto Func = []() {1209 OSSpinLock spin_lock{};1210 OSSpinLockLock(&spin_lock);1211 };1212 ExpectRealtimeDeath(Func, "OSSpinLockLock");1213 ExpectNonRealtimeSurvival(Func);1214}1215 1216TEST(TestRtsanInterceptors, OsNoSpinLockLockDiesWhenRealtime) {1217 OSSpinLock lock{};1218 auto Func = [&]() { _os_nospin_lock_lock(&lock); };1219 ExpectRealtimeDeath(Func, "_os_nospin_lock_lock");1220 ExpectNonRealtimeSurvival(Func);1221}1222#pragma clang diagnostic pop //"-Wdeprecated-declarations"1223 1224TEST(TestRtsanInterceptors, OsUnfairLockLockDiesWhenRealtime) {1225 auto Func = []() {1226 os_unfair_lock_s unfair_lock{};1227 os_unfair_lock_lock(&unfair_lock);1228 };1229 ExpectRealtimeDeath(Func, "os_unfair_lock_lock");1230 ExpectNonRealtimeSurvival(Func);1231}1232#endif // SANITIZER_APPLE1233 1234#if SANITIZER_LINUX1235TEST(TestRtsanInterceptors, SpinLockLockDiesWhenRealtime) {1236 pthread_spinlock_t spin_lock;1237 pthread_spin_init(&spin_lock, PTHREAD_PROCESS_SHARED);1238 auto Func = [&]() { pthread_spin_lock(&spin_lock); };1239 ExpectRealtimeDeath(Func, "pthread_spin_lock");1240 ExpectNonRealtimeSurvival(Func);1241}1242#endif1243 1244TEST(TestRtsanInterceptors, PthreadCondInitDiesWhenRealtime) {1245 pthread_cond_t cond{};1246 auto Func = [&cond]() { pthread_cond_init(&cond, nullptr); };1247 ExpectRealtimeDeath(Func, "pthread_cond_init");1248 ExpectNonRealtimeSurvival(Func);1249}1250 1251TEST(TestRtsanInterceptors, PthreadCondDestroyDiesWhenRealtime) {1252 pthread_cond_t cond{};1253 ASSERT_EQ(0, pthread_cond_init(&cond, nullptr));1254 1255 auto Func = [&cond]() { pthread_cond_destroy(&cond); };1256 ExpectRealtimeDeath(Func, "pthread_cond_destroy");1257 ExpectNonRealtimeSurvival(Func);1258 1259 pthread_cond_destroy(&cond);1260}1261 1262TEST(TestRtsanInterceptors, PthreadCondSignalDiesWhenRealtime) {1263 pthread_cond_t cond{};1264 ASSERT_EQ(0, pthread_cond_init(&cond, nullptr));1265 1266 auto Func = [&cond]() { pthread_cond_signal(&cond); };1267 ExpectRealtimeDeath(Func, "pthread_cond_signal");1268 ExpectNonRealtimeSurvival(Func);1269 1270 pthread_cond_destroy(&cond);1271}1272 1273TEST(TestRtsanInterceptors, PthreadCondBroadcastDiesWhenRealtime) {1274 pthread_cond_t cond{};1275 ASSERT_EQ(0, pthread_cond_init(&cond, nullptr));1276 1277 auto Func = [&cond]() { pthread_cond_broadcast(&cond); };1278 ExpectRealtimeDeath(Func, "pthread_cond_broadcast");1279 ExpectNonRealtimeSurvival(Func);1280 1281 pthread_cond_destroy(&cond);1282}1283 1284TEST(TestRtsanInterceptors, PthreadCondWaitDiesWhenRealtime) {1285 pthread_cond_t cond;1286 pthread_mutex_t mutex;1287 ASSERT_EQ(0, pthread_cond_init(&cond, nullptr));1288 ASSERT_EQ(0, pthread_mutex_init(&mutex, nullptr));1289 1290 auto Func = [&]() { pthread_cond_wait(&cond, &mutex); };1291 ExpectRealtimeDeath(Func, "pthread_cond_wait");1292 // It's very difficult to test the success case here without doing some1293 // sleeping, which is at the mercy of the scheduler. What's really important1294 // here is the interception - so we're only testing that for now.1295 1296 pthread_cond_destroy(&cond);1297 pthread_mutex_destroy(&mutex);1298}1299 1300class PthreadRwlockTest : public ::testing::Test {1301protected:1302 void SetUp() override {1303 pthread_rwlock_init(&rw_lock, nullptr);1304 is_locked = false;1305 }1306 1307 void TearDown() override {1308 if (is_locked)1309 Unlock();1310 1311 pthread_rwlock_destroy(&rw_lock);1312 }1313 1314 void RdLock() {1315 ASSERT_TRUE(!is_locked);1316 pthread_rwlock_rdlock(&rw_lock);1317 is_locked = true;1318 }1319 1320 void WrLock() {1321 ASSERT_TRUE(!is_locked);1322 pthread_rwlock_wrlock(&rw_lock);1323 is_locked = true;1324 }1325 1326 void Unlock() {1327 ASSERT_TRUE(is_locked);1328 pthread_rwlock_unlock(&rw_lock);1329 is_locked = false;1330 }1331 1332private:1333 pthread_rwlock_t rw_lock;1334 bool is_locked;1335};1336 1337TEST_F(PthreadRwlockTest, PthreadRwlockRdlockDiesWhenRealtime) {1338 auto Func = [this]() { RdLock(); };1339 ExpectRealtimeDeath(Func, "pthread_rwlock_rdlock");1340}1341 1342TEST_F(PthreadRwlockTest, PthreadRwlockRdlockSurvivesWhenNonRealtime) {1343 auto Func = [this]() { RdLock(); };1344 ExpectNonRealtimeSurvival(Func);1345}1346 1347TEST_F(PthreadRwlockTest, PthreadRwlockUnlockDiesWhenRealtime) {1348 RdLock();1349 1350 auto Func = [this]() { Unlock(); };1351 ExpectRealtimeDeath(Func, "pthread_rwlock_unlock");1352}1353 1354TEST_F(PthreadRwlockTest, PthreadRwlockUnlockSurvivesWhenNonRealtime) {1355 RdLock();1356 1357 auto Func = [this]() { Unlock(); };1358 ExpectNonRealtimeSurvival(Func);1359}1360 1361TEST_F(PthreadRwlockTest, PthreadRwlockWrlockDiesWhenRealtime) {1362 auto Func = [this]() { WrLock(); };1363 1364 ExpectRealtimeDeath(Func, "pthread_rwlock_wrlock");1365}1366 1367TEST_F(PthreadRwlockTest, PthreadRwlockWrlockSurvivesWhenNonRealtime) {1368 auto Func = [this]() { WrLock(); };1369 1370 ExpectNonRealtimeSurvival(Func);1371}1372 1373/*1374 Sockets1375*/1376TEST(TestRtsanInterceptors, GetAddrInfoDiesWhenRealtime) {1377 auto Func = []() {1378 addrinfo *info{};1379 getaddrinfo("localhost", "http", nullptr, &info);1380 };1381 ExpectRealtimeDeath(Func, "getaddrinfo");1382 ExpectNonRealtimeSurvival(Func);1383}1384 1385TEST(TestRtsanInterceptors, GetNameInfoDiesWhenRealtime) {1386 auto Func = []() {1387 char host[NI_MAXHOST];1388 char serv[NI_MAXSERV];1389 getnameinfo(nullptr, 0, host, NI_MAXHOST, serv, NI_MAXSERV, 0);1390 };1391 ExpectRealtimeDeath(Func, "getnameinfo");1392 ExpectNonRealtimeSurvival(Func);1393}1394 1395TEST(TestRtsanInterceptors, BindingASocketDiesWhenRealtime) {1396 auto Func = []() { EXPECT_NE(bind(kNotASocketFd, nullptr, 0), 0); };1397 ExpectRealtimeDeath(Func, "bind");1398 ExpectNonRealtimeSurvival(Func);1399}1400 1401TEST(TestRtsanInterceptors, ListeningOnASocketDiesWhenRealtime) {1402 auto Func = []() { EXPECT_NE(listen(kNotASocketFd, 0), 0); };1403 ExpectRealtimeDeath(Func, "listen");1404 ExpectNonRealtimeSurvival(Func);1405}1406 1407TEST(TestRtsanInterceptors, AcceptingASocketDiesWhenRealtime) {1408 auto Func = []() { EXPECT_LT(accept(kNotASocketFd, nullptr, nullptr), 0); };1409 ExpectRealtimeDeath(Func, "accept");1410 ExpectNonRealtimeSurvival(Func);1411}1412 1413#if SANITIZER_INTERCEPT_ACCEPT41414TEST(TestRtsanInterceptors, Accepting4ASocketDiesWhenRealtime) {1415 auto Func = []() {1416 EXPECT_LT(accept4(kNotASocketFd, nullptr, nullptr, 0), 0);1417 };1418 ExpectRealtimeDeath(Func, "accept4");1419 ExpectNonRealtimeSurvival(Func);1420}1421#endif1422 1423TEST(TestRtsanInterceptors, ConnectingASocketDiesWhenRealtime) {1424 auto Func = []() { EXPECT_NE(connect(kNotASocketFd, nullptr, 0), 0); };1425 ExpectRealtimeDeath(Func, "connect");1426 ExpectNonRealtimeSurvival(Func);1427}1428 1429TEST(TestRtsanInterceptors, OpeningASocketDiesWhenRealtime) {1430 auto Func = []() { socket(PF_INET, SOCK_STREAM, 0); };1431 ExpectRealtimeDeath(Func, "socket");1432 ExpectNonRealtimeSurvival(Func);1433}1434 1435TEST(TestRtsanInterceptors, SendToASocketDiesWhenRealtime) {1436 auto Func = []() { send(0, nullptr, 0, 0); };1437 ExpectRealtimeDeath(Func, "send");1438 ExpectNonRealtimeSurvival(Func);1439}1440 1441TEST(TestRtsanInterceptors, SendmsgToASocketDiesWhenRealtime) {1442 msghdr msg{};1443 auto Func = [&]() { sendmsg(0, &msg, 0); };1444 ExpectRealtimeDeath(Func, "sendmsg");1445 ExpectNonRealtimeSurvival(Func);1446}1447 1448#if SANITIZER_INTERCEPT_SENDMMSG1449TEST(TestRtsanInterceptors, SendmmsgOnASocketDiesWhenRealtime) {1450 mmsghdr msg{};1451 auto Func = [&]() { sendmmsg(0, &msg, 0, 0); };1452 ExpectRealtimeDeath(Func, "sendmmsg");1453 ExpectNonRealtimeSurvival(Func);1454}1455#endif1456 1457TEST(TestRtsanInterceptors, SendtoToASocketDiesWhenRealtime) {1458 sockaddr addr{};1459 socklen_t len{};1460 auto Func = [&]() { sendto(0, nullptr, 0, 0, &addr, len); };1461 ExpectRealtimeDeath(Func, "sendto");1462 ExpectNonRealtimeSurvival(Func);1463}1464 1465TEST(TestRtsanInterceptors, RecvFromASocketDiesWhenRealtime) {1466 auto Func = []() { recv(0, nullptr, 0, 0); };1467 ExpectRealtimeDeath(Func, "recv");1468 ExpectNonRealtimeSurvival(Func);1469}1470 1471TEST(TestRtsanInterceptors, RecvfromOnASocketDiesWhenRealtime) {1472 sockaddr addr{};1473 socklen_t len{};1474 auto Func = [&]() { recvfrom(0, nullptr, 0, 0, &addr, &len); };1475 ExpectRealtimeDeath(Func, "recvfrom");1476 ExpectNonRealtimeSurvival(Func);1477}1478 1479TEST(TestRtsanInterceptors, RecvmsgOnASocketDiesWhenRealtime) {1480 msghdr msg{};1481 auto Func = [&]() { recvmsg(0, &msg, 0); };1482 ExpectRealtimeDeath(Func, "recvmsg");1483 ExpectNonRealtimeSurvival(Func);1484}1485 1486#if SANITIZER_INTERCEPT_RECVMMSG1487TEST(TestRtsanInterceptors, RecvmmsgOnASocketDiesWhenRealtime) {1488 mmsghdr msg{};1489 auto Func = [&]() { recvmmsg(0, &msg, 0, 0, nullptr); };1490 ExpectRealtimeDeath(Func, "recvmmsg");1491 ExpectNonRealtimeSurvival(Func);1492}1493#endif1494 1495TEST(TestRtsanInterceptors, ShutdownOnASocketDiesWhenRealtime) {1496 auto Func = [&]() { shutdown(0, 0); };1497 ExpectRealtimeDeath(Func, "shutdown");1498 ExpectNonRealtimeSurvival(Func);1499}1500 1501#if SANITIZER_INTERCEPT_GETSOCKNAME1502TEST(TestRtsanInterceptors, GetsocknameOnASocketDiesWhenRealtime) {1503 sockaddr addr{};1504 socklen_t len{};1505 auto Func = [&]() { getsockname(0, &addr, &len); };1506 ExpectRealtimeDeath(Func, "getsockname");1507 ExpectNonRealtimeSurvival(Func);1508}1509#endif1510 1511#if SANITIZER_INTERCEPT_GETPEERNAME1512TEST(TestRtsanInterceptors, GetpeernameOnASocketDiesWhenRealtime) {1513 sockaddr addr{};1514 socklen_t len{};1515 auto Func = [&]() { getpeername(0, &addr, &len); };1516 ExpectRealtimeDeath(Func, "getpeername");1517 ExpectNonRealtimeSurvival(Func);1518}1519#endif1520 1521#if SANITIZER_INTERCEPT_GETSOCKOPT1522TEST(TestRtsanInterceptors, GetsockoptOnASocketDiesWhenRealtime) {1523 int val = 0;1524 socklen_t len = static_cast<socklen_t>(sizeof(val));1525 auto Func = [&val, &len]() {1526 getsockopt(0, SOL_SOCKET, SO_REUSEADDR, &val, &len);1527 };1528 ExpectRealtimeDeath(Func, "getsockopt");1529 ExpectNonRealtimeSurvival(Func);1530}1531 1532TEST(TestRtsanInterceptors, SetsockoptOnASocketDiesWhenRealtime) {1533 int val = 0;1534 socklen_t len = static_cast<socklen_t>(sizeof(val));1535 auto Func = [&val, &len]() {1536 setsockopt(0, SOL_SOCKET, SO_REUSEADDR, &val, len);1537 };1538 ExpectRealtimeDeath(Func, "setsockopt");1539 ExpectNonRealtimeSurvival(Func);1540}1541#endif1542 1543TEST(TestRtsanInterceptors, SocketpairDiesWhenRealtime) {1544 int pair[2]{};1545 auto Func = [&pair]() { socketpair(0, 0, 0, pair); };1546 ExpectRealtimeDeath(Func, "socketpair");1547 ExpectNonRealtimeSurvival(Func);1548}1549 1550/*1551 I/O Multiplexing1552*/1553 1554TEST(TestRtsanInterceptors, PollDiesWhenRealtime) {1555 struct pollfd fds[1];1556 fds[0].fd = 0;1557 fds[0].events = POLLIN;1558 1559 auto Func = [&fds]() { poll(fds, 1, 0); };1560 1561 ExpectRealtimeDeath(Func, "poll");1562 ExpectNonRealtimeSurvival(Func);1563}1564 1565#if !SANITIZER_APPLE1566// FIXME: This should work on Darwin as well1567// see the comment near the interceptor1568TEST(TestRtsanInterceptors, SelectDiesWhenRealtime) {1569 fd_set readfds;1570 FD_ZERO(&readfds);1571 FD_SET(0, &readfds);1572 struct timeval timeout = {0, 0};1573 1574 auto Func = [&readfds, &timeout]() {1575 select(1, &readfds, nullptr, nullptr, &timeout);1576 };1577 ExpectRealtimeDeath(Func, "select");1578 ExpectNonRealtimeSurvival(Func);1579}1580#endif1581 1582TEST(TestRtsanInterceptors, PSelectDiesWhenRealtime) {1583 fd_set readfds;1584 FD_ZERO(&readfds);1585 FD_SET(0, &readfds);1586 struct timespec timeout = {0, 0};1587 1588 auto Func = [&]() {1589 pselect(1, &readfds, nullptr, nullptr, &timeout, nullptr);1590 };1591 ExpectRealtimeDeath(Func, "pselect");1592 ExpectNonRealtimeSurvival(Func);1593}1594 1595#if SANITIZER_INTERCEPT_EPOLL1596TEST(TestRtsanInterceptors, EpollCreateDiesWhenRealtime) {1597 auto Func = []() { epoll_create(1); };1598 ExpectRealtimeDeath(Func, "epoll_create");1599 ExpectNonRealtimeSurvival(Func);1600}1601 1602TEST(TestRtsanInterceptors, EpollCreate1DiesWhenRealtime) {1603 auto Func = []() { epoll_create1(EPOLL_CLOEXEC); };1604 ExpectRealtimeDeath(Func, "epoll_create1");1605 ExpectNonRealtimeSurvival(Func);1606}1607 1608class EpollTest : public ::testing::Test {1609protected:1610 void SetUp() override {1611 epfd = epoll_create1(EPOLL_CLOEXEC);1612 ASSERT_GE(epfd, 0);1613 }1614 1615 void TearDown() override {1616 if (epfd >= 0)1617 close(epfd);1618 }1619 1620 int GetEpollFd() { return epfd; }1621 1622private:1623 int epfd = -1;1624};1625 1626TEST_F(EpollTest, EpollCtlDiesWhenRealtime) {1627 auto Func = [this]() {1628 struct epoll_event event = {.events = EPOLLIN, .data = {.fd = 0}};1629 epoll_ctl(GetEpollFd(), EPOLL_CTL_ADD, 0, &event);1630 };1631 ExpectRealtimeDeath(Func, "epoll_ctl");1632 ExpectNonRealtimeSurvival(Func);1633}1634 1635TEST_F(EpollTest, EpollWaitDiesWhenRealtime) {1636 auto Func = [this]() {1637 struct epoll_event events[1];1638 epoll_wait(GetEpollFd(), events, 1, 0);1639 };1640 1641 ExpectRealtimeDeath(Func, "epoll_wait");1642 ExpectNonRealtimeSurvival(Func);1643}1644 1645TEST_F(EpollTest, EpollPWaitDiesWhenRealtime) {1646 auto Func = [this]() {1647 struct epoll_event events[1];1648 epoll_pwait(GetEpollFd(), events, 1, 0, nullptr);1649 };1650 1651 ExpectRealtimeDeath(Func, "epoll_pwait");1652 ExpectNonRealtimeSurvival(Func);1653}1654#endif // SANITIZER_INTERCEPT_EPOLL1655 1656#if SANITIZER_INTERCEPT_PPOLL1657TEST(TestRtsanInterceptors, PpollDiesWhenRealtime) {1658 struct pollfd fds[1];1659 fds[0].fd = 0;1660 fds[0].events = POLLIN;1661 1662 timespec ts = {0, 0};1663 1664 auto Func = [&fds, &ts]() { ppoll(fds, 1, &ts, nullptr); };1665 1666 ExpectRealtimeDeath(Func, "ppoll");1667 ExpectNonRealtimeSurvival(Func);1668}1669#endif1670 1671#if SANITIZER_INTERCEPT_KQUEUE1672TEST(TestRtsanInterceptors, KqueueDiesWhenRealtime) {1673 auto Func = []() { kqueue(); };1674 ExpectRealtimeDeath(Func, "kqueue");1675 ExpectNonRealtimeSurvival(Func);1676}1677 1678class KqueueTest : public ::testing::Test {1679protected:1680 void SetUp() override {1681 kq = kqueue();1682 ASSERT_GE(kq, 0);1683 }1684 1685 void TearDown() override {1686 if (kq >= 0)1687 close(kq);1688 }1689 1690 int GetKqueueFd() { return kq; }1691 1692private:1693 int kq = -1;1694};1695 1696TEST_F(KqueueTest, KeventDiesWhenRealtime) {1697 struct kevent event;1698 EV_SET(&event, 0, EVFILT_READ, EV_ADD, 0, 0, nullptr);1699 struct timespec timeout = {0, 0};1700 1701 auto Func = [this, event, timeout]() {1702 kevent(GetKqueueFd(), &event, 1, nullptr, 0, &timeout);1703 };1704 1705 ExpectRealtimeDeath(Func, "kevent");1706 ExpectNonRealtimeSurvival(Func);1707}1708 1709TEST_F(KqueueTest, Kevent64DiesWhenRealtime) {1710 struct kevent64_s event;1711 EV_SET64(&event, 0, EVFILT_READ, EV_ADD, 0, 0, 0, 0, 0);1712 struct timespec timeout = {0, 0};1713 1714 auto Func = [this, event, timeout]() {1715 kevent64(GetKqueueFd(), &event, 1, nullptr, 0, 0, &timeout);1716 };1717 1718 ExpectRealtimeDeath(Func, "kevent64");1719 ExpectNonRealtimeSurvival(Func);1720}1721#endif // SANITIZER_INTERCEPT_KQUEUE1722 1723#if SANITIZER_LINUX1724TEST(TestRtsanInterceptors, InotifyInitDiesWhenRealtime) {1725 auto Func = []() { inotify_init(); };1726 ExpectRealtimeDeath(Func, "inotify_init");1727 ExpectNonRealtimeSurvival(Func);1728}1729 1730TEST(TestRtsanInterceptors, InotifyInit1DiesWhenRealtime) {1731 auto Func = []() { inotify_init1(0); };1732 ExpectRealtimeDeath(Func, "inotify_init1");1733 ExpectNonRealtimeSurvival(Func);1734}1735 1736TEST(TestRtsanInterceptors, InotifyAddWatchDiesWhenRealtime) {1737 int fd = inotify_init();1738 EXPECT_THAT(fd, Ne(-1));1739 auto Func = [fd]() {1740 inotify_add_watch(fd, "/tmp/rtsan_inotify", IN_CREATE);1741 };1742 ExpectRealtimeDeath(Func, "inotify_add_watch");1743 ExpectNonRealtimeSurvival(Func);1744}1745 1746TEST(TestRtsanInterceptors, InotifyRmWatchDiesWhenRealtime) {1747 int fd = inotify_init();1748 EXPECT_THAT(fd, Ne(-1));1749 auto Func = [fd]() { inotify_rm_watch(fd, -1); };1750 ExpectRealtimeDeath(Func, "inotify_rm_watch");1751 ExpectNonRealtimeSurvival(Func);1752}1753 1754TEST(TestRtsanInterceptors, TimerfdCreateDiesWhenRealtime) {1755 auto Func = []() { timerfd_create(CLOCK_MONOTONIC, 0); };1756 ExpectRealtimeDeath(Func, "timerfd_create");1757 ExpectNonRealtimeSurvival(Func);1758}1759 1760TEST(TestRtsanInterceptors, TimerfdSettimeDiesWhenRealtime) {1761 int fd = timerfd_create(CLOCK_MONOTONIC, 0);1762 EXPECT_THAT(fd, Ne(-1));1763 auto ts = itimerspec{{0, 0}, {0, 0}};1764 auto Func = [fd, ts]() { timerfd_settime(fd, 0, &ts, NULL); };1765 ExpectRealtimeDeath(Func, "timerfd_settime");1766 ExpectNonRealtimeSurvival(Func);1767}1768 1769TEST(TestRtsanInterceptors, TimerfdGettimeDiesWhenRealtime) {1770 int fd = timerfd_create(CLOCK_MONOTONIC, 0);1771 EXPECT_THAT(fd, Ne(-1));1772 itimerspec ts{};1773 auto Func = [fd, &ts]() { timerfd_gettime(fd, &ts); };1774 ExpectRealtimeDeath(Func, "timerfd_gettime");1775 ExpectNonRealtimeSurvival(Func);1776}1777 1778TEST(TestRtsanInterceptors, EventfdDiesWhenRealtime) {1779 auto Func = []() { eventfd(EFD_CLOEXEC, 0); };1780 ExpectRealtimeDeath(Func, "eventfd");1781 ExpectNonRealtimeSurvival(Func);1782}1783#endif1784 1785TEST(TestRtsanInterceptors, MkfifoDiesWhenRealtime) {1786 auto Func = []() { mkfifo("/tmp/rtsan_test_fifo", 0); };1787 ExpectRealtimeDeath(Func, "mkfifo");1788 ExpectNonRealtimeSurvival(Func);1789}1790 1791TEST(TestRtsanInterceptors, PipeDiesWhenRealtime) {1792 int fds[2];1793 auto Func = [&fds]() { pipe(fds); };1794 ExpectRealtimeDeath(Func, "pipe");1795 ExpectNonRealtimeSurvival(Func);1796}1797 1798#if !SANITIZER_APPLE1799TEST(TestRtsanInterceptors, Pipe2DiesWhenRealtime) {1800 int fds[2];1801 auto Func = [&fds]() { pipe2(fds, O_CLOEXEC); };1802 ExpectRealtimeDeath(Func, "pipe2");1803 ExpectNonRealtimeSurvival(Func);1804}1805#endif1806 1807#pragma clang diagnostic push1808#pragma clang diagnostic ignored "-Wdeprecated-declarations"1809TEST(TestRtsanInterceptors, SyscallDiesWhenRealtime) {1810 auto Func = []() { syscall(SYS_getpid); };1811 ExpectRealtimeDeath(Func, "syscall");1812 ExpectNonRealtimeSurvival(Func);1813}1814 1815TEST(TestRtsanInterceptors, GetPidReturnsSame) {1816 int pid = syscall(SYS_getpid);1817 EXPECT_THAT(pid, Ne(-1));1818 1819 EXPECT_THAT(getpid(), Eq(pid));1820}1821#pragma clang diagnostic pop1822 1823#endif // SANITIZER_POSIX1824