changeset 275:1e3617d8a951

- mach-o loader fix (discovered on High Sierra, not sure what other versions were affected)
author Tassilo Philipp
date Thu, 01 Feb 2018 12:59:00 +0100
parents 5c8eb8f34ae6
children 277fe1ff3e14
files dynload/dynload_syms_mach-o.c
diffstat 1 files changed, 18 insertions(+), 8 deletions(-) [+]
line wrap: on
line diff
--- a/dynload/dynload_syms_mach-o.c	Sat Dec 30 00:36:00 2017 +0100
+++ b/dynload/dynload_syms_mach-o.c	Thu Feb 01 12:59:00 2018 +0100
@@ -7,7 +7,7 @@
  License:
 
    Copyright (c) 2007-2015 Olivier Chafik <olivier.chafik@gmail.com>,
-                      2017 refactored completely for stability, API
+                 2017-2018 refactored completely for stability, API
                            consistency and portability by Tassilo Philipp.
 
    Permission to use, copy, modify, and distribute this software for any
@@ -114,12 +114,20 @@
 			if(cmd->cmd == SEGMEND_COMMAND_ID)
 			{
 				const struct SEGMENT_COMMAND* seg = (struct SEGMENT_COMMAND*)cmd;
-				if((seg->fileoff == 0) && (seg->filesize != 0))
+				/*@@@ unsure why I used this instead of checking __TEXT: if((seg->fileoff == 0) && (seg->filesize != 0))*/
+				if(strcmp(seg->segname, "__TEXT") == 0)
 					slide = (uintptr_t)pHeader - seg->vmaddr; /* effective offset of segment from header */
 
+				/* If we have __LINKEDIT segment (= raw data for dynamic linkers), use that one to find symbal table address. */
 				if(strcmp(seg->segname, "__LINKEDIT") == 0) {
-					/* Adjust pBase depending on where __LINKEDIT segment is */
+					/* Recompute pBase relative to where __LINKEDIT segment is in memory. */
 					pBase = (const char*)(seg->vmaddr - seg->fileoff) + slide;
+
+					/*@@@ we might want to also check maxprot and initprot here:
+						VM_PROT_READ    ((vm_prot_t) 0x01)
+						VM_PROT_WRITE   ((vm_prot_t) 0x02)
+						VM_PROT_EXECUTE ((vm_prot_t) 0x04)*/
+
 					symOffset = slide; /* this is also offset of symbols */
 				}
 			}
@@ -138,13 +146,15 @@
 				pSyms->symOffset    = symOffset;
 				pSyms->pLib         = pLib;
 			}
-			else if(cmd->cmd == LC_DYSYMTAB)
+			else if(cmd->cmd == LC_DYSYMTAB && !dysymtab_cmd/* only init once - just safety check */)
 			{
-				dysymtab_cmd = (const struct dysymtab_command*)cmd;
-				/*@@@ check if(cmd->cmdsize != sizeof(struct dysymtab_command)) {
-					dlFreeMem....
+				/* @@@ unused, we'll always run over all symbols, and not check locals, globals, etc.
+				if(cmd->cmdsize != sizeof(struct symtab_command)) {
+					dlSymsCleanup(pSyms);
 					break;
-				}*/
+				}
+
+				dysymtab_cmd = (const struct dysymtab_command*)cmd;*/
 			}
 		}
 	}