public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc r14-7658] gccrs: expand: Add prc macro expander and registration
@ 2024-01-16 17:51 Arthur Cohen
0 siblings, 0 replies; only message in thread
From: Arthur Cohen @ 2024-01-16 17:51 UTC (permalink / raw)
To: gcc-cvs
https://gcc.gnu.org/g:663c4102a8ad43ec409e04d5ab834d38f161bdb5
commit r14-7658-g663c4102a8ad43ec409e04d5ab834d38f161bdb5
Author: Pierre-Emmanuel Patry <pierre-emmanuel.patry@embecosm.com>
Date: Thu May 18 14:05:25 2023 +0200
gccrs: expand: Add prc macro expander and registration
Add containers and functions to the hir-map in order to register and
lookup all three kind of procedural macros.
Add a first draft for attribute procedural macro expansion. This
expander still lack proper error handling as well as polishing.
gcc/rust/ChangeLog:
* util/rust-hir-map.cc (Mappings::insert_bang_proc_macro):
Add a function to insert a new bang proc macro.
(Mappings::lookup_bang_proc_macro): Add a function to lookup a
bang procedural macro.
(Mappings::insert_derive_proc_macro): Add a function to insert a
derive procedural macro.
(Mappings::lookup_derive_proc_macro): Add a function to lookup a
derive procedural macro.
(Mappings::insert_attribute_proc_macro): Add a function to
insert an attribute procedural macro.
(Mappings::lookup_attribute_proc_macro): Add a function to
lookup an attribute procedural macro.
* util/rust-hir-map.h: Add function prototypes.
* expand/rust-expand-visitor.cc (ExpandVisitor::expand_outer_attribute):
Implement expansion of outer attributes.
(ExpandVisitor::expand_inner_attribute):
Add call for inner attribute expansion.
* expand/rust-expand-visitor.h:
Add new procedural macro expander attribute.
* expand/rust-proc-macro.cc (load_macros_array): Add a function
to load the proc macro array from a given shared object.
(load_macros): Add a function to retrieve procedural macro
vector from a given shared object.
(ProcMacroExpander::import_proc_macros): Add a function to load
procedural macros from a given extern crate name.
* expand/rust-proc-macro.h (RUST_PROC_MACRO_H): Add new
proc-macro file.
(class ProcMacroExpander): Add new ProcMacroExpander class.
* rust-session-manager.cc (Session::expansion): Create new macro
expander and feed it to the expand visitor.
* util/rust-attributes.cc: Add macro_export builtin attribute.
Signed-off-by: Pierre-Emmanuel Patry <pierre-emmanuel.patry@embecosm.com>
Diff:
---
gcc/rust/expand/rust-expand-visitor.cc | 8 ++--
gcc/rust/expand/rust-expand-visitor.h | 6 ++-
gcc/rust/expand/rust-proc-macro.cc | 43 ++++++++++++++++++
gcc/rust/expand/rust-proc-macro.h | 79 ++++++++++++++++++++++++++++++++++
gcc/rust/rust-session-manager.cc | 3 +-
gcc/rust/util/rust-attributes.cc | 1 +
gcc/rust/util/rust-hir-map.cc | 66 ++++++++++++++++++++++++++++
gcc/rust/util/rust-hir-map.h | 29 ++++++++++++-
8 files changed, 229 insertions(+), 6 deletions(-)
diff --git a/gcc/rust/expand/rust-expand-visitor.cc b/gcc/rust/expand/rust-expand-visitor.cc
index b95649d5cd6..04a899f1497 100644
--- a/gcc/rust/expand/rust-expand-visitor.cc
+++ b/gcc/rust/expand/rust-expand-visitor.cc
@@ -17,6 +17,7 @@
// <http://www.gnu.org/licenses/>.
#include "rust-expand-visitor.h"
+#include "rust-proc-macro.h"
#include "rust-attributes.h"
#include "rust-ast.h"
#include "rust-type.h"
@@ -1551,7 +1552,8 @@ template <typename T>
void
ExpandVisitor::expand_outer_attribute (T &item, AST::SimplePath &path)
{
- // FIXME: Implement outer attribute expansion
+ // FIXME: Retrieve path from segments + local use statements instead of string
+ proc_expander.expand_attribute_proc_macro (item, path);
}
template <typename T>
@@ -1585,8 +1587,8 @@ template <typename T>
void
ExpandVisitor::expand_inner_attribute (T &item, AST::SimplePath &path)
{
- // TODO: Warn about instability ?
- // FIXME: Implement expansion for that particular path
+ // FIXME: Retrieve path from segments + local use statements instead of string
+ proc_expander.expand_attribute_proc_macro (item, path);
}
template <typename T>
diff --git a/gcc/rust/expand/rust-expand-visitor.h b/gcc/rust/expand/rust-expand-visitor.h
index 85893347def..fd72d0b6771 100644
--- a/gcc/rust/expand/rust-expand-visitor.h
+++ b/gcc/rust/expand/rust-expand-visitor.h
@@ -21,6 +21,7 @@
#include "rust-ast-visitor.h"
#include "rust-macro-expand.h"
+#include "rust-proc-macro.h"
namespace Rust {
@@ -39,7 +40,9 @@ is_builtin (AST::Attribute &attr);
class ExpandVisitor : public AST::ASTVisitor
{
public:
- ExpandVisitor (MacroExpander &expander) : expander (expander) {}
+ ExpandVisitor (MacroExpander &expander, ProcMacroExpander &proc_expander)
+ : expander (expander), proc_expander (proc_expander)
+ {}
/* Expand all of the macro invocations currently contained in a crate */
void go (AST::Crate &crate);
@@ -374,6 +377,7 @@ public:
private:
MacroExpander &expander;
+ ProcMacroExpander &proc_expander;
};
} // namespace Rust
diff --git a/gcc/rust/expand/rust-proc-macro.cc b/gcc/rust/expand/rust-proc-macro.cc
index 22744cb547d..a53a5d87ab9 100644
--- a/gcc/rust/expand/rust-proc-macro.cc
+++ b/gcc/rust/expand/rust-proc-macro.cc
@@ -61,4 +61,47 @@ load_macros (std::string path)
array->macros + array->length);
}
+void
+ProcMacroExpander::import_proc_macros (std::string extern_crate)
+{
+ auto path = session.extern_crates.find (extern_crate);
+ if (path == session.extern_crates.end ())
+ {
+ // Extern crate path is not available.
+ // FIXME: Emit error
+ rust_error_at (Location (), "Cannot find requested proc macro crate");
+ gcc_unreachable ();
+ }
+ auto macros = load_macros (path->second);
+
+ std::string prefix = extern_crate + "::";
+ for (auto ¯o : macros)
+ {
+ switch (macro.tag)
+ {
+ case ProcMacro::CUSTOM_DERIVE:
+ rust_debug ("Found one derive proc macro.");
+ mappings->insert_derive_proc_macro (
+ std::make_pair (extern_crate,
+ macro.payload.custom_derive.trait_name),
+ macro.payload.custom_derive);
+ break;
+ case ProcMacro::ATTR:
+ rust_debug ("Found one attribute proc macro.");
+ mappings->insert_attribute_proc_macro (
+ std::make_pair (extern_crate, macro.payload.attribute.name),
+ macro.payload.attribute);
+ break;
+ case ProcMacro::BANG:
+ rust_debug ("Found one bang proc macro.");
+ mappings->insert_bang_proc_macro (
+ std::make_pair (extern_crate, macro.payload.bang.name),
+ macro.payload.bang);
+ break;
+ default:
+ gcc_unreachable ();
+ }
+ }
+}
+
} // namespace Rust
diff --git a/gcc/rust/expand/rust-proc-macro.h b/gcc/rust/expand/rust-proc-macro.h
index 779d3c70fbc..244d274773c 100644
--- a/gcc/rust/expand/rust-proc-macro.h
+++ b/gcc/rust/expand/rust-proc-macro.h
@@ -17,6 +17,13 @@
#ifndef RUST_PROC_MACRO_H
#define RUST_PROC_MACRO_H
+#include <string>
+#include "rust-hir-map.h"
+#include "rust-name-resolver.h"
+#include "rust-session-manager.h"
+#include "rust-ast.h"
+#include "rust-ast-collector.h"
+#include "rust-token-converter.h"
#include "libproc_macro/proc_macro.h"
namespace Rust {
@@ -29,6 +36,78 @@ namespace Rust {
const std::vector<ProcMacro::Procmacro>
load_macros (std::string path);
+class ProcMacroExpander
+{
+public:
+ ProcMacroExpander (Session &session)
+ : session (session), has_changed_flag (false),
+ resolver (Resolver::Resolver::get ()),
+ mappings (Analysis::Mappings::get ())
+
+ {}
+
+ ~ProcMacroExpander () = default;
+
+ void import_proc_macros (std::string extern_crate);
+
+ template <typename T>
+ void expand_derive_proc_macro (T &item, std::string &trait_name)
+ {}
+
+ template <typename T>
+ void expand_bang_proc_macro (T &item, AST::SimplePath &path)
+ {}
+
+ template <typename T>
+ void expand_attribute_proc_macro (T &item, AST::SimplePath &path)
+ {
+ ProcMacro::Attribute macro;
+
+ std::string crate = path.get_segments ()[0].get_segment_name ();
+ std::string name = path.get_segments ()[1].get_segment_name ();
+ if (!mappings->lookup_attribute_proc_macro (std::make_pair (crate, name),
+ macro))
+ {
+ // FIXME: Resolve this path segment instead of taking it directly.
+ import_proc_macros (crate);
+ }
+
+ if (!mappings->lookup_attribute_proc_macro (std::make_pair (crate, name),
+ macro))
+ {
+ rust_error_at (Location (), "procedural macro %s not found",
+ name.c_str ());
+ rust_assert (false);
+ }
+ // FIXME: Attach result back to the ast
+ std::vector<TokenPtr> tokens;
+ AST::TokenCollector collector (tokens);
+
+ collector.visit (item);
+
+ std::vector<const_TokenPtr> vec;
+ for (auto i : collector.collect_tokens ())
+ {
+ vec.push_back (std::const_pointer_cast<Token> (i));
+ }
+
+ // FIXME: Handle attributes
+ macro.macro (ProcMacro::TokenStream::make_tokenstream (), convert (vec));
+ }
+
+ bool has_changed () const { return has_changed_flag; }
+
+ void reset_changed_state () { has_changed_flag = false; }
+
+private:
+ Session &session;
+ bool has_changed_flag;
+
+public:
+ Resolver::Resolver *resolver;
+ Analysis::Mappings *mappings;
+};
+
} // namespace Rust
#endif /* ! RUST_PROC_MACRO_H */
diff --git a/gcc/rust/rust-session-manager.cc b/gcc/rust/rust-session-manager.cc
index c7bbe89b281..401d70590c4 100644
--- a/gcc/rust/rust-session-manager.cc
+++ b/gcc/rust/rust-session-manager.cc
@@ -867,12 +867,13 @@ Session::expansion (AST::Crate &crate)
/* expand by calling cxtctxt object's monotonic_expander's expand_crate
* method. */
MacroExpander expander (crate, cfg, *this);
+ ProcMacroExpander proc_expander (*this);
while (!fixed_point_reached && iterations < cfg.recursion_limit)
{
CfgStrip ().go (crate);
Resolver::EarlyNameResolver ().go (crate);
- ExpandVisitor (expander).go (crate);
+ ExpandVisitor (expander, proc_expander).go (crate);
fixed_point_reached = !expander.has_changed ();
expander.reset_changed_state ();
diff --git a/gcc/rust/util/rust-attributes.cc b/gcc/rust/util/rust-attributes.cc
index 3a33d0629f2..4c7cb869861 100644
--- a/gcc/rust/util/rust-attributes.cc
+++ b/gcc/rust/util/rust-attributes.cc
@@ -43,6 +43,7 @@ static const BuiltinAttrDefinition __definitions[]
{"rustc_builtin_macro", EXPANSION},
{"path", EXPANSION},
{"macro_use", NAME_RESOLUTION},
+ {"macro_export", NAME_RESOLUTION},
// FIXME: This is not implemented yet, see
// https://github.com/Rust-GCC/gccrs/issues/1475
{"target_feature", CODE_GENERATION},
diff --git a/gcc/rust/util/rust-hir-map.cc b/gcc/rust/util/rust-hir-map.cc
index 93066f52d95..2f6d02d4187 100644
--- a/gcc/rust/util/rust-hir-map.cc
+++ b/gcc/rust/util/rust-hir-map.cc
@@ -941,6 +941,72 @@ Mappings::get_exported_macros ()
return exportedMacros;
}
+void
+Mappings::insert_derive_proc_macro (
+ std::pair<std::string, std::string> hierarchy, ProcMacro::CustomDerive macro)
+{
+ auto it = procmacroDeriveMappings.find (hierarchy);
+ rust_assert (it == procmacroDeriveMappings.end ());
+
+ procmacroDeriveMappings[hierarchy] = macro;
+}
+
+void
+Mappings::insert_bang_proc_macro (std::pair<std::string, std::string> hierarchy,
+ ProcMacro::Bang macro)
+{
+ auto it = procmacroBangMappings.find (hierarchy);
+ rust_assert (it == procmacroBangMappings.end ());
+
+ procmacroBangMappings[hierarchy] = macro;
+}
+
+void
+Mappings::insert_attribute_proc_macro (
+ std::pair<std::string, std::string> hierarchy, ProcMacro::Attribute macro)
+{
+ auto it = procmacroAttributeMappings.find (hierarchy);
+ rust_assert (it == procmacroAttributeMappings.end ());
+
+ procmacroAttributeMappings[hierarchy] = macro;
+}
+
+bool
+Mappings::lookup_derive_proc_macro (
+ std::pair<std::string, std::string> hierarchy, ProcMacro::CustomDerive ¯o)
+{
+ auto it = procmacroDeriveMappings.find (hierarchy);
+ if (it == procmacroDeriveMappings.end ())
+ return false;
+
+ macro = it->second;
+ return true;
+}
+
+bool
+Mappings::lookup_bang_proc_macro (std::pair<std::string, std::string> hierarchy,
+ ProcMacro::Bang ¯o)
+{
+ auto it = procmacroBangMappings.find (hierarchy);
+ if (it == procmacroBangMappings.end ())
+ return false;
+
+ macro = it->second;
+ return true;
+}
+
+bool
+Mappings::lookup_attribute_proc_macro (
+ std::pair<std::string, std::string> hierarchy, ProcMacro::Attribute ¯o)
+{
+ auto it = procmacroAttributeMappings.find (hierarchy);
+ if (it == procmacroAttributeMappings.end ())
+ return false;
+
+ macro = it->second;
+ return true;
+}
+
void
Mappings::insert_visibility (NodeId id, Privacy::ModuleVisibility visibility)
{
diff --git a/gcc/rust/util/rust-hir-map.h b/gcc/rust/util/rust-hir-map.h
index 21d1bc0622a..60498dec91c 100644
--- a/gcc/rust/util/rust-hir-map.h
+++ b/gcc/rust/util/rust-hir-map.h
@@ -28,6 +28,7 @@
#include "rust-hir-full-decls.h"
#include "rust-lang-item.h"
#include "rust-privacy-common.h"
+#include "libproc_macro/proc_macro.h"
namespace Rust {
namespace Analysis {
@@ -282,6 +283,22 @@ public:
void insert_exported_macro (AST::MacroRulesDefinition &def);
std::vector<NodeId> &get_exported_macros ();
+ void insert_derive_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::CustomDerive macro);
+ void insert_bang_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::Bang macro);
+ void
+ insert_attribute_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::Attribute macro);
+
+ bool lookup_derive_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::CustomDerive ¯o);
+ bool lookup_bang_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::Bang ¯o);
+ bool
+ lookup_attribute_proc_macro (std::pair<std::string, std::string> hierachy,
+ ProcMacro::Attribute ¯o);
+
void insert_visibility (NodeId id, Privacy::ModuleVisibility visibility);
bool lookup_visibility (NodeId id, Privacy::ModuleVisibility &def);
@@ -350,11 +367,21 @@ private:
// all hirid nodes
std::map<CrateNum, std::set<HirId>> hirNodesWithinCrate;
- // macros
+ // MBE macros
std::map<NodeId, AST::MacroRulesDefinition *> macroMappings;
std::map<NodeId, AST::MacroRulesDefinition *> macroInvocations;
std::vector<NodeId> exportedMacros;
+ // Procedural macros
+ std::map<std::pair<std::string, std::string>, ProcMacro::CustomDerive>
+ procmacroDeriveMappings;
+
+ std::map<std::pair<std::string, std::string>, ProcMacro::Bang>
+ procmacroBangMappings;
+
+ std::map<std::pair<std::string, std::string>, ProcMacro::Attribute>
+ procmacroAttributeMappings;
+
// crate names
std::map<CrateNum, std::string> crate_names;
^ permalink raw reply [flat|nested] only message in thread
only message in thread, other threads:[~2024-01-16 17:51 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2024-01-16 17:51 [gcc r14-7658] gccrs: expand: Add prc macro expander and registration Arthur Cohen
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).