From 51cd16cbd592d1b8da3888d6a4f9c684ed50a02a Mon Sep 17 00:00:00 2001 From: David Woodhouse Date: Wed, 22 Jan 2014 15:08:42 +0000 Subject: [PATCH] [x86] Allow segment and address-size overrides for MOVS[BWLQ] (PR9385) git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@199807 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/X86/AsmParser/X86AsmParser.cpp | 39 +++++++++++++++-------- lib/Target/X86/X86InstrInfo.td | 16 +++++----- test/MC/X86/index-operations.s | 10 ++++++ test/MC/X86/x86-16.s | 6 ++-- test/MC/X86/x86-32.s | 6 ++-- test/MC/X86/x86-64.s | 8 ++--- 6 files changed, 54 insertions(+), 31 deletions(-) diff --git a/lib/Target/X86/AsmParser/X86AsmParser.cpp b/lib/Target/X86/AsmParser/X86AsmParser.cpp index 5f3498c7c3c..d6b2ad418e4 100644 --- a/lib/Target/X86/AsmParser/X86AsmParser.cpp +++ b/lib/Target/X86/AsmParser/X86AsmParser.cpp @@ -2358,19 +2358,6 @@ ParseInstruction(ParseInstructionInfo &Info, StringRef Name, SMLoc NameLoc, } } - // Transform "movs[bwl] %ds:(%esi), %es:(%edi)" into "movs[bwl]" - if (Name.startswith("movs") && Operands.size() == 3 && - (Name == "movsb" || Name == "movsw" || Name == "movsl" || - (is64BitMode() && Name == "movsq"))) { - X86Operand &Op = *(X86Operand*)Operands.begin()[1]; - X86Operand &Op2 = *(X86Operand*)Operands.begin()[2]; - if (isSrcOp(Op) && isDstOp(Op2)) { - Operands.pop_back(); - Operands.pop_back(); - delete &Op; - delete &Op2; - } - } // Transform "lods[bwlq]" into "lods[bwlq] ($SIREG)" for appropriate // values of $SIREG according to the mode. It would be nice if this // could be achieved with InstAlias in the tables. @@ -2416,6 +2403,32 @@ ParseInstruction(ParseInstructionInfo &Info, StringRef Name, SMLoc NameLoc, } } + // Add default SI and DI operands to "movs[bwlq]". + if ((Name.startswith("movs") && + (Name == "movs" || Name == "movsb" || Name == "movsw" || + Name == "movsl" || Name == "movsd" || Name == "movsq")) || + (Name.startswith("smov") && + (Name == "smov" || Name == "smovb" || Name == "smovw" || + Name == "smovl" || Name == "smovd" || Name == "smovq"))) { + if (Operands.size() == 1) { + if (Name == "movsd") + Operands.back() = X86Operand::CreateToken("movsl", NameLoc); + if (isParsingIntelSyntax()) { + Operands.push_back(DefaultMemDIOperand(NameLoc)); + Operands.push_back(DefaultMemSIOperand(NameLoc)); + } else { + Operands.push_back(DefaultMemSIOperand(NameLoc)); + Operands.push_back(DefaultMemDIOperand(NameLoc)); + } + } else if (Operands.size() == 3) { + X86Operand &Op = *(X86Operand*)Operands.begin()[1]; + X86Operand &Op2 = *(X86Operand*)Operands.begin()[2]; + if (!doSrcDstMatch(Op, Op2)) + return Error(Op.getStartLoc(), + "mismatching source and destination index registers"); + } + } + // FIXME: Hack to handle recognize s{hr,ar,hl} $1, . Canonicalize to // "shift ". if ((Name.startswith("shr") || Name.startswith("sar") || diff --git a/lib/Target/X86/X86InstrInfo.td b/lib/Target/X86/X86InstrInfo.td index 0fe93cc4fea..13c310290aa 100644 --- a/lib/Target/X86/X86InstrInfo.td +++ b/lib/Target/X86/X86InstrInfo.td @@ -1137,10 +1137,14 @@ def BSR64rm : RI<0xBD, MRMSrcMem, (outs GR64:$dst), (ins i64mem:$src), let SchedRW = [WriteMicrocoded] in { // These uses the DF flag in the EFLAGS register to inc or dec EDI and ESI let Defs = [EDI,ESI], Uses = [EDI,ESI,EFLAGS] in { -def MOVSB : I<0xA4, RawFrm, (outs), (ins), "movsb", [], IIC_MOVS>; -def MOVSW : I<0xA5, RawFrm, (outs), (ins), "movsw", [], IIC_MOVS>, OpSize; -def MOVSL : I<0xA5, RawFrm, (outs), (ins), "movs{l|d}", [], IIC_MOVS>, OpSize16; -def MOVSQ : RI<0xA5, RawFrm, (outs), (ins), "movsq", [], IIC_MOVS>; +def MOVSB : I<0xA4, RawFrmDstSrc, (outs dstidx8:$dst), (ins srcidx8:$src), + "movsb\t{$src, $dst|$dst, $src}", [], IIC_MOVS>; +def MOVSW : I<0xA5, RawFrmDstSrc, (outs dstidx16:$dst), (ins srcidx16:$src), + "movsw\t{$src, $dst|$dst, $src}", [], IIC_MOVS>, OpSize; +def MOVSL : I<0xA5, RawFrmDstSrc, (outs dstidx32:$dst), (ins srcidx32:$src), + "movs{l|d}\t{$src, $dst|$dst, $src}", [], IIC_MOVS>, OpSize16; +def MOVSQ : RI<0xA5, RawFrmDstSrc, (outs dstidx64:$dst), (ins srcidx64:$src), + "movsq\t{$src, $dst|$dst, $src}", [], IIC_MOVS>; } // These uses the DF flag in the EFLAGS register to inc or dec EDI and ESI @@ -2593,10 +2597,6 @@ def : InstAlias<"movq $src, $dst", def : InstAlias<"movq $src, $dst", (MMX_MOVD64from64rr GR64:$dst, VR64:$src), 0>; -// movsd with no operands (as opposed to the SSE scalar move of a double) is an -// alias for movsl. (as in rep; movsd) -def : InstAlias<"movsd", (MOVSL), 0>; - // movsx aliases def : InstAlias<"movsx $src, $dst", (MOVSX16rr8 GR16:$dst, GR8:$src), 0>; def : InstAlias<"movsx $src, $dst", (MOVSX16rm8 GR16:$dst, i8mem:$src), 0>; diff --git a/test/MC/X86/index-operations.s b/test/MC/X86/index-operations.s index 7bd29aca2cd..bf6d87fb2b8 100644 --- a/test/MC/X86/index-operations.s +++ b/test/MC/X86/index-operations.s @@ -119,3 +119,13 @@ cmpsq (%rdi), (%rsi) // 64: cmpsq %es:(%rdi), (%rsi) # encoding: [0x48,0xa7] // ERR32: 64-bit // ERR16: 64-bit + +movsb (%esi), (%edi) +// 64: movsb (%esi), %es:(%edi) # encoding: [0x67,0xa4] +// 32: movsb (%esi), %es:(%edi) # encoding: [0xa4] +// 16: movsb (%esi), %es:(%edi) # encoding: [0x67,0xa4] + +movsl %gs:(%esi), (%edi) +// 64: movsl %gs:(%esi), %es:(%edi) # encoding: [0x65,0x67,0xa5] +// 32: movsl %gs:(%esi), %es:(%edi) # encoding: [0x65,0xa5] +// 16: movsl %gs:(%esi), %es:(%edi) # encoding: [0x66,0x65,0x67,0xa5] diff --git a/test/MC/X86/x86-16.s b/test/MC/X86/x86-16.s index 41b5f51dbc7..ae700fa771e 100644 --- a/test/MC/X86/x86-16.s +++ b/test/MC/X86/x86-16.s @@ -824,21 +824,21 @@ pshufw $90, %mm4, %mm0 insl insl %dx, %es:(%di) -// CHECK: movsb # encoding: [0xa4] +// CHECK: movsb (%si), %es:(%di) # encoding: [0xa4] // CHECK: movsb // CHECK: movsb movsb movsb %ds:(%si), %es:(%di) movsb (%si), %es:(%di) -// CHECK: movsw # encoding: [0xa5] +// CHECK: movsw (%si), %es:(%di) # encoding: [0xa5] // CHECK: movsw // CHECK: movsw movsw movsw %ds:(%si), %es:(%di) movsw (%si), %es:(%di) -// CHECK: movsl # encoding: [0x66,0xa5] +// CHECK: movsl (%si), %es:(%di) # encoding: [0x66,0xa5] // CHECK: movsl // CHECK: movsl movsl diff --git a/test/MC/X86/x86-32.s b/test/MC/X86/x86-32.s index e661f664b7e..3d75c6fefa7 100644 --- a/test/MC/X86/x86-32.s +++ b/test/MC/X86/x86-32.s @@ -900,21 +900,21 @@ pshufw $90, %mm4, %mm0 insl insl %dx, %es:(%edi) -// CHECK: movsb # encoding: [0xa4] +// CHECK: movsb (%esi), %es:(%edi) # encoding: [0xa4] // CHECK: movsb // CHECK: movsb movsb movsb %ds:(%esi), %es:(%edi) movsb (%esi), %es:(%edi) -// CHECK: movsw # encoding: [0x66,0xa5] +// CHECK: movsw (%esi), %es:(%edi) # encoding: [0x66,0xa5] // CHECK: movsw // CHECK: movsw movsw movsw %ds:(%esi), %es:(%edi) movsw (%esi), %es:(%edi) -// CHECK: movsl # encoding: [0xa5] +// CHECK: movsl (%esi), %es:(%edi) # encoding: [0xa5] // CHECK: movsl // CHECK: movsl movsl diff --git a/test/MC/X86/x86-64.s b/test/MC/X86/x86-64.s index 08adfccf762..e39cefee849 100644 --- a/test/MC/X86/x86-64.s +++ b/test/MC/X86/x86-64.s @@ -1085,21 +1085,21 @@ xsetbv // CHECK: xsetbv # encoding: [0x0f,0x01,0xd1] insl insl %dx, %es:(%rdi) -// CHECK: movsb # encoding: [0xa4] +// CHECK: movsb (%rsi), %es:(%rdi) # encoding: [0xa4] // CHECK: movsb // CHECK: movsb movsb movsb %ds:(%rsi), %es:(%rdi) movsb (%rsi), %es:(%rdi) -// CHECK: movsw # encoding: [0x66,0xa5] +// CHECK: movsw (%rsi), %es:(%rdi) # encoding: [0x66,0xa5] // CHECK: movsw // CHECK: movsw movsw movsw %ds:(%rsi), %es:(%rdi) movsw (%rsi), %es:(%rdi) -// CHECK: movsl # encoding: [0xa5] +// CHECK: movsl (%rsi), %es:(%rdi) # encoding: [0xa5] // CHECK: movsl // CHECK: movsl movsl @@ -1109,7 +1109,7 @@ xsetbv // CHECK: xsetbv # encoding: [0x0f,0x01,0xd1] // CHECK: movsl movsl (%rsi), (%rdi) -// CHECK: movsq # encoding: [0x48,0xa5] +// CHECK: movsq (%rsi), %es:(%rdi) # encoding: [0x48,0xa5] // CHECK: movsq // CHECK: movsq movsq -- 2.34.1