1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 2; RUN: llc < %s -stackrealign -mtriple i386-apple-darwin -mcpu=i486 | FileCheck %s 3 4%struct.foo = type { [88 x i8] } 5 6declare void @bar(ptr nocapture, ptr align 4 byval(%struct.foo)) nounwind 7declare void @baz(ptr) nounwind 8 9; PR15249 10; We can't use rep;movsl here because it clobbers the base pointer in %esi. 11define void @test1(ptr nocapture %x, i32 %y) nounwind { 12; CHECK-LABEL: test1: 13; CHECK: ## %bb.0: 14; CHECK-NEXT: pushl %ebp 15; CHECK-NEXT: movl %esp, %ebp 16; CHECK-NEXT: pushl %ebx 17; CHECK-NEXT: pushl %edi 18; CHECK-NEXT: pushl %esi 19; CHECK-NEXT: andl $-16, %esp 20; CHECK-NEXT: subl $80, %esp 21; CHECK-NEXT: movl %esp, %esi 22; CHECK-NEXT: movl 8(%ebp), %ecx 23; CHECK-NEXT: movl 12(%ebp), %edx 24; CHECK-NEXT: movl %esp, %eax 25; CHECK-NEXT: addl $15, %edx 26; CHECK-NEXT: andl $-16, %edx 27; CHECK-NEXT: subl %edx, %eax 28; CHECK-NEXT: movl %eax, %esp 29; CHECK-NEXT: subl $4, %esp 30; CHECK-NEXT: movl 84(%ecx), %edi 31; CHECK-NEXT: movl 80(%ecx), %ebx 32; CHECK-NEXT: movl 76(%ecx), %edx 33; CHECK-NEXT: movl %edx, 68(%esi) ## 4-byte Spill 34; CHECK-NEXT: movl 72(%ecx), %edx 35; CHECK-NEXT: movl %edx, 64(%esi) ## 4-byte Spill 36; CHECK-NEXT: movl 68(%ecx), %edx 37; CHECK-NEXT: movl %edx, 60(%esi) ## 4-byte Spill 38; CHECK-NEXT: movl 64(%ecx), %edx 39; CHECK-NEXT: movl %edx, 56(%esi) ## 4-byte Spill 40; CHECK-NEXT: movl 60(%ecx), %edx 41; CHECK-NEXT: movl %edx, 52(%esi) ## 4-byte Spill 42; CHECK-NEXT: movl 56(%ecx), %edx 43; CHECK-NEXT: movl %edx, 48(%esi) ## 4-byte Spill 44; CHECK-NEXT: movl 52(%ecx), %edx 45; CHECK-NEXT: movl %edx, 44(%esi) ## 4-byte Spill 46; CHECK-NEXT: movl 48(%ecx), %edx 47; CHECK-NEXT: movl %edx, 40(%esi) ## 4-byte Spill 48; CHECK-NEXT: movl 44(%ecx), %edx 49; CHECK-NEXT: movl %edx, 36(%esi) ## 4-byte Spill 50; CHECK-NEXT: movl 40(%ecx), %edx 51; CHECK-NEXT: movl %edx, 32(%esi) ## 4-byte Spill 52; CHECK-NEXT: movl 36(%ecx), %edx 53; CHECK-NEXT: movl %edx, 28(%esi) ## 4-byte Spill 54; CHECK-NEXT: movl 32(%ecx), %edx 55; CHECK-NEXT: movl %edx, 24(%esi) ## 4-byte Spill 56; CHECK-NEXT: movl 28(%ecx), %edx 57; CHECK-NEXT: movl %edx, 20(%esi) ## 4-byte Spill 58; CHECK-NEXT: movl 24(%ecx), %edx 59; CHECK-NEXT: movl %edx, 16(%esi) ## 4-byte Spill 60; CHECK-NEXT: movl 20(%ecx), %edx 61; CHECK-NEXT: movl %edx, 12(%esi) ## 4-byte Spill 62; CHECK-NEXT: movl 16(%ecx), %edx 63; CHECK-NEXT: movl %edx, 8(%esi) ## 4-byte Spill 64; CHECK-NEXT: movl 12(%ecx), %edx 65; CHECK-NEXT: movl %edx, 4(%esi) ## 4-byte Spill 66; CHECK-NEXT: movl 8(%ecx), %edx 67; CHECK-NEXT: movl %edx, (%esi) ## 4-byte Spill 68; CHECK-NEXT: movl (%ecx), %edx 69; CHECK-NEXT: movl %edx, 72(%esi) ## 4-byte Spill 70; CHECK-NEXT: movl 4(%ecx), %ecx 71; CHECK-NEXT: pushl %edi 72; CHECK-NEXT: pushl %ebx 73; CHECK-NEXT: pushl 68(%esi) ## 4-byte Folded Reload 74; CHECK-NEXT: pushl 64(%esi) ## 4-byte Folded Reload 75; CHECK-NEXT: pushl 60(%esi) ## 4-byte Folded Reload 76; CHECK-NEXT: pushl 56(%esi) ## 4-byte Folded Reload 77; CHECK-NEXT: pushl 52(%esi) ## 4-byte Folded Reload 78; CHECK-NEXT: pushl 48(%esi) ## 4-byte Folded Reload 79; CHECK-NEXT: pushl 44(%esi) ## 4-byte Folded Reload 80; CHECK-NEXT: pushl 40(%esi) ## 4-byte Folded Reload 81; CHECK-NEXT: pushl 36(%esi) ## 4-byte Folded Reload 82; CHECK-NEXT: pushl 32(%esi) ## 4-byte Folded Reload 83; CHECK-NEXT: pushl 28(%esi) ## 4-byte Folded Reload 84; CHECK-NEXT: pushl 24(%esi) ## 4-byte Folded Reload 85; CHECK-NEXT: pushl 20(%esi) ## 4-byte Folded Reload 86; CHECK-NEXT: pushl 16(%esi) ## 4-byte Folded Reload 87; CHECK-NEXT: pushl 12(%esi) ## 4-byte Folded Reload 88; CHECK-NEXT: pushl 8(%esi) ## 4-byte Folded Reload 89; CHECK-NEXT: pushl 4(%esi) ## 4-byte Folded Reload 90; CHECK-NEXT: pushl (%esi) ## 4-byte Folded Reload 91; CHECK-NEXT: pushl %ecx 92; CHECK-NEXT: pushl 72(%esi) ## 4-byte Folded Reload 93; CHECK-NEXT: pushl %eax 94; CHECK-NEXT: calll _bar 95; CHECK-NEXT: leal -12(%ebp), %esp 96; CHECK-NEXT: popl %esi 97; CHECK-NEXT: popl %edi 98; CHECK-NEXT: popl %ebx 99; CHECK-NEXT: popl %ebp 100; CHECK-NEXT: retl 101 %dynalloc = alloca i8, i32 %y, align 1 102 call void @bar(ptr %dynalloc, ptr align 4 byval(%struct.foo) %x) 103 ret void 104} 105 106; PR19012 107; Also don't clobber %esi if the dynamic alloca comes after the memcpy. 108define void @test2(ptr nocapture %x, i32 %y, ptr %z) nounwind { 109; CHECK-LABEL: test2: 110; CHECK: ## %bb.0: 111; CHECK-NEXT: pushl %ebp 112; CHECK-NEXT: movl %esp, %ebp 113; CHECK-NEXT: pushl %ebx 114; CHECK-NEXT: pushl %edi 115; CHECK-NEXT: pushl %esi 116; CHECK-NEXT: andl $-16, %esp 117; CHECK-NEXT: subl $80, %esp 118; CHECK-NEXT: movl %esp, %esi 119; CHECK-NEXT: movl 12(%ebp), %edi 120; CHECK-NEXT: movl 8(%ebp), %eax 121; CHECK-NEXT: subl $4, %esp 122; CHECK-NEXT: movl 84(%eax), %edx 123; CHECK-NEXT: movl 80(%eax), %ebx 124; CHECK-NEXT: movl 76(%eax), %ecx 125; CHECK-NEXT: movl %ecx, 68(%esi) ## 4-byte Spill 126; CHECK-NEXT: movl 72(%eax), %ecx 127; CHECK-NEXT: movl %ecx, 64(%esi) ## 4-byte Spill 128; CHECK-NEXT: movl 68(%eax), %ecx 129; CHECK-NEXT: movl %ecx, 60(%esi) ## 4-byte Spill 130; CHECK-NEXT: movl 64(%eax), %ecx 131; CHECK-NEXT: movl %ecx, 56(%esi) ## 4-byte Spill 132; CHECK-NEXT: movl 60(%eax), %ecx 133; CHECK-NEXT: movl %ecx, 52(%esi) ## 4-byte Spill 134; CHECK-NEXT: movl 56(%eax), %ecx 135; CHECK-NEXT: movl %ecx, 48(%esi) ## 4-byte Spill 136; CHECK-NEXT: movl 52(%eax), %ecx 137; CHECK-NEXT: movl %ecx, 44(%esi) ## 4-byte Spill 138; CHECK-NEXT: movl 48(%eax), %ecx 139; CHECK-NEXT: movl %ecx, 40(%esi) ## 4-byte Spill 140; CHECK-NEXT: movl 44(%eax), %ecx 141; CHECK-NEXT: movl %ecx, 36(%esi) ## 4-byte Spill 142; CHECK-NEXT: movl 40(%eax), %ecx 143; CHECK-NEXT: movl %ecx, 32(%esi) ## 4-byte Spill 144; CHECK-NEXT: movl 36(%eax), %ecx 145; CHECK-NEXT: movl %ecx, 28(%esi) ## 4-byte Spill 146; CHECK-NEXT: movl 32(%eax), %ecx 147; CHECK-NEXT: movl %ecx, 24(%esi) ## 4-byte Spill 148; CHECK-NEXT: movl 28(%eax), %ecx 149; CHECK-NEXT: movl %ecx, 20(%esi) ## 4-byte Spill 150; CHECK-NEXT: movl 24(%eax), %ecx 151; CHECK-NEXT: movl %ecx, 16(%esi) ## 4-byte Spill 152; CHECK-NEXT: movl 20(%eax), %ecx 153; CHECK-NEXT: movl %ecx, 12(%esi) ## 4-byte Spill 154; CHECK-NEXT: movl 16(%eax), %ecx 155; CHECK-NEXT: movl %ecx, 8(%esi) ## 4-byte Spill 156; CHECK-NEXT: movl 12(%eax), %ecx 157; CHECK-NEXT: movl %ecx, 4(%esi) ## 4-byte Spill 158; CHECK-NEXT: movl 8(%eax), %ecx 159; CHECK-NEXT: movl %ecx, (%esi) ## 4-byte Spill 160; CHECK-NEXT: movl (%eax), %ecx 161; CHECK-NEXT: movl %ecx, 72(%esi) ## 4-byte Spill 162; CHECK-NEXT: movl 4(%eax), %eax 163; CHECK-NEXT: pushl %edx 164; CHECK-NEXT: pushl %ebx 165; CHECK-NEXT: pushl 68(%esi) ## 4-byte Folded Reload 166; CHECK-NEXT: pushl 64(%esi) ## 4-byte Folded Reload 167; CHECK-NEXT: pushl 60(%esi) ## 4-byte Folded Reload 168; CHECK-NEXT: pushl 56(%esi) ## 4-byte Folded Reload 169; CHECK-NEXT: pushl 52(%esi) ## 4-byte Folded Reload 170; CHECK-NEXT: pushl 48(%esi) ## 4-byte Folded Reload 171; CHECK-NEXT: pushl 44(%esi) ## 4-byte Folded Reload 172; CHECK-NEXT: pushl 40(%esi) ## 4-byte Folded Reload 173; CHECK-NEXT: pushl 36(%esi) ## 4-byte Folded Reload 174; CHECK-NEXT: pushl 32(%esi) ## 4-byte Folded Reload 175; CHECK-NEXT: pushl 28(%esi) ## 4-byte Folded Reload 176; CHECK-NEXT: pushl 24(%esi) ## 4-byte Folded Reload 177; CHECK-NEXT: pushl 20(%esi) ## 4-byte Folded Reload 178; CHECK-NEXT: pushl 16(%esi) ## 4-byte Folded Reload 179; CHECK-NEXT: pushl 12(%esi) ## 4-byte Folded Reload 180; CHECK-NEXT: pushl 8(%esi) ## 4-byte Folded Reload 181; CHECK-NEXT: pushl 4(%esi) ## 4-byte Folded Reload 182; CHECK-NEXT: pushl (%esi) ## 4-byte Folded Reload 183; CHECK-NEXT: pushl %eax 184; CHECK-NEXT: pushl 72(%esi) ## 4-byte Folded Reload 185; CHECK-NEXT: pushl 16(%ebp) 186; CHECK-NEXT: calll _bar 187; CHECK-NEXT: addl $96, %esp 188; CHECK-NEXT: movl %esp, %eax 189; CHECK-NEXT: addl $15, %edi 190; CHECK-NEXT: andl $-16, %edi 191; CHECK-NEXT: subl %edi, %eax 192; CHECK-NEXT: movl %eax, %esp 193; CHECK-NEXT: subl $12, %esp 194; CHECK-NEXT: pushl %eax 195; CHECK-NEXT: calll _baz 196; CHECK-NEXT: leal -12(%ebp), %esp 197; CHECK-NEXT: popl %esi 198; CHECK-NEXT: popl %edi 199; CHECK-NEXT: popl %ebx 200; CHECK-NEXT: popl %ebp 201; CHECK-NEXT: retl 202 call void @bar(ptr %z, ptr align 4 byval(%struct.foo) %x) 203 %dynalloc = alloca i8, i32 %y, align 1 204 call void @baz(ptr %dynalloc) 205 ret void 206} 207 208; Check that we do use rep movs if we make the alloca static. 209define void @test3(ptr nocapture %x, i32 %y, ptr %z) nounwind { 210; CHECK-LABEL: test3: 211; CHECK: ## %bb.0: 212; CHECK-NEXT: pushl %ebp 213; CHECK-NEXT: movl %esp, %ebp 214; CHECK-NEXT: pushl %edi 215; CHECK-NEXT: pushl %esi 216; CHECK-NEXT: andl $-16, %esp 217; CHECK-NEXT: subl $112, %esp 218; CHECK-NEXT: movl 16(%ebp), %eax 219; CHECK-NEXT: movl 8(%ebp), %esi 220; CHECK-NEXT: leal {{[0-9]+}}(%esp), %edi 221; CHECK-NEXT: movl $22, %ecx 222; CHECK-NEXT: rep;movsl (%esi), %es:(%edi) 223; CHECK-NEXT: movl %eax, (%esp) 224; CHECK-NEXT: calll _bar 225; CHECK-NEXT: leal {{[0-9]+}}(%esp), %eax 226; CHECK-NEXT: movl %eax, (%esp) 227; CHECK-NEXT: calll _baz 228; CHECK-NEXT: leal -8(%ebp), %esp 229; CHECK-NEXT: popl %esi 230; CHECK-NEXT: popl %edi 231; CHECK-NEXT: popl %ebp 232; CHECK-NEXT: retl 233 call void @bar(ptr %z, ptr align 4 byval(%struct.foo) %x) 234 %statalloc = alloca i8, i32 8, align 1 235 call void @baz(ptr %statalloc) 236 ret void 237} 238