From 9be3bb2c0a258fd6a7d3d05d232a21930c757d3c Mon Sep 17 00:00:00 2001
From: "H.J. Lu" <hjl.tools@gmail.com>
Date: Wed, 29 Apr 2020 04:52:46 -0700
Subject: [PATCH] x86: Allow -fcf-protection with external thunk

Allow -fcf-protection with external thunk since the external thunk can be
made compatible with -fcf-protection.

gcc/

	PR target/93654
	* config/i386/i386-options.c (ix86_set_indirect_branch_type):
	Allow -fcf-protection with -mindirect-branch=thunk-extern and
	-mfunction-return=thunk-extern.
	* doc/invoke.texi: Update notes for -fcf-protection=branch with
	-mindirect-branch=thunk-extern and -mindirect-return=thunk-extern.

gcc/testsuite/

	PR target/93654
	* gcc.target/i386/pr93654.c: New test.
---
 gcc/ChangeLog                           |  9 +++++++++
 gcc/config/i386/i386-options.c          |  4 ++++
 gcc/doc/invoke.texi                     | 10 +++++++---
 gcc/testsuite/ChangeLog                 |  5 +++++
 gcc/testsuite/gcc.target/i386/pr93654.c |  9 +++++++++
 5 files changed, 34 insertions(+), 3 deletions(-)
 create mode 100644 gcc/testsuite/gcc.target/i386/pr93654.c

diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 2287ff97ea1f..67417932afc6 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,12 @@
+2020-04-29  H.J. Lu  <hongjiu.lu@intel.com>
+
+	PR target/93654
+	* config/i386/i386-options.c (ix86_set_indirect_branch_type):
+	Allow -fcf-protection with -mindirect-branch=thunk-extern and
+	-mfunction-return=thunk-extern.
+	* doc/invoke.texi: Update notes for -fcf-protection=branch with
+	-mindirect-branch=thunk-extern and -mindirect-return=thunk-extern.
+
 2020-04-29  Richard Sandiford  <richard.sandiford@arm.com>
 
 	* doc/sourcebuild.texi: Add missing arm_arch_v8a_hard_ok anchor.
diff --git a/gcc/config/i386/i386-options.c b/gcc/config/i386/i386-options.c
index e0be49325341..5c21fce06a4c 100644
--- a/gcc/config/i386/i386-options.c
+++ b/gcc/config/i386/i386-options.c
@@ -3083,6 +3083,8 @@ ix86_set_indirect_branch_type (tree fndecl)
 		? "thunk-extern" : "thunk"));
 
       if (cfun->machine->indirect_branch_type != indirect_branch_keep
+	  && (cfun->machine->indirect_branch_type
+	      != indirect_branch_thunk_extern)
 	  && (flag_cf_protection & CF_RETURN))
 	error ("%<-mindirect-branch%> and %<-fcf-protection%> are not "
 	       "compatible");
@@ -3126,6 +3128,8 @@ ix86_set_indirect_branch_type (tree fndecl)
 		? "thunk-extern" : "thunk"));
 
       if (cfun->machine->function_return_type != indirect_branch_keep
+	  && (cfun->machine->function_return_type
+	      != indirect_branch_thunk_extern)
 	  && (flag_cf_protection & CF_RETURN))
 	error ("%<-mfunction-return%> and %<-fcf-protection%> are not "
 	       "compatible");
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index fed38e88ae55..5bb7d94833e5 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -30097,9 +30097,9 @@ Note that @option{-mcmodel=large} is incompatible with
 @option{-mindirect-branch=thunk-extern} since the thunk function may
 not be reachable in the large code model.
 
-Note that @option{-mindirect-branch=thunk-extern} is incompatible with
-@option{-fcf-protection=branch} since the external thunk cannot be modified
-to disable control-flow check.
+Note that @option{-mindirect-branch=thunk-extern} is compatible with
+@option{-fcf-protection=branch} since the external thunk can be made
+to enable control-flow check.
 
 @item -mfunction-return=@var{choice}
 @opindex mfunction-return
@@ -30112,6 +30112,10 @@ object file.  You can control this behavior for a specific function by
 using the function attribute @code{function_return}.
 @xref{Function Attributes}.
 
+Note that @option{-mindirect-return=thunk-extern} is compatible with
+@option{-fcf-protection=branch} since the external thunk can be made
+to enable control-flow check.
+
 Note that @option{-mcmodel=large} is incompatible with
 @option{-mfunction-return=thunk} and
 @option{-mfunction-return=thunk-extern} since the thunk function may
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index b4d1ee2b8c21..b635ce1939d6 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2020-04-29  H.J. Lu  <hongjiu.lu@intel.com>
+
+	PR target/93654
+	* gcc.target/i386/pr93654.c: New test.
+
 2020-04-29  Richard Sandiford  <richard.sandiford@arm.com>
 
 	* lib/target-supports.exp: Add v8a_hard to the list of arm_arch_*
diff --git a/gcc/testsuite/gcc.target/i386/pr93654.c b/gcc/testsuite/gcc.target/i386/pr93654.c
new file mode 100644
index 000000000000..ec5bdce86a6b
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr93654.c
@@ -0,0 +1,9 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fcf-protection -mfunction-return=thunk-extern -mindirect-branch=thunk-extern" } */
+
+int
+bar (void (*foo) (void))
+{
+  foo (); 
+  return 0;
+}
-- 
GitLab