1 #ifndef _VKPROGRAMS_HPP
2 #define _VKPROGRAMS_HPP
3 /*-------------------------------------------------------------------------
4  * Vulkan CTS Framework
5  * --------------------
6  *
7  * Copyright (c) 2015 Google 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 Program utilities.
24  *//*--------------------------------------------------------------------*/
25 
26 #include "vkDefs.hpp"
27 #include "vkRef.hpp"
28 #include "vkSpirVProgram.hpp"
29 #include "gluShaderProgram.hpp"
30 #include "deUniquePtr.hpp"
31 #include "deSTLUtil.hpp"
32 
33 #include <vector>
34 #include <map>
35 
36 namespace tcu
37 {
38 class TestLog;
39 } // tcu
40 
41 namespace vk
42 {
43 
44 enum ProgramFormat
45 {
46 	PROGRAM_FORMAT_SPIRV = 0,
47 
48 	PROGRAM_FORMAT_LAST
49 };
50 
51 class ProgramBinary
52 {
53 public:
54 								ProgramBinary	(ProgramFormat format, size_t binarySize, const deUint8* binary);
55 
getFormat(void) const56 	ProgramFormat				getFormat		(void) const { return m_format;										}
getSize(void) const57 	size_t						getSize			(void) const { return m_binary.size();								}
getBinary(void) const58 	const deUint8*				getBinary		(void) const { return m_binary.empty() ? DE_NULL : &m_binary[0];	}
59 
60 private:
61 	const ProgramFormat			m_format;
62 	const std::vector<deUint8>	m_binary;
63 };
64 
65 template<typename Program>
66 class ProgramCollection
67 {
68 public:
69 								ProgramCollection	(void);
70 								~ProgramCollection	(void);
71 
72 	void						clear				(void);
73 
74 	Program&					add					(const std::string& name);
75 	void						add					(const std::string& name, de::MovePtr<Program>& program);
76 
77 	bool						contains			(const std::string& name) const;
78 	const Program&				get					(const std::string& name) const;
79 
80 	class Iterator
81 	{
82 	private:
83 		typedef typename std::map<std::string, Program*>::const_iterator	IteratorImpl;
84 
85 	public:
Iterator(const IteratorImpl & i)86 		explicit			Iterator	(const IteratorImpl& i) : m_impl(i) {}
87 
operator ++(void)88 		Iterator&			operator++	(void)			{ ++m_impl; return *this;	}
operator *(void) const89 		const Program&		operator*	(void) const	{ return getProgram();		}
90 
getName(void) const91 		const std::string&	getName		(void) const	{ return m_impl->first;		}
getProgram(void) const92 		const Program&		getProgram	(void) const	{ return *m_impl->second;	}
93 
operator ==(const Iterator & other) const94 		bool				operator==	(const Iterator& other) const	{ return m_impl == other.m_impl;	}
operator !=(const Iterator & other) const95 		bool				operator!=	(const Iterator& other) const	{ return m_impl != other.m_impl;	}
96 
97 	private:
98 
99 		IteratorImpl	m_impl;
100 	};
101 
begin(void) const102 	Iterator					begin				(void) const { return Iterator(m_programs.begin());	}
end(void) const103 	Iterator					end					(void) const { return Iterator(m_programs.end());	}
104 
105 private:
106 	typedef std::map<std::string, Program*>	ProgramMap;
107 
108 	ProgramMap					m_programs;
109 };
110 
111 template<typename Program>
ProgramCollection(void)112 ProgramCollection<Program>::ProgramCollection (void)
113 {
114 }
115 
116 template<typename Program>
~ProgramCollection(void)117 ProgramCollection<Program>::~ProgramCollection (void)
118 {
119 	clear();
120 }
121 
122 template<typename Program>
clear(void)123 void ProgramCollection<Program>::clear (void)
124 {
125 	for (typename ProgramMap::const_iterator i = m_programs.begin(); i != m_programs.end(); ++i)
126 		delete i->second;
127 	m_programs.clear();
128 }
129 
130 template<typename Program>
add(const std::string & name)131 Program& ProgramCollection<Program>::add (const std::string& name)
132 {
133 	DE_ASSERT(!contains(name));
134 	de::MovePtr<Program> prog = de::newMovePtr<Program>();
135 	m_programs[name] = prog.get();
136 	prog.release();
137 	return *m_programs[name];
138 }
139 
140 template<typename Program>
add(const std::string & name,de::MovePtr<Program> & program)141 void ProgramCollection<Program>::add (const std::string& name, de::MovePtr<Program>& program)
142 {
143 	DE_ASSERT(!contains(name));
144 	m_programs[name] = program.get();
145 	program.release();
146 }
147 
148 template<typename Program>
contains(const std::string & name) const149 bool ProgramCollection<Program>::contains (const std::string& name) const
150 {
151 	return de::contains(m_programs, name);
152 }
153 
154 template<typename Program>
get(const std::string & name) const155 const Program& ProgramCollection<Program>::get (const std::string& name) const
156 {
157 	DE_ASSERT(contains(name));
158 	return *m_programs.find(name)->second;
159 }
160 
161 typedef vk::ProgramCollection<glu::ProgramSources>	GlslSourceCollection;
162 typedef vk::ProgramCollection<vk::SpirVAsmSource>	SpirVAsmCollection;
163 
164 struct SourceCollections
165 {
166 	GlslSourceCollection	glslSources;
167 	SpirVAsmCollection		spirvAsmSources;
168 };
169 
170 typedef ProgramCollection<ProgramBinary>		BinaryCollection;
171 
172 ProgramBinary*			buildProgram		(const glu::ProgramSources& program, ProgramFormat binaryFormat, glu::ShaderProgramInfo* buildInfo);
173 ProgramBinary*			assembleProgram		(const vk::SpirVAsmSource& program, SpirVProgramInfo* buildInfo);
174 void					disassembleProgram	(const ProgramBinary& program, std::ostream* dst);
175 bool					validateProgram		(const ProgramBinary& program, std::ostream* dst);
176 
177 Move<VkShaderModule>	createShaderModule	(const DeviceInterface& deviceInterface, VkDevice device, const ProgramBinary& binary, VkShaderModuleCreateFlags flags);
178 
179 glu::ShaderType			getGluShaderType	(VkShaderStageFlagBits shaderStage);
180 VkShaderStageFlagBits	getVkShaderStage	(glu::ShaderType shaderType);
181 
182 } // vk
183 
184 #endif // _VKPROGRAMS_HPP
185