[llvm] r175370 - Turn the enum attributes DenseSet in AttrBuilder into a set of bits.

Benjamin Kramer benny.kra at googlemail.com
Sat Feb 16 11:13:19 PST 2013


Author: d0k
Date: Sat Feb 16 13:13:18 2013
New Revision: 175370

URL: http://llvm.org/viewvc/llvm-project?rev=175370&view=rev
Log:
Turn the enum attributes DenseSet in AttrBuilder into a set of bits.

Avoids malloc and is a lot denser. We lose iteration over target independent
attributes, but that's a strange interface anyways and didn't have any users
outside of AttrBuilder.

Modified:
    llvm/trunk/include/llvm/IR/Attributes.h
    llvm/trunk/lib/IR/Attributes.cpp

Modified: llvm/trunk/include/llvm/IR/Attributes.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/IR/Attributes.h?rev=175370&r1=175369&r2=175370&view=diff
==============================================================================
--- llvm/trunk/include/llvm/IR/Attributes.h (original)
+++ llvm/trunk/include/llvm/IR/Attributes.h Sat Feb 16 13:13:18 2013
@@ -17,8 +17,8 @@
 #define LLVM_IR_ATTRIBUTES_H
 
 #include "llvm/ADT/ArrayRef.h"
-#include "llvm/ADT/DenseSet.h"
 #include "llvm/ADT/FoldingSet.h"
+#include "llvm/Support/PointerLikeTypeTraits.h"
 #include <cassert>
 #include <map>
 #include <string>
@@ -30,6 +30,7 @@ class AttributeImpl;
 class AttributeSetImpl;
 class AttributeSetNode;
 class Constant;
+template<typename T> struct DenseMapInfo;
 class LLVMContext;
 class Type;
 
@@ -101,9 +102,6 @@ public:
     ZExt,                  ///< Zero extended before/after call
 
     EndAttrKinds,          ///< Sentinal value useful for loops
-
-    AttrKindEmptyKey,      ///< Empty key value for DenseMapInfo
-    AttrKindTombstoneKey   ///< Tombstone key value for DenseMapInfo
   };
 private:
   AttributeImpl *pImpl;
@@ -187,26 +185,6 @@ public:
 
 //===----------------------------------------------------------------------===//
 /// \class
-/// \brief Provide DenseMapInfo for Attribute::AttrKinds. This is used by
-/// AttrBuilder.
-template<> struct DenseMapInfo<Attribute::AttrKind> {
-  static inline Attribute::AttrKind getEmptyKey() {
-    return Attribute::AttrKindEmptyKey;
-  }
-  static inline Attribute::AttrKind getTombstoneKey() {
-    return Attribute::AttrKindTombstoneKey;
-  }
-  static unsigned getHashValue(const Attribute::AttrKind &Val) {
-    return Val * 37U;
-  }
-  static bool isEqual(const Attribute::AttrKind &LHS,
-                      const Attribute::AttrKind &RHS) {
-    return LHS == RHS;
-  }
-};
-
-//===----------------------------------------------------------------------===//
-/// \class
 /// \brief This class holds the attributes for a function, its return value, and
 /// its parameters. You access the attributes for each of them via an index into
 /// the AttributeSet object. The function attributes are at index
