aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/rust/analysis/rust-name-resolution.cc8
-rw-r--r--gcc/rust/analysis/rust-name-resolution.h4
-rw-r--r--gcc/rust/analysis/rust-scan.cc8
-rw-r--r--gcc/rust/analysis/rust-scan.h4
-rw-r--r--gcc/rust/analysis/rust-type-resolution.cc8
-rw-r--r--gcc/rust/analysis/rust-type-resolution.h4
-rw-r--r--gcc/rust/ast/rust-ast-full-decls.h7
-rw-r--r--gcc/rust/ast/rust-ast-full-test.cc13
-rw-r--r--gcc/rust/ast/rust-ast-visitor.h4
-rw-r--r--gcc/rust/ast/rust-ast.h10
-rw-r--r--gcc/rust/ast/rust-expr.h131
-rw-r--r--gcc/rust/backend/rust-compile.cc8
-rw-r--r--gcc/rust/backend/rust-compile.h4
-rw-r--r--gcc/rust/parse/rust-parse-impl.h128
-rw-r--r--gcc/rust/parse/rust-parse.h3
15 files changed, 231 insertions, 113 deletions
diff --git a/gcc/rust/analysis/rust-name-resolution.cc b/gcc/rust/analysis/rust-name-resolution.cc
index 582f8ac..28a4af8 100644
--- a/gcc/rust/analysis/rust-name-resolution.cc
+++ b/gcc/rust/analysis/rust-name-resolution.cc
@@ -361,12 +361,12 @@ void
NameResolution::visit (AST::IfLetExprConseqIfLet &expr)
{}
// void NameResolution::visit(MatchCase& match_case) {}
-void
+/*void
NameResolution::visit (AST::MatchCaseBlockExpr &match_case)
-{}
-void
+{}*/
+/*void
NameResolution::visit (AST::MatchCaseExpr &match_case)
-{}
+{}*/
void
NameResolution::visit (AST::MatchExpr &expr)
{}
diff --git a/gcc/rust/analysis/rust-name-resolution.h b/gcc/rust/analysis/rust-name-resolution.h
index 51ef450..b3bc780 100644
--- a/gcc/rust/analysis/rust-name-resolution.h
+++ b/gcc/rust/analysis/rust-name-resolution.h
@@ -112,8 +112,8 @@ public:
void visit (AST::IfLetExprConseqIf &expr) override;
void visit (AST::IfLetExprConseqIfLet &expr) override;
// void visit(MatchCase& match_case) override;
- void visit (AST::MatchCaseBlockExpr &match_case) override;
- void visit (AST::MatchCaseExpr &match_case) override;
+ // void visit (AST::MatchCaseBlockExpr &match_case) override;
+ // void visit (AST::MatchCaseExpr &match_case) override;
void visit (AST::MatchExpr &expr) override;
void visit (AST::AwaitExpr &expr) override;
void visit (AST::AsyncBlockExpr &expr) override;
diff --git a/gcc/rust/analysis/rust-scan.cc b/gcc/rust/analysis/rust-scan.cc
index 4c032b0..402ac32 100644
--- a/gcc/rust/analysis/rust-scan.cc
+++ b/gcc/rust/analysis/rust-scan.cc
@@ -297,12 +297,12 @@ void
TopLevelScan::visit (AST::IfLetExprConseqIfLet &expr)
{}
// void TopLevelScan::visit(MatchCase& match_case) {}
-void
+/*void
TopLevelScan::visit (AST::MatchCaseBlockExpr &match_case)
-{}
-void
+{}*/
+/*void
TopLevelScan::visit (AST::MatchCaseExpr &match_case)
-{}
+{}*/
void
TopLevelScan::visit (AST::MatchExpr &expr)
{}
diff --git a/gcc/rust/analysis/rust-scan.h b/gcc/rust/analysis/rust-scan.h
index e898d41..77beeca 100644
--- a/gcc/rust/analysis/rust-scan.h
+++ b/gcc/rust/analysis/rust-scan.h
@@ -117,8 +117,8 @@ public:
virtual void visit (AST::IfLetExprConseqIf &expr);
virtual void visit (AST::IfLetExprConseqIfLet &expr);
// virtual void visit(MatchCase& match_case);
- virtual void visit (AST::MatchCaseBlockExpr &match_case);
- virtual void visit (AST::MatchCaseExpr &match_case);
+ // virtual void visit (AST::MatchCaseBlockExpr &match_case);
+ // virtual void visit (AST::MatchCaseExpr &match_case);
virtual void visit (AST::MatchExpr &expr);
virtual void visit (AST::AwaitExpr &expr);
virtual void visit (AST::AsyncBlockExpr &expr);
diff --git a/gcc/rust/analysis/rust-type-resolution.cc b/gcc/rust/analysis/rust-type-resolution.cc
index 8edebba..3503a83 100644
--- a/gcc/rust/analysis/rust-type-resolution.cc
+++ b/gcc/rust/analysis/rust-type-resolution.cc
@@ -704,12 +704,12 @@ void
TypeResolution::visit (AST::IfLetExprConseqIfLet &expr)
{}
// void TypeResolution::visit(MatchCase& match_case) {}
-void
+/*void
TypeResolution::visit (AST::MatchCaseBlockExpr &match_case)
-{}
-void
+{}*/
+/*void
TypeResolution::visit (AST::MatchCaseExpr &match_case)
-{}
+{}*/
void
TypeResolution::visit (AST::MatchExpr &expr)
{}
diff --git a/gcc/rust/analysis/rust-type-resolution.h b/gcc/rust/analysis/rust-type-resolution.h
index 6f74719..af4594e 100644
--- a/gcc/rust/analysis/rust-type-resolution.h
+++ b/gcc/rust/analysis/rust-type-resolution.h
@@ -188,8 +188,8 @@ public:
void visit (AST::IfLetExprConseqIf &expr) override;
void visit (AST::IfLetExprConseqIfLet &expr) override;
// void visit(MatchCase& match_case) override;
- void visit (AST::MatchCaseBlockExpr &match_case) override;
- void visit (AST::MatchCaseExpr &match_case) override;
+ // void visit (AST::MatchCaseBlockExpr &match_case) override;
+ // void visit (AST::MatchCaseExpr &match_case) override;
void visit (AST::MatchExpr &expr) override;
void visit (AST::AwaitExpr &expr) override;
void visit (AST::AsyncBlockExpr &expr) override;
diff --git a/gcc/rust/ast/rust-ast-full-decls.h b/gcc/rust/ast/rust-ast-full-decls.h
index a76a599..9b604a5 100644
--- a/gcc/rust/ast/rust-ast-full-decls.h
+++ b/gcc/rust/ast/rust-ast-full-decls.h
@@ -134,9 +134,10 @@ namespace Rust {
class IfLetExprConseqIf;
class IfLetExprConseqIfLet;
struct MatchArm;
- class MatchCase;
- class MatchCaseBlockExpr;
- class MatchCaseExpr;
+ // class MatchCase;
+ // class MatchCaseBlockExpr;
+ // class MatchCaseExpr;
+ struct MatchCase;
class MatchExpr;
class AwaitExpr;
class AsyncBlockExpr;
diff --git a/gcc/rust/ast/rust-ast-full-test.cc b/gcc/rust/ast/rust-ast-full-test.cc
index 75ea74d..33d1736 100644
--- a/gcc/rust/ast/rust-ast-full-test.cc
+++ b/gcc/rust/ast/rust-ast-full-test.cc
@@ -2391,11 +2391,12 @@ MatchCase::as_string () const
std::string str ("MatchCase: (match arm) ");
str += "\n Match arm matcher: \n" + arm.as_string ();
+ str += "\n Expr: " + expr->as_string ();
return str;
}
-std::string
+/*std::string
MatchCaseBlockExpr::as_string () const
{
std::string str = MatchCase::as_string ();
@@ -2413,7 +2414,7 @@ MatchCaseExpr::as_string () const
str += "\n Expr: " + expr->as_string ();
return str;
-}
+}*/
std::string
MatchExpr::as_string () const
@@ -2447,9 +2448,7 @@ MatchExpr::as_string () const
else
{
for (const auto &arm : match_arms)
- {
- str += "\n " + arm->as_string ();
- }
+ str += "\n " + arm.as_string ();
}
return str;
@@ -5759,7 +5758,7 @@ IfLetExprConseqIfLet::accept_vis (ASTVisitor &vis)
vis.visit (*this);
}
-void
+/*void
MatchCaseBlockExpr::accept_vis (ASTVisitor &vis)
{
vis.visit (*this);
@@ -5769,7 +5768,7 @@ void
MatchCaseExpr::accept_vis (ASTVisitor &vis)
{
vis.visit (*this);
-}
+}*/
void
MatchExpr::accept_vis (ASTVisitor &vis)
diff --git a/gcc/rust/ast/rust-ast-visitor.h b/gcc/rust/ast/rust-ast-visitor.h
index 0d89d51..b48e8f3 100644
--- a/gcc/rust/ast/rust-ast-visitor.h
+++ b/gcc/rust/ast/rust-ast-visitor.h
@@ -113,8 +113,8 @@ public:
virtual void visit (IfLetExprConseqIf &expr) = 0;
virtual void visit (IfLetExprConseqIfLet &expr) = 0;
// virtual void visit(MatchCase& match_case) = 0;
- virtual void visit (MatchCaseBlockExpr &match_case) = 0;
- virtual void visit (MatchCaseExpr &match_case) = 0;
+ // virtual void visit (MatchCaseBlockExpr &match_case) = 0;
+ // virtual void visit (MatchCaseExpr &match_case) = 0;
virtual void visit (MatchExpr &expr) = 0;
virtual void visit (AwaitExpr &expr) = 0;
virtual void visit (AsyncBlockExpr &expr) = 0;
diff --git a/gcc/rust/ast/rust-ast.h b/gcc/rust/ast/rust-ast.h
index 4c115b2..f9fbc36 100644
--- a/gcc/rust/ast/rust-ast.h
+++ b/gcc/rust/ast/rust-ast.h
@@ -2,11 +2,6 @@
#define RUST_AST_BASE_H
// Base for AST used in gccrs, basically required by all specific ast things
-// GCC imports
-#include "config.h"
-#include "system.h"
-#include "coretypes.h" // order: config, system, coretypes
-
#include "rust-system.h"
// STL imports
@@ -847,6 +842,9 @@ public:
* methods. */
virtual Location get_locus_slow () const { return Location (); }
+ // HACK: strictly not needed, but faster than full downcast clone
+ virtual bool is_expr_without_block () const = 0;
+
virtual void accept_vis (ASTVisitor &vis) = 0;
protected:
@@ -887,6 +885,8 @@ protected:
return clone_expr_without_block_impl ();
}
+ bool is_expr_without_block () const final override { return true; };
+
public:
// Unique pointer custom clone function
std::unique_ptr<ExprWithoutBlock> clone_expr_without_block () const
diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h
index 727cf3c..b989006 100644
--- a/gcc/rust/ast/rust-expr.h
+++ b/gcc/rust/ast/rust-expr.h
@@ -28,6 +28,8 @@ protected:
return clone_expr_with_block_impl ();
}
+ bool is_expr_without_block () const final override { return false; };
+
public:
// Unique pointer custom clone function
std::unique_ptr<ExprWithBlock> clone_expr_with_block () const
@@ -889,12 +891,12 @@ protected:
// Value array elements
class ArrayElemsValues : public ArrayElems
{
- std::vector<std::unique_ptr<Expr>> values;
+ std::vector<std::unique_ptr<Expr> > values;
// TODO: should this store location data?
public:
- ArrayElemsValues (std::vector<std::unique_ptr<Expr>> elems)
+ ArrayElemsValues (std::vector<std::unique_ptr<Expr> > elems)
: values (std::move (elems))
{}
@@ -1117,7 +1119,7 @@ class TupleExpr : public ExprWithoutBlock
{
std::vector<Attribute> inner_attrs;
- std::vector<std::unique_ptr<Expr>> tuple_elems;
+ std::vector<std::unique_ptr<Expr> > tuple_elems;
// replaces (inlined version of) TupleElements
Location locus;
@@ -1127,7 +1129,7 @@ public:
std::vector<Attribute> get_inner_attrs () const { return inner_attrs; }
- TupleExpr (std::vector<std::unique_ptr<Expr>> tuple_elements,
+ TupleExpr (std::vector<std::unique_ptr<Expr> > tuple_elements,
std::vector<Attribute> inner_attribs,
std::vector<Attribute> outer_attribs, Location locus)
: ExprWithoutBlock (std::move (outer_attribs)),
@@ -1493,7 +1495,7 @@ class StructExprStructFields : public StructExprStruct
{
public:
// std::vector<StructExprField> fields;
- std::vector<std::unique_ptr<StructExprField>> fields;
+ std::vector<std::unique_ptr<StructExprField> > fields;
// bool has_struct_base;
StructBase struct_base;
@@ -1513,7 +1515,7 @@ public:
// Constructor for StructExprStructFields when no struct base is used
StructExprStructFields (
PathInExpression struct_path,
- std::vector<std::unique_ptr<StructExprField>> expr_fields, Location locus,
+ std::vector<std::unique_ptr<StructExprField> > expr_fields, Location locus,
StructBase base_struct = StructBase::error (),
std::vector<Attribute> inner_attribs = std::vector<Attribute> (),
std::vector<Attribute> outer_attribs = std::vector<Attribute> ())
@@ -1608,7 +1610,7 @@ protected:
class StructExprTuple : public StructExpr
{
std::vector<Attribute> inner_attrs;
- std::vector<std::unique_ptr<Expr>> exprs;
+ std::vector<std::unique_ptr<Expr> > exprs;
Location locus;
@@ -1622,7 +1624,7 @@ public:
}*/
StructExprTuple (PathInExpression struct_path,
- std::vector<std::unique_ptr<Expr>> tuple_exprs,
+ std::vector<std::unique_ptr<Expr> > tuple_exprs,
std::vector<Attribute> inner_attribs,
std::vector<Attribute> outer_attribs, Location locus)
: StructExpr (std::move (struct_path), std::move (outer_attribs)),
@@ -1867,7 +1869,7 @@ protected:
class EnumExprStruct : public EnumVariantExpr
{
// std::vector<EnumExprField> fields;
- std::vector<std::unique_ptr<EnumExprField>> fields;
+ std::vector<std::unique_ptr<EnumExprField> > fields;
Location locus;
@@ -1879,7 +1881,7 @@ public:
}*/
EnumExprStruct (PathInExpression enum_variant_path,
- std::vector<std::unique_ptr<EnumExprField>> variant_fields,
+ std::vector<std::unique_ptr<EnumExprField> > variant_fields,
std::vector<Attribute> outer_attribs, Location locus)
: EnumVariantExpr (std::move (enum_variant_path),
std::move (outer_attribs)),
@@ -1936,7 +1938,7 @@ protected:
// Tuple-like syntax enum variant instance creation AST node
class EnumExprTuple : public EnumVariantExpr
{
- std::vector<std::unique_ptr<Expr>> values;
+ std::vector<std::unique_ptr<Expr> > values;
Location locus;
@@ -1948,7 +1950,7 @@ public:
}*/
EnumExprTuple (PathInExpression enum_variant_path,
- std::vector<std::unique_ptr<Expr>> variant_values,
+ std::vector<std::unique_ptr<Expr> > variant_values,
std::vector<Attribute> outer_attribs, Location locus)
: EnumVariantExpr (std::move (enum_variant_path),
std::move (outer_attribs)),
@@ -2051,7 +2053,7 @@ class CallExpr : public ExprWithoutBlock
public:
std::unique_ptr<Expr> function;
// inlined form of CallParams
- std::vector<std::unique_ptr<Expr>> params;
+ std::vector<std::unique_ptr<Expr> > params;
Location locus;
@@ -2064,7 +2066,7 @@ public:
}*/
CallExpr (std::unique_ptr<Expr> function_expr,
- std::vector<std::unique_ptr<Expr>> function_params,
+ std::vector<std::unique_ptr<Expr> > function_params,
std::vector<Attribute> outer_attribs, Location locus)
: ExprWithoutBlock (std::move (outer_attribs)),
function (std::move (function_expr)),
@@ -2128,7 +2130,7 @@ class MethodCallExpr : public ExprWithoutBlock
std::unique_ptr<Expr> receiver;
PathExprSegment method_name;
// inlined form of CallParams
- std::vector<std::unique_ptr<Expr>> params;
+ std::vector<std::unique_ptr<Expr> > params;
Location locus;
@@ -2141,7 +2143,7 @@ public:
MethodCallExpr (std::unique_ptr<Expr> call_receiver,
PathExprSegment method_path,
- std::vector<std::unique_ptr<Expr>> method_params,
+ std::vector<std::unique_ptr<Expr> > method_params,
std::vector<Attribute> outer_attribs, Location locus)
: ExprWithoutBlock (std::move (outer_attribs)),
receiver (std::move (call_receiver)),
@@ -2407,7 +2409,7 @@ public:
std::vector<Attribute> inner_attrs;
// bool has_statements;
- std::vector<std::unique_ptr<Stmt>> statements;
+ std::vector<std::unique_ptr<Stmt> > statements;
// bool has_expr;
std::unique_ptr<ExprWithoutBlock> expr; // inlined from Statements
@@ -2421,7 +2423,7 @@ public:
// Returns whether the block contains an expression
bool has_expr () const { return expr != nullptr; }
- BlockExpr (std::vector<std::unique_ptr<Stmt>> block_statements,
+ BlockExpr (std::vector<std::unique_ptr<Stmt> > block_statements,
std::unique_ptr<ExprWithoutBlock> block_expr,
std::vector<Attribute> inner_attribs,
std::vector<Attribute> outer_attribs, Location locus)
@@ -3278,14 +3280,14 @@ protected:
class WhileLetLoopExpr : public BaseLoopExpr
{
// MatchArmPatterns patterns;
- std::vector<std::unique_ptr<Pattern>> match_arm_patterns; // inlined
+ std::vector<std::unique_ptr<Pattern> > match_arm_patterns; // inlined
std::unique_ptr<Expr> condition;
public:
std::string as_string () const override;
// Constructor with a loop label
- WhileLetLoopExpr (std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ WhileLetLoopExpr (std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> condition,
std::unique_ptr<BlockExpr> loop_block, Location locus,
LoopLabel loop_label = LoopLabel::error (),
@@ -3622,7 +3624,7 @@ protected:
class IfLetExpr : public ExprWithBlock
{
// MatchArmPatterns patterns;
- std::vector<std::unique_ptr<Pattern>> match_arm_patterns; // inlined
+ std::vector<std::unique_ptr<Pattern> > match_arm_patterns; // inlined
std::unique_ptr<Expr> value;
std::unique_ptr<BlockExpr> if_block;
@@ -3631,7 +3633,7 @@ class IfLetExpr : public ExprWithBlock
public:
std::string as_string () const override;
- IfLetExpr (std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ IfLetExpr (std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> value, std::unique_ptr<BlockExpr> if_block,
Location locus)
: ExprWithBlock (std::vector<Attribute> ()),
@@ -3774,7 +3776,7 @@ public:
std::string as_string () const override;
IfLetExprConseqElse (
- std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> value, std::unique_ptr<BlockExpr> if_block,
std::unique_ptr<BlockExpr> else_block, Location locus)
: IfLetExpr (std::move (match_arm_patterns), std::move (value),
@@ -3839,7 +3841,7 @@ class IfLetExprConseqIf : public IfLetExpr
public:
std::string as_string () const override;
- IfLetExprConseqIf (std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ IfLetExprConseqIf (std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> value,
std::unique_ptr<BlockExpr> if_block,
std::unique_ptr<IfExpr> if_expr, Location locus)
@@ -3905,7 +3907,7 @@ public:
std::string as_string () const override;
IfLetExprConseqIfLet (
- std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> value, std::unique_ptr<BlockExpr> if_block,
std::unique_ptr<IfLetExpr> if_let_expr, Location locus)
: IfLetExpr (std::move (match_arm_patterns), std::move (value),
@@ -3966,7 +3968,7 @@ struct MatchArm
private:
std::vector<Attribute> outer_attrs;
// MatchArmPatterns patterns;
- std::vector<std::unique_ptr<Pattern>> match_arm_patterns; // inlined
+ std::vector<std::unique_ptr<Pattern> > match_arm_patterns; // inlined
// bool has_match_arm_guard;
// inlined from MatchArmGuard
@@ -3979,7 +3981,7 @@ public:
bool has_match_arm_guard () const { return guard_expr != nullptr; }
// Constructor for match arm with a guard expression
- MatchArm (std::vector<std::unique_ptr<Pattern>> match_arm_patterns,
+ MatchArm (std::vector<std::unique_ptr<Pattern> > match_arm_patterns,
std::unique_ptr<Expr> guard_expr = nullptr,
std::vector<Attribute> outer_attrs = std::vector<Attribute> ())
: outer_attrs (std::move (outer_attrs)),
@@ -3988,9 +3990,7 @@ public:
{}
// Copy constructor with clone
- MatchArm (MatchArm const &other)
- : /*match_arm_patterns(other.match_arm_patterns),*/ outer_attrs (
- other.outer_attrs)
+ MatchArm (MatchArm const &other) : outer_attrs (other.outer_attrs)
{
// guard to protect from null pointer dereference
if (other.guard_expr != nullptr)
@@ -4006,9 +4006,10 @@ public:
// Overload assignment operator to clone
MatchArm &operator= (MatchArm const &other)
{
- // match_arm_patterns = other.match_arm_patterns;
outer_attrs = other.outer_attrs;
- guard_expr = other.guard_expr->clone_expr ();
+
+ if (other.guard_expr != nullptr)
+ guard_expr = other.guard_expr->clone_expr ();
match_arm_patterns.reserve (other.match_arm_patterns.size ());
for (const auto &e : other.match_arm_patterns)
@@ -4027,12 +4028,13 @@ public:
// Creates a match arm in an error state.
static MatchArm create_error ()
{
- return MatchArm (std::vector<std::unique_ptr<Pattern>> ());
+ return MatchArm (std::vector<std::unique_ptr<Pattern> > ());
}
std::string as_string () const;
};
+/*
// Base "match case" for a match expression - abstract
class MatchCase
{
@@ -4059,7 +4061,45 @@ public:
virtual void accept_vis (ASTVisitor &vis) = 0;
};
+*/
+
+/* A "match case" - a correlated match arm and resulting expression. Not
+ * abstract. */
+struct MatchCase
+{
+private:
+ MatchArm arm;
+ std::unique_ptr<Expr> expr;
+
+ /* TODO: does whether trailing comma exists need to be stored? currently
+ * assuming it is only syntactical and has no effect on meaning. */
+
+public:
+ MatchCase (MatchArm arm, std::unique_ptr<Expr> expr)
+ : arm (std::move (arm)), expr (std::move (expr))
+ {}
+
+ MatchCase (const MatchCase &other)
+ : arm (other.arm), expr (other.expr->clone_expr ())
+ {}
+ MatchCase &operator= (const MatchCase &other)
+ {
+ arm = other.arm;
+ expr = other.expr->clone_expr ();
+
+ return *this;
+ }
+
+ MatchCase (MatchCase &&other) = default;
+ MatchCase &operator= (MatchCase &&other) = default;
+
+ ~MatchCase () = default;
+
+ std::string as_string () const;
+};
+
+#if 0
// Block expression match case
class MatchCaseBlockExpr : public MatchCase
{
@@ -4147,6 +4187,7 @@ protected:
return new MatchCaseExpr (*this);
}
};
+#endif
// Match expression AST node
class MatchExpr : public ExprWithBlock
@@ -4156,7 +4197,9 @@ class MatchExpr : public ExprWithBlock
// bool has_match_arms;
// MatchArms match_arms;
- std::vector<std::unique_ptr<MatchCase>> match_arms; // inlined from MatchArms
+ // std::vector<std::unique_ptr<MatchCase> > match_arms; // inlined from
+ // MatchArms
+ std::vector<MatchCase> match_arms;
Location locus;
@@ -4167,7 +4210,8 @@ public:
bool has_match_arms () const { return !match_arms.empty (); }
MatchExpr (std::unique_ptr<Expr> branch_value,
- std::vector<std::unique_ptr<MatchCase>> match_arms,
+ // std::vector<std::unique_ptr<MatchCase> > match_arms,
+ std::vector<MatchCase> match_arms,
std::vector<Attribute> inner_attrs,
std::vector<Attribute> outer_attrs, Location locus)
: ExprWithBlock (std::move (outer_attrs)),
@@ -4178,14 +4222,13 @@ public:
// Copy constructor requires clone due to unique_ptr
MatchExpr (MatchExpr const &other)
- : ExprWithBlock (other),
- branch_value (
- other.branch_value->clone_expr ()), /*match_arms(other.match_arms),*/
- inner_attrs (other.inner_attrs), locus (other.locus)
+ : ExprWithBlock (other), branch_value (other.branch_value->clone_expr ()),
+ inner_attrs (other.inner_attrs), match_arms (other.match_arms),
+ locus (other.locus)
{
- match_arms.reserve (other.match_arms.size ());
+ /*match_arms.reserve (other.match_arms.size ());
for (const auto &e : other.match_arms)
- match_arms.push_back (e->clone_match_case ());
+ match_arms.push_back (e->clone_match_case ());*/
}
// Overloaded assignment operator to clone due to unique_ptr
@@ -4193,14 +4236,14 @@ public:
{
ExprWithBlock::operator= (other);
branch_value = other.branch_value->clone_expr ();
- // match_arms = other.match_arms;
inner_attrs = other.inner_attrs;
+ match_arms = other.match_arms;
// outer_attrs = other.outer_attrs;
locus = other.locus;
- match_arms.reserve (other.match_arms.size ());
+ /*match_arms.reserve (other.match_arms.size ());
for (const auto &e : other.match_arms)
- match_arms.push_back (e->clone_match_case ());
+ match_arms.push_back (e->clone_match_case ());*/
return *this;
}
diff --git a/gcc/rust/backend/rust-compile.cc b/gcc/rust/backend/rust-compile.cc
index 2b9b5bb..6374a45 100644
--- a/gcc/rust/backend/rust-compile.cc
+++ b/gcc/rust/backend/rust-compile.cc
@@ -889,12 +889,12 @@ Compilation::visit (AST::IfLetExprConseqIfLet &expr)
}
// void Compilation::visit(MatchCase& match_case) {}
-void
+/*void
Compilation::visit (AST::MatchCaseBlockExpr &match_case)
-{}
-void
+{}*/
+/*void
Compilation::visit (AST::MatchCaseExpr &match_case)
-{}
+{}*/
void
Compilation::visit (AST::MatchExpr &expr)
{}
diff --git a/gcc/rust/backend/rust-compile.h b/gcc/rust/backend/rust-compile.h
index b28f0ee..ba03483 100644
--- a/gcc/rust/backend/rust-compile.h
+++ b/gcc/rust/backend/rust-compile.h
@@ -116,8 +116,8 @@ public:
virtual void visit (AST::IfLetExprConseqIf &expr);
virtual void visit (AST::IfLetExprConseqIfLet &expr);
// virtual void visit(MatchCase& match_case);
- virtual void visit (AST::MatchCaseBlockExpr &match_case);
- virtual void visit (AST::MatchCaseExpr &match_case);
+ // virtual void visit (AST::MatchCaseBlockExpr &match_case);
+ // virtual void visit (AST::MatchCaseExpr &match_case);
virtual void visit (AST::MatchExpr &expr);
virtual void visit (AST::AwaitExpr &expr);
virtual void visit (AST::AsyncBlockExpr &expr);
diff --git a/gcc/rust/parse/rust-parse-impl.h b/gcc/rust/parse/rust-parse-impl.h
index 286d7a4..468312e 100644
--- a/gcc/rust/parse/rust-parse-impl.h
+++ b/gcc/rust/parse/rust-parse-impl.h
@@ -3895,7 +3895,8 @@ Parser<ManagedTokenSource>::parse_struct (
lexer.skip_token ();
// parse struct fields, if any
- std::vector<AST::StructField> struct_fields = parse_struct_fields ();
+ std::vector<AST::StructField> struct_fields
+ = parse_struct_fields ([] (TokenId id) { return id == RIGHT_CURLY; });
if (!skip_token (RIGHT_CURLY))
{
@@ -3938,42 +3939,69 @@ Parser<ManagedTokenSource>::parse_struct_fields ()
// Return empty field list if no field there
if (initial_field.is_error ())
- {
- return fields;
- }
+ return fields;
fields.push_back (std::move (initial_field));
- // maybe think of a better control structure here - do-while with an initial
- // error state? basically, loop through field list until can't find any more
- // params
- while (true)
+ while (lexer.peek_token ()->get_id () == COMMA)
{
- if (lexer.peek_token ()->get_id () != COMMA)
+ lexer.skip_token ();
+
+ AST::StructField field = parse_struct_field ();
+
+ if (field.is_error ())
{
+ // would occur with trailing comma, so allowed
break;
}
- // skip comma if applies
+ fields.push_back (std::move (field));
+ }
+
+ fields.shrink_to_fit ();
+ return fields;
+ // TODO: template if possible (parse_non_ptr_seq)
+}
+
+// Parses struct fields in struct declarations.
+template <typename ManagedTokenSource>
+template <typename EndTokenPred>
+std::vector<AST::StructField>
+Parser<ManagedTokenSource>::parse_struct_fields (EndTokenPred is_end_tok)
+{
+ std::vector<AST::StructField> fields;
+
+ AST::StructField initial_field = parse_struct_field ();
+
+ // Return empty field list if no field there
+ if (initial_field.is_error ())
+ return fields;
+
+ fields.push_back (std::move (initial_field));
+
+ while (lexer.peek_token ()->get_id () == COMMA)
+ {
lexer.skip_token ();
- AST::StructField field = parse_struct_field ();
+ if (is_end_tok (lexer.peek_token ()->get_id ()))
+ break;
- if (!field.is_error ())
- {
- fields.push_back (std::move (field));
- }
- else
+ AST::StructField field = parse_struct_field ();
+ if (field.is_error ())
{
- // this would occur with a trailing comma, which is allowed
- break;
+ /* TODO: should every field be ditched just because one couldn't be
+ * parsed? */
+ rust_error_at (lexer.peek_token ()->get_locus (),
+ "failed to parse struct field in struct fields");
+ return {};
}
+
+ fields.push_back (std::move (field));
}
+ fields.shrink_to_fit ();
return fields;
-
- // TODO: this shares basically all code with function params and tuple fields
- // - templates?
+ // TODO: template if possible (parse_non_ptr_seq)
}
// Parses a single struct field (in a struct definition). Does not parse commas.
@@ -4257,7 +4285,8 @@ Parser<ManagedTokenSource>::parse_enum_item ()
// struct enum item
lexer.skip_token ();
- std::vector<AST::StructField> struct_fields = parse_struct_fields ();
+ std::vector<AST::StructField> struct_fields
+ = parse_struct_fields ([] (TokenId id) { return id == RIGHT_CURLY; });
if (!skip_token (RIGHT_CURLY))
{
@@ -4326,7 +4355,8 @@ Parser<ManagedTokenSource>::parse_union (
/* parse union inner items as "struct fields" because hey, syntax reuse. Spec
* said so. */
- std::vector<AST::StructField> union_fields = parse_struct_fields ();
+ std::vector<AST::StructField> union_fields
+ = parse_struct_fields ([] (TokenId id) { return id == RIGHT_CURLY; });
if (!skip_token (RIGHT_CURLY))
{
@@ -8017,18 +8047,20 @@ Parser<ManagedTokenSource>::parse_match_expr (
std::vector<AST::Attribute> inner_attrs = parse_inner_attributes ();
// parse match arms (if they exist)
- std::vector<std::unique_ptr<AST::MatchCase> > match_arms;
+ // std::vector<std::unique_ptr<AST::MatchCase> > match_arms;
+ std::vector<AST::MatchCase> match_arms;
- // FIXME: absolute worst control structure ever
// parse match cases
- while (true)
+ while (lexer.peek_token ()->get_id () != RIGHT_CURLY)
{
// parse match arm itself, which is required
AST::MatchArm arm = parse_match_arm ();
if (arm.is_error ())
{
- // not necessarily an error
- break;
+ // TODO is this worth throwing everything away?
+ rust_error_at (lexer.peek_token ()->get_locus (),
+ "failed to parse match arm in match arms");
+ return nullptr;
}
if (!skip_token (MATCH_ARROW))
@@ -8038,6 +8070,45 @@ Parser<ManagedTokenSource>::parse_match_expr (
return nullptr;
}
+ std::unique_ptr<AST::Expr> expr = parse_expr ();
+ if (expr == nullptr)
+ {
+ rust_error_at (lexer.peek_token ()->get_locus (),
+ "failed to parse expr in match arm in match expr");
+ // skip somewhere?
+ return nullptr;
+ }
+ bool is_expr_without_block = expr->is_expr_without_block ();
+
+ // construct match case expr and add to cases
+ match_arms.push_back (AST::MatchCase (std::move (arm), std::move (expr)));
+
+ // handle comma presence
+ if (lexer.peek_token ()->get_id () != COMMA)
+ {
+ if (!is_expr_without_block)
+ {
+ // allowed even if not final case
+ continue;
+ }
+ else if (is_expr_without_block
+ && lexer.peek_token ()->get_id () != RIGHT_CURLY)
+ {
+ // not allowed if not final case
+ rust_error_at (lexer.peek_token ()->get_locus (),
+ "exprwithoutblock requires comma after match case "
+ "expression in match arm (if not final case)");
+ return nullptr;
+ }
+ else
+ {
+ // otherwise, must be final case, so fine
+ break;
+ }
+ }
+ lexer.skip_token ();
+
+#if 0
// branch on next token - if '{', block expr, otherwise just expr
if (lexer.peek_token ()->get_id () == LEFT_CURLY)
{
@@ -8089,6 +8160,7 @@ Parser<ManagedTokenSource>::parse_match_expr (
}
lexer.skip_token ();
}
+#endif
}
if (!skip_token (RIGHT_CURLY))
diff --git a/gcc/rust/parse/rust-parse.h b/gcc/rust/parse/rust-parse.h
index b2de05e..e2f3a78 100644
--- a/gcc/rust/parse/rust-parse.h
+++ b/gcc/rust/parse/rust-parse.h
@@ -189,6 +189,8 @@ private:
std::unique_ptr<AST::Struct>
parse_struct (AST::Visibility vis, std::vector<AST::Attribute> outer_attrs);
std::vector<AST::StructField> parse_struct_fields ();
+ template <typename EndTokenPred>
+ std::vector<AST::StructField> parse_struct_fields (EndTokenPred is_end_token);
AST::StructField parse_struct_field ();
std::vector<AST::TupleField> parse_tuple_fields ();
AST::TupleField parse_tuple_field ();
@@ -528,6 +530,7 @@ private:
= std::vector<AST::Attribute> (),
bool pratt_parse = false);
std::unique_ptr<AST::StructExprField> parse_struct_expr_field ();
+ bool will_be_expr_with_block ();
// Type-related
std::unique_ptr<AST::Type> parse_type ();