From ab7f9b170d854b8d5be55a94f48ad67727b4d0bc Mon Sep 17 00:00:00 2001 From: Luke Cheeseman Date: Mon, 24 Sep 2018 15:13:48 +0000 Subject: [PATCH] [Arm][AsmParser] Restrict register list size for VSTM/VLDM - The assembler accepts VSTM/VLDM with register lists (specifically double registers lists) with more than 16 registers specified - The Arm architecture reference manual says this instruction must not contain more than 16 registers when the registers are doubleword registers - This addresses one of the concerns in https://bugs.llvm.org/show_bug.cgi?id=38389 Differential Revision: https://reviews.llvm.org/D52082 llvm-svn: 342891 --- llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp | 9 +++++++++ llvm/test/MC/ARM/single-precision-fp.s | 15 +++++++++++++++ 2 files changed, 24 insertions(+) diff --git a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp index 9e84a67..3e44014 100644 --- a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp +++ b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp @@ -6841,6 +6841,15 @@ bool ARMAsmParser::validateInstruction(MCInst &Inst, "destination operands must be sequential"); break; } + case ARM::VLDMDIA: + case ARM::VSTMDIA: { + ARMOperand &Op = static_cast(*Operands[3]); + auto &RegList = Op.getRegList(); + if (RegList.size() < 1 || RegList.size() > 16) + return Error(Operands[3]->getStartLoc(), + "list of registers must be at least 1 and at most 16"); + break; + } } return false; diff --git a/llvm/test/MC/ARM/single-precision-fp.s b/llvm/test/MC/ARM/single-precision-fp.s index 665244a..f658e71 100644 --- a/llvm/test/MC/ARM/single-precision-fp.s +++ b/llvm/test/MC/ARM/single-precision-fp.s @@ -171,6 +171,21 @@ @ CHECK-ERRORS: error: instruction requires: double precision VFP @ CHECK-ERRORS-NEXT: vrintm.f64 d3, d2 + vstm r4, {} + vstm r4, {d15-d30} + vstm r4, {d15-d31} + vstm r4, {s15-s31} + vldm r4, {d15-d30} + vldm r4, {d15-d31} + vldm r4, {s15-s31} +@ CHECK-ERRORS: error: register expected +@ CHECK: vstmia r4, {d15, d16, d17, d18, d19, d20, d21, d22, d23, d24, d25, d26, d27, d28, d29, d30} +@ CHECK-ERRORS: error: list of registers must be at least 1 and at most 16 +@ CHECK: vstmia r4, {s15, s16, s17, s18, s19, s20, s21, s22, s23, s24, s25, s26, s27, s28, s29, s30, s31} +@ CHECK: vldmia r4, {d15, d16, d17, d18, d19, d20, d21, d22, d23, d24, d25, d26, d27, d28, d29, d30} +@ CHECK-ERRORS: error: list of registers must be at least 1 and at most 16 +@ CHECK: vldmia r4, {s15, s16, s17, s18, s19, s20, s21, s22, s23, s24, s25, s26, s27, s28, s29, s30, s31} + @ Double precisionish operations that actually *are* allowed. vldr d0, [sp] vstr d3, [sp] -- 2.7.4