diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp index 56c6bd9d2688b..15115115b92f6 100644 --- a/llvm/lib/Target/X86/X86ISelLowering.cpp +++ b/llvm/lib/Target/X86/X86ISelLowering.cpp @@ -39160,6 +39160,15 @@ X86TargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, return Res; } + // Make sure it isn't a register that requires AVX512. + if (!Subtarget.hasAVX512() && isFRClass(*Res.second) && + TRI->getEncodingValue(Res.first) & 0x10) { + // Register requires EVEX prefix. + Res.first = 0; + Res.second = nullptr; + return Res; + } + // Otherwise, check to see if this is a register class of the wrong value // type. For example, we want to map "{ax},i32" -> {eax}, we don't want it to // turn into {ax},{dx}. diff --git a/llvm/test/CodeGen/X86/asm-reject-xmm16.ll b/llvm/test/CodeGen/X86/asm-reject-xmm16.ll new file mode 100644 index 0000000000000..eee0064c96409 --- /dev/null +++ b/llvm/test/CodeGen/X86/asm-reject-xmm16.ll @@ -0,0 +1,8 @@ +; RUN: not llc -o /dev/null %s 2>&1 | FileCheck %s +target triple = "x86_64--" + +; CHECK: error: couldn't allocate output register for constraint '{xmm16}' +define i64 @blup() { + %v = tail call i64 asm "", "={xmm16},0"(i64 0) + ret i64 %v +}