1; RUN: llc < %s -O0 -march=x86-64 -mcpu=corei7 -verify-machineinstrs | FileCheck %s --check-prefix X64 2; RUN: llc < %s -O0 -march=x86 -mcpu=corei7 -verify-machineinstrs | FileCheck %s --check-prefix X32 3; RUN: llc < %s -O0 -march=x86 -mcpu=corei7 -mattr=-cmov -verify-machineinstrs | FileCheck %s --check-prefix NOCMOV 4 5@sc32 = external global i32 6 7define void @atomic_fetch_add32() nounwind { 8; X64-LABEL: atomic_fetch_add32: 9; X32-LABEL: atomic_fetch_add32: 10entry: 11; 32-bit 12 %t1 = atomicrmw add i32* @sc32, i32 1 acquire 13; X64: lock 14; X64: incl 15; X32: lock 16; X32: incl 17 %t2 = atomicrmw add i32* @sc32, i32 3 acquire 18; X64: lock 19; X64: addl $3 20; X32: lock 21; X32: addl $3 22 %t3 = atomicrmw add i32* @sc32, i32 5 acquire 23; X64: lock 24; X64: xaddl 25; X32: lock 26; X32: xaddl 27 %t4 = atomicrmw add i32* @sc32, i32 %t3 acquire 28; X64: lock 29; X64: addl 30; X32: lock 31; X32: addl 32 ret void 33; X64: ret 34; X32: ret 35} 36 37define void @atomic_fetch_sub32() nounwind { 38; X64-LABEL: atomic_fetch_sub32: 39; X32-LABEL: atomic_fetch_sub32: 40 %t1 = atomicrmw sub i32* @sc32, i32 1 acquire 41; X64: lock 42; X64: decl 43; X32: lock 44; X32: decl 45 %t2 = atomicrmw sub i32* @sc32, i32 3 acquire 46; X64: lock 47; X64: subl $3 48; X32: lock 49; X32: subl $3 50 %t3 = atomicrmw sub i32* @sc32, i32 5 acquire 51; X64: lock 52; X64: xaddl 53; X32: lock 54; X32: xaddl 55 %t4 = atomicrmw sub i32* @sc32, i32 %t3 acquire 56; X64: lock 57; X64: subl 58; X32: lock 59; X32: subl 60 ret void 61; X64: ret 62; X32: ret 63} 64 65define void @atomic_fetch_and32() nounwind { 66; X64-LABEL: atomic_fetch_and32: 67; X32-LABEL: atomic_fetch_and32: 68 %t1 = atomicrmw and i32* @sc32, i32 3 acquire 69; X64: lock 70; X64: andl $3 71; X32: lock 72; X32: andl $3 73 %t2 = atomicrmw and i32* @sc32, i32 5 acquire 74; X64: andl 75; X64: lock 76; X64: cmpxchgl 77; X32: andl 78; X32: lock 79; X32: cmpxchgl 80 %t3 = atomicrmw and i32* @sc32, i32 %t2 acquire 81; X64: lock 82; X64: andl 83; X32: lock 84; X32: andl 85 ret void 86; X64: ret 87; X32: ret 88} 89 90define void @atomic_fetch_or32() nounwind { 91; X64-LABEL: atomic_fetch_or32: 92; X32-LABEL: atomic_fetch_or32: 93 %t1 = atomicrmw or i32* @sc32, i32 3 acquire 94; X64: lock 95; X64: orl $3 96; X32: lock 97; X32: orl $3 98 %t2 = atomicrmw or i32* @sc32, i32 5 acquire 99; X64: orl 100; X64: lock 101; X64: cmpxchgl 102; X32: orl 103; X32: lock 104; X32: cmpxchgl 105 %t3 = atomicrmw or i32* @sc32, i32 %t2 acquire 106; X64: lock 107; X64: orl 108; X32: lock 109; X32: orl 110 ret void 111; X64: ret 112; X32: ret 113} 114 115define void @atomic_fetch_xor32() nounwind { 116; X64-LABEL: atomic_fetch_xor32: 117; X32-LABEL: atomic_fetch_xor32: 118 %t1 = atomicrmw xor i32* @sc32, i32 3 acquire 119; X64: lock 120; X64: xorl $3 121; X32: lock 122; X32: xorl $3 123 %t2 = atomicrmw xor i32* @sc32, i32 5 acquire 124; X64: xorl 125; X64: lock 126; X64: cmpxchgl 127; X32: xorl 128; X32: lock 129; X32: cmpxchgl 130 %t3 = atomicrmw xor i32* @sc32, i32 %t2 acquire 131; X64: lock 132; X64: xorl 133; X32: lock 134; X32: xorl 135 ret void 136; X64: ret 137; X32: ret 138} 139 140define void @atomic_fetch_nand32(i32 %x) nounwind { 141; X64-LABEL: atomic_fetch_nand32: 142; X32-LABEL: atomic_fetch_nand32: 143 %t1 = atomicrmw nand i32* @sc32, i32 %x acquire 144; X64: andl 145; X64: notl 146; X64: lock 147; X64: cmpxchgl 148; X32: andl 149; X32: notl 150; X32: lock 151; X32: cmpxchgl 152 ret void 153; X64: ret 154; X32: ret 155} 156 157define void @atomic_fetch_max32(i32 %x) nounwind { 158; X64-LABEL: atomic_fetch_max32: 159; X32-LABEL: atomic_fetch_max32: 160 161 %t1 = atomicrmw max i32* @sc32, i32 %x acquire 162; X64: subl 163; X64: cmov 164; X64: lock 165; X64: cmpxchgl 166 167; X32: subl 168; X32: cmov 169; X32: lock 170; X32: cmpxchgl 171 172; NOCMOV: subl 173; NOCMOV: jge 174; NOCMOV: lock 175; NOCMOV: cmpxchgl 176 ret void 177; X64: ret 178; X32: ret 179; NOCMOV: ret 180} 181 182define void @atomic_fetch_min32(i32 %x) nounwind { 183; X64-LABEL: atomic_fetch_min32: 184; X32-LABEL: atomic_fetch_min32: 185; NOCMOV-LABEL: atomic_fetch_min32: 186 187 %t1 = atomicrmw min i32* @sc32, i32 %x acquire 188; X64: subl 189; X64: cmov 190; X64: lock 191; X64: cmpxchgl 192 193; X32: subl 194; X32: cmov 195; X32: lock 196; X32: cmpxchgl 197 198; NOCMOV: subl 199; NOCMOV: jle 200; NOCMOV: lock 201; NOCMOV: cmpxchgl 202 ret void 203; X64: ret 204; X32: ret 205; NOCMOV: ret 206} 207 208define void @atomic_fetch_umax32(i32 %x) nounwind { 209; X64-LABEL: atomic_fetch_umax32: 210; X32-LABEL: atomic_fetch_umax32: 211; NOCMOV-LABEL: atomic_fetch_umax32: 212 213 %t1 = atomicrmw umax i32* @sc32, i32 %x acquire 214; X64: subl 215; X64: cmov 216; X64: lock 217; X64: cmpxchgl 218 219; X32: subl 220; X32: cmov 221; X32: lock 222; X32: cmpxchgl 223 224; NOCMOV: subl 225; NOCMOV: ja 226; NOCMOV: lock 227; NOCMOV: cmpxchgl 228 ret void 229; X64: ret 230; X32: ret 231; NOCMOV: ret 232} 233 234define void @atomic_fetch_umin32(i32 %x) nounwind { 235; X64-LABEL: atomic_fetch_umin32: 236; X32-LABEL: atomic_fetch_umin32: 237; NOCMOV-LABEL: atomic_fetch_umin32: 238 239 %t1 = atomicrmw umin i32* @sc32, i32 %x acquire 240; X64: subl 241; X64: cmov 242; X64: lock 243; X64: cmpxchgl 244 245; X32: subl 246; X32: cmov 247; X32: lock 248; X32: cmpxchgl 249 250; NOCMOV: subl 251; NOCMOV: jb 252; NOCMOV: lock 253; NOCMOV: cmpxchgl 254 ret void 255; X64: ret 256; X32: ret 257; NOCMOV: ret 258} 259 260define void @atomic_fetch_cmpxchg32() nounwind { 261; X64-LABEL: atomic_fetch_cmpxchg32: 262; X32-LABEL: atomic_fetch_cmpxchg32: 263 264 %t1 = cmpxchg i32* @sc32, i32 0, i32 1 acquire acquire 265; X64: lock 266; X64: cmpxchgl 267; X32: lock 268; X32: cmpxchgl 269 ret void 270; X64: ret 271; X32: ret 272} 273 274define void @atomic_fetch_store32(i32 %x) nounwind { 275; X64-LABEL: atomic_fetch_store32: 276; X32-LABEL: atomic_fetch_store32: 277 278 store atomic i32 %x, i32* @sc32 release, align 4 279; X64-NOT: lock 280; X64: movl 281; X32-NOT: lock 282; X32: movl 283 ret void 284; X64: ret 285; X32: ret 286} 287 288define void @atomic_fetch_swap32(i32 %x) nounwind { 289; X64-LABEL: atomic_fetch_swap32: 290; X32-LABEL: atomic_fetch_swap32: 291 292 %t1 = atomicrmw xchg i32* @sc32, i32 %x acquire 293; X64-NOT: lock 294; X64: xchgl 295; X32-NOT: lock 296; X32: xchgl 297 ret void 298; X64: ret 299; X32: ret 300} 301