xref: /aosp_15_r20/external/deqp/external/vulkancts/modules/vulkan/pipeline/vktPipelineReferenceRenderer.cpp (revision 35238bce31c2a825756842865a792f8cf7f89930)
1 /*------------------------------------------------------------------------
2  * Vulkan Conformance Tests
3  * ------------------------
4  *
5  * Copyright (c) 2015 The Khronos Group Inc.
6  * Copyright (c) 2015 Imagination Technologies Ltd.
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *      http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  *//*!
21  * \file
22  * \brief Reference renderer.
23  *//*--------------------------------------------------------------------*/
24 
25 #include "vktPipelineReferenceRenderer.hpp"
26 #include "vktPipelineClearUtil.hpp"
27 #include "rrShadingContext.hpp"
28 #include "rrVertexAttrib.hpp"
29 
30 namespace vkt
31 {
32 namespace pipeline
33 {
34 
35 using namespace vk;
36 
mapVkBlendFactor(VkBlendFactor blend)37 rr::BlendFunc mapVkBlendFactor(VkBlendFactor blend)
38 {
39     switch (blend)
40     {
41     case VK_BLEND_FACTOR_ZERO:
42         return rr::BLENDFUNC_ZERO;
43     case VK_BLEND_FACTOR_ONE:
44         return rr::BLENDFUNC_ONE;
45     case VK_BLEND_FACTOR_SRC_COLOR:
46         return rr::BLENDFUNC_SRC_COLOR;
47     case VK_BLEND_FACTOR_ONE_MINUS_SRC_COLOR:
48         return rr::BLENDFUNC_ONE_MINUS_SRC_COLOR;
49     case VK_BLEND_FACTOR_DST_COLOR:
50         return rr::BLENDFUNC_DST_COLOR;
51     case VK_BLEND_FACTOR_ONE_MINUS_DST_COLOR:
52         return rr::BLENDFUNC_ONE_MINUS_DST_COLOR;
53     case VK_BLEND_FACTOR_SRC_ALPHA:
54         return rr::BLENDFUNC_SRC_ALPHA;
55     case VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA:
56         return rr::BLENDFUNC_ONE_MINUS_SRC_ALPHA;
57     case VK_BLEND_FACTOR_DST_ALPHA:
58         return rr::BLENDFUNC_DST_ALPHA;
59     case VK_BLEND_FACTOR_ONE_MINUS_DST_ALPHA:
60         return rr::BLENDFUNC_ONE_MINUS_DST_ALPHA;
61     case VK_BLEND_FACTOR_CONSTANT_COLOR:
62         return rr::BLENDFUNC_CONSTANT_COLOR;
63     case VK_BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR:
64         return rr::BLENDFUNC_ONE_MINUS_CONSTANT_COLOR;
65     case VK_BLEND_FACTOR_CONSTANT_ALPHA:
66         return rr::BLENDFUNC_CONSTANT_ALPHA;
67     case VK_BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA:
68         return rr::BLENDFUNC_ONE_MINUS_CONSTANT_ALPHA;
69     case VK_BLEND_FACTOR_SRC_ALPHA_SATURATE:
70         return rr::BLENDFUNC_SRC_ALPHA_SATURATE;
71     case VK_BLEND_FACTOR_SRC1_COLOR:
72         return rr::BLENDFUNC_SRC1_COLOR;
73     case VK_BLEND_FACTOR_ONE_MINUS_SRC1_COLOR:
74         return rr::BLENDFUNC_ONE_MINUS_SRC1_COLOR;
75     case VK_BLEND_FACTOR_SRC1_ALPHA:
76         return rr::BLENDFUNC_SRC1_ALPHA;
77     case VK_BLEND_FACTOR_ONE_MINUS_SRC1_ALPHA:
78         return rr::BLENDFUNC_ONE_MINUS_SRC1_ALPHA;
79     default:
80         DE_ASSERT(false);
81     }
82     return rr::BLENDFUNC_LAST;
83 }
84 
mapVkBlendOp(VkBlendOp blendOp)85 rr::BlendEquation mapVkBlendOp(VkBlendOp blendOp)
86 {
87     switch (blendOp)
88     {
89     case VK_BLEND_OP_ADD:
90         return rr::BLENDEQUATION_ADD;
91     case VK_BLEND_OP_SUBTRACT:
92         return rr::BLENDEQUATION_SUBTRACT;
93     case VK_BLEND_OP_REVERSE_SUBTRACT:
94         return rr::BLENDEQUATION_REVERSE_SUBTRACT;
95     case VK_BLEND_OP_MIN:
96         return rr::BLENDEQUATION_MIN;
97     case VK_BLEND_OP_MAX:
98         return rr::BLENDEQUATION_MAX;
99     default:
100         DE_ASSERT(false);
101     }
102     return rr::BLENDEQUATION_LAST;
103 }
104 
mapVkColorComponentFlags(VkColorComponentFlags flags)105 tcu::BVec4 mapVkColorComponentFlags(VkColorComponentFlags flags)
106 {
107     return tcu::BVec4((flags & VK_COLOR_COMPONENT_R_BIT) != 0, (flags & VK_COLOR_COMPONENT_G_BIT) != 0,
108                       (flags & VK_COLOR_COMPONENT_B_BIT) != 0, (flags & VK_COLOR_COMPONENT_A_BIT) != 0);
109 }
110 
mapVkCompareOp(VkCompareOp compareFunc)111 rr::TestFunc mapVkCompareOp(VkCompareOp compareFunc)
112 {
113     switch (compareFunc)
114     {
115     case VK_COMPARE_OP_NEVER:
116         return rr::TESTFUNC_NEVER;
117     case VK_COMPARE_OP_LESS:
118         return rr::TESTFUNC_LESS;
119     case VK_COMPARE_OP_EQUAL:
120         return rr::TESTFUNC_EQUAL;
121     case VK_COMPARE_OP_LESS_OR_EQUAL:
122         return rr::TESTFUNC_LEQUAL;
123     case VK_COMPARE_OP_GREATER:
124         return rr::TESTFUNC_GREATER;
125     case VK_COMPARE_OP_NOT_EQUAL:
126         return rr::TESTFUNC_NOTEQUAL;
127     case VK_COMPARE_OP_GREATER_OR_EQUAL:
128         return rr::TESTFUNC_GEQUAL;
129     case VK_COMPARE_OP_ALWAYS:
130         return rr::TESTFUNC_ALWAYS;
131     default:
132         DE_ASSERT(false);
133     }
134     return rr::TESTFUNC_LAST;
135 }
136 
mapVkPrimitiveTopology(VkPrimitiveTopology primitiveTopology)137 rr::PrimitiveType mapVkPrimitiveTopology(VkPrimitiveTopology primitiveTopology)
138 {
139     switch (primitiveTopology)
140     {
141     case VK_PRIMITIVE_TOPOLOGY_POINT_LIST:
142         return rr::PRIMITIVETYPE_POINTS;
143     case VK_PRIMITIVE_TOPOLOGY_LINE_LIST:
144         return rr::PRIMITIVETYPE_LINES;
145     case VK_PRIMITIVE_TOPOLOGY_LINE_STRIP:
146         return rr::PRIMITIVETYPE_LINE_STRIP;
147     case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST:
148         return rr::PRIMITIVETYPE_TRIANGLES;
149     case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_FAN:
150         return rr::PRIMITIVETYPE_TRIANGLE_FAN;
151     case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP:
152         return rr::PRIMITIVETYPE_TRIANGLE_STRIP;
153     case VK_PRIMITIVE_TOPOLOGY_LINE_LIST_WITH_ADJACENCY:
154         return rr::PRIMITIVETYPE_LINES_ADJACENCY;
155     case VK_PRIMITIVE_TOPOLOGY_LINE_STRIP_WITH_ADJACENCY:
156         return rr::PRIMITIVETYPE_LINE_STRIP_ADJACENCY;
157     case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST_WITH_ADJACENCY:
158         return rr::PRIMITIVETYPE_TRIANGLES_ADJACENCY;
159     case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP_WITH_ADJACENCY:
160         return rr::PRIMITIVETYPE_TRIANGLE_STRIP_ADJACENCY;
161     default:
162         DE_ASSERT(false);
163     }
164     return rr::PRIMITIVETYPE_LAST;
165 }
166 
mapVkStencilOp(vk::VkStencilOp stencilOp)167 rr::StencilOp mapVkStencilOp(vk::VkStencilOp stencilOp)
168 {
169     switch (stencilOp)
170     {
171     case VK_STENCIL_OP_KEEP:
172         return rr::STENCILOP_KEEP;
173     case VK_STENCIL_OP_ZERO:
174         return rr::STENCILOP_ZERO;
175     case VK_STENCIL_OP_REPLACE:
176         return rr::STENCILOP_REPLACE;
177     case VK_STENCIL_OP_INCREMENT_AND_CLAMP:
178         return rr::STENCILOP_INCR;
179     case VK_STENCIL_OP_DECREMENT_AND_CLAMP:
180         return rr::STENCILOP_DECR;
181     case VK_STENCIL_OP_INVERT:
182         return rr::STENCILOP_INVERT;
183     case VK_STENCIL_OP_INCREMENT_AND_WRAP:
184         return rr::STENCILOP_INCR_WRAP;
185     case VK_STENCIL_OP_DECREMENT_AND_WRAP:
186         return rr::STENCILOP_DECR_WRAP;
187     default:
188         DE_ASSERT(false);
189     }
190     return rr::STENCILOP_LAST;
191 }
192 
swizzle(const tcu::Vec4 & color,const tcu::UVec4 & swizzle)193 tcu::Vec4 swizzle(const tcu::Vec4 &color, const tcu::UVec4 &swizzle)
194 {
195     const float channelValues[] = {0.0f, 1.0f, color.x(), color.y(), color.z(), color.w()};
196 
197     return tcu::Vec4(channelValues[swizzle.x()], channelValues[swizzle.y()], channelValues[swizzle.z()],
198                      channelValues[swizzle.w()]);
199 }
200 
ReferenceRenderer(int surfaceWidth,int surfaceHeight,int numSamples,const tcu::TextureFormat & colorFormat,const tcu::TextureFormat & depthStencilFormat,const rr::Program * const program)201 ReferenceRenderer::ReferenceRenderer(int surfaceWidth, int surfaceHeight, int numSamples,
202                                      const tcu::TextureFormat &colorFormat,
203                                      const tcu::TextureFormat &depthStencilFormat, const rr::Program *const program)
204     : m_surfaceWidth(surfaceWidth)
205     , m_surfaceHeight(surfaceHeight)
206     , m_numSamples(numSamples)
207     , m_colorFormat(colorFormat)
208     , m_depthStencilFormat(depthStencilFormat)
209     , m_program(program)
210 {
211     const tcu::TextureChannelClass formatClass = tcu::getTextureChannelClass(colorFormat.type);
212     const bool hasDepthStencil                 = (m_depthStencilFormat.order != tcu::TextureFormat::CHANNELORDER_LAST);
213     const bool hasDepthBufferOnly              = (m_depthStencilFormat.order == tcu::TextureFormat::D);
214     const bool hasStencilBufferOnly            = (m_depthStencilFormat.order == tcu::TextureFormat::S);
215     const int actualSamples                    = (formatClass == tcu::TEXTURECHANNELCLASS_SIGNED_INTEGER ||
216                                formatClass == tcu::TEXTURECHANNELCLASS_UNSIGNED_INTEGER) ?
217                                                      1 :
218                                                      m_numSamples;
219 
220     m_colorBuffer.setStorage(m_colorFormat, actualSamples, m_surfaceWidth, m_surfaceHeight);
221     m_resolveColorBuffer.setStorage(m_colorFormat, m_surfaceWidth, m_surfaceHeight);
222 
223     if (formatClass == tcu::TEXTURECHANNELCLASS_SIGNED_INTEGER)
224     {
225         tcu::clear(m_colorBuffer.getAccess(), defaultClearColorInt(m_colorFormat));
226         tcu::clear(m_resolveColorBuffer.getAccess(), defaultClearColorInt(m_colorFormat));
227     }
228     else if (formatClass == tcu::TEXTURECHANNELCLASS_UNSIGNED_INTEGER)
229     {
230         tcu::clear(m_colorBuffer.getAccess(), defaultClearColorUint(m_colorFormat));
231         tcu::clear(m_resolveColorBuffer.getAccess(), defaultClearColorUint(m_colorFormat));
232     }
233     else
234     {
235         tcu::Vec4 clearColor = defaultClearColor(m_colorFormat);
236 
237         if (isSRGB(m_colorFormat))
238             clearColor = tcu::linearToSRGB(clearColor);
239 
240         tcu::clear(m_colorBuffer.getAccess(), clearColor);
241         tcu::clear(m_resolveColorBuffer.getAccess(), clearColor);
242     }
243 
244     if (hasDepthStencil)
245     {
246         if (hasDepthBufferOnly)
247         {
248             m_depthStencilBuffer.setStorage(m_depthStencilFormat, actualSamples, surfaceWidth, surfaceHeight);
249             tcu::clearDepth(m_depthStencilBuffer.getAccess(), defaultClearDepth());
250 
251             m_resolveDepthStencilBuffer.setStorage(m_depthStencilFormat, surfaceWidth, surfaceHeight);
252             tcu::clearDepth(m_resolveDepthStencilBuffer.getAccess(), defaultClearDepth());
253 
254             m_renderTarget = new rr::RenderTarget(
255                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_colorBuffer.getAccess()),
256                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_depthStencilBuffer.getAccess()));
257         }
258         else if (hasStencilBufferOnly)
259         {
260             m_depthStencilBuffer.setStorage(m_depthStencilFormat, actualSamples, surfaceWidth, surfaceHeight);
261             tcu::clearStencil(m_depthStencilBuffer.getAccess(), defaultClearStencil());
262 
263             m_resolveDepthStencilBuffer.setStorage(m_depthStencilFormat, surfaceWidth, surfaceHeight);
264             tcu::clearStencil(m_resolveDepthStencilBuffer.getAccess(), defaultClearStencil());
265 
266             m_renderTarget = new rr::RenderTarget(
267                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_colorBuffer.getAccess()),
268                 rr::MultisamplePixelBufferAccess(),
269                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_depthStencilBuffer.getAccess()));
270         }
271         else
272         {
273             m_depthStencilBuffer.setStorage(m_depthStencilFormat, actualSamples, surfaceWidth, surfaceHeight);
274 
275             tcu::clearDepth(m_depthStencilBuffer.getAccess(), defaultClearDepth());
276             tcu::clearStencil(m_depthStencilBuffer.getAccess(), defaultClearStencil());
277 
278             m_resolveDepthStencilBuffer.setStorage(m_depthStencilFormat, surfaceWidth, surfaceHeight);
279             tcu::clearDepth(m_resolveDepthStencilBuffer.getAccess(), defaultClearDepth());
280 
281             m_renderTarget = new rr::RenderTarget(
282                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_colorBuffer.getAccess()),
283                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_depthStencilBuffer.getAccess()),
284                 rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_depthStencilBuffer.getAccess()));
285         }
286     }
287     else
288     {
289         m_renderTarget =
290             new rr::RenderTarget(rr::MultisamplePixelBufferAccess::fromMultisampleAccess(m_colorBuffer.getAccess()));
291     }
292 }
293 
~ReferenceRenderer(void)294 ReferenceRenderer::~ReferenceRenderer(void)
295 {
296     delete m_renderTarget;
297 }
298 
colorClear(const tcu::Vec4 & color)299 void ReferenceRenderer::colorClear(const tcu::Vec4 &color)
300 {
301     tcu::clear(m_colorBuffer.getAccess(), color);
302     tcu::clear(m_resolveColorBuffer.getAccess(), color);
303 }
304 
draw(const rr::RenderState & renderState,const rr::PrimitiveType primitive,const std::vector<Vertex4RGBA> & vertexBuffer)305 void ReferenceRenderer::draw(const rr::RenderState &renderState, const rr::PrimitiveType primitive,
306                              const std::vector<Vertex4RGBA> &vertexBuffer)
307 {
308     const rr::PrimitiveList primitives(primitive, (int)vertexBuffer.size(), 0);
309 
310     std::vector<tcu::Vec4> positions;
311     std::vector<tcu::Vec4> colors;
312 
313     for (size_t vertexNdx = 0; vertexNdx < vertexBuffer.size(); vertexNdx++)
314     {
315         const Vertex4RGBA &v = vertexBuffer[vertexNdx];
316         positions.push_back(v.position);
317         colors.push_back(v.color);
318     }
319 
320     rr::VertexAttrib vertexAttribs[2];
321 
322     // Position attribute
323     vertexAttribs[0].type    = rr::VERTEXATTRIBTYPE_FLOAT;
324     vertexAttribs[0].size    = 4;
325     vertexAttribs[0].pointer = positions.data();
326     // UV attribute
327     vertexAttribs[1].type    = rr::VERTEXATTRIBTYPE_FLOAT;
328     vertexAttribs[1].size    = 4;
329     vertexAttribs[1].pointer = colors.data();
330 
331     rr::DrawCommand drawQuadCommand(renderState, *m_renderTarget, *m_program, 2, vertexAttribs, primitives);
332 
333     m_renderer.draw(drawQuadCommand);
334 }
draw(const rr::RenderState & renderState,const rr::PrimitiveType primitive,const std::vector<Vertex4RGBARGBA> & vertexBuffer)335 void ReferenceRenderer::draw(const rr::RenderState &renderState, const rr::PrimitiveType primitive,
336                              const std::vector<Vertex4RGBARGBA> &vertexBuffer)
337 {
338     const rr::PrimitiveList primitives(primitive, (int)vertexBuffer.size(), 0);
339 
340     std::vector<tcu::Vec4> positions;
341     std::vector<tcu::Vec4> color0s;
342     std::vector<tcu::Vec4> color1s;
343 
344     for (size_t vertexNdx = 0; vertexNdx < vertexBuffer.size(); vertexNdx++)
345     {
346         const Vertex4RGBARGBA &v = vertexBuffer[vertexNdx];
347         positions.push_back(v.position);
348         color0s.push_back(v.color0);
349         color1s.push_back(v.color1);
350     }
351 
352     rr::VertexAttrib vertexAttribs[3];
353 
354     // Position attribute
355     vertexAttribs[0].type    = rr::VERTEXATTRIBTYPE_FLOAT;
356     vertexAttribs[0].size    = 4;
357     vertexAttribs[0].pointer = positions.data();
358     // Color0 attribute
359     vertexAttribs[1].type    = rr::VERTEXATTRIBTYPE_FLOAT;
360     vertexAttribs[1].size    = 4;
361     vertexAttribs[1].pointer = color0s.data();
362     // Color1 attribute
363     vertexAttribs[2].type    = rr::VERTEXATTRIBTYPE_FLOAT;
364     vertexAttribs[2].size    = 4;
365     vertexAttribs[2].pointer = color1s.data();
366 
367     rr::DrawCommand drawQuadCommand(renderState, *m_renderTarget, *m_program, 3, vertexAttribs, primitives);
368 
369     m_renderer.draw(drawQuadCommand);
370 }
371 
draw(const rr::RenderState & renderState,const rr::PrimitiveType primitive,const std::vector<Vertex4Tex4> & vertexBuffer)372 void ReferenceRenderer::draw(const rr::RenderState &renderState, const rr::PrimitiveType primitive,
373                              const std::vector<Vertex4Tex4> &vertexBuffer)
374 {
375     const rr::PrimitiveList primitives(primitive, (int)vertexBuffer.size(), 0);
376 
377     std::vector<tcu::Vec4> positions;
378     std::vector<tcu::Vec4> texCoords;
379 
380     for (size_t vertexNdx = 0; vertexNdx < vertexBuffer.size(); vertexNdx++)
381     {
382         const Vertex4Tex4 &v = vertexBuffer[vertexNdx];
383         positions.push_back(v.position);
384         texCoords.push_back(v.texCoord);
385     }
386 
387     rr::VertexAttrib vertexAttribs[2];
388 
389     // Position attribute
390     vertexAttribs[0].type    = rr::VERTEXATTRIBTYPE_FLOAT;
391     vertexAttribs[0].size    = 4;
392     vertexAttribs[0].pointer = positions.data();
393     // UV attribute
394     vertexAttribs[1].type    = rr::VERTEXATTRIBTYPE_FLOAT;
395     vertexAttribs[1].size    = 4;
396     vertexAttribs[1].pointer = texCoords.data();
397 
398     rr::DrawCommand drawQuadCommand(renderState, *m_renderTarget, *m_program, 2, vertexAttribs, primitives);
399 
400     m_renderer.draw(drawQuadCommand);
401 }
402 
getAccess(void)403 tcu::PixelBufferAccess ReferenceRenderer::getAccess(void)
404 {
405     rr::MultisampleConstPixelBufferAccess multiSampleAccess =
406         rr::MultisampleConstPixelBufferAccess::fromMultisampleAccess(m_colorBuffer.getAccess());
407     rr::resolveMultisampleColorBuffer(m_resolveColorBuffer.getAccess(), multiSampleAccess);
408 
409     return m_resolveColorBuffer.getAccess();
410 }
411 
getDepthStencilAccess(void)412 tcu::PixelBufferAccess ReferenceRenderer::getDepthStencilAccess(void)
413 {
414     rr::MultisampleConstPixelBufferAccess multiSampleAccess =
415         rr::MultisampleConstPixelBufferAccess::fromMultisampleAccess(m_depthStencilBuffer.getAccess());
416     rr::resolveMultisampleColorBuffer(m_resolveDepthStencilBuffer.getAccess(), multiSampleAccess);
417 
418     return m_resolveDepthStencilBuffer.getAccess();
419 }
420 
getViewportState(void) const421 const rr::ViewportState ReferenceRenderer::getViewportState(void) const
422 {
423     return rr::ViewportState(rr::WindowRectangle(0, 0, m_surfaceWidth, m_surfaceHeight));
424 }
425 
426 } // namespace pipeline
427 } // namespace vkt
428