Open Model Railroad Network (OpenMRN)
Loading...
Searching...
No Matches
LimitedPool.hxx
Go to the documentation of this file.
1
37#ifndef _UTILS_LIMITEDPOOL_HXX_
38#define _UTILS_LIMITEDPOOL_HXX_
39
40#include "utils/Buffer.hxx"
41
47class LimitedPool : public Pool, private Atomic
48{
49public:
57 unsigned entry_size, unsigned entry_count, Pool *base_pool = nullptr)
58 : itemSize_(entry_size)
59 , freeCount_(entry_count)
61 {
62 }
63
65 size_t free_items() override
66 {
67 return freeCount_;
68 }
69
73 size_t free_items(size_t size) override
74 {
75 return size == itemSize_ ? freeCount_ : 0;
76 }
77
78protected:
80 BufferBase *alloc_untyped(size_t size, Executable *flow) override
81 {
82 HASSERT(size == itemSize_);
83 if (!flow)
84 {
85 DIE("LimitedPool only supports async allocation.");
86 }
87 BufferBase *b = nullptr;
88 {
89 AtomicHolder h(this);
90 if (freeCount_ > 0)
91 {
92 --freeCount_;
93 b = base_pool()->alloc_untyped(size, nullptr);
94 HASSERT(b);
95 b->pool_ = this;
96 }
97 }
98 if (b)
99 {
100 flow->alloc_result(b);
101 return b;
102 }
103 else
104 {
105 waitingQueue_.insert(flow);
106 return nullptr;
107 }
108 }
109
111 void free(BufferBase *item) override
112 {
113 HASSERT(item->size() == itemSize_);
114 Executable *waiting = NULL;
115 {
116 AtomicHolder h(this);
117 waiting = static_cast<Executable *>(waitingQueue_.next().item);
118 if (!waiting)
119 {
120 ++freeCount_;
121 }
122 }
123 if (waiting)
124 {
125 waiting->alloc_result(item);
126 }
127 else
128 {
129 base_pool()->free(item);
130 }
131 }
132
133private:
136 {
137 if (basePool_)
138 {
139 return basePool_;
140 }
141 return mainBufferPool;
142 }
143
145 uint16_t itemSize_;
147 uint16_t freeCount_;
152};
153
154#endif // _UTILS_LIMITEDPOOL_HXX_
DynamicPool * mainBufferPool
main buffer pool instance
Definition Buffer.cxx:37
See OSMutexLock in os/OS.hxx.
Definition Atomic.hxx:153
Lightweight locking class for protecting small critical sections.
Definition Atomic.hxx:130
Abstract base class for all Buffers.
Definition Buffer.hxx:85
Pool * pool_
Reference to the pool from whence this buffer came.
Definition Buffer.hxx:136
size_t size()
Definition Buffer.hxx:121
An object that can be scheduled on an executor to run.
virtual void alloc_result(QMember *item)
Return the result of an alloc_async() from a memory Pool.
Implementation of a Pool interface that takes memory from mainBufferPool (configurable) but limits th...
Q waitingQueue_
Async allocators waiting for free buffers.
Pool * base_pool()
LimitedPool(unsigned entry_size, unsigned entry_count, Pool *base_pool=nullptr)
Pool * basePool_
Where to allocate memory from.
BufferBase * alloc_untyped(size_t size, Executable *flow) override
Internal helper funciton used by the Buffer implementation.
size_t free_items() override
Number of free items in the pool.
size_t free_items(size_t size) override
Number of free items in the pool for a given allocation size.
uint16_t itemSize_
How many bytes each entry should be.
void free(BufferBase *item) override
Function called when a buffer refcount reaches zero.
uint16_t freeCount_
How many entries can still be allocated.
Pool of previously allocated, but currently unused, items.
Definition Buffer.hxx:278
virtual void free(BufferBase *item)=0
Release an item back to the free pool.
virtual BufferBase * alloc_untyped(size_t size, Executable *flow)=0
Untyped buffer allocation method, used be descendants.
This class implements a linked list "queue" of buffers.
Definition Queue.hxx:98
void insert(QMember *item, unsigned index=0)
Add an item to the back of the queue.
Definition Queue.hxx:124
QMember * next(unsigned index)
Get an item from the front of the queue.
Definition Queue.hxx:167
#define HASSERT(x)
Checks that the value of expression x is true, else terminates the current process.
Definition macros.h:138
#define DIE(MSG)
Unconditionally terminates the current process with a message.
Definition macros.h:143