Closed
Description
For this code, foo()
and bar()
are functionally the same.
use std::mem;
#[repr(C)]
struct Inner {
data: [i64; 4],
}
extern "C" {
fn init(ptr: *mut Inner);
}
pub struct Outer {
inner: Inner,
}
pub unsafe fn foo() -> Outer {
let mut outer = mem::uninitialized::<Outer>();
init(&mut outer.inner);
outer
}
pub unsafe fn bar() -> Outer {
let mut inner = mem::uninitialized::<Inner>();
init(&mut inner);
Outer { inner }
}
However, the output from cargo rustc --release -- --emit asm
shows needless copying for bar()
.
;snip...
;function foo:
.cfi_startproc
pushq %rbx
.Ltmp0:
.cfi_def_cfa_offset 16
.Ltmp1:
.cfi_offset %rbx, -16
movq %rdi, %rbx
callq init@PLT
movq %rbx, %rax
popq %rbx
retq
;snip...
;function bar:
.cfi_startproc
pushq %rbx
.Ltmp2:
.cfi_def_cfa_offset 16
subq $32, %rsp
.Ltmp3:
.cfi_def_cfa_offset 48
.Ltmp4:
.cfi_offset %rbx, -16
movq %rdi, %rbx
leaq (%rsp), %rdi
callq init@PLT
movups (%rsp), %xmm0
movups 16(%rsp), %xmm1
movups %xmm1, 16(%rbx)
movups %xmm0, (%rbx)
movq %rbx, %rax
addq $32, %rsp
popq %rbx
retq
;snip...