You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
290 lines
9.4 KiB
290 lines
9.4 KiB
4 months ago
|
#ifndef _RSGEXPRESSION_HPP
|
||
|
#define _RSGEXPRESSION_HPP
|
||
|
/*-------------------------------------------------------------------------
|
||
|
* drawElements Quality Program Random Shader Generator
|
||
|
* ----------------------------------------------------
|
||
|
*
|
||
|
* Copyright 2014 The Android Open Source Project
|
||
|
*
|
||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||
|
* you may not use this file except in compliance with the License.
|
||
|
* You may obtain a copy of the License at
|
||
|
*
|
||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||
|
*
|
||
|
* Unless required by applicable law or agreed to in writing, software
|
||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||
|
* See the License for the specific language governing permissions and
|
||
|
* limitations under the License.
|
||
|
*
|
||
|
*//*!
|
||
|
* \file
|
||
|
* \brief Expressions.
|
||
|
*
|
||
|
* Creating expressions:
|
||
|
* + Children must be created in in reverse evaluation order.
|
||
|
* - Must be tokenized / evaluated taking that order in account.
|
||
|
*
|
||
|
* Evaluation:
|
||
|
* + Done recursively. (Do we have enough stack?)
|
||
|
* + R-values: Nodes must implement getValue() in some way. Value
|
||
|
* must be valid after evaluate().
|
||
|
* + L-values: Valid writable value access proxy must be returned after
|
||
|
* evaluate().
|
||
|
*//*--------------------------------------------------------------------*/
|
||
|
|
||
|
#include "rsgDefs.hpp"
|
||
|
#include "rsgGeneratorState.hpp"
|
||
|
#include "rsgVariableValue.hpp"
|
||
|
#include "rsgVariable.hpp"
|
||
|
#include "rsgVariableManager.hpp"
|
||
|
#include "rsgExecutionContext.hpp"
|
||
|
|
||
|
namespace rsg
|
||
|
{
|
||
|
|
||
|
// \todo [2011-06-10 pyry] Declare in ShaderParameters?
|
||
|
const float unusedValueWeight = 0.05f;
|
||
|
|
||
|
class Expression
|
||
|
{
|
||
|
public:
|
||
|
virtual ~Expression (void);
|
||
|
|
||
|
// Shader generation API
|
||
|
virtual Expression* createNextChild (GeneratorState& state) = DE_NULL;
|
||
|
virtual void tokenize (GeneratorState& state, TokenStream& str) const = DE_NULL;
|
||
|
|
||
|
// Execution API
|
||
|
virtual void evaluate (ExecutionContext& ctx) = DE_NULL;
|
||
|
virtual ExecConstValueAccess getValue (void) const = DE_NULL;
|
||
|
virtual ExecValueAccess getLValue (void) const { DE_ASSERT(DE_FALSE); throw Exception("Expression::getLValue(): not L-value node"); }
|
||
|
|
||
|
static Expression* createRandom (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
static Expression* createRandomLValue (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
};
|
||
|
|
||
|
class VariableAccess : public Expression
|
||
|
{
|
||
|
public:
|
||
|
virtual ~VariableAccess (void) {}
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const { DE_UNREF(state); str << Token(m_variable->getName()); }
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx);
|
||
|
ExecConstValueAccess getValue (void) const { return m_valueAccess; }
|
||
|
ExecValueAccess getLValue (void) const { return m_valueAccess; }
|
||
|
|
||
|
protected:
|
||
|
VariableAccess (void) : m_variable(DE_NULL) {}
|
||
|
|
||
|
const Variable* m_variable;
|
||
|
ExecValueAccess m_valueAccess;
|
||
|
};
|
||
|
|
||
|
class VariableRead : public VariableAccess
|
||
|
{
|
||
|
public:
|
||
|
VariableRead (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
VariableRead (const Variable* variable);
|
||
|
virtual ~VariableRead (void) {}
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
};
|
||
|
|
||
|
class VariableWrite : public VariableAccess
|
||
|
{
|
||
|
public:
|
||
|
VariableWrite (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~VariableWrite (void) {}
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
};
|
||
|
|
||
|
class FloatLiteral : public Expression
|
||
|
{
|
||
|
public:
|
||
|
FloatLiteral (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
FloatLiteral (float customValue);
|
||
|
virtual ~FloatLiteral (void) {}
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx) { DE_UNREF(ctx); }
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_FLOAT)); }
|
||
|
|
||
|
private:
|
||
|
ExecValueStorage m_value;
|
||
|
};
|
||
|
|
||
|
class IntLiteral : public Expression
|
||
|
{
|
||
|
public:
|
||
|
IntLiteral (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~IntLiteral (void) {}
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx) { DE_UNREF(ctx); }
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_INT)); }
|
||
|
|
||
|
private:
|
||
|
ExecValueStorage m_value;
|
||
|
};
|
||
|
|
||
|
class BoolLiteral : public Expression
|
||
|
{
|
||
|
public:
|
||
|
BoolLiteral (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
BoolLiteral (bool customValue);
|
||
|
virtual ~BoolLiteral (void) {}
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state) { DE_UNREF(state); return DE_NULL; }
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx) { DE_UNREF(ctx); }
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(VariableType::getScalarType(VariableType::TYPE_BOOL)); }
|
||
|
|
||
|
private:
|
||
|
ExecValueStorage m_value;
|
||
|
};
|
||
|
|
||
|
class ConstructorOp : public Expression
|
||
|
{
|
||
|
public:
|
||
|
ConstructorOp (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~ConstructorOp (void);
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state);
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx);
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(m_valueRange.getType()); }
|
||
|
|
||
|
private:
|
||
|
ValueRange m_valueRange;
|
||
|
ExecValueStorage m_value;
|
||
|
|
||
|
std::vector<ValueRange> m_inputValueRanges;
|
||
|
std::vector<Expression*> m_inputExpressions;
|
||
|
};
|
||
|
|
||
|
class AssignOp : public Expression
|
||
|
{
|
||
|
public:
|
||
|
AssignOp (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~AssignOp (void);
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state);
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
// \todo [2011-02-28 pyry] LValue variant of AssignOp
|
||
|
// static float getLValueWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& ctx);
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(m_valueRange.getType()); }
|
||
|
|
||
|
private:
|
||
|
ValueRange m_valueRange;
|
||
|
ExecValueStorage m_value;
|
||
|
|
||
|
Expression* m_lvalueExpr;
|
||
|
Expression* m_rvalueExpr;
|
||
|
};
|
||
|
|
||
|
class ParenOp : public Expression
|
||
|
{
|
||
|
public:
|
||
|
ParenOp (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~ParenOp (void);
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state);
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
void setChild (Expression* expression);
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& execCtx) { m_child->evaluate(execCtx); }
|
||
|
ExecConstValueAccess getValue (void) const { return m_child->getValue(); }
|
||
|
|
||
|
private:
|
||
|
ValueRange m_valueRange;
|
||
|
Expression* m_child;
|
||
|
};
|
||
|
|
||
|
class SwizzleOp : public Expression
|
||
|
{
|
||
|
public:
|
||
|
SwizzleOp (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~SwizzleOp (void);
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state);
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& execCtx);
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(m_outValueRange.getType()); }
|
||
|
|
||
|
private:
|
||
|
ValueRange m_outValueRange;
|
||
|
int m_numInputElements;
|
||
|
deUint8 m_swizzle[4];
|
||
|
Expression* m_child;
|
||
|
ExecValueStorage m_value;
|
||
|
};
|
||
|
|
||
|
class TexLookup : public Expression
|
||
|
{
|
||
|
public:
|
||
|
TexLookup (GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
virtual ~TexLookup (void);
|
||
|
|
||
|
Expression* createNextChild (GeneratorState& state);
|
||
|
void tokenize (GeneratorState& state, TokenStream& str) const;
|
||
|
|
||
|
static float getWeight (const GeneratorState& state, ConstValueRangeAccess valueRange);
|
||
|
|
||
|
void evaluate (ExecutionContext& execCtx);
|
||
|
ExecConstValueAccess getValue (void) const { return m_value.getValue(m_valueType); }
|
||
|
|
||
|
private:
|
||
|
enum Type
|
||
|
{
|
||
|
TYPE_TEXTURE2D,
|
||
|
TYPE_TEXTURE2D_LOD,
|
||
|
TYPE_TEXTURE2D_PROJ,
|
||
|
TYPE_TEXTURE2D_PROJ_LOD,
|
||
|
|
||
|
TYPE_TEXTURECUBE,
|
||
|
TYPE_TEXTURECUBE_LOD,
|
||
|
|
||
|
TYPE_LAST
|
||
|
};
|
||
|
|
||
|
Type m_type;
|
||
|
const Variable* m_sampler;
|
||
|
Expression* m_coordExpr;
|
||
|
Expression* m_lodBiasExpr;
|
||
|
VariableType m_valueType;
|
||
|
ExecValueStorage m_value;
|
||
|
};
|
||
|
|
||
|
} // rsg
|
||
|
|
||
|
#endif // _RSGEXPRESSION_HPP
|