diff --git a/src/Evaluator/EvalValues/EvalValue.cpp b/src/Evaluator/EvalValues/EvalValue.cpp index d26b34b..1c2f52c 100644 --- a/src/Evaluator/EvalValues/EvalValue.cpp +++ b/src/Evaluator/EvalValues/EvalValue.cpp @@ -2,6 +2,7 @@ #include "NumericEvalValue.hpp" #include "StringEvalValue.hpp" #include +#include namespace Porygon::Evaluation { @@ -26,6 +27,7 @@ namespace Porygon::Evaluation { return v->EvaluateString()->c_str(); } + EvalValue *CreateIntegerEvalValue(long l) { return new IntegerEvalValue(l); } diff --git a/src/Evaluator/EvalValues/ScriptFunctionEvalValue.hpp b/src/Evaluator/EvalValues/ScriptFunctionEvalValue.hpp index 8cb3d3b..2f1dbc9 100644 --- a/src/Evaluator/EvalValues/ScriptFunctionEvalValue.hpp +++ b/src/Evaluator/EvalValues/ScriptFunctionEvalValue.hpp @@ -1,6 +1,3 @@ -#include - -#include #ifndef PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP #define PORYGONLANG_SCRIPTFUNCTIONEVALVALUE_HPP @@ -10,7 +7,6 @@ #include "../../ScriptType.hpp" #include "EvalValue.hpp" #include "../../Binder/BoundStatements/BoundStatement.hpp" -#include "../Evaluator.hpp" #include "../EvaluationScope/EvaluationScope.hpp" using namespace std; diff --git a/src/Evaluator/Evaluator.cpp b/src/Evaluator/Evaluator.cpp index 54957fb..ed058ad 100644 --- a/src/Evaluator/Evaluator.cpp +++ b/src/Evaluator/Evaluator.cpp @@ -285,8 +285,8 @@ namespace Porygon::Evaluation { } auto type = std::dynamic_pointer_cast(function->GetType()); - auto parameterTypes = type->GetParameterTypes(); if (type -> IsScriptFunction()){ + auto parameterTypes = type->GetParameterTypes(); auto scriptFunctionType = std::dynamic_pointer_cast(type); auto parameterKeys = scriptFunctionType->GetParameterKeys(); auto originalScope = this->_evaluationScope; diff --git a/src/ScriptType.cpp b/src/ScriptType.cpp index 7f0e407..e15fbe9 100644 --- a/src/ScriptType.cpp +++ b/src/ScriptType.cpp @@ -1,4 +1,5 @@ #include "Script.hpp" +#include "UserData/UserDataFunctionType.hpp" namespace Porygon{ const bool ScriptType::CanBeIndexedWith(ScriptType *indexer) const{ @@ -25,6 +26,14 @@ namespace Porygon{ ScriptType* CreateStringScriptType(bool knownAtBind, uint32_t hash){ return new StringScriptType(knownAtBind, hash); } + + ScriptType* CreateUserDataFunctionScriptType(ScriptType* returnType, ScriptType* parameters[], size_t parameterCount){ + vector> vector(parameterCount); + for (int i = 0; i < parameterCount; i++){ + vector[i] = shared_ptr(parameters[i]); + } + return new UserData::UserDataFunctionType(shared_ptr(returnType), vector); + } } } diff --git a/src/UserData/UserDataFunction.cpp b/src/UserData/UserDataFunction.cpp index 5162d8b..0d3e990 100644 --- a/src/UserData/UserDataFunction.cpp +++ b/src/UserData/UserDataFunction.cpp @@ -1,2 +1,12 @@ #include "UserDataFunction.hpp" + +using namespace Porygon::Evaluation; + +namespace Porygon::UserData{ + extern "C" { + EvalValue * CreateFunctionEvalValue(Evaluation::EvalValue* (*func)(void* , EvalValue* [], int ), void* obj) { + return new UserDataFunction(func, obj); + } + } +} diff --git a/src/UserData/UserDataFunction.hpp b/src/UserData/UserDataFunction.hpp index 4cda7cd..9081269 100644 --- a/src/UserData/UserDataFunction.hpp +++ b/src/UserData/UserDataFunction.hpp @@ -3,6 +3,7 @@ #include #include "../Evaluator/EvalValues/ScriptFunctionEvalValue.hpp" +#include "UserDataFunctionType.hpp" namespace Porygon::UserData{ class UserDataFunction : public Evaluation::GenericFunctionEvalValue { @@ -15,14 +16,18 @@ namespace Porygon::UserData{ _obj = obj; } public: - UserDataFunction(Evaluation::EvalValue* (*call)(void* obj, EvalValue* parameters[], int parameterCount), void* obj, - shared_ptr type) : GenericFunctionEvalValue(std::move(type), rand()){ + UserDataFunction(Evaluation::EvalValue* (*call)(void* obj, EvalValue* parameters[], int parameterCount), void* obj) : + GenericFunctionEvalValue(make_shared(nullptr, vector>{}), rand()){ _call = call; _obj = obj; } EvalValue* Call(EvalValue* parameters[], int parameterCount){ - return _call(_obj, parameters, parameterCount); + try{ + return _call(_obj, parameters, parameterCount); + } catch (...){ + throw Evaluation::EvaluationException("An error occurred while executing a userdata function."); + } } const shared_ptr Clone() const final { diff --git a/src/UserData/UserDataScriptType.hpp b/src/UserData/UserDataScriptType.hpp index a043879..165d07e 100644 --- a/src/UserData/UserDataScriptType.hpp +++ b/src/UserData/UserDataScriptType.hpp @@ -31,7 +31,7 @@ namespace Porygon::UserData { } const bool CanBeIndexedWithIdentifier(uint32_t hash) const final { - return true; + return _userData -> ContainsField(hash); } UserDataField *GetField(uint32_t id) { diff --git a/src/UserData/UserDataValue.cpp b/src/UserData/UserDataValue.cpp index 2d444b1..1e3ce77 100644 --- a/src/UserData/UserDataValue.cpp +++ b/src/UserData/UserDataValue.cpp @@ -6,5 +6,10 @@ namespace Porygon::UserData { UserDataValue *CreateUserDataEvalValue(uint32_t typeHash, void *obj) { return new UserDataValue(typeHash, obj); } + + void* EvaluateUserDataObj(UserDataValue *v){ + return v -> GetObjectPointer(); + } + } } \ No newline at end of file diff --git a/src/UserData/UserDataValue.hpp b/src/UserData/UserDataValue.hpp index afe09a5..65eee12 100644 --- a/src/UserData/UserDataValue.hpp +++ b/src/UserData/UserDataValue.hpp @@ -56,6 +56,10 @@ namespace Porygon::UserData { auto field = _userData->GetField(fieldId); field->Set(_obj, value.get()); } + + void* GetObjectPointer(){ + return _obj; + } }; } diff --git a/tests/integration/UserData.cpp b/tests/integration/UserData.cpp index 1948385..3e90921 100644 --- a/tests/integration/UserData.cpp +++ b/tests/integration/UserData.cpp @@ -37,8 +37,7 @@ private: } static EvalValue* GetFooFunction(void* obj){ - return new UserDataFunction(CallFooFunction, obj, - make_shared(make_shared(true, false), vector>(0))); + return new UserDataFunction(CallFooFunction, obj); } static EvalValue* CallAddition(void* obj, EvalValue* parameters[], int parameterCount){ @@ -51,7 +50,7 @@ private: static GenericFunctionScriptType* AdditionFunctionType; static EvalValue* GetAdditionFunction(void* obj){ - return new UserDataFunction(CallAddition, obj, shared_ptr(AdditionFunctionType)); + return new UserDataFunction(CallAddition, obj); } public: