https://gcc.gnu.org/g:55e9aef65b2d3705089c2de601867aa6e7cc261d
commit r17-4404-g55e9aef65b2d3705089c2de601867aa6e7cc261d Author: Yongqiang Tian <[email protected]> Date: Wed Sep 16 22:17:21 2026 +1000 combine: Ignore debug insns in volatile checks [PR127422] A DEBUG_INSN can retain a volatile MEM after the corresponding ordinary instruction has been deleted. Do not treat that non-executing payload as an intervening volatile access in can_combine_p. Assisted-by: OpenAI Codex 5.6 Sol, co-reviewed by Claude and Yongqiang Tian. PR rtl-optimization/127422 gcc/ChangeLog: * combine.cc (can_combine_p): Ignore debug instructions when scanning for intervening volatile references. gcc/testsuite/ChangeLog: * gcc.dg/pr127422.c: New test. Signed-off-by: Yongqiang Tian <[email protected]> Diff: --- gcc/combine.cc | 5 ++++- gcc/testsuite/gcc.dg/pr127422.c | 35 +++++++++++++++++++++++++++++++++++ 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/gcc/combine.cc b/gcc/combine.cc index 35c6a5299507..11427f5a9204 100644 --- a/gcc/combine.cc +++ b/gcc/combine.cc @@ -2024,7 +2024,10 @@ can_combine_p (rtx_insn *insn, rtx_insn *i3, rtx_insn *pred ATTRIBUTE_UNUSED, : volatile_insn_p; for (p = NEXT_INSN (insn); p != i3; p = NEXT_INSN (p)) - if (INSN_P (p) && p != succ && p != succ2 && is_volatile_p (PATTERN (p))) + if (NONDEBUG_INSN_P (p) + && p != succ + && p != succ2 + && is_volatile_p (PATTERN (p))) return false; /* If INSN contains an autoincrement or autodecrement, make sure that diff --git a/gcc/testsuite/gcc.dg/pr127422.c b/gcc/testsuite/gcc.dg/pr127422.c new file mode 100644 index 000000000000..bba30ad78449 --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr127422.c @@ -0,0 +1,35 @@ +/* PR rtl-optimization/127422 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -fcompare-debug" } */ + +static int ordinary_0 = 3; +static int ordinary_1 = 22; +static volatile int effect_0 = 6; +static volatile int effect_1 = 23; +static int ordinary_2 = 41; +__attribute__ ((used)) int *ordinary_escape[] + = { &ordinary_0, &ordinary_1, &ordinary_2 }; + +static inline __attribute__ ((always_inline)) +unsigned long long +accumulate (unsigned long long acc, unsigned long long val) +{ + return acc + val; +} + +unsigned long long +foo (void) +{ + int staged_ordinary_0 = ordinary_0; + int staged_ordinary_1 = ordinary_1; + int staged_effect_0 = effect_0; + int staged_effect_1 = effect_1; + int staged_ordinary_2 = ordinary_2; + unsigned long long sum = 0; + sum = accumulate (sum, staged_ordinary_0); + sum = accumulate (sum, staged_ordinary_1); + sum = accumulate (sum, staged_effect_0); + sum = accumulate (sum, staged_effect_1); + sum = accumulate (sum, staged_ordinary_2); + return sum; +}
