This is the mail archive of the
binutils@sources.redhat.com
mailing list for the binutils project.
Re: PATCH: BZ/175: Fix dynamic string offset
- From: "H. J. Lu" <hjl at lucon dot org>
- To: Jim Wilson <wilson at specifixinc dot com>
- Cc: jakub at redhat dot com, binutils at sources dot redhat dot com
- Date: Fri, 4 Jun 2004 13:04:56 -0700
- Subject: Re: PATCH: BZ/175: Fix dynamic string offset
- References: <20040529222358.GA9983@lucon.org> <1086038644.1064.4.camel@leaf.tuliptree.org> <20040602192144.GA12672@lucon.org>
On Wed, Jun 02, 2004 at 12:21:44PM -0700, H. J. Lu wrote:
> On Mon, May 31, 2004 at 02:24:03PM -0700, Jim Wilson wrote:
> > On Sat, 2004-05-29 at 15:23, H. J. Lu wrote:
> > > I think Alan may be right. I backed out my patch for the time being. I
> > > think we should pass r_addend to _bfd_merged_section_offset only for
> > > section symbols. For local and global symbols, merge will adjust their
> > > st_values. We shouldn't pass r_addend against them to
> > > _bfd_merged_section_offset.
> >
> > This looks reasonable to me, not that I know what I'm talking about
> > though. This seems to implement the idea of keeping internal and
> > programmer offsets separate, as you aren't passing the programmer offset
> > through to bfd_merged_section_offset now.
> >
> > If this is right, then does that imply that elf32-ppc.c and
> > elf64-alpha.c are broken?
>
> As far as I can tell, _bfd_merged_section_offset is used to adjust
> either the value of a symbol or the addend of a relocation. If it is
> used for value, addend shouldn't be passed to _bfd_merged_section_offset
> directly and should be added onto its return value.
>
>
Here is a patch. It uses _bfd_elf_rela_local_sym to compute the offset
of local symbol.
H.J.
-----
2004-06-04 H.J. Lu <hongjiu.lu@intel.com>
* elf32-ppc.c ( (ppc_elf_relax_section): Compute locate symbol
offset with _bfd_elf_rela_local_sym. Add addend to return value
of _bfd_merged_section_offset for global symbols instead of
passing to it.
* elfxx-ia64.c (elfNN_ia64_relax_section): Likewise.
--- bfd/elf32-ppc.c.merge 2004-05-25 22:34:02.000000000 -0700
+++ bfd/elf32-ppc.c 2004-06-04 12:44:10.030043957 -0700
@@ -1747,6 +1747,7 @@ ppc_elf_relax_section (bfd *abfd,
{
/* A local symbol. */
Elf_Internal_Sym *isym;
+ Elf_Internal_Rela rel;
/* Read this BFD's local symbols. */
if (isymbuf == NULL)
@@ -1769,7 +1770,9 @@ ppc_elf_relax_section (bfd *abfd,
else
tsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
- toff = isym->st_value;
+ rel = *irel;
+ toff = _bfd_elf_rela_local_sym (abfd, isym, &tsec, &rel);
+ toff += rel.r_addend;
}
else
{
@@ -1799,6 +1802,13 @@ ppc_elf_relax_section (bfd *abfd,
}
else
continue;
+
+ if (tsec->sec_info_type == ELF_INFO_TYPE_MERGE)
+ toff = _bfd_merged_section_offset (abfd, &tsec,
+ elf_section_data (tsec)->sec_info,
+ toff);
+
+ toff += irel->r_addend;
}
/* If the branch and target are in the same section, you have
@@ -1807,12 +1817,6 @@ ppc_elf_relax_section (bfd *abfd,
if (tsec == isec)
continue;
- toff += irel->r_addend;
- if (tsec->sec_info_type == ELF_INFO_TYPE_MERGE)
- toff = _bfd_merged_section_offset (abfd, &tsec,
- elf_section_data (tsec)->sec_info,
- toff);
-
symaddr = tsec->output_section->vma + tsec->output_offset + toff;
roff = irel->r_offset;
--- bfd/elfxx-ia64.c.merge 2004-06-04 06:21:39.000000000 -0700
+++ bfd/elfxx-ia64.c 2004-06-04 12:44:37.222542858 -0700
@@ -847,6 +847,7 @@ elfNN_ia64_relax_section (abfd, sec, lin
{
/* A local symbol. */
Elf_Internal_Sym *isym;
+ Elf_Internal_Rela rel;
/* Read this BFD's local symbols. */
if (isymbuf == NULL)
@@ -872,8 +873,11 @@ elfNN_ia64_relax_section (abfd, sec, lin
else
tsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
- toff = isym->st_value;
dyn_i = get_dyn_sym_info (ia64_info, NULL, abfd, irel, FALSE);
+
+ rel = *irel;
+ toff = _bfd_elf_rela_local_sym (abfd, isym, &tsec, &rel);
+ toff += rel.r_addend;
}
else
{
@@ -918,14 +922,14 @@ elfNN_ia64_relax_section (abfd, sec, lin
tsec = h->root.u.def.section;
toff = h->root.u.def.value;
}
- }
- if (tsec->sec_info_type == ELF_INFO_TYPE_MERGE)
- toff = _bfd_merged_section_offset (abfd, &tsec,
- elf_section_data (tsec)->sec_info,
- toff + irel->r_addend);
- else
- toff += irel->r_addend;
+ if (tsec->sec_info_type == ELF_INFO_TYPE_MERGE)
+ toff = _bfd_merged_section_offset (abfd, &tsec,
+ elf_section_data (tsec)->sec_info,
+ toff);
+
+ toff += irel->r_addend;
+ }
symaddr = tsec->output_section->vma + tsec->output_offset + toff;