[Ada] Compiler may blow up on array aggregates whose size is very large
The compiler may crash when compiling array aggregates where the computation of the size produces a very large number that overflows (possibly producing a small result), such as with an aggregate of a type that is an array of arrays, where each array range has close to Integer'Last elements. That can lead to Aggr_Size_OK returning incorrectly returning True, following on to allocating a very large array in function Flatten that blows the stack. The size computation was being performed using type Int, so this was changed to use universal arithmetic. 2019-08-13 Gary Dismukes <dismukes@adacore.com> gcc/ada/ * exp_aggr.adb (Aggr_Size_OK): Compute the aggregate size using universal arithmetic, to avoid situations where the size computation overflows. gcc/testsuite/ * gnat.dg/aggr26.adb: New testcase. From-SVN: r274348
This commit is contained in:
parent
6aaab5081f
commit
4167b07523
@ -1,3 +1,9 @@
|
||||
2019-08-13 Gary Dismukes <dismukes@adacore.com>
|
||||
|
||||
* exp_aggr.adb (Aggr_Size_OK): Compute the aggregate size using
|
||||
universal arithmetic, to avoid situations where the size
|
||||
computation overflows.
|
||||
|
||||
2019-08-13 Justin Squirek <squirek@adacore.com>
|
||||
|
||||
* repinfo.adb (List_Scalar_Storage_Order): Modify conditionals
|
||||
|
@ -344,7 +344,7 @@ package body Exp_Aggr is
|
||||
Lo : Node_Id;
|
||||
Hi : Node_Id;
|
||||
Indx : Node_Id;
|
||||
Siz : Int;
|
||||
Size : Uint;
|
||||
Lov : Uint;
|
||||
Hiv : Uint;
|
||||
|
||||
@ -468,7 +468,7 @@ package body Exp_Aggr is
|
||||
Max_Aggr_Size := 5000;
|
||||
end if;
|
||||
|
||||
Siz := Component_Count (Component_Type (Typ));
|
||||
Size := UI_From_Int (Component_Count (Component_Type (Typ)));
|
||||
|
||||
Indx := First_Index (Typ);
|
||||
while Present (Indx) loop
|
||||
@ -538,14 +538,17 @@ package body Exp_Aggr is
|
||||
return False;
|
||||
end if;
|
||||
|
||||
Siz := Siz * UI_To_Int (Rng);
|
||||
end;
|
||||
-- Compute the size using universal arithmetic to avoid the
|
||||
-- possibility of overflow on very large aggregates.
|
||||
|
||||
if Siz <= 0
|
||||
or else Siz > Max_Aggr_Size
|
||||
then
|
||||
return False;
|
||||
end if;
|
||||
Size := Size * Rng;
|
||||
|
||||
if Size <= 0
|
||||
or else Size > Max_Aggr_Size
|
||||
then
|
||||
return False;
|
||||
end if;
|
||||
end;
|
||||
|
||||
-- Bounds must be in integer range, for later array construction
|
||||
|
||||
|
@ -1,3 +1,7 @@
|
||||
2019-08-13 Gary Dismukes <dismukes@adacore.com>
|
||||
|
||||
* gnat.dg/aggr26.adb: New testcase.
|
||||
|
||||
2019-08-13 Yannick Moy <moy@adacore.com>
|
||||
|
||||
* gnat.dg/allocator2.adb, gnat.dg/allocator2.ads: New testcase.
|
||||
|
10
gcc/testsuite/gnat.dg/aggr26.adb
Normal file
10
gcc/testsuite/gnat.dg/aggr26.adb
Normal file
@ -0,0 +1,10 @@
|
||||
-- { dg-do compile }
|
||||
|
||||
procedure Aggr26 is
|
||||
|
||||
type Row is array (Positive) of Integer;
|
||||
H : array (Positive) of Row := (others => (others => 0)); -- { dg-warning "\"Storage_Error\" will be raised at run time" }
|
||||
|
||||
begin
|
||||
null;
|
||||
end Aggr26;
|
Loading…
Reference in New Issue
Block a user