From: Arnaud Charlet <charlet@adacore.com>
To: gcc-patches@gcc.gnu.org
Cc: Ed Schonberg <schonberg@adacore.com>
Subject: [Ada] Optimization of array aggregates
Date: Thu, 21 Oct 2010 10:24:00 -0000 [thread overview]
Message-ID: <20101021100611.GA18228@adacore.com> (raw)
[-- Attachment #1: Type: text/plain, Size: 795 bytes --]
This patch improves the handling of array aggregates with static components.
It allows constant folding of aggregates with a single association given by
an expanded name, and it allows in-place assignments for aggregates when the
array type has an index type that has a non-standard representation.
Tested on x86_64-pc-linux-gnu, committed on trunk
2010-10-21 Ed Schonberg <schonberg@adacore.com>
* exp_aggr.adb (Flatten): An association for a subtype may be an
expanded name.
(Safe_Left_Hand_Side): An unchecked conversion is part of a safe
left-hand side if the expression is.
(Is_Safe_Index): new predicate
Minor clean up in identier names (Indices -> Indexes).
* exp_ch3.adb (Expand_Freeze_Enumeration_Type): Indicate that the
generated Rep_To_Pos function is a Pure_Function.
[-- Attachment #2: difs --]
[-- Type: text/plain, Size: 9212 bytes --]
Index: exp_aggr.adb
===================================================================
--- exp_aggr.adb (revision 165755)
+++ exp_aggr.adb (working copy)
@@ -227,7 +227,7 @@ package body Exp_Aggr is
Index : Node_Id;
Into : Node_Id;
Scalar_Comp : Boolean;
- Indices : List_Id := No_List;
+ Indexes : List_Id := No_List;
Flist : Node_Id := Empty) return List_Id;
-- This recursive routine returns a list of statements containing the
-- loops and assignments that are needed for the expansion of the array
@@ -244,7 +244,7 @@ package body Exp_Aggr is
--
-- Scalar_Comp is True if the component type of the aggregate is scalar.
--
- -- Indices is the current list of expressions used to index the
+ -- Indexes is the current list of expressions used to index the
-- object we are writing into.
--
-- Flist is an expression representing the finalization list on which
@@ -701,7 +701,7 @@ package body Exp_Aggr is
Index : Node_Id;
Into : Node_Id;
Scalar_Comp : Boolean;
- Indices : List_Id := No_List;
+ Indexes : List_Id := No_List;
Flist : Node_Id := Empty) return List_Id
is
Loc : constant Source_Ptr := Sloc (N);
@@ -728,7 +728,7 @@ package body Exp_Aggr is
-- N to Build_Loop contains no sub-aggregates, then this function
-- returns the assignment statement:
--
- -- Into (Indices, Ind) := Expr;
+ -- Into (Indexes, Ind) := Expr;
--
-- Otherwise we call Build_Code recursively
--
@@ -741,7 +741,7 @@ package body Exp_Aggr is
-- This routine returns the for loop statement
--
-- for J in Index_Base'(L) .. Index_Base'(H) loop
- -- Into (Indices, J) := Expr;
+ -- Into (Indexes, J) := Expr;
-- end loop;
--
-- Otherwise we call Build_Code recursively.
@@ -756,7 +756,7 @@ package body Exp_Aggr is
-- J : Index_Base := L;
-- while J < H loop
-- J := Index_Base'Succ (J);
- -- Into (Indices, J) := Expr;
+ -- Into (Indexes, J) := Expr;
-- end loop;
--
-- Otherwise we call Build_Code recursively
@@ -942,7 +942,7 @@ package body Exp_Aggr is
F : Entity_Id;
A : Node_Id;
- New_Indices : List_Id;
+ New_Indexes : List_Id;
Indexed_Comp : Node_Id;
Expr_Q : Node_Id;
Comp_Type : Entity_Id := Empty;
@@ -982,13 +982,13 @@ package body Exp_Aggr is
-- Start of processing for Gen_Assign
begin
- if No (Indices) then
- New_Indices := New_List;
+ if No (Indexes) then
+ New_Indexes := New_List;
else
- New_Indices := New_Copy_List_Tree (Indices);
+ New_Indexes := New_Copy_List_Tree (Indexes);
end if;
- Append_To (New_Indices, Ind);
+ Append_To (New_Indexes, Ind);
if Present (Flist) then
F := New_Copy_Tree (Flist);
@@ -1014,7 +1014,7 @@ package body Exp_Aggr is
Index => Next_Index (Index),
Into => Into,
Scalar_Comp => Scalar_Comp,
- Indices => New_Indices,
+ Indexes => New_Indexes,
Flist => F));
end if;
@@ -1024,7 +1024,7 @@ package body Exp_Aggr is
Checks_Off
(Make_Indexed_Component (Loc,
Prefix => New_Copy_Tree (Into),
- Expressions => New_Indices));
+ Expressions => New_Indexes));
Set_Assignment_OK (Indexed_Comp);
@@ -1045,7 +1045,7 @@ package body Exp_Aggr is
Comp_Type := Component_Type (Etype (N));
pragma Assert (Comp_Type = Ctype); -- AI-287
- elsif Present (Next (First (New_Indices))) then
+ elsif Present (Next (First (New_Indexes))) then
-- Ada 2005 (AI-287): Do nothing in case of default initialized
-- component because we have received the component type in
@@ -3946,9 +3946,9 @@ package body Exp_Aggr is
exit Component_Loop;
- -- Case of a subtype mark
+ -- Case of a subtype mark, identifier or expanded name
- elsif Nkind (Choice) = N_Identifier
+ elsif Is_Entity_Name (Choice)
and then Is_Type (Entity (Choice))
then
Lo := Type_Low_Bound (Etype (Choice));
@@ -4217,7 +4217,7 @@ package body Exp_Aggr is
Comp : Node_Id;
Decl : Node_Id;
Typ : constant Entity_Id := Etype (N);
- Indices : constant List_Id := New_List;
+ Indexes : constant List_Id := New_List;
Num : Int;
Sub_Agg : Node_Id;
@@ -4239,7 +4239,7 @@ package body Exp_Aggr is
Next (Comp);
end loop;
- Append_To (Indices,
+ Append_To (Indexes,
Make_Range (Loc,
Low_Bound => Make_Integer_Literal (Loc, 1),
High_Bound => Make_Integer_Literal (Loc, Num)));
@@ -4255,7 +4255,7 @@ package body Exp_Aggr is
Make_Range (Loc,
Low_Bound => Aggr_Low (D),
High_Bound => Aggr_High (D)),
- Indices);
+ Indexes);
end loop;
end if;
@@ -4264,10 +4264,10 @@ package body Exp_Aggr is
Defining_Identifier => Agg_Type,
Type_Definition =>
Make_Constrained_Array_Definition (Loc,
- Discrete_Subtype_Definitions => Indices,
- Component_Definition =>
+ Discrete_Subtype_Definitions => Indexes,
+ Component_Definition =>
Make_Component_Definition (Loc,
- Aliased_Present => False,
+ Aliased_Present => False,
Subtype_Indication =>
New_Occurrence_Of (Component_Type (Typ), Loc))));
@@ -4940,6 +4940,41 @@ package body Exp_Aggr is
-------------------------
function Safe_Left_Hand_Side (N : Node_Id) return Boolean is
+ function Is_Safe_Index (Indx : Node_Id) return Boolean;
+ -- If the left-hand side includes an indexed component, check that
+ -- the indexes are free of side-effect.
+
+ -------------------
+ -- Is_Safe_Index --
+ -------------------
+
+ function Is_Safe_Index (Indx : Node_Id) return Boolean is
+ begin
+ if Is_Entity_Name (Indx) then
+ return True;
+
+ elsif Nkind (Indx) = N_Integer_Literal then
+ return True;
+
+ elsif Nkind (Indx) = N_Function_Call
+ and then Is_Entity_Name (Name (Indx))
+ and then
+ Has_Pragma_Pure_Function (Entity (Name (Indx)))
+ then
+ return True;
+
+ elsif Nkind (Indx) = N_Type_Conversion
+ and then Is_Safe_Index (Expression (Indx))
+ then
+ return True;
+
+ else
+ return False;
+ end if;
+ end Is_Safe_Index;
+
+ -- Start of processing for Safe_Left_Hand_Side
+
begin
if Is_Entity_Name (N) then
return True;
@@ -4952,10 +4987,13 @@ package body Exp_Aggr is
elsif Nkind (N) = N_Indexed_Component
and then Safe_Left_Hand_Side (Prefix (N))
and then
- (Is_Entity_Name (First (Expressions (N)))
- or else Nkind (First (Expressions (N))) = N_Integer_Literal)
+ Is_Safe_Index (First (Expressions (N)))
then
return True;
+
+ elsif Nkind (N) = N_Unchecked_Type_Conversion then
+ return Safe_Left_Hand_Side (Expression (N));
+
else
return False;
end if;
@@ -6101,7 +6139,7 @@ package body Exp_Aggr is
Index => First_Index (Typ),
Into => Target,
Scalar_Comp => Is_Scalar_Type (Component_Type (Typ)),
- Indices => No_List,
+ Indexes => No_List,
Flist => Flist);
end if;
end Late_Expansion;
Index: exp_ch3.adb
===================================================================
--- exp_ch3.adb (revision 165755)
+++ exp_ch3.adb (working copy)
@@ -5858,6 +5858,11 @@ package body Exp_Ch3 is
Set_TSS (Typ, Fent);
Set_Is_Pure (Fent);
+ -- The Pure flag will be reset is the current context is not pure.
+ -- For optimization purposes and constant-folding, indicate that the
+ -- Rep_To_Pos function can be considered free of side effects.
+
+ Set_Has_Pragma_Pure_Function (Fent);
if not Debug_Generated_Code then
Set_Debug_Info_Off (Fent);
next reply other threads:[~2010-10-21 10:06 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-10-21 10:24 Arnaud Charlet [this message]
2010-10-21 11:44 ` Duncan Sands
2010-10-21 13:20 ` Robert Dewar
-- strict thread matches above, loose matches on Subject: below --
2010-10-07 13:07 Arnaud Charlet
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20101021100611.GA18228@adacore.com \
--to=charlet@adacore.com \
--cc=gcc-patches@gcc.gnu.org \
--cc=schonberg@adacore.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).