summaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ada/exp_ch4.adb105
1 files changed, 50 insertions, 55 deletions
diff --git a/gcc/ada/exp_ch4.adb b/gcc/ada/exp_ch4.adb
index 978225e4b94..fa76b9630ca 100644
--- a/gcc/ada/exp_ch4.adb
+++ b/gcc/ada/exp_ch4.adb
@@ -2936,9 +2936,10 @@ package body Exp_Ch4 is
-- and their unrestricted access used instead of the coextension.
function Size_In_Storage_Elements (E : Entity_Id) return Node_Id;
- -- Given a type E, returns a node representing the code to compute the
- -- size in storage elements for the given type. This is not as trivial
- -- as one might expect, as explained in the body.
+ -- Given a constrained array type E, returns a node representing the
+ -- code to compute the size in storage elements for the given type.
+ -- This is done without using the attribute (which malfunctins for
+ -- large sizes ???)
---------------------------------------
-- Complete_Coextension_Finalization --
@@ -3180,10 +3181,7 @@ package body Exp_Ch4 is
-- 32-bit limit on a 32-bit machine, and precisely the trouble
-- is that we get overflows when sizes are greater than 2**31.
- -- So what we end up doing is using this expression for non-array
- -- types, where it is not quite right, but should be good enough
- -- most of the time. But for non-packed arrays, instead we compute
- -- the expression:
+ -- So what we end up doing for array types is to use the expression:
-- number-of-elements * component_type'Max_Size_In_Storage_Elements
@@ -3192,48 +3190,38 @@ package body Exp_Ch4 is
-- are too large, and which in the absence of a check results in
-- undetected chaos ???
- if Is_Array_Type (E) and then Is_Constrained (E) then
- declare
- Len : Node_Id;
- Res : Node_Id;
-
- begin
- for J in 1 .. Number_Dimensions (E) loop
- Len :=
- Make_Attribute_Reference (Loc,
- Prefix => New_Occurrence_Of (E, Loc),
- Attribute_Name => Name_Length,
- Expressions => New_List (
- Make_Integer_Literal (Loc, J)));
-
- if J = 1 then
- Res := Len;
+ declare
+ Len : Node_Id;
+ Res : Node_Id;
- else
- Res :=
- Make_Op_Multiply (Loc,
- Left_Opnd => Res,
- Right_Opnd => Len);
- end if;
- end loop;
+ begin
+ for J in 1 .. Number_Dimensions (E) loop
+ Len :=
+ Make_Attribute_Reference (Loc,
+ Prefix => New_Occurrence_Of (E, Loc),
+ Attribute_Name => Name_Length,
+ Expressions => New_List (
+ Make_Integer_Literal (Loc, J)));
- return
- Make_Op_Multiply (Loc,
- Left_Opnd => Len,
- Right_Opnd =>
- Make_Attribute_Reference (Loc,
- Prefix => New_Occurrence_Of (Component_Type (E), Loc),
- Attribute_Name => Name_Max_Size_In_Storage_Elements));
- end;
+ if J = 1 then
+ Res := Len;
- -- Here for other than non-bit-packed array
+ else
+ Res :=
+ Make_Op_Multiply (Loc,
+ Left_Opnd => Res,
+ Right_Opnd => Len);
+ end if;
+ end loop;
- else
return
- Make_Attribute_Reference (Loc,
- Prefix => New_Occurrence_Of (E, Loc),
- Attribute_Name => Name_Max_Size_In_Storage_Elements);
- end if;
+ Make_Op_Multiply (Loc,
+ Left_Opnd => Len,
+ Right_Opnd =>
+ Make_Attribute_Reference (Loc,
+ Prefix => New_Occurrence_Of (Component_Type (E), Loc),
+ Attribute_Name => Name_Max_Size_In_Storage_Elements));
+ end;
end Size_In_Storage_Elements;
-- Start of processing for Expand_N_Allocator
@@ -3363,18 +3351,25 @@ package body Exp_Ch4 is
-- raise Storage_Error;
-- end if;
- -- where 3.5 gigabytes is a constant large enough to accomodate
- -- any reasonable request for
+ -- where 3.5 gigabytes is a constant large enough to accomodate any
+ -- reasonable request for. But we can't do it this way because at
+ -- least at the moment we don't compute this attribute right, and
+ -- can silently give wrong results when the result gets large. Since
+ -- this is all about large results, that's bad, so instead we only
+ -- applly the check for constrained arrays, and manually compute the
+ -- value of the attribute ???
- Insert_Action (N,
- Make_Raise_Storage_Error (Loc,
- Condition =>
- Make_Op_Gt (Loc,
- Left_Opnd => Size_In_Storage_Elements (Etyp),
- Right_Opnd =>
- Make_Integer_Literal (Loc,
- Intval => Uint_7 * (Uint_2 ** 29))),
- Reason => SE_Object_Too_Large));
+ if Is_Array_Type (Etyp) and then Is_Constrained (Etyp) then
+ Insert_Action (N,
+ Make_Raise_Storage_Error (Loc,
+ Condition =>
+ Make_Op_Gt (Loc,
+ Left_Opnd => Size_In_Storage_Elements (Etyp),
+ Right_Opnd =>
+ Make_Integer_Literal (Loc,
+ Intval => Uint_7 * (Uint_2 ** 29))),
+ Reason => SE_Object_Too_Large));
+ end if;
end if;
-- Handle case of qualified expression (other than optimization above)