Mips specific inline asm operand modifier 'M':

Print the high order register of a double word register operand.

In 32 bit mode, a 64 bit double word integer will be represented
by 2 32 bit registers. This modifier causes the high order register
to be used in the asm expression. It is useful if you are using 
doubles in assembler and continue to control register to variable
relationships.

This patch also fixes a related bug in a previous patch:

    case 'D': // Second part of a double word register operand
    case 'L': // Low order register of a double word register operand
    case 'M': // High order register of a double word register operand

I got 'D' and 'M' confused. The second part of a double word operand
will only match 'M' for one of the endianesses. I had 'L' and 'D'
be the opposite twins when 'L' and 'M' are.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@160429 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Jack Carter
2012-07-18 06:41:36 +00:00
parent 18a1b616ea
commit a0f14afee1
2 changed files with 150 additions and 84 deletions

View File

@@ -355,6 +355,7 @@ bool MipsAsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNum,
}
case 'D': // Second part of a double word register operand
case 'L': // Low order register of a double word register operand
case 'M': // High order register of a double word register operand
{
if (OpNum == 0)
return true;
@@ -377,12 +378,16 @@ bool MipsAsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNum,
unsigned RegOp = OpNum;
if (!Subtarget->isGP64bit()){
// Endianess reverses which register holds the high or low value
// between M and L.
switch(ExtraCode[0]) {
case 'D':
RegOp = (Subtarget->isLittle()) ? OpNum : OpNum+1;
case 'M':
RegOp = (Subtarget->isLittle()) ? OpNum + 1 : OpNum;
break;
case 'L':
RegOp = (Subtarget->isLittle()) ? OpNum+1 : OpNum;
RegOp = (Subtarget->isLittle()) ? OpNum : OpNum + 1;
break;
case 'D': // Always the second part
RegOp = OpNum + 1;
}
if (RegOp >= MI->getNumOperands())
return true;