diff mbox series

[COMMITTED,05/10] ada: Simplify Note_Uplevel_Bound procedure

Message ID 20240903082102.2268026-5-poulhies@adacore.com
State New
Headers show
Series [COMMITTED,01/10] ada: Fix Finalize_Storage_Only bug in b-i-p calls | expand

Commit Message

Marc Poulhiès Sept. 3, 2024, 8:20 a.m. UTC
The procedure Note_Uplevel_Bound was implemented as a custom expression
tree walk. This change replaces this custom tree traversal by a more
idiomatic use of Traverse_Proc.

gcc/ada/

	* exp_unst.adb (Check_Static_Type::Note_Uplevel_Bound): Refactor
	to use the generic Traverse_Proc.
	(Check_Static_Type): Adjust calls to Note_Uplevel_Bound as the
	previous second parameter was unused, so removed.

Tested on x86_64-pc-linux-gnu, committed on master.

---
 gcc/ada/exp_unst.adb | 169 +++++++++++++++++--------------------------
 1 file changed, 66 insertions(+), 103 deletions(-)
diff mbox series

Patch

diff --git a/gcc/ada/exp_unst.adb b/gcc/ada/exp_unst.adb
index 7ff1ea621bb..fb48a64ac86 100644
--- a/gcc/ada/exp_unst.adb
+++ b/gcc/ada/exp_unst.adb
@@ -507,78 +507,90 @@  package body Exp_Unst is
             is
                T : constant Entity_Id := Get_Fullest_View (In_T);
 
-               procedure Note_Uplevel_Bound (N : Node_Id; Ref : Node_Id);
+               procedure Note_Uplevel_Bound (N : Node_Id);
                --  N is the bound of a dynamic type. This procedure notes that
                --  this bound is uplevel referenced, it can handle references
                --  to entities (typically _FIRST and _LAST entities), and also
                --  attribute references of the form T'name (name is typically
                --  FIRST or LAST) where T is the uplevel referenced bound.
-               --  Ref, if Present, is the location of the reference to
-               --  replace.
 
                ------------------------
                -- Note_Uplevel_Bound --
                ------------------------
 
-               procedure Note_Uplevel_Bound (N : Node_Id; Ref : Node_Id) is
-               begin
-                  --  Entity name case. Make sure that the entity is declared
-                  --  in a subprogram. This may not be the case for a type in a
-                  --  loop appearing in a precondition.
-                  --  Exclude explicitly discriminants (that can appear
-                  --  in bounds of discriminated components) and enumeration
-                  --  literals.
-
-                  if Is_Entity_Name (N) then
-                     if Present (Entity (N))
-                       and then not Is_Type (Entity (N))
-                       and then Present (Enclosing_Subprogram (Entity (N)))
-                       and then
-                         Ekind (Entity (N))
-                           not in E_Discriminant | E_Enumeration_Literal
-                     then
-                        Note_Uplevel_Ref
-                          (E      => Entity (N),
-                           N      => Empty,
-                           Caller => Current_Subprogram,
-                           Callee => Enclosing_Subprogram (Entity (N)));
-                     end if;
+               procedure Note_Uplevel_Bound (N : Node_Id) is
 
-                  --  Attribute or indexed component case
+                  function Note_Uplevel_Bound_Trav
+                    (N : Node_Id) return Traverse_Result;
+                  --  Tree visitor that marks entities that are uplevel
+                  --  referenced.
 
-                  elsif Nkind (N) in
-                          N_Attribute_Reference | N_Indexed_Component
-                  then
-                     Note_Uplevel_Bound (Prefix (N), Ref);
+                  procedure Do_Note_Uplevel_Bound
+                    is new Traverse_Proc (Note_Uplevel_Bound_Trav);
+                  --  Subtree visitor instantiation
 
-                     --  The indices of the indexed components, or the
-                     --  associated expressions of an attribute reference,
-                     --  may also involve uplevel references.
+                  -----------------------------
+                  -- Note_Uplevel_Bound_Trav --
+                  -----------------------------
 
-                     declare
-                        Expr : Node_Id;
+                  function Note_Uplevel_Bound_Trav
+                    (N : Node_Id) return Traverse_Result
+                  is
+                  begin
+                     --  Entity name case. Make sure that the entity is
+                     --  declared in a subprogram. This may not be the case for
+                     --  a type in a loop appearing in a precondition. Exclude
+                     --  explicitly discriminants (that can appear in bounds of
+                     --  discriminated components), enumeration literals and
+                     --  block.
+
+                     if Is_Entity_Name (N) then
+                        if Present (Entity (N))
+                          and then not Is_Type (Entity (N))
+                          and then Present
+                            (Enclosing_Subprogram (Entity (N)))
+                          and then
+                            Ekind (Entity (N))
+                              not in E_Discriminant | E_Enumeration_Literal
+                                | E_Block
+                        then
+                           Note_Uplevel_Ref
+                             (E      => Entity (N),
+                              N      => Empty,
+                              Caller => Current_Subprogram,
+                              Callee => Enclosing_Subprogram (Entity (N)));
+                        end if;
+                     end if;
 
