Back from the dyld: vm_allocate to fix corruption.
This fixes the corruption incidentally resolved by assigning to an unused variable by properly allocating memory for structs before assigning to them. This will resolve the segfault on return issue, as the saved return address is no longer clobbered.
This commit is contained in:
+140
-136
@@ -237,6 +237,7 @@ typedef void * (*NSAddressOfSymbol_ptr)(NSSymbol symbol);
|
||||
typedef /*Loader*/void * (*JustInTimeLoaderMake_ptr)(void *apis, void *ma, const char* path, const struct FileID * fileId, uint64_t sliceOffset, bool willNeverUnload, bool leaveMapped, bool overridesCache, uint16_t overridesDylibIndex);
|
||||
typedef void * (*AnalyzeSegmentsLayout_ptr)(void *ma, uintptr_t * vmSpace, bool * hasZeroFill);
|
||||
typedef void * (*VMAllocate_ptr)(uint64_t target_task, void * address, uint64_t size, int flags);
|
||||
typedef void * (*VMDeallocate_ptr)(uint64_t target_task, void * address, uint64_t size);
|
||||
typedef void * (*WithRegions_ptr)(void *ma, void * callback);
|
||||
typedef void * (*MMap_ptr)(void * sdg, void *addr, size_t length, int prot, int flags, int fd, uint64_t offset);
|
||||
void * memcpy2(void *dest, const void *src, size_t len);
|
||||
@@ -259,7 +260,7 @@ typedef uint64_t (*SimpleDPrintf_ptr)(uint64_t fd, const char * fmt, const void
|
||||
|
||||
uint64_t find_macho(uint64_t addr, unsigned int increment);
|
||||
uint64_t find_dylib(uint64_t addr, unsigned int increment);
|
||||
uint64_t find_symbol(uint64_t base, char* symbol, uint64_t offset);
|
||||
void * find_symbol(uint64_t base, char* symbol, uint64_t offset);
|
||||
int string_compare(const char* s1, const char* s2);
|
||||
int detect_sierra();
|
||||
uint64_t syscall_shared_region_check_np();
|
||||
@@ -327,7 +328,7 @@ int main(int argc, char** argv)
|
||||
return 1;
|
||||
}
|
||||
|
||||
NSCreateObjectFileImageFromMemory_ptr NSCreateObjectFileImageFromMemory_func = (void*)find_symbol(dyld, "_NSCreateObjectFileImageFromMemory", offset);
|
||||
NSCreateObjectFileImageFromMemory_ptr NSCreateObjectFileImageFromMemory_func = find_symbol(dyld, "_NSCreateObjectFileImageFromMemory", offset);
|
||||
while (!NSCreateObjectFileImageFromMemory_func) {
|
||||
if (sierra) {
|
||||
dyld = find_dylib(dyld + 0x1000, 0x1000);
|
||||
@@ -338,20 +339,21 @@ int main(int argc, char** argv)
|
||||
if (!dyld) {
|
||||
return 1;
|
||||
}
|
||||
NSCreateObjectFileImageFromMemory_func = (void*)find_symbol(dyld, "_NSCreateObjectFileImageFromMemory", offset);
|
||||
}
|
||||
NSCreateObjectFileImageFromMemory_func = find_symbol(dyld, "_NSCreateObjectFileImageFromMemory", offset);
|
||||
}
|
||||
#ifdef DEBUG
|
||||
print("good symbol!\n");
|
||||
#endif
|
||||
|
||||
void* gDyld = (void*)find_symbol(dyld, "__ZN5dyld45gDyldE", offset);
|
||||
void* gDyld = find_symbol(dyld, "__ZN5dyld45gDyldE", offset);
|
||||
//printf("gDyld: %lld\n", gDyld);
|
||||
void * addr_main = 0;
|
||||
if (gDyld != 0) {
|
||||
#ifdef DEBUG
|
||||
print("gDyld found, using dual hijack technique.\n");
|
||||
#endif
|
||||
// Also known as the RuntimeState or Allocator.
|
||||
__block void* apis = ((struct libdyldDyld4Section*)gDyld)->apis;
|
||||
void* apis = ((struct libdyldDyld4Section*)gDyld)->apis;
|
||||
#ifdef DEBUG
|
||||
printf("apis: %lld\n", apis);
|
||||
printf("config: %i\n", (int)*(void **)(apis+8));
|
||||
@@ -364,7 +366,7 @@ int main(int argc, char** argv)
|
||||
#ifdef DEBUG
|
||||
printf("sdyld: %lld\n", sdyld);
|
||||
#endif
|
||||
JustInTimeLoaderMake_ptr JustInTimeLoaderMake_func = (void*)find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader4makeERNS_12RuntimeStateEPKN5dyld313MachOAnalyzerEPKcRKNS_6FileIDEybbbt", sdyld);
|
||||
JustInTimeLoaderMake_ptr JustInTimeLoaderMake_func = find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader4makeERNS_12RuntimeStateEPKN5dyld313MachOAnalyzerEPKcRKNS_6FileIDEybbbt", sdyld);
|
||||
while (!JustInTimeLoaderMake_func) {
|
||||
sdyld = find_macho(sdyld + 0x1000, 0x1000);
|
||||
if (sdyld == 1) {
|
||||
@@ -374,18 +376,18 @@ int main(int argc, char** argv)
|
||||
return 1;
|
||||
}
|
||||
//printf("Dyld: %lld\n", sdyld);
|
||||
JustInTimeLoaderMake_func = (void*)find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader4makeERNS_12RuntimeStateEPKN5dyld313MachOAnalyzerEPKcRKNS_6FileIDEybbbt", sdyld);
|
||||
JustInTimeLoaderMake_func = find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader4makeERNS_12RuntimeStateEPKN5dyld313MachOAnalyzerEPKcRKNS_6FileIDEybbbt", sdyld);
|
||||
}
|
||||
//printf("Errno: %i\n", *(int*)find_symbol(sdyld, "_errno", sdyld));
|
||||
//printf("JITLMP: %lld\n", JustInTimeLoaderMake_func);
|
||||
SimpleDPrintf_ptr SimpleDPrintf_func = (void*)find_symbol(sdyld, "__simple_dprintf", sdyld);
|
||||
SimpleDPrintf_ptr SimpleDPrintf_func = find_symbol(sdyld, "__simple_dprintf", sdyld);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "SimpleDPrintf_func: %lld\n", SimpleDPrintf_func);
|
||||
#endif
|
||||
// Loader::mapSegments
|
||||
uintptr_t vmSpace = 0;
|
||||
bool hasZeroFill;
|
||||
AnalyzeSegmentsLayout_ptr AnalyzeSegmentsLayout_func = (void*)find_symbol(sdyld, "__ZNK5dyld313MachOAnalyzer21analyzeSegmentsLayoutERyRb", sdyld);
|
||||
AnalyzeSegmentsLayout_ptr AnalyzeSegmentsLayout_func = find_symbol(sdyld, "__ZNK5dyld313MachOAnalyzer21analyzeSegmentsLayoutERyRb", sdyld);
|
||||
#ifdef DEBUG
|
||||
print("Analyzing Segments.\n");
|
||||
#endif
|
||||
@@ -412,7 +414,7 @@ int main(int argc, char** argv)
|
||||
SimpleDPrintf_func(1, "Translated: %s\n", isTranslated ? "true" : "false");
|
||||
#endif
|
||||
uintptr_t loadAddress = 0;
|
||||
VMAllocate_ptr VMAllocate_func = (void*)find_symbol(sdyld, "_vm_allocate", sdyld);
|
||||
VMAllocate_ptr VMAllocate_func = find_symbol(sdyld, "_vm_allocate", sdyld);
|
||||
uint64_t mach_task_self = *(uint64_t*)find_symbol(sdyld, "_mach_task_self_", sdyld);
|
||||
void * vmallocate_ret = VMAllocate_func(mach_task_self, &loadAddress, vmSpace, /*VM_FLAGS_ANYWHERE: */0x1);
|
||||
#ifdef DEBUG
|
||||
@@ -421,14 +423,14 @@ int main(int argc, char** argv)
|
||||
#endif
|
||||
// Put regions together...
|
||||
// JustInTimeLoader::withRegions via MachOAnalyzer::getAllSegmentsInfos
|
||||
WithRegions_ptr WithRegions_func = (void*)find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader11withRegionsEPKN5dyld313MachOAnalyzerEU13block_pointerFvRKNS1_5ArrayINS_6Loader6RegionEEEE", sdyld);
|
||||
WithRegions_ptr WithRegions_func = find_symbol(sdyld, "__ZN5dyld416JustInTimeLoader11withRegionsEPKN5dyld313MachOAnalyzerEU13block_pointerFvRKNS1_5ArrayINS_6Loader6RegionEEEE", sdyld);
|
||||
WithRegions_func((void*)buffer, ^(struct ArrayOfRegions * rptr) {
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Region Ptrs: %lld\n", rptr);
|
||||
SimpleDPrintf_func(1, "usedCount: %lld\n", rptr->_usedCount);
|
||||
SimpleDPrintf_func(1, "allocCount: %lld\n", rptr->_allocCount);
|
||||
#endif
|
||||
__block uint32_t segIndex = 0;
|
||||
uint32_t segIndex = 0;
|
||||
uint64_t sliceOffset = 0;
|
||||
uint64_t lastOffset = 0;
|
||||
for (int i = 0 ; i < rptr->_usedCount; i++) {
|
||||
@@ -447,7 +449,7 @@ int main(int argc, char** argv)
|
||||
if ( (region.vmOffset == 0) && (segIndex > 0) )
|
||||
continue;
|
||||
int perms = region.perms;
|
||||
MMap_ptr MMap_func = (void*)find_symbol(sdyld, "__ZNK5dyld415SyscallDelegate4mmapEPvmiiim", sdyld);
|
||||
MMap_ptr MMap_func = find_symbol(sdyld, "__ZNK5dyld415SyscallDelegate4mmapEPvmiiim", sdyld);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Errno: %i\n", *(int*)find_symbol(sdyld, "_errno", sdyld));
|
||||
SimpleDPrintf_func(1, "Addr: %lld\n", (void*)(loadAddress + region.vmOffset));
|
||||
@@ -469,7 +471,7 @@ int main(int argc, char** argv)
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Errno: %i\n", *(int*)find_symbol(sdyld, "_errno", sdyld));
|
||||
#endif
|
||||
Mprotect_ptr Mprotect_func = (void*)find_symbol(sdyld, "__ZNK5dyld415SyscallDelegate8mprotectEPvmi", sdyld);
|
||||
Mprotect_ptr Mprotect_func = find_symbol(sdyld, "__ZNK5dyld415SyscallDelegate8mprotectEPvmi", sdyld);
|
||||
Mprotect_func(*(void **)(apis+ 8), segAddress, (size_t)region.fileSize, perms);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "SegAddress: %lld\n", segAddress);
|
||||
@@ -480,8 +482,18 @@ int main(int argc, char** argv)
|
||||
});
|
||||
// Okay, we should be good to go with JustInTimeLoader::make.
|
||||
// __ZNK5dyld39MachOFile11installNameEv: ""
|
||||
WithLoadersWriteLock_ptr WithLoadersWriteLock_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState20withLoadersWriteLockEU13block_pointerFvvE", sdyld);
|
||||
__block void * topLoader;
|
||||
WithLoadersWriteLock_ptr WithLoadersWriteLock_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState20withLoadersWriteLockEU13block_pointerFvvE", sdyld);
|
||||
// We cannot use __block as it corrupts the stack, so we have to use a malloc technique to pass data.
|
||||
uintptr_t structspace = 0;
|
||||
uint64_t structspacesize = sizeof(void *)+ // rtopLoader
|
||||
sizeof(struct FileID)+ // fileid
|
||||
sizeof(struct LoadChain)+ // loadChainMain
|
||||
sizeof(struct LoadChain)+ // loadChainCaller
|
||||
sizeof(struct LoadChain)+ // loadChain
|
||||
sizeof(struct LoadOptions)+ // depOptions
|
||||
sizeof(struct diagnostics); // diag
|
||||
VMAllocate_func(mach_task_self, &structspace, structspacesize, 0x1);
|
||||
uint64_t * rtopLoader = (uint64_t *)(structspace);;
|
||||
WithLoadersWriteLock_func(apis, ^(){
|
||||
struct Loaded * loaded = (struct Loaded*)(apis+32);
|
||||
uintptr_t startLoaderCount = loaded->size;
|
||||
@@ -490,18 +502,19 @@ int main(int argc, char** argv)
|
||||
SimpleDPrintf_func(1, "Loaded first: %lld\n", (loaded->elements));
|
||||
SimpleDPrintf_func(1, "Loaded Capacity: %lld\n", loaded->capacity);
|
||||
#endif
|
||||
struct FileID fileid;// = { 0, 0, false };
|
||||
fileid.iNode = 0;
|
||||
fileid.modTime = 0;
|
||||
fileid.isValid = false;
|
||||
struct FileID * fileid = (struct FileID *)(rtopLoader+sizeof(void *));// = { 0, 0, false };
|
||||
fileid->iNode = 0;
|
||||
fileid->modTime = 0;
|
||||
fileid->isValid = false;
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Apis: %lld\n", apis);
|
||||
SimpleDPrintf_func(1, "LoadAddress: %lld\n", loadAddress);
|
||||
SimpleDPrintf_func(1, "JITLMP: %lld\n", JustInTimeLoaderMake_func);
|
||||
#endif
|
||||
topLoader = JustInTimeLoaderMake_func(apis, (void *)loadAddress, "", &fileid, 0, false, true, false, 0);
|
||||
void * topLoader = JustInTimeLoaderMake_func(apis, (void *)loadAddress, "", fileid, 0, false, true, false, 0);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "TopLoader: %lld\n", topLoader);
|
||||
SimpleDPrintf_func(1, "Toploader (*(int*)this): %i\n", *(int *)topLoader);
|
||||
SimpleDPrintf_func(1, "Loaded Size: %lld\n", loaded->size);
|
||||
SimpleDPrintf_func(1, "Loaded Capacity: %lld\n", loaded->capacity);
|
||||
#endif
|
||||
@@ -518,39 +531,41 @@ int main(int argc, char** argv)
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "lateLeaveMapped: %lld\n", pl->lateLeaveMapped);
|
||||
#endif
|
||||
struct LoadChain loadChainMain = { 0, *(void **)(apis+24) };
|
||||
struct LoadChain * loadChainMain = (struct LoadChain *)(fileid+sizeof(struct FileID));// = { 0, *(void **)(apis+24) };
|
||||
loadChainMain->previous = 0;
|
||||
loadChainMain->image = *(void **)(apis+24);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "mainExecutableLoader: %lld\n", *(void **)(apis+24));
|
||||
SimpleDPrintf_func(1, "mainExecutableLoader: %lld\n", loadChainMain.image);
|
||||
SimpleDPrintf_func(1, "mainExecutableLoader: %lld\n", loadChainMain->image);
|
||||
#endif
|
||||
// This is required for some reason, if you find out comment below.
|
||||
struct PartialLoader * pl2 = (struct PartialLoader *)(*(void **)(apis+24));
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Magic2: %lld\n", pl2->magic);
|
||||
#endif
|
||||
struct LoadChain loadChainCaller = { &loadChainMain, &(loaded->elements[0]) };
|
||||
struct LoadChain * loadChainCaller = (struct LoadChain *)(loadChainMain+sizeof(struct LoadChain));// = { &loadChainMain, &(loaded->elements[0]) };
|
||||
loadChainCaller->previous = &loadChainMain;
|
||||
loadChainCaller->image = &(loaded->elements[0]);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "LoadedElements: %lld\n", &(loaded->elements[0]));
|
||||
SimpleDPrintf_func(1, "Toploader (*(int*)this): %i\n", *(int *)topLoader);
|
||||
#endif
|
||||
struct LoadChain loadChain = { &loadChainCaller, topLoader };
|
||||
struct LoadOptions depOptions;
|
||||
depOptions.staticLinkage = true;
|
||||
depOptions.rtldLocal = false; // RTLD_LOCAL only effects top level dylib
|
||||
depOptions.rtldNoDelete = true;
|
||||
depOptions.canBeDylib = true;
|
||||
depOptions.rpathStack = &loadChain;
|
||||
depOptions.useFallBackPaths = true;
|
||||
LoadDependents_ptr LoadDependents_func = (void*)find_symbol(sdyld, "__ZN5dyld46Loader14loadDependentsER11DiagnosticsRNS_12RuntimeStateERKNS0_11LoadOptionsE", sdyld);
|
||||
struct diagnostics diag;
|
||||
diag._buffer = 0;
|
||||
LoadDependents_func(topLoader, &diag, apis, &depOptions);
|
||||
if (diag._buffer != 0) {
|
||||
struct LoadChain * loadChain = (struct LoadChain *)(loadChainCaller+sizeof(struct LoadChain));// = { &loadChainCaller, topLoader };
|
||||
loadChain->previous = &loadChainCaller;
|
||||
loadChain->image = topLoader;
|
||||
struct LoadOptions * depOptions = (struct LoadOptions *)(loadChain+sizeof(struct LoadChain));
|
||||
depOptions->staticLinkage = false;
|
||||
depOptions->rtldLocal = false; // RTLD_LOCAL only effects top level dylib
|
||||
depOptions->rtldNoDelete = true;
|
||||
depOptions->canBeDylib = true;
|
||||
depOptions->rpathStack = loadChain;
|
||||
depOptions->useFallBackPaths = true;
|
||||
LoadDependents_ptr LoadDependents_func = find_symbol(sdyld, "__ZN5dyld46Loader14loadDependentsER11DiagnosticsRNS_12RuntimeStateERKNS0_11LoadOptionsE", sdyld);
|
||||
struct diagnostics * diag = (struct diagnostics *)(depOptions+sizeof(struct LoadOptions));
|
||||
diag->_buffer = 0;
|
||||
LoadDependents_func(topLoader, diag, apis, depOptions);
|
||||
if (diag->_buffer != 0) {
|
||||
#ifdef DEBUG
|
||||
print("Error\n");
|
||||
#endif
|
||||
};
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "buffer: %lld\n", diag._buffer);
|
||||
SimpleDPrintf_func(1, "buffer: %lld\n", diag->_buffer);
|
||||
SimpleDPrintf_func(1, "startLoaderCount: %lld\n", startLoaderCount);
|
||||
#endif
|
||||
uint64_t newLoadersCount = loaded->size - startLoaderCount;
|
||||
@@ -558,18 +573,18 @@ int main(int argc, char** argv)
|
||||
SimpleDPrintf_func(1, "newLoadersCount: %lld\n", newLoadersCount);
|
||||
#endif
|
||||
void * * newLoaders = &loaded->elements[startLoaderCount];
|
||||
__block struct ArrayOfLoaderPointers newLoadersArray = { newLoaders, newLoadersCount, newLoadersCount };
|
||||
struct ArrayOfLoaderPointers newLoadersArray = { newLoaders, newLoadersCount, newLoadersCount };
|
||||
if (newLoadersCount != 0) {
|
||||
NotifyDebuggerLoad_ptr NotifyDebuggerLoad_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState18notifyDebuggerLoadERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyDebuggerLoad_ptr NotifyDebuggerLoad_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState18notifyDebuggerLoadERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyDebuggerLoad_func(apis, &newLoadersArray);
|
||||
if (*(char *)(apis + 0x7f) != '\0') {
|
||||
AddWeakDefs_ptr AddWeakDefs_func = (void*)find_symbol(sdyld, "__ZN5dyld46Loader16addWeakDefsToMapERNS_12RuntimeStateERKN5dyld35ArrayIPKS0_EE", sdyld);
|
||||
AddWeakDefs_ptr AddWeakDefs_func = find_symbol(sdyld, "__ZN5dyld46Loader16addWeakDefsToMapERNS_12RuntimeStateERKN5dyld35ArrayIPKS0_EE", sdyld);
|
||||
AddWeakDefs_func(apis, &newLoadersArray);
|
||||
#ifdef DEBUG
|
||||
print("WeakRefed\n");
|
||||
#endif
|
||||
}
|
||||
ApplyFixups_ptr ApplyFixups_func = (void*)find_symbol(sdyld, "__ZNK5dyld46Loader11applyFixupsER11DiagnosticsRNS_12RuntimeStateERNS_34DyldCacheDataConstLazyScopedWriterEb", sdyld);
|
||||
ApplyFixups_ptr ApplyFixups_func = find_symbol(sdyld, "__ZNK5dyld46Loader11applyFixupsER11DiagnosticsRNS_12RuntimeStateERNS_34DyldCacheDataConstLazyScopedWriterEb", sdyld);
|
||||
struct DyldCacheDataConstLazyScopedWriter dcdclsw = { apis, false };
|
||||
for (int i = 0; i != newLoadersCount; ++i) {
|
||||
#ifdef DEBUG
|
||||
@@ -579,132 +594,121 @@ int main(int argc, char** argv)
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Ldr: %lld\n", ldr);
|
||||
#endif
|
||||
ApplyFixups_func(ldr, &diag, apis, &dcdclsw, true);
|
||||
ApplyFixups_func(ldr, diag, apis, &dcdclsw, true);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Diag: %lld\n", diag._buffer);
|
||||
SimpleDPrintf_func(1, "Diag: %lld\n", diag->_buffer);
|
||||
#endif
|
||||
}
|
||||
// TODO: Figure out if we need addPermanentRanges.
|
||||
NotifyDtrace_ptr NotifyDtrace_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState12notifyDtraceERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyDtrace_ptr NotifyDtrace_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState12notifyDtraceERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyDtrace_func(apis, &newLoadersArray);
|
||||
RebindMissingFlatLazySymbols_ptr RebindMissingFlatLazySymbols_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState28rebindMissingFlatLazySymbolsERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
RebindMissingFlatLazySymbols_ptr RebindMissingFlatLazySymbols_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState28rebindMissingFlatLazySymbolsERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
RebindMissingFlatLazySymbols_func(apis, &newLoadersArray);
|
||||
for (int i = 0; i != newLoadersCount; ++i) {
|
||||
void * ldr = newLoaders[i];
|
||||
#ifdef DEBUG
|
||||
print("Setting up locals.\n");
|
||||
#endif
|
||||
GetMA_ptr GetMA_func = (void*)find_symbol(sdyld, "__ZNK5dyld46Loader11loadAddressERNS_12RuntimeStateE", sdyld);
|
||||
GetMA_ptr GetMA_func = find_symbol(sdyld, "__ZNK5dyld46Loader11loadAddressERNS_12RuntimeStateE", sdyld);
|
||||
const void* * ma = GetMA_func(ldr, apis);
|
||||
HasThreadLocalVariables_ptr HasThreadLocalVariables_func = (void*)find_symbol(sdyld, "__ZNK5dyld39MachOFile23hasThreadLocalVariablesEv", sdyld);
|
||||
HasThreadLocalVariables_ptr HasThreadLocalVariables_func = find_symbol(sdyld, "__ZNK5dyld39MachOFile23hasThreadLocalVariablesEv", sdyld);
|
||||
if (HasThreadLocalVariables_func(ma) == true) {
|
||||
#ifdef DEBUG
|
||||
print("Has local variables.\n");
|
||||
#endif
|
||||
SetUpTLVs_ptr SetUpTLVs_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState9setUpTLVsEPKN5dyld313MachOAnalyzerE", sdyld);
|
||||
SetUpTLVs_ptr SetUpTLVs_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState9setUpTLVsEPKN5dyld313MachOAnalyzerE", sdyld);
|
||||
SetUpTLVs_func(apis, ma);
|
||||
}
|
||||
};
|
||||
}
|
||||
IncDlRefCount_ptr IncDlRefCount_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState13incDlRefCountEPKNS_6LoaderE", sdyld);
|
||||
IncDlRefCount_ptr IncDlRefCount_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState13incDlRefCountEPKNS_6LoaderE", sdyld);
|
||||
IncDlRefCount_func(apis, topLoader);
|
||||
#ifdef DEBUG
|
||||
print("Notifying.\n");
|
||||
#endif
|
||||
NotifyLoad_ptr NotifyLoad_func = (void*)find_symbol(sdyld, "__ZN5dyld412RuntimeState10notifyLoadERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyLoad_ptr NotifyLoad_func = find_symbol(sdyld, "__ZN5dyld412RuntimeState10notifyLoadERKN5dyld35ArrayIPKNS_6LoaderEEE", sdyld);
|
||||
NotifyLoad_func(apis, &newLoadersArray);
|
||||
#ifdef DEBUG
|
||||
print("Initializing\n");
|
||||
#endif
|
||||
RunInitializers_ptr RunInitializers_func = (void*)find_symbol(sdyld, "__ZNK5dyld46Loader38runInitializersBottomUpPlusUpwardLinksERNS_12RuntimeStateE", sdyld);
|
||||
RunInitializers_ptr RunInitializers_func = find_symbol(sdyld, "__ZNK5dyld46Loader38runInitializersBottomUpPlusUpwardLinksERNS_12RuntimeStateE", sdyld);
|
||||
RunInitializers_func(topLoader, apis);
|
||||
*rtopLoader = (uint64_t)topLoader;
|
||||
});
|
||||
uintptr_t flags = 0;
|
||||
void* handle = (void*)((((uintptr_t)topLoader) << 1) | flags);
|
||||
void* handle = (void*)((((uintptr_t)*rtopLoader) << 1) | flags);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "Handle: %lld\n", handle);
|
||||
#endif
|
||||
VMDeallocate_ptr VMDeallocate_func = find_symbol(sdyld, "_vm_deallocate", sdyld);
|
||||
VMDeallocate_func(mach_task_self, (void *)structspace, structspacesize);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "VMDeallocated: %lld\n", structspace);
|
||||
#endif
|
||||
NSModule nm = handle;
|
||||
NSLookupSymbolInModule_ptr NSLookupSymbolInModule_func = (void*)find_symbol(dyld, "_NSLookupSymbolInModule", offset);
|
||||
NSLookupSymbolInModule_ptr NSLookupSymbolInModule_func = find_symbol(dyld, "_NSLookupSymbolInModule", offset);
|
||||
NSSymbol sym_main = NSLookupSymbolInModule_func(nm, "_main");
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "sym_main: %lld\n", sym_main);
|
||||
#endif
|
||||
NSAddressOfSymbol_ptr NSAddressOfSymbol_func = (void*)find_symbol(dyld, "_NSAddressOfSymbol", offset);
|
||||
NSAddressOfSymbol_ptr NSAddressOfSymbol_func = find_symbol(dyld, "_NSAddressOfSymbol", offset);
|
||||
addr_main = NSAddressOfSymbol_func(sym_main);
|
||||
} else {
|
||||
NSLinkModule_ptr NSLinkModule_func = find_symbol(dyld, "_NSLinkModule", offset);
|
||||
if (!NSLinkModule_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
NSLookupSymbolInModule_ptr NSLookupSymbolInModule_func = find_symbol(dyld, "_NSLookupSymbolInModule", offset);
|
||||
if (!NSLookupSymbolInModule_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
NSAddressOfSymbol_ptr NSAddressOfSymbol_func = find_symbol(dyld, "_NSAddressOfSymbol", offset);
|
||||
if (!NSAddressOfSymbol_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*if (*(char*)buffer == 'b') {*/
|
||||
/*print("magic b!\n");*/
|
||||
/*}*/
|
||||
*(char*)buffer = '\xcf';
|
||||
((uint32_t *)buffer)[3] = MH_BUNDLE;
|
||||
|
||||
NSObjectFileImage fi = 0;
|
||||
if (NSCreateObjectFileImageFromMemory_func((void*)buffer, buffer_size, &fi) != 1) {
|
||||
return 1;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
print("created!\n");
|
||||
#endif
|
||||
|
||||
NSModule nm = NSLinkModule_func(fi, "", NSLINKMODULE_OPTION_PRIVATE | NSLINKMODULE_OPTION_BINDNOW | NSLINKMODULE_OPTION_RETURN_ON_ERROR);
|
||||
if (!nm) {
|
||||
#ifdef DEBUG
|
||||
print("no nm!\n");
|
||||
#endif
|
||||
return 1;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
print("good nm!\n");
|
||||
#endif
|
||||
|
||||
NSSymbol sym_main = NSLookupSymbolInModule_func(nm, "_main");
|
||||
if (!sym_main) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
void * addr_main = NSAddressOfSymbol_func(sym_main);
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "addr_main: %lld\n", addr_main);
|
||||
#endif
|
||||
int(*main_func)(int, char**) = (int(*)(int, char**))addr_main;
|
||||
#ifdef DEBUG
|
||||
SimpleDPrintf_func(1, "main_func: %lld\n", main_func);
|
||||
#endif
|
||||
char* socket = (char*)(size_t)argc;
|
||||
char *new_argv[] = { "m", socket, NULL };
|
||||
int new_argc = 2;
|
||||
#ifdef DEBUG
|
||||
print("Calling main.\n");
|
||||
#endif
|
||||
main_func(new_argc, new_argv);
|
||||
#ifdef DEBUG
|
||||
print("Returning.\n");
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
NSLinkModule_ptr NSLinkModule_func = (void*)find_symbol(dyld, "_NSLinkModule", offset);
|
||||
if (!NSLinkModule_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
NSLookupSymbolInModule_ptr NSLookupSymbolInModule_func = (void*)find_symbol(dyld, "_NSLookupSymbolInModule", offset);
|
||||
if (!NSLookupSymbolInModule_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
NSAddressOfSymbol_ptr NSAddressOfSymbol_func = (void*)find_symbol(dyld, "_NSAddressOfSymbol", offset);
|
||||
if (!NSAddressOfSymbol_func) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*if (*(char*)buffer == 'b') {*/
|
||||
/*print("magic b!\n");*/
|
||||
/*}*/
|
||||
*(char*)buffer = '\xcf';
|
||||
((uint32_t *)buffer)[3] = MH_BUNDLE;
|
||||
|
||||
NSObjectFileImage fi = 0;
|
||||
if (NSCreateObjectFileImageFromMemory_func((void*)buffer, buffer_size, &fi) != 1) {
|
||||
return 1;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
print("created!\n");
|
||||
#endif
|
||||
|
||||
NSModule nm = NSLinkModule_func(fi, "", NSLINKMODULE_OPTION_PRIVATE | NSLINKMODULE_OPTION_BINDNOW | NSLINKMODULE_OPTION_RETURN_ON_ERROR);
|
||||
if (!nm) {
|
||||
#ifdef DEBUG
|
||||
print("no nm!\n");
|
||||
#endif
|
||||
return 1;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
print("good nm!\n");
|
||||
#endif
|
||||
|
||||
NSSymbol sym_main = NSLookupSymbolInModule_func(nm, "_main");
|
||||
if (!sym_main) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
void * addr_main = NSAddressOfSymbol_func(sym_main);
|
||||
if (!addr_main) {
|
||||
return 1;
|
||||
}
|
||||
if (!addr_main) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
print("found main!\n");
|
||||
print("found main!\n");
|
||||
#endif
|
||||
|
||||
};
|
||||
int(*main_func)(int, char**) = (int(*)(int, char**))addr_main;
|
||||
char* socket = (char*)(size_t)argc;
|
||||
char *new_argv[] = { "m", socket, NULL };
|
||||
@@ -712,7 +716,7 @@ int main(int argc, char** argv)
|
||||
return main_func(new_argc, new_argv);
|
||||
}
|
||||
|
||||
uint64_t find_symbol(uint64_t base, char* symbol, uint64_t offset)
|
||||
void * find_symbol(uint64_t base, char* symbol, uint64_t offset)
|
||||
{
|
||||
struct segment_command_64 *sc, *linkedit, *text;
|
||||
struct load_command *lc;
|
||||
@@ -755,14 +759,14 @@ uint64_t find_symbol(uint64_t base, char* symbol, uint64_t offset)
|
||||
/*print("\n");*/
|
||||
/*#endif*/
|
||||
if (string_compare(name, symbol) == 0) {
|
||||
return nl[i].n_value + offset;
|
||||
return (void*)(nl[i].n_value + offset);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint64_t syscall_chmod(uint64_t path, long mode)
|
||||
uint64_t syscall_chmod(uint64_t path, long mode)
|
||||
{
|
||||
uint64_t chmod_no = 0x200000f;
|
||||
uint64_t ret = 0;
|
||||
@@ -805,7 +809,7 @@ uint64_t find_dylib(uint64_t addr, unsigned int increment)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int string_compare(const char* s1, const char* s2)
|
||||
int string_compare(const char* s1, const char* s2)
|
||||
{
|
||||
while (*s1 != '\0' && *s1 == *s2)
|
||||
{
|
||||
@@ -891,7 +895,7 @@ uint64_t roundUp(uint64_t numToRound, uint64_t multiple)
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
int string_len(const char* s1)
|
||||
int string_len(const char* s1)
|
||||
{
|
||||
const char* s2 = s1;
|
||||
while (*s2 != '\0')
|
||||
@@ -901,7 +905,7 @@ int string_len(const char* s1)
|
||||
return (s2 - s1);
|
||||
}
|
||||
|
||||
void print(char * str)
|
||||
void print(char * str)
|
||||
{
|
||||
long write = 0x2000004;
|
||||
long stdout = 1;
|
||||
|
||||
Reference in New Issue
Block a user