Home | History | Annotate | Download | only in angle_tests
      1 #include "ANGLETest.h"
      2 
      3 #include <cstdint>
      4 
      5 class BufferDataTest : public ANGLETest
      6 {
      7   protected:
      8     BufferDataTest()
      9         : mBuffer(0),
     10           mProgram(0),
     11           mAttribLocation(-1)
     12     {
     13         setWindowWidth(16);
     14         setWindowHeight(16);
     15         setConfigRedBits(8);
     16         setConfigGreenBits(8);
     17         setConfigBlueBits(8);
     18         setConfigAlphaBits(8);
     19         setConfigDepthBits(24);
     20     }
     21 
     22     virtual void SetUp()
     23     {
     24         ANGLETest::SetUp();
     25 
     26         const char * vsSource = SHADER_SOURCE
     27         (
     28             attribute vec4 position;
     29             attribute float in_attrib;
     30             varying float v_attrib;
     31             void main()
     32             {
     33                 v_attrib = in_attrib;
     34                 gl_Position = position;
     35             }
     36         );
     37 
     38         const char * fsSource = SHADER_SOURCE
     39         (
     40             precision mediump float;
     41             varying float v_attrib;
     42             void main()
     43             {
     44                 gl_FragColor = vec4(v_attrib, 0, 0, 1);
     45             }
     46         );
     47 
     48         glGenBuffers(1, &mBuffer);
     49         ASSERT_NE(mBuffer, 0U);
     50 
     51         mProgram = CompileProgram(vsSource, fsSource);
     52         ASSERT_NE(mProgram, 0U);
     53 
     54         mAttribLocation = glGetAttribLocation(mProgram, "in_attrib");
     55         ASSERT_NE(mAttribLocation, -1);
     56 
     57         glClearColor(0, 0, 0, 0);
     58         glClearDepthf(0.0);
     59         glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
     60 
     61         glDisable(GL_DEPTH_TEST);
     62 
     63         ASSERT_GL_NO_ERROR();
     64     }
     65 
     66     virtual void TearDown()
     67     {
     68         glDeleteBuffers(1, &mBuffer);
     69         glDeleteProgram(mProgram);
     70 
     71         ANGLETest::TearDown();
     72     }
     73 
     74     GLuint mBuffer;
     75     GLuint mProgram;
     76     GLint mAttribLocation;
     77 };
     78 
     79 TEST_F(BufferDataTest, NULLData)
     80 {
     81     glBindBuffer(GL_ARRAY_BUFFER, mBuffer);
     82     EXPECT_GL_NO_ERROR();
     83 
     84     const int numIterations = 128;
     85     for (int i = 0; i < numIterations; ++i)
     86     {
     87         GLsizei bufferSize = sizeof(GLfloat) * (i + 1);
     88         glBufferData(GL_ARRAY_BUFFER, bufferSize, NULL, GL_STATIC_DRAW);
     89         EXPECT_GL_NO_ERROR();
     90 
     91         for (int j = 0; j < bufferSize; j++)
     92         {
     93             for (int k = 0; k < bufferSize - j; k++)
     94             {
     95                 glBufferSubData(GL_ARRAY_BUFFER, k, j, NULL);
     96                 EXPECT_GL_NO_ERROR();
     97             }
     98         }
     99     }
    100 }
    101 
    102 TEST_F(BufferDataTest, ZeroNonNULLData)
    103 {
    104     glBindBuffer(GL_ARRAY_BUFFER, mBuffer);
    105     EXPECT_GL_NO_ERROR();
    106 
    107     char *zeroData = new char[0];
    108     glBufferData(GL_ARRAY_BUFFER, 0, zeroData, GL_STATIC_DRAW);
    109     EXPECT_GL_NO_ERROR();
    110 
    111     glBufferSubData(GL_ARRAY_BUFFER, 0, 0, zeroData);
    112     EXPECT_GL_NO_ERROR();
    113 
    114     delete [] zeroData;
    115 }
    116 
    117 TEST_F(BufferDataTest, NULLResolvedData)
    118 {
    119     glBindBuffer(GL_ARRAY_BUFFER, mBuffer);
    120     glBufferData(GL_ARRAY_BUFFER, 128, NULL, GL_DYNAMIC_DRAW);
    121 
    122     glUseProgram(mProgram);
    123     glVertexAttribPointer(mAttribLocation, 1, GL_FLOAT, GL_FALSE, 4, NULL);
    124     glEnableVertexAttribArray(mAttribLocation);
    125     glBindBuffer(GL_ARRAY_BUFFER, 0);
    126 
    127     drawQuad(mProgram, "position", 0.5f);
    128 }
    129 
    130 TEST_F(BufferDataTest, HugeSetDataShouldNotCrash)
    131 {
    132     glBindBuffer(GL_ARRAY_BUFFER, mBuffer);
    133     EXPECT_GL_NO_ERROR();
    134 
    135     GLsizei allocSize = std::numeric_limits<GLsizei>::max() >> 2;
    136 
    137     uint8_t *data = NULL;
    138     while (data == NULL && allocSize >= 4)
    139     {
    140         data = new (std::nothrow) uint8_t[allocSize];
    141 
    142         if (data == NULL)
    143         {
    144             allocSize >>= 1;
    145         }
    146     }
    147 
    148     ASSERT_NE(static_cast<uint8_t*>(NULL), data);
    149     memset(data, 0, allocSize);
    150 
    151     float * fValue = reinterpret_cast<float*>(data);
    152     for (unsigned int f = 0; f < 6; f++)
    153     {
    154         fValue[f] = 1.0f;
    155     }
    156 
    157     glBufferData(GL_ARRAY_BUFFER, allocSize, data, GL_STATIC_DRAW);
    158 
    159     GLenum error = glGetError();
    160     if (error == GL_NO_ERROR)
    161     {
    162         // If we didn't fail because of an out of memory error, try drawing a quad
    163         // using the large buffer
    164 
    165         // DISABLED because it takes a long time, but left for posterity
    166 
    167         //glUseProgram(mProgram);
    168         //glVertexAttribPointer(mAttribLocation, 1, GL_FLOAT, GL_FALSE, 4, NULL);
    169         //glEnableVertexAttribArray(mAttribLocation);
    170         //glBindBuffer(GL_ARRAY_BUFFER, 0);
    171         //drawQuad(mProgram, "position", 0.5f);
    172         //swapBuffers();
    173 
    174         //// Draw operations can also generate out-of-memory, which is in-spec
    175         //error = glGetError();
    176         //if (error == GL_NO_ERROR)
    177         //{
    178         //    GLint viewportSize[4];
    179         //    glGetIntegerv(GL_VIEWPORT, viewportSize);
    180 
    181         //    GLint midPixelX = (viewportSize[0] + viewportSize[2]) / 2;
    182         //    GLint midPixelY = (viewportSize[1] + viewportSize[3]) / 2;
    183 
    184         //    EXPECT_PIXEL_EQ(midPixelX, midPixelY, 255, 0, 0, 255);
    185         //}
    186         //else
    187         //{
    188         //    EXPECT_EQ(GL_OUT_OF_MEMORY, error);
    189         //}
    190     }
    191     else
    192     {
    193         EXPECT_EQ(GL_OUT_OF_MEMORY, error);
    194     }
    195 
    196     delete[] data;
    197 }
    198 
    199 class IndexedBufferCopyTest : public ANGLETest
    200 {
    201   protected:
    202     IndexedBufferCopyTest()
    203     {
    204         setWindowWidth(16);
    205         setWindowHeight(16);
    206         setConfigRedBits(8);
    207         setConfigGreenBits(8);
    208         setConfigBlueBits(8);
    209         setConfigAlphaBits(8);
    210         setConfigDepthBits(24);
    211         setClientVersion(3);
    212     }
    213 
    214     virtual void SetUp()
    215     {
    216         ANGLETest::SetUp();
    217 
    218         const char * vsSource = SHADER_SOURCE
    219         (
    220             attribute vec3 in_attrib;
    221             varying vec3 v_attrib;
    222             void main()
    223             {
    224                 v_attrib = in_attrib;
    225                 gl_Position = vec4(0.0, 0.0, 0.5, 1.0);
    226                 gl_PointSize = 100.0;
    227             }
    228         );
    229 
    230         const char * fsSource = SHADER_SOURCE
    231         (
    232             precision mediump float;
    233             varying vec3 v_attrib;
    234             void main()
    235             {
    236                 gl_FragColor = vec4(v_attrib, 1);
    237             }
    238         );
    239 
    240         glGenBuffers(2, mBuffers);
    241         ASSERT_NE(mBuffers[0], 0U);
    242         ASSERT_NE(mBuffers[1], 0U);
    243 
    244         glGenBuffers(1, &mElementBuffer);
    245         ASSERT_NE(mElementBuffer, 0U);
    246 
    247         mProgram = CompileProgram(vsSource, fsSource);
    248         ASSERT_NE(mProgram, 0U);
    249 
    250         mAttribLocation = glGetAttribLocation(mProgram, "in_attrib");
    251         ASSERT_NE(mAttribLocation, -1);
    252 
    253         glClearColor(0, 0, 0, 0);
    254         glDisable(GL_DEPTH_TEST);
    255         glClear(GL_COLOR_BUFFER_BIT);
    256 
    257         ASSERT_GL_NO_ERROR();
    258     }
    259 
    260     virtual void TearDown()
    261     {
    262         glDeleteBuffers(2, mBuffers);
    263         glDeleteBuffers(1, &mElementBuffer);
    264         glDeleteProgram(mProgram);
    265 
    266         ANGLETest::TearDown();
    267     }
    268 
    269     GLuint mBuffers[2];
    270     GLuint mElementBuffer;
    271     GLuint mProgram;
    272     GLint mAttribLocation;
    273 };
    274 
    275 // The following test covers an ANGLE bug where our index ranges
    276 // weren't updated from CopyBufferSubData calls
    277 // https://code.google.com/p/angleproject/issues/detail?id=709
    278 TEST_F(IndexedBufferCopyTest, IndexRangeBug)
    279 {
    280     unsigned char vertexData[] = { 255, 0, 0, 0, 0, 0 };
    281     unsigned int indexData[] = { 0, 1 };
    282 
    283     glBindBuffer(GL_ARRAY_BUFFER, mBuffers[0]);
    284     glBufferData(GL_ARRAY_BUFFER, sizeof(char) * 6, vertexData, GL_STATIC_DRAW);
    285 
    286     glUseProgram(mProgram);
    287     glVertexAttribPointer(mAttribLocation, 3, GL_UNSIGNED_BYTE, GL_TRUE, 3, NULL);
    288     glEnableVertexAttribArray(mAttribLocation);
    289 
    290     ASSERT_GL_NO_ERROR();
    291 
    292     glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, mElementBuffer);
    293     glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(int) * 1, indexData, GL_STATIC_DRAW);
    294 
    295     glUseProgram(mProgram);
    296 
    297     ASSERT_GL_NO_ERROR();
    298 
    299     glDrawElements(GL_POINTS, 1, GL_UNSIGNED_INT, NULL);
    300 
    301     EXPECT_GL_NO_ERROR();
    302     EXPECT_PIXEL_EQ(0, 0, 255, 0, 0, 255);
    303 
    304     glBindBuffer(GL_COPY_READ_BUFFER, mBuffers[1]);
    305     glBufferData(GL_COPY_READ_BUFFER, 4, &indexData[1], GL_STATIC_DRAW);
    306 
    307     glBindBuffer(GL_COPY_WRITE_BUFFER, mElementBuffer);
    308 
    309     glCopyBufferSubData(GL_COPY_READ_BUFFER, GL_COPY_WRITE_BUFFER, 0, 0, sizeof(int));
    310 
    311     ASSERT_GL_NO_ERROR();
    312 
    313     glClear(GL_COLOR_BUFFER_BIT);
    314     EXPECT_PIXEL_EQ(0, 0, 0, 0, 0, 0);
    315 
    316     unsigned char newData[] = { 0, 255, 0 };
    317     glBufferSubData(GL_ARRAY_BUFFER, 3, 3, newData);
    318 
    319     glDrawElements(GL_POINTS, 1, GL_UNSIGNED_INT, NULL);
    320 
    321     EXPECT_GL_NO_ERROR();
    322     EXPECT_PIXEL_EQ(0, 0, 0, 255, 0, 255);
    323 }
    324