diff options
Diffstat (limited to 'view/sharedcache/core/SharedCache.cpp')
| -rw-r--r-- | view/sharedcache/core/SharedCache.cpp | 152 |
1 files changed, 80 insertions, 72 deletions
diff --git a/view/sharedcache/core/SharedCache.cpp b/view/sharedcache/core/SharedCache.cpp index b734a6b1..0f61da63 100644 --- a/view/sharedcache/core/SharedCache.cpp +++ b/view/sharedcache/core/SharedCache.cpp @@ -133,6 +133,24 @@ std::string base_name(std::string const& path) return path.substr(path.find_last_of("/\\") + 1); } +BNSegmentFlag SegmentFlagsFromMachOProtections(int initProt, int maxProt) { + + uint32_t flags = 0; + if (initProt & MACHO_VM_PROT_READ) + flags |= SegmentReadable; + if (initProt & MACHO_VM_PROT_WRITE) + flags |= SegmentWritable; + if (initProt & MACHO_VM_PROT_EXECUTE) + flags |= SegmentExecutable; + if (((initProt & MACHO_VM_PROT_WRITE) == 0) && + ((maxProt & MACHO_VM_PROT_WRITE) == 0)) + flags |= SegmentDenyWrite; + if (((initProt & MACHO_VM_PROT_EXECUTE) == 0) && + ((maxProt & MACHO_VM_PROT_EXECUTE) == 0)) + flags |= SegmentDenyExecute; + return (BNSegmentFlag)flags; +} + #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wunused-function" @@ -305,11 +323,7 @@ void SharedCache::PerformInitialLoad() for (size_t i = 0; i < primaryCacheHeader.mappingCount; i++) { baseFile->Read(&mapping, primaryCacheHeader.mappingOffset + (i * sizeof(mapping)), sizeof(mapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = mapping.fileOffset; - mapRawToAddrAndSize.second.first = mapping.address; - mapRawToAddrAndSize.second.second = mapping.size; - cache.mappings.push_back(mapRawToAddrAndSize); + cache.mappings.push_back(mapping); } MutableState().backingCaches.push_back(std::move(cache)); @@ -373,11 +387,7 @@ void SharedCache::PerformInitialLoad() for (size_t i = 0; i < primaryCacheHeader.mappingCount; i++) { baseFile->Read(&mapping, primaryCacheHeader.mappingOffset + (i * sizeof(mapping)), sizeof(mapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = mapping.fileOffset; - mapRawToAddrAndSize.second.first = mapping.address; - mapRawToAddrAndSize.second.second = mapping.size; - cache.mappings.push_back(std::move(mapRawToAddrAndSize)); + cache.mappings.push_back(mapping); } MutableState().backingCaches.push_back(std::move(cache)); @@ -449,11 +459,7 @@ void SharedCache::PerformInitialLoad() { subCacheFile->Read(&subCacheMapping, subCacheHeader.mappingOffset + (j * sizeof(subCacheMapping)), sizeof(subCacheMapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = subCacheMapping.fileOffset; - mapRawToAddrAndSize.second.first = subCacheMapping.address; - mapRawToAddrAndSize.second.second = subCacheMapping.size; - subCache.mappings.push_back(std::move(mapRawToAddrAndSize)); + subCache.mappings.push_back(subCacheMapping); } if (subCacheHeader.mappingCount == 1 && subCacheHeader.imagesCountOld == 0 && subCacheHeader.imagesCount == 0 @@ -485,11 +491,7 @@ void SharedCache::PerformInitialLoad() for (size_t i = 0; i < primaryCacheHeader.mappingCount; i++) { baseFile->Read(&mapping, primaryCacheHeader.mappingOffset + (i * sizeof(mapping)), sizeof(mapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = mapping.fileOffset; - mapRawToAddrAndSize.second.first = mapping.address; - mapRawToAddrAndSize.second.second = mapping.size; - cache.mappings.push_back(std::move(mapRawToAddrAndSize)); + cache.mappings.push_back(mapping); } MutableState().backingCaches.push_back(std::move(cache)); @@ -545,11 +547,7 @@ void SharedCache::PerformInitialLoad() { subCacheFile->Read(&subCacheMapping, subCacheHeader.mappingOffset + (j * sizeof(subCacheMapping)), sizeof(subCacheMapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = subCacheMapping.fileOffset; - mapRawToAddrAndSize.second.first = subCacheMapping.address; - mapRawToAddrAndSize.second.second = subCacheMapping.size; - subCache.mappings.push_back(std::move(mapRawToAddrAndSize)); + subCache.mappings.push_back(subCacheMapping); } MutableState().backingCaches.push_back(std::move(subCache)); @@ -591,11 +589,7 @@ void SharedCache::PerformInitialLoad() { subCacheFile->Read(&subCacheMapping, subCacheHeader.mappingOffset + (j * sizeof(subCacheMapping)), sizeof(subCacheMapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = subCacheMapping.fileOffset; - mapRawToAddrAndSize.second.first = subCacheMapping.address; - mapRawToAddrAndSize.second.second = subCacheMapping.size; - subCache.mappings.push_back(std::move(mapRawToAddrAndSize)); + subCache.mappings.push_back(subCacheMapping); } MutableState().backingCaches.push_back(std::move(subCache)); @@ -612,11 +606,7 @@ void SharedCache::PerformInitialLoad() for (size_t i = 0; i < primaryCacheHeader.mappingCount; i++) { baseFile->Read(&mapping, primaryCacheHeader.mappingOffset + (i * sizeof(mapping)), sizeof(mapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = mapping.fileOffset; - mapRawToAddrAndSize.second.first = mapping.address; - mapRawToAddrAndSize.second.second = mapping.size; - cache.mappings.push_back(std::move(mapRawToAddrAndSize)); + cache.mappings.push_back(mapping); } MutableState().backingCaches.push_back(std::move(cache)); @@ -694,12 +684,7 @@ void SharedCache::PerformInitialLoad() { subCacheFile->Read(&subCacheMapping, subCacheHeader.mappingOffset + (j * sizeof(subCacheMapping)), sizeof(subCacheMapping)); - - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = subCacheMapping.fileOffset; - mapRawToAddrAndSize.second.first = subCacheMapping.address; - mapRawToAddrAndSize.second.second = subCacheMapping.size; - subCache.mappings.push_back(std::move(mapRawToAddrAndSize)); + subCache.mappings.push_back(subCacheMapping); if (subCachePath.find(".dylddata") != std::string::npos) { @@ -756,11 +741,7 @@ void SharedCache::PerformInitialLoad() { subCacheFile->Read(&subCacheMapping, subCacheHeader.mappingOffset + (j * sizeof(subCacheMapping)), sizeof(subCacheMapping)); - std::pair<uint64_t, std::pair<uint64_t, uint64_t>> mapRawToAddrAndSize; - mapRawToAddrAndSize.first = subCacheMapping.fileOffset; - mapRawToAddrAndSize.second.first = subCacheMapping.address; - mapRawToAddrAndSize.second.second = subCacheMapping.size; - subCache.mappings.push_back(std::move(mapRawToAddrAndSize)); + subCache.mappings.push_back(subCacheMapping); } MutableState().backingCaches.push_back(std::move(subCache)); @@ -806,19 +787,7 @@ void SharedCache::PerformInitialLoad() sectionRegion.prettyName = imageHeader.value().identifierPrefix + "::" + std::string(segName); sectionRegion.start = segment.vmaddr; sectionRegion.size = segment.vmsize; - uint32_t flags = 0; - if (segment.initprot & MACHO_VM_PROT_READ) - flags |= SegmentReadable; - if (segment.initprot & MACHO_VM_PROT_WRITE) - flags |= SegmentWritable; - if (segment.initprot & MACHO_VM_PROT_EXECUTE) - flags |= SegmentExecutable; - if (((segment.initprot & MACHO_VM_PROT_WRITE) == 0) && - ((segment.maxprot & MACHO_VM_PROT_WRITE) == 0)) - flags |= SegmentDenyWrite; - if (((segment.initprot & MACHO_VM_PROT_EXECUTE) == 0) && - ((segment.maxprot & MACHO_VM_PROT_EXECUTE) == 0)) - flags |= SegmentDenyExecute; + uint32_t flags = SegmentFlagsFromMachOProtections(segment.initprot, segment.maxprot); // if we're positive we have an entry point for some reason, force the segment // executable. this helps with kernel images. @@ -850,11 +819,10 @@ void SharedCache::PerformInitialLoad() for (const auto& mapping : cache.mappings) { MemoryRegion region; - region.start = mapping.second.first; - region.size = mapping.second.second; + region.start = mapping.address; + region.size = mapping.size; region.prettyName = base_name(cache.path) + "::" + std::to_string(i); - // FIXME flags!!! BackingCache.mapping needs refactored to store this information! - region.flags = (BNSegmentFlag)(BNSegmentFlag::SegmentReadable | BNSegmentFlag::SegmentExecutable); + region.flags = SegmentFlagsFromMachOProtections(mapping.initProt, mapping.maxProt); MutableState().nonImageRegions.push_back(std::move(region)); i++; } @@ -998,7 +966,7 @@ std::shared_ptr<VM> SharedCache::GetVMMap(bool mapPages) { for (const auto& mapping : cache.mappings) { - vm->MapPages(m_dscView, m_dscView->GetFile()->GetSessionId(), mapping.second.first, mapping.first, mapping.second.second, cache.path, + vm->MapPages(m_dscView, m_dscView->GetFile()->GetSessionId(), mapping.address, mapping.fileOffset, mapping.size, cache.path, [this, vm=vm](std::shared_ptr<MMappedFileAccessor> mmap){ ParseAndApplySlideInfoForFile(mmap); }); @@ -1065,9 +1033,9 @@ void SharedCache::ParseAndApplySlideInfoForFile(std::shared_ptr<MMappedFileAcces { for (const auto& mapping : backingCache.mappings) { - if (mapping.second.first < base) + if (mapping.address < base) { - base = mapping.second.first; + base = mapping.address; break; } } @@ -1696,7 +1664,7 @@ bool SharedCache::LoadSectionAtAddress(uint64_t address) m_dscView->GetParentView()->WriteBuffer(rawViewEnd, buff); m_dscView->GetParentView()->AddAutoSegment(rawViewEnd, region.size, rawViewEnd, region.size, region.flags); m_dscView->AddUserSegment(region.start, region.size, rawViewEnd, region.size, region.flags); - m_dscView->AddUserSection(name, region.start, region.size, ReadOnlyCodeSectionSemantics); + m_dscView->AddUserSection(name, region.start, region.size, region.flags & SegmentDenyExecute ? ReadOnlyDataSectionSemantics : ReadOnlyCodeSectionSemantics); m_dscView->WriteBuffer(region.start, buff); region.loaded = true; @@ -3298,11 +3266,11 @@ extern "C" mappings = (BNDSCBackingCacheMapping*)malloc(sizeof(BNDSCBackingCacheMapping) * viewCaches[i].mappings.size()); size_t j = 0; - for (const auto& [fileOffset, mapping] : viewCaches[i].mappings) + for (const auto& mapping : viewCaches[i].mappings) { - mappings[j].vmAddress = mapping.first; - mappings[j].size = mapping.second; - mappings[j].fileOffset = fileOffset; + mappings[j].vmAddress = mapping.address; + mappings[j].size = mapping.size; + mappings[j].fileOffset = mapping.fileOffset; j++; } caches[i].mappings = mappings; @@ -3445,6 +3413,34 @@ void InitDSCViewType() namespace SharedCacheCore { +void Serialize(SerializationContext& context, const dyld_cache_mapping_info& value) +{ + context.writer.StartArray(); + Serialize(context, value.address); + Serialize(context, value.size); + Serialize(context, value.fileOffset); + Serialize(context, value.maxProt); + Serialize(context, value.initProt); + context.writer.EndArray(); +} + +void Deserialize(DeserializationContext& context, std::string_view name, std::vector<dyld_cache_mapping_info>& b) +{ + + auto bArr = context.doc[name.data()].GetArray(); + for (auto& s : bArr) + { + dyld_cache_mapping_info mapping; + auto s2 = s.GetArray(); + mapping.address = s2[0].GetUint64(); + mapping.size = s2[1].GetUint64(); + mapping.fileOffset = s2[2].GetUint64(); + mapping.maxProt = s2[3].GetUint(); + mapping.initProt = s2[4].GetUint(); + b.push_back(mapping); + } +} + void SharedCache::Store(SerializationContext& context) const { Serialize(context, "metadataVersion", METADATA_VERSION); @@ -3616,6 +3612,19 @@ void SharedCache::Load(DeserializationContext& context) m_metadataValid = true; } +void BackingCache::Store(SerializationContext& context) const +{ + MSS(path); + MSS(isPrimary); + MSS(mappings); +} +void BackingCache::Load(DeserializationContext& context) +{ + MSL(path); + MSL(isPrimary); + MSL(mappings); +} + #if defined(__GNUC__) || defined(__clang__) __attribute__((always_inline)) void SharedCache::AssertMutable() const #elif defined(_MSC_VER) @@ -3664,5 +3673,4 @@ const std::unordered_map<uint64_t, SharedCacheMachOHeader>& SharedCache::AllImag { return State().headers; } - } // namespace SharedCacheCore |
