Index: gpu/command_buffer/service/gpu_scheduler.cc |
=================================================================== |
--- gpu/command_buffer/service/gpu_scheduler.cc (revision 106500) |
+++ gpu/command_buffer/service/gpu_scheduler.cc (working copy) |
@@ -4,6 +4,7 @@ |
#include "gpu/command_buffer/service/gpu_scheduler.h" |
+#include "base/bind.h" |
#include "base/callback.h" |
#include "base/command_line.h" |
#include "base/compiler_specific.h" |
@@ -18,6 +19,9 @@ |
using ::base::SharedMemory; |
namespace gpu { |
+namespace { |
+const uint64 kPollFencePeriod = 4; |
+} |
GpuScheduler::GpuScheduler(CommandBuffer* command_buffer, |
gles2::GLES2Decoder* decoder, |
@@ -56,8 +60,31 @@ |
if (state.error != error::kNoError) |
return; |
+ // Check that the GPU has passed all fences. |
+ while (!unschedule_fences_.empty()) { |
+ if (glTestFenceNV(unschedule_fences_.front().fence)) { |
+ glDeleteFencesNV(1, &unschedule_fences_.front().fence); |
+ unschedule_fences_.front().task.Run(); |
+ unschedule_fences_.pop(); |
+ } else { |
+ SetScheduled(false); |
+ MessageLoop::current()->PostDelayedTask( |
+ FROM_HERE, |
+ base::Bind(&GpuScheduler::SetScheduled, AsWeakPtr(), true), |
+ kPollFencePeriod); |
+ return; |
+ } |
+ } |
+ |
+ // One of the unschedule fence tasks might have unscheduled us. |
+ if (!IsScheduled()) |
+ return; |
+ |
error::Error error = error::kNoError; |
while (!parser_->IsEmpty()) { |
+ DCHECK(IsScheduled()); |
+ DCHECK(unschedule_fences_.empty()); |
+ |
error = parser_->ProcessCommand(); |
// TODO(piman): various classes duplicate various pieces of state, leading |
@@ -127,4 +154,21 @@ |
command_processed_callback_.reset(callback); |
} |
+void GpuScheduler::DeferToFence(base::Closure task) { |
+ UnscheduleFence fence; |
+ |
+ glGenFencesNV(1, &fence.fence); |
+ glSetFenceNV(fence.fence, GL_ALL_COMPLETED_NV); |
+ |
+ fence.task = task; |
+ |
+ unschedule_fences_.push(fence); |
+} |
+ |
+GpuScheduler::UnscheduleFence::UnscheduleFence() : fence(0) { |
+} |
+ |
+GpuScheduler::UnscheduleFence::~UnscheduleFence() { |
+} |
+ |
} // namespace gpu |