John Aughey wrote:
I have a class that implements a buffer pool that allocates block of memory, and the users "free" the memory when it is no longer needed back to the buffer pool. Future allocations simply return the front of the free list.
Simple enough, and the class returns shared_array<T> objects to automatically free the memory back into the proper buffer pool.
The problem is, this mechanism is used so that during real-time operation (this is a real-time system), there is absolutely no memory allocations required. However, inside shared_array, it uses detail::shared_count and inside shared_count it performs a new to create a sp_counted_base object. So for every smart pointer object that supplies a deleter, it must perform a new.
My proposal would be to include another constructor to both shared_array (and probably it's corresponding smart pointer brothers) and to shared_count that looks like:
shared_array(T *p, sp_counted_base *d) : px(p), pn(d) { }
shared_count(sp_counted_base *d) : pi_(d) { }
(I haven't implemented this yet, so the above may not be quite right)
The purpose of this is to supply an sp_counted_base object to the shared_* object that does the delete functionality. This eliminates the new in the case where a sp_counted_base object can be supplied. In the case of the managed buffer pool mentioned above, the sp_counted_base object could be allocated with the corresponding buffer, and then re-used for subsequent "allocations" from the free list. This should result in no dynamic allocations to create a shared_* object with a corresponding deleter.
I hope this makes sense. It should only require two new constuctors.
Yes, it makes perfect sense. Unfortunately it requires much more than just
two new constructors. sp_counted_base would need to be documented; many
shared_ptr operations would need to be respecified in terms of
sp_counted_base operations. This is, of course, possible to do for
boost::shared_ptr, but it would be unwise to overspecify
std::tr1::shared_ptr in such a way, and I am reluctant to add features to
boost::shared_ptr that have little chance to become standard.
http://std.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1450.html
There is one way to convince shared_ptr/shared_array to not allocate memory,
although I'm not sure whether it can be applied to your environment as-is.
First #define BOOST_SP_USE_QUICK_ALLOCATOR to make shared_ptr use