Skip to content

Commit

Permalink
Rework function special parameters
Browse files Browse the repository at this point in the history
Make self param and variadic param Param, introduce Param class and make
function parameters param too.
Self can now be represented as a standard parameter and is thus no longer
required as a separate function attribute.
Prevent self pointers and allow self in standard functions during parsing
so they could be rejected at a later stage.

gcc/rust/ChangeLog:

	* ast/rust-ast-collector.cc (TokenCollector::visit): Add visitor for
	VariadicParam and remove Self parameter visitor from Function visit.
	* expand/rust-cfg-strip.cc (CfgStrip::maybe_strip_self_param): Remove
	function.
	(CfgStrip::maybe_strip_trait_method_decl): Remove self parameter visit.
	(CfgStrip::maybe_strip_function_params): Handle new function
	parameters.
	(CfgStrip::visit): Handle VariadicParam, SelfParam and FunctionParam.
	* expand/rust-expand-visitor.cc (ExpandVisitor::expand_self_param):
	Remove function.
	(ExpandVisitor::expand_trait_method_decl): Do not visit self parameter.
	(ExpandVisitor::visit): Add visit for VariadicParam, FunctionParam and
	SelfParam.
	(ExpandVisitor::expand_function_params): Visit parameters instead.
	* expand/rust-expand-visitor.h: Update function prototypes.
	* resolve/rust-ast-resolve-item.cc (ResolveItem::visit): Update visit
	with new parameters.
	(ResolveTraitItems::visit): Likewise.
	* resolve/rust-early-name-resolver.cc (EarlyNameResolver::visit):
	Update visit functions with the new visitor functions for VariadicParam
	SelfParam and FunctionParam.
	* resolve/rust-early-name-resolver.h: Update function prototypes.
	* ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Update visitor
	according to the new function parameter structures.
	* ast/rust-ast-visitor.h: Update prototypes and add visitor virtual
	functions for SelfParam, FunctionParam and VariadicParam.
	* ast/rust-ast.cc (Function::Function): Move constructor in
	implementation instead of header.
	(Function::operator=): Likewise.
	(Function::as_string): Update function with pointer dereference.
	(VariadicParam::as_string): Likewise.
	(TraitFunctionDecl::as_string): Likewise.
	(TraitMethodDecl::as_string): Likewise.
	(FunctionParam::accept_vis): Add function for visitor.
	(SelfParam::accept_vis): Likewise.
	(VariadicParam::accept_vis): Likewise.
	(TraitItemFunc::TraitItemFunc): Move constructor to implementation
	file.
	(TraitItemFunc::operator=): Likewise.
	(TraitItemMethod::TraitItemMethod): Likewise.
	(TraitItemMethod::operator=): Likewise.
	* ast/rust-item.h (class Function): Remove self optional member.
	(class TraitMethodDecl): Likewise.
	(class TraitFunctionDecl): Likewise.
	(class Param): Add abstract parameter class.
	(class SelfParam): Inherit from Param and remove parameter common
	members.
	(class FunctionParam): Likewise.
	(class VariadicParam): Likewise.
	(struct Visibility): Move structure declaration.
	(class VisItem):  Likewise.
	* checks/errors/rust-ast-validation.cc (ASTValidation::visit): Add
	a self parameter check during AST validation.
	* checks/errors/rust-ast-validation.h: Add function prototype.
	* expand/rust-derive-clone.cc (DeriveClone::clone_fn): Update function
	constructor.
	* hir/rust-ast-lower-base.cc (ASTLoweringBase::lower_self): Rework
	function for the new parameters.
	(ASTLoweringBase::visit): Add visit functions for VariadicParam,
	FunctionParam and SelfParam.
	* hir/rust-ast-lower-base.h: Update function prototypes.
	* parse/rust-parse-impl.h (Parser::parse_function): Update function
	according to new function representation.
	(Parser::parse_function_param): Return vector of abstract param instead
	of FunctionParam.
	(Parser::parse_method): Update according to new representation.
	(Parser::parse_trait_item): Likewise.
	(Parser::parse_self_param): Error out with
	self pointers and prevent the lexer from eating regular function
	parameters. Update return type.
	* parse/rust-parse.h: Update function return types.
	* ast/rust-ast-collector.h: Add VariadicParam visit prototype.
	* ast/rust-ast.h (struct Visibility): Move struct declaration.
	(class VisItem): Likewise.
	* ast/rust-expr.h: Update included files.
	* checks/errors/rust-feature-gate.h: Add visitor functions for
	SelfParam, FunctionParam and VariadicParam.
	* expand/rust-cfg-strip.h: Update function prototypes.
	* expand/rust-derive.h: Likewise.
	* hir/rust-ast-lower-implitem.h: Handle special arguments.
	* hir/rust-ast-lower-item.cc (ASTLoweringItem::visit): Likewise.
	* metadata/rust-export-metadata.cc (ExportContext::emit_function):
	Likewise.
	* resolve/rust-ast-resolve-base.cc (ResolverBase::visit): Add visitor
	functions.
	* resolve/rust-ast-resolve-base.h: Update prototypes.
	* resolve/rust-ast-resolve-stmt.h: Handle new parameter kind.
	* resolve/rust-default-resolver.cc (DefaultResolver::visit): Likewise.
	* resolve/rust-default-resolver.h: Update prototype.
	* util/rust-attributes.cc (AttributeChecker::visit): Add visitor
	functions for SelfParam and VariadicParam.
	* util/rust-attributes.h: Add visit prototypes.

