x86; Add -mmanual-endbr and cf_check function attribute

Currently GCC inserts ENDBR instruction at entries of all non-static
functions, unless LTO compilation is used.  Marking all functions,
which are not called indirectly with nocf_check attribute, is not
ideal since 99% of functions in a program may be of this kind.

This patch adds -mmanual-endbr and cf_check function attribute.  They
can be used together with -fcf-protection such that ENDBR instruction
is inserted only at entries of functions with cf_check attribute.  It
can limit number of ENDBR instructions to reduce program size.

gcc/

	* config/i386/i386.c (rest_of_insert_endbranch): Insert ENDBR
	at the function entry only when -mmanual-endbr isn't used or
	there is cf_check function attribute.
	(ix86_attribute_table): Add cf_check.
	* config/i386/i386.opt: Add -mmanual-endbr.
	* doc/extend.texi: Document cf_check attribute.
	* doc/invoke.texi: Document -mmanual-endbr.

gcc/testsuite/

	* gcc.target/i386/cf_check-1.c: New test.
	* gcc.target/i386/cf_check-2.c: Likewise.
	* gcc.target/i386/cf_check-3.c: Likewise.
	* gcc.target/i386/cf_check-4.c: Likewise.
	* gcc.target/i386/cf_check-5.c: Likewise.

From-SVN: r267154
This commit is contained in:
H.J. Lu 2018-12-14 21:35:36 +00:00 committed by H.J. Lu
parent c759830b29
commit 06553c89f5
11 changed files with 96 additions and 1 deletions

View File

@ -1,3 +1,13 @@
2018-12-14 H.J. Lu <hongjiu.lu@intel.com>
* config/i386/i386.c (rest_of_insert_endbranch): Insert ENDBR
at the function entry only when -mmanual-endbr isn't used or
there is cf_check function attribute.
(ix86_attribute_table): Add cf_check.
* config/i386/i386.opt: Add -mmanual-endbr.
* doc/extend.texi: Document cf_check attribute.
* doc/invoke.texi: Document -mmanual-endbr.
2018-12-14 Thomas Schwinge <thomas@codesourcery.com>
Cesar Philippidis <cesar@codesourcery.com>

View File

@ -2640,6 +2640,9 @@ rest_of_insert_endbranch (void)
if (!lookup_attribute ("nocf_check",
TYPE_ATTRIBUTES (TREE_TYPE (cfun->decl)))
&& (!flag_manual_endbr
|| lookup_attribute ("cf_check",
DECL_ATTRIBUTES (cfun->decl)))
&& !cgraph_node::get (cfun->decl)->only_called_directly_p ())
{
/* Queue ENDBR insertion to x86_function_profiler. */
@ -45260,6 +45263,9 @@ static const struct attribute_spec ix86_attribute_table[] =
ix86_handle_fentry_name, NULL },
{ "fentry_section", 1, 1, true, false, false, false,
ix86_handle_fentry_name, NULL },
{ "cf_check", 0, 0, true, false, false, false,
ix86_handle_fndecl_attribute, NULL },
/* End element. */
{ NULL, 0, 0, false, false, false, false, NULL, NULL }
};

View File

@ -1028,6 +1028,11 @@ Target Report Undocumented Var(flag_cet_switch) Init(0)
Turn on CET instrumentation for switch statements that use a jump table and
an indirect jump.
mmanual-endbr
Target Report Var(flag_manual_endbr) Init(0)
Insert ENDBR instruction at function entry only via cf_check attribute
for CET instrumentation.
mforce-indirect-call
Target Report Var(flag_force_indirect_call) Init(0)
Make all function calls indirect.

View File

@ -6095,6 +6095,13 @@ foo (void)
@}
@end smallexample
@item cf_check
@cindex @code{cf_check} function attribute, x86
The @code{cf_check} attribute on a function is used to inform the
compiler that ENDBR instruction should be placed at the function
entry when @option{-fcf-protection=branch} is enabled.
@item indirect_return
@cindex @code{indirect_return} function attribute, x86

View File

@ -1263,7 +1263,7 @@ See RS/6000 and PowerPC Options.
-msse4a -m3dnow -m3dnowa -mpopcnt -mabm -mbmi -mtbm -mfma4 -mxop @gol
-mlzcnt -mbmi2 -mfxsr -mxsave -mxsaveopt -mrtm -mlwp @gol
-mmwaitx -mclzero -mpku -mthreads -mgfni -mvaes -mwaitpkg @gol
-mshstk -mforce-indirect-call -mavx512vbmi2 @gol
-mshstk -mmanual-endbr -mforce-indirect-call -mavx512vbmi2 @gol
-mvpclmulqdq -mavx512bitalg -mmovdiri -mmovdir64b -mavx512vpopcntdq @gol
-mcldemote -mms-bitfields -mno-align-stringops -minline-all-stringops @gol
-minline-stringops-dynamically -mstringop-strategy=@var{alg} @gol
@ -27968,6 +27968,13 @@ Force all calls to functions to be indirect. This is useful
when using Intel Processor Trace where it generates more precise timing
information for function calls.
@item -mmanual-endbr
@opindex mmanual-endbr
Insert ENDBR instruction at function entry only via the @code{cf_check}
function attribute. This is useful when used with the option
@option{-fcf-protection=branch} to control ENDBR insertion at the
function entry.
@item -mcall-ms2sysv-xlogues
@opindex mcall-ms2sysv-xlogues
@opindex mno-call-ms2sysv-xlogues

View File

@ -1,3 +1,11 @@
2018-12-14 H.J. Lu <hongjiu.lu@intel.com>
* gcc.target/i386/cf_check-1.c: New test.
* gcc.target/i386/cf_check-2.c: Likewise.
* gcc.target/i386/cf_check-3.c: Likewise.
* gcc.target/i386/cf_check-4.c: Likewise.
* gcc.target/i386/cf_check-5.c: Likewise.
2018-12-14 Thomas Schwinge <thomas@codesourcery.com>
Cesar Philippidis <cesar@codesourcery.com>

View File

@ -0,0 +1,11 @@
/* { dg-do compile } */
/* { dg-options "-O2 -fcf-protection -mmanual-endbr" } */
/* { dg-final { scan-assembler-not {\mendbr} } } */
extern void bar (void) __attribute__((__cf_check__));
void
foo (void)
{
bar ();
}

View File

@ -0,0 +1,11 @@
/* { dg-do compile } */
/* { dg-options "-O2 -fcf-protection -mno-manual-endbr" } */
/* { dg-final { scan-assembler-times {\mendbr} 1 } } */
extern void bar (void) __attribute__((__cf_check__));
void
foo (void)
{
bar ();
}

View File

@ -0,0 +1,11 @@
/* { dg-do compile } */
/* { dg-options "-O2 -fcf-protection=none" } */
/* { dg-final { scan-assembler-not {\mendbr} } } */
extern void bar (void) __attribute__((__cf_check__));
void
foo (void)
{
bar ();
}

View File

@ -0,0 +1,10 @@
/* { dg-do compile } */
/* { dg-options "-O2 -fcf-protection -mmanual-endbr" } */
/* { dg-final { scan-assembler-times {\mendbr} 1 } } */
extern void foo (void) __attribute__((__cf_check__));
void
foo (void)
{
}

View File

@ -0,0 +1,9 @@
/* { dg-do compile } */
/* { dg-options "-O2 -fcf-protection -mmanual-endbr" } */
/* { dg-final { scan-assembler-times {\mendbr} 1 } } */
__attribute__((__cf_check__))
void
foo (void)
{
}