• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*-------------------------------------------------------------------------
2  * drawElements Quality Program Random Shader Generator
3  * ----------------------------------------------------
4  *
5  * Copyright 2014 The Android Open Source Project
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  *//*!
20  * \file
21  * \brief Shader Class.
22  *//*--------------------------------------------------------------------*/
23 
24 #include "rsgShader.hpp"
25 
26 using std::vector;
27 
28 namespace rsg
29 {
30 
31 namespace
32 {
33 
34 template <typename T>
deleteVectorElements(std::vector<T * > & vec)35 void deleteVectorElements (std::vector<T*>& vec)
36 {
37 	for (typename std::vector<T*>::iterator i = vec.begin(); i != vec.end(); i++)
38 		delete *i;
39 	vec.clear();
40 }
41 
42 } // anonymous
43 
Function(void)44 Function::Function (void)
45 {
46 }
47 
Function(const char * name)48 Function::Function (const char* name)
49 	: m_name(name)
50 {
51 }
52 
~Function(void)53 Function::~Function (void)
54 {
55 	deleteVectorElements(m_parameters);
56 }
57 
ShaderInput(const Variable * variable,ConstValueRangeAccess valueRange)58 ShaderInput::ShaderInput (const Variable* variable, ConstValueRangeAccess valueRange)
59 	: m_variable	(variable)
60 	, m_min			(variable->getType().getScalarSize())
61 	, m_max			(variable->getType().getScalarSize())
62 {
63 	ValueAccess(variable->getType(), &m_min[0]) = valueRange.getMin().value();
64 	ValueAccess(variable->getType(), &m_max[0]) = valueRange.getMax().value();
65 }
66 
Shader(Type type)67 Shader::Shader (Type type)
68 	: m_type			(type)
69 	, m_mainFunction	("main")
70 {
71 }
72 
~Shader(void)73 Shader::~Shader (void)
74 {
75 	deleteVectorElements(m_functions);
76 	deleteVectorElements(m_globalStatements);
77 	deleteVectorElements(m_inputs);
78 	deleteVectorElements(m_uniforms);
79 }
80 
getOutputs(vector<const Variable * > & outputs) const81 void Shader::getOutputs (vector<const Variable*>& outputs) const
82 {
83 	outputs.clear();
84 	const vector<Variable*>& globalVars = m_globalScope.getDeclaredVariables();
85 	for (vector<Variable*>::const_iterator i = globalVars.begin(); i != globalVars.end(); i++)
86 	{
87 		const Variable* var = *i;
88 		if (var->getStorage() == Variable::STORAGE_SHADER_OUT)
89 			outputs.push_back(var);
90 	}
91 }
92 
tokenize(GeneratorState & state,TokenStream & str) const93 void Shader::tokenize (GeneratorState& state, TokenStream& str) const
94 {
95 	// Add default precision for float in fragment shaders \todo [pyry] Proper precision handling
96 	if (state.getShader().getType() == Shader::TYPE_FRAGMENT)
97 		str << Token::PRECISION << Token::MEDIUM_PRECISION << Token::FLOAT << Token::SEMICOLON << Token::NEWLINE;
98 
99 	// Tokenize global declaration statements
100 	for (int ndx = (int)m_globalStatements.size()-1; ndx >= 0; ndx--)
101 		m_globalStatements[ndx]->tokenize(state, str);
102 
103 	// Tokenize all functions
104 	for (int ndx = (int)m_functions.size()-1; ndx >= 0; ndx--)
105 	{
106 		str << Token::NEWLINE;
107 		m_functions[ndx]->tokenize(state, str);
108 	}
109 
110 	// Tokenize main
111 	str << Token::NEWLINE;
112 	m_mainFunction.tokenize(state, str);
113 }
114 
execute(ExecutionContext & execCtx) const115 void Shader::execute (ExecutionContext& execCtx) const
116 {
117 	// Execute global statements (declarations)
118 	for (vector<Statement*>::const_reverse_iterator i = m_globalStatements.rbegin(); i != m_globalStatements.rend(); i++)
119 		(*i)->execute(execCtx);
120 
121 	// \todo [2011-03-08 pyry] Proper function calls
122 	m_mainFunction.getBody().execute(execCtx);
123 }
124 
tokenize(GeneratorState & state,TokenStream & str) const125 void Function::tokenize (GeneratorState& state, TokenStream& str) const
126 {
127 	// Return type
128 	m_returnType.tokenizeShortType(str);
129 
130 	// Function name
131 	DE_ASSERT(m_name != "");
132 	str << Token(m_name.c_str());
133 
134 	// Parameters
135 	str << Token::LEFT_PAREN;
136 
137 	for (vector<Variable*>::const_iterator i = m_parameters.begin(); i != m_parameters.end(); i++)
138 	{
139 		if (i != m_parameters.begin())
140 			str << Token::COMMA;
141 		(*i)->tokenizeDeclaration(state, str);
142 	}
143 
144 	str << Token::RIGHT_PAREN << Token::NEWLINE;
145 
146 	// Tokenize body
147 	m_functionBlock.tokenize(state, str);
148 }
149 
150 } // rsg
151