Make SubRegIndex size mandatory, following r183020.
authorAhmed Bougacha <ahmed.bougacha@gmail.com>
Fri, 31 May 2013 23:45:26 +0000 (23:45 +0000)
committerAhmed Bougacha <ahmed.bougacha@gmail.com>
Fri, 31 May 2013 23:45:26 +0000 (23:45 +0000)
This also makes TableGen able to compute sizes/offsets of synthesized
indices representing tuples.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@183061 91177308-0d34-0410-b5e6-96231b3b80d8

14 files changed:
include/llvm/MC/MCRegisterInfo.h
include/llvm/Target/Target.td
lib/MC/MCRegisterInfo.cpp
lib/Target/AArch64/AArch64RegisterInfo.td
lib/Target/Hexagon/HexagonRegisterInfo.td
lib/Target/MSP430/MSP430RegisterInfo.td
lib/Target/Mips/MipsRegisterInfo.td
lib/Target/PowerPC/PPCRegisterInfo.td
lib/Target/R600/AMDGPURegisterInfo.td
lib/Target/Sparc/SparcRegisterInfo.td
lib/Target/SystemZ/SystemZRegisterInfo.td
utils/TableGen/CodeGenRegisters.cpp
utils/TableGen/CodeGenRegisters.h
utils/TableGen/RegisterInfoEmitter.cpp

index 002f71d5018241599e94e3eff75882d53c8a668e..3fa89c109c1c68dec1b853b3ea37f33c17fb1bb2 100644 (file)
@@ -338,12 +338,15 @@ public:
   /// otherwise.
   unsigned getSubRegIndex(unsigned RegNo, unsigned SubRegNo) const;
 
-  /// \brief Get the bit range covered by a given sub-register index.
-  /// In some cases, for instance non-contiguous synthesized indices,
-  /// there is no meaningful bit range to get, so return true if \p Offset
-  /// and \p Size were set.
-  bool getSubRegIdxCoveredBits(unsigned Idx,
-                               unsigned &Offset, unsigned &Size) const;
+  /// \brief Get the size of the bit range covered by a sub-register index.
+  /// If the index isn't continuous, return the sum of the sizes of its parts.
+  /// If the index is used to access subregisters of different sizes, return -1.
+  unsigned getSubRegIdxSize(unsigned Idx) const;
+
+  /// \brief Get the offset of the bit range covered by a sub-register index.
+  /// If an Offset doesn't make sense (the index isn't continuous, or is used to
+  /// access sub-registers at different offsets), return -1.
+  unsigned getSubRegIdxOffset(unsigned Idx) const;
 
   /// \brief Return the human-readable symbolic target-specific name for the
   /// specified physical register.
index c201f6baab0a1226fce9db8fb3e0815645ddcbda..a9644d4dd5ef3ed1c323283aa927ccfd3a180707 100644 (file)
@@ -22,13 +22,16 @@ include "llvm/IR/Intrinsics.td"
 class RegisterClass; // Forward def
 
 // SubRegIndex - Use instances of SubRegIndex to identify subregisters.
