This plugs a loophole in the validation of component size aspects/clauses 
specified for array types, by copying what is done for record types.

Tested on x86-64/Linux, applied on the mainline.


2026-02-08  Eric Botcazou  <[email protected]>
            Liam Powell  <[email protected]>

        PR ada/121576
        * freeze.adb (Freeze_Array_Type): When the component size is
        specified, check that it is valid when the component type is
        either a fixed-point type or a bit-packed array type.


2026-02-08  Eric Botcazou  <[email protected]>
            Liam Powell  <[email protected]>

        * gnat.dg/specs/component_size1.ads: New test.

-- 
Eric Botcazou
diff --git a/gcc/ada/freeze.adb b/gcc/ada/freeze.adb
index c1c6bac1fd6..836d84f6534 100644
--- a/gcc/ada/freeze.adb
+++ b/gcc/ada/freeze.adb
@@ -3645,6 +3645,9 @@ package body Freeze is
          Clause : Node_Id;
          --  Set to Component_Size clause or Atomic pragma, if any
 
+         Junk : Boolean;
+         pragma Warnings (Off, Junk);
+
          Non_Standard_Enum : Boolean := False;
          --  Set true if any of the index types is an enumeration type with a
          --  non-standard representation.
@@ -3793,6 +3796,21 @@ package body Freeze is
                   then
                      Complain_CS ("independent", Min => True);
                   end if;
+
+                  --  If the component is of a fixed-point type, we must check
+                  --  the size. This is not done until the freeze point since,
+                  --  for fixed-point types, we do not know the size until the
+                  --  type is frozen. Likewise for a bit-packed array type.
+
+                  if Is_Fixed_Point_Type (Ctyp)
+                    or else Is_Bit_Packed_Array (Ctyp)
+                  then
+                     Clause :=
+                       Get_Attribute_Definition_Clause
+                         (FS, Attribute_Component_Size);
+                     Check_Size
+                       (Expression (Clause), Ctyp, Component_Size (Arr), Junk);
+                  end if;
                end CS_Check;
 
             --  Check for Aliased or Atomic or Full Access or Independent
--  { dg-do compile }
--  { dg-options "-gnatc" }

package Component_Size1 is

  type T1 is delta 2.0**(-8) range 0.0 .. 1.0 - 2.0**(-8);

  type Arr1 is array (Boolean) of T1
    with Component_Size => 1; -- { dg-error "too small" }

  type Rec1 is record
    Comp : T1;
  end record;
  for Rec1 use record
    Comp at 0 range 0 .. 0; -- { dg-error "too small" }
  end record;

  type T2 is array (1 .. 8) of Boolean with Pack => True;

  type Arr2 is array (Boolean) of T2
    with Component_Size => 1; -- { dg-error "too small" }

  type Rec2 is record
    Comp : T2;
  end record;
  for Rec2 use record
    Comp at 0 range 0 .. 0; -- { dg-error "too small" }
  end record;

end Component_Size1;

Reply via email to