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); |