Index: third_party/WebKit/Source/modules/webgl/WebGL2RenderingContextBase.cpp |
diff --git a/third_party/WebKit/Source/modules/webgl/WebGL2RenderingContextBase.cpp b/third_party/WebKit/Source/modules/webgl/WebGL2RenderingContextBase.cpp |
index 33c94ce4305b2b71abc3ffa947e9bfeff9a3c3aa..b7b60499909d1b3a3019415d3b5c698c803e7717 100644 |
--- a/third_party/WebKit/Source/modules/webgl/WebGL2RenderingContextBase.cpp |
+++ b/third_party/WebKit/Source/modules/webgl/WebGL2RenderingContextBase.cpp |
@@ -148,6 +148,9 @@ void WebGL2RenderingContextBase::initializeNewContext() |
webContext()->getIntegerv(GL_MAX_3D_TEXTURE_SIZE, &m_max3DTextureSize); |
m_max3DTextureLevel = WebGLTexture::computeLevelCount(m_max3DTextureSize, m_max3DTextureSize, m_max3DTextureSize); |
+ m_maxArrayTextureLayers = 0; |
+ webContext()->getIntegerv(GL_MAX_ARRAY_TEXTURE_LAYERS, &m_maxArrayTextureLayers); |
+ |
GLint numCombinedTextureImageUnits = 0; |
webContext()->getIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &numCombinedTextureImageUnits); |
m_samplerUnits.clear(); |
@@ -243,17 +246,61 @@ void WebGL2RenderingContextBase::blitFramebuffer(GLint srcX0, GLint srcY0, GLint |
webContext()->blitFramebufferCHROMIUM(srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1, mask, filter); |
} |
-void WebGL2RenderingContextBase::framebufferTextureLayer(GLenum target, GLenum attachment, const WebGLTexture* texture, GLint level, GLint layer) |
+bool WebGL2RenderingContextBase::validateTexFuncLayer(const char* functionName, GLenum texTarget, GLint layer) |
{ |
- if (isContextLost()) |
- return; |
+ if (layer < 0) { |
+ synthesizeGLError(GL_INVALID_VALUE, functionName, "layer out of range"); |
+ return false; |
+ } |
+ switch (texTarget) { |
+ case GL_TEXTURE_3D: |
+ if (layer > m_max3DTextureSize - 1) { |
+ synthesizeGLError(GL_INVALID_VALUE, functionName, "layer out of range"); |
+ return false; |
+ } |
+ break; |
+ case GL_TEXTURE_2D_ARRAY: |
+ if (layer > m_maxArrayTextureLayers - 1) { |
+ synthesizeGLError(GL_INVALID_VALUE, functionName, "layer out of range"); |
+ return false; |
+ } |
+ break; |
+ default: |
+ ASSERT_NOT_REACHED(); |
+ return false; |
+ } |
+ return true; |
+} |
+void WebGL2RenderingContextBase::framebufferTextureLayer(ScriptState* scriptState, GLenum target, GLenum attachment, WebGLTexture* texture, GLint level, GLint layer) |
+{ |
+ if (isContextLost() || !validateFramebufferFuncParameters("framebufferTextureLayer", target, attachment)) |
+ return; |
if (texture && !texture->validate(contextGroup(), this)) { |
synthesizeGLError(GL_INVALID_VALUE, "framebufferTextureLayer", "no texture or texture not from this context"); |
return; |
} |
+ GLenum textarget = texture ? texture->getTarget() : 0; |
+ if (texture) { |
+ if (textarget != GL_TEXTURE_3D && textarget != GL_TEXTURE_2D_ARRAY) { |
+ synthesizeGLError(GL_INVALID_OPERATION, "framebufferTextureLayer", "invalid texture type"); |
+ return; |
+ } |
+ if (!validateTexFuncLayer("framebufferTextureLayer", textarget, layer)) |
+ return; |
+ if (!validateTexFuncLevel("framebufferTextureLayer", textarget, level)) |
+ return; |
+ } |
+ WebGLFramebuffer* framebufferBinding = getFramebufferBinding(target); |
+ if (!framebufferBinding || !framebufferBinding->object()) { |
+ synthesizeGLError(GL_INVALID_OPERATION, "framebufferTextureLayer", "no framebuffer bound"); |
+ return; |
+ } |
webContext()->framebufferTextureLayer(target, attachment, objectOrZero(texture), level, layer); |
+ framebufferBinding->setAttachmentForBoundFramebuffer(target, attachment, textarget, texture, level, layer); |
+ applyStencilTest(); |
+ preserveObjectWrapper(scriptState, framebufferBinding, "attachment", attachment, texture); |
} |
ScriptValue WebGL2RenderingContextBase::getInternalformatParameter(ScriptState* scriptState, GLenum target, GLenum internalformat, GLenum pname) |