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
44namespace rsg
45{
46
47// \todo [2011-06-10 pyry] Declare in ShaderParameters?
48const float unusedValueWeight = 0.05f;
49
50class Expression
51{
52public:
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;
62	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
68class VariableAccess : public Expression
69{
70public:
71	virtual						~VariableAccess		(void) {}
72
73	Expression*					createNextChild		(GeneratorState& state)							{ DE_UNREF(state); return DE_NULL;						}
74	void						tokenize			(GeneratorState& state, TokenStream& str) const	{ DE_UNREF(state); str << Token(m_variable->getName());	}
75
76	void						evaluate			(ExecutionContext& ctx);
77	ExecConstValueAccess		getValue			(void) const									{ return m_valueAccess;									}
78	ExecValueAccess				getLValue			(void) const									{ return m_valueAccess;									}
79
80protected:
81								VariableAccess		(void) : m_variable(DE_NULL) {}
82
83	const Variable*				m_variable;
84	ExecValueAccess				m_valueAccess;
85};
86
87class VariableRead : public VariableAccess
88{
89public:
90								VariableRead		(GeneratorState& state, ConstValueRangeAccess valueRange);
91								VariableRead		(const Variable* variable);
92	virtual						~VariableRead		(void) {}
93
94	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
95};
96
97class VariableWrite : public VariableAccess
98{
99public:
100								VariableWrite		(GeneratorState& state, ConstValueRangeAccess valueRange);
101	virtual						~VariableWrite		(void) {}
102
103	static float				getWeight			(const GeneratorState& state, ConstValueRangeAccess valueRange);
104};
105
106class FloatLiteral : public Expression
107{
108public:
109								FloatLiteral		(GeneratorState& state, ConstValueRangeAccess valueRange);
110	virtual						~FloatLiteral		(void) {}
111
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
117	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
118	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_FLOAT)); }
119
120private:
121	ExecValueStorage			m_value;
122};
123
124class IntLiteral : public Expression
125{
126public:
127								IntLiteral			(GeneratorState& state, ConstValueRangeAccess valueRange);
128	virtual						~IntLiteral			(void) {}
129
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
135	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
136	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_INT)); }
137
138private:
139	ExecValueStorage			m_value;
140};
141
142class BoolLiteral : public Expression
143{
144public:
145								BoolLiteral			(GeneratorState& state, ConstValueRangeAccess valueRange);
146	virtual						~BoolLiteral		(void) {}
147
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
153	void						evaluate			(ExecutionContext& ctx) { DE_UNREF(ctx); }
154	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_BOOL)); }
155
156private:
157	ExecValueStorage			m_value;
158};
159
160class ConstructorOp : public Expression
161{
162public:
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);
172	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueRange.getType()); }
173
174private:
175	ValueRange					m_valueRange;
176	ExecValueStorage			m_value;
177
178	std::vector<ValueRange>		m_inputValueRanges;
179	std::vector<Expression*>	m_inputExpressions;
180};
181
182class AssignOp : public Expression
183{
184public:
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);
197	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueRange.getType()); }
198
199private:
200	ValueRange					m_valueRange;
201	ExecValueStorage			m_value;
202
203	Expression*					m_lvalueExpr;
204	Expression*					m_rvalueExpr;
205};
206
207class ParenOp : public Expression
208{
209public:
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
218	void						evaluate			(ExecutionContext& execCtx)		{ m_child->evaluate(execCtx);	}
219	ExecConstValueAccess		getValue			(void) const					{ return m_child->getValue();	}
220
221private:
222	ValueRange					m_valueRange;
223	Expression*					m_child;
224};
225
226class SwizzleOp : public Expression
227{
228public:
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);
238	ExecConstValueAccess		getValue			(void) const					{ return m_value.getValue(m_outValueRange.getType()); }
239
240private:
241	ValueRange					m_outValueRange;
242	int							m_numInputElements;
243	deUint8						m_swizzle[4];
244	Expression*					m_child;
245	ExecValueStorage			m_value;
246};
247
248class TexLookup : public Expression
249{
250public:
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);
260	ExecConstValueAccess		getValue			(void) const { return m_value.getValue(m_valueType); }
261
262private:
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