• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 The SwiftShader Authors. All Rights Reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //    http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #ifndef sw_Renderer_hpp
16 #define sw_Renderer_hpp
17 
18 #include "Blitter.hpp"
19 #include "PixelProcessor.hpp"
20 #include "Primitive.hpp"
21 #include "SetupProcessor.hpp"
22 #include "VertexProcessor.hpp"
23 #include "Vulkan/VkDescriptorSet.hpp"
24 #include "Vulkan/VkPipeline.hpp"
25 
26 #include "marl/finally.h"
27 #include "marl/pool.h"
28 #include "marl/ticket.h"
29 
30 #include <atomic>
31 #include <list>
32 #include <mutex>
33 #include <thread>
34 
35 namespace vk {
36 
37 class DescriptorSet;
38 class Device;
39 class Query;
40 class PipelineLayout;
41 
42 }  // namespace vk
43 
44 namespace sw {
45 
46 class CountedEvent;
47 struct DrawCall;
48 class PixelShader;
49 class VertexShader;
50 struct Task;
51 class Resource;
52 struct Constants;
53 
54 static constexpr int MaxBatchSize = 128;
55 static constexpr int MaxBatchCount = 16;
56 static constexpr int MaxClusterCount = 16;
57 static constexpr int MaxDrawCount = 16;
58 
59 using TriangleBatch = std::array<Triangle, MaxBatchSize>;
60 using PrimitiveBatch = std::array<Primitive, MaxBatchSize>;
61 
62 struct DrawData
63 {
64 	vk::DescriptorSet::Bindings descriptorSets = {};
65 	vk::DescriptorSet::DynamicOffsets descriptorDynamicOffsets = {};
66 
67 	const void *input[MAX_INTERFACE_COMPONENTS / 4];
68 	unsigned int robustnessSize[MAX_INTERFACE_COMPONENTS / 4];
69 	unsigned int stride[MAX_INTERFACE_COMPONENTS / 4];
70 	const void *indices;
71 
72 	int instanceID;
73 	int baseVertex;
74 	float lineWidth;
75 	int viewID;
76 
77 	PixelProcessor::Stencil stencil[2];  // clockwise, counterclockwise
78 	PixelProcessor::Factor factor;
79 	unsigned int occlusion[MaxClusterCount];  // Number of pixels passing depth test
80 
81 	float4 WxF;
82 	float4 HxF;
83 	float4 X0xF;
84 	float4 Y0xF;
85 	float4 halfPixelX;
86 	float4 halfPixelY;
87 	float viewportHeight;
88 	float depthRange;
89 	float depthNear;
90 	float minimumResolvableDepthDifference;
91 	float constantDepthBias;
92 	float slopeDepthBias;
93 	float depthBiasClamp;
94 	bool depthClipEnable;
95 
96 	unsigned int *colorBuffer[MAX_COLOR_BUFFERS];
97 	int colorPitchB[MAX_COLOR_BUFFERS];
98 	int colorSliceB[MAX_COLOR_BUFFERS];
99 	float *depthBuffer;
100 	int depthPitchB;
101 	int depthSliceB;
102 	unsigned char *stencilBuffer;
103 	int stencilPitchB;
104 	int stencilSliceB;
105 
106 	int scissorX0;
107 	int scissorX1;
108 	int scissorY0;
109 	int scissorY1;
110 
111 	float4 a2c0;
112 	float4 a2c1;
113 	float4 a2c2;
114 	float4 a2c3;
115 
116 	vk::Pipeline::PushConstantStorage pushConstants;
117 };
118 
119 struct DrawCall
120 {
121 	struct BatchData
122 	{
123 		using Pool = marl::BoundedPool<BatchData, MaxBatchCount, marl::PoolPolicy::Preserve>;
124 
125 		TriangleBatch triangles;
126 		PrimitiveBatch primitives;
127 		VertexTask vertexTask;
128 		unsigned int id;
129 		unsigned int firstPrimitive;
130 		unsigned int numPrimitives;
131 		int numVisible;
132 		marl::Ticket clusterTickets[MaxClusterCount];
133 	};
134 
135 	using Pool = marl::BoundedPool<DrawCall, MaxDrawCount, marl::PoolPolicy::Preserve>;
136 	using SetupFunction = int (*)(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
137 
138 	DrawCall();
139 	~DrawCall();
140 
141 	static void run(vk::Device *device, const marl::Loan<DrawCall> &draw, marl::Ticket::Queue *tickets, marl::Ticket::Queue clusterQueues[MaxClusterCount]);
142 	static void processVertices(vk::Device *device, DrawCall *draw, BatchData *batch);
143 	static void processPrimitives(vk::Device *device, DrawCall *draw, BatchData *batch);
144 	static void processPixels(vk::Device *device, const marl::Loan<DrawCall> &draw, const marl::Loan<BatchData> &batch, const std::shared_ptr<marl::Finally> &finally);
145 	void setup();
146 	void teardown(vk::Device *device);
147 
148 	int id;
149 
150 	BatchData::Pool *batchDataPool;
151 	unsigned int numPrimitives;
152 	unsigned int numPrimitivesPerBatch;
153 	unsigned int numBatches;
154 
155 	VkPrimitiveTopology topology;
156 	VkProvokingVertexModeEXT provokingVertexMode;
157 	VkIndexType indexType;
158 	VkLineRasterizationModeEXT lineRasterizationMode;
159 
160 	bool depthClipEnable;
161 
162 	VertexProcessor::RoutineType vertexRoutine;
163 	SetupProcessor::RoutineType setupRoutine;
164 	PixelProcessor::RoutineType pixelRoutine;
165 	bool containsImageWrite;
166 
167 	SetupFunction setupPrimitives;
168 	SetupProcessor::State setupState;
169 
170 	vk::ImageView *colorBuffer[MAX_COLOR_BUFFERS];
171 	vk::ImageView *depthBuffer;
172 	vk::ImageView *stencilBuffer;
173 	vk::DescriptorSet::Array descriptorSetObjects;
174 	const vk::PipelineLayout *pipelineLayout;
175 	sw::CountedEvent *events;
176 
177 	vk::Query *occlusionQuery;
178 
179 	DrawData *data;
180 
181 	static void processPrimitiveVertices(
182 	    unsigned int triangleIndicesOut[MaxBatchSize + 1][3],
183 	    const void *primitiveIndices,
184 	    VkIndexType indexType,
185 	    unsigned int start,
186 	    unsigned int triangleCount,
187 	    VkPrimitiveTopology topology,
188 	    VkProvokingVertexModeEXT provokingVertexMode);
189 
190 	static int setupSolidTriangles(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
191 	static int setupWireframeTriangles(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
192 	static int setupPointTriangles(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
193 	static int setupLines(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
194 	static int setupPoints(vk::Device *device, Triangle *triangles, Primitive *primitives, const DrawCall *drawCall, int count);
195 
196 	static bool setupLine(vk::Device *device, Primitive &primitive, Triangle &triangle, const DrawCall &draw);
197 	static bool setupPoint(vk::Device *device, Primitive &primitive, Triangle &triangle, const DrawCall &draw);
198 };
199 
200 class alignas(16) Renderer
201 {
202 public:
203 	Renderer(vk::Device *device);
204 
205 	virtual ~Renderer();
206 
207 	void *operator new(size_t size);
208 	void operator delete(void *mem);
209 
hasOcclusionQuery() const210 	bool hasOcclusionQuery() const { return occlusionQuery != nullptr; }
211 
212 	void draw(const vk::GraphicsPipeline *pipeline, const vk::DynamicState &dynamicState, unsigned int count, int baseVertex,
213 	          CountedEvent *events, int instanceID, int viewID, void *indexBuffer, const VkExtent3D &framebufferExtent,
214 	          vk::Pipeline::PushConstantStorage const &pushConstants, bool update = true);
215 
216 	void addQuery(vk::Query *query);
217 	void removeQuery(vk::Query *query);
218 
219 	void synchronize();
220 
221 private:
222 	DrawCall::Pool drawCallPool;
223 	DrawCall::BatchData::Pool batchDataPool;
224 
225 	std::atomic<int> nextDrawID = { 0 };
226 
227 	vk::Query *occlusionQuery = nullptr;
228 	marl::Ticket::Queue drawTickets;
229 	marl::Ticket::Queue clusterQueues[MaxClusterCount];
230 
231 	VertexProcessor vertexProcessor;
232 	PixelProcessor pixelProcessor;
233 	SetupProcessor setupProcessor;
234 
235 	VertexProcessor::State vertexState;
236 	SetupProcessor::State setupState;
237 	PixelProcessor::State pixelState;
238 
239 	VertexProcessor::RoutineType vertexRoutine;
240 	SetupProcessor::RoutineType setupRoutine;
241 	PixelProcessor::RoutineType pixelRoutine;
242 
243 	vk::Device *device;
244 };
245 
246 }  // namespace sw
247 
248 #endif  // sw_Renderer_hpp
249