summaryrefslogtreecommitdiff
path: root/gcc/ada/atree.adb
diff options
context:
space:
mode:
authorBob Duff <duff@adacore.com>2021-07-29 11:15:46 -0400
committerPierre-Marie de Rodat <derodat@adacore.com>2021-09-23 13:06:14 +0000
commit99e30ba8c01f80a81891223069d47d8a611082c4 (patch)
tree2bfbbf0e257e54ccf041809b15680cfb8b58c83a /gcc/ada/atree.adb
parent7165704bfaae012cb28e5411619218da6fb8320d (diff)
downloadgcc-99e30ba8c01f80a81891223069d47d8a611082c4.tar.gz
[Ada] Cleanup and efficiency improvements
gcc/ada/ * gen_il-gen.adb: Generate getters and setters with much of the code inlined. Generate code for storing a few fields in the node header, to avoid the extra level of indirection for those fields. We generate the header type, so we don't have to duplicate hand-written Ada and C code to depend on the number of header fields. Declare constants for slot size. Use short names because these are used all over. Remove Put_Low_Level_Accessor_Instantiations, Put_Low_Level_C_Getter, which are no longer needed. Rename Put_High_Level_C_Getter-->Put_C_Getter. * atree.ads, atree.adb: Take into account the header slots. Take into account the single Node_Or_Entity_Field type. Remove "pragma Assertion_Policy (Ignore);", because the routines in this package are no longer efficiency critical. * atree.h: Remove low-level getters, which are no longer used by sinfo.h and einfo.h. * einfo-utils.adb: Avoid crash in Known_Alignment. * live.adb, sem_eval.adb: Remove code that prevents Node_Id from having a predicate. We don't actually add a predicate to Node_Id, but we want to be able to for temporary debugging. * sinfo-utils.adb: Remove code that prevents Node_Id from having a predicate. Take into account the single Node_Or_Entity_Field type. * sinfo-utils.ads: Minor. * table.ads (Table_Type): Make the components aliased, because low-level setters in Atree need to take 'Access. * treepr.adb: Take into account the single Node_Or_Entity_Field type. Make some code more robust, so we can print out half-baked nodes. * types.ads: Move types here for visibility purposes. * gcc-interface/gigi.h, gcc-interface/trans.c: Take into account the Node_Header change in the GNAT front end. * gcc-interface/cuintp.c, gcc-interface/targtyps.c: Add because gigi.h now refers to type Node_Header, which is in sinfo.h.
Diffstat (limited to 'gcc/ada/atree.adb')
-rw-r--r--gcc/ada/atree.adb489
1 files changed, 284 insertions, 205 deletions
diff --git a/gcc/ada/atree.adb b/gcc/ada/atree.adb
index d69d4037ebc..00565d66d85 100644
--- a/gcc/ada/atree.adb
+++ b/gcc/ada/atree.adb
@@ -23,20 +23,12 @@
-- --
------------------------------------------------------------------------------
--- Assertions in this package are too slow, and are mostly needed when working
--- on this package itself, or on gen_il, so we disable them.
--- To debug low-level bugs in this area, comment out the following pragma,
--- and run with -gnatd_v.
-
-pragma Assertion_Policy (Ignore);
-
with Aspects; use Aspects;
with Debug; use Debug;
with Namet; use Namet;
with Nlists; use Nlists;
with Opt; use Opt;
with Output; use Output;
-with Seinfo; use Seinfo;
with Sinfo.Utils; use Sinfo.Utils;
with System.Storage_Elements;
@@ -153,7 +145,11 @@ package body Atree is
function Size_In_Slots (N : Node_Or_Entity_Id) return Slot_Count;
-- Number of slots belonging to N. This can be less than
- -- Size_In_Slots_To_Alloc for entities.
+ -- Size_In_Slots_To_Alloc for entities. Includes both header
+ -- and dynamic slots.
+
+ function Size_In_Slots_Dynamic (N : Node_Or_Entity_Id) return Slot_Count;
+ -- Just counts the number of dynamic slots
function Size_In_Slots_To_Alloc (N : Node_Or_Entity_Id) return Slot_Count;
function Size_In_Slots_To_Alloc (Kind : Node_Kind) return Slot_Count;
@@ -161,35 +157,47 @@ package body Atree is
-- to allocate the max, because we don't know the Ekind when this is
-- called.
- function Off_0 (N : Node_Id) return Node_Offset;
- -- Offset of the first slot of N (offset 0) in Slots.Table
+ function Off_F (N : Node_Id) return Node_Offset with Inline;
+ -- Offset of the first dynamic slot of N in Slots.Table.
+ -- The actual offset of this slot from the start of the node
+ -- is not 0; this is logically the first slot after the header
+ -- slots.
+
+ function Off_0 (N : Node_Id) return Node_Offset'Base with Inline;
+ -- This is for zero-origin addressing of the dynamic slots.
+ -- It points to slot 0 of N in Slots.Table, which does not exist,
+ -- because the first few slots are stored in the header.
- function Off_L (N : Node_Id) return Node_Offset;
+ function Off_L (N : Node_Id) return Node_Offset with Inline;
-- Offset of the last slot of N in Slots.Table
- procedure Zero_Slots (First, Last : Node_Offset) with Inline;
- -- Set slots in the range F..L to zero
+ procedure Zero_Dynamic_Slots (First, Last : Node_Offset'Base) with Inline;
+ -- Set dynamic slots in the range First..Last to zero
+
+ procedure Zero_Header_Slots (N : Node_Or_Entity_Id) with Inline;
+ -- Zero the header slots belonging to N
procedure Zero_Slots (N : Node_Or_Entity_Id) with Inline;
- -- Zero the slots belonging to N
+ -- Zero the slots belonging to N (both header and dynamic)
- procedure Copy_Slots (From, To : Node_Offset; Num_Slots : Slot_Count)
+ procedure Copy_Dynamic_Slots
+ (From, To : Node_Offset; Num_Slots : Slot_Count)
with Inline;
-- Copy Num_Slots slots from From to To. Caller is responsible for ensuring
-- that the Num_Slots at To are a reasonable place to copy to.
procedure Copy_Slots (Source, Destination : Node_Id) with Inline;
- -- Copies the slots of Source to Destination; uses the node kind to
- -- determine the Num_Slots.
+ -- Copies the slots (both header and dynamic) of Source to Destination;
+ -- uses the node kind to determine the Num_Slots.
function Get_Field_Value
- (N : Node_Id; Field : Node_Field) return Field_Size_32_Bit;
+ (N : Node_Id; Field : Node_Or_Entity_Field) return Field_Size_32_Bit;
-- Get any field value as a Field_Size_32_Bit. If the field is smaller than
-- 32 bits, convert it to Field_Size_32_Bit. The Field must be present in
-- the Nkind of N.
procedure Set_Field_Value
- (N : Node_Id; Field : Node_Field; Val : Field_Size_32_Bit);
+ (N : Node_Id; Field : Node_Or_Entity_Field; Val : Field_Size_32_Bit);
-- Set any field value as a Field_Size_32_Bit. If the field is smaller than
-- 32 bits, convert it from Field_Size_32_Bit, and Val had better be small
-- enough. The Field must be present in the Nkind of N.
@@ -199,10 +207,6 @@ package body Atree is
-- Called whenever Nkind is modified. Raises an exception if not all
-- vanishing fields are in their initial zero state.
- function Get_Field_Value
- (N : Entity_Id; Field : Entity_Field) return Field_Size_32_Bit;
- procedure Set_Field_Value
- (N : Entity_Id; Field : Entity_Field; Val : Field_Size_32_Bit);
procedure Check_Vanishing_Fields
(Old_N : Entity_Id; New_Kind : Entity_Kind);
-- Above are the same as the ones for nodes, but for entities
@@ -405,7 +409,8 @@ package body Atree is
pragma Assert (N'Valid);
pragma Assert (N <= Node_Offsets.Last);
- pragma Assert (Off_0 (N) <= Off_L (N));
+ pragma Assert (Off_L (N) >= Off_0 (N));
+ pragma Assert (Off_L (N) >= Off_F (N) - 1);
pragma Assert (Off_L (N) <= Slots.Last);
pragma Assert (Nkind (N)'Valid);
pragma Assert (Nkind (N) /= N_Unused_At_End);
@@ -469,8 +474,9 @@ package body Atree is
function Cast is new
Unchecked_Conversion (Field_Size_1_Bit, Field_Type);
+ Val : constant Field_Size_1_Bit := Get_1_Bit_Val (N, Offset);
begin
- return Cast (Get_1_Bit_Val (N, Offset));
+ return Cast (Val);
end Get_1_Bit_Field;
function Get_2_Bit_Field
@@ -480,8 +486,9 @@ package body Atree is
function Cast is new
Unchecked_Conversion (Field_Size_2_Bit, Field_Type);
+ Val : constant Field_Size_2_Bit := Get_2_Bit_Val (N, Offset);
begin
- return Cast (Get_2_Bit_Val (N, Offset));
+ return Cast (Val);
end Get_2_Bit_Field;
function Get_4_Bit_Field
@@ -491,8 +498,9 @@ package body Atree is
function Cast is new
Unchecked_Conversion (Field_Size_4_Bit, Field_Type);
+ Val : constant Field_Size_4_Bit := Get_4_Bit_Val (N, Offset);
begin
- return Cast (Get_4_Bit_Val (N, Offset));
+ return Cast (Val);
end Get_4_Bit_Field;
function Get_8_Bit_Field
@@ -502,8 +510,9 @@ package body Atree is
function Cast is new
Unchecked_Conversion (Field_Size_8_Bit, Field_Type);
+ Val : constant Field_Size_8_Bit := Get_8_Bit_Val (N, Offset);
begin
- return Cast (Get_8_Bit_Val (N, Offset));
+ return Cast (Val);
end Get_8_Bit_Field;
function Get_32_Bit_Field
@@ -514,7 +523,8 @@ package body Atree is
function Cast is new
Unchecked_Conversion (Field_Size_32_Bit, Field_Type);
- Result : constant Field_Type := Cast (Get_32_Bit_Val (N, Offset));
+ Val : constant Field_Size_32_Bit := Get_32_Bit_Val (N, Offset);
+ Result : constant Field_Type := Cast (Val);
-- Note: declaring Result here instead of directly returning
-- Cast (...) helps CodePeer understand that there are no issues
-- around uninitialized variables.
@@ -612,133 +622,214 @@ package body Atree is
Set_32_Bit_Val (N, Offset, Cast (Val));
end Set_32_Bit_Field;
+ pragma Style_Checks ("M90");
+
+ -----------------------------------
+ -- Low-level getters and setters --
+ -----------------------------------
+
+ -- In the getters and setters below, we use shifting and masking to
+ -- simulate packed arrays. F_Size is the field size in bits. Mask is
+ -- that number of 1 bits in the low-order bits. F_Per_Slot is the number
+ -- of fields per slot. Slot_Off is the offset of the slot of interest.
+ -- S is the slot at that offset. V is the amount to shift by.
+
+ function In_NH (Slot_Off : Field_Offset) return Boolean is
+ (Slot_Off < Seinfo.N_Head);
+ -- In_NH stands for "in Node_Header", not "in New Hampshire"
+
+ function Get_Slot
+ (N : Node_Or_Entity_Id; Slot_Off : Field_Offset)
+ return Slot is
+ (if In_NH (Slot_Off) then
+ Node_Offsets.Table (N).Slots (Slot_Off)
+ else Slots.Table (Node_Offsets.Table (N).Offset + Slot_Off));
+ -- Get the slot, either directly from the node header, or indirectly
+ -- from the Slots table.
+
function Get_1_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset) return Field_Size_1_Bit
is
- -- We wish we were using packed arrays, but instead we're simulating
- -- them with modular integers. L here (and elsewhere) is the 'Length
- -- of that simulated array.
- L : constant Field_Offset := Slot_Size / 1;
-
- pragma Debug (Validate_Node_And_Offset (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 1;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ S : constant Slot := Get_Slot (N, Slot_Off);
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset (N, Slot_Off));
+ Raw : constant Field_Size_1_Bit :=
+ Field_Size_1_Bit (Shift_Right (S, V) and Mask);
begin
- return Field_Size_1_Bit (Shift_Right (S, V) and 1);
+ return Raw;
end Get_1_Bit_Val;
function Get_2_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset) return Field_Size_2_Bit
is
- L : constant Field_Offset := Slot_Size / 2;
-
- pragma Debug (Validate_Node_And_Offset (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 2;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ S : constant Slot := Get_Slot (N, Slot_Off);
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset (N, Slot_Off));
+ Raw : constant Field_Size_2_Bit :=
+ Field_Size_2_Bit (Shift_Right (S, V) and Mask);
begin
- return Field_Size_2_Bit (Shift_Right (S, V) and 3);
+ return Raw;
end Get_2_Bit_Val;
function Get_4_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset) return Field_Size_4_Bit
is
- L : constant Field_Offset := Slot_Size / 4;
-
- pragma Debug (Validate_Node_And_Offset (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 4;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ S : constant Slot := Get_Slot (N, Slot_Off);
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset (N, Slot_Off));
+ Raw : constant Field_Size_4_Bit :=
+ Field_Size_4_Bit (Shift_Right (S, V) and Mask);
begin
- return Field_Size_4_Bit (Shift_Right (S, V) and 15);
+ return Raw;
end Get_4_Bit_Val;
function Get_8_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset) return Field_Size_8_Bit
is
- L : constant Field_Offset := Slot_Size / 8;
-
- pragma Debug (Validate_Node_And_Offset (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 8;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ S : constant Slot := Get_Slot (N, Slot_Off);
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset (N, Slot_Off));
+ Raw : constant Field_Size_8_Bit :=
+ Field_Size_8_Bit (Shift_Right (S, V) and Mask);
begin
- return Field_Size_8_Bit (Shift_Right (S, V) and 255);
+ return Raw;
end Get_8_Bit_Val;
function Get_32_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset) return Field_Size_32_Bit
is
- pragma Debug (Validate_Node_And_Offset (N, Offset));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset);
+ F_Size : constant := 32;
+ -- No Mask needed
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ S : constant Slot := Get_Slot (N, Slot_Off);
+ pragma Debug (Validate_Node_And_Offset (N, Slot_Off));
+ Raw : constant Field_Size_32_Bit :=
+ Field_Size_32_Bit (S);
begin
- return Field_Size_32_Bit (S);
+ return Raw;
end Get_32_Bit_Val;
+ type Slot_Ptr is access all Slot;
+ function Get_Slot_Ptr
+ (N : Node_Or_Entity_Id; Slot_Off : Field_Offset)
+ return Slot_Ptr is
+ (if In_NH (Slot_Off) then
+ Node_Offsets.Table (N).Slots (Slot_Off)'Access
+ else Slots.Table (Node_Offsets.Table (N).Offset + Slot_Off)'Access);
+
procedure Set_1_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset; Val : Field_Size_1_Bit)
is
- L : constant Field_Offset := Slot_Size / 1;
-
- pragma Debug (Validate_Node_And_Offset_Write (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 1;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ Ptr : constant Slot_Ptr := Get_Slot_Ptr (N, Slot_Off);
+ S : Slot renames Ptr.all;
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset_Write (N, Slot_Off));
begin
- S := (S and not Shift_Left (1, V)) or Shift_Left (Slot (Val), V);
+ S := (S and not Shift_Left (Mask, V)) or Shift_Left (Slot (Val), V);
end Set_1_Bit_Val;
procedure Set_2_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset; Val : Field_Size_2_Bit)
is
- L : constant Field_Offset := Slot_Size / 2;
-
- pragma Debug (Validate_Node_And_Offset_Write (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 2;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ Ptr : constant Slot_Ptr := Get_Slot_Ptr (N, Slot_Off);
+ S : Slot renames Ptr.all;
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset_Write (N, Slot_Off));
begin
- S := (S and not Shift_Left (3, V)) or Shift_Left (Slot (Val), V);
+ S := (S and not Shift_Left (Mask, V)) or Shift_Left (Slot (Val), V);
end Set_2_Bit_Val;
procedure Set_4_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset; Val : Field_Size_4_Bit)
is
- L : constant Field_Offset := Slot_Size / 4;
-
- pragma Debug (Validate_Node_And_Offset_Write (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 4;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ Ptr : constant Slot_Ptr := Get_Slot_Ptr (N, Slot_Off);
+ S : Slot renames Ptr.all;
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset_Write (N, Slot_Off));
begin
- S := (S and not Shift_Left (15, V)) or Shift_Left (Slot (Val), V);
+ S := (S and not Shift_Left (Mask, V)) or Shift_Left (Slot (Val), V);
end Set_4_Bit_Val;
procedure Set_8_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset; Val : Field_Size_8_Bit)
is
- L : constant Field_Offset := Slot_Size / 8;
-
- pragma Debug (Validate_Node_And_Offset_Write (N, Offset / L));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset / L);
- V : constant Natural := Natural ((Offset mod L) * (Slot_Size / L));
+ F_Size : constant := 8;
+ Mask : constant := 2**F_Size - 1;
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ Ptr : constant Slot_Ptr := Get_Slot_Ptr (N, Slot_Off);
+ S : Slot renames Ptr.all;
+ V : constant Natural := Natural ((Offset mod F_Per_Slot) * F_Size);
+ pragma Debug (Validate_Node_And_Offset_Write (N, Slot_Off));
begin
- S := (S and not Shift_Left (255, V)) or Shift_Left (Slot (Val), V);
+ S := (S and not Shift_Left (Mask, V)) or Shift_Left (Slot (Val), V);
end Set_8_Bit_Val;
procedure Set_32_Bit_Val
(N : Node_Or_Entity_Id; Offset : Field_Offset; Val : Field_Size_32_Bit)
is
- pragma Debug (Validate_Node_And_Offset_Write (N, Offset));
-
- S : Slot renames Slots.Table (Node_Offsets.Table (N) + Offset);
+ F_Size : constant := 32;
+ -- No Mask needed
+ F_Per_Slot : constant Field_Offset := Slot_Size / F_Size;
+ Slot_Off : constant Field_Offset := Offset / F_Per_Slot;
+ Ptr : constant Slot_Ptr := Get_Slot_Ptr (N, Slot_Off);
+ S : Slot renames Ptr.all;
+ pragma Debug (Validate_Node_And_Offset_Write (N, Slot_Off));
begin
S := Slot (Val);
end Set_32_Bit_Val;
+ ----------------------
+ -- Print_Atree_Info --
+ ----------------------
+
+ procedure Print_Atree_Info (N : Node_Or_Entity_Id) is
+ function Cast is new Unchecked_Conversion (Slot, Int);
+ begin
+ Write_Int (Int (Size_In_Slots (N)));
+ Write_Str (" slots (");
+ Write_Int (Int (Off_0 (N)));
+ Write_Str (" .. ");
+ Write_Int (Int (Off_L (N)));
+ Write_Str ("):");
+
+ for Off in Off_0 (N) .. Off_L (N) loop
+ Write_Str (" ");
+ Write_Int (Cast (Get_Slot (N, Off)));
+ end loop;
+
+ Write_Eol;
+ end Print_Atree_Info;
+
end Atree_Private_Part;
---------------
@@ -751,13 +842,12 @@ package body Atree is
-- etc.
function Get_Field_Value
- (N : Node_Id; Field : Node_Field) return Field_Size_32_Bit
+ (N : Node_Id; Field : Node_Or_Entity_Field) return Field_Size_32_Bit
is
- pragma Assert (Field_Checking.Field_Present (Nkind (N), Field));
- Desc : Field_Descriptor renames Node_Field_Descriptors (Field);
+ Desc : Seinfo.Field_Descriptor renames Field_Descriptors (Field);
begin
- case Field_Size (Desc.Kind) is
+ case Seinfo.Field_Size (Desc.Kind) is
when 1 => return Field_Size_32_Bit (Get_1_Bit_Val (N, Desc.Offset));
when 2 => return Field_Size_32_Bit (Get_2_Bit_Val (N, Desc.Offset));
when 4 => return Field_Size_32_Bit (Get_4_Bit_Val (N, Desc.Offset));
@@ -767,13 +857,12 @@ package body Atree is
end Get_Field_Value;
procedure Set_Field_Value
- (N : Node_Id; Field : Node_Field; Val : Field_Size_32_Bit)
+ (N : Node_Id; Field : Node_Or_Entity_Field; Val : Field_Size_32_Bit)
is
- pragma Assert (Field_Checking.Field_Present (Nkind (N), Field));
- Desc : Field_Descriptor renames Node_Field_Descriptors (Field);
+ Desc : Seinfo.Field_Descriptor renames Field_Descriptors (Field);
begin
- case Field_Size (Desc.Kind) is
+ case Seinfo.Field_Size (Desc.Kind) is
when 1 => Set_1_Bit_Val (N, Desc.Offset, Field_Size_1_Bit (Val));
when 2 => Set_2_Bit_Val (N, Desc.Offset, Field_Size_2_Bit (Val));
when 4 => Set_4_Bit_Val (N, Desc.Offset, Field_Size_4_Bit (Val));
@@ -782,13 +871,15 @@ package body Atree is
end case;
end Set_Field_Value;
- procedure Reinit_Field_To_Zero (N : Node_Id; Field : Node_Field) is
+ procedure Reinit_Field_To_Zero
+ (N : Node_Id; Field : Node_Or_Entity_Field)
+ is
begin
Set_Field_Value (N, Field, 0);
end Reinit_Field_To_Zero;
function Field_Is_Initial_Zero
- (N : Node_Id; Field : Node_Field) return Boolean is
+ (N : Node_Id; Field : Node_Or_Entity_Field) return Boolean is
begin
return Get_Field_Value (N, Field) = 0;
end Field_Is_Initial_Zero;
@@ -839,47 +930,6 @@ package body Atree is
end loop;
end Check_Vanishing_Fields;
- function Get_Field_Value
- (N : Entity_Id; Field : Entity_Field) return Field_Size_32_Bit
- is
- pragma Assert (Field_Checking.Field_Present (Ekind (N), Field));
- Desc : Field_Descriptor renames Entity_Field_Descriptors (Field);
- begin
- case Field_Size (Desc.Kind) is
- when 1 => return Field_Size_32_Bit (Get_1_Bit_Val (N, Desc.Offset));
- when 2 => return Field_Size_32_Bit (Get_2_Bit_Val (N, Desc.Offset));
- when 4 => return Field_Size_32_Bit (Get_4_Bit_Val (N, Desc.Offset));
- when 8 => return Field_Size_32_Bit (Get_8_Bit_Val (N, Desc.Offset));
- when others => return Get_32_Bit_Val (N, Desc.Offset); -- 32
- end case;
- end Get_Field_Value;
-
- procedure Set_Field_Value
- (N : Entity_Id; Field : Entity_Field; Val : Field_Size_32_Bit)
- is
- pragma Assert (Field_Checking.Field_Present (Ekind (N), Field));
- Desc : Field_Descriptor renames Entity_Field_Descriptors (Field);
- begin
- case Field_Size (Desc.Kind) is
- when 1 => Set_1_Bit_Val (N, Desc.Offset, Field_Size_1_Bit (Val));
- when 2 => Set_2_Bit_Val (N, Desc.Offset, Field_Size_2_Bit (Val));
- when 4 => Set_4_Bit_Val (N, Desc.Offset, Field_Size_4_Bit (Val));
- when 8 => Set_8_Bit_Val (N, Desc.Offset, Field_Size_8_Bit (Val));
- when others => Set_32_Bit_Val (N, Desc.Offset, Val); -- 32
- end case;
- end Set_Field_Value;
-
- procedure Reinit_Field_To_Zero (N : Node_Id; Field : Entity_Field) is
- begin
- Set_Field_Value (N, Field, 0);
- end Reinit_Field_To_Zero;
-
- function Field_Is_Initial_Zero
- (N : Entity_Id; Field : Entity_Field) return Boolean is
- begin
- return Get_Field_Value (N, Field) = 0;
- end Field_Is_Initial_Zero;
-
procedure Check_Vanishing_Fields
(Old_N : Entity_Id; New_Kind : Entity_Kind)
is
@@ -918,7 +968,7 @@ package body Atree is
end Check_Vanishing_Fields;
Nkind_Offset : constant Field_Offset :=
- Node_Field_Descriptors (F_Nkind).Offset;
+ Field_Descriptors (F_Nkind).Offset;
procedure Set_Node_Kind_Type is new Set_8_Bit_Field (Node_Kind) with Inline;
@@ -943,35 +993,43 @@ package body Atree is
if Old_Size < New_Size then
declare
Old_Last_Slot : constant Node_Offset := Slots.Last;
- Old_Off_0 : constant Node_Offset := Off_0 (N);
+ Old_Off_F : constant Node_Offset := Off_F (N);
begin
- if Old_Last_Slot = Old_Off_0 + Old_Size - 1 then
+ if Old_Last_Slot = Old_Off_F + Old_Size - 1 then
-- In this case, the slots are at the end of Slots.Table, so we
-- don't need to move them.
Slots.Set_Last (Old_Last_Slot + New_Size - Old_Size);
else
-- Move the slots
- All_Node_Offsets (N) := Alloc_Slots (New_Size);
- Copy_Slots (Old_Off_0, Off_0 (N), Old_Size);
- pragma Debug (Zero_Slots (Old_Off_0, Old_Off_0 + Old_Size - 1));
+
+ declare
+ New_Off_F : constant Node_Offset := Alloc_Slots (New_Size);
+ begin
+ All_Node_Offsets (N).Offset := New_Off_F - Seinfo.N_Head;
+ Copy_Dynamic_Slots (Old_Off_F, New_Off_F, Old_Size);
+ pragma Debug
+ (Zero_Dynamic_Slots (Old_Off_F, Old_Off_F + Old_Size - 1));
+ end;
end if;
end;
- Zero_Slots (Off_0 (N) + Old_Size, Slots.Last);
+ Zero_Dynamic_Slots (Off_F (N) + Old_Size, Slots.Last);
end if;
Set_Node_Kind_Type (N, Nkind_Offset, Val);
pragma Debug (Validate_Node_Write (N));
+
+ New_Node_Debugging_Output (N);
end Mutate_Nkind;
procedure Mutate_Nkind (N : Node_Id; Val : Node_Kind) is
begin
- Mutate_Nkind (N, Val, Old_Size => Size_In_Slots (N));
+ Mutate_Nkind (N, Val, Old_Size => Size_In_Slots_Dynamic (N));
end Mutate_Nkind;
Ekind_Offset : constant Field_Offset :=
- Entity_Field_Descriptors (F_Ekind).Offset;
+ Field_Descriptors (F_Ekind).Offset;
procedure Set_Entity_Kind_Type is new Set_8_Bit_Field (Entity_Kind)
with Inline;
@@ -993,6 +1051,8 @@ package body Atree is
Set_Entity_Kind_Type (N, Ekind_Offset, Val);
pragma Debug (Validate_Node_Write (N));
+
+ New_Node_Debugging_Output (N);
end Mutate_Ekind;
-----------------------
@@ -1006,8 +1066,9 @@ package body Atree is
Sz : constant Slot_Count := Size_In_Slots_To_Alloc (Kind);
Sl : constant Node_Offset := Alloc_Slots (Sz);
begin
- Node_Offsets.Table (Result) := Sl;
- Zero_Slots (Sl, Sl + Sz - 1);
+ Node_Offsets.Table (Result).Offset := Sl - Seinfo.N_Head;
+ Zero_Dynamic_Slots (Sl, Sl + Sz - 1);
+ Zero_Header_Slots (Result);
end;
Init_Nkind (Result, Kind);
@@ -1045,7 +1106,7 @@ package body Atree is
pragma Assert (Nkind (N) not in N_Entity);
pragma Assert (New_Kind not in N_Entity);
- Old_Size : constant Slot_Count := Size_In_Slots (N);
+ Old_Size : constant Slot_Count := Size_In_Slots_Dynamic (N);
New_Size : constant Slot_Count := Size_In_Slots_To_Alloc (New_Kind);
Save_Sloc : constant Source_Ptr := Sloc (N);
@@ -1068,15 +1129,16 @@ package body Atree is
New_Offset : constant Field_Offset := Alloc_Slots (New_Size);
begin
pragma Debug (Zero_Slots (N));
- Node_Offsets.Table (N) := New_Offset;
- Zero_Slots (New_Offset, New_Offset + New_Size - 1);
+ Node_Offsets.Table (N).Offset := New_Offset - Seinfo.N_Head;
+ Zero_Dynamic_Slots (New_Offset, New_Offset + New_Size - 1);
+ Zero_Header_Slots (N);
end;
else
Zero_Slots (N);
end if;
- Mutate_Nkind (N, New_Kind, Old_Size);
+ Init_Nkind (N, New_Kind); -- Not Mutate, because of Zero_Slots above
Set_Sloc (N, Save_Sloc);
Set_In_List (N, Save_In_List);
@@ -1095,8 +1157,10 @@ package body Atree is
-- Copy_Slots --
----------------
- procedure Copy_Slots (From, To : Node_Offset; Num_Slots : Slot_Count) is
- pragma Assert (From /= To);
+ procedure Copy_Dynamic_Slots
+ (From, To : Node_Offset; Num_Slots : Slot_Count)
+ is
+ pragma Assert (if Num_Slots /= 0 then From /= To);
All_Slots : Slots.Table_Type renames
Slots.Table (Slots.First .. Slots.Last);
@@ -1109,21 +1173,21 @@ package body Atree is
begin
Destination_Slots := Source_Slots;
- end Copy_Slots;
+ end Copy_Dynamic_Slots;
procedure Copy_Slots (Source, Destination : Node_Id) is
pragma Debug (Validate_Node (Source));
- pragma Debug (Validate_Node_Write (Destination));
pragma Assert (Source /= Destination);
- S_Size : constant Slot_Count := Size_In_Slots (Source);
+ S_Size : constant Slot_Count := Size_In_Slots_Dynamic (Source);
All_Node_Offsets : Node_Offsets.Table_Type renames
Node_Offsets.Table (Node_Offsets.First .. Node_Offsets.Last);
begin
- Copy_Slots
- (All_Node_Offsets (Source), All_Node_Offsets (Destination), S_Size);
+ Copy_Dynamic_Slots
+ (Off_F (Source), Off_F (Destination), S_Size);
+ All_Node_Offsets (Destination).Slots := All_Node_Offsets (Source).Slots;
end Copy_Slots;
---------------
@@ -1152,14 +1216,14 @@ package body Atree is
if D_Size < S_Size then
pragma Debug (Zero_Slots (Destination)); -- destroy old slots
- Node_Offsets.Table (Destination) := Alloc_Slots (S_Size);
+ Node_Offsets.Table (Destination).Offset :=
+ Alloc_Slots (S_Size) - Seinfo.N_Head;
end if;
Copy_Slots (Source, Destination);
Set_In_List (Destination, Save_In_List);
Set_Link (Destination, Save_Link);
-
Set_Paren_Count_Of_Copy (Target => Destination, Source => Source);
end Copy_Node;
@@ -1371,7 +1435,7 @@ package body Atree is
(Is_Entity (E1) and then Is_Entity (E2)
and then not In_List (E1) and then not In_List (E2));
- Old_E1 : constant Node_Offset := Node_Offsets.Table (E1);
+ Old_E1 : constant Seinfo.Node_Header := Node_Offsets.Table (E1);
begin
Node_Offsets.Table (E1) := Node_Offsets.Table (E2);
@@ -1404,6 +1468,7 @@ package body Atree is
pragma Assert (not Is_Entity (Source));
Old_Kind : constant Node_Kind := Nkind (Source);
+ pragma Assert (Old_Kind in N_Direct_Name);
New_Kind : constant Node_Kind :=
(case Old_Kind is
when N_Character_Literal => N_Defining_Character_Literal,
@@ -1469,8 +1534,9 @@ package body Atree is
begin
for J in Fields'Range loop
declare
+ use Seinfo;
Desc : Field_Descriptor renames
- Node_Field_Descriptors (Fields (J));
+ Field_Descriptors (Fields (J));
begin
if Desc.Kind in Node_Id_Field | List_Id_Field then
Fix_Parent (Get_Node_Field_Union (Fix_Node, Desc.Offset));
@@ -1620,7 +1686,8 @@ package body Atree is
end if;
return New_Id : constant Node_Id := Alloc_Node_Id do
- Node_Offsets.Table (New_Id) := Alloc_Slots (S_Size);
+ Node_Offsets.Table (New_Id).Offset :=
+ Alloc_Slots (S_Size) - Seinfo.N_Head;
Orig_Nodes.Append (New_Id);
Copy_Slots (Source, New_Id);
@@ -1676,7 +1743,7 @@ package body Atree is
-- source nodes, then reset Current_Error_Node. This is useful
-- if we bomb during parsing to get a error location for the bomb.
- if New_Sloc > No_Location and then Comes_From_Source_Default then
+ if New_Sloc > No_Location and then Comes_From_Source_Default then
Current_Error_Node := New_Id;
end if;
@@ -1765,16 +1832,25 @@ package body Atree is
-- Off_0 --
-----------
- function Off_0 (N : Node_Id) return Node_Offset is
+ function Off_0 (N : Node_Id) return Node_Offset'Base is
pragma Debug (Validate_Node (N));
All_Node_Offsets : Node_Offsets.Table_Type renames
Node_Offsets.Table (Node_Offsets.First .. Node_Offsets.Last);
begin
- return All_Node_Offsets (N);
+ return All_Node_Offsets (N).Offset;
end Off_0;
-----------
+ -- Off_F --
+ -----------
+
+ function Off_F (N : Node_Id) return Node_Offset is
+ begin
+ return Off_0 (N) + Seinfo.N_Head;
+ end Off_F;
+
+ -----------
-- Off_L --
-----------
@@ -1784,7 +1860,7 @@ package body Atree is
All_Node_Offsets : Node_Offsets.Table_Type renames
Node_Offsets.Table (Node_Offsets.First .. Node_Offsets.Last);
begin
- return All_Node_Offsets (N) + Size_In_Slots (N) - 1;
+ return All_Node_Offsets (N).Offset + Size_In_Slots (N) - 1;
end Off_L;
-------------------
@@ -1855,28 +1931,6 @@ package body Atree is
Set_Comes_From_Source (NewN, Comes_From_Source (OldN));
end Preserve_Comes_From_Source;
- ----------------------
- -- Print_Atree_Info --
- ----------------------
-
- procedure Print_Atree_Info (N : Node_Or_Entity_Id) is
- function Cast is new Unchecked_Conversion (Slot, Int);
- begin
- Write_Int (Int (Size_In_Slots (N)));
- Write_Str (" slots (");
- Write_Int (Int (Off_0 (N)));
- Write_Str (" .. ");
- Write_Int (Int (Off_L (N)));
- Write_Str ("):");
-
- for Off in Off_0 (N) .. Off_L (N) loop
- Write_Str (" ");
- Write_Int (Cast (Slots.Table (Off)));
- end loop;
-
- Write_Eol;
- end Print_Atree_Info;
-
-------------------
-- Relocate_Node --
-------------------
@@ -1926,7 +1980,7 @@ package body Atree is
procedure Destroy_New_Node is
begin
Zero_Slots (New_Node);
- Node_Offsets.Table (New_Node) := Field_Offset'Base'Last;
+ Node_Offsets.Table (New_Node).Offset := Field_Offset'Base'Last;
end Destroy_New_Node;
begin
@@ -2182,11 +2236,15 @@ package body Atree is
Rewriting_Proc := Proc;
end Set_Rewriting_Proc;
+ ----------------------------
+ -- Size_In_Slots_To_Alloc --
+ ----------------------------
+
function Size_In_Slots_To_Alloc (Kind : Node_Kind) return Slot_Count is
begin
return
(if Kind in N_Entity then Einfo.Entities.Max_Entity_Size
- else Sinfo.Nodes.Size (Kind));
+ else Sinfo.Nodes.Size (Kind)) - Seinfo.N_Head;
-- Unfortunately, we don't know the Entity_Kind, so we have to use the
-- max.
end Size_In_Slots_To_Alloc;
@@ -2197,6 +2255,10 @@ package body Atree is
return Size_In_Slots_To_Alloc (Nkind (N));
end Size_In_Slots_To_Alloc;
+ -------------------
+ -- Size_In_Slots --
+ -------------------
+
function Size_In_Slots (N : Node_Or_Entity_Id) return Slot_Count is
begin
pragma Assert (Nkind (N) /= N_Unused_At_Start);
@@ -2205,6 +2267,15 @@ package body Atree is
else Sinfo.Nodes.Size (Nkind (N)));
end Size_In_Slots;
+ ---------------------------
+ -- Size_In_Slots_Dynamic --
+ ---------------------------
+
+ function Size_In_Slots_Dynamic (N : Node_Or_Entity_Id) return Slot_Count is
+ begin
+ return Size_In_Slots (N) - Seinfo.N_Head;
+ end Size_In_Slots_Dynamic;
+
-------------------
-- Traverse_Func --
-------------------
@@ -2372,14 +2443,22 @@ package body Atree is
-- Zero_Slots --
----------------
- procedure Zero_Slots (First, Last : Node_Offset) is
+ procedure Zero_Dynamic_Slots (First, Last : Node_Offset'Base) is
begin
Slots.Table (First .. Last) := (others => 0);
- end Zero_Slots;
+ end Zero_Dynamic_Slots;
+
+ procedure Zero_Header_Slots (N : Node_Or_Entity_Id) is
+ All_Node_Offsets : Node_Offsets.Table_Type renames
+ Node_Offsets.Table (Node_Offsets.First .. Node_Offsets.Last);
+ begin
+ All_Node_Offsets (N).Slots := (others => 0);
+ end Zero_Header_Slots;
procedure Zero_Slots (N : Node_Or_Entity_Id) is
begin
- Zero_Slots (Off_0 (N), Off_L (N));
+ Zero_Dynamic_Slots (Off_F (N), Off_L (N));
+ Zero_Header_Slots (N);
end Zero_Slots;
end Atree;