https://gcc.gnu.org/bugzilla/show_bug.cgi?id=127688

            Bug ID: 127688
           Summary: -fcompare-debug failure when DEBUG_INSN changes
                    selective-scheduling issue-group markers
           Product: gcc
           Version: 17.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: rtl-optimization
          Assignee: unassigned at gcc dot gnu.org
          Reporter: yqtian668 at gmail dot com
  Target Milestone: ---

Created attachment 65734
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=65734&action=edit
input 1

GCC fails its `-fcompare-debug` check for two existing GCC tests when the
second scheduling pass uses selective scheduling.  Both failures have the
same cause: a `DEBUG_INSN` changes which ordinary instructions receive the
`TImode` marker for the beginning of an issue group.

Tested revision:

```text
fc79df73ccd91f677c5990a3dadd83e2620404f9
gcc version 17.0.0 20260826 (experimental) (GCC)
```

The build was configured with:

```text
--target=x86_64-pc-linux-gnu --disable-bootstrap --enable-languages=c
--disable-multilib --disable-nls --disable-werror --enable-checking=yes
```

The smaller reproducer is the attached `gcc.dg/pr85423.c`:

```sh
xgcc -B/path/to/gcc -O2 -fselective-scheduling2 \
  -fvar-tracking-assignments -fno-guess-branch-probability \
  -fno-peephole2 -fno-ssa-phiopt -fno-tree-pre \
  --param=max-jump-thread-duplication-stmts=8 -march=nano -w \
  -fcompare-debug -c pr85423.c -o pr85423.o
```

Actual result:

```text
xgcc: error: pr85423.c: '-fcompare-debug' failure (length)
```

The attached `gcc.dg/pr80463.c` independently triggers the same failure and
root cause with its original options:

```sh
xgcc -B/path/to/gcc -g -O2 -fvar-tracking-assignments \
  -fselective-scheduling2 -ftree-loop-vectorize \
  -fnon-call-exceptions -fno-tree-vrp -fno-gcse-lm \
  -fno-tree-loop-im -fno-reorder-blocks-and-partition \
  -fno-reorder-blocks -fno-move-loop-invariants -w \
  -fcompare-debug -c pr80463.c -o pr80463.o
```

For `pr85423.c`, the x86-64 `.text` section is byte-identical between `-g0`
and `-g`.  The final RTL is not identical: three ordinary instructions lose
their `:TI` mode in the debug compilation.  One representative difference is:

```diff
-(insn/f:TI ...
+(insn/f ...
```

The complete final-insns difference is attached.  GCC documents in
`gcc/doc/rtl.texi` that the second Haifa scheduling pass sets an instruction
to `TImode` when it begins an issue group, and that later passes, especially
machine-dependent reorg, may rely on that marker.

The apparent cause is `put_TImodes()` in `gcc/sel-sched.cc`.  Its loop skips
non-insn RTL but does not skip debug instructions:

```c++
if (!INSN_P (insn))
  continue;

clock = INSN_SCHED_CYCLE (insn);
cost = (last_clock == -1) ? 1 : clock - last_clock;
...
last_clock = clock;
```

`DEBUG_INSN` satisfies `INSN_P`.  A debug instruction can therefore update
`last_clock` for a new scheduling cycle.  The following ordinary instruction
then has zero computed cost and does not receive the `TImode` marker that it
receives without debug information.

As a causal check, changing the membership test to

```c++
if (!INSN_P (insn) || DEBUG_INSN_P (insn))
  continue;
```

makes both reproducers pass `-fcompare-debug`.  For each reproducer, the
patched `-g0` `.text` is byte-identical to the unmodified `-g0` `.text`, and
the patched `-g` and `-g0` `.text` sections are byte-identical.

The diagnostic change is attached to document the causal check; it is not
intended to prescribe the final patch or its regression test.

The same `put_TImodes()` loop is still present in GCC master revision
`2e70e94cef1d76dbb3202d64184a7a8329c92f4e` by source inspection.  The
execution results above are from the tested revision `fc79df73ccd9`.

Expected result: non-executable debug instructions should not consume an
issue-cycle transition or change issue-group markers on ordinary
instructions.

Reply via email to