From ba9a9199d01b0fdd4bf9a54914f8058bf71f30c5 Mon Sep 17 00:00:00 2001
From: Ferenc Szontágh <szf@fsociety.hu>
Date: Thu, 17 Apr 2025 16:03:01 +0000
Subject: [PATCH] unary and binary operations
---
src/Symbols/SymbolContainer.hpp | 136 +++++++++++++++++++++++++++++++++++++-------
1 files changed, 113 insertions(+), 23 deletions(-)
diff --git a/src/Symbols/SymbolContainer.hpp b/src/Symbols/SymbolContainer.hpp
index 1985c50..c0bb814 100644
--- a/src/Symbols/SymbolContainer.hpp
+++ b/src/Symbols/SymbolContainer.hpp
@@ -1,51 +1,141 @@
-// SymbolContainer.hpp
#ifndef SYMBOL_CONTAINER_HPP
#define SYMBOL_CONTAINER_HPP
+#include <memory>
+#include <stdexcept>
+#include <unordered_map>
+
#include "SymbolTable.hpp"
+
+#define NSMGR Symbols::SymbolContainer::instance()
namespace Symbols {
class SymbolContainer {
- std::shared_ptr<SymbolTable> globalScope_;
- std::shared_ptr<SymbolTable> currentScope_;
+ std::unordered_map<std::string, std::shared_ptr<SymbolTable>> scopes_;
+ std::string currentScope_ = "global";
+ std::string previousScope_ = "global";
-public:
- SymbolContainer() {
- globalScope_ = std::make_shared<SymbolTable>();
- currentScope_ = globalScope_;
+ public:
+ static SymbolContainer * instance() {
+ static SymbolContainer instance_;
+ return &instance_;
}
- void enterScope() {
- currentScope_ = std::make_shared<SymbolTable>(currentScope_);
+ explicit SymbolContainer(const std::string & default_scope_name = "global") { create(default_scope_name); }
+
+ // --- Scope management ---
+
+ void create(const std::string & name) {
+ scopes_[name] = std::make_shared<SymbolTable>();
+ previousScope_ = currentScope_;
+ currentScope_ = name;
}
- void leaveScope() {
- if (currentScope_->getParent()) {
- currentScope_ = currentScope_->getParent();
+ void enter(const std::string & name) {
+ if (scopes_.contains(name)) {
+ previousScope_ = currentScope_;
+ currentScope_ = name;
+ } else {
+ throw std::runtime_error("Scope does not exist: " + name);
}
}
- void define(const std::string& ns, const SymbolPtr& symbol) {
- currentScope_->define(ns, symbol);
+ void enterPreviousScope() { currentScope_ = previousScope_; }
+
+ [[nodiscard]] std::string currentScopeName() const { return currentScope_; }
+
+ std::vector<std::string> getScopeNames() const {
+ std::vector<std::string> result;
+ result.reserve(scopes_.size());
+ for (const auto & [scopeName, _] : scopes_) {
+ result.push_back(scopeName);
+ }
+ return result;
}
- SymbolPtr resolve(const std::string& ns, const std::string& name) const {
- return currentScope_->get(ns, name);
+ // --- Symbol operations ---
+
+ std::string add(const SymbolPtr & symbol) {
+ const std::string ns = getNamespaceForSymbol(symbol);
+ scopes_[currentScope_]->define(ns, symbol);
+ return ns;
}
- bool exists(const std::string& ns, const std::string& name) const {
- return currentScope_->exists(ns, name);
+ std::vector<std::string> getNameSpaces(const std::string & scopeName) const {
+ std::vector<std::string> result;
+ auto it = scopes_.find(scopeName);
+ if (it != scopes_.end()) {
+ return it->second->listNSs();
+ }
+ return result;
}
- std::vector<SymbolPtr> listNamespace(const std::string& ns) const {
- return currentScope_->listAll(ns);
+ std::vector<SymbolPtr> getAll(const std::string & ns = "") const {
+ std::vector<SymbolPtr> result;
+ for (const auto & [_, table] : scopes_) {
+ auto symbols = ns.empty() ? table->listAll() : table->listAll(ns);
+ result.insert(result.end(), symbols.begin(), symbols.end());
+ }
+ return result;
}
- std::shared_ptr<SymbolTable> getGlobalScope() const { return globalScope_; }
- std::shared_ptr<SymbolTable> getCurrentScope() const { return currentScope_; }
+ bool exists(const std::string & name, std::string fullNamespace = "") const {
+ if (fullNamespace.empty()) {
+ fullNamespace = currentScope_;
+ }
+
+ for (const auto & [_, table] : scopes_) {
+ if (table->exists(fullNamespace, name)) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ SymbolPtr get(const std::string & fullNamespace, const std::string & name) const {
+ for (const auto & [_, table] : scopes_) {
+ auto sym = table->get(fullNamespace, name);
+ if (sym) {
+ return sym;
+ }
+ }
+ return nullptr;
+ }
+
+ static std::string dump() {
+ std::string result = "";
+
+ std::cout << "\n--- Defined Scopes ---" << '\n';
+ for (const auto & scope_name : instance()->getScopeNames()) {
+ result += scope_name + '\n';
+ for (const auto & sname : instance()->getNameSpaces(scope_name)) {
+ result += "\t -" + sname + '\n';
+ for (const auto & symbol : instance()->getAll(sname)) {
+ result += symbol->dump() + '\n';
+ }
+ }
+ }
+ return result;
+ }
+
+ private:
+ std::string getNamespaceForSymbol(const SymbolPtr & symbol) const {
+ std::string base = symbol->context().empty() ? currentScope_ : symbol->context();
+
+ switch (symbol->type()) {
+ case Symbols::Kind::Variable:
+ return base + ".variables";
+ case Symbols::Kind::Function:
+ return base + ".functions";
+ case Symbols::Kind::Constant:
+ return base + ".constants";
+ default:
+ return base + ".others";
+ }
+ }
};
-} // namespace Symbols
+} // namespace Symbols
#endif
--
Gitblit v1.9.3