Home | History | Annotate | Download | only in ADT
      1 //===- llvm/ADT/ValueMap.h - Safe map from Values to data -------*- C++ -*-===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 // This file defines the ValueMap class.  ValueMap maps Value* or any subclass
     11 // to an arbitrary other type.  It provides the DenseMap interface but updates
     12 // itself to remain safe when keys are RAUWed or deleted.  By default, when a
     13 // key is RAUWed from V1 to V2, the old mapping V1->target is removed, and a new
     14 // mapping V2->target is added.  If V2 already existed, its old target is
     15 // overwritten.  When a key is deleted, its mapping is removed.
     16 //
     17 // You can override a ValueMap's Config parameter to control exactly what
     18 // happens on RAUW and destruction and to get called back on each event.  It's
     19 // legal to call back into the ValueMap from a Config's callbacks.  Config
     20 // parameters should inherit from ValueMapConfig<KeyT> to get default
     21 // implementations of all the methods ValueMap uses.  See ValueMapConfig for
     22 // documentation of the functions you can override.
     23 //
     24 //===----------------------------------------------------------------------===//
     25 
     26 #ifndef LLVM_ADT_VALUEMAP_H
     27 #define LLVM_ADT_VALUEMAP_H
     28 
     29 #include "llvm/ADT/DenseMap.h"
     30 #include "llvm/Support/ValueHandle.h"
     31 #include "llvm/Support/type_traits.h"
     32 #include "llvm/Support/Mutex.h"
     33 
     34 #include <iterator>
     35 
     36 namespace llvm {
     37 
     38 template<typename KeyT, typename ValueT, typename Config, typename ValueInfoT>
     39 class ValueMapCallbackVH;
     40 
     41 template<typename DenseMapT, typename KeyT>
     42 class ValueMapIterator;
     43 template<typename DenseMapT, typename KeyT>
     44 class ValueMapConstIterator;
     45 
     46 /// This class defines the default behavior for configurable aspects of
     47 /// ValueMap<>.  User Configs should inherit from this class to be as compatible
     48 /// as possible with future versions of ValueMap.
     49 template<typename KeyT>
     50 struct ValueMapConfig {
     51   /// If FollowRAUW is true, the ValueMap will update mappings on RAUW. If it's
     52   /// false, the ValueMap will leave the original mapping in place.
     53   enum { FollowRAUW = true };
     54 
     55   // All methods will be called with a first argument of type ExtraData.  The
     56   // default implementations in this class take a templated first argument so
     57   // that users' subclasses can use any type they want without having to
     58   // override all the defaults.
     59   struct ExtraData {};
     60 
     61   template<typename ExtraDataT>
     62   static void onRAUW(const ExtraDataT & /*Data*/, KeyT /*Old*/, KeyT /*New*/) {}
     63   template<typename ExtraDataT>
     64   static void onDelete(const ExtraDataT &/*Data*/, KeyT /*Old*/) {}
     65 
     66   /// Returns a mutex that should be acquired around any changes to the map.
     67   /// This is only acquired from the CallbackVH (and held around calls to onRAUW
     68   /// and onDelete) and not inside other ValueMap methods.  NULL means that no
     69   /// mutex is necessary.
     70   template<typename ExtraDataT>
     71   static sys::Mutex *getMutex(const ExtraDataT &/*Data*/) { return NULL; }
     72 };
     73 
     74 /// See the file comment.
     75 template<typename KeyT, typename ValueT, typename Config = ValueMapConfig<KeyT>,
     76          typename ValueInfoT = DenseMapInfo<ValueT> >
     77 class ValueMap {
     78   friend class ValueMapCallbackVH<KeyT, ValueT, Config, ValueInfoT>;
     79   typedef ValueMapCallbackVH<KeyT, ValueT, Config, ValueInfoT> ValueMapCVH;
     80   typedef DenseMap<ValueMapCVH, ValueT, DenseMapInfo<ValueMapCVH>,
     81                    ValueInfoT> MapT;
     82   typedef typename Config::ExtraData ExtraData;
     83   MapT Map;
     84   ExtraData Data;
     85   ValueMap(const ValueMap&); // DO NOT IMPLEMENT
     86   ValueMap& operator=(const ValueMap&); // DO NOT IMPLEMENT
     87 public:
     88   typedef KeyT key_type;
     89   typedef ValueT mapped_type;
     90   typedef std::pair<KeyT, ValueT> value_type;
     91 
     92   explicit ValueMap(unsigned NumInitBuckets = 64)
     93     : Map(NumInitBuckets), Data() {}
     94   explicit ValueMap(const ExtraData &Data, unsigned NumInitBuckets = 64)
     95     : Map(NumInitBuckets), Data(Data) {}
     96 
     97   ~ValueMap() {}
     98 
     99   typedef ValueMapIterator<MapT, KeyT> iterator;
    100   typedef ValueMapConstIterator<MapT, KeyT> const_iterator;
    101   inline iterator begin() { return iterator(Map.begin()); }
    102   inline iterator end() { return iterator(Map.end()); }
    103   inline const_iterator begin() const { return const_iterator(Map.begin()); }
    104   inline const_iterator end() const { return const_iterator(Map.end()); }
    105 
    106   bool empty() const { return Map.empty(); }
    107   unsigned size() const { return Map.size(); }
    108 
    109   /// Grow the map so that it has at least Size buckets. Does not shrink
    110   void resize(size_t Size) { Map.resize(Size); }
    111 
    112   void clear() { Map.clear(); }
    113 
    114   /// count - Return true if the specified key is in the map.
    115   bool count(const KeyT &Val) const {
    116     return Map.count(Wrap(Val));
    117   }
    118 
    119   iterator find(const KeyT &Val) {
    120     return iterator(Map.find(Wrap(Val)));
    121   }
    122   const_iterator find(const KeyT &Val) const {
    123     return const_iterator(Map.find(Wrap(Val)));
    124   }
    125 
    126   /// lookup - Return the entry for the specified key, or a default
    127   /// constructed value if no such entry exists.
    128   ValueT lookup(const KeyT &Val) const {
    129     return Map.lookup(Wrap(Val));
    130   }
    131 
    132   // Inserts key,value pair into the map if the key isn't already in the map.
    133   // If the key is already in the map, it returns false and doesn't update the
    134   // value.
    135   std::pair<iterator, bool> insert(const std::pair<KeyT, ValueT> &KV) {
    136     std::pair<typename MapT::iterator, bool> map_result=
    137       Map.insert(std::make_pair(Wrap(KV.first), KV.second));
    138     return std::make_pair(iterator(map_result.first), map_result.second);
    139   }
    140 
    141   /// insert - Range insertion of pairs.
    142   template<typename InputIt>
    143   void insert(InputIt I, InputIt E) {
    144     for (; I != E; ++I)
    145       insert(*I);
    146   }
    147 
    148 
    149   bool erase(const KeyT &Val) {
    150     return Map.erase(Wrap(Val));
    151   }
    152   void erase(iterator I) {
    153     return Map.erase(I.base());
    154   }
    155 
    156   value_type& FindAndConstruct(const KeyT &Key) {
    157     return Map.FindAndConstruct(Wrap(Key));
    158   }
    159 
    160   ValueT &operator[](const KeyT &Key) {
    161     return Map[Wrap(Key)];
    162   }
    163 
    164   /// isPointerIntoBucketsArray - Return true if the specified pointer points
    165   /// somewhere into the ValueMap's array of buckets (i.e. either to a key or
    166   /// value in the ValueMap).
    167   bool isPointerIntoBucketsArray(const void *Ptr) const {
    168     return Map.isPointerIntoBucketsArray(Ptr);
    169   }
    170 
    171   /// getPointerIntoBucketsArray() - Return an opaque pointer into the buckets
    172   /// array.  In conjunction with the previous method, this can be used to
    173   /// determine whether an insertion caused the ValueMap to reallocate.
    174   const void *getPointerIntoBucketsArray() const {
    175     return Map.getPointerIntoBucketsArray();
    176   }
    177 
    178 private:
    179   // Takes a key being looked up in the map and wraps it into a
    180   // ValueMapCallbackVH, the actual key type of the map.  We use a helper
    181   // function because ValueMapCVH is constructed with a second parameter.
    182   ValueMapCVH Wrap(KeyT key) const {
    183     // The only way the resulting CallbackVH could try to modify *this (making
    184     // the const_cast incorrect) is if it gets inserted into the map.  But then
    185     // this function must have been called from a non-const method, making the
    186     // const_cast ok.
    187     return ValueMapCVH(key, const_cast<ValueMap*>(this));
    188   }
    189 };
    190 
    191 // This CallbackVH updates its ValueMap when the contained Value changes,
    192 // according to the user's preferences expressed through the Config object.
    193 template<typename KeyT, typename ValueT, typename Config, typename ValueInfoT>
    194 class ValueMapCallbackVH : public CallbackVH {
    195   friend class ValueMap<KeyT, ValueT, Config, ValueInfoT>;
    196   friend struct DenseMapInfo<ValueMapCallbackVH>;
    197   typedef ValueMap<KeyT, ValueT, Config, ValueInfoT> ValueMapT;
    198   typedef typename llvm::remove_pointer<KeyT>::type KeySansPointerT;
    199 
    200   ValueMapT *Map;
    201 
    202   ValueMapCallbackVH(KeyT Key, ValueMapT *Map)
    203       : CallbackVH(const_cast<Value*>(static_cast<const Value*>(Key))),
    204         Map(Map) {}
    205 
    206 public:
    207   KeyT Unwrap() const { return cast_or_null<KeySansPointerT>(getValPtr()); }
    208 
    209   virtual void deleted() {
    210     // Make a copy that won't get changed even when *this is destroyed.
    211     ValueMapCallbackVH Copy(*this);
    212     sys::Mutex *M = Config::getMutex(Copy.Map->Data);
    213     if (M)
    214       M->acquire();
    215     Config::onDelete(Copy.Map->Data, Copy.Unwrap());  // May destroy *this.
    216     Copy.Map->Map.erase(Copy);  // Definitely destroys *this.
    217     if (M)
    218       M->release();
    219   }
    220   virtual void allUsesReplacedWith(Value *new_key) {
    221     assert(isa<KeySansPointerT>(new_key) &&
    222            "Invalid RAUW on key of ValueMap<>");
    223     // Make a copy that won't get changed even when *this is destroyed.
    224     ValueMapCallbackVH Copy(*this);
    225     sys::Mutex *M = Config::getMutex(Copy.Map->Data);
    226     if (M)
    227       M->acquire();
    228 
    229     KeyT typed_new_key = cast<KeySansPointerT>(new_key);
    230     // Can destroy *this:
    231     Config::onRAUW(Copy.Map->Data, Copy.Unwrap(), typed_new_key);
    232     if (Config::FollowRAUW) {
    233       typename ValueMapT::MapT::iterator I = Copy.Map->Map.find(Copy);
    234       // I could == Copy.Map->Map.end() if the onRAUW callback already
    235       // removed the old mapping.
    236       if (I != Copy.Map->Map.end()) {
    237         ValueT Target(I->second);
    238         Copy.Map->Map.erase(I);  // Definitely destroys *this.
    239         Copy.Map->insert(std::make_pair(typed_new_key, Target));
    240       }
    241     }
    242     if (M)
    243       M->release();
    244   }
    245 };
    246 
    247 template<typename KeyT, typename ValueT, typename Config, typename ValueInfoT>
    248 struct DenseMapInfo<ValueMapCallbackVH<KeyT, ValueT, Config, ValueInfoT> > {
    249   typedef ValueMapCallbackVH<KeyT, ValueT, Config, ValueInfoT> VH;
    250   typedef DenseMapInfo<KeyT> PointerInfo;
    251 
    252   static inline VH getEmptyKey() {
    253     return VH(PointerInfo::getEmptyKey(), NULL);
    254   }
    255   static inline VH getTombstoneKey() {
    256     return VH(PointerInfo::getTombstoneKey(), NULL);
    257   }
    258   static unsigned getHashValue(const VH &Val) {
    259     return PointerInfo::getHashValue(Val.Unwrap());
    260   }
    261   static bool isEqual(const VH &LHS, const VH &RHS) {
    262     return LHS == RHS;
    263   }
    264 };
    265 
    266 
    267 template<typename DenseMapT, typename KeyT>
    268 class ValueMapIterator :
    269     public std::iterator<std::forward_iterator_tag,
    270                          std::pair<KeyT, typename DenseMapT::mapped_type>,
    271                          ptrdiff_t> {
    272   typedef typename DenseMapT::iterator BaseT;
    273   typedef typename DenseMapT::mapped_type ValueT;
    274   BaseT I;
    275 public:
    276   ValueMapIterator() : I() {}
    277 
    278   ValueMapIterator(BaseT I) : I(I) {}
    279 
    280   BaseT base() const { return I; }
    281 
    282   struct ValueTypeProxy {
    283     const KeyT first;
    284     ValueT& second;
    285     ValueTypeProxy *operator->() { return this; }
    286     operator std::pair<KeyT, ValueT>() const {
    287       return std::make_pair(first, second);
    288     }
    289   };
    290 
    291   ValueTypeProxy operator*() const {
    292     ValueTypeProxy Result = {I->first.Unwrap(), I->second};
    293     return Result;
    294   }
    295 
    296   ValueTypeProxy operator->() const {
    297     return operator*();
    298   }
    299 
    300   bool operator==(const ValueMapIterator &RHS) const {
    301     return I == RHS.I;
    302   }
    303   bool operator!=(const ValueMapIterator &RHS) const {
    304     return I != RHS.I;
    305   }
    306 
    307   inline ValueMapIterator& operator++() {  // Preincrement
    308     ++I;
    309     return *this;
    310   }
    311   ValueMapIterator operator++(int) {  // Postincrement
    312     ValueMapIterator tmp = *this; ++*this; return tmp;
    313   }
    314 };
    315 
    316 template<typename DenseMapT, typename KeyT>
    317 class ValueMapConstIterator :
    318     public std::iterator<std::forward_iterator_tag,
    319                          std::pair<KeyT, typename DenseMapT::mapped_type>,
    320                          ptrdiff_t> {
    321   typedef typename DenseMapT::const_iterator BaseT;
    322   typedef typename DenseMapT::mapped_type ValueT;
    323   BaseT I;
    324 public:
    325   ValueMapConstIterator() : I() {}
    326   ValueMapConstIterator(BaseT I) : I(I) {}
    327   ValueMapConstIterator(ValueMapIterator<DenseMapT, KeyT> Other)
    328     : I(Other.base()) {}
    329 
    330   BaseT base() const { return I; }
    331 
    332   struct ValueTypeProxy {
    333     const KeyT first;
    334     const ValueT& second;
    335     ValueTypeProxy *operator->() { return this; }
    336     operator std::pair<KeyT, ValueT>() const {
    337       return std::make_pair(first, second);
    338     }
    339   };
    340 
    341   ValueTypeProxy operator*() const {
    342     ValueTypeProxy Result = {I->first.Unwrap(), I->second};
    343     return Result;
    344   }
    345 
    346   ValueTypeProxy operator->() const {
    347     return operator*();
    348   }
    349 
    350   bool operator==(const ValueMapConstIterator &RHS) const {
    351     return I == RHS.I;
    352   }
    353   bool operator!=(const ValueMapConstIterator &RHS) const {
    354     return I != RHS.I;
    355   }
    356 
    357   inline ValueMapConstIterator& operator++() {  // Preincrement
    358     ++I;
    359     return *this;
    360   }
    361   ValueMapConstIterator operator++(int) {  // Postincrement
    362     ValueMapConstIterator tmp = *this; ++*this; return tmp;
    363   }
    364 };
    365 
    366 } // end namespace llvm
    367 
    368 #endif
    369