diff --git a/src/expand/mod.cpp b/src/expand/mod.cpp index 726c2b30..0d2649a8 100644 --- a/src/expand/mod.cpp +++ b/src/expand/mod.cpp @@ -1987,6 +1987,44 @@ void Expand_Mod_Early(::AST::Crate& crate, ::AST::Module& mod, std::vectorpath().is_trivial() && mi->path().as_trivial() == "macro_rules" ) { + auto mi_owned = mv$(*mi); + + TRACE_FUNCTION_F("Macro invoke " << mi_owned.path()); + + auto ttl = Expand_Macro(crate, {}, mod, mi_owned); + assert( mi_owned.path().is_valid() ); + + if( ttl.get() ) + { + // Re-parse tt + assert(ttl.get()); + DEBUG("-- Parsing as mod items"); + // Move the item list out + auto old_items = std::move(mod.m_items); + // Parse module items + Parse_ModRoot_Items(*ttl, mod); + auto new_item_count = mod.m_items.size(); + // Then insert the newly created items + old_items.insert(old_items.begin() + idx + 1, std::make_move_iterator(mod.m_items.begin()), std::make_move_iterator(mod.m_items.end())); + // and move the (updated) item list back in + mod.m_items = std::move(old_items); + + auto next_non_macro_item = idx + 1 + new_item_count; + //macro_recursion_stack.push_back(next_non_macro_item == mod.m_items.size() ? nullptr : &*mod.m_items[next_non_macro_item]); + } + mod.m_items[idx]->data.as_MacroInv() = mv$(mi_owned); + } + } + } } void Expand(::AST::Crate& crate) diff --git a/src/resolve/common.cpp b/src/resolve/common.cpp index 038cab8d..b5c12b2f 100644 --- a/src/resolve/common.cpp +++ b/src/resolve/common.cpp @@ -152,16 +152,23 @@ namespace { auto ec_it = AST::g_implicit_crates.find(name); if(ec_it != AST::g_implicit_crates.end()) { - const auto& ec = crate.m_extern_crates.at(ec_it->second); - DEBUG("Implicitly imported crate"); - //if( e.nodes.size() > 1 ) - //{ - return get_module_hir(ec.m_hir->m_root_module, path, 1, ignore_last, out_path); - //} - //else - //{ - // return ResolveModuleRef::make_ImplicitPrelude({}); - //} + if( ec_it->second == "" ) { + // This crate! + return get_module_ast(crate.m_root_module, path, 1, ignore_last, out_path); + } + else { + ASSERT_BUG(sp, crate.m_extern_crates.count(ec_it->second), "Crate \"" << ec_it->second << "\" not loaded (for \"" << ec_it->first << "\")"); + const auto& ec = crate.m_extern_crates.at(ec_it->second); + DEBUG("Implicitly imported crate"); + //if( e.nodes.size() > 1 ) + //{ + return get_module_hir(ec.m_hir->m_root_module, path, 1, ignore_last, out_path); + //} + //else + //{ + // return ResolveModuleRef::make_ImplicitPrelude({}); + //} + } } } DEBUG("Not found"); @@ -447,7 +454,7 @@ namespace { ResolveItemRef find_item(const AST::Module& mod, const RcString& name, ResolveNamespace ns, ::AST::AbsolutePath* out_path=nullptr) //ResolveModuleRef get_source_module_for_name(const AST::Module& mod, const RcString& name, ResolveNamespace ns, ::AST::AbsolutePath* out_path=nullptr) { - TRACE_FUNCTION_F("Looking for " << name << " in " << mod.path()); + TRACE_FUNCTION_F("Looking for " << name << " in " << mod.path() << " (ns=" << ns << ")"); if( mod.m_index_populated ) { TODO(sp, "Look up in index"); @@ -477,6 +484,7 @@ namespace { { for(const auto& i : mod.macros()) { + DEBUG("> MACRO " << i.name); if(i.name == name) { DEBUG("Found in ast (macro)"); diff --git a/src/resolve/common.hpp b/src/resolve/common.hpp index 0aa41865..82a1961b 100644 --- a/src/resolve/common.hpp +++ b/src/resolve/common.hpp @@ -65,6 +65,14 @@ enum class ResolveNamespace Value, Macro, }; +static inline ::std::ostream& operator<<(::std::ostream& os, ResolveNamespace ns) { + switch(ns) { + case ResolveNamespace::Namespace: return os << "Namespace"; + case ResolveNamespace::Value: return os << "Value"; + case ResolveNamespace::Macro: return os << "Macro"; + } + return os << "?"; +} /// /// Obtain a reference to the module pointed to by `path` (relative to `base_path`)