Signed-off-by: Pierre-Emmanuel Patry <[email protected]>
  • Loading branch information
P-E-P committed Nov 14, 2023
1 parent ca5ccfc commit fe0d34c
Show file tree
Hide file tree
Showing 34 changed files with 1,089 additions and 739 deletions.
27 changes: 13 additions & 14 deletions gcc/rust/ast/rust-ast-collector.cc
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
// along with GCC; see the file COPYING3. If not see
// <http://www.gnu.org/licenses/>.
#include "rust-ast-collector.h"
#include "rust-item.h"

namespace Rust {
namespace AST {
Expand Down Expand Up @@ -190,6 +191,17 @@ TokenCollector::visit (FunctionParam &param)
}
}

void
TokenCollector::visit (VariadicParam &param)
{
if (param.has_pattern ())
{
visit (param.get_pattern ());
push (Rust::Token::make (COLON, UNDEF_LOCATION));
}
push (Rust::Token::make (ELLIPSIS, UNDEF_LOCATION));
}

void
TokenCollector::visit (Attribute &attrib)
{
Expand Down Expand Up @@ -1783,13 +1795,6 @@ TokenCollector::visit (Function &function)

push (Rust::Token::make (LEFT_PAREN, UNDEF_LOCATION));

if (function.has_self_param ())
{
visit (function.get_self_param ());
if (!function.get_function_params ().empty ())
push (Rust::Token::make (COMMA, UNDEF_LOCATION));
}

visit_items_joined_by_separator (function.get_function_params ());
push (Rust::Token::make (RIGHT_PAREN, UNDEF_LOCATION));

Expand Down Expand Up @@ -2069,13 +2074,7 @@ TokenCollector::visit (TraitItemMethod &item)
push (Rust::Token::make_identifier (UNDEF_LOCATION, std::move (id)));
push (Rust::Token::make (LEFT_PAREN, UNDEF_LOCATION));

visit (method.get_self_param ());

if (!method.get_function_params ().empty ())
{
push (Rust::Token::make (COMMA, UNDEF_LOCATION));
visit_items_joined_by_separator (method.get_function_params (), COMMA);
}
visit_items_joined_by_separator (method.get_function_params (), COMMA);

push (Rust::Token::make (RIGHT_PAREN, UNDEF_LOCATION));

Expand Down
1 change: 1 addition & 0 deletions gcc/rust/ast/rust-ast-collector.h
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,7 @@ class TokenCollector : public ASTVisitor
void visit (Literal &lit, location_t locus = UNDEF_LOCATION);

void visit (FunctionParam &param);
void visit (VariadicParam &param);
void visit (Attribute &attrib);
void visit (Visibility &vis);
void visit (std::vector<std::unique_ptr<GenericParam>> &params);
Expand Down
26 changes: 19 additions & 7 deletions gcc/rust/ast/rust-ast-visitor.cc
Original file line number Diff line number Diff line change
Expand Up @@ -707,12 +707,6 @@ void
DefaultASTVisitor::visit (AST::FunctionQualifiers &qualifiers)
{}

void
DefaultASTVisitor::visit (AST::SelfParam &self)
{
visit (self.get_lifetime ());
}

void
DefaultASTVisitor::visit (AST::WhereClause &where)
{
Expand All @@ -726,7 +720,18 @@ DefaultASTVisitor::visit (AST::FunctionParam &param)
if (param.has_name ())
visit (param.get_pattern ());

if (!param.is_variadic ())
visit (param.get_type ());
}

void
DefaultASTVisitor::visit (AST::SelfParam &param)
{
visit_outer_attrs (param);

if (param.has_lifetime ())
visit (param.get_lifetime ());

if (param.has_type ())
visit (param.get_type ());
}

Expand Down Expand Up @@ -1438,6 +1443,13 @@ DefaultASTVisitor::visit (AST::BareFunctionType &type)
visit (type.get_return_type ());
}

