Chromium Code Reviews| Index: gpu/command_buffer/client/gl_in_process_context.cc |
| diff --git a/gpu/command_buffer/client/gl_in_process_context.cc b/gpu/command_buffer/client/gl_in_process_context.cc |
| index 7e17929ab8fd431f2e5b6b281cb531fb67a5644e..f465915d21a76cc0d30ac650e13d5e739571938b 100644 |
| --- a/gpu/command_buffer/client/gl_in_process_context.cc |
| +++ b/gpu/command_buffer/client/gl_in_process_context.cc |
| @@ -4,6 +4,7 @@ |
| #include "gpu/command_buffer/client/gl_in_process_context.h" |
| +#include <deque> |
| #include <utility> |
| #include <vector> |
| @@ -123,7 +124,6 @@ class GLInProcessContextImpl |
| void Destroy(); |
| bool IsCommandBufferContextLost(); |
| void PollQueryCallbacks(); |
| - void CallQueryCallback(size_t index); |
| gles2::ImageManager* GetImageManager(); |
| @@ -143,7 +143,7 @@ class GLInProcessContextImpl |
| bool context_lost_; |
| typedef std::pair<unsigned, base::Closure> QueryCallback; |
| - std::vector<QueryCallback> query_callbacks_; |
| + std::deque<QueryCallback> query_callbacks_; |
| DISALLOW_COPY_AND_ASSIGN(GLInProcessContextImpl); |
| }; |
| @@ -504,9 +504,12 @@ bool GLInProcessContextImpl::Initialize( |
| void GLInProcessContextImpl::Destroy() { |
| while (!query_callbacks_.empty()) { |
| - CallQueryCallback(0); |
| + base::Closure query_callback = query_callbacks_.back().second; |
| + query_callbacks_.pop_back(); |
| + query_callback.Run(); |
| } |
| + |
| bool context_lost = IsCommandBufferContextLost(); |
| if (gles2_implementation_) { |
| @@ -547,16 +550,19 @@ void GLInProcessContextImpl::OnContextLost() { |
| } |
| } |
| -void GLInProcessContextImpl::CallQueryCallback(size_t index) { |
| - DCHECK_LT(index, query_callbacks_.size()); |
| - QueryCallback query_callback = query_callbacks_[index]; |
| - query_callbacks_[index] = query_callbacks_.back(); |
| - query_callbacks_.pop_back(); |
| - query_callback.second.Run(); |
| -} |
| - |
| void GLInProcessContextImpl::PollQueryCallbacks() { |
| - for (size_t i = 0; i < query_callbacks_.size();) { |
| + // Queries are put on to to the query_callback_ deque from the FRONT. |
| + // This means that if there are several queries of the same type in |
| + // the queue, and we find that one of them has finished, the rest |
| + // of them should be finished too. We want to make sure that |
|
piman
2013/06/28 23:35:46
That's not true though.
An async texture upload do
hubbe
2013/06/29 00:13:56
Async readpixels (and maybe other queries) *do* fi
|
| + // a) Query callbacks are called in the right order |
| + // b) query_callbacks_ is in a good state when we call the callbacks |
| + // To do that we pul out the queries that have completed and put them |
| + // in a separate container in reversed order, then we compress |
| + // query_callbacks_ and before invoking the callbacks. |
| + std::deque<QueryCallback> to_call; |
| + size_t queries_left = 0; |
| + for (size_t i = 0; i < query_callbacks_.size(); i++) { |
| unsigned query = query_callbacks_[i].first; |
| GLuint param = 0; |
| gles2::GLES2Implementation* gl = GetImplementation(); |
| @@ -566,11 +572,16 @@ void GLInProcessContextImpl::PollQueryCallbacks() { |
| param = 1; |
| } |
| if (param) { |
| - CallQueryCallback(i); |
| + to_call.push_front(query_callbacks_[i]); |
| } else { |
| - i++; |
| + query_callbacks_[queries_left++] = query_callbacks_[i]; |
| } |
| } |
| + query_callbacks_.resize(queries_left); |
| + for (size_t i = 0; i < to_call.size(); i++) { |
| + to_call[i].second.Run(); |
| + } |
| + |
| if (!query_callbacks_.empty()) { |
| base::MessageLoop::current()->PostDelayedTask( |
| FROM_HERE, |
| @@ -583,7 +594,7 @@ void GLInProcessContextImpl::PollQueryCallbacks() { |
| void GLInProcessContextImpl::SignalQuery( |
| unsigned query, |
| const base::Closure& callback) { |
| - query_callbacks_.push_back(std::make_pair(query, callback)); |
| + query_callbacks_.push_front(std::make_pair(query, callback)); |
| // If size > 1, there is already a poll callback pending. |
| if (query_callbacks_.size() == 1) { |
| PollQueryCallbacks(); |