[LLVMdev] Problem with cross class joins in the RegisterCoalescer

Patrik Hägglund patrik.h.hagglund at ericsson.com
Thu Jan 19 02:16:56 PST 2012


Hi,

Is it intended that in some cases it is necessary to use
"-disable-cross-class-join" to be sure the resulting code is ok?

I have several cases where cross class joins are carried out that makes
the code turn out illegal, because the "new" register class is not
allowed in all instructions where it is now used.

For example, by joining %vreg4, %vreg7 and %vreg9 the following code

      %vreg7<def> = COPY %vreg4:lo16; aNl_0_7:%vreg7 aN32_0_7:%vreg4
      %vreg9<def> = COPY %vreg7; rN:%vreg9 aNl_0_7:%vreg7
      %vreg17<def> = load %vreg9<kill>; aN40_0_7:%vreg17 rN:%vreg9

is turned into

      %vreg17<def> = load %vreg4:lo16<kill>; aN40_0_7:%vreg17 
aN32_0_7:%vreg4

The load instruction however, can only use registers from the rN class,
but the coalescer has changed so it now uses the lo16 part of a aN32
register (which it cannot).

Moves can be carried out from a aN32:lo16 part to an rN register, but
aN32:lo16 and rN cannot be replaced with eachother in all instructions.

The "-disable-cross-class-join" flag prevents this problem from
happening but I'm afraid it will also prevent other (non-problematic)
cross class joins from happening so I'm hesitant to use it.

So, should this not happen, or is the flag needed, or is this just a
sign that we have a really weird or buggy register model?



More information about the llvm-dev mailing list