summaryrefslogtreecommitdiff
path: root/view/sharedcache/core/MappedFileAccessor.cpp
diff options
context:
space:
mode:
authorMark Rowe <mark@vector35.com>2026-02-23 23:26:27 -0800
committerMark Rowe <mark@vector35.com>2026-02-24 14:24:54 -0800
commita72b98ed5a357bb380d81f07f3f36946aa729bb2 (patch)
treeca48b3607721fa2c109b7989ae4b911bab89ea6d /view/sharedcache/core/MappedFileAccessor.cpp
parent3eda43f185a0411538745a99e251122e6a9192e0 (diff)
[DSC] Simplify file mapping to fix intermittent unrelocated pointers
The `FileAccessorCache`'s LRU eviction could discard a file's mapped data after slide info had already been applied to it. Future accesses to the file produced a fresh mapping, but failed to reapply the slide info. This could result in pointers not correctly being slid, such as in https://github.com/Vector35/binaryninja-api/issues/7689. The LRU cache existed to stay within OS file descriptor limits, since the old `MappedFile` held its fd open for the lifetime of the mapping. There's no real reason for it to hold the file descriptor open like this. Closing it after `mmap` is sufficient to avoid the file descriptor limits. `MappedFileRegion` replaces the combination of `FileAccessorCache`, `WeakFileAccessor`, and `MappedFileAccessor`. It closes the fd immediately after mmap, so all files can stay mapped without consuming descriptors, making the cache unnecessary. `MappedFileRegion` is owned directly by the `CacheEntry` for its full lifetime. Slide info is applied exactly once to each `MappedFileRegion`.
Diffstat (limited to 'view/sharedcache/core/MappedFileAccessor.cpp')
-rw-r--r--view/sharedcache/core/MappedFileAccessor.cpp111
1 files changed, 0 insertions, 111 deletions
diff --git a/view/sharedcache/core/MappedFileAccessor.cpp b/view/sharedcache/core/MappedFileAccessor.cpp
deleted file mode 100644
index 4f9f99a8..00000000
--- a/view/sharedcache/core/MappedFileAccessor.cpp
+++ /dev/null
@@ -1,111 +0,0 @@
-#include "MappedFileAccessor.h"
-
-std::shared_ptr<MappedFileAccessor> MappedFileAccessor::Open(const std::string& filePath)
-{
- auto file = MappedFile::OpenFile(filePath);
- if (!file.has_value())
- return nullptr;
- if (file->Map() != MapStatus::Success)
- return nullptr;
- return std::make_shared<MappedFileAccessor>(std::move(*file));
-}
-
-// TODO: Will obviously not work on 32bit binaries, need to make WritePointer64 and 32 equiv.
-void MappedFileAccessor::WritePointer(size_t address, size_t pointer)
-{
- if (address + sizeof(size_t*) > Length())
- throw UnmappedAccessException(address + sizeof(size_t*), Length());
- m_dirty = true;
- *reinterpret_cast<size_t*>(&m_file._mmap[address]) = pointer;
-}
-
-std::string MappedFileAccessor::ReadNullTermString(size_t address, const size_t maxLength) const
-{
- if (address > Length())
- return "";
- // If we are not given a maxLength (i.e. -1) than we will set the max address to the length of the file.
- const size_t maxAddr = (maxLength != -1) ? std::min(address + maxLength, Length()) : Length();
- // Read a null-terminated string manually to avoid errors related to string length on Linux.
- std::string str;
- str.reserve(140);
- for (size_t currAddr = address; currAddr < maxAddr; ++currAddr)
- {
- char c = m_file._mmap[currAddr];
- if (c == '\0')
- break;
- str += c;
- }
- str.shrink_to_fit();
- return str;
-}
-
-uint8_t MappedFileAccessor::ReadUInt8(size_t address) const
-{
- return Read<uint8_t>(address);
-}
-
-int8_t MappedFileAccessor::ReadInt8(size_t address) const
-{
- return Read<int8_t>(address);
-}
-
-uint16_t MappedFileAccessor::ReadUInt16(size_t address) const
-{
- return Read<uint16_t>(address);
-}
-
-int16_t MappedFileAccessor::ReadInt16(size_t address) const
-{
- return Read<int16_t>(address);
-}
-
-
-uint32_t MappedFileAccessor::ReadUInt32(size_t address) const
-{
- return Read<uint32_t>(address);
-}
-
-int32_t MappedFileAccessor::ReadInt32(size_t address) const
-{
- return Read<int32_t>(address);
-}
-
-uint64_t MappedFileAccessor::ReadUInt64(size_t address) const
-{
- return Read<uint64_t>(address);
-}
-
-int64_t MappedFileAccessor::ReadInt64(size_t address) const
-{
- return Read<int64_t>(address);
-}
-
-BinaryNinja::DataBuffer MappedFileAccessor::ReadBuffer(size_t addr, size_t length) const
-{
- if (addr + length > Length())
- throw UnmappedAccessException(addr + length, Length());
- return {&m_file._mmap[addr], length};
-}
-
-std::pair<const uint8_t*, const uint8_t*> MappedFileAccessor::ReadSpan(size_t addr, size_t length)
-{
- if (addr + length > Length())
- throw UnmappedAccessException(addr + length, Length());
- const uint8_t* data = &m_file._mmap[addr];
- return {data, data + length};
-}
-
-void MappedFileAccessor::Read(void* dest, size_t addr, size_t length) const
-{
- if (addr + length > Length())
- throw UnmappedAccessException(addr + length, Length());
- memcpy(dest, &m_file._mmap[addr], length);
-}
-
-template <typename T>
-T MappedFileAccessor::Read(size_t address) const
-{
- T result;
- Read(&result, address, sizeof(T));
- return result;
-}