summaryrefslogtreecommitdiff
path: root/gcc/ada
diff options
context:
space:
mode:
authorOlivier Hainque <hainque@adacore.com>2011-01-04 09:30:06 +0000
committerEric Botcazou <ebotcazou@gcc.gnu.org>2011-01-04 09:30:06 +0000
commit2a02d0907c0b500018ba900e93239e1b03281c67 (patch)
treefe02110a5e9b80b984e5374d408f68b56fd163ec /gcc/ada
parent89f5e978044c3086e99418ea6855bd1faacba2a0 (diff)
downloadgcc-2a02d0907c0b500018ba900e93239e1b03281c67.tar.gz
trans.c (BLOCK_SOURCE_END_LOCATION): Provide default.
* gcc-interface/trans.c (BLOCK_SOURCE_END_LOCATION): Provide default. (set_end_locus_from_node): New function. (Subprogram_Body_to_gnu): Use it to mark both the inner BIND_EXPR we make and the function end_locus. (Compilation_Unit_to_gnu): Call it instead of a straight Sloc_to_locus for the elaboration subprogram. (set_gnu_expr_location_from_node) <default case>: Use it to attempt to set the end_locus of the expression as well. Co-Authored-By: Eric Botcazou <ebotcazou@adacore.com> From-SVN: r168455
Diffstat (limited to 'gcc/ada')
-rw-r--r--gcc/ada/ChangeLog12
-rw-r--r--gcc/ada/gcc-interface/trans.c85
2 files changed, 86 insertions, 11 deletions
diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog
index 8920d8e8e52..57d9c58b28f 100644
--- a/gcc/ada/ChangeLog
+++ b/gcc/ada/ChangeLog
@@ -1,3 +1,15 @@
+2011-01-04 Olivier Hainque <hainque@adacore.com>
+ Eric Botcazou <ebotcazou@adacore.com>
+
+ * gcc-interface/trans.c (BLOCK_SOURCE_END_LOCATION): Provide default.
+ (set_end_locus_from_node): New function.
+ (Subprogram_Body_to_gnu): Use it to mark both the inner BIND_EXPR we
+ make and the function end_locus.
+ (Compilation_Unit_to_gnu): Call it instead of a straight Sloc_to_locus
+ for the elaboration subprogram.
+ (set_gnu_expr_location_from_node) <default case>: Use it to attempt to
+ set the end_locus of the expression as well.
+
2011-01-04 Eric Botcazou <ebotcazou@adacore.com>
PR ada/47131
diff --git a/gcc/ada/gcc-interface/trans.c b/gcc/ada/gcc-interface/trans.c
index 673c4f833cf..9bf7c3d77b7 100644
--- a/gcc/ada/gcc-interface/trans.c
+++ b/gcc/ada/gcc-interface/trans.c
@@ -64,6 +64,13 @@
#define TARGET_ABI_OPEN_VMS 0
#endif
+/* In configurations where blocks have no end_locus attached, just
+ sink assignments into a dummy global. */
+#ifndef BLOCK_SOURCE_END_LOCATION
+static location_t block_end_locus_sink;
+#define BLOCK_SOURCE_END_LOCATION(BLOCK) block_end_locus_sink
+#endif
+
/* For efficient float-to-int rounding, it is necessary to know whether
floating-point arithmetic may use wider intermediate results. When
FP_ARITH_MAY_WIDEN is not defined, be conservative and only assume
@@ -205,6 +212,7 @@ static tree extract_values (tree, tree);
static tree pos_to_constructor (Node_Id, tree, Entity_Id);
static tree maybe_implicit_deref (tree);
static void set_expr_location_from_node (tree, Node_Id);
+static bool set_end_locus_from_node (tree, Node_Id);
static void set_gnu_expr_location_from_node (tree, Node_Id);
static int lvalue_required_p (Node_Id, tree, bool, bool, bool);
static tree build_raise_check (int, tree, enum exception_info_kind);
@@ -2654,15 +2662,14 @@ Subprogram_Body_to_gnu (Node_Id gnat_node)
gnu_result = end_stmt_group ();
}
- /* Set the end location. */
- Sloc_to_locus
- ((Present (End_Label (Handled_Statement_Sequence (gnat_node)))
- ? Sloc (End_Label (Handled_Statement_Sequence (gnat_node)))
- : Sloc (gnat_node)),
- &DECL_STRUCT_FUNCTION (gnu_subprog_decl)->function_end_locus);
-
end_subprog_body (gnu_result);
+ /* Attempt setting the end_locus of our GCC body tree, typically a
+ BIND_EXPR or STATEMENT_LIST, then the end_locus of our GCC subprogram
+ declaration tree. */
+ set_end_locus_from_node (gnu_result, gnat_node);
+ set_end_locus_from_node (gnu_subprog_decl, gnat_node);
+
/* Finally annotate the parameters and disconnect the trees for parameters
that we have turned into variables since they are now unusable. */
for (gnat_param = First_Formal_With_Extras (gnat_subprog_id);
@@ -3797,9 +3804,7 @@ Compilation_Unit_to_gnu (Node_Id gnat_node)
gnat_poplevel ();
DECL_SAVED_TREE (gnu_elab_proc_decl) = end_stmt_group ();
- Sloc_to_locus
- (Sloc (gnat_unit),
- &DECL_STRUCT_FUNCTION (gnu_elab_proc_decl)->function_end_locus);
+ set_end_locus_from_node (gnu_elab_proc_decl, gnat_unit);
info->next = elab_info_list;
info->elab_proc = gnu_elab_proc_decl;
@@ -7741,7 +7746,10 @@ set_gnu_expr_location_from_node (tree node, Node_Id gnat_node)
default:
if (!REFERENCE_CLASS_P (node) && !EXPR_HAS_LOCATION (node))
- set_expr_location_from_node (node, gnat_node);
+ {
+ set_expr_location_from_node (node, gnat_node);
+ set_end_locus_from_node (node, gnat_node);
+ }
break;
}
}
@@ -7806,6 +7814,61 @@ post_error_ne_num (const char *msg, Node_Id node, Entity_Id ent, int num)
Error_Msg_Uint_1 = UI_From_Int (num);
post_error_ne (msg, node, ent);
}
+
+/* Set the end_locus information for GNU_NODE, if any, from an explicit end
+ location associated with GNAT_NODE or GNAT_NODE itself, whichever makes
+ most sense. Return true if a sensible assignment was performed. */
+
+static bool
+set_end_locus_from_node (tree gnu_node, Node_Id gnat_node)
+{
+ Node_Id gnat_end_label = Empty;
+ location_t end_locus;
+
+ /* Pick the GNAT node of which we'll take the sloc to assign to the GCC node
+ end_locus when there is one. We consider only GNAT nodes with a possible
+ End_Label attached. If the End_Label actually was unassigned, fallback
+ on the orginal node. We'd better assign an explicit sloc associated with
+ the outer construct in any case. */
+
+ switch (Nkind (gnat_node))
+ {
+ case N_Package_Body:
+ case N_Subprogram_Body:
+ case N_Block_Statement:
+ gnat_end_label = End_Label (Handled_Statement_Sequence (gnat_node));
+ break;
+
+ case N_Package_Declaration:
+ gnat_end_label = End_Label (Specification (gnat_node));
+ break;
+
+ default:
+ return false;
+ }
+
+ gnat_node = Present (gnat_end_label) ? gnat_end_label : gnat_node;
+
+ /* Some expanded subprograms have neither an End_Label nor a Sloc
+ attached. Notify that to callers. */
+
+ if (!Sloc_to_locus (Sloc (gnat_node), &end_locus))
+ return false;
+
+ switch (TREE_CODE (gnu_node))
+ {
+ case BIND_EXPR:
+ BLOCK_SOURCE_END_LOCATION (BIND_EXPR_BLOCK (gnu_node)) = end_locus;
+ return true;
+
+ case FUNCTION_DECL:
+ DECL_STRUCT_FUNCTION (gnu_node)->function_end_locus = end_locus;
+ return true;
+
+ default:
+ return false;
+ }
+}
/* Similar to post_error_ne, but T is a GCC tree representing the number to
write. If T represents a constant, the text inside curly brackets in