This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Ada] Extend -gnatw.z warning to array types


The -gnatw.z switch causes the compiler to issue a warning on record
types subject to both an alignment clause and a size clause, when the
specified size is not a multiple of the alignment in bits, because this
means that the Object_Size will be strictly larger than the specified
size.

It makes sense to extend this warning to array types, but not to the
cases of bit-packed arrays where the size is not a multiple of storage
unit and the specified alignment is the minimum one, because there would
be no way to get rid of it apart from explicitly silencing it.

The compiler must issue the warning:

p.ads:5:03: warning: size is not a multiple of alignment for "Triplet"
p.ads:5:03: warning: size of 24 specified at line 4
p.ads:5:03: warning: Object_Size will be increased to 32

on the following package:

package P is

  type Triplet is new String (1 .. 3);
  for Triplet'Size use 24;
  for Triplet'Alignment use 4;

  type Arr is array (1 .. 7) of Boolean;
  pragma Pack (Arr);
  for Arr'Size use 7;
  for Arr'Alignment use 1;

end P;

Tested on x86_64-pc-linux-gnu, committed on trunk

2019-07-03  Eric Botcazou  <ebotcazou@adacore.com>

gcc/ada/

	* doc/gnat_ugn/building_executable_programs_with_gnat.rst
	(Warning message control): Document that -gnatw.z/Z apply to
	array types.
	* freeze.adb (Freeze_Entity): Give -gnatw.z warning for array
	types as well, but not if the specified alignment is the minimum
	one.
	* gnat_ugn.texi: Regenerate.
--- gcc/ada/doc/gnat_ugn/building_executable_programs_with_gnat.rst
+++ gcc/ada/doc/gnat_ugn/building_executable_programs_with_gnat.rst
@@ -4045,8 +4045,8 @@ of the pragma in the :title:`GNAT_Reference_manual`).
 :switch:`-gnatw.z`
   *Activate warnings for size not a multiple of alignment.*
 
-  This switch activates warnings for cases of record types with
-  specified ``Size`` and ``Alignment`` attributes where the
+  This switch activates warnings for cases of array and record types
+  with specified ``Size`` and ``Alignment`` attributes where the
   size is not a multiple of the alignment, resulting in an object
   size that is greater than the specified size. The default
   is that such warnings are generated.
@@ -4058,12 +4058,11 @@ of the pragma in the :title:`GNAT_Reference_manual`).
 :switch:`-gnatw.Z`
   *Suppress warnings for size not a multiple of alignment.*
 
-  This switch suppresses warnings for cases of record types with
-  specified ``Size`` and ``Alignment`` attributes where the
+  This switch suppresses warnings for cases of array and record types
+  with specified ``Size`` and ``Alignment`` attributes where the
   size is not a multiple of the alignment, resulting in an object
-  size that is greater than the specified size.
-  The warning can also be
-  suppressed by giving an explicit ``Object_Size`` value.
+  size that is greater than the specified size. The warning can also
+  be suppressed by giving an explicit ``Object_Size`` value.
 
 
 .. index:: -Wunused (gcc)

--- gcc/ada/freeze.adb
+++ gcc/ada/freeze.adb
@@ -5943,17 +5943,29 @@ package body Freeze is
             Inherit_Aspects_At_Freeze_Point (E);
          end if;
 
-         --  Check for incompatible size and alignment for record type
+         --  Case of array type
+
+         if Is_Array_Type (E) then
+            Freeze_Array_Type (E);
+         end if;
+
+         --  Check for incompatible size and alignment for array/record type
 
          if Warn_On_Size_Alignment
-           and then Is_Record_Type (E)
-           and then Has_Size_Clause (E) and then Has_Alignment_Clause (E)
+           and then (Is_Array_Type (E) or else Is_Record_Type (E))
+           and then Has_Size_Clause (E)
+           and then Has_Alignment_Clause (E)
 
            --  If explicit Object_Size clause given assume that the programmer
            --  knows what he is doing, and expects the compiler behavior.
 
            and then not Has_Object_Size_Clause (E)
 
+           --  It does not really make sense to warn for the minimum alignment
+           --  since the programmer could not get rid of the warning.
+
+           and then Alignment (E) > 1
+
            --  Check for size not a multiple of alignment
 
            and then RM_Size (E) mod (Alignment (E) * System_Storage_Unit) /= 0
@@ -5994,15 +6006,10 @@ package body Freeze is
             end;
          end if;
 
-         --  Array type
-
-         if Is_Array_Type (E) then
-            Freeze_Array_Type (E);
-
          --  For a class-wide type, the corresponding specific type is
          --  frozen as well (RM 13.14(15))
 
-         elsif Is_Class_Wide_Type (E) then
+         if Is_Class_Wide_Type (E) then
             Freeze_And_Append (Root_Type (E), N, Result);
 
             --  If the base type of the class-wide type is still incomplete,

--- gcc/ada/gnat_ugn.texi
+++ gcc/ada/gnat_ugn.texi
@@ -12683,8 +12683,8 @@ sizes or conventions.
 
 @emph{Activate warnings for size not a multiple of alignment.}
 
-This switch activates warnings for cases of record types with
-specified @code{Size} and @code{Alignment} attributes where the
+This switch activates warnings for cases of array and record types
+with specified @code{Size} and @code{Alignment} attributes where the
 size is not a multiple of the alignment, resulting in an object
 size that is greater than the specified size. The default
 is that such warnings are generated.
@@ -12701,12 +12701,11 @@ is that such warnings are generated.
 
 @emph{Suppress warnings for size not a multiple of alignment.}
 
-This switch suppresses warnings for cases of record types with
-specified @code{Size} and @code{Alignment} attributes where the
+This switch suppresses warnings for cases of array and record types
+with specified @code{Size} and @code{Alignment} attributes where the
 size is not a multiple of the alignment, resulting in an object
-size that is greater than the specified size.
-The warning can also be
-suppressed by giving an explicit @code{Object_Size} value.
+size that is greater than the specified size. The warning can also
+be suppressed by giving an explicit @code{Object_Size} value.
 @end table
 
 @geindex -Wunused (gcc)


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]