]> AND Public Git Repository - simgrid.git/blob - src/mc/sosp/Snapshot_test.cpp
Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
try to solve the -Wundefined-var-template thing with clang
[simgrid.git] / src / mc / sosp / Snapshot_test.cpp
1 /* Copyright (c) 2014-2023. The SimGrid Team. All rights reserved.          */
2
3 /* This program is free software; you can redistribute it and/or modify it
4  * under the terms of the license (GNU LGPL) which comes with this package. */
5
6 #include "src/3rd-party/catch.hpp"
7 #include "src/mc/mc_config.hpp"
8 #include "src/mc/sosp/Snapshot.hpp"
9
10 #include <cstddef>
11 #include <memory>
12 #include <sys/mman.h>
13 #include <xbt/random.hpp>
14
15 /**************** Class BOOST_tests *************************/
16 using simgrid::mc::Region;
17 class snap_test_helper {
18   simgrid::mc::PageStore page_store_{500};
19   simgrid::mc::RemoteProcessMemory memory_{getpid(), nullptr};
20
21   struct prologue_return {
22     size_t size;
23     std::byte* src;
24     std::byte* dstn;
25     std::unique_ptr<Region> region0;
26     std::unique_ptr<Region> region;
27   };
28   prologue_return prologue(int n); // common to the below 5 fxs
29
30 public:
31   void read_whole_region();
32   void read_region_parts();
33   void compare_whole_region();
34   void compare_region_parts();
35   void read_pointer();
36
37   static void init_memory(std::byte* mem, size_t size);
38   static void basic_requirements();
39 };
40
41 void snap_test_helper::init_memory(std::byte* mem, size_t size)
42 {
43   std::generate_n(mem, size, []() { return static_cast<std::byte>(simgrid::xbt::random::uniform_int(0, 0xff)); });
44 }
45
46 void snap_test_helper::basic_requirements()
47 {
48   REQUIRE(xbt_pagesize == getpagesize());
49   REQUIRE(1 << xbt_pagebits == xbt_pagesize);
50 }
51
52 snap_test_helper::prologue_return snap_test_helper::prologue(int n)
53 {
54   // Store region page(s):
55   size_t byte_size = n * xbt_pagesize;
56   auto* source =
57       static_cast<std::byte*>(mmap(nullptr, byte_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0));
58   INFO("Could not allocate source memory");
59   REQUIRE(source != MAP_FAILED);
60
61   // Init memory and take snapshots:
62   init_memory(source, byte_size);
63   auto region0 =
64       std::make_unique<simgrid::mc::Region>(page_store_, memory_, simgrid::mc::RegionType::Data, source, byte_size);
65   for (int i = 0; i < n; i += 2) {
66     init_memory(source + i * xbt_pagesize, xbt_pagesize);
67   }
68   auto region =
69       std::make_unique<simgrid::mc::Region>(page_store_, memory_, simgrid::mc::RegionType::Data, source, byte_size);
70
71   auto* destination =
72       static_cast<std::byte*>(mmap(nullptr, byte_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0));
73   INFO("Could not allocate destination memory");
74   REQUIRE(destination != MAP_FAILED);
75
76   return {.size    = byte_size,
77           .src     = source,
78           .dstn    = destination,
79           .region0 = std::move(region0),
80           .region  = std::move(region)};
81 }
82
83 void snap_test_helper::read_whole_region()
84 {
85   for (int n = 1; n != 32; ++n) {
86     prologue_return ret = prologue(n);
87     const void* read    = ret.region->read(ret.dstn, ret.src, ret.size);
88     INFO("Mismatch in MC_region_read()");
89     REQUIRE(not memcmp(ret.src, read, ret.size));
90
91     munmap(ret.dstn, ret.size);
92     munmap(ret.src, ret.size);
93   }
94 }
95
96 void snap_test_helper::read_region_parts()
97 {
98   for (int n = 1; n != 32; ++n) {
99     prologue_return ret = prologue(n);
100
101     for (int j = 0; j != 100; ++j) {
102       size_t offset    = simgrid::xbt::random::uniform_int(0, ret.size - 1);
103       size_t size      = simgrid::xbt::random::uniform_int(0, ret.size - offset - 1);
104       const void* read = ret.region->read(ret.dstn, (const char*)ret.src + offset, size);
105       INFO("Mismatch in MC_region_read()");
106       REQUIRE(not memcmp((char*)ret.src + offset, read, size));
107     }
108     munmap(ret.dstn, ret.size);
109     munmap(ret.src, ret.size);
110   }
111 }
112
113 void snap_test_helper::compare_whole_region()
114 {
115   for (int n = 1; n != 32; ++n) {
116     prologue_return ret = prologue(n);
117
118     INFO("Unexpected match in MC_snapshot_region_memcmp() with previous snapshot");
119     REQUIRE(MC_snapshot_region_memcmp(ret.src, ret.region0.get(), ret.src, ret.region.get(), ret.size));
120
121     munmap(ret.dstn, ret.size);
122     munmap(ret.src, ret.size);
123   }
124 }
125
126 void snap_test_helper::compare_region_parts()
127 {
128   for (int n = 1; n != 32; ++n) {
129     prologue_return ret = prologue(n);
130
131     for (int j = 0; j != 100; ++j) {
132       size_t offset = simgrid::xbt::random::uniform_int(0, ret.size - 1);
133       size_t size   = simgrid::xbt::random::uniform_int(0, ret.size - offset - 1);
134
135       INFO("Mismatch in MC_snapshot_region_memcmp()");
136       REQUIRE(not MC_snapshot_region_memcmp((char*)ret.src + offset, ret.region.get(), (char*)ret.src + offset,
137                                             ret.region.get(), size));
138     }
139     munmap(ret.dstn, ret.size);
140     munmap(ret.src, ret.size);
141   }
142 }
143
144 const int some_global_variable  = 42;
145 const void* const some_global_pointer = &some_global_variable;
146 void snap_test_helper::read_pointer()
147 {
148   prologue_return ret = prologue(1);
149   memcpy(ret.src, &some_global_pointer, sizeof(void*));
150   const simgrid::mc::Region region2(page_store_, memory_, simgrid::mc::RegionType::Data, ret.src, ret.size);
151   INFO("Mismtach in MC_region_read_pointer()");
152   REQUIRE(MC_region_read_pointer(&region2, ret.src) == some_global_pointer);
153
154   munmap(ret.dstn, ret.size);
155   munmap(ret.src, ret.size);
156 }
157
158 /*************** End: class snap_test_helper *****************************/
159
160 TEST_CASE("MC::Snapshot: A copy/snapshot of a given memory region", "MC::Snapshot")
161 {
162   INFO("Sparse snapshot (using pages)");
163
164   snap_test_helper::basic_requirements();
165
166   snap_test_helper snap_test;
167
168   INFO("Read whole region");
169   snap_test.read_whole_region();
170
171   INFO("Read region parts");
172   snap_test.read_region_parts();
173
174   INFO("Compare whole region");
175   snap_test.compare_whole_region();
176
177   INFO("Compare region parts");
178   snap_test.compare_region_parts();
179
180   INFO("Read pointer");
181   snap_test.read_pointer();
182 }