void GrBufferAllocPool::reset() { VALIDATE(); fBytesInUse = 0; if (fBlocks.count()) { GrGeometryBuffer* buffer = fBlocks.back().fBuffer; if (buffer->isLocked()) { buffer->unlock(); } } // fPreallocBuffersInUse will be decremented down to zero in the while loop int preallocBuffersInUse = fPreallocBuffersInUse; while (!fBlocks.empty()) { this->destroyBlock(); } if (fPreallocBuffers.count()) { // must set this after above loop. fPreallocBufferStartIdx = (fPreallocBufferStartIdx + preallocBuffersInUse) % fPreallocBuffers.count(); } // we may have created a large cpu mirror of a large VB. Reset the size // to match our pre-allocated VBs. fCpuData.reset(fMinBlockSize); SkASSERT(0 == fPreallocBuffersInUse); VALIDATE(); }
void GrBufferAllocPool::validate(bool unusedBlockAllowed) const { if (NULL != fBufferPtr) { SkASSERT(!fBlocks.empty()); if (fBlocks.back().fBuffer->isLocked()) { GrGeometryBuffer* buf = fBlocks.back().fBuffer; SkASSERT(buf->lockPtr() == fBufferPtr); } else { SkASSERT(fCpuData.get() == fBufferPtr); } } else { SkASSERT(fBlocks.empty() || !fBlocks.back().fBuffer->isLocked()); } size_t bytesInUse = 0; for (int i = 0; i < fBlocks.count() - 1; ++i) { SkASSERT(!fBlocks[i].fBuffer->isLocked()); } for (int i = 0; i < fBlocks.count(); ++i) { size_t bytes = fBlocks[i].fBuffer->sizeInBytes() - fBlocks[i].fBytesFree; bytesInUse += bytes; SkASSERT(bytes || unusedBlockAllowed); } SkASSERT(bytesInUse == fBytesInUse); if (unusedBlockAllowed) { SkASSERT((fBytesInUse && !fBlocks.empty()) || (!fBytesInUse && (fBlocks.count() < 2))); } else { SkASSERT((0 == fBytesInUse) == fBlocks.empty()); } }
GrBufferAllocPool::GrBufferAllocPool(GrGpu* gpu, BufferType bufferType, bool frequentResetHint, size_t blockSize, int preallocBufferCnt) : fBlocks(GrMax(8, 2*preallocBufferCnt)) { GrAssert(NULL != gpu); fGpu = gpu; fGpu->ref(); fGpuIsReffed = true; fBufferType = bufferType; fFrequentResetHint = frequentResetHint; fBufferPtr = NULL; fMinBlockSize = GrMax(GrBufferAllocPool_MIN_BLOCK_SIZE, blockSize); fBytesInUse = 0; fPreallocBuffersInUse = 0; fFirstPreallocBuffer = 0; for (int i = 0; i < preallocBufferCnt; ++i) { GrGeometryBuffer* buffer = this->createBuffer(fMinBlockSize); if (NULL != buffer) { *fPreallocBuffers.append() = buffer; buffer->ref(); } } }
GrBufferAllocPool::~GrBufferAllocPool() { VALIDATE(); if (fBlocks.count()) { GrGeometryBuffer* buffer = fBlocks.back().fBuffer; if (buffer->isLocked()) { buffer->unlock(); } } while (!fBlocks.empty()) { destroyBlock(); } fPreallocBuffers.unrefAll(); releaseGpuRef(); }
GrBufferAllocPool::~GrBufferAllocPool() { VALIDATE(); if (fBlocks.count()) { GrGeometryBuffer* buffer = fBlocks.back().fBuffer; if (buffer->isMapped()) { UNMAP_BUFFER(fBlocks.back()); } } while (!fBlocks.empty()) { this->destroyBlock(); } fPreallocBuffers.unrefAll(); fGpu->unref(); }
void GrBufferAllocPool::flushCpuData(const BufferBlock& block, size_t flushSize) { GrGeometryBuffer* buffer = block.fBuffer; SkASSERT(buffer); SkASSERT(!buffer->isMapped()); SkASSERT(fCpuData.get() == fBufferPtr); SkASSERT(flushSize <= buffer->gpuMemorySize()); VALIDATE(true); if (GrCaps::kNone_MapFlags != fGpu->caps()->mapBufferFlags() && flushSize > fGeometryBufferMapThreshold) { void* data = buffer->map(); if (data) { memcpy(data, fBufferPtr, flushSize); UNMAP_BUFFER(block); return; } } buffer->updateData(fBufferPtr, flushSize); VALIDATE(true); }
void GrBufferAllocPool::reset() { VALIDATE(); fBytesInUse = 0; if (fBlocks.count()) { GrGeometryBuffer* buffer = fBlocks.back().fBuffer; if (buffer->isLocked()) { buffer->unlock(); } } while (!fBlocks.empty()) { destroyBlock(); } if (fPreallocBuffers.count()) { // must set this after above loop. fFirstPreallocBuffer = (fFirstPreallocBuffer + fPreallocBuffersInUse) % fPreallocBuffers.count(); } fCpuData.reset(fGpu->getCaps().fBufferLockSupport ? 0 : fMinBlockSize); GrAssert(0 == fPreallocBuffersInUse); VALIDATE(); }
void GrBufferAllocPool::validate(bool unusedBlockAllowed) const { bool wasDestroyed = false; if (fBufferPtr) { SkASSERT(!fBlocks.empty()); if (fBlocks.back().fBuffer->isMapped()) { GrGeometryBuffer* buf = fBlocks.back().fBuffer; SkASSERT(buf->mapPtr() == fBufferPtr); } else { SkASSERT(fCpuData.get() == fBufferPtr); } } else { SkASSERT(fBlocks.empty() || !fBlocks.back().fBuffer->isMapped()); } size_t bytesInUse = 0; for (int i = 0; i < fBlocks.count() - 1; ++i) { SkASSERT(!fBlocks[i].fBuffer->isMapped()); } for (int i = 0; !wasDestroyed && i < fBlocks.count(); ++i) { if (fBlocks[i].fBuffer->wasDestroyed()) { wasDestroyed = true; } else { size_t bytes = fBlocks[i].fBuffer->gpuMemorySize() - fBlocks[i].fBytesFree; bytesInUse += bytes; SkASSERT(bytes || unusedBlockAllowed); } } if (!wasDestroyed) { SkASSERT(bytesInUse == fBytesInUse); if (unusedBlockAllowed) { SkASSERT((fBytesInUse && !fBlocks.empty()) || (!fBytesInUse && (fBlocks.count() < 2))); } else { SkASSERT((0 == fBytesInUse) == fBlocks.empty()); } } }