[PATCH] D59733: ARM: Allow cp10/cp11 coprocessor register access with a warning

Stefan Agner via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Sat Mar 23 03:01:39 PDT 2019


falstaff84 created this revision.
falstaff84 added reviewers: rengolin, olista01, t.p.northover, efriedma, psmith.
Herald added subscribers: llvm-commits, jdoerfert, kristof.beyls, javed.absar.
Herald added a project: LLVM.

The Linux kernel uses quite some mcr/mrc instructions throughout the ARM port. Probably most of them could be converted to the appropriate vmsr/vmrs instructions along with appropriate FPU definition, e.g.:

  arch/arm/vfp/vfpmodule.c:345:2: error: invalid operand for instruction
          fmxr(FPEXC, fpexc & ~(FPEXC_EX|FPEXC_DEX|FPEXC_FP2V|FPEXC_VV|FPEXC_TRAP_MASK));
          ^
  arch/arm/vfp/vfpinstr.h:82:6: note: expanded from macro 'fmxr'
          asm("mcr p10, 7, %0, " vfpreg(_vfp_) ", cr0, 0 @ fmxr   " #_vfp_ ", %0" \
              ^
  <inline asm>:1:6: note: instantiated into assembly here
          mcr p10, 7, r0, cr8, cr0, 0 @ fmxr      FPEXC, r0
              ^

However, there is at least one case where an unofficial/(SoC specific?) control register is accessed:

  static u32 venum_read_pmresr(void)
  {
          u32 val;
          asm volatile("mrc p10, 7, %0, c11, c0, 0" : "=r" (val));
          return val;
  }

There is no register definition for control register 11 in lib/Target/ARM/ARMRegisterInfo.td.

This patch converts the restriction of mcr/mrc cp10/cp11 instructions to warnings. The warnings can be suppressed using -no-deprecated-warn which is probably what the Linux kernel will use for the time being.

See also the discussion on the kernel side, tracked in this issue: https://github.com/ClangBuiltLinux/linux/issues/306.


Repository:
  rL LLVM

https://reviews.llvm.org/D59733

Files:
  lib/Target/ARM/ARMInstrInfo.td
  lib/Target/ARM/AsmParser/ARMAsmParser.cpp
  lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp


Index: lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp
===================================================================
--- lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp
+++ lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp
@@ -63,6 +63,25 @@
       return true;
     }
   }
+  if (STI.getFeatureBits()[llvm::ARM::HasV7Ops] &&
+      ((MI.getOperand(0).isImm() && MI.getOperand(0).getImm() == 10) ||
+       (MI.getOperand(0).isImm() && MI.getOperand(0).getImm() == 11))) {
+    Info = "since v7, cp10 and cp11 are reserved for advanced SIMD or floating "
+           "point instructions";
+    return true;
+  }
+  return false;
+}
+
+static bool getMRCDeprecationInfo(MCInst &MI, const MCSubtargetInfo &STI,
+                                  std::string &Info) {
+  if (STI.getFeatureBits()[llvm::ARM::HasV7Ops] &&
+      ((MI.getOperand(0).isImm() && MI.getOperand(0).getImm() == 10) ||
+       (MI.getOperand(0).isImm() && MI.getOperand(0).getImm() == 11))) {
+    Info = "since v7, cp10 and cp11 are reserved for advanced SIMD or floating "
+           "point instructions";
+    return true;
+  }
   return false;
 }
 
Index: lib/Target/ARM/AsmParser/ARMAsmParser.cpp
===================================================================
--- lib/Target/ARM/AsmParser/ARMAsmParser.cpp
+++ lib/Target/ARM/AsmParser/ARMAsmParser.cpp
@@ -3665,9 +3665,6 @@
   int Num = MatchCoprocessorOperandName(Tok.getString(), 'p');
   if (Num == -1)
     return MatchOperand_NoMatch;
-  // ARMv7 and v8 don't allow cp10/cp11 due to VFP/NEON specific instructions
-  if ((hasV7Ops() || hasV8Ops()) && (Num == 10 || Num == 11))
-    return MatchOperand_NoMatch;
 
   Parser.Lex(); // Eat identifier token.
   Operands.push_back(ARMOperand::CreateCoprocNum(Num, S));
Index: lib/Target/ARM/ARMInstrInfo.td
===================================================================
--- lib/Target/ARM/ARMInstrInfo.td
+++ lib/Target/ARM/ARMInstrInfo.td
@@ -5376,7 +5376,8 @@
 def MRC : MovRCopro<"mrc", 1 /* from coprocessor to ARM core register */,
                     (outs GPRwithAPSR:$Rt),
                     (ins p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, c_imm:$CRm,
-                         imm0_7:$opc2), []>;
+                         imm0_7:$opc2), []>,
+                    ComplexDeprecationPredicate<"MRC">;
 def : ARMInstAlias<"mrc${p} $cop, $opc1, $Rt, $CRn, $CRm",
                    (MRC GPRwithAPSR:$Rt, p_imm:$cop, imm0_7:$opc1, c_imm:$CRn,
                         c_imm:$CRm, 0, pred:$p)>;


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D59733.191990.patch
Type: text/x-patch
Size: 2490 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20190323/233536e9/attachment.bin>


More information about the llvm-commits mailing list