Add missing cache clears to D3D buffer classes.
BUG=angle:709
Change-Id: I93f92b916a0da26975cd459399cc2873cb4ab9f0
Reviewed-on: https://chromium-review.googlesource.com/210642
Tested-by: Jamie Madill <jmadill@chromium.org>
Reviewed-by: Nicolas Capens <capn@chromium.org>
diff --git a/src/libGLESv2/renderer/d3d/BufferD3D.h b/src/libGLESv2/renderer/d3d/BufferD3D.h
index 8e204b9..0d57338 100644
--- a/src/libGLESv2/renderer/d3d/BufferD3D.h
+++ b/src/libGLESv2/renderer/d3d/BufferD3D.h
@@ -31,7 +31,6 @@
unsigned int getSerial() const { return mSerial; }
virtual size_t getSize() const = 0;
- virtual void clear() = 0;
virtual bool supportsDirectBinding() const = 0;
virtual Renderer* getRenderer() = 0;
diff --git a/src/libGLESv2/renderer/d3d/d3d11/Buffer11.cpp b/src/libGLESv2/renderer/d3d/d3d11/Buffer11.cpp
index 30e2902..e41d58d 100644
--- a/src/libGLESv2/renderer/d3d/d3d11/Buffer11.cpp
+++ b/src/libGLESv2/renderer/d3d/d3d11/Buffer11.cpp
@@ -162,12 +162,14 @@
mMappedStorage(NULL),
mResolvedDataRevision(0),
mReadUsageCount(0)
-{
-}
+{}
Buffer11::~Buffer11()
{
- clear();
+ for (auto it = mBufferStorages.begin(); it != mBufferStorages.end(); it++)
+ {
+ SafeDelete(it->second);
+ }
}
Buffer11 *Buffer11::makeBuffer11(BufferImpl *buffer)
@@ -176,19 +178,6 @@
return static_cast<Buffer11*>(buffer);
}
-void Buffer11::clear()
-{
- for (auto it = mBufferStorages.begin(); it != mBufferStorages.end(); it++)
- {
- SafeDelete(it->second);
- }
-
- mBufferStorages.clear();
-
- mSize = 0;
- mResolvedDataRevision = 0;
-}
-
void Buffer11::setData(const void* data, size_t size, GLenum usage)
{
mIndexRangeCache.clear();
@@ -322,6 +311,7 @@
mSize = std::max<size_t>(mSize, destOffset + size);
}
+ mIndexRangeCache.invalidateRange(destOffset, size);
invalidateStaticData();
}
@@ -352,6 +342,8 @@
if ((access & GL_MAP_WRITE_BIT) > 0)
{
+ mIndexRangeCache.invalidateRange(offset, length);
+
// Update the data revision immediately, since the data might be changed at any time
mMappedStorage->setDataRevision(mMappedStorage->getDataRevision() + 1);
}
@@ -375,6 +367,7 @@
transformFeedbackStorage->setDataRevision(transformFeedbackStorage->getDataRevision() + 1);
}
+ mIndexRangeCache.clear();
invalidateStaticData();
}
@@ -470,6 +463,8 @@
packStorage->packPixels(srcTexture, srcSubresource, params);
packStorage->setDataRevision(latestStorage ? latestStorage->getDataRevision() + 1 : 1);
}
+
+ mIndexRangeCache.clear();
}
Buffer11::BufferStorage11 *Buffer11::getBufferStorage(BufferUsage usage)
diff --git a/src/libGLESv2/renderer/d3d/d3d11/Buffer11.h b/src/libGLESv2/renderer/d3d/d3d11/Buffer11.h
index e56be24..51d47ec 100644
--- a/src/libGLESv2/renderer/d3d/d3d11/Buffer11.h
+++ b/src/libGLESv2/renderer/d3d/d3d11/Buffer11.h
@@ -59,7 +59,6 @@
// BufferD3D implementation
virtual size_t getSize() const { return mSize; }
- virtual void clear();
virtual bool supportsDirectBinding() const { return true; }
virtual Renderer* getRenderer();
diff --git a/src/libGLESv2/renderer/d3d/d3d9/Buffer9.cpp b/src/libGLESv2/renderer/d3d/d3d9/Buffer9.cpp
index feec414..47198d4 100644
--- a/src/libGLESv2/renderer/d3d/d3d9/Buffer9.cpp
+++ b/src/libGLESv2/renderer/d3d/d3d9/Buffer9.cpp
@@ -18,13 +18,11 @@
: BufferD3D(),
mRenderer(renderer),
mSize(0)
-{
-
-}
+{}
Buffer9::~Buffer9()
{
-
+ mSize = 0;
}
Buffer9 *Buffer9::makeBuffer9(BufferImpl *buffer)
@@ -33,11 +31,6 @@
return static_cast<Buffer9*>(buffer);
}
-void Buffer9::clear()
-{
- mSize = 0;
-}
-
void Buffer9::setData(const void* data, size_t size, GLenum usage)
{
if (size > mMemory.size())
@@ -55,7 +48,6 @@
}
mIndexRangeCache.clear();
-
invalidateStaticData();
if (usage == GL_STATIC_DRAW)
@@ -99,6 +91,7 @@
memcpy(mMemory.data() + destOffset, sourceBuffer->mMemory.data() + sourceOffset, size);
}
+ mIndexRangeCache.invalidateRange(destOffset, size);
invalidateStaticData();
}
diff --git a/src/libGLESv2/renderer/d3d/d3d9/Buffer9.h b/src/libGLESv2/renderer/d3d/d3d9/Buffer9.h
index ec25ec3..f12ee00 100644
--- a/src/libGLESv2/renderer/d3d/d3d9/Buffer9.h
+++ b/src/libGLESv2/renderer/d3d/d3d9/Buffer9.h
@@ -27,7 +27,6 @@
// BufferD3D implementation
virtual size_t getSize() const { return mSize; }
- virtual void clear();
virtual bool supportsDirectBinding() const { return false; }
virtual Renderer* getRenderer();
diff --git a/tests/angle_tests/BufferDataTest.cpp b/tests/angle_tests/BufferDataTest.cpp
index 3fdbfbb..83cfd66 100644
--- a/tests/angle_tests/BufferDataTest.cpp
+++ b/tests/angle_tests/BufferDataTest.cpp
@@ -2,7 +2,7 @@
class BufferDataTest : public ANGLETest
{
-protected:
+ protected:
BufferDataTest()
: mBuffer(0),
mProgram(0),
@@ -184,3 +184,128 @@
delete[] data;
}
+class IndexedBufferCopyTest : public ANGLETest
+{
+ protected:
+ IndexedBufferCopyTest()
+ {
+ setWindowWidth(16);
+ setWindowHeight(16);
+ setConfigRedBits(8);
+ setConfigGreenBits(8);
+ setConfigBlueBits(8);
+ setConfigAlphaBits(8);
+ setConfigDepthBits(24);
+ setClientVersion(3);
+ }
+
+ virtual void SetUp()
+ {
+ ANGLETest::SetUp();
+
+ const char * vsSource = SHADER_SOURCE
+ (
+ attribute vec3 in_attrib;
+ varying vec3 v_attrib;
+ void main()
+ {
+ v_attrib = in_attrib;
+ gl_Position = vec4(0.0, 0.0, 0.5, 1.0);
+ gl_PointSize = 100.0;
+ }
+ );
+
+ const char * fsSource = SHADER_SOURCE
+ (
+ precision mediump float;
+ varying vec3 v_attrib;
+ void main()
+ {
+ gl_FragColor = vec4(v_attrib, 1);
+ }
+ );
+
+ glGenBuffers(2, mBuffers);
+ ASSERT_NE(mBuffers[0], 0U);
+ ASSERT_NE(mBuffers[1], 0U);
+
+ glGenBuffers(1, &mElementBuffer);
+ ASSERT_NE(mElementBuffer, 0U);
+
+ mProgram = compileProgram(vsSource, fsSource);
+ ASSERT_NE(mProgram, 0U);
+
+ mAttribLocation = glGetAttribLocation(mProgram, "in_attrib");
+ ASSERT_NE(mAttribLocation, -1);
+
+ glClearColor(0, 0, 0, 0);
+ glDisable(GL_DEPTH_TEST);
+ glClear(GL_COLOR_BUFFER_BIT);
+
+ ASSERT_GL_NO_ERROR();
+ }
+
+ virtual void TearDown()
+ {
+ glDeleteBuffers(2, mBuffers);
+ glDeleteBuffers(1, &mElementBuffer);
+ glDeleteProgram(mProgram);
+
+ ANGLETest::TearDown();
+ }
+
+ GLuint mBuffers[2];
+ GLuint mElementBuffer;
+ GLuint mProgram;
+ GLint mAttribLocation;
+};
+
+// The following test covers an ANGLE bug where our index ranges
+// weren't updated from CopyBufferSubData calls
+// https://code.google.com/p/angleproject/issues/detail?id=709
+TEST_F(IndexedBufferCopyTest, IndexRangeBug)
+{
+ unsigned char vertexData[] = { 255, 0, 0, 0, 0, 0 };
+ unsigned int indexData[] = { 0, 1 };
+
+ glBindBuffer(GL_ARRAY_BUFFER, mBuffers[0]);
+ glBufferData(GL_ARRAY_BUFFER, sizeof(char) * 6, vertexData, GL_STATIC_DRAW);
+
+ glUseProgram(mProgram);
+ glVertexAttribPointer(mAttribLocation, 3, GL_UNSIGNED_BYTE, GL_TRUE, 3, NULL);
+ glEnableVertexAttribArray(mAttribLocation);
+
+ ASSERT_GL_NO_ERROR();
+
+ glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, mElementBuffer);
+ glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(int) * 1, indexData, GL_STATIC_DRAW);
+
+ glUseProgram(mProgram);
+
+ ASSERT_GL_NO_ERROR();
+
+ glDrawElements(GL_POINTS, 1, GL_UNSIGNED_INT, NULL);
+
+ EXPECT_GL_NO_ERROR();
+ EXPECT_PIXEL_EQ(0, 0, 255, 0, 0, 255);
+
+ glBindBuffer(GL_COPY_READ_BUFFER, mBuffers[1]);
+ glBufferData(GL_COPY_READ_BUFFER, 4, &indexData[1], GL_STATIC_DRAW);
+
+ glBindBuffer(GL_COPY_WRITE_BUFFER, mElementBuffer);
+
+ glCopyBufferSubData(GL_COPY_READ_BUFFER, GL_COPY_WRITE_BUFFER, 0, 0, sizeof(int));
+
+ ASSERT_GL_NO_ERROR();
+
+ glClear(GL_COLOR_BUFFER_BIT);
+ EXPECT_PIXEL_EQ(0, 0, 0, 0, 0, 0);
+
+ unsigned char newData[] = { 0, 255, 0 };
+ glBufferSubData(GL_ARRAY_BUFFER, 3, 3, newData);
+
+ glDrawElements(GL_POINTS, 1, GL_UNSIGNED_INT, NULL);
+
+ EXPECT_GL_NO_ERROR();
+ EXPECT_PIXEL_EQ(0, 0, 0, 255, 0, 255);
+}