From: Arthur Cohen <arthur.co...@embecosm.com> gcc/rust/ChangeLog:
* hir/tree/rust-hir-stmt.h (class LetStmt): Add optional diverging else expression. * hir/tree/rust-hir-stmt.cc: Likewise. * hir/rust-ast-lower-stmt.cc (ASTLoweringStmt::visit): Add handling for lowering diverging else. --- gcc/rust/hir/rust-ast-lower-stmt.cc | 14 ++++++++++---- gcc/rust/hir/tree/rust-hir-stmt.cc | 12 +++++++++++- gcc/rust/hir/tree/rust-hir-stmt.h | 16 ++++++++++++++++ 3 files changed, 37 insertions(+), 5 deletions(-) diff --git a/gcc/rust/hir/rust-ast-lower-stmt.cc b/gcc/rust/hir/rust-ast-lower-stmt.cc index fd2cdfb0f11..dbb1723dfc5 100644 --- a/gcc/rust/hir/rust-ast-lower-stmt.cc +++ b/gcc/rust/hir/rust-ast-lower-stmt.cc @@ -76,20 +76,26 @@ ASTLoweringStmt::visit (AST::LetStmt &stmt) type = std::unique_ptr<Type> (ASTLoweringType::translate (stmt.get_type ())); - tl::optional<std::unique_ptr<HIR::Expr>> init_expression = tl::nullopt; + tl::optional<std::unique_ptr<HIR::Expr>> init_expr = tl::nullopt; + tl::optional<std::unique_ptr<HIR::Expr>> else_expr = tl::nullopt; if (stmt.has_init_expr ()) - init_expression = std::unique_ptr<HIR::Expr> ( + init_expr = std::unique_ptr<HIR::Expr> ( ASTLoweringExpr::translate (stmt.get_init_expr ())); + if (stmt.has_else_expr ()) + else_expr = std::unique_ptr<HIR::Expr> ( + ASTLoweringExpr::translate (stmt.get_else_expr ())); + auto crate_num = mappings.get_current_crate (); Analysis::NodeMapping mapping (crate_num, stmt.get_node_id (), mappings.get_next_hir_id (crate_num), UNKNOWN_LOCAL_DEFID); translated = new HIR::LetStmt (mapping, std::unique_ptr<HIR::Pattern> (variables), - std::move (init_expression), std::move (type), - stmt.get_outer_attrs (), stmt.get_locus ()); + std::move (init_expr), std::move (else_expr), + std::move (type), stmt.get_outer_attrs (), + stmt.get_locus ()); } void diff --git a/gcc/rust/hir/tree/rust-hir-stmt.cc b/gcc/rust/hir/tree/rust-hir-stmt.cc index 025f67e2c9b..fd58e29c7f8 100644 --- a/gcc/rust/hir/tree/rust-hir-stmt.cc +++ b/gcc/rust/hir/tree/rust-hir-stmt.cc @@ -26,11 +26,13 @@ namespace HIR { LetStmt::LetStmt (Analysis::NodeMapping mappings, std::unique_ptr<Pattern> variables_pattern, tl::optional<std::unique_ptr<Expr>> init_expr, + tl::optional<std::unique_ptr<Expr>> else_expr, tl::optional<std::unique_ptr<Type>> type, AST::AttrVec outer_attrs, location_t locus) : Stmt (std::move (mappings)), outer_attrs (std::move (outer_attrs)), variables_pattern (std::move (variables_pattern)), type (std::move (type)), - init_expr (std::move (init_expr)), locus (locus) + init_expr (std::move (init_expr)), else_expr (std::move (else_expr)), + locus (locus) {} LetStmt::LetStmt (LetStmt const &other) @@ -43,6 +45,8 @@ LetStmt::LetStmt (LetStmt const &other) // guard to prevent null dereference (always required) if (other.has_init_expr ()) init_expr = other.get_init_expr ().clone_expr (); + if (other.has_else_expr ()) + else_expr = other.get_else_expr ().clone_expr (); if (other.has_type ()) type = other.get_type ().clone_type (); @@ -67,6 +71,12 @@ LetStmt::operator= (LetStmt const &other) init_expr = other.get_init_expr ().clone_expr (); else init_expr = nullptr; + + if (other.has_else_expr ()) + else_expr = other.get_else_expr ().clone_expr (); + else + else_expr = tl::nullopt; + if (other.has_type ()) type = other.get_type ().clone_type (); else diff --git a/gcc/rust/hir/tree/rust-hir-stmt.h b/gcc/rust/hir/tree/rust-hir-stmt.h index 3db1728202e..9c1a9eccc38 100644 --- a/gcc/rust/hir/tree/rust-hir-stmt.h +++ b/gcc/rust/hir/tree/rust-hir-stmt.h @@ -101,6 +101,7 @@ class LetStmt : public Stmt tl::optional<std::unique_ptr<Type>> type; tl::optional<std::unique_ptr<Expr>> init_expr; + tl::optional<std::unique_ptr<Expr>> else_expr; location_t locus; @@ -113,12 +114,15 @@ public: // Returns whether let statement has an initialisation expression. bool has_init_expr () const { return init_expr.has_value (); } + // Returns whether let statement has a diverging else expression. + bool has_else_expr () const { return else_expr.has_value (); } std::string as_string () const override; LetStmt (Analysis::NodeMapping mappings, std::unique_ptr<Pattern> variables_pattern, tl::optional<std::unique_ptr<Expr>> init_expr, + tl::optional<std::unique_ptr<Expr>> else_expr, tl::optional<std::unique_ptr<Type>> type, AST::AttrVec outer_attrs, location_t locus); @@ -167,6 +171,18 @@ public: return *init_expr.value (); } + HIR::Expr &get_else_expr () + { + rust_assert (*else_expr); + return *else_expr.value (); + } + + const HIR::Expr &get_else_expr () const + { + rust_assert (*else_expr); + return *else_expr.value (); + } + HIR::Pattern &get_pattern () { return *variables_pattern; } bool is_item () const override final { return false; } -- 2.49.0