Implements binding unary expressions
This commit is contained in:
@@ -1,8 +1,9 @@
|
||||
|
||||
#include "Binder.hpp"
|
||||
|
||||
BoundScriptStatement *Binder::Bind(ParsedScriptStatement *s) {
|
||||
BoundScriptStatement *Binder::Bind(Script* script, ParsedScriptStatement *s) {
|
||||
auto binder = Binder();
|
||||
binder.ScriptData = script;
|
||||
auto statements = s->GetStatements();
|
||||
vector<BoundStatement*> boundStatements (statements.size());
|
||||
for (int i = 0; i < statements.size(); i++){
|
||||
@@ -44,6 +45,8 @@ BoundExpression* Binder::BindExpression(ParsedExpression* expression){
|
||||
|
||||
case ParsedExpressionKind ::Binary:
|
||||
return this -> BindBinaryOperator((BinaryExpression*)expression);
|
||||
case ParsedExpressionKind ::Unary:
|
||||
return this -> BindUnaryOperator((UnaryExpression*)expression);
|
||||
|
||||
case ParsedExpressionKind ::Parenthesized:
|
||||
return BindExpression(((ParenthesizedExpression*)expression)->GetInnerExpression());
|
||||
@@ -67,10 +70,10 @@ BoundExpression* Binder::BindBinaryOperator(BinaryExpression* expression){
|
||||
auto rightNumeric = (NumericScriptType*)boundRightType;
|
||||
if (leftNumeric->IsAwareOfFloat() && rightNumeric->IsAwareOfFloat()){
|
||||
return new BoundBinaryExpression(boundLeft, boundRight,
|
||||
BoundBinaryOperator::Addition, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
BoundBinaryOperation::Addition, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
}
|
||||
else{
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::Addition, new NumericScriptType(false, false));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::Addition, new NumericScriptType(false, false));
|
||||
}
|
||||
}
|
||||
//TODO: String Concatenation
|
||||
@@ -81,10 +84,10 @@ BoundExpression* Binder::BindBinaryOperator(BinaryExpression* expression){
|
||||
auto rightNumeric = (NumericScriptType*)boundRightType;
|
||||
if (leftNumeric->IsAwareOfFloat() && rightNumeric->IsAwareOfFloat()){
|
||||
return new BoundBinaryExpression(boundLeft, boundRight,
|
||||
BoundBinaryOperator::Subtraction, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
BoundBinaryOperation::Subtraction, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
}
|
||||
else{
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::Subtraction, new NumericScriptType(false, false));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::Subtraction, new NumericScriptType(false, false));
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -94,10 +97,10 @@ BoundExpression* Binder::BindBinaryOperator(BinaryExpression* expression){
|
||||
auto rightNumeric = (NumericScriptType*)boundRightType;
|
||||
if (leftNumeric->IsAwareOfFloat() && rightNumeric->IsAwareOfFloat()){
|
||||
return new BoundBinaryExpression(boundLeft, boundRight,
|
||||
BoundBinaryOperator::Multiplication, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
BoundBinaryOperation::Multiplication, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
}
|
||||
else{
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::Multiplication, new NumericScriptType(false, false));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::Multiplication, new NumericScriptType(false, false));
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -107,26 +110,57 @@ BoundExpression* Binder::BindBinaryOperator(BinaryExpression* expression){
|
||||
auto rightNumeric = (NumericScriptType*)boundRightType;
|
||||
if (leftNumeric->IsAwareOfFloat() && rightNumeric->IsAwareOfFloat()){
|
||||
return new BoundBinaryExpression(boundLeft, boundRight,
|
||||
BoundBinaryOperator::Division, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
BoundBinaryOperation::Division, new NumericScriptType(true, leftNumeric->IsFloat() || rightNumeric->IsFloat()));
|
||||
}
|
||||
else{
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::Division, new NumericScriptType(false, false));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::Division, new NumericScriptType(false, false));
|
||||
}
|
||||
}
|
||||
break;
|
||||
case BinaryOperatorKind ::Equality:
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::Equality, new ScriptType(TypeClass::Bool));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::Equality, new ScriptType(TypeClass::Bool));
|
||||
case BinaryOperatorKind ::LogicalAnd:
|
||||
if (boundLeftType->GetClass() == TypeClass::Bool && boundRightType->GetClass() == TypeClass::Bool)
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::LogicalAnd, new ScriptType(TypeClass::Bool));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::LogicalAnd, new ScriptType(TypeClass::Bool));
|
||||
break;
|
||||
case BinaryOperatorKind ::LogicalOr:
|
||||
if (boundLeftType->GetClass() == TypeClass::Bool && boundRightType->GetClass() == TypeClass::Bool)
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperator::LogicalOr, new ScriptType(TypeClass::Bool));
|
||||
return new BoundBinaryExpression(boundLeft, boundRight, BoundBinaryOperation::LogicalOr, new ScriptType(TypeClass::Bool));
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
//TODO: Log error
|
||||
return new BoundBadExpression(boundLeft->GetStartPosition(), boundRight->GetEndPosition() - boundLeft->GetStartPosition());
|
||||
this -> ScriptData -> Diagnostics->LogError(DiagnosticCode::NoBinaryOperationFound, expression->GetStartPosition(), expression->GetLength());
|
||||
return new BoundBadExpression(expression->GetStartPosition(), expression->GetLength());
|
||||
}
|
||||
|
||||
BoundExpression* Binder::BindUnaryOperator(UnaryExpression* expression){
|
||||
auto operand = this -> BindExpression(expression->GetOperand());
|
||||
auto operandType = operand -> GetType();
|
||||
switch (expression->GetOperatorKind()){
|
||||
case UnaryOperatorKind ::Identity:
|
||||
if (operandType->GetClass() == TypeClass::Number){
|
||||
// Identity won't change anything during evaluation, so just return the inner operand.
|
||||
return operand;
|
||||
}
|
||||
break;
|
||||
case UnaryOperatorKind ::Negation:
|
||||
if (operandType->GetClass() == TypeClass::Number){
|
||||
auto innerType = (NumericScriptType*)operandType;
|
||||
return new BoundUnaryExpression(operand, BoundUnaryOperation::Negation, new NumericScriptType(innerType->IsAwareOfFloat(),
|
||||
innerType->IsFloat()), expression->GetStartPosition(), expression->GetLength());
|
||||
}
|
||||
break;
|
||||
case UnaryOperatorKind ::LogicalNegation:
|
||||
if (operandType->GetClass() == TypeClass::Bool){
|
||||
return new BoundUnaryExpression(operand, BoundUnaryOperation::LogicalNegation, new ScriptType(TypeClass::Bool),
|
||||
expression->GetStartPosition(), expression->GetLength());
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
this -> ScriptData -> Diagnostics->LogError(DiagnosticCode::NoUnaryOperationFound, expression->GetStartPosition(), expression->GetLength());
|
||||
return new BoundBadExpression(expression->GetStartPosition(), expression->GetLength());
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user