-                     begin
-                        Expr := First (Expressions (N));
-                        while Present (Expr) loop
-                           Note_Uplevel_Bound (Expr, Ref);
-                           Next (Expr);
-                        end loop;
-                     end;
+                     --  N_Function_Call are handled later, don't touch them
+                     --  yet.
+                     if Nkind (N) in N_Function_Call
+                     then
+                        return Skip;
+
+                     --  In N_Selected_Component and N_Expanded_Name, only the
+                     --  prefix may be referencing a uplevel entity.
+
+                     elsif Nkind (N) in N_Selected_Component
+                         | N_Expanded_Name
+                     then
+                        Do_Note_Uplevel_Bound (Prefix (N));
+                        return Skip;
 
                      --  The type of the prefix may be have an uplevel
                      --  reference if this needs bounds.
 
-                     if Nkind (N) = N_Attribute_Reference then
+                     elsif Nkind (N) = N_Attribute_Reference then
                         declare
                            Attr : constant Attribute_Id :=
                                     Get_Attribute_Id (Attribute_Name (N));
                            DT   : Boolean := False;
 
                         begin
-                           if (Attr = Attribute_First
-                                 or else Attr = Attribute_Last
-                                 or else Attr = Attribute_Length)
+                           if Attr in
+                                Attribute_First
+                                | Attribute_Last
+                                | Attribute_Length
                              and then Is_Constrained (Etype (Prefix (N)))
                            then
                               Check_Static_Type
@@ -587,59 +599,10 @@  package body Exp_Unst is
                         end;
                      end if;
 
-                  --  Binary operator cases. These can apply to arrays for
-                  --  which we may need bounds.
-
-                  elsif Nkind (N) in N_Binary_Op then
-                     Note_Uplevel_Bound (Left_Opnd (N),  Ref);
-                     Note_Uplevel_Bound (Right_Opnd (N), Ref);
-
-                  --  Unary operator case
-
-                  elsif Nkind (N) in N_Unary_Op then
-                     Note_Uplevel_Bound (Right_Opnd (N), Ref);
-
-                  --  Explicit dereference and selected component case
-
-                  elsif Nkind (N) in
-                          N_Explicit_Dereference | N_Selected_Component
-                  then
-                     Note_Uplevel_Bound (Prefix (N), Ref);
-
-                  --  Conditional expressions
-
-                  elsif Nkind (N) = N_If_Expression then
-                     declare
-                        Expr : Node_Id;
-
-                     begin
-                        Expr := First (Expressions (N));
-                        while Present (Expr) loop
-                           Note_Uplevel_Bound (Expr, Ref);
-                           Next (Expr);
-                        end loop;
-                     end;
-
-                  elsif Nkind (N) = N_Case_Expression then
-                     declare
-                        Alternative : Node_Id;
-
-                     begin
-                        Note_Uplevel_Bound (Expression (N), Ref);
-
-                        Alternative := First (Alternatives (N));
-                        while Present (Alternative) loop
-                           Note_Uplevel_Bound (Expression (Alternative), Ref);
-                        end loop;
-                     end;
-
-                  --  Conversion case
-
-                  elsif Nkind (N) in
-                          N_Type_Conversion | N_Unchecked_Type_Conversion
-                  then
-                     Note_Uplevel_Bound (Expression (N), Ref);
-                  end if;
+                     return OK;
+                  end Note_Uplevel_Bound_Trav;
+               begin
+                  Do_Note_Uplevel_Bound (N);
                end Note_Uplevel_Bound;
 
             --  Start of processing for Check_Static_Type
@@ -673,12 +636,12 @@  package body Exp_Unst is
 
                   begin
                      if not Is_Static_Expression (LB) then
-                        Note_Uplevel_Bound (LB, N);
+                        Note_Uplevel_Bound (LB);
                         DT := True;
                      end if;
 
                      if not Is_Static_Expression (UB) then
-                        Note_Uplevel_Bound (UB, N);
+                        Note_Uplevel_Bound (UB);
                         DT := True;
                      end if;
                   end;
@@ -704,7 +667,7 @@  package body Exp_Unst is
                         D := First_Elmt (Discriminant_Constraint (T));
                         while Present (D) loop
                            if not Is_Static_Expression (Node (D)) then
-                              Note_Uplevel_Bound (Node (D), N);
+                              Note_Uplevel_Bound (Node (D));
                               DT := True;
                            end if;