diff options
Diffstat (limited to 'chromium/content/common/gpu/gpu_command_buffer_stub.cc')
-rw-r--r-- | chromium/content/common/gpu/gpu_command_buffer_stub.cc | 144 |
1 files changed, 91 insertions, 53 deletions
diff --git a/chromium/content/common/gpu/gpu_command_buffer_stub.cc b/chromium/content/common/gpu/gpu_command_buffer_stub.cc index 18a666dcd9f..6e541ab4645 100644 --- a/chromium/content/common/gpu/gpu_command_buffer_stub.cc +++ b/chromium/content/common/gpu/gpu_command_buffer_stub.cc @@ -5,17 +5,15 @@ #include "base/bind.h" #include "base/bind_helpers.h" #include "base/command_line.h" -#include "base/debug/trace_event.h" #include "base/hash.h" #include "base/json/json_writer.h" #include "base/memory/shared_memory.h" #include "base/time/time.h" +#include "base/trace_event/trace_event.h" #include "build/build_config.h" -#include "content/common/gpu/devtools_gpu_instrumentation.h" #include "content/common/gpu/gpu_channel.h" #include "content/common/gpu/gpu_channel_manager.h" #include "content/common/gpu/gpu_command_buffer_stub.h" -#include "content/common/gpu/gpu_memory_buffer_factory.h" #include "content/common/gpu/gpu_memory_manager.h" #include "content/common/gpu/gpu_memory_tracking.h" #include "content/common/gpu/gpu_messages.h" @@ -23,8 +21,8 @@ #include "content/common/gpu/image_transport_surface.h" #include "content/common/gpu/media/gpu_video_decode_accelerator.h" #include "content/common/gpu/media/gpu_video_encode_accelerator.h" -#include "content/common/gpu/sync_point_manager.h" #include "content/public/common/content_client.h" +#include "content/public/common/content_switches.h" #include "gpu/command_buffer/common/constants.h" #include "gpu/command_buffer/common/gles2_cmd_utils.h" #include "gpu/command_buffer/common/mailbox.h" @@ -36,6 +34,8 @@ #include "gpu/command_buffer/service/mailbox_manager.h" #include "gpu/command_buffer/service/memory_tracking.h" #include "gpu/command_buffer/service/query_manager.h" +#include "gpu/command_buffer/service/sync_point_manager.h" +#include "gpu/command_buffer/service/valuebuffer_manager.h" #include "ui/gl/gl_bindings.h" #include "ui/gl/gl_switches.h" @@ -112,10 +112,10 @@ const int64 kHandleMoreWorkPeriodBusyMs = 1; // Prevents idle work from being starved. const int64 kMaxTimeSinceIdleMs = 10; -class DevToolsChannelData : public base::debug::ConvertableToTraceFormat { +class DevToolsChannelData : public base::trace_event::ConvertableToTraceFormat { public: - static scoped_refptr<base::debug::ConvertableToTraceFormat> CreateForChannel( - GpuChannel* channel); + static scoped_refptr<base::trace_event::ConvertableToTraceFormat> + CreateForChannel(GpuChannel* channel); void AppendAsTraceFormat(std::string* out) const override { std::string tmp; @@ -130,7 +130,7 @@ class DevToolsChannelData : public base::debug::ConvertableToTraceFormat { DISALLOW_COPY_AND_ASSIGN(DevToolsChannelData); }; -scoped_refptr<base::debug::ConvertableToTraceFormat> +scoped_refptr<base::trace_event::ConvertableToTraceFormat> DevToolsChannelData::CreateForChannel(GpuChannel* channel) { scoped_ptr<base::DictionaryValue> res(new base::DictionaryValue); res->SetInteger("renderer_pid", channel->renderer_pid()); @@ -149,6 +149,8 @@ GpuCommandBufferStub::GpuCommandBufferStub( GpuCommandBufferStub* share_group, const gfx::GLSurfaceHandle& handle, gpu::gles2::MailboxManager* mailbox_manager, + gpu::gles2::SubscriptionRefSet* subscription_ref_set, + gpu::ValueStateMap* pending_valuebuffer_state, const gfx::Size& size, const gpu::gles2::DisallowedFeatures& disallowed_features, const std::vector<int32>& attribs, @@ -193,11 +195,21 @@ GpuCommandBufferStub::GpuCommandBufferStub( new GpuCommandBufferMemoryTracker(channel), channel_->gpu_channel_manager()->shader_translator_cache(), NULL, + subscription_ref_set, + pending_valuebuffer_state, attrib_parser.bind_generates_resource); } use_virtualized_gl_context_ |= context_group_->feature_info()->workarounds().use_virtualized_gl_contexts; + + bool is_offscreen = surface_id_ == 0; + if (is_offscreen && initial_size_.IsEmpty()) { + // If we're an offscreen surface with zero width and/or height, set to a + // non-zero size so that we have a complete framebuffer for operations like + // glClear. + initial_size_ = gfx::Size(1, 1); + } } GpuCommandBufferStub::~GpuCommandBufferStub() { @@ -216,9 +228,6 @@ bool GpuCommandBufferStub::OnMessageReceived(const IPC::Message& message) { "GPUTask", "data", DevToolsChannelData::CreateForChannel(channel())); - // TODO(yurys): remove devtools_gpu_instrumentation call once DevTools - // Timeline migrates to tracing crbug.com/361045. - devtools_gpu_instrumentation::ScopedGpuTask task(channel()); FastSetActiveURL(active_url_, active_url_hash_); bool have_context = false; @@ -227,10 +236,15 @@ bool GpuCommandBufferStub::OnMessageReceived(const IPC::Message& message) { // handler can assume that the context is current (not necessary for // RetireSyncPoint or WaitSyncPoint). if (decoder_.get() && + message.type() != GpuCommandBufferMsg_SetGetBuffer::ID && message.type() != GpuCommandBufferMsg_WaitForTokenInRange::ID && message.type() != GpuCommandBufferMsg_WaitForGetOffsetInRange::ID && + message.type() != GpuCommandBufferMsg_RegisterTransferBuffer::ID && + message.type() != GpuCommandBufferMsg_DestroyTransferBuffer::ID && message.type() != GpuCommandBufferMsg_RetireSyncPoint::ID && - message.type() != GpuCommandBufferMsg_SignalSyncPoint::ID) { + message.type() != GpuCommandBufferMsg_SignalSyncPoint::ID && + message.type() != + GpuCommandBufferMsg_SetClientHasMemoryAllocationChangedCallback::ID) { if (!MakeCurrent()) return false; have_context = true; @@ -309,30 +323,26 @@ void GpuCommandBufferStub::PollWork() { return; if (scheduler_) { - bool fences_complete = scheduler_->PollUnscheduleFences(); - // Perform idle work if all fences are complete. - if (fences_complete) { - uint64 current_messages_processed = - channel()->gpu_channel_manager()->MessagesProcessed(); - // We're idle when no messages were processed or scheduled. - bool is_idle = - (previous_messages_processed_ == current_messages_processed) && - !channel()->gpu_channel_manager()->HandleMessagesScheduled(); - if (!is_idle && !last_idle_time_.is_null()) { - base::TimeDelta time_since_idle = base::TimeTicks::Now() - - last_idle_time_; - base::TimeDelta max_time_since_idle = - base::TimeDelta::FromMilliseconds(kMaxTimeSinceIdleMs); - - // Force idle when it's been too long since last time we were idle. - if (time_since_idle > max_time_since_idle) - is_idle = true; - } + uint64 current_messages_processed = + channel()->gpu_channel_manager()->MessagesProcessed(); + // We're idle when no messages were processed or scheduled. + bool is_idle = + (previous_messages_processed_ == current_messages_processed) && + !channel()->gpu_channel_manager()->HandleMessagesScheduled(); + if (!is_idle && !last_idle_time_.is_null()) { + base::TimeDelta time_since_idle = + base::TimeTicks::Now() - last_idle_time_; + base::TimeDelta max_time_since_idle = + base::TimeDelta::FromMilliseconds(kMaxTimeSinceIdleMs); + + // Force idle when it's been too long since last time we were idle. + if (time_since_idle > max_time_since_idle) + is_idle = true; + } - if (is_idle) { - last_idle_time_ = base::TimeTicks::Now(); - scheduler_->PerformIdleWork(); - } + if (is_idle) { + last_idle_time_ = base::TimeTicks::Now(); + scheduler_->PerformIdleWork(); } } ScheduleDelayedWork(kHandleMoreWorkPeriodBusyMs); @@ -376,9 +386,8 @@ void GpuCommandBufferStub::ScheduleDelayedWork(int64 delay) { delay = 0; } - base::MessageLoop::current()->PostDelayedTask( - FROM_HERE, - base::Bind(&GpuCommandBufferStub::PollWork, AsWeakPtr()), + base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( + FROM_HERE, base::Bind(&GpuCommandBufferStub::PollWork, AsWeakPtr()), base::TimeDelta::FromMilliseconds(delay)); } @@ -420,9 +429,11 @@ void GpuCommandBufferStub::Destroy() { scheduler_.reset(); bool have_context = false; - if (decoder_ && command_buffer_ && - command_buffer_->GetLastState().error != gpu::error::kLostContext) - have_context = decoder_->MakeCurrent(); + if (decoder_ && decoder_->GetGLContext()) { + // Try to make the context current regardless of whether it was lost, so we + // don't leak resources. + have_context = decoder_->GetGLContext()->MakeCurrent(surface_.get()); + } FOR_EACH_OBSERVER(DestructionObserver, destruction_observers_, OnWillDestroyStub()); @@ -462,6 +473,13 @@ void GpuCommandBufferStub::OnInitialize( decoder_.reset(::gpu::gles2::GLES2Decoder::Create(context_group_.get())); + if (!base::CommandLine::ForCurrentProcess()->HasSwitch( + switches::kSingleProcess) && + !base::CommandLine::ForCurrentProcess()->HasSwitch( + switches::kInProcessGPU)) { + decoder_->SetAllowExit(true); + } + scheduler_.reset(new gpu::GpuScheduler(command_buffer_.get(), decoder_.get(), decoder_.get())); @@ -566,8 +584,8 @@ void GpuCommandBufferStub::OnInitialize( return; } - if (CommandLine::ForCurrentProcess()->HasSwitch( - switches::kEnableGPUServiceLogging)) { + if (base::CommandLine::ForCurrentProcess()->HasSwitch( + switches::kEnableGPUServiceLogging)) { decoder_->set_log_commands(true); } @@ -670,7 +688,7 @@ void GpuCommandBufferStub::OnParseError() { DCHECK(command_buffer_.get()); gpu::CommandBuffer::State state = command_buffer_->GetLastState(); IPC::Message* msg = new GpuCommandBufferMsg_Destroyed( - route_id_, state.context_lost_reason); + route_id_, state.context_lost_reason, state.error); msg->set_unblock(true); Send(msg); @@ -820,7 +838,7 @@ void GpuCommandBufferStub::OnCreateVideoDecoder( IPC::Message* reply_message) { TRACE_EVENT0("gpu", "GpuCommandBufferStub::OnCreateVideoDecoder"); GpuVideoDecodeAccelerator* decoder = new GpuVideoDecodeAccelerator( - decoder_route_id, this, channel_->io_message_loop()); + decoder_route_id, this, channel_->io_task_runner()); decoder->Initialize(profile, reply_message); // decoder is registered as a DestructionObserver of this stub and will // self-delete during destruction of this stub. @@ -956,12 +974,26 @@ void GpuCommandBufferStub::OnCreateImage(int32 id, return; } - GpuChannelManager* manager = channel_->gpu_channel_manager(); - scoped_refptr<gfx::GLImage> image = - manager->gpu_memory_buffer_factory() - ->AsImageFactory() - ->CreateImageForGpuMemoryBuffer( - handle, size, format, internalformat, channel()->client_id()); + if (!gpu::ImageFactory::IsGpuMemoryBufferFormatSupported( + format, decoder_->GetCapabilities())) { + LOG(ERROR) << "Format is not supported."; + return; + } + + if (!gpu::ImageFactory::IsImageSizeValidForGpuMemoryBufferFormat(size, + format)) { + LOG(ERROR) << "Invalid image size for format."; + return; + } + + if (!gpu::ImageFactory::IsImageFormatCompatibleWithGpuMemoryBufferFormat( + internalformat, format)) { + LOG(ERROR) << "Incompatible image format."; + return; + } + + scoped_refptr<gfx::GLImage> image = channel()->CreateImageForGpuMemoryBuffer( + handle, size, format, internalformat); if (!image.get()) return; @@ -1074,7 +1106,7 @@ void GpuCommandBufferStub::MarkContextLost() { command_buffer_->SetContextLostReason(gpu::error::kUnknown); if (decoder_) - decoder_->LoseContext(GL_UNKNOWN_CONTEXT_RESET_ARB); + decoder_->MarkContextLost(gpu::error::kUnknown); command_buffer_->SetParseError(gpu::error::kLostContext); } @@ -1082,9 +1114,15 @@ uint64 GpuCommandBufferStub::GetMemoryUsage() const { return GetMemoryManager()->GetClientMemoryUsage(this); } -void GpuCommandBufferStub::SwapBuffersCompleted( +void GpuCommandBufferStub::SendSwapBuffersCompleted( const std::vector<ui::LatencyInfo>& latency_info) { Send(new GpuCommandBufferMsg_SwapBuffersCompleted(route_id_, latency_info)); } +void GpuCommandBufferStub::SendUpdateVSyncParameters(base::TimeTicks timebase, + base::TimeDelta interval) { + Send(new GpuCommandBufferMsg_UpdateVSyncParameters(route_id_, timebase, + interval)); +} + } // namespace content |