aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorKushal Pal <kushalpal109@gmail.com>2024-01-26 11:35:24 +0530
committerArthur Cohen <arthur.cohen@embecosm.com>2024-02-07 12:40:24 +0100
commit41cbf917de55341069efa389ec21f90a1197da53 (patch)
tree39ccdca02bb21e0d009b88bc5ea9fa1925e01c26 /gcc
parent4be51abd5e829b2b9e8f4b7bc48212c17cf4c3f9 (diff)
downloadgcc-41cbf917de55341069efa389ec21f90a1197da53.zip
gcc-41cbf917de55341069efa389ec21f90a1197da53.tar.gz
gcc-41cbf917de55341069efa389ec21f90a1197da53.tar.bz2
gccrs: Add missing visitors for AST::Function.
To use AST::Function instead of AST::TraitItemFunc and AST::TraitItemMethod, we need to provide similar visitors during lowering and resolving phase. gcc/rust/ChangeLog: * hir/rust-ast-lower-implitem.cc (ASTLowerTraitItem::visit): Provide visitor for AST::Function. * hir/rust-ast-lower-implitem.h: Likewise. * resolve/rust-ast-resolve-implitem.h: Likewise. * resolve/rust-ast-resolve-item.cc (ResolveTraitItems::visit): Likewise. * resolve/rust-ast-resolve-item.h: Likewise. Signed-off-by: Kushal Pal <kushalpal109@gmail.com>
Diffstat (limited to 'gcc')
-rw-r--r--gcc/rust/hir/rust-ast-lower-implitem.cc86
-rw-r--r--gcc/rust/hir/rust-ast-lower-implitem.h1
-rw-r--r--gcc/rust/resolve/rust-ast-resolve-implitem.h20
-rw-r--r--gcc/rust/resolve/rust-ast-resolve-item.cc88
-rw-r--r--gcc/rust/resolve/rust-ast-resolve-item.h1
5 files changed, 196 insertions, 0 deletions
diff --git a/gcc/rust/hir/rust-ast-lower-implitem.cc b/gcc/rust/hir/rust-ast-lower-implitem.cc
index 98db1dc..77230e7 100644
--- a/gcc/rust/hir/rust-ast-lower-implitem.cc
+++ b/gcc/rust/hir/rust-ast-lower-implitem.cc
@@ -228,6 +228,92 @@ ASTLowerTraitItem::translate (AST::AssociatedItem *item)
}
void
+ASTLowerTraitItem::visit (AST::Function &func)
+{
+ std::vector<std::unique_ptr<HIR::WhereClauseItem> > where_clause_items;
+ HIR::WhereClause where_clause (std::move (where_clause_items));
+ HIR::FunctionQualifiers qualifiers
+ = lower_qualifiers (func.get_qualifiers ());
+
+ std::vector<std::unique_ptr<HIR::GenericParam> > generic_params;
+ if (func.has_generics ())
+ generic_params = lower_generic_params (func.get_generic_params ());
+
+ std::unique_ptr<HIR::Type> return_type
+ = func.has_return_type () ? std::unique_ptr<HIR::Type> (
+ ASTLoweringType::translate (func.get_return_type ().get ()))
+ : nullptr;
+
+ // set self parameter to error if this is a method
+ // else lower to hir
+ HIR::SelfParam self_param = func.has_self_param ()
+ ? lower_self (func.get_self_param ())
+ : HIR::SelfParam::error ();
+
+ std::vector<HIR::FunctionParam> function_params;
+ for (auto &p : func.get_function_params ())
+ {
+ if (p->is_variadic () || p->is_self ())
+ continue;
+
+ auto param = static_cast<AST::FunctionParam *> (p.get ());
+
+ auto translated_pattern = std::unique_ptr<HIR::Pattern> (
+ ASTLoweringPattern::translate (param->get_pattern ().get ()));
+ auto translated_type = std::unique_ptr<HIR::Type> (
+ ASTLoweringType::translate (param->get_type ().get ()));
+
+ auto crate_num = mappings->get_current_crate ();
+ Analysis::NodeMapping mapping (crate_num, param->get_node_id (),
+ mappings->get_next_hir_id (crate_num),
+ UNKNOWN_LOCAL_DEFID);
+
+ auto hir_param
+ = HIR::FunctionParam (mapping, std::move (translated_pattern),
+ std::move (translated_type), param->get_locus ());
+ function_params.push_back (hir_param);
+ }
+
+ HIR::TraitFunctionDecl decl (func.get_function_name (),
+ std::move (qualifiers),
+ std::move (generic_params),
+ std::move (self_param),
+ std::move (function_params),
+ std::move (return_type),
+ std::move (where_clause));
+ bool terminated = false;
+ std::unique_ptr<HIR::BlockExpr> block_expr
+ = func.has_body () ? std::unique_ptr<HIR::BlockExpr> (
+ ASTLoweringBlock::translate (func.get_definition ()->get (),
+ &terminated))
+ : nullptr;
+
+ auto crate_num = mappings->get_current_crate ();
+ Analysis::NodeMapping mapping (crate_num, func.get_node_id (),
+ mappings->get_next_hir_id (crate_num),
+ mappings->get_next_localdef_id (crate_num));
+
+ auto *trait_item
+ = new HIR::TraitItemFunc (mapping, std::move (decl), std::move (block_expr),
+ func.get_outer_attrs (), func.get_locus ());
+ translated = trait_item;
+ if (func.has_self_param ())
+ {
+ // insert mappings for self
+ mappings->insert_hir_self_param (&self_param);
+ mappings->insert_location (self_param.get_mappings ().get_hirid (),
+ self_param.get_locus ());
+ }
+
+ // add the mappings for the function params at the end
+ for (auto &param : trait_item->get_decl ().get_function_params ())
+ {
+ mappings->insert_hir_param (&param);
+ mappings->insert_location (mapping.get_hirid (), param.get_locus ());
+ }
+}
+
+void
ASTLowerTraitItem::visit (AST::TraitItemFunc &func)
{
AST::TraitFunctionDecl &ref = func.get_trait_function_decl ();
diff --git a/gcc/rust/hir/rust-ast-lower-implitem.h b/gcc/rust/hir/rust-ast-lower-implitem.h
index 3a266b4..b9d12cc 100644
--- a/gcc/rust/hir/rust-ast-lower-implitem.h
+++ b/gcc/rust/hir/rust-ast-lower-implitem.h
@@ -48,6 +48,7 @@ class ASTLowerTraitItem : public ASTLoweringBase
public:
static HIR::TraitItem *translate (AST::AssociatedItem *item);
+ void visit (AST::Function &func) override;
void visit (AST::TraitItemFunc &func) override;
void visit (AST::TraitItemMethod &method) override;
void visit (AST::TraitItemConst &constant) override;
diff --git a/gcc/rust/resolve/rust-ast-resolve-implitem.h b/gcc/rust/resolve/rust-ast-resolve-implitem.h
index 365bdd61..d9c9bcb 100644
--- a/gcc/rust/resolve/rust-ast-resolve-implitem.h
+++ b/gcc/rust/resolve/rust-ast-resolve-implitem.h
@@ -110,6 +110,26 @@ public:
item->accept_vis (resolver);
};
+ void visit (AST::Function &function) override
+ {
+ auto decl
+ = CanonicalPath::new_seg (function.get_node_id (),
+ function.get_function_name ().as_string ());
+ auto path = prefix.append (decl);
+ auto cpath = canonical_prefix.append (decl);
+
+ resolver->get_name_scope ().insert (
+ path, function.get_node_id (), function.get_locus (), false,
+ Rib::ItemType::Function,
+ [&] (const CanonicalPath &, NodeId, location_t locus) -> void {
+ rich_location r (line_table, function.get_locus ());
+ r.add_range (locus);
+ rust_error_at (r, "redefined multiple times");
+ });
+
+ mappings->insert_canonical_path (function.get_node_id (), cpath);
+ }
+
void visit (AST::TraitItemFunc &function) override
{
auto decl = CanonicalPath::new_seg (
diff --git a/gcc/rust/resolve/rust-ast-resolve-item.cc b/gcc/rust/resolve/rust-ast-resolve-item.cc
index 60eca5b..6037fe5 100644
--- a/gcc/rust/resolve/rust-ast-resolve-item.cc
+++ b/gcc/rust/resolve/rust-ast-resolve-item.cc
@@ -46,6 +46,94 @@ ResolveTraitItems::go (AST::AssociatedItem *item, const CanonicalPath &prefix,
}
void
+ResolveTraitItems::visit (AST::Function &function)
+{
+ auto decl
+ = CanonicalPath::new_seg (function.get_node_id (),
+ function.get_function_name ().as_string ());
+ auto path = prefix.append (decl);
+ auto cpath = canonical_prefix.append (decl);
+ mappings->insert_canonical_path (function.get_node_id (), cpath);
+
+ NodeId scope_node_id = function.get_node_id ();
+ resolver->get_name_scope ().push (scope_node_id);
+ resolver->get_type_scope ().push (scope_node_id);
+ resolver->get_label_scope ().push (scope_node_id);
+ resolver->push_new_name_rib (resolver->get_name_scope ().peek ());
+ resolver->push_new_type_rib (resolver->get_type_scope ().peek ());
+ resolver->push_new_label_rib (resolver->get_type_scope ().peek ());
+
+ if (function.has_generics ())
+ for (auto &generic : function.get_generic_params ())
+ ResolveGenericParam::go (generic.get (), prefix, canonical_prefix);
+
+ if (function.has_return_type ())
+ ResolveType::go (function.get_return_type ().get ());
+
+ // self turns into (self: Self) as a function param
+ std::vector<PatternBinding> bindings
+ = {PatternBinding (PatternBoundCtx::Product, std::set<Identifier> ())};
+
+ // we make a new scope so the names of parameters are resolved and shadowed
+ // correctly
+ for (auto &p : function.get_function_params ())
+ {
+ if (p->is_variadic ())
+ {
+ auto param = static_cast<AST::VariadicParam *> (p.get ());
+ PatternDeclaration::go (param->get_pattern ().get (),
+ Rib::ItemType::Param, bindings);
+ }
+ else if (p->is_self ())
+ {
+ auto param = static_cast<AST::SelfParam *> (p.get ());
+ // FIXME: which location should be used for Rust::Identifier `self`?
+ AST::IdentifierPattern self_pattern (
+ param->get_node_id (), {"self"}, param->get_locus (),
+ param->get_has_ref (), param->get_is_mut (),
+ std::unique_ptr<AST::Pattern> (nullptr));
+
+ PatternDeclaration::go (&self_pattern, Rib::ItemType::Param);
+
+ if (param->has_type ())
+ {
+ // This shouldn't happen the parser should already error for this
+ rust_assert (!param->get_has_ref ());
+ ResolveType::go (param->get_type ().get ());
+ }
+ else
+ {
+ // here we implicitly make self have a type path of Self
+ std::vector<std::unique_ptr<AST::TypePathSegment>> segments;
+ segments.push_back (std::unique_ptr<AST::TypePathSegment> (
+ new AST::TypePathSegment ("Self", false, param->get_locus ())));
+
+ AST::TypePath self_type_path (std::move (segments),
+ param->get_locus ());
+ ResolveType::go (&self_type_path);
+ }
+ }
+ else
+ {
+ auto param = static_cast<AST::FunctionParam *> (p.get ());
+ ResolveType::go (param->get_type ().get ());
+ PatternDeclaration::go (param->get_pattern ().get (),
+ Rib::ItemType::Param, bindings);
+ }
+ }
+
+ if (function.has_where_clause ())
+ ResolveWhereClause::Resolve (function.get_where_clause ());
+
+ // trait items have an optional body
+ if (function.has_body ())
+ ResolveExpr::go (function.get_definition ()->get (), path, cpath);
+
+ resolver->get_name_scope ().pop ();
+ resolver->get_type_scope ().pop ();
+ resolver->get_label_scope ().pop ();
+}
+void
ResolveTraitItems::visit (AST::TraitItemType &type)
{
auto decl = CanonicalPath::new_seg (type.get_node_id (),
diff --git a/gcc/rust/resolve/rust-ast-resolve-item.h b/gcc/rust/resolve/rust-ast-resolve-item.h
index 712fe62..33a78e2 100644
--- a/gcc/rust/resolve/rust-ast-resolve-item.h
+++ b/gcc/rust/resolve/rust-ast-resolve-item.h
@@ -35,6 +35,7 @@ public:
static void go (AST::AssociatedItem *item, const CanonicalPath &prefix,
const CanonicalPath &canonical_prefix);
+ void visit (AST::Function &type) override;
void visit (AST::TraitItemType &type) override;
void visit (AST::TraitItemFunc &func) override;
void visit (AST::TraitItemMethod &func) override;