; NOTE: Assertions have been autogenerated by utils/update_analyze_test_checks.py UTC_ARGS: --version 5 ; RUN: opt -passes='print' -disable-output %s 2>&1 | FileCheck %s target datalayout = "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-n32:64-S128-Fn32" define i32 @last_loaded_with_or_exit(i32 %n, ptr %arr) mustprogress { ; CHECK-LABEL: 'last_loaded_with_or_exit' ; CHECK-NEXT: Classifying expressions for: @last_loaded_with_or_exit ; CHECK-NEXT: %iv = phi i32 [ %iv.next, %latch ], [ 0, %entry ] ; CHECK-NEXT: --> {0,+,1}<%header> U: full-set S: full-set Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: %last_loaded = phi i32 [ %last_loaded.next, %latch ], [ 0, %entry ] ; CHECK-NEXT: --> %last_loaded U: full-set S: full-set Exits: <> LoopDispositions: { %header: Variant } ; CHECK-NEXT: %iv_minus_one = add i32 -1, %iv ; CHECK-NEXT: --> {-1,+,1}<%header> U: full-set S: full-set Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: %stay = or i1 %iv_lt_n, %iv_minus_one_lt_n ; CHECK-NEXT: --> (%iv_minus_one_lt_n umax %iv_lt_n) U: full-set S: full-set Exits: <> LoopDispositions: { %header: Variant } ; CHECK-NEXT: %body_iv_minus_one = add i32 -1, %iv ; CHECK-NEXT: --> {-1,+,1}<%header> U: full-set S: full-set Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: %idx = zext nneg i32 %body_iv_minus_one to i64 ; CHECK-NEXT: --> (zext i32 {-1,+,1}<%header> to i64) U: [0,4294967296) S: [0,4294967296) Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: %addr = getelementptr inbounds i32, ptr %arr, i64 %idx ; CHECK-NEXT: --> ((4 * (zext i32 {-1,+,1}<%header> to i64)) + %arr) U: full-set S: full-set Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: %loaded = load i32, ptr %addr, align 4 ; CHECK-NEXT: --> %loaded U: full-set S: full-set Exits: <> LoopDispositions: { %header: Variant } ; CHECK-NEXT: %last_loaded.next = phi i32 [ %last_loaded, %body ], [ %loaded, %do_load ] ; CHECK-NEXT: --> %last_loaded.next U: full-set S: full-set Exits: <> LoopDispositions: { %header: Variant } ; CHECK-NEXT: %iv.next = add i32 %iv, 1 ; CHECK-NEXT: --> {1,+,1}<%header> U: full-set S: full-set Exits: <> LoopDispositions: { %header: Computable } ; CHECK-NEXT: Determining loop execution counts for: @last_loaded_with_or_exit ; CHECK-NEXT: Loop %header: Unpredictable backedge-taken count. ; CHECK-NEXT: Loop %header: Unpredictable constant max backedge-taken count. ; CHECK-NEXT: Loop %header: Unpredictable symbolic max backedge-taken count. ; entry: br label %header header: %iv = phi i32 [ %iv.next, %latch ], [ 0, %entry ] %last_loaded = phi i32 [ %last_loaded.next, %latch ], [ 0, %entry ] %iv_lt_n = icmp ult i32 %iv, %n %iv_minus_one = add i32 -1, %iv %iv_minus_one_lt_n = icmp ult i32 %iv_minus_one, %n %stay = or i1 %iv_lt_n, %iv_minus_one_lt_n br i1 %stay, label %body, label %exit body: %body_iv_minus_one = add i32 -1, %iv %body_iv_minus_one_nonneg = icmp sgt i32 %body_iv_minus_one, -1 br i1 %body_iv_minus_one_nonneg, label %do_load, label %latch do_load: %idx = zext nneg i32 %body_iv_minus_one to i64 %addr = getelementptr inbounds i32, ptr %arr, i64 %idx %loaded = load i32, ptr %addr br label %latch latch: %last_loaded.next = phi i32 [ %last_loaded, %body ], [ %loaded, %do_load ] %iv.next = add i32 %iv, 1 br label %header exit: ret i32 %last_loaded }