mem_map_test.cc revision ef7d42fca18c16fbaf103822ad16f23246e2905d
1/*
2 * Copyright (C) 2013 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include "mem_map.h"
18
19#include "UniquePtr.h"
20#include "gtest/gtest.h"
21
22namespace art {
23
24class MemMapTest : public testing::Test {
25 public:
26  static byte* BaseBegin(MemMap* mem_map) {
27    return reinterpret_cast<byte*>(mem_map->base_begin_);
28  }
29  static size_t BaseSize(MemMap* mem_map) {
30    return mem_map->base_size_;
31  }
32
33  static void RemapAtEndTest(bool low_4gb) {
34    std::string error_msg;
35    // Cast the page size to size_t.
36    const size_t page_size = static_cast<size_t>(kPageSize);
37    // Map a two-page memory region.
38    MemMap* m0 = MemMap::MapAnonymous("MemMapTest_RemapAtEndTest_map0",
39                                      nullptr,
40                                      2 * page_size,
41                                      PROT_READ | PROT_WRITE,
42                                      low_4gb,
43                                      &error_msg);
44    // Check its state and write to it.
45    byte* base0 = m0->Begin();
46    ASSERT_TRUE(base0 != nullptr) << error_msg;
47    size_t size0 = m0->Size();
48    EXPECT_EQ(m0->Size(), 2 * page_size);
49    EXPECT_EQ(BaseBegin(m0), base0);
50    EXPECT_EQ(BaseSize(m0), size0);
51    memset(base0, 42, 2 * page_size);
52    // Remap the latter half into a second MemMap.
53    MemMap* m1 = m0->RemapAtEnd(base0 + page_size,
54                                "MemMapTest_RemapAtEndTest_map1",
55                                PROT_READ | PROT_WRITE,
56                                &error_msg);
57    // Check the states of the two maps.
58    EXPECT_EQ(m0->Begin(), base0) << error_msg;
59    EXPECT_EQ(m0->Size(), page_size);
60    EXPECT_EQ(BaseBegin(m0), base0);
61    EXPECT_EQ(BaseSize(m0), page_size);
62    byte* base1 = m1->Begin();
63    size_t size1 = m1->Size();
64    EXPECT_EQ(base1, base0 + page_size);
65    EXPECT_EQ(size1, page_size);
66    EXPECT_EQ(BaseBegin(m1), base1);
67    EXPECT_EQ(BaseSize(m1), size1);
68    // Write to the second region.
69    memset(base1, 43, page_size);
70    // Check the contents of the two regions.
71    for (size_t i = 0; i < page_size; ++i) {
72      EXPECT_EQ(base0[i], 42);
73    }
74    for (size_t i = 0; i < page_size; ++i) {
75      EXPECT_EQ(base1[i], 43);
76    }
77    // Unmap the first region.
78    delete m0;
79    // Make sure the second region is still accessible after the first
80    // region is unmapped.
81    for (size_t i = 0; i < page_size; ++i) {
82      EXPECT_EQ(base1[i], 43);
83    }
84    delete m1;
85  }
86};
87
88TEST_F(MemMapTest, MapAnonymousEmpty) {
89  std::string error_msg;
90  UniquePtr<MemMap> map(MemMap::MapAnonymous("MapAnonymousEmpty",
91                                             nullptr,
92                                             0,
93                                             PROT_READ,
94                                             false,
95                                             &error_msg));
96  ASSERT_TRUE(map.get() != nullptr) << error_msg;
97  ASSERT_TRUE(error_msg.empty());
98  map.reset(MemMap::MapAnonymous("MapAnonymousEmpty",
99                                 nullptr,
100                                 kPageSize,
101                                 PROT_READ | PROT_WRITE,
102                                 false,
103                                 &error_msg));
104  ASSERT_TRUE(map.get() != nullptr) << error_msg;
105  ASSERT_TRUE(error_msg.empty());
106}
107
108#ifdef __LP64__
109TEST_F(MemMapTest, MapAnonymousEmpty32bit) {
110  std::string error_msg;
111  UniquePtr<MemMap> map(MemMap::MapAnonymous("MapAnonymousEmpty",
112                                             nullptr,
113                                             kPageSize,
114                                             PROT_READ | PROT_WRITE,
115                                             true,
116                                             &error_msg));
117  ASSERT_TRUE(map.get() != nullptr) << error_msg;
118  ASSERT_TRUE(error_msg.empty());
119  ASSERT_LT(reinterpret_cast<uintptr_t>(BaseBegin(map.get())), 1ULL << 32);
120}
121#endif
122
123TEST_F(MemMapTest, RemapAtEnd) {
124  RemapAtEndTest(false);
125}
126
127#ifdef __LP64__
128TEST_F(MemMapTest, RemapAtEnd32bit) {
129  RemapAtEndTest(true);
130}
131#endif
132
133}  // namespace art
134