void
DefaultASTVisitor::visit (AST::VariadicParam &param)
{
if (param.has_pattern ())
visit (param.get_pattern ());
}

void
ContextualASTVisitor::visit (AST::Crate &crate)
{
Expand Down
10 changes: 8 additions & 2 deletions gcc/rust/ast/rust-ast-visitor.h
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
// full include not required - only forward decls
#include "rust-ast-full-decls.h"
#include "rust-ast.h"
#include "rust-item.h"
#include "rust-system.h"

namespace Rust {
Expand Down Expand Up @@ -129,6 +130,10 @@ class ASTVisitor

// rust-item.h
virtual void visit (TypeParam &param) = 0;
virtual void visit (SelfParam &param) = 0;
virtual void visit (FunctionParam &param) = 0;
virtual void visit (VariadicParam &param) = 0;

// virtual void visit(WhereClauseItem& item) = 0;
virtual void visit (LifetimeWhereClauseItem &item) = 0;
virtual void visit (TypeBoundWhereClauseItem &item) = 0;
Expand Down Expand Up @@ -386,6 +391,9 @@ class DefaultASTVisitor : public ASTVisitor
virtual void visit (AST::SliceType &type) override;
virtual void visit (AST::InferredType &type) override;
virtual void visit (AST::BareFunctionType &type) override;
virtual void visit (AST::SelfParam &self) override;
virtual void visit (AST::FunctionParam &param) override;
virtual void visit (AST::VariadicParam &param) override;

template <typename T> void visit (T &node);

Expand All @@ -406,9 +414,7 @@ class DefaultASTVisitor : public ASTVisitor
virtual void visit (AST::MatchArm &arm);
virtual void visit (AST::Visibility &vis);
virtual void visit (AST::FunctionQualifiers &qualifiers);
virtual void visit (AST::SelfParam &self);
virtual void visit (AST::WhereClause &where);
virtual void visit (AST::FunctionParam &param);
virtual void visit (AST::StructField &field);
virtual void visit (AST::TupleField &field);
virtual void visit (AST::TraitFunctionDecl &decl);
Expand Down
146 changes: 141 additions & 5 deletions gcc/rust/ast/rust-ast.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1090,6 +1090,62 @@ Union::as_string () const
return str;
}

Function::Function (Function const &other)
: VisItem (other), qualifiers (other.qualifiers),
function_name (other.function_name), where_clause (other.where_clause),
locus (other.locus), is_default (other.is_default)
{
// guard to prevent null dereference (always required)
if (other.return_type != nullptr)
return_type = other.return_type->clone_type ();

// guard to prevent null dereference (only required if error state)
if (other.function_body != nullptr)
function_body = other.function_body->clone_block_expr ();

generic_params.reserve (other.generic_params.size ());
for (const auto &e : other.generic_params)
generic_params.push_back (e->clone_generic_param ());

function_params.reserve (other.function_params.size ());
for (const auto &e : other.function_params)
function_params.push_back (e->clone_param ());
}

Function &
Function::operator= (Function const &other)
{
VisItem::operator= (other);
function_name = other.function_name;
qualifiers = other.qualifiers;
where_clause = other.where_clause;
// visibility = other.visibility->clone_visibility();
// outer_attrs = other.outer_attrs;
locus = other.locus;
is_default = other.is_default;

// guard to prevent null dereference (always required)
if (other.return_type != nullptr)
return_type = other.return_type->clone_type ();
else
return_type = nullptr;

// guard to prevent null dereference (only required if error state)
if (other.function_body != nullptr)
function_body = other.function_body->clone_block_expr ();
else
function_body = nullptr;

generic_params.reserve (other.generic_params.size ());
for (const auto &e : other.generic_params)
generic_params.push_back (e->clone_generic_param ());

function_params.reserve (other.function_params.size ());
for (const auto &e : other.function_params)
function_params.push_back (e->clone_param ());

return *this;
}
std::string
Function::as_string () const
{
Expand Down Expand Up @@ -1149,7 +1205,7 @@ Function::as_string () const
str += "(";
for (; i != e; i++)
{
str += (*i).as_string ();
str += (*i)->as_string ();
if (e != i + 1)
str += ", ";
}
Expand Down Expand Up @@ -2245,6 +2301,33 @@ FunctionParam::as_string () const
return param_name->as_string () + " : " + type->as_string ();
}

void
FunctionParam::accept_vis (ASTVisitor &vis)
{
vis.visit (*this);
}

void
SelfParam::accept_vis (ASTVisitor &vis)
{
vis.visit (*this);
}

void
VariadicParam::accept_vis (ASTVisitor &vis)
{
vis.visit (*this);
}

std::string
VariadicParam::as_string () const
{
if (has_pattern ())
return get_pattern ()->as_string () + " : ...";
else
return "...";
}

std::string
FunctionQualifiers::as_string () const
{
Expand Down Expand Up @@ -3013,6 +3096,33 @@ NamedFunctionParam::as_string () const
return str;
}

TraitItemFunc::TraitItemFunc (TraitItemFunc const &other)
: TraitItem (other.locus), outer_attrs (other.outer_attrs), decl (other.decl)
{
node_id = other.node_id;

// guard to prevent null dereference
if (other.block_expr != nullptr)
block_expr = other.block_expr->clone_block_expr ();
}

TraitItemFunc &
TraitItemFunc::operator= (TraitItemFunc const &other)
{
TraitItem::operator= (other);
outer_attrs = other.outer_attrs;
decl = other.decl;
locus = other.locus;
node_id = other.node_id;

// guard to prevent null dereference
if (other.block_expr != nullptr)
block_expr = other.block_expr->clone_block_expr ();
else
block_expr = nullptr;

return *this;
}
std::string
TraitItemFunc::as_string () const
{
Expand Down Expand Up @@ -3062,7 +3172,7 @@ TraitFunctionDecl::as_string () const
if (has_params ())
{
for (const auto &param : function_params)
str += "\n " + param.as_string ();
str += "\n " + param->as_string ();
}
else
{
Expand All @@ -3084,6 +3194,34 @@ TraitFunctionDecl::as_string () const
return str;
}

TraitItemMethod::TraitItemMethod (TraitItemMethod const &other)
: TraitItem (other.locus), outer_attrs (other.outer_attrs), decl (other.decl)
{
node_id = other.node_id;

// guard to prevent null dereference
if (other.block_expr != nullptr)
block_expr = other.block_expr->clone_block_expr ();
}

TraitItemMethod &
TraitItemMethod::operator= (TraitItemMethod const &other)
{
TraitItem::operator= (other);
outer_attrs = other.outer_attrs;
decl = other.decl;
locus = other.locus;
node_id = other.node_id;

// guard to prevent null dereference
if (other.block_expr != nullptr)
block_expr = other.block_expr->clone_block_expr ();
else
block_expr = nullptr;

return *this;
}

std::string
TraitItemMethod::as_string () const
{
Expand Down Expand Up @@ -3129,13 +3267,11 @@ TraitMethodDecl::as_string () const
}
}

str += "\n Self param: " + self_param.as_string ();

str += "\n Function params: ";
if (has_params ())
{
for (const auto &param : function_params)
str += "\n " + param.as_string ();
str += "\n " + param->as_string ();
}
else
{
Expand Down
Loading

0 comments on commit fe0d34c

Please sign in to comment.