mirror of
https://codeberg.org/ProgramSnail/lang_2023.git
synced 2025-12-06 06:58:45 +00:00
bool literals, fixes
This commit is contained in:
parent
b1aff1935d
commit
d31979166e
24 changed files with 179 additions and 46 deletions
|
|
@ -139,6 +139,7 @@ private:
|
||||||
void Visit(StringLiteral* node) override;
|
void Visit(StringLiteral* node) override;
|
||||||
void Visit(CharLiteral* node) override;
|
void Visit(CharLiteral* node) override;
|
||||||
void Visit(UnitLiteral* node) override;
|
void Visit(UnitLiteral* node) override;
|
||||||
|
void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
void Visit(Literal& node) override; // variant
|
void Visit(Literal& node) override; // variant
|
||||||
private:
|
private:
|
||||||
|
|
|
||||||
|
|
@ -10,13 +10,13 @@ inline void PrintPosition(std::ostream& out,
|
||||||
std::pair<size_t, size_t> start_position,
|
std::pair<size_t, size_t> start_position,
|
||||||
std::pair<size_t, size_t> end_position) {
|
std::pair<size_t, size_t> end_position) {
|
||||||
out << '['
|
out << '['
|
||||||
<< start_position.first
|
<< start_position.first + 1
|
||||||
<< ", "
|
<< ", "
|
||||||
<< start_position.second
|
<< start_position.second + 1
|
||||||
<< "] - ["
|
<< "] - ["
|
||||||
<< end_position.first
|
<< end_position.first + 1
|
||||||
<< ", "
|
<< ", "
|
||||||
<< end_position.second
|
<< end_position.second + 1
|
||||||
<< ']';
|
<< ']';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,8 +5,10 @@
|
||||||
// for clangd
|
// for clangd
|
||||||
#include "contexts.hpp"
|
#include "contexts.hpp"
|
||||||
#include "global_info.hpp"
|
#include "global_info.hpp"
|
||||||
|
#include "interpreter_tree.hpp"
|
||||||
#include "type_info_contexts.hpp"
|
#include "type_info_contexts.hpp"
|
||||||
#include "visitor.hpp"
|
#include "visitor.hpp"
|
||||||
|
#include "error_handling.hpp"
|
||||||
|
|
||||||
namespace interpreter {
|
namespace interpreter {
|
||||||
|
|
||||||
|
|
@ -14,11 +16,20 @@ class ExecuteVisitor : public Visitor {
|
||||||
public:
|
public:
|
||||||
explicit ExecuteVisitor(info::GlobalInfo& global_info,
|
explicit ExecuteVisitor(info::GlobalInfo& global_info,
|
||||||
info::TypeInfoContextManager& type_info_context_manager,
|
info::TypeInfoContextManager& type_info_context_manager,
|
||||||
info::ContextManager& context_manager)
|
info::ContextManager& context_manager,
|
||||||
|
interpreter::tokens::PartitionStatement* execution_root)
|
||||||
: namespace_visitor_(global_info.CreateVisitor()),
|
: namespace_visitor_(global_info.CreateVisitor()),
|
||||||
type_info_context_manager_(type_info_context_manager),
|
type_info_context_manager_(type_info_context_manager),
|
||||||
context_manager_(context_manager) {}
|
context_manager_(context_manager) {}
|
||||||
|
|
||||||
|
void VisitSourceFile(SourceFile* source_file) override {
|
||||||
|
error_handling::HandleInternalError("VisitSourceFile unavailible", "ExecuteVisitor.VisitSourceFile");
|
||||||
|
};
|
||||||
|
|
||||||
|
void ExecutePartition(interpreter::tokens::PartitionStatement* partition) {
|
||||||
|
Visit(partition);
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// Sources -----------------
|
// Sources -----------------
|
||||||
|
|
||||||
|
|
@ -39,8 +50,7 @@ private:
|
||||||
void Visit(TypeDefinitionStatement* node) override;
|
void Visit(TypeDefinitionStatement* node) override;
|
||||||
void Visit(AbstractTypeDefinitionStatement* node) override;
|
void Visit(AbstractTypeDefinitionStatement* node) override;
|
||||||
void Visit(TypeclassDefinitionStatement* node) override;
|
void Visit(TypeclassDefinitionStatement* node) override;
|
||||||
void Visit(ExecutableStatement* node) override;
|
void Visit(PartitionStatement* node) override;
|
||||||
void Visit(TestStatement* node) override;
|
|
||||||
|
|
||||||
// Definition parts
|
// Definition parts
|
||||||
|
|
||||||
|
|
@ -125,6 +135,7 @@ private:
|
||||||
void Visit(StringLiteral* node) override;
|
void Visit(StringLiteral* node) override;
|
||||||
void Visit(CharLiteral* node) override;
|
void Visit(CharLiteral* node) override;
|
||||||
void Visit(UnitLiteral* node) override;
|
void Visit(UnitLiteral* node) override;
|
||||||
|
void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
||||||
|
|
|
||||||
|
|
@ -119,6 +119,7 @@ private:
|
||||||
// // void Visit(StringLiteral* node) override;
|
// // void Visit(StringLiteral* node) override;
|
||||||
// // void Visit(CharLiteral* node) override;
|
// // void Visit(CharLiteral* node) override;
|
||||||
// // void Visit(UnitLiteral* node) override;
|
// // void Visit(UnitLiteral* node) override;
|
||||||
|
// // void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
||||||
|
|
|
||||||
|
|
@ -36,7 +36,8 @@ public:
|
||||||
void AddImport(definition::Import&& import_info, const std::optional<std::string>& name = std::nullopt);
|
void AddImport(definition::Import&& import_info, const std::optional<std::string>& name = std::nullopt);
|
||||||
|
|
||||||
void AddEnterNamespace(const std::string& name,
|
void AddEnterNamespace(const std::string& name,
|
||||||
std::optional<utils::IsConstModifier> modifier = std::nullopt);
|
std::optional<utils::IsConstModifier> modifier,
|
||||||
|
const interpreter::tokens::BaseNode& base_node);
|
||||||
|
|
||||||
void EnterNamespace(const std::string& name);
|
void EnterNamespace(const std::string& name);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -108,13 +108,15 @@ struct NumberLiteral;
|
||||||
struct StringLiteral;
|
struct StringLiteral;
|
||||||
struct CharLiteral;
|
struct CharLiteral;
|
||||||
struct UnitLiteral;
|
struct UnitLiteral;
|
||||||
|
struct BoolLiteral;
|
||||||
|
|
||||||
using Literal = std::variant<
|
using Literal = std::variant<
|
||||||
std::unique_ptr<FloatNumberLiteral>,
|
std::unique_ptr<FloatNumberLiteral>,
|
||||||
std::unique_ptr<NumberLiteral>,
|
std::unique_ptr<NumberLiteral>,
|
||||||
std::unique_ptr<StringLiteral>,
|
std::unique_ptr<StringLiteral>,
|
||||||
std::unique_ptr<CharLiteral>,
|
std::unique_ptr<CharLiteral>,
|
||||||
std::unique_ptr<UnitLiteral>>;
|
std::unique_ptr<UnitLiteral>,
|
||||||
|
std::unique_ptr<BoolLiteral>>;
|
||||||
|
|
||||||
//
|
//
|
||||||
struct NameExpression;
|
struct NameExpression;
|
||||||
|
|
@ -703,4 +705,10 @@ struct UnitLiteral {
|
||||||
BaseNode base;
|
BaseNode base;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct BoolLiteral {
|
||||||
|
BaseNode base;
|
||||||
|
|
||||||
|
bool value;
|
||||||
|
};
|
||||||
|
|
||||||
} // namespace interpereter::tokens
|
} // namespace interpereter::tokens
|
||||||
|
|
|
||||||
|
|
@ -110,13 +110,14 @@ private:
|
||||||
// Identifiers, constants, etc. -----------------
|
// Identifiers, constants, etc. -----------------
|
||||||
|
|
||||||
// // void Visit(ExtendedName* node) override;
|
// // void Visit(ExtendedName* node) override;
|
||||||
// //
|
|
||||||
// // void Visit(std::string* node) override; // std::string
|
// // void Visit(std::string* node) override; // std::string
|
||||||
// //
|
|
||||||
// // void Visit(FloatNumberLiteral* node) override;
|
// // void Visit(FloatNumberLiteral* node) override;
|
||||||
// // void Visit(NumberLiteral* node) override;
|
// // void Visit(NumberLiteral* node) override;
|
||||||
// // void Visit(StringLiteral* node) override;
|
// // void Visit(StringLiteral* node) override;
|
||||||
// // void Visit(CharLiteral* node) override;
|
// // void Visit(CharLiteral* node) override;
|
||||||
|
// // void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
info::GlobalInfo::NamespaceVisitor namespace_visitor_;
|
||||||
|
|
|
||||||
|
|
@ -127,6 +127,7 @@ const std::string NumberLiteral = "number_literal";
|
||||||
const std::string StringLiteral = "string_literal";
|
const std::string StringLiteral = "string_literal";
|
||||||
const std::string CharLiteral = "char_literal";
|
const std::string CharLiteral = "char_literal";
|
||||||
const std::string UnitLiteral = "unit_literal";
|
const std::string UnitLiteral = "unit_literal";
|
||||||
|
const std::string BoolLiteral = "bool_literal";
|
||||||
|
|
||||||
const std::string Literal = "literal";
|
const std::string Literal = "literal";
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -118,6 +118,7 @@ private:
|
||||||
void Visit(StringLiteral* node) override;
|
void Visit(StringLiteral* node) override;
|
||||||
void Visit(CharLiteral* node) override;
|
void Visit(CharLiteral* node) override;
|
||||||
void Visit(UnitLiteral* node) override;
|
void Visit(UnitLiteral* node) override;
|
||||||
|
void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::ostream& out_;
|
std::ostream& out_;
|
||||||
|
|
|
||||||
|
|
@ -122,6 +122,7 @@ private:
|
||||||
void Visit(StringLiteral* node) override;
|
void Visit(StringLiteral* node) override;
|
||||||
void Visit(CharLiteral* node) override;
|
void Visit(CharLiteral* node) override;
|
||||||
void Visit(UnitLiteral* node) override;
|
void Visit(UnitLiteral* node) override;
|
||||||
|
void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -119,6 +119,7 @@ private:
|
||||||
void Visit(StringLiteral* node) override;
|
void Visit(StringLiteral* node) override;
|
||||||
void Visit(CharLiteral* node) override;
|
void Visit(CharLiteral* node) override;
|
||||||
void Visit(UnitLiteral* node) override;
|
void Visit(UnitLiteral* node) override;
|
||||||
|
void Visit(BoolLiteral* node) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::ostream& out_;
|
std::ostream& out_;
|
||||||
|
|
|
||||||
|
|
@ -78,6 +78,37 @@ enum class InternalType {
|
||||||
Unit = 5,
|
Unit = 5,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
inline std::optional<InternalType> ToInternalType(const std::string& type) {
|
||||||
|
if (type.empty()) {
|
||||||
|
return std::nullopt;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (type[0]) {
|
||||||
|
case 'F':
|
||||||
|
if (type == "Float") { return InternalType::Float; }
|
||||||
|
break;
|
||||||
|
case 'I':
|
||||||
|
if (type == "Int") { return InternalType::Int; }
|
||||||
|
break;
|
||||||
|
case 'S':
|
||||||
|
if (type == "String") { return InternalType::String; }
|
||||||
|
break;
|
||||||
|
case 'C':
|
||||||
|
if (type == "Char") { return InternalType::Char; }
|
||||||
|
break;
|
||||||
|
case 'B':
|
||||||
|
if (type == "Bool") { return InternalType::Bool; }
|
||||||
|
break;
|
||||||
|
case 'U':
|
||||||
|
if (type == "Unit") { return InternalType::Unit; }
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return std::nullopt;
|
||||||
|
}
|
||||||
|
|
||||||
class TupleType {
|
class TupleType {
|
||||||
public:
|
public:
|
||||||
TupleType() = default;
|
TupleType() = default;
|
||||||
|
|
|
||||||
|
|
@ -136,6 +136,7 @@ protected:
|
||||||
virtual void Visit(StringLiteral* node);
|
virtual void Visit(StringLiteral* node);
|
||||||
virtual void Visit(CharLiteral* node);
|
virtual void Visit(CharLiteral* node);
|
||||||
virtual void Visit(UnitLiteral* node);
|
virtual void Visit(UnitLiteral* node);
|
||||||
|
virtual void Visit(BoolLiteral* node);
|
||||||
|
|
||||||
virtual void Visit(Literal& node); // variant
|
virtual void Visit(Literal& node); // variant
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1 +1 @@
|
||||||
Subproject commit 0d034ea18377d25429fe04e768458df2cc00586a
|
Subproject commit 82f3a4edebad870fbf7d28bfd06bcc67731d5837
|
||||||
|
|
@ -1531,6 +1531,13 @@ void BuildVisitor::Visit(UnitLiteral* node) {
|
||||||
SetPosition(node->base, current_node_);
|
SetPosition(node->base, current_node_);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void BuildVisitor::Visit(BoolLiteral* node) {
|
||||||
|
SetPosition(node->base, current_node_);
|
||||||
|
|
||||||
|
std::string literal = current_node_.GetValue();
|
||||||
|
node->value = (literal == "true"); // always "false" in other way
|
||||||
|
}
|
||||||
|
|
||||||
void BuildVisitor::Visit(Literal& node) {
|
void BuildVisitor::Visit(Literal& node) {
|
||||||
auto parse_node = current_node_;
|
auto parse_node = current_node_;
|
||||||
|
|
||||||
|
|
@ -1553,6 +1560,9 @@ void BuildVisitor::Visit(Literal& node) {
|
||||||
} else if (current_node_type == parser::tokens::UnitLiteral) {
|
} else if (current_node_type == parser::tokens::UnitLiteral) {
|
||||||
node = std::make_unique<UnitLiteral>();
|
node = std::make_unique<UnitLiteral>();
|
||||||
Visit(std::get<std::unique_ptr<UnitLiteral>>(node).get());
|
Visit(std::get<std::unique_ptr<UnitLiteral>>(node).get());
|
||||||
|
} else if (current_node_type == parser::tokens::BoolLiteral) {
|
||||||
|
node = std::make_unique<BoolLiteral>();
|
||||||
|
Visit(std::get<std::unique_ptr<BoolLiteral>>(node).get());
|
||||||
} else {
|
} else {
|
||||||
// error
|
// error
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -73,12 +73,7 @@ void ExecuteVisitor::Visit(TypeclassDefinitionStatement* node) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ExecuteVisitor::Visit(ExecutableStatement* node) {
|
void ExecuteVisitor::Visit(PartitionStatement* node) {
|
||||||
Visit(&node->name);
|
|
||||||
Visitor::Visit(node->value);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ExecuteVisitor::Visit(TestStatement* node) {
|
|
||||||
Visit(&node->name);
|
Visit(&node->name);
|
||||||
Visitor::Visit(node->value);
|
Visitor::Visit(node->value);
|
||||||
}
|
}
|
||||||
|
|
@ -391,5 +386,7 @@ void ExecuteVisitor::Visit(CharLiteral* node) {}
|
||||||
|
|
||||||
void ExecuteVisitor::Visit(UnitLiteral* node) {}
|
void ExecuteVisitor::Visit(UnitLiteral* node) {}
|
||||||
|
|
||||||
|
void ExecuteVisitor::Visit(BoolLiteral* node) {}
|
||||||
|
|
||||||
} // namespace interpreter
|
} // namespace interpreter
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ namespace interpreter {
|
||||||
// Namespaces, partitions -----------------
|
// Namespaces, partitions -----------------
|
||||||
|
|
||||||
void FindSymbolsVisitor::Visit(Namespace* node) {
|
void FindSymbolsVisitor::Visit(Namespace* node) {
|
||||||
namespace_visitor_.AddEnterNamespace(node->type, node->modifier);
|
namespace_visitor_.AddEnterNamespace(node->type, node->modifier, node->base);
|
||||||
Visitor::Visit(&node->scope);
|
Visitor::Visit(&node->scope);
|
||||||
namespace_visitor_.ExitNamespace();
|
namespace_visitor_.ExitNamespace();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,10 @@
|
||||||
|
#include <variant>
|
||||||
|
|
||||||
// for clangd
|
// for clangd
|
||||||
#include "../include/global_info.hpp"
|
#include "../include/global_info.hpp"
|
||||||
|
#include "../include/types.hpp"
|
||||||
#include "../include/error_handling.hpp"
|
#include "../include/error_handling.hpp"
|
||||||
#include <variant>
|
|
||||||
|
|
||||||
namespace info {
|
namespace info {
|
||||||
|
|
||||||
|
|
@ -15,7 +18,12 @@ void GlobalInfo::NamespaceVisitor::AddImport(definition::Import&& import_info,
|
||||||
}
|
}
|
||||||
|
|
||||||
void GlobalInfo::NamespaceVisitor::AddEnterNamespace(const std::string& name,
|
void GlobalInfo::NamespaceVisitor::AddEnterNamespace(const std::string& name,
|
||||||
std::optional<utils::IsConstModifier> modifier) {
|
std::optional<utils::IsConstModifier> modifier,
|
||||||
|
const interpreter::tokens::BaseNode& base_node) {
|
||||||
|
if (type::ToInternalType(name).has_value()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't define basic type namespace", base_node);
|
||||||
|
}
|
||||||
|
|
||||||
definition::Namespace* namespace_info = nullptr;
|
definition::Namespace* namespace_info = nullptr;
|
||||||
if (modifier.has_value()) {
|
if (modifier.has_value()) {
|
||||||
if (modifier.value() == utils::IsConstModifier::Const) {
|
if (modifier.value() == utils::IsConstModifier::Const) {
|
||||||
|
|
@ -122,6 +130,10 @@ utils::IdType GlobalInfo::NamespaceVisitor::AddFunctionDefinition(const std::str
|
||||||
utils::IdType GlobalInfo::NamespaceVisitor::AddType(const std::string& type,
|
utils::IdType GlobalInfo::NamespaceVisitor::AddType(const std::string& type,
|
||||||
definition::Type&& type_info,
|
definition::Type&& type_info,
|
||||||
const interpreter::tokens::BaseNode& base_node) {
|
const interpreter::tokens::BaseNode& base_node) {
|
||||||
|
if (type::ToInternalType(type).has_value()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't redefine basic type", base_node);
|
||||||
|
}
|
||||||
|
|
||||||
size_t id = 0;
|
size_t id = 0;
|
||||||
|
|
||||||
auto type_id_iter = namespace_stack_.back()->types.find(type);
|
auto type_id_iter = namespace_stack_.back()->types.find(type);
|
||||||
|
|
@ -181,6 +193,10 @@ utils::IdType GlobalInfo::NamespaceVisitor::AddType(const std::string& type,
|
||||||
utils::IdType GlobalInfo::NamespaceVisitor::AddAbstractType(const std::string& abstract_type,
|
utils::IdType GlobalInfo::NamespaceVisitor::AddAbstractType(const std::string& abstract_type,
|
||||||
definition::AbstractType&& abstract_type_info,
|
definition::AbstractType&& abstract_type_info,
|
||||||
const interpreter::tokens::BaseNode& base_node) {
|
const interpreter::tokens::BaseNode& base_node) {
|
||||||
|
if (type::ToInternalType(abstract_type).has_value()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't redefine basic type as abstract type", base_node);
|
||||||
|
}
|
||||||
|
|
||||||
if (!FindAbstractType(abstract_type).has_value()) {
|
if (!FindAbstractType(abstract_type).has_value()) {
|
||||||
utils::IdType id = global_info_.abstract_types_.size();
|
utils::IdType id = global_info_.abstract_types_.size();
|
||||||
global_info_.name_to_abstract_type_[abstract_type] = id;
|
global_info_.name_to_abstract_type_[abstract_type] = id;
|
||||||
|
|
@ -197,6 +213,10 @@ utils::IdType GlobalInfo::NamespaceVisitor::AddAbstractType(const std::string& a
|
||||||
utils::IdType GlobalInfo::NamespaceVisitor::AddTypeclass(const std::string& typeclass,
|
utils::IdType GlobalInfo::NamespaceVisitor::AddTypeclass(const std::string& typeclass,
|
||||||
definition::Typeclass&& typeclass_info,
|
definition::Typeclass&& typeclass_info,
|
||||||
const interpreter::tokens::BaseNode& base_node) {
|
const interpreter::tokens::BaseNode& base_node) {
|
||||||
|
if (type::ToInternalType(typeclass).has_value()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't redefine basic type as typeclass", base_node);
|
||||||
|
}
|
||||||
|
|
||||||
if (!FindTypeclass(typeclass).has_value()) {
|
if (!FindTypeclass(typeclass).has_value()) {
|
||||||
size_t id = global_info_.typeclasses_.size();
|
size_t id = global_info_.typeclasses_.size();
|
||||||
global_info_.name_to_typeclass_[typeclass] = id;
|
global_info_.name_to_typeclass_[typeclass] = id;
|
||||||
|
|
@ -211,6 +231,10 @@ utils::IdType GlobalInfo::NamespaceVisitor::AddTypeclass(const std::string& type
|
||||||
utils::IdType GlobalInfo::NamespaceVisitor::AddConstructor(const std::string& constructor,
|
utils::IdType GlobalInfo::NamespaceVisitor::AddConstructor(const std::string& constructor,
|
||||||
definition::Constructor&& constructor_info,
|
definition::Constructor&& constructor_info,
|
||||||
const interpreter::tokens::BaseNode& base_node) {
|
const interpreter::tokens::BaseNode& base_node) {
|
||||||
|
if (type::ToInternalType(constructor).has_value()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't redefine basic type as constructor", base_node);
|
||||||
|
}
|
||||||
|
|
||||||
auto constructor_id_iter = namespace_stack_.back()->constructors.find(constructor);
|
auto constructor_id_iter = namespace_stack_.back()->constructors.find(constructor);
|
||||||
|
|
||||||
if (constructor_id_iter == namespace_stack_.back()->constructors.end()) {
|
if (constructor_id_iter == namespace_stack_.back()->constructors.end()) {
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,9 @@
|
||||||
|
#include <optional>
|
||||||
|
|
||||||
// for clangd
|
// for clangd
|
||||||
#include "../include/link_symbols_visitor.hpp"
|
#include "../include/link_symbols_visitor.hpp"
|
||||||
#include "../include/error_handling.hpp"
|
#include "../include/error_handling.hpp"
|
||||||
#include <optional>
|
#include "../include/types.hpp"
|
||||||
|
|
||||||
namespace interpreter {
|
namespace interpreter {
|
||||||
|
|
||||||
|
|
@ -50,8 +52,20 @@ void LinkSymbolsVisitor::Visit(TypeExpression* node) { // TODO: check
|
||||||
node->type_id_ = namespace_visitor_.FindType(path, node->type.type);
|
node->type_id_ = namespace_visitor_.FindType(path, node->type.type);
|
||||||
node->constructor_id_ = namespace_visitor_.FindConstructor(path, node->type.type);
|
node->constructor_id_ = namespace_visitor_.FindConstructor(path, node->type.type);
|
||||||
|
|
||||||
if (path.size() == 0 && namespace_visitor_.FindAbstractType(node->type.type).has_value()) { // TODO
|
// internal type
|
||||||
|
if (info::type::ToInternalType(node->type.type).has_value()) {
|
||||||
|
if (!node->path.empty()) {
|
||||||
|
error_handling::HandleTypecheckError("Internal type is not in namespace", node->base);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!node->type.parameters.empty()) {
|
||||||
|
error_handling::HandleTypecheckError("Can't parametrize internal type", node->base);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// abstract / basic / TODO: local abstract type
|
// abstract / basic / TODO: local abstract type
|
||||||
|
if (path.size() == 0 && namespace_visitor_.FindAbstractType(node->type.type).has_value()) { // TODO
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -742,4 +742,8 @@ void PrintVisitor::Visit(UnitLiteral* node) {
|
||||||
out_ << "[Unit ()] ";
|
out_ << "[Unit ()] ";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void PrintVisitor::Visit(BoolLiteral* node) {
|
||||||
|
out_ << "[Bool " << (node->value ? "true" : "false") << "] ";
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace interpreter
|
} // namespace interpreter
|
||||||
|
|
|
||||||
|
|
@ -765,7 +765,6 @@ void TypeCheckVisitor::Visit(FunctionCallExpression* node) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (node->prefix.has_value()) {
|
if (node->prefix.has_value()) {
|
||||||
|
|
||||||
if (std::holds_alternative<std::unique_ptr<SubExpressionToken>>(node->prefix.value())) {
|
if (std::holds_alternative<std::unique_ptr<SubExpressionToken>>(node->prefix.value())) {
|
||||||
Visitor::Visit(*std::get<std::unique_ptr<SubExpressionToken>>(node->prefix.value()));
|
Visitor::Visit(*std::get<std::unique_ptr<SubExpressionToken>>(node->prefix.value()));
|
||||||
|
|
||||||
|
|
@ -857,7 +856,7 @@ void TypeCheckVisitor::Visit(FunctionCallExpression* node) {
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
||||||
if (function_declaration.argument_types.size() + 1 != node->arguments.size()) {
|
if (function_declaration.argument_types.size() != node->arguments.size() + 1) {
|
||||||
error_handling::HandleTypecheckError("Mismatched argument count in function call expression", node->base);
|
error_handling::HandleTypecheckError("Mismatched argument count in function call expression", node->base);
|
||||||
}
|
}
|
||||||
for (size_t i = 0; i < node->arguments.size(); ++i) {
|
for (size_t i = 0; i < node->arguments.size(); ++i) {
|
||||||
|
|
@ -1015,7 +1014,7 @@ void TypeCheckVisitor::Visit(ArrayExpression* node) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (node->elements.size() == 0) {
|
if (node->elements.empty()) {
|
||||||
error_handling::HandleInternalError("Element size is 0", "TypeCheckVisitor.ArrayExpression");
|
error_handling::HandleInternalError("Element size is 0", "TypeCheckVisitor.ArrayExpression");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1032,7 +1031,7 @@ void TypeCheckVisitor::Visit(PartitionName* node) {} // Handled in partition ( e
|
||||||
|
|
||||||
void TypeCheckVisitor::Visit(NameExpression* node) {
|
void TypeCheckVisitor::Visit(NameExpression* node) {
|
||||||
// TODO: move, etc.
|
// TODO: move, etc.
|
||||||
if (node->names.size() == 0) {
|
if (node->names.empty()) {
|
||||||
error_handling::HandleInternalError("Name expression with zero names", "TypeCheckVisitor.NameExpression");
|
error_handling::HandleInternalError("Name expression with zero names", "TypeCheckVisitor.NameExpression");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1136,7 +1135,7 @@ void TypeCheckVisitor::Visit(VariantName* node) {
|
||||||
}
|
}
|
||||||
|
|
||||||
for (size_t i = 0; i < node->names.size(); ++i) {
|
for (size_t i = 0; i < node->names.size(); ++i) {
|
||||||
if (maybe_type_value.value()->GetConstructors()[i].GetFields().size() == 0) {
|
if (maybe_type_value.value()->GetConstructors()[i].GetFields().empty()) {
|
||||||
current_type_ = context_manager_.AddType(
|
current_type_ = context_manager_.AddType(
|
||||||
info::type::OptionalType(context_manager_.AddType(info::type::InternalType::Unit, utils::ValueType::Tmp), context_manager_.GetTypeManager()),
|
info::type::OptionalType(context_manager_.AddType(info::type::InternalType::Unit, utils::ValueType::Tmp), context_manager_.GetTypeManager()),
|
||||||
utils::IsConstModifierToValueType(is_const_definition_.value())); // TODO ??
|
utils::IsConstModifierToValueType(is_const_definition_.value())); // TODO ??
|
||||||
|
|
@ -1254,13 +1253,21 @@ void TypeCheckVisitor::Visit(VariantType* node) {
|
||||||
node->base.type_ = current_type_;
|
node->base.type_ = current_type_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: better function design
|
||||||
// TODO handle local abstract types, abstract types, aliases, etc.
|
// TODO handle local abstract types, abstract types, aliases, etc.
|
||||||
void TypeCheckVisitor::Visit(TypeExpression* node) {
|
void TypeCheckVisitor::Visit(TypeExpression* node) {
|
||||||
std::unordered_map<std::string, utils::IdType> context;
|
std::unordered_map<std::string, utils::IdType> context;
|
||||||
CollectTypeExpressionContext(*node, context);
|
CollectTypeExpressionContext(*node, context);
|
||||||
|
|
||||||
|
auto maybe_internal_type = info::type::ToInternalType(node->type.type);
|
||||||
|
|
||||||
|
if (maybe_internal_type.has_value()) {
|
||||||
|
// checks made in link_symbols_visitor
|
||||||
|
|
||||||
|
current_type_ = context_manager_.AddType<info::type::InternalType>(maybe_internal_type.value(), utils::ValueType::Tmp);
|
||||||
|
} else {
|
||||||
std::optional<utils::IdType> maybe_local_abstract_type = context_manager_.GetLocalAbstractType(node->type.type);
|
std::optional<utils::IdType> maybe_local_abstract_type = context_manager_.GetLocalAbstractType(node->type.type);
|
||||||
if (node->path.size() == 0 && maybe_local_abstract_type.has_value()) {
|
if (node->path.empty() && maybe_local_abstract_type.has_value()) {
|
||||||
current_type_ = maybe_local_abstract_type.value();
|
current_type_ = maybe_local_abstract_type.value();
|
||||||
} else if (node->type.type_id_.has_value()) { // TODO: chack that names are different (always true ??)
|
} else if (node->type.type_id_.has_value()) { // TODO: chack that names are different (always true ??)
|
||||||
|
|
||||||
|
|
@ -1276,6 +1283,7 @@ void TypeCheckVisitor::Visit(TypeExpression* node) {
|
||||||
} else {
|
} else {
|
||||||
error_handling::HandleTypecheckError("Type not found", node->base);
|
error_handling::HandleTypecheckError("Type not found", node->base);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (node->array_size.has_value()) {
|
if (node->array_size.has_value()) {
|
||||||
current_type_ = context_manager_.AddType(
|
current_type_ = context_manager_.AddType(
|
||||||
|
|
@ -1342,6 +1350,12 @@ void TypeCheckVisitor::Visit(UnitLiteral* node) {
|
||||||
node->base.type_ = current_type_;
|
node->base.type_ = current_type_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TypeCheckVisitor::Visit(BoolLiteral* node) {
|
||||||
|
current_type_ = context_manager_.AddType(info::type::InternalType::Bool, utils::ValueType::Tmp);
|
||||||
|
|
||||||
|
node->base.type_ = current_type_;
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
||||||
void TypeCheckVisitor::CollectTypeContext(const ParametrizedType& type,
|
void TypeCheckVisitor::CollectTypeContext(const ParametrizedType& type,
|
||||||
|
|
|
||||||
|
|
@ -1065,4 +1065,14 @@ void TypedPrintVisitor::Visit(UnitLiteral* node) {
|
||||||
out_ << ") ()] ";
|
out_ << ") ()] ";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TypedPrintVisitor::Visit(BoolLiteral* node) {
|
||||||
|
out_ << "[bool : (";
|
||||||
|
|
||||||
|
if (node->base.type_.has_value()) {
|
||||||
|
out_ << context_manager_.GetAnyType(node->base.type_.value())->GetTypeName();
|
||||||
|
}
|
||||||
|
|
||||||
|
out_ << ") " << (node->value ? "true" : "false") << "] ";
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace interpreter
|
} // namespace interpreter
|
||||||
|
|
|
||||||
|
|
@ -285,6 +285,9 @@ void Visitor::Visit(Literal& node) {
|
||||||
case 4:
|
case 4:
|
||||||
Visit(std::get<std::unique_ptr<UnitLiteral>>(node).get());
|
Visit(std::get<std::unique_ptr<UnitLiteral>>(node).get());
|
||||||
break;
|
break;
|
||||||
|
case 5:
|
||||||
|
Visit(std::get<std::unique_ptr<BoolLiteral>>(node).get());
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
// error
|
// error
|
||||||
break;
|
break;
|
||||||
|
|
@ -674,5 +677,7 @@ void Visitor::Visit(CharLiteral* node) {}
|
||||||
|
|
||||||
void Visitor::Visit(UnitLiteral* node) {}
|
void Visitor::Visit(UnitLiteral* node) {}
|
||||||
|
|
||||||
|
void Visitor::Visit(BoolLiteral* node) {}
|
||||||
|
|
||||||
} // namespace interpreter
|
} // namespace interpreter
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,3 @@
|
||||||
basic String
|
|
||||||
basic Int
|
|
||||||
basic Unit
|
|
||||||
|
|
||||||
decl print : String -> Unit
|
decl print : String -> Unit
|
||||||
|
|
||||||
decl func : String -> Int
|
decl func : String -> Int
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue