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 // A class to emulate GLES2 over command buffers. | 5 // A class to emulate GLES2 over command buffers. |
6 | 6 |
7 #include "gpu/command_buffer/client/gles2_implementation.h" | 7 #include "gpu/command_buffer/client/gles2_implementation.h" |
8 | 8 |
9 #include <GLES2/gl2ext.h> | 9 #include <GLES2/gl2ext.h> |
10 #include <GLES2/gl2extchromium.h> | 10 #include <GLES2/gl2extchromium.h> |
11 #include <algorithm> | 11 #include <algorithm> |
12 #include <limits> | 12 #include <limits> |
13 #include <map> | 13 #include <map> |
14 #include <queue> | 14 #include <queue> |
15 #include <set> | 15 #include <set> |
16 #include <sstream> | 16 #include <sstream> |
17 #include <string> | 17 #include <string> |
18 #include "base/bind.h" | 18 #include "base/bind.h" |
19 #include "gpu/command_buffer/client/buffer_tracker.h" | 19 #include "gpu/command_buffer/client/buffer_tracker.h" |
20 #include "gpu/command_buffer/client/gpu_control.h" | 20 #include "gpu/command_buffer/client/gpu_control.h" |
21 #include "gpu/command_buffer/client/program_info_manager.h" | 21 #include "gpu/command_buffer/client/program_info_manager.h" |
22 #include "gpu/command_buffer/client/query_tracker.h" | 22 #include "gpu/command_buffer/client/query_tracker.h" |
23 #include "gpu/command_buffer/client/transfer_buffer.h" | 23 #include "gpu/command_buffer/client/transfer_buffer.h" |
24 #include "gpu/command_buffer/client/vertex_array_object_manager.h" | 24 #include "gpu/command_buffer/client/vertex_array_object_manager.h" |
25 #include "gpu/command_buffer/common/gles2_cmd_utils.h" | 25 #include "gpu/command_buffer/common/gles2_cmd_utils.h" |
26 #include "gpu/command_buffer/common/trace_event.h" | 26 #include "gpu/command_buffer/common/trace_event.h" |
27 | 27 |
28 #if defined(__native_client__) && !defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | |
29 #define GLES2_SUPPORT_CLIENT_SIDE_ARRAYS | |
30 #endif | |
31 | |
32 #if defined(GPU_CLIENT_DEBUG) | 28 #if defined(GPU_CLIENT_DEBUG) |
33 #include "base/command_line.h" | 29 #include "base/command_line.h" |
34 #include "gpu/command_buffer/client/gpu_switches.h" | 30 #include "gpu/command_buffer/client/gpu_switches.h" |
35 #endif | 31 #endif |
36 | 32 |
37 namespace gpu { | 33 namespace gpu { |
38 namespace gles2 { | 34 namespace gles2 { |
39 | 35 |
40 // A 32-bit and 64-bit compatible way of converting a pointer to a GLuint. | 36 // A 32-bit and 64-bit compatible way of converting a pointer to a GLuint. |
41 static GLuint ToGLuint(const void* ptr) { | 37 static GLuint ToGLuint(const void* ptr) { |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
79 --gles2_implementation_->use_count_; | 75 --gles2_implementation_->use_count_; |
80 CHECK_EQ(0, gles2_implementation_->use_count_); | 76 CHECK_EQ(0, gles2_implementation_->use_count_); |
81 } | 77 } |
82 | 78 |
83 GLES2Implementation::GLES2Implementation( | 79 GLES2Implementation::GLES2Implementation( |
84 GLES2CmdHelper* helper, | 80 GLES2CmdHelper* helper, |
85 ShareGroup* share_group, | 81 ShareGroup* share_group, |
86 TransferBufferInterface* transfer_buffer, | 82 TransferBufferInterface* transfer_buffer, |
87 bool bind_generates_resource, | 83 bool bind_generates_resource, |
88 bool lose_context_when_out_of_memory, | 84 bool lose_context_when_out_of_memory, |
| 85 bool support_client_side_arrays, |
89 GpuControl* gpu_control) | 86 GpuControl* gpu_control) |
90 : helper_(helper), | 87 : helper_(helper), |
91 transfer_buffer_(transfer_buffer), | 88 transfer_buffer_(transfer_buffer), |
92 angle_pack_reverse_row_order_status_(kUnknownExtensionStatus), | 89 angle_pack_reverse_row_order_status_(kUnknownExtensionStatus), |
93 chromium_framebuffer_multisample_(kUnknownExtensionStatus), | 90 chromium_framebuffer_multisample_(kUnknownExtensionStatus), |
94 pack_alignment_(4), | 91 pack_alignment_(4), |
95 unpack_alignment_(4), | 92 unpack_alignment_(4), |
96 unpack_flip_y_(false), | 93 unpack_flip_y_(false), |
97 unpack_row_length_(0), | 94 unpack_row_length_(0), |
98 unpack_skip_rows_(0), | 95 unpack_skip_rows_(0), |
99 unpack_skip_pixels_(0), | 96 unpack_skip_pixels_(0), |
100 pack_reverse_row_order_(false), | 97 pack_reverse_row_order_(false), |
101 active_texture_unit_(0), | 98 active_texture_unit_(0), |
102 bound_framebuffer_(0), | 99 bound_framebuffer_(0), |
103 bound_read_framebuffer_(0), | 100 bound_read_framebuffer_(0), |
104 bound_renderbuffer_(0), | 101 bound_renderbuffer_(0), |
105 current_program_(0), | 102 current_program_(0), |
106 bound_array_buffer_id_(0), | 103 bound_array_buffer_id_(0), |
107 bound_pixel_pack_transfer_buffer_id_(0), | 104 bound_pixel_pack_transfer_buffer_id_(0), |
108 bound_pixel_unpack_transfer_buffer_id_(0), | 105 bound_pixel_unpack_transfer_buffer_id_(0), |
109 async_upload_token_(0), | 106 async_upload_token_(0), |
110 async_upload_sync_(NULL), | 107 async_upload_sync_(NULL), |
111 async_upload_sync_shm_id_(0), | 108 async_upload_sync_shm_id_(0), |
112 async_upload_sync_shm_offset_(0), | 109 async_upload_sync_shm_offset_(0), |
113 error_bits_(0), | 110 error_bits_(0), |
114 debug_(false), | 111 debug_(false), |
115 lose_context_when_out_of_memory_(lose_context_when_out_of_memory), | 112 lose_context_when_out_of_memory_(lose_context_when_out_of_memory), |
| 113 support_client_side_arrays_(support_client_side_arrays), |
116 use_count_(0), | 114 use_count_(0), |
117 error_message_callback_(NULL), | 115 error_message_callback_(NULL), |
118 gpu_control_(gpu_control), | 116 gpu_control_(gpu_control), |
119 capabilities_(gpu_control->GetCapabilities()), | 117 capabilities_(gpu_control->GetCapabilities()), |
120 weak_ptr_factory_(this) { | 118 weak_ptr_factory_(this) { |
121 DCHECK(helper); | 119 DCHECK(helper); |
122 DCHECK(transfer_buffer); | 120 DCHECK(transfer_buffer); |
123 DCHECK(gpu_control); | 121 DCHECK(gpu_control); |
124 | 122 |
125 std::stringstream ss; | 123 std::stringstream ss; |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
184 static_state_.int_state.num_shader_binary_formats); | 182 static_state_.int_state.num_shader_binary_formats); |
185 | 183 |
186 texture_units_.reset( | 184 texture_units_.reset( |
187 new TextureUnit[ | 185 new TextureUnit[ |
188 static_state_.int_state.max_combined_texture_image_units]); | 186 static_state_.int_state.max_combined_texture_image_units]); |
189 | 187 |
190 query_tracker_.reset(new QueryTracker(mapped_memory_.get())); | 188 query_tracker_.reset(new QueryTracker(mapped_memory_.get())); |
191 buffer_tracker_.reset(new BufferTracker(mapped_memory_.get())); | 189 buffer_tracker_.reset(new BufferTracker(mapped_memory_.get())); |
192 | 190 |
193 query_id_allocator_.reset(new IdAllocator()); | 191 query_id_allocator_.reset(new IdAllocator()); |
194 #if defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | 192 if (support_client_side_arrays_) { |
195 GetIdHandler(id_namespaces::kBuffers)->MakeIds( | 193 GetIdHandler(id_namespaces::kBuffers)->MakeIds( |
196 this, kClientSideArrayId, arraysize(reserved_ids_), &reserved_ids_[0]); | 194 this, kClientSideArrayId, arraysize(reserved_ids_), &reserved_ids_[0]); |
197 #endif | 195 } |
198 | 196 |
199 vertex_array_object_manager_.reset(new VertexArrayObjectManager( | 197 vertex_array_object_manager_.reset(new VertexArrayObjectManager( |
200 static_state_.int_state.max_vertex_attribs, | 198 static_state_.int_state.max_vertex_attribs, |
201 reserved_ids_[0], | 199 reserved_ids_[0], |
202 reserved_ids_[1])); | 200 reserved_ids_[1], |
| 201 support_client_side_arrays_)); |
203 | 202 |
204 // GL_BIND_GENERATES_RESOURCE_CHROMIUM state must be the same | 203 // GL_BIND_GENERATES_RESOURCE_CHROMIUM state must be the same |
205 // on Client & Service. | 204 // on Client & Service. |
206 if (static_state_.int_state.bind_generates_resource_chromium != | 205 if (static_state_.int_state.bind_generates_resource_chromium != |
207 (share_group_->bind_generates_resource() ? 1 : 0)) { | 206 (share_group_->bind_generates_resource() ? 1 : 0)) { |
208 SetGLError(GL_INVALID_OPERATION, | 207 SetGLError(GL_INVALID_OPERATION, |
209 "Initialize", | 208 "Initialize", |
210 "Service bind_generates_resource mismatch."); | 209 "Service bind_generates_resource mismatch."); |
211 return false; | 210 return false; |
212 } | 211 } |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
289 } | 288 } |
290 | 289 |
291 GLES2Implementation::~GLES2Implementation() { | 290 GLES2Implementation::~GLES2Implementation() { |
292 // Make sure the queries are finished otherwise we'll delete the | 291 // Make sure the queries are finished otherwise we'll delete the |
293 // shared memory (mapped_memory_) which will free the memory used | 292 // shared memory (mapped_memory_) which will free the memory used |
294 // by the queries. The GPU process when validating that memory is still | 293 // by the queries. The GPU process when validating that memory is still |
295 // shared will fail and abort (ie, it will stop running). | 294 // shared will fail and abort (ie, it will stop running). |
296 WaitForCmd(); | 295 WaitForCmd(); |
297 query_tracker_.reset(); | 296 query_tracker_.reset(); |
298 | 297 |
299 #if defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | 298 if (support_client_side_arrays_) |
300 DeleteBuffers(arraysize(reserved_ids_), &reserved_ids_[0]); | 299 DeleteBuffers(arraysize(reserved_ids_), &reserved_ids_[0]); |
301 #endif | |
302 | 300 |
303 // Release any per-context data in share group. | 301 // Release any per-context data in share group. |
304 share_group_->FreeContext(this); | 302 share_group_->FreeContext(this); |
305 | 303 |
306 buffer_tracker_.reset(); | 304 buffer_tracker_.reset(); |
307 | 305 |
308 FreeAllAsyncUploadBuffers(); | 306 FreeAllAsyncUploadBuffers(); |
309 | 307 |
310 if (async_upload_sync_) { | 308 if (async_upload_sync_) { |
311 mapped_memory_->Free(async_upload_sync_); | 309 mapped_memory_->Free(async_upload_sync_); |
(...skipping 894 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1206 << GLES2Util::GetStringBool(normalized) << ", " | 1204 << GLES2Util::GetStringBool(normalized) << ", " |
1207 << stride << ", " | 1205 << stride << ", " |
1208 << static_cast<const void*>(ptr) << ")"); | 1206 << static_cast<const void*>(ptr) << ")"); |
1209 // Record the info on the client side. | 1207 // Record the info on the client side. |
1210 if (!vertex_array_object_manager_->SetAttribPointer( | 1208 if (!vertex_array_object_manager_->SetAttribPointer( |
1211 bound_array_buffer_id_, index, size, type, normalized, stride, ptr)) { | 1209 bound_array_buffer_id_, index, size, type, normalized, stride, ptr)) { |
1212 SetGLError(GL_INVALID_OPERATION, "glVertexAttribPointer", | 1210 SetGLError(GL_INVALID_OPERATION, "glVertexAttribPointer", |
1213 "client side arrays are not allowed in vertex array objects."); | 1211 "client side arrays are not allowed in vertex array objects."); |
1214 return; | 1212 return; |
1215 } | 1213 } |
1216 #if defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | 1214 if (!support_client_side_arrays_ || bound_array_buffer_id_ != 0) { |
1217 if (bound_array_buffer_id_ != 0) { | |
1218 // Only report NON client side buffers to the service. | 1215 // Only report NON client side buffers to the service. |
1219 if (!ValidateOffset("glVertexAttribPointer", | 1216 if (!ValidateOffset("glVertexAttribPointer", |
1220 reinterpret_cast<GLintptr>(ptr))) { | 1217 reinterpret_cast<GLintptr>(ptr))) { |
1221 return; | 1218 return; |
1222 } | 1219 } |
1223 helper_->VertexAttribPointer(index, size, type, normalized, stride, | 1220 helper_->VertexAttribPointer(index, size, type, normalized, stride, |
1224 ToGLuint(ptr)); | 1221 ToGLuint(ptr)); |
1225 } | 1222 } |
1226 #else // !defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | |
1227 if (!ValidateOffset("glVertexAttribPointer", | |
1228 reinterpret_cast<GLintptr>(ptr))) { | |
1229 return; | |
1230 } | |
1231 helper_->VertexAttribPointer(index, size, type, normalized, stride, | |
1232 ToGLuint(ptr)); | |
1233 #endif // !defined(GLES2_SUPPORT_CLIENT_SIDE_ARRAYS) | |
1234 CheckGLError(); | 1223 CheckGLError(); |
1235 } | 1224 } |
1236 | 1225 |
1237 void GLES2Implementation::VertexAttribDivisorANGLE( | 1226 void GLES2Implementation::VertexAttribDivisorANGLE( |
1238 GLuint index, GLuint divisor) { | 1227 GLuint index, GLuint divisor) { |
1239 GPU_CLIENT_SINGLE_THREAD_CHECK(); | 1228 GPU_CLIENT_SINGLE_THREAD_CHECK(); |
1240 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glVertexAttribDivisorANGLE(" | 1229 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glVertexAttribDivisorANGLE(" |
1241 << index << ", " | 1230 << index << ", " |
1242 << divisor << ") "); | 1231 << divisor << ") "); |
1243 // Record the info on the client side. | 1232 // Record the info on the client side. |
(...skipping 2702 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3946 if (height <= 0) { | 3935 if (height <= 0) { |
3947 SetGLError(GL_INVALID_VALUE, "glCreateImageCHROMIUM", "height <= 0"); | 3936 SetGLError(GL_INVALID_VALUE, "glCreateImageCHROMIUM", "height <= 0"); |
3948 return 0; | 3937 return 0; |
3949 } | 3938 } |
3950 | 3939 |
3951 if (!ValidImageFormat(internalformat)) { | 3940 if (!ValidImageFormat(internalformat)) { |
3952 SetGLError(GL_INVALID_VALUE, "glCreateImageCHROMIUM", "invalid format"); | 3941 SetGLError(GL_INVALID_VALUE, "glCreateImageCHROMIUM", "invalid format"); |
3953 return 0; | 3942 return 0; |
3954 } | 3943 } |
3955 | 3944 |
3956 // Flush the command stream to ensure ordering in case the newly | |
3957 // returned image_id has recently been in use with a different buffer. | |
3958 helper_->CommandBufferHelper::Flush(); | |
3959 int32_t image_id = | 3945 int32_t image_id = |
3960 gpu_control_->CreateImage(buffer, width, height, internalformat); | 3946 gpu_control_->CreateImage(buffer, width, height, internalformat); |
3961 if (image_id < 0) { | 3947 if (image_id < 0) { |
3962 SetGLError(GL_OUT_OF_MEMORY, "glCreateImageCHROMIUM", "image_id < 0"); | 3948 SetGLError(GL_OUT_OF_MEMORY, "glCreateImageCHROMIUM", "image_id < 0"); |
3963 return 0; | 3949 return 0; |
3964 } | 3950 } |
3965 return image_id; | 3951 return image_id; |
3966 } | 3952 } |
3967 | 3953 |
3968 GLuint GLES2Implementation::CreateImageCHROMIUM(ClientBuffer buffer, | 3954 GLuint GLES2Implementation::CreateImageCHROMIUM(ClientBuffer buffer, |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4082 return true; | 4068 return true; |
4083 } | 4069 } |
4084 | 4070 |
4085 // Include the auto-generated part of this file. We split this because it means | 4071 // Include the auto-generated part of this file. We split this because it means |
4086 // we can easily edit the non-auto generated parts right here in this file | 4072 // we can easily edit the non-auto generated parts right here in this file |
4087 // instead of having to edit some template or the code generator. | 4073 // instead of having to edit some template or the code generator. |
4088 #include "gpu/command_buffer/client/gles2_implementation_impl_autogen.h" | 4074 #include "gpu/command_buffer/client/gles2_implementation_impl_autogen.h" |
4089 | 4075 |
4090 } // namespace gles2 | 4076 } // namespace gles2 |
4091 } // namespace gpu | 4077 } // namespace gpu |
OLD | NEW |