aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/ChangeLog6
-rw-r--r--src/unexmacosx.c29
2 files changed, 29 insertions, 6 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index 918af2c6335..206ded2aaa5 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,9 @@
12007-11-24 YAMAMOTO Mitsuharu <mituharu@math.s.chiba-u.ac.jp>
2
3 * unexmacosx.c (copy_data_segment): Also copy __gcc_except_tab and
4 __objc_* sections.
5 (unrelocate) [_LP64]: Set relocation base to address of data segment.
6
12007-11-23 Andreas Schwab <schwab@suse.de> 72007-11-23 Andreas Schwab <schwab@suse.de>
2 8
3 * editfns.c (Fformat): Handle %c specially since it requires the 9 * editfns.c (Fformat): Handle %c specially since it requires the
diff --git a/src/unexmacosx.c b/src/unexmacosx.c
index 3646aec6983..eceffc4af4b 100644
--- a/src/unexmacosx.c
+++ b/src/unexmacosx.c
@@ -819,7 +819,9 @@ copy_data_segment (struct load_command *lc)
819 || strncmp (sectp->sectname, "__la_sym_ptr2", 16) == 0 819 || strncmp (sectp->sectname, "__la_sym_ptr2", 16) == 0
820 || strncmp (sectp->sectname, "__dyld", 16) == 0 820 || strncmp (sectp->sectname, "__dyld", 16) == 0
821 || strncmp (sectp->sectname, "__const", 16) == 0 821 || strncmp (sectp->sectname, "__const", 16) == 0
822 || strncmp (sectp->sectname, "__cfstring", 16) == 0) 822 || strncmp (sectp->sectname, "__cfstring", 16) == 0
823 || strncmp (sectp->sectname, "__gcc_except_tab", 16) == 0
824 || strncmp (sectp->sectname, "__objc_", 7) == 0)
823 { 825 {
824 if (!unexec_copy (sectp->offset, old_file_offset, sectp->size)) 826 if (!unexec_copy (sectp->offset, old_file_offset, sectp->size))
825 unexec_error ("cannot copy section %s", sectp->sectname); 827 unexec_error ("cannot copy section %s", sectp->sectname);
@@ -904,6 +906,20 @@ unrelocate (const char *name, off_t reloff, int nrel)
904 struct relocation_info reloc_info; 906 struct relocation_info reloc_info;
905 struct scattered_relocation_info *sc_reloc_info 907 struct scattered_relocation_info *sc_reloc_info
906 = (struct scattered_relocation_info *) &reloc_info; 908 = (struct scattered_relocation_info *) &reloc_info;
909 vm_address_t reloc_base, location;
910
911#ifdef _LP64
912#if __ppc64__
913 reloc_base = (data_segment_scp->vmaddr >= 0x100000000
914 ? data_segment_scp->vmaddr : 0);
915#else
916 /* First writable segment address. */
917 reloc_base = data_segment_scp->vmaddr;
918#endif
919#else
920 /* First segment address in the file (unless MH_SPLIT_SEGS set). */
921 reloc_base = 0;
922#endif
907 923
908 for (unreloc_count = 0, i = 0; i < nrel; i++) 924 for (unreloc_count = 0, i = 0; i < nrel; i++)
909 { 925 {
@@ -917,14 +933,15 @@ unrelocate (const char *name, off_t reloff, int nrel)
917 switch (reloc_info.r_type) 933 switch (reloc_info.r_type)
918 { 934 {
919 case GENERIC_RELOC_VANILLA: 935 case GENERIC_RELOC_VANILLA:
920 if (reloc_info.r_address >= data_segment_scp->vmaddr 936 location = reloc_base + reloc_info.r_address;
921 && reloc_info.r_address < (data_segment_scp->vmaddr 937 if (location >= data_segment_scp->vmaddr
922 + data_segment_scp->vmsize)) 938 && location < (data_segment_scp->vmaddr
939 + data_segment_scp->vmsize))
923 { 940 {
924 off_t src_off = data_segment_old_fileoff 941 off_t src_off = data_segment_old_fileoff
925 + reloc_info.r_address - data_segment_scp->vmaddr; 942 + (location - data_segment_scp->vmaddr);
926 off_t dst_off = data_segment_scp->fileoff 943 off_t dst_off = data_segment_scp->fileoff
927 + reloc_info.r_address - data_segment_scp->vmaddr; 944 + (location - data_segment_scp->vmaddr);
928 945
929 if (!unexec_copy (dst_off, src_off, 1 << reloc_info.r_length)) 946 if (!unexec_copy (dst_off, src_off, 1 << reloc_info.r_length))
930 unexec_error ("unrelocate: %s:%d cannot copy original value", 947 unexec_error ("unrelocate: %s:%d cannot copy original value",