| 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 <limits.h> | 7 #include <limits.h> |
| 8 #include <stddef.h> | 8 #include <stddef.h> |
| 9 #include <stdint.h> | 9 #include <stdint.h> |
| 10 #include <stdio.h> | 10 #include <stdio.h> |
| (...skipping 5331 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5342 "id not generated by glGenBuffers"); | 5342 "id not generated by glGenBuffers"); |
| 5343 return; | 5343 return; |
| 5344 } | 5344 } |
| 5345 | 5345 |
| 5346 // It's a new id so make a buffer for it. | 5346 // It's a new id so make a buffer for it. |
| 5347 glGenBuffersARB(1, &service_id); | 5347 glGenBuffersARB(1, &service_id); |
| 5348 CreateBuffer(client_id, service_id); | 5348 CreateBuffer(client_id, service_id); |
| 5349 buffer = GetBuffer(client_id); | 5349 buffer = GetBuffer(client_id); |
| 5350 DCHECK(buffer); | 5350 DCHECK(buffer); |
| 5351 } | 5351 } |
| 5352 if (!buffer_manager()->SetTarget(buffer, target)) { | |
| 5353 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | |
| 5354 "buffer bound to more than 1 target"); | |
| 5355 return; | |
| 5356 } | |
| 5357 service_id = buffer->service_id(); | 5352 service_id = buffer->service_id(); |
| 5358 } | 5353 } |
| 5359 LogClientServiceForInfo(buffer, client_id, function_name); | 5354 LogClientServiceForInfo(buffer, client_id, function_name); |
| 5360 | 5355 |
| 5361 scoped_refptr<IndexedBufferBindingHost> bindings; | 5356 scoped_refptr<IndexedBufferBindingHost> bindings; |
| 5362 switch (target) { | 5357 switch (target) { |
| 5363 case GL_TRANSFORM_FEEDBACK_BUFFER: | 5358 case GL_TRANSFORM_FEEDBACK_BUFFER: |
| 5364 bindings = state_.bound_transform_feedback.get(); | 5359 bindings = state_.bound_transform_feedback.get(); |
| 5365 break; | 5360 break; |
| 5366 case GL_UNIFORM_BUFFER: | 5361 case GL_UNIFORM_BUFFER: |
| (...skipping 426 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5793 return; | 5788 return; |
| 5794 } | 5789 } |
| 5795 if (buffer->GetMappedRange()) { | 5790 if (buffer->GetMappedRange()) { |
| 5796 std::string msg = base::StringPrintf( | 5791 std::string msg = base::StringPrintf( |
| 5797 "bound buffer bound at index %i is mapped", static_cast<int>(ii)); | 5792 "bound buffer bound at index %i is mapped", static_cast<int>(ii)); |
| 5798 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, msg.c_str()); | 5793 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, msg.c_str()); |
| 5799 return; | 5794 return; |
| 5800 } | 5795 } |
| 5801 } | 5796 } |
| 5802 transform_feedback->DoBeginTransformFeedback(primitive_mode); | 5797 transform_feedback->DoBeginTransformFeedback(primitive_mode); |
| 5803 DCHECK(transform_feedback->active()); | |
| 5804 } | 5798 } |
| 5805 | 5799 |
| 5806 void GLES2DecoderImpl::DoEndTransformFeedback() { | 5800 void GLES2DecoderImpl::DoEndTransformFeedback() { |
| 5807 const char* function_name = "glEndTransformFeedback"; | 5801 const char* function_name = "glEndTransformFeedback"; |
| 5808 DCHECK(state_.bound_transform_feedback.get()); | 5802 DCHECK(state_.bound_transform_feedback.get()); |
| 5809 if (!state_.bound_transform_feedback->active()) { | 5803 if (!state_.bound_transform_feedback->active()) { |
| 5810 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 5804 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 5811 "transform feedback is not active"); | 5805 "transform feedback is not active"); |
| 5812 return; | 5806 return; |
| 5813 } | 5807 } |
| (...skipping 3697 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 9511 LOCAL_SET_GL_ERROR( | 9505 LOCAL_SET_GL_ERROR( |
| 9512 GL_INVALID_OPERATION, function_name, | 9506 GL_INVALID_OPERATION, function_name, |
| 9513 "Source and destination textures of the draw are the same."); | 9507 "Source and destination textures of the draw are the same."); |
| 9514 return false; | 9508 return false; |
| 9515 } | 9509 } |
| 9516 | 9510 |
| 9517 return state_.vertex_attrib_manager | 9511 return state_.vertex_attrib_manager |
| 9518 ->ValidateBindings(function_name, | 9512 ->ValidateBindings(function_name, |
| 9519 this, | 9513 this, |
| 9520 feature_info_.get(), | 9514 feature_info_.get(), |
| 9521 buffer_manager(), | |
| 9522 state_.current_program.get(), | 9515 state_.current_program.get(), |
| 9523 max_vertex_accessed, | 9516 max_vertex_accessed, |
| 9524 instanced, | 9517 instanced, |
| 9525 primcount); | 9518 primcount); |
| 9526 } | 9519 } |
| 9527 | 9520 |
| 9528 bool GLES2DecoderImpl::SimulateAttrib0( | 9521 bool GLES2DecoderImpl::SimulateAttrib0( |
| 9529 const char* function_name, GLuint max_vertex_accessed, bool* simulated) { | 9522 const char* function_name, GLuint max_vertex_accessed, bool* simulated) { |
| 9530 DCHECK(simulated); | 9523 DCHECK(simulated); |
| 9531 *simulated = false; | 9524 *simulated = false; |
| (...skipping 301 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 9833 LOCAL_RENDER_WARNING("Render count or primcount is 0."); | 9826 LOCAL_RENDER_WARNING("Render count or primcount is 0."); |
| 9834 return error::kNoError; | 9827 return error::kNoError; |
| 9835 } | 9828 } |
| 9836 | 9829 |
| 9837 if (feature_info_->IsWebGL2OrES3Context()) { | 9830 if (feature_info_->IsWebGL2OrES3Context()) { |
| 9838 if (!AttribsTypeMatch()) { | 9831 if (!AttribsTypeMatch()) { |
| 9839 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 9832 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9840 "vertexAttrib function must match shader attrib type"); | 9833 "vertexAttrib function must match shader attrib type"); |
| 9841 return error::kNoError; | 9834 return error::kNoError; |
| 9842 } | 9835 } |
| 9836 if (state_.bound_array_buffer.get() && |
| 9837 state_.bound_array_buffer->GetMappedRange()) { |
| 9838 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9839 "bound ARRAY_BUFFER is mapped"); |
| 9840 return error::kNoError; |
| 9841 } |
| 9843 } | 9842 } |
| 9844 | 9843 |
| 9845 base::CheckedNumeric<GLuint> checked_max_vertex = first; | 9844 base::CheckedNumeric<GLuint> checked_max_vertex = first; |
| 9846 checked_max_vertex += count - 1; | 9845 checked_max_vertex += count - 1; |
| 9847 // first and count-1 are both a non-negative int, so their sum fits an | 9846 // first and count-1 are both a non-negative int, so their sum fits an |
| 9848 // unsigned int. | 9847 // unsigned int. |
| 9849 if (!checked_max_vertex.IsValid()) { | 9848 GLuint max_vertex_accessed = checked_max_vertex.ValueOrDie(); |
| 9850 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, | |
| 9851 "first + count overflow"); | |
| 9852 return error::kNoError; | |
| 9853 } | |
| 9854 GLuint max_vertex_accessed = checked_max_vertex.ValueOrDefault(0); | |
| 9855 if (IsDrawValid(function_name, max_vertex_accessed, instanced, primcount)) { | 9849 if (IsDrawValid(function_name, max_vertex_accessed, instanced, primcount)) { |
| 9856 if (!ClearUnclearedTextures()) { | 9850 if (!ClearUnclearedTextures()) { |
| 9857 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "out of memory"); | 9851 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "out of memory"); |
| 9858 return error::kNoError; | 9852 return error::kNoError; |
| 9859 } | 9853 } |
| 9860 bool simulated_attrib_0 = false; | 9854 bool simulated_attrib_0 = false; |
| 9861 if (!SimulateAttrib0( | 9855 if (!SimulateAttrib0( |
| 9862 function_name, max_vertex_accessed, &simulated_attrib_0)) { | 9856 function_name, max_vertex_accessed, &simulated_attrib_0)) { |
| 9863 return error::kNoError; | 9857 return error::kNoError; |
| 9864 } | 9858 } |
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 9929 error::Error GLES2DecoderImpl::DoDrawElements(const char* function_name, | 9923 error::Error GLES2DecoderImpl::DoDrawElements(const char* function_name, |
| 9930 bool instanced, | 9924 bool instanced, |
| 9931 GLenum mode, | 9925 GLenum mode, |
| 9932 GLsizei count, | 9926 GLsizei count, |
| 9933 GLenum type, | 9927 GLenum type, |
| 9934 int32_t offset, | 9928 int32_t offset, |
| 9935 GLsizei primcount) { | 9929 GLsizei primcount) { |
| 9936 error::Error error = WillAccessBoundFramebufferForDraw(); | 9930 error::Error error = WillAccessBoundFramebufferForDraw(); |
| 9937 if (error != error::kNoError) | 9931 if (error != error::kNoError) |
| 9938 return error; | 9932 return error; |
| 9933 if (!state_.vertex_attrib_manager->element_array_buffer()) { |
| 9934 LOCAL_SET_GL_ERROR( |
| 9935 GL_INVALID_OPERATION, function_name, "No element array buffer bound"); |
| 9936 return error::kNoError; |
| 9937 } |
| 9939 | 9938 |
| 9940 if (count < 0) { | 9939 if (count < 0) { |
| 9941 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "count < 0"); | 9940 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "count < 0"); |
| 9942 return error::kNoError; | 9941 return error::kNoError; |
| 9943 } | 9942 } |
| 9944 if (offset < 0) { | 9943 if (offset < 0) { |
| 9945 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "offset < 0"); | 9944 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "offset < 0"); |
| 9946 return error::kNoError; | 9945 return error::kNoError; |
| 9947 } | 9946 } |
| 9948 if (!validators_->draw_mode.IsValid(mode)) { | 9947 if (!validators_->draw_mode.IsValid(mode)) { |
| 9949 LOCAL_SET_GL_ERROR_INVALID_ENUM(function_name, mode, "mode"); | 9948 LOCAL_SET_GL_ERROR_INVALID_ENUM(function_name, mode, "mode"); |
| 9950 return error::kNoError; | 9949 return error::kNoError; |
| 9951 } | 9950 } |
| 9952 if (!validators_->index_type.IsValid(type)) { | 9951 if (!validators_->index_type.IsValid(type)) { |
| 9953 LOCAL_SET_GL_ERROR_INVALID_ENUM(function_name, type, "type"); | 9952 LOCAL_SET_GL_ERROR_INVALID_ENUM(function_name, type, "type"); |
| 9954 return error::kNoError; | 9953 return error::kNoError; |
| 9955 } | 9954 } |
| 9956 if (primcount < 0) { | 9955 if (primcount < 0) { |
| 9957 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "primcount < 0"); | 9956 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "primcount < 0"); |
| 9958 return error::kNoError; | 9957 return error::kNoError; |
| 9959 } | 9958 } |
| 9960 Buffer* element_array_buffer = buffer_manager()->RequestBufferAccess( | |
| 9961 &state_, GL_ELEMENT_ARRAY_BUFFER, function_name); | |
| 9962 if (!element_array_buffer) { | |
| 9963 return error::kNoError; | |
| 9964 } | |
| 9965 | 9959 |
| 9966 if (!CheckBoundDrawFramebufferValid(function_name)) { | 9960 if (!CheckBoundDrawFramebufferValid(function_name)) { |
| 9967 return error::kNoError; | 9961 return error::kNoError; |
| 9968 } | 9962 } |
| 9969 | 9963 |
| 9970 if (state_.bound_transform_feedback.get() && | 9964 if (state_.bound_transform_feedback.get() && |
| 9971 state_.bound_transform_feedback->active() && | 9965 state_.bound_transform_feedback->active() && |
| 9972 !state_.bound_transform_feedback->paused()) { | 9966 !state_.bound_transform_feedback->paused()) { |
| 9973 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 9967 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9974 "transformfeedback is active and not paused"); | 9968 "transformfeedback is active and not paused"); |
| 9975 return error::kNoError; | 9969 return error::kNoError; |
| 9976 } | 9970 } |
| 9977 | 9971 |
| 9978 if (count == 0 || primcount == 0) { | 9972 if (count == 0 || primcount == 0) { |
| 9979 return error::kNoError; | 9973 return error::kNoError; |
| 9980 } | 9974 } |
| 9981 | 9975 |
| 9982 if (feature_info_->IsWebGL2OrES3Context()) { | 9976 if (feature_info_->IsWebGL2OrES3Context()) { |
| 9983 if (!AttribsTypeMatch()) { | 9977 if (!AttribsTypeMatch()) { |
| 9984 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 9978 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9985 "vertexAttrib function must match shader attrib type"); | 9979 "vertexAttrib function must match shader attrib type"); |
| 9986 return error::kNoError; | 9980 return error::kNoError; |
| 9987 } | 9981 } |
| 9982 if (state_.bound_array_buffer.get() && |
| 9983 state_.bound_array_buffer->GetMappedRange()) { |
| 9984 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9985 "bound ARRAY_BUFFER is mapped"); |
| 9986 return error::kNoError; |
| 9987 } |
| 9988 if (state_.vertex_attrib_manager->element_array_buffer() && |
| 9989 state_.vertex_attrib_manager->element_array_buffer() |
| 9990 ->GetMappedRange()) { |
| 9991 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 9992 "bound ELEMENT_ARRAY_BUFFER is mapped"); |
| 9993 return error::kNoError; |
| 9994 } |
| 9988 } | 9995 } |
| 9989 | 9996 |
| 9990 GLuint max_vertex_accessed; | 9997 GLuint max_vertex_accessed; |
| 9998 Buffer* element_array_buffer = |
| 9999 state_.vertex_attrib_manager->element_array_buffer(); |
| 10000 |
| 9991 if (!element_array_buffer->GetMaxValueForRange( | 10001 if (!element_array_buffer->GetMaxValueForRange( |
| 9992 offset, count, type, | 10002 offset, count, type, |
| 9993 state_.enable_flags.primitive_restart_fixed_index, | 10003 state_.enable_flags.primitive_restart_fixed_index, |
| 9994 &max_vertex_accessed)) { | 10004 &max_vertex_accessed)) { |
| 9995 LOCAL_SET_GL_ERROR( | 10005 LOCAL_SET_GL_ERROR( |
| 9996 GL_INVALID_OPERATION, function_name, "range out of bounds for buffer"); | 10006 GL_INVALID_OPERATION, function_name, "range out of bounds for buffer"); |
| 9997 return error::kNoError; | 10007 return error::kNoError; |
| 9998 } | 10008 } |
| 9999 | 10009 |
| 10000 if (IsDrawValid(function_name, max_vertex_accessed, instanced, primcount)) { | 10010 if (IsDrawValid(function_name, max_vertex_accessed, instanced, primcount)) { |
| (...skipping 1074 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11075 WriteAlphaData<uint16_t>(pixels, height, channel_count, alpha_channel, | 11085 WriteAlphaData<uint16_t>(pixels, height, channel_count, alpha_channel, |
| 11076 unpadded_row_size, padded_row_size, 0x3C00); | 11086 unpadded_row_size, padded_row_size, 0x3C00); |
| 11077 break; | 11087 break; |
| 11078 } | 11088 } |
| 11079 } | 11089 } |
| 11080 } | 11090 } |
| 11081 } | 11091 } |
| 11082 | 11092 |
| 11083 error::Error GLES2DecoderImpl::HandleReadPixels(uint32_t immediate_data_size, | 11093 error::Error GLES2DecoderImpl::HandleReadPixels(uint32_t immediate_data_size, |
| 11084 const volatile void* cmd_data) { | 11094 const volatile void* cmd_data) { |
| 11085 const char* func_name = "glReadPixels"; | |
| 11086 const volatile gles2::cmds::ReadPixels& c = | 11095 const volatile gles2::cmds::ReadPixels& c = |
| 11087 *static_cast<const volatile gles2::cmds::ReadPixels*>(cmd_data); | 11096 *static_cast<const volatile gles2::cmds::ReadPixels*>(cmd_data); |
| 11088 TRACE_EVENT0("gpu", "GLES2DecoderImpl::HandleReadPixels"); | 11097 TRACE_EVENT0("gpu", "GLES2DecoderImpl::HandleReadPixels"); |
| 11089 error::Error fbo_error = WillAccessBoundFramebufferForRead(); | 11098 error::Error fbo_error = WillAccessBoundFramebufferForRead(); |
| 11090 if (fbo_error != error::kNoError) | 11099 if (fbo_error != error::kNoError) |
| 11091 return fbo_error; | 11100 return fbo_error; |
| 11092 GLint x = c.x; | 11101 GLint x = c.x; |
| 11093 GLint y = c.y; | 11102 GLint y = c.y; |
| 11094 GLsizei width = c.width; | 11103 GLsizei width = c.width; |
| 11095 GLsizei height = c.height; | 11104 GLsizei height = c.height; |
| 11096 GLenum format = c.format; | 11105 GLenum format = c.format; |
| 11097 GLenum type = c.type; | 11106 GLenum type = c.type; |
| 11098 uint32_t pixels_shm_id = c.pixels_shm_id; | 11107 uint32_t pixels_shm_id = c.pixels_shm_id; |
| 11099 uint32_t pixels_shm_offset = c.pixels_shm_offset; | 11108 uint32_t pixels_shm_offset = c.pixels_shm_offset; |
| 11100 uint32_t result_shm_id = c.result_shm_id; | 11109 uint32_t result_shm_id = c.result_shm_id; |
| 11101 uint32_t result_shm_offset = c.result_shm_offset; | 11110 uint32_t result_shm_offset = c.result_shm_offset; |
| 11102 GLboolean async = static_cast<GLboolean>(c.async); | 11111 GLboolean async = static_cast<GLboolean>(c.async); |
| 11103 if (width < 0 || height < 0) { | 11112 if (width < 0 || height < 0) { |
| 11104 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, "dimensions < 0"); | 11113 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, "glReadPixels", "dimensions < 0"); |
| 11105 return error::kNoError; | 11114 return error::kNoError; |
| 11106 } | 11115 } |
| 11107 typedef cmds::ReadPixels::Result Result; | 11116 typedef cmds::ReadPixels::Result Result; |
| 11108 | 11117 |
| 11109 PixelStoreParams params; | 11118 PixelStoreParams params; |
| 11110 if (pixels_shm_id == 0) { | 11119 if (pixels_shm_id == 0) { |
| 11111 params = state_.GetPackParams(); | 11120 params = state_.GetPackParams(); |
| 11112 } else { | 11121 } else { |
| 11113 // When reading into client buffer, we actually set pack parameters to 0 | 11122 // When reading into client buffer, we actually set pack parameters to 0 |
| 11114 // (except for alignment) before calling glReadPixels. This makes sure we | 11123 // (except for alignment) before calling glReadPixels. This makes sure we |
| (...skipping 14 matching lines...) Expand all Loading... |
| 11129 &unpadded_row_size, | 11138 &unpadded_row_size, |
| 11130 &padded_row_size, | 11139 &padded_row_size, |
| 11131 &skip_size, | 11140 &skip_size, |
| 11132 &padding)) { | 11141 &padding)) { |
| 11133 return error::kOutOfBounds; | 11142 return error::kOutOfBounds; |
| 11134 } | 11143 } |
| 11135 | 11144 |
| 11136 uint8_t* pixels = nullptr; | 11145 uint8_t* pixels = nullptr; |
| 11137 Buffer* buffer = state_.bound_pixel_pack_buffer.get(); | 11146 Buffer* buffer = state_.bound_pixel_pack_buffer.get(); |
| 11138 if (pixels_shm_id == 0) { | 11147 if (pixels_shm_id == 0) { |
| 11139 if (!buffer) { | 11148 if (buffer) { |
| 11149 if (buffer->GetMappedRange()) { |
| 11150 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glReadPixels", |
| 11151 "pixel pack buffer should not be mapped to client memory"); |
| 11152 return error::kNoError; |
| 11153 } |
| 11154 uint32_t size = 0; |
| 11155 if (!SafeAddUint32(pixels_size + skip_size, pixels_shm_offset, &size)) { |
| 11156 LOCAL_SET_GL_ERROR( |
| 11157 GL_INVALID_VALUE, "glReadPixels", "size + offset overflow"); |
| 11158 return error::kNoError; |
| 11159 } |
| 11160 if (static_cast<uint32_t>(buffer->size()) < size) { |
| 11161 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glReadPixels", |
| 11162 "pixel pack buffer is not large enough"); |
| 11163 return error::kNoError; |
| 11164 } |
| 11165 pixels = reinterpret_cast<uint8_t *>(pixels_shm_offset); |
| 11166 pixels += skip_size; |
| 11167 } else { |
| 11140 return error::kInvalidArguments; | 11168 return error::kInvalidArguments; |
| 11141 } | 11169 } |
| 11142 if (!buffer_manager()->RequestBufferAccess( | |
| 11143 state_.GetErrorState(), buffer, func_name, "pixel pack buffer")) { | |
| 11144 return error::kNoError; | |
| 11145 } | |
| 11146 uint32_t size = 0; | |
| 11147 if (!SafeAddUint32(pixels_size + skip_size, pixels_shm_offset, &size)) { | |
| 11148 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, "size + offset overflow"); | |
| 11149 return error::kNoError; | |
| 11150 } | |
| 11151 if (static_cast<uint32_t>(buffer->size()) < size) { | |
| 11152 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glReadPixels", | |
| 11153 "pixel pack buffer is not large enough"); | |
| 11154 return error::kNoError; | |
| 11155 } | |
| 11156 pixels = reinterpret_cast<uint8_t *>(pixels_shm_offset); | |
| 11157 pixels += skip_size; | |
| 11158 } else { | 11170 } else { |
| 11159 if (buffer) { | 11171 if (buffer) { |
| 11160 return error::kInvalidArguments; | 11172 return error::kInvalidArguments; |
| 11161 } | 11173 } else { |
| 11162 DCHECK_EQ(0u, skip_size); | 11174 DCHECK_EQ(0u, skip_size); |
| 11163 pixels = GetSharedMemoryAs<uint8_t*>( | 11175 pixels = GetSharedMemoryAs<uint8_t*>( |
| 11164 pixels_shm_id, pixels_shm_offset, pixels_size); | 11176 pixels_shm_id, pixels_shm_offset, pixels_size); |
| 11165 if (!pixels) { | 11177 if (!pixels) { |
| 11166 return error::kOutOfBounds; | 11178 return error::kOutOfBounds; |
| 11179 } |
| 11167 } | 11180 } |
| 11168 } | 11181 } |
| 11169 | 11182 |
| 11170 Result* result = nullptr; | 11183 Result* result = nullptr; |
| 11171 if (result_shm_id != 0) { | 11184 if (result_shm_id != 0) { |
| 11172 result = GetSharedMemoryAs<Result*>( | 11185 result = GetSharedMemoryAs<Result*>( |
| 11173 result_shm_id, result_shm_offset, sizeof(*result)); | 11186 result_shm_id, result_shm_offset, sizeof(*result)); |
| 11174 if (!result) { | 11187 if (!result) { |
| 11175 return error::kOutOfBounds; | 11188 return error::kOutOfBounds; |
| 11176 } | 11189 } |
| 11177 if (result->success != 0) { | 11190 if (result->success != 0) { |
| 11178 return error::kInvalidArguments; | 11191 return error::kInvalidArguments; |
| 11179 } | 11192 } |
| 11180 } | 11193 } |
| 11181 | 11194 |
| 11182 if (!validators_->read_pixel_format.IsValid(format)) { | 11195 if (!validators_->read_pixel_format.IsValid(format)) { |
| 11183 LOCAL_SET_GL_ERROR_INVALID_ENUM(func_name, format, "format"); | 11196 LOCAL_SET_GL_ERROR_INVALID_ENUM("glReadPixels", format, "format"); |
| 11184 return error::kNoError; | 11197 return error::kNoError; |
| 11185 } | 11198 } |
| 11186 if (!validators_->read_pixel_type.IsValid(type)) { | 11199 if (!validators_->read_pixel_type.IsValid(type)) { |
| 11187 LOCAL_SET_GL_ERROR_INVALID_ENUM(func_name, type, "type"); | 11200 LOCAL_SET_GL_ERROR_INVALID_ENUM("glReadPixels", type, "type"); |
| 11188 return error::kNoError; | 11201 return error::kNoError; |
| 11189 } | 11202 } |
| 11190 | 11203 |
| 11191 if (!CheckBoundReadFramebufferValid( | 11204 if (!CheckBoundReadFramebufferValid("glReadPixels", |
| 11192 func_name, GL_INVALID_FRAMEBUFFER_OPERATION)) { | 11205 GL_INVALID_FRAMEBUFFER_OPERATION)) { |
| 11193 return error::kNoError; | 11206 return error::kNoError; |
| 11194 } | 11207 } |
| 11195 GLenum src_internal_format = GetBoundReadFramebufferInternalFormat(); | 11208 GLenum src_internal_format = GetBoundReadFramebufferInternalFormat(); |
| 11196 if (src_internal_format == 0) { | 11209 if (src_internal_format == 0) { |
| 11197 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, "no valid color image"); | 11210 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glReadPixels", |
| 11211 "no valid color image"); |
| 11198 return error::kNoError; | 11212 return error::kNoError; |
| 11199 } | 11213 } |
| 11200 std::vector<GLenum> accepted_formats; | 11214 std::vector<GLenum> accepted_formats; |
| 11201 std::vector<GLenum> accepted_types; | 11215 std::vector<GLenum> accepted_types; |
| 11202 switch (src_internal_format) { | 11216 switch (src_internal_format) { |
| 11203 case GL_R8UI: | 11217 case GL_R8UI: |
| 11204 case GL_R16UI: | 11218 case GL_R16UI: |
| 11205 case GL_R32UI: | 11219 case GL_R32UI: |
| 11206 case GL_RG8UI: | 11220 case GL_RG8UI: |
| 11207 case GL_RG16UI: | 11221 case GL_RG16UI: |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11269 GLint preferred_format = 0; | 11283 GLint preferred_format = 0; |
| 11270 DoGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_FORMAT, &preferred_format, 1); | 11284 DoGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_FORMAT, &preferred_format, 1); |
| 11271 GLint preferred_type = 0; | 11285 GLint preferred_type = 0; |
| 11272 DoGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_TYPE, &preferred_type, 1); | 11286 DoGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_TYPE, &preferred_type, 1); |
| 11273 if (format == static_cast<GLenum>(preferred_format) && | 11287 if (format == static_cast<GLenum>(preferred_format) && |
| 11274 type == static_cast<GLenum>(preferred_type)) { | 11288 type == static_cast<GLenum>(preferred_type)) { |
| 11275 format_type_acceptable = true; | 11289 format_type_acceptable = true; |
| 11276 } | 11290 } |
| 11277 } | 11291 } |
| 11278 if (!format_type_acceptable) { | 11292 if (!format_type_acceptable) { |
| 11279 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, | 11293 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, "glReadPixels", |
| 11280 "format and type incompatible with the current read framebuffer"); | 11294 "format and type incompatible with the current read framebuffer"); |
| 11281 return error::kNoError; | 11295 return error::kNoError; |
| 11282 } | 11296 } |
| 11283 if (type == GL_HALF_FLOAT_OES && !gl_version_info().is_es) { | 11297 if (type == GL_HALF_FLOAT_OES && !gl_version_info().is_es) { |
| 11284 type = GL_HALF_FLOAT; | 11298 type = GL_HALF_FLOAT; |
| 11285 } | 11299 } |
| 11286 if (width == 0 || height == 0) { | 11300 if (width == 0 || height == 0) { |
| 11287 return error::kNoError; | 11301 return error::kNoError; |
| 11288 } | 11302 } |
| 11289 | 11303 |
| 11290 // Get the size of the current fbo or backbuffer. | 11304 // Get the size of the current fbo or backbuffer. |
| 11291 gfx::Size max_size = GetBoundReadFramebufferSize(); | 11305 gfx::Size max_size = GetBoundReadFramebufferSize(); |
| 11292 | 11306 |
| 11293 int32_t max_x; | 11307 int32_t max_x; |
| 11294 int32_t max_y; | 11308 int32_t max_y; |
| 11295 if (!SafeAddInt32(x, width, &max_x) || !SafeAddInt32(y, height, &max_y)) { | 11309 if (!SafeAddInt32(x, width, &max_x) || !SafeAddInt32(y, height, &max_y)) { |
| 11296 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, "dimensions out of range"); | 11310 LOCAL_SET_GL_ERROR( |
| 11311 GL_INVALID_VALUE, "glReadPixels", "dimensions out of range"); |
| 11297 return error::kNoError; | 11312 return error::kNoError; |
| 11298 } | 11313 } |
| 11299 | 11314 |
| 11300 LOCAL_COPY_REAL_GL_ERRORS_TO_WRAPPER(func_name); | 11315 LOCAL_COPY_REAL_GL_ERRORS_TO_WRAPPER("glReadPixels"); |
| 11301 | 11316 |
| 11302 ScopedResolvedFramebufferBinder binder(this, false, true); | 11317 ScopedResolvedFramebufferBinder binder(this, false, true); |
| 11303 GLenum read_format = GetBoundReadFramebufferInternalFormat(); | 11318 GLenum read_format = GetBoundReadFramebufferInternalFormat(); |
| 11304 | 11319 |
| 11305 gfx::Rect rect(x, y, width, height); // Safe before we checked above. | 11320 gfx::Rect rect(x, y, width, height); // Safe before we checked above. |
| 11306 gfx::Rect max_rect(max_size); | 11321 gfx::Rect max_rect(max_size); |
| 11307 if (!max_rect.Contains(rect)) { | 11322 if (!max_rect.Contains(rect)) { |
| 11308 rect.Intersect(max_rect); | 11323 rect.Intersect(max_rect); |
| 11309 if (!rect.IsEmpty()) { | 11324 if (!rect.IsEmpty()) { |
| 11310 if (y < 0) { | 11325 if (y < 0) { |
| (...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11393 glReadPixels(x, max_y - 1, width, 1, format, type, pixels); | 11408 glReadPixels(x, max_y - 1, width, 1, format, type, pixels); |
| 11394 glPixelStorei(GL_PACK_ALIGNMENT, state_.pack_alignment); | 11409 glPixelStorei(GL_PACK_ALIGNMENT, state_.pack_alignment); |
| 11395 } else { | 11410 } else { |
| 11396 glReadPixels(x, y, width, height, format, type, pixels); | 11411 glReadPixels(x, y, width, height, format, type, pixels); |
| 11397 } | 11412 } |
| 11398 } else { | 11413 } else { |
| 11399 glReadPixels(x, y, width, height, format, type, pixels); | 11414 glReadPixels(x, y, width, height, format, type, pixels); |
| 11400 } | 11415 } |
| 11401 } | 11416 } |
| 11402 if (pixels_shm_id != 0) { | 11417 if (pixels_shm_id != 0) { |
| 11403 GLenum error = LOCAL_PEEK_GL_ERROR(func_name); | 11418 GLenum error = LOCAL_PEEK_GL_ERROR("glReadPixels"); |
| 11404 if (error == GL_NO_ERROR) { | 11419 if (error == GL_NO_ERROR) { |
| 11405 if (result) { | 11420 if (result) { |
| 11406 result->success = 1; | 11421 result->success = 1; |
| 11407 result->row_length = static_cast<uint32_t>(rect.width()); | 11422 result->row_length = static_cast<uint32_t>(rect.width()); |
| 11408 result->num_rows = static_cast<uint32_t>(rect.height()); | 11423 result->num_rows = static_cast<uint32_t>(rect.height()); |
| 11409 } | 11424 } |
| 11410 FinishReadPixels(width, height, format, type, pixels_shm_id, | 11425 FinishReadPixels(width, height, format, type, pixels_shm_id, |
| 11411 pixels_shm_offset, result_shm_id, result_shm_offset, | 11426 pixels_shm_offset, result_shm_id, result_shm_offset, |
| 11412 state_.pack_alignment, read_format, 0); | 11427 state_.pack_alignment, read_format, 0); |
| 11413 } | 11428 } |
| (...skipping 1390 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 12804 if (state_.bound_pixel_unpack_buffer->GetMappedRange() != nullptr) { | 12819 if (state_.bound_pixel_unpack_buffer->GetMappedRange() != nullptr) { |
| 12805 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 12820 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 12806 "pixel unpack buffer is mapped"); | 12821 "pixel unpack buffer is mapped"); |
| 12807 return false; | 12822 return false; |
| 12808 } | 12823 } |
| 12809 | 12824 |
| 12810 base::CheckedNumeric<GLintptr> pbo_bytes_required( | 12825 base::CheckedNumeric<GLintptr> pbo_bytes_required( |
| 12811 reinterpret_cast<GLintptr>(data)); | 12826 reinterpret_cast<GLintptr>(data)); |
| 12812 pbo_bytes_required += bytes_required; | 12827 pbo_bytes_required += bytes_required; |
| 12813 if (!pbo_bytes_required.IsValid() || | 12828 if (!pbo_bytes_required.IsValid() || |
| 12814 pbo_bytes_required.ValueOrDefault(0) > | 12829 pbo_bytes_required.ValueOrDie() > |
| 12815 state_.bound_pixel_unpack_buffer->size()) { | 12830 state_.bound_pixel_unpack_buffer->size()) { |
| 12816 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, | 12831 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, function_name, |
| 12817 "pixel unpack buffer is not large enough"); | 12832 "pixel unpack buffer is not large enough"); |
| 12818 return false; | 12833 return false; |
| 12819 } | 12834 } |
| 12820 } | 12835 } |
| 12821 | 12836 |
| 12822 return true; | 12837 return true; |
| 12823 } | 12838 } |
| 12824 | 12839 |
| (...skipping 4408 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 17233 break; | 17248 break; |
| 17234 } | 17249 } |
| 17235 } else { | 17250 } else { |
| 17236 glGetInternalformativ(target, format, pname, num_values, params); | 17251 glGetInternalformativ(target, format, pname, num_values, params); |
| 17237 } | 17252 } |
| 17238 result->SetNumResults(num_values); | 17253 result->SetNumResults(num_values); |
| 17239 return error::kNoError; | 17254 return error::kNoError; |
| 17240 } | 17255 } |
| 17241 | 17256 |
| 17242 error::Error GLES2DecoderImpl::HandleMapBufferRange( | 17257 error::Error GLES2DecoderImpl::HandleMapBufferRange( |
| 17243 uint32_t immediate_data_size, const volatile void* cmd_data) { | 17258 uint32_t immediate_data_size, |
| 17259 const volatile void* cmd_data) { |
| 17244 if (!unsafe_es3_apis_enabled()) { | 17260 if (!unsafe_es3_apis_enabled()) { |
| 17245 return error::kUnknownCommand; | 17261 return error::kUnknownCommand; |
| 17246 } | 17262 } |
| 17247 | 17263 |
| 17248 const char* func_name = "glMapBufferRange"; | 17264 const char* func_name = "glMapBufferRange"; |
| 17249 const volatile gles2::cmds::MapBufferRange& c = | 17265 const volatile gles2::cmds::MapBufferRange& c = |
| 17250 *static_cast<const volatile gles2::cmds::MapBufferRange*>(cmd_data); | 17266 *static_cast<const volatile gles2::cmds::MapBufferRange*>(cmd_data); |
| 17251 GLenum target = static_cast<GLenum>(c.target); | 17267 GLenum target = static_cast<GLenum>(c.target); |
| 17252 GLbitfield access = static_cast<GLbitfield>(c.access); | 17268 GLbitfield access = static_cast<GLbitfield>(c.access); |
| 17253 GLintptr offset = static_cast<GLintptr>(c.offset); | 17269 GLintptr offset = static_cast<GLintptr>(c.offset); |
| 17254 GLsizeiptr size = static_cast<GLsizeiptr>(c.size); | 17270 GLsizeiptr size = static_cast<GLsizeiptr>(c.size); |
| 17255 uint32_t data_shm_id = static_cast<uint32_t>(c.data_shm_id); | 17271 uint32_t data_shm_id = static_cast<uint32_t>(c.data_shm_id); |
| 17256 uint32_t data_shm_offset = static_cast<uint32_t>(c.data_shm_offset); | 17272 uint32_t data_shm_offset = static_cast<uint32_t>(c.data_shm_offset); |
| 17257 | 17273 |
| 17258 typedef cmds::MapBufferRange::Result Result; | 17274 typedef cmds::MapBufferRange::Result Result; |
| 17259 Result* result = GetSharedMemoryAs<Result*>( | 17275 Result* result = GetSharedMemoryAs<Result*>( |
| 17260 c.result_shm_id, c.result_shm_offset, sizeof(*result)); | 17276 c.result_shm_id, c.result_shm_offset, sizeof(*result)); |
| 17261 if (!result) { | 17277 if (!result) { |
| 17262 return error::kOutOfBounds; | 17278 return error::kOutOfBounds; |
| 17263 } | 17279 } |
| 17264 if (*result != 0) { | 17280 if (*result != 0) { |
| 17265 *result = 0; | 17281 *result = 0; |
| 17266 return error::kInvalidArguments; | 17282 return error::kInvalidArguments; |
| 17267 } | 17283 } |
| 17268 if (!validators_->buffer_target.IsValid(target)) { | 17284 if (!validators_->buffer_target.IsValid(target)) { |
| 17269 LOCAL_SET_GL_ERROR_INVALID_ENUM(func_name, target, "target"); | 17285 LOCAL_SET_GL_ERROR_INVALID_ENUM(func_name, target, "target"); |
| 17270 return error::kNoError; | 17286 return error::kNoError; |
| 17271 } | 17287 } |
| 17288 Buffer* buffer = buffer_manager()->GetBufferInfoForTarget(&state_, target); |
| 17289 if (!buffer) { |
| 17290 LOCAL_SET_GL_ERROR( |
| 17291 GL_INVALID_OPERATION, func_name, "no buffer bound to target"); |
| 17292 return error::kNoError; |
| 17293 } |
| 17294 if (buffer->GetMappedRange()) { |
| 17295 LOCAL_SET_GL_ERROR( |
| 17296 GL_INVALID_OPERATION, func_name, "buffer is already mapped"); |
| 17297 return error::kNoError; |
| 17298 } |
| 17272 if (size == 0) { | 17299 if (size == 0) { |
| 17273 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, "size is zero"); | 17300 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, "size is zero"); |
| 17274 return error::kNoError; | 17301 return error::kNoError; |
| 17275 } | 17302 } |
| 17276 Buffer* buffer = buffer_manager()->RequestBufferAccess( | 17303 if (!buffer->CheckRange(offset, size)) { |
| 17277 &state_, target, offset, size, func_name); | 17304 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, "invalid range"); |
| 17278 if (!buffer) { | |
| 17279 return error::kNoError; | 17305 return error::kNoError; |
| 17280 } | 17306 } |
| 17281 if (state_.bound_transform_feedback->active() && | |
| 17282 !state_.bound_transform_feedback->paused()) { | |
| 17283 size_t used_binding_count = | |
| 17284 state_.current_program->effective_transform_feedback_varyings().size(); | |
| 17285 if (state_.bound_transform_feedback->UsesBuffer( | |
| 17286 used_binding_count, buffer)) { | |
| 17287 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, | |
| 17288 "active transform feedback is using this buffer"); | |
| 17289 return error::kNoError; | |
| 17290 } | |
| 17291 } | |
| 17292 | |
| 17293 int8_t* mem = | 17307 int8_t* mem = |
| 17294 GetSharedMemoryAs<int8_t*>(data_shm_id, data_shm_offset, size); | 17308 GetSharedMemoryAs<int8_t*>(data_shm_id, data_shm_offset, size); |
| 17295 if (!mem) { | 17309 if (!mem) { |
| 17296 return error::kOutOfBounds; | 17310 return error::kOutOfBounds; |
| 17297 } | 17311 } |
| 17298 if (AnyOtherBitsSet(access, (GL_MAP_READ_BIT | | 17312 if (AnyOtherBitsSet(access, (GL_MAP_READ_BIT | |
| 17299 GL_MAP_WRITE_BIT | | 17313 GL_MAP_WRITE_BIT | |
| 17300 GL_MAP_INVALIDATE_RANGE_BIT | | 17314 GL_MAP_INVALIDATE_RANGE_BIT | |
| 17301 GL_MAP_INVALIDATE_BUFFER_BIT | | 17315 GL_MAP_INVALIDATE_BUFFER_BIT | |
| 17302 GL_MAP_FLUSH_EXPLICIT_BIT | | 17316 GL_MAP_FLUSH_EXPLICIT_BIT | |
| (...skipping 13 matching lines...) Expand all Loading... |
| 17316 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, | 17330 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, |
| 17317 "Incompatible access bits with MAP_READ_BIT"); | 17331 "Incompatible access bits with MAP_READ_BIT"); |
| 17318 return error::kNoError; | 17332 return error::kNoError; |
| 17319 } | 17333 } |
| 17320 if (AllBitsSet(access, GL_MAP_FLUSH_EXPLICIT_BIT) && | 17334 if (AllBitsSet(access, GL_MAP_FLUSH_EXPLICIT_BIT) && |
| 17321 !AllBitsSet(access, GL_MAP_WRITE_BIT)) { | 17335 !AllBitsSet(access, GL_MAP_WRITE_BIT)) { |
| 17322 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, | 17336 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, |
| 17323 "MAP_FLUSH_EXPLICIT_BIT set without MAP_WRITE_BIT"); | 17337 "MAP_FLUSH_EXPLICIT_BIT set without MAP_WRITE_BIT"); |
| 17324 return error::kNoError; | 17338 return error::kNoError; |
| 17325 } | 17339 } |
| 17340 if (target == GL_TRANSFORM_FEEDBACK_BUFFER && |
| 17341 state_.bound_transform_feedback->active()) { |
| 17342 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, |
| 17343 "transform feedback is active"); |
| 17344 return error::kNoError; |
| 17345 } |
| 17326 if (AllBitsSet(access, GL_MAP_INVALIDATE_BUFFER_BIT)) { | 17346 if (AllBitsSet(access, GL_MAP_INVALIDATE_BUFFER_BIT)) { |
| 17327 // To be on the safe side, always map GL_MAP_INVALIDATE_BUFFER_BIT to | 17347 // To be on the safe side, always map GL_MAP_INVALIDATE_BUFFER_BIT to |
| 17328 // GL_MAP_INVALIDATE_RANGE_BIT. | 17348 // GL_MAP_INVALIDATE_RANGE_BIT. |
| 17329 access = (access & ~GL_MAP_INVALIDATE_BUFFER_BIT); | 17349 access = (access & ~GL_MAP_INVALIDATE_BUFFER_BIT); |
| 17330 access = (access | GL_MAP_INVALIDATE_RANGE_BIT); | 17350 access = (access | GL_MAP_INVALIDATE_RANGE_BIT); |
| 17331 } | 17351 } |
| 17332 // Always filter out GL_MAP_UNSYNCHRONIZED_BIT to get rid of undefined | 17352 // Always filter out GL_MAP_UNSYNCHRONIZED_BIT to get rid of undefined |
| 17333 // behaviors. | 17353 // behaviors. |
| 17334 access = (access & ~GL_MAP_UNSYNCHRONIZED_BIT); | 17354 access = (access & ~GL_MAP_UNSYNCHRONIZED_BIT); |
| 17335 if (AllBitsSet(access, GL_MAP_WRITE_BIT) && | 17355 if (AllBitsSet(access, GL_MAP_WRITE_BIT) && |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 17379 if (!AllBitsSet(mapped_range->access, GL_MAP_WRITE_BIT) || | 17399 if (!AllBitsSet(mapped_range->access, GL_MAP_WRITE_BIT) || |
| 17380 AllBitsSet(mapped_range->access, GL_MAP_FLUSH_EXPLICIT_BIT)) { | 17400 AllBitsSet(mapped_range->access, GL_MAP_FLUSH_EXPLICIT_BIT)) { |
| 17381 // If we don't need to write back, or explict flush is required, no copying | 17401 // If we don't need to write back, or explict flush is required, no copying |
| 17382 // back is needed. | 17402 // back is needed. |
| 17383 } else { | 17403 } else { |
| 17384 void* mem = mapped_range->GetShmPointer(); | 17404 void* mem = mapped_range->GetShmPointer(); |
| 17385 DCHECK(mem); | 17405 DCHECK(mem); |
| 17386 DCHECK(mapped_range->pointer); | 17406 DCHECK(mapped_range->pointer); |
| 17387 memcpy(mapped_range->pointer, mem, mapped_range->size); | 17407 memcpy(mapped_range->pointer, mem, mapped_range->size); |
| 17388 if (buffer->shadowed()) { | 17408 if (buffer->shadowed()) { |
| 17389 buffer->SetRange(mapped_range->offset, mapped_range->size, mem); | 17409 bool success = buffer->SetRange( |
| 17410 mapped_range->offset, mapped_range->size, mem); |
| 17411 DCHECK(success); |
| 17390 } | 17412 } |
| 17391 } | 17413 } |
| 17392 buffer->RemoveMappedRange(); | 17414 buffer->RemoveMappedRange(); |
| 17393 GLboolean rt = glUnmapBuffer(target); | 17415 GLboolean rt = glUnmapBuffer(target); |
| 17394 if (rt == GL_FALSE) { | 17416 if (rt == GL_FALSE) { |
| 17395 // At this point, we have already done the necessary validation, so | 17417 // At this point, we have already done the necessary validation, so |
| 17396 // GL_FALSE indicates data corruption. | 17418 // GL_FALSE indicates data corruption. |
| 17397 // TODO(zmo): We could redo the map / copy data / unmap to recover, but | 17419 // TODO(zmo): We could redo the map / copy data / unmap to recover, but |
| 17398 // the second unmap could still return GL_FALSE. For now, we simply lose | 17420 // the second unmap could still return GL_FALSE. For now, we simply lose |
| 17399 // the contexts in the share group. | 17421 // the contexts in the share group. |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 17436 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, | 17458 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, func_name, |
| 17437 "offset + size out of bounds"); | 17459 "offset + size out of bounds"); |
| 17438 return; | 17460 return; |
| 17439 } | 17461 } |
| 17440 char* client_data = reinterpret_cast<char*>(mapped_range->GetShmPointer()); | 17462 char* client_data = reinterpret_cast<char*>(mapped_range->GetShmPointer()); |
| 17441 DCHECK(client_data); | 17463 DCHECK(client_data); |
| 17442 char* gpu_data = reinterpret_cast<char*>(mapped_range->pointer); | 17464 char* gpu_data = reinterpret_cast<char*>(mapped_range->pointer); |
| 17443 DCHECK(gpu_data); | 17465 DCHECK(gpu_data); |
| 17444 memcpy(gpu_data + offset, client_data + offset, size); | 17466 memcpy(gpu_data + offset, client_data + offset, size); |
| 17445 if (buffer->shadowed()) { | 17467 if (buffer->shadowed()) { |
| 17446 buffer->SetRange(mapped_range->offset + offset, size, client_data + offset); | 17468 bool success = buffer->SetRange( |
| 17469 mapped_range->offset + offset, size, client_data + offset); |
| 17470 DCHECK(success); |
| 17447 } | 17471 } |
| 17448 glFlushMappedBufferRange(target, offset, size); | 17472 glFlushMappedBufferRange(target, offset, size); |
| 17449 } | 17473 } |
| 17450 | 17474 |
| 17451 // Note that GL_LOST_CONTEXT is specific to GLES. | 17475 // Note that GL_LOST_CONTEXT is specific to GLES. |
| 17452 // For desktop GL we have to query the reset status proactively. | 17476 // For desktop GL we have to query the reset status proactively. |
| 17453 void GLES2DecoderImpl::OnContextLostError() { | 17477 void GLES2DecoderImpl::OnContextLostError() { |
| 17454 if (!WasContextLost()) { | 17478 if (!WasContextLost()) { |
| 17455 // Need to lose current context before broadcasting! | 17479 // Need to lose current context before broadcasting! |
| 17456 CheckResetStatus(); | 17480 CheckResetStatus(); |
| (...skipping 366 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 17823 num_coords_expected += 5; | 17847 num_coords_expected += 5; |
| 17824 break; | 17848 break; |
| 17825 default: | 17849 default: |
| 17826 LOCAL_SET_GL_ERROR(GL_INVALID_ENUM, kFunctionName, "invalid command"); | 17850 LOCAL_SET_GL_ERROR(GL_INVALID_ENUM, kFunctionName, "invalid command"); |
| 17827 return error::kNoError; | 17851 return error::kNoError; |
| 17828 } | 17852 } |
| 17829 } | 17853 } |
| 17830 } | 17854 } |
| 17831 | 17855 |
| 17832 if (!num_coords_expected.IsValid() || | 17856 if (!num_coords_expected.IsValid() || |
| 17833 num_coords != num_coords_expected.ValueOrDefault(0)) { | 17857 num_coords != num_coords_expected.ValueOrDie()) { |
| 17834 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, kFunctionName, | 17858 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, kFunctionName, |
| 17835 "numCoords does not match commands"); | 17859 "numCoords does not match commands"); |
| 17836 return error::kNoError; | 17860 return error::kNoError; |
| 17837 } | 17861 } |
| 17838 | 17862 |
| 17839 const void* coords = NULL; | 17863 const void* coords = NULL; |
| 17840 | 17864 |
| 17841 if (num_coords > 0) { | 17865 if (num_coords > 0) { |
| 17842 uint32_t coords_size = 0; | 17866 uint32_t coords_size = 0; |
| 17843 uint32_t coord_type_size = | 17867 uint32_t coord_type_size = |
| (...skipping 797 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 18641 } | 18665 } |
| 18642 | 18666 |
| 18643 // Include the auto-generated part of this file. We split this because it means | 18667 // Include the auto-generated part of this file. We split this because it means |
| 18644 // we can easily edit the non-auto generated parts right here in this file | 18668 // we can easily edit the non-auto generated parts right here in this file |
| 18645 // instead of having to edit some template or the code generator. | 18669 // instead of having to edit some template or the code generator. |
| 18646 #include "base/macros.h" | 18670 #include "base/macros.h" |
| 18647 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" | 18671 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" |
| 18648 | 18672 |
| 18649 } // namespace gles2 | 18673 } // namespace gles2 |
| 18650 } // namespace gpu | 18674 } // namespace gpu |
| OLD | NEW |