Avoid using POINTER_DIFF_EXPR for overlap checks [PR119399]

In r10-4803-g8489e1f45b50600c I'd used POINTER_DIFF_EXPR to subtract
the two pointers involved in an overlap test.  I'm not sure whether
I'd specifically chosen that over MINUS_EXPR or not; if so, the only
reason I can think of is that it is probably faster on targets with
PSImode pointers.  Regardless, as the PR points out, subtracting
unrelated pointers using POINTER_DIFF_EXPR is undefined behaviour.

gcc/
	PR tree-optimization/119399
	* tree-data-ref.cc (create_waw_or_war_checks): Use a MINUS_EXPR
	on two converted pointers, rather than converting a POINTER_DIFF_EXPR
	on the pointers.

gcc/testsuite/
	PR tree-optimization/119399
	* gcc.dg/vect/pr119399.c: New test.
This commit is contained in:
Richard Sandiford 2025-04-10 11:03:04 +01:00
parent 72dff34bcd
commit 4c8c373495
2 changed files with 14 additions and 3 deletions

View file

@ -0,0 +1,10 @@
/* { dg-do compile } */
/* { dg-additional-options "-fdump-tree-vect-raw" } */
void foo(int *p, int *q, int n)
{
for (int i = 0; i < n; i++)
p[i] = q[i] + 1;
}
/* { dg-final { scan-tree-dump-not {<pointer_diff_expr,} "vect" } } */

View file

@ -2498,9 +2498,10 @@ create_waw_or_war_checks (tree *cond_expr,
limit = fold_build2 (PLUS_EXPR, sizetype, limit,
size_int (last_chunk_a + last_chunk_b));
tree subject = fold_build2 (POINTER_DIFF_EXPR, ssizetype, addr_b, addr_a);
subject = fold_build2 (PLUS_EXPR, sizetype,
fold_convert (sizetype, subject), bias);
tree subject = fold_build2 (MINUS_EXPR, sizetype,
fold_convert (sizetype, addr_b),
fold_convert (sizetype, addr_a));
subject = fold_build2 (PLUS_EXPR, sizetype, subject, bias);
*cond_expr = fold_build2 (GT_EXPR, boolean_type_node, subject, limit);
if (dump_enabled_p ())