From: Ulrich Weigand Date: Mon, 8 Jul 2013 14:49:37 +0000 (+0000) Subject: [PowerPC] Support basic compare mnemonics X-Git-Url: http://plrg.eecs.uci.edu/git/?a=commitdiff_plain;h=9e5bbeab1f6f79375c24bfab87c28f5f4c5afea1;p=oota-llvm.git [PowerPC] Support basic compare mnemonics This adds support for the basic mnemoics (with the L operand) for the fixed-point compare instructions. These are defined as aliases for the already existing CMPW/CMPD patterns, depending on the value of L. This requires use of InstAlias patterns with immediate literal operands. To make this work, we need two further changes: - define a RegisterPrefix, because otherwise literals 0 and 1 would be parsed as literal register names - provide a PPCAsmParser::validateTargetOperandClass routine to recognize immediate literals (like ARM does) git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@185826 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Target/PowerPC/AsmParser/PPCAsmParser.cpp b/lib/Target/PowerPC/AsmParser/PPCAsmParser.cpp index 237ecdc60e4..790a98e06db 100644 --- a/lib/Target/PowerPC/AsmParser/PPCAsmParser.cpp +++ b/lib/Target/PowerPC/AsmParser/PPCAsmParser.cpp @@ -229,6 +229,8 @@ public: SmallVectorImpl &Operands); virtual bool ParseDirective(AsmToken DirectiveID); + + unsigned validateTargetOperandClass(MCParsedAsmOperand *Op, unsigned Kind); }; /// PPCOperand - Instances of this class represent a parsed PowerPC machine @@ -1232,3 +1234,25 @@ extern "C" void LLVMInitializePowerPCAsmParser() { #define GET_REGISTER_MATCHER #define GET_MATCHER_IMPLEMENTATION #include "PPCGenAsmMatcher.inc" + +// Define this matcher function after the auto-generated include so we +// have the match class enum definitions. +unsigned PPCAsmParser::validateTargetOperandClass(MCParsedAsmOperand *AsmOp, + unsigned Kind) { + // If the kind is a token for a literal immediate, check if our asm + // operand matches. This is for InstAliases which have a fixed-value + // immediate in the syntax. + int64_t ImmVal; + switch (Kind) { + case MCK_0: ImmVal = 0; break; + case MCK_1: ImmVal = 1; break; + default: return Match_InvalidOperand; + } + + PPCOperand *Op = static_cast(AsmOp); + if (Op->isImm() && Op->getImm() == ImmVal) + return Match_Success; + + return Match_InvalidOperand; +} + diff --git a/lib/Target/PowerPC/PPC.td b/lib/Target/PowerPC/PPC.td index eb73c676ad7..d7e2cad961a 100644 --- a/lib/Target/PowerPC/PPC.td +++ b/lib/Target/PowerPC/PPC.td @@ -272,10 +272,20 @@ def PPCAsmParser : AsmParser { let ShouldEmitMatchRegisterName = 0; } +def PPCAsmParserVariant : AsmParserVariant { + int Variant = 0; + + // We do not use hard coded registers in asm strings. However, some + // InstAlias definitions use immediate literals. Set RegisterPrefix + // so that those are not misinterpreted as registers. + string RegisterPrefix = "%"; +} + def PPC : Target { // Information about the instructions. let InstructionSet = PPCInstrInfo; let AssemblyWriters = [PPCAsmWriter]; let AssemblyParsers = [PPCAsmParser]; + let AssemblyParserVariants = [PPCAsmParserVariant]; } diff --git a/lib/Target/PowerPC/PPCInstrInfo.td b/lib/Target/PowerPC/PPCInstrInfo.td index fbf61f063aa..3aafb5c9638 100644 --- a/lib/Target/PowerPC/PPCInstrInfo.td +++ b/lib/Target/PowerPC/PPCInstrInfo.td @@ -2578,6 +2578,15 @@ def : InstAlias<"cmpd $rA, $rB", (CMPD CR0, g8rc:$rA, g8rc:$rB)>; def : InstAlias<"cmpldi $rA, $imm", (CMPLDI CR0, g8rc:$rA, u16imm:$imm)>; def : InstAlias<"cmpld $rA, $rB", (CMPLD CR0, g8rc:$rA, g8rc:$rB)>; +def : InstAlias<"cmpi $bf, 0, $rA, $imm", (CMPWI crrc:$bf, gprc:$rA, s16imm:$imm)>; +def : InstAlias<"cmp $bf, 0, $rA, $rB", (CMPW crrc:$bf, gprc:$rA, gprc:$rB)>; +def : InstAlias<"cmpli $bf, 0, $rA, $imm", (CMPLWI crrc:$bf, gprc:$rA, u16imm:$imm)>; +def : InstAlias<"cmpl $bf, 0, $rA, $rB", (CMPLW crrc:$bf, gprc:$rA, gprc:$rB)>; +def : InstAlias<"cmpi $bf, 1, $rA, $imm", (CMPDI crrc:$bf, g8rc:$rA, s16imm:$imm)>; +def : InstAlias<"cmp $bf, 1, $rA, $rB", (CMPD crrc:$bf, g8rc:$rA, g8rc:$rB)>; +def : InstAlias<"cmpli $bf, 1, $rA, $imm", (CMPLDI crrc:$bf, g8rc:$rA, u16imm:$imm)>; +def : InstAlias<"cmpl $bf, 1, $rA, $rB", (CMPLD crrc:$bf, g8rc:$rA, g8rc:$rB)>; + multiclass TrapExtendedMnemonic { def : InstAlias<"td"#name#"i $rA, $imm", (TDI to, g8rc:$rA, s16imm:$imm)>; def : InstAlias<"td"#name#" $rA, $rB", (TD to, g8rc:$rA, g8rc:$rB)>; diff --git a/test/MC/PowerPC/ppc64-encoding.s b/test/MC/PowerPC/ppc64-encoding.s index eac039a61bd..d82d86fd010 100644 --- a/test/MC/PowerPC/ppc64-encoding.s +++ b/test/MC/PowerPC/ppc64-encoding.s @@ -344,7 +344,25 @@ # FIXME: divdeuo 2, 3, 4 # FIXME: divdeuo. 2, 3, 4 -# FIXME: Fixed-point compare instructions +# Fixed-point compare instructions + +# CHECK: cmpdi 2, 3, 128 # encoding: [0x2d,0x23,0x00,0x80] + cmpi 2, 1, 3, 128 +# CHECK: cmpd 2, 3, 4 # encoding: [0x7d,0x23,0x20,0x00] + cmp 2, 1, 3, 4 +# CHECK: cmpldi 2, 3, 128 # encoding: [0x29,0x23,0x00,0x80] + cmpli 2, 1, 3, 128 +# CHECK: cmpld 2, 3, 4 # encoding: [0x7d,0x23,0x20,0x40] + cmpl 2, 1, 3, 4 + +# CHECK: cmpwi 2, 3, 128 # encoding: [0x2d,0x03,0x00,0x80] + cmpi 2, 0, 3, 128 +# CHECK: cmpw 2, 3, 4 # encoding: [0x7d,0x03,0x20,0x00] + cmp 2, 0, 3, 4 +# CHECK: cmplwi 2, 3, 128 # encoding: [0x29,0x03,0x00,0x80] + cmpli 2, 0, 3, 128 +# CHECK: cmplw 2, 3, 4 # encoding: [0x7d,0x03,0x20,0x40] + cmpl 2, 0, 3, 4 # Fixed-point trap instructions