459 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py2; RUN: opt < %s -passes=correlated-propagation -S | FileCheck %s3 4declare void @llvm.assume(i1)5 6; Divisor is constant. X's range is known7 8define i8 @constant.divisor.v3(i8 %x) {9; CHECK-LABEL: @constant.divisor.v3(10; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 311; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])12; CHECK-NEXT: ret i8 [[X]]13;14 %cmp.x.upper = icmp ult i8 %x, 315 call void @llvm.assume(i1 %cmp.x.upper)16 %rem = urem i8 %x, 317 ret i8 %rem18}19define i8 @constant.divisor.v4(i8 %x) {20; CHECK-LABEL: @constant.divisor.v4(21; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 422; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])23; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]24; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 325; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 326; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]27; CHECK-NEXT: ret i8 [[REM]]28;29 %cmp.x.upper = icmp ult i8 %x, 430 call void @llvm.assume(i1 %cmp.x.upper)31 %rem = urem i8 %x, 332 ret i8 %rem33}34define i8 @constant.divisor.x.range.v4(ptr %x.ptr) {35; CHECK-LABEL: @constant.divisor.x.range.v4(36; CHECK-NEXT: [[X:%.*]] = load i8, ptr [[X_PTR:%.*]], align 1, !range [[RNG0:![0-9]+]]37; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]38; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 339; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 340; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]41; CHECK-NEXT: ret i8 [[REM]]42;43 %x = load i8, ptr %x.ptr, !range !{ i8 0, i8 4 }44 %rem = urem i8 %x, 345 ret i8 %rem46}47define i8 @constant.divisor.x.mask.v4(i8 %x) {48; CHECK-LABEL: @constant.divisor.x.mask.v4(49; CHECK-NEXT: [[X_MASKED:%.*]] = and i8 [[X:%.*]], 350; CHECK-NEXT: [[X_MASKED_FROZEN:%.*]] = freeze i8 [[X_MASKED]]51; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_MASKED_FROZEN]], 352; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_MASKED_FROZEN]], 353; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_MASKED_FROZEN]], i8 [[REM_UREM]]54; CHECK-NEXT: ret i8 [[REM]]55;56 %x.masked = and i8 %x, 357 %rem = urem i8 %x.masked, 358 ret i8 %rem59}60define i8 @constant.divisor.v5(i8 %x) {61; CHECK-LABEL: @constant.divisor.v5(62; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 563; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])64; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]65; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 366; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 367; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]68; CHECK-NEXT: ret i8 [[REM]]69;70 %cmp.x.upper = icmp ult i8 %x, 571 call void @llvm.assume(i1 %cmp.x.upper)72 %rem = urem i8 %x, 373 ret i8 %rem74}75define i8 @constant.divisor.v6(i8 %x) {76; CHECK-LABEL: @constant.divisor.v6(77; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 678; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])79; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]80; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 381; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 382; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]83; CHECK-NEXT: ret i8 [[REM]]84;85 %cmp.x.upper = icmp ult i8 %x, 686 call void @llvm.assume(i1 %cmp.x.upper)87 %rem = urem i8 %x, 388 ret i8 %rem89}90define i8 @constant.divisor.v7(i8 %x) {91; CHECK-LABEL: @constant.divisor.v7(92; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 793; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])94; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], 395; CHECK-NEXT: ret i8 [[REM]]96;97 %cmp.x.upper = icmp ult i8 %x, 798 call void @llvm.assume(i1 %cmp.x.upper)99 %rem = urem i8 %x, 3100 ret i8 %rem101}102 103define i8 @constant.divisor.v6to8(i8 %x) {104; CHECK-LABEL: @constant.divisor.v6to8(105; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X:%.*]], 6106; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])107; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X]], 9108; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])109; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], 3110; CHECK-NEXT: ret i8 [[REM]]111;112 %cmp.x.lower = icmp uge i8 %x, 6113 call void @llvm.assume(i1 %cmp.x.lower)114 %cmp.x.upper = icmp ult i8 %x, 9115 call void @llvm.assume(i1 %cmp.x.upper)116 %rem = urem i8 %x, 3117 ret i8 %rem118}119 120define i8 @constant.divisor.v9to11(i8 %x) {121; CHECK-LABEL: @constant.divisor.v9to11(122; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X:%.*]], 9123; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])124; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X]], 12125; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])126; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], 3127; CHECK-NEXT: ret i8 [[REM]]128;129 %cmp.x.lower = icmp uge i8 %x, 9130 call void @llvm.assume(i1 %cmp.x.lower)131 %cmp.x.upper = icmp ult i8 %x, 12132 call void @llvm.assume(i1 %cmp.x.upper)133 %rem = urem i8 %x, 3134 ret i8 %rem135}136 137define i8 @constant.divisor.v12to14(i8 %x) {138; CHECK-LABEL: @constant.divisor.v12to14(139; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X:%.*]], 12140; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])141; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X]], 15142; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])143; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], 3144; CHECK-NEXT: ret i8 [[REM]]145;146 %cmp.x.lower = icmp uge i8 %x, 12147 call void @llvm.assume(i1 %cmp.x.lower)148 %cmp.x.upper = icmp ult i8 %x, 15149 call void @llvm.assume(i1 %cmp.x.upper)150 %rem = urem i8 %x, 3151 ret i8 %rem152}153 154define i8 @constant.divisor.v6to11(i8 %x) {155; CHECK-LABEL: @constant.divisor.v6to11(156; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X:%.*]], 6157; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])158; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X]], 12159; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])160; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], 3161; CHECK-NEXT: ret i8 [[REM]]162;163 %cmp.x.lower = icmp uge i8 %x, 6164 call void @llvm.assume(i1 %cmp.x.lower)165 %cmp.x.upper = icmp ult i8 %x, 12166 call void @llvm.assume(i1 %cmp.x.upper)167 %rem = urem i8 %x, 3168 ret i8 %rem169}170 171; Both are variable. Bounds are known172 173define i8 @variable.v3(i8 %x, i8 %y) {174; CHECK-LABEL: @variable.v3(175; CHECK-NEXT: [[CMP_X:%.*]] = icmp ult i8 [[X:%.*]], 3176; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X]])177; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3178; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])179; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4180; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])181; CHECK-NEXT: ret i8 [[X]]182;183 %cmp.x = icmp ult i8 %x, 3184 call void @llvm.assume(i1 %cmp.x)185 %cmp.y.lower = icmp uge i8 %y, 3186 call void @llvm.assume(i1 %cmp.y.lower)187 %cmp.y.upper = icmp ule i8 %y, 4188 call void @llvm.assume(i1 %cmp.y.upper)189 %rem = urem i8 %x, %y190 ret i8 %rem191}192define i8 @variable.v4(i8 %x, i8 %y) {193; CHECK-LABEL: @variable.v4(194; CHECK-NEXT: [[CMP_X:%.*]] = icmp ult i8 [[X:%.*]], 4195; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X]])196; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3197; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])198; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4199; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])200; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]201; CHECK-NEXT: [[Y_FROZEN:%.*]] = freeze i8 [[Y]]202; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], [[Y_FROZEN]]203; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], [[Y_FROZEN]]204; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]205; CHECK-NEXT: ret i8 [[REM]]206;207 %cmp.x = icmp ult i8 %x, 4208 call void @llvm.assume(i1 %cmp.x)209 %cmp.y.lower = icmp uge i8 %y, 3210 call void @llvm.assume(i1 %cmp.y.lower)211 %cmp.y.upper = icmp ule i8 %y, 4212 call void @llvm.assume(i1 %cmp.y.upper)213 %rem = urem i8 %x, %y214 ret i8 %rem215}216define i8 @variable.v4.range(ptr %x.ptr, ptr %y.ptr) {217; CHECK-LABEL: @variable.v4.range(218; CHECK-NEXT: [[X:%.*]] = load i8, ptr [[X_PTR:%.*]], align 1, !range [[RNG0]]219; CHECK-NEXT: [[Y:%.*]] = load i8, ptr [[Y_PTR:%.*]], align 1, !range [[RNG1:![0-9]+]]220; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]221; CHECK-NEXT: [[Y_FROZEN:%.*]] = freeze i8 [[Y]]222; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], [[Y_FROZEN]]223; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], [[Y_FROZEN]]224; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]225; CHECK-NEXT: ret i8 [[REM]]226;227 %x = load i8, ptr %x.ptr, !range !{ i8 0, i8 4 }228 %y = load i8, ptr %y.ptr, !range !{ i8 3, i8 5 }229 %rem = urem i8 %x, %y230 ret i8 %rem231}232define i8 @variable.v5(i8 %x, i8 %y) {233; CHECK-LABEL: @variable.v5(234; CHECK-NEXT: [[CMP_X:%.*]] = icmp ult i8 [[X:%.*]], 5235; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X]])236; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3237; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])238; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4239; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])240; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]241; CHECK-NEXT: [[Y_FROZEN:%.*]] = freeze i8 [[Y]]242; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], [[Y_FROZEN]]243; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], [[Y_FROZEN]]244; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]245; CHECK-NEXT: ret i8 [[REM]]246;247 %cmp.x = icmp ult i8 %x, 5248 call void @llvm.assume(i1 %cmp.x)249 %cmp.y.lower = icmp uge i8 %y, 3250 call void @llvm.assume(i1 %cmp.y.lower)251 %cmp.y.upper = icmp ule i8 %y, 4252 call void @llvm.assume(i1 %cmp.y.upper)253 %rem = urem i8 %x, %y254 ret i8 %rem255}256define i8 @variable.v6(i8 %x, i8 %y) {257; CHECK-LABEL: @variable.v6(258; CHECK-NEXT: [[CMP_X:%.*]] = icmp ult i8 [[X:%.*]], 6259; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X]])260; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3261; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])262; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4263; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])264; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]265; CHECK-NEXT: [[Y_FROZEN:%.*]] = freeze i8 [[Y]]266; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], [[Y_FROZEN]]267; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], [[Y_FROZEN]]268; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]269; CHECK-NEXT: ret i8 [[REM]]270;271 %cmp.x = icmp ult i8 %x, 6272 call void @llvm.assume(i1 %cmp.x)273 %cmp.y.lower = icmp uge i8 %y, 3274 call void @llvm.assume(i1 %cmp.y.lower)275 %cmp.y.upper = icmp ule i8 %y, 4276 call void @llvm.assume(i1 %cmp.y.upper)277 %rem = urem i8 %x, %y278 ret i8 %rem279}280define i8 @variable.v7(i8 %x, i8 %y) {281; CHECK-LABEL: @variable.v7(282; CHECK-NEXT: [[CMP_X:%.*]] = icmp ult i8 [[X:%.*]], 7283; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X]])284; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3285; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])286; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4287; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])288; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], [[Y]]289; CHECK-NEXT: ret i8 [[REM]]290;291 %cmp.x = icmp ult i8 %x, 7292 call void @llvm.assume(i1 %cmp.x)293 %cmp.y.lower = icmp uge i8 %y, 3294 call void @llvm.assume(i1 %cmp.y.lower)295 %cmp.y.upper = icmp ule i8 %y, 4296 call void @llvm.assume(i1 %cmp.y.upper)297 %rem = urem i8 %x, %y298 ret i8 %rem299}300 301define i8 @variable.v6to8.v3to4(i8 %x, i8 %y) {302; CHECK-LABEL: @variable.v6to8.v3to4(303; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X:%.*]], 6304; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])305; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X]], 8306; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])307; CHECK-NEXT: [[CMP_Y_LOWER:%.*]] = icmp samesign uge i8 [[Y:%.*]], 3308; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_LOWER]])309; CHECK-NEXT: [[CMP_Y_UPPER:%.*]] = icmp ule i8 [[Y]], 4310; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_Y_UPPER]])311; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X]], [[Y]]312; CHECK-NEXT: ret i8 [[REM]]313;314 %cmp.x.lower = icmp uge i8 %x, 6315 call void @llvm.assume(i1 %cmp.x.lower)316 %cmp.x.upper = icmp ult i8 %x, 8317 call void @llvm.assume(i1 %cmp.x.upper)318 %cmp.y.lower = icmp uge i8 %y, 3319 call void @llvm.assume(i1 %cmp.y.lower)320 %cmp.y.upper = icmp ule i8 %y, 4321 call void @llvm.assume(i1 %cmp.y.upper)322 %rem = urem i8 %x, %y323 ret i8 %rem324}325 326; Constant divisor327 328define i8 @large.divisor.v0(i8 %x) {329; CHECK-LABEL: @large.divisor.v0(330; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 127331; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])332; CHECK-NEXT: ret i8 [[X]]333;334 %cmp.x.upper = icmp ult i8 %x, 127335 call void @llvm.assume(i1 %cmp.x.upper)336 %rem = urem i8 %x, 127337 ret i8 %rem338}339define i8 @large.divisor.v1(i8 %x) {340; CHECK-LABEL: @large.divisor.v1(341; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], -128342; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])343; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]344; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 127345; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 127346; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]347; CHECK-NEXT: ret i8 [[REM]]348;349 %cmp.x.upper = icmp ult i8 %x, 128350 call void @llvm.assume(i1 %cmp.x.upper)351 %rem = urem i8 %x, 127352 ret i8 %rem353}354define i8 @large.divisor.v1.range(ptr %x.ptr) {355; CHECK-LABEL: @large.divisor.v1.range(356; CHECK-NEXT: [[X:%.*]] = load i8, ptr [[X_PTR:%.*]], align 1, !range [[RNG2:![0-9]+]]357; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]358; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], 127359; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], 127360; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]361; CHECK-NEXT: ret i8 [[REM]]362;363 %x = load i8, ptr %x.ptr, !range !{ i8 0, i8 128 }364 %rem = urem i8 %x, 127365 ret i8 %rem366}367define i8 @large.divisor.v2.unbound.x(i8 %x) {368; CHECK-LABEL: @large.divisor.v2.unbound.x(369; CHECK-NEXT: [[REM:%.*]] = urem i8 [[X:%.*]], 127370; CHECK-NEXT: ret i8 [[REM]]371;372 %rem = urem i8 %x, 127373 ret i8 %rem374}375 376define i8 @large.divisor.with.overflow.v0(i8 %x) {377; CHECK-LABEL: @large.divisor.with.overflow.v0(378; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], -128379; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])380; CHECK-NEXT: ret i8 [[X]]381;382 %cmp.x.upper = icmp ult i8 %x, 128383 call void @llvm.assume(i1 %cmp.x.upper)384 %rem = urem i8 %x, 128385 ret i8 %rem386}387define i8 @large.divisor.with.overflow.v1(i8 %x) {388; CHECK-LABEL: @large.divisor.with.overflow.v1(389; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], -127390; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])391; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]392; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], -128393; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], -128394; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]395; CHECK-NEXT: ret i8 [[REM]]396;397 %cmp.x.upper = icmp ult i8 %x, 129398 call void @llvm.assume(i1 %cmp.x.upper)399 %rem = urem i8 %x, 128400 ret i8 %rem401}402define i8 @large.divisor.with.overflow.v1.range(ptr %x.ptr) {403; CHECK-LABEL: @large.divisor.with.overflow.v1.range(404; CHECK-NEXT: [[X:%.*]] = load i8, ptr [[X_PTR:%.*]], align 1, !range [[RNG3:![0-9]+]]405; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X]]406; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], -128407; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], -128408; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]409; CHECK-NEXT: ret i8 [[REM]]410;411 %x = load i8, ptr %x.ptr, !range !{ i8 0, i8 129 }412 %rem = urem i8 %x, 128413 ret i8 %rem414}415define i8 @large.divisor.with.overflow.v2.unbound.x(i8 %x) {416; CHECK-LABEL: @large.divisor.with.overflow.v2.unbound.x(417; CHECK-NEXT: [[X_FROZEN:%.*]] = freeze i8 [[X:%.*]]418; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X_FROZEN]], -128419; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X_FROZEN]], -128420; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X_FROZEN]], i8 [[REM_UREM]]421; CHECK-NEXT: ret i8 [[REM]]422;423 %rem = urem i8 %x, 128424 ret i8 %rem425}426 427define i1 @icmp_after_expansion(i8 noundef %x) {428; CHECK-LABEL: @icmp_after_expansion(429; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 6430; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])431; CHECK-NEXT: [[REM_UREM:%.*]] = sub nuw i8 [[X]], 3432; CHECK-NEXT: [[REM_CMP:%.*]] = icmp ult i8 [[X]], 3433; CHECK-NEXT: [[REM:%.*]] = select i1 [[REM_CMP]], i8 [[X]], i8 [[REM_UREM]]434; CHECK-NEXT: ret i1 false435;436 %cmp.x.upper = icmp ult i8 %x, 6437 call void @llvm.assume(i1 %cmp.x.upper)438 %rem = urem i8 %x, 3439 %cmp = icmp eq i8 %rem, 3440 ret i1 %cmp441}442 443define i8 @known_uge(i8 noundef %x) {444; CHECK-LABEL: @known_uge(445; CHECK-NEXT: [[CMP_X_UPPER:%.*]] = icmp ult i8 [[X:%.*]], 6446; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_UPPER]])447; CHECK-NEXT: [[CMP_X_LOWER:%.*]] = icmp samesign uge i8 [[X]], 3448; CHECK-NEXT: call void @llvm.assume(i1 [[CMP_X_LOWER]])449; CHECK-NEXT: [[REM:%.*]] = sub nuw i8 [[X]], 3450; CHECK-NEXT: ret i8 [[REM]]451;452 %cmp.x.upper = icmp ult i8 %x, 6453 call void @llvm.assume(i1 %cmp.x.upper)454 %cmp.x.lower = icmp uge i8 %x, 3455 call void @llvm.assume(i1 %cmp.x.lower)456 %rem = urem i8 %x, 3457 ret i8 %rem458}459