Closed
Description
The following program:
#![crate_type = "lib"]
use std::ptr;
use std::slice;
pub struct RawSlice<'a>
{
s: &'a mut [u8]
}
impl<'a> RawSlice<'a> {
fn write(&mut self, buf: &[u8]) {
let dest_data = self.s.as_mut_ptr();
let src_data = buf.as_ptr();
unsafe {
ptr::copy_nonoverlapping(src_data, dest_data, buf.len());
self.s = slice::from_raw_parts_mut(dest_data.offset(buf.len() as isize), self.s.len() - buf.len());
}
}
}
pub fn do_write(r: &mut RawSlice, k: [u8; 4]) {
r.write(&[1, 2, 3, 4]);
r.write(&[1, 2, 3, 4]);
r.write(&[1, 2, 3, 4]);
r.write(&[1, 2, 3, 4]);
}
Compiles to:
pushq %rbp
movq %rsp, %rbp
movq (%rdi), %rax
movl $67305985, (%rax)
addq $-4, 8(%rdi)
movl $67305985, 4(%rax)
addq $-4, 8(%rdi)
movl $67305985, 8(%rax)
addq $-4, 8(%rdi)
movl $67305985, 12(%rax)
addq $16, %rax
movq 8(%rdi), %rcx
addq $-4, %rcx
movq %rax, (%rdi)
movq %rcx, 8(%rdi)
popq %rbp
retq
Ideally all of the addq -4 would be folded together. I suspect that either rust is emitting the wrong aliasing info or llvm is not properly dealing with the information.