This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH v2][C][ADA] use function descriptors instead of trampolines in C
- From: "Uecker, Martin" <Martin dot Uecker at med dot uni-goettingen dot de>
- To: "gcc-patches at gcc dot gnu dot org" <gcc-patches at gcc dot gnu dot org>
- Cc: "law at redhat dot com" <law at redhat dot com>, "ebotcazou at adacore dot com" <ebotcazou at adacore dot com>, "joseph at codesourcery dot com" <joseph at codesourcery dot com>
- Date: Mon, 20 Aug 2018 14:07:01 +0000
- Subject: [PATCH v2][C][ADA] use function descriptors instead of trampolines in C
- References: <1534005653.22677.9.camel@med.uni-goettingen.de> <1534609978.14596.2.camel@med.uni-goettingen.de>
This is a new version which adds proper changelog entries and
a test case (no actual code changes).
Bootstrapped an regression tested on x86_64.
gcc/
* common.opt (flag_trampolines): Change default.
* calls.c (prepare_call_address): Remove check for
flag_trampolines. Decision is now made in FEs.
* tree-nested.c (convert_tramp_reference_op): Likewise.
gcc/ada/
* gcc-interface/trans.c (Attribute_to_gnu): Add check for
flag_trampolines.
gcc/c/
* c-objc-common.h: Define
LANG_HOOKS_CUSTOM_FUNCTION_DESCRIPTORS.
* c-typeck.c (function_to_pointer_conversion): If using
descriptors
instead of trampolines, amend function address with
FUNC_ADDR_BY_DESCRIPTOR and calls with
ALL_EXPR_BY_DESCRIPTOR.
gcc/testsuite/
* gcc.dg/trampoline-2.c: New test.
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index ec1fb242c23..e5f3844e8fd 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2018-08-20 Martin Uecker <martin.uecker@med.uni-goettingen.de>
+
+ * common.opt (flag_trampolines): Change default.
+ * calls.c (prepare_call_address): Remove check for
+ flag_trampolines. Decision is now made in FEs.
+ * tree-nested.c (convert_tramp_reference_op): Likewise.
+
2018-08-19 Uros Bizjak <ubizjak@gmail.com>
PR target/86994
diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog
index 792811fb989..d906909774b 100644
--- a/gcc/ada/ChangeLog
+++ b/gcc/ada/ChangeLog
@@ -1,3 +1,8 @@
+2018-08-20 Martin Uecker <martin.uecker@med.uni-goettingen.de>
+
+ * gcc-interface/trans.c (Attribute_to_gnu): Add check for
+ flag_trampolines.
+
2018-08-03 Pierre-Marie de Rodat <derodat@adacore.com>
Reverts
diff --git a/gcc/ada/gcc-interface/trans.c b/gcc/ada/gcc-
interface/trans.c
index 0371d00fce1..1b95f7070ac 100644
--- a/gcc/ada/gcc-interface/trans.c
+++ b/gcc/ada/gcc-interface/trans.c
@@ -1769,7 +1769,8 @@ Attribute_to_gnu (Node_Id gnat_node, tree
*gnu_result_type_p, int attribute)
if ((attribute == Attr_Access
|| attribute == Attr_Unrestricted_Access)
&& targetm.calls.custom_function_descriptors > 0
- && Can_Use_Internal_Rep (Etype (gnat_node)))
+ && Can_Use_Internal_Rep (Etype (gnat_node))
+ && (flag_trampolines != 1))
FUNC_ADDR_BY_DESCRIPTOR (gnu_expr) = 1;
/* Otherwise, we need to check that we are not violating
the
@@ -4341,7 +4342,8 @@ Call_to_gnu (Node_Id gnat_node, tree
*gnu_result_type_p, tree gnu_target,
/* If the access type doesn't require foreign-compatible
representation,
be prepared for descriptors. */
if (targetm.calls.custom_function_descriptors > 0
- && Can_Use_Internal_Rep (Etype (Prefix (Name (gnat_node)))))
+ && Can_Use_Internal_Rep (Etype (Prefix (Name (gnat_node))))
+ && (flag_trampolines != 1))
by_descriptor = true;
}
else if (Nkind (Name (gnat_node)) == N_Attribute_Reference)
diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog
index 7bde11c1f19..028a7284e41 100644
--- a/gcc/c/ChangeLog
+++ b/gcc/c/ChangeLog
@@ -1,3 +1,10 @@
+2018-08-20 Martin Uecker <martin.uecker@med.uni-goettingen.de>
+
+ * c-objc-common.h: Define
LANG_HOOKS_CUSTOM_FUNCTION_DESCRIPTORS.
+ * c-typeck.c (function_to_pointer_conversion): If using
descriptors
+ instead of trampolines, amend function address with
+ FUNC_ADDR_BY_DESCRIPTOR and calls with ALL_EXPR_BY_DESCRIPTOR.
+
2018-08-15 David Malcolm <dmalcolm@redhat.com>
* c-objc-common.c: Include "gcc-rich-location.h".
diff --git a/gcc/c/c-objc-common.h b/gcc/c/c-objc-common.h
index 78e768c2366..ef039560eb9 100644
--- a/gcc/c/c-objc-common.h
+++ b/gcc/c/c-objc-common.h
@@ -110,4 +110,7 @@ along with GCC; see the file COPYING3. If not see
#undef LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P
#define LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P c_vla_unspec_p
+
+#undef LANG_HOOKS_CUSTOM_FUNCTION_DESCRIPTORS
+#define LANG_HOOKS_CUSTOM_FUNCTION_DESCRIPTORS true
#endif /* GCC_C_OBJC_COMMON */
diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c
index 726ea832ae1..a6a962d1e01 100644
--- a/gcc/c/c-typeck.c
+++ b/gcc/c/c-typeck.c
@@ -1912,7 +1912,13 @@ function_to_pointer_conversion (location_t loc,
tree exp)
if (TREE_NO_WARNING (orig_exp))
TREE_NO_WARNING (exp) = 1;
- return build_unary_op (loc, ADDR_EXPR, exp, false);
+ tree r = build_unary_op (loc, ADDR_EXPR, exp, false);
+
+ if ((TREE_CODE(r) == ADDR_EXPR)
+ && (flag_trampolines == 0))
+ FUNC_ADDR_BY_DESCRIPTOR (r) = 1;
+
+ return r;
}
/* Mark EXP as read, not just set, for set but not used -Wunused
@@ -3135,6 +3141,11 @@ build_function_call_vec (location_t loc,
vec<location_t> arg_loc,
else
result = build_call_array_loc (loc, TREE_TYPE (fntype),
function, nargs, argarray);
+
+ if ((TREE_CODE (result) == CALL_EXPR)
+ && (flag_trampolines == 0))
+ CALL_EXPR_BY_DESCRIPTOR (result) = 1;
+
/* If -Wnonnull warning has been diagnosed, avoid diagnosing it
again
later. */
if (warned_p && TREE_CODE (result) == CALL_EXPR)
diff --git a/gcc/calls.c b/gcc/calls.c
index 384c0238748..1367e0305a3 100644
--- a/gcc/calls.c
+++ b/gcc/calls.c
@@ -230,7 +230,7 @@ prepare_call_address (tree fndecl_or_type, rtx
funexp, rtx static_chain_value,
{
/* If it's an indirect call by descriptor, generate code to
perform
runtime identification of the pointer and load the
descriptor. */
- if ((flags & ECF_BY_DESCRIPTOR) && !flag_trampolines)
+ if (flags & ECF_BY_DESCRIPTOR)
{
const int bit_val =
targetm.calls.custom_function_descriptors;
rtx call_lab = gen_label_rtx ();
diff --git a/gcc/common.opt b/gcc/common.opt
index ebc3ef43ce2..e56b134ba77 100644
--- a/gcc/common.opt
+++ b/gcc/common.opt
@@ -2479,7 +2479,7 @@ Common Report Var(flag_tracer) Optimization
Perform superblock formation via tail duplication.
ftrampolines
-Common Report Var(flag_trampolines) Init(0)
+Common Report Var(flag_trampolines) Init(-1)
For targets that normally need trampolines for nested functions,
always
generate them instead of using descriptors.
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index e89f4a4c093..8469a57eac3 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,7 @@
+2018-08-20 Martin Uecker <martin.uecker@med.uni-goettingen.de>
+
+ * gcc.dg/trampoline-2.c: New test.
+
2018-08-18 Iain Sandoe <iain@sandoe.co.uk>
* gcc.dg/debug/dwarf2/pr80263.c: Suppress pubtypes output
diff --git a/gcc/testsuite/gcc.dg/trampoline-2.c
b/gcc/testsuite/gcc.dg/trampoline-2.c
new file mode 100644
index 00000000000..7b3a2b64462
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/trampoline-2.c
@@ -0,0 +1,23 @@
+/* test that nested function work without trampolines for -fno-
trampolines */
+/* Origin: Martin Uecker <martin.uecker@med.uni-goettingen.de> */
+/* { dg-do run { target x86_64-*-* } } */
+/* { dg-options "-std=gnu11 -O2 -Wtrampolines -fno-trampolines" } */
+
+static int p(void) { return +1; }
+static int m(void) { return -1; }
+static int z(void) { return 0; }
+
+typedef int (*funptr_t)(void);
+
+static int A(int k, funptr_t a1, funptr_t a2, funptr_t a3, funptr_t
a4, funptr_t a5)
+{
+ int B(void) { return A(--k, B, a1, a2, a3, a4); }
+
+ return (k <= 0) ? (a4() + a5()) : (B());
+}
+
+int main(void)
+{
+ return (0 == A(5, p, m, m, p, z)) ? 0 : 1;
+}
+
diff --git a/gcc/tree-nested.c b/gcc/tree-nested.c
index 4c8eda94f14..4b49024b917 100644
--- a/gcc/tree-nested.c
+++ b/gcc/tree-nested.c
@@ -2497,7 +2497,7 @@ convert_tramp_reference_op (tree *tp, int
*walk_subtrees, void *data)
continue;
/* Decide whether to generate a descriptor or a trampoline. */
- descr = FUNC_ADDR_BY_DESCRIPTOR (t) && !flag_trampolines;
+ descr = FUNC_ADDR_BY_DESCRIPTOR (t);
if (descr)
x = lookup_descr_for_decl (i, decl, INSERT);