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 <algorithm> | 9 #include <algorithm> |
10 #include <map> | 10 #include <map> |
(...skipping 1361 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1372 } | 1372 } |
1373 | 1373 |
1374 GLuint buffer_id; | 1374 GLuint buffer_id; |
1375 if (GetBoundPixelTransferBuffer(target, "glBufferData", &buffer_id)) { | 1375 if (GetBoundPixelTransferBuffer(target, "glBufferData", &buffer_id)) { |
1376 if (!buffer_id) { | 1376 if (!buffer_id) { |
1377 return; | 1377 return; |
1378 } | 1378 } |
1379 | 1379 |
1380 BufferTracker::Buffer* buffer = buffer_tracker_->GetBuffer(buffer_id); | 1380 BufferTracker::Buffer* buffer = buffer_tracker_->GetBuffer(buffer_id); |
1381 if (buffer) { | 1381 if (buffer) { |
1382 // Free buffer memory, pending the passage of a token. | 1382 if (buffer->used()) { |
1383 buffer_tracker_->FreePendingToken(buffer, helper_->InsertToken()); | 1383 buffer->set_used(false); |
1384 buffer->set_unused_token(helper_->InsertToken()); | |
1385 } | |
1386 DisposeTransferBuffer(buffer); | |
1387 } | |
1384 | 1388 |
1385 // Remove old buffer. | 1389 CheckBuffersPendingAsyncComplete(); |
1386 buffer_tracker_->RemoveBuffer(buffer_id); | |
1387 } | |
1388 | 1390 |
1389 // Create new buffer. | 1391 // Create new buffer. |
1390 buffer = buffer_tracker_->CreateBuffer(buffer_id, size); | 1392 buffer = buffer_tracker_->CreateBuffer(buffer_id, size); |
1391 DCHECK(buffer); | 1393 DCHECK(buffer); |
1394 buffer->set_used(true); | |
1392 if (buffer->address() && data) | 1395 if (buffer->address() && data) |
1393 memcpy(buffer->address(), data, size); | 1396 memcpy(buffer->address(), data, size); |
1394 return; | 1397 return; |
1395 } | 1398 } |
1396 | 1399 |
1397 if (size == 0) { | 1400 if (size == 0) { |
1398 return; | 1401 return; |
1399 } | 1402 } |
1400 | 1403 |
1401 // If there is no data just send BufferData | 1404 // If there is no data just send BufferData |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1505 GLenum target, GLintptr offset, GLsizeiptr size, const void* data) { | 1508 GLenum target, GLintptr offset, GLsizeiptr size, const void* data) { |
1506 GPU_CLIENT_SINGLE_THREAD_CHECK(); | 1509 GPU_CLIENT_SINGLE_THREAD_CHECK(); |
1507 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glBufferSubData(" | 1510 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glBufferSubData(" |
1508 << GLES2Util::GetStringBufferTarget(target) << ", " | 1511 << GLES2Util::GetStringBufferTarget(target) << ", " |
1509 << offset << ", " << size << ", " | 1512 << offset << ", " << size << ", " |
1510 << static_cast<const void*>(data) << ")"); | 1513 << static_cast<const void*>(data) << ")"); |
1511 BufferSubDataHelper(target, offset, size, data); | 1514 BufferSubDataHelper(target, offset, size, data); |
1512 CheckGLError(); | 1515 CheckGLError(); |
1513 } | 1516 } |
1514 | 1517 |
1518 void GLES2Implementation::FreeTransferBuffer(BufferTracker::Buffer *buffer) { | |
1519 int32 token = buffer->unused_token(); | |
1520 // FIXME: This kind of checks exist elsewhere; is it correct? | |
1521 if (token) { | |
1522 if (helper_->HasTokenPassed(token)) | |
piman
2014/01/08 05:08:04
Maybe this logic (if the token is passed, free imm
| |
1523 buffer_tracker_->Free(buffer); | |
1524 else | |
1525 buffer_tracker_->FreePendingToken(buffer, token); | |
1526 } | |
1527 } | |
1528 | |
1529 void GLES2Implementation::DisposeTransferBuffer(BufferTracker::Buffer* buffer) { | |
1530 if (buffer->async_query_id()) { | |
1531 QueryTracker::Query* query = | |
1532 query_tracker_->GetQuery(buffer->async_query_id()); | |
1533 if (!query->CheckResultsAvailable(helper_)) { | |
1534 // Async upload not completed, queue release. | |
1535 released_buffers_pending_async_complete_.push_back(buffer); | |
1536 buffer_tracker_->UnmanageBuffer(buffer->id()); | |
1537 return; | |
1538 } | |
1539 } | |
1540 | |
1541 FreeTransferBuffer(buffer); | |
1542 buffer_tracker_->RemoveBuffer(buffer->id()); | |
1543 } | |
1544 | |
1545 void GLES2Implementation::CheckBuffersPendingAsyncComplete() { | |
epennerAtGoogle
2014/01/07 00:47:59
Hmm, it's unfortunate that we have to check all of
reveman
2014/01/07 06:32:06
you could just keep the list sorted based on query
jadahl
2014/01/07 10:52:03
The enumeration will improve this situation indeed
| |
1546 BufferList::iterator it = released_buffers_pending_async_complete_.begin(); | |
1547 while (it != released_buffers_pending_async_complete_.end()) { | |
1548 BufferTracker::Buffer* buffer = *it; | |
1549 QueryTracker::Query* query = | |
1550 query_tracker_->GetQuery(buffer->async_query_id()); | |
1551 if (query->CheckResultsAvailable(helper_)) { | |
1552 it = released_buffers_pending_async_complete_.erase(it); | |
1553 FreeTransferBuffer(buffer); | |
1554 delete buffer; | |
1555 } else { | |
1556 ++it; | |
1557 } | |
1558 } | |
1559 } | |
1560 | |
1515 bool GLES2Implementation::GetBoundPixelTransferBuffer( | 1561 bool GLES2Implementation::GetBoundPixelTransferBuffer( |
1516 GLenum target, | 1562 GLenum target, |
1517 const char* function_name, | 1563 const char* function_name, |
1518 GLuint* buffer_id) { | 1564 GLuint* buffer_id) { |
1519 *buffer_id = 0; | 1565 *buffer_id = 0; |
1520 | 1566 |
1521 switch (target) { | 1567 switch (target) { |
1522 case GL_PIXEL_PACK_TRANSFER_BUFFER_CHROMIUM: | 1568 case GL_PIXEL_PACK_TRANSFER_BUFFER_CHROMIUM: |
1523 *buffer_id = bound_pixel_pack_transfer_buffer_id_; | 1569 *buffer_id = bound_pixel_pack_transfer_buffer_id_; |
1524 break; | 1570 break; |
(...skipping 872 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2397 } | 2443 } |
2398 | 2444 |
2399 // NOTE #1: On old versions of OpenGL, calling glBindXXX with an unused id | 2445 // NOTE #1: On old versions of OpenGL, calling glBindXXX with an unused id |
2400 // generates a new resource. On newer versions of OpenGL they don't. The code | 2446 // generates a new resource. On newer versions of OpenGL they don't. The code |
2401 // related to binding below will need to change if we switch to the new OpenGL | 2447 // related to binding below will need to change if we switch to the new OpenGL |
2402 // model. Specifically it assumes a bind will succeed which is always true in | 2448 // model. Specifically it assumes a bind will succeed which is always true in |
2403 // the old model but possibly not true in the new model if another context has | 2449 // the old model but possibly not true in the new model if another context has |
2404 // deleted the resource. | 2450 // deleted the resource. |
2405 | 2451 |
2406 bool GLES2Implementation::BindBufferHelper( | 2452 bool GLES2Implementation::BindBufferHelper( |
2407 GLenum target, GLuint buffer) { | 2453 GLenum target, GLuint buffer_id) { |
2454 BufferTracker::Buffer* buffer; | |
2455 | |
2408 // TODO(gman): See note #1 above. | 2456 // TODO(gman): See note #1 above. |
2409 bool changed = false; | 2457 bool changed = false; |
2410 switch (target) { | 2458 switch (target) { |
2411 case GL_ARRAY_BUFFER: | 2459 case GL_ARRAY_BUFFER: |
2412 if (bound_array_buffer_id_ != buffer) { | 2460 if (bound_array_buffer_id_ != buffer_id) { |
2413 bound_array_buffer_id_ = buffer; | 2461 bound_array_buffer_id_ = buffer_id; |
2414 changed = true; | 2462 changed = true; |
2415 } | 2463 } |
2416 break; | 2464 break; |
2417 case GL_ELEMENT_ARRAY_BUFFER: | 2465 case GL_ELEMENT_ARRAY_BUFFER: |
2418 changed = vertex_array_object_manager_->BindElementArray(buffer); | 2466 changed = vertex_array_object_manager_->BindElementArray(buffer_id); |
2419 break; | 2467 break; |
2420 case GL_PIXEL_PACK_TRANSFER_BUFFER_CHROMIUM: | 2468 case GL_PIXEL_PACK_TRANSFER_BUFFER_CHROMIUM: |
2421 bound_pixel_pack_transfer_buffer_id_ = buffer; | 2469 bound_pixel_pack_transfer_buffer_id_ = buffer_id; |
2422 break; | 2470 break; |
2423 case GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM: | 2471 case GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM: |
2424 bound_pixel_unpack_transfer_buffer_id_ = buffer; | 2472 // Mark any previously bound buffer as unused. |
2473 if (bound_pixel_unpack_transfer_buffer_id_ != buffer_id && | |
2474 bound_pixel_unpack_transfer_buffer_id_ != 0) { | |
2475 buffer = | |
2476 buffer_tracker_->GetBuffer(bound_pixel_unpack_transfer_buffer_id_); | |
2477 if (buffer) { | |
2478 buffer->set_unused_token(helper_->InsertToken()); | |
2479 } | |
2480 } | |
2481 | |
2482 bound_pixel_unpack_transfer_buffer_id_ = buffer_id; | |
2483 buffer = buffer_tracker_->GetBuffer(buffer_id); | |
2484 if (buffer) { | |
2485 buffer->set_used(true); | |
2486 buffer->set_unused_token(0); | |
2487 } | |
2488 | |
2425 break; | 2489 break; |
2426 default: | 2490 default: |
2427 changed = true; | 2491 changed = true; |
2428 break; | 2492 break; |
2429 } | 2493 } |
2430 // TODO(gman): There's a bug here. If the target is invalid the ID will not be | 2494 // TODO(gman): There's a bug here. If the target is invalid the ID will not be |
2431 // used even though it's marked it as used here. | 2495 // used even though it's marked it as used here. |
2432 GetIdHandler(id_namespaces::kBuffers)->MarkAsUsedForBind(buffer); | 2496 GetIdHandler(id_namespaces::kBuffers)->MarkAsUsedForBind(buffer_id); |
2433 return changed; | 2497 return changed; |
2434 } | 2498 } |
2435 | 2499 |
2436 bool GLES2Implementation::BindFramebufferHelper( | 2500 bool GLES2Implementation::BindFramebufferHelper( |
2437 GLenum target, GLuint framebuffer) { | 2501 GLenum target, GLuint framebuffer) { |
2438 // TODO(gman): See note #1 above. | 2502 // TODO(gman): See note #1 above. |
2439 bool changed = false; | 2503 bool changed = false; |
2440 switch (target) { | 2504 switch (target) { |
2441 case GL_FRAMEBUFFER: | 2505 case GL_FRAMEBUFFER: |
2442 if (bound_framebuffer_ != framebuffer || | 2506 if (bound_framebuffer_ != framebuffer || |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2556 SetGLError( | 2620 SetGLError( |
2557 GL_INVALID_VALUE, | 2621 GL_INVALID_VALUE, |
2558 "glDeleteBuffers", "id not created by this context."); | 2622 "glDeleteBuffers", "id not created by this context."); |
2559 return; | 2623 return; |
2560 } | 2624 } |
2561 for (GLsizei ii = 0; ii < n; ++ii) { | 2625 for (GLsizei ii = 0; ii < n; ++ii) { |
2562 if (buffers[ii] == bound_array_buffer_id_) { | 2626 if (buffers[ii] == bound_array_buffer_id_) { |
2563 bound_array_buffer_id_ = 0; | 2627 bound_array_buffer_id_ = 0; |
2564 } | 2628 } |
2565 vertex_array_object_manager_->UnbindBuffer(buffers[ii]); | 2629 vertex_array_object_manager_->UnbindBuffer(buffers[ii]); |
2630 | |
2566 BufferTracker::Buffer* buffer = buffer_tracker_->GetBuffer(buffers[ii]); | 2631 BufferTracker::Buffer* buffer = buffer_tracker_->GetBuffer(buffers[ii]); |
2567 if (buffer) { | 2632 if (buffer) { |
2568 // Free buffer memory, pending the passage of a token. | 2633 buffer->set_used(false); |
2569 buffer_tracker_->FreePendingToken(buffer, helper_->InsertToken()); | 2634 buffer->set_unused_token(helper_->InsertToken()); |
2570 // Remove buffer. | 2635 DisposeTransferBuffer(buffer); |
2571 buffer_tracker_->RemoveBuffer(buffers[ii]); | |
2572 } | 2636 } |
2637 | |
2573 if (buffers[ii] == bound_pixel_unpack_transfer_buffer_id_) { | 2638 if (buffers[ii] == bound_pixel_unpack_transfer_buffer_id_) { |
2574 bound_pixel_unpack_transfer_buffer_id_ = 0; | 2639 bound_pixel_unpack_transfer_buffer_id_ = 0; |
2575 } | 2640 } |
2576 } | 2641 } |
2577 } | 2642 } |
2578 | 2643 |
2579 void GLES2Implementation::DeleteBuffersStub( | 2644 void GLES2Implementation::DeleteBuffersStub( |
2580 GLsizei n, const GLuint* buffers) { | 2645 GLsizei n, const GLuint* buffers) { |
2581 helper_->DeleteBuffersImmediate(n, buffers); | 2646 helper_->DeleteBuffersImmediate(n, buffers); |
2582 } | 2647 } |
(...skipping 1055 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3638 } | 3703 } |
3639 if (!buffer->mapped()) { | 3704 if (!buffer->mapped()) { |
3640 SetGLError(GL_INVALID_OPERATION, "glUnmapBufferCHROMIUM", "not mapped"); | 3705 SetGLError(GL_INVALID_OPERATION, "glUnmapBufferCHROMIUM", "not mapped"); |
3641 return false; | 3706 return false; |
3642 } | 3707 } |
3643 buffer->set_mapped(false); | 3708 buffer->set_mapped(false); |
3644 CheckGLError(); | 3709 CheckGLError(); |
3645 return true; | 3710 return true; |
3646 } | 3711 } |
3647 | 3712 |
3713 void GLES2Implementation::BeginQueryAsyncPixelUnpackCompleted( | |
3714 BufferTracker::Buffer *buffer) { | |
3715 DCHECK(!current_private_unpack_query_); | |
3716 | |
3717 GLuint id; | |
3718 GetIdHandler(id_namespaces::kQueries)->MakeIds(this, 0, 1, &id); | |
3719 QueryTracker::Query* query = | |
3720 query_tracker_->CreateQuery( | |
3721 id, GL_ASYNC_PIXEL_UNPACK_COMPLETED_PRIVATE_CHROMIUM); | |
3722 if (!query) { | |
3723 MustBeContextLost(); | |
3724 return; | |
3725 } | |
3726 | |
3727 buffer->set_async_query_id(id); | |
3728 query->Begin(this); | |
3729 CheckGLError(); | |
3730 | |
3731 current_private_unpack_query_ = query; | |
3732 } | |
3733 | |
3734 void GLES2Implementation::EndQueryAsyncPixelUnpackCompleted() { | |
3735 DCHECK(current_private_unpack_query_); | |
3736 | |
3737 current_private_unpack_query_->End(this); | |
3738 current_private_unpack_query_ = NULL; | |
3739 CheckGLError(); | |
3740 } | |
3741 | |
3648 void GLES2Implementation::AsyncTexImage2DCHROMIUM( | 3742 void GLES2Implementation::AsyncTexImage2DCHROMIUM( |
3649 GLenum target, GLint level, GLint internalformat, GLsizei width, | 3743 GLenum target, GLint level, GLint internalformat, GLsizei width, |
3650 GLsizei height, GLint border, GLenum format, GLenum type, | 3744 GLsizei height, GLint border, GLenum format, GLenum type, |
3651 const void* pixels) { | 3745 const void* pixels) { |
3652 GPU_CLIENT_SINGLE_THREAD_CHECK(); | 3746 GPU_CLIENT_SINGLE_THREAD_CHECK(); |
3653 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glTexImage2D(" | 3747 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glTexImage2D(" |
3654 << GLES2Util::GetStringTextureTarget(target) << ", " | 3748 << GLES2Util::GetStringTextureTarget(target) << ", " |
3655 << level << ", " | 3749 << level << ", " |
3656 << GLES2Util::GetStringTextureInternalFormat(internalformat) << ", " | 3750 << GLES2Util::GetStringTextureInternalFormat(internalformat) << ", " |
3657 << width << ", " << height << ", " << border << ", " | 3751 << width << ", " << height << ", " << border << ", " |
(...skipping 24 matching lines...) Expand all Loading... | |
3682 | 3776 |
3683 // Otherwise, async uploads require a transfer buffer to be bound. | 3777 // Otherwise, async uploads require a transfer buffer to be bound. |
3684 // TODO(hubbe): Make MapBufferCHROMIUM block if someone tries to re-use | 3778 // TODO(hubbe): Make MapBufferCHROMIUM block if someone tries to re-use |
3685 // the buffer before the transfer is finished. (Currently such | 3779 // the buffer before the transfer is finished. (Currently such |
3686 // synchronization has to be handled manually.) | 3780 // synchronization has to be handled manually.) |
3687 GLuint offset = ToGLuint(pixels); | 3781 GLuint offset = ToGLuint(pixels); |
3688 BufferTracker::Buffer* buffer = GetBoundPixelUnpackTransferBufferIfValid( | 3782 BufferTracker::Buffer* buffer = GetBoundPixelUnpackTransferBufferIfValid( |
3689 bound_pixel_unpack_transfer_buffer_id_, | 3783 bound_pixel_unpack_transfer_buffer_id_, |
3690 "glAsyncTexImage2DCHROMIUM", offset, size); | 3784 "glAsyncTexImage2DCHROMIUM", offset, size); |
3691 if (buffer && buffer->shm_id() != -1) { | 3785 if (buffer && buffer->shm_id() != -1) { |
3786 BeginQueryAsyncPixelUnpackCompleted(buffer); | |
3692 helper_->AsyncTexImage2DCHROMIUM( | 3787 helper_->AsyncTexImage2DCHROMIUM( |
3693 target, level, internalformat, width, height, border, format, type, | 3788 target, level, internalformat, width, height, border, format, type, |
3694 buffer->shm_id(), buffer->shm_offset() + offset); | 3789 buffer->shm_id(), buffer->shm_offset() + offset); |
3790 EndQueryAsyncPixelUnpackCompleted(); | |
3695 } | 3791 } |
3696 } | 3792 } |
3697 | 3793 |
3698 void GLES2Implementation::AsyncTexSubImage2DCHROMIUM( | 3794 void GLES2Implementation::AsyncTexSubImage2DCHROMIUM( |
3699 GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, | 3795 GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, |
3700 GLsizei height, GLenum format, GLenum type, const void* pixels) { | 3796 GLsizei height, GLenum format, GLenum type, const void* pixels) { |
3701 GPU_CLIENT_SINGLE_THREAD_CHECK(); | 3797 GPU_CLIENT_SINGLE_THREAD_CHECK(); |
3702 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glAsyncTexSubImage2DCHROMIUM(" | 3798 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glAsyncTexSubImage2DCHROMIUM(" |
3703 << GLES2Util::GetStringTextureTarget(target) << ", " | 3799 << GLES2Util::GetStringTextureTarget(target) << ", " |
3704 << level << ", " | 3800 << level << ", " |
(...skipping 21 matching lines...) Expand all Loading... | |
3726 | 3822 |
3727 // Async uploads require a transfer buffer to be bound. | 3823 // Async uploads require a transfer buffer to be bound. |
3728 // TODO(hubbe): Make MapBufferCHROMIUM block if someone tries to re-use | 3824 // TODO(hubbe): Make MapBufferCHROMIUM block if someone tries to re-use |
3729 // the buffer before the transfer is finished. (Currently such | 3825 // the buffer before the transfer is finished. (Currently such |
3730 // synchronization has to be handled manually.) | 3826 // synchronization has to be handled manually.) |
3731 GLuint offset = ToGLuint(pixels); | 3827 GLuint offset = ToGLuint(pixels); |
3732 BufferTracker::Buffer* buffer = GetBoundPixelUnpackTransferBufferIfValid( | 3828 BufferTracker::Buffer* buffer = GetBoundPixelUnpackTransferBufferIfValid( |
3733 bound_pixel_unpack_transfer_buffer_id_, | 3829 bound_pixel_unpack_transfer_buffer_id_, |
3734 "glAsyncTexSubImage2DCHROMIUM", offset, size); | 3830 "glAsyncTexSubImage2DCHROMIUM", offset, size); |
3735 if (buffer && buffer->shm_id() != -1) { | 3831 if (buffer && buffer->shm_id() != -1) { |
3832 BeginQueryAsyncPixelUnpackCompleted(buffer); | |
3736 helper_->AsyncTexSubImage2DCHROMIUM( | 3833 helper_->AsyncTexSubImage2DCHROMIUM( |
3737 target, level, xoffset, yoffset, width, height, format, type, | 3834 target, level, xoffset, yoffset, width, height, format, type, |
3738 buffer->shm_id(), buffer->shm_offset() + offset); | 3835 buffer->shm_id(), buffer->shm_offset() + offset); |
3836 EndQueryAsyncPixelUnpackCompleted(); | |
3739 } | 3837 } |
3740 } | 3838 } |
3741 | 3839 |
3742 void GLES2Implementation::WaitAsyncTexImage2DCHROMIUM(GLenum target) { | 3840 void GLES2Implementation::WaitAsyncTexImage2DCHROMIUM(GLenum target) { |
3743 GPU_CLIENT_SINGLE_THREAD_CHECK(); | 3841 GPU_CLIENT_SINGLE_THREAD_CHECK(); |
3744 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glWaitAsyncTexImage2DCHROMIUM(" | 3842 GPU_CLIENT_LOG("[" << GetLogPrefix() << "] glWaitAsyncTexImage2DCHROMIUM(" |
3745 << GLES2Util::GetStringTextureTarget(target) << ")"); | 3843 << GLES2Util::GetStringTextureTarget(target) << ")"); |
3746 helper_->WaitAsyncTexImage2DCHROMIUM(target); | 3844 helper_->WaitAsyncTexImage2DCHROMIUM(target); |
3747 CheckGLError(); | 3845 CheckGLError(); |
3748 } | 3846 } |
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3915 CheckGLError(); | 4013 CheckGLError(); |
3916 } | 4014 } |
3917 | 4015 |
3918 // Include the auto-generated part of this file. We split this because it means | 4016 // Include the auto-generated part of this file. We split this because it means |
3919 // we can easily edit the non-auto generated parts right here in this file | 4017 // we can easily edit the non-auto generated parts right here in this file |
3920 // instead of having to edit some template or the code generator. | 4018 // instead of having to edit some template or the code generator. |
3921 #include "gpu/command_buffer/client/gles2_implementation_impl_autogen.h" | 4019 #include "gpu/command_buffer/client/gles2_implementation_impl_autogen.h" |
3922 | 4020 |
3923 } // namespace gles2 | 4021 } // namespace gles2 |
3924 } // namespace gpu | 4022 } // namespace gpu |
OLD | NEW |