@@ -400,16 +378,17 @@ template<> struct DenseMapInfo<Attribute
 /// value, however, is not. So this can be used as a quick way to test for
 /// equality, presence of attributes, etc.
 class AttrBuilder {
-  DenseSet<Attribute::AttrKind> Attrs;
+  uint64_t Attrs;
   std::map<std::string, std::string> TargetDepAttrs;
   uint64_t Alignment;
   uint64_t StackAlignment;
 public:
-  AttrBuilder() : Alignment(0), StackAlignment(0) {}
-  explicit AttrBuilder(uint64_t Val) : Alignment(0), StackAlignment(0) {
+  AttrBuilder() : Attrs(0), Alignment(0), StackAlignment(0) {}
+  explicit AttrBuilder(uint64_t Val)
+    : Attrs(0), Alignment(0), StackAlignment(0) {
     addRawValue(Val);
   }
-  AttrBuilder(const Attribute &A) : Alignment(0), StackAlignment(0) {
+  AttrBuilder(const Attribute &A) : Attrs(0), Alignment(0), StackAlignment(0) {
     addAttribute(A);
   }
   AttrBuilder(AttributeSet AS, unsigned Idx);
@@ -442,7 +421,11 @@ public:
   AttrBuilder &merge(const AttrBuilder &B);
 
   /// \brief Return true if the builder has the specified attribute.
-  bool contains(Attribute::AttrKind A) const;
+  bool contains(Attribute::AttrKind A) const {
+    assert((unsigned)A < 64 && A < Attribute::EndAttrKinds &&
+           "Attribute out of range!");
+    return Attrs & (1ULL << A);
+  }
 
   /// \brief Return true if the builder has the specified target-dependent
   /// attribute.
@@ -472,17 +455,9 @@ public:
   /// the form used internally in Attribute.
   AttrBuilder &addStackAlignmentAttr(unsigned Align);
 
-  // Iterators for target-independent attributes.
-  typedef DenseSet<Attribute::AttrKind>::iterator       iterator;
-  typedef DenseSet<Attribute::AttrKind>::const_iterator const_iterator;
-
-  iterator begin()             { return Attrs.begin(); }
-  iterator end()               { return Attrs.end(); }
-
-  const_iterator begin() const { return Attrs.begin(); }
-  const_iterator end() const   { return Attrs.end(); }
-
-  bool empty() const           { return Attrs.empty(); }
+  /// \brief Return true if the builder contains no target-independent
+  /// attributes.
+  bool empty() const { return Attrs == 0; }
 
   // Iterators for target-dependent attributes.
   typedef std::pair<std::string, std::string>                td_type;

Modified: llvm/trunk/lib/IR/Attributes.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/IR/Attributes.cpp?rev=175370&r1=175369&r2=175370&view=diff
==============================================================================
--- llvm/trunk/lib/IR/Attributes.cpp (original)
+++ llvm/trunk/lib/IR/Attributes.cpp Sat Feb 16 13:13:18 2013
@@ -355,8 +355,6 @@ uint64_t AttributeImpl::getAttrMask(Attr
   // FIXME: Remove this.
   switch (Val) {
   case Attribute::EndAttrKinds:
-  case Attribute::AttrKindEmptyKey:
-  case Attribute::AttrKindTombstoneKey:
     llvm_unreachable("Synthetic enumerators which should never get here");
 
   case Attribute::None:            return 0;
@@ -597,8 +595,11 @@ AttributeSet AttributeSet::get(LLVMConte
 
   // Add target-independent attributes.
   SmallVector<std::pair<unsigned, Attribute>, 8> Attrs;
-  for (AttrBuilder::iterator I = B.begin(), E = B.end(); I != E; ++I) {
-    Attribute::AttrKind Kind = *I;
+  for (Attribute::AttrKind Kind = Attribute::None;
+       Kind != Attribute::EndAttrKinds; ++Kind) {
+    if (!B.contains(Kind))
+      continue;
+
     if (Kind == Attribute::Alignment)
       Attrs.push_back(std::make_pair(Idx, Attribute::
                                      getWithAlignment(C, B.getAlignment())));
@@ -907,7 +908,7 @@ void AttributeSet::dump() const {
 //===----------------------------------------------------------------------===//
 
 AttrBuilder::AttrBuilder(AttributeSet AS, unsigned Idx)
-  : Alignment(0), StackAlignment(0) {
+  : Attrs(0), Alignment(0), StackAlignment(0) {
   AttributeSetImpl *pImpl = AS.pImpl;
   if (!pImpl) return;
 
@@ -923,14 +924,16 @@ AttrBuilder::AttrBuilder(AttributeSet AS
 }
 
 void AttrBuilder::clear() {
-  Attrs.clear();
+  Attrs = 0;
   Alignment = StackAlignment = 0;
 }
 
 AttrBuilder &AttrBuilder::addAttribute(Attribute::AttrKind Val) {
+  assert((unsigned)Val < 64 && Val < Attribute::EndAttrKinds &&
+         "Attribute out of range!");
   assert(Val != Attribute::Alignment && Val != Attribute::StackAlignment &&
          "Adding alignment attribute without adding alignment value!");
-  Attrs.insert(Val);
+  Attrs |= 1ULL << Val;
   return *this;
 }
 
@@ -941,7 +944,7 @@ AttrBuilder &AttrBuilder::addAttribute(A
   }
 
   Attribute::AttrKind Kind = Attr.getKindAsEnum();
-  Attrs.insert(Kind);
+  Attrs |= 1ULL << Kind;
 
   if (Kind == Attribute::Alignment)
     Alignment = Attr.getAlignment();
@@ -956,7 +959,9 @@ AttrBuilder &AttrBuilder::addAttribute(S
 }
 
 AttrBuilder &AttrBuilder::removeAttribute(Attribute::AttrKind Val) {
-  Attrs.erase(Val);
+  assert((unsigned)Val < 64 && Val < Attribute::EndAttrKinds &&
+         "Attribute out of range!");
+  Attrs &= ~(1ULL << Val);
 
   if (Val == Attribute::Alignment)
     Alignment = 0;
@@ -980,7 +985,7 @@ AttrBuilder &AttrBuilder::removeAttribut
     Attribute Attr = *I;
     if (Attr.isEnumAttribute() || Attr.isAlignAttribute()) {
       Attribute::AttrKind Kind = I->getKindAsEnum();
-      Attrs.erase(Kind);
+      Attrs &= ~(1ULL << Kind);
 
       if (Kind == Attribute::Alignment)
         Alignment = 0;
@@ -1011,7 +1016,7 @@ AttrBuilder &AttrBuilder::addAlignmentAt
   assert(isPowerOf2_32(Align) && "Alignment must be a power of two.");
   assert(Align <= 0x40000000 && "Alignment too large.");
 
-  Attrs.insert(Attribute::Alignment);
+  Attrs |= 1ULL << Attribute::Alignment;
   Alignment = Align;
   return *this;
 }
@@ -1023,7 +1028,7 @@ AttrBuilder &AttrBuilder::addStackAlignm
   assert(isPowerOf2_32(Align) && "Alignment must be a power of two.");
   assert(Align <= 0x100 && "Alignment too large.");
 
-  Attrs.insert(Attribute::StackAlignment);
+  Attrs |= 1ULL << Attribute::StackAlignment;
   StackAlignment = Align;
   return *this;
 }
@@ -1036,7 +1041,7 @@ AttrBuilder &AttrBuilder::merge(const At
   if (!StackAlignment)
     StackAlignment = B.StackAlignment;
 
-  Attrs.insert(B.Attrs.begin(), B.Attrs.end());
+  Attrs |= B.Attrs;
 
   for (td_const_iterator I = B.TargetDepAttrs.begin(),
          E = B.TargetDepAttrs.end(); I != E; ++I)
@@ -1045,16 +1050,12 @@ AttrBuilder &AttrBuilder::merge(const At
   return *this;
 }
 
-bool AttrBuilder::contains(Attribute::AttrKind A) const {
-  return Attrs.count(A);
-}
-
 bool AttrBuilder::contains(StringRef A) const {
   return TargetDepAttrs.find(A) != TargetDepAttrs.end();
 }
 
 bool AttrBuilder::hasAttributes() const {
-  return !Attrs.empty() || !TargetDepAttrs.empty();
+  return Attrs != 0 || !TargetDepAttrs.empty();
 }
 
 bool AttrBuilder::hasAttributes(AttributeSet A, uint64_t Index) const {
@@ -1071,7 +1072,7 @@ bool AttrBuilder::hasAttributes(Attribut
        I != E; ++I) {
     Attribute Attr = *I;
     if (Attr.isEnumAttribute() || Attr.isAlignAttribute()) {
-      if (Attrs.count(I->getKindAsEnum()))
+      if (Attrs & (1ULL << I->getKindAsEnum()))
         return true;
     } else {
       assert(Attr.isStringAttribute() && "Invalid attribute kind!");
@@ -1087,10 +1088,8 @@ bool AttrBuilder::hasAlignmentAttr() con
 }
 
 bool AttrBuilder::operator==(const AttrBuilder &B) {
-  for (DenseSet<Attribute::AttrKind>::iterator I = Attrs.begin(),
-         E = Attrs.end(); I != E; ++I)
-    if (!B.Attrs.count(*I))
-      return false;
+  if (Attrs != B.Attrs)
+    return false;
 
   for (td_const_iterator I = TargetDepAttrs.begin(),
          E = TargetDepAttrs.end(); I != E; ++I)
@@ -1107,7 +1106,7 @@ AttrBuilder &AttrBuilder::addRawValue(ui
   for (Attribute::AttrKind I = Attribute::None; I != Attribute::EndAttrKinds;
        I = Attribute::AttrKind(I + 1)) {
     if (uint64_t A = (Val & AttributeImpl::getAttrMask(I))) {
-      Attrs.insert(I);
+      Attrs |= 1ULL << I;
  
       if (I == Attribute::Alignment)
         Alignment = 1ULL << ((A >> 16) - 1);





More information about the llvm-commits mailing list