2005-07-24 15:12:37 +01:00
|
|
|
/* $Id$ */
|
|
|
|
|
2007-03-21 15:19:33 +00:00
|
|
|
/** @file oldpool.h */
|
|
|
|
|
2006-12-03 20:03:40 +00:00
|
|
|
#ifndef OLDPOOL_H
|
|
|
|
#define OLDPOOL_H
|
2005-02-01 18:30:11 +00:00
|
|
|
|
|
|
|
/* The function that is called after a new block is added
|
|
|
|
start_item is the first item of the new made block */
|
2006-12-03 17:27:43 +00:00
|
|
|
typedef void OldMemoryPoolNewBlock(uint start_item);
|
2006-04-18 19:48:50 +01:00
|
|
|
/* The function that is called before a block is cleaned up */
|
2006-12-03 17:27:43 +00:00
|
|
|
typedef void OldMemoryPoolCleanBlock(uint start_item, uint end_item);
|
2005-02-01 18:30:11 +00:00
|
|
|
|
|
|
|
/**
|
2006-12-03 17:27:43 +00:00
|
|
|
* Stuff for dynamic vehicles. Use the wrappers to access the OldMemoryPool
|
2005-02-01 18:30:11 +00:00
|
|
|
* please try to avoid manual calls!
|
|
|
|
*/
|
2007-08-01 23:10:54 +01:00
|
|
|
struct OldMemoryPoolBase {
|
|
|
|
void CleanPool();
|
|
|
|
bool AddBlockToPool();
|
|
|
|
bool AddBlockIfNeeded(uint index);
|
|
|
|
|
|
|
|
protected:
|
|
|
|
OldMemoryPoolBase(const char *name, uint max_blocks, uint block_size_bits, uint item_size,
|
|
|
|
OldMemoryPoolNewBlock *new_block_proc, OldMemoryPoolCleanBlock *clean_block_proc) :
|
|
|
|
name(name), max_blocks(max_blocks), block_size_bits(block_size_bits), item_size(item_size),
|
|
|
|
new_block_proc(new_block_proc), clean_block_proc(clean_block_proc), current_blocks(0),
|
|
|
|
total_items(0), blocks(NULL) {}
|
|
|
|
|
2007-01-10 18:56:51 +00:00
|
|
|
const char* name; ///< Name of the pool (just for debugging)
|
2005-02-01 18:30:11 +00:00
|
|
|
|
2007-01-10 18:56:51 +00:00
|
|
|
uint max_blocks; ///< The max amount of blocks this pool can have
|
|
|
|
uint block_size_bits; ///< The size of each block in bits
|
|
|
|
uint item_size; ///< How many bytes one block is
|
2005-02-01 18:30:11 +00:00
|
|
|
|
2006-03-09 20:37:51 +00:00
|
|
|
/// Pointer to a function that is called after a new block is added
|
2006-12-03 17:27:43 +00:00
|
|
|
OldMemoryPoolNewBlock *new_block_proc;
|
2006-04-18 19:48:50 +01:00
|
|
|
/// Pointer to a function that is called to clean a block
|
2006-12-03 17:27:43 +00:00
|
|
|
OldMemoryPoolCleanBlock *clean_block_proc;
|
2005-02-01 18:30:11 +00:00
|
|
|
|
2006-03-09 20:37:51 +00:00
|
|
|
uint current_blocks; ///< How many blocks we have in our pool
|
|
|
|
uint total_items; ///< How many items we now have in this pool
|
2005-02-01 18:30:11 +00:00
|
|
|
|
2007-08-01 23:10:54 +01:00
|
|
|
public:
|
2006-03-09 20:37:51 +00:00
|
|
|
byte **blocks; ///< An array of blocks (one block hold all the items)
|
2007-08-01 23:10:54 +01:00
|
|
|
|
|
|
|
inline uint GetSize()
|
|
|
|
{
|
|
|
|
return this->total_items;
|
|
|
|
}
|
|
|
|
|
|
|
|
inline bool CanAllocateMoreBlocks()
|
|
|
|
{
|
|
|
|
return this->current_blocks < this->max_blocks;
|
|
|
|
}
|
|
|
|
|
|
|
|
inline uint GetBlockCount()
|
|
|
|
{
|
|
|
|
return this->current_blocks;
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
template <typename T>
|
|
|
|
struct OldMemoryPool : public OldMemoryPoolBase {
|
|
|
|
OldMemoryPool(const char *name, uint max_blocks, uint block_size_bits, uint item_size,
|
|
|
|
OldMemoryPoolNewBlock *new_block_proc, OldMemoryPoolCleanBlock *clean_block_proc) :
|
|
|
|
OldMemoryPoolBase(name, max_blocks, block_size_bits, item_size, new_block_proc, clean_block_proc) {}
|
|
|
|
|
|
|
|
inline T *Get(uint index)
|
|
|
|
{
|
|
|
|
assert(index < this->GetSize());
|
|
|
|
return (T*)(this->blocks[index >> this->block_size_bits] +
|
|
|
|
(index & ((1 << this->block_size_bits) - 1)) * sizeof(T));
|
|
|
|
}
|
2005-02-01 18:30:11 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Those are the wrappers:
|
|
|
|
* CleanPool cleans the pool up, but you can use AddBlockToPool directly again
|
|
|
|
* (no need to call CreatePool!)
|
|
|
|
* AddBlockToPool adds 1 more block to the pool. Returns false if there is no
|
|
|
|
* more room
|
|
|
|
*/
|
2007-08-01 23:10:54 +01:00
|
|
|
static inline void CleanPool(OldMemoryPoolBase *array) { array->CleanPool(); }
|
|
|
|
static inline bool AddBlockToPool(OldMemoryPoolBase *array) { return array->AddBlockToPool(); }
|
2005-02-01 18:30:11 +00:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Adds blocks to the pool if needed (and possible) till index fits inside the pool
|
|
|
|
*
|
|
|
|
* @return Returns false if adding failed
|
|
|
|
*/
|
2007-08-01 23:10:54 +01:00
|
|
|
static inline bool AddBlockIfNeeded(OldMemoryPoolBase *array, uint index) { return array->AddBlockIfNeeded(index); }
|
2005-02-01 18:30:11 +00:00
|
|
|
|
2006-10-28 11:54:20 +01:00
|
|
|
|
2006-12-03 17:27:43 +00:00
|
|
|
#define OLD_POOL_ENUM(name, type, block_size_bits, max_blocks) \
|
2006-10-28 11:54:20 +01:00
|
|
|
enum { \
|
|
|
|
name##_POOL_BLOCK_SIZE_BITS = block_size_bits, \
|
|
|
|
name##_POOL_MAX_BLOCKS = max_blocks \
|
|
|
|
};
|
|
|
|
|
|
|
|
|
2006-12-03 17:27:43 +00:00
|
|
|
#define OLD_POOL_ACCESSORS(name, type) \
|
2007-08-01 23:10:54 +01:00
|
|
|
static inline type* Get##name(uint index) { return _##name##_pool.Get(index); } \
|
|
|
|
static inline uint Get##name##PoolSize() { return _##name##_pool.GetSize(); }
|
2006-10-28 11:54:20 +01:00
|
|
|
|
|
|
|
|
2006-12-03 17:27:43 +00:00
|
|
|
#define DECLARE_OLD_POOL(name, type, block_size_bits, max_blocks) \
|
|
|
|
OLD_POOL_ENUM(name, type, block_size_bits, max_blocks) \
|
2007-08-01 23:10:54 +01:00
|
|
|
extern OldMemoryPool<type> _##name##_pool; \
|
2006-12-03 17:27:43 +00:00
|
|
|
OLD_POOL_ACCESSORS(name, type)
|
2006-10-28 11:54:20 +01:00
|
|
|
|
|
|
|
|
2006-12-03 17:27:43 +00:00
|
|
|
#define DEFINE_OLD_POOL(name, type, new_block_proc, clean_block_proc) \
|
2007-08-01 23:10:54 +01:00
|
|
|
OldMemoryPool<type> _##name##_pool( \
|
2006-10-28 11:54:20 +01:00
|
|
|
#name, name##_POOL_MAX_BLOCKS, name##_POOL_BLOCK_SIZE_BITS, sizeof(type), \
|
2007-08-01 23:10:54 +01:00
|
|
|
new_block_proc, clean_block_proc);
|
2006-10-28 11:54:20 +01:00
|
|
|
|
|
|
|
|
2006-12-03 17:27:43 +00:00
|
|
|
#define STATIC_OLD_POOL(name, type, block_size_bits, max_blocks, new_block_proc, clean_block_proc) \
|
|
|
|
OLD_POOL_ENUM(name, type, block_size_bits, max_blocks) \
|
|
|
|
static DEFINE_OLD_POOL(name, type, new_block_proc, clean_block_proc) \
|
|
|
|
OLD_POOL_ACCESSORS(name, type)
|
2006-10-28 11:54:20 +01:00
|
|
|
|
2006-12-03 20:03:40 +00:00
|
|
|
#endif /* OLDPOOL_H */
|