SparcInstr.def: added 'r' and 'i' versions of MOV(F)cc instructions

SparcInstrSelection.cpp:
* Fixed opcodes to return correct 'i' version since the two functions are each
  only used in one place.
* Changed name of function to have an 'i' in the name to signify that they each
  return an immediate form of the opcode.
* Added a warning if either of the functions is ever used in a context which
  requires a register-version opcode.

SparcV9_F4.td: fixed class F4_3, added F4_4 and notes that F4_{1,2} need fixing
SparcV9.td: added the MOV(F)cc instructions

llvm-svn: 6548
This commit is contained in:
Misha Brukman 2003-06-02 20:55:14 +00:00
parent e837bd5b48
commit 6f65b13ed3
4 changed files with 193 additions and 85 deletions

@ -244,44 +244,76 @@ I(MOVRGEZ, "movrgez", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CONDL_FLAG | M_
// Conditional move on integer condition code.
// The first argument specifies the ICC register: %icc or %xcc
I(MOVA , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVN , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNE , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVE , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVG , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLE , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGE , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVL , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGU , "movgu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLEU, "movleu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCC , "movcc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCS , "movcs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVPOS, "movpos", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNEG, "movneg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVC , "movvc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVS , "movvs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVAr , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVAi , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNr , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNi , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNEr , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNEi , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVEr , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVEi , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGr , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGi , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLEr , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLEi , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGEr , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGEi , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLr , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLi , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGUr , "movgu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVGUi , "movgu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLEUr, "movleu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVLEUi, "movleu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCCr , "movcc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCCi , "movcc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCSr , "movcs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVCSi , "movcs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVPOSr, "movpos", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVPOSi, "movpos", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNEGr, "movneg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVNEGi, "movneg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVCr , "movvc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVCi , "movvc", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVSr , "movvs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVVSi , "movvs", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
// Conditional move (of integer register) on floating point condition code.
// The first argument is the FCCn register (0 <= n <= 3).
// Note that the enum name above is not the same as the assembly mnemonic
// because some of the assembly mnemonics are the same as the move on
// integer CC (e.g., MOVG), and we cannot have the same enum entry twice.
I(MOVFA , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFN , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFU , "movu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFG , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUG , "movug", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFL , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUL , "movul", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLG , "movlg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFNE , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFE , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUE , "movue", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFGE , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUGE, "movuge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLE , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFULE, "movule", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFO , "movo", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFAr , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFAi , "mova", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFNr , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFNi , "movn", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUr , "movu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUi , "movu", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFGr , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFGi , "movg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUGr , "movug", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUGi , "movug", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLr , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLi , "movl", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFULr , "movul", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFULi , "movul", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLGr , "movlg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLGi , "movlg", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFNEr , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFNEi , "movne", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFEr , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFEi , "move", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUEr , "movue", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUEi , "movue", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFGEr , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFGEi , "movge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUGEr, "movuge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFUGEi, "movuge", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLEr , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFLEi , "movle", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFULEr, "movule", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFULEi, "movule", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFOr , "movo", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
I(MOVFOi , "movo", 3, 2, B12, true , 0, 2, SPARC_SINGLE, M_CC_FLAG | M_INT_FLAG)
// Conditional move of floating point register on each of the above:
// i. on integer comparison with zero.

@ -402,19 +402,26 @@ ChooseBccInstruction(const InstructionNode* instrNode,
}
// WARNING: since this function has only one caller, it always returns
// the opcode that expects an immediate and a register. If this function
// is ever used in cases where an opcode that takes two registers is required,
// then modify this function and use convertOpcodeFromRegToImm() where required.
//
// It will be necessary to expand convertOpcodeFromRegToImm() to handle the
// new cases of opcodes.
static inline MachineOpCode
ChooseMovFpccInstruction(const InstructionNode* instrNode)
ChooseMovFpcciInstruction(const InstructionNode* instrNode)
{
MachineOpCode opCode = V9::INVALID_OPCODE;
switch(instrNode->getInstruction()->getOpcode())
{
case Instruction::SetEQ: opCode = V9::MOVFE; break;
case Instruction::SetNE: opCode = V9::MOVFNE; break;
case Instruction::SetLE: opCode = V9::MOVFLE; break;
case Instruction::SetGE: opCode = V9::MOVFGE; break;
case Instruction::SetLT: opCode = V9::MOVFL; break;
case Instruction::SetGT: opCode = V9::MOVFG; break;
case Instruction::SetEQ: opCode = V9::MOVFEi; break;
case Instruction::SetNE: opCode = V9::MOVFNEi; break;
case Instruction::SetLE: opCode = V9::MOVFLEi; break;
case Instruction::SetGE: opCode = V9::MOVFGEi; break;
case Instruction::SetLT: opCode = V9::MOVFLi; break;
case Instruction::SetGT: opCode = V9::MOVFGi; break;
default:
assert(0 && "Unrecognized VM instruction!");
break;
@ -432,19 +439,26 @@ ChooseMovFpccInstruction(const InstructionNode* instrNode)
// (i.e., we want to test inverse of a condition)
// (The latter two cases do not seem to arise because SetNE needs nothing.)
//
// WARNING: since this function has only one caller, it always returns
// the opcode that expects an immediate and a register. If this function
// is ever used in cases where an opcode that takes two registers is required,
// then modify this function and use convertOpcodeFromRegToImm() where required.
//
// It will be necessary to expand convertOpcodeFromRegToImm() to handle the
// new cases of opcodes.
static MachineOpCode
ChooseMovpccAfterSub(const InstructionNode* instrNode)
ChooseMovpcciAfterSub(const InstructionNode* instrNode)
{
MachineOpCode opCode = V9::INVALID_OPCODE;
switch(instrNode->getInstruction()->getOpcode())
{
case Instruction::SetEQ: opCode = V9::MOVE; break;
case Instruction::SetLE: opCode = V9::MOVLE; break;
case Instruction::SetGE: opCode = V9::MOVGE; break;
case Instruction::SetLT: opCode = V9::MOVL; break;
case Instruction::SetGT: opCode = V9::MOVG; break;
case Instruction::SetNE: opCode = V9::MOVNE; break;
case Instruction::SetEQ: opCode = V9::MOVEi; break;
case Instruction::SetLE: opCode = V9::MOVLEi; break;
case Instruction::SetGE: opCode = V9::MOVGEi; break;
case Instruction::SetLT: opCode = V9::MOVLi; break;
case Instruction::SetGT: opCode = V9::MOVGi; break;
case Instruction::SetNE: opCode = V9::MOVNEi; break;
default: assert(0 && "Unrecognized VM instr!"); break;
}
@ -2049,8 +2063,8 @@ GetInstructionsByRule(InstructionNode* subtreeRoot,
if (computeBoolVal) {
MachineOpCode movOpCode = (isFPCompare
? ChooseMovFpccInstruction(subtreeRoot)
: ChooseMovpccAfterSub(subtreeRoot));
? ChooseMovFpcciInstruction(subtreeRoot)
: ChooseMovpcciAfterSub(subtreeRoot));
// Unconditionally set register to 0
M = BuildMI(V9::SETHI, 2).addZImm(0).addRegDef(setCCInstr);

@ -381,42 +381,72 @@ def FMOVFO : F4_7<2, 0b110101, 0b1111, "fmovfo">; // fmovfo r, r
// Section A.35: Move Integer Register on Condition (MOVcc) - p194
// For integer condition codes
#if 0
def MOVA :
def MOVN :
def MOVNE :
def MOVE :
def MOVG :
def MOVLE :
def MOVGE :
def MOVL :
def MOVGU :
def MOVLEU :
def MOVCC :
def MOVCS :
def MOVPOS :
def MOVNEG :
def MOVVC :
def MOVVS :
def MOVAr : F4_3<2, 0b101100, 0b1000, "mova">; // mova i/xcc, rs2, rd
def MOVAi : F4_4<2, 0b101100, 0b1000, "mova">; // mova i/xcc, rs2, rd
def MOVNr : F4_3<2, 0b101100, 0b0000, "movn">; // mova i/xcc, rs2, rd
def MOVNi : F4_4<2, 0b101100, 0b0000, "movn">; // mova i/xcc, rs2, rd
def MOVNEr : F4_3<2, 0b101100, 0b1001, "movne">; // mova i/xcc, rs2, rd
def MOVNEi : F4_4<2, 0b101100, 0b1001, "movne">; // mova i/xcc, rs2, rd
def MOVEr : F4_3<2, 0b101100, 0b0001, "move">; // mova i/xcc, rs2, rd
def MOVEi : F4_4<2, 0b101100, 0b0001, "move">; // mova i/xcc, rs2, rd
def MOVGr : F4_3<2, 0b101100, 0b1010, "movg">; // mova i/xcc, rs2, rd
def MOVGi : F4_4<2, 0b101100, 0b1010, "movg">; // mova i/xcc, rs2, rd
def MOVLEr : F4_3<2, 0b101100, 0b0010, "movle">; // mova i/xcc, rs2, rd
def MOVLEi : F4_4<2, 0b101100, 0b0010, "movle">; // mova i/xcc, rs2, rd
def MOVGEr : F4_3<2, 0b101100, 0b1011, "movge">; // mova i/xcc, rs2, rd
def MOVGEi : F4_4<2, 0b101100, 0b1011, "movge">; // mova i/xcc, rs2, rd
def MOVLr : F4_3<2, 0b101100, 0b0011, "movl">; // mova i/xcc, rs2, rd
def MOVLi : F4_4<2, 0b101100, 0b0011, "movl">; // mova i/xcc, rs2, rd
def MOVGUr : F4_3<2, 0b101100, 0b1100, "movgu">; // mova i/xcc, rs2, rd
def MOVGUi : F4_4<2, 0b101100, 0b1100, "movgu">; // mova i/xcc, rs2, rd
def MOVLEUr : F4_3<2, 0b101100, 0b0100, "movleu">; // mova i/xcc, rs2, rd
def MOVLEUi : F4_4<2, 0b101100, 0b0100, "movleu">; // mova i/xcc, rs2, rd
def MOVCCr : F4_3<2, 0b101100, 0b1101, "movcc">; // mova i/xcc, rs2, rd
def MOVCCi : F4_4<2, 0b101100, 0b1101, "movcc">; // mova i/xcc, rs2, rd
def MOVCSr : F4_3<2, 0b101100, 0b0101, "movcs">; // mova i/xcc, rs2, rd
def MOVCSi : F4_4<2, 0b101100, 0b0101, "movcs">; // mova i/xcc, rs2, rd
def MOVPOSr : F4_3<2, 0b101100, 0b1110, "movpos">; // mova i/xcc, rs2, rd
def MOVPOSi : F4_4<2, 0b101100, 0b1110, "movpos">; // mova i/xcc, rs2, rd
def MOVNEGr : F4_3<2, 0b101100, 0b0110, "movneg">; // mova i/xcc, rs2, rd
def MOVNEGi : F4_4<2, 0b101100, 0b0110, "movneg">; // mova i/xcc, rs2, rd
def MOVVCr : F4_3<2, 0b101100, 0b1111, "movvc">; // mova i/xcc, rs2, rd
def MOVVCi : F4_4<2, 0b101100, 0b1111, "movvc">; // mova i/xcc, rs2, rd
def MOVVSr : F4_3<2, 0b101100, 0b0111, "movvs">; // mova i/xcc, rs2, rd
def MOVVSi : F4_4<2, 0b101100, 0b0111, "movvs">; // mova i/xcc, rs2, rd
// For floating-point condition codes
def MOVFA :
def MOVFN :
def MOVFU :
def MOVFG :
def MOVFUG :
def MOVFL :
def MOVFUL :
def MOVFLG :
def MOVFNE :
def MOVFE :
def MOVFUE :
def MOVFGE :
def MOVFUGE :
def MOVFLE :
def MOVFULE :
def MOVFO :
#endif
def MOVFAr : F4_3<2, 0b101100, 0b1000, "movfa">; // mova i/xcc, rs2, rd
def MOVFAi : F4_4<2, 0b101100, 0b1000, "movfa">; // mova i/xcc, rs2, rd
def MOVFNr : F4_3<2, 0b101100, 0b0000, "movfn">; // mova i/xcc, rs2, rd
def MOVFNi : F4_4<2, 0b101100, 0b0000, "movfn">; // mova i/xcc, rs2, rd
def MOVFUr : F4_3<2, 0b101100, 0b0111, "movfu">; // mova i/xcc, rs2, rd
def MOVFUi : F4_4<2, 0b101100, 0b0111, "movfu">; // mova i/xcc, rs2, rd
def MOVFGr : F4_3<2, 0b101100, 0b0110, "movfg">; // mova i/xcc, rs2, rd
def MOVFGi : F4_4<2, 0b101100, 0b0110, "movfg">; // mova i/xcc, rs2, rd
def MOVFUGr : F4_3<2, 0b101100, 0b0101, "movfug">; // mova i/xcc, rs2, rd
def MOVFUGi : F4_4<2, 0b101100, 0b0101, "movfug">; // mova i/xcc, rs2, rd
def MOVFLr : F4_3<2, 0b101100, 0b0100, "movfl">; // mova i/xcc, rs2, rd
def MOVFLi : F4_4<2, 0b101100, 0b0100, "movfl">; // mova i/xcc, rs2, rd
def MOVFULr : F4_3<2, 0b101100, 0b0011, "movful">; // mova i/xcc, rs2, rd
def MOVFULi : F4_4<2, 0b101100, 0b0011, "movful">; // mova i/xcc, rs2, rd
def MOVFLGr : F4_3<2, 0b101100, 0b0010, "movflg">; // mova i/xcc, rs2, rd
def MOVFLGi : F4_4<2, 0b101100, 0b0010, "movflg">; // mova i/xcc, rs2, rd
def MOVFNEr : F4_3<2, 0b101100, 0b0001, "movfne">; // mova i/xcc, rs2, rd
def MOVFNEi : F4_4<2, 0b101100, 0b0001, "movfne">; // mova i/xcc, rs2, rd
def MOVFEr : F4_3<2, 0b101100, 0b1001, "movfe">; // mova i/xcc, rs2, rd
def MOVFEi : F4_4<2, 0b101100, 0b1001, "movfe">; // mova i/xcc, rs2, rd
def MOVFUEr : F4_3<2, 0b101100, 0b1010, "movfue">; // mova i/xcc, rs2, rd
def MOVFUEi : F4_4<2, 0b101100, 0b1010, "movfue">; // mova i/xcc, rs2, rd
def MOVFGEr : F4_3<2, 0b101100, 0b1011, "movfge">; // mova i/xcc, rs2, rd
def MOVFGEi : F4_4<2, 0b101100, 0b1011, "movfge">; // mova i/xcc, rs2, rd
def MOVFUGEr : F4_3<2, 0b101100, 0b1100, "movfuge">; // mova i/xcc, rs2, rd
def MOVFUGEi : F4_4<2, 0b101100, 0b1100, "movfuge">; // mova i/xcc, rs2, rd
def MOVFLEr : F4_3<2, 0b101100, 0b1101, "movfle">; // mova i/xcc, rs2, rd
def MOVFLEi : F4_4<2, 0b101100, 0b1101, "movfle">; // mova i/xcc, rs2, rd
def MOVFULEr : F4_3<2, 0b101100, 0b1110, "movfule">; // mova i/xcc, rs2, rd
def MOVFULEi : F4_4<2, 0b101100, 0b1110, "movfule">; // mova i/xcc, rs2, rd
def MOVFOr : F4_3<2, 0b101100, 0b1111, "movfo">; // mova i/xcc, rs2, rd
def MOVFOi : F4_4<2, 0b101100, 0b1111, "movfo">; // mova i/xcc, rs2, rd
// FIXME: Section A.36: Move Integer Register on Register Condition (MOVR)

@ -53,8 +53,23 @@ class F4_rs1rs2 : F4_rs1 {
set Inst{4-0} = rs2;
}
// F4_cc - Common class of instructions that have a cond field
class F4_cond : F4 {
bits<4> cond;
set Inst{17-14} = cond;
}
// F4_cc - Common class of instructions that have cc register as first operand
class F4_condcc : F4_cond {
bits<3> cc;
set Inst{18} = cc{2};
set Inst{12} = cc{1};
set Inst{11} = cc{0};
}
// Actual F4 instruction classes
// FIXME: order of operands is incorrect!!
class F4_1<bits<2> opVal, bits<6> op3Val, string name> : F4_rdrs1rs2 {
bits<2> cc;
@ -66,6 +81,7 @@ class F4_1<bits<2> opVal, bits<6> op3Val, string name> : F4_rdrs1rs2 {
//set Inst{10-5} = dontcare;
}
// FIXME: order of operands is incorrect!!
class F4_2<bits<2> opVal, bits<6> op3Val, string name> : F4_rdsimm11rs1 {
bits<2> cc;
@ -76,15 +92,31 @@ class F4_2<bits<2> opVal, bits<6> op3Val, string name> : F4_rdsimm11rs1 {
set Inst{12-11} = cc;
}
class F4_3<bits<2> opVal, bits<6> op3Val, string name> : F3_rd {
class F4_3<bits<2> opVal, bits<6> op3Val, bits<4> condVal,
string name> : F4_condcc {
bits<5> rs2;
bits<2> cc;
set op = opVal;
set op3 = op3Val;
set cond = condVal;
set Name = name;
set Inst{13} = 0; // i bit
set Inst{12-11} = cc;
//set Inst{10-5} = dontcare;
set Inst{4-0} = rs2;
}
class F4_4<bits<2> opVal, bits<6> op3Val, bits<4> condVal,
string name> : F4_condcc {
bits<11> sim11;
bits<5> rd;
set op = opVal;
set op3 = op3Val;
set cond = condVal;
set Name = name;
set Inst{13} = 1; // i bit
set Inst{10-0} = sim11;
}
// FIXME: F4 classes 4