Fix signed integer overflow in vertex array tests
authorAri Suonpaa <ari.suonpaa@siru.fi>
Wed, 1 Dec 2021 07:27:16 +0000 (09:27 +0200)
committerMatthew Netsch <quic_mnetsch@quicinc.com>
Thu, 2 Dec 2021 20:58:48 +0000 (20:58 +0000)
Random quad calculation in some of the vertex array tests were
calculating ranges for allowed quad sizes using signed integers,
and there was a chance for an overflow, which is undefined behavior.

Now the quad calculation randomizes only coordinates instead of
coordinates and the quad size. This lets us avoid the calculation
of the range.

Some bug fixes to the quad randomization code were also added.

VK-GL-CTS Issue: 3357

Affects:

dEQP-GLES3.functional.vertex_arrays.*

Components: OpenGL ES
Change-Id: I651ac6cef94e15d3fc0bc322ea8d65cbd96a4c2d

modules/glshared/glsVertexArrayTests.cpp

index a9f6471..8cff9f5 100644 (file)
@@ -377,69 +377,6 @@ inline GLValue::Double minValue (void)
 }
 
 template<class T>
-inline T abs (T val);
-
-template<>
-inline GLValue::Fixed abs (GLValue::Fixed val)
-{
-       return GLValue::Fixed::create(0x7FFFu & val.getValue());
-}
-
-template<>
-inline GLValue::Ubyte abs (GLValue::Ubyte val)
-{
-       return val;
-}
-
-template<>
-inline GLValue::Byte abs (GLValue::Byte val)
-{
-       return GLValue::Byte::create(0x7Fu & val.getValue());
-}
-
-template<>
-inline GLValue::Ushort abs (GLValue::Ushort val)
-{
-       return val;
-}
-
-template<>
-inline GLValue::Short abs (GLValue::Short val)
-{
-       return GLValue::Short::create(0x7FFFu & val.getValue());
-}
-
-template<>
-inline GLValue::Float abs (GLValue::Float val)
-{
-       return GLValue::Float::create(std::fabs(val.to<float>()));
-}
-
-template<>
-inline GLValue::Uint abs (GLValue::Uint val)
-{
-       return val;
-}
-
-template<>
-inline GLValue::Int abs (GLValue::Int val)
-{
-       return GLValue::Int::create(0x7FFFFFFFu & val.getValue());
-}
-
-template<>
-inline GLValue::Half abs (GLValue::Half val)
-{
-       return GLValue::Half::create(std::fabs(val.to<float>()));
-}
-
-template<>
-inline GLValue::Double abs (GLValue::Double val)
-{
-       return GLValue::Double::create(std::fabs(val.to<float>()));
-}
-
-template<class T>
 static inline void alignmentSafeAssignment (char* dst, T val)
 {
        std::memcpy(dst, &val, sizeof(T));
@@ -1597,11 +1534,11 @@ char* RandomArrayGenerator::createQuads (int seed, int count, int componentCount
                                // attempt to find a good (i.e not extremely small) quad
                                for (int attemptNdx = 0; attemptNdx < 4; ++attemptNdx)
                                {
-                                       x1 = roundTo(minDiff, getRandom<T>(rnd, min, max));
-                                       x2 = roundTo(minDiff, getRandom<T>(rnd, minDiff, abs<T>(max - x1)));
+                                       x1 = roundTo(minDiff, getRandom<T>(rnd, min, max - minDiff));
+                                       x2 = roundTo(minDiff, getRandom<T>(rnd, x1 + minDiff, max));
 
-                                       y1 = roundTo(minDiff, getRandom<T>(rnd, min, max));
-                                       y2 = roundTo(minDiff, getRandom<T>(rnd, minDiff, abs<T>(max - y1)));
+                                       y1 = roundTo(minDiff, getRandom<T>(rnd, min, max - minDiff));
+                                       y2 = roundTo(minDiff, getRandom<T>(rnd, y1 + minDiff, max));
 
                                        z = (componentCount > 2) ? roundTo(minDiff, (getRandom<T>(rnd, min, max))) : (T::create(0));
                                        w = (componentCount > 3) ? roundTo(minDiff, (getRandom<T>(rnd, min, max))) : (T::create(1));
@@ -1611,9 +1548,12 @@ char* RandomArrayGenerator::createQuads (int seed, int count, int componentCount
                                                break;
 
                                        // The result quad is too thin?
-                                       if ((deFloatAbs(x2.template to<float>() + z.template to<float>()) < minDiff.template to<float>()) ||
-                                               (deFloatAbs(y2.template to<float>() + w.template to<float>()) < minDiff.template to<float>()))
+                                       if ((deFloatAbs(x2.template to<float>() - x1.template to<float>()) < minDiff.template to<float>()) ||
+                                               (deFloatAbs(y2.template to<float>() - y1.template to<float>()) < minDiff.template to<float>()))
+                                       {
+                                               DE_ASSERT(attemptNdx < 3);
                                                continue;
+                                       }
 
                                        // all ok
                                        break;
@@ -1622,20 +1562,20 @@ char* RandomArrayGenerator::createQuads (int seed, int count, int componentCount
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride]), x1);
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + componentStride]), y1);
 
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride]), x1 + x2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride]), x2);
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride + componentStride]), y1);
 
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 2]), x1);
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 2 + componentStride]), y1 + y2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 2 + componentStride]), y2);
 
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 3]), x1);
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 3 + componentStride]), y1 + y2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 3 + componentStride]), y2);
 
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 4]), x1 + x2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 4]), x2);
                                alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 4 + componentStride]), y1);
 
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 5]), x1 + x2);
-                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 5 + componentStride]), y1 + y2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 5]), x2);
+                               alignmentSafeAssignment<T>(&(resultData[quadNdx * quadStride + stride * 5 + componentStride]), y2);
 
                                if (componentCount > 2)
                                {