On Tue, May 10, 2022 at 9:25 AM H.J. Lu <hjl.to...@gmail.com> wrote: > > Mark a function with SYMBOL_FLAG_FUNCTION_ENDBR when inserting ENDBR at > function entry. Skip the 4-byte ENDBR when emitting a direct call/jmp > to a local function with ENDBR at function entry. > > This has been tested on Linux kernel. > > gcc/ > > PR target/102953 > * config/i386/i386-features.cc > (rest_of_insert_endbr_and_patchable_area): Set > SYMBOL_FLAG_FUNCTION_ENDBR when inserting ENDBR. > * config/i386/i386.cc (ix86_print_operand): Skip the 4-byte ENDBR > when calling the local function with ENDBR at function entry. > * config/i386/i386.h (SYMBOL_FLAG_FUNCTION_ENDBR): New. > (SYMBOL_FLAG_FUNCTION_ENDBR_P): Likewise. > > gcc/testsuite/ > > PR target/102953 > * gcc.target/i386/pr102953-1.c: New test. > * gcc.target/i386/pr102953-2.c: Likewise. > --- > gcc/config/i386/i386-features.cc | 2 ++ > gcc/config/i386/i386.cc | 11 +++++++- > gcc/config/i386/i386.h | 5 ++++ > gcc/testsuite/gcc.target/i386/pr102953-1.c | 25 ++++++++++++++++++ > gcc/testsuite/gcc.target/i386/pr102953-2.c | 30 ++++++++++++++++++++++ > 5 files changed, 72 insertions(+), 1 deletion(-) > create mode 100644 gcc/testsuite/gcc.target/i386/pr102953-1.c > create mode 100644 gcc/testsuite/gcc.target/i386/pr102953-2.c > > diff --git a/gcc/config/i386/i386-features.cc > b/gcc/config/i386/i386-features.cc > index 6fe41c3c24f..3ca1131ed59 100644 > --- a/gcc/config/i386/i386-features.cc > +++ b/gcc/config/i386/i386-features.cc > @@ -1979,6 +1979,8 @@ rest_of_insert_endbr_and_patchable_area (bool > need_endbr, > || (TARGET_DLLIMPORT_DECL_ATTRIBUTES > && DECL_DLLIMPORT_P (cfun->decl)))) > { > + rtx symbol = XEXP (DECL_RTL (cfun->decl), 0); > + SYMBOL_REF_FLAGS (symbol) |= SYMBOL_FLAG_FUNCTION_ENDBR; > if (crtl->profile && flag_fentry) > { > /* Queue ENDBR insertion to x86_function_profiler. > diff --git a/gcc/config/i386/i386.cc b/gcc/config/i386/i386.cc > index 86752a6516a..ad1de239bef 100644 > --- a/gcc/config/i386/i386.cc > +++ b/gcc/config/i386/i386.cc > @@ -13787,7 +13787,16 @@ ix86_print_operand (FILE *file, rtx x, int code) > else if (flag_pic || MACHOPIC_INDIRECT) > output_pic_addr_const (file, x, code); > else > - output_addr_const (file, x); > + { > + /* Skip ENDBR when emitting a direct call/jmp to a local > + function with ENDBR at function entry. */ > + if (code == 'P' > + && GET_CODE (x) == SYMBOL_REF > + && SYMBOL_REF_LOCAL_P (x) > + && SYMBOL_FLAG_FUNCTION_ENDBR_P (x)) > + x = gen_rtx_PLUS (Pmode, x, GEN_INT (4)); > + output_addr_const (file, x); > + } > } > } > > diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h > index 363082ba47b..7a6317fea57 100644 > --- a/gcc/config/i386/i386.h > +++ b/gcc/config/i386/i386.h > @@ -2792,6 +2792,11 @@ extern GTY(()) tree ms_va_list_type_node; > #define SYMBOL_REF_STUBVAR_P(X) \ > ((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_STUBVAR) != 0) > > +/* Flag to mark a function with ENDBR at entry. */ > +#define SYMBOL_FLAG_FUNCTION_ENDBR (SYMBOL_FLAG_MACH_DEP << 5) > +#define SYMBOL_FLAG_FUNCTION_ENDBR_P(X) \ > + ((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_FUNCTION_ENDBR) != 0) > + > extern void debug_ready_dispatch (void); > extern void debug_dispatch_window (int); > > diff --git a/gcc/testsuite/gcc.target/i386/pr102953-1.c > b/gcc/testsuite/gcc.target/i386/pr102953-1.c > new file mode 100644 > index 00000000000..2afad391baf > --- /dev/null > +++ b/gcc/testsuite/gcc.target/i386/pr102953-1.c > @@ -0,0 +1,25 @@ > +/* { dg-do compile { target { ! *-*-darwin* } } } */ > +/* { dg-options "-O2 -fno-pic -fplt -fcf-protection" } */ > + > +extern int func (int); > + > +extern int i; > + > +__attribute__ ((noclone, noinline, noipa)) > +static int > +bar (int x) > +{ > + if (x == 0) > + return x; > + return bar (x - 1) + func (x); > +} > + > +void * > +foo (void) > +{ > + i = bar (2); > + return bar; > +} > + > +/* { dg-final { scan-assembler-times {call\t_?bar\+4\M} 2 } } */ > +/* { dg-final { scan-assembler-times {call\t_?func\M} 1 } } */ > diff --git a/gcc/testsuite/gcc.target/i386/pr102953-2.c > b/gcc/testsuite/gcc.target/i386/pr102953-2.c > new file mode 100644 > index 00000000000..5b8d517f4f2 > --- /dev/null > +++ b/gcc/testsuite/gcc.target/i386/pr102953-2.c > @@ -0,0 +1,30 @@ > +/* { dg-do compile { target { ! *-*-darwin* } } } */ > +/* { dg-options "-O2 -fno-pic -fplt -fcf-protection" } */ > + > +static int bar (int x); > +extern int func (int); > + > +int > +foo (int i) > +{ > + return bar (i); > +} > + > +void * > +bar_p (void) > +{ > + return bar; > +} > + > +__attribute__ ((noclone, noinline, noipa)) > +static int > +bar (int x) > +{ > + if (x == 0) > + return x; > + return bar (x - 1) + func (x); > +} > + > +/* { dg-final { scan-assembler-times {call\t_?bar\+4\M} 1 } } */ > +/* { dg-final { scan-assembler-times {jmp\t_?bar\+4\M} 1 } } */ > +/* { dg-final { scan-assembler-times {call\t_?func\M} 1 } } */ > -- > 2.35.1 >
PING. -- H.J.