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 "gpu/command_buffer/service/gles2_cmd_decoder.h" | 5 #include "gpu/command_buffer/service/gles2_cmd_decoder.h" |
6 | 6 |
7 #include <stdio.h> | 7 #include <stdio.h> |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
10 #include <list> | 10 #include <list> |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
52 #include "gpu/command_buffer/service/renderbuffer_manager.h" | 52 #include "gpu/command_buffer/service/renderbuffer_manager.h" |
53 #include "gpu/command_buffer/service/shader_manager.h" | 53 #include "gpu/command_buffer/service/shader_manager.h" |
54 #include "gpu/command_buffer/service/shader_translator.h" | 54 #include "gpu/command_buffer/service/shader_translator.h" |
55 #include "gpu/command_buffer/service/shader_translator_cache.h" | 55 #include "gpu/command_buffer/service/shader_translator_cache.h" |
56 #include "gpu/command_buffer/service/stream_texture.h" | 56 #include "gpu/command_buffer/service/stream_texture.h" |
57 #include "gpu/command_buffer/service/stream_texture_manager.h" | 57 #include "gpu/command_buffer/service/stream_texture_manager.h" |
58 #include "gpu/command_buffer/service/texture_manager.h" | 58 #include "gpu/command_buffer/service/texture_manager.h" |
59 #include "gpu/command_buffer/service/vertex_array_manager.h" | 59 #include "gpu/command_buffer/service/vertex_array_manager.h" |
60 #include "gpu/command_buffer/service/vertex_attrib_manager.h" | 60 #include "gpu/command_buffer/service/vertex_attrib_manager.h" |
61 #include "ui/gl/gl_bindings.h" | 61 #include "ui/gl/gl_bindings.h" |
62 #include "ui/gl/gl_fence.h" | |
62 #include "ui/gl/gl_image.h" | 63 #include "ui/gl/gl_image.h" |
63 #include "ui/gl/gl_implementation.h" | 64 #include "ui/gl/gl_implementation.h" |
64 #include "ui/gl/gl_surface.h" | 65 #include "ui/gl/gl_surface.h" |
65 | 66 |
66 #if defined(OS_MACOSX) | 67 #if defined(OS_MACOSX) |
67 #include "ui/gl/io_surface_support_mac.h" | 68 #include "ui/gl/io_surface_support_mac.h" |
68 #endif | 69 #endif |
69 | 70 |
70 // TODO(zmo): we can't include "City.h" due to type def conflicts. | 71 // TODO(zmo): we can't include "City.h" due to type def conflicts. |
71 extern uint64 CityHash64(const char*, size_t); | 72 extern uint64 CityHash64(const char*, size_t); |
(...skipping 398 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
470 GLuint id() const { | 471 GLuint id() const { |
471 return id_; | 472 return id_; |
472 } | 473 } |
473 | 474 |
474 private: | 475 private: |
475 GLES2DecoderImpl* decoder_; | 476 GLES2DecoderImpl* decoder_; |
476 GLuint id_; | 477 GLuint id_; |
477 DISALLOW_COPY_AND_ASSIGN(BackFramebuffer); | 478 DISALLOW_COPY_AND_ASSIGN(BackFramebuffer); |
478 }; | 479 }; |
479 | 480 |
481 struct FenceCallback { | |
482 explicit FenceCallback() | |
483 : fence(gfx::GLFence::Create()) { | |
484 DCHECK(fence); | |
485 } | |
486 void AddCallback(base::Closure cb) { | |
487 callbacks.push_back(cb); | |
488 } | |
489 std::vector<base::Closure> callbacks; | |
490 scoped_ptr<gfx::GLFence> fence; | |
491 }; | |
492 | |
493 | |
480 // } // anonymous namespace. | 494 // } // anonymous namespace. |
481 | 495 |
482 bool GLES2Decoder::GetServiceTextureId(uint32 client_texture_id, | 496 bool GLES2Decoder::GetServiceTextureId(uint32 client_texture_id, |
483 uint32* service_texture_id) { | 497 uint32* service_texture_id) { |
484 return false; | 498 return false; |
485 } | 499 } |
486 | 500 |
487 GLES2Decoder::GLES2Decoder() | 501 GLES2Decoder::GLES2Decoder() |
488 : initialized_(false), | 502 : initialized_(false), |
489 debug_(false), | 503 debug_(false), |
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
580 virtual QueryManager* GetQueryManager() OVERRIDE { | 594 virtual QueryManager* GetQueryManager() OVERRIDE { |
581 return query_manager_.get(); | 595 return query_manager_.get(); |
582 } | 596 } |
583 virtual VertexArrayManager* GetVertexArrayManager() OVERRIDE { | 597 virtual VertexArrayManager* GetVertexArrayManager() OVERRIDE { |
584 return vertex_array_manager_.get(); | 598 return vertex_array_manager_.get(); |
585 } | 599 } |
586 virtual bool ProcessPendingQueries() OVERRIDE; | 600 virtual bool ProcessPendingQueries() OVERRIDE; |
587 virtual bool HasMoreIdleWork() OVERRIDE; | 601 virtual bool HasMoreIdleWork() OVERRIDE; |
588 virtual void PerformIdleWork() OVERRIDE; | 602 virtual void PerformIdleWork() OVERRIDE; |
589 | 603 |
604 virtual void WaitForReadPixels(base::Closure callback) OVERRIDE; | |
605 | |
590 virtual void SetResizeCallback( | 606 virtual void SetResizeCallback( |
591 const base::Callback<void(gfx::Size, float)>& callback) OVERRIDE; | 607 const base::Callback<void(gfx::Size, float)>& callback) OVERRIDE; |
592 | 608 |
593 virtual Logger* GetLogger() OVERRIDE; | 609 virtual Logger* GetLogger() OVERRIDE; |
594 virtual ErrorState* GetErrorState() OVERRIDE; | 610 virtual ErrorState* GetErrorState() OVERRIDE; |
595 | 611 |
596 virtual void SetShaderCacheCallback( | 612 virtual void SetShaderCacheCallback( |
597 const ShaderCacheCallback& callback) OVERRIDE; | 613 const ShaderCacheCallback& callback) OVERRIDE; |
598 virtual void SetWaitSyncPointCallback( | 614 virtual void SetWaitSyncPointCallback( |
599 const WaitSyncPointCallback& callback) OVERRIDE; | 615 const WaitSyncPointCallback& callback) OVERRIDE; |
(...skipping 950 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1550 state_.bound_draw_framebuffer.get() == NULL && | 1566 state_.bound_draw_framebuffer.get() == NULL && |
1551 surface_->DeferDraws(); | 1567 surface_->DeferDraws(); |
1552 } | 1568 } |
1553 | 1569 |
1554 bool ShouldDeferReads() { | 1570 bool ShouldDeferReads() { |
1555 return !offscreen_target_frame_buffer_.get() && | 1571 return !offscreen_target_frame_buffer_.get() && |
1556 state_.bound_read_framebuffer.get() == NULL && | 1572 state_.bound_read_framebuffer.get() == NULL && |
1557 surface_->DeferDraws(); | 1573 surface_->DeferDraws(); |
1558 } | 1574 } |
1559 | 1575 |
1576 void ProcessPendingReadPixels(); | |
1577 void FinishReadPixels(const cmds::ReadPixels& c, GLuint buffer); | |
1578 | |
1560 void ForceCompileShaderIfPending(Shader* shader); | 1579 void ForceCompileShaderIfPending(Shader* shader); |
1561 | 1580 |
1562 // Generate a member function prototype for each command in an automated and | 1581 // Generate a member function prototype for each command in an automated and |
1563 // typesafe way. | 1582 // typesafe way. |
1564 #define GLES2_CMD_OP(name) \ | 1583 #define GLES2_CMD_OP(name) \ |
1565 Error Handle ## name( \ | 1584 Error Handle ## name( \ |
1566 uint32 immediate_data_size, \ | 1585 uint32 immediate_data_size, \ |
1567 const cmds::name& args); \ | 1586 const cmds::name& args); \ |
1568 | 1587 |
1569 GLES2_COMMAND_LIST(GLES2_CMD_OP) | 1588 GLES2_COMMAND_LIST(GLES2_CMD_OP) |
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1718 GLsizei viewport_max_width_; | 1737 GLsizei viewport_max_width_; |
1719 GLsizei viewport_max_height_; | 1738 GLsizei viewport_max_height_; |
1720 | 1739 |
1721 // Command buffer stats. | 1740 // Command buffer stats. |
1722 int texture_upload_count_; | 1741 int texture_upload_count_; |
1723 base::TimeDelta total_texture_upload_time_; | 1742 base::TimeDelta total_texture_upload_time_; |
1724 base::TimeDelta total_processing_commands_time_; | 1743 base::TimeDelta total_processing_commands_time_; |
1725 | 1744 |
1726 scoped_ptr<GPUTracer> gpu_tracer_; | 1745 scoped_ptr<GPUTracer> gpu_tracer_; |
1727 | 1746 |
1747 std::queue<linked_ptr<FenceCallback> > pending_readpixel_fences_; | |
1748 | |
1728 DISALLOW_COPY_AND_ASSIGN(GLES2DecoderImpl); | 1749 DISALLOW_COPY_AND_ASSIGN(GLES2DecoderImpl); |
1729 }; | 1750 }; |
1730 | 1751 |
1731 ScopedGLErrorSuppressor::ScopedGLErrorSuppressor( | 1752 ScopedGLErrorSuppressor::ScopedGLErrorSuppressor( |
1732 const char* function_name, GLES2DecoderImpl* decoder) | 1753 const char* function_name, GLES2DecoderImpl* decoder) |
1733 : function_name_(function_name), | 1754 : function_name_(function_name), |
1734 decoder_(decoder) { | 1755 decoder_(decoder) { |
1735 ERRORSTATE_COPY_REAL_GL_ERRORS_TO_WRAPPER(decoder_->GetErrorState(), | 1756 ERRORSTATE_COPY_REAL_GL_ERRORS_TO_WRAPPER(decoder_->GetErrorState(), |
1736 function_name_); | 1757 function_name_); |
1737 } | 1758 } |
(...skipping 754 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2492 // that can be safely migrated between the iGPU and the dGPU. Mark | 2513 // that can be safely migrated between the iGPU and the dGPU. Mark |
2493 // those contexts as safe to forcibly transition between the GPUs. | 2514 // those contexts as safe to forcibly transition between the GPUs. |
2494 // http://crbug.com/180876, http://crbug.com/227228 | 2515 // http://crbug.com/180876, http://crbug.com/227228 |
2495 if (!offscreen) | 2516 if (!offscreen) |
2496 context_->SetSafeToForceGpuSwitch(); | 2517 context_->SetSafeToForceGpuSwitch(); |
2497 | 2518 |
2498 async_pixel_transfer_manager_.reset( | 2519 async_pixel_transfer_manager_.reset( |
2499 AsyncPixelTransferManager::Create(context.get())); | 2520 AsyncPixelTransferManager::Create(context.get())); |
2500 async_pixel_transfer_manager_->Initialize(texture_manager()); | 2521 async_pixel_transfer_manager_->Initialize(texture_manager()); |
2501 | 2522 |
2523 | |
piman
2013/07/01 22:24:08
nit: extra blank line unnecessary.
hubbe
2013/07/01 22:34:41
Done.
| |
2502 return true; | 2524 return true; |
2503 } | 2525 } |
2504 | 2526 |
2505 void GLES2DecoderImpl::UpdateCapabilities() { | 2527 void GLES2DecoderImpl::UpdateCapabilities() { |
2506 util_.set_num_compressed_texture_formats( | 2528 util_.set_num_compressed_texture_formats( |
2507 validators_->compressed_texture_format.GetValues().size()); | 2529 validators_->compressed_texture_format.GetValues().size()); |
2508 util_.set_num_shader_binary_formats( | 2530 util_.set_num_shader_binary_formats( |
2509 validators_->shader_binary_format.GetValues().size()); | 2531 validators_->shader_binary_format.GetValues().size()); |
2510 } | 2532 } |
2511 | 2533 |
(...skipping 289 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2801 // Rebind the FBO if it was unbound by the context. | 2823 // Rebind the FBO if it was unbound by the context. |
2802 if (workarounds().unbind_fbo_on_context_switch) | 2824 if (workarounds().unbind_fbo_on_context_switch) |
2803 RestoreFramebufferBindings(); | 2825 RestoreFramebufferBindings(); |
2804 | 2826 |
2805 clear_state_dirty_ = true; | 2827 clear_state_dirty_ = true; |
2806 | 2828 |
2807 return true; | 2829 return true; |
2808 } | 2830 } |
2809 | 2831 |
2810 void GLES2DecoderImpl::ProcessFinishedAsyncTransfers() { | 2832 void GLES2DecoderImpl::ProcessFinishedAsyncTransfers() { |
2833 ProcessPendingReadPixels(); | |
2811 if (engine() && query_manager_.get()) | 2834 if (engine() && query_manager_.get()) |
2812 query_manager_->ProcessPendingTransferQueries(); | 2835 query_manager_->ProcessPendingTransferQueries(); |
2813 | 2836 |
2814 // TODO(epenner): Is there a better place to do this? | 2837 // TODO(epenner): Is there a better place to do this? |
2815 // This needs to occur before we execute any batch of commands | 2838 // This needs to occur before we execute any batch of commands |
2816 // from the client, as the client may have recieved an async | 2839 // from the client, as the client may have recieved an async |
2817 // completion while issuing those commands. | 2840 // completion while issuing those commands. |
2818 // "DidFlushStart" would be ideal if we had such a callback. | 2841 // "DidFlushStart" would be ideal if we had such a callback. |
2819 async_pixel_transfer_manager_->BindCompletedAsyncTransfers(); | 2842 async_pixel_transfer_manager_->BindCompletedAsyncTransfers(); |
2820 } | 2843 } |
(...skipping 712 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3533 } | 3556 } |
3534 GLuint service_id = glCreateShader(type); | 3557 GLuint service_id = glCreateShader(type); |
3535 if (service_id != 0) { | 3558 if (service_id != 0) { |
3536 CreateShader(client_id, service_id, type); | 3559 CreateShader(client_id, service_id, type); |
3537 } | 3560 } |
3538 return true; | 3561 return true; |
3539 } | 3562 } |
3540 | 3563 |
3541 void GLES2DecoderImpl::DoFinish() { | 3564 void GLES2DecoderImpl::DoFinish() { |
3542 glFinish(); | 3565 glFinish(); |
3566 ProcessPendingReadPixels(); | |
3543 ProcessPendingQueries(); | 3567 ProcessPendingQueries(); |
3544 } | 3568 } |
3545 | 3569 |
3546 void GLES2DecoderImpl::DoFlush() { | 3570 void GLES2DecoderImpl::DoFlush() { |
3547 glFlush(); | 3571 glFlush(); |
3548 ProcessPendingQueries(); | 3572 ProcessPendingQueries(); |
3549 } | 3573 } |
3550 | 3574 |
3551 void GLES2DecoderImpl::DoActiveTexture(GLenum texture_unit) { | 3575 void GLES2DecoderImpl::DoActiveTexture(GLenum texture_unit) { |
3552 GLuint texture_index = texture_unit - GL_TEXTURE0; | 3576 GLuint texture_index = texture_unit - GL_TEXTURE0; |
(...skipping 3148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
6701 return error::kNoError; | 6725 return error::kNoError; |
6702 } | 6726 } |
6703 | 6727 |
6704 state_.vertex_attrib_manager->SetDivisor( | 6728 state_.vertex_attrib_manager->SetDivisor( |
6705 index, | 6729 index, |
6706 divisor); | 6730 divisor); |
6707 glVertexAttribDivisorANGLE(index, divisor); | 6731 glVertexAttribDivisorANGLE(index, divisor); |
6708 return error::kNoError; | 6732 return error::kNoError; |
6709 } | 6733 } |
6710 | 6734 |
6735 void GLES2DecoderImpl::FinishReadPixels( | |
6736 const cmds::ReadPixels& c, | |
6737 GLuint buffer) { | |
6738 TRACE_EVENT0("gpu", "GLES2DecoderImpl::FinishReadPixels"); | |
6739 GLsizei width = c.width; | |
6740 GLsizei height = c.height; | |
6741 GLenum format = c.format; | |
6742 GLenum type = c.type; | |
6743 typedef cmds::ReadPixels::Result Result; | |
6744 uint32 pixels_size; | |
6745 Result* result = NULL; | |
6746 if (c.result_shm_id != 0) { | |
6747 result = GetSharedMemoryAs<Result*>( | |
6748 c.result_shm_id, c.result_shm_offset, sizeof(*result)); | |
6749 if (!result) { | |
6750 if (buffer != 0) { | |
6751 glDeleteBuffersARB(1, &buffer); | |
6752 } | |
6753 return; | |
6754 } | |
6755 } | |
6756 GLES2Util::ComputeImageDataSizes( | |
6757 width, height, format, type, state_.pack_alignment, &pixels_size, | |
6758 NULL, NULL); | |
6759 void* pixels = GetSharedMemoryAs<void*>( | |
6760 c.pixels_shm_id, c.pixels_shm_offset, pixels_size); | |
6761 if (!pixels) { | |
6762 if (buffer != 0) { | |
6763 glDeleteBuffersARB(1, &buffer); | |
6764 } | |
6765 return; | |
6766 } | |
6767 | |
6768 if (buffer != 0) { | |
6769 glBindBuffer(GL_PIXEL_PACK_BUFFER_ARB, buffer); | |
6770 void* data = glMapBuffer(GL_PIXEL_PACK_BUFFER_ARB, GL_READ_ONLY); | |
6771 memcpy(pixels, data, pixels_size); | |
6772 // GL_PIXEL_PACK_BUFFER_ARB is currently unused, so we don't | |
6773 // have to restore the state. | |
6774 glUnmapBuffer(GL_PIXEL_PACK_BUFFER_ARB); | |
6775 glBindBuffer(GL_PIXEL_PACK_BUFFER_ARB, 0); | |
6776 glDeleteBuffersARB(1, &buffer); | |
6777 } | |
6778 | |
6779 if (result != NULL) { | |
6780 *result = true; | |
6781 } | |
6782 | |
6783 GLenum read_format = GetBoundReadFrameBufferInternalFormat(); | |
6784 uint32 channels_exist = GLES2Util::GetChannelsForFormat(read_format); | |
6785 if ((channels_exist & 0x0008) == 0 && | |
6786 workarounds().clear_alpha_in_readpixels) { | |
6787 // Set the alpha to 255 because some drivers are buggy in this regard. | |
6788 uint32 temp_size; | |
6789 | |
6790 uint32 unpadded_row_size; | |
6791 uint32 padded_row_size; | |
6792 if (!GLES2Util::ComputeImageDataSizes( | |
6793 width, 2, format, type, state_.pack_alignment, &temp_size, | |
6794 &unpadded_row_size, &padded_row_size)) { | |
6795 return; | |
6796 } | |
6797 // NOTE: Assumes the type is GL_UNSIGNED_BYTE which was true at the time | |
6798 // of this implementation. | |
6799 if (type != GL_UNSIGNED_BYTE) { | |
6800 return; | |
6801 } | |
6802 switch (format) { | |
6803 case GL_RGBA: | |
6804 case GL_BGRA_EXT: | |
6805 case GL_ALPHA: { | |
6806 int offset = (format == GL_ALPHA) ? 0 : 3; | |
6807 int step = (format == GL_ALPHA) ? 1 : 4; | |
6808 uint8* dst = static_cast<uint8*>(pixels) + offset; | |
6809 for (GLint yy = 0; yy < height; ++yy) { | |
6810 uint8* end = dst + unpadded_row_size; | |
6811 for (uint8* d = dst; d < end; d += step) { | |
6812 *d = 255; | |
6813 } | |
6814 dst += padded_row_size; | |
6815 } | |
6816 break; | |
6817 } | |
6818 default: | |
6819 break; | |
6820 } | |
6821 } | |
6822 } | |
6823 | |
6824 | |
6711 error::Error GLES2DecoderImpl::HandleReadPixels( | 6825 error::Error GLES2DecoderImpl::HandleReadPixels( |
6712 uint32 immediate_data_size, const cmds::ReadPixels& c) { | 6826 uint32 immediate_data_size, const cmds::ReadPixels& c) { |
6713 if (ShouldDeferReads()) | 6827 if (ShouldDeferReads()) |
6714 return error::kDeferCommandUntilLater; | 6828 return error::kDeferCommandUntilLater; |
6715 GLint x = c.x; | 6829 GLint x = c.x; |
6716 GLint y = c.y; | 6830 GLint y = c.y; |
6717 GLsizei width = c.width; | 6831 GLsizei width = c.width; |
6718 GLsizei height = c.height; | 6832 GLsizei height = c.height; |
6719 GLenum format = c.format; | 6833 GLenum format = c.format; |
6720 GLenum type = c.type; | 6834 GLenum type = c.type; |
6835 GLboolean async = c.async; | |
6721 if (width < 0 || height < 0) { | 6836 if (width < 0 || height < 0) { |
6722 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, "glReadPixels", "dimensions < 0"); | 6837 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, "glReadPixels", "dimensions < 0"); |
6723 return error::kNoError; | 6838 return error::kNoError; |
6724 } | 6839 } |
6725 typedef cmds::ReadPixels::Result Result; | 6840 typedef cmds::ReadPixels::Result Result; |
6726 uint32 pixels_size; | 6841 uint32 pixels_size; |
6727 if (!GLES2Util::ComputeImageDataSizes( | 6842 if (!GLES2Util::ComputeImageDataSizes( |
6728 width, height, format, type, state_.pack_alignment, &pixels_size, | 6843 width, height, format, type, state_.pack_alignment, &pixels_size, |
6729 NULL, NULL)) { | 6844 NULL, NULL)) { |
6730 return error::kOutOfBounds; | 6845 return error::kOutOfBounds; |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
6810 memset(dst, 0, unpadded_row_size); | 6925 memset(dst, 0, unpadded_row_size); |
6811 | 6926 |
6812 // If the row is in range, copy it. | 6927 // If the row is in range, copy it. |
6813 if (ry >= 0 && ry < max_size.height() && read_width > 0) { | 6928 if (ry >= 0 && ry < max_size.height() && read_width > 0) { |
6814 glReadPixels( | 6929 glReadPixels( |
6815 read_x, ry, read_width, 1, format, type, dst + dest_row_offset); | 6930 read_x, ry, read_width, 1, format, type, dst + dest_row_offset); |
6816 } | 6931 } |
6817 dst += padded_row_size; | 6932 dst += padded_row_size; |
6818 } | 6933 } |
6819 } else { | 6934 } else { |
6935 if (async && features().use_async_readpixels) { | |
6936 GLuint buffer; | |
6937 glGenBuffersARB(1, &buffer); | |
6938 glBindBuffer(GL_PIXEL_PACK_BUFFER_ARB, buffer); | |
6939 glBufferData(GL_PIXEL_PACK_BUFFER_ARB, pixels_size, NULL, GL_STREAM_READ); | |
6940 GLenum error = glGetError(); | |
6941 if (error == GL_NO_ERROR) { | |
6942 glReadPixels(x, y, width, height, format, type, 0); | |
6943 pending_readpixel_fences_.push(linked_ptr<FenceCallback>( | |
6944 new FenceCallback())); | |
6945 WaitForReadPixels(base::Bind( | |
6946 &GLES2DecoderImpl::FinishReadPixels, | |
6947 base::internal::SupportsWeakPtrBase::StaticAsWeakPtr | |
6948 <GLES2DecoderImpl>(this), | |
6949 c, buffer)); | |
6950 glBindBuffer(GL_PIXEL_PACK_BUFFER_ARB, 0); | |
6951 return error::kNoError; | |
6952 } | |
6953 } | |
6820 glReadPixels(x, y, width, height, format, type, pixels); | 6954 glReadPixels(x, y, width, height, format, type, pixels); |
6821 } | 6955 } |
6822 GLenum error = LOCAL_PEEK_GL_ERROR("glReadPixels"); | 6956 GLenum error = LOCAL_PEEK_GL_ERROR("glReadPixels"); |
6823 if (error == GL_NO_ERROR) { | 6957 if (error == GL_NO_ERROR) { |
6824 if (result != NULL) { | 6958 if (result != NULL) { |
6825 *result = true; | 6959 *result = true; |
6826 } | 6960 } |
6827 | 6961 FinishReadPixels(c, 0); |
6828 GLenum read_format = GetBoundReadFrameBufferInternalFormat(); | |
6829 uint32 channels_exist = GLES2Util::GetChannelsForFormat(read_format); | |
6830 if ((channels_exist & 0x0008) == 0 && | |
6831 workarounds().clear_alpha_in_readpixels) { | |
6832 // Set the alpha to 255 because some drivers are buggy in this regard. | |
6833 uint32 temp_size; | |
6834 | |
6835 uint32 unpadded_row_size; | |
6836 uint32 padded_row_size; | |
6837 if (!GLES2Util::ComputeImageDataSizes( | |
6838 width, 2, format, type, state_.pack_alignment, &temp_size, | |
6839 &unpadded_row_size, &padded_row_size)) { | |
6840 LOCAL_SET_GL_ERROR( | |
6841 GL_INVALID_VALUE, "glReadPixels", "dimensions out of range"); | |
6842 return error::kNoError; | |
6843 } | |
6844 // NOTE: Assumes the type is GL_UNSIGNED_BYTE which was true at the time | |
6845 // of this implementation. | |
6846 if (type != GL_UNSIGNED_BYTE) { | |
6847 LOCAL_SET_GL_ERROR( | |
6848 GL_INVALID_OPERATION, "glReadPixels", | |
6849 "unsupported readPixel format"); | |
6850 return error::kNoError; | |
6851 } | |
6852 switch (format) { | |
6853 case GL_RGBA: | |
6854 case GL_BGRA_EXT: | |
6855 case GL_ALPHA: { | |
6856 int offset = (format == GL_ALPHA) ? 0 : 3; | |
6857 int step = (format == GL_ALPHA) ? 1 : 4; | |
6858 uint8* dst = static_cast<uint8*>(pixels) + offset; | |
6859 for (GLint yy = 0; yy < height; ++yy) { | |
6860 uint8* end = dst + unpadded_row_size; | |
6861 for (uint8* d = dst; d < end; d += step) { | |
6862 *d = 255; | |
6863 } | |
6864 dst += padded_row_size; | |
6865 } | |
6866 break; | |
6867 } | |
6868 default: | |
6869 break; | |
6870 } | |
6871 } | |
6872 } | 6962 } |
6873 | 6963 |
6874 return error::kNoError; | 6964 return error::kNoError; |
6875 } | 6965 } |
6876 | 6966 |
6877 error::Error GLES2DecoderImpl::HandlePixelStorei( | 6967 error::Error GLES2DecoderImpl::HandlePixelStorei( |
6878 uint32 immediate_data_size, const cmds::PixelStorei& c) { | 6968 uint32 immediate_data_size, const cmds::PixelStorei& c) { |
6879 GLenum pname = c.pname; | 6969 GLenum pname = c.pname; |
6880 GLenum param = c.param; | 6970 GLenum param = c.param; |
6881 if (!validators_->pixel_store.IsValid(pname)) { | 6971 if (!validators_->pixel_store.IsValid(pname)) { |
(...skipping 2209 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
9091 bool GLES2DecoderImpl::ProcessPendingQueries() { | 9181 bool GLES2DecoderImpl::ProcessPendingQueries() { |
9092 if (query_manager_.get() == NULL) { | 9182 if (query_manager_.get() == NULL) { |
9093 return false; | 9183 return false; |
9094 } | 9184 } |
9095 if (!query_manager_->ProcessPendingQueries()) { | 9185 if (!query_manager_->ProcessPendingQueries()) { |
9096 current_decoder_error_ = error::kOutOfBounds; | 9186 current_decoder_error_ = error::kOutOfBounds; |
9097 } | 9187 } |
9098 return query_manager_->HavePendingQueries(); | 9188 return query_manager_->HavePendingQueries(); |
9099 } | 9189 } |
9100 | 9190 |
9191 // Note that if there are no pending readpixels right now, | |
9192 // this function will call the callback immediately. | |
9193 void GLES2DecoderImpl::WaitForReadPixels(base::Closure callback) { | |
9194 if (features().use_async_readpixels && !pending_readpixel_fences_.empty()) { | |
9195 pending_readpixel_fences_.back()->callbacks.push_back(callback); | |
9196 } else { | |
9197 callback.Run(); | |
9198 } | |
9199 } | |
9200 | |
9201 void GLES2DecoderImpl::ProcessPendingReadPixels() { | |
9202 while (!pending_readpixel_fences_.empty() && | |
9203 pending_readpixel_fences_.front()->fence->HasCompleted()) { | |
9204 std::vector<base::Closure> callbacks = | |
9205 pending_readpixel_fences_.front()->callbacks; | |
9206 pending_readpixel_fences_.pop(); | |
9207 for (size_t i = 0; i < callbacks.size(); i++) { | |
9208 callbacks[i].Run(); | |
9209 } | |
9210 } | |
9211 } | |
9212 | |
9101 bool GLES2DecoderImpl::HasMoreIdleWork() { | 9213 bool GLES2DecoderImpl::HasMoreIdleWork() { |
9102 return async_pixel_transfer_manager_->NeedsProcessMorePendingTransfers(); | 9214 return !pending_readpixel_fences_.empty() || |
9215 async_pixel_transfer_manager_->NeedsProcessMorePendingTransfers(); | |
9103 } | 9216 } |
9104 | 9217 |
9105 void GLES2DecoderImpl::PerformIdleWork() { | 9218 void GLES2DecoderImpl::PerformIdleWork() { |
9219 ProcessPendingReadPixels(); | |
9106 if (!async_pixel_transfer_manager_->NeedsProcessMorePendingTransfers()) | 9220 if (!async_pixel_transfer_manager_->NeedsProcessMorePendingTransfers()) |
9107 return; | 9221 return; |
9108 async_pixel_transfer_manager_->ProcessMorePendingTransfers(); | 9222 async_pixel_transfer_manager_->ProcessMorePendingTransfers(); |
9109 ProcessFinishedAsyncTransfers(); | 9223 ProcessFinishedAsyncTransfers(); |
9110 } | 9224 } |
9111 | 9225 |
9112 error::Error GLES2DecoderImpl::HandleBeginQueryEXT( | 9226 error::Error GLES2DecoderImpl::HandleBeginQueryEXT( |
9113 uint32 immediate_data_size, const cmds::BeginQueryEXT& c) { | 9227 uint32 immediate_data_size, const cmds::BeginQueryEXT& c) { |
9114 GLenum target = static_cast<GLenum>(c.target); | 9228 GLenum target = static_cast<GLenum>(c.target); |
9115 GLuint client_id = static_cast<GLuint>(c.id); | 9229 GLuint client_id = static_cast<GLuint>(c.id); |
9116 int32 sync_shm_id = static_cast<int32>(c.sync_data_shm_id); | 9230 int32 sync_shm_id = static_cast<int32>(c.sync_data_shm_id); |
9117 uint32 sync_shm_offset = static_cast<uint32>(c.sync_data_shm_offset); | 9231 uint32 sync_shm_offset = static_cast<uint32>(c.sync_data_shm_offset); |
9118 | 9232 |
9119 switch (target) { | 9233 switch (target) { |
9120 case GL_COMMANDS_ISSUED_CHROMIUM: | 9234 case GL_COMMANDS_ISSUED_CHROMIUM: |
9121 case GL_LATENCY_QUERY_CHROMIUM: | 9235 case GL_LATENCY_QUERY_CHROMIUM: |
9122 case GL_ASYNC_PIXEL_TRANSFERS_COMPLETED_CHROMIUM: | 9236 case GL_ASYNC_PIXEL_TRANSFERS_COMPLETED_CHROMIUM: |
9237 case GL_ASYNC_READ_PIXELS_COMPLETED_CHROMIUM: | |
9123 case GL_GET_ERROR_QUERY_CHROMIUM: | 9238 case GL_GET_ERROR_QUERY_CHROMIUM: |
9124 break; | 9239 break; |
9125 default: | 9240 default: |
9126 if (!features().occlusion_query_boolean) { | 9241 if (!features().occlusion_query_boolean) { |
9127 LOCAL_SET_GL_ERROR( | 9242 LOCAL_SET_GL_ERROR( |
9128 GL_INVALID_OPERATION, "glBeginQueryEXT", | 9243 GL_INVALID_OPERATION, "glBeginQueryEXT", |
9129 "not enabled for occlusion queries"); | 9244 "not enabled for occlusion queries"); |
9130 return error::kNoError; | 9245 return error::kNoError; |
9131 } | 9246 } |
9132 break; | 9247 break; |
9133 } | 9248 } |
9134 | 9249 |
9250 // TODO(hubbe): Make it possible to have one query per type running at the | |
9251 // same time. | |
9135 if (state_.current_query.get()) { | 9252 if (state_.current_query.get()) { |
9136 LOCAL_SET_GL_ERROR( | 9253 LOCAL_SET_GL_ERROR( |
9137 GL_INVALID_OPERATION, "glBeginQueryEXT", "query already in progress"); | 9254 GL_INVALID_OPERATION, "glBeginQueryEXT", "query already in progress"); |
9138 return error::kNoError; | 9255 return error::kNoError; |
9139 } | 9256 } |
9140 | 9257 |
9141 if (client_id == 0) { | 9258 if (client_id == 0) { |
9142 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glBeginQueryEXT", "id is 0"); | 9259 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glBeginQueryEXT", "id is 0"); |
9143 return error::kNoError; | 9260 return error::kNoError; |
9144 } | 9261 } |
(...skipping 1201 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
10346 return error::kNoError; | 10463 return error::kNoError; |
10347 } | 10464 } |
10348 | 10465 |
10349 // Include the auto-generated part of this file. We split this because it means | 10466 // Include the auto-generated part of this file. We split this because it means |
10350 // we can easily edit the non-auto generated parts right here in this file | 10467 // we can easily edit the non-auto generated parts right here in this file |
10351 // instead of having to edit some template or the code generator. | 10468 // instead of having to edit some template or the code generator. |
10352 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" | 10469 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" |
10353 | 10470 |
10354 } // namespace gles2 | 10471 } // namespace gles2 |
10355 } // namespace gpu | 10472 } // namespace gpu |
OLD | NEW |