Loading...
--- dyld/dyld-421.2/interlinked-dylibs/SharedCache.cpp
+++ dyld/dyld-433.5/interlinked-dylibs/SharedCache.cpp
@@ -52,6 +52,8 @@
#include <unordered_map>
#include <unordered_set>
+#include "MachOProxy.h"
+
#include "OptimizerBranches.h"
#include "CacheFileAbstraction.hpp"
@@ -184,18 +186,26 @@
}
SharedCache::SharedCache(Manifest& manifest,
- const std::string& configuration, const std::string& architecture) :
- _manifest(manifest), _arch(archForString(architecture)),
- _archManifest(manifest.configurations.find(configuration)->second.architectures.find(architecture)->second), _buffer(nullptr),
- _fileSize(0), _vmSize(0), _aliasCount(0), _slideInfoFileOffset(0), _slideInfoBufferSize(0) {
+ const std::string& configuration, const std::string& architecture)
+ : _manifest(manifest)
+ , _arch(archForString(architecture))
+ , _archManifest(manifest.configuration(configuration).architecture(architecture))
+ , _buffer(nullptr)
+ , _fileSize(0)
+ , _vmSize(0)
+ , _aliasCount(0)
+ , _slideInfoFileOffset(0)
+ , _slideInfoBufferSize(0)
+{
auto maxCacheVMSize = sharedRegionRegionSize(_arch);
- for ( auto& includedDylib : _archManifest.results.dylibs ) {
- if (includedDylib.second.included) {
+ for (auto& includedIdentifier : _archManifest.results.dylibs) {
+ if (includedIdentifier.second.included) {
//assert(manifest.dylibs.count(includedDylib.first) > 0);
//assert(manifest.dylibs.find(includedDylib.first)->second.proxies.count(architecture) > 0);
- MachOProxy* proxy = _manifest.dylibProxy( includedDylib.first, architecture );
+ MachOProxy* proxy = MachOProxy::forIdentifier(includedIdentifier.first, architecture);
assert(proxy != nullptr);
+ assert(proxy->isDylib());
_dylibs.push_back(proxy);
}
}
@@ -211,9 +221,9 @@
_aliasCount += dylib->installNameAliases.size();
}
- sortDylibs(_manifest.dylibOrderFile);
- if ( !_manifest.dirtyDataOrderFile.empty() )
- loadDirtyDataOrderFile(_manifest.dirtyDataOrderFile);
+ sortDylibs(_manifest.dylibOrderFile());
+ if (!_manifest.dirtyDataOrderFile().empty())
+ loadDirtyDataOrderFile(_manifest.dirtyDataOrderFile());
assignSegmentAddresses();
if ( _vmSize > maxCacheVMSize )
@@ -304,7 +314,7 @@
std::vector<uint64_t> emptyBranchPoolOffsets;
buildUnoptimizedCache();
optimizeObjC(false/*not production*/);
- if (_manifest.platform == "osx") {
+ if (_manifest.platform() == "osx") {
optimizeLinkedit(false, false, emptyBranchPoolOffsets);
} else {
optimizeLinkedit(true, false, emptyBranchPoolOffsets);
@@ -324,7 +334,7 @@
});
_vmSize = endAddr - sharedRegionStartExecutableAddress(_arch);
- if (_manifest.platform == "osx") {
+ if (_manifest.platform() == "osx") {
appendCodeSignature("release");
} else {
appendCodeSignature("development");
@@ -398,12 +408,12 @@
std::unordered_set<const void*> seenHeaders;
forEachImage([&](const void* machHeader, const char* installName, time_t mtime,
- ino_t inode, const std::vector<MachOProxy::Segment>& segments) {
+ ino_t inode, const std::vector<MachOProxySegment>& segments) {
if ( !seenHeaders.count(machHeader) ) {
seenHeaders.insert(machHeader);
fprintf(fmap, "%s\n", installName);
- for (const MachOProxy::Segment& seg : segments) {
+ for (const auto& seg : segments) {
uint64_t vmAddr = 0;
for (int i=0; i < regionSizes.size(); ++i) {
if ( (seg.fileOffset >= regionFileOffsets[i]) && (seg.fileOffset < (regionFileOffsets[i]+regionSizes[i])) ) {
@@ -415,15 +425,14 @@
}
});
-
::fclose(fmap);
return true;
}
template <typename P>
-std::vector<MachOProxy::Segment> getSegments(const void* cacheBuffer, const void* machHeader)
-{
- std::vector<MachOProxy::Segment> result;
+std::vector<MachOProxySegment> getSegments(const void* cacheBuffer, const void* machHeader)
+{
+ std::vector<MachOProxySegment> result;
macho_header<P>* mh = (macho_header<P>*)machHeader;
const uint32_t cmd_count = mh->ncmds();
const macho_load_command<P>* cmd = (macho_load_command<P>*)((uint8_t*)mh + sizeof(macho_header<P>));
@@ -431,9 +440,11 @@
if ( cmd->cmd() != macho_segment_command<P>::CMD )
continue;
macho_segment_command<P>* segCmd = (macho_segment_command<P>*)cmd;
- MachOProxy::Segment seg;
+ MachOProxySegment seg;
+ seg.name = segCmd->segname();
seg.name = segCmd->segname();
seg.size = segCmd->vmsize();
+ seg.vmaddr = segCmd->vmaddr();
seg.diskSize = (uint32_t)segCmd->filesize();
seg.fileOffset = (uint32_t)segCmd->fileoff();
seg.protection = segCmd->initprot();
@@ -783,8 +794,14 @@
uint64_t endReadOnlyAddress = align(addr, sharedRegionRegionAlignment(_arch));
_readOnlyRegion.size = endReadOnlyAddress - _readOnlyRegion.address;
_fileSize = _readOnlyRegion.fileOffset + _readOnlyRegion.size;
+
+ // FIXME: Confirm these numbers for all platform/arch combos
// assume LINKEDIT optimzation reduces LINKEDITs to %40 of original size
- _vmSize = _readOnlyRegion.address+(_readOnlyRegion.size * 2/5) - _textRegion.address;
+ if (_manifest.platform() == "osx") {
+ _vmSize = _readOnlyRegion.address + (_readOnlyRegion.size * 9 / 10) - _textRegion.address;
+ } else {
+ _vmSize = _readOnlyRegion.address + (_readOnlyRegion.size * 2 / 5) - _textRegion.address;
+ }
}
uint64_t SharedCache::pathHash(const char* path)
@@ -1329,7 +1346,7 @@
for (auto& dylib : _dylibs) {
auto textSeg = _segmentMap[dylib][0];
images->set_address(textSeg.address);
- if (_manifest.platform == "osx") {
+ if (_manifest.platform() == "osx") {
images->set_modTime(dylib->lastModTime);
images->set_inode(dylib->inode);
} else {
@@ -1345,7 +1362,7 @@
if (!dylib->installNameAliases.empty()) {
for (const std::string& alias : dylib->installNameAliases) {
images->set_address(_segmentMap[dylib][0].address);
- if (_manifest.platform == "osx") {
+ if (_manifest.platform() == "osx") {
images->set_modTime(dylib->lastModTime);
images->set_inode(dylib->inode);
} else {
@@ -1368,9 +1385,9 @@
// write text image array and image names pool at same time
for (auto& dylib : _dylibs) {
- textImages->set_uuid(dylib->uuid);
+ textImages->set_uuid(dylib->uuid.get());
textImages->set_loadAddress(_segmentMap[dylib][0].address);
- textImages->set_textSegmentSize((uint32_t)dylib->segments[0].size);
+ textImages->set_textSegmentSize((uint32_t)_segmentMap[dylib].front().cacheSegSize);
textImages->set_pathOffset(stringOffset);
::strcpy((char*)&buffer[stringOffset], dylib->installName.c_str());
stringOffset += dylib->installName.size()+1;
@@ -1403,34 +1420,19 @@
void SharedCache::bindAll(void)
{
- std::unordered_map<std::string, void*> dylibPathToMachHeader;
- for (auto& dylib : _dylibs) {
- void* mh = (uint8_t*)_buffer.get() + _segmentMap[dylib][0].cacheFileOffset;
- dylibPathToMachHeader[dylib->installName] = mh;
- for (const std::string& path : dylib->installNameAliases) {
- if (path != dylib->installName) {
- dylibPathToMachHeader[path] = mh;
- }
- }
- }
-
- bindAllImagesInCache(dylibPathToMachHeader, _pointersForASLR);
+ bindAllImagesInCache(_dylibs, _segmentMap, _pointersForASLR);
}
void SharedCache::writeCacheSegments(void)
{
uint8_t* cacheBytes = (uint8_t*)_buffer.get();
for (auto& dylib : _dylibs) {
- struct stat stat_buf;
- const uint8_t* srcDylib;
- bool rootless;
-
- std::tie(srcDylib, stat_buf, rootless) = fileCache.cacheLoad(dylib->path);
+ const uint8_t* srcDylib = dylib->getBuffer();
+
for (auto& seg : _segmentMap[dylib]) {
- uint32_t segFileOffset = dylib->fatFileOffset + seg.base->fileOffset;
uint64_t copySize = std::min(seg.cacheSegSize, (uint64_t)seg.base->diskSize);
verboseLog("copy segment %12s (0x%08llX bytes) to %p (logical addr 0x%llX) for %s", seg.base->name.c_str(), copySize, &cacheBytes[seg.cacheFileOffset], seg.address, dylib->installName.c_str());
- ::memcpy(&cacheBytes[seg.cacheFileOffset], &srcDylib[segFileOffset], copySize);
+ ::memcpy(&cacheBytes[seg.cacheFileOffset], &srcDylib[seg.base->fileOffset], copySize);
}
}
}
@@ -1443,7 +1445,7 @@
uint8_t dscHashType = CS_HASHTYPE_SHA1;
uint8_t dscHashSize = CS_HASH_SIZE_SHA1;
uint32_t dscDigestFormat = kCCDigestSHA1;
- if ( _manifest.platform == "osx" ) {
+ if (_manifest.platform() == "osx") {
dscHashType = CS_HASHTYPE_SHA256;
dscHashSize = CS_HASH_SIZE_SHA256;
dscDigestFormat = kCCDigestSHA256;