[RFC] TableGen help for relaxation

Hello LLVM,

My target has a complex relaxation hierarchy. Perhaps a modest
TableGen extension would help consolidate most of the work involved in
choosing a relaxed opcode. I also notice the x86 relaxation code with
a comment wondering if TableGen could improve life.

Does the following outline sound interesting?

1) Add a new field of type 'Instruction' to the Instruction class
called "RelaxedInstr"

2) Target instructions optionally set RelaxedInstr, as in:

def JMP32 : Instruction<stuff>; // no relaxation from here
def JMP8 : Instruction<stuff> {
      let RelaxedInstr = JMP32; // relax to 32-bit jmp
}

3) The tblgen -gen-instr-info processor uses RelaxedInstruction to
create the RelaxedOpcode field for the corresponding MCInst. The
RelaxedOpcode field contains the target specific opcode (an
enumeration value) of the specified RelaxedInstr.

4) From C++, targets access the RelaxedOpcode field as needed, akin to
TSFlags. This eliminates the headaches of massive opcode switch
statements in targets like mine.

It's unclear to me how to handle the default value of an 'Instruction'
when no relaxation exists.

Regards,
-steve

It is possible to get the same result using tablegen instruction mappings.
http://llvm.org/docs/HowToUseInstrMappings.html

For Octasic's Opus architecture, we use instruction mappings extensively to
describe relation between instructions, including relaxed vs non-relaxed
jump opcode. Tablegen will generate the huge switch case automatically.

Francois Pichet
Octasic.

Hi Francois,
Thanks for the pointer. Unfortunately, I'm having trouble with this idea.

To implement getRelaxedOpcode InstrMapping, I need to search for some
specific property of the relaxed opcode. I'm not sure how to create
this searchable property without something grossly artificial. For
example, SystemZ does this:

// Return the memory form of a register instruction.
def getMemOpcode : InstrMapping {
  let FilterClass = "InstSystemZ";
  let RowFields = ["OpKey"];
  let ColFields = ["OpType"];
  let KeyCol = ["reg"];
  let ValueCols = [["mem"]];
}

in which they look for instructions with property OpType to be exactly
"mem" or "reg" with both instruction having the same OpKey. My
relaxation problem is a much more arbitrary progression from one
instruction to its relaxation. The underlying instructions don't
match nor do field sizes grow dependably.

Cheers,
-steve