Boost logo

Boost :

From: Greg Colvin (Gregory.Colvin_at_[hidden])
Date: 2002-09-03 12:34:21


At 11:03 AM 9/3/2002, Rob Stewart wrote:
>From: Carlo Wood <carlo_at_[hidden]>
>>
>> It would be pretty hard to only use stack allocated memory,
>> I think. Let me give some internal details.
>>
>> What is needed are three vectors:
>[snip]
>> What is according to you the maximum number of
>> template arguments, substitutions and qualifiers in a type?
>>
>> The code also uses about 25 internal strings.
>> Each of these strings might need an arbitrary size,
>[snip]
>> The point is that the actual size of memory needed
>> is not related to the demangler code, but to the
>> application and its circumstances. And so is the
>> needed memory model.
>>
>> By simply allowing the user to pass an Allocator
>> parameter for the most general interface, they can
>> deal with this issue themself (pre-allocation, seperate
>> memory pool or whatever) and adjust the load on their
>> resources according to their need.
>>
>> Stack allocation could be implemented through a
>> "pre-allocated" memory pool in the first call (a wrapper).
>
>Yes, the user could provide the allocator that does whatever is appropriate for
>the application, and that's not a bad approach. However, using preallocated
>memory is easier than you're making it out to be. All (!) you need to do is
>create an allocator that assigns memory from a large pool that it preallocates.
>IOW, instead of calling a heap function which carves memory out of a large
>chunk, the allocator manages its own (smaller) large chunk. (Note that I'm not
>saying this is easy, but you don't need to decide how much memory to allocate
>for each data structure.)
>
>> Actually, I think that allocators like this should
>> be part of boost too, and NOT as a part of my demangler
>> library, but provided seperately.
>
>That is certainly a valid point. Of course, you could implement it first within
>your library, then submit it for a separate review later. Then, when accepted,
>you could change demangle() to use that new allocator. (Isn't it good that I'm
>here to suggest work for you?) Seriously, if you were to do the work to
>implement your library, it could be the start of a set of commonly needed
>allocators.

Warning -- Untested Code Ahead:

   template<typename T, int N> class local_alloc {
      char buffer[N];
      int free;
   public:
      local_alloc() : free(0) {}
      pointer allocate(size_t n,const void*) {
         if (free + n > N)
            return std::allocate(n,0);
         free += n;
         return buffer + free;
      }
      void deallocate(pointer p, size_t n) {
         if (std::less((char*)p,buffer) || std::less(buffer+N-n,(char*)p))
            std::deallocate(p,n);
      }
      typedef T* pointer;
      typedef T& reference;
      typedef const T* const_pointer;
      typedef const T& const_reference;
      typedef T value_type;
      typedef size_t size_type;
      typedef ptrdiff_t difference_type;
      bool operator==(const local_alloc& r) const { return this == &r; }
      bool operator!=(const local_alloc& r) const { return this != &r; }
      size_t max_size() const {
         size_t n = (size_t)(-1) / sizeof(T);
         return 0 < n ? n : 1;
      }
      pointer address(T& t) { return &t; }
      const_pointer address(const T& t) { return &t; }
      void construct(pointer p, const T& t) {
         new((void *)p) T(t);
      }
      void destroy(pointer p) {
         p->~T();
      }
   };


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk