]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
gccrs: Fix ICE on raw reference
authorPhilip Herron <herron.philip@googlemail.com>
Thu, 3 Apr 2025 14:39:58 +0000 (15:39 +0100)
committerArthur Cohen <arthur.cohen@embecosm.com>
Tue, 8 Apr 2025 08:17:13 +0000 (10:17 +0200)
This patch adds support for raw references which enforce the pointer
type away from a reference type.

Fixes Rust-GCC#3667

gcc/rust/ChangeLog:

* backend/rust-compile-base.cc (HIRCompileBase::address_expression): allow optional type
* backend/rust-compile-base.h: update prototype
* backend/rust-compile-expr.cc (CompileExpr::visit): update borrow expr
* backend/rust-compile-extern.h: remove unused debug
* backend/rust-compile-resolve-path.cc (HIRCompileBase::query_compile): update usage
* hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): lower raw ref
* hir/tree/rust-hir-expr.cc (BorrowExpr::BorrowExpr): add flag for raw ref
* hir/tree/rust-hir-expr.h (class BorrowExpr): add new raw ref field
* typecheck/rust-hir-type-check-expr.cc (TypeCheckExpr::visit): add handle for raw ref

gcc/testsuite/ChangeLog:

* rust/compile/issue-3667.rs: New test.

Signed-off-by: Philip Herron <herron.philip@googlemail.com>
gcc/rust/backend/rust-compile-base.cc
gcc/rust/backend/rust-compile-base.h
gcc/rust/backend/rust-compile-expr.cc
gcc/rust/backend/rust-compile-extern.h
gcc/rust/backend/rust-compile-resolve-path.cc
gcc/rust/hir/rust-ast-lower-expr.cc
gcc/rust/hir/tree/rust-hir-expr.cc
gcc/rust/hir/tree/rust-hir-expr.h
gcc/rust/typecheck/rust-hir-type-check-expr.cc
gcc/testsuite/rust/compile/issue-3667.rs [new file with mode: 0644]

index b6bee8f9c2f10aeb88dd7e320b403484a11f8a44..0647718c841cd7f007e7ce6f5b31c799d03b7ad8 100644 (file)
@@ -549,7 +549,7 @@ HIRCompileBase::mark_addressable (tree exp, location_t locus)
 }
 
 tree
-HIRCompileBase::address_expression (tree expr, location_t location)
+HIRCompileBase::address_expression (tree expr, location_t location, tree ptrty)
 {
   if (expr == error_mark_node)
     return error_mark_node;
@@ -557,7 +557,10 @@ HIRCompileBase::address_expression (tree expr, location_t location)
   if (!mark_addressable (expr, location))
     return error_mark_node;
 
-  return build_fold_addr_expr_loc (location, expr);
+  if (ptrty == NULL || ptrty == error_mark_node)
+    ptrty = build_pointer_type (TREE_TYPE (expr));
+
+  return build_fold_addr_expr_with_type_loc (location, expr, ptrty);
 }
 
 tree
index 64c8106d1c2817c1d540eb350afff77de661b6e6..467bfd0a4f7366a9c319c55f1db01202f964f77f 100644 (file)
@@ -29,7 +29,8 @@ class HIRCompileBase
 public:
   virtual ~HIRCompileBase () {}
 
-  static tree address_expression (tree expr, location_t locus);
+  static tree address_expression (tree expr, location_t locus,
+                                 tree ptrty = NULL_TREE);
 
   static tree compile_constant_expr (
     Context *ctx, HirId coercion_id, TyTy::BaseType *resolved_type,
index e4ab9f010b8e260fa7994c80c12a63600edd0d01..37856a77f2c770cbfe3ea76eb8c40630628618e5 100644 (file)
@@ -905,7 +905,8 @@ CompileExpr::visit (HIR::BorrowExpr &expr)
                                       &tyty))
     return;
 
-  translated = address_expression (main_expr, expr.get_locus ());
+  tree expected_type = TyTyResolveCompile::compile (ctx, tyty);
+  translated = address_expression (main_expr, expr.get_locus (), expected_type);
 }
 
 void
index bacd1c044ec51cb778c2be97bbac60d17fae10c2..d6aa5899f624bc830e03f52e0f2997969c28619b 100644 (file)
@@ -34,16 +34,10 @@ class CompileExternItem : public HIRCompileBase,
 public:
   static tree compile (HIR::ExternalItem *item, Context *ctx,
                       TyTy::BaseType *concrete = nullptr,
-                      bool is_query_mode = false,
                       location_t ref_locus = UNDEF_LOCATION)
   {
     CompileExternItem compiler (ctx, concrete, ref_locus);
     item->accept_vis (compiler);
-
-    if (is_query_mode && compiler.reference == error_mark_node)
-      rust_internal_error_at (ref_locus, "failed to compile extern item: %s",
-                             item->as_string ().c_str ());
-
     return compiler.reference;
   }
 
