Chromium Code Reviews| Index: gpu/command_buffer/client/fenced_allocator.cc |
| diff --git a/gpu/command_buffer/client/fenced_allocator.cc b/gpu/command_buffer/client/fenced_allocator.cc |
| index 0e90bf385b4d0f8a9dded299cfb5a04b1aef2137..157827b3c8ff9f12702338dfa8a8e8507ca8958d 100644 |
| --- a/gpu/command_buffer/client/fenced_allocator.cc |
| +++ b/gpu/command_buffer/client/fenced_allocator.cc |
| @@ -42,10 +42,14 @@ FencedAllocator::FencedAllocator(unsigned int size, |
| } |
| FencedAllocator::~FencedAllocator() { |
| - // Free blocks pending tokens. |
| + // Free blocks pending tokens and serials. |
| for (unsigned int i = 0; i < blocks_.size(); ++i) { |
| if (blocks_[i].state == FREE_PENDING_TOKEN) { |
| i = WaitForTokenAndFreeBlock(i); |
| + } else if (blocks_[i].state == FREE_PENDING_SERIAL) { |
| + Block &block = blocks_[i]; |
| + block.state = FREE; |
| + CollapseFreeBlock(i); |
|
piman
2014/01/11 02:02:32
This is probably ok in the current use, if we can
jadahl
2014/01/16 16:24:39
Where do you suggest we document this? Here?
|
| } |
| } |
| // These checks are not valid if the service has crashed or lost the context. |
| @@ -113,6 +117,16 @@ void FencedAllocator::FreePendingToken( |
| block.token = token; |
| } |
| +void FencedAllocator::FreePendingSerial( |
| + FencedAllocator::Offset offset, uint32 serial) { |
| + BlockIndex index = GetBlockByOffset(offset); |
| + Block &block = blocks_[index]; |
| + if (block.state == IN_USE) |
| + bytes_in_use_ -= block.size; |
| + block.state = FREE_PENDING_SERIAL; |
| + block.serial = serial; |
| +} |
| + |
| // Gets the max of the size of the blocks marked as free. |
| unsigned int FencedAllocator::GetLargestFreeSize() { |
| FreeUnused(); |
| @@ -132,7 +146,7 @@ unsigned int FencedAllocator::GetLargestFreeOrPendingSize() { |
| unsigned int current_size = 0; |
| for (unsigned int i = 0; i < blocks_.size(); ++i) { |
| Block &block = blocks_[i]; |
| - if (block.state == IN_USE) { |
| + if (block.state == IN_USE || block.state == FREE_PENDING_SERIAL) { |
| max_size = std::max(max_size, current_size); |
| current_size = 0; |
| } else { |
| @@ -204,11 +218,16 @@ FencedAllocator::BlockIndex FencedAllocator::WaitForTokenAndFreeBlock( |
| // Frees any blocks pending a token for which the token has been read. |
| void FencedAllocator::FreeUnused() { |
| int32 last_token_read = helper_->last_token_read(); |
| + uint32 last_serial_read = helper_->last_serial_read(); |
| for (unsigned int i = 0; i < blocks_.size();) { |
| Block& block = blocks_[i]; |
| if (block.state == FREE_PENDING_TOKEN && block.token <= last_token_read) { |
| block.state = FREE; |
| i = CollapseFreeBlock(i); |
| + } else if (block.state == FREE_PENDING_SERIAL && |
| + block.serial <= last_serial_read) { |
|
reveman
2014/01/11 23:39:04
maybe use a switch statement here and above
|
| + block.state = FREE; |
| + i = CollapseFreeBlock(i); |
| } else { |
| ++i; |
| } |
| @@ -228,7 +247,12 @@ FencedAllocator::Offset FencedAllocator::AllocInBlock(BlockIndex index, |
| block.state = IN_USE; |
| return offset; |
| } |
| - Block newblock = { FREE, offset + size, block.size - size, kUnusedToken}; |
| + Block newblock = { |
| + FREE, offset + size, |
| + block.size - size, |
| + kUnusedToken, |
| + kUnusedSerial |
| + }; |
| block.state = IN_USE; |
| block.size = size; |
| // this is the last thing being done because it may invalidate block; |
| @@ -238,7 +262,13 @@ FencedAllocator::Offset FencedAllocator::AllocInBlock(BlockIndex index, |
| // The blocks are in offset order, so we can do a binary search. |
| FencedAllocator::BlockIndex FencedAllocator::GetBlockByOffset(Offset offset) { |
| - Block templ = { IN_USE, offset, 0, kUnusedToken }; |
| + Block templ = { |
| + IN_USE, |
| + offset, |
| + 0, |
| + kUnusedToken, |
| + kUnusedSerial |
| + }; |
| Container::iterator it = std::lower_bound(blocks_.begin(), blocks_.end(), |
| templ, OffsetCmp()); |
| DCHECK(it != blocks_.end() && it->offset == offset); |