-class SubRegIndex<int size = -1, int offset = 0> {
+class SubRegIndex<int size, int offset = 0> {
   string Namespace = "";
 
   // Size - Size (in bits) of the sub-registers represented by this index.
   int Size = size;
 
   // Offset - Offset of the first bit that is part of this sub-register index.
+  // Set it to -1 if the same index is used to represent sub-registers that can
+  // be at different offsets (for example when using an index to access an
+  // element in a register tuple).
   int Offset = offset;
 
   // ComposedOf - A list of two SubRegIndex instances, [A, B].
@@ -58,7 +61,9 @@ class SubRegIndex<int size = -1, int offset = 0> {
 // ComposedSubRegIndex - A sub-register that is the result of composing A and B.
 // Offset is set to the sum of A and B's Offsets. Size is set to B's Size.
 class ComposedSubRegIndex<SubRegIndex A, SubRegIndex B>
-  : SubRegIndex<B.Size, -1> {
+  : SubRegIndex<B.Size, !if(!eq(A.Offset, -1), -1,
+                        !if(!eq(B.Offset, -1), -1,
+                            !add(A.Offset, B.Offset)))> {
   // See SubRegIndex.
   let ComposedOf = [A, B];
 }
index 06d6d9680ddc9b63f090588fdf42b278751406a9..ce79cd5c2c6bc5178f69d32ee6e4b543fb892042 100644 (file)
@@ -46,17 +46,16 @@ unsigned MCRegisterInfo::getSubRegIndex(unsigned Reg, unsigned SubReg) const {
   return 0;
 }
 
-bool MCRegisterInfo::getSubRegIdxCoveredBits(unsigned Idx, unsigned &Offset,
-                                             unsigned &Size) const {
+unsigned MCRegisterInfo::getSubRegIdxSize(unsigned Idx) const {
   assert(Idx && Idx < getNumSubRegIndices() &&
          "This is not a subregister index");
-  // Get a pointer to the corresponding SubRegIdxRanges struct.
-  const SubRegCoveredBits *Bits = &SubRegIdxRanges[Idx];
-  if (Bits->Offset == (uint16_t)-1 || Bits->Size == (uint16_t)-1)
-    return false;
-  Offset = Bits->Offset;
-  Size = Bits->Size;
-  return true;
+  return SubRegIdxRanges[Idx].Size;
+}
+
+unsigned MCRegisterInfo::getSubRegIdxOffset(unsigned Idx) const {
+  assert(Idx && Idx < getNumSubRegIndices() &&
+         "This is not a subregister index");
+  return SubRegIdxRanges[Idx].Offset;
 }
 
 int MCRegisterInfo::getDwarfRegNum(unsigned RegNum, bool isEH) const {
index bd79546371c5c6296ce376bce0916d37c9433d7e..cc2bb6135cccc6f7f8c5fd52df3b925b3cf40ec2 100644 (file)
 //===----------------------------------------------------------------------===//
 
 let Namespace = "AArch64" in {
-def sub_128 : SubRegIndex;
-def sub_64 : SubRegIndex;
-def sub_32 : SubRegIndex;
-def sub_16 : SubRegIndex;
-def sub_8  : SubRegIndex;
+def sub_128 : SubRegIndex<128>;
+def sub_64 : SubRegIndex<64>;
+def sub_32 : SubRegIndex<32>;
+def sub_16 : SubRegIndex<16>;
+def sub_8  : SubRegIndex<8>;
 
 // The VPR registers are handled as sub-registers of FPR equivalents, but
 // they're really the same thing. We give this concept a special index.
-def sub_alias : SubRegIndex;
+def sub_alias : SubRegIndex<128>;
 }
 
 // Registers are identified with 5-bit ID numbers.
index fe41fc3bc60cd5afb16ee450e2885b62f0675b8a..8ea1b7e75db7c95094d52b9be5e5489faed2acb0 100644 (file)
@@ -57,8 +57,8 @@ let Namespace = "Hexagon" in {
     let Aliases = [R];
   }
 
-  def subreg_loreg  : SubRegIndex;
-  def subreg_hireg  : SubRegIndex;
+  def subreg_loreg  : SubRegIndex<32>;
+  def subreg_hireg  : SubRegIndex<32, 32>;
 
   // Integer registers.
   def R0 : Ri< 0, "r0">, DwarfRegNum<[0]>;
index 07619d0675b8aa67012d6bd8647c277a0a7a0a18..4010781a8608d3ed67446c23dc214b002539bbf0 100644 (file)
@@ -43,7 +43,7 @@ def R13B : MSP430Reg<13, "r13">;
 def R14B : MSP430Reg<14, "r14">;
 def R15B : MSP430Reg<15, "r15">;
 
-def subreg_8bit : SubRegIndex { let Namespace = "MSP430"; }
+def subreg_8bit : SubRegIndex<8> { let Namespace = "MSP430"; }
 
 let SubRegIndices = [subreg_8bit] in {
 def PCW  : MSP430RegWithSubregs<0,  "r0",  [PCB]>;
index 229f1677c04493b68005b5bbaa694745ebb8a852..ad6912c557b0b0b1410835c7d74b3c7793bfdcfd 100644 (file)
 //  Declarations that describe the MIPS register file
 //===----------------------------------------------------------------------===//
 let Namespace = "Mips" in {
-def sub_fpeven : SubRegIndex;
-def sub_fpodd  : SubRegIndex;
-def sub_32     : SubRegIndex;
-def sub_lo     : SubRegIndex;
-def sub_hi     : SubRegIndex;
-def sub_dsp16_19 : SubRegIndex;
-def sub_dsp20    : SubRegIndex;
-def sub_dsp21    : SubRegIndex;
-def sub_dsp22    : SubRegIndex;
-def sub_dsp23    : SubRegIndex;
+def sub_fpeven : SubRegIndex<32>;
+def sub_fpodd  : SubRegIndex<32, 32>;
+def sub_32     : SubRegIndex<32>;
+def sub_lo     : SubRegIndex<32>;
+def sub_hi     : SubRegIndex<32, 32>;
+def sub_dsp16_19 : SubRegIndex<4, 16>;
+def sub_dsp20    : SubRegIndex<1, 20>;
+def sub_dsp21    : SubRegIndex<1, 21>;
+def sub_dsp22    : SubRegIndex<1, 22>;
+def sub_dsp23    : SubRegIndex<1, 23>;
 }
 
 class Unallocatable {
index 57a25f5143fa843c91b1526bb2bb8ead4b9d7eb7..b1b4f06394437f0f5737d5b5fd0448d0eff62868 100644 (file)
 //===----------------------------------------------------------------------===//
 
 let Namespace = "PPC" in {
-def sub_lt : SubRegIndex;
-def sub_gt : SubRegIndex;
-def sub_eq : SubRegIndex;
-def sub_un : SubRegIndex;
-def sub_32 : SubRegIndex;
+def sub_lt : SubRegIndex<1>;
+def sub_gt : SubRegIndex<1, 1>;
+def sub_eq : SubRegIndex<1, 2>;
+def sub_un : SubRegIndex<1, 3>;
+def sub_32 : SubRegIndex<32>;
 }
 
 
index b5aca0347fb06221b322805442e004f69aa3d5b4..835a1464395c3a627fe9db56ba190fbaeefd2939 100644 (file)
@@ -14,7 +14,8 @@
 let Namespace = "AMDGPU" in {
 
 foreach Index = 0-15 in {
-  def sub#Index : SubRegIndex;
+  // Indices are used in a variety of ways here, so don't set a size/offset.
+  def sub#Index : SubRegIndex<-1, -1>;
 }
 
 def INDIRECT_BASE_ADDR : Register <"INDIRECT_BASE_ADDR">;
index d1edcb6de1f4d3e55a1a6cfa2faadd7016288b42..b57fd3ddafb1923355f2c07ad7a2a9e2425e3894 100644 (file)
@@ -21,8 +21,8 @@ class SparcCtrlReg<string n>: Register<n> {
 }
 
 let Namespace = "SP" in {
-def sub_even : SubRegIndex;
-def sub_odd  : SubRegIndex;
+def sub_even : SubRegIndex<32>;
+def sub_odd  : SubRegIndex<32, 32>;
 }
 
 // Registers are identified with 5-bit ID numbers.
index 7795fffb640de1e9eaba088adbc92f9cb5df08fa..d65553e7500b7f376c3680df080b42429ef123fb 100644 (file)
@@ -21,9 +21,10 @@ class SystemZRegWithSubregs<string n, list<Register> subregs>
 }
 
 let Namespace = "SystemZ" in {
-def subreg_32bit  : SubRegIndex; // could also be known as "subreg_high32"
-def subreg_high   : SubRegIndex;
-def subreg_low    : SubRegIndex;
+def subreg_32bit  : SubRegIndex<32>; // could also be named "subreg_high32"
+// Indices are used in a variety of ways, so don't set an Offset.
+def subreg_high   : SubRegIndex<64, -1>;
+def subreg_low    : SubRegIndex<64, -1>;
 def subreg_low32  : ComposedSubRegIndex<subreg_low, subreg_32bit>;
 }
 
index 3eed3ffb5f4aee6149625a37bc6c30e3ac1ed21b..daa7eab658d88373ce20c6460b9f41f751490da6 100644 (file)
@@ -1092,11 +1092,24 @@ getConcatSubRegIndex(const SmallVector<CodeGenSubRegIndex*, 8> &Parts) {
 
   // None exists, synthesize one.
   std::string Name = Parts.front()->getName();
+  // Determine whether all parts are contiguous.
+  bool isContinuous = true;
+  unsigned Size = Parts.front()->Size;
+  unsigned LastOffset = Parts.front()->Offset;
+  unsigned LastSize = Parts.front()->Size;
   for (unsigned i = 1, e = Parts.size(); i != e; ++i) {
     Name += '_';
     Name += Parts[i]->getName();
+    Size += Parts[i]->Size;
+    if (Parts[i]->Offset != (LastOffset + LastSize))
+      isContinuous = false;
+    LastOffset = Parts[i]->Offset;
+    LastSize = Parts[i]->Size;
   }
-  return Idx = createSubRegIndex(Name, Parts.front()->getNamespace());
+  Idx = createSubRegIndex(Name, Parts.front()->getNamespace());
+  Idx->Size = Size;
+  Idx->Offset = isContinuous ? Parts.front()->Offset : -1;
+  return Idx;
 }
 
 void CodeGenRegBank::computeComposites() {
index c83455149a6fdddbd3ecb147b1a872ce27c35c06..f9edc6553ac9d80db8cda370b74846a4b15a6bab 100644 (file)
@@ -37,10 +37,10 @@ namespace llvm {
     Record *const TheDef;
     std::string Name;
     std::string Namespace;
-    uint16_t Size;
-    uint16_t Offset;
 
   public:
+    uint16_t Size;
+    uint16_t Offset;
     const unsigned EnumValue;
     unsigned LaneMask;
 
@@ -54,8 +54,6 @@ namespace llvm {
     const std::string &getName() const { return Name; }
     const std::string &getNamespace() const { return Namespace; }
     std::string getQualifiedName() const;
-    uint16_t getSize() const { return Size; }
-    uint16_t getOffset() const { return Offset; }
 
     // Order CodeGenSubRegIndex pointers by EnumValue.
     struct Less {
index 9978237a185a9e001887df8ed0665414d4077372..1a6cc3a01c2d5efac8b0726aceccc2d104cb0d36 100644 (file)
@@ -798,8 +798,8 @@ RegisterInfoEmitter::runMCDesc(raw_ostream &OS, CodeGenTarget &Target,
   for (ArrayRef<CodeGenSubRegIndex*>::const_iterator
          SRI = SubRegIndices.begin(), SRE = SubRegIndices.end();
          SRI != SRE; ++SRI) {
-    OS << "  { " << (*SRI)->getOffset() << ", "
-                 << (*SRI)->getSize()
+    OS << "  { " << (*SRI)->Offset << ", "
+                 << (*SRI)->Size
        << " },\t// " << (*SRI)->getName() << "\n";
   }
   OS << "};\n\n";