[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
bug#20614: Segmentation fault when building on Power8 Little Endian
From: |
Andreas Schwab |
Subject: |
bug#20614: Segmentation fault when building on Power8 Little Endian |
Date: |
Sat, 10 Oct 2015 17:44:24 +0200 |
User-agent: |
Gnus/5.13 (Gnus v5.13) Emacs/24.5 (gnu/linux) |
Please try this patch instead:
diff --git a/src/unexelf.c b/src/unexelf.c
index 483da6e..2e8b4c7 100644
--- a/src/unexelf.c
+++ b/src/unexelf.c
@@ -616,6 +616,32 @@ find_section (const char *name, const char *section_names,
const char *file_name
return -1;
}
+/* Find the index of the first bss (NOBITS) section, count the number
+ of bss sections that follow and compute the overall size of these
+ sections. */
+static int
+find_bss_sections (const char *file_name,
+ ElfW(Ehdr) *old_file_h, ElfW(Shdr) *old_section_h,
+ ElfW (Word) *size, int *num)
+{
+ ptrdiff_t idx;
+
+ for (idx = 1; idx < old_file_h->e_shnum; idx++)
+ if (OLD_SECTION_H (idx).sh_type == SHT_NOBITS)
+ {
+ ptrdiff_t idx2 = idx;
+
+ while (OLD_SECTION_H (idx2 + 1).sh_type == SHT_NOBITS)
+ idx2++;
+ *size = (OLD_SECTION_H (idx2).sh_addr + OLD_SECTION_H (idx2).sh_size
+ - OLD_SECTION_H (idx).sh_addr);
+ *num = idx2 + 1 - idx;
+ return idx;
+ }
+ fatal ("Can't find bss section in %s", file_name);
+ return -1;
+}
+
/* ****************************************************************
* unexec
*
@@ -652,13 +678,14 @@ unexec (const char *new_name, const char *old_name)
ElfW (Addr) old_bss_addr, new_bss_addr;
ElfW (Word) old_bss_size, new_data2_size;
+ int n_bss_sections;
ElfW (Off) new_data2_offset;
ElfW (Addr) new_data2_addr;
ElfW (Off) old_bss_offset;
ElfW (Word) new_data2_incr;
ptrdiff_t n, nn;
- ptrdiff_t old_bss_index, old_sbss_index, old_plt_index;
+ ptrdiff_t old_bss_index;
ptrdiff_t old_data_index, new_data2_index;
#if defined _SYSTYPE_SYSV || defined __sgi
ptrdiff_t old_mdebug_index;
@@ -716,50 +743,12 @@ unexec (const char *new_name, const char *old_name)
/* Find the old .bss section. Figure out parameters of the new
data2 and bss sections. */
- old_bss_index = find_section (".bss", old_section_names,
- old_name, old_file_h, old_section_h, 0);
-
- old_sbss_index = find_section (".sbss", old_section_names,
- old_name, old_file_h, old_section_h, 1);
- if (old_sbss_index != -1)
- if (OLD_SECTION_H (old_sbss_index).sh_type != SHT_NOBITS)
- old_sbss_index = -1;
-
- /* PowerPC64 has .plt in the BSS section. */
- old_plt_index = find_section (".plt", old_section_names,
- old_name, old_file_h, old_section_h, 1);
- if (old_plt_index != -1)
- if (OLD_SECTION_H (old_plt_index).sh_type != SHT_NOBITS)
- old_plt_index = -1;
+ old_bss_index = find_bss_sections (old_name, old_file_h, old_section_h,
+ &old_bss_size, &n_bss_sections);
- if (old_sbss_index == -1 && old_plt_index == -1)
- {
- old_bss_addr = OLD_SECTION_H (old_bss_index).sh_addr;
- old_bss_size = OLD_SECTION_H (old_bss_index).sh_size;
- old_bss_offset = OLD_SECTION_H (old_bss_index).sh_offset;
- new_data2_index = old_bss_index;
- }
- else if (old_plt_index != -1
- && (old_sbss_index == -1
- || (OLD_SECTION_H (old_sbss_index).sh_addr
- > OLD_SECTION_H (old_plt_index).sh_addr)))
- {
- old_bss_addr = OLD_SECTION_H (old_plt_index).sh_addr;
- old_bss_size = OLD_SECTION_H (old_bss_index).sh_size
- + OLD_SECTION_H (old_plt_index).sh_size;
- if (old_sbss_index != -1)
- old_bss_size += OLD_SECTION_H (old_sbss_index).sh_size;
- old_bss_offset = OLD_SECTION_H (old_plt_index).sh_offset;
- new_data2_index = old_plt_index;
- }
- else
- {
- old_bss_addr = OLD_SECTION_H (old_sbss_index).sh_addr;
- old_bss_size = OLD_SECTION_H (old_bss_index).sh_size
- + OLD_SECTION_H (old_sbss_index).sh_size;
- old_bss_offset = OLD_SECTION_H (old_sbss_index).sh_offset;
- new_data2_index = old_sbss_index;
- }
+ old_bss_addr = OLD_SECTION_H (old_bss_index).sh_addr;
+ old_bss_offset = OLD_SECTION_H (old_bss_index).sh_offset;
+ new_data2_index = old_bss_index;
/* Find the old .data section. Figure out parameters of
the new data2 and bss sections. */
@@ -851,20 +840,11 @@ unexec (const char *new_name, const char *old_name)
{
/* Compute maximum of all requirements for alignment of section. */
ElfW (Word) alignment = (NEW_PROGRAM_H (n)).p_align;
- if ((OLD_SECTION_H (old_bss_index)).sh_addralign > alignment)
+ if (OLD_SECTION_H (old_bss_index).sh_addralign > alignment)
alignment = OLD_SECTION_H (old_bss_index).sh_addralign;
-#ifdef __sgi
- /* According to r02kar@x4u2.desy.de (Karsten Kuenne)
- and oliva@gnu.org (Alexandre Oliva), on IRIX 5.2, we
- always get "Program segment above .bss" when dumping
- when the executable doesn't have an sbss section. */
- if (old_sbss_index != -1)
-#endif /* __sgi */
if (NEW_PROGRAM_H (n).p_vaddr + NEW_PROGRAM_H (n).p_filesz
- > (old_sbss_index == -1
- ? old_bss_addr
- : round_up (old_bss_addr, alignment)))
+ > round_up (old_bss_addr, alignment))
fatal ("Program segment above .bss in %s", old_name);
if (NEW_PROGRAM_H (n).p_type == PT_LOAD
@@ -932,12 +912,10 @@ unexec (const char *new_name, const char *old_name)
memcpy (&NEW_SECTION_H (nn), &OLD_SECTION_H (n),
old_file_h->e_shentsize);
- if (n == old_bss_index
- /* The new bss and sbss section's size is zero, and its file offset
- and virtual address should be off by NEW_DATA2_SIZE. */
- || n == old_sbss_index || n == old_plt_index
- )
+ if (n >= old_bss_index && n < old_bss_index + n_bss_sections)
{
+ /* The new bss section's size is zero, and its file offset
+ and virtual address should be off by NEW_DATA2_SIZE. */
/* NN should be `old_s?bss_index + 1' at this point. */
NEW_SECTION_H (nn).sh_offset = new_data2_offset + new_data2_size;
NEW_SECTION_H (nn).sh_addr = new_data2_addr + new_data2_size;
@@ -998,15 +976,6 @@ temacs:
&& NEW_SECTION_H (nn).sh_type != SHT_DYNSYM)
PATCH_INDEX (NEW_SECTION_H (nn).sh_info);
- if (old_sbss_index != -1)
- if (!strcmp (old_section_names + NEW_SECTION_H (nn).sh_name, ".sbss"))
- {
- NEW_SECTION_H (nn).sh_offset =
- round_up (NEW_SECTION_H (nn).sh_offset,
- NEW_SECTION_H (nn).sh_addralign);
- NEW_SECTION_H (nn).sh_type = SHT_PROGBITS;
- }
-
/* Now, start to copy the content of sections. */
if (NEW_SECTION_H (nn).sh_type == SHT_NULL
|| NEW_SECTION_H (nn).sh_type == SHT_NOBITS)
@@ -1226,7 +1195,7 @@ temacs:
nn = symp->st_shndx;
if (nn > old_bss_index)
nn--;
- if (nn == old_bss_index)
+ if (nn >= old_bss_index && nn < old_bss_index + n_bss_sections)
memset (new, 0, symp->st_size);
else
{
--
2.6.1
Andreas.
--
Andreas Schwab, SUSE Labs, schwab@suse.de
GPG Key fingerprint = 0196 BAD8 1CE9 1970 F4BE 1748 E4D4 88E3 0EEA B9D7
"And now for something completely different."
- bug#20614: Segmentation fault when building on Power8 Little Endian, (continued)
- bug#20614: Segmentation fault when building on Power8 Little Endian, Eli Zaretskii, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Petr Hracek, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Petr Hracek, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Eli Zaretskii, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Petr Hracek, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, YAMAMOTO Mitsuharu, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Petr Hracek, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, YAMAMOTO Mitsuharu, 2015/10/08
- bug#20614: Segmentation fault when building on Power8 Little Endian, Jaromir Capik, 2015/10/09
- bug#20614: Segmentation fault when building on Power8 Little Endian, YAMAMOTO Mitsuharu, 2015/10/10
- bug#20614: Segmentation fault when building on Power8 Little Endian,
Andreas Schwab <=
- bug#20614: Segmentation fault when building on Power8 Little Endian, Petr Hracek, 2015/10/13
- bug#20614: Segmentation fault when building on Power8 Little Endian, Andreas Schwab, 2015/10/13
- bug#20614: Segmentation fault when building on Power8 Little Endian, Jaromir Capik, 2015/10/16
- bug#20614: Segmentation fault when building on Power8 Little Endian, Andreas Schwab, 2015/10/19
bug#20614: Segmentation fault when building on Power8 Little Endian, Florian Weimer, 2015/10/08