summaryrefslogtreecommitdiffstats
path: root/gcc/ada
diff options
context:
space:
mode:
authorcharlet <charlet@138bc75d-0d04-0410-961f-82ee72b054a4>2008-05-20 12:44:43 +0000
committercharlet <charlet@138bc75d-0d04-0410-961f-82ee72b054a4>2008-05-20 12:44:43 +0000
commit497260ff15267fd4331606ecc1c25649031748f3 (patch)
tree8e2cbf2aa50782a9ae8bbcfee5b13e1a490c22ba /gcc/ada
parent3caa76d900d49af0aefed83f9522e60668b8b59b (diff)
downloadppe42-gcc-497260ff15267fd4331606ecc1c25649031748f3.tar.gz
ppe42-gcc-497260ff15267fd4331606ecc1c25649031748f3.zip
2008-05-20 Tristan Gingold <gingold@adacore.com>
* decl.c: Do not emit a variable for a object that has an address representation clause whose value is known at compile time. When a variable has an address clause whose value is known at compile time, refer to this variable by using directly the address instead of dereferencing a pointer. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@135618 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/ada')
-rw-r--r--gcc/ada/decl.c39
1 files changed, 36 insertions, 3 deletions
diff --git a/gcc/ada/decl.c b/gcc/ada/decl.c
index 8565305c2d5..8f29ca77dfc 100644
--- a/gcc/ada/decl.c
+++ b/gcc/ada/decl.c
@@ -122,6 +122,17 @@ static void check_ok_for_atomic (tree, Entity_Id, bool);
static int compatible_signatures_p (tree ftype1, tree ftype2);
static void rest_of_type_decl_compilation_no_defer (tree);
+/* Return true if GNAT_ADDRESS is a compile time known value.
+ In particular catch System'To_Address. */
+
+static bool
+compile_time_known_address_p (Node_Id gnat_address)
+{
+ return ((Nkind (gnat_address) == N_Unchecked_Type_Conversion
+ && Compile_Time_Known_Value (Expression (gnat_address)))
+ || Compile_Time_Known_Value (gnat_address));
+}
+
/* Given GNAT_ENTITY, an entity in the incoming GNAT tree, return a
GCC type corresponding to that entity. GNAT_ENTITY is assumed to
refer to an Ada type. */
@@ -1026,7 +1037,9 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition)
= build_reference_type_for_mode (gnu_type, ptr_mode, true);
gnu_address = convert (gnu_type, gnu_address);
used_by_ref = true;
- const_flag = !Is_Public (gnat_entity);
+ const_flag = !Is_Public (gnat_entity)
+ || compile_time_known_address_p (Expression (Address_Clause
+ (gnat_entity)));
/* If we don't have an initializing expression for the underlying
variable, the initializing expression for the pointer is the
@@ -1058,9 +1071,24 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition)
= build_reference_type_for_mode (gnu_type, ptr_mode, true);
gnu_size = NULL_TREE;
- gnu_expr = NULL_TREE;
/* No point in taking the address of an initializing expression
that isn't going to be used. */
+ gnu_expr = NULL_TREE;
+
+ /* If it has an address clause whose value is known at compile
+ time, make the object a CONST_DECL. This will avoid a
+ useless dereference. */
+ if (Present (Address_Clause (gnat_entity)))
+ {
+ Node_Id gnat_address
+ = Expression (Address_Clause (gnat_entity));
+
+ if (compile_time_known_address_p (gnat_address))
+ {
+ gnu_expr = gnat_to_gnu (gnat_address);
+ const_flag = true;
+ }
+ }
used_by_ref = true;
}
@@ -1258,7 +1286,8 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition)
for these. */
if (TREE_CODE (gnu_decl) == CONST_DECL
&& (definition || Sloc (gnat_entity) > Standard_Location)
- && (Is_Public (gnat_entity)
+ && ((Is_Public (gnat_entity)
+ && !Present (Address_Clause (gnat_entity)))
|| optimize == 0
|| Address_Taken (gnat_entity)
|| Is_Aliased (gnat_entity)
@@ -1271,6 +1300,10 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition)
gnat_entity);
SET_DECL_CONST_CORRESPONDING_VAR (gnu_decl, gnu_corr_var);
+
+ /* As debugging information will be generated for the variable,
+ do not generate information for the constant. */
+ DECL_IGNORED_P (gnu_decl) = true;
}
/* If this is declared in a block that contains a block with an
OpenPOWER on IntegriCloud