- if (strcmp ((char *) (symnames + symp->st_name), "_end") == 0
- || strcmp ((char *) (symnames + symp->st_name), "end") == 0
- || strcmp ((char *) (symnames + symp->st_name), "_edata") == 0
- || strcmp ((char *) (symnames + symp->st_name), "edata") == 0)
- memcpy (&symp->st_value, &new_bss_addr, sizeof (new_bss_addr));
+ {
+ if (strcmp ((char *) (symnames + symp->st_name), "_end") == 0
+ || strcmp ((char *) (symnames + symp->st_name), "end") == 0
+ || strcmp ((char *) (symnames + symp->st_name), "_edata") == 0
+ || strcmp ((char *) (symnames + symp->st_name), "edata") == 0)
+ memcpy (&symp->st_value, &new_bss_addr, sizeof (new_bss_addr));
+
+ /* Strictly speaking, #ifdef below is not necessary. But we
+ keep it to indicate that this kind of change may also be
+ necessary for other unexecs to support GNUstep. */
+#ifdef NS_IMPL_GNUSTEP
+ /* ObjC runtime modifies the values of some data structures
+ such as classes and selectors in the .data section after
+ loading. As the dump process copies the .data section
+ from the current process, that causes problems when the
+ modified classes are reinitialized in the dumped
+ executable. We copy such data from the old file, not
+ from the current process. */
+ if (strncmp ((char *) (symnames + symp->st_name),
+ "_OBJC_", sizeof ("_OBJC_") - 1) == 0)
+ {
+ caddr_t old, new;
+
+ new = ((symp->st_value - NEW_SECTION_H (symp->st_shndx).sh_addr)
+ + NEW_SECTION_H (symp->st_shndx).sh_offset + new_base);
+ /* "Unpatch" index. */
+ nn = symp->st_shndx;
+ if (nn > old_bss_index)
+ nn--;
+ if (nn == old_bss_index)
+ memset (new, 0, symp->st_size);
+ else
+ {
+ old = ((symp->st_value
+ - NEW_SECTION_H (symp->st_shndx).sh_addr)
+ + OLD_SECTION_H (nn).sh_offset + old_base);
+ memcpy (new, old, symp->st_size);
+ }
+ }
+#endif
+ }