On 1/10/2026 9:11 AM, Stefan Schulze Frielinghaus wrote:
From: Stefan Schulze Frielinghaus <[email protected]>

This fixes

t.c:17:3: error: 'asm' operand has impossible constraints or there are not 
enough registers
    17 |   __asm__ ("" : "=f" (a), "={fr2}" (e) : "{fr1}" (d));
       |   ^~~~~~~

on powerpc64le-unknown-linux-gnu for the attached test.  Prior cse1 we have

(insn 2 4 3 2 (set (reg/v:TF 120 [ c ])
         (reg:TF 33 1 [ c ])) "t.c":14:26 614 {*movtf_64bit_dm}
      (nil))
...
(insn 10 9 6 2 (parallel [
             (set (reg:DF 121)
                 (asm_operands:DF ("") ("=f") 0 [
                         (reg:TF 124)
                     ]
                      [
                         (asm_input:TF ("{fr1}") t.c:17)
                     ]
                      [] t.c:17))
             (set (reg:DF 123 [ e ])
                 (asm_operands:DF ("") ("={fr2}") 1 [
                         (reg:TF 124)
                     ]
                      [
                         (asm_input:TF ("{fr1}") t.c:17)
                     ]
                      [] t.c:17))
             (clobber (reg:SI 98 ca))
         ]) "t.c":17:3 -1
      (nil))
...
(insn 12 11 13 2 (set (reg:TF 33 1)
             (reg/v:TF 120 [ c ])) "t.c":18:12 614 {*movtf_64bit_dm}
      (nil))

During cse1, in insn 12 pseudo 120 is substituted with hard register 33
rendering the resulting insn trivial which is why the insn gets removed
afterwards.  Since hard register 33 has a use after insn 12, the
register is live before and after insn 10.  This leaves us with the
non-trivial problem, during LRA, to also assign hard register 33 to
pseudo 124 which is coming from the constraint of insn 10.  Since hard
registers are not tracked, except for liveness, this cannot be solved by
reloads which is why we end up with an error.

Therefore, treat single register constraints as clobbers of the
respective hard registers.  This includes constraints associated a
single register class as well as hard register constraints.

gcc/ChangeLog:

        * cse.cc (invalidate_from_sets_and_clobbers): Consider any hard
        register referred to by any single register constraint
        potentially being clobbered.

gcc/testsuite/ChangeLog:

        * gcc.target/powerpc/asm-hard-reg-2.c: New test.
Can we really get at the register classes while in CSE?   That's a bit of a surprise.  My recollection is these kinds of cases a handled by the likely-spilled hooks.   Look in hash_rtx, where that code is lying around.

Jeff


jeff

Reply via email to