1 #ifndef _RSGEXPRESSION_HPP
2 #define _RSGEXPRESSION_HPP
3 /*-------------------------------------------------------------------------
4  * drawElements Quality Program Random Shader Generator
5  * ----------------------------------------------------
6  *
7  * Copyright 2014 The Android Open Source Project
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 Expressions.
24  *
25  * Creating expressions:
26  *  + Children must be created in in reverse evaluation order.
27  *    - Must be tokenized / evaluated taking that order in account.
28  *
29  * Evaluation:
30  *  + Done recursively. (Do we have enough stack?)
31  *  + R-values: Nodes must implement getValue() in some way. Value
32  *    must be valid after evaluate().
33  *  + L-values: Valid writable value access proxy must be returned after
34  *    evaluate().
35  *//*--------------------------------------------------------------------*/
36 
37 #include "rsgDefs.hpp"
38 #include "rsgGeneratorState.hpp"
39 #include "rsgVariableValue.hpp"
40 #include "rsgVariable.hpp"
41 #include "rsgVariableManager.hpp"
42 #include "rsgExecutionContext.hpp"
43 
44 namespace rsg
45 {
46 
47 // \todo [2011-06-10 pyry] Declare in ShaderParameters?
48 const float unusedValueWeight = 0.05f;
49 
50 class Expression
51 {
52 public:
53 	virtual							~Expression			(void);
54 
55 	// Shader generation API
56 	virtual Expression*				createNextChild		(GeneratorState& state) = DE_NULL;
57 	virtual void					tokenize			(GeneratorState& state, TokenStream& str) const	= DE_NULL;
58 
59 	// Execution API
60 	virtual void					evaluate			(ExecutionContext& ctx)	= DE_NULL;
61 	virtual ExecConstValueAccess	getValue			(void) const			= DE_NULL;
getLValue(void) const62 	virtual ExecValueAccess			getLValue			(void) const { DE_ASSERT(DE_FALSE); throw Exception("Expression::getLValue(): not L-value node"); }
63 
64 	static Expression*				createRandom		(GeneratorState& state, ConstValueRangeAccess valueRange);
65 	static Expression*				createRandomLValue	(GeneratorState& state, ConstValueRangeAccess valueRange);
66 };
67 
68 class VariableAccess : public Expression
69 {
70 public:
~VariableAccess(void)71 	virtual						~VariableAccess		(void) {}
72 
createNextChild(GeneratorState & state)73 	Expression*					createNextChild		(GeneratorState& state)							{ DE_UNREF(state); return DE_NULL;						}
tokenize(GeneratorState & state,TokenStream & str) const74 	void						tokenize			(GeneratorState& state, TokenStream& str) const	{ DE_UNREF(state); str << Token(m_variable->getName());	}
75 
76 	void						evaluate			(ExecutionContext& ctx);
getValue(void) const77 	ExecConstValueAccess		getValue			(void) const									{ return m_valueAccess;									}
getLValue(void) const78 	ExecValueAccess				getLValue			(void) const									{ return m_valueAccess;									}
79 
80 protected:
VariableAccess(void)81 								VariableAccess		(void) : m_variable(DE_NULL) {}
82 
83 	const Variable*				m_variable;
84 	ExecValueAccess				m_valueAccess;
85 };
86 
87 class VariableRead : public VariableAccess
88 {
89 public:
90 								VariableRead		(GeneratorState& state, ConstValueRangeAccess valueRange);
91 								VariableRead		(const Variable* variable);
~VariableRead(void)92 	virtual						~VariableRead		(void) {}
93 
94 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
95 };
96 
97 class VariableWrite : public VariableAccess
98 {
99 public:
100 								VariableWrite		(GeneratorState& state, ConstValueRangeAccess valueRange);
~VariableWrite(void)101 	virtual						~VariableWrite		(void) {}
102 
103 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
104 };
105 
106 class FloatLiteral : public Expression
107 {
108 public:
109 								FloatLiteral		(GeneratorState& state, ConstValueRangeAccess valueRange);
~FloatLiteral(void)110 	virtual						~FloatLiteral		(void) {}
111 
createNextChild(GeneratorState & state)112 	Expression*					createNextChild		(GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
113 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
114 
115 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
116 
evaluate(ExecutionContext & ctx)117 	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
getValue(void) const118 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_FLOAT)); }
119 
120 private:
121 	ExecValueStorage			m_value;
122 };
123 
124 class IntLiteral : public Expression
125 {
126 public:
127 								IntLiteral			(GeneratorState& state, ConstValueRangeAccess valueRange);
~IntLiteral(void)128 	virtual						~IntLiteral			(void) {}
129 
createNextChild(GeneratorState & state)130 	Expression*					createNextChild		(GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
131 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
132 
133 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
134 
evaluate(ExecutionContext & ctx)135 	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
getValue(void) const136 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_INT)); }
137 
138 private:
139 	ExecValueStorage			m_value;
140 };
141 
142 class BoolLiteral : public Expression
143 {
144 public:
145 								BoolLiteral			(GeneratorState& state, ConstValueRangeAccess valueRange);
~BoolLiteral(void)146 	virtual						~BoolLiteral		(void) {}
147 
createNextChild(GeneratorState & state)148 	Expression*					createNextChild		(GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
149 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
150 
151 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
152 
evaluate(ExecutionContext & ctx)153 	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
getValue(void) const154 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_BOOL)); }
155 
156 private:
157 	ExecValueStorage			m_value;
158 };
159 
160 class ConstructorOp : public Expression
161 {
162 public:
163 								ConstructorOp		(GeneratorState& state, ConstValueRangeAccess valueRange);
164 	virtual						~ConstructorOp		(void);
165 
166 	Expression*					createNextChild		(GeneratorState& state);
167 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
168 
169 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
170 
171 	void						evaluate			(ExecutionContext& ctx);
getValue(void) const172 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueRange.getType()); }
173 
174 private:
175 	ValueRange					m_valueRange;
176 	ExecValueStorage			m_value;
177 
178 	std::vector<ValueRange>		m_inputValueRanges;
179 	std::vector<Expression*>	m_inputExpressions;
180 };
181 
182 class AssignOp : public Expression
183 {
184 public:
185 								AssignOp			(GeneratorState& state, ConstValueRangeAccess valueRange);
186 	virtual						~AssignOp			(void);
187 
188 	Expression*					createNextChild		(GeneratorState& state);
189 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
190 
191 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
192 
193 	// \todo [2011-02-28 pyry] LValue variant of AssignOp
194 //	static float				getLValueWeight		(const GeneratorState& state, ConstValueRangeAccess valueRange);
195 
196 	void						evaluate			(ExecutionContext& ctx);
getValue(void) const197 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueRange.getType()); }
198 
199 private:
200 	ValueRange					m_valueRange;
201 	ExecValueStorage			m_value;
202 
203 	Expression*					m_lvalueExpr;
204 	Expression*					m_rvalueExpr;
205 };
206 
207 class ParenOp : public Expression
208 {
209 public:
210 								ParenOp				(GeneratorState& state, ConstValueRangeAccess valueRange);
211 	virtual						~ParenOp			(void);
212 
213 	Expression*					createNextChild		(GeneratorState& state);
214 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
215 
216 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
217 
evaluate(ExecutionContext & execCtx)218 	void						evaluate			(ExecutionContext& execCtx)		{ m_child->evaluate(execCtx);	}
getValue(void) const219 	ExecConstValueAccess		getValue			(void) const					{ return m_child->getValue();	}
220 
221 private:
222 	ValueRange					m_valueRange;
223 	Expression*					m_child;
224 };
225 
226 class SwizzleOp : public Expression
227 {
228 public:
229 								SwizzleOp			(GeneratorState& state, ConstValueRangeAccess valueRange);
230 	virtual						~SwizzleOp			(void);
231 
232 	Expression*					createNextChild		(GeneratorState& state);
233 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
234 
235 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
236 
237 	void						evaluate			(ExecutionContext& execCtx);
getValue(void) const238 	ExecConstValueAccess		getValue			(void) const					{ return m_value.getValue(m_outValueRange.getType()); }
239 
240 private:
241 	ValueRange					m_outValueRange;
242 	int							m_numInputElements;
243 	deUint8						m_swizzle[4];
244 	Expression*					m_child;
245 	ExecValueStorage			m_value;
246 };
247 
248 class TexLookup : public Expression
249 {
250 public:
251 								TexLookup			(GeneratorState& state, ConstValueRangeAccess valueRange);
252 	virtual						~TexLookup			(void);
253 
254 	Expression*					createNextChild		(GeneratorState& state);
255 	void						tokenize			(GeneratorState& state, TokenStream& str) const;
256 
257 	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
258 
259 	void						evaluate			(ExecutionContext& execCtx);
getValue(void) const260 	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueType); }
261 
262 private:
263 	enum Type
264 	{
265 		TYPE_TEXTURE2D,
266 		TYPE_TEXTURE2D_LOD,
267 		TYPE_TEXTURE2D_PROJ,
268 		TYPE_TEXTURE2D_PROJ_LOD,
269 
270 		TYPE_TEXTURECUBE,
271 		TYPE_TEXTURECUBE_LOD,
272 
273 		TYPE_LAST
274 	};
275 
276 	Type						m_type;
277 	const Variable*				m_sampler;
278 	Expression*					m_coordExpr;
279 	Expression*					m_lodBiasExpr;
280 	VariableType				m_valueType;
281 	ExecValueStorage			m_value;
282 };
283 
284 } // rsg
285 
286 #endif // _RSGEXPRESSION_HPP
287