diff options
author | gman@chromium.org <gman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-07-14 01:43:00 +0000 |
---|---|---|
committer | gman@chromium.org <gman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-07-14 01:43:00 +0000 |
commit | 8cd62f61b53e532b829b986326755404bbcaf6ad (patch) | |
tree | 4337cfb576348ecca0bb1398741189e602f43ad8 /gpu/command_buffer/client/gles2_implementation.cc | |
parent | fc0d0378566936f09ead042d19b8031aebea0984 (diff) | |
download | chromium_src-8cd62f61b53e532b829b986326755404bbcaf6ad.zip chromium_src-8cd62f61b53e532b829b986326755404bbcaf6ad.tar.gz chromium_src-8cd62f61b53e532b829b986326755404bbcaf6ad.tar.bz2 |
Adds MapBufferSubData and MapTexSubImage2D.
This is only the internal command buffer implementation.
Connecting these functions publicly to PPAPI or whatever
will happen separate from this CL.
It's not clear to me where to put GL_READ_ONLY and GL_WRITE_ONLY
Probably the same place we expose these 2 functions to the public.
TEST=unit test
BUG=none
Review URL: http://codereview.chromium.org/2956005
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@52263 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'gpu/command_buffer/client/gles2_implementation.cc')
-rw-r--r-- | gpu/command_buffer/client/gles2_implementation.cc | 102 |
1 files changed, 102 insertions, 0 deletions
diff --git a/gpu/command_buffer/client/gles2_implementation.cc b/gpu/command_buffer/client/gles2_implementation.cc index fd72ed2..52afc74 100644 --- a/gpu/command_buffer/client/gles2_implementation.cc +++ b/gpu/command_buffer/client/gles2_implementation.cc @@ -5,6 +5,8 @@ // A class to emluate GLES2 over command buffers. #include "../client/gles2_implementation.h" +#include <GLES2/gles2_command_buffer.h> +#include "../client/mapped_memory.h" #include "../common/gles2_cmd_utils.h" #include "../common/id_allocator.h" @@ -420,6 +422,8 @@ GLES2Implementation::GLES2Implementation( result_buffer_ = transfer_buffer; result_shm_offset_ = 0; + mapped_memory_.reset(new MappedMemoryManager(helper_)); + if (share_resources) { buffer_id_handler_.reset( new SharedIdHandler(this, id_namespaces::kBuffers)); @@ -1462,5 +1466,103 @@ GLboolean GLES2Implementation::CommandBufferEnable(const char* feature) { #endif // defined(GLES2_SUPPORT_CLIENT_SIDE_BUFFERS) +void* GLES2Implementation::MapBufferSubData( + GLuint target, GLintptr offset, GLsizeiptr size, GLenum access) { + // NOTE: target is NOT checked because the service will check it + // and we don't know what targets are valid. + if (access != GL_WRITE_ONLY) { + SetGLError(GL_INVALID_ENUM, "MapBufferSubData: bad access mode"); + return NULL; + } + if (offset < 0 || size < 0) { + SetGLError(GL_INVALID_VALUE, "MapBufferSubData: bad range"); + return NULL; + } + int32 shm_id; + unsigned int shm_offset; + void* mem = mapped_memory_->Alloc(size, &shm_id, &shm_offset); + if (!mem) { + SetGLError(GL_OUT_OF_MEMORY, "MapBufferSubData: out of memory"); + return NULL; + } + + std::pair<MappedBufferMap::iterator, bool> result = + mapped_buffers_.insert(std::make_pair( + mem, + MappedBuffer( + access, shm_id, mem, shm_offset, target, offset, size))); + return mem; +} + +void GLES2Implementation::UnmapBufferSubData(const void* mem) { + MappedBufferMap::iterator it = mapped_buffers_.find(mem); + if (it == mapped_buffers_.end()) { + SetGLError(GL_INVALID_VALUE, "UnmapBufferSubData: buffer not mapped"); + return; + } + const MappedBuffer& mb = it->second; + helper_->BufferSubData( + mb.target, mb.offset, mb.size, mb.shm_id, mb.shm_offset); + mapped_memory_->FreePendingToken(mb.shm_memory, helper_->InsertToken()); + mapped_buffers_.erase(it); +} + +void* GLES2Implementation::MapTexSubImage2D( + GLenum target, + GLint level, + GLint xoffset, + GLint yoffset, + GLsizei width, + GLsizei height, + GLenum format, + GLenum type, + GLenum access) { + if (access != GL_WRITE_ONLY) { + SetGLError(GL_INVALID_ENUM, "MapTexSubImage2D: bad access mode"); + return NULL; + } + // NOTE: target is NOT checked because the service will check it + // and we don't know what targets are valid. + if (level < 0 || xoffset < 0 || yoffset < 0 || width < 0 || height < 0) { + SetGLError(GL_INVALID_VALUE, "MapTexSubImage2D: bad dimensions"); + return NULL; + } + uint32 size; + if (!GLES2Util::ComputeImageDataSize( + width, height, format, type, unpack_alignment_, &size)) { + SetGLError(GL_INVALID_VALUE, "MapTexSubImage2D: image size too large"); + return NULL; + } + int32 shm_id; + unsigned int shm_offset; + void* mem = mapped_memory_->Alloc(size, &shm_id, &shm_offset); + if (!mem) { + SetGLError(GL_OUT_OF_MEMORY, "MapTexSubImage2D: out of memory"); + return NULL; + } + + std::pair<MappedTextureMap::iterator, bool> result = + mapped_textures_.insert(std::make_pair( + mem, + MappedTexture( + access, shm_id, mem, shm_offset, + target, level, xoffset, yoffset, width, height, format, type))); + return mem; +} + +void GLES2Implementation::UnmapTexSubImage2D(const void* mem) { + MappedTextureMap::iterator it = mapped_textures_.find(mem); + if (it == mapped_textures_.end()) { + SetGLError(GL_INVALID_VALUE, "UnmapTexSubImage2D: texture not mapped"); + return; + } + const MappedTexture& mt = it->second; + helper_->TexSubImage2D( + mt.target, mt.level, mt.xoffset, mt.yoffset, mt.width, mt.height, + mt.format, mt.type, mt.shm_id, mt.shm_offset); + mapped_memory_->FreePendingToken(mt.shm_memory, helper_->InsertToken()); + mapped_textures_.erase(it); +} + } // namespace gles2 } // namespace gpu |