From f6145affbf810fca24512c1bcb89b9ad8d0aba71 Mon Sep 17 00:00:00 2001 From: Craig Topper Date: Tue, 6 Jan 2015 08:59:30 +0000 Subject: [PATCH] [X86] Add OpSize32 to XBEGIN_4. Add XBEGIN_2 with OpSize16. Requires new AsmParserOperand types that detect 16-bit and 32/64-bit mode so that we choose the right instruction based on default sizing without predicates. This is necessary since predicates mess up the disassembler table building. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@225256 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/X86/AsmParser/X86Operand.h | 8 ++++++++ lib/Target/X86/X86InstrControl.td | 8 ++++---- lib/Target/X86/X86InstrInfo.td | 22 ++++++++++++++++++++++ lib/Target/X86/X86InstrTSX.td | 9 ++++++--- test/MC/Disassembler/X86/x86-64.txt | 3 +++ utils/TableGen/X86RecognizableInstr.cpp | 6 ++++-- 6 files changed, 47 insertions(+), 9 deletions(-) diff --git a/lib/Target/X86/AsmParser/X86Operand.h b/lib/Target/X86/AsmParser/X86Operand.h index 4362fc5026d..6675d4dc045 100644 --- a/lib/Target/X86/AsmParser/X86Operand.h +++ b/lib/Target/X86/AsmParser/X86Operand.h @@ -254,6 +254,14 @@ struct X86Operand : public MCParsedAsmOperand { !getMemIndexReg() && getMemScale() == 1; } + bool isAbsMem16() const { + return isAbsMem() && Mem.ModeSize == 16; + } + + bool isAbsMem32() const { + return isAbsMem() && Mem.ModeSize != 16; + } + bool isSrcIdx() const { return !getMemIndexReg() && getMemScale() == 1 && (getMemBaseReg() == X86::RSI || getMemBaseReg() == X86::ESI || diff --git a/lib/Target/X86/X86InstrControl.td b/lib/Target/X86/X86InstrControl.td index 5dbddef0bd6..71415c6fde8 100644 --- a/lib/Target/X86/X86InstrControl.td +++ b/lib/Target/X86/X86InstrControl.td @@ -60,9 +60,9 @@ let isBarrier = 1, isBranch = 1, isTerminator = 1, SchedRW = [WriteJump] in { def JMP_1 : Ii8PCRel<0xEB, RawFrm, (outs), (ins brtarget8:$dst), "jmp\t$dst", [(br bb:$dst)], IIC_JMP_REL>; let hasSideEffects = 0, isCodeGenOnly = 1, ForceDisassemble = 1 in { - def JMP_2 : Ii16PCRel<0xE9, RawFrm, (outs), (ins brtarget:$dst), + def JMP_2 : Ii16PCRel<0xE9, RawFrm, (outs), (ins brtarget16:$dst), "jmp\t$dst", [], IIC_JMP_REL>, OpSize16; - def JMP_4 : Ii32PCRel<0xE9, RawFrm, (outs), (ins brtarget:$dst), + def JMP_4 : Ii32PCRel<0xE9, RawFrm, (outs), (ins brtarget32:$dst), "jmp\t$dst", [], IIC_JMP_REL>, OpSize32; } } @@ -73,9 +73,9 @@ let isBranch = 1, isTerminator = 1, Uses = [EFLAGS], SchedRW = [WriteJump] in { def _1 : Ii8PCRel ; let hasSideEffects = 0, isCodeGenOnly = 1, ForceDisassemble = 1 in { - def _2 : Ii16PCRel, OpSize16, TB; - def _4 : Ii32PCRel, TB, OpSize32; } } diff --git a/lib/Target/X86/X86InstrInfo.td b/lib/Target/X86/X86InstrInfo.td index f5680924e4e..069b48896b5 100644 --- a/lib/Target/X86/X86InstrInfo.td +++ b/lib/Target/X86/X86InstrInfo.td @@ -377,6 +377,28 @@ def brtarget8 : Operand; } +// Special parsers to detect mode to disambiguate. +def X86AbsMem16AsmOperand : AsmOperandClass { + let Name = "AbsMem16"; + let RenderMethod = "addAbsMemOperands"; + let SuperClasses = [X86AbsMemAsmOperand]; +} + +def X86AbsMem32AsmOperand : AsmOperandClass { + let Name = "AbsMem32"; + let RenderMethod = "addAbsMemOperands"; + let SuperClasses = [X86AbsMemAsmOperand]; +} + +// Branch targets have OtherVT type and print as pc-relative values. +let OperandType = "OPERAND_PCREL", + PrintMethod = "printPCRelImm" in { +let ParserMatchClass = X86AbsMem16AsmOperand in + def brtarget16 : Operand; +let ParserMatchClass = X86AbsMem32AsmOperand in + def brtarget32 : Operand; +} + let RenderMethod = "addSrcIdxOperands" in { def X86SrcIdx8Operand : AsmOperandClass { let Name = "SrcIdx8"; diff --git a/lib/Target/X86/X86InstrTSX.td b/lib/Target/X86/X86InstrTSX.td index 4940efc4443..7267d752653 100644 --- a/lib/Target/X86/X86InstrTSX.td +++ b/lib/Target/X86/X86InstrTSX.td @@ -23,9 +23,12 @@ def XBEGIN : I<0, Pseudo, (outs GR32:$dst), (ins), "# XBEGIN", [(set GR32:$dst, (int_x86_xbegin))]>, Requires<[HasRTM]>; -let isBranch = 1, isTerminator = 1, Defs = [EAX] in -def XBEGIN_4 : Ii32PCRel<0xc7, MRM_F8, (outs), (ins brtarget:$dst), - "xbegin\t$dst", []>, Requires<[HasRTM]>; +let isBranch = 1, isTerminator = 1, Defs = [EAX] in { +def XBEGIN_2 : Ii16PCRel<0xc7, MRM_F8, (outs), (ins brtarget16:$dst), + "xbegin\t$dst", []>, OpSize16, Requires<[HasRTM]>; +def XBEGIN_4 : Ii32PCRel<0xc7, MRM_F8, (outs), (ins brtarget32:$dst), + "xbegin\t$dst", []>, OpSize32, Requires<[HasRTM]>; +} def XEND : I<0x01, MRM_D5, (outs), (ins), "xend", [(int_x86_xend)]>, TB, Requires<[HasRTM]>; diff --git a/test/MC/Disassembler/X86/x86-64.txt b/test/MC/Disassembler/X86/x86-64.txt index 70c8ae0dcc0..e67a4f9383e 100644 --- a/test/MC/Disassembler/X86/x86-64.txt +++ b/test/MC/Disassembler/X86/x86-64.txt @@ -107,6 +107,9 @@ # CHECK: xbegin 53 0xc7 0xf8 0x35 0x00 0x00 0x00 +# CHECK: xbegin 53 +0x66 0xc7 0xf8 0x35 0x00 + # CHECK: xend 0x0f 0x01 0xd5 diff --git a/utils/TableGen/X86RecognizableInstr.cpp b/utils/TableGen/X86RecognizableInstr.cpp index 1ee376e103c..9351fcb0fec 100644 --- a/utils/TableGen/X86RecognizableInstr.cpp +++ b/utils/TableGen/X86RecognizableInstr.cpp @@ -956,7 +956,8 @@ OperandType RecognizableInstr::typeFromString(const std::string &s, TYPE("SSECC", TYPE_IMM3) TYPE("AVXCC", TYPE_IMM5) TYPE("AVX512RC", TYPE_IMM32) - TYPE("brtarget", TYPE_RELv) + TYPE("brtarget32", TYPE_RELv) + TYPE("brtarget16", TYPE_RELv) TYPE("brtarget8", TYPE_REL8) TYPE("f80mem", TYPE_M80FP) TYPE("lea32mem", TYPE_LEA) @@ -1212,7 +1213,8 @@ RecognizableInstr::relocationEncodingFromString(const std::string &s, ENCODING("i64i32imm_pcrel", ENCODING_ID) ENCODING("i16imm_pcrel", ENCODING_IW) ENCODING("i32imm_pcrel", ENCODING_ID) - ENCODING("brtarget", ENCODING_Iv) + ENCODING("brtarget32", ENCODING_Iv) + ENCODING("brtarget16", ENCODING_Iv) ENCODING("brtarget8", ENCODING_IB) ENCODING("i64imm", ENCODING_IO) ENCODING("offset16_8", ENCODING_Ia)