Implements more pack/unpack states.
Pack: row length, skip rows, skip pixels.
Unpack: image height, skip images, skip rows, skip pixels.

BUG=angleproject:512
BUG=angleproject:1095

Change-Id: I11e3bc05d23419b72c92b96aabd3f0bacd983626
Reviewed-on: https://chromium-review.googlesource.com/304370
Tryjob-Request: Jamie Madill <jmadill@chromium.org>
Reviewed-by: Jamie Madill <jmadill@chromium.org>
Tested-by: Jamie Madill <jmadill@chromium.org>
diff --git a/src/libANGLE/Context.cpp b/src/libANGLE/Context.cpp
index e31a8b7..fb1683e 100644
--- a/src/libANGLE/Context.cpp
+++ b/src/libANGLE/Context.cpp
@@ -1106,7 +1106,7 @@
         case GL_PACK_ROW_LENGTH:
         case GL_PACK_SKIP_ROWS:
         case GL_PACK_SKIP_PIXELS:
-            if (!mExtensions.packSubimage)
+            if ((mClientVersion < 3) && !mExtensions.packSubimage)
             {
                 return false;
             }
@@ -1116,7 +1116,7 @@
         case GL_UNPACK_ROW_LENGTH:
         case GL_UNPACK_SKIP_ROWS:
         case GL_UNPACK_SKIP_PIXELS:
-            if (!mExtensions.unpackSubimage)
+            if ((mClientVersion < 3) && !mExtensions.unpackSubimage)
             {
                 return false;
             }
@@ -1237,6 +1237,8 @@
       case GL_PACK_SKIP_ROWS:
       case GL_PACK_SKIP_PIXELS:
       case GL_UNPACK_ROW_LENGTH:
+      case GL_UNPACK_IMAGE_HEIGHT:
+      case GL_UNPACK_SKIP_IMAGES:
       case GL_UNPACK_SKIP_ROWS:
       case GL_UNPACK_SKIP_PIXELS:
         {
diff --git a/src/libANGLE/State.cpp b/src/libANGLE/State.cpp
index 746b514..32112a8 100644
--- a/src/libANGLE/State.cpp
+++ b/src/libANGLE/State.cpp
@@ -28,9 +28,16 @@
     // TODO(jmadill): additional ES3 state
     mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_ALIGNMENT);
     mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_ROW_LENGTH);
+    mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
+    mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_SKIP_IMAGES);
+    mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_SKIP_ROWS);
+    mUnpackStateBitMask.set(DIRTY_BIT_UNPACK_SKIP_PIXELS);
 
     mPackStateBitMask.set(DIRTY_BIT_PACK_ALIGNMENT);
     mPackStateBitMask.set(DIRTY_BIT_PACK_REVERSE_ROW_ORDER);
+    mPackStateBitMask.set(DIRTY_BIT_PACK_ROW_LENGTH);
+    mPackStateBitMask.set(DIRTY_BIT_PACK_SKIP_ROWS);
+    mPackStateBitMask.set(DIRTY_BIT_PACK_SKIP_PIXELS);
 
     mClearStateBitMask.set(DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
     mClearStateBitMask.set(DIRTY_BIT_SCISSOR_TEST_ENABLED);
@@ -1116,6 +1123,39 @@
     return mPack.reverseRowOrder;
 }
 
+void State::setPackRowLength(GLint rowLength)
+{
+    mPack.rowLength = rowLength;
+    mDirtyBits.set(DIRTY_BIT_PACK_ROW_LENGTH);
+}
+
+GLint State::getPackRowLength() const
+{
+    return mPack.rowLength;
+}
+
+void State::setPackSkipRows(GLint skipRows)
+{
+    mPack.skipRows = skipRows;
+    mDirtyBits.set(DIRTY_BIT_PACK_SKIP_ROWS);
+}
+
+GLint State::getPackSkipRows() const
+{
+    return mPack.skipRows;
+}
+
+void State::setPackSkipPixels(GLint skipPixels)
+{
+    mPack.skipPixels = skipPixels;
+    mDirtyBits.set(DIRTY_BIT_PACK_SKIP_PIXELS);
+}
+
+GLint State::getPackSkipPixels() const
+{
+    return mPack.skipPixels;
+}
+
 const PixelPackState &State::getPackState() const
 {
     return mPack;
@@ -1148,6 +1188,50 @@
     return mUnpack.rowLength;
 }
 
