diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index deef95e1c..ef1939071 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1044,7 +1044,6 @@ set (PCH_SOURCES scripting/thingdef_data.cpp scripting/thingdef_properties.cpp scripting/backend/codegen.cpp - scripting/backend/dynarrays.cpp scripting/backend/vmbuilder.cpp scripting/decorate/olddecorations.cpp scripting/decorate/thingdef_exp.cpp @@ -1151,6 +1150,7 @@ set (PCH_SOURCES common/objects/dobjgc.cpp common/objects/dobjtype.cpp common/scripting/core/dictionary.cpp + common/scripting/core/dynarrays.cpp common/scripting/core/symbols.cpp common/scripting/core/types.cpp common/scripting/core/scopebarrier.cpp diff --git a/src/scripting/backend/dynarrays.cpp b/src/common/scripting/core/dynarrays.cpp similarity index 100% rename from src/scripting/backend/dynarrays.cpp rename to src/common/scripting/core/dynarrays.cpp diff --git a/src/scripting/backend/codegen.cpp b/src/scripting/backend/codegen.cpp index 86316c724..fb15b6060 100644 --- a/src/scripting/backend/codegen.cpp +++ b/src/scripting/backend/codegen.cpp @@ -7726,6 +7726,52 @@ static bool CheckArgSize(FName fname, FArgumentList &args, int min, int max, FSc return true; } +//========================================================================== +// +// FindClassMemberFunction +// +// Looks for a name in a class's symbol table and outputs appropriate messages +// +//========================================================================== + +PFunction* FindClassMemberFunction(PContainerType* selfcls, PContainerType* funccls, FName name, FScriptPosition& sc, bool* error, const VersionInfo& version, bool nodeprecated) +{ + // Skip ACS_NamedExecuteWithResult. Anything calling this should use the builtin instead. + if (name == NAME_ACS_NamedExecuteWithResult) return nullptr; + + PSymbolTable* symtable; + auto symbol = selfcls->Symbols.FindSymbolInTable(name, symtable); + auto funcsym = dyn_cast(symbol); + + if (symbol != nullptr) + { + auto cls_ctx = PType::toClass(funccls); + auto cls_target = funcsym ? PType::toClass(funcsym->OwningClass) : nullptr; + if (funcsym == nullptr) + { + if (PClass::FindClass(name)) return nullptr; // Special case when a class's member variable hides a global class name. This should still work. + sc.Message(MSG_ERROR, "%s is not a member function of %s", name.GetChars(), selfcls->TypeName.GetChars()); + } + else if ((funcsym->Variants[0].Flags & VARF_Private) && symtable != &funccls->Symbols) + { + // private access is only allowed if the symbol table belongs to the class in which the current function is being defined. + sc.Message(MSG_ERROR, "%s is declared private and not accessible", symbol->SymbolName.GetChars()); + } + else if ((funcsym->Variants[0].Flags & VARF_Protected) && symtable != &funccls->Symbols && (!cls_ctx || !cls_target || !cls_ctx->Descriptor->IsDescendantOf(cls_target->Descriptor))) + { + sc.Message(MSG_ERROR, "%s is declared protected and not accessible", symbol->SymbolName.GetChars()); + } + // ZScript will skip this because it prints its own message. + else if ((funcsym->Variants[0].Flags & VARF_Deprecated) && funcsym->mVersion <= version && !nodeprecated) + { + sc.Message(MSG_WARNING, "Call to deprecated function %s", symbol->SymbolName.GetChars()); + } + } + // return nullptr if the name cannot be found in the symbol table so that the calling code can do other checks. + return funcsym; +} + + //========================================================================== // // diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 7eaa78c7d..d3de454a4 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -229,51 +229,6 @@ PFunction *CreateAnonymousFunction(PContainerType *containingclass, PType *retur return sym; } -//========================================================================== -// -// FindClassMemberFunction -// -// Looks for a name in a class's symbol table and outputs appropriate messages -// -//========================================================================== - -PFunction *FindClassMemberFunction(PContainerType *selfcls, PContainerType *funccls, FName name, FScriptPosition &sc, bool *error, const VersionInfo &version, bool nodeprecated) -{ - // Skip ACS_NamedExecuteWithResult. Anything calling this should use the builtin instead. - if (name == NAME_ACS_NamedExecuteWithResult) return nullptr; - - PSymbolTable *symtable; - auto symbol = selfcls->Symbols.FindSymbolInTable(name, symtable); - auto funcsym = dyn_cast(symbol); - - if (symbol != nullptr) - { - auto cls_ctx = PType::toClass(funccls); - auto cls_target = funcsym ? PType::toClass(funcsym->OwningClass) : nullptr; - if (funcsym == nullptr) - { - if (PClass::FindClass(name)) return nullptr; // Special case when a class's member variable hides a global class name. This should still work. - sc.Message(MSG_ERROR, "%s is not a member function of %s", name.GetChars(), selfcls->TypeName.GetChars()); - } - else if ((funcsym->Variants[0].Flags & VARF_Private) && symtable != &funccls->Symbols) - { - // private access is only allowed if the symbol table belongs to the class in which the current function is being defined. - sc.Message(MSG_ERROR, "%s is declared private and not accessible", symbol->SymbolName.GetChars()); - } - else if ((funcsym->Variants[0].Flags & VARF_Protected) && symtable != &funccls->Symbols && (!cls_ctx || !cls_target || !cls_ctx->Descriptor->IsDescendantOf(cls_target->Descriptor))) - { - sc.Message(MSG_ERROR, "%s is declared protected and not accessible", symbol->SymbolName.GetChars()); - } - // ZScript will skip this because it prints its own message. - else if ((funcsym->Variants[0].Flags & VARF_Deprecated) && funcsym->mVersion <= version && !nodeprecated) - { - sc.Message(MSG_WARNING, "Call to deprecated function %s", symbol->SymbolName.GetChars()); - } - } - // return nullptr if the name cannot be found in the symbol table so that the calling code can do other checks. - return funcsym; -} - //========================================================================== // // CreateDamageFunction