diff mbox series

[2/8] x86/EFI: sections may not live at VA 0 in PE binaries

Message ID 5d7c61b0-8441-dccc-4917-cc8a436fd96f@suse.com (mailing list archive)
State Superseded
Headers show
Series x86/EFI: build adjustments | expand

Commit Message

Jan Beulich April 1, 2021, 9:44 a.m. UTC
PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
least 2.36 would silently truncate the (negative) difference when a
section is placed below the image base. Such sections would also be
wrongly placed ahead of all "normal" ones. Since, for the time being,
we build xen.efi with --strip-debug anyway, .stab* can't appear. And
.comment has an entry in /DISCARD/ already anyway in the EFI case.

Because of their unclear origin, keep the directives for the ELF case
though.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
---
It's certainly odd that we have stabs section entries in the script, but
no Dwarf ones.

Comments

Andrew Cooper April 1, 2021, 12:01 p.m. UTC | #1
On 01/04/2021 10:44, Jan Beulich wrote:
> PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
> least 2.36 would silently truncate the (negative) difference when a
> section is placed below the image base. Such sections would also be
> wrongly placed ahead of all "normal" ones. Since, for the time being,
> we build xen.efi with --strip-debug anyway, .stab* can't appear. And
> .comment has an entry in /DISCARD/ already anyway in the EFI case.
>
> Because of their unclear origin, keep the directives for the ELF case
> though.
>
> Signed-off-by: Jan Beulich <jbeulich@suse.com>
> ---
> It's certainly odd that we have stabs section entries in the script, but
> no Dwarf ones.

Its not odd in the slightest, given the heritage and lack of anyone
touching the linker file unless something is broken.

We've got dwarf symbols in xen-syms, have we not?

~Andrew
Jan Beulich April 1, 2021, 1:51 p.m. UTC | #2
On 01.04.2021 14:01, Andrew Cooper wrote:
> On 01/04/2021 10:44, Jan Beulich wrote:
>> PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
>> least 2.36 would silently truncate the (negative) difference when a
>> section is placed below the image base. Such sections would also be
>> wrongly placed ahead of all "normal" ones. Since, for the time being,
>> we build xen.efi with --strip-debug anyway, .stab* can't appear. And
>> .comment has an entry in /DISCARD/ already anyway in the EFI case.
>>
>> Because of their unclear origin, keep the directives for the ELF case
>> though.
>>
>> Signed-off-by: Jan Beulich <jbeulich@suse.com>
>> ---
>> It's certainly odd that we have stabs section entries in the script, but
>> no Dwarf ones.
> 
> Its not odd in the slightest, given the heritage and lack of anyone
> touching the linker file unless something is broken.

Heritage? Was stabs debug info ever used in any build of Xen?

> We've got dwarf symbols in xen-syms, have we not?

Yes, and that's why I mention the oddity: We have Dwarf debug info (and
hence .debug_* sections) in xen-syms without mentioning them in the
script, and we don't have stabs debug info in xen-syms yet we mention
the sections.

Jan
Roger Pau Monne April 21, 2021, 8:52 a.m. UTC | #3
On Thu, Apr 01, 2021 at 11:44:45AM +0200, Jan Beulich wrote:
> PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
> least 2.36 would silently truncate the (negative) difference when a
> section is placed below the image base. Such sections would also be
> wrongly placed ahead of all "normal" ones. Since, for the time being,
> we build xen.efi with --strip-debug anyway, .stab* can't appear. And
> .comment has an entry in /DISCARD/ already anyway in the EFI case.
> 
> Because of their unclear origin, keep the directives for the ELF case
> though.

It's my understadng thonse sections are only there for debug purposes,
and never part of the final xen binary as they are stripped?

Could we maybe remove the section load address of 0 and instead just
use the (NOLOAD) directive?

Does it really matter to place them at address 0?

I also wonder, is this change fixing some existing bug, or it's just a
cleanup change?

I also only see the .comment section in my binary output, so maybe
it's fine to just remove them from the script?

Does the Arm linker script need a similar treatment?

Thanks, Roger.
Jan Beulich April 21, 2021, 10:32 a.m. UTC | #4
On 21.04.2021 10:52, Roger Pau Monné wrote:
> On Thu, Apr 01, 2021 at 11:44:45AM +0200, Jan Beulich wrote:
>> PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
>> least 2.36 would silently truncate the (negative) difference when a
>> section is placed below the image base. Such sections would also be
>> wrongly placed ahead of all "normal" ones. Since, for the time being,
>> we build xen.efi with --strip-debug anyway, .stab* can't appear. And
>> .comment has an entry in /DISCARD/ already anyway in the EFI case.
>>
>> Because of their unclear origin, keep the directives for the ELF case
>> though.
> 
> It's my understadng thonse sections are only there for debug purposes,
> and never part of the final xen binary as they are stripped?
> 
> Could we maybe remove the section load address of 0 and instead just
> use the (NOLOAD) directive?

