1cb93a386Sopenharmony_ci/* 2cb93a386Sopenharmony_ci * Copyright 2016 Google Inc. 3cb93a386Sopenharmony_ci * 4cb93a386Sopenharmony_ci * Use of this source code is governed by a BSD-style license that can be 5cb93a386Sopenharmony_ci * found in the LICENSE file. 6cb93a386Sopenharmony_ci */ 7cb93a386Sopenharmony_ci 8cb93a386Sopenharmony_ci#ifndef SKSL_BINARYEXPRESSION 9cb93a386Sopenharmony_ci#define SKSL_BINARYEXPRESSION 10cb93a386Sopenharmony_ci 11cb93a386Sopenharmony_ci#include "src/sksl/SkSLLexer.h" 12cb93a386Sopenharmony_ci#include "src/sksl/SkSLOperators.h" 13cb93a386Sopenharmony_ci#include "src/sksl/ir/SkSLExpression.h" 14cb93a386Sopenharmony_ci#include "src/sksl/ir/SkSLFieldAccess.h" 15cb93a386Sopenharmony_ci#include "src/sksl/ir/SkSLIndexExpression.h" 16cb93a386Sopenharmony_ci#include "src/sksl/ir/SkSLSwizzle.h" 17cb93a386Sopenharmony_ci#include "src/sksl/ir/SkSLTernaryExpression.h" 18cb93a386Sopenharmony_ci 19cb93a386Sopenharmony_ci#include <memory> 20cb93a386Sopenharmony_ci 21cb93a386Sopenharmony_cinamespace SkSL { 22cb93a386Sopenharmony_ci 23cb93a386Sopenharmony_ci/** 24cb93a386Sopenharmony_ci * A binary operation. 25cb93a386Sopenharmony_ci */ 26cb93a386Sopenharmony_ciclass BinaryExpression final : public Expression { 27cb93a386Sopenharmony_cipublic: 28cb93a386Sopenharmony_ci inline static constexpr Kind kExpressionKind = Kind::kBinary; 29cb93a386Sopenharmony_ci 30cb93a386Sopenharmony_ci BinaryExpression(int line, std::unique_ptr<Expression> left, Operator op, 31cb93a386Sopenharmony_ci std::unique_ptr<Expression> right, const Type* type) 32cb93a386Sopenharmony_ci : INHERITED(line, kExpressionKind, type) 33cb93a386Sopenharmony_ci , fLeft(std::move(left)) 34cb93a386Sopenharmony_ci , fOperator(op) 35cb93a386Sopenharmony_ci , fRight(std::move(right)) { 36cb93a386Sopenharmony_ci // If we are assigning to a VariableReference, ensure that it is set to Write or ReadWrite. 37cb93a386Sopenharmony_ci SkASSERT(!op.isAssignment() || CheckRef(*this->left())); 38cb93a386Sopenharmony_ci } 39cb93a386Sopenharmony_ci 40cb93a386Sopenharmony_ci // Creates a potentially-simplified form of the expression. Determines the result type 41cb93a386Sopenharmony_ci // programmatically. Typechecks and coerces input expressions; reports errors via ErrorReporter. 42cb93a386Sopenharmony_ci static std::unique_ptr<Expression> Convert(const Context& context, 43cb93a386Sopenharmony_ci std::unique_ptr<Expression> left, 44cb93a386Sopenharmony_ci Operator op, 45cb93a386Sopenharmony_ci std::unique_ptr<Expression> right); 46cb93a386Sopenharmony_ci 47cb93a386Sopenharmony_ci // Creates a potentially-simplified form of the expression. Determines the result type 48cb93a386Sopenharmony_ci // programmatically. Asserts if the expressions do not typecheck or are otherwise invalid. 49cb93a386Sopenharmony_ci static std::unique_ptr<Expression> Make(const Context& context, 50cb93a386Sopenharmony_ci std::unique_ptr<Expression> left, 51cb93a386Sopenharmony_ci Operator op, 52cb93a386Sopenharmony_ci std::unique_ptr<Expression> right); 53cb93a386Sopenharmony_ci 54cb93a386Sopenharmony_ci // Creates a potentially-simplified form of the expression. Result type is passed in. 55cb93a386Sopenharmony_ci // Asserts if the expressions do not typecheck or are otherwise invalid. 56cb93a386Sopenharmony_ci static std::unique_ptr<Expression> Make(const Context& context, 57cb93a386Sopenharmony_ci std::unique_ptr<Expression> left, 58cb93a386Sopenharmony_ci Operator op, 59cb93a386Sopenharmony_ci std::unique_ptr<Expression> right, 60cb93a386Sopenharmony_ci const Type* resultType); 61cb93a386Sopenharmony_ci 62cb93a386Sopenharmony_ci std::unique_ptr<Expression>& left() { 63cb93a386Sopenharmony_ci return fLeft; 64cb93a386Sopenharmony_ci } 65cb93a386Sopenharmony_ci 66cb93a386Sopenharmony_ci const std::unique_ptr<Expression>& left() const { 67cb93a386Sopenharmony_ci return fLeft; 68cb93a386Sopenharmony_ci } 69cb93a386Sopenharmony_ci 70cb93a386Sopenharmony_ci std::unique_ptr<Expression>& right() { 71cb93a386Sopenharmony_ci return fRight; 72cb93a386Sopenharmony_ci } 73cb93a386Sopenharmony_ci 74cb93a386Sopenharmony_ci const std::unique_ptr<Expression>& right() const { 75cb93a386Sopenharmony_ci return fRight; 76cb93a386Sopenharmony_ci } 77cb93a386Sopenharmony_ci 78cb93a386Sopenharmony_ci Operator getOperator() const { 79cb93a386Sopenharmony_ci return fOperator; 80cb93a386Sopenharmony_ci } 81cb93a386Sopenharmony_ci 82cb93a386Sopenharmony_ci bool isConstantOrUniform() const override { 83cb93a386Sopenharmony_ci return this->left()->isConstantOrUniform() && this->right()->isConstantOrUniform(); 84cb93a386Sopenharmony_ci } 85cb93a386Sopenharmony_ci 86cb93a386Sopenharmony_ci bool hasProperty(Property property) const override { 87cb93a386Sopenharmony_ci if (property == Property::kSideEffects && this->getOperator().isAssignment()) { 88cb93a386Sopenharmony_ci return true; 89cb93a386Sopenharmony_ci } 90cb93a386Sopenharmony_ci return this->left()->hasProperty(property) || this->right()->hasProperty(property); 91cb93a386Sopenharmony_ci } 92cb93a386Sopenharmony_ci 93cb93a386Sopenharmony_ci std::unique_ptr<Expression> clone() const override; 94cb93a386Sopenharmony_ci 95cb93a386Sopenharmony_ci String description() const override; 96cb93a386Sopenharmony_ci 97cb93a386Sopenharmony_ciprivate: 98cb93a386Sopenharmony_ci static bool CheckRef(const Expression& expr); 99cb93a386Sopenharmony_ci 100cb93a386Sopenharmony_ci std::unique_ptr<Expression> fLeft; 101cb93a386Sopenharmony_ci Operator fOperator; 102cb93a386Sopenharmony_ci std::unique_ptr<Expression> fRight; 103cb93a386Sopenharmony_ci 104cb93a386Sopenharmony_ci using INHERITED = Expression; 105cb93a386Sopenharmony_ci}; 106cb93a386Sopenharmony_ci 107cb93a386Sopenharmony_ci} // namespace SkSL 108cb93a386Sopenharmony_ci 109cb93a386Sopenharmony_ci#endif 110