[v2,4/4] tree-object-size: Fall back to wholesize for non-const offset
Checks
Context |
Check |
Description |
linaro-tcwg-bot/tcwg_gcc_build--master-arm |
success
|
Build passed
|
linaro-tcwg-bot/tcwg_gcc_check--master-arm |
success
|
Test passed
|
linaro-tcwg-bot/tcwg_gcc_build--master-aarch64 |
success
|
Build passed
|
linaro-tcwg-bot/tcwg_gcc_check--master-aarch64 |
success
|
Test passed
|
Commit Message
Don't bail out early if the offset to a pointer in __builtin_object_size
is a variable, return the wholesize instead since that is a better
fallback for maximum estimate. This should keep checks in place for
fortified functions to constrain overflows to at lesat some extent.
gcc/ChangeLog:
PR middle-end/77608
* tree-object-size.cc (plus_stmt_object_size): Drop check for
constant offset.
* testsuite/gcc.dg/builtin-object-size-1.c (test14): New test.
Signed-off-by: Siddhesh Poyarekar <siddhesh@gotplt.org>
---
gcc/testsuite/gcc.dg/builtin-object-size-1.c | 19 +++++++++++++++++++
gcc/tree-object-size.cc | 7 ++++---
2 files changed, 23 insertions(+), 3 deletions(-)
Comments
On Fri, Sep 20, 2024 at 12:40:29PM -0400, Siddhesh Poyarekar wrote:
> Don't bail out early if the offset to a pointer in __builtin_object_size
> is a variable, return the wholesize instead since that is a better
> fallback for maximum estimate. This should keep checks in place for
> fortified functions to constrain overflows to at lesat some extent.
>
> gcc/ChangeLog:
>
> PR middle-end/77608
> * tree-object-size.cc (plus_stmt_object_size): Drop check for
> constant offset.
> * testsuite/gcc.dg/builtin-object-size-1.c (test14): New test.
>
> Signed-off-by: Siddhesh Poyarekar <siddhesh@gotplt.org>
> ---
> gcc/testsuite/gcc.dg/builtin-object-size-1.c | 19 +++++++++++++++++++
> gcc/tree-object-size.cc | 7 ++++---
> 2 files changed, 23 insertions(+), 3 deletions(-)
>
> diff --git a/gcc/testsuite/gcc.dg/builtin-object-size-1.c b/gcc/testsuite/gcc.dg/builtin-object-size-1.c
> index 6ffe12be683..5a24087ae1e 100644
> --- a/gcc/testsuite/gcc.dg/builtin-object-size-1.c
> +++ b/gcc/testsuite/gcc.dg/builtin-object-size-1.c
> @@ -791,6 +791,25 @@ test13 (unsigned cond)
> #endif
> }
>
> +void
> +__attribute__ ((noinline))
> +test14 (unsigned off)
> +{
> + char *buf2 = malloc (10);
> + char *p;
> + size_t t;
> +
> + p = &buf2[off];
> +
> +#ifdef __builtin_object_size
> + if (__builtin_object_size (p, 0) != 10 - off)
> + FAIL ();
> +#else
> + if (__builtin_object_size (p, 0) != 10)
> + FAIL ();
> +#endif
> +}
> +
> int
> main (void)
> {
> diff --git a/gcc/tree-object-size.cc b/gcc/tree-object-size.cc
> index 1b569c3d12b..ebd2a4650aa 100644
> --- a/gcc/tree-object-size.cc
> +++ b/gcc/tree-object-size.cc
> @@ -1595,8 +1595,7 @@ plus_stmt_object_size (struct object_size_info *osi, tree var, gimple *stmt)
> op1 = try_collapsing_offset (op1, NULL_TREE, NOP_EXPR, object_size_type);
>
> /* Handle PTR + OFFSET here. */
> - if (size_valid_p (op1, object_size_type)
> - && (TREE_CODE (op0) == SSA_NAME || TREE_CODE (op0) == ADDR_EXPR))
> + if ((TREE_CODE (op0) == SSA_NAME || TREE_CODE (op0) == ADDR_EXPR))
> {
> if (TREE_CODE (op0) == SSA_NAME)
> {
> @@ -1621,7 +1620,9 @@ plus_stmt_object_size (struct object_size_info *osi, tree var, gimple *stmt)
> if (size_unknown_p (bytes, 0))
> ;
> else if ((object_size_type & OST_DYNAMIC)
> - || bytes != wholesize || compare_tree_int (op1, offset_limit) <= 0)
> + || bytes != wholesize
> + || (size_valid_p (op1, object_size_type)
> + && compare_tree_int (op1, offset_limit) <= 0))
> bytes = size_for_offset (bytes, op1, wholesize);
> /* In the static case, with a negative offset, the best estimate for
> minimum size is size_unknown but for maximum size, the wholesize is a
LGTM.
Jakub
@@ -791,6 +791,25 @@ test13 (unsigned cond)
#endif
}
+void
+__attribute__ ((noinline))
+test14 (unsigned off)
+{
+ char *buf2 = malloc (10);
+ char *p;
+ size_t t;
+
+ p = &buf2[off];
+
+#ifdef __builtin_object_size
+ if (__builtin_object_size (p, 0) != 10 - off)
+ FAIL ();
+#else
+ if (__builtin_object_size (p, 0) != 10)
+ FAIL ();
+#endif
+}
+
int
main (void)
{
@@ -1595,8 +1595,7 @@ plus_stmt_object_size (struct object_size_info *osi, tree var, gimple *stmt)
op1 = try_collapsing_offset (op1, NULL_TREE, NOP_EXPR, object_size_type);
/* Handle PTR + OFFSET here. */
- if (size_valid_p (op1, object_size_type)
- && (TREE_CODE (op0) == SSA_NAME || TREE_CODE (op0) == ADDR_EXPR))
+ if ((TREE_CODE (op0) == SSA_NAME || TREE_CODE (op0) == ADDR_EXPR))
{
if (TREE_CODE (op0) == SSA_NAME)
{
@@ -1621,7 +1620,9 @@ plus_stmt_object_size (struct object_size_info *osi, tree var, gimple *stmt)
if (size_unknown_p (bytes, 0))
;
else if ((object_size_type & OST_DYNAMIC)
- || bytes != wholesize || compare_tree_int (op1, offset_limit) <= 0)
+ || bytes != wholesize
+ || (size_valid_p (op1, object_size_type)
+ && compare_tree_int (op1, offset_limit) <= 0))
bytes = size_for_offset (bytes, op1, wholesize);
/* In the static case, with a negative offset, the best estimate for
minimum size is size_unknown but for maximum size, the wholesize is a