aboutsummaryrefslogtreecommitdiff
path: root/gcc/rust/hir
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/rust/hir')
-rw-r--r--gcc/rust/hir/rust-ast-lower-expr.h55
-rw-r--r--gcc/rust/hir/tree/rust-hir-expr.h15
2 files changed, 64 insertions, 6 deletions
diff --git a/gcc/rust/hir/rust-ast-lower-expr.h b/gcc/rust/hir/rust-ast-lower-expr.h
index b919905..a165eaf 100644
--- a/gcc/rust/hir/rust-ast-lower-expr.h
+++ b/gcc/rust/hir/rust-ast-lower-expr.h
@@ -26,6 +26,42 @@
namespace Rust {
namespace HIR {
+class ArrayCapacityConstant : public ASTLoweringBase
+{
+public:
+ static bool fold (AST::Expr *expr, size_t *folded_result)
+ {
+ ArrayCapacityConstant folder;
+ expr->accept_vis (folder);
+ *folded_result = folder.result;
+ return folder.ok;
+ }
+
+ virtual ~ArrayCapacityConstant () {}
+
+ void visit (AST::LiteralExpr &expr)
+ {
+ switch (expr.get_lit_type ())
+ {
+ case AST::Literal::LitType::INT: {
+ ok = true;
+ std::stringstream ss (expr.as_string ());
+ ss >> result;
+ }
+ break;
+
+ default:
+ return;
+ }
+ }
+
+private:
+ ArrayCapacityConstant () : ok (false), result (-1) {}
+
+ bool ok;
+ size_t result;
+}; // namespace Resolver
+
class ASTLoweringExpr : public ASTLoweringBase
{
public:
@@ -209,8 +245,23 @@ public:
void visit (AST::ArrayElemsCopied &elems)
{
- // TODO
- gcc_unreachable ();
+ HIR::Expr *element
+ = ASTLoweringExpr::translate (elems.get_elem_to_copy ().get ());
+ HIR::Expr *num_copies
+ = ASTLoweringExpr::translate (elems.get_num_copies ().get ());
+
+ size_t folded;
+ if (!ArrayCapacityConstant::fold (elems.get_num_copies ().get (), &folded))
+ {
+ rust_fatal_error (elems.get_num_copies ()->get_locus_slow (),
+ "failed to fold capacity constant");
+ return;
+ }
+
+ translated_array_elems
+ = new HIR::ArrayElemsCopied (std::unique_ptr<HIR::Expr> (element),
+ std::unique_ptr<HIR::Expr> (num_copies),
+ folded);
}
void visit (AST::LiteralExpr &expr)
diff --git a/gcc/rust/hir/tree/rust-hir-expr.h b/gcc/rust/hir/tree/rust-hir-expr.h
index 7c32ac2..1110f98 100644
--- a/gcc/rust/hir/tree/rust-hir-expr.h
+++ b/gcc/rust/hir/tree/rust-hir-expr.h
@@ -980,21 +980,25 @@ class ArrayElemsCopied : public ArrayElems
{
std::unique_ptr<Expr> elem_to_copy;
std::unique_ptr<Expr> num_copies;
+ size_t folded_copy_amount;
// TODO: should this store location data?
public:
// Constructor requires pointers for polymorphism
ArrayElemsCopied (std::unique_ptr<Expr> copied_elem,
- std::unique_ptr<Expr> copy_amount)
+ std::unique_ptr<Expr> copy_amount,
+ size_t folded_copy_amount)
: elem_to_copy (std::move (copied_elem)),
- num_copies (std::move (copy_amount))
+ num_copies (std::move (copy_amount)),
+ folded_copy_amount (folded_copy_amount)
{}
// Copy constructor required due to unique_ptr - uses custom clone
ArrayElemsCopied (ArrayElemsCopied const &other)
: elem_to_copy (other.elem_to_copy->clone_expr ()),
- num_copies (other.num_copies->clone_expr ())
+ num_copies (other.num_copies->clone_expr ()),
+ folded_copy_amount (other.folded_copy_amount)
{}
// Overloaded assignment operator for deep copying
@@ -1002,6 +1006,7 @@ public:
{
elem_to_copy = other.elem_to_copy->clone_expr ();
num_copies = other.num_copies->clone_expr ();
+ folded_copy_amount = other.folded_copy_amount;
return *this;
}
@@ -1014,7 +1019,9 @@ public:
void accept_vis (HIRVisitor &vis) override;
- size_t get_num_elements () const override { return 0; }
+ size_t get_num_elements () const override { return folded_copy_amount; }
+
+ Expr *get_elem_to_copy () { return elem_to_copy.get (); }
protected:
ArrayElemsCopied *clone_array_elems_impl () const override