diff --git a/lib/Target/X86/AsmParser/X86AsmParser.cpp b/lib/Target/X86/AsmParser/X86AsmParser.cpp index 28e30769abc..21faa962a91 100644 --- a/lib/Target/X86/AsmParser/X86AsmParser.cpp +++ b/lib/Target/X86/AsmParser/X86AsmParser.cpp @@ -620,9 +620,6 @@ X86Operand *X86ATTAsmParser::ParseMemOperand(unsigned SegReg, SMLoc MemStart) { bool X86ATTAsmParser:: ParseInstruction(StringRef Name, SMLoc NameLoc, SmallVectorImpl &Operands) { - // FIXME: This is not correct at all. - if (Name == "movzx") Name = "movzb"; - StringRef PatchedName = Name; // FIXME: Hack to recognize cmp{ss,sd,ps,pd}. diff --git a/lib/Target/X86/X86InstrInfo.td b/lib/Target/X86/X86InstrInfo.td index ab9869abc5c..f5463c0d6ab 100644 --- a/lib/Target/X86/X86InstrInfo.td +++ b/lib/Target/X86/X86InstrInfo.td @@ -1259,6 +1259,10 @@ include "X86InstrCompiler.td" //===----------------------------------------------------------------------===// // movsx aliases +def : InstAlias<(outs GR16:$dst), (ins GR8 :$src), + "movsx $src, $dst", + (MOVSX16rr8W GR16:$dst, GR8:$src)>; + def : InstAlias<(outs GR32:$dst), (ins GR8 :$src), "movsx $src, $dst", (MOVSX32rr8 GR32:$dst, GR8:$src)>; @@ -1266,6 +1270,35 @@ def : InstAlias<(outs GR32:$dst), (ins GR16:$src), "movsx $src, $dst", (MOVSX32rr16 GR32:$dst, GR16:$src)>; +def : InstAlias<(outs GR64:$dst), (ins GR8 :$src), + "movsx $src, $dst", + (MOVSX64rr8 GR64:$dst, GR8:$src)>; +def : InstAlias<(outs GR64:$dst), (ins GR16:$src), + "movsx $src, $dst", + (MOVSX64rr16 GR64:$dst, GR16:$src)>; +def : InstAlias<(outs GR64:$dst), (ins GR32:$src), + "movsx $src, $dst", + (MOVSX64rr32 GR64:$dst, GR32:$src)>; + +// movzx aliases +def : InstAlias<(outs GR16:$dst), (ins GR8 :$src), + "movzx $src, $dst", + (MOVZX16rr8W GR16:$dst, GR8:$src)>; + +def : InstAlias<(outs GR32:$dst), (ins GR8 :$src), + "movzx $src, $dst", + (MOVZX32rr8 GR32:$dst, GR8:$src)>; +def : InstAlias<(outs GR32:$dst), (ins GR16:$src), + "movzx $src, $dst", + (MOVZX32rr16 GR32:$dst, GR16:$src)>; + +def : InstAlias<(outs GR64:$dst), (ins GR8 :$src), + "movzx $src, $dst", + (MOVZX64rr8_Q GR64:$dst, GR8:$src)>; +def : InstAlias<(outs GR64:$dst), (ins GR16:$src), + "movzx $src, $dst", + (MOVZX64rr16_Q GR64:$dst, GR16:$src)>; +// Note: No GR32->GR64 movzx form. // TODO: lidtl/lidtq can be opcode aliases, perhaps others. diff --git a/test/MC/X86/x86-64.s b/test/MC/X86/x86-64.s index a115b342aa8..5cc08441a6d 100644 --- a/test/MC/X86/x86-64.s +++ b/test/MC/X86/x86-64.s @@ -648,9 +648,51 @@ btq $0x01,%rdx // CHECK: encoding: [0x48,0x0f,0xb6,0xf0] movzx %al, %rsi -// CHECK: movzbq (%rsp), %rsi -// CHECK: encoding: [0x48,0x0f,0xb6,0x34,0x24] - movzx 0(%rsp), %rsi +// CHECK: movsbw %al, %ax +// CHECK: encoding: [0x66,0x0f,0xbe,0xc0] +movsx %al, %ax + +// CHECK: movsbl %al, %eax +// CHECK: encoding: [0x0f,0xbe,0xc0] +movsx %al, %eax + +// CHECK: movswl %ax, %eax +// CHECK: encoding: [0x0f,0xbf,0xc0] +movsx %ax, %eax + +// CHECK: movsbq %bl, %rax +// CHECK: encoding: [0x48,0x0f,0xbe,0xc3] +movsx %bl, %rax + +// CHECK: movswq %cx, %rax +// CHECK: encoding: [0x48,0x0f,0xbf,0xc1] +movsx %cx, %rax + +// CHECK: movslq %edi, %rax +// CHECK: encoding: [0x48,0x63,0xc7] +movsx %edi, %rax + +// CHECK: movzbw %al, %ax +// CHECK: encoding: [0x66,0x0f,0xb6,0xc0] +movzx %al, %ax + +// CHECK: movzbl %al, %eax +// CHECK: encoding: [0x0f,0xb6,0xc0] +movzx %al, %eax + +// CHECK: movzwl %ax, %eax +// CHECK: encoding: [0x0f,0xb7,0xc0] +movzx %ax, %eax + +// CHECK: movzbq %bl, %rax +// CHECK: encoding: [0x48,0x0f,0xb6,0xc3] +movzx %bl, %rax + +// CHECK: movzwq %cx, %rax +// CHECK: encoding: [0x48,0x0f,0xb7,0xc1] +movzx %cx, %rax + + // rdar://7873482 diff --git a/utils/TableGen/AsmMatcherEmitter.cpp b/utils/TableGen/AsmMatcherEmitter.cpp index b4b6331b6c4..f422106ef56 100644 --- a/utils/TableGen/AsmMatcherEmitter.cpp +++ b/utils/TableGen/AsmMatcherEmitter.cpp @@ -357,12 +357,18 @@ struct MatchableInfo { MatchableInfo(const CodeGenInstruction &CGI) : TheDef(CGI.TheDef), OperandList(CGI.Operands), AsmString(CGI.AsmString) { + InstrName = TheDef->getName(); } MatchableInfo(const CodeGenInstAlias *Alias) : TheDef(Alias->TheDef), OperandList(Alias->Operands), AsmString(Alias->AsmString) { - + + // FIXME: Huge hack. + DefInit *DI = dynamic_cast(Alias->Result->getOperator()); + assert(DI); + + InstrName = DI->getDef()->getName(); } void Initialize(const AsmMatcherInfo &Info, @@ -551,8 +557,6 @@ void MatchableInfo::dump() { void MatchableInfo::Initialize(const AsmMatcherInfo &Info, SmallPtrSet &SingletonRegisters) { - InstrName = TheDef->getName(); - // TODO: Eventually support asmparser for Variant != 0. AsmString = CodeGenInstruction::FlattenAsmStringVariants(AsmString, 0); @@ -974,7 +978,7 @@ void AsmMatcherInfo::BuildInfo() { // Validate the alias definitions. II->Validate(CommentDelimiter, false); - //Matchables.push_back(II.take()); + Matchables.push_back(II.take()); } // Build info for the register classes. diff --git a/utils/TableGen/CodeGenInstruction.cpp b/utils/TableGen/CodeGenInstruction.cpp index 8a05374d8c4..7428f2c88fe 100644 --- a/utils/TableGen/CodeGenInstruction.cpp +++ b/utils/TableGen/CodeGenInstruction.cpp @@ -110,6 +110,12 @@ CGIOperandList::CGIOperandList(Record *R) : TheDef(R) { MIOperandNo, NumOps, MIOpInfo)); MIOperandNo += NumOps; } + + + // Make sure the constraints list for each operand is large enough to hold + // constraint info, even if none is present. + for (unsigned i = 0, e = OperandList.size(); i != e; ++i) + OperandList[i].Constraints.resize(OperandList[i].MINumOperands); } @@ -235,11 +241,6 @@ static void ParseConstraint(const std::string &CStr, CGIOperandList &Ops) { } static void ParseConstraints(const std::string &CStr, CGIOperandList &Ops) { - // Make sure the constraints list for each operand is large enough to hold - // constraint info, even if none is present. - for (unsigned i = 0, e = Ops.size(); i != e; ++i) - Ops[i].Constraints.resize(Ops[i].MINumOperands); - if (CStr.empty()) return; const std::string delims(","); @@ -390,5 +391,5 @@ FlattenAsmStringVariants(StringRef Cur, unsigned Variant) { CodeGenInstAlias::CodeGenInstAlias(Record *R) : TheDef(R), Operands(R) { AsmString = R->getValueAsString("AsmString"); - + Result = R->getValueAsDag("ResultInst"); } diff --git a/utils/TableGen/CodeGenInstruction.h b/utils/TableGen/CodeGenInstruction.h index f05a88fd022..78c88d797d3 100644 --- a/utils/TableGen/CodeGenInstruction.h +++ b/utils/TableGen/CodeGenInstruction.h @@ -250,6 +250,9 @@ namespace llvm { /// to the alias. CGIOperandList Operands; + /// Result - The result instruction. + DagInit *Result; + CodeGenInstAlias(Record *R); }; }