diff options
author | gman@chromium.org <gman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-03-02 00:44:29 +0000 |
---|---|---|
committer | gman@chromium.org <gman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-03-02 00:44:29 +0000 |
commit | ddd968b875f51efee01401fd307f4c691dfd6a9a (patch) | |
tree | f9df8a06531e546b717a8fa328597e787198b142 /gpu/command_buffer/client | |
parent | 516fc39eeea5658b9aeeda0094d5817edd5ec235 (diff) | |
download | chromium_src-ddd968b875f51efee01401fd307f4c691dfd6a9a.zip chromium_src-ddd968b875f51efee01401fd307f4c691dfd6a9a.tar.gz chromium_src-ddd968b875f51efee01401fd307f4c691dfd6a9a.tar.bz2 |
Attempt to submit this CL for the 3rd time. No changes.
http://src.chromium.org/viewvc/chrome?view=rev&revision=40212
TEST=none
BUG=none
Review URL: http://codereview.chromium.org/661309
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@40329 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'gpu/command_buffer/client')
-rw-r--r-- | gpu/command_buffer/client/gles2_cmd_helper_autogen.h | 31 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_implementation.cc | 159 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_implementation.h | 23 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_implementation_autogen.h | 136 |
4 files changed, 275 insertions, 74 deletions
diff --git a/gpu/command_buffer/client/gles2_cmd_helper_autogen.h b/gpu/command_buffer/client/gles2_cmd_helper_autogen.h index df3ed0e..6ae38f4 100644 --- a/gpu/command_buffer/client/gles2_cmd_helper_autogen.h +++ b/gpu/command_buffer/client/gles2_cmd_helper_autogen.h @@ -491,14 +491,9 @@ c.Init(program, pname, params_shm_id, params_shm_offset); } - void GetProgramInfoLog( - GLuint program, GLsizei bufsize, uint32 length_shm_id, - uint32 length_shm_offset, uint32 infolog_shm_id, - uint32 infolog_shm_offset) { + void GetProgramInfoLog(GLuint program, uint32 bucket_id) { gles2::GetProgramInfoLog& c = GetCmdSpace<gles2::GetProgramInfoLog>(); - c.Init( - program, bufsize, length_shm_id, length_shm_offset, infolog_shm_id, - infolog_shm_offset); + c.Init(program, bucket_id); } void GetRenderbufferParameteriv( @@ -516,14 +511,9 @@ c.Init(shader, pname, params_shm_id, params_shm_offset); } - void GetShaderInfoLog( - GLuint shader, GLsizei bufsize, uint32 length_shm_id, - uint32 length_shm_offset, uint32 infolog_shm_id, - uint32 infolog_shm_offset) { + void GetShaderInfoLog(GLuint shader, uint32 bucket_id) { gles2::GetShaderInfoLog& c = GetCmdSpace<gles2::GetShaderInfoLog>(); - c.Init( - shader, bufsize, length_shm_id, length_shm_offset, infolog_shm_id, - infolog_shm_offset); + c.Init(shader, bucket_id); } void GetShaderPrecisionFormat( @@ -534,19 +524,14 @@ c.Init(shadertype, precisiontype, result_shm_id, result_shm_offset); } - void GetShaderSource( - GLuint shader, GLsizei bufsize, uint32 length_shm_id, - uint32 length_shm_offset, uint32 source_shm_id, - uint32 source_shm_offset) { + void GetShaderSource(GLuint shader, uint32 bucket_id) { gles2::GetShaderSource& c = GetCmdSpace<gles2::GetShaderSource>(); - c.Init( - shader, bufsize, length_shm_id, length_shm_offset, source_shm_id, - source_shm_offset); + c.Init(shader, bucket_id); } - void GetString(GLenum name) { + void GetString(GLenum name, uint32 bucket_id) { gles2::GetString& c = GetCmdSpace<gles2::GetString>(); - c.Init(name); + c.Init(name, bucket_id); } void GetTexParameterfv( diff --git a/gpu/command_buffer/client/gles2_implementation.cc b/gpu/command_buffer/client/gles2_implementation.cc index 450e48d..0dacb54 100644 --- a/gpu/command_buffer/client/gles2_implementation.cc +++ b/gpu/command_buffer/client/gles2_implementation.cc @@ -29,7 +29,8 @@ GLES2Implementation::GLES2Implementation( transfer_buffer_(transfer_buffer_size, helper, transfer_buffer), transfer_buffer_id_(transfer_buffer_id), pack_alignment_(4), - unpack_alignment_(4) { + unpack_alignment_(4), + error_bits_(0) { // Eat 1 id so we start at 1 instead of 0. GLuint eat; MakeIds(1, &eat); @@ -58,12 +59,47 @@ void GLES2Implementation::WaitForCmd() { helper_->CommandBufferHelper::Finish(); } +GLenum GLES2Implementation::GetError() { + return GetGLError(); +} + +GLenum GLES2Implementation::GetGLError() { + // Check the GL error first, then our wrapped error. + typedef gles2::GetError::Result Result; + Result* result = GetResultAs<Result*>(); + *result = GL_NO_ERROR; + helper_->GetError(result_shm_id(), result_shm_offset()); + WaitForCmd(); + GLenum error = *result; + if (error == GL_NO_ERROR && error_bits_ != 0) { + for (uint32 mask = 1; mask != 0; mask = mask << 1) { + if ((error_bits_ & mask) != 0) { + error = GLES2Util::GLErrorBitToGLError(mask); + break; + } + } + } + + if (error != GL_NO_ERROR) { + // There was an error, clear the corresponding wrapped error. + error_bits_ &= ~GLES2Util::GLErrorToErrorBit(error); + } + return error; +} + +void GLES2Implementation::SetGLError(GLenum error) { + error_bits_ |= GLES2Util::GLErrorToErrorBit(error); +} + void GLES2Implementation::GetBucketContents(uint32 bucket_id, std::vector<int8>* data) { DCHECK(data); + typedef cmd::GetBucketSize::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->GetBucketSize(bucket_id, result_shm_id(), result_shm_offset()); WaitForCmd(); - uint32 size = GetResultAs<cmd::GetBucketSize::Result>(); + uint32 size = *result; data->resize(size); if (size > 0u) { uint32 max_size = transfer_buffer_.GetLargestFreeOrPendingSize(); @@ -108,15 +144,25 @@ void GLES2Implementation::SetBucketContents( } } -std::string GLES2Implementation::GetBucketAsString(uint32 bucket_id) { +bool GLES2Implementation::GetBucketAsString( + uint32 bucket_id, std::string* str) { + DCHECK(str); std::vector<int8> data; + // NOTE: strings are passed NULL terminated. That means the empty + // string will have a size of 1 and no-string will have a size of 0 GetBucketContents(bucket_id, &data); - return std::string(reinterpret_cast<char*>(&data[0]), data.size()); + if (data.empty()) { + return false; + } + str->assign(&data[0], &data[0] + data.size() - 1); + return true; } void GLES2Implementation::SetBucketAsString( uint32 bucket_id, const std::string& str) { - SetBucketContents(bucket_id, str.c_str(), str.size()); + // NOTE: strings are passed NULL terminated. That means the empty + // string will have a size of 1 and no-string will have a size of 0 + SetBucketContents(bucket_id, str.c_str(), str.size() + 1); } void GLES2Implementation::DrawElements( @@ -157,18 +203,24 @@ void GLES2Implementation::GetVertexAttribPointerv( GLint GLES2Implementation::GetAttribLocation( GLuint program, const char* name) { + typedef cmd::GetBucketSize::Result Result; + Result* result = GetResultAs<Result*>(); + *result = -1; helper_->GetAttribLocationImmediate( program, name, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLint>(); + return *result; } GLint GLES2Implementation::GetUniformLocation( GLuint program, const char* name) { + typedef cmd::GetBucketSize::Result Result; + Result* result = GetResultAs<Result*>(); + *result = -1; helper_->GetUniformLocationImmediate( program, name, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLint>(); + return *result; } void GLES2Implementation::PixelStorei(GLenum pname, GLint param) { @@ -195,6 +247,10 @@ void GLES2Implementation::VertexAttribPointer( void GLES2Implementation::ShaderSource( GLuint shader, GLsizei count, const char** source, const GLint* length) { + if (count < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } // TODO(gman): change to use buckets and check that there is enough room. // Compute the total size. @@ -233,6 +289,15 @@ void GLES2Implementation::BufferData( void GLES2Implementation::BufferSubData( GLenum target, GLintptr offset, GLsizeiptr size, const void* data) { + if (size == 0) { + return; + } + + if (size < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + const int8* source = static_cast<const int8*>(data); GLsizeiptr max_size = transfer_buffer_.GetLargestFreeOrPendingSize(); while (size) { @@ -252,7 +317,11 @@ void GLES2Implementation::BufferSubData( void GLES2Implementation::CompressedTexImage2D( GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, GLsizei image_size, const void* data) { - // TODO(gman): Switch to use buckets alwayst or at least if no room in shared + if (width < 0 || height < 0 || level < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + // TODO(gman): Switch to use buckets always or at least if no room in shared // memory. DCHECK_LE(image_size, static_cast<GLsizei>( @@ -268,7 +337,11 @@ void GLES2Implementation::CompressedTexImage2D( void GLES2Implementation::CompressedTexSubImage2D( GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei image_size, const void* data) { - // TODO(gman): Switch to use buckets alwayst or at least if no room in shared + if (width < 0 || height < 0 || level < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + // TODO(gman): Switch to use buckets always or at least if no room in shared // memory. DCHECK_LE(image_size, static_cast<GLsizei>( @@ -285,6 +358,10 @@ void GLES2Implementation::TexImage2D( GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const void* pixels) { + if (level < 0 || height < 0 || width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->TexImage2D( target, level, internalformat, width, height, border, format, type, 0, 0); if (pixels) { @@ -295,6 +372,10 @@ void GLES2Implementation::TexImage2D( void GLES2Implementation::TexSubImage2D( GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, const void* pixels) { + if (level < 0 || height < 0 || width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } const int8* source = static_cast<const int8*>(pixels); GLsizeiptr max_size = transfer_buffer_.GetLargestFreeOrPendingSize(); GLsizeiptr unpadded_row_size = GLES2Util::ComputeImageDataSize( @@ -355,8 +436,16 @@ GLenum GLES2Implementation::CheckFramebufferStatus(GLenum target) { void GLES2Implementation::GetActiveAttrib( GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, char* name) { + if (bufsize < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + // Clear the bucket so if we the command fails nothing will be in it. + helper_->SetBucketSize(kResultBucketId, 0); typedef gles2::GetActiveAttrib::Result Result; Result* result = static_cast<Result*>(result_buffer_); + // Set as failed so if the command fails we'll recover. + result->success = false; helper_->GetActiveAttrib(program, index, kResultBucketId, result_shm_id(), result_shm_offset()); WaitForCmd(); @@ -386,8 +475,16 @@ void GLES2Implementation::GetActiveAttrib( void GLES2Implementation::GetActiveUniform( GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, char* name) { + if (bufsize < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + // Clear the bucket so if we the command fails nothing will be in it. + helper_->SetBucketSize(kResultBucketId, 0); typedef gles2::GetActiveUniform::Result Result; Result* result = static_cast<Result*>(result_buffer_); + // Set as failed so if the command fails we'll recover. + result->success = false; helper_->GetActiveUniform(program, index, kResultBucketId, result_shm_id(), result_shm_offset()); WaitForCmd(); @@ -416,6 +513,10 @@ void GLES2Implementation::GetActiveUniform( void GLES2Implementation::GetAttachedShaders( GLuint program, GLsizei maxcount, GLsizei* count, GLuint* shaders) { + if (maxcount < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } typedef gles2::GetAttachedShaders::Result Result; uint32 size = Result::ComputeSize(maxcount); Result* result = transfer_buffer_.AllocTyped<Result>(size); @@ -433,16 +534,6 @@ void GLES2Implementation::GetAttachedShaders( transfer_buffer_.FreePendingToken(result, token); } -void GLES2Implementation::GetProgramInfoLog( - GLuint program, GLsizei bufsize, GLsizei* length, char* infolog) { - // TODO(gman): implement. -} - -void GLES2Implementation::GetShaderInfoLog( - GLuint shader, GLsizei bufsize, GLsizei* length, char* infolog) { - // TODO(gman): implement. -} - void GLES2Implementation::GetShaderPrecisionFormat( GLenum shadertype, GLenum precisiontype, GLint* range, GLint* precision) { typedef gles2::GetShaderPrecisionFormat::Result Result; @@ -461,14 +552,26 @@ void GLES2Implementation::GetShaderPrecisionFormat( } } -void GLES2Implementation::GetShaderSource( - GLuint shader, GLsizei bufsize, GLsizei* length, char* source) { - // TODO(gman): implement. -} - const GLubyte* GLES2Implementation::GetString(GLenum name) { - // TODO(gman): implement. - return 0; + const char* result; + GLStringMap::const_iterator it = gl_strings_.find(name); + if (it != gl_strings_.end()) { + result = it->second.c_str(); + } else { + // Clear the bucket so if we the command fails nothing will be in it. + helper_->SetBucketSize(kResultBucketId, 0); + helper_->GetString(name, kResultBucketId); + std::string str; + if (GetBucketAsString(kResultBucketId, &str)) { + std::pair<GLStringMap::const_iterator, bool> insert_result = + gl_strings_.insert(std::make_pair(name, str)); + DCHECK(insert_result.second); + result = insert_result.first->second.c_str(); + } else { + result = NULL; + } + } + return reinterpret_cast<const GLubyte*>(result); } void GLES2Implementation::GetUniformfv( @@ -492,6 +595,10 @@ void GLES2Implementation::ReadPixels( GLenum type, void* pixels) { // Note: Negative widths and heights are not handled here but are handled // by the service side so the glGetError wrapping works. + if (width < 0 || height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } if (width == 0 || height == 0) { return; } diff --git a/gpu/command_buffer/client/gles2_implementation.h b/gpu/command_buffer/client/gles2_implementation.h index 579e0d3..339ed4b 100644 --- a/gpu/command_buffer/client/gles2_implementation.h +++ b/gpu/command_buffer/client/gles2_implementation.h @@ -5,6 +5,7 @@ #ifndef GPU_COMMAND_BUFFER_CLIENT_GLES2_IMPLEMENTATION_H_ #define GPU_COMMAND_BUFFER_CLIENT_GLES2_IMPLEMENTATION_H_ +#include <map> #include <string> #include <vector> #include "gpu/command_buffer/common/gles2_cmd_utils.h" @@ -62,9 +63,15 @@ class GLES2Implementation { // Gets the value of the result. template <typename T> T GetResultAs() const { - return *static_cast<T*>(result_buffer_); + return static_cast<T>(result_buffer_); } + // Gets the GLError through our wrapper. + GLenum GetGLError(); + + // Sets our wrapper for the GLError. + void SetGLError(GLenum error); + // Waits for all commands to execute. void WaitForCmd(); @@ -78,8 +85,9 @@ class GLES2Implementation { // Sets the contents of a bucket. void SetBucketContents(uint32 bucket_id, const void* data, size_t size); - // Gets the contents of a bucket as a string. - std::string GetBucketAsString(uint32 bucket_id); + // Gets the contents of a bucket as a string. Returns false if there is no + // string available which is a separate case from the empty string. + bool GetBucketAsString(uint32 bucket_id, std::string* str); // Sets the contents of a bucket as a string. void SetBucketAsString(uint32 bucket_id, const std::string& str); @@ -102,10 +110,17 @@ class GLES2Implementation { // unpack alignment as last set by glPixelStorei GLint unpack_alignment_; + // Current GL error bits. + uint32 error_bits_; + + // Map of GLenum to Strings for glGetString. We need to cache these because + // the pointer passed back to the client has to remain valid for eternity. + typedef std::map<uint32, std::string> GLStringMap; + GLStringMap gl_strings_; + DISALLOW_COPY_AND_ASSIGN(GLES2Implementation); }; - } // namespace gles2 } // namespace gpu diff --git a/gpu/command_buffer/client/gles2_implementation_autogen.h b/gpu/command_buffer/client/gles2_implementation_autogen.h index 8b30119..b758002 100644 --- a/gpu/command_buffer/client/gles2_implementation_autogen.h +++ b/gpu/command_buffer/client/gles2_implementation_autogen.h @@ -103,6 +103,14 @@ void CompressedTexSubImage2D( void CopyTexImage2D( GLenum target, GLint level, GLenum internalformat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border) { + if (width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + if (height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->CopyTexImage2D( target, level, internalformat, x, y, width, height, border); } @@ -110,6 +118,14 @@ void CopyTexImage2D( void CopyTexSubImage2D( GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height) { + if (width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + if (height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->CopyTexSubImage2D( target, level, xoffset, yoffset, x, y, width, height); } @@ -185,6 +201,10 @@ void DisableVertexAttribArray(GLuint index) { } void DrawArrays(GLenum mode, GLint first, GLsizei count) { + if (count < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->DrawArrays(mode, first, count); } @@ -274,11 +294,7 @@ void GetBufferParameteriv(GLenum target, GLenum pname, GLint* params) { memcpy(params, result_buffer_, num_values * sizeof(*params)); } -GLenum GetError() { - helper_->GetError(result_shm_id(), result_shm_offset()); - WaitForCmd(); - return GetResultAs<GLenum>(); -} +GLenum GetError(); void GetFloatv(GLenum pname, GLfloat* params) { helper_->GetFloatv(pname, result_shm_id(), result_shm_offset()); @@ -314,10 +330,21 @@ void GetProgramiv(GLuint program, GLenum pname, GLint* params) { memcpy(params, result_buffer_, num_values * sizeof(*params)); } -// TODO(gman): Implement this void GetProgramInfoLog( - GLuint program, GLsizei bufsize, GLsizei* length, char* infolog); - + GLuint program, GLsizei bufsize, GLsizei* length, char* infolog) { + helper_->SetBucketSize(kResultBucketId, 0); + helper_->GetProgramInfoLog(program, kResultBucketId); + std::string str; + if (GetBucketAsString(kResultBucketId, &str)) { + GLsizei max_size = + std::min(static_cast<size_t>(bufsize) - 1, str.size()); + if (length != NULL) { + *length = max_size; + } + memcpy(infolog, str.c_str(), max_size); + infolog[max_size] = '\0'; + } +} void GetRenderbufferParameteriv(GLenum target, GLenum pname, GLint* params) { helper_->GetRenderbufferParameteriv( target, pname, result_shm_id(), result_shm_offset()); @@ -335,17 +362,39 @@ void GetShaderiv(GLuint shader, GLenum pname, GLint* params) { memcpy(params, result_buffer_, num_values * sizeof(*params)); } -// TODO(gman): Implement this void GetShaderInfoLog( - GLuint shader, GLsizei bufsize, GLsizei* length, char* infolog); - + GLuint shader, GLsizei bufsize, GLsizei* length, char* infolog) { + helper_->SetBucketSize(kResultBucketId, 0); + helper_->GetShaderInfoLog(shader, kResultBucketId); + std::string str; + if (GetBucketAsString(kResultBucketId, &str)) { + GLsizei max_size = + std::min(static_cast<size_t>(bufsize) - 1, str.size()); + if (length != NULL) { + *length = max_size; + } + memcpy(infolog, str.c_str(), max_size); + infolog[max_size] = '\0'; + } +} void GetShaderPrecisionFormat( GLenum shadertype, GLenum precisiontype, GLint* range, GLint* precision); -// TODO(gman): Implement this void GetShaderSource( - GLuint shader, GLsizei bufsize, GLsizei* length, char* source); - + GLuint shader, GLsizei bufsize, GLsizei* length, char* source) { + helper_->SetBucketSize(kResultBucketId, 0); + helper_->GetShaderSource(shader, kResultBucketId); + std::string str; + if (GetBucketAsString(kResultBucketId, &str)) { + GLsizei max_size = + std::min(static_cast<size_t>(bufsize) - 1, str.size()); + if (length != NULL) { + *length = max_size; + } + memcpy(source, str.c_str(), max_size); + source[max_size] = '\0'; + } +} const GLubyte* GetString(GLenum name); void GetTexParameterfv(GLenum target, GLenum pname, GLfloat* params) { @@ -397,45 +446,66 @@ void Hint(GLenum target, GLenum mode) { } GLboolean IsBuffer(GLuint buffer) { + typedef IsBuffer::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsBuffer(buffer, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsEnabled(GLenum cap) { + typedef IsEnabled::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsEnabled(cap, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsFramebuffer(GLuint framebuffer) { + typedef IsFramebuffer::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsFramebuffer(framebuffer, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsProgram(GLuint program) { + typedef IsProgram::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsProgram(program, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsRenderbuffer(GLuint renderbuffer) { + typedef IsRenderbuffer::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsRenderbuffer(renderbuffer, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsShader(GLuint shader) { + typedef IsShader::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsShader(shader, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } GLboolean IsTexture(GLuint texture) { + typedef IsTexture::Result Result; + Result* result = GetResultAs<Result*>(); + *result = 0; helper_->IsTexture(texture, result_shm_id(), result_shm_offset()); WaitForCmd(); - return GetResultAs<GLboolean>(); + return *result; } void LineWidth(GLfloat width) { @@ -458,6 +528,14 @@ void ReadPixels( void RenderbufferStorage( GLenum target, GLenum internalformat, GLsizei width, GLsizei height) { + if (width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + if (height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->RenderbufferStorage(target, internalformat, width, height); } @@ -466,6 +544,14 @@ void SampleCoverage(GLclampf value, GLboolean invert) { } void Scissor(GLint x, GLint y, GLsizei width, GLsizei height) { + if (width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + if (height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->Scissor(x, y, width, height); } @@ -645,6 +731,14 @@ void VertexAttribPointer( const void* ptr); void Viewport(GLint x, GLint y, GLsizei width, GLsizei height) { + if (width < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } + if (height < 0) { + SetGLError(GL_INVALID_VALUE); + return; + } helper_->Viewport(x, y, width, height); } |