+void State::setUnpackImageHeight(GLint imageHeight)
+{
+    mUnpack.imageHeight = imageHeight;
+    mDirtyBits.set(DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
+}
+
+GLint State::getUnpackImageHeight() const
+{
+    return mUnpack.imageHeight;
+}
+
+void State::setUnpackSkipImages(GLint skipImages)
+{
+    mUnpack.skipImages = skipImages;
+    mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_IMAGES);
+}
+
+GLint State::getUnpackSkipImages() const
+{
+    return mUnpack.skipImages;
+}
+
+void State::setUnpackSkipRows(GLint skipRows)
+{
+    mUnpack.skipRows = skipRows;
+    mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_ROWS);
+}
+
+GLint State::getUnpackSkipRows() const
+{
+    return mUnpack.skipRows;
+}
+
+void State::setUnpackSkipPixels(GLint skipPixels)
+{
+    mUnpack.skipPixels = skipPixels;
+    mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_PIXELS);
+}
+
+GLint State::getUnpackSkipPixels() const
+{
+    return mUnpack.skipPixels;
+}
+
 const PixelUnpackState &State::getUnpackState() const
 {
     return mUnpack;
@@ -1250,8 +1334,29 @@
       case GL_CURRENT_PROGRAM:                          *params = mProgram ? mProgram->id() : 0;                  break;
       case GL_PACK_ALIGNMENT:                           *params = mPack.alignment;                                break;
       case GL_PACK_REVERSE_ROW_ORDER_ANGLE:             *params = mPack.reverseRowOrder;                          break;
+      case GL_PACK_ROW_LENGTH:
+          *params = mPack.rowLength;
+          break;
+      case GL_PACK_SKIP_ROWS:
+          *params = mPack.skipRows;
+          break;
+      case GL_PACK_SKIP_PIXELS:
+          *params = mPack.skipPixels;
+          break;
       case GL_UNPACK_ALIGNMENT:                         *params = mUnpack.alignment;                              break;
       case GL_UNPACK_ROW_LENGTH:                        *params = mUnpack.rowLength;                              break;
+      case GL_UNPACK_IMAGE_HEIGHT:
+          *params = mUnpack.imageHeight;
+          break;
+      case GL_UNPACK_SKIP_IMAGES:
+          *params = mUnpack.skipImages;
+          break;
+      case GL_UNPACK_SKIP_ROWS:
+          *params = mUnpack.skipRows;
+          break;
+      case GL_UNPACK_SKIP_PIXELS:
+          *params = mUnpack.skipPixels;
+          break;
       case GL_GENERATE_MIPMAP_HINT:                     *params = mGenerateMipmapHint;                            break;
       case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:      *params = mFragmentShaderDerivativeHint;                  break;
       case GL_ACTIVE_TEXTURE:
diff --git a/src/libANGLE/State.h b/src/libANGLE/State.h
index b53dce6..64c3fa7 100644
--- a/src/libANGLE/State.h
+++ b/src/libANGLE/State.h
@@ -232,6 +232,12 @@
     GLint getPackAlignment() const;
     void setPackReverseRowOrder(bool reverseRowOrder);
     bool getPackReverseRowOrder() const;
+    void setPackRowLength(GLint rowLength);
+    GLint getPackRowLength() const;
+    void setPackSkipRows(GLint skipRows);
+    GLint getPackSkipRows() const;
+    void setPackSkipPixels(GLint skipPixels);
+    GLint getPackSkipPixels() const;
     const PixelPackState &getPackState() const;
     PixelPackState &getPackState();
 
@@ -240,6 +246,14 @@
     GLint getUnpackAlignment() const;
     void setUnpackRowLength(GLint rowLength);
     GLint getUnpackRowLength() const;
+    void setUnpackImageHeight(GLint imageHeight);
+    GLint getUnpackImageHeight() const;
+    void setUnpackSkipImages(GLint skipImages);
+    GLint getUnpackSkipImages() const;
+    void setUnpackSkipRows(GLint skipRows);
+    GLint getUnpackSkipRows() const;
+    void setUnpackSkipPixels(GLint skipPixels);
+    GLint getUnpackSkipPixels() const;
     const PixelUnpackState &getUnpackState() const;
     PixelUnpackState &getUnpackState();
 
@@ -289,8 +303,15 @@
         DIRTY_BIT_CLEAR_STENCIL,
         DIRTY_BIT_UNPACK_ALIGNMENT,
         DIRTY_BIT_UNPACK_ROW_LENGTH,
+        DIRTY_BIT_UNPACK_IMAGE_HEIGHT,
+        DIRTY_BIT_UNPACK_SKIP_IMAGES,
+        DIRTY_BIT_UNPACK_SKIP_ROWS,
+        DIRTY_BIT_UNPACK_SKIP_PIXELS,
         DIRTY_BIT_PACK_ALIGNMENT,
         DIRTY_BIT_PACK_REVERSE_ROW_ORDER,
+        DIRTY_BIT_PACK_ROW_LENGTH,
+        DIRTY_BIT_PACK_SKIP_ROWS,
+        DIRTY_BIT_PACK_SKIP_PIXELS,
         DIRTY_BIT_DITHER_ENABLED,
         DIRTY_BIT_GENERATE_MIPMAP_HINT,
         DIRTY_BIT_SHADER_DERIVATIVE_HINT,
diff --git a/src/libANGLE/formatutils.cpp b/src/libANGLE/formatutils.cpp
index 0bfe872..0ea125e 100644
--- a/src/libANGLE/formatutils.cpp
+++ b/src/libANGLE/formatutils.cpp
@@ -589,9 +589,23 @@
     return rx::roundUp(rowBytes, static_cast<GLuint>(alignment));
 }
 
-GLuint InternalFormat::computeDepthPitch(GLenum formatType, GLsizei width, GLsizei height, GLint alignment, GLint rowLength) const
+GLuint InternalFormat::computeDepthPitch(GLenum formatType,
+                                         GLsizei width,
+                                         GLsizei height,
+                                         GLint alignment,
+                                         GLint rowLength,
+                                         GLint imageHeight) const
 {
-    return computeRowPitch(formatType, width, alignment, rowLength) * height;
+    GLuint rows;
+    if (imageHeight > 0)
+    {
+        rows = imageHeight;
+    }
+    else
+    {
+        rows = height;
+    }
+    return computeRowPitch(formatType, width, alignment, rowLength) * rows;
 }
 
 GLuint InternalFormat::computeBlockSize(GLenum formatType, GLsizei width, GLsizei height) const
