Fixes and changes for function declarations, using shared_ptr instead of raw pointers
This commit is contained in:
parent
6936b26cae
commit
1231a77761
|
@ -1,5 +1,8 @@
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
|
|
||||||
#include "Binder.hpp"
|
#include "Binder.hpp"
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
BoundScriptStatement *Binder::Bind(Script* script, ParsedScriptStatement *s, BoundScope* scriptScope) {
|
BoundScriptStatement *Binder::Bind(Script* script, ParsedScriptStatement *s, BoundScope* scriptScope) {
|
||||||
auto binder = Binder();
|
auto binder = Binder();
|
||||||
|
@ -75,22 +78,27 @@ ScriptType* ParseTypeIdentifier(HashedString s){
|
||||||
BoundStatement *Binder::BindFunctionDeclarationStatement(ParsedStatement *statement) {
|
BoundStatement *Binder::BindFunctionDeclarationStatement(ParsedStatement *statement) {
|
||||||
auto functionStatement = (ParsedFunctionDeclarationStatement*) statement;
|
auto functionStatement = (ParsedFunctionDeclarationStatement*) statement;
|
||||||
auto parameters = functionStatement->GetParameters();
|
auto parameters = functionStatement->GetParameters();
|
||||||
vector<ScriptType*> parameterTypes = vector<ScriptType*>(parameters.size());
|
vector<std::shared_ptr<ScriptType>> parameterTypes = vector<std::shared_ptr<ScriptType>>(parameters.size());
|
||||||
vector<int> parameterKeys = vector<int>(parameters.size());
|
vector<std::shared_ptr<BoundVariableKey>> parameterKeys = vector<std::shared_ptr<BoundVariableKey>>(parameters.size());
|
||||||
this->_scope->GoInnerScope();
|
this->_scope->GoInnerScope();
|
||||||
auto scopeId = this->_scope->GetCurrentScope();
|
|
||||||
for (int i = 0; i < parameters.size(); i++){
|
for (int i = 0; i < parameters.size(); i++){
|
||||||
auto var = parameters[i];
|
auto var = parameters[i];
|
||||||
auto parsedType = ParseTypeIdentifier(var->GetType());
|
auto parsedType = ParseTypeIdentifier(var->GetType());
|
||||||
parameterTypes[i] = parsedType;
|
parameterTypes[i] = std::shared_ptr<ScriptType>(parsedType);
|
||||||
parameterKeys[i] = var->GetIdentifier().GetHash();
|
auto parameterAssignment = this->_scope->CreateExplicitLocal(var->GetIdentifier().GetHash(), *parsedType);
|
||||||
this->_scope->CreateExplicitLocal(var->GetIdentifier().GetHash(), *parsedType);
|
if (parameterAssignment.GetResult() == VariableAssignmentResult::Ok){
|
||||||
|
parameterKeys[i] = std::shared_ptr<BoundVariableKey>(parameterAssignment.GetKey());
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
//TODO: log error
|
||||||
|
continue;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
auto boundBlock = this -> BindBlockStatement(functionStatement->GetBlock());
|
auto boundBlock = this -> BindBlockStatement(functionStatement->GetBlock());
|
||||||
this->_scope->GoOuterScope();
|
this->_scope->GoOuterScope();
|
||||||
auto identifier = functionStatement->GetIdentifier();
|
auto identifier = functionStatement->GetIdentifier();
|
||||||
auto returnType = new ScriptType(TypeClass::Nil);
|
auto returnType = std::make_shared<ScriptType>(TypeClass::Nil);
|
||||||
auto type = new FunctionScriptType(returnType, parameterTypes, parameterKeys, scopeId);
|
auto type = new FunctionScriptType(returnType, parameterTypes, parameterKeys);
|
||||||
auto assignment = this->_scope->AssignVariable(identifier.GetHash(), *type);
|
auto assignment = this->_scope->AssignVariable(identifier.GetHash(), *type);
|
||||||
if (assignment.GetResult() == VariableAssignmentResult::Ok){
|
if (assignment.GetResult() == VariableAssignmentResult::Ok){
|
||||||
return new BoundFunctionDeclarationStatement(type, assignment.GetKey(), (BoundBlockStatement*)boundBlock);
|
return new BoundFunctionDeclarationStatement(type, assignment.GetKey(), (BoundBlockStatement*)boundBlock);
|
||||||
|
|
|
@ -0,0 +1,43 @@
|
||||||
|
|
||||||
|
#ifndef PORYGONLANG_BOUNDFUNCTIONDECLARATIONSTATEMENT_HPP
|
||||||
|
#define PORYGONLANG_BOUNDFUNCTIONDECLARATIONSTATEMENT_HPP
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
|
#include "BoundStatement.hpp"
|
||||||
|
|
||||||
|
class BoundFunctionDeclarationStatement : public BoundStatement{
|
||||||
|
BoundVariableKey* _key;
|
||||||
|
std::shared_ptr<BoundBlockStatement> _block;
|
||||||
|
FunctionScriptType* _type;
|
||||||
|
public:
|
||||||
|
BoundFunctionDeclarationStatement(FunctionScriptType* type, BoundVariableKey* key, BoundBlockStatement* block){
|
||||||
|
_key = key;
|
||||||
|
_block = shared_ptr<BoundBlockStatement>(block);
|
||||||
|
_type = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
~BoundFunctionDeclarationStatement() final{
|
||||||
|
delete _key;
|
||||||
|
delete _type;
|
||||||
|
}
|
||||||
|
|
||||||
|
BoundStatementKind GetKind() final{
|
||||||
|
return BoundStatementKind ::FunctionDeclaration;
|
||||||
|
}
|
||||||
|
|
||||||
|
BoundVariableKey* GetKey(){
|
||||||
|
return _key;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::shared_ptr<BoundBlockStatement> GetBlock(){
|
||||||
|
return _block;
|
||||||
|
}
|
||||||
|
|
||||||
|
FunctionScriptType* GetType(){
|
||||||
|
return _type;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
#include "BoundStatement.hpp"
|
||||||
|
|
||||||
|
#endif //PORYGONLANG_BOUNDFUNCTIONDECLARATIONSTATEMENT_HPP
|
|
@ -8,6 +8,7 @@
|
||||||
#include "../BoundExpressions/BoundExpression.hpp"
|
#include "../BoundExpressions/BoundExpression.hpp"
|
||||||
#include "../BoundVariables/BoundVariableKey.hpp"
|
#include "../BoundVariables/BoundVariableKey.hpp"
|
||||||
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
enum class BoundStatementKind{
|
enum class BoundStatementKind{
|
||||||
|
@ -115,32 +116,6 @@ public:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class BoundFunctionDeclarationStatement : public BoundStatement{
|
#include "BoundFunctionDeclarationStatement.hpp"
|
||||||
BoundVariableKey* _key;
|
|
||||||
BoundBlockStatement* _block;
|
|
||||||
FunctionScriptType* _type;
|
|
||||||
public:
|
|
||||||
BoundFunctionDeclarationStatement(FunctionScriptType* type, BoundVariableKey* key, BoundBlockStatement* block){
|
|
||||||
_key = key;
|
|
||||||
_block = block;
|
|
||||||
_type = type;
|
|
||||||
}
|
|
||||||
|
|
||||||
BoundStatementKind GetKind() final{
|
|
||||||
return BoundStatementKind ::FunctionDeclaration;
|
|
||||||
}
|
|
||||||
|
|
||||||
BoundVariableKey* GetKey(){
|
|
||||||
return _key;
|
|
||||||
}
|
|
||||||
|
|
||||||
BoundBlockStatement* GetBlock(){
|
|
||||||
return _block;
|
|
||||||
}
|
|
||||||
|
|
||||||
FunctionScriptType* GetType(){
|
|
||||||
return _type;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif //PORYGONLANG_BOUNDSTATEMENT_HPP
|
#endif //PORYGONLANG_BOUNDSTATEMENT_HPP
|
||||||
|
|
|
@ -30,7 +30,11 @@ void BoundScope::GoInnerScope() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void BoundScope::GoOuterScope() {
|
void BoundScope::GoOuterScope() {
|
||||||
_localScope[_currentScope - 1]->clear();
|
auto scope = _localScope[_currentScope - 1];
|
||||||
|
for (auto v : *scope){
|
||||||
|
delete v.second;
|
||||||
|
}
|
||||||
|
scope->clear();
|
||||||
_currentScope--;
|
_currentScope--;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,16 +2,18 @@
|
||||||
#ifndef PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP
|
#ifndef PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP
|
||||||
#define PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP
|
#define PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
#include "../../ScriptType.hpp"
|
#include "../../ScriptType.hpp"
|
||||||
#include "EvalValue.hpp"
|
#include "EvalValue.hpp"
|
||||||
#include "../../Binder/BoundStatements/BoundStatement.hpp"
|
#include "../../Binder/BoundStatements/BoundStatement.hpp"
|
||||||
#include "../Evaluator.hpp"
|
#include "../Evaluator.hpp"
|
||||||
|
|
||||||
|
|
||||||
class ScriptFunctionEvalValue : public EvalValue{
|
class ScriptFunctionEvalValue : public EvalValue{
|
||||||
BoundBlockStatement* _innerBlock;
|
std::shared_ptr<BoundBlockStatement> _innerBlock;
|
||||||
FunctionScriptType _type;
|
FunctionScriptType _type;
|
||||||
public:
|
public:
|
||||||
explicit ScriptFunctionEvalValue(BoundBlockStatement* innerBlock, const FunctionScriptType& type)
|
explicit ScriptFunctionEvalValue(std::shared_ptr<BoundBlockStatement> innerBlock, const FunctionScriptType& type)
|
||||||
: _type(type)
|
: _type(type)
|
||||||
{
|
{
|
||||||
_innerBlock = innerBlock;
|
_innerBlock = innerBlock;
|
||||||
|
@ -21,10 +23,6 @@ public:
|
||||||
return new ScriptFunctionEvalValue(_innerBlock, _type);
|
return new ScriptFunctionEvalValue(_innerBlock, _type);
|
||||||
}
|
}
|
||||||
|
|
||||||
~ScriptFunctionEvalValue() final{
|
|
||||||
delete _innerBlock;
|
|
||||||
}
|
|
||||||
|
|
||||||
ScriptType* GetType() final{
|
ScriptType* GetType() final{
|
||||||
return &_type;
|
return &_type;
|
||||||
};
|
};
|
||||||
|
@ -42,13 +40,13 @@ public:
|
||||||
for (int i = 0; i < parameterTypes.size() && i < parameterKeys.size() && i < parameters.size(); i++){
|
for (int i = 0; i < parameterTypes.size() && i < parameterKeys.size() && i < parameters.size(); i++){
|
||||||
auto parameter = parameters[i];
|
auto parameter = parameters[i];
|
||||||
auto requiredType = parameterTypes[i];
|
auto requiredType = parameterTypes[i];
|
||||||
if (parameter->GetType() != requiredType){
|
if (parameter->GetType() != requiredType.get()){
|
||||||
throw EvaluationException("Passed wrong type to function.");
|
throw EvaluationException("Passed wrong type to function.");
|
||||||
}
|
}
|
||||||
auto key = parameterKeys[i];
|
auto key = parameterKeys[i];
|
||||||
scope->CreateVariable(_type.GetScopeId(), key, parameter->Clone());
|
scope->CreateVariable(key->GetScopeId(), key->GetIdentifier(), parameter->Clone());
|
||||||
}
|
}
|
||||||
evaluator->EvaluateBlockStatement(_innerBlock);
|
evaluator->EvaluateBlockStatement(_innerBlock.get());
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -215,5 +215,10 @@ public:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class FunctionCallExpression : public ParsedExpression{
|
||||||
|
|
||||||
|
public:
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
#endif //PORYGONLANG_PARSEDEXPRESSION_HPP
|
#endif //PORYGONLANG_PARSEDEXPRESSION_HPP
|
||||||
|
|
|
@ -1,8 +1,12 @@
|
||||||
|
#include <utility>
|
||||||
|
|
||||||
#ifndef PORYGONLANG_SCRIPTTYPE_HPP
|
#ifndef PORYGONLANG_SCRIPTTYPE_HPP
|
||||||
#define PORYGONLANG_SCRIPTTYPE_HPP
|
#define PORYGONLANG_SCRIPTTYPE_HPP
|
||||||
|
|
||||||
#include <utility>
|
#include <utility>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <memory>
|
||||||
|
#include "Binder/BoundVariables/BoundVariableKey.hpp"
|
||||||
|
|
||||||
enum class TypeClass{
|
enum class TypeClass{
|
||||||
Error,
|
Error,
|
||||||
|
@ -58,40 +62,28 @@ public:
|
||||||
};
|
};
|
||||||
|
|
||||||
class FunctionScriptType : public ScriptType{
|
class FunctionScriptType : public ScriptType{
|
||||||
ScriptType* _returnType;
|
std::shared_ptr<ScriptType> _returnType;
|
||||||
std::vector<ScriptType*> _parameterTypes;
|
std::vector<std::shared_ptr<ScriptType>> _parameterTypes;
|
||||||
std::vector<int> _parameterKeys;
|
std::vector<std::shared_ptr<BoundVariableKey>> _parameterKeys;
|
||||||
int _scopeId;
|
|
||||||
public:
|
public:
|
||||||
FunctionScriptType(ScriptType* returnType, std::vector<ScriptType*> parameterTypes, std::vector<int> parameterKeys, int scopeId)
|
FunctionScriptType(std::shared_ptr<ScriptType> returnType, std::vector<std::shared_ptr<ScriptType>> parameterTypes,
|
||||||
|
std::vector<std::shared_ptr<BoundVariableKey>> parameterKeys)
|
||||||
: ScriptType(TypeClass::Function){
|
: ScriptType(TypeClass::Function){
|
||||||
_returnType = returnType;
|
_returnType = std::move(returnType);
|
||||||
_parameterTypes = std::move(parameterTypes);
|
_parameterTypes = std::move(parameterTypes);
|
||||||
_parameterKeys = std::move(parameterKeys);
|
_parameterKeys = std::move(parameterKeys);
|
||||||
_scopeId = scopeId;
|
|
||||||
}
|
}
|
||||||
~FunctionScriptType() final{
|
|
||||||
delete _returnType;
|
|
||||||
for (auto t: _parameterTypes){
|
|
||||||
delete t;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ScriptType* GetReturnType(){
|
ScriptType* GetReturnType(){
|
||||||
return _returnType;
|
return _returnType.get();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<ScriptType*> GetParameterTypes(){
|
std::vector<std::shared_ptr<ScriptType>> GetParameterTypes(){
|
||||||
return _parameterTypes;
|
return _parameterTypes;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<int> GetParameterKeys(){
|
std::vector<std::shared_ptr<BoundVariableKey>> GetParameterKeys(){
|
||||||
return _parameterKeys;
|
return _parameterKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
int GetScopeId(){
|
|
||||||
return _scopeId;
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif //PORYGONLANG_SCRIPTTYPE_HPP
|
#endif //PORYGONLANG_SCRIPTTYPE_HPP
|
||||||
|
|
|
@ -12,6 +12,4 @@ TEST_CASE( "Define script function", "[integration]" ) {
|
||||||
delete script;
|
delete script;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in New Issue