https://gcc.gnu.org/g:cf0a79be059e5ad2d58ca6a30429ec90c4879ead
commit r16-6617-gcf0a79be059e5ad2d58ca6a30429ec90c4879ead Author: Eric Botcazou <[email protected]> Date: Wed Dec 10 21:40:27 2025 +0100 ada: Change 'Size of formal unconstrained discriminated in out parameters When the discriminated type is declared with default discriminants, it is definite, so objects of the type can be declared without constraints, are thus unconstrained, and are allocated with the maximum size by GNAT. When these objects are passed as actuals of formal in out parameters, it makes sense for the 'Size computed for them from within the subprogram to also be the above "unconstrained" size instead of the "constrained" size computed from the value of the discriminants present in them. gcc/ada/ChangeLog: * exp_attr.adb (Expand_Size_Attribute): If the attribute is applied to a formal parameter allocated with an extra Constrained parameter, use the value of the latter to choose between the "unconstrained" or the "constrained" size of the formal parameter. Diff: --- gcc/ada/exp_attr.adb | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/gcc/ada/exp_attr.adb b/gcc/ada/exp_attr.adb index 8816ec6ea8a2..03cb02841fdf 100644 --- a/gcc/ada/exp_attr.adb +++ b/gcc/ada/exp_attr.adb @@ -8960,7 +8960,7 @@ package body Exp_Attr is then Set_Actual_Designated_Subtype (Pref, Get_Actual_Subtype (Pref)); - -- If Size was applied to a slice of a bit-packed array, we rewrite + -- If Size is applied to a slice of a bit-packed array, we rewrite -- it into the product of Length and Component_Size. We need to do so -- because bit-packed arrays are represented internally as arrays of -- System.Unsigned_Types.Packed_Byte for code generation purposes so @@ -8976,6 +8976,27 @@ package body Exp_Attr is Prefix => Duplicate_Subexpr (Pref, Name_Req => True), Attribute_Name => Name_Component_Size))); Analyze_And_Resolve (N, Typ); + + -- If Size is applied to a formal parameter that has got a dynamic + -- indication of its constrained status, return the "constrained" + -- size if the status is True, that is to say the size based on the + -- constraints of the actual, and the "unconstrained" size if the + -- status is False, that is to say the Object_Size of the type. + + elsif Is_Entity_Name (Pref) + and then Is_Formal (Entity (Pref)) + and then Present (Extra_Constrained (Entity (Pref))) + then + Rewrite (N, + Make_If_Expression (Loc, + Expressions => New_List ( + New_Occurrence_Of (Extra_Constrained (Entity (Pref)), Loc), + Relocate_Node (N), + Make_Attribute_Reference (Loc, + Prefix => New_Occurrence_Of (Etype (Pref), Loc), + Attribute_Name => Name_Object_Size)))); + Set_Analyzed (Next (First (Expressions (N)))); + Analyze_And_Resolve (N, Typ); end if; -- Apply the required checks last, after rewriting has taken place