@@ -616,6 +630,15 @@
     }
 }
 
+GLuint InternalFormat::computeSkipPixels(GLint rowPitch,
+                                         GLint depthPitch,
+                                         GLint skipImages,
+                                         GLint skipRows,
+                                         GLint skipPixels) const
+{
+    return skipImages * depthPitch + skipRows * rowPitch + skipPixels * pixelBytes;
+}
+
 GLenum GetSizedInternalFormat(GLenum internalFormat, GLenum type)
 {
     const InternalFormat& formatInfo = GetInternalFormatInfo(internalFormat);
diff --git a/src/libANGLE/formatutils.h b/src/libANGLE/formatutils.h
index 92a27b1..4ac1265 100644
--- a/src/libANGLE/formatutils.h
+++ b/src/libANGLE/formatutils.h
@@ -66,8 +66,18 @@
     SupportCheckFunction filterSupport;
 
     GLuint computeRowPitch(GLenum formatType, GLsizei width, GLint alignment, GLint rowLength) const;
-    GLuint computeDepthPitch(GLenum formatType, GLsizei width, GLsizei height, GLint alignment, GLint rowLength) const;
+    GLuint computeDepthPitch(GLenum formatType,
+                             GLsizei width,
+                             GLsizei height,
+                             GLint alignment,
+                             GLint rowLength,
+                             GLint imageHeight) const;
     GLuint computeBlockSize(GLenum formatType, GLsizei width, GLsizei height) const;
+    GLuint computeSkipPixels(GLint rowPitch,
+                             GLint depthPitch,
+                             GLint skipImages,
+                             GLint skipRows,
+                             GLint skipPixels) const;
 };
 const InternalFormat &GetInternalFormatInfo(GLenum internalFormat);
 
