/* * Copyright (c) 2021 Huawei Device Co., Ltd. * 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. */ #include "script_expression.h" #include "script_function.h" #include "script_interpreter.h" #include "script_utils.h" using namespace std; namespace Uscript { UScriptExpression::UScriptExpression(ExpressionType expressType) : expressType_(expressType) {} UScriptExpression::~UScriptExpression() {} UScriptExpression* AssignExpression::CreateExpression(const std::string identifier, UScriptExpression *expression) { return new AssignExpression(identifier, expression); } void AssignExpression::AddIdentifier(const std::string &identifier) { multipleIdentifiers_.push_back(identifier); } UScriptExpression* AssignExpression::AddIdentifier(UScriptExpression *expression, const std::string identifier) { auto assign = reinterpret_cast<AssignExpression*>(expression); if (assign != nullptr) { assign->AddIdentifier(identifier); } return assign; } // binary operator UScriptExpression* BinaryExpression::CreateExpression(ExpressionAction action, UScriptExpression *left, UScriptExpression *right) { return new BinaryExpression(action, left, right); } UScriptExpression* FunctionCallExpression::CreateExpression(const std::string identifier, ScriptParams *params) { return new FunctionCallExpression(identifier, params); } UScriptValuePtr UScriptExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { return std::make_shared<UScriptValue>(UScriptValue::VALUE_TYPE_ERROR); } UScriptValuePtr IntegerExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { return std::make_shared<IntegerValue>(this->value_); } UScriptValuePtr FloatExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { return std::make_shared<FloatValue>(this->value_); } UScriptValuePtr StringExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { return std::make_shared<StringValue>(this->value_); } UScriptValuePtr IdentifierExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { INTERPRETER_LOGI(inter, local, "Execute statements identifier %s ", identifier_.c_str()); UScriptValuePtr variable = inter.FindVariable(local, identifier_); INTERPRETER_LOGI(inter, local, "IdentifierExpression::Execute '%s = %s ' ", identifier_.c_str(), UScriptValue::ScriptToString(variable).c_str()); if (variable != nullptr) { return variable; } return std::make_shared<UScriptValue>(UScriptValue::VALUE_TYPE_ERROR); } int32_t IdentifierExpression::GetIdentifierName(UScriptExpression *expression, std::string &name) { if (expression->GetExpressType() != EXPRESSION_TYPE_IDENTIFIER) { return USCRIPT_INVALID_PARAM; } else { auto identifier = reinterpret_cast<IdentifierExpression*>(expression); if (identifier != nullptr) { name = identifier->GetIdentifier(); return USCRIPT_SUCCESS; } } return USCRIPT_INVALID_PARAM; } UScriptValuePtr AssignExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { UScriptValuePtr result = expression_->Execute(inter, local); INTERPRETER_LOGI(inter, local, "AssignExpression::Execute update local var '%s = %s ' ", identifier_.c_str(), UScriptValue::ScriptToString(result).c_str()); if (result->GetValueType() == UScriptValue::VALUE_TYPE_ERROR) { return result; } UScriptValuePtr var = inter.FindVariable(local, identifier_); if (var != nullptr) { inter.UpdateVariable(local, identifier_, result); return result; } std::vector<std::string> identifiers; identifiers.push_back(identifier_); identifiers.insert(identifiers.begin() + 1, multipleIdentifiers_.begin(), multipleIdentifiers_.end()); size_t index = 0; local->UpdateVariables(inter, result, identifiers, index); return result; } UScriptValuePtr BinaryExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { static std::vector<std::string> opStr = { "", "add", "sub", "mul", "div", ">", ">=", "<", "<=", "==", "!=", "&&", "||" }; UScriptValuePtr left; UScriptValuePtr right; INTERPRETER_LOGI(inter, local, "BinaryExpression::Execute "); if (left_ != nullptr) { left = left_->Execute(inter, local); } if (action_ == OR_OPERATOR && left != nullptr && left->IsTrue()) { INTERPRETER_LOGE(inter, local, "BinaryExpression::Execute left:%s %s", UScriptValue::ScriptToString(left).c_str(), opStr[action_].c_str()); return std::make_shared<IntegerValue>(1); } if (right_ != nullptr) { right = right_->Execute(inter, local); } if (left != nullptr && right != nullptr) { UScriptValuePtr value = left->Computer(action_, right); INTERPRETER_LOGI(inter, local, "BinaryExpression::Execute left:%s %s right:%s result:%s", UScriptValue::ScriptToString(left).c_str(), opStr[action_].c_str(), UScriptValue::ScriptToString(right).c_str(), UScriptValue::ScriptToString(value).c_str()); return value; } return std::make_shared<ErrorValue>(USCRIPT_ERROR_INTERPRET); } UScriptValuePtr FunctionCallExpression::Execute(ScriptInterpreter &inter, UScriptContextPtr local) { UScriptValuePtr v; INTERPRETER_LOGI(inter, local, "FunctionCallExpression::Execute %s ", functionName_.c_str()); if (inter.IsNativeFunction(functionName_)) { return inter.ExecuteNativeFunc(local, functionName_, params_); } return inter.ExecuteFunction(local, functionName_, params_); } BinaryExpression::~BinaryExpression() { delete left_; delete right_; } AssignExpression::~AssignExpression() { delete this->expression_; } FunctionCallExpression::~FunctionCallExpression() { delete params_; } } // namespace Uscript