void* FixedAllocator::Allocate() { if (allocChunk_ == 0 || allocChunk_->blocksAvailable_ == 0) { Chunks::iterator i = chunks_.begin(); for (;; ++i) { if (i == chunks_.end()) { // Initialize chunks_.reserve(chunks_.size() + 1); Chunk newChunk; newChunk.Init(blockSize_, numBlocks_); chunks_.push_back(newChunk); allocChunk_ = &chunks_.back(); deallocChunk_ = &chunks_.front(); break; } if (i->blocksAvailable_ > 0) { allocChunk_ = &*i; break; } } } assert(allocChunk_ != 0); assert(allocChunk_->blocksAvailable_ > 0); return allocChunk_->Allocate(blockSize_); }
bool FixedAllocator::MakeNewChunk( void ) { bool allocated = false; try { std::size_t size = chunks_.size(); // Calling chunks_.reserve *before* creating and initializing the new // Chunk means that nothing is leaked by this function in case an // exception is thrown from reserve. if ( chunks_.capacity() == size ) { if ( 0 == size ) size = 4; chunks_.reserve( size * 2 ); } Chunk newChunk; allocated = newChunk.Init( blockSize_, numBlocks_ ); if ( allocated ) chunks_.push_back( newChunk ); } catch ( ... ) { allocated = false; } if ( !allocated ) return false; allocChunk_ = &chunks_.back(); deallocChunk_ = &chunks_.front(); return true; }
// create new chunk at front of chain of chunks // Chunk* Zone::NewChunk(int size) { Chunk* chunk = reinterpret_cast<Chunk*>(Malloced::New(size)); if (chunk != 0) { chunk->Init(head_, size); head_ = chunk; } return chunk; }