public inbox for devel@edk2.groups.io
 help / color / mirror / Atom feed
* [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
@ 2019-11-07  9:06 Ard Biesheuvel
  2019-11-07  9:09 ` Ard Biesheuvel
  2019-11-08  0:39 ` [edk2-devel] " Liming Gao
  0 siblings, 2 replies; 6+ messages in thread
From: Ard Biesheuvel @ 2019-11-07  9:06 UTC (permalink / raw)
  To: devel; +Cc: eugene, Ard Biesheuvel

In order to permit the use of compilers that only implement the small
code model [which involves the use of ADRP instructions that require
4 KB segment alignment] for generating PE/COFF binaries with a small
footprint, we patch ADRP instructions into ADR instructions while doing
the ELF to PE/COFF conversion.

As it turns out, the linker may be doing the same, but for different
reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
affects ADRP instructions appearing at a certain offset in memory, and
one of the mitigations for this erratum is to patch them into ADR
instructions at link time if the symbol reference is within -/+ 1 MB.
However, the LD linker fails to update the static relocation tables, and
so we end up with an ADR instruction in the fully linked binary, but
with a relocation entry in the RELA section identifying it as an ADRP
instruction.

Since the linker has already updated the symbol reference, there is no
handling needed in GenFw for such instructions, and we can simply treat
it as an ordinary ADR. However, since it is guaranteed to be accompanied
by an add or load instruction with a LO12 relocation referencing the same
symbol, the section offset check we apply to ADR instructions is going to
take place anyway, so we can just disregard the ADR instruction entirely.

Reported-by: Eugene Cohen <eugene@hp.com>
Suggested-by: Eugene Cohen <eugene@hp.com>
Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
---
 BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c b/BaseTools/Source/C/GenFw/Elf64Convert.c
index d574300ac4fe..d623dce1f9da 100644
--- a/BaseTools/Source/C/GenFw/Elf64Convert.c
+++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
@@ -1044,6 +1044,19 @@ WriteSections64 (
             /* fall through */
 
           case R_AARCH64_ADR_PREL_PG_HI21:
+            //
+            // In order to handle Cortex-A53 erratum #843419, the LD linker may
+            // convert ADRP instructions into ADR instructions, but without
+            // updating the static relocation type, and so we may end up here
+            // while the instruction in question is actually ADR. So let's
+            // just disregard it: the section offset check we apply below to
+            // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC
+            // companion instruction as well, so it is safe to omit it here.
+            //
+            if ((*(UINT32 *)Targ & BIT31) == 0) {
+              break;
+            }
+
             //
             // AArch64 PG_H21 relocations are typically paired with ABS_LO12
             // relocations, where a PC-relative reference with +/- 4 GB range is
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
  2019-11-07  9:06 [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already Ard Biesheuvel
@ 2019-11-07  9:09 ` Ard Biesheuvel
  2019-11-07 12:17   ` Cohen, Eugene
  2019-11-07 16:14   ` Leif Lindholm
  2019-11-08  0:39 ` [edk2-devel] " Liming Gao
  1 sibling, 2 replies; 6+ messages in thread
From: Ard Biesheuvel @ 2019-11-07  9:09 UTC (permalink / raw)
  To: edk2-devel-groups-io, Leif Lindholm, Gao, Liming; +Cc: Cohen, Eugene

(+ Leif, Liming)

On Thu, 7 Nov 2019 at 10:06, Ard Biesheuvel <ard.biesheuvel@linaro.org> wrote:
>
> In order to permit the use of compilers that only implement the small
> code model [which involves the use of ADRP instructions that require
> 4 KB segment alignment] for generating PE/COFF binaries with a small
> footprint, we patch ADRP instructions into ADR instructions while doing
> the ELF to PE/COFF conversion.
>
> As it turns out, the linker may be doing the same, but for different
> reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
> affects ADRP instructions appearing at a certain offset in memory, and
> one of the mitigations for this erratum is to patch them into ADR
> instructions at link time if the symbol reference is within -/+ 1 MB.
> However, the LD linker fails to update the static relocation tables, and
> so we end up with an ADR instruction in the fully linked binary, but
> with a relocation entry in the RELA section identifying it as an ADRP
> instruction.
>
> Since the linker has already updated the symbol reference, there is no
> handling needed in GenFw for such instructions, and we can simply treat
> it as an ordinary ADR. However, since it is guaranteed to be accompanied
> by an add or load instruction with a LO12 relocation referencing the same
> symbol, the section offset check we apply to ADR instructions is going to
> take place anyway, so we can just disregard the ADR instruction entirely.
>
> Reported-by: Eugene Cohen <eugene@hp.com>
> Suggested-by: Eugene Cohen <eugene@hp.com>
> Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
> ---
>  BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
>  1 file changed, 13 insertions(+)
>
> diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c b/BaseTools/Source/C/GenFw/Elf64Convert.c
> index d574300ac4fe..d623dce1f9da 100644
> --- a/BaseTools/Source/C/GenFw/Elf64Convert.c
> +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
> @@ -1044,6 +1044,19 @@ WriteSections64 (
>              /* fall through */
>
>            case R_AARCH64_ADR_PREL_PG_HI21:
> +            //
> +            // In order to handle Cortex-A53 erratum #843419, the LD linker may
> +            // convert ADRP instructions into ADR instructions, but without
> +            // updating the static relocation type, and so we may end up here
> +            // while the instruction in question is actually ADR. So let's
> +            // just disregard it: the section offset check we apply below to
> +            // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC
> +            // companion instruction as well, so it is safe to omit it here.
> +            //
> +            if ((*(UINT32 *)Targ & BIT31) == 0) {
> +              break;
> +            }
> +
>              //
>              // AArch64 PG_H21 relocations are typically paired with ABS_LO12
>              // relocations, where a PC-relative reference with +/- 4 GB range is
> --
> 2.17.1
>

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
  2019-11-07  9:09 ` Ard Biesheuvel
@ 2019-11-07 12:17   ` Cohen, Eugene
  2019-11-07 16:14   ` Leif Lindholm
  1 sibling, 0 replies; 6+ messages in thread
From: Cohen, Eugene @ 2019-11-07 12:17 UTC (permalink / raw)
  To: Ard Biesheuvel, edk2-devel-groups-io, Leif Lindholm, Gao, Liming

Ard,

Fantastic discovery tracking this down to the toolchain.

Tested-by: Eugene Cohen <eugene@hp.com>

Thanks,

Eugene

> -----Original Message-----
> From: Ard Biesheuvel <ard.biesheuvel@linaro.org>
> Sent: Thursday, November 07, 2019 2:09 AM
> To: edk2-devel-groups-io <devel@edk2.groups.io>; Leif Lindholm
> <leif.lindholm@linaro.org>; Gao, Liming <liming.gao@intel.com>
> Cc: Cohen, Eugene <eugene@hp.com>
> Subject: Re: [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP
> instructions that are patched already
> 
> (+ Leif, Liming)
> 
> On Thu, 7 Nov 2019 at 10:06, Ard Biesheuvel <ard.biesheuvel@linaro.org>
> wrote:
> >
> > In order to permit the use of compilers that only implement the small
> > code model [which involves the use of ADRP instructions that require
> > 4 KB segment alignment] for generating PE/COFF binaries with a small
> > footprint, we patch ADRP instructions into ADR instructions while
> > doing the ELF to PE/COFF conversion.
> >
> > As it turns out, the linker may be doing the same, but for different
> > reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
> > affects ADRP instructions appearing at a certain offset in memory, and
> > one of the mitigations for this erratum is to patch them into ADR
> > instructions at link time if the symbol reference is within -/+ 1 MB.
> > However, the LD linker fails to update the static relocation tables,
> > and so we end up with an ADR instruction in the fully linked binary,
> > but with a relocation entry in the RELA section identifying it as an
> > ADRP instruction.
> >
> > Since the linker has already updated the symbol reference, there is no
> > handling needed in GenFw for such instructions, and we can simply
> > treat it as an ordinary ADR. However, since it is guaranteed to be
> > accompanied by an add or load instruction with a LO12 relocation
> > referencing the same symbol, the section offset check we apply to ADR
> > instructions is going to take place anyway, so we can just disregard the ADR
> instruction entirely.
> >
> > Reported-by: Eugene Cohen <eugene@hp.com>
> > Suggested-by: Eugene Cohen <eugene@hp.com>
> > Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
> > ---
> >  BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
> >  1 file changed, 13 insertions(+)
> >
> > diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c
> > b/BaseTools/Source/C/GenFw/Elf64Convert.c
> > index d574300ac4fe..d623dce1f9da 100644
> > --- a/BaseTools/Source/C/GenFw/Elf64Convert.c
> > +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
> > @@ -1044,6 +1044,19 @@ WriteSections64 (
> >              /* fall through */
> >
> >            case R_AARCH64_ADR_PREL_PG_HI21:
> > +            //
> > +            // In order to handle Cortex-A53 erratum #843419, the LD linker may
> > +            // convert ADRP instructions into ADR instructions, but without
> > +            // updating the static relocation type, and so we may end up here
> > +            // while the instruction in question is actually ADR. So let's
> > +            // just disregard it: the section offset check we apply below to
> > +            // ADR instructions will trigger for its
> R_AARCH64_xxx_ABS_LO12_NC
> > +            // companion instruction as well, so it is safe to omit it here.
> > +            //
> > +            if ((*(UINT32 *)Targ & BIT31) == 0) {
> > +              break;
> > +            }
> > +
> >              //
> >              // AArch64 PG_H21 relocations are typically paired with ABS_LO12
> >              // relocations, where a PC-relative reference with +/- 4
> > GB range is
> > --
> > 2.17.1
> >


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
  2019-11-07  9:09 ` Ard Biesheuvel
  2019-11-07 12:17   ` Cohen, Eugene
@ 2019-11-07 16:14   ` Leif Lindholm
  1 sibling, 0 replies; 6+ messages in thread
From: Leif Lindholm @ 2019-11-07 16:14 UTC (permalink / raw)
  To: Ard Biesheuvel; +Cc: edk2-devel-groups-io, Gao, Liming, Cohen, Eugene

I *think* I understand what's going on (thank you for detailed commit
message and comment block). And that looks like a good workaround.

Thanks!
Reviewed-by: Leif Lindholm <leif.lindholm@linaro.org>


On Thu, Nov 07, 2019 at 10:09:27AM +0100, Ard Biesheuvel wrote:
> (+ Leif, Liming)
> 
> On Thu, 7 Nov 2019 at 10:06, Ard Biesheuvel <ard.biesheuvel@linaro.org> wrote:
> >
> > In order to permit the use of compilers that only implement the small
> > code model [which involves the use of ADRP instructions that require
> > 4 KB segment alignment] for generating PE/COFF binaries with a small
> > footprint, we patch ADRP instructions into ADR instructions while doing
> > the ELF to PE/COFF conversion.
> >
> > As it turns out, the linker may be doing the same, but for different
> > reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
> > affects ADRP instructions appearing at a certain offset in memory, and
> > one of the mitigations for this erratum is to patch them into ADR
> > instructions at link time if the symbol reference is within -/+ 1 MB.
> > However, the LD linker fails to update the static relocation tables, and
> > so we end up with an ADR instruction in the fully linked binary, but
> > with a relocation entry in the RELA section identifying it as an ADRP
> > instruction.
> >
> > Since the linker has already updated the symbol reference, there is no
> > handling needed in GenFw for such instructions, and we can simply treat
> > it as an ordinary ADR. However, since it is guaranteed to be accompanied
> > by an add or load instruction with a LO12 relocation referencing the same
> > symbol, the section offset check we apply to ADR instructions is going to
> > take place anyway, so we can just disregard the ADR instruction entirely.
> >
> > Reported-by: Eugene Cohen <eugene@hp.com>
> > Suggested-by: Eugene Cohen <eugene@hp.com>
> > Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
> > ---
> >  BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
> >  1 file changed, 13 insertions(+)
> >
> > diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c b/BaseTools/Source/C/GenFw/Elf64Convert.c
> > index d574300ac4fe..d623dce1f9da 100644
> > --- a/BaseTools/Source/C/GenFw/Elf64Convert.c
> > +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
> > @@ -1044,6 +1044,19 @@ WriteSections64 (
> >              /* fall through */
> >
> >            case R_AARCH64_ADR_PREL_PG_HI21:
> > +            //
> > +            // In order to handle Cortex-A53 erratum #843419, the LD linker may
> > +            // convert ADRP instructions into ADR instructions, but without
> > +            // updating the static relocation type, and so we may end up here
> > +            // while the instruction in question is actually ADR. So let's
> > +            // just disregard it: the section offset check we apply below to
> > +            // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC
> > +            // companion instruction as well, so it is safe to omit it here.
> > +            //
> > +            if ((*(UINT32 *)Targ & BIT31) == 0) {
> > +              break;
> > +            }
> > +
> >              //
> >              // AArch64 PG_H21 relocations are typically paired with ABS_LO12
> >              // relocations, where a PC-relative reference with +/- 4 GB range is
> > --
> > 2.17.1
> >

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [edk2-devel] [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
  2019-11-07  9:06 [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already Ard Biesheuvel
  2019-11-07  9:09 ` Ard Biesheuvel
@ 2019-11-08  0:39 ` Liming Gao
  2019-11-08  8:00   ` Ard Biesheuvel
  1 sibling, 1 reply; 6+ messages in thread
From: Liming Gao @ 2019-11-08  0:39 UTC (permalink / raw)
  To: devel@edk2.groups.io, ard.biesheuvel@linaro.org; +Cc: eugene@hp.com

Acked-by: Liming Gao <liming.gao@intel.com>

>-----Original Message-----
>From: devel@edk2.groups.io [mailto:devel@edk2.groups.io] On Behalf Of Ard
>Biesheuvel
>Sent: Thursday, November 07, 2019 5:06 PM
>To: devel@edk2.groups.io
>Cc: eugene@hp.com; Ard Biesheuvel <ard.biesheuvel@linaro.org>
>Subject: [edk2-devel] [PATCH 1/1] BaseTools/GenFw AARCH64: disregard
>ADRP instructions that are patched already
>
>In order to permit the use of compilers that only implement the small
>code model [which involves the use of ADRP instructions that require
>4 KB segment alignment] for generating PE/COFF binaries with a small
>footprint, we patch ADRP instructions into ADR instructions while doing
>the ELF to PE/COFF conversion.
>
>As it turns out, the linker may be doing the same, but for different
>reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
>affects ADRP instructions appearing at a certain offset in memory, and
>one of the mitigations for this erratum is to patch them into ADR
>instructions at link time if the symbol reference is within -/+ 1 MB.
>However, the LD linker fails to update the static relocation tables, and
>so we end up with an ADR instruction in the fully linked binary, but
>with a relocation entry in the RELA section identifying it as an ADRP
>instruction.
>
>Since the linker has already updated the symbol reference, there is no
>handling needed in GenFw for such instructions, and we can simply treat
>it as an ordinary ADR. However, since it is guaranteed to be accompanied
>by an add or load instruction with a LO12 relocation referencing the same
>symbol, the section offset check we apply to ADR instructions is going to
>take place anyway, so we can just disregard the ADR instruction entirely.
>
>Reported-by: Eugene Cohen <eugene@hp.com>
>Suggested-by: Eugene Cohen <eugene@hp.com>
>Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
>---
> BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
> 1 file changed, 13 insertions(+)
>
>diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c
>b/BaseTools/Source/C/GenFw/Elf64Convert.c
>index d574300ac4fe..d623dce1f9da 100644
>--- a/BaseTools/Source/C/GenFw/Elf64Convert.c
>+++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
>@@ -1044,6 +1044,19 @@ WriteSections64 (
>             /* fall through */
>
>           case R_AARCH64_ADR_PREL_PG_HI21:
>+            //
>+            // In order to handle Cortex-A53 erratum #843419, the LD linker may
>+            // convert ADRP instructions into ADR instructions, but without
>+            // updating the static relocation type, and so we may end up here
>+            // while the instruction in question is actually ADR. So let's
>+            // just disregard it: the section offset check we apply below to
>+            // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC
>+            // companion instruction as well, so it is safe to omit it here.
>+            //
>+            if ((*(UINT32 *)Targ & BIT31) == 0) {
>+              break;
>+            }
>+
>             //
>             // AArch64 PG_H21 relocations are typically paired with ABS_LO12
>             // relocations, where a PC-relative reference with +/- 4 GB range is
>--
>2.17.1
>
>
>


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [edk2-devel] [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already
  2019-11-08  0:39 ` [edk2-devel] " Liming Gao
@ 2019-11-08  8:00   ` Ard Biesheuvel
  0 siblings, 0 replies; 6+ messages in thread
From: Ard Biesheuvel @ 2019-11-08  8:00 UTC (permalink / raw)
  To: Gao, Liming; +Cc: devel@edk2.groups.io, eugene@hp.com

On Fri, 8 Nov 2019 at 01:39, Gao, Liming <liming.gao@intel.com> wrote:
>
> Acked-by: Liming Gao <liming.gao@intel.com>
>

Thanks all

Pushed as 9e9f0be353d4..f55c76b301f1

> >-----Original Message-----
> >From: devel@edk2.groups.io [mailto:devel@edk2.groups.io] On Behalf Of Ard
> >Biesheuvel
> >Sent: Thursday, November 07, 2019 5:06 PM
> >To: devel@edk2.groups.io
> >Cc: eugene@hp.com; Ard Biesheuvel <ard.biesheuvel@linaro.org>
> >Subject: [edk2-devel] [PATCH 1/1] BaseTools/GenFw AARCH64: disregard
> >ADRP instructions that are patched already
> >
> >In order to permit the use of compilers that only implement the small
> >code model [which involves the use of ADRP instructions that require
> >4 KB segment alignment] for generating PE/COFF binaries with a small
> >footprint, we patch ADRP instructions into ADR instructions while doing
> >the ELF to PE/COFF conversion.
> >
> >As it turns out, the linker may be doing the same, but for different
> >reasons: there is a silicon erratum #843419 for ARM Cortex-A53 which
> >affects ADRP instructions appearing at a certain offset in memory, and
> >one of the mitigations for this erratum is to patch them into ADR
> >instructions at link time if the symbol reference is within -/+ 1 MB.
> >However, the LD linker fails to update the static relocation tables, and
> >so we end up with an ADR instruction in the fully linked binary, but
> >with a relocation entry in the RELA section identifying it as an ADRP
> >instruction.
> >
> >Since the linker has already updated the symbol reference, there is no
> >handling needed in GenFw for such instructions, and we can simply treat
> >it as an ordinary ADR. However, since it is guaranteed to be accompanied
> >by an add or load instruction with a LO12 relocation referencing the same
> >symbol, the section offset check we apply to ADR instructions is going to
> >take place anyway, so we can just disregard the ADR instruction entirely.
> >
> >Reported-by: Eugene Cohen <eugene@hp.com>
> >Suggested-by: Eugene Cohen <eugene@hp.com>
> >Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
> >---
> > BaseTools/Source/C/GenFw/Elf64Convert.c | 13 +++++++++++++
> > 1 file changed, 13 insertions(+)
> >
> >diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c
> >b/BaseTools/Source/C/GenFw/Elf64Convert.c
> >index d574300ac4fe..d623dce1f9da 100644
> >--- a/BaseTools/Source/C/GenFw/Elf64Convert.c
> >+++ b/BaseTools/Source/C/GenFw/Elf64Convert.c
> >@@ -1044,6 +1044,19 @@ WriteSections64 (
> >             /* fall through */
> >
> >           case R_AARCH64_ADR_PREL_PG_HI21:
> >+            //
> >+            // In order to handle Cortex-A53 erratum #843419, the LD linker may
> >+            // convert ADRP instructions into ADR instructions, but without
> >+            // updating the static relocation type, and so we may end up here
> >+            // while the instruction in question is actually ADR. So let's
> >+            // just disregard it: the section offset check we apply below to
> >+            // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC
> >+            // companion instruction as well, so it is safe to omit it here.
> >+            //
> >+            if ((*(UINT32 *)Targ & BIT31) == 0) {
> >+              break;
> >+            }
> >+
> >             //
> >             // AArch64 PG_H21 relocations are typically paired with ABS_LO12
> >             // relocations, where a PC-relative reference with +/- 4 GB range is
> >--
> >2.17.1
> >
> >
> >
>

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2019-11-08  8:00 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2019-11-07  9:06 [PATCH 1/1] BaseTools/GenFw AARCH64: disregard ADRP instructions that are patched already Ard Biesheuvel
2019-11-07  9:09 ` Ard Biesheuvel
2019-11-07 12:17   ` Cohen, Eugene
2019-11-07 16:14   ` Leif Lindholm
2019-11-08  0:39 ` [edk2-devel] " Liming Gao
2019-11-08  8:00   ` Ard Biesheuvel

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox