• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #ifndef _VKRESOURCEINTERFACE_HPP
2 #define _VKRESOURCEINTERFACE_HPP
3 /*-------------------------------------------------------------------------
4  * Vulkan CTS Framework
5  * --------------------
6  *
7  * Copyright (c) 2021 The Khronos Group Inc.
8  *
9  * Licensed under the Apache License, Version 2.0 (the "License");
10  * you may not use this file except in compliance with the License.
11  * You may obtain a copy of the License at
12  *
13  *      http://www.apache.org/licenses/LICENSE-2.0
14  *
15  * Unless required by applicable law or agreed to in writing, software
16  * distributed under the License is distributed on an "AS IS" BASIS,
17  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18  * See the License for the specific language governing permissions and
19  * limitations under the License.
20  *
21  *//*!
22  * \file
23  * \brief Defines class for handling resources ( programs, pipelines, files, etc. )
24  *//*--------------------------------------------------------------------*/
25 
26 #include "vkDefs.hpp"
27 #include "tcuTestLog.hpp"
28 #include "tcuTestContext.hpp"
29 #include "vkPrograms.hpp"
30 #include "vkBinaryRegistry.hpp"
31 #include "deSharedPtr.hpp"
32 #include "deDefs.hpp"
33 #include <map>
34 #ifdef CTS_USES_VULKANSC
35 	#include "vksClient.hpp"
36 	#include "tcuMaybe.hpp"
37 //	#include "vksStructsVKSC.hpp"
38 #endif // CTS_USES_VULKANSC
39 
40 namespace vk
41 {
42 
43 class ResourceInterface
44 {
45 public:
46 																ResourceInterface			(tcu::TestContext&						testCtx);
47 	virtual														~ResourceInterface			();
48 
49 	virtual void												initDevice					(DeviceInterface&						deviceInterface,
50 																							 VkDevice								device) = 0;
51 	// use deinitDevice when your DeviceDriverSC is created and removed inside TestInstance
52 	virtual void												deinitDevice				(VkDevice								device) = 0;
53 
54 	virtual void												initTestCase				(const std::string&						casePath);
55 	const std::string&											getCasePath					() const;
56 
57 	// buildProgram
58 	template <typename InfoType, typename IteratorType>
59 	vk::ProgramBinary*											buildProgram				(const std::string&						casePath,
60 																							 IteratorType							iter,
61 																							 const vk::BinaryRegistryReader&		prebuiltBinRegistry,
62 																							 vk::BinaryCollection*					progCollection);
63 
64 #ifdef CTS_USES_VULKANSC
65 	void														initApiVersion				(const deUint32							version);
66 	bool														isVulkanSC					(void) const;
67 
68 	deUint64													incResourceCounter			();
69 	std::mutex&													getStatMutex				();
70 	VkDeviceObjectReservationCreateInfo&						getStatCurrent				();
71 	VkDeviceObjectReservationCreateInfo&						getStatMax					();
72 	const VkDeviceObjectReservationCreateInfo&					getStatMax					() const;
73 	void														setHandleDestroy			(bool									value);
74 	bool														isEnabledHandleDestroy		() const;
75 
76 	virtual void												registerDeviceFeatures		(VkDevice								device,
77 																							 const VkDeviceCreateInfo*				pCreateInfo) const = 0;
78 	virtual void												unregisterDeviceFeatures	(VkDevice								device) const = 0;
79 	virtual VkResult											createShaderModule			(VkDevice								device,
80 																							 const VkShaderModuleCreateInfo*		pCreateInfo,
81 																							 const VkAllocationCallbacks*			pAllocator,
82 																							 VkShaderModule*						pShaderModule,
83 																							 bool									normalMode) const = 0;
84 	virtual VkResult											createGraphicsPipelines		(VkDevice								device,
85 																							 VkPipelineCache						pipelineCache,
86 																							 deUint32 createInfoCount,
87 																							 const VkGraphicsPipelineCreateInfo*	pCreateInfos,
88 																							 const VkAllocationCallbacks*			pAllocator,
89 																							 VkPipeline*							pPipelines,
90 																							 bool									normalMode) const = 0;
91 	virtual VkResult											createComputePipelines		(VkDevice								device,
92 																							 VkPipelineCache						pipelineCache,
93 																							 deUint32								createInfoCount,
94 																							 const VkComputePipelineCreateInfo*		pCreateInfos,
95 																							 const VkAllocationCallbacks*			pAllocator,
96 																							 VkPipeline*							pPipelines,
97 																							 bool									normalMode) const = 0;
98 	virtual void												destroyPipeline				(VkDevice								device,
99 																							 VkPipeline								pipeline,
100 																							 const VkAllocationCallbacks*			pAllocator) const = 0;
101 	virtual void												createRenderPass			(VkDevice								device,
102 																							 const VkRenderPassCreateInfo*			pCreateInfo,
103 																							 const VkAllocationCallbacks*			pAllocator,
104 																							 VkRenderPass*							pRenderPass) const = 0;
105 	virtual void												createRenderPass2			(VkDevice								device,
106 																							 const VkRenderPassCreateInfo2*			pCreateInfo,
107 																							 const VkAllocationCallbacks*			pAllocator,
108 																							 VkRenderPass*							pRenderPass) const = 0;
109 	virtual void												createPipelineLayout		(VkDevice								device,
110 																							 const VkPipelineLayoutCreateInfo*		pCreateInfo,
111 																							 const VkAllocationCallbacks*			pAllocator,
112 																							 VkPipelineLayout*						pPipelineLayout) const = 0;
113 	virtual void												createDescriptorSetLayout	(VkDevice								device,
114 																							 const VkDescriptorSetLayoutCreateInfo*	pCreateInfo,
115 																							 const VkAllocationCallbacks*			pAllocator,
116 																							 VkDescriptorSetLayout*					pSetLayout) const = 0;
117 	virtual void												createSampler				(VkDevice								device,
118 																							 const VkSamplerCreateInfo*				pCreateInfo,
119 																							 const VkAllocationCallbacks*			pAllocator,
120 																							 VkSampler*								pSampler) const = 0;
121 	virtual void												createSamplerYcbcrConversion(VkDevice								device,
122 																							 const VkSamplerYcbcrConversionCreateInfo*	pCreateInfo,
123 																							 const VkAllocationCallbacks*			pAllocator,
124 																							 VkSamplerYcbcrConversion*				pYcbcrConversion) const = 0;
125 	virtual void												createCommandPool			(VkDevice								device,
126 																							 const VkCommandPoolCreateInfo*			pCreateInfo,
127 																							 const VkAllocationCallbacks*			pAllocator,
128 																							 VkCommandPool*							pCommandPool) const = 0;
129 	virtual void												allocateCommandBuffers		(VkDevice								device,
130 																							 const VkCommandBufferAllocateInfo*		pAllocateInfo,
131 																							 VkCommandBuffer*						pCommandBuffers) const = 0;
132 	virtual void												increaseCommandBufferSize	(VkCommandBuffer						commandBuffer,
133 																							 VkDeviceSize							commandSize) const = 0;
134 	virtual void												resetCommandPool			(VkDevice								device,
135 																							 VkCommandPool							commandPool,
136 																							 VkCommandPoolResetFlags				flags) const = 0;
137 
138 	void														removeRedundantObjects		();
139 	void														finalizeCommandBuffers		();
140 	std::vector<deUint8>										exportData					() const;
141 	void														importData					(std::vector<deUint8>&					importText) const;
142 	virtual void												importPipelineCacheData		(const PlatformInterface&				vkp,
143 																							 VkInstance								instance,
144 																							 const InstanceInterface&				vki,
145 																							 VkPhysicalDevice						physicalDevice,
146 																							 deUint32								queueIndex) = 0;
147 	void														registerObjectHash			(deUint64								handle,
148 																							 std::size_t							hashValue) const;
149 	const std::map<deUint64, std::size_t>&						getObjectHashes				() const;
150 
151 	void														preparePipelinePoolSizes	();
152 	std::vector<VkPipelinePoolSize>								getPipelinePoolSizes		() const;
153 	void														fillPoolEntrySize			(vk::VkPipelineOfflineCreateInfo&		pipelineIdentifier) const;
154 	vksc_server::VulkanCommandMemoryConsumption					getNextCommandPoolSize		();
155 	std::size_t													getCacheDataSize			() const;
156 	const deUint8*												getCacheData				() const;
157 	VkPipelineCache												getPipelineCache			(VkDevice								device) const;
158 	virtual void												resetObjects				() = 0;
159 	virtual void												resetPipelineCaches			() = 0;
160 #endif // CTS_USES_VULKANSC
161 
162 protected:
163 	virtual vk::ProgramBinary*									compileProgram				(const vk::ProgramIdentifier&			progId,
164 																							 const vk::GlslSource&					source,
165 																							 glu::ShaderProgramInfo*				buildInfo,
166 																							 const tcu::CommandLine&				commandLine) = 0;
167 	virtual vk::ProgramBinary*									compileProgram				(const vk::ProgramIdentifier&			progId,
168 																							 const vk::HlslSource&					source,
169 																							 glu::ShaderProgramInfo*				buildInfo,
170 																							 const tcu::CommandLine&				commandLine) = 0;
171 	virtual vk::ProgramBinary*									compileProgram				(const vk::ProgramIdentifier&			progId,
172 																							 const vk::SpirVAsmSource&				source,
173 																							 vk::SpirVProgramInfo*					buildInfo,
174 																							 const tcu::CommandLine&				commandLine) = 0;
175 
176 	tcu::TestContext&											m_testCtx;
177 	std::string													m_currentTestPath;
178 
179 #ifdef CTS_USES_VULKANSC
180 	mutable vksc_server::VulkanPipelineCacheInput					m_pipelineInput;
181 	mutable std::map<deUint64, std::size_t>							m_objectHashes;
182 	mutable std::vector<vksc_server::VulkanCommandMemoryConsumption>
183 																	m_commandPoolMemoryConsumption;
184 	mutable deUint32												m_commandPoolIndex;
185 	mutable std::map<VkCommandBuffer, vksc_server::VulkanCommandMemoryConsumption>
186 																	m_commandBufferMemoryConsumption;
187 	mutable std::map<VkDevice, std::string>							m_deviceFeatures;
188 	mutable std::map<VkDevice, std::vector<std::string>>			m_deviceExtensions;
189 
190 	std::map<VkDevice,de::SharedPtr<Move<VkPipelineCache>>>			m_pipelineCache;
191 
192 	mutable std::mutex												m_mutex;
193 	mutable deUint64												m_resourceCounter;
194 	mutable VkDeviceObjectReservationCreateInfo						m_statCurrent;
195 	mutable VkDeviceObjectReservationCreateInfo						m_statMax;
196 
197 	std::vector<deUint8>											m_cacheData;
198 	mutable std::map<VkPipeline, VkPipelineOfflineCreateInfo>		m_pipelineIdentifiers;
199 	mutable std::vector<vksc_server::VulkanPipelineSize>			m_pipelineSizes;
200 	std::vector<VkPipelinePoolSize>									m_pipelinePoolSizes;
201 	tcu::Maybe<deUint32>											m_version;
202 	tcu::Maybe<bool>												m_vulkanSC;
203 	bool															m_enabledHandleDestroy;
204 #endif // CTS_USES_VULKANSC
205 };
206 
207 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateSamplerYcbcrConversionFunc)		(VkDevice device, const VkSamplerYcbcrConversionCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkSamplerYcbcrConversion* pYcbcrConversion);
208 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroySamplerYcbcrConversionFunc)		(VkDevice device, VkSamplerYcbcrConversion ycbcrConversion, const VkAllocationCallbacks* pAllocator);
209 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateSamplerFunc)						(VkDevice device, const VkSamplerCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkSampler* pSampler);
210 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroySamplerFunc)					(VkDevice device, VkSampler sampler, const VkAllocationCallbacks* pAllocator);
211 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateShaderModuleFunc)				(VkDevice device, const VkShaderModuleCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkShaderModule* pShaderModule);
212 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyShaderModuleFunc)				(VkDevice device, VkShaderModule shaderModule, const VkAllocationCallbacks* pAllocator);
213 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateRenderPassFunc)					(VkDevice device, const VkRenderPassCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkRenderPass* pRenderPass);
214 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateRenderPass2Func)					(VkDevice device, const VkRenderPassCreateInfo2* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkRenderPass* pRenderPass);
215 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyRenderPassFunc)					(VkDevice device, VkRenderPass renderPass, const VkAllocationCallbacks* pAllocator);
216 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateDescriptorSetLayoutFunc)			(VkDevice device, const VkDescriptorSetLayoutCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkDescriptorSetLayout* pSetLayout);
217 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyDescriptorSetLayoutFunc)		(VkDevice device, VkDescriptorSetLayout descriptorSetLayout, const VkAllocationCallbacks* pAllocator);
218 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreatePipelineLayoutFunc)				(VkDevice device, const VkPipelineLayoutCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkPipelineLayout* pPipelineLayout);
219 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyPipelineLayoutFunc)				(VkDevice device, VkPipelineLayout pipelineLayout, const VkAllocationCallbacks* pAllocator);
220 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateGraphicsPipelinesFunc)			(VkDevice device, VkPipelineCache pipelineCache, deUint32 createInfoCount, const VkGraphicsPipelineCreateInfo* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines);
221 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreateComputePipelinesFunc)			(VkDevice device, VkPipelineCache pipelineCache, deUint32 createInfoCount, const VkComputePipelineCreateInfo* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines);
222 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyPipelineFunc)					(VkDevice device, VkPipeline pipeline, const VkAllocationCallbacks* pAllocator);
223 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* CreatePipelineCacheFunc)				(VkDevice device, const VkPipelineCacheCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkPipelineCache* pPipelineCache);
224 typedef VKAPI_ATTR void		(VKAPI_CALL* DestroyPipelineCacheFunc)				(VkDevice device, VkPipelineCache pipelineCache, const VkAllocationCallbacks* pAllocator);
225 typedef VKAPI_ATTR VkResult	(VKAPI_CALL* GetPipelineCacheDataFunc)				(VkDevice device, VkPipelineCache pipelineCache, deUintptr* pDataSize, void* pData);
226 #ifdef CTS_USES_VULKANSC
227 typedef VKAPI_ATTR void		(VKAPI_CALL* GetCommandPoolMemoryConsumptionFunc)	(VkDevice device, VkCommandPool commandPool, VkCommandBuffer commandBuffer, VkCommandPoolMemoryConsumption* pConsumption);
228 #endif // CTS_USES_VULKANSC
229 
230 class ResourceInterfaceStandard : public ResourceInterface
231 {
232 public:
233 								ResourceInterfaceStandard	(tcu::TestContext&						testCtx);
234 
235 	void						initDevice					(DeviceInterface&						deviceInterface,
236 															 VkDevice								device) override;
237 	void						deinitDevice				(VkDevice								device) override;
238 
239 #ifdef CTS_USES_VULKANSC
240 	void						registerDeviceFeatures		(VkDevice								device,
241 															const VkDeviceCreateInfo*				pCreateInfo) const override;
242 	void						unregisterDeviceFeatures	(VkDevice								device) const override;
243 	VkResult					createShaderModule			(VkDevice								device,
244 															 const VkShaderModuleCreateInfo*		pCreateInfo,
245 															 const VkAllocationCallbacks*			pAllocator,
246 															 VkShaderModule*						pShaderModule,
247 															 bool									normalMode) const override;
248 	VkResult					createGraphicsPipelines		(VkDevice								device,
249 															 VkPipelineCache						pipelineCache,
250 															 deUint32 createInfoCount,
251 															 const VkGraphicsPipelineCreateInfo*	pCreateInfos,
252 															 const VkAllocationCallbacks*			pAllocator,
253 															 VkPipeline*							pPipelines,
254 															 bool									normalMode) const override;
255 	VkResult					createComputePipelines		(VkDevice								device,
256 															 VkPipelineCache						pipelineCache,
257 															 deUint32								createInfoCount,
258 															 const VkComputePipelineCreateInfo*		pCreateInfos,
259 															 const VkAllocationCallbacks*			pAllocator,
260 															 VkPipeline*							pPipelines,
261 															 bool									normalMode) const override;
262 	void						destroyPipeline				(VkDevice								device,
263 															 VkPipeline								pipeline,
264 															 const VkAllocationCallbacks*			pAllocator) const override;
265 	void						createRenderPass			(VkDevice								device,
266 															 const VkRenderPassCreateInfo*			pCreateInfo,
267 															 const VkAllocationCallbacks*			pAllocator,
268 															 VkRenderPass*							pRenderPass) const override;
269 	void						createRenderPass2			(VkDevice								device,
270 															 const VkRenderPassCreateInfo2*			pCreateInfo,
271 															 const VkAllocationCallbacks*			pAllocator,
272 															 VkRenderPass*							pRenderPass) const override;
273 	void						createPipelineLayout		(VkDevice								device,
274 															 const VkPipelineLayoutCreateInfo*		pCreateInfo,
275 															 const VkAllocationCallbacks*			pAllocator,
276 															 VkPipelineLayout*						pPipelineLayout) const override;
277 	void						createDescriptorSetLayout	(VkDevice								device,
278 															 const VkDescriptorSetLayoutCreateInfo*	pCreateInfo,
279 															 const VkAllocationCallbacks*			pAllocator,
280 															 VkDescriptorSetLayout*					pSetLayout) const override;
281 	void						createSampler				(VkDevice								device,
282 															 const VkSamplerCreateInfo*				pCreateInfo,
283 															 const VkAllocationCallbacks*			pAllocator,
284 															 VkSampler*								pSampler) const override;
285 	void						createSamplerYcbcrConversion(VkDevice								device,
286 															 const VkSamplerYcbcrConversionCreateInfo*	pCreateInfo,
287 															 const VkAllocationCallbacks*			pAllocator,
288 															 VkSamplerYcbcrConversion*				pYcbcrConversion) const override;
289 	void						createCommandPool			(VkDevice								device,
290 															 const VkCommandPoolCreateInfo*			pCreateInfo,
291 															 const VkAllocationCallbacks*			pAllocator,
292 															 VkCommandPool*							pCommandPool) const override;
293 	void						allocateCommandBuffers		(VkDevice								device,
294 															 const VkCommandBufferAllocateInfo*		pAllocateInfo,
295 															 VkCommandBuffer*						pCommandBuffers) const override;
296 	void						increaseCommandBufferSize	(VkCommandBuffer						commandBuffer,
297 															 VkDeviceSize							commandSize) const override;
298 	void						resetCommandPool			(VkDevice								device,
299 															 VkCommandPool							commandPool,
300 															 VkCommandPoolResetFlags				flags) const override;
301 	void						importPipelineCacheData		(const PlatformInterface&				vkp,
302 															 VkInstance								instance,
303 															 const InstanceInterface&				vki,
304 															 VkPhysicalDevice						physicalDevice,
305 															 deUint32								queueIndex) override;
306 	void						resetObjects				() override;
307 	void						resetPipelineCaches			() override;
308 #endif // CTS_USES_VULKANSC
309 
310 protected:
311 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
312 															 const vk::GlslSource&					source,
313 															 glu::ShaderProgramInfo*				buildInfo,
314 															 const tcu::CommandLine&				commandLine) override;
315 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
316 															 const vk::HlslSource&					source,
317 															 glu::ShaderProgramInfo*				buildInfo,
318 															 const tcu::CommandLine&				commandLine) override;
319 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
320 															 const vk::SpirVAsmSource&				source,
321 															 vk::SpirVProgramInfo*					buildInfo,
322 															 const tcu::CommandLine&				commandLine) override;
323 
324 	std::map<VkDevice,CreateShaderModuleFunc>				m_createShaderModuleFunc;
325 	std::map<VkDevice,CreateGraphicsPipelinesFunc>			m_createGraphicsPipelinesFunc;
326 	std::map<VkDevice,CreateComputePipelinesFunc>			m_createComputePipelinesFunc;
327 };
328 
329 #ifdef CTS_USES_VULKANSC
330 
331 class ResourceInterfaceVKSC : public ResourceInterfaceStandard
332 {
333 public:
334 								ResourceInterfaceVKSC		(tcu::TestContext&						testCtx);
335 
336 	VkResult					createShaderModule			(VkDevice								device,
337 															 const VkShaderModuleCreateInfo*		pCreateInfo,
338 															 const VkAllocationCallbacks*			pAllocator,
339 															 VkShaderModule*						pShaderModule,
340 															 bool									normalMode) const override;
341 
342 	void						importPipelineCacheData		(const PlatformInterface&				vkp,
343 															 VkInstance								instance,
344 															 const InstanceInterface&				vki,
345 															 VkPhysicalDevice						physicalDevice,
346 															 deUint32								queueIndex) override;
347 
348 protected:
349 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
350 															 const vk::GlslSource&					source,
351 															 glu::ShaderProgramInfo*				buildInfo,
352 															 const tcu::CommandLine&				commandLine) override;
353 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
354 															 const vk::HlslSource&					source,
355 															 glu::ShaderProgramInfo*				buildInfo,
356 															 const tcu::CommandLine&				commandLine) override;
357 	vk::ProgramBinary*			compileProgram				(const vk::ProgramIdentifier&			progId,
358 															 const vk::SpirVAsmSource&				source,
359 															 vk::SpirVProgramInfo*					buildInfo,
360 															 const tcu::CommandLine&				commandLine) override;
361 
362 private:
363 	vksc_server::Server*		getServer					();
364 	bool						noServer					() const;
365 
366 	std::string								m_address;
367 	std::shared_ptr<vksc_server::Server>	m_server;
368 };
369 
370 class MultithreadedDestroyGuard
371 {
372 public:
373 	MultithreadedDestroyGuard	(de::SharedPtr<vk::ResourceInterface> resourceInterface);
374 	~MultithreadedDestroyGuard	();
375 private:
376 	de::SharedPtr<vk::ResourceInterface> m_resourceInterface;
377 };
378 
379 #endif // CTS_USES_VULKANSC
380 
381 template <typename InfoType, typename IteratorType>
buildProgram(const std::string & casePath,IteratorType iter,const vk::BinaryRegistryReader & prebuiltBinRegistry,vk::BinaryCollection * progCollection)382 vk::ProgramBinary* ResourceInterface::buildProgram			(const std::string&					casePath,
383 															 IteratorType						iter,
384 															 const vk::BinaryRegistryReader&	prebuiltBinRegistry,
385 															 vk::BinaryCollection*				progCollection)
386 {
387 	const vk::ProgramIdentifier		progId			(casePath, iter.getName());
388 	tcu::TestLog&					log				= m_testCtx.getLog();
389 	const tcu::CommandLine&			commandLine		= m_testCtx.getCommandLine();
390 	const tcu::ScopedLogSection		progSection		(log, iter.getName(), "Program: " + iter.getName());
391 	de::MovePtr<vk::ProgramBinary>	binProg;
392 	InfoType						buildInfo;
393 
394 	try
395 	{
396 		binProg = de::MovePtr<vk::ProgramBinary>(compileProgram(progId, iter.getProgram(), &buildInfo, commandLine));
397 		log << buildInfo;
398 	}
399 	catch (const tcu::NotSupportedError& err)
400 	{
401 		// Try to load from cache
402 		log << err << tcu::TestLog::Message << "Building from source not supported, loading stored binary instead" << tcu::TestLog::EndMessage;
403 
404 		binProg = de::MovePtr<vk::ProgramBinary>(prebuiltBinRegistry.loadProgram(progId));
405 
406 		log << iter.getProgram();
407 	}
408 	catch (const tcu::Exception&)
409 	{
410 		// Build failed for other reason
411 		log << buildInfo;
412 		throw;
413 	}
414 
415 	TCU_CHECK_INTERNAL(binProg);
416 
417 	{
418 		vk::ProgramBinary* const	returnBinary = binProg.get();
419 
420 		progCollection->add(progId.programName, binProg);
421 
422 		return returnBinary;
423 	}
424 }
425 
426 } // vk
427 
428 #endif // _VKRESOURCEINTERFACE_HPP
429