index bba0498ddfa7ca67f06988bd6a3b4f6fa02164d7..81d2dbb033f13a4618bae3cf3849a05a976f4846 100644 (file)
@@ -261,10 +261,10 @@ HIRCompileBase::query_compile (HirId ref, TyTy::BaseType *lookup,
       HIR::ExternalItem *resolved_extern_item = hir_extern_item->first;
       if (!lookup->has_substitutions_defined ())
        return CompileExternItem::compile (resolved_extern_item, ctx, nullptr,
-                                          true, expr_locus);
+                                          expr_locus);
       else
        return CompileExternItem::compile (resolved_extern_item, ctx, lookup,
-                                          true, expr_locus);
+                                          expr_locus);
     }
   else
     {
index 9f363c0b5043a4ca924892522cfc10aae0dc3a2c..9c763806c80bf64e0f31419be385b3e424509549 100644 (file)
@@ -633,9 +633,6 @@ ASTLoweringExpr::visit (AST::ContinueExpr &expr)
 void
 ASTLoweringExpr::visit (AST::BorrowExpr &expr)
 {
-  if (expr.is_raw_borrow ())
-    rust_unreachable ();
-
   HIR::Expr *borrow_lvalue
     = ASTLoweringExpr::translate (expr.get_borrowed_expr ());
 
@@ -646,8 +643,8 @@ ASTLoweringExpr::visit (AST::BorrowExpr &expr)
 
   auto *borrow_expr
     = new HIR::BorrowExpr (mapping, std::unique_ptr<HIR::Expr> (borrow_lvalue),
-                          expr.get_mutability (), expr.get_outer_attrs (),
-                          expr.get_locus ());
+                          expr.get_mutability (), expr.is_raw_borrow (),
+                          expr.get_outer_attrs (), expr.get_locus ());
 
   if (expr.get_is_double_borrow ())
     {
@@ -659,8 +656,8 @@ ASTLoweringExpr::visit (AST::BorrowExpr &expr)
       borrow_expr
        = new HIR::BorrowExpr (mapping,
                               std::unique_ptr<HIR::Expr> (borrow_expr),
-                              expr.get_mutability (), expr.get_outer_attrs (),
-                              expr.get_locus ());
+                              expr.get_mutability (), expr.is_raw_borrow (),
+                              expr.get_outer_attrs (), expr.get_locus ());
     }
 
   translated = borrow_expr;
index 2ded789e60b15c49066a3850f088f1e0a73ce1e3..bb7ebfbc617bd7ae56b350f12aa57964f394e062 100644 (file)
@@ -81,10 +81,10 @@ OperatorExpr::operator= (OperatorExpr const &other)
 
 BorrowExpr::BorrowExpr (Analysis::NodeMapping mappings,
                        std::unique_ptr<Expr> borrow_lvalue, Mutability mut,
-                       AST::AttrVec outer_attribs, location_t locus)
+                       bool raw, AST::AttrVec outer_attribs, location_t locus)
   : OperatorExpr (std::move (mappings), std::move (borrow_lvalue),
                  std::move (outer_attribs), locus),
-    mut (mut)
+    mut (mut), raw (raw)
 {}
 
 DereferenceExpr::DereferenceExpr (Analysis::NodeMapping mappings,
index f8f212884b67f60ea44d570c5f212bda729eaaeb..3ff38b340655187f7775bbeba8d6a54e20a63a46 100644 (file)
@@ -199,12 +199,13 @@ public:
 class BorrowExpr : public OperatorExpr
 {
   Mutability mut;
+  bool raw;
 
 public:
   std::string as_string () const override;
 
   BorrowExpr (Analysis::NodeMapping mappings,
-             std::unique_ptr<Expr> borrow_lvalue, Mutability mut,
+             std::unique_ptr<Expr> borrow_lvalue, Mutability mut, bool raw,
              AST::AttrVec outer_attribs, location_t locus);
 
   void accept_vis (HIRFullVisitor &vis) override;
@@ -212,6 +213,7 @@ public:
 
   Mutability get_mut () const { return mut; }
   bool is_mut () const { return mut == Mutability::Mut; }
+  bool is_raw_borrow () const { return raw; }
 
 protected:
   /* Use covariance to implement clone function as returning this object rather
index b7fdc13961515a300c938bd838c9bf53f2f3e16e..791795f3b0e0e0a4439e8cbb98c18f19567e556b 100644 (file)
@@ -1463,6 +1463,15 @@ TypeCheckExpr::visit (HIR::BorrowExpr &expr)
        }
     }
 
+  if (expr.is_raw_borrow ())
+    {
+      infered = new TyTy::PointerType (expr.get_mappings ().get_hirid (),
+                                      TyTy::TyVar (resolved_base->get_ref ()),
+                                      expr.get_mut ());
+
+      return;
+    }
+
   infered = new TyTy::ReferenceType (expr.get_mappings ().get_hirid (),
                                     TyTy::TyVar (resolved_base->get_ref ()),
                                     expr.get_mut ());
diff --git a/gcc/testsuite/rust/compile/issue-3667.rs b/gcc/testsuite/rust/compile/issue-3667.rs
new file mode 100644 (file)
index 0000000..e72069c
--- /dev/null
@@ -0,0 +1,24 @@
+// { dg-options "-w" }
+#![feature(raw_ref_op)]
+
+const pq1: () = {
+    let mut x = 2;
+    &raw mut x;
+}; //~ mutable reference
+
+static B: () = {
+    let mut x = 2;
+    &raw mut x;
+}; //~ mutable reference
+
+static mut C: () = {
+    let mut x = 2;
+    &raw mut x;
+}; //~ mutable reference
+
+const fn foo() {
+    let mut x = 0;
+    let y = &raw mut x; //~ mutable reference
+}
+
+fn main() {}