===================================================================
@@ -33,6 +33,10 @@
#include "elf_loader.h"
#include "spebase.h"
+#ifndef PF_OVERLAY
+#define PF_OVERLAY (1 << 27)
+#endif
+
#ifdef DEBUG
static void display_debug_output(Elf32_Ehdr *elf_start, Elf32_Shdr *sh);
#endif /*DEBUG*/
@@ -153,20 +157,6 @@ _base_spe_parse_isolated_elf(spe_program
return 0;
}
-static int
-overlay(Elf32_Phdr *ph, Elf32_Phdr *prev_ph)
-{
- /*
- * If our ph segment virtual address fits within that of the
- * previous ph, this is an overlay.
- */
- if (prev_ph && (ph->p_vaddr >= prev_ph->p_vaddr) &&
- (ph->p_vaddr < (prev_ph->p_vaddr + prev_ph->p_memsz)))
- return 1;
- else
- return 0;
-}
-
static void
copy_to_ld_buffer(spe_program_handle_t *handle, void *buffer, Elf32_Phdr
*ph, Elf32_Off toe_addr, long toe_size)
@@ -242,7 +232,7 @@ _base_spe_load_spe_elf (spe_program_hand
{
Elf32_Ehdr *ehdr;
Elf32_Phdr *phdr;
- Elf32_Phdr *ph, *prev_ph;
+ Elf32_Phdr *ph;
Elf32_Shdr *shdr;
Elf32_Shdr *sh;
@@ -303,10 +293,10 @@ _base_spe_load_spe_elf (spe_program_hand
* Load all PT_LOAD segments onto the SPE local store buffer.
*/
DEBUG_PRINTF("Segments: 0x%x\n", ehdr->e_phnum);
- for (ph = phdr, prev_ph = NULL; ph < &phdr[ehdr->e_phnum]; ++ph) {
+ for (ph = phdr; ph < &phdr[ehdr->e_phnum]; ++ph) {
switch (ph->p_type) {
case PT_LOAD:
- if (!overlay(ph, prev_ph)) {
+ if (!(ph->p_flags & PF_OVERLAY)) {
if (ph->p_filesz < ph->p_memsz) {
DEBUG_PRINTF("padding loaded image with zeros:\n");
DEBUG_PRINTF("start: 0x%04x\n", ph->p_vaddr + ph->p_filesz);
There is a bug in the libspe2 elf loader that prevents it from correctly loading overlay segments. This was brought up by Ulrich Weigand. Here is the Bug description: spebase/elf_loader.c contains a routine "overlay" that attempts to determine whether a PT_LOAD segment represents an overlay that is not supposed to be loader. However, caller of overlay always passes in a prev_ph argument of NULL, causing overlay to always return 0. This causes all PT_LOAD segments to be loaded, regardless of whether or not they are overlay segments. This causes unnecessary loads to be performed. In addition, if the linker has designated one segment as "overlay init", i.e. pre-loaded contents of the overlay buffer, the ELF loader does not reliably ensure that the overlay init segment is the one that's present after load. The proper identification of overlay segments should use the PF_OVERLAY p_flags bit that the linker sets to indicate PT_LOAD segments that should not be loaded. The following patch fixed this bug. Signed-off-by: D.Herrendoerfer <herrend [at] de [dot] ibm [dot] com>