xref: /llvm-project/libc/test/src/sys/mman/linux/shm_test.cpp (revision 04aaa35d40d8c5ff030014866691f9a56e59c142)
1f6f42af0SSchrodinger ZHU Yifan //===-- Unittests for shm_open/shm_unlink ---------------------------------===//
2f6f42af0SSchrodinger ZHU Yifan //
3f6f42af0SSchrodinger ZHU Yifan // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4f6f42af0SSchrodinger ZHU Yifan // See https://llvm.org/LICENSE.txt for license information.
5f6f42af0SSchrodinger ZHU Yifan // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f6f42af0SSchrodinger ZHU Yifan //
7f6f42af0SSchrodinger ZHU Yifan //===----------------------------------------------------------------------===//
8f6f42af0SSchrodinger ZHU Yifan 
9e241964bSMichael Jones #include "hdr/fcntl_macros.h"
10f6f42af0SSchrodinger ZHU Yifan #include "src/__support/OSUtil/syscall.h"
114f77677cSMikhail R. Gadelha #include "src/fcntl/fcntl.h"
12f6f42af0SSchrodinger ZHU Yifan #include "src/sys/mman/mmap.h"
13f6f42af0SSchrodinger ZHU Yifan #include "src/sys/mman/munmap.h"
14f6f42af0SSchrodinger ZHU Yifan #include "src/sys/mman/shm_open.h"
15f6f42af0SSchrodinger ZHU Yifan #include "src/sys/mman/shm_unlink.h"
16f6f42af0SSchrodinger ZHU Yifan #include "src/unistd/close.h"
17f6f42af0SSchrodinger ZHU Yifan #include "src/unistd/ftruncate.h"
18f6f42af0SSchrodinger ZHU Yifan #include "test/UnitTest/ErrnoSetterMatcher.h"
19*04aaa35dSMichael Jones #include "test/UnitTest/Test.h"
20f6f42af0SSchrodinger ZHU Yifan #include <sys/syscall.h>
21f6f42af0SSchrodinger ZHU Yifan 
22f6f42af0SSchrodinger ZHU Yifan using namespace LIBC_NAMESPACE::testing::ErrnoSetterMatcher;
23f6f42af0SSchrodinger ZHU Yifan // since shm_open/shm_unlink are wrappers around open/unlink, we only focus on
24f6f42af0SSchrodinger ZHU Yifan // testing basic cases and name conversions.
25f6f42af0SSchrodinger ZHU Yifan 
26f6f42af0SSchrodinger ZHU Yifan TEST(LlvmLibcShmTest, Basic) {
27f6f42af0SSchrodinger ZHU Yifan   const char *name = "/test_shm_open";
28f6f42af0SSchrodinger ZHU Yifan   int fd;
29f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(fd = LIBC_NAMESPACE::shm_open(name, O_CREAT | O_RDWR, 0666),
30f6f42af0SSchrodinger ZHU Yifan               returns(GE(0)).with_errno(EQ(0)));
31f6f42af0SSchrodinger ZHU Yifan 
32f6f42af0SSchrodinger ZHU Yifan   // check that FD_CLOEXEC is set by default.
334f77677cSMikhail R. Gadelha   long flag = LIBC_NAMESPACE::fcntl(fd, F_GETFD);
34f6f42af0SSchrodinger ZHU Yifan   ASSERT_GE(static_cast<int>(flag), 0);
35f6f42af0SSchrodinger ZHU Yifan   EXPECT_NE(static_cast<int>(flag) & FD_CLOEXEC, 0);
36f6f42af0SSchrodinger ZHU Yifan 
37f6f42af0SSchrodinger ZHU Yifan   // allocate space using ftruncate
38f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::ftruncate(fd, 4096), Succeeds());
39f6f42af0SSchrodinger ZHU Yifan   // map the shared memory
40f6f42af0SSchrodinger ZHU Yifan   void *addr = LIBC_NAMESPACE::mmap(nullptr, 4096, PROT_READ | PROT_WRITE,
41f6f42af0SSchrodinger ZHU Yifan                                     MAP_SHARED, fd, 0);
42f6f42af0SSchrodinger ZHU Yifan   ASSERT_NE(addr, MAP_FAILED);
43f6f42af0SSchrodinger ZHU Yifan   // just write random data to the shared memory
44f6f42af0SSchrodinger ZHU Yifan   char data[] = "Despite its name, LLVM has little to do with traditional "
45f6f42af0SSchrodinger ZHU Yifan                 "virtual machines.";
46f6f42af0SSchrodinger ZHU Yifan   for (size_t i = 0; i < sizeof(data); ++i)
47f6f42af0SSchrodinger ZHU Yifan     static_cast<char *>(addr)[i] = data[i];
48f6f42af0SSchrodinger ZHU Yifan 
49f6f42af0SSchrodinger ZHU Yifan   // close fd does not affect the mapping
50f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::close(fd), Succeeds());
51f6f42af0SSchrodinger ZHU Yifan   for (size_t i = 0; i < sizeof(data); ++i)
52f6f42af0SSchrodinger ZHU Yifan     EXPECT_EQ(static_cast<char *>(addr)[i], data[i]);
53f6f42af0SSchrodinger ZHU Yifan 
54f6f42af0SSchrodinger ZHU Yifan   // unmap the shared memory
55f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::munmap(addr, 4096), Succeeds());
56f6f42af0SSchrodinger ZHU Yifan   // remove the shared memory
57f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::shm_unlink(name), Succeeds());
58f6f42af0SSchrodinger ZHU Yifan }
59f6f42af0SSchrodinger ZHU Yifan 
60f6f42af0SSchrodinger ZHU Yifan TEST(LlvmLibcShmTest, NameConversion) {
61f6f42af0SSchrodinger ZHU Yifan   const char *name = "////test_shm_open";
62f6f42af0SSchrodinger ZHU Yifan   int fd;
63f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(fd = LIBC_NAMESPACE::shm_open(name, O_CREAT | O_RDWR, 0666),
64f6f42af0SSchrodinger ZHU Yifan               returns(GE(0)).with_errno(EQ(0)));
65f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::close(fd), Succeeds());
66f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::shm_unlink(name), Succeeds());
67f6f42af0SSchrodinger ZHU Yifan 
68f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::shm_open("/123/123", O_CREAT | O_RDWR, 0666),
69f6f42af0SSchrodinger ZHU Yifan               Fails(EINVAL));
70f6f42af0SSchrodinger ZHU Yifan 
71f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::shm_open("/.", O_CREAT | O_RDWR, 0666),
72f6f42af0SSchrodinger ZHU Yifan               Fails(EINVAL));
73f6f42af0SSchrodinger ZHU Yifan 
74f6f42af0SSchrodinger ZHU Yifan   ASSERT_THAT(LIBC_NAMESPACE::shm_open("/..", O_CREAT | O_RDWR, 0666),
75f6f42af0SSchrodinger ZHU Yifan               Fails(EINVAL));
76f6f42af0SSchrodinger ZHU Yifan }
77