Skip to content

Useless while loop with a step of 2 doesn't optimize away #60616

Closed
@lambda

Description

@lambda

While investigating a variant of #59281 and #57517 reported on Reddit, I found that even a while loop version still had an extra loop that wasn't optimized away. A minimal example that demonstrates the issue:

pub fn bongo(num: u32) -> () {
  let mut x = 0;
  while x < num {
    x += 2
  }
}

While the same loop with a step increment of 1 does optimize away the loop:

pub fn bongo(num: u32) -> () {
  let mut x = 0;
  while x < num {
    x += 1
  }
}

It looks like this optimization happens in rustc before LLVM. Increment by 2:

; playground::bongo
; Function Attrs: norecurse nounwind nonlazybind readnone uwtable
define void @_ZN10playground5bongo17hf57bf6382d7a4b02E(i32 %num) unnamed_addr #0 {
start:
  br label %bb1

bb1:                                              ; preds = %bb1, %start
  %x.0 = phi i32 [ 0, %start ], [ %1, %bb1 ]
  %0 = icmp ult i32 %x.0, %num
  %1 = add i32 %x.0, 2
  br i1 %0, label %bb1, label %bb2

bb2:                                              ; preds = %bb1
  ret void
}

Increment by 1:

; playground::bongo
; Function Attrs: norecurse nounwind nonlazybind readnone uwtable
define void @_ZN10playground5bongo17hf57bf6382d7a4b02E(i32 %num) unnamed_addr #0 {
start:
  ret void
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-codegenArea: Code generationI-slowIssue: Problems and improvements with respect to performance of generated code.T-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions