[1/1] Replace flag_strict_flex_arrays with DECL_NOT_FLEXARRAY in middle-end
Checks
Commit Message
We should not directly check flag_strict_flex_arrays in the middle end.
Instead, check DECL_NOT_FLEXARRAY(array_field_decl) which is set by
C/C++ FEs according to -fstrict-flex-arrays and the corresponding attribute
attached to the array_field.
As a result, We will lose the LEVEL information of -fstrict-flex-arrays in
the middle end. -Wstrict-flex-arrays will not be able to issue such
information. update the testing cases accordingly.
gcc/ChangeLog:
* attribs.cc (strict_flex_array_level_of): Move this function to ...
* attribs.h (strict_flex_array_level_of): Remove the declaration.
* gimple-array-bounds.cc (array_bounds_checker::check_array_ref):
replace the referece to strict_flex_array_level_of with
DECL_NOT_FLEXARRAY.
* tree.cc (component_ref_size): Likewise.
gcc/c/ChangeLog:
* c-decl.cc (strict_flex_array_level_of): ... here.
gcc/testsuite/ChangeLog:
* gcc.dg/Warray-bounds-flex-arrays-1.c: Delete the level information
from the message issued by -Wstrict-flex-arrays.
* gcc.dg/Warray-bounds-flex-arrays-2.c: Likewise.
* gcc.dg/Warray-bounds-flex-arrays-3.c: Likewise.
* gcc.dg/Warray-bounds-flex-arrays-4.c: Likewise.
* gcc.dg/Warray-bounds-flex-arrays-5.c: Likewise.
* gcc.dg/Warray-bounds-flex-arrays-6.c: Likewise.
* gcc.dg/Wstrict-flex-arrays-2.c: Likewise.
* gcc.dg/Wstrict-flex-arrays-3.c: Likewise.
* gcc.dg/Wstrict-flex-arrays.c: Likewise.
---
gcc/attribs.cc | 30 ------------
gcc/attribs.h | 2 -
gcc/c/c-decl.cc | 28 +++++++++++
gcc/gimple-array-bounds.cc | 46 ++++---------------
.../gcc.dg/Warray-bounds-flex-arrays-1.c | 2 +-
.../gcc.dg/Warray-bounds-flex-arrays-2.c | 4 +-
.../gcc.dg/Warray-bounds-flex-arrays-3.c | 6 +--
.../gcc.dg/Warray-bounds-flex-arrays-4.c | 2 +-
.../gcc.dg/Warray-bounds-flex-arrays-5.c | 4 +-
.../gcc.dg/Warray-bounds-flex-arrays-6.c | 6 +--
gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c | 8 ++--
gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c | 8 ++--
gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c | 8 ++--
gcc/tree.cc | 37 +++------------
14 files changed, 68 insertions(+), 123 deletions(-)
Comments
On Thu, 12 Jan 2023, Qing Zhao wrote:
> We should not directly check flag_strict_flex_arrays in the middle end.
> Instead, check DECL_NOT_FLEXARRAY(array_field_decl) which is set by
> C/C++ FEs according to -fstrict-flex-arrays and the corresponding attribute
> attached to the array_field.
>
> As a result, We will lose the LEVEL information of -fstrict-flex-arrays in
> the middle end. -Wstrict-flex-arrays will not be able to issue such
> information. update the testing cases accordingly.
OK.
Thanks,
Richard.
> gcc/ChangeLog:
>
> * attribs.cc (strict_flex_array_level_of): Move this function to ...
> * attribs.h (strict_flex_array_level_of): Remove the declaration.
> * gimple-array-bounds.cc (array_bounds_checker::check_array_ref):
> replace the referece to strict_flex_array_level_of with
> DECL_NOT_FLEXARRAY.
> * tree.cc (component_ref_size): Likewise.
>
> gcc/c/ChangeLog:
>
> * c-decl.cc (strict_flex_array_level_of): ... here.
>
> gcc/testsuite/ChangeLog:
>
> * gcc.dg/Warray-bounds-flex-arrays-1.c: Delete the level information
> from the message issued by -Wstrict-flex-arrays.
> * gcc.dg/Warray-bounds-flex-arrays-2.c: Likewise.
> * gcc.dg/Warray-bounds-flex-arrays-3.c: Likewise.
> * gcc.dg/Warray-bounds-flex-arrays-4.c: Likewise.
> * gcc.dg/Warray-bounds-flex-arrays-5.c: Likewise.
> * gcc.dg/Warray-bounds-flex-arrays-6.c: Likewise.
> * gcc.dg/Wstrict-flex-arrays-2.c: Likewise.
> * gcc.dg/Wstrict-flex-arrays-3.c: Likewise.
> * gcc.dg/Wstrict-flex-arrays.c: Likewise.
> ---
> gcc/attribs.cc | 30 ------------
> gcc/attribs.h | 2 -
> gcc/c/c-decl.cc | 28 +++++++++++
> gcc/gimple-array-bounds.cc | 46 ++++---------------
> .../gcc.dg/Warray-bounds-flex-arrays-1.c | 2 +-
> .../gcc.dg/Warray-bounds-flex-arrays-2.c | 4 +-
> .../gcc.dg/Warray-bounds-flex-arrays-3.c | 6 +--
> .../gcc.dg/Warray-bounds-flex-arrays-4.c | 2 +-
> .../gcc.dg/Warray-bounds-flex-arrays-5.c | 4 +-
> .../gcc.dg/Warray-bounds-flex-arrays-6.c | 6 +--
> gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c | 8 ++--
> gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c | 8 ++--
> gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c | 8 ++--
> gcc/tree.cc | 37 +++------------
> 14 files changed, 68 insertions(+), 123 deletions(-)
>
> diff --git a/gcc/attribs.cc b/gcc/attribs.cc
> index 49cb299a3c1..7db730cf831 100644
> --- a/gcc/attribs.cc
> +++ b/gcc/attribs.cc
> @@ -2456,36 +2456,6 @@ init_attr_rdwr_indices (rdwr_map *rwm, tree attrs)
> }
> }
>
> -/* Get the LEVEL of the strict_flex_array for the ARRAY_FIELD based on the
> - values of attribute strict_flex_array and the flag_strict_flex_arrays. */
> -unsigned int
> -strict_flex_array_level_of (tree array_field)
> -{
> - gcc_assert (TREE_CODE (array_field) == FIELD_DECL);
> - unsigned int strict_flex_array_level = flag_strict_flex_arrays;
> -
> - tree attr_strict_flex_array
> - = lookup_attribute ("strict_flex_array", DECL_ATTRIBUTES (array_field));
> - /* If there is a strict_flex_array attribute attached to the field,
> - override the flag_strict_flex_arrays. */
> - if (attr_strict_flex_array)
> - {
> - /* Get the value of the level first from the attribute. */
> - unsigned HOST_WIDE_INT attr_strict_flex_array_level = 0;
> - gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
> - attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
> - gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
> - attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
> - gcc_assert (tree_fits_uhwi_p (attr_strict_flex_array));
> - attr_strict_flex_array_level = tree_to_uhwi (attr_strict_flex_array);
> -
> - /* The attribute has higher priority than flag_struct_flex_array. */
> - strict_flex_array_level = attr_strict_flex_array_level;
> - }
> - return strict_flex_array_level;
> -}
> -
> -
> /* Return the access specification for a function parameter PARM
> or null if the current function has no such specification. */
>
> diff --git a/gcc/attribs.h b/gcc/attribs.h
> index e7540f71d6a..140e70b64e0 100644
> --- a/gcc/attribs.h
> +++ b/gcc/attribs.h
> @@ -398,6 +398,4 @@ extern void init_attr_rdwr_indices (rdwr_map *, tree);
> extern attr_access *get_parm_access (rdwr_map &, tree,
> tree = current_function_decl);
>
> -extern unsigned int strict_flex_array_level_of (tree);
> -
> #endif // GCC_ATTRIBS_H
> diff --git a/gcc/c/c-decl.cc b/gcc/c/c-decl.cc
> index d76ffb3380d..38647c100c1 100644
> --- a/gcc/c/c-decl.cc
> +++ b/gcc/c/c-decl.cc
> @@ -9047,6 +9047,34 @@ finish_incomplete_vars (tree incomplete_vars, bool toplevel)
> }
> }
>
> +/* Get the LEVEL of the strict_flex_array for the ARRAY_FIELD based on the
> + values of attribute strict_flex_array and the flag_strict_flex_arrays. */
> +static unsigned int
> +strict_flex_array_level_of (tree array_field)
> +{
> + gcc_assert (TREE_CODE (array_field) == FIELD_DECL);
> + unsigned int strict_flex_array_level = flag_strict_flex_arrays;
> +
> + tree attr_strict_flex_array
> + = lookup_attribute ("strict_flex_array", DECL_ATTRIBUTES (array_field));
> + /* If there is a strict_flex_array attribute attached to the field,
> + override the flag_strict_flex_arrays. */
> + if (attr_strict_flex_array)
> + {
> + /* Get the value of the level first from the attribute. */
> + unsigned HOST_WIDE_INT attr_strict_flex_array_level = 0;
> + gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
> + attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
> + gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
> + attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
> + gcc_assert (tree_fits_uhwi_p (attr_strict_flex_array));
> + attr_strict_flex_array_level = tree_to_uhwi (attr_strict_flex_array);
> +
> + /* The attribute has higher priority than flag_struct_flex_array. */
> + strict_flex_array_level = attr_strict_flex_array_level;
> + }
> + return strict_flex_array_level;
> +}
>
> /* Determine whether the FIELD_DECL X is a flexible array member according to
> the following info:
> diff --git a/gcc/gimple-array-bounds.cc b/gcc/gimple-array-bounds.cc
> index 116200a317f..66fd46e9b6c 100644
> --- a/gcc/gimple-array-bounds.cc
> +++ b/gcc/gimple-array-bounds.cc
> @@ -350,18 +350,14 @@ array_bounds_checker::check_array_ref (location_t location, tree ref,
>
> /* Set to the type of the special array member for a COMPONENT_REF. */
> special_array_member sam{ };
> -
> + tree afield_decl = NULL_TREE;
> tree arg = TREE_OPERAND (ref, 0);
> - const bool compref = TREE_CODE (arg) == COMPONENT_REF;
> - unsigned int strict_flex_array_level = flag_strict_flex_arrays;
>
> - if (compref)
> + if (TREE_CODE (arg) == COMPONENT_REF)
> {
> /* Try to determine special array member type for this COMPONENT_REF. */
> sam = component_ref_sam_type (arg);
> - /* Get the level of strict_flex_array for this array field. */
> - tree afield_decl = TREE_OPERAND (arg, 1);
> - strict_flex_array_level = strict_flex_array_level_of (afield_decl);
> + afield_decl = TREE_OPERAND (arg, 1);
> }
>
> get_up_bounds_for_array_ref (ref, &decl, &up_bound, &up_bound_p1);
> @@ -412,39 +408,15 @@ array_bounds_checker::check_array_ref (location_t location, tree ref,
>
> /* issue warnings for -Wstrict-flex-arrays according to the level of
> flag_strict_flex_arrays. */
> - if (out_of_bound && warn_strict_flex_arrays)
> - switch (strict_flex_array_level)
> - {
> - case 3:
> - /* Issue additional warnings for trailing arrays [0]. */
> - if (sam == special_array_member::trail_0)
> + if ((out_of_bound && warn_strict_flex_arrays)
> + && (((sam == special_array_member::trail_0)
> + || (sam == special_array_member::trail_1)
> + || (sam == special_array_member::trail_n))
> + && DECL_NOT_FLEXARRAY (afield_decl)))
> warned = warning_at (location, OPT_Wstrict_flex_arrays,
> "trailing array %qT should not be used as "
> - "a flexible array member for level 3",
> + "a flexible array member",
> artype);
> - /* FALLTHROUGH. */
> - case 2:
> - /* Issue additional warnings for trailing arrays [1]. */
> - if (sam == special_array_member::trail_1)
> - warned = warning_at (location, OPT_Wstrict_flex_arrays,
> - "trailing array %qT should not be used as "
> - "a flexible array member for level 2 and "
> - "above", artype);
> - /* FALLTHROUGH. */
> - case 1:
> - /* Issue warnings for trailing arrays [n]. */
> - if (sam == special_array_member::trail_n)
> - warned = warning_at (location, OPT_Wstrict_flex_arrays,
> - "trailing array %qT should not be used as "
> - "a flexible array member for level 1 and "
> - "above", artype);
> - break;
> - case 0:
> - /* Do nothing. */
> - break;
> - default:
> - gcc_unreachable ();
> - }
>
> /* Avoid more warnings when checking more significant subscripts
> of the same expression. */
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-1.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-1.c
> index 65c9fec43af..fd2aacf6452 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-1.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-1.c
> @@ -32,7 +32,7 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /* { dg-bogus "array subscript " } */
> trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-2.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-2.c
> index 2b5a895c598..55b7535424b 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-2.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-2.c
> @@ -32,9 +32,9 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /* { dg-warning "array subscript 2 is above array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
>
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-3.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-3.c
> index 25b903f2615..abdf8f15c78 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-3.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-3.c
> @@ -32,11 +32,11 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_0->c[1] = 1; /*{ dg-warning "array subscript 1 is outside array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 3" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript" } */
>
> }
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-4.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-4.c
> index 5fc500a19ca..82b38ff1ad1 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-4.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-4.c
> @@ -32,7 +32,7 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /* { dg-bogus "array subscript " } */
> trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-5.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-5.c
> index 30bb4ca8832..dca02288be7 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-5.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-5.c
> @@ -32,9 +32,9 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
>
> diff --git a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-6.c b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-6.c
> index e847a44516e..fc9f73b4535 100644
> --- a/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-6.c
> +++ b/gcc/testsuite/gcc.dg/Warray-bounds-flex-arrays-6.c
> @@ -32,11 +32,11 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_4 *trailing_flex)
> {
> normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
> - /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
> + /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_0->c[1] = 1; /*{ dg-warning "array subscript 1 is outside array bounds of" } */
> - /* { dg-warning "should not be used as a flexible array member for level 3" "" { target *-*-* } .-1 } */
> + /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
> trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
>
> }
> diff --git a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c
> index 2e241f96208..befc604f19b 100644
> --- a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c
> +++ b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-2.c
> @@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_3 *trailing_0,
> struct trailing_array_4 *trailing_flex)
> {
> - normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
> - trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member for level 2 and above" } */
> - trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member for level 2 and above" } */
> - trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 2 and above" } */
> + normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
> + trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member" } */
> + trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member" } */
> + trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
>
> }
> diff --git a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c
> index 97eb65ba0a9..cc37a092c3e 100644
> --- a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c
> +++ b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays-3.c
> @@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_3 *trailing_0,
> struct trailing_array_4 *trailing_flex)
> {
> - normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
> - trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member for level 2 and above" } */
> - trailing_0->c[1] = 1; /* { dg-warning "should not be used as a flexible array member for level 3" } */
> - trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 3" } */
> + normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
> + trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member" } */
> + trailing_0->c[1] = 1; /* { dg-warning "should not be used as a flexible array member" } */
> + trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
>
> }
> diff --git a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c
> index 110fdc72778..735b23a1dc6 100644
> --- a/gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c
> +++ b/gcc/testsuite/gcc.dg/Wstrict-flex-arrays.c
> @@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
> struct trailing_array_3 *trailing_0,
> struct trailing_array_4 *trailing_flex)
> {
> - normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
> - trailing_1->c[2] = 2; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
> - trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
> - trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
> + normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
> + trailing_1->c[2] = 2; /* { dg-bogus "should not be used as a flexible array member" } */
> + trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member" } */
> + trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
>
> }
> diff --git a/gcc/tree.cc b/gcc/tree.cc
> index 78b64ee98b3..7473912a065 100644
> --- a/gcc/tree.cc
> +++ b/gcc/tree.cc
> @@ -13074,38 +13074,15 @@ component_ref_size (tree ref, special_array_member *sam /* = NULL */)
> || *sam == special_array_member::trail_n)
> return memsize;
>
> - /* flag_strict_flex_arrays will control how to treat
> - the trailing arrays as flexiable array members. */
> -
> tree afield_decl = TREE_OPERAND (ref, 1);
> - unsigned int strict_flex_array_level
> - = strict_flex_array_level_of (afield_decl);
> -
> - switch (strict_flex_array_level)
> - {
> - case 3:
> - /* Treaing 0-length trailing arrays as normal array. */
> - if (*sam == special_array_member::trail_0)
> - return size_zero_node;
> - /* FALLTHROUGH. */
> - case 2:
> - /* Treating 1-element trailing arrays as normal array. */
> - if (*sam == special_array_member::trail_1)
> - return memsize;
> - /* FALLTHROUGH. */
> - case 1:
> - /* Treating 2-or-more elements trailing arrays as normal
> - array. */
> - if (*sam == special_array_member::trail_n)
> - return memsize;
> - /* FALLTHROUGH. */
> - case 0:
> - break;
> - default:
> - gcc_unreachable ();
> - }
> + gcc_assert (TREE_CODE (afield_decl) == FIELD_DECL);
> + /* if the trailing array is a not a flexible array member, treat it as
> + a normal array. */
> + if (DECL_NOT_FLEXARRAY (afield_decl)
> + && *sam != special_array_member::int_0)
> + return memsize;
>
> - if (*sam == special_array_member::int_0)
> + if (*sam == special_array_member::int_0)
> memsize = NULL_TREE;
>
> /* For a reference to a flexible array member of a union
>
@@ -2456,36 +2456,6 @@ init_attr_rdwr_indices (rdwr_map *rwm, tree attrs)
}
}
-/* Get the LEVEL of the strict_flex_array for the ARRAY_FIELD based on the
- values of attribute strict_flex_array and the flag_strict_flex_arrays. */
-unsigned int
-strict_flex_array_level_of (tree array_field)
-{
- gcc_assert (TREE_CODE (array_field) == FIELD_DECL);
- unsigned int strict_flex_array_level = flag_strict_flex_arrays;
-
- tree attr_strict_flex_array
- = lookup_attribute ("strict_flex_array", DECL_ATTRIBUTES (array_field));
- /* If there is a strict_flex_array attribute attached to the field,
- override the flag_strict_flex_arrays. */
- if (attr_strict_flex_array)
- {
- /* Get the value of the level first from the attribute. */
- unsigned HOST_WIDE_INT attr_strict_flex_array_level = 0;
- gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
- attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
- gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
- attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
- gcc_assert (tree_fits_uhwi_p (attr_strict_flex_array));
- attr_strict_flex_array_level = tree_to_uhwi (attr_strict_flex_array);
-
- /* The attribute has higher priority than flag_struct_flex_array. */
- strict_flex_array_level = attr_strict_flex_array_level;
- }
- return strict_flex_array_level;
-}
-
-
/* Return the access specification for a function parameter PARM
or null if the current function has no such specification. */
@@ -398,6 +398,4 @@ extern void init_attr_rdwr_indices (rdwr_map *, tree);
extern attr_access *get_parm_access (rdwr_map &, tree,
tree = current_function_decl);
-extern unsigned int strict_flex_array_level_of (tree);
-
#endif // GCC_ATTRIBS_H
@@ -9047,6 +9047,34 @@ finish_incomplete_vars (tree incomplete_vars, bool toplevel)
}
}
+/* Get the LEVEL of the strict_flex_array for the ARRAY_FIELD based on the
+ values of attribute strict_flex_array and the flag_strict_flex_arrays. */
+static unsigned int
+strict_flex_array_level_of (tree array_field)
+{
+ gcc_assert (TREE_CODE (array_field) == FIELD_DECL);
+ unsigned int strict_flex_array_level = flag_strict_flex_arrays;
+
+ tree attr_strict_flex_array
+ = lookup_attribute ("strict_flex_array", DECL_ATTRIBUTES (array_field));
+ /* If there is a strict_flex_array attribute attached to the field,
+ override the flag_strict_flex_arrays. */
+ if (attr_strict_flex_array)
+ {
+ /* Get the value of the level first from the attribute. */
+ unsigned HOST_WIDE_INT attr_strict_flex_array_level = 0;
+ gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
+ attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
+ gcc_assert (TREE_VALUE (attr_strict_flex_array) != NULL_TREE);
+ attr_strict_flex_array = TREE_VALUE (attr_strict_flex_array);
+ gcc_assert (tree_fits_uhwi_p (attr_strict_flex_array));
+ attr_strict_flex_array_level = tree_to_uhwi (attr_strict_flex_array);
+
+ /* The attribute has higher priority than flag_struct_flex_array. */
+ strict_flex_array_level = attr_strict_flex_array_level;
+ }
+ return strict_flex_array_level;
+}
/* Determine whether the FIELD_DECL X is a flexible array member according to
the following info:
@@ -350,18 +350,14 @@ array_bounds_checker::check_array_ref (location_t location, tree ref,
/* Set to the type of the special array member for a COMPONENT_REF. */
special_array_member sam{ };
-
+ tree afield_decl = NULL_TREE;
tree arg = TREE_OPERAND (ref, 0);
- const bool compref = TREE_CODE (arg) == COMPONENT_REF;
- unsigned int strict_flex_array_level = flag_strict_flex_arrays;
- if (compref)
+ if (TREE_CODE (arg) == COMPONENT_REF)
{
/* Try to determine special array member type for this COMPONENT_REF. */
sam = component_ref_sam_type (arg);
- /* Get the level of strict_flex_array for this array field. */
- tree afield_decl = TREE_OPERAND (arg, 1);
- strict_flex_array_level = strict_flex_array_level_of (afield_decl);
+ afield_decl = TREE_OPERAND (arg, 1);
}
get_up_bounds_for_array_ref (ref, &decl, &up_bound, &up_bound_p1);
@@ -412,39 +408,15 @@ array_bounds_checker::check_array_ref (location_t location, tree ref,
/* issue warnings for -Wstrict-flex-arrays according to the level of
flag_strict_flex_arrays. */
- if (out_of_bound && warn_strict_flex_arrays)
- switch (strict_flex_array_level)
- {
- case 3:
- /* Issue additional warnings for trailing arrays [0]. */
- if (sam == special_array_member::trail_0)
+ if ((out_of_bound && warn_strict_flex_arrays)
+ && (((sam == special_array_member::trail_0)
+ || (sam == special_array_member::trail_1)
+ || (sam == special_array_member::trail_n))
+ && DECL_NOT_FLEXARRAY (afield_decl)))
warned = warning_at (location, OPT_Wstrict_flex_arrays,
"trailing array %qT should not be used as "
- "a flexible array member for level 3",
+ "a flexible array member",
artype);
- /* FALLTHROUGH. */
- case 2:
- /* Issue additional warnings for trailing arrays [1]. */
- if (sam == special_array_member::trail_1)
- warned = warning_at (location, OPT_Wstrict_flex_arrays,
- "trailing array %qT should not be used as "
- "a flexible array member for level 2 and "
- "above", artype);
- /* FALLTHROUGH. */
- case 1:
- /* Issue warnings for trailing arrays [n]. */
- if (sam == special_array_member::trail_n)
- warned = warning_at (location, OPT_Wstrict_flex_arrays,
- "trailing array %qT should not be used as "
- "a flexible array member for level 1 and "
- "above", artype);
- break;
- case 0:
- /* Do nothing. */
- break;
- default:
- gcc_unreachable ();
- }
/* Avoid more warnings when checking more significant subscripts
of the same expression. */
@@ -32,7 +32,7 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /* { dg-bogus "array subscript " } */
trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
@@ -32,9 +32,9 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /* { dg-warning "array subscript 2 is above array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
@@ -32,11 +32,11 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_0->c[1] = 1; /*{ dg-warning "array subscript 1 is outside array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 3" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript" } */
}
@@ -32,7 +32,7 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /* { dg-bogus "array subscript " } */
trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
@@ -32,9 +32,9 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_0->c[1] = 1; /* { dg-bogus "array subscript " } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
@@ -32,11 +32,11 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_4 *trailing_flex)
{
normal->c[5] = 5; /*{ dg-warning "array subscript 5 is above array bounds of" } */
- /*{ dg-warning "should not be used as a flexible array member for level 1 and above" "" { target *-*-* } .-1 } */
+ /*{ dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_1->c[2] = 2; /*{ dg-warning "array subscript 2 is above array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 2 and above" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_0->c[1] = 1; /*{ dg-warning "array subscript 1 is outside array bounds of" } */
- /* { dg-warning "should not be used as a flexible array member for level 3" "" { target *-*-* } .-1 } */
+ /* { dg-warning "should not be used as a flexible array member" "" { target *-*-* } .-1 } */
trailing_flex->c[10] = 10; /* { dg-bogus "array subscript " } */
}
@@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_3 *trailing_0,
struct trailing_array_4 *trailing_flex)
{
- normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
- trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member for level 2 and above" } */
- trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member for level 2 and above" } */
- trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 2 and above" } */
+ normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
+ trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member" } */
+ trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member" } */
+ trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
}
@@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_3 *trailing_0,
struct trailing_array_4 *trailing_flex)
{
- normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
- trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member for level 2 and above" } */
- trailing_0->c[1] = 1; /* { dg-warning "should not be used as a flexible array member for level 3" } */
- trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 3" } */
+ normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
+ trailing_1->c[2] = 2; /* { dg-warning "should not be used as a flexible array member" } */
+ trailing_0->c[1] = 1; /* { dg-warning "should not be used as a flexible array member" } */
+ trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
}
@@ -31,9 +31,9 @@ void __attribute__((__noinline__)) stuff(
struct trailing_array_3 *trailing_0,
struct trailing_array_4 *trailing_flex)
{
- normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member for level 1 and above" } */
- trailing_1->c[2] = 2; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
- trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
- trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member for level 1 and above" } */
+ normal->c[5] = 5; /*{ dg-warning "should not be used as a flexible array member" } */
+ trailing_1->c[2] = 2; /* { dg-bogus "should not be used as a flexible array member" } */
+ trailing_0->c[1] = 1; /* { dg-bogus "should not be used as a flexible array member" } */
+ trailing_flex->c[10] = 10; /* { dg-bogus "should not be used as a flexible array member" } */
}
@@ -13074,38 +13074,15 @@ component_ref_size (tree ref, special_array_member *sam /* = NULL */)
|| *sam == special_array_member::trail_n)
return memsize;
- /* flag_strict_flex_arrays will control how to treat
- the trailing arrays as flexiable array members. */
-
tree afield_decl = TREE_OPERAND (ref, 1);
- unsigned int strict_flex_array_level
- = strict_flex_array_level_of (afield_decl);
-
- switch (strict_flex_array_level)
- {
- case 3:
- /* Treaing 0-length trailing arrays as normal array. */
- if (*sam == special_array_member::trail_0)
- return size_zero_node;
- /* FALLTHROUGH. */
- case 2:
- /* Treating 1-element trailing arrays as normal array. */
- if (*sam == special_array_member::trail_1)
- return memsize;
- /* FALLTHROUGH. */
- case 1:
- /* Treating 2-or-more elements trailing arrays as normal
- array. */
- if (*sam == special_array_member::trail_n)
- return memsize;
- /* FALLTHROUGH. */
- case 0:
- break;
- default:
- gcc_unreachable ();
- }
+ gcc_assert (TREE_CODE (afield_decl) == FIELD_DECL);
+ /* if the trailing array is a not a flexible array member, treat it as
+ a normal array. */
+ if (DECL_NOT_FLEXARRAY (afield_decl)
+ && *sam != special_array_member::int_0)
+ return memsize;
- if (*sam == special_array_member::int_0)
+ if (*sam == special_array_member::int_0)
memsize = NULL_TREE;
/* For a reference to a flexible array member of a union