From 496d3819d9d5439bcfcbd20691b4789d6c727fd0 Mon Sep 17 00:00:00 2001 From: ProgramSnail Date: Tue, 2 May 2023 16:16:55 +0300 Subject: [PATCH] . --- include/global_info.hpp | 15 ++++++++---- include/interpreter_tree.hpp | 4 ++-- include/type_info_contexts.hpp | 44 ++++++++++++++++++++++++++++++---- src/find_symbols_visitor.cpp | 2 -- src/global_info.cpp | 12 +++++++++- src/link_symbols_visitor.cpp | 10 ++++++-- 6 files changed, 71 insertions(+), 16 deletions(-) diff --git a/include/global_info.hpp b/include/global_info.hpp index b33dc79..babd93e 100644 --- a/include/global_info.hpp +++ b/include/global_info.hpp @@ -18,6 +18,11 @@ public: friend GlobalInfo; NamespaceVisitor() = delete; public: + struct Path { + std::vector> path_types; + definition::Namespace* result; + } + void AddImport(definition::Import&& import_info, const std::optional& name = std::nullopt); void AddEnterNamespace(const std::string& name, @@ -57,6 +62,8 @@ public: std::optional FindType(const std::optional>& path, const std::string& type); + std::optional FindLocalType(const std::string& type); + std::optional FindAbstractType(const std::string& abstract_type); std::optional FindTypeclass(const std::string& typeclass); @@ -96,22 +103,22 @@ public: return NamespaceVisitor(*this); } - // TODO: remember about vector realloc + // remember about vector realloc definition::Function* GetFunctionInfo(utils::IdType id) { return &functions_[id]; } - // TODO: remember about vector realloc + // remember about vector realloc definition::Type* GetTypeInfo(utils::IdType id) { return &types_[id]; } - // TODO: remember about vector realloc + // remember about vector realloc definition::Typeclass* GetTypeclassInfo(utils::IdType id) { return &typeclasses_[id]; } - // TODO: remember about vector realloc + // remember about vector realloc definition::Constructor* GetConstructorInfo(utils::IdType id) { return &constructors_[id]; } diff --git a/include/interpreter_tree.hpp b/include/interpreter_tree.hpp index 50770d5..eaf587f 100644 --- a/include/interpreter_tree.hpp +++ b/include/interpreter_tree.hpp @@ -557,8 +557,6 @@ struct TypeExpression { TypeSubExpression type; std::optional array_size; // if array; 0 - dynamic size - - utils::IdType type_id_; }; struct ExtendedScopedAnyType { @@ -584,6 +582,8 @@ struct ParametrizedTypeclass { struct ParametrizedType { AnyTypeIdentifier type; std::vector> parameters; + + std::optional type_id_; // std::nullopt, if it is namespace without type }; // ----------------- Comments [IGNORE] ----------------- diff --git a/include/type_info_contexts.hpp b/include/type_info_contexts.hpp index 24be4ad..24a63ac 100644 --- a/include/type_info_contexts.hpp +++ b/include/type_info_contexts.hpp @@ -6,7 +6,6 @@ #include // for clangd -#include "error_handling.hpp" #include "types.hpp" #include "utils.hpp" @@ -37,13 +36,19 @@ public: // TODO: variable modifiers bool DefineVariable(const std::string& name, utils::IdType type_id) { + // check in previous contexts ?? return contexts_.back().DefineVariable(name, type_id); } - bool DefineLocalAbstractType() { - // TODO + bool DefineLocalAbstractType(const std::string& name, utils::IdType type_id) { + if (GetLocalAbstractType(name)) { + return false; + } + contexts_.back().DefineLocalAbstractType(name, type_id); + return true; } + bool RemoveVariable(const std::string& name) { for (ssize_t i = (ssize_t)contexts_.size() - 1; i >= 0; --i) { if (contexts_[i].RemoveVariable(name)) { @@ -70,16 +75,34 @@ public: return std::nullopt; } + std::optional GetLocalAbstractType(const std::string& name) { + for (ssize_t i = (ssize_t)contexts_.size() - 1; i >= 0; --i) { + auto maybe_type = contexts_[i].GetLocalAbstractType(name); + if (maybe_type.has_value()) { + return maybe_type.value(); + } + } + return std::nullopt; + } + private: class Context { public: Context(bool hide_previous) : hide_previous_(hide_previous) {} bool DefineVariable(const std::string& name, utils::IdType type_id) { - if (variables_.count(name) > 0) { + if (local_abstract_types_.count(name) > 0) { return false; } - variables_[name] = type_id; + local_abstract_types_[name] = type_id; + return true; + } + + bool DefineLocalAbstractType(const std::string& name, utils::IdType type_id) { + if (local_abstract_types_.count(name) > 0) { + return false; + } + local_abstract_types_[name] = type_id; return true; } @@ -97,10 +120,21 @@ private: return variable_iter->second; } + std::optional GetLocalAbstractType(const std::string& name) { + auto local_abstract_type_iter = local_abstract_types_.find(name); + + if (local_abstract_type_iter == local_abstract_types_.end()) { + return std::nullopt; + } + + return local_abstract_type_iter->second; + } + bool IsFirst() { return hide_previous_; } private: bool hide_previous_; std::unordered_map variables_; + std::unordered_map local_abstract_types_; }; std::vector contexts_; diff --git a/src/find_symbols_visitor.cpp b/src/find_symbols_visitor.cpp index 4a91bf2..cdee223 100644 --- a/src/find_symbols_visitor.cpp +++ b/src/find_symbols_visitor.cpp @@ -1,8 +1,6 @@ // for clangd #include "../include/find_symbols_visitor.hpp" -// TODO - namespace interpreter { // Sources ----------------- diff --git a/src/global_info.cpp b/src/global_info.cpp index 864d181..5ae8f99 100644 --- a/src/global_info.cpp +++ b/src/global_info.cpp @@ -167,7 +167,7 @@ utils::IdType GlobalInfo::NamespaceVisitor::AddAbstractType(const std::string& a if (!FindAbstractType(abstract_type).has_value()) { size_t id = global_info_.abstract_types_.size(); global_info_.name_to_abstract_type_[abstract_type] = id; - global_info_.abstract_types_.push_b(ack(std::move(abstract_type_info)); + global_info_.abstract_types_.push_back(std::move(abstract_type_info)); } error_handling::HandleTypecheckError("More then one abstract type with the same name in namespace"); @@ -261,6 +261,16 @@ std::optional GlobalInfo::NamespaceVisitor::FindType( }); } +std::optional GlobalInfo::NamespaceVisitor::FindLocalType(const std::string& type) { + auto type_id_iter = namespace_stack_.back()->types.find(type); + + if (type_id_iter != namespace_stack_.back()->types.end()) { + return type_id_iter->second; + } + + return std::nullopt; +} + std::optional GlobalInfo::NamespaceVisitor::FindAbstractType(const std::string& abstract_type) { auto abstract_type_id_iter = global_info_.name_to_abstract_type_.find(abstract_type); diff --git a/src/link_symbols_visitor.cpp b/src/link_symbols_visitor.cpp index 48356a1..a6dd0de 100644 --- a/src/link_symbols_visitor.cpp +++ b/src/link_symbols_visitor.cpp @@ -1,6 +1,7 @@ // for clangd #include "../include/link_symbols_visitor.hpp" #include "../include/error_handling.hpp" +#include namespace interpreter { @@ -20,8 +21,13 @@ const std::string& NameFromTypeSubExpression(const TypeSubExpression& type) { void LinkSymbolsVisitor::Visit(Namespace* node) { // Visitor::Visit(&node->type); // not needed - auto maybe_type = namespace_visitor_.FindType(std::nullopt, node->type); // TODO: find only in local namespace - auto maybe_typeclass = namespace_visitor_.FindType(std::nullopt, node->type); // TODO: find only if in global namespace + std::optional maybe_type = namespace_visitor_.FindLocalType(node->type); + + std::optional maybe_typeclass; + if (namespace_visitor_.GetCurrentPath().size() == 0) { + maybe_typeclass = namespace_visitor_.FindTypeclass(node->type); + } + if (maybe_type.has_value() && maybe_typeclass.has_value()) { error_handling::HandleTypecheckError("Ambigious namespace name (typeclass or type)"); }