OpenASIP  2.0
SafePointer.hh
Go to the documentation of this file.
1 /*
2  Copyright (c) 2002-2009 Tampere University.
3 
4  This file is part of TTA-Based Codesign Environment (TCE).
5 
6  Permission is hereby granted, free of charge, to any person obtaining a
7  copy of this software and associated documentation files (the "Software"),
8  to deal in the Software without restriction, including without limitation
9  the rights to use, copy, modify, merge, publish, distribute, sublicense,
10  and/or sell copies of the Software, and to permit persons to whom the
11  Software is furnished to do so, subject to the following conditions:
12 
13  The above copyright notice and this permission notice shall be included in
14  all copies or substantial portions of the Software.
15 
16  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  DEALINGS IN THE SOFTWARE.
23  */
24 /**
25  * @file SafePointer.hh
26  *
27  * Declaration of SafePointer class and utility classes and types related
28  * to ReferenceManager.
29  *
30  * @author Pekka Jääskeläinen 2003 (pjaaskel-no.spam-cs.tut.fi)
31  * @note reviewed 29 Aug 2003 by rm, ml, ac, tr
32  *
33  * @note rating: yellow
34  */
35 
36 #ifndef TTA_SAFEPOINTER_HH
37 #define TTA_SAFEPOINTER_HH
38 
39 #include <cstddef> // NULL
40 #include <set>
41 #include <map>
42 #include <list>
43 #include <iterator>
44 #include <sstream>
45 
46 //#include "hash_map.hh"
47 #include "Application.hh"
48 #include "ReferenceKey.hh"
49 #include "Exception.hh" // IllegalParameters, UnresolvedReference
50 
51 namespace TPEF {
52 
53 class SafePointable;
54 
55 /**
56  *
57  * Contains classes, utility classes and types related to reference managing.
58  *
59  */
60 namespace ReferenceManager {
61 
62 class SafePointer;
63 
64 ///////////////////////////////////////////////////////////////////////////////
65 // SafePointerList
66 ///////////////////////////////////////////////////////////////////////////////
67 /**
68  * List of SafePointers that are all pointing to the same object.
69  *
70  */
72 public:
73  /// Type of the container to hold the SafePointers in.
74  typedef std::list<SafePointer*> SafePointerListType;
75 
76  /// Type of the list length value.
77  typedef std::string::size_type LengthType;
78 
81 
82  virtual ~SafePointerList();
83 
84  void setReference(const SafePointable* obj);
85  SafePointable* reference() const;
86 
87  void append(SafePointer* newSafePointer);
88  void append(SafePointerList* anotherSafePointerList);
89 
90  SafePointer* front() const;
91 
92  void cleanup();
93  void cleanupDead();
94 
95  LengthType length() const;
96 
97 private:
98  /// Object that SafePointers in this list are pointing to.
100 
101  /// Container for SafePointers.
103 };
104 
105 /**
106  * Class containing all the hash functions if hash_map is
107  * used. However the use of hash_map will make program very slow
108  * unless MapTools::containsValue() is not optimised for
109  * hash_tables or that function should be circumvented.
110  */
112 public:
113  size_t operator()(const SectionIndexKey& key) const {
114  return key.index()^
115  (static_cast<size_t>(key.sectionId()) <<
116  ((sizeof(size_t) - sizeof(SectionId)) *
117  BYTE_BITWIDTH));
118  }
119 
120  size_t operator()(const SectionOffsetKey& key) const {
121  return key.offset()^
122  (static_cast<size_t>(key.sectionId()) <<
123  ((sizeof(size_t) - sizeof(SectionId)) *
124  BYTE_BITWIDTH));
125  }
126 
127  size_t operator()(const FileOffsetKey& key) const {
128  return key.fileOffset();
129  }
130 
131  size_t operator()(const SectionKey& key) const {
132  return key.sectionId();
133  }
134 
135  size_t operator()(const SafePointable* const & key) const {
136  return reinterpret_cast<size_t>(key);
137  }
138 };
139 
140 // TODO: for hash map implementation check SafePointer.cc line 424 TODO
141 // MapTools::containsValue call takes very long time for hash maps..
142 
143 /// Unordered set of SafePointers.
144 typedef std::set<SafePointer*> SafePointerSet;
145 
146 /// Map for SafePointers that are requested using SectionIndexKeys.
147 typedef std::map<SectionIndexKey, SafePointerList*> SectionIndexMap;
148 //typedef hash_map<SectionIndexKey, SafePointerList*,
149 // HashFunctions> SectionIndexMap;
150 
151 /// Map for SafePointers that are requested using SectionOffsetKeys.
152 typedef std::map<SectionOffsetKey, SafePointerList*> SectionOffsetMap;
153 //typedef hash_map<SectionOffsetKey, SafePointerList*,
154 // HashFunctions> SectionOffsetMap;
155 
156 /// Map for SafePointers that are requested using FileOffsetKeys.
157 typedef std::map<FileOffsetKey, SafePointerList*> FileOffsetMap;
158 //typedef hash_map<FileOffsetKey, SafePointerList*,
159 // HashFunctions> FileOffsetMap;
160 
161 /// Map for SafePointers that are requested using SectionKeys.
162 typedef std::map<SectionKey, SafePointerList*> SectionMap;
163 //typedef hash_map<SectionKey, SafePointerList*,
164 // HashFunctions> SectionMap;
165 
166 
167 /// Map for resolved references, that is SafePointers that are pointing to
168 /// the created object.
169 typedef std::map<const SafePointable*, SafePointerList*> ReferenceMap;
170 //typedef hash_map<const SafePointable*, SafePointerList*,
171 // HashFunctions> ReferenceMap;
172 
173 
174 ///////////////////////////////////////////////////////////////////////////////
175 // SafePointer
176 ///////////////////////////////////////////////////////////////////////////////
177 /**
178  * Indirection for object references.
179  *
180  * Allows updating references later on, thus allows referencing objects that
181  * are created later. Helps with the dangling pointers problem, too.
182  *
183  * References to objects that are not created yet are made with different kind
184  * of keys. These keys refer for example to sections and offsets in source
185  * binary file while reading the binary. After the binary is read and the
186  * object model of binary is constructed, these keys and keytables have no use.
187  */
188 class SafePointer {
189 public:
190  virtual ~SafePointer();
191 
192  SafePointable* pointer() const;
193  void setPointer(SafePointable* object);
194 
195  static bool isAlive(SafePointer* pointerToCheck);
196  static bool isReferenced(const SafePointable* object);
197 
198  static void addObjectReference(
199  SectionIndexKey key, const SafePointable* obj);
200  static void addObjectReference(
201  SectionOffsetKey key, const SafePointable* obj);
202  static void addObjectReference(FileOffsetKey key, const SafePointable* obj);
203  static void addObjectReference(SectionKey key, const SafePointable* obj);
204 
207  static FileOffsetKey fileOffsetKeyFor(const SafePointable* obj);
208  static SectionKey sectionKeyFor(const SafePointable* obj);
209 
210  static void notifyDeleted(const SafePointable* obj);
211  static void notifyDeleted(SafePointer* safePointer);
212 
213  static void resolve();
214 
215  static void cleanupKeyTables();
216  static void cleanup();
217 
218  template <typename MapType>
219  static bool unresolvedReferences(const MapType& mapToCheck,
220  const ReferenceKey **unresolvedKey);
221 
222  static const SafePointer* replaceReference(
223  const SafePointer* old, SafePointable* obj);
224 
225  static void replaceAllReferences(
226  SafePointable* newObj, SafePointable* oldObj);
227 
228  /// The default SafePointer that is used in null references.
229  static const SafePointer null;
230 
231 #ifndef NDEBUG
232 #ifndef DOXYGEN_SHOULD_SKIP_THIS
233 
234 /**
235  * Creates SafePointer with debug data of creation place of pointer.
236  *
237  * Just calls debugCreate method, with full parameters.
238  *
239  * Creation place of SafePointer is very important to know
240  * because it's very hard to find where SafePointer that points
241  * to wrong place was created.
242  */
243 #define CREATE_SAFEPOINTER(x) \
244  ReferenceManager::SafePointer::debugCreate( x , __FILE__, __LINE__)
245 
246  // Debug methods... don't delete.
247 
248  // methods for testing
249  static const SectionIndexMap* SIMap();
250  static const SafePointerList* SIMapAt(SectionIndexKey k);
251  static const SectionOffsetMap* SOMap();
252  static const SafePointerList* SOMapAt(SectionOffsetKey k);
253  static const FileOffsetMap* FOMap();
254  static const SafePointerList* FOMapAt(FileOffsetKey k);
255  static const ReferenceMap* RMap();
256  static const SafePointerList* RMapAt(SafePointable* k);
257  static const SectionMap* SMap();
258  static const SafePointerList* SMapAt(SectionKey k);
259 
260  // methods to set and get debug string
261  void setDebugString(std::string aStr);
262  std::string debugString() const;
263 
264  template <typename ObjType>
265  static SafePointer* debugCreate(ObjType obj, const char *file, int line);
266 
267 #endif // DOXYGEN_SHOULD_SKIP_THIS
268 
269 #else
270 
271 /**
272  * Creates SafePointer without debug data.
273  *
274  * Just calls genericCreate method.
275  */
276 #define CREATE_SAFEPOINTER(x) \
277  ReferenceManager::SafePointer::genericCreate(x)
278 #endif
279 
280  template <typename ObjType>
281  static SafePointer* genericCreate(ObjType obj);
282 
283 
284 protected:
288  SafePointer(SectionKey key);
289  SafePointer(SafePointable* object);
290 
291  template <typename KeyType, typename MapType>
293  const KeyType& key,
294  MapType& destinationMap,
295  SafePointer* newSafePointer);
296 
297  template <typename KeyType, typename MapType>
298  static void genericAddObjectReference(
299  const KeyType& key, MapType& destinationMap, const SafePointable* obj);
300 
301  template <typename KeyType, typename MapType>
302  static KeyType genericKeyFor(const SafePointable* obj, MapType& sourceMap);
303 
304  template <typename MapType>
305  static void safelyCleanupKeyTable(
306  MapType& sourceMap,
307  std::set<SafePointerList*>&
308  listsToDelete);
309 
310 private:
311 
312  /// The reference to the real object.
314 
315  /// Map of SafePointers that are requested using SectionIndexKeys.
317 
318  /// Map of SafePointers that are requested using SectionOffsetKeys.
320 
321  /// Map of SafePointers that are requested using FileOffsetKeys.
323 
324  /// Map of SafePointers that are requested using SectionKeys.
326 
327  /// Map of SafePointers that have resolved references.
329 
330  /// Set that cointains all alive (not deleted) SafePointers for extra
331  /// safety.
333 
334  // KeyFor cache stuff to make genericKeyFor function to work O(1) speed
335  // after first call
336 
337  /// Key type for cache, void* is pointer to key map
338  /// (sectioMap_, sectionOffsetMap, ...)
339  typedef std::pair<const SafePointable*, void*> KeyForCacheKey;
340  typedef std::map<KeyForCacheKey,const ReferenceKey*> KeyForCacheMap;
341 
342  /// Map for cache.
344 
345  /// Assignment not allowed.
347 
348  /// Copying not allowed.
350 
351 #ifndef NDEBUG
352  std::string debugString_;
353 #endif
354 
355 };
356 
357 } // namespace ReferenceManager
358 }
359 
360 #include "SafePointer.icc"
361 
362 #endif
TPEF::ReferenceManager::SafePointer::replaceReference
static const SafePointer * replaceReference(const SafePointer *old, SafePointable *obj)
TPEF::SectionId
HalfWord SectionId
Type for storing binary file section ids.
Definition: TPEFBaseType.hh:43
TPEF::ReferenceManager::FileOffsetKey::fileOffset
FileOffset fileOffset() const
TPEF::ReferenceManager::SectionOffsetKey::offset
SectionOffset offset() const
TPEF::ReferenceManager::SafePointer::isReferenced
static bool isReferenced(const SafePointable *object)
Definition: SafePointer.cc:282
TPEF::ReferenceManager::SafePointerList::setReference
void setReference(const SafePointable *obj)
Definition: SafePointer.cc:113
TPEF::ReferenceManager::HashFunctions::operator()
size_t operator()(const FileOffsetKey &key) const
Definition: SafePointer.hh:127
TPEF::ReferenceManager::SafePointerList
Definition: SafePointer.hh:71
TPEF::ReferenceManager::SafePointerList::reference_
SafePointable * reference_
Object that SafePointers in this list are pointing to.
Definition: SafePointer.hh:99
TPEF::ReferenceManager::SectionIndexKey::index
SectionIndex index() const
Exception.hh
TPEF::ReferenceManager::SafePointer::genericRegisterPointer
void genericRegisterPointer(const KeyType &key, MapType &destinationMap, SafePointer *newSafePointer)
TPEF::ReferenceManager::SafePointer::fileOffsetKeyFor
static FileOffsetKey fileOffsetKeyFor(const SafePointable *obj)
Definition: SafePointer.cc:394
TPEF::ReferenceManager::SafePointerSet
std::set< SafePointer * > SafePointerSet
Unordered set of SafePointers.
Definition: SafePointer.hh:144
TPEF::ReferenceManager::SafePointerList::length
LengthType length() const
TPEF::ReferenceManager::SafePointer::sectionOffsetMap_
static SectionOffsetMap * sectionOffsetMap_
Map of SafePointers that are requested using SectionOffsetKeys.
Definition: SafePointer.hh:319
TPEF::ReferenceManager::ReferenceMap
std::map< const SafePointable *, SafePointerList * > ReferenceMap
Map for resolved references, that is SafePointers that are pointing to the created object.
Definition: SafePointer.hh:169
TPEF::ReferenceManager::SafePointer::cleanup
static void cleanup()
Definition: SafePointer.cc:667
TPEF::ReferenceManager::SectionKey::sectionId
SectionId sectionId() const
TPEF::ReferenceManager::SafePointer::KeyForCacheKey
std::pair< const SafePointable *, void * > KeyForCacheKey
Key type for cache, void* is pointer to key map (sectioMap_, sectionOffsetMap, ......
Definition: SafePointer.hh:339
TPEF::ReferenceManager::SectionIndexKey
Definition: ReferenceKey.hh:65
TPEF::ReferenceManager::SafePointer::genericAddObjectReference
static void genericAddObjectReference(const KeyType &key, MapType &destinationMap, const SafePointable *obj)
TPEF::ReferenceManager::SafePointer::addObjectReference
static void addObjectReference(SectionIndexKey key, const SafePointable *obj)
Definition: SafePointer.cc:306
TPEF::ReferenceManager::SafePointer::keyForCache_
static KeyForCacheMap * keyForCache_
Map for cache.
Definition: SafePointer.hh:343
TPEF::ReferenceManager::SafePointer::notifyDeleted
static void notifyDeleted(const SafePointable *obj)
Definition: SafePointer.cc:421
TPEF::ReferenceManager::SectionIndexMap
std::map< SectionIndexKey, SafePointerList * > SectionIndexMap
Map for SafePointers that are requested using SectionIndexKeys.
Definition: SafePointer.hh:147
TPEF::ReferenceManager::SafePointer::sectionMap_
static SectionMap * sectionMap_
Map of SafePointers that are requested using SectionKeys.
Definition: SafePointer.hh:325
TPEF::ReferenceManager::SafePointer::fileOffsetMap_
static FileOffsetMap * fileOffsetMap_
Map of SafePointers that are requested using FileOffsetKeys.
Definition: SafePointer.hh:322
TPEF::ReferenceManager::SafePointer::genericCreate
static SafePointer * genericCreate(ObjType obj)
TPEF::ReferenceManager::SafePointer::cleanupKeyTables
static void cleanupKeyTables()
Definition: SafePointer.cc:644
TPEF::ReferenceManager::SectionOffsetKey::sectionId
SectionId sectionId() const
TPEF::ReferenceManager::FileOffsetMap
std::map< FileOffsetKey, SafePointerList * > FileOffsetMap
Map for SafePointers that are requested using FileOffsetKeys.
Definition: SafePointer.hh:157
TPEF::ReferenceManager::SectionIndexKey::sectionId
SectionId sectionId() const
TPEF::ReferenceManager::SafePointer
Definition: SafePointer.hh:188
TPEF::ReferenceManager::SafePointer::referenceMap_
static ReferenceMap * referenceMap_
Map of SafePointers that have resolved references.
Definition: SafePointer.hh:328
TPEF::ReferenceManager::SafePointerList::reference
SafePointable * reference() const
TPEF::ReferenceManager::HashFunctions::operator()
size_t operator()(const SectionIndexKey &key) const
Definition: SafePointer.hh:113
TPEF::ReferenceManager::SectionOffsetMap
std::map< SectionOffsetKey, SafePointerList * > SectionOffsetMap
Map for SafePointers that are requested using SectionOffsetKeys.
Definition: SafePointer.hh:152
TPEF::ReferenceManager::SafePointer::~SafePointer
virtual ~SafePointer()
Definition: SafePointer.cc:256
TPEF::ReferenceManager::SafePointer::sectionKeyFor
static SectionKey sectionKeyFor(const SafePointable *obj)
Definition: SafePointer.cc:408
Application.hh
TPEF::ReferenceManager::SafePointerList::SafePointerListType
std::list< SafePointer * > SafePointerListType
Type of the container to hold the SafePointers in.
Definition: SafePointer.hh:74
TPEF::ReferenceManager::SafePointer::pointer
SafePointable * pointer() const
TPEF::ReferenceManager::SafePointer::sectionOffsetKeyFor
static SectionOffsetKey sectionOffsetKeyFor(const SafePointable *obj)
Definition: SafePointer.cc:380
TPEF::ReferenceManager::SafePointerList::append
void append(SafePointer *newSafePointer)
Definition: SafePointer.cc:132
TPEF::ReferenceManager::SafePointer::aliveSafePointers_
static SafePointerSet * aliveSafePointers_
Set that cointains all alive (not deleted) SafePointers for extra safety.
Definition: SafePointer.hh:332
TPEF::SafePointable
Definition: SafePointable.hh:48
TPEF::ReferenceManager::SafePointer::operator=
SafePointer & operator=(SafePointer &)
Assignment not allowed.
TPEF::ReferenceManager::SafePointerList::cleanupDead
void cleanupDead()
Definition: SafePointer.cc:173
TPEF::ReferenceManager::SafePointer::setPointer
void setPointer(SafePointable *object)
TPEF::ReferenceManager::SafePointer::sectionIndexMap_
static SectionIndexMap * sectionIndexMap_
Map of SafePointers that are requested using SectionIndexKeys.
Definition: SafePointer.hh:316
TPEF::ReferenceManager::SafePointer::KeyForCacheMap
std::map< KeyForCacheKey, const ReferenceKey * > KeyForCacheMap
Definition: SafePointer.hh:340
TPEF::ReferenceManager::SafePointer::genericKeyFor
static KeyType genericKeyFor(const SafePointable *obj, MapType &sourceMap)
TPEF::ReferenceManager::HashFunctions::operator()
size_t operator()(const SectionOffsetKey &key) const
Definition: SafePointer.hh:120
TPEF::ReferenceManager::SafePointer::SafePointer
SafePointer(SectionIndexKey key)
Definition: SafePointer.cc:199
TPEF::ReferenceManager::SafePointer::debugString_
std::string debugString_
Definition: SafePointer.hh:352
TPEF::ReferenceManager::SectionKey
Definition: ReferenceKey.hh:145
TPEF::ReferenceManager::HashFunctions
Definition: SafePointer.hh:111
TPEF::ReferenceManager::FileOffsetKey
Definition: ReferenceKey.hh:121
TPEF::ReferenceManager::SafePointer::safelyCleanupKeyTable
static void safelyCleanupKeyTable(MapType &sourceMap, std::set< SafePointerList * > &listsToDelete)
TPEF::ReferenceManager::ReferenceKey
Definition: ReferenceKey.hh:50
TPEF::ReferenceManager::SafePointer::isAlive
static bool isAlive(SafePointer *pointerToCheck)
Definition: SafePointer.cc:267
TPEF::ReferenceManager::SafePointerList::LengthType
std::string::size_type LengthType
Type of the list length value.
Definition: SafePointer.hh:77
TPEF::ReferenceManager::SafePointerList::front
SafePointer * front() const
BYTE_BITWIDTH
const Byte BYTE_BITWIDTH
Definition: BaseType.hh:136
TPEF::ReferenceManager::HashFunctions::operator()
size_t operator()(const SafePointable *const &key) const
Definition: SafePointer.hh:135
TPEF::ReferenceManager::SafePointerList::list_
SafePointerListType list_
Container for SafePointers.
Definition: SafePointer.hh:102
TPEF::ReferenceManager::SafePointer::unresolvedReferences
static bool unresolvedReferences(const MapType &mapToCheck, const ReferenceKey **unresolvedKey)
TPEF::ReferenceManager::HashFunctions::operator()
size_t operator()(const SectionKey &key) const
Definition: SafePointer.hh:131
TPEF::ReferenceManager::SafePointer::sectionIndexKeyFor
static SectionIndexKey sectionIndexKeyFor(const SafePointable *obj)
Definition: SafePointer.cc:366
TPEF::ReferenceManager::SafePointer::resolve
static void resolve()
Definition: SafePointer.cc:480
TPEF::ReferenceManager::SectionOffsetKey
Definition: ReferenceKey.hh:93
TPEF::ReferenceManager::SafePointerList::cleanup
void cleanup()
Definition: SafePointer.cc:164
TPEF::ReferenceManager::SafePointer::replaceAllReferences
static void replaceAllReferences(SafePointable *newObj, SafePointable *oldObj)
ReferenceKey.hh
SafePointer.icc
TPEF::ReferenceManager::SectionMap
std::map< SectionKey, SafePointerList * > SectionMap
Map for SafePointers that are requested using SectionKeys.
Definition: SafePointer.hh:162
TPEF::ReferenceManager::SafePointerList::~SafePointerList
virtual ~SafePointerList()
Definition: SafePointer.cc:103
TPEF::ReferenceManager::SafePointerList::SafePointerList
SafePointerList()
Definition: SafePointer.cc:82
TPEF
Definition: Assembler.hh:43
TPEF::ReferenceManager::SafePointer::object_
SafePointable * object_
The reference to the real object.
Definition: SafePointer.hh:313