commit: 9fdf5a30ded9c691d9fcdb787e72f8dd0f111f8a Author: Sam James <sam <AT> gentoo <DOT> org> AuthorDate: Thu Jul 3 01:28:39 2025 +0000 Commit: Sam James <sam <AT> gentoo <DOT> org> CommitDate: Thu Jul 3 01:29:23 2025 +0000 URL: https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=9fdf5a30
16.0.0: revert patches breaking _FORTIFY_SOURCE Bug: https://gcc.gnu.org/PR120929 Signed-off-by: Sam James <sam <AT> gentoo.org> ...the-counted_by-attribute-of-pointers-in-a.patch | 670 +++++++++++++++++++++ ...the-counted_by-attribute-of-pointers-in-b.patch | 382 ++++++++++++ 16.0.0/gentoo/README.history | 2 + 3 files changed, 1054 insertions(+) diff --git a/16.0.0/gentoo/85_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-a.patch b/16.0.0/gentoo/85_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-a.patch new file mode 100644 index 0000000..b503500 --- /dev/null +++ b/16.0.0/gentoo/85_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-a.patch @@ -0,0 +1,670 @@ +https://gcc.gnu.org/PR120929 + +From 75017c57b4f66552d02efda7e7d5eade1ba0ee80 Mon Sep 17 00:00:00 2001 +Message-ID: <75017c57b4f66552d02efda7e7d5eade1ba0ee80.1751506033.git....@gentoo.org> +From: Sam James <[email protected]> +Date: Thu, 3 Jul 2025 02:26:55 +0100 +Subject: [PATCH 1/2] Revert "Use the counted_by attribute of pointers in array + bound checker." + +This reverts commit 9d579c522d551eaa807e438206e19a91a3def67f. +--- + gcc/c-family/c-gimplify.cc | 28 -- + gcc/c-family/c-ubsan.cc | 316 +----------------- + .../ubsan/pointer-counted-by-bounds-2.c | 51 --- + .../ubsan/pointer-counted-by-bounds-3.c | 42 --- + .../ubsan/pointer-counted-by-bounds-4.c | 42 --- + .../ubsan/pointer-counted-by-bounds-5.c | 40 --- + .../gcc.dg/ubsan/pointer-counted-by-bounds.c | 46 --- + 7 files changed, 16 insertions(+), 549 deletions(-) + delete mode 100644 gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-2.c + delete mode 100644 gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-3.c + delete mode 100644 gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-4.c + delete mode 100644 gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-5.c + delete mode 100644 gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds.c + +diff --git a/gcc/c-family/c-gimplify.cc b/gcc/c-family/c-gimplify.cc +index e905059708f7..c6fb7646567e 100644 +--- a/gcc/c-family/c-gimplify.cc ++++ b/gcc/c-family/c-gimplify.cc +@@ -66,20 +66,6 @@ along with GCC; see the file COPYING3. If not see + walk back up, we check that they fit our constraints, and copy them + into temporaries if not. */ + +- +-/* Check whether TP is an address computation whose base is a call to +- .ACCESS_WITH_SIZE. */ +- +-static bool +-is_address_with_access_with_size (tree tp) +-{ +- if (TREE_CODE (tp) == POINTER_PLUS_EXPR +- && (TREE_CODE (TREE_OPERAND (tp, 0)) == INDIRECT_REF) +- && (is_access_with_size_p (TREE_OPERAND (TREE_OPERAND (tp, 0), 0)))) +- return true; +- return false; +-} +- + /* Callback for c_genericize. */ + + static tree +@@ -135,20 +121,6 @@ ubsan_walk_array_refs_r (tree *tp, int *walk_subtrees, void *data) + walk_tree (&TREE_OPERAND (*tp, 1), ubsan_walk_array_refs_r, pset, pset); + walk_tree (&TREE_OPERAND (*tp, 0), ubsan_walk_array_refs_r, pset, pset); + } +- else if (TREE_CODE (*tp) == INDIRECT_REF +- && is_address_with_access_with_size (TREE_OPERAND (*tp, 0))) +- { +- ubsan_maybe_instrument_array_ref (&TREE_OPERAND (*tp, 0), false); +- /* Make sure ubsan_maybe_instrument_array_ref is not called again on +- the POINTER_PLUS_EXPR, so ensure it is not walked again and walk +- its subtrees manually. */ +- tree aref = TREE_OPERAND (*tp, 0); +- pset->add (aref); +- *walk_subtrees = 0; +- walk_tree (&TREE_OPERAND (aref, 0), ubsan_walk_array_refs_r, pset, pset); +- } +- else if (is_address_with_access_with_size (*tp)) +- ubsan_maybe_instrument_array_ref (tp, true); + return NULL_TREE; + } + +diff --git a/gcc/c-family/c-ubsan.cc b/gcc/c-family/c-ubsan.cc +index 38514a4046c3..78b786854699 100644 +--- a/gcc/c-family/c-ubsan.cc ++++ b/gcc/c-family/c-ubsan.cc +@@ -554,322 +554,38 @@ ubsan_instrument_bounds (location_t loc, tree array, tree *index, + *index, bound); + } + +- +-/* Instrument array bounds for the pointer array address which is +- an INDIRECT_REF to the call to .ACCESS_WITH_SIZE. We create special +- builtin, that gets expanded in the sanopt pass, and make an array +- dimention of it. POINTER_ADDR is the pointer array's base address. +- *INDEX is an index to the array. +- IGNORE_OFF_BY_ONE is true if the POINTER_ADDR is not inside an +- INDIRECT_REF. +- Return NULL_TREE if no instrumentation is emitted. */ +- +-tree +-ubsan_instrument_bounds_pointer_address (location_t loc, tree pointer_addr, +- tree *index, +- bool ignore_off_by_one) +-{ +- gcc_assert (TREE_CODE (pointer_addr) == INDIRECT_REF); +- tree call = TREE_OPERAND (pointer_addr, 0); +- if (!is_access_with_size_p (call)) +- return NULL_TREE; +- tree bound = get_bound_from_access_with_size (call); +- +- if (ignore_off_by_one) +- bound = fold_build2 (PLUS_EXPR, TREE_TYPE (bound), bound, +- build_int_cst (TREE_TYPE (bound), +- 1)); +- +- /* Don't emit instrumentation in the most common cases. */ +- tree idx = NULL_TREE; +- if (TREE_CODE (*index) == INTEGER_CST) +- idx = *index; +- else if (TREE_CODE (*index) == BIT_AND_EXPR +- && TREE_CODE (TREE_OPERAND (*index, 1)) == INTEGER_CST) +- idx = TREE_OPERAND (*index, 1); +- if (idx +- && TREE_CODE (bound) == INTEGER_CST +- && tree_int_cst_sgn (idx) >= 0 +- && tree_int_cst_lt (idx, bound)) +- return NULL_TREE; +- +- *index = save_expr (*index); +- +- /* Create an array_type for the corresponding pointer array. */ +- tree itype = build_range_type (sizetype, size_zero_node, NULL_TREE); +- /* The array's element type can be get from the return type of the call to +- .ACCESS_WITH_SIZE. */ +- tree element_type = TREE_TYPE (TREE_TYPE (TREE_TYPE (call))); +- tree array_type = build_array_type (element_type, itype); +- /* Create a "(T *) 0" tree node to describe the array type. */ +- tree zero_with_type = build_int_cst (build_pointer_type (array_type), 0); +- return build_call_expr_internal_loc (loc, IFN_UBSAN_BOUNDS, +- void_type_node, 3, zero_with_type, +- *index, bound); +-} +- +-/* This structure is to combine a factor with its parent and its position +- * in its parent tree. */ +-struct factor_t +-{ +- tree factor; +- tree parent; /* the parent tree of this factor. */ +- int pos; /* the position of this factor in its parent tree. */ +-}; +- +-/* for a multiply expression like: +- ((long unsigned int) m * (long unsigned int) SAVE_EXPR <n>) * 4 +- +- locate all the factors, the parents of the factor and the position of +- the factor in its parent, and put them to VEC_FACTORS. */ +- +-static void +-get_factors_from_mul_expr (tree mult_expr, tree parent, +- int pos, auto_vec<factor_t> *vec_factors) +-{ +- struct factor_t mult_factor = {0, 0, -1}; +- mult_factor.factor = mult_expr; +- mult_factor.parent = parent; +- mult_factor.pos = pos; +- +- while (CONVERT_EXPR_CODE_P (TREE_CODE (mult_expr))) +- { +- mult_factor.parent = mult_expr; +- mult_factor.pos = 0; +- mult_expr = TREE_OPERAND (mult_expr, 0); +- mult_factor.factor = mult_expr; +- } +- if (TREE_CODE (mult_expr) != MULT_EXPR) +- vec_factors->safe_push (mult_factor); +- else +- { +- get_factors_from_mul_expr (TREE_OPERAND (mult_expr, 0), mult_expr, +- 0, vec_factors); +- get_factors_from_mul_expr (TREE_OPERAND (mult_expr, 1), mult_expr, +- 1, vec_factors); +- } +-} +- +-/* Given an OFFSET expression, and the ELEMENT_SIZE, +- get the index expression from OFFSET and return it. +- For example: +- OFFSET: +- ((long unsigned int) m * (long unsigned int) SAVE_EXPR <n>) * 4 +- ELEMENT_SIZE: +- (sizetype) SAVE_EXPR <n> * 4 +- get the index as (long unsigned int) m, and return it. +- The INDEX_P holds the pointer to the parent tree of the index, +- INDEX_N holds the position of the index in its parent. */ +- +-static tree +-get_index_from_offset (tree offset, tree *index_p, +- int *index_n, tree element_size) +-{ +- if (TREE_CODE (offset) != MULT_EXPR) +- return NULL_TREE; +- +- auto_vec<factor_t> e_factors, o_factors; +- get_factors_from_mul_expr (element_size, NULL, -1, &e_factors); +- get_factors_from_mul_expr (offset, *index_p, *index_n, &o_factors); +- +- if (e_factors.is_empty () || o_factors.is_empty ()) +- return NULL_TREE; +- +- bool all_found = true; +- for (unsigned i = 0; i < e_factors.length (); i++) +- { +- factor_t e_size_factor = e_factors[i]; +- bool found = false; +- for (unsigned j = 0; j < o_factors.length ();) +- { +- factor_t o_exp_factor = o_factors[j]; +- if (operand_equal_p (e_size_factor.factor, o_exp_factor.factor)) +- { +- o_factors.unordered_remove (j); +- found = true; +- break; +- } +- else +- j++; +- } +- if (!found) +- all_found = false; +- } +- +- if (!all_found) +- return NULL_TREE; +- +- if (o_factors.length () != 1) +- return NULL_TREE; +- +- *index_p = o_factors[0].parent; +- *index_n = o_factors[0].pos; +- return o_factors[0].factor; +-} +- +-/* For an pointer + offset computation expression, such as, +- *.ACCESS_WITH_SIZE (p->c, &p->b, 1, 0, -1, 0B) +- + (sizetype) ((long unsigned int) index * 4 +- Return the index of this pointer array reference, +- set the parent tree of INDEX to *INDEX_P. +- set the operand position of the INDEX in the parent tree to *INDEX_N. +- If failed, return NULL_TREE. */ +- +-static tree +-get_index_from_pointer_addr_expr (tree pointer, tree *index_p, int *index_n) +-{ +- *index_p = NULL_TREE; +- *index_n = -1; +- if (TREE_CODE (TREE_OPERAND (pointer, 0)) != INDIRECT_REF) +- return NULL_TREE; +- tree call = TREE_OPERAND (TREE_OPERAND (pointer, 0), 0); +- if (!is_access_with_size_p (call)) +- return NULL_TREE; +- +- /* Get the pointee type of the call to .ACCESS_WITH_SIZE. +- This should be the element type of the pointer array. */ +- tree pointee_type = TREE_TYPE (TREE_TYPE (TREE_TYPE (call))); +- tree pointee_size = TYPE_SIZE_UNIT (pointee_type); +- +- tree index_exp = TREE_OPERAND (pointer, 1); +- *index_p = pointer; +- *index_n = 1; +- +- if (!(TREE_CODE (index_exp) != MULT_EXPR +- && tree_int_cst_equal (pointee_size, integer_one_node))) +- { +- while (CONVERT_EXPR_CODE_P (TREE_CODE (index_exp))) +- { +- *index_p = index_exp; +- *index_n = 0; +- index_exp = TREE_OPERAND (index_exp, 0); +- } +- index_exp = get_index_from_offset (index_exp, index_p, +- index_n, pointee_size); +- +- if (!index_exp) +- return NULL_TREE; +- } +- +- while (CONVERT_EXPR_CODE_P (TREE_CODE (index_exp))) +- { +- *index_p = index_exp; +- *index_n = 0; +- index_exp = TREE_OPERAND (index_exp, 0); +- } +- +- return index_exp; +-} +- +-/* Return TRUE when the EXPR is a pointer array address that could be +- instrumented. +- We only instrument an address computation similar as the following: +- *.ACCESS_WITH_SIZE (p->c, &p->b, 1, 0, -1, 0B) +- + (sizetype) ((long unsigned int) index * 4) +- if the EXPR is instrumentable, return TRUE and +- set the index to *INDEX. +- set the *.ACCESS_WITH_SIZE to *BASE. +- set the parent tree of INDEX to *INDEX_P. +- set the operand position of the INDEX in the parent tree to INDEX_N. */ +- +-static bool +-is_instrumentable_pointer_array_address (tree expr, tree *base, +- tree *index, tree *index_p, +- int *index_n) +-{ +- /* For a poiner array address as: +- (*.ACCESS_WITH_SIZE (p->c, &p->b, 1, 0, -1, 0B) +- + (sizetype) ((long unsigned int) index * 4) +- op0 is the call to *.ACCESS_WITH_SIZE; +- op1 is the index. */ +- if (TREE_CODE (expr) != POINTER_PLUS_EXPR) +- return false; +- +- tree op0 = TREE_OPERAND (expr, 0); +- if (TREE_CODE (op0) != INDIRECT_REF) +- return false; +- if (!is_access_with_size_p (TREE_OPERAND (op0, 0))) +- return false; +- tree op1 = get_index_from_pointer_addr_expr (expr, index_p, index_n); +- if (op1 != NULL_TREE) +- { +- *base = op0; +- *index = op1; +- return true; +- } +- return false; +-} +- +-/* Return true iff T is an array or an indirect reference that was +- instrumented by SANITIZE_BOUNDS. */ ++/* Return true iff T is an array that was instrumented by SANITIZE_BOUNDS. */ + + bool +-ubsan_array_ref_instrumented_p (tree t) ++ubsan_array_ref_instrumented_p (const_tree t) + { +- if (TREE_CODE (t) != ARRAY_REF +- && TREE_CODE (t) != MEM_REF) ++ if (TREE_CODE (t) != ARRAY_REF) + return false; + +- bool is_array = (TREE_CODE (t) == ARRAY_REF); +- tree op0 = NULL_TREE; +- tree op1 = NULL_TREE; +- tree index_p = NULL_TREE; +- int index_n = 0; +- if (is_array) +- { +- op1 = TREE_OPERAND (t, 1); +- return TREE_CODE (op1) == COMPOUND_EXPR +- && TREE_CODE (TREE_OPERAND (op1, 0)) == CALL_EXPR +- && CALL_EXPR_FN (TREE_OPERAND (op1, 0)) == NULL_TREE +- && CALL_EXPR_IFN (TREE_OPERAND (op1, 0)) == IFN_UBSAN_BOUNDS; +- } +- else if (is_instrumentable_pointer_array_address (t, &op0, &op1, +- &index_p, &index_n)) +- return TREE_CODE (op1) == COMPOUND_EXPR +- && TREE_CODE (TREE_OPERAND (op1, 0)) == CALL_EXPR +- && CALL_EXPR_FN (TREE_OPERAND (op1, 0)) == NULL_TREE +- && CALL_EXPR_IFN (TREE_OPERAND (op1, 0)) == IFN_UBSAN_BOUNDS; +- +- return false; ++ tree op1 = TREE_OPERAND (t, 1); ++ return TREE_CODE (op1) == COMPOUND_EXPR ++ && TREE_CODE (TREE_OPERAND (op1, 0)) == CALL_EXPR ++ && CALL_EXPR_FN (TREE_OPERAND (op1, 0)) == NULL_TREE ++ && CALL_EXPR_IFN (TREE_OPERAND (op1, 0)) == IFN_UBSAN_BOUNDS; + } + +-/* Instrument an ARRAY_REF or an address computation whose base address is +- a call to .ACCESS_WITH_SIZE, if it hasn't already been instrumented. +- IGNORE_OFF_BY_ONE is true if the ARRAY_REF is inside a ADDR_EXPR, or the +- address computation is not inside a INDIRECT_REF. */ ++/* Instrument an ARRAY_REF, if it hasn't already been instrumented. ++ IGNORE_OFF_BY_ONE is true if the ARRAY_REF is inside a ADDR_EXPR. */ + + void + ubsan_maybe_instrument_array_ref (tree *expr_p, bool ignore_off_by_one) + { +- tree e = NULL_TREE; +- tree op0 = NULL_TREE; +- tree op1 = NULL_TREE; +- tree index_p = NULL_TREE; /* the parent tree of INDEX. */ +- int index_n = 0; /* the operand position of INDEX in the parent tree. */ +- + if (!ubsan_array_ref_instrumented_p (*expr_p) + && sanitize_flags_p (SANITIZE_BOUNDS | SANITIZE_BOUNDS_STRICT) + && current_function_decl != NULL_TREE) + { +- if (TREE_CODE (*expr_p) == ARRAY_REF) +- { +- op0 = TREE_OPERAND (*expr_p, 0); +- op1 = TREE_OPERAND (*expr_p, 1); +- index_p = *expr_p; +- index_n = 1; +- e = ubsan_instrument_bounds (EXPR_LOCATION (*expr_p), op0, +- &op1, ignore_off_by_one); +- } +- else if (is_instrumentable_pointer_array_address (*expr_p, &op0, &op1, +- &index_p, &index_n)) +- e = ubsan_instrument_bounds_pointer_address (EXPR_LOCATION (*expr_p), +- op0, &op1, +- ignore_off_by_one); +- +- /* Replace the original INDEX with the instrumented INDEX. */ ++ tree op0 = TREE_OPERAND (*expr_p, 0); ++ tree op1 = TREE_OPERAND (*expr_p, 1); ++ tree e = ubsan_instrument_bounds (EXPR_LOCATION (*expr_p), op0, &op1, ++ ignore_off_by_one); + if (e != NULL_TREE) +- TREE_OPERAND (index_p, index_n) +- = build2 (COMPOUND_EXPR, TREE_TYPE (op1), e, op1); ++ TREE_OPERAND (*expr_p, 1) = build2 (COMPOUND_EXPR, TREE_TYPE (op1), ++ e, op1); + } + } + +diff --git a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-2.c b/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-2.c +deleted file mode 100644 +index 0653eccff3e1..000000000000 +--- a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-2.c ++++ /dev/null +@@ -1,51 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in +- bounds sanitizer combined with VLA. */ +-/* { dg-do run } */ +-/* { dg-options "-fsanitize=bounds" } */ +-/* { dg-output "index 11 out of bounds for type 'int \\\[\\\*\\\]\\\[\\\*\\\]'\[^\n\r]*(\n|\r\n|\r)" } */ +-/* { dg-output "\[^\n\r]*index 20 out of bounds for type 'int \\\[\\\*\\\]\\\[\\\*\\\]\\\[\\\*\\\]'\[^\n\r]*(\n|\r\n|\r)" } */ +-/* { dg-output "\[^\n\r]*index 11 out of bounds for type 'int \\\[\\\*\\\]\\\[\\\*\\\]'\[^\n\r]*(\n|\r\n|\r)" } */ +-/* { dg-output "\[^\n\r]*index 10 out of bounds for type 'int \\\[\\\*\\\]'\[^\n\r]*(\n|\r\n|\r)" } */ +- +- +-#include <stdlib.h> +- +-void __attribute__((__noinline__)) setup_and_test_vla (int n, int m) +-{ +- struct foo { +- int n; +- int (*p)[n] __attribute__((counted_by(n))); +- } *f; +- +- f = (struct foo *) malloc (sizeof (struct foo)); +- f->p = (int (*)[n]) malloc (m * sizeof (int[n])); +- f->n = m; +- f->p[m][n-1] = 1; +- free (f->p); +- free (f); +- return; +-} +- +-void __attribute__((__noinline__)) setup_and_test_vla_1 (int n1, int n2, int m) +-{ +- struct foo { +- int n; +- int (*p)[n2][n1] __attribute__((counted_by(n))); +- } *f; +- +- f = (struct foo *) malloc (sizeof(struct foo)); +- f->p = (int (*)[n2][n1]) malloc (m * sizeof (int[n2][n1])); +- f->n = m; +- f->p[m][n2][n1] = 1; +- free (f->p); +- free (f); +- return; +-} +- +-int main(int argc, char *argv[]) +-{ +- setup_and_test_vla (10, 11); +- setup_and_test_vla_1 (10, 11, 20); +- return 0; +-} +- +diff --git a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-3.c b/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-3.c +deleted file mode 100644 +index 731422d7789a..000000000000 +--- a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-3.c ++++ /dev/null +@@ -1,42 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in bounds +- sanitizer. when counted_by field is negative value. */ +-/* { dg-do run } */ +-/* { dg-options "-fsanitize=bounds" } */ +- +-#include <stdlib.h> +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-} *array_annotated; +- +-void __attribute__((__noinline__)) setup (int annotated_count) +-{ +- array_annotated +- = (struct annotated *)malloc (sizeof (struct annotated)); +- array_annotated->c = (int *) malloc (sizeof (int) * 10); +- array_annotated->b = annotated_count; +- +- return; +-} +- +-void __attribute__((__noinline__)) test (int annotated_index) +-{ +- array_annotated->c[annotated_index] = 2; +-} +- +-void cleanup () +-{ +- free (array_annotated->c); +- free (array_annotated); +-} +- +-int main(int argc, char *argv[]) +-{ +- setup (-3); +- test (2); +- cleanup (); +- return 0; +-} +- +-/* { dg-output "25:21: runtime error: index 2 out of bounds for type" } */ +diff --git a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-4.c b/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-4.c +deleted file mode 100644 +index 52f202f51f9f..000000000000 +--- a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-4.c ++++ /dev/null +@@ -1,42 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in bounds +- sanitizer. when counted_by field is zero value. */ +-/* { dg-do run } */ +-/* { dg-options "-fsanitize=bounds" } */ +- +-#include <stdlib.h> +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-} *array_annotated; +- +-void __attribute__((__noinline__)) setup (int annotated_count) +-{ +- array_annotated +- = (struct annotated *)malloc (sizeof (struct annotated)); +- array_annotated->c = (int *)malloc (sizeof (int) * 10); +- array_annotated->b = annotated_count; +- +- return; +-} +- +-void __attribute__((__noinline__)) test (int annotated_index) +-{ +- array_annotated->c[annotated_index] = 2; +-} +- +-void cleanup () +-{ +- free (array_annotated->c); +- free (array_annotated); +-} +- +-int main(int argc, char *argv[]) +-{ +- setup (0); +- test (1); +- cleanup (); +- return 0; +-} +- +-/* { dg-output "25:21: runtime error: index 1 out of bounds for type" } */ +diff --git a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-5.c b/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-5.c +deleted file mode 100644 +index 8ad7572d1405..000000000000 +--- a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds-5.c ++++ /dev/null +@@ -1,40 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in +- bounds sanitizer. */ +-/* { dg-do run } */ +-/* { dg-options "-fsanitize=bounds" } */ +- +-#include <stdlib.h> +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-} *p_array_annotated; +- +-void __attribute__((__noinline__)) setup (int annotated_count) +-{ +- p_array_annotated +- = (struct annotated *)malloc (sizeof (struct annotated)); +- p_array_annotated->c = (int *) malloc (annotated_count * sizeof (int)); +- p_array_annotated->b = annotated_count; +- +- return; +-} +- +-void cleanup () +-{ +- free (p_array_annotated->c); +- free (p_array_annotated); +-} +- +-int main(int argc, char *argv[]) +-{ +- int i; +- setup (10); +- for (i = 0; i < 11; i++) +- p_array_annotated->c[i] = 2; // goes boom at i == 10 +- cleanup (); +- return 0; +-} +- +- +-/* { dg-output "34:25: runtime error: index 10 out of bounds for type" } */ +diff --git a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds.c b/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds.c +deleted file mode 100644 +index c5a1ac53be6d..000000000000 +--- a/gcc/testsuite/gcc.dg/ubsan/pointer-counted-by-bounds.c ++++ /dev/null +@@ -1,46 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in +- bounds sanitizer. */ +-/* { dg-do run } */ +-/* { dg-options "-fsanitize=bounds" } */ +- +-#include <stdlib.h> +- +-struct pointer_array { +- int b; +- int *c; +-} *p_array; +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-} *p_array_annotated; +- +-void __attribute__((__noinline__)) setup (int normal_count, int annotated_count) +-{ +- p_array +- = (struct pointer_array *) malloc (sizeof (struct pointer_array)); +- p_array->c = (int *) malloc (normal_count * sizeof (int)); +- p_array->b = normal_count; +- +- p_array_annotated +- = (struct annotated *) malloc (sizeof (struct annotated)); +- p_array_annotated->c = (int *) malloc (annotated_count * sizeof (int)); +- p_array_annotated->b = annotated_count; +- +- return; +-} +- +-void __attribute__((__noinline__)) test (int normal_index, int annotated_index) +-{ +- p_array->c[normal_index] = 1; +- p_array_annotated->c[annotated_index] = 2; +-} +- +-int main(int argc, char *argv[]) +-{ +- setup (10, 10); +- test (10, 10); +- return 0; +-} +- +-/* { dg-output "36:23: runtime error: index 10 out of bounds for type" } */ + +base-commit: b8a7d51253695febe6598069ccd89280b45d0abe +-- +2.50.0 + diff --git a/16.0.0/gentoo/86_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-b.patch b/16.0.0/gentoo/86_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-b.patch new file mode 100644 index 0000000..c704da9 --- /dev/null +++ b/16.0.0/gentoo/86_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-b.patch @@ -0,0 +1,382 @@ +https://gcc.gnu.org/PR120929 + +From 67769e431a764258ea3b3b983eae19089864fe62 Mon Sep 17 00:00:00 2001 +Message-ID: <67769e431a764258ea3b3b983eae19089864fe62.1751506033.git....@gentoo.org> +In-Reply-To: <75017c57b4f66552d02efda7e7d5eade1ba0ee80.1751506033.git....@gentoo.org> +References: <75017c57b4f66552d02efda7e7d5eade1ba0ee80.1751506033.git....@gentoo.org> +From: Sam James <[email protected]> +Date: Thu, 3 Jul 2025 02:27:06 +0100 +Subject: [PATCH 2/2] Revert "Use the counted_by attribute of pointers in + builtinin-object-size." + +This reverts commit 7165ca43caf47007f5ceaa46c034618d397d42ec. +--- + .../gcc.dg/pointer-counted-by-4-char.c | 6 -- + .../gcc.dg/pointer-counted-by-4-float.c | 6 -- + .../gcc.dg/pointer-counted-by-4-struct.c | 10 --- + .../gcc.dg/pointer-counted-by-4-union.c | 10 --- + gcc/testsuite/gcc.dg/pointer-counted-by-4.c | 77 ------------------- + gcc/testsuite/gcc.dg/pointer-counted-by-5.c | 56 -------------- + gcc/testsuite/gcc.dg/pointer-counted-by-6.c | 56 -------------- + gcc/testsuite/gcc.dg/pointer-counted-by-7.c | 32 -------- + gcc/tree-object-size.cc | 19 +---- + 9 files changed, 3 insertions(+), 269 deletions(-) + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-4-char.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-4-float.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-4-struct.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-4-union.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-4.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-5.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-6.c + delete mode 100644 gcc/testsuite/gcc.dg/pointer-counted-by-7.c + +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-4-char.c b/gcc/testsuite/gcc.dg/pointer-counted-by-4-char.c +deleted file mode 100644 +index c404e5b8ccec..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-4-char.c ++++ /dev/null +@@ -1,6 +0,0 @@ +-/* Test the attribute counted_by for pointer field and its usage in +- * __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +-#define PTR_TYPE char +-#include "pointer-counted-by-4.c" +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-4-float.c b/gcc/testsuite/gcc.dg/pointer-counted-by-4-float.c +deleted file mode 100644 +index 383d8fb656df..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-4-float.c ++++ /dev/null +@@ -1,6 +0,0 @@ +-/* Test the attribute counted_by for pointer field and its usage in +- * __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +-#define PTR_TYPE float +-#include "pointer-counted-by-4.c" +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-4-struct.c b/gcc/testsuite/gcc.dg/pointer-counted-by-4-struct.c +deleted file mode 100644 +index 50246d29477b..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-4-struct.c ++++ /dev/null +@@ -1,10 +0,0 @@ +-/* Test the attribute counted_by for pointer field and its usage in +- * __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +-struct A { +- int a; +- char *b; +-}; +-#define PTR_TYPE struct A +-#include "pointer-counted-by-4.c" +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-4-union.c b/gcc/testsuite/gcc.dg/pointer-counted-by-4-union.c +deleted file mode 100644 +index e786d9961475..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-4-union.c ++++ /dev/null +@@ -1,10 +0,0 @@ +-/* Test the attribute counted_by for pointer field and its usage in +- * __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +-union A { +- int a; +- float b; +-}; +-#define PTR_TYPE union A +-#include "pointer-counted-by-4.c" +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-4.c b/gcc/testsuite/gcc.dg/pointer-counted-by-4.c +deleted file mode 100644 +index c4b36311c704..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-4.c ++++ /dev/null +@@ -1,77 +0,0 @@ +-/* Test the attribute counted_by for pointer field and its usage in +- * __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +- +-#include "builtin-object-size-common.h" +-#ifndef PTR_TYPE +-#define PTR_TYPE int +-#endif +-struct pointer_array { +- int b; +- PTR_TYPE *c; +-} *p_array; +- +-struct annotated { +- PTR_TYPE *c __attribute__ ((counted_by (b))); +- int b; +-} *p_array_annotated; +- +-struct nested_annotated { +- PTR_TYPE *c __attribute__ ((counted_by (b))); +- struct { +- union { +- int b; +- float f; +- }; +- int n; +- }; +-} *p_array_nested_annotated; +- +-void __attribute__((__noinline__)) setup (int normal_count, int attr_count) +-{ +- p_array +- = (struct pointer_array *) malloc (sizeof (struct pointer_array)); +- p_array->c = (PTR_TYPE *) malloc (sizeof (PTR_TYPE) * normal_count); +- p_array->b = normal_count; +- +- p_array_annotated +- = (struct annotated *) malloc (sizeof (struct annotated)); +- p_array_annotated->c = (PTR_TYPE *) malloc (sizeof (PTR_TYPE) * attr_count); +- p_array_annotated->b = attr_count; +- +- p_array_nested_annotated +- = (struct nested_annotated *) malloc (sizeof (struct nested_annotated)); +- p_array_nested_annotated->c = (PTR_TYPE *) malloc (sizeof (PTR_TYPE) * attr_count); +- p_array_nested_annotated->b = attr_count; +- +- return; +-} +- +-void __attribute__((__noinline__)) test () +-{ +- EXPECT(__builtin_dynamic_object_size(p_array->c, 1), -1); +- EXPECT(__builtin_dynamic_object_size(p_array_annotated->c, 1), +- p_array_annotated->b * sizeof (PTR_TYPE)); +- EXPECT(__builtin_dynamic_object_size(p_array_nested_annotated->c, 1), +- p_array_nested_annotated->b * sizeof (PTR_TYPE)); +-} +- +-void cleanup () +-{ +- free (p_array->c); +- free (p_array); +- free (p_array_annotated->c); +- free (p_array_annotated); +- free (p_array_nested_annotated->c); +- free (p_array_nested_annotated); +-} +- +-int main(int argc, char *argv[]) +-{ +- setup (10,10); +- test (); +- DONE (); +- cleanup (); +- return 0; +-} +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-5.c b/gcc/testsuite/gcc.dg/pointer-counted-by-5.c +deleted file mode 100644 +index b43ffdf4df9f..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-5.c ++++ /dev/null +@@ -1,56 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in +- * __builtin_dynamic_object_size: when the counted_by field is negative. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +- +-#include "builtin-object-size-common.h" +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-} *array_annotated; +- +-struct nested_annotated { +- int *c __attribute__ ((counted_by (b))); +- struct { +- union { +- int b; +- float f; +- }; +- int n; +- }; +-} *array_nested_annotated; +- +-void __attribute__((__noinline__)) setup (int attr_count) +-{ +- array_annotated +- = (struct annotated *)malloc (sizeof (struct annotated)); +- array_annotated->b = attr_count; +- +- array_nested_annotated +- = (struct nested_annotated *)malloc (sizeof (struct nested_annotated)); +- array_nested_annotated->b = attr_count - 1; +- +- return; +-} +- +-void __attribute__((__noinline__)) test () +-{ +- EXPECT(__builtin_dynamic_object_size(array_annotated->c, 1), 0); +- EXPECT(__builtin_dynamic_object_size(array_nested_annotated->c, 1), 0); +-} +- +-void cleanup () +-{ +- free (array_annotated); +- free (array_nested_annotated); +-} +- +-int main(int argc, char *argv[]) +-{ +- setup (-10); +- test (); +- DONE (); +- cleanup (); +- return 0; +-} +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-6.c b/gcc/testsuite/gcc.dg/pointer-counted-by-6.c +deleted file mode 100644 +index 355558cd161d..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-6.c ++++ /dev/null +@@ -1,56 +0,0 @@ +-/* Test the attribute counted_by for pointer fields and its usage in +- * __builtin_dynamic_object_size: when the type of the pointer +- * is casting to another type. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +- +-#include "builtin-object-size-common.h" +- +-typedef unsigned short u16; +- +-struct info { +- u16 data_len; +- char *data __attribute__((counted_by(data_len))); +-}; +- +-struct foo { +- int a; +- int b; +-}; +- +-static __attribute__((__noinline__)) +-struct info *setup () +-{ +- struct info *p; +- size_t bytes = 3 * sizeof(struct foo); +- +- p = (struct info *) malloc (sizeof (struct info)); +- p->data = (char *) malloc (bytes); +- p->data_len = bytes; +- +- return p; +-} +- +-static void +-__attribute__((__noinline__)) report (struct info *p) +-{ +- struct foo *bar = (struct foo *)p->data; +- EXPECT(__builtin_dynamic_object_size((char *)(bar + 1), 1), +- sizeof (struct foo) * 2); +- EXPECT(__builtin_dynamic_object_size((char *)(bar + 2), 1), +- sizeof (struct foo)); +-} +- +-void cleanup (struct info *p) +-{ +- free (p->data); +- free (p); +-} +- +-int main(int argc, char *argv[]) +-{ +- struct info *p = setup(); +- report(p); +- cleanup (p); +- return 0; +-} +diff --git a/gcc/testsuite/gcc.dg/pointer-counted-by-7.c b/gcc/testsuite/gcc.dg/pointer-counted-by-7.c +deleted file mode 100644 +index af1ab2794007..000000000000 +--- a/gcc/testsuite/gcc.dg/pointer-counted-by-7.c ++++ /dev/null +@@ -1,32 +0,0 @@ +-/* Additional test of the attribute counted_by for pointer field and its usage +- in __builtin_dynamic_object_size. */ +-/* { dg-do run } */ +-/* { dg-options "-O2" } */ +- +-#include "builtin-object-size-common.h" +- +-struct annotated { +- int b; +- int *c __attribute__ ((counted_by (b))); +-}; +- +-struct annotated __attribute__((__noinline__)) setup (int attr_count) +-{ +- struct annotated p_array_annotated; +- p_array_annotated.c = (int *) malloc (sizeof (int) * attr_count); +- p_array_annotated.b = attr_count; +- +- return p_array_annotated; +-} +- +-int main(int argc, char *argv[]) +-{ +- struct annotated x = setup (10); +- int *p = x.c; +- x = setup (20); +- EXPECT(__builtin_dynamic_object_size (p, 1), 10 * sizeof (int)); +- EXPECT(__builtin_dynamic_object_size (x.c, 1), 20 * sizeof (int)); +- free (p); +- free (x.c); +- DONE (); +-} +diff --git a/gcc/tree-object-size.cc b/gcc/tree-object-size.cc +index ec4419fbab1d..f348673ae758 100644 +--- a/gcc/tree-object-size.cc ++++ b/gcc/tree-object-size.cc +@@ -773,12 +773,10 @@ addr_object_size (struct object_size_info *osi, const_tree ptr, + 4th argument TYPE_OF_SIZE: A constant 0 with its TYPE being the same as the TYPE + of the object referenced by REF_TO_SIZE + 6th argument: A constant 0 with the pointer TYPE to the original flexible +- array type or pointer field type. ++ array type. + + The size of the element can be retrived from the TYPE of the 6th argument +- of the call, which is the pointer to the original flexible array type or +- the type of the original pointer field. */ +- ++ of the call, which is the pointer to the array type. */ + static tree + access_with_size_object_size (const gcall *call, int object_size_type) + { +@@ -788,7 +786,7 @@ access_with_size_object_size (const gcall *call, int object_size_type) + + gcc_assert (gimple_call_internal_p (call, IFN_ACCESS_WITH_SIZE)); + /* The type of the 6th argument type is the pointer TYPE to the original +- flexible array type or to the original pointer type. */ ++ flexible array type. */ + tree pointer_to_array_type = TREE_TYPE (gimple_call_arg (call, 5)); + gcc_assert (POINTER_TYPE_P (pointer_to_array_type)); + tree element_type = TREE_TYPE (TREE_TYPE (pointer_to_array_type)); +@@ -1856,17 +1854,6 @@ collect_object_sizes_for (struct object_size_info *osi, tree var) + if (TREE_CODE (rhs) == SSA_NAME + && POINTER_TYPE_P (TREE_TYPE (rhs))) + reexamine = merge_object_sizes (osi, var, rhs); +- /* Handle the following stmt #2 to propagate the size from the +- stmt #1 to #3: +- 1 _1 = .ACCESS_WITH_SIZE (_3, _4, 1, 0, -1, 0B); +- 2 _5 = *_1; +- 3 _6 = __builtin_dynamic_object_size (_5, 1); +- */ +- else if (TREE_CODE (rhs) == MEM_REF +- && POINTER_TYPE_P (TREE_TYPE (rhs)) +- && TREE_CODE (TREE_OPERAND (rhs, 0)) == SSA_NAME +- && integer_zerop (TREE_OPERAND (rhs, 1))) +- reexamine = merge_object_sizes (osi, var, TREE_OPERAND (rhs, 0)); + else + expr_object_size (osi, var, rhs); + } +-- +2.50.0 + diff --git a/16.0.0/gentoo/README.history b/16.0.0/gentoo/README.history index 5bf2e2f..4fcaa04 100644 --- a/16.0.0/gentoo/README.history +++ b/16.0.0/gentoo/README.history @@ -1,6 +1,8 @@ 5 ???? - 85_all_PR120840.patch + + 85_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-a.patch + + 86_all_PR120929-Revert-Use-the-counted_by-attribute-of-pointers-in-b.patch 4 30 June 2025
