diff --git a/llvm/include/llvm/Target/Target.td b/llvm/include/llvm/Target/Target.td --- a/llvm/include/llvm/Target/Target.td +++ b/llvm/include/llvm/Target/Target.td @@ -653,6 +653,11 @@ /// instruction selection predicates. FastISel cannot handle such cases, but /// SelectionDAG can. bit FastISelShouldIgnore = false; + + /// HasPositionOrder: Indicate tablegen to sort the instructions by record + /// ID, so that instruction that is defined earlier can be sorted earlier + /// in the assembly matching table. + bit HasPositionOrder = false; } /// Defines an additional encoding that disassembles to the given instruction diff --git a/llvm/lib/Target/X86/AsmParser/X86AsmParser.cpp b/llvm/lib/Target/X86/AsmParser/X86AsmParser.cpp --- a/llvm/lib/Target/X86/AsmParser/X86AsmParser.cpp +++ b/llvm/lib/Target/X86/AsmParser/X86AsmParser.cpp @@ -4270,24 +4270,6 @@ ForcedVEXEncoding != VEXEncoding_VEX3)) return Match_Unsupported; - // These instructions match ambiguously with their VEX encoded counterparts - // and appear first in the matching table. Reject them unless we're forcing - // EVEX encoding. - // FIXME: We really need a way to break the ambiguity. - switch (Opc) { - case X86::VCVTSD2SIZrm_Int: - case X86::VCVTSD2SI64Zrm_Int: - case X86::VCVTSS2SIZrm_Int: - case X86::VCVTSS2SI64Zrm_Int: - case X86::VCVTTSD2SIZrm: case X86::VCVTTSD2SIZrm_Int: - case X86::VCVTTSD2SI64Zrm: case X86::VCVTTSD2SI64Zrm_Int: - case X86::VCVTTSS2SIZrm: case X86::VCVTTSS2SIZrm_Int: - case X86::VCVTTSS2SI64Zrm: case X86::VCVTTSS2SI64Zrm_Int: - if (ForcedVEXEncoding != VEXEncoding_EVEX) - return Match_Unsupported; - break; - } - return Match_Success; } diff --git a/llvm/lib/Target/X86/X86InstrFormats.td b/llvm/lib/Target/X86/X86InstrFormats.td --- a/llvm/lib/Target/X86/X86InstrFormats.td +++ b/llvm/lib/Target/X86/X86InstrFormats.td @@ -296,6 +296,8 @@ // If this is a pseudo instruction, mark it isCodeGenOnly. let isCodeGenOnly = !eq(!cast(f), "Pseudo"); + let HasPositionOrder = 1; + // // Attributes specific to X86 instructions... // diff --git a/llvm/utils/TableGen/AsmMatcherEmitter.cpp b/llvm/utils/TableGen/AsmMatcherEmitter.cpp --- a/llvm/utils/TableGen/AsmMatcherEmitter.cpp +++ b/llvm/utils/TableGen/AsmMatcherEmitter.cpp @@ -636,6 +636,15 @@ if (RequiredFeatures.size() != RHS.RequiredFeatures.size()) return RequiredFeatures.size() > RHS.RequiredFeatures.size(); + // For X86 AVX/AVX512 instructions, we prefer vex encoding because the + // vex encoding size is smaller. Since X86InstrSSE.td is included ahead + // of X86InstrAVX512.td, the AVX instruction ID is less than AVX512 ID. + // We use the ID to sort AVX instruction before AVX512 instruction in + // matching table. + if (TheDef->isSubClassOf("Instruction") && + TheDef->getValueAsBit("HasPositionOrder")) + return TheDef->getID() < RHS.TheDef->getID(); + return false; }