Where is #[rustc_box] implemented?

The implementation of box_new, contains an attribute #[rustc_box] and a call to Box::new, which then again ends up calling box_new.

So, when I read the solution for a similar post, it did not explain anything more than the fact that compiler needs to do more. However, what exactly does the compiler need to do and where is it doing it?

Here's the conversion from the intrinsic to the ExprKind::Box.

Then see my answer in the other thread:

2 Likes

Thanks @quinedot - I'm sorry but I'm not able to see how those code snippets in the links you shared are in any way connected to #[rustc_box].

Put another way - If I were to insert #[rustc_box] anywhere in the code, does the compiler insert some other code there like a procedural macro does?

The box_new intrinnsic replaces rustc_box. Relative to the code you linked, rustc_box only exists in cfg(bootstrap) (~ some previous compiler versions), which means it doesn't exist in 1.86.[1] If you want to dig into the rustc_box mechanics in previous compiler versions, maybe after this PR is a good place to start. A quick skim of the diff indicates it was just another way to get to ExprKind::Box though.

Not in current versions of the compiler (it no longer exists).


  1. Here's the bootstrap bump that removed the transition function. â†Šī¸Ž

Thanks @quinedot . I tried to test it. Following is the patch:

diff --git a/compiler/rustc_mir_build/Cargo.toml b/compiler/rustc_mir_build/Cargo.toml
index 1534865cdd3..afafb4febf5 100644
--- a/compiler/rustc_mir_build/Cargo.toml
+++ b/compiler/rustc_mir_build/Cargo.toml
@@ -6,6 +6,7 @@ edition = "2024"
 [dependencies]
 # tidy-alphabetical-start
 itertools = "0.12"
+libc = "0.2"
 
 rustc_abi = { path = "../rustc_abi" }
 rustc_apfloat = "0.2.0"
diff --git a/compiler/rustc_mir_build/src/thir/cx/expr.rs b/compiler/rustc_mir_build/src/thir/cx/expr.rs
index fde23413972..cd5dc83e050 100644
--- a/compiler/rustc_mir_build/src/thir/cx/expr.rs
+++ b/compiler/rustc_mir_build/src/thir/cx/expr.rs
@@ -23,6 +23,12 @@
 
 use crate::thir::cx::ThirBuildCx;
 
+use libc::{c_char, c_int};
+
+unsafe extern "C" {
+    fn printf(fmt: *const c_char, ...) -> c_int;
+}
+
 impl<'tcx> ThirBuildCx<'tcx> {
     /// Create a THIR expression for the given HIR expression. This expands all
     /// adjustments and directly adds the type information from the
@@ -391,6 +397,12 @@ fn make_mirror_unadjusted(&mut self, expr: &'tcx hir::Expr<'tcx>) -> Expr<'tcx>
                         );
                     }
                     let value = &args[0];
+                    let v = unsafe { libc::getenv(b"FOO_DEBUG\0".as_ptr() as *const i8 ) } as *const c_char;
+                    if !v.is_null() {
+                        unsafe {
+                            printf("FOO_DEBUG:compiler/rustc_mir_build/src/thir/cx/expr.rs:make_mirror_unadjusted():403\n\0".as_ptr() as *const i8);
+                        }
+                    }
                     return Expr {
                         temp_lifetime: TempLifetime { temp_lifetime, backwards_incompatible },
                         ty: expr_ty,

Unfortunately, it did not work when I tried to verify the above compiler change using the following code that I compiled with the modified compiler:

fn main() {
    let x = 5;
    let mut y = Box::new(x);

    *y = 6;
    println!("*y: {}", *y);
    println!("x: {}", x); 
}

Am I doing something wrong or is ExprKind::Box not getting called at alll?

That is, printf was not called, if I understand your intents correctly?

Yes, that's correct - printf was not called.

You may need to compile with -Z build-std -- the monomorphic form of Box::<T>::new might have already been converted to ExprKind::Box.

Thanks for your response @riking . Do you know how I can use this flag for compiler build? In bootstrap.example.toml, I can see options to pass extra compiler and linker flags to the LLCM CMake build, but not to the compiler that builds the compiler.