From 8660933f273a2937996c9f38fa30ac13f632e1e3 Mon Sep 17 00:00:00 2001 From: Deukhoofd Date: Fri, 8 Jan 2021 18:18:24 +0100 Subject: [PATCH] More work on binder type registration, support in REPL to show registered types. --- grammar.ebnf | 2 +- repl/ResultWindow.hpp | 58 ++++++ repl/main.cpp | 225 ++++++++++++----------- src/Binder/Binder.cpp | 32 +++- src/Binder/BoundNamespaceStringifier.hpp | 64 +++++++ src/Binder/BoundType.hpp | 39 +++- src/CoreData/Identifier.hpp | 2 +- src/CoreData/PrimitiveTypes.hpp | 22 +-- src/Diagnostics/DiagnosticType.hpp | 1 + src/Diagnostics/DiagnosticTypeEN_US.hpp | 5 +- src/Parser/Parser.cpp | 3 +- src/Utils/TreePrinter.hpp | 13 -- 12 files changed, 320 insertions(+), 146 deletions(-) create mode 100644 repl/ResultWindow.hpp create mode 100644 src/Binder/BoundNamespaceStringifier.hpp delete mode 100644 src/Utils/TreePrinter.hpp diff --git a/grammar.ebnf b/grammar.ebnf index cf992a8..9a81d68 100644 --- a/grammar.ebnf +++ b/grammar.ebnf @@ -86,7 +86,7 @@ virtprop ::= ['private' | 'protected'] type ['&'] identifier '{' {('g func ::= {'shared' | 'external'} ['private' | 'protected'] [((type ['&']) | '~')] identifier paramlist ['const'] funcattr (';' | statblock); funcdef ::= {'external' | 'shared'} 'funcdef' type ['&'] identifier paramlist ';' class ::= {'shared' | 'abstract' | 'final' | 'external'} 'class' identifier - (';' | ([':' identifier {',' identifier}] '{' {virtprop | func | var | funcdef} '}')); + (';' | ([':' identifier {',' identifier}] '{' {virtprop | func | var | funcdef | class} '}')); mixin ::= 'mixin' class; enum ::= {'shared' | 'external'} 'enum' identifier [ ':' primtype ] (';' | ('{' identifier ['=' expr] {',' identifier ['=' expr]} '}')); import ::= 'import' type ['&'] identifier paramlist funcattr 'from' string ';'; diff --git a/repl/ResultWindow.hpp b/repl/ResultWindow.hpp new file mode 100644 index 0000000..bcaf7d0 --- /dev/null +++ b/repl/ResultWindow.hpp @@ -0,0 +1,58 @@ +#ifndef MALACHSCRIPT_RESULTWINDOW_HPP +#define MALACHSCRIPT_RESULTWINDOW_HPP +#include +#include +#include "../src/Binder/BoundNamespaceStringifier.hpp" +#include "../src/Parser/Statements/ParsedStatementStringifier.hpp" + +namespace MalachScriptRepl { + class ResultWindow { + public: + enum class View { ParseTree, TypeList }; + + ResultWindow(int height, int width, int y, int x) { _window = newwin(height, width, y, x); } + + void SetResult(const MalachScript::Parser::ParsedStatement* statement, + const MalachScript::Binder::BoundNamespace* ns) { + std::stringstream parsedTreeStringStream; + MalachScript::Parser::ParsedStatementStringifier::Stringify(statement, parsedTreeStringStream, "", true); + _parseTree = parsedTreeStringStream.str(); + + std::stringstream boundNamespaceStringStream; + MalachScript::Binder::BoundNamespaceStringifier::Stringify(ns, boundNamespaceStringStream); + _boundNamespace = boundNamespaceStringStream.str(); + + switch (_view) { + case View::ParseTree: SetParseTree(); break; + case View::TypeList: SetTypeList(); break; + } + } + + void SetView(View view) { + _view = view; + switch (view) { + case View::ParseTree: SetParseTree(); break; + case View::TypeList: SetTypeList(); break; + } + } + + private: + WINDOW* _window; + std::string _parseTree; + std::string _boundNamespace; + View _view; + + inline void SetParseTree() { + wclear(_window); + waddstr(_window, _parseTree.c_str()); + wrefresh(_window); + } + inline void SetTypeList() { + wclear(_window); + waddstr(_window, _boundNamespace.c_str()); + wrefresh(_window); + } + }; +} + +#endif // MALACHSCRIPT_RESULTWINDOW_HPP diff --git a/repl/main.cpp b/repl/main.cpp index 7c40d60..6c5d2e0 100644 --- a/repl/main.cpp +++ b/repl/main.cpp @@ -1,129 +1,136 @@ #include #include #include +#include "../src/Binder/Binder.hpp" #include "../src/Diagnostics/DiagnosticTypeEN_US.hpp" #include "../src/Parser/Lexer/Lexer.hpp" #include "../src/Parser/Parser.hpp" -#include "../src/Parser/Statements/ParsedStatementStringifier.hpp" #include "InputWindow.hpp" +#include "ResultWindow.hpp" -void ParseAndUpdate(const std::vector& lines, WINDOW* diagnosticsWindow, WINDOW* parsedWindow, - MalachScriptRepl::InputWindow& inputWindow) { - std::string script; - for (size_t i = 0; i < lines.size(); i++) { - script += lines[i]; - if (i != lines.size() - 1) { - script += '\n'; +namespace MalachScriptRepl { + void ParseAndUpdate(const std::vector& lines, WINDOW* diagnosticsWindow, ResultWindow* parsedWindow, + MalachScriptRepl::InputWindow& inputWindow) { + std::string script; + for (size_t i = 0; i < lines.size(); i++) { + script += lines[i]; + if (i != lines.size() - 1) { + script += '\n'; + } } + + std::ofstream outfile; + outfile.open("script.ms", std::ios::out | std::ios::trunc); + outfile << (char*)script.data(); + outfile.close(); + + auto logger = MalachScript::Diagnostics::Logger(); + auto lexer = MalachScript::Parser::Lexer("diag", script, &logger); + const auto* firstToken = lexer.Lex(); + const auto* parsedResult = MalachScript::Parser::Parser::Parse(firstToken, "diag", &logger); + + auto* ns = new MalachScript::Binder::BoundNamespace(); + const MalachScript::Binder::Binder::log_func log = + [&logger](MalachScript::Diagnostics::DiagnosticLevel level, MalachScript::Diagnostics::DiagnosticType type, + const MalachScript::TextSpan& span, + const std::vector& formats) { logger.Log(level, type, "", span, formats); }; + MalachScript::Binder::Binder::Bind(ns, {parsedResult}, log); + + const MalachScript::Diagnostics::Diagnostic* diag = nullptr; + wclear(diagnosticsWindow); + + if (!logger.GetMessages().empty()) { + diag = &logger.GetMessages()[0]; + + wattron(diagnosticsWindow, COLOR_PAIR(1)); + waddch(diagnosticsWindow, '['); + waddstr(diagnosticsWindow, "Error"); + waddch(diagnosticsWindow, ']'); + wattroff(diagnosticsWindow, COLOR_PAIR(1)); + waddch(diagnosticsWindow, ' '); + waddstr(diagnosticsWindow, std::to_string(diag->GetSpan().GetStart() + 1).c_str()); + waddch(diagnosticsWindow, '-'); + waddstr(diagnosticsWindow, std::to_string(diag->GetSpan().GetEnd() + 1).c_str()); + waddch(diagnosticsWindow, ' '); + + waddstr(diagnosticsWindow, MalachScript::Diagnostics::DiagnosticTypeHelper::ToEnglishString(diag).c_str()); + + waddch(diagnosticsWindow, '\n'); + } + wrefresh(diagnosticsWindow); + + parsedWindow->SetResult(parsedResult, ns); + inputWindow.SetScriptWithDiagnostics(script, diag); + delete parsedResult; } - std::ofstream outfile; - outfile.open("script.ms", std::ios::out | std::ios::trunc); - outfile << (char*)script.data(); - outfile.close(); + int Run() { + setlocale(LC_ALL, ""); + initscr(); + cbreak(); + noecho(); + keypad(stdscr, true); + set_tabsize(4); - auto logger = MalachScript::Diagnostics::Logger(); - auto lexer = MalachScript::Parser::Lexer("diag", script, &logger); - const auto* firstToken = lexer.Lex(); - const auto* parsedResult = MalachScript::Parser::Parser::Parse(firstToken, "diag", &logger); + start_color(); + init_pair(1, COLOR_RED, COLOR_BLACK); + clear(); - const MalachScript::Diagnostics::Diagnostic* diag = nullptr; - wclear(diagnosticsWindow); + int maxX; + int maxY; + getmaxyx(stdscr, maxY, maxX); + wresize(stdscr, maxY, maxX); + wrefresh(stdscr); - if (!logger.GetMessages().empty()) { - diag = &logger.GetMessages()[0]; + const int inputFieldSize = 30; - wattron(diagnosticsWindow, COLOR_PAIR(1)); - waddch(diagnosticsWindow, '['); - waddstr(diagnosticsWindow, "Error"); - waddch(diagnosticsWindow, ']'); - wattroff(diagnosticsWindow, COLOR_PAIR(1)); - waddch(diagnosticsWindow, ' '); - waddstr(diagnosticsWindow, std::to_string(diag->GetSpan().GetStart() + 1).c_str()); - waddch(diagnosticsWindow, '-'); - waddstr(diagnosticsWindow, std::to_string(diag->GetSpan().GetEnd() + 1).c_str()); - waddch(diagnosticsWindow, ' '); + wborder(stdscr, 0, 0, 0, 0, 0, 0, 0, 0); + wmove(stdscr, 31, 1); + whline(stdscr, ACS_HLINE, maxX - 2); + wmove(stdscr, 32, maxX / 2); + wvline(stdscr, ACS_VLINE, 25); - waddstr(diagnosticsWindow, MalachScript::Diagnostics::DiagnosticTypeHelper::ToEnglishString(diag).c_str()); + wrefresh(stdscr); - waddch(diagnosticsWindow, '\n'); + [[maybe_unused]] auto* diagnosticsWindow = newwin(25, (maxX - 4) / 2, 32, 2); + + auto* parsedResultWindow = new ResultWindow(25, (maxX - 4) / 2 - 2, 32, (maxX - 4) / 2 + 4); + + auto inputWindow = MalachScriptRepl::InputWindow(inputFieldSize, maxX - 3, 1, 2); + inputWindow.RegisterOnChange( + [diagnosticsWindow, parsedResultWindow, &inputWindow](const std::vector& lines) { + ParseAndUpdate(lines, diagnosticsWindow, parsedResultWindow, inputWindow); + }); + + int c; + bool running = true; + while (running) { + c = inputWindow.GetInput(); + switch (c) { + case 27: running = false; break; + + case KEY_LEFT: inputWindow.MoveCursorLeft(); break; + case KEY_RIGHT: inputWindow.MoveCursorRight(); break; + case KEY_UP: inputWindow.MoveCursorUp(); break; + case KEY_DOWN: inputWindow.MoveCursorDown(); break; + case KEY_BACKSPACE: + case 127: inputWindow.Backspace(); break; + case 10: + case KEY_ENTER: inputWindow.Return(); break; + case 9: + case KEY_STAB: inputWindow.Tab(); break; + case KEY_END: inputWindow.GoToEndOfLine(); break; + case KEY_HOME: inputWindow.GoToStartOfLine(); break; + case KEY_F(1): parsedResultWindow->SetView(ResultWindow::View::ParseTree); break; + case KEY_F(2): parsedResultWindow->SetView(ResultWindow::View::TypeList); break; + default: inputWindow.Input(c); break; + } + inputWindow.Refresh(); + } + endwin(); + + return EXIT_SUCCESS; } - wrefresh(diagnosticsWindow); - - wclear(parsedWindow); - std::stringstream ss; - MalachScript::Parser::ParsedStatementStringifier::Stringify(parsedResult, ss, "", true); - - waddstr(parsedWindow, ss.str().c_str()); - wrefresh(parsedWindow); - - inputWindow.SetScriptWithDiagnostics(script, diag); - delete parsedResult; } -int main([[maybe_unused]] int argc, [[maybe_unused]] const char* argv[]) { - setlocale(LC_ALL, ""); - initscr(); - cbreak(); - noecho(); - keypad(stdscr, true); - set_tabsize(4); - - start_color(); - init_pair(1, COLOR_RED, COLOR_BLACK); - clear(); - - int maxX; - int maxY; - getmaxyx(stdscr, maxY, maxX); - wresize(stdscr, maxY, maxX); - wrefresh(stdscr); - - const int inputFieldSize = 30; - - wborder(stdscr, 0, 0, 0, 0, 0, 0, 0, 0); - wmove(stdscr, 31, 1); - whline(stdscr, ACS_HLINE, maxX - 2); - wmove(stdscr, 32, maxX / 2); - wvline(stdscr, ACS_VLINE, 25); - - wrefresh(stdscr); - - [[maybe_unused]] auto* diagnosticsWindow = newwin(25, (maxX - 4) / 2, 32, 2); - - auto* parsedResultWindow = newwin(25, (maxX - 4) / 2 - 2, 32, (maxX - 4) / 2 + 4); - wrefresh(parsedResultWindow); - - auto inputWindow = MalachScriptRepl::InputWindow(inputFieldSize, maxX - 3, 1, 2); - inputWindow.RegisterOnChange( - [diagnosticsWindow, parsedResultWindow, &inputWindow](const std::vector& lines) { - ParseAndUpdate(lines, diagnosticsWindow, parsedResultWindow, inputWindow); - }); - - int c; - bool running = true; - while (running) { - c = inputWindow.GetInput(); - switch (c) { - case 27: running = false; break; - - case KEY_LEFT: inputWindow.MoveCursorLeft(); break; - case KEY_RIGHT: inputWindow.MoveCursorRight(); break; - case KEY_UP: inputWindow.MoveCursorUp(); break; - case KEY_DOWN: inputWindow.MoveCursorDown(); break; - case KEY_BACKSPACE: - case 127: inputWindow.Backspace(); break; - case 10: - case KEY_ENTER: inputWindow.Return(); break; - case 9: - case KEY_STAB: inputWindow.Tab(); break; - case KEY_END: inputWindow.GoToEndOfLine(); break; - case KEY_HOME: inputWindow.GoToStartOfLine(); break; - default: inputWindow.Input(c); break; - } - inputWindow.Refresh(); - } - endwin(); - - return EXIT_SUCCESS; -} \ No newline at end of file +int main([[maybe_unused]] int argc, [[maybe_unused]] const char* argv[]) { return MalachScriptRepl::Run(); } \ No newline at end of file diff --git a/src/Binder/Binder.cpp b/src/Binder/Binder.cpp index d75c30f..84c6170 100644 --- a/src/Binder/Binder.cpp +++ b/src/Binder/Binder.cpp @@ -54,13 +54,23 @@ namespace MalachScript::Binder { case Parser::ParsedStatementKind::Class: { const auto* s = static_cast(statement); auto identifier = s->GetIdentifier(); - if (activeType.has_value()) { + auto type = ns->ResolveType(s->GetIdentifier()); + if (!type.has_value()) { + if (activeType.has_value()) { + type = activeType.value()->ResolveType(s->GetIdentifier()); + } } - auto* type = new BoundType(s->GetClassAttr()); + if (type.has_value()) { + log(DiagnosticLevel::Error, DiagnosticType::TypeAlreadyDefined, s->GetSpan(), + {identifier.GetStdString()}); + break; + } + + type = new BoundType(identifier, s->GetClassAttr()); if (activeType.has_value()) { - activeType.value()->RegisterType(identifier, type); + activeType.value()->RegisterType(identifier, type.value()); } else { - ns->RegisterType(identifier, type); + ns->RegisterType(identifier, type.value()); } for (const auto& child : s->GetBody()) { TypeRegistrationFirstPass(ns, child.get(), type, log); @@ -92,7 +102,12 @@ namespace MalachScript::Binder { const auto* s = static_cast(statement); auto type = ns->ResolveType(s->GetIdentifier()); if (!type.has_value()) { - throw std::logic_error("Shouldn't be reached"); + if (activeType.has_value()) { + type = activeType.value()->ResolveType(s->GetIdentifier()); + } + if (!type.has_value()) { + throw std::logic_error("Shouldn't be reached"); + } } for (const auto& inherits : s->GetInherits()) { auto inheritType = ResolveType(ns, inherits); @@ -152,7 +167,12 @@ namespace MalachScript::Binder { const auto* s = static_cast(statement); auto type = ns->ResolveType(s->GetIdentifier()); if (!type.has_value()) { - throw std::logic_error("Shouldn't be reached"); + if (activeType.has_value()) { + type = activeType.value()->ResolveType(s->GetIdentifier()); + } + if (!type.has_value()) { + throw std::logic_error("Shouldn't be reached"); + } } for (const auto& child : s->GetBody()) { TypeRegistrationThirdPass(ns, child.get(), type.value(), log); diff --git a/src/Binder/BoundNamespaceStringifier.hpp b/src/Binder/BoundNamespaceStringifier.hpp new file mode 100644 index 0000000..e687f56 --- /dev/null +++ b/src/Binder/BoundNamespaceStringifier.hpp @@ -0,0 +1,64 @@ +#ifndef MALACHSCRIPT_BOUNDNAMESPACESTRINGIFIER_HPP +#define MALACHSCRIPT_BOUNDNAMESPACESTRINGIFIER_HPP + +#include "BoundNamespace.hpp" + +template static std::vector> mapToVector(const std::unordered_map& map) { + auto vec = std::vector>(map.begin(), map.end()); + std::reverse(vec.begin(), vec.end()); + return vec; +}; + +namespace MalachScript::Binder { + class BoundNamespaceStringifier { + static void StringifyField(const MalachScript::Identifier& identifier, const BoundVariable* field, + std::stringstream& stream, const std::string& prefix, bool isLast) { + stream << prefix; + stream << (isLast ? "└──" : "├──"); + stream << identifier << ": " << field->GetType()->GetIdentifier(); + } + static void StringifyType(const MalachScript::Identifier& identifier, const BoundType* type, + std::stringstream& stream, const std::string& prefix, bool isLast) { + stream << prefix; + stream << (isLast ? "└──" : "├──"); + stream << "class " << identifier << " (size: " << type->GetSize() << ")"; + auto types = mapToVector(type->GetTypes()); + for (size_t i = 0; i < types.size(); i++) { + stream << std::endl; + StringifyType(types[i].first, types[i].second, stream, prefix + (isLast ? " " : "│ "), + i == types.size() - 1); + } + auto fields = mapToVector(type->GetFieldsLookup()); + for (size_t i = 0; i < fields.size(); i++) { + stream << std::endl; + StringifyField(fields[i].first, fields[i].second, stream, prefix + (isLast ? " " : "│ "), + i == fields.size() - 1); + } + } + static void StringifyNamespace(const MalachScript::Identifier& identifier, const BoundNamespace* boundNamespace, + std::stringstream& stream, const std::string& prefix, bool isLast) { + stream << prefix; + stream << (isLast ? "└──" : "├──"); + stream << "namespace " << identifier; + auto types = mapToVector(boundNamespace->GetTypes()); + for (size_t i = 0; i < types.size(); i++) { + stream << std::endl; + StringifyType(types[i].first, types[i].second, stream, prefix + (isLast ? " " : "│ "), + i == types.size() - 1); + } + auto namespaces = mapToVector(boundNamespace->GetNamespaces()); + for (size_t i = 0; i < namespaces.size(); i++) { + stream << std::endl; + StringifyNamespace(namespaces[i].first, namespaces[i].second, stream, + prefix + (isLast ? " " : "│ "), i == namespaces.size() - 1); + } + } + + public: + static void Stringify(const BoundNamespace* ns, std::stringstream& stream) { + StringifyNamespace("global"_id, ns, stream, "", true); + } + }; +} + +#endif // MALACHSCRIPT_BOUNDNAMESPACESTRINGIFIER_HPP diff --git a/src/Binder/BoundType.hpp b/src/Binder/BoundType.hpp index e4a7de1..89e718c 100644 --- a/src/Binder/BoundType.hpp +++ b/src/Binder/BoundType.hpp @@ -7,14 +7,31 @@ namespace MalachScript::Binder { class BoundType { public: - BoundType(ClassAttr classAttr) : _classAttr(classAttr) {} - BoundType(ClassAttr classAttr, size_t size) : _classAttr(classAttr), _size(size), _inherits(0) {} + BoundType(Identifier identifier, ClassAttr classAttr) : _identifier(identifier), _classAttr(classAttr) {} + BoundType(Identifier identifier, ClassAttr classAttr, size_t size) + : _identifier(identifier), _classAttr(classAttr), _size(size), _inherits(0) {} inline void Finalise() noexcept { + if (_initialised) { + return; + } _initialised = true; - // TODO: Calculate size + for (auto& inherits : _inherits) { + if (!inherits->IsInitialised()) { + const_cast(inherits)->Finalise(); + } + _size += inherits->GetSize(); + } + for (auto& field : _fields) { + if (!field->GetType()->IsInitialised()) { + const_cast(field->GetType())->Finalise(); + } + _size += field->GetType()->GetSize(); + } } + [[nodiscard]] inline const Identifier& GetIdentifier() const noexcept { return _identifier; } [[nodiscard]] inline size_t GetSize() const noexcept { return _size; } + [[nodiscard]] inline bool IsInitialised() const noexcept { return _initialised; } [[nodiscard]] inline ClassAttr GetAttributes() const noexcept { return _classAttr; } inline void AddInheritType(const BoundType* type) { _inherits.push_back(type); } @@ -27,8 +44,24 @@ namespace MalachScript::Binder { _types[identifier] = const_cast(type); } + [[nodiscard]] inline const std::unordered_map& GetTypes() const noexcept { + return _types; + } + [[nodiscard]] inline const std::unordered_map& GetFieldsLookup() const noexcept { + return _fieldsLookup; + } + + inline std::optional ResolveType(const Identifier& identifier) const noexcept { + auto find = _types.find(identifier); + if (find == _types.end()) { + return {}; + } + return find->second; + } + private: bool _initialised = false; + Identifier _identifier; ClassAttr _classAttr; size_t _size = 0; std::vector _inherits; diff --git a/src/CoreData/Identifier.hpp b/src/CoreData/Identifier.hpp index 6e1bf21..d9c6a25 100644 --- a/src/CoreData/Identifier.hpp +++ b/src/CoreData/Identifier.hpp @@ -48,7 +48,7 @@ namespace MalachScript { uint32_t _hash; public: - Identifier() : _str(nullptr), _length(0), _hash(0) {} + Identifier() : _str(empty.c_str()), _length(0), _hash(0) {} constexpr Identifier(const char* c) : _str(c), _length(CalcLength(c)), _hash(Hash(c)) {} constexpr Identifier(const char* c, size_t length) : _str(c), _length(length), _hash(Hash(c)) {} constexpr Identifier(const char* c, size_t length, uint32_t hash) : _str(c), _length(length), _hash(hash) {} diff --git a/src/CoreData/PrimitiveTypes.hpp b/src/CoreData/PrimitiveTypes.hpp index ccf600b..2f7b792 100644 --- a/src/CoreData/PrimitiveTypes.hpp +++ b/src/CoreData/PrimitiveTypes.hpp @@ -27,17 +27,17 @@ namespace MalachScript { static constinit Identifier _autoName = "auto"; - static Binder::BoundType _int8Type = Binder::BoundType(ClassAttr::None, sizeof(int8_t)); - static Binder::BoundType _int16Type = Binder::BoundType(ClassAttr::None, sizeof(int16_t)); - static Binder::BoundType _int32Type = Binder::BoundType(ClassAttr::None, sizeof(int32_t)); - static Binder::BoundType _int64Type = Binder::BoundType(ClassAttr::None, sizeof(int64_t)); - static Binder::BoundType _uint8Type = Binder::BoundType(ClassAttr::None, sizeof(uint8_t)); - static Binder::BoundType _uint16Type = Binder::BoundType(ClassAttr::None, sizeof(uint16_t)); - static Binder::BoundType _uint32Type = Binder::BoundType(ClassAttr::None, sizeof(uint32_t)); - static Binder::BoundType _uint64Type = Binder::BoundType(ClassAttr::None, sizeof(uint64_t)); - static Binder::BoundType _floatType = Binder::BoundType(ClassAttr::None, sizeof(float)); - static Binder::BoundType _doubleType = Binder::BoundType(ClassAttr::None, sizeof(double)); - static Binder::BoundType _boolType = Binder::BoundType(ClassAttr::None, sizeof(uint8_t)); + static Binder::BoundType _int8Type = Binder::BoundType(_int8Name, ClassAttr::None, sizeof(int8_t)); + static Binder::BoundType _int16Type = Binder::BoundType(_int16Name, ClassAttr::None, sizeof(int16_t)); + static Binder::BoundType _int32Type = Binder::BoundType(_int32Name, ClassAttr::None, sizeof(int32_t)); + static Binder::BoundType _int64Type = Binder::BoundType(_int64Name, ClassAttr::None, sizeof(int64_t)); + static Binder::BoundType _uint8Type = Binder::BoundType(_uint8Name, ClassAttr::None, sizeof(uint8_t)); + static Binder::BoundType _uint16Type = Binder::BoundType(_uint16Name, ClassAttr::None, sizeof(uint16_t)); + static Binder::BoundType _uint32Type = Binder::BoundType(_uint32Name, ClassAttr::None, sizeof(uint32_t)); + static Binder::BoundType _uint64Type = Binder::BoundType(_uint64Name, ClassAttr::None, sizeof(uint64_t)); + static Binder::BoundType _floatType = Binder::BoundType(_floatName, ClassAttr::None, sizeof(float)); + static Binder::BoundType _doubleType = Binder::BoundType(_doubleName, ClassAttr::None, sizeof(double)); + static Binder::BoundType _boolType = Binder::BoundType(_boolName, ClassAttr::None, sizeof(uint8_t)); class PrimitiveTypes { public: diff --git a/src/Diagnostics/DiagnosticType.hpp b/src/Diagnostics/DiagnosticType.hpp index 89023d5..368a7be 100644 --- a/src/Diagnostics/DiagnosticType.hpp +++ b/src/Diagnostics/DiagnosticType.hpp @@ -10,6 +10,7 @@ namespace MalachScript::Diagnostics { DoubleProperty, UnknownType, + TypeAlreadyDefined, }; } diff --git a/src/Diagnostics/DiagnosticTypeEN_US.hpp b/src/Diagnostics/DiagnosticTypeEN_US.hpp index d8447f7..3976305 100644 --- a/src/Diagnostics/DiagnosticTypeEN_US.hpp +++ b/src/Diagnostics/DiagnosticTypeEN_US.hpp @@ -24,7 +24,10 @@ namespace MalachScript::Diagnostics { } case DiagnosticType::DoubleProperty: return "Property block found twice."; - case DiagnosticType::UnknownType: util::Format("Unknown Type Encounted: '{0}'", diag->GetFormats()); + case DiagnosticType::UnknownType: + return util::Format("Unknown Type Encounted: '{0}'", diag->GetFormats()); + case DiagnosticType::TypeAlreadyDefined: + return util::Format("Type already defined: '{0}'", diag->GetFormats()); } return std::to_string((uint8_t)diag->GetType()); } diff --git a/src/Parser/Parser.cpp b/src/Parser/Parser.cpp index 06d566b..7ff4073 100644 --- a/src/Parser/Parser.cpp +++ b/src/Parser/Parser.cpp @@ -159,7 +159,8 @@ namespace MalachScript::Parser { ScopedPtr statement = nullptr; // TODO: Sort by complexity if (!ParseVirtProp(statement, current, log) && !ParseFunc(statement, current, log) && - !ParseVar(statement, current, log) && !ParseFuncDef(statement, current, log)) { + !ParseVar(statement, current, log) && !ParseFuncDef(statement, current, log) && + !ParseClass(statement, current, log)) { logUnexpectedTokenWithoutExpected(current); break; } diff --git a/src/Utils/TreePrinter.hpp b/src/Utils/TreePrinter.hpp deleted file mode 100644 index f29f916..0000000 --- a/src/Utils/TreePrinter.hpp +++ /dev/null @@ -1,13 +0,0 @@ -#ifndef MALACHSCRIPT_TREEPRINTER_HPP -#define MALACHSCRIPT_TREEPRINTER_HPP -#include - -class MalachScript::Utils { - class TreePrinter { - public: - private: - std::stringstream _stream; - }; -}; - -#endif // MALACHSCRIPT_TREEPRINTER_HPP