diff --git a/src/libANGLE/renderer/d3d/FramebufferD3D.cpp b/src/libANGLE/renderer/d3d/FramebufferD3D.cpp
index b5cc1be..c41b3a6 100644
--- a/src/libANGLE/renderer/d3d/FramebufferD3D.cpp
+++ b/src/libANGLE/renderer/d3d/FramebufferD3D.cpp
@@ -250,17 +250,15 @@
 {
     const gl::PixelPackState &packState = state.getPackState();
 
-    if (packState.rowLength != 0 || packState.skipRows != 0 || packState.skipPixels != 0)
-    {
-        UNIMPLEMENTED();
-        return gl::Error(GL_INVALID_OPERATION, "invalid pixel store parameters in readPixels");
-    }
-
     GLenum sizedInternalFormat = gl::GetSizedInternalFormat(format, type);
     const gl::InternalFormat &sizedFormatInfo = gl::GetInternalFormatInfo(sizedInternalFormat);
-    GLuint outputPitch = sizedFormatInfo.computeRowPitch(type, area.width, packState.alignment, 0);
+    GLuint outputPitch =
+        sizedFormatInfo.computeRowPitch(type, area.width, packState.alignment, packState.rowLength);
+    GLsizei outputSkipBytes = sizedFormatInfo.computeSkipPixels(
+        outputPitch, 0, 0, packState.skipRows, packState.skipPixels);
 
-    return readPixels(area, format, type, outputPitch, packState, reinterpret_cast<uint8_t*>(pixels));
+    return readPixelsImpl(area, format, type, outputPitch, packState,
+                          reinterpret_cast<uint8_t *>(pixels) + outputSkipBytes);
 }
 
 gl::Error FramebufferD3D::blit(const gl::State &state, const gl::Rectangle &sourceArea, const gl::Rectangle &destArea,
diff --git a/src/libANGLE/renderer/d3d/FramebufferD3D.h b/src/libANGLE/renderer/d3d/FramebufferD3D.h
index 42f76ff..ff51db0 100644
--- a/src/libANGLE/renderer/d3d/FramebufferD3D.h
+++ b/src/libANGLE/renderer/d3d/FramebufferD3D.h
@@ -91,8 +91,12 @@
   private:
     virtual gl::Error clear(const gl::State &state, const ClearParameters &clearParams) = 0;
 
-    virtual gl::Error readPixels(const gl::Rectangle &area, GLenum format, GLenum type, size_t outputPitch,
-                                 const gl::PixelPackState &pack, uint8_t *pixels) const = 0;
+    virtual gl::Error readPixelsImpl(const gl::Rectangle &area,
+                                     GLenum format,
+                                     GLenum type,
+                                     size_t outputPitch,
+                                     const gl::PixelPackState &pack,
+                                     uint8_t *pixels) const = 0;
 
     virtual gl::Error blit(const gl::Rectangle &sourceArea, const gl::Rectangle &destArea, const gl::Rectangle *scissor,
                            bool blitRenderTarget, bool blitDepth, bool blitStencil, GLenum filter,
diff --git a/src/libANGLE/renderer/d3d/TextureD3D.cpp b/src/libANGLE/renderer/d3d/TextureD3D.cpp
index 0687ac8..cdb2c47 100644
--- a/src/libANGLE/renderer/d3d/TextureD3D.cpp
+++ b/src/libANGLE/renderer/d3d/TextureD3D.cpp
@@ -165,14 +165,6 @@
                                    const uint8_t *pixels,
                                    ptrdiff_t layerOffset)
 {
-    if (unpack.skipRows != 0 || unpack.skipPixels != 0 || unpack.imageHeight != 0 || unpack.skipImages != 0)
-    {
-        // TODO(jmadill): additional unpack parameters
-        // return no error here to work around dEQP-GLES3 failing to state reset.
-        UNIMPLEMENTED();
-        return gl::Error(GL_NO_ERROR);
-    }
-
     ImageD3D *image = getImage(index);
     ASSERT(image);
 
@@ -258,12 +250,6 @@
                                              const uint8_t *pixels,
                                              ptrdiff_t layerOffset)
 {
-    if (unpack.skipRows != 0 || unpack.skipPixels != 0 || unpack.imageHeight != 0 || unpack.skipImages != 0)
-    {
-        UNIMPLEMENTED();
-        return gl::Error(GL_INVALID_OPERATION, "unimplemented pixel store state");
-    }
-
     // We no longer need the "GLenum format" parameter to TexImage to determine what data format "pixels" contains.
     // From our image internal format we know how many channels to expect, and "type" gives the format of pixel's components.
     const uint8_t *pixelData = NULL;
@@ -295,12 +281,6 @@
                                          const gl::PixelUnpackState &unpack, const uint8_t *pixels,
                                          ptrdiff_t layerOffset)
 {
-    if (unpack.skipRows != 0 || unpack.skipPixels != 0 || unpack.imageHeight != 0 || unpack.skipImages != 0)
-    {
-        UNIMPLEMENTED();
-        return gl::Error(GL_INVALID_OPERATION, "unimplemented pixel store state");
-    }
-
     const uint8_t *pixelData = NULL;
     gl::Error error = GetUnpackPointer(unpack, pixels, layerOffset, &pixelData);
     if (error.isError())
@@ -333,6 +313,15 @@
 gl::Error TextureD3D::fastUnpackPixels(const gl::PixelUnpackState &unpack, const uint8_t *pixels, const gl::Box &destArea,
                                        GLenum sizedInternalFormat, GLenum type, RenderTargetD3D *destRenderTarget)
 {
+    if (unpack.skipRows != 0 || unpack.skipPixels != 0 || unpack.imageHeight != 0 ||
+        unpack.skipImages != 0)
+    {
+        // TODO(jmadill): additional unpack parameters
+        UNIMPLEMENTED();
+        return gl::Error(GL_INVALID_OPERATION,
+                         "Unimplemented pixel store parameters in fastUnpackPixels");
+    }
+
     // No-op
     if (destArea.width <= 0 && destArea.height <= 0 && destArea.depth <= 0)
     {
@@ -765,12 +754,6 @@
 {
     ASSERT(target == GL_TEXTURE_2D && area.depth == 1 && area.z == 0);
 
-    if (unpack.skipRows != 0 || unpack.skipPixels != 0 || unpack.imageHeight != 0 || unpack.skipImages != 0)
-    {
-        UNIMPLEMENTED();
-        return gl::Error(GL_INVALID_OPERATION, "unimplemented pixel store state");
-    }
-
     GLint level          = static_cast<GLint>(imageLevel);
     gl::ImageIndex index = gl::ImageIndex::Make2D(level);
     if (isFastUnpackable(unpack, getInternalFormat(level)) && isLevelComplete(level))
@@ -2563,7 +2546,8 @@
     redefineImage(level, sizedInternalFormat, size);
 
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(sizedInternalFormat);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(type, size.width, size.height, unpack.alignment, unpack.rowLength);
+    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(
+        type, size.width, size.height, unpack.alignment, unpack.rowLength, unpack.imageHeight);
 
     for (int i = 0; i < size.depth; i++)
     {
@@ -2590,7 +2574,8 @@
     ASSERT(target == GL_TEXTURE_2D_ARRAY);
     GLint level                          = static_cast<GLint>(imageLevel);
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(getInternalFormat(level));
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(type, area.width, area.height, unpack.alignment, unpack.rowLength);
+    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(
+        type, area.width, area.height, unpack.alignment, unpack.rowLength, unpack.imageHeight);
 
     for (int i = 0; i < area.depth; i++)
     {
@@ -2625,7 +2610,8 @@
     redefineImage(level, internalFormat, size);
 
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalFormat);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, size.width, size.height, 1, 0);
+    GLsizei inputDepthPitch =
+        formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, size.width, size.height, 1, 0, 0);
 
     for (int i = 0; i < size.depth; i++)
     {
@@ -2648,7 +2634,8 @@
     ASSERT(target == GL_TEXTURE_2D_ARRAY);
 
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(format);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0);
+    GLsizei inputDepthPitch =
+        formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0, 0);
 
     for (int i = 0; i < area.depth; i++)
     {
diff --git a/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp b/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
index 76bb15c..cedcc08 100644
--- a/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
+++ b/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
@@ -289,7 +289,12 @@
     return gl::Error(GL_NO_ERROR);
 }
 
-gl::Error Framebuffer11::readPixels(const gl::Rectangle &area, GLenum format, GLenum type, size_t outputPitch, const gl::PixelPackState &pack, uint8_t *pixels) const
+gl::Error Framebuffer11::readPixelsImpl(const gl::Rectangle &area,
+                                        GLenum format,
+                                        GLenum type,
+                                        size_t outputPitch,
+                                        const gl::PixelPackState &pack,
+                                        uint8_t *pixels) const
 {
     ID3D11Texture2D *colorBufferTexture = nullptr;
     unsigned int subresourceIndex = 0;
@@ -306,6 +311,13 @@
     gl::Buffer *packBuffer = pack.pixelBuffer.get();
     if (packBuffer != nullptr)
     {
+        if (pack.rowLength != 0 || pack.skipRows != 0 || pack.skipPixels != 0)
+        {
+            UNIMPLEMENTED();
+            return gl::Error(GL_INVALID_OPERATION,
+                             "Unimplemented pixel store parameters in readPixelsImpl");
+        }
+
         Buffer11 *packBufferStorage = GetImplAs<Buffer11>(packBuffer);
         PackPixelsParams packParams(area, format, type, static_cast<GLuint>(outputPitch), pack,
                                     reinterpret_cast<ptrdiff_t>(pixels));
diff --git a/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h b/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
index dfadd58..b4b4e03 100644
--- a/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
+++ b/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
@@ -31,8 +31,12 @@
   private:
     gl::Error clear(const gl::State &state, const ClearParameters &clearParams) override;
 
-    gl::Error readPixels(const gl::Rectangle &area, GLenum format, GLenum type, size_t outputPitch,
-                         const gl::PixelPackState &pack, uint8_t *pixels) const override;
+    gl::Error readPixelsImpl(const gl::Rectangle &area,
+                             GLenum format,
+                             GLenum type,
+                             size_t outputPitch,
+                             const gl::PixelPackState &pack,
+                             uint8_t *pixels) const override;
 
     gl::Error blit(const gl::Rectangle &sourceArea, const gl::Rectangle &destArea, const gl::Rectangle *scissor,
                    bool blitRenderTarget, bool blitDepth, bool blitStencil, GLenum filter,
diff --git a/src/libANGLE/renderer/d3d/d3d11/Image11.cpp b/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
index 0d7ae74..8d5efed 100644
--- a/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
+++ b/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
@@ -247,7 +247,10 @@
 {
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
     GLsizei inputRowPitch = formatInfo.computeRowPitch(type, area.width, unpack.alignment, unpack.rowLength);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(type, area.width, area.height, unpack.alignment, unpack.rowLength);
+    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(
+        type, area.width, area.height, unpack.alignment, unpack.rowLength, unpack.imageHeight);
+    GLsizei inputSkipBytes = formatInfo.computeSkipPixels(
+        inputRowPitch, inputDepthPitch, unpack.skipImages, unpack.skipRows, unpack.skipPixels);
 
     const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mDXGIFormat);
     GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
@@ -264,8 +267,8 @@
 
     uint8_t *offsetMappedData = (reinterpret_cast<uint8_t*>(mappedImage.pData) + (area.y * mappedImage.RowPitch + area.x * outputPixelSize + area.z * mappedImage.DepthPitch));
     loadFunction(area.width, area.height, area.depth,
-                 reinterpret_cast<const uint8_t*>(input), inputRowPitch, inputDepthPitch,
-                 offsetMappedData, mappedImage.RowPitch, mappedImage.DepthPitch);
+                 reinterpret_cast<const uint8_t *>(input) + inputSkipBytes, inputRowPitch,
+                 inputDepthPitch, offsetMappedData, mappedImage.RowPitch, mappedImage.DepthPitch);
 
     unmap();
 
@@ -276,7 +279,8 @@
 {
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
     GLsizei inputRowPitch = formatInfo.computeRowPitch(GL_UNSIGNED_BYTE, area.width, 1, 0);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0);
+    GLsizei inputDepthPitch =
+        formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0, 0);
 
     const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mDXGIFormat);
     GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
diff --git a/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp b/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
index 42b1b3b..3913b59 100644
--- a/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
+++ b/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
@@ -649,7 +649,10 @@
     int height = destBox ? destBox->height : static_cast<int>(image->getHeight());
     int depth = destBox ? destBox->depth : static_cast<int>(image->getDepth());
     UINT srcRowPitch = internalFormatInfo.computeRowPitch(type, width, unpack.alignment, unpack.rowLength);
-    UINT srcDepthPitch = internalFormatInfo.computeDepthPitch(type, width, height, unpack.alignment, unpack.rowLength);
+    UINT srcDepthPitch = internalFormatInfo.computeDepthPitch(type, width, height, unpack.alignment,
+                                                              unpack.rowLength, unpack.imageHeight);
+    GLsizei srcSkipBytes = internalFormatInfo.computeSkipPixels(
+        srcRowPitch, srcDepthPitch, unpack.skipImages, unpack.skipRows, unpack.skipPixels);
 
     const d3d11::TextureFormat &d3d11Format = d3d11::GetTextureFormatInfo(image->getInternalFormat(), mRenderer->getRenderer11DeviceCaps());
     const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(d3d11Format.texFormat);
@@ -669,8 +672,7 @@
 
     // TODO: fast path
     LoadImageFunction loadFunction = d3d11Format.loadFunctions.at(type);
-    loadFunction(width, height, depth,
-                 pixelData, srcRowPitch, srcDepthPitch,
+    loadFunction(width, height, depth, pixelData + srcSkipBytes, srcRowPitch, srcDepthPitch,
                  conversionBuffer->data(), bufferRowPitch, bufferDepthPitch);
 
     ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
diff --git a/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp b/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
index 26b1026..1499bf2 100644
--- a/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
+++ b/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
@@ -1213,6 +1213,8 @@
     extensions->fboRenderMipmap = false;
     extensions->debugMarker = true;
     extensions->eglImage                 = true;
+    extensions->unpackSubimage           = true;
+    extensions->packSubimage             = true;
 
     // D3D11 Feature Level 10_0+ uses SV_IsFrontFace in HLSL to emulate gl_FrontFacing.
     // D3D11 Feature Level 9_3 doesn't support SV_IsFrontFace, and has no equivalent, so can't support gl_FrontFacing.
diff --git a/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.cpp b/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.cpp
index e4dfd41..15e3167 100644
--- a/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.cpp
+++ b/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.cpp
@@ -73,7 +73,12 @@
     return mRenderer->clear(clearParams, colorAttachment, depthStencilAttachment);
 }
 
-gl::Error Framebuffer9::readPixels(const gl::Rectangle &area, GLenum format, GLenum type, size_t outputPitch, const gl::PixelPackState &pack, uint8_t *pixels) const
+gl::Error Framebuffer9::readPixelsImpl(const gl::Rectangle &area,
+                                       GLenum format,
+                                       GLenum type,
+                                       size_t outputPitch,
+                                       const gl::PixelPackState &pack,
+                                       uint8_t *pixels) const
 {
     ASSERT(pack.pixelBuffer.get() == nullptr);
 
diff --git a/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.h b/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.h
index 223259d..88055d3 100644
--- a/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.h
+++ b/src/libANGLE/renderer/d3d/d3d9/Framebuffer9.h
@@ -28,8 +28,12 @@
   private:
     gl::Error clear(const gl::State &state, const ClearParameters &clearParams) override;
 
-    gl::Error readPixels(const gl::Rectangle &area, GLenum format, GLenum type, size_t outputPitch,
-                         const gl::PixelPackState &pack, uint8_t *pixels) const override;
+    gl::Error readPixelsImpl(const gl::Rectangle &area,
+                             GLenum format,
+                             GLenum type,
+                             size_t outputPitch,
+                             const gl::PixelPackState &pack,
+                             uint8_t *pixels) const override;
 
     gl::Error blit(const gl::Rectangle &sourceArea, const gl::Rectangle &destArea, const gl::Rectangle *scissor,
                    bool blitRenderTarget, bool blitDepth, bool blitStencil, GLenum filter,
diff --git a/src/libANGLE/renderer/d3d/d3d9/Image9.cpp b/src/libANGLE/renderer/d3d/d3d9/Image9.cpp
index a64f6ca..df0fae4 100644
--- a/src/libANGLE/renderer/d3d/d3d9/Image9.cpp
+++ b/src/libANGLE/renderer/d3d/d3d9/Image9.cpp
@@ -480,6 +480,8 @@
 
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
     GLsizei inputRowPitch = formatInfo.computeRowPitch(type, area.width, unpack.alignment, unpack.rowLength);
+    GLsizei inputSkipBytes = formatInfo.computeSkipPixels(inputRowPitch, 0, unpack.skipImages,
+                                                          unpack.skipRows, unpack.skipPixels);
 
     const d3d9::TextureFormat &d3dFormatInfo = d3d9::GetTextureFormatInfo(mInternalFormat);
     ASSERT(d3dFormatInfo.loadFunction != NULL);
@@ -498,8 +500,9 @@
     }
 
     d3dFormatInfo.loadFunction(area.width, area.height, area.depth,
-                               reinterpret_cast<const uint8_t*>(input), inputRowPitch, 0,
-                               reinterpret_cast<uint8_t*>(locked.pBits), locked.Pitch, 0);
+                               reinterpret_cast<const uint8_t *>(input) + inputSkipBytes,
+                               inputRowPitch, 0, reinterpret_cast<uint8_t *>(locked.pBits),
+                               locked.Pitch, 0);
 
     unlock();
 
@@ -513,7 +516,8 @@
 
     const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
     GLsizei inputRowPitch = formatInfo.computeRowPitch(GL_UNSIGNED_BYTE, area.width, 1, 0);
-    GLsizei inputDepthPitch = formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0);
+    GLsizei inputDepthPitch =
+        formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0, 0);
 
     const d3d9::TextureFormat &d3d9FormatInfo = d3d9::GetTextureFormatInfo(mInternalFormat);
 
diff --git a/src/libANGLE/renderer/d3d/d3d9/renderer9_utils.cpp b/src/libANGLE/renderer/d3d/d3d9/renderer9_utils.cpp
index afa0181..ed9c146 100644
--- a/src/libANGLE/renderer/d3d/d3d9/renderer9_utils.cpp
+++ b/src/libANGLE/renderer/d3d/d3d9/renderer9_utils.cpp
@@ -574,6 +574,8 @@
     extensions->colorBufferFloat = false;
     extensions->debugMarker = true;
     extensions->eglImage               = true;
+    extensions->unpackSubimage         = true;
+    extensions->packSubimage           = true;
 
     // D3D9 has no concept of separate masks and refs for front and back faces in the depth stencil
     // state.
diff --git a/src/libANGLE/renderer/gl/StateManagerGL.cpp b/src/libANGLE/renderer/gl/StateManagerGL.cpp
index 12db094..1519472 100644
--- a/src/libANGLE/renderer/gl/StateManagerGL.cpp
+++ b/src/libANGLE/renderer/gl/StateManagerGL.cpp
@@ -1353,6 +1353,22 @@
                 // TODO(jmadill): split this
                 setPixelUnpackState(state.getUnpackState());
                 break;
+            case gl::State::DIRTY_BIT_UNPACK_IMAGE_HEIGHT:
+                // TODO(jmadill): split this
+                setPixelUnpackState(state.getUnpackState());
+                break;
+            case gl::State::DIRTY_BIT_UNPACK_SKIP_IMAGES:
+                // TODO(jmadill): split this
+                setPixelUnpackState(state.getUnpackState());
+                break;
+            case gl::State::DIRTY_BIT_UNPACK_SKIP_ROWS:
+                // TODO(jmadill): split this
+                setPixelUnpackState(state.getUnpackState());
+                break;
+            case gl::State::DIRTY_BIT_UNPACK_SKIP_PIXELS:
+                // TODO(jmadill): split this
+                setPixelUnpackState(state.getUnpackState());
+                break;
             case gl::State::DIRTY_BIT_PACK_ALIGNMENT:
                 // TODO(jmadill): split this
                 setPixelPackState(state.getPackState());
@@ -1361,6 +1377,18 @@
                 // TODO(jmadill): split this
                 setPixelPackState(state.getPackState());
                 break;
+            case gl::State::DIRTY_BIT_PACK_ROW_LENGTH:
+                // TODO(jmadill): split this
+                setPixelPackState(state.getPackState());
+                break;
+            case gl::State::DIRTY_BIT_PACK_SKIP_ROWS:
+                // TODO(jmadill): split this
+                setPixelPackState(state.getPackState());
+                break;
+            case gl::State::DIRTY_BIT_PACK_SKIP_PIXELS:
+                // TODO(jmadill): split this
+                setPixelPackState(state.getPackState());
+                break;
             case gl::State::DIRTY_BIT_DITHER_ENABLED:
                 // TODO(jmadill): implement this
                 break;
diff --git a/src/libANGLE/validationES.cpp b/src/libANGLE/validationES.cpp
index d233931..ee096ce 100644
--- a/src/libANGLE/validationES.cpp
+++ b/src/libANGLE/validationES.cpp
@@ -1057,7 +1057,9 @@
     GLenum sizedInternalFormat = GetSizedInternalFormat(format, type);
     const InternalFormat &sizedFormatInfo = GetInternalFormatInfo(sizedInternalFormat);
 
-    GLsizei outputPitch = sizedFormatInfo.computeRowPitch(type, width, context->getState().getPackAlignment(), 0);
+    GLsizei outputPitch =
+        sizedFormatInfo.computeRowPitch(type, width, context->getState().getPackAlignment(),
+                                        context->getState().getPackRowLength());
     // sized query sanity check
     if (bufSize)
     {
diff --git a/src/libGLESv2/entry_points_gles_2_0.cpp b/src/libGLESv2/entry_points_gles_2_0.cpp
index f9c661d..2c524a1 100644
--- a/src/libGLESv2/entry_points_gles_2_0.cpp
+++ b/src/libGLESv2/entry_points_gles_2_0.cpp
@@ -3148,37 +3148,37 @@
 
           case GL_UNPACK_IMAGE_HEIGHT:
             ASSERT(context->getClientVersion() >= 3);
-            state.getUnpackState().imageHeight = param;
+            state.setUnpackImageHeight(param);
             break;
 
           case GL_UNPACK_SKIP_IMAGES:
-            ASSERT(context->getClientVersion() >= 3);
-            state.getUnpackState().skipImages = param;
+              ASSERT(context->getClientVersion() >= 3);
+              state.setUnpackSkipImages(param);
             break;
 
           case GL_UNPACK_SKIP_ROWS:
               ASSERT((context->getClientVersion() >= 3) || context->getExtensions().unpackSubimage);
-            state.getUnpackState().skipRows = param;
+              state.setUnpackSkipRows(param);
             break;
 
           case GL_UNPACK_SKIP_PIXELS:
               ASSERT((context->getClientVersion() >= 3) || context->getExtensions().unpackSubimage);
-            state.getUnpackState().skipPixels = param;
+              state.setUnpackSkipPixels(param);
             break;
 
           case GL_PACK_ROW_LENGTH:
               ASSERT((context->getClientVersion() >= 3) || context->getExtensions().packSubimage);
-            state.getPackState().rowLength = param;
+              state.setPackRowLength(param);
             break;
 
           case GL_PACK_SKIP_ROWS:
               ASSERT((context->getClientVersion() >= 3) || context->getExtensions().packSubimage);
-            state.getPackState().skipRows = param;
+              state.setPackSkipRows(param);
             break;
 
           case GL_PACK_SKIP_PIXELS:
               ASSERT((context->getClientVersion() >= 3) || context->getExtensions().packSubimage);
-            state.getPackState().skipPixels = param;
+              state.setPackSkipPixels(param);
             break;
 
           default:
diff --git a/src/tests/deqp_support/deqp_gles3_test_expectations.txt b/src/tests/deqp_support/deqp_gles3_test_expectations.txt
index f0f839b..0955502 100644
--- a/src/tests/deqp_support/deqp_gles3_test_expectations.txt
+++ b/src/tests/deqp_support/deqp_gles3_test_expectations.txt
@@ -325,11 +325,6 @@
 1095 WIN : dEQP-GLES3.functional.texture.specification.random_teximage2d.cube_0 = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.random_teximage2d.cube_3 = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.random_teximage2d.cube_7 = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_unpack_params.* = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_pbo.rgb8_skip_rows_2d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_pbo.rgb8_skip_rows_cube = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_pbo.rgb8_skip_pixels_2d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_pbo.rgb8_skip_pixels_cube = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_depth.depth_component32f = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_depth.depth32f_stencil8 = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage2d_depth_pbo.depth_component32f = FAIL
@@ -360,11 +355,6 @@
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_texsubimage2d.r16ui_cube = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_texsubimage2d.r8i_cube = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_texsubimage2d.r8ui_cube = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_unpack_params.* = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_pbo.rgb8_skip_rows_2d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_pbo.rgb8_skip_rows_cube = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_pbo.rgb8_skip_pixels_2d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_pbo.rgb8_skip_pixels_cube = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_depth.depth_component32f = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage2d_depth.depth32f_stencil8 = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_copyteximage2d.cube_luminance = FAIL
@@ -380,28 +370,10 @@
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_copytexsubimage2d.cube_luminance_alpha = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_copytexsubimage2d.cube_rgb = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.basic_copytexsubimage2d.cube_rgba = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_unpack_params.* = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_image_height_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_image_height_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_images_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_images_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_rows_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_rows_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_pixels_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_pbo.rgb8_skip_pixels_3d = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_depth.depth_component32f_2d_array = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_depth.depth32f_stencil8_2d_array = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_depth_pbo.depth_component32f_2d_array = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.teximage3d_depth_pbo.depth32f_stencil8_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_unpack_params.* = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_image_height_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_image_height_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_images_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_images_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_rows_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_rows_3d = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_pixels_2d_array = FAIL
-1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_pbo.rgb8_skip_pixels_3d = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_depth.depth_component32f_2d_array = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.texsubimage3d_depth.depth32f_stencil8_2d_array = FAIL
 1095 WIN : dEQP-GLES3.functional.texture.specification.texstorage2d.format.rgba32i_cube = FAIL
@@ -1124,34 +1096,10 @@
 1101 WIN : dEQP-GLES3.functional.negative_api.state.get_framebuffer_attachment_parameteriv = FAIL
 1101 WIN : dEQP-GLES3.functional.negative_api.state.is_transform_feedback = FAIL
 1101 WIN : dEQP-GLES3.functional.negative_api.state.is_vertex_array = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_ubyte_17 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_ubyte_19 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_ubyte_23 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_ubyte_29 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_int_17 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_int_19 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_int_23 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_int_29 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_uint_17 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_uint_19 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_uint_23 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.rgba_uint_29 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.choose_17 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.choose_19 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.choose_23 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.rowlength.choose_29 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_ubyte_0_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_ubyte_3_0 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_ubyte_3_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_ubyte_3_5 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_int_0_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_int_3_0 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_int_3_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_int_3_5 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_uint_0_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_uint_3_0 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_uint_3_3 = FAIL
-1101 WIN : dEQP-GLES3.functional.read_pixels.skip.rgba_uint_3_5 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.skip.choose_0_3 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.skip.choose_3_0 = FAIL
 1101 WIN : dEQP-GLES3.functional.read_pixels.skip.choose_3_3 = FAIL
@@ -1166,38 +1114,6 @@
 1101 WIN : dEQP-GLES3.functional.state_query.boolean.rasterizer_discard_getfloat = FAIL
 1101 WIN : dEQP-GLES3.functional.state_query.integers.max_fragment_uniform_components_getinteger64 = FAIL
 1101 WIN : dEQP-GLES3.functional.state_query.integers.max_fragment_uniform_components_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_image_height_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_image_height_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_image_height_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_image_height_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_images_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_images_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_images_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_images_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_row_length_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_row_length_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_row_length_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_row_length_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_rows_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_rows_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_rows_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_rows_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_pixels_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_pixels_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_pixels_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.unpack_skip_pixels_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_row_length_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_row_length_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_row_length_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_row_length_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_rows_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_rows_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_rows_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_rows_getfloat = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_pixels_getboolean = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_pixels_getinteger = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_pixels_getinteger64 = FAIL
-1101 WIN : dEQP-GLES3.functional.state_query.integers.pack_skip_pixels_getfloat = FAIL
 1101 WIN : dEQP-GLES3.functional.state_query.integers.compressed_texture_formats_getinteger = FAIL
 1101 WIN : dEQP-GLES3.functional.state_query.integers.compressed_texture_formats_getinteger64 = FAIL
 1101 WIN : dEQP-GLES3.functional.state_query.integers.compressed_texture_formats_getfloat = FAIL