Skip to content

Commit 9f05bd7

Browse files
committed
feat: add write option to MemoryMap
1 parent d81a674 commit 9f05bd7

2 files changed

Lines changed: 30 additions & 28 deletions

File tree

include/REX/REX/MemoryMap.h

Lines changed: 15 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -54,34 +54,36 @@ namespace REX
5454
return m_file != REX::W32::INVALID_HANDLE_VALUE;
5555
}
5656

57-
bool create(const std::string_view a_name, std::size_t a_size)
57+
bool create(bool a_write, const std::string_view a_name, std::size_t a_size)
5858
{
5959
close();
6060

61-
if (create_impl(a_name, a_size))
61+
if (create_impl(a_write, a_name, a_size))
6262
return true;
6363

6464
close();
6565
return false;
6666
}
6767

68-
bool create(std::filesystem::path a_path, const std::string_view a_name, std::size_t a_size = DYNAMIC_SIZE)
68+
bool create(bool a_write, std::filesystem::path a_path, const std::string_view a_name, std::size_t a_size = DYNAMIC_SIZE)
6969
{
7070
close();
7171

72-
m_file = REX::W32::CreateFileW(a_path.c_str(), REX::W32::GENERIC_READ | REX::W32::GENERIC_WRITE, REX::W32::FILE_SHARE_READ | REX::W32::FILE_SHARE_WRITE, nullptr, REX::W32::OPEN_EXISTING, REX::W32::FILE_ATTRIBUTE_READONLY, nullptr);
72+
const auto access = a_write ? REX::W32::GENERIC_READ | REX::W32::GENERIC_WRITE : REX::W32::GENERIC_READ;
73+
const auto share = a_write ? REX::W32::FILE_SHARE_READ | REX::W32::FILE_SHARE_WRITE : REX::W32::FILE_SHARE_READ;
74+
m_file = REX::W32::CreateFileW(a_path.c_str(), access, share, nullptr, REX::W32::OPEN_EXISTING, REX::W32::FILE_ATTRIBUTE_READONLY, nullptr);
7375
if (m_file == REX::W32::INVALID_HANDLE_VALUE)
7476
return false;
7577

76-
if (create_impl(a_name, a_size))
78+
if (create_impl(a_write, a_name, a_size))
7779
return true;
7880

7981
close();
8082
return false;
8183
}
8284

8385
private:
84-
bool create_impl(const std::string_view a_name, std::size_t a_size)
86+
bool create_impl(bool a_write, const std::string_view a_name, std::size_t a_size)
8587
{
8688
REX::W32::LARGE_INTEGER size;
8789
if (a_size == DYNAMIC_SIZE) {
@@ -90,21 +92,23 @@ namespace REX
9092

9193
if (REX::W32::GetFileSizeEx(m_file, &size) == 0)
9294
return false;
95+
9396
} else {
9497
size.value = a_size;
9598
}
9699

97-
m_map = REX::W32::OpenFileMappingA(REX::W32::FILE_MAP_READ | REX::W32::FILE_MAP_WRITE, false, a_name.data());
100+
const auto access = a_write ? REX::W32::FILE_MAP_READ | REX::W32::FILE_MAP_WRITE : REX::W32::FILE_MAP_READ;
101+
m_map = REX::W32::OpenFileMappingA(access, false, a_name.data());
98102
if (!m_map) {
99-
m_map = REX::W32::CreateFileMappingA(m_file, nullptr, REX::W32::PAGE_READWRITE, size.hi, size.lo, a_name.data());
100-
if (!m_map) {
103+
const auto protect = a_write ? REX::W32::PAGE_READWRITE : REX::W32::PAGE_READONLY;
104+
m_map = REX::W32::CreateFileMappingA(m_file, nullptr, protect, size.hi, size.lo, a_name.data());
105+
if (!m_map)
101106
return false;
102-
}
103107

104108
m_owner = true;
105109
}
106110

107-
m_mapView = REX::W32::MapViewOfFile(m_map, REX::W32::FILE_MAP_READ | REX::W32::FILE_MAP_WRITE, 0, 0, size.value);
111+
m_mapView = REX::W32::MapViewOfFile(m_map, access, 0, 0, size.value);
108112
if (!m_mapView)
109113
return false;
110114

src/REL/IDDB.cpp

Lines changed: 15 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -163,20 +163,19 @@ namespace REL
163163

164164
const auto mapName = std::format("COMMONLIB_IDDB_OFFSETS_{}", mod->version().string("_"));
165165
const auto byteSize = static_cast<std::size_t>(header.address_count()) * sizeof(mapping_t);
166-
if (m_mmap.create(mapName, byteSize)) {
167-
m_id2offset = { reinterpret_cast<mapping_t*>(m_mmap.data()), header.address_count() };
168-
169-
if (m_mmap.is_owner()) {
170-
unpack_file(in, header);
171-
std::sort(
172-
m_id2offset.begin(),
173-
m_id2offset.end(),
174-
[](auto&& a_lhs, auto&& a_rhs) {
175-
return a_lhs.id < a_rhs.id;
176-
});
177-
}
178-
} else {
179-
REX::FAIL("Failed to create shared mapping!");
166+
if (!m_mmap.create(true, mapName, byteSize))
167+
REX::FAIL("Failed to create Address Library MemoryMap!\nError: {}", REX::W32::GetLastError());
168+
169+
m_id2offset = { reinterpret_cast<mapping_t*>(m_mmap.data()), header.address_count() };
170+
171+
if (m_mmap.is_owner()) {
172+
unpack_file(in, header);
173+
std::sort(
174+
m_id2offset.begin(),
175+
m_id2offset.end(),
176+
[](auto&& a_lhs, auto&& a_rhs) {
177+
return a_lhs.id < a_rhs.id;
178+
});
180179
}
181180
} catch (const std::system_error&) {
182181
REX::FAIL(L"Failed to open Address Library file!\nPath: {}", m_path.wstring());
@@ -187,9 +186,8 @@ namespace REL
187186
{
188187
const auto mod = Module::GetSingleton();
189188
const auto mapName = std::format("COMMONLIB_IDDB_OFFSETS_{}", mod->version().string("_"));
190-
if (!m_mmap.create(m_path, mapName)) {
191-
REX::FAIL(L"Failed to open Address Library file!\nPath: {}", m_path.wstring());
192-
}
189+
if (!m_mmap.create(false, m_path, mapName))
190+
REX::FAIL(L"Failed to create Address Library MemoryMap!\nError: {}\nPath: {}", REX::W32::GetLastError(), m_path.wstring());
193191

194192
m_id2offset = {
195193
reinterpret_cast<mapping_t*>(m_mmap.data() + sizeof(std::uint64_t)),

0 commit comments

Comments
 (0)