339 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; Check that a division is bypassed when appropriate only.3; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=atom < %s | FileCheck -check-prefixes=CHECK,ATOM %s4; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=x86-64 < %s | FileCheck -check-prefixes=CHECK,REST,X64 %s5; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=silvermont < %s | FileCheck -check-prefixes=CHECK,REST,SLM %s6; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=skylake < %s | FileCheck -check-prefixes=CHECK,REST,SKL %s7; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=goldmont < %s | FileCheck -check-prefixes=CHECK,REST,GMT %s8; RUN: llc -mtriple=x86_64-unknown-linux-gnu -mcpu=gracemont < %s | FileCheck -check-prefixes=CHECK,REST,GMT %s9; RUN: llc -profile-summary-huge-working-set-size-threshold=1 -mtriple=x86_64-unknown-linux-gnu -mcpu=skylake < %s | FileCheck -check-prefixes=HUGEWS %s10 11; Verify that div32 is bypassed only for Atoms.12define i32 @div32(i32 %a, i32 %b) {13; ATOM-LABEL: div32:14; ATOM: # %bb.0: # %entry15; ATOM-NEXT: movl %edi, %eax16; ATOM-NEXT: orl %esi, %eax17; ATOM-NEXT: testl $-256, %eax18; ATOM-NEXT: je .LBB0_119; ATOM-NEXT: # %bb.2:20; ATOM-NEXT: movl %edi, %eax21; ATOM-NEXT: cltd22; ATOM-NEXT: idivl %esi23; ATOM-NEXT: retq24; ATOM-NEXT: .LBB0_1:25; ATOM-NEXT: movzbl %dil, %eax26; ATOM-NEXT: divb %sil27; ATOM-NEXT: movzbl %al, %eax28; ATOM-NEXT: retq29;30; REST-LABEL: div32:31; REST: # %bb.0: # %entry32; REST-NEXT: movl %edi, %eax33; REST-NEXT: cltd34; REST-NEXT: idivl %esi35; REST-NEXT: retq36;37; HUGEWS-LABEL: div32:38; HUGEWS: # %bb.0: # %entry39; HUGEWS-NEXT: movl %edi, %eax40; HUGEWS-NEXT: cltd41; HUGEWS-NEXT: idivl %esi42; HUGEWS-NEXT: retq43entry:44 %div = sdiv i32 %a, %b45 ret i32 %div46}47 48; Verify that div64 is always bypassed.49define i64 @div64(i64 %a, i64 %b) {50; ATOM-LABEL: div64:51; ATOM: # %bb.0: # %entry52; ATOM-NEXT: movq %rdi, %rcx53; ATOM-NEXT: movq %rdi, %rax54; ATOM-NEXT: orq %rsi, %rcx55; ATOM-NEXT: shrq $32, %rcx56; ATOM-NEXT: je .LBB1_157; ATOM-NEXT: # %bb.2:58; ATOM-NEXT: cqto59; ATOM-NEXT: idivq %rsi60; ATOM-NEXT: retq61; ATOM-NEXT: .LBB1_1:62; ATOM-NEXT: # kill: def $eax killed $eax killed $rax63; ATOM-NEXT: xorl %edx, %edx64; ATOM-NEXT: divl %esi65; ATOM-NEXT: # kill: def $eax killed $eax def $rax66; ATOM-NEXT: retq67;68; X64-LABEL: div64:69; X64: # %bb.0: # %entry70; X64-NEXT: movq %rdi, %rax71; X64-NEXT: movq %rdi, %rcx72; X64-NEXT: orq %rsi, %rcx73; X64-NEXT: shrq $32, %rcx74; X64-NEXT: je .LBB1_175; X64-NEXT: # %bb.2:76; X64-NEXT: cqto77; X64-NEXT: idivq %rsi78; X64-NEXT: retq79; X64-NEXT: .LBB1_1:80; X64-NEXT: # kill: def $eax killed $eax killed $rax81; X64-NEXT: xorl %edx, %edx82; X64-NEXT: divl %esi83; X64-NEXT: # kill: def $eax killed $eax def $rax84; X64-NEXT: retq85;86; SLM-LABEL: div64:87; SLM: # %bb.0: # %entry88; SLM-NEXT: movq %rdi, %rcx89; SLM-NEXT: movq %rdi, %rax90; SLM-NEXT: orq %rsi, %rcx91; SLM-NEXT: shrq $32, %rcx92; SLM-NEXT: je .LBB1_193; SLM-NEXT: # %bb.2:94; SLM-NEXT: cqto95; SLM-NEXT: idivq %rsi96; SLM-NEXT: retq97; SLM-NEXT: .LBB1_1:98; SLM-NEXT: xorl %edx, %edx99; SLM-NEXT: # kill: def $eax killed $eax killed $rax100; SLM-NEXT: divl %esi101; SLM-NEXT: # kill: def $eax killed $eax def $rax102; SLM-NEXT: retq103;104; SKL-LABEL: div64:105; SKL: # %bb.0: # %entry106; SKL-NEXT: movq %rdi, %rax107; SKL-NEXT: movq %rdi, %rcx108; SKL-NEXT: orq %rsi, %rcx109; SKL-NEXT: shrq $32, %rcx110; SKL-NEXT: je .LBB1_1111; SKL-NEXT: # %bb.2:112; SKL-NEXT: cqto113; SKL-NEXT: idivq %rsi114; SKL-NEXT: retq115; SKL-NEXT: .LBB1_1:116; SKL-NEXT: # kill: def $eax killed $eax killed $rax117; SKL-NEXT: xorl %edx, %edx118; SKL-NEXT: divl %esi119; SKL-NEXT: # kill: def $eax killed $eax def $rax120; SKL-NEXT: retq121;122; GMT-LABEL: div64:123; GMT: # %bb.0: # %entry124; GMT-NEXT: movq %rdi, %rax125; GMT-NEXT: cqto126; GMT-NEXT: idivq %rsi127; GMT-NEXT: retq128;129; HUGEWS-LABEL: div64:130; HUGEWS: # %bb.0: # %entry131; HUGEWS-NEXT: movq %rdi, %rax132; HUGEWS-NEXT: cqto133; HUGEWS-NEXT: idivq %rsi134; HUGEWS-NEXT: retq135entry:136 %div = sdiv i64 %a, %b137 ret i64 %div138}139 140 141; Verify that no extra code is generated when optimizing for size.142 143define i64 @div64_optsize(i64 %a, i64 %b) optsize {144; CHECK-LABEL: div64_optsize:145; CHECK: # %bb.0:146; CHECK-NEXT: movq %rdi, %rax147; CHECK-NEXT: cqto148; CHECK-NEXT: idivq %rsi149; CHECK-NEXT: retq150;151; HUGEWS-LABEL: div64_optsize:152; HUGEWS: # %bb.0:153; HUGEWS-NEXT: movq %rdi, %rax154; HUGEWS-NEXT: cqto155; HUGEWS-NEXT: idivq %rsi156; HUGEWS-NEXT: retq157 %div = sdiv i64 %a, %b158 ret i64 %div159}160 161define i64 @div64_pgso(i64 %a, i64 %b) !prof !15 {162; CHECK-LABEL: div64_pgso:163; CHECK: # %bb.0:164; CHECK-NEXT: movq %rdi, %rax165; CHECK-NEXT: cqto166; CHECK-NEXT: idivq %rsi167; CHECK-NEXT: retq168;169; HUGEWS-LABEL: div64_pgso:170; HUGEWS: # %bb.0:171; HUGEWS-NEXT: movq %rdi, %rax172; HUGEWS-NEXT: cqto173; HUGEWS-NEXT: idivq %rsi174; HUGEWS-NEXT: retq175 %div = sdiv i64 %a, %b176 ret i64 %div177}178 179define i64 @div64_hugews(i64 %a, i64 %b) {180; ATOM-LABEL: div64_hugews:181; ATOM: # %bb.0:182; ATOM-NEXT: movq %rdi, %rcx183; ATOM-NEXT: movq %rdi, %rax184; ATOM-NEXT: orq %rsi, %rcx185; ATOM-NEXT: shrq $32, %rcx186; ATOM-NEXT: je .LBB4_1187; ATOM-NEXT: # %bb.2:188; ATOM-NEXT: cqto189; ATOM-NEXT: idivq %rsi190; ATOM-NEXT: retq191; ATOM-NEXT: .LBB4_1:192; ATOM-NEXT: # kill: def $eax killed $eax killed $rax193; ATOM-NEXT: xorl %edx, %edx194; ATOM-NEXT: divl %esi195; ATOM-NEXT: # kill: def $eax killed $eax def $rax196; ATOM-NEXT: retq197;198; X64-LABEL: div64_hugews:199; X64: # %bb.0:200; X64-NEXT: movq %rdi, %rax201; X64-NEXT: movq %rdi, %rcx202; X64-NEXT: orq %rsi, %rcx203; X64-NEXT: shrq $32, %rcx204; X64-NEXT: je .LBB4_1205; X64-NEXT: # %bb.2:206; X64-NEXT: cqto207; X64-NEXT: idivq %rsi208; X64-NEXT: retq209; X64-NEXT: .LBB4_1:210; X64-NEXT: # kill: def $eax killed $eax killed $rax211; X64-NEXT: xorl %edx, %edx212; X64-NEXT: divl %esi213; X64-NEXT: # kill: def $eax killed $eax def $rax214; X64-NEXT: retq215;216; SLM-LABEL: div64_hugews:217; SLM: # %bb.0:218; SLM-NEXT: movq %rdi, %rcx219; SLM-NEXT: movq %rdi, %rax220; SLM-NEXT: orq %rsi, %rcx221; SLM-NEXT: shrq $32, %rcx222; SLM-NEXT: je .LBB4_1223; SLM-NEXT: # %bb.2:224; SLM-NEXT: cqto225; SLM-NEXT: idivq %rsi226; SLM-NEXT: retq227; SLM-NEXT: .LBB4_1:228; SLM-NEXT: xorl %edx, %edx229; SLM-NEXT: # kill: def $eax killed $eax killed $rax230; SLM-NEXT: divl %esi231; SLM-NEXT: # kill: def $eax killed $eax def $rax232; SLM-NEXT: retq233;234; SKL-LABEL: div64_hugews:235; SKL: # %bb.0:236; SKL-NEXT: movq %rdi, %rax237; SKL-NEXT: movq %rdi, %rcx238; SKL-NEXT: orq %rsi, %rcx239; SKL-NEXT: shrq $32, %rcx240; SKL-NEXT: je .LBB4_1241; SKL-NEXT: # %bb.2:242; SKL-NEXT: cqto243; SKL-NEXT: idivq %rsi244; SKL-NEXT: retq245; SKL-NEXT: .LBB4_1:246; SKL-NEXT: # kill: def $eax killed $eax killed $rax247; SKL-NEXT: xorl %edx, %edx248; SKL-NEXT: divl %esi249; SKL-NEXT: # kill: def $eax killed $eax def $rax250; SKL-NEXT: retq251;252; GMT-LABEL: div64_hugews:253; GMT: # %bb.0:254; GMT-NEXT: movq %rdi, %rax255; GMT-NEXT: cqto256; GMT-NEXT: idivq %rsi257; GMT-NEXT: retq258;259; HUGEWS-LABEL: div64_hugews:260; HUGEWS: # %bb.0:261; HUGEWS-NEXT: movq %rdi, %rax262; HUGEWS-NEXT: cqto263; HUGEWS-NEXT: idivq %rsi264; HUGEWS-NEXT: retq265 %div = sdiv i64 %a, %b266 ret i64 %div267}268 269define i32 @div32_optsize(i32 %a, i32 %b) optsize {270; CHECK-LABEL: div32_optsize:271; CHECK: # %bb.0:272; CHECK-NEXT: movl %edi, %eax273; CHECK-NEXT: cltd274; CHECK-NEXT: idivl %esi275; CHECK-NEXT: retq276;277; HUGEWS-LABEL: div32_optsize:278; HUGEWS: # %bb.0:279; HUGEWS-NEXT: movl %edi, %eax280; HUGEWS-NEXT: cltd281; HUGEWS-NEXT: idivl %esi282; HUGEWS-NEXT: retq283 %div = sdiv i32 %a, %b284 ret i32 %div285}286 287define i32 @div32_pgso(i32 %a, i32 %b) !prof !15 {288; CHECK-LABEL: div32_pgso:289; CHECK: # %bb.0:290; CHECK-NEXT: movl %edi, %eax291; CHECK-NEXT: cltd292; CHECK-NEXT: idivl %esi293; CHECK-NEXT: retq294;295; HUGEWS-LABEL: div32_pgso:296; HUGEWS: # %bb.0:297; HUGEWS-NEXT: movl %edi, %eax298; HUGEWS-NEXT: cltd299; HUGEWS-NEXT: idivl %esi300; HUGEWS-NEXT: retq301 %div = sdiv i32 %a, %b302 ret i32 %div303}304 305define i32 @div32_minsize(i32 %a, i32 %b) minsize {306; CHECK-LABEL: div32_minsize:307; CHECK: # %bb.0:308; CHECK-NEXT: movl %edi, %eax309; CHECK-NEXT: cltd310; CHECK-NEXT: idivl %esi311; CHECK-NEXT: retq312;313; HUGEWS-LABEL: div32_minsize:314; HUGEWS: # %bb.0:315; HUGEWS-NEXT: movl %edi, %eax316; HUGEWS-NEXT: cltd317; HUGEWS-NEXT: idivl %esi318; HUGEWS-NEXT: retq319 %div = sdiv i32 %a, %b320 ret i32 %div321}322 323!llvm.module.flags = !{!1}324!1 = !{i32 1, !"ProfileSummary", !2}325!2 = !{!3, !4, !5, !6, !7, !8, !9, !10}326!3 = !{!"ProfileFormat", !"InstrProf"}327!4 = !{!"TotalCount", i64 10000}328!5 = !{!"MaxCount", i64 1000}329!6 = !{!"MaxInternalCount", i64 1}330!7 = !{!"MaxFunctionCount", i64 1000}331!8 = !{!"NumCounts", i64 3}332!9 = !{!"NumFunctions", i64 3}333!10 = !{!"DetailedSummary", !11}334!11 = !{!12, !13, !14}335!12 = !{i32 10000, i64 1000, i32 1}336!13 = !{i32 999000, i64 1000, i32 3}337!14 = !{i32 999999, i64 5, i32 3}338!15 = !{!"function_entry_count", i64 0}339