OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/browser/gpu/browser_gpu_channel_host_factory.h" | 5 #include "content/browser/gpu/browser_gpu_channel_host_factory.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/debug/trace_event.h" | 8 #include "base/debug/trace_event.h" |
9 #include "base/synchronization/waitable_event.h" | 9 #include "base/synchronization/waitable_event.h" |
10 #include "base/threading/thread_restrictions.h" | 10 #include "base/threading/thread_restrictions.h" |
(...skipping 18 matching lines...) Expand all Loading... | |
29 CreateRequest() | 29 CreateRequest() |
30 : event(true, false), gpu_host_id(0), route_id(MSG_ROUTING_NONE), | 30 : event(true, false), gpu_host_id(0), route_id(MSG_ROUTING_NONE), |
31 result(CREATE_COMMAND_BUFFER_FAILED) {} | 31 result(CREATE_COMMAND_BUFFER_FAILED) {} |
32 ~CreateRequest() {} | 32 ~CreateRequest() {} |
33 base::WaitableEvent event; | 33 base::WaitableEvent event; |
34 int gpu_host_id; | 34 int gpu_host_id; |
35 int32 route_id; | 35 int32 route_id; |
36 CreateCommandBufferResult result; | 36 CreateCommandBufferResult result; |
37 }; | 37 }; |
38 | 38 |
39 struct BrowserGpuChannelHostFactory::AllocateGpuMemoryBufferRequest { | |
40 AllocateGpuMemoryBufferRequest() | |
41 : event(true, false), width(0), height(0), internalformat(0), usage(0) {} | |
piman
2014/09/05 22:30:37
nit: might as well providing instead a constructor
reveman
2014/09/05 23:58:43
Did it this way to be consistent with CreateReques
| |
42 ~AllocateGpuMemoryBufferRequest() {} | |
43 base::WaitableEvent event; | |
44 size_t width; | |
45 size_t height; | |
46 unsigned internalformat; | |
47 unsigned usage; | |
48 scoped_ptr<gfx::GpuMemoryBuffer> result; | |
49 }; | |
50 | |
39 class BrowserGpuChannelHostFactory::EstablishRequest | 51 class BrowserGpuChannelHostFactory::EstablishRequest |
40 : public base::RefCountedThreadSafe<EstablishRequest> { | 52 : public base::RefCountedThreadSafe<EstablishRequest> { |
41 public: | 53 public: |
42 static scoped_refptr<EstablishRequest> Create(CauseForGpuLaunch cause, | 54 static scoped_refptr<EstablishRequest> Create(CauseForGpuLaunch cause, |
43 int gpu_client_id, | 55 int gpu_client_id, |
44 int gpu_host_id); | 56 int gpu_host_id); |
45 void Wait(); | 57 void Wait(); |
46 void Cancel(); | 58 void Cancel(); |
47 | 59 |
48 int gpu_host_id() { return gpu_host_id_; } | 60 int gpu_host_id() { return gpu_host_id_; } |
(...skipping 307 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
356 established_callbacks_[n].Run(); | 368 established_callbacks_[n].Run(); |
357 | 369 |
358 established_callbacks_.clear(); | 370 established_callbacks_.clear(); |
359 } | 371 } |
360 | 372 |
361 scoped_ptr<gfx::GpuMemoryBuffer> | 373 scoped_ptr<gfx::GpuMemoryBuffer> |
362 BrowserGpuChannelHostFactory::AllocateGpuMemoryBuffer(size_t width, | 374 BrowserGpuChannelHostFactory::AllocateGpuMemoryBuffer(size_t width, |
363 size_t height, | 375 size_t height, |
364 unsigned internalformat, | 376 unsigned internalformat, |
365 unsigned usage) { | 377 unsigned usage) { |
366 if (!GpuMemoryBufferImpl::IsFormatValid(internalformat) || | 378 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
piman
2014/09/05 22:30:37
Couldn't this be called on the compositor thread?
reveman
2014/09/05 23:58:43
I didn't think of that. Changed DCHECKs as suggest
| |
367 !GpuMemoryBufferImpl::IsUsageValid(usage)) | |
368 return scoped_ptr<gfx::GpuMemoryBuffer>(); | |
369 | 379 |
370 return GpuMemoryBufferImpl::Create(gfx::Size(width, height), | 380 AllocateGpuMemoryBufferRequest request; |
371 internalformat, | 381 request.width = width; |
372 usage).PassAs<gfx::GpuMemoryBuffer>(); | 382 request.height = height; |
383 request.internalformat = internalformat; | |
384 request.usage = usage; | |
385 | |
386 GetIOLoopProxy()->PostTask( | |
387 FROM_HERE, | |
388 base::Bind(&BrowserGpuChannelHostFactory::AllocateGpuMemoryBufferOnIO, | |
389 base::Unretained(&request))); | |
390 | |
391 // We're blocking the UI thread, which is generally undesirable. | |
392 TRACE_EVENT0("browser", | |
393 "BrowserGpuChannelHostFactory::AllocateGpuMemoryBuffer"); | |
394 base::ThreadRestrictions::ScopedAllowWait allow_wait; | |
395 request.event.Wait(); | |
396 return request.result.Pass(); | |
397 } | |
398 | |
399 void BrowserGpuChannelHostFactory::DeleteGpuMemoryBuffer( | |
400 scoped_ptr<gfx::GpuMemoryBuffer> buffer) { | |
401 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | |
402 | |
403 GetIOLoopProxy()->PostTask( | |
404 FROM_HERE, | |
405 base::Bind(&BrowserGpuChannelHostFactory::DeleteGpuMemoryBufferOnIO, | |
406 base::Passed(&buffer))); | |
407 } | |
408 | |
409 void BrowserGpuChannelHostFactory::CreateGpuMemoryBuffer( | |
410 const gfx::GpuMemoryBufferHandle& handle, | |
411 const gfx::Size& size, | |
412 unsigned internalformat, | |
413 unsigned usage, | |
414 const CreateGpuMemoryBufferCallback& callback) { | |
415 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | |
416 | |
417 GpuProcessHost* host = GpuProcessHost::FromID(gpu_host_id_); | |
418 if (!host) { | |
419 callback.Run(gfx::GpuMemoryBufferHandle()); | |
420 return; | |
421 } | |
422 | |
423 uint32 request_id = next_create_gpu_memory_buffer_request_id_++; | |
424 create_gpu_memory_buffer_requests_[request_id] = callback; | |
425 | |
426 host->CreateGpuMemoryBuffer( | |
427 handle, | |
428 size, | |
429 internalformat, | |
430 usage, | |
431 base::Bind(&BrowserGpuChannelHostFactory::OnGpuMemoryBufferCreated, | |
432 base::Unretained(this), | |
433 request_id)); | |
434 } | |
435 | |
436 void BrowserGpuChannelHostFactory::DestroyGpuMemoryBuffer( | |
437 const gfx::GpuMemoryBufferHandle& handle, | |
438 int32 sync_point) { | |
439 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | |
440 | |
441 GpuProcessHost* host = GpuProcessHost::FromID(gpu_host_id_); | |
442 if (!host) | |
443 return; | |
444 | |
445 host->DestroyGpuMemoryBuffer(handle, sync_point); | |
373 } | 446 } |
374 | 447 |
375 // static | 448 // static |
376 void BrowserGpuChannelHostFactory::AddFilterOnIO( | 449 void BrowserGpuChannelHostFactory::AddFilterOnIO( |
377 int host_id, | 450 int host_id, |
378 scoped_refptr<IPC::MessageFilter> filter) { | 451 scoped_refptr<IPC::MessageFilter> filter) { |
379 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 452 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); |
380 | 453 |
381 GpuProcessHost* host = GpuProcessHost::FromID(host_id); | 454 GpuProcessHost* host = GpuProcessHost::FromID(host_id); |
382 if (host) | 455 if (host) |
(...skipping 16 matching lines...) Expand all Loading... | |
399 target_task_runner); | 472 target_task_runner); |
400 filter->AddRoute(MSG_ROUTING_CONTROL, handler); | 473 filter->AddRoute(MSG_ROUTING_CONTROL, handler); |
401 | 474 |
402 GetIOLoopProxy()->PostTask( | 475 GetIOLoopProxy()->PostTask( |
403 FROM_HERE, | 476 FROM_HERE, |
404 base::Bind(&BrowserGpuChannelHostFactory::AddFilterOnIO, | 477 base::Bind(&BrowserGpuChannelHostFactory::AddFilterOnIO, |
405 gpu_host_id_, | 478 gpu_host_id_, |
406 filter)); | 479 filter)); |
407 } | 480 } |
408 | 481 |
409 void BrowserGpuChannelHostFactory::CreateGpuMemoryBuffer( | 482 // static |
410 const gfx::GpuMemoryBufferHandle& handle, | 483 void BrowserGpuChannelHostFactory::AllocateGpuMemoryBufferOnIO( |
411 const gfx::Size& size, | 484 AllocateGpuMemoryBufferRequest* request) { |
412 unsigned internalformat, | 485 if (!GpuMemoryBufferImpl::IsFormatValid(request->internalformat) || |
413 unsigned usage, | 486 !GpuMemoryBufferImpl::IsUsageValid(request->usage)) { |
414 const CreateGpuMemoryBufferCallback& callback) { | 487 request->result = scoped_ptr<gfx::GpuMemoryBuffer>(); |
415 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 488 request->event.Signal(); |
piman
2014/09/05 22:30:37
To confirm, if the GPU process dies while a reques
reveman
2014/09/05 23:58:43
No, unless I misunderstood your question. This cod
piman
2014/09/06 00:28:23
Then I'm confused... Shouldn't we signal the event
reveman
2014/09/06 20:30:49
If the format or usage is an invalid value that ca
piman
2014/09/08 18:33:57
ACK about early reject, but what about the general
reveman
2014/09/08 19:58:57
So this patch doesn't actually make it possible to
| |
416 uint32 request_id = next_create_gpu_memory_buffer_request_id_++; | |
417 create_gpu_memory_buffer_requests_[request_id] = callback; | |
418 GetIOLoopProxy()->PostTask( | |
419 FROM_HERE, | |
420 base::Bind(&BrowserGpuChannelHostFactory::CreateGpuMemoryBufferOnIO, | |
421 base::Unretained(this), | |
422 handle, | |
423 size, | |
424 internalformat, | |
425 usage, | |
426 request_id)); | |
427 } | |
428 | |
429 void BrowserGpuChannelHostFactory::DestroyGpuMemoryBuffer( | |
430 const gfx::GpuMemoryBufferHandle& handle, | |
431 int32 sync_point) { | |
432 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | |
433 GetIOLoopProxy()->PostTask( | |
434 FROM_HERE, | |
435 base::Bind(&BrowserGpuChannelHostFactory::DestroyGpuMemoryBufferOnIO, | |
436 base::Unretained(this), | |
437 handle, | |
438 sync_point)); | |
439 } | |
440 | |
441 void BrowserGpuChannelHostFactory::CreateGpuMemoryBufferOnIO( | |
442 const gfx::GpuMemoryBufferHandle& handle, | |
443 const gfx::Size& size, | |
444 unsigned internalformat, | |
445 unsigned usage, | |
446 uint32 request_id) { | |
447 GpuProcessHost* host = GpuProcessHost::FromID(gpu_host_id_); | |
448 if (!host) { | |
449 GpuMemoryBufferCreatedOnIO(request_id, gfx::GpuMemoryBufferHandle()); | |
450 return; | 489 return; |
451 } | 490 } |
452 | 491 |
453 host->CreateGpuMemoryBuffer( | 492 request->result = GpuMemoryBufferImpl::Create( |
454 handle, | 493 gfx::Size(request->width, request->height), |
piman
2014/09/05 22:30:37
nit: indent looks weird
reveman
2014/09/05 23:58:43
I agree but this seems to be the way cl format lik
| |
455 size, | 494 request->internalformat, |
456 internalformat, | 495 request->usage).PassAs<gfx::GpuMemoryBuffer>(); |
457 usage, | 496 request->event.Signal(); |
458 base::Bind(&BrowserGpuChannelHostFactory::GpuMemoryBufferCreatedOnIO, | |
459 base::Unretained(this), | |
460 request_id)); | |
461 } | 497 } |
462 | 498 |
463 void BrowserGpuChannelHostFactory::GpuMemoryBufferCreatedOnIO( | 499 // static |
464 uint32 request_id, | 500 void BrowserGpuChannelHostFactory::DeleteGpuMemoryBufferOnIO( |
465 const gfx::GpuMemoryBufferHandle& handle) { | 501 scoped_ptr<gfx::GpuMemoryBuffer> buffer) { |
466 BrowserThread::PostTask( | |
467 BrowserThread::UI, | |
468 FROM_HERE, | |
469 base::Bind(&BrowserGpuChannelHostFactory::OnGpuMemoryBufferCreated, | |
470 base::Unretained(this), | |
471 request_id, | |
472 handle)); | |
473 } | 502 } |
474 | 503 |
475 void BrowserGpuChannelHostFactory::OnGpuMemoryBufferCreated( | 504 void BrowserGpuChannelHostFactory::OnGpuMemoryBufferCreated( |
476 uint32 request_id, | 505 uint32 request_id, |
477 const gfx::GpuMemoryBufferHandle& handle) { | 506 const gfx::GpuMemoryBufferHandle& handle) { |
507 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | |
508 | |
478 CreateGpuMemoryBufferCallbackMap::iterator iter = | 509 CreateGpuMemoryBufferCallbackMap::iterator iter = |
479 create_gpu_memory_buffer_requests_.find(request_id); | 510 create_gpu_memory_buffer_requests_.find(request_id); |
480 DCHECK(iter != create_gpu_memory_buffer_requests_.end()); | 511 DCHECK(iter != create_gpu_memory_buffer_requests_.end()); |
481 iter->second.Run(handle); | 512 iter->second.Run(handle); |
482 create_gpu_memory_buffer_requests_.erase(iter); | 513 create_gpu_memory_buffer_requests_.erase(iter); |
483 } | 514 } |
484 | 515 |
485 void BrowserGpuChannelHostFactory::DestroyGpuMemoryBufferOnIO( | |
486 const gfx::GpuMemoryBufferHandle& handle, | |
487 int32 sync_point) { | |
488 GpuProcessHost* host = GpuProcessHost::FromID(gpu_host_id_); | |
489 if (!host) | |
490 return; | |
491 | |
492 host->DestroyGpuMemoryBuffer(handle, sync_point); | |
493 } | |
494 | |
495 } // namespace content | 516 } // namespace content |
OLD | NEW |