Skip to content

Commit

Permalink
cg_llvm: use index-based loop in write_operand_repeatedly
Browse files Browse the repository at this point in the history
This is easier for LLVM to analyze.
  • Loading branch information
erikdesjardins committed Jun 11, 2023
1 parent b8a5001 commit bd0aae9
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 15 deletions.
22 changes: 7 additions & 15 deletions compiler/rustc_codegen_llvm/src/builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -572,8 +572,6 @@ impl<'a, 'll, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'll, 'tcx> {
) {
let zero = self.const_usize(0);
let count = self.const_usize(count);
let start = dest.project_index(self, zero).llval;
let end = dest.project_index(self, count).llval;

let header_bb = self.append_sibling_block("repeat_loop_header");
let body_bb = self.append_sibling_block("repeat_loop_body");
Expand All @@ -582,24 +580,18 @@ impl<'a, 'll, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'll, 'tcx> {
self.br(header_bb);

let mut header_bx = Self::build(self.cx, header_bb);
let current = header_bx.phi(self.val_ty(start), &[start], &[self.llbb()]);
let i = header_bx.phi(self.val_ty(zero), &[zero], &[self.llbb()]);

let keep_going = header_bx.icmp(IntPredicate::IntNE, current, end);
let keep_going = header_bx.icmp(IntPredicate::IntULT, i, count);
header_bx.cond_br(keep_going, body_bb, next_bb);

let mut body_bx = Self::build(self.cx, body_bb);
let align = dest.align.restrict_for_offset(dest.layout.field(self.cx(), 0).size);
cg_elem
.val
.store(&mut body_bx, PlaceRef::new_sized_aligned(current, cg_elem.layout, align));

let next = body_bx.inbounds_gep(
self.backend_type(cg_elem.layout),
current,
&[self.const_usize(1)],
);
let dest_elem = dest.project_index(&mut body_bx, i);
cg_elem.val.store(&mut body_bx, dest_elem);

let next = body_bx.unchecked_uadd(i, self.const_usize(1));
body_bx.br(header_bb);
header_bx.add_incoming_to_phi(current, next, body_bb);
header_bx.add_incoming_to_phi(i, next, body_bb);

*self = Self::build(self.cx, next_bb);
}
Expand Down
12 changes: 12 additions & 0 deletions tests/codegen/issues/issue-111603.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,18 @@

use std::sync::Arc;

// CHECK-LABEL: @new_from_array
#[no_mangle]
pub fn new_from_array(x: u64) -> Arc<[u64]> {
// Ensure that we only generate one alloca for the array.

// CHECK: alloca
// CHECK-SAME: [1000 x i64]
// CHECK-NOT: alloca
let array = [x; 1000];
Arc::new(array)
}

// CHECK-LABEL: @new_uninit
#[no_mangle]
pub fn new_uninit(x: u64) -> Arc<[u64; 1000]> {
Expand Down

0 comments on commit bd0aae9

Please sign in to comment.