(NOLOAD) is meaningless for PE.

> Does it really matter to place them at address 0?

That's the convention for ELF, and also what ld defaults to for debugging
sections.

> I also wonder, is this change fixing some existing bug, or it's just a
> cleanup change?

If there were sections at 0, the resulting PE binary would end up broken.
Prior to binutils 2.37 this brokenness is silent, i.e. the linker doesn't
issue any form of diagnostic. The change therefore is addressing a latent
issue - if any such section started being non-empty, we'd be in trouble.

> I also only see the .comment section in my binary output, so maybe
> it's fine to just remove them from the script?

Which binary are you referring to - ELF or PE? In the former case, yes,
that's what the statement is for. In the latter case I can't see how this
would be, with .comment being explicitly part of /DISCARD/ in that case.

> Does the Arm linker script need a similar treatment?

No idea - they don't use ld to produce a PE binary. In fact during my
work on the binutils side for all of this, I was given a hint that on Arm
linking ELF objects into PE output may currently not be possible at all.

Jan
Roger Pau Monne April 21, 2021, 12:57 p.m. UTC | #5
On Wed, Apr 21, 2021 at 12:32:42PM +0200, Jan Beulich wrote:
> On 21.04.2021 10:52, Roger Pau Monné wrote:
> > On Thu, Apr 01, 2021 at 11:44:45AM +0200, Jan Beulich wrote:
> >> PE binaries specify section addresses by (32-bit) RVA. GNU ld up to at
> >> least 2.36 would silently truncate the (negative) difference when a
> >> section is placed below the image base. Such sections would also be
> >> wrongly placed ahead of all "normal" ones. Since, for the time being,
> >> we build xen.efi with --strip-debug anyway, .stab* can't appear. And
> >> .comment has an entry in /DISCARD/ already anyway in the EFI case.
> >>
> >> Because of their unclear origin, keep the directives for the ELF case
> >> though.
> > 
> > It's my understadng thonse sections are only there for debug purposes,
> > and never part of the final xen binary as they are stripped?
> > 
> > Could we maybe remove the section load address of 0 and instead just
> > use the (NOLOAD) directive?
> 
> (NOLOAD) is meaningless for PE.
> 
> > Does it really matter to place them at address 0?
> 
> That's the convention for ELF, and also what ld defaults to for debugging
> sections.
> 
> > I also wonder, is this change fixing some existing bug, or it's just a
> > cleanup change?
> 
> If there were sections at 0, the resulting PE binary would end up broken.
> Prior to binutils 2.37 this brokenness is silent, i.e. the linker doesn't
> issue any form of diagnostic. The change therefore is addressing a latent
> issue - if any such section started being non-empty, we'd be in trouble.
> 
> > I also only see the .comment section in my binary output, so maybe
> > it's fine to just remove them from the script?
> 
> Which binary are you referring to - ELF or PE? In the former case, yes,
> that's what the statement is for. In the latter case I can't see how this
> would be, with .comment being explicitly part of /DISCARD/ in that case.

So from a bit of searching I just did it seems like stab sections
where used during the 90s with ELF, but that this has long been
superseded by DWARF 2 becoming the default in the late 90s, hence I
think it would be fine to just remove those sections even in the ELF
case?

Thanks, Roger.
Jan Beulich April 21, 2021, 1:28 p.m. UTC | #6
On 21.04.2021 14:57, Roger Pau Monné wrote:
> So from a bit of searching I just did it seems like stab sections
> where used during the 90s with ELF, but that this has long been
> superseded by DWARF 2 becoming the default in the late 90s, hence I
> think it would be fine to just remove those sections even in the ELF
> case?

Well, maybe. Even up-to-date gcc still supports -gstabs. Plus I seem
to have a vague recollection that Andrew objected to their removal
at some (not overly distant) point. I can't find any reference there
though, so Andrew: Do you have any specific thoughts here?

Of course with the stabs sections gone, .comment would remain. I'm
very firm in not wanting to leave any statements there putting
sections at VA zero. Irrespective of .comment (to take this example)
being listed under /DISCARD/ for PE. This would only be acceptable
(to me) if ld would always have at least warned about such sections.

Jan
diff mbox series

Patch

--- a/xen/arch/x86/xen.lds.S
+++ b/xen/arch/x86/xen.lds.S
@@ -347,6 +347,7 @@  SECTIONS
 #endif
   }
 
+#ifndef EFI
   /* Stabs debugging sections.  */
   .stab 0 : { *(.stab) }
   .stabstr 0 : { *(.stabstr) }
@@ -355,6 +356,7 @@  SECTIONS
   .stab.index 0 : { *(.stab.index) }
   .stab.indexstr 0 : { *(.stab.indexstr) }
   .comment 0 : { *(.comment) }
+#endif
 }
 
 ASSERT(__2M_rwdata_end <= XEN_VIRT_END - XEN_VIRT_START + __XEN_VIRT_START -