xref: /aosp_15_r20/external/deqp/framework/common/tcuTexVerifierUtil.cpp (revision 35238bce31c2a825756842865a792f8cf7f89930)
1*35238bceSAndroid Build Coastguard Worker /*-------------------------------------------------------------------------
2*35238bceSAndroid Build Coastguard Worker  * drawElements Quality Program Tester Core
3*35238bceSAndroid Build Coastguard Worker  * ----------------------------------------
4*35238bceSAndroid Build Coastguard Worker  *
5*35238bceSAndroid Build Coastguard Worker  * Copyright 2014 The Android Open Source Project
6*35238bceSAndroid Build Coastguard Worker  *
7*35238bceSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
8*35238bceSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
9*35238bceSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
10*35238bceSAndroid Build Coastguard Worker  *
11*35238bceSAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
12*35238bceSAndroid Build Coastguard Worker  *
13*35238bceSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
14*35238bceSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
15*35238bceSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16*35238bceSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
17*35238bceSAndroid Build Coastguard Worker  * limitations under the License.
18*35238bceSAndroid Build Coastguard Worker  *
19*35238bceSAndroid Build Coastguard Worker  *//*!
20*35238bceSAndroid Build Coastguard Worker  * \file
21*35238bceSAndroid Build Coastguard Worker  * \brief Internal utilities shared between TexLookup and TexCompare verifiers.
22*35238bceSAndroid Build Coastguard Worker  *//*--------------------------------------------------------------------*/
23*35238bceSAndroid Build Coastguard Worker 
24*35238bceSAndroid Build Coastguard Worker #include "tcuTexVerifierUtil.hpp"
25*35238bceSAndroid Build Coastguard Worker #include "tcuFloat.hpp"
26*35238bceSAndroid Build Coastguard Worker 
27*35238bceSAndroid Build Coastguard Worker namespace tcu
28*35238bceSAndroid Build Coastguard Worker {
29*35238bceSAndroid Build Coastguard Worker namespace TexVerifierUtil
30*35238bceSAndroid Build Coastguard Worker {
31*35238bceSAndroid Build Coastguard Worker 
computeFloatingPointError(const float value,const int numAccurateBits)32*35238bceSAndroid Build Coastguard Worker float computeFloatingPointError(const float value, const int numAccurateBits)
33*35238bceSAndroid Build Coastguard Worker {
34*35238bceSAndroid Build Coastguard Worker     DE_ASSERT(numAccurateBits >= 0);
35*35238bceSAndroid Build Coastguard Worker     DE_ASSERT(numAccurateBits <= 23);
36*35238bceSAndroid Build Coastguard Worker 
37*35238bceSAndroid Build Coastguard Worker     const int numGarbageBits = 23 - numAccurateBits;
38*35238bceSAndroid Build Coastguard Worker     const uint32_t mask      = (1u << numGarbageBits) - 1u;
39*35238bceSAndroid Build Coastguard Worker     const int exp            = tcu::Float32(value).exponent();
40*35238bceSAndroid Build Coastguard Worker 
41*35238bceSAndroid Build Coastguard Worker     return Float32::construct(+1, exp, (1u << 23) | mask).asFloat() - Float32::construct(+1, exp, 1u << 23).asFloat();
42*35238bceSAndroid Build Coastguard Worker }
43*35238bceSAndroid Build Coastguard Worker 
computeFixedPointError(const int numAccurateBits)44*35238bceSAndroid Build Coastguard Worker float computeFixedPointError(const int numAccurateBits)
45*35238bceSAndroid Build Coastguard Worker {
46*35238bceSAndroid Build Coastguard Worker     return computeFloatingPointError(1.0f, numAccurateBits);
47*35238bceSAndroid Build Coastguard Worker }
48*35238bceSAndroid Build Coastguard Worker 
computeColorBitsError(const int bits,const int numAccurateBits)49*35238bceSAndroid Build Coastguard Worker float computeColorBitsError(const int bits, const int numAccurateBits)
50*35238bceSAndroid Build Coastguard Worker {
51*35238bceSAndroid Build Coastguard Worker     // Color bits error is not a generic function, it just for compute the error value that cannot be accurately shown in integer data format.
52*35238bceSAndroid Build Coastguard Worker     //
53*35238bceSAndroid Build Coastguard Worker     //        "bits" is color bit width, "numAccurateBits" is the number of accurate bits in color bits, "1 << (bits - numAccurateBits)" is the threshold in integer.
54*35238bceSAndroid Build Coastguard Worker     //        "1.0f / 256.0f" is epsilon value, to make sure the threshold use to calculate in float can be a little bigger than the real value.
55*35238bceSAndroid Build Coastguard Worker     return (float(1 << (bits - numAccurateBits)) + 1.0f / 256.0f) / float((1 << bits) - 1);
56*35238bceSAndroid Build Coastguard Worker }
57*35238bceSAndroid Build Coastguard Worker 
computeNonNormalizedCoordBounds(const bool normalizedCoords,const int dim,const float coord,const int coordBits,const int uvBits)58*35238bceSAndroid Build Coastguard Worker Vec2 computeNonNormalizedCoordBounds(const bool normalizedCoords, const int dim, const float coord, const int coordBits,
59*35238bceSAndroid Build Coastguard Worker                                      const int uvBits)
60*35238bceSAndroid Build Coastguard Worker {
61*35238bceSAndroid Build Coastguard Worker     const float coordErr = computeFloatingPointError(coord, coordBits);
62*35238bceSAndroid Build Coastguard Worker     const float minN     = coord - coordErr;
63*35238bceSAndroid Build Coastguard Worker     const float maxN     = coord + coordErr;
64*35238bceSAndroid Build Coastguard Worker     const float minA     = normalizedCoords ? minN * float(dim) : minN;
65*35238bceSAndroid Build Coastguard Worker     const float maxA     = normalizedCoords ? maxN * float(dim) : maxN;
66*35238bceSAndroid Build Coastguard Worker     const float minC     = minA - computeFixedPointError(uvBits);
67*35238bceSAndroid Build Coastguard Worker     const float maxC     = maxA + computeFixedPointError(uvBits);
68*35238bceSAndroid Build Coastguard Worker 
69*35238bceSAndroid Build Coastguard Worker     DE_ASSERT(minC <= maxC);
70*35238bceSAndroid Build Coastguard Worker 
71*35238bceSAndroid Build Coastguard Worker     return Vec2(minC, maxC);
72*35238bceSAndroid Build Coastguard Worker }
73*35238bceSAndroid Build Coastguard Worker 
getPossibleCubeFaces(const Vec3 & coord,const IVec3 & bits,CubeFace * faces,int & numFaces)74*35238bceSAndroid Build Coastguard Worker void getPossibleCubeFaces(const Vec3 &coord, const IVec3 &bits, CubeFace *faces, int &numFaces)
75*35238bceSAndroid Build Coastguard Worker {
76*35238bceSAndroid Build Coastguard Worker     const float x  = coord.x();
77*35238bceSAndroid Build Coastguard Worker     const float y  = coord.y();
78*35238bceSAndroid Build Coastguard Worker     const float z  = coord.z();
79*35238bceSAndroid Build Coastguard Worker     const float ax = de::abs(x);
80*35238bceSAndroid Build Coastguard Worker     const float ay = de::abs(y);
81*35238bceSAndroid Build Coastguard Worker     const float az = de::abs(z);
82*35238bceSAndroid Build Coastguard Worker     const float ex = computeFloatingPointError(x, bits.x());
83*35238bceSAndroid Build Coastguard Worker     const float ey = computeFloatingPointError(y, bits.y());
84*35238bceSAndroid Build Coastguard Worker     const float ez = computeFloatingPointError(z, bits.z());
85*35238bceSAndroid Build Coastguard Worker 
86*35238bceSAndroid Build Coastguard Worker     numFaces = 0;
87*35238bceSAndroid Build Coastguard Worker 
88*35238bceSAndroid Build Coastguard Worker     if (ay + ey < ax - ex && az + ez < ax - ex)
89*35238bceSAndroid Build Coastguard Worker     {
90*35238bceSAndroid Build Coastguard Worker         if (x >= ex)
91*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_X;
92*35238bceSAndroid Build Coastguard Worker         if (x <= ex)
93*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_X;
94*35238bceSAndroid Build Coastguard Worker     }
95*35238bceSAndroid Build Coastguard Worker     else if (ax + ex < ay - ey && az + ez < ay - ey)
96*35238bceSAndroid Build Coastguard Worker     {
97*35238bceSAndroid Build Coastguard Worker         if (y >= ey)
98*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_Y;
99*35238bceSAndroid Build Coastguard Worker         if (y <= ey)
100*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_Y;
101*35238bceSAndroid Build Coastguard Worker     }
102*35238bceSAndroid Build Coastguard Worker     else if (ax + ex < az - ez && ay + ey < az - ez)
103*35238bceSAndroid Build Coastguard Worker     {
104*35238bceSAndroid Build Coastguard Worker         if (z >= ez)
105*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_Z;
106*35238bceSAndroid Build Coastguard Worker         if (z <= ez)
107*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_Z;
108*35238bceSAndroid Build Coastguard Worker     }
109*35238bceSAndroid Build Coastguard Worker     else
110*35238bceSAndroid Build Coastguard Worker     {
111*35238bceSAndroid Build Coastguard Worker         // One or more components are equal (or within error bounds). Allow all faces where major axis is not zero.
112*35238bceSAndroid Build Coastguard Worker         if (ax > ex)
113*35238bceSAndroid Build Coastguard Worker         {
114*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_X;
115*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_X;
116*35238bceSAndroid Build Coastguard Worker         }
117*35238bceSAndroid Build Coastguard Worker 
118*35238bceSAndroid Build Coastguard Worker         if (ay > ey)
119*35238bceSAndroid Build Coastguard Worker         {
120*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_Y;
121*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_Y;
122*35238bceSAndroid Build Coastguard Worker         }
123*35238bceSAndroid Build Coastguard Worker 
124*35238bceSAndroid Build Coastguard Worker         if (az > ez)
125*35238bceSAndroid Build Coastguard Worker         {
126*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_NEGATIVE_Z;
127*35238bceSAndroid Build Coastguard Worker             faces[numFaces++] = CUBEFACE_POSITIVE_Z;
128*35238bceSAndroid Build Coastguard Worker         }
129*35238bceSAndroid Build Coastguard Worker     }
130*35238bceSAndroid Build Coastguard Worker }
131*35238bceSAndroid Build Coastguard Worker 
getUnnormalizedCoordSampler(const Sampler & sampler)132*35238bceSAndroid Build Coastguard Worker Sampler getUnnormalizedCoordSampler(const Sampler &sampler)
133*35238bceSAndroid Build Coastguard Worker {
134*35238bceSAndroid Build Coastguard Worker     Sampler copy          = sampler;
135*35238bceSAndroid Build Coastguard Worker     copy.normalizedCoords = false;
136*35238bceSAndroid Build Coastguard Worker     return copy;
137*35238bceSAndroid Build Coastguard Worker }
138*35238bceSAndroid Build Coastguard Worker 
imod(int a,int b)139*35238bceSAndroid Build Coastguard Worker static inline int imod(int a, int b)
140*35238bceSAndroid Build Coastguard Worker {
141*35238bceSAndroid Build Coastguard Worker     int m = a % b;
142*35238bceSAndroid Build Coastguard Worker     return m < 0 ? m + b : m;
143*35238bceSAndroid Build Coastguard Worker }
144*35238bceSAndroid Build Coastguard Worker 
mirror(int a)145*35238bceSAndroid Build Coastguard Worker static inline int mirror(int a)
146*35238bceSAndroid Build Coastguard Worker {
147*35238bceSAndroid Build Coastguard Worker     return a >= 0 ? a : -(1 + a);
148*35238bceSAndroid Build Coastguard Worker }
149*35238bceSAndroid Build Coastguard Worker 
wrap(Sampler::WrapMode mode,int c,int size)150*35238bceSAndroid Build Coastguard Worker int wrap(Sampler::WrapMode mode, int c, int size)
151*35238bceSAndroid Build Coastguard Worker {
152*35238bceSAndroid Build Coastguard Worker     switch (mode)
153*35238bceSAndroid Build Coastguard Worker     {
154*35238bceSAndroid Build Coastguard Worker     // \note CL and GL modes are handled identically here, as verification process accounts for
155*35238bceSAndroid Build Coastguard Worker     //         accuracy differences caused by different methods (wrapping vs. denormalizing first).
156*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::CLAMP_TO_BORDER:
157*35238bceSAndroid Build Coastguard Worker         return deClamp32(c, -1, size);
158*35238bceSAndroid Build Coastguard Worker 
159*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::CLAMP_TO_EDGE:
160*35238bceSAndroid Build Coastguard Worker         return deClamp32(c, 0, size - 1);
161*35238bceSAndroid Build Coastguard Worker 
162*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::REPEAT_GL:
163*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::REPEAT_CL:
164*35238bceSAndroid Build Coastguard Worker         return imod(c, size);
165*35238bceSAndroid Build Coastguard Worker 
166*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::MIRRORED_ONCE:
167*35238bceSAndroid Build Coastguard Worker         c = deClamp32(c, -size, size);
168*35238bceSAndroid Build Coastguard Worker         // Fall-through
169*35238bceSAndroid Build Coastguard Worker 
170*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::MIRRORED_REPEAT_GL:
171*35238bceSAndroid Build Coastguard Worker     case tcu::Sampler::MIRRORED_REPEAT_CL:
172*35238bceSAndroid Build Coastguard Worker         return (size - 1) - mirror(imod(c, 2 * size) - size);
173*35238bceSAndroid Build Coastguard Worker 
174*35238bceSAndroid Build Coastguard Worker     default:
175*35238bceSAndroid Build Coastguard Worker         DE_ASSERT(false);
176*35238bceSAndroid Build Coastguard Worker         return 0;
177*35238bceSAndroid Build Coastguard Worker     }
178*35238bceSAndroid Build Coastguard Worker }
179*35238bceSAndroid Build Coastguard Worker } // namespace TexVerifierUtil
180*35238bceSAndroid Build Coastguard Worker } // namespace tcu
181