source: proiecte/swift/trunk/lib/hoard-371/src/manageonesuperblock.h @ 176

Last change on this file since 176 was 176, checked in by (none), 14 years ago
  • imported repo from "guagal"
File size: 2.2 KB
Line 
1// -*- C++ -*-
2
3/**
4 * @file manageonesuperblock.h
5 * @author Emery Berger <http://www.cs.umass.edu/~emery>
6 */
7
8
9#ifndef _MANAGEONESUPERBLOCK_H_
10#define _MANAGEONESUPERBLOCK_H_
11
12/**
13 * @class  ManageOneSuperblock
14 * @brief  A layer that caches exactly one superblock, thus avoiding costly lookups.
15 * @author Emery Berger <http://www.cs.umass.edu/~emery>
16 */
17
18namespace Hoard {
19
20template <class SuperHeap>
21class ManageOneSuperblock : public SuperHeap {
22public:
23
24  typedef typename SuperHeap::SuperblockType SuperblockType;
25
26  /// Get memory from the current superblock.
27  inline void * malloc (size_t sz) {
28    if (_current) {
29      void * ptr = _current->malloc (sz);
30      if (ptr) {
31        assert (_current->getSize(ptr) >= sz);
32        return ptr;
33      }
34    }
35    return slowMallocPath (sz);
36  }
37
38  /// Try to free the pointer to this superblock first.
39  inline void free (void * ptr) {
40    SuperblockType * s = SuperHeap::getSuperblock (ptr);
41    if (s == _current) {
42      _current->free (ptr);
43    } else {
44      SuperHeap::free (ptr);
45    }
46  }
47
48  /// Get the current superblock and remove it.
49  SuperblockType * get (void) {
50    if (_current) {
51      SuperblockType * s = _current;
52      _current = NULL;
53      return s;
54    } else {
55      // There's none cached, so just get one from the superheap.
56      return SuperHeap::get();
57    }
58  }
59
60  /// Put the superblock into the cache.
61  inline void put (SuperblockType * s) {
62    if (!s || (s == _current) || (!s->isValidSuperblock())) {
63      // Ignore if we already are holding this superblock, of if we
64      // got a NULL pointer, or if it's invalid.
65      return;
66    }
67    if (_current) {
68      // We have one already -- push it out.
69      SuperHeap::put (_current);
70    }
71    _current = s;
72  }
73
74private:
75
76  /// Obtain a superblock and return an object from it.
77  void * slowMallocPath (size_t sz) {
78    void * ptr = NULL;
79    while (!ptr) {
80      if (_current) {
81        ptr = _current->malloc (sz);
82        if (ptr) {
83          return ptr;
84        } else {
85          SuperHeap::put (_current);
86        }
87      }
88      _current = SuperHeap::get();
89      if (!_current) {
90        return NULL;
91      }
92      ptr = _current->malloc (sz);
93    }
94    return ptr;
95  }
96
97  /// The current superblock.
98  SuperblockType * _current;
99
100};
101
102}
103
104#endif
Note: See TracBrowser for help on using the repository browser.