From 0c09a01e9ea0608df0ae6754f67d630c1e40bb04 Mon Sep 17 00:00:00 2001 From: Eric Botcazou Date: Mon, 15 May 2017 08:27:44 +0000 Subject: [PATCH] trans.c (Compilation_Unit_to_gnu): Skip subprograms on the inlined list that are not public. * gcc-interface/trans.c (Compilation_Unit_to_gnu): Skip subprograms on the inlined list that are not public. * gcc-interface/utils.c (create_subprog_decl): Clear TREE_PUBLIC if there is a pragma Inline_Always on the subprogram. From-SVN: r248051 --- gcc/ada/ChangeLog | 7 +++++++ gcc/ada/gcc-interface/trans.c | 9 +++++++++ gcc/ada/gcc-interface/utils.c | 17 +++++++++++++---- 3 files changed, 29 insertions(+), 4 deletions(-) diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog index 29d49d96164..8fa7ab7821f 100644 --- a/gcc/ada/ChangeLog +++ b/gcc/ada/ChangeLog @@ -1,3 +1,10 @@ +2017-05-15 Eric Botcazou + + * gcc-interface/trans.c (Compilation_Unit_to_gnu): Skip subprograms on + the inlined list that are not public. + * gcc-interface/utils.c (create_subprog_decl): Clear TREE_PUBLIC if + there is a pragma Inline_Always on the subprogram. + 2017-05-15 Eric Botcazou * gcc-interface/trans.c (gnat_to_gnu) : Fix formatting. diff --git a/gcc/ada/gcc-interface/trans.c b/gcc/ada/gcc-interface/trans.c index ef0db27c8ca..117ce261b62 100644 --- a/gcc/ada/gcc-interface/trans.c +++ b/gcc/ada/gcc-interface/trans.c @@ -5472,6 +5472,15 @@ Compilation_Unit_to_gnu (Node_Id gnat_node) if (!optimize && !Has_Pragma_Inline_Always (gnat_entity)) continue; + /* The set of inlined subprograms is computed from data recorded early + during expansion and it can be a strict superset of the final set + computed after semantic analysis, for example if a call to such a + subprogram occurs in a pragma Assert and assertions are disabled. + In that case, semantic analysis resets Is_Public to false but the + entry for the subprogram in the inlining tables is stalled. */ + if (!Is_Public (gnat_entity)) + continue; + gnat_body = Parent (Declaration_Node (gnat_entity)); if (Nkind (gnat_body) != N_Subprogram_Body) { diff --git a/gcc/ada/gcc-interface/utils.c b/gcc/ada/gcc-interface/utils.c index 4fabddfe5e1..345b8a4f163 100644 --- a/gcc/ada/gcc-interface/utils.c +++ b/gcc/ada/gcc-interface/utils.c @@ -3220,10 +3220,19 @@ create_subprog_decl (tree name, tree asm_name, tree type, tree param_decl_list, case is_required: if (Back_End_Inlining) - decl_attributes (&subprog_decl, - tree_cons (get_identifier ("always_inline"), - NULL_TREE, NULL_TREE), - ATTR_FLAG_TYPE_IN_PLACE); + { + decl_attributes (&subprog_decl, + tree_cons (get_identifier ("always_inline"), + NULL_TREE, NULL_TREE), + ATTR_FLAG_TYPE_IN_PLACE); + + /* Inline_Always guarantees that every direct call is inlined and + that there is no indirect reference to the subprogram, so the + instance in the original package (as well as its clones in the + client packages created for inter-unit inlining) can be made + private, which causes the out-of-line body to be eliminated. */ + TREE_PUBLIC (subprog_decl) = 0; + } /* ... fall through ... */