1 // RUN: %clang_cc1 -verify -triple x86_64-apple-darwin10 -fopenmp -x c -emit-llvm %s -o - | FileCheck %s 2 // RUN: %clang_cc1 -fopenmp -x c -triple x86_64-apple-darwin10 -emit-pch -o %t %s 3 // RUN: %clang_cc1 -fopenmp -x c -triple x86_64-apple-darwin10 -include-pch %t -verify %s -emit-llvm -o - | FileCheck %s 4 // expected-no-diagnostics 5 // REQUIRES: x86-registered-target 6 #ifndef HEADER 7 #define HEADER 8 9 _Bool bv, bx; 10 char cv, cx; 11 unsigned char ucv, ucx; 12 short sv, sx; 13 unsigned short usv, usx; 14 int iv, ix; 15 unsigned int uiv, uix; 16 long lv, lx; 17 unsigned long ulv, ulx; 18 long long llv, llx; 19 unsigned long long ullv, ullx; 20 float fv, fx; 21 double dv, dx; 22 long double ldv, ldx; 23 _Complex int civ, cix; 24 _Complex float cfv, cfx; 25 _Complex double cdv, cdx; 26 27 typedef int int4 __attribute__((__vector_size__(16))); 28 int4 int4x; 29 30 struct BitFields { 31 int : 32; 32 int a : 31; 33 } bfx; 34 35 struct BitFields_packed { 36 int : 32; 37 int a : 31; 38 } __attribute__ ((__packed__)) bfx_packed; 39 40 struct BitFields2 { 41 int : 31; 42 int a : 1; 43 } bfx2; 44 45 struct BitFields2_packed { 46 int : 31; 47 int a : 1; 48 } __attribute__ ((__packed__)) bfx2_packed; 49 50 struct BitFields3 { 51 int : 11; 52 int a : 14; 53 } bfx3; 54 55 struct BitFields3_packed { 56 int : 11; 57 int a : 14; 58 } __attribute__ ((__packed__)) bfx3_packed; 59 60 struct BitFields4 { 61 short : 16; 62 int a: 1; 63 long b : 7; 64 } bfx4; 65 66 struct BitFields4_packed { 67 short : 16; 68 int a: 1; 69 long b : 7; 70 } __attribute__ ((__packed__)) bfx4_packed; 71 72 typedef float float2 __attribute__((ext_vector_type(2))); 73 float2 float2x; 74 75 // Register "0" is currently an invalid register for global register variables. 76 // Use "esp" instead of "0". 77 // register int rix __asm__("0"); 78 register int rix __asm__("esp"); 79 80 int main() { 81 // CHECK-NOT: atomicrmw 82 #pragma omp atomic 83 ++dv; 84 // CHECK: atomicrmw add i8* @{{.+}}, i8 1 monotonic 85 #pragma omp atomic 86 bx++; 87 // CHECK: atomicrmw add i8* @{{.+}}, i8 1 monotonic 88 #pragma omp atomic update 89 ++cx; 90 // CHECK: atomicrmw sub i8* @{{.+}}, i8 1 monotonic 91 #pragma omp atomic 92 ucx--; 93 // CHECK: atomicrmw sub i16* @{{.+}}, i16 1 monotonic 94 #pragma omp atomic update 95 --sx; 96 // CHECK: [[USV:%.+]] = load i16, i16* @{{.+}}, 97 // CHECK: [[EXPR:%.+]] = zext i16 [[USV]] to i32 98 // CHECK: [[X:%.+]] = load atomic i16, i16* [[X_ADDR:@.+]] monotonic 99 // CHECK: br label %[[CONT:.+]] 100 // CHECK: [[CONT]] 101 // CHECK: [[EXPECTED:%.+]] = phi i16 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 102 // CHECK: [[CONV:%.+]] = zext i16 [[EXPECTED]] to i32 103 // CHECK: [[ADD:%.+]] = add nsw i32 [[CONV]], [[EXPR]] 104 // CHECK: [[DESIRED:%.+]] = trunc i32 [[ADD]] to i16 105 // CHECK: store i16 [[DESIRED]], i16* [[TEMP:%.+]], 106 // CHECK: [[DESIRED:%.+]] = load i16, i16* [[TEMP]], 107 // CHECK: [[RES:%.+]] = cmpxchg i16* [[X_ADDR]], i16 [[EXPECTED]], i16 [[DESIRED]] monotonic monotonic 108 // CHECK: [[OLD_X]] = extractvalue { i16, i1 } [[RES]], 0 109 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i16, i1 } [[RES]], 1 110 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 111 // CHECK: [[EXIT]] 112 #pragma omp atomic 113 usx += usv; 114 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}}, 115 // CHECK: [[X:%.+]] = load atomic i32, i32* [[X_ADDR:@.+]] monotonic 116 // CHECK: br label %[[CONT:.+]] 117 // CHECK: [[CONT]] 118 // CHECK: [[EXPECTED:%.+]] = phi i32 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 119 // CHECK: [[DESIRED:%.+]] = mul nsw i32 [[EXPECTED]], [[EXPR]] 120 // CHECK: store i32 [[DESIRED]], i32* [[TEMP:%.+]], 121 // CHECK: [[DESIRED:%.+]] = load i32, i32* [[TEMP]], 122 // CHECK: [[RES:%.+]] = cmpxchg i32* [[X_ADDR]], i32 [[EXPECTED]], i32 [[DESIRED]] monotonic monotonic 123 // CHECK: [[OLD_X]] = extractvalue { i32, i1 } [[RES]], 0 124 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i32, i1 } [[RES]], 1 125 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 126 // CHECK: [[EXIT]] 127 #pragma omp atomic update 128 ix *= iv; 129 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}}, 130 // CHECK: atomicrmw sub i32* @{{.+}}, i32 [[EXPR]] monotonic 131 #pragma omp atomic 132 uix -= uiv; 133 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}}, 134 // CHECK: [[X:%.+]] = load atomic i32, i32* [[X_ADDR:@.+]] monotonic 135 // CHECK: br label %[[CONT:.+]] 136 // CHECK: [[CONT]] 137 // CHECK: [[EXPECTED:%.+]] = phi i32 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 138 // CHECK: [[DESIRED:%.+]] = shl i32 [[EXPECTED]], [[EXPR]] 139 // CHECK: store i32 [[DESIRED]], i32* [[TEMP:%.+]], 140 // CHECK: [[DESIRED:%.+]] = load i32, i32* [[TEMP]], 141 // CHECK: [[RES:%.+]] = cmpxchg i32* [[X_ADDR]], i32 [[EXPECTED]], i32 [[DESIRED]] monotonic monotonic 142 // CHECK: [[OLD_X]] = extractvalue { i32, i1 } [[RES]], 0 143 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i32, i1 } [[RES]], 1 144 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 145 // CHECK: [[EXIT]] 146 #pragma omp atomic update 147 ix <<= iv; 148 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}}, 149 // CHECK: [[X:%.+]] = load atomic i32, i32* [[X_ADDR:@.+]] monotonic 150 // CHECK: br label %[[CONT:.+]] 151 // CHECK: [[CONT]] 152 // CHECK: [[EXPECTED:%.+]] = phi i32 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 153 // CHECK: [[DESIRED:%.+]] = lshr i32 [[EXPECTED]], [[EXPR]] 154 // CHECK: store i32 [[DESIRED]], i32* [[TEMP:%.+]], 155 // CHECK: [[DESIRED:%.+]] = load i32, i32* [[TEMP]], 156 // CHECK: [[RES:%.+]] = cmpxchg i32* [[X_ADDR]], i32 [[EXPECTED]], i32 [[DESIRED]] monotonic monotonic 157 // CHECK: [[OLD_X]] = extractvalue { i32, i1 } [[RES]], 0 158 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i32, i1 } [[RES]], 1 159 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 160 // CHECK: [[EXIT]] 161 #pragma omp atomic 162 uix >>= uiv; 163 // CHECK: [[EXPR:%.+]] = load i64, i64* @{{.+}}, 164 // CHECK: [[X:%.+]] = load atomic i64, i64* [[X_ADDR:@.+]] monotonic 165 // CHECK: br label %[[CONT:.+]] 166 // CHECK: [[CONT]] 167 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 168 // CHECK: [[DESIRED:%.+]] = sdiv i64 [[EXPECTED]], [[EXPR]] 169 // CHECK: store i64 [[DESIRED]], i64* [[TEMP:%.+]], 170 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[TEMP]], 171 // CHECK: [[RES:%.+]] = cmpxchg i64* [[X_ADDR]], i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 172 // CHECK: [[OLD_X]] = extractvalue { i64, i1 } [[RES]], 0 173 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 174 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 175 // CHECK: [[EXIT]] 176 #pragma omp atomic update 177 lx /= lv; 178 // CHECK: [[EXPR:%.+]] = load i64, i64* @{{.+}}, 179 // CHECK: atomicrmw and i64* @{{.+}}, i64 [[EXPR]] monotonic 180 #pragma omp atomic 181 ulx &= ulv; 182 // CHECK: [[EXPR:%.+]] = load i64, i64* @{{.+}}, 183 // CHECK: atomicrmw xor i64* @{{.+}}, i64 [[EXPR]] monotonic 184 #pragma omp atomic update 185 llx ^= llv; 186 // CHECK: [[EXPR:%.+]] = load i64, i64* @{{.+}}, 187 // CHECK: atomicrmw or i64* @{{.+}}, i64 [[EXPR]] monotonic 188 #pragma omp atomic 189 ullx |= ullv; 190 // CHECK: [[EXPR:%.+]] = load float, float* @{{.+}}, 191 // CHECK: [[OLD:%.+]] = load atomic i32, i32* bitcast (float* [[X_ADDR:@.+]] to i32*) monotonic 192 // CHECK: br label %[[CONT:.+]] 193 // CHECK: [[CONT]] 194 // CHECK: [[EXPECTED:%.+]] = phi i32 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 195 // CHECK: [[BITCAST:%.+]] = bitcast float* [[TEMP:%.+]] to i32* 196 // CHECK: [[OLD:%.+]] = bitcast i32 [[EXPECTED]] to float 197 // CHECK: [[ADD:%.+]] = fadd float [[OLD]], [[EXPR]] 198 // CHECK: store float [[ADD]], float* [[TEMP]], 199 // CHECK: [[DESIRED:%.+]] = load i32, i32* [[BITCAST]], 200 // CHECK: [[RES:%.+]] = cmpxchg i32* bitcast (float* [[X_ADDR]] to i32*), i32 [[EXPECTED]], i32 [[DESIRED]] monotonic monotonic 201 // CHECK: [[PREV:%.+]] = extractvalue { i32, i1 } [[RES]], 0 202 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i32, i1 } [[RES]], 1 203 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 204 // CHECK: [[EXIT]] 205 #pragma omp atomic update 206 fx = fx + fv; 207 // CHECK: [[EXPR:%.+]] = load double, double* @{{.+}}, 208 // CHECK: [[OLD:%.+]] = load atomic i64, i64* bitcast (double* [[X_ADDR:@.+]] to i64*) monotonic 209 // CHECK: br label %[[CONT:.+]] 210 // CHECK: [[CONT]] 211 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 212 // CHECK: [[BITCAST:%.+]] = bitcast double* [[TEMP:%.+]] to i64* 213 // CHECK: [[OLD:%.+]] = bitcast i64 [[EXPECTED]] to double 214 // CHECK: [[SUB:%.+]] = fsub double [[EXPR]], [[OLD]] 215 // CHECK: store double [[SUB]], double* [[TEMP]], 216 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[BITCAST]], 217 // CHECK: [[RES:%.+]] = cmpxchg i64* bitcast (double* [[X_ADDR]] to i64*), i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 218 // CHECK: [[PREV:%.+]] = extractvalue { i64, i1 } [[RES]], 0 219 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 220 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 221 // CHECK: [[EXIT]] 222 #pragma omp atomic 223 dx = dv - dx; 224 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}}, 225 // CHECK: [[OLD:%.+]] = load atomic i128, i128* bitcast (x86_fp80* [[X_ADDR:@.+]] to i128*) monotonic 226 // CHECK: br label %[[CONT:.+]] 227 // CHECK: [[CONT]] 228 // CHECK: [[EXPECTED:%.+]] = phi i128 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 229 // CHECK: [[BITCAST:%.+]] = bitcast x86_fp80* [[TEMP:%.+]] to i128* 230 // CHECK: store i128 [[EXPECTED]], i128* [[BITCAST]], 231 // CHECK: [[BITCAST1:%.+]] = bitcast x86_fp80* [[TEMP1:%.+]] to i128* 232 // CHECK: store i128 [[EXPECTED]], i128* [[BITCAST1]], 233 // CHECK: [[OLD:%.+]] = load x86_fp80, x86_fp80* [[TEMP1]] 234 // CHECK: [[MUL:%.+]] = fmul x86_fp80 [[OLD]], [[EXPR]] 235 // CHECK: store x86_fp80 [[MUL]], x86_fp80* [[TEMP]] 236 // CHECK: [[DESIRED:%.+]] = load i128, i128* [[BITCAST]] 237 // CHECK: [[RES:%.+]] = cmpxchg i128* bitcast (x86_fp80* [[X_ADDR]] to i128*), i128 [[EXPECTED]], i128 [[DESIRED]] monotonic monotonic 238 // CHECK: [[PREV:%.+]] = extractvalue { i128, i1 } [[RES]], 0 239 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i128, i1 } [[RES]], 1 240 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 241 // CHECK: [[EXIT]] 242 #pragma omp atomic update 243 ldx = ldx * ldv; 244 // CHECK: [[EXPR_RE:%.+]] = load i32, i32* getelementptr inbounds ({ i32, i32 }, { i32, i32 }* @{{.+}}, i32 0, i32 0) 245 // CHECK: [[EXPR_IM:%.+]] = load i32, i32* getelementptr inbounds ({ i32, i32 }, { i32, i32 }* @{{.+}}, i32 0, i32 1) 246 // CHECK: [[BITCAST:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR:%.+]] to i8* 247 // CHECK: call void @__atomic_load(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR:@.+]] to i8*), i8* [[BITCAST]], i32 0) 248 // CHECK: br label %[[CONT:.+]] 249 // CHECK: [[CONT]] 250 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 0 251 // CHECK: [[X_RE:%.+]] = load i32, i32* [[X_RE_ADDR]] 252 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 1 253 // CHECK: [[X_IM:%.+]] = load i32, i32* [[X_IM_ADDR]] 254 // <Skip checks for complex calculations> 255 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR:%.+]], i32 0, i32 0 256 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR]], i32 0, i32 1 257 // CHECK: store i32 %{{.+}}, i32* [[X_RE_ADDR]] 258 // CHECK: store i32 %{{.+}}, i32* [[X_IM_ADDR]] 259 // CHECK: [[EXPECTED:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR]] to i8* 260 // CHECK: [[DESIRED:%.+]] = bitcast { i32, i32 }* [[DESIRED_ADDR]] to i8* 261 // CHECK: [[SUCCESS_FAIL:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR]] to i8*), i8* [[EXPECTED]], i8* [[DESIRED]], i32 0, i32 0) 262 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 263 // CHECK: [[EXIT]] 264 #pragma omp atomic 265 cix = civ / cix; 266 // CHECK: [[EXPR_RE:%.+]] = load float, float* getelementptr inbounds ({ float, float }, { float, float }* @{{.+}}, i32 0, i32 0) 267 // CHECK: [[EXPR_IM:%.+]] = load float, float* getelementptr inbounds ({ float, float }, { float, float }* @{{.+}}, i32 0, i32 1) 268 // CHECK: [[BITCAST:%.+]] = bitcast { float, float }* [[EXPECTED_ADDR:%.+]] to i8* 269 // CHECK: call void @__atomic_load(i64 8, i8* bitcast ({ float, float }* [[X_ADDR:@.+]] to i8*), i8* [[BITCAST]], i32 0) 270 // CHECK: br label %[[CONT:.+]] 271 // CHECK: [[CONT]] 272 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[EXPECTED_ADDR]], i32 0, i32 0 273 // CHECK: [[X_RE:%.+]] = load float, float* [[X_RE_ADDR]] 274 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[EXPECTED_ADDR]], i32 0, i32 1 275 // CHECK: [[X_IM:%.+]] = load float, float* [[X_IM_ADDR]] 276 // <Skip checks for complex calculations> 277 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[DESIRED_ADDR:%.+]], i32 0, i32 0 278 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[DESIRED_ADDR]], i32 0, i32 1 279 // CHECK: store float %{{.+}}, float* [[X_RE_ADDR]] 280 // CHECK: store float %{{.+}}, float* [[X_IM_ADDR]] 281 // CHECK: [[EXPECTED:%.+]] = bitcast { float, float }* [[EXPECTED_ADDR]] to i8* 282 // CHECK: [[DESIRED:%.+]] = bitcast { float, float }* [[DESIRED_ADDR]] to i8* 283 // CHECK: [[SUCCESS_FAIL:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 8, i8* bitcast ({ float, float }* [[X_ADDR]] to i8*), i8* [[EXPECTED]], i8* [[DESIRED]], i32 0, i32 0) 284 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 285 // CHECK: [[EXIT]] 286 #pragma omp atomic update 287 cfx = cfv + cfx; 288 // CHECK: [[EXPR_RE:%.+]] = load double, double* getelementptr inbounds ({ double, double }, { double, double }* @{{.+}}, i32 0, i32 0) 289 // CHECK: [[EXPR_IM:%.+]] = load double, double* getelementptr inbounds ({ double, double }, { double, double }* @{{.+}}, i32 0, i32 1) 290 // CHECK: [[BITCAST:%.+]] = bitcast { double, double }* [[EXPECTED_ADDR:%.+]] to i8* 291 // CHECK: call void @__atomic_load(i64 16, i8* bitcast ({ double, double }* [[X_ADDR:@.+]] to i8*), i8* [[BITCAST]], i32 5) 292 // CHECK: br label %[[CONT:.+]] 293 // CHECK: [[CONT]] 294 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { double, double }, { double, double }* [[EXPECTED_ADDR]], i32 0, i32 0 295 // CHECK: [[X_RE:%.+]] = load double, double* [[X_RE_ADDR]] 296 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { double, double }, { double, double }* [[EXPECTED_ADDR]], i32 0, i32 1 297 // CHECK: [[X_IM:%.+]] = load double, double* [[X_IM_ADDR]] 298 // <Skip checks for complex calculations> 299 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { double, double }, { double, double }* [[DESIRED_ADDR:%.+]], i32 0, i32 0 300 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { double, double }, { double, double }* [[DESIRED_ADDR]], i32 0, i32 1 301 // CHECK: store double %{{.+}}, double* [[X_RE_ADDR]] 302 // CHECK: store double %{{.+}}, double* [[X_IM_ADDR]] 303 // CHECK: [[EXPECTED:%.+]] = bitcast { double, double }* [[EXPECTED_ADDR]] to i8* 304 // CHECK: [[DESIRED:%.+]] = bitcast { double, double }* [[DESIRED_ADDR]] to i8* 305 // CHECK: [[SUCCESS_FAIL:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 16, i8* bitcast ({ double, double }* [[X_ADDR]] to i8*), i8* [[EXPECTED]], i8* [[DESIRED]], i32 5, i32 5) 306 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 307 // CHECK: [[EXIT]] 308 // CHECK: call{{.*}} @__kmpc_flush( 309 #pragma omp atomic seq_cst 310 cdx = cdx - cdv; 311 // CHECK: [[BV:%.+]] = load i8, i8* @{{.+}} 312 // CHECK: [[BOOL:%.+]] = trunc i8 [[BV]] to i1 313 // CHECK: [[EXPR:%.+]] = zext i1 [[BOOL]] to i64 314 // CHECK: atomicrmw and i64* @{{.+}}, i64 [[EXPR]] monotonic 315 #pragma omp atomic update 316 ulx = ulx & bv; 317 // CHECK: [[CV:%.+]] = load i8, i8* @{{.+}}, align 1 318 // CHECK: [[EXPR:%.+]] = sext i8 [[CV]] to i32 319 // CHECK: [[BX:%.+]] = load atomic i8, i8* [[BX_ADDR:@.+]] monotonic 320 // CHECK: br label %[[CONT:.+]] 321 // CHECK: [[CONT]] 322 // CHECK: [[EXPECTED:%.+]] = phi i8 [ [[BX]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 323 // CHECK: [[OLD:%.+]] = trunc i8 [[EXPECTED]] to i1 324 // CHECK: [[X_RVAL:%.+]] = zext i1 [[OLD]] to i32 325 // CHECK: [[AND:%.+]] = and i32 [[EXPR]], [[X_RVAL]] 326 // CHECK: [[CAST:%.+]] = icmp ne i32 [[AND]], 0 327 // CHECK: [[DESIRED:%.+]] = zext i1 [[CAST]] to i8 328 // CHECK: store i8 [[DESIRED]], i8* [[TEMP:%.+]], 329 // CHECK: [[DESIRED:%.+]] = load i8, i8* [[TEMP]], 330 // CHECK: [[RES:%.+]] = cmpxchg i8* [[BX_ADDR]], i8 [[EXPECTED]], i8 [[DESIRED]] monotonic monotonic 331 // CHECK: [[OLD_X:%.+]] = extractvalue { i8, i1 } [[RES]], 0 332 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i8, i1 } [[RES]], 1 333 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 334 // CHECK: [[EXIT]] 335 #pragma omp atomic 336 bx = cv & bx; 337 // CHECK: [[UCV:%.+]] = load i8, i8* @{{.+}}, 338 // CHECK: [[EXPR:%.+]] = zext i8 [[UCV]] to i32 339 // CHECK: [[X:%.+]] = load atomic i8, i8* [[CX_ADDR:@.+]] seq_cst 340 // CHECK: br label %[[CONT:.+]] 341 // CHECK: [[CONT]] 342 // CHECK: [[EXPECTED:%.+]] = phi i8 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 343 // CHECK: [[X_RVAL:%.+]] = sext i8 [[EXPECTED]] to i32 344 // CHECK: [[ASHR:%.+]] = ashr i32 [[X_RVAL]], [[EXPR]] 345 // CHECK: [[DESIRED:%.+]] = trunc i32 [[ASHR]] to i8 346 // CHECK: store i8 [[DESIRED]], i8* [[TEMP:%.+]], 347 // CHECK: [[DESIRED:%.+]] = load i8, i8* [[TEMP]], 348 // CHECK: [[RES:%.+]] = cmpxchg i8* [[CX_ADDR]], i8 [[EXPECTED]], i8 [[DESIRED]] seq_cst seq_cst 349 // CHECK: [[OLD_X:%.+]] = extractvalue { i8, i1 } [[RES]], 0 350 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i8, i1 } [[RES]], 1 351 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 352 // CHECK: [[EXIT]] 353 // CHECK: call{{.*}} @__kmpc_flush( 354 #pragma omp atomic update, seq_cst 355 cx = cx >> ucv; 356 // CHECK: [[SV:%.+]] = load i16, i16* @{{.+}}, 357 // CHECK: [[EXPR:%.+]] = sext i16 [[SV]] to i32 358 // CHECK: [[X:%.+]] = load atomic i64, i64* [[ULX_ADDR:@.+]] monotonic 359 // CHECK: br label %[[CONT:.+]] 360 // CHECK: [[CONT]] 361 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 362 // CHECK: [[X_RVAL:%.+]] = trunc i64 [[EXPECTED]] to i32 363 // CHECK: [[SHL:%.+]] = shl i32 [[EXPR]], [[X_RVAL]] 364 // CHECK: [[DESIRED:%.+]] = sext i32 [[SHL]] to i64 365 // CHECK: store i64 [[DESIRED]], i64* [[TEMP:%.+]], 366 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[TEMP]], 367 // CHECK: [[RES:%.+]] = cmpxchg i64* [[ULX_ADDR]], i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 368 // CHECK: [[OLD_X:%.+]] = extractvalue { i64, i1 } [[RES]], 0 369 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 370 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 371 // CHECK: [[EXIT]] 372 #pragma omp atomic update 373 ulx = sv << ulx; 374 // CHECK: [[USV:%.+]] = load i16, i16* @{{.+}}, 375 // CHECK: [[EXPR:%.+]] = zext i16 [[USV]] to i64 376 // CHECK: [[X:%.+]] = load atomic i64, i64* [[LX_ADDR:@.+]] monotonic 377 // CHECK: br label %[[CONT:.+]] 378 // CHECK: [[CONT]] 379 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 380 // CHECK: [[DESIRED:%.+]] = srem i64 [[EXPECTED]], [[EXPR]] 381 // CHECK: store i64 [[DESIRED]], i64* [[TEMP:%.+]], 382 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[TEMP]], 383 // CHECK: [[RES:%.+]] = cmpxchg i64* [[LX_ADDR]], i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 384 // CHECK: [[OLD_X:%.+]] = extractvalue { i64, i1 } [[RES]], 0 385 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 386 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 387 // CHECK: [[EXIT]] 388 #pragma omp atomic 389 lx = lx % usv; 390 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}} 391 // CHECK: atomicrmw or i32* @{{.+}}, i32 [[EXPR]] seq_cst 392 // CHECK: call{{.*}} @__kmpc_flush( 393 #pragma omp atomic seq_cst, update 394 uix = iv | uix; 395 // CHECK: [[EXPR:%.+]] = load i32, i32* @{{.+}} 396 // CHECK: atomicrmw and i32* @{{.+}}, i32 [[EXPR]] monotonic 397 #pragma omp atomic 398 ix = ix & uiv; 399 // CHECK: [[EXPR:%.+]] = load i64, i64* @{{.+}}, 400 // CHECK: [[BITCAST:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR:%.+]] to i8* 401 // CHECK: call void @__atomic_load(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR:@.+]] to i8*), i8* [[BITCAST]], i32 0) 402 // CHECK: br label %[[CONT:.+]] 403 // CHECK: [[CONT]] 404 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 0 405 // CHECK: [[X_RE:%.+]] = load i32, i32* [[X_RE_ADDR]] 406 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 1 407 // CHECK: [[X_IM:%.+]] = load i32, i32* [[X_IM_ADDR]] 408 // <Skip checks for complex calculations> 409 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR:%.+]], i32 0, i32 0 410 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR]], i32 0, i32 1 411 // CHECK: store i32 %{{.+}}, i32* [[X_RE_ADDR]] 412 // CHECK: store i32 %{{.+}}, i32* [[X_IM_ADDR]] 413 // CHECK: [[EXPECTED:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR]] to i8* 414 // CHECK: [[DESIRED:%.+]] = bitcast { i32, i32 }* [[DESIRED_ADDR]] to i8* 415 // CHECK: [[SUCCESS_FAIL:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR]] to i8*), i8* [[EXPECTED]], i8* [[DESIRED]], i32 0, i32 0) 416 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 417 // CHECK: [[EXIT]] 418 #pragma omp atomic update 419 cix = lv + cix; 420 // CHECK: [[ULV:%.+]] = load i64, i64* @{{.+}}, 421 // CHECK: [[EXPR:%.+]] = uitofp i64 [[ULV]] to float 422 // CHECK: [[OLD:%.+]] = load atomic i32, i32* bitcast (float* [[X_ADDR:@.+]] to i32*) monotonic 423 // CHECK: br label %[[CONT:.+]] 424 // CHECK: [[CONT]] 425 // CHECK: [[EXPECTED:%.+]] = phi i32 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 426 // CHECK: [[BITCAST:%.+]] = bitcast float* [[TEMP:%.+]] to i32* 427 // CHECK: [[OLD:%.+]] = bitcast i32 [[EXPECTED]] to float 428 // CHECK: [[MUL:%.+]] = fmul float [[OLD]], [[EXPR]] 429 // CHECK: store float [[MUL]], float* [[TEMP]], 430 // CHECK: [[DESIRED:%.+]] = load i32, i32* [[BITCAST]], 431 // CHECK: [[RES:%.+]] = cmpxchg i32* bitcast (float* [[X_ADDR]] to i32*), i32 [[EXPECTED]], i32 [[DESIRED]] monotonic monotonic 432 // CHECK: [[PREV:%.+]] = extractvalue { i32, i1 } [[RES]], 0 433 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i32, i1 } [[RES]], 1 434 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 435 // CHECK: [[EXIT]] 436 #pragma omp atomic 437 fx = fx * ulv; 438 // CHECK: [[LLV:%.+]] = load i64, i64* @{{.+}}, 439 // CHECK: [[EXPR:%.+]] = sitofp i64 [[LLV]] to double 440 // CHECK: [[OLD:%.+]] = load atomic i64, i64* bitcast (double* [[X_ADDR:@.+]] to i64*) monotonic 441 // CHECK: br label %[[CONT:.+]] 442 // CHECK: [[CONT]] 443 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 444 // CHECK: [[BITCAST:%.+]] = bitcast double* [[TEMP:%.+]] to i64* 445 // CHECK: [[OLD:%.+]] = bitcast i64 [[EXPECTED]] to double 446 // CHECK: [[DIV:%.+]] = fdiv double [[OLD]], [[EXPR]] 447 // CHECK: store double [[DIV]], double* [[TEMP]], 448 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[BITCAST]], 449 // CHECK: [[RES:%.+]] = cmpxchg i64* bitcast (double* [[X_ADDR]] to i64*), i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 450 // CHECK: [[PREV:%.+]] = extractvalue { i64, i1 } [[RES]], 0 451 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 452 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 453 // CHECK: [[EXIT]] 454 #pragma omp atomic update 455 dx /= llv; 456 // CHECK: [[ULLV:%.+]] = load i64, i64* @{{.+}}, 457 // CHECK: [[EXPR:%.+]] = uitofp i64 [[ULLV]] to x86_fp80 458 // CHECK: [[OLD:%.+]] = load atomic i128, i128* bitcast (x86_fp80* [[X_ADDR:@.+]] to i128*) monotonic 459 // CHECK: br label %[[CONT:.+]] 460 // CHECK: [[CONT]] 461 // CHECK: [[EXPECTED:%.+]] = phi i128 [ [[OLD]], %{{.+}} ], [ [[PREV:%.+]], %[[CONT]] ] 462 // CHECK: [[BITCAST1:%.+]] = bitcast x86_fp80* [[TEMP1:%.+]] to i128* 463 // CHECK: [[BITCAST:%.+]] = bitcast x86_fp80* [[TEMP:%.+]] to i128* 464 // CHECK: store i128 [[EXPECTED]], i128* [[BITCAST]] 465 // CHECK: [[OLD:%.+]] = load x86_fp80, x86_fp80* [[TEMP]] 466 // CHECK: [[SUB:%.+]] = fsub x86_fp80 [[OLD]], [[EXPR]] 467 // CHECK: store x86_fp80 [[SUB]], x86_fp80* [[TEMP1]] 468 // CHECK: [[DESIRED:%.+]] = load i128, i128* [[BITCAST1]] 469 // CHECK: [[RES:%.+]] = cmpxchg i128* bitcast (x86_fp80* [[X_ADDR]] to i128*), i128 [[EXPECTED]], i128 [[DESIRED]] monotonic monotonic 470 // CHECK: [[PREV:%.+]] = extractvalue { i128, i1 } [[RES]], 0 471 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i128, i1 } [[RES]], 1 472 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 473 // CHECK: [[EXIT]] 474 #pragma omp atomic 475 ldx -= ullv; 476 // CHECK: [[EXPR:%.+]] = load float, float* @{{.+}}, 477 // CHECK: [[BITCAST:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR:%.+]] to i8* 478 // CHECK: call void @__atomic_load(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR:@.+]] to i8*), i8* [[BITCAST]], i32 0) 479 // CHECK: br label %[[CONT:.+]] 480 // CHECK: [[CONT]] 481 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 0 482 // CHECK: [[X_RE:%.+]] = load i32, i32* [[X_RE_ADDR]] 483 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[EXPECTED_ADDR]], i32 0, i32 1 484 // CHECK: [[X_IM:%.+]] = load i32, i32* [[X_IM_ADDR]] 485 // <Skip checks for complex calculations> 486 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR:%.+]], i32 0, i32 0 487 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { i32, i32 }, { i32, i32 }* [[DESIRED_ADDR]], i32 0, i32 1 488 // CHECK: store i32 %{{.+}}, i32* [[X_RE_ADDR]] 489 // CHECK: store i32 %{{.+}}, i32* [[X_IM_ADDR]] 490 // CHECK: [[EXPECTED:%.+]] = bitcast { i32, i32 }* [[EXPECTED_ADDR]] to i8* 491 // CHECK: [[DESIRED:%.+]] = bitcast { i32, i32 }* [[DESIRED_ADDR]] to i8* 492 // CHECK: [[SUCCESS_FAIL:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 8, i8* bitcast ({ i32, i32 }* [[X_ADDR]] to i8*), i8* [[EXPECTED]], i8* [[DESIRED]], i32 0, i32 0) 493 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 494 // CHECK: [[EXIT]] 495 #pragma omp atomic update 496 cix = fv / cix; 497 // CHECK: [[EXPR:%.+]] = load double, double* @{{.+}}, 498 // CHECK: [[X:%.+]] = load atomic i16, i16* [[X_ADDR:@.+]] monotonic 499 // CHECK: br label %[[CONT:.+]] 500 // CHECK: [[CONT]] 501 // CHECK: [[EXPECTED:%.+]] = phi i16 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 502 // CHECK: [[CONV:%.+]] = sext i16 [[EXPECTED]] to i32 503 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CONV]] to double 504 // CHECK: [[ADD:%.+]] = fadd double [[X_RVAL]], [[EXPR]] 505 // CHECK: [[DESIRED:%.+]] = fptosi double [[ADD]] to i16 506 // CHECK: store i16 [[DESIRED]], i16* [[TEMP:%.+]] 507 // CHECK: [[DESIRED:%.+]] = load i16, i16* [[TEMP]] 508 // CHECK: [[RES:%.+]] = cmpxchg i16* [[X_ADDR]], i16 [[EXPECTED]], i16 [[DESIRED]] monotonic monotonic 509 // CHECK: [[OLD_X]] = extractvalue { i16, i1 } [[RES]], 0 510 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i16, i1 } [[RES]], 1 511 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 512 // CHECK: [[EXIT]] 513 #pragma omp atomic 514 sx = sx + dv; 515 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}}, 516 // CHECK: [[XI8:%.+]] = load atomic i8, i8* [[X_ADDR:@.+]] monotonic 517 // CHECK: br label %[[CONT:.+]] 518 // CHECK: [[CONT]] 519 // CHECK: [[EXPECTED:%.+]] = phi i8 [ [[XI8]], %{{.+}} ], [ [[OLD_XI8:%.+]], %[[CONT]] ] 520 // CHECK: [[BOOL_EXPECTED:%.+]] = trunc i8 [[EXPECTED]] to i1 521 // CHECK: [[CONV:%.+]] = zext i1 [[BOOL_EXPECTED]] to i32 522 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CONV]] to x86_fp80 523 // CHECK: [[MUL:%.+]] = fmul x86_fp80 [[EXPR]], [[X_RVAL]] 524 // CHECK: [[BOOL_DESIRED:%.+]] = fcmp une x86_fp80 [[MUL]], 0xK00000000000000000000 525 // CHECK: [[DESIRED:%.+]] = zext i1 [[BOOL_DESIRED]] to i8 526 // CHECK: store i8 [[DESIRED]], i8* [[TEMP:%.+]] 527 // CHECK: [[DESIRED:%.+]] = load i8, i8* [[TEMP]] 528 // CHECK: [[RES:%.+]] = cmpxchg i8* [[X_ADDR]], i8 [[EXPECTED]], i8 [[DESIRED]] monotonic monotonic 529 // CHECK: [[OLD_XI8:%.+]] = extractvalue { i8, i1 } [[RES]], 0 530 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i8, i1 } [[RES]], 1 531 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 532 // CHECK: [[EXIT]] 533 #pragma omp atomic update 534 bx = ldv * bx; 535 // CHECK: [[EXPR_RE:%.+]] = load i32, i32* getelementptr inbounds ({ i32, i32 }, { i32, i32 }* [[CIV_ADDR:@.+]], i32 0, i32 0), 536 // CHECK: [[EXPR_IM:%.+]] = load i32, i32* getelementptr inbounds ({ i32, i32 }, { i32, i32 }* [[CIV_ADDR]], i32 0, i32 1), 537 // CHECK: [[XI8:%.+]] = load atomic i8, i8* [[X_ADDR:@.+]] monotonic 538 // CHECK: br label %[[CONT:.+]] 539 // CHECK: [[CONT]] 540 // CHECK: [[EXPECTED:%.+]] = phi i8 [ [[XI8]], %{{.+}} ], [ [[OLD_XI8:%.+]], %[[CONT]] ] 541 // CHECK: [[BOOL_EXPECTED:%.+]] = trunc i8 [[EXPECTED]] to i1 542 // CHECK: [[X_RVAL:%.+]] = zext i1 [[BOOL_EXPECTED]] to i32 543 // CHECK: [[SUB_RE:%.+]] = sub i32 [[EXPR_RE:%.+]], [[X_RVAL]] 544 // CHECK: [[SUB_IM:%.+]] = sub i32 [[EXPR_IM:%.+]], 0 545 // CHECK: icmp ne i32 [[SUB_RE]], 0 546 // CHECK: icmp ne i32 [[SUB_IM]], 0 547 // CHECK: [[BOOL_DESIRED:%.+]] = or i1 548 // CHECK: [[DESIRED:%.+]] = zext i1 [[BOOL_DESIRED]] to i8 549 // CHECK: store i8 [[DESIRED]], i8* [[TEMP:%.+]] 550 // CHECK: [[DESIRED:%.+]] = load i8, i8* [[TEMP]] 551 // CHECK: [[RES:%.+]] = cmpxchg i8* [[X_ADDR]], i8 [[EXPECTED]], i8 [[DESIRED]] monotonic monotonic 552 // CHECK: [[OLD_XI8:%.+]] = extractvalue { i8, i1 } [[RES]], 0 553 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i8, i1 } [[RES]], 1 554 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 555 // CHECK: [[EXIT]] 556 #pragma omp atomic 557 bx = civ - bx; 558 // CHECK: [[EXPR_RE:%.+]] = load float, float* getelementptr inbounds ({ float, float }, { float, float }* @{{.+}}, i32 0, i32 0) 559 // CHECK: [[EXPR_IM:%.+]] = load float, float* getelementptr inbounds ({ float, float }, { float, float }* @{{.+}}, i32 0, i32 1) 560 // CHECK: [[X:%.+]] = load atomic i16, i16* [[X_ADDR:@.+]] monotonic 561 // CHECK: br label %[[CONT:.+]] 562 // CHECK: [[CONT]] 563 // CHECK: [[EXPECTED:%.+]] = phi i16 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 564 // CHECK: [[CONV:%.+]] = zext i16 [[EXPECTED]] to i32 565 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CONV]] to float 566 // <Skip checks for complex calculations> 567 // CHECK: [[X_RE_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[TEMP:%.+]], i32 0, i32 0 568 // CHECK: [[X_RE:%.+]] = load float, float* [[X_RE_ADDR]] 569 // CHECK: [[X_IM_ADDR:%.+]] = getelementptr inbounds { float, float }, { float, float }* [[TEMP]], i32 0, i32 1 570 // CHECK: [[X_IM:%.+]] = load float, float* [[X_IM_ADDR]] 571 // CHECK: [[DESIRED:%.+]] = fptoui float [[X_RE]] to i16 572 // CHECK: store i16 [[DESIRED]], i16* [[TEMP:%.+]] 573 // CHECK: [[DESIRED:%.+]] = load i16, i16* [[TEMP]] 574 // CHECK: [[RES:%.+]] = cmpxchg i16* [[X_ADDR]], i16 [[EXPECTED]], i16 [[DESIRED]] monotonic monotonic 575 // CHECK: [[OLD_X]] = extractvalue { i16, i1 } [[RES]], 0 576 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i16, i1 } [[RES]], 1 577 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 578 // CHECK: [[EXIT]] 579 #pragma omp atomic update 580 usx /= cfv; 581 // CHECK: [[EXPR_RE:%.+]] = load double, double* getelementptr inbounds ({ double, double }, { double, double }* @{{.+}}, i32 0, i32 0) 582 // CHECK: [[EXPR_IM:%.+]] = load double, double* getelementptr inbounds ({ double, double }, { double, double }* @{{.+}}, i32 0, i32 1) 583 // CHECK: [[X:%.+]] = load atomic i64, i64* [[X_ADDR:@.+]] monotonic 584 // CHECK: br label %[[CONT:.+]] 585 // CHECK: [[CONT]] 586 // CHECK: [[EXPECTED:%.+]] = phi i64 [ [[X]], %{{.+}} ], [ [[OLD_X:%.+]], %[[CONT]] ] 587 // CHECK: [[X_RVAL:%.+]] = sitofp i64 [[EXPECTED]] to double 588 // CHECK: [[ADD_RE:%.+]] = fadd double [[X_RVAL]], [[EXPR_RE]] 589 // CHECK: [[ADD_IM:%.+]] = fadd double 0.000000e+00, [[EXPR_IM]] 590 // CHECK: [[DESIRED:%.+]] = fptosi double [[ADD_RE]] to i64 591 // CHECK: store i64 [[DESIRED]], i64* [[TEMP:%.+]] 592 // CHECK: [[DESIRED:%.+]] = load i64, i64* [[TEMP]] 593 // CHECK: [[RES:%.+]] = cmpxchg i64* [[X_ADDR]], i64 [[EXPECTED]], i64 [[DESIRED]] monotonic monotonic 594 // CHECK: [[OLD_X]] = extractvalue { i64, i1 } [[RES]], 0 595 // CHECK: [[SUCCESS_FAIL:%.+]] = extractvalue { i64, i1 } [[RES]], 1 596 // CHECK: br i1 [[SUCCESS_FAIL]], label %[[EXIT:.+]], label %[[CONT]] 597 // CHECK: [[EXIT]] 598 #pragma omp atomic 599 llx += cdv; 600 // CHECK: [[IDX:%.+]] = load i16, i16* @{{.+}} 601 // CHECK: load i8, i8* 602 // CHECK: [[VEC_ITEM_VAL:%.+]] = zext i1 %{{.+}} to i32 603 // CHECK: [[I128VAL:%.+]] = load atomic i128, i128* bitcast (<4 x i32>* [[DEST:@.+]] to i128*) monotonic 604 // CHECK: br label %[[CONT:.+]] 605 // CHECK: [[CONT]] 606 // CHECK: [[OLD_I128:%.+]] = phi i128 [ [[I128VAL]], %{{.+}} ], [ [[FAILED_I128_OLD_VAL:%.+]], %[[CONT]] ] 607 // CHECK: [[BITCAST:%.+]] = bitcast <4 x i32>* [[TEMP:%.+]] to i128* 608 // CHECK: store i128 [[OLD_I128]], i128* [[BITCAST]], 609 // CHECK: [[OLD_VEC_VAL:%.+]] = bitcast i128 [[OLD_I128]] to <4 x i32> 610 // CHECK: store <4 x i32> [[OLD_VEC_VAL]], <4 x i32>* [[LDTEMP:%.+]], 611 // CHECK: [[VEC_VAL:%.+]] = load <4 x i32>, <4 x i32>* [[LDTEMP]] 612 // CHECK: [[ITEM:%.+]] = extractelement <4 x i32> [[VEC_VAL]], i16 [[IDX]] 613 // CHECK: [[OR:%.+]] = or i32 [[ITEM]], [[VEC_ITEM_VAL]] 614 // CHECK: [[VEC_VAL:%.+]] = load <4 x i32>, <4 x i32>* [[TEMP]] 615 // CHECK: [[NEW_VEC_VAL:%.+]] = insertelement <4 x i32> [[VEC_VAL]], i32 [[OR]], i16 [[IDX]] 616 // CHECK: store <4 x i32> [[NEW_VEC_VAL]], <4 x i32>* [[TEMP]] 617 // CHECK: [[NEW_I128:%.+]] = load i128, i128* [[BITCAST]] 618 // CHECK: [[RES:%.+]] = cmpxchg i128* bitcast (<4 x i32>* [[DEST]] to i128*), i128 [[OLD_I128]], i128 [[NEW_I128]] monotonic monotonic 619 // CHECK: [[FAILED_I128_OLD_VAL:%.+]] = extractvalue { i128, i1 } [[RES]], 0 620 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i128, i1 } [[RES]], 1 621 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 622 // CHECK: [[EXIT]] 623 #pragma omp atomic update 624 int4x[sv] |= bv; 625 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 626 // CHECK: [[PREV_VALUE:%.+]] = load atomic i32, i32* bitcast (i8* getelementptr (i8, i8* bitcast (%struct.BitFields* @{{.+}} to i8*), i64 4) to i32*) monotonic 627 // CHECK: br label %[[CONT:.+]] 628 // CHECK: [[CONT]] 629 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i32 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 630 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP1:%.+]], 631 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP:%.+]], 632 // CHECK: [[A_LD:%.+]] = load i32, i32* [[TEMP]], 633 // CHECK: [[A_SHL:%.+]] = shl i32 [[A_LD]], 1 634 // CHECK: [[A_ASHR:%.+]] = ashr i32 [[A_SHL]], 1 635 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[A_ASHR]] to x86_fp80 636 // CHECK: [[SUB:%.+]] = fsub x86_fp80 [[X_RVAL]], [[EXPR]] 637 // CHECK: [[CONV:%.+]] = fptosi x86_fp80 [[SUB]] to i32 638 // CHECK: [[NEW_VAL:%.+]] = load i32, i32* [[TEMP1]], 639 // CHECK: [[BF_VALUE:%.+]] = and i32 [[CONV]], 2147483647 640 // CHECK: [[BF_CLEAR:%.+]] = and i32 [[NEW_VAL]], -2147483648 641 // CHECK: or i32 [[BF_CLEAR]], [[BF_VALUE]] 642 // CHECK: store i32 %{{.+}}, i32* [[TEMP1]] 643 // CHECK: [[NEW_BF_VALUE:%.+]] = load i32, i32* [[TEMP1]] 644 // CHECK: [[RES:%.+]] = cmpxchg i32* bitcast (i8* getelementptr (i8, i8* bitcast (%struct.BitFields* @{{.+}} to i8*), i64 4) to i32*), i32 [[OLD_BF_VALUE]], i32 [[NEW_BF_VALUE]] monotonic monotonic 645 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i32, i1 } [[RES]], 0 646 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i32, i1 } [[RES]], 1 647 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 648 // CHECK: [[EXIT]] 649 #pragma omp atomic 650 bfx.a = bfx.a - ldv; 651 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 652 // CHECK: [[BITCAST:%.+]] = bitcast i32* [[LDTEMP:%.+]] to i8* 653 // CHECK: call void @__atomic_load(i64 4, i8* getelementptr (i8, i8* bitcast (%struct.BitFields_packed* @{{.+}} to i8*), i64 4), i8* [[BITCAST]], i32 0) 654 // CHECK: br label %[[CONT:.+]] 655 // CHECK: [[CONT]] 656 // CHECK: [[PREV_VALUE:%.+]] = load i32, i32* [[LDTEMP]] 657 // CHECK: store i32 [[PREV_VALUE]], i32* [[TEMP1:%.+]], 658 // CHECK: [[PREV_VALUE:%.+]] = load i32, i32* [[LDTEMP]] 659 // CHECK: store i32 [[PREV_VALUE]], i32* [[TEMP:%.+]], 660 // CHECK: [[A_LD:%.+]] = load i32, i32* [[TEMP]], 661 // CHECK: [[A_SHL:%.+]] = shl i32 [[A_LD]], 1 662 // CHECK: [[A_ASHR:%.+]] = ashr i32 [[A_SHL]], 1 663 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[A_ASHR]] to x86_fp80 664 // CHECK: [[MUL:%.+]] = fmul x86_fp80 [[X_RVAL]], [[EXPR]] 665 // CHECK: [[CONV:%.+]] = fptosi x86_fp80 [[MUL]] to i32 666 // CHECK: [[NEW_VAL:%.+]] = load i32, i32* [[TEMP1]], 667 // CHECK: [[BF_VALUE:%.+]] = and i32 [[CONV]], 2147483647 668 // CHECK: [[BF_CLEAR:%.+]] = and i32 [[NEW_VAL]], -2147483648 669 // CHECK: or i32 [[BF_CLEAR]], [[BF_VALUE]] 670 // CHECK: store i32 %{{.+}}, i32* [[TEMP1]] 671 // CHECK: [[BITCAST_TEMP_OLD_BF_ADDR:%.+]] = bitcast i32* [[LDTEMP]] to i8* 672 // CHECK: [[BITCAST_TEMP_NEW_BF_ADDR:%.+]] = bitcast i32* [[TEMP1]] to i8* 673 // CHECK: [[FAIL_SUCCESS:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 4, i8* getelementptr (i8, i8* bitcast (%struct.BitFields_packed* @{{.+}} to i8*), i64 4), i8* [[BITCAST_TEMP_OLD_BF_ADDR]], i8* [[BITCAST_TEMP_NEW_BF_ADDR]], i32 0, i32 0) 674 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 675 // CHECK: [[EXIT]] 676 #pragma omp atomic update 677 bfx_packed.a *= ldv; 678 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 679 // CHECK: [[PREV_VALUE:%.+]] = load atomic i32, i32* getelementptr inbounds (%struct.BitFields2, %struct.BitFields2* @{{.+}}, i32 0, i32 0) monotonic 680 // CHECK: br label %[[CONT:.+]] 681 // CHECK: [[CONT]] 682 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i32 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 683 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP1:%.+]], 684 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP:%.+]], 685 // CHECK: [[A_LD:%.+]] = load i32, i32* [[TEMP]], 686 // CHECK: [[A_ASHR:%.+]] = ashr i32 [[A_LD]], 31 687 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[A_ASHR]] to x86_fp80 688 // CHECK: [[SUB:%.+]] = fsub x86_fp80 [[X_RVAL]], [[EXPR]] 689 // CHECK: [[CONV:%.+]] = fptosi x86_fp80 [[SUB]] to i32 690 // CHECK: [[NEW_VAL:%.+]] = load i32, i32* [[TEMP1]], 691 // CHECK: [[BF_AND:%.+]] = and i32 [[CONV]], 1 692 // CHECK: [[BF_VALUE:%.+]] = shl i32 [[BF_AND]], 31 693 // CHECK: [[BF_CLEAR:%.+]] = and i32 [[NEW_VAL]], 2147483647 694 // CHECK: or i32 [[BF_CLEAR]], [[BF_VALUE]] 695 // CHECK: store i32 %{{.+}}, i32* [[TEMP1]] 696 // CHECK: [[NEW_BF_VALUE:%.+]] = load i32, i32* [[TEMP1]] 697 // CHECK: [[RES:%.+]] = cmpxchg i32* getelementptr inbounds (%struct.BitFields2, %struct.BitFields2* @{{.+}}, i32 0, i32 0), i32 [[OLD_BF_VALUE]], i32 [[NEW_BF_VALUE]] monotonic monotonic 698 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i32, i1 } [[RES]], 0 699 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i32, i1 } [[RES]], 1 700 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 701 // CHECK: [[EXIT]] 702 #pragma omp atomic 703 bfx2.a -= ldv; 704 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 705 // CHECK: [[PREV_VALUE:%.+]] = load atomic i8, i8* getelementptr (i8, i8* bitcast (%struct.BitFields2_packed* @{{.+}} to i8*), i64 3) monotonic 706 // CHECK: br label %[[CONT:.+]] 707 // CHECK: [[CONT]] 708 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i8 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 709 // CHECK: [[BITCAST1:%.+]] = bitcast i32* %{{.+}} to i8* 710 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST1]], 711 // CHECK: [[BITCAST:%.+]] = bitcast i32* %{{.+}} to i8* 712 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST]], 713 // CHECK: [[A_LD:%.+]] = load i8, i8* [[BITCAST]], 714 // CHECK: [[A_ASHR:%.+]] = ashr i8 [[A_LD]], 7 715 // CHECK: [[CAST:%.+]] = sext i8 [[A_ASHR]] to i32 716 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CAST]] to x86_fp80 717 // CHECK: [[DIV:%.+]] = fdiv x86_fp80 [[EXPR]], [[X_RVAL]] 718 // CHECK: [[NEW_VAL:%.+]] = fptosi x86_fp80 [[DIV]] to i32 719 // CHECK: [[TRUNC:%.+]] = trunc i32 [[NEW_VAL]] to i8 720 // CHECK: [[BF_LD:%.+]] = load i8, i8* [[BITCAST1]], 721 // CHECK: [[BF_AND:%.+]] = and i8 [[TRUNC]], 1 722 // CHECK: [[BF_VALUE:%.+]] = shl i8 [[BF_AND]], 7 723 // CHECK: [[BF_CLEAR:%.+]] = and i8 %{{.+}}, 127 724 // CHECK: or i8 [[BF_CLEAR]], [[BF_VALUE]] 725 // CHECK: store i8 %{{.+}}, i8* [[BITCAST1]] 726 // CHECK: [[NEW_BF_VALUE:%.+]] = load i8, i8* [[BITCAST1]] 727 // CHECK: [[RES:%.+]] = cmpxchg i8* getelementptr (i8, i8* bitcast (%struct.BitFields2_packed* @{{.+}} to i8*), i64 3), i8 [[OLD_BF_VALUE]], i8 [[NEW_BF_VALUE]] monotonic monotonic 728 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i8, i1 } [[RES]], 0 729 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i8, i1 } [[RES]], 1 730 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 731 // CHECK: [[EXIT]] 732 #pragma omp atomic update 733 bfx2_packed.a = ldv / bfx2_packed.a; 734 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 735 // CHECK: [[PREV_VALUE:%.+]] = load atomic i32, i32* getelementptr inbounds (%struct.BitFields3, %struct.BitFields3* @{{.+}}, i32 0, i32 0) monotonic 736 // CHECK: br label %[[CONT:.+]] 737 // CHECK: [[CONT]] 738 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i32 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 739 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP1:%.+]], 740 // CHECK: store i32 [[OLD_BF_VALUE]], i32* [[TEMP:%.+]], 741 // CHECK: [[A_LD:%.+]] = load i32, i32* [[TEMP]], 742 // CHECK: [[A_SHL:%.+]] = shl i32 [[A_LD]], 7 743 // CHECK: [[A_ASHR:%.+]] = ashr i32 [[A_SHL]], 18 744 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[A_ASHR]] to x86_fp80 745 // CHECK: [[DIV:%.+]] = fdiv x86_fp80 [[X_RVAL]], [[EXPR]] 746 // CHECK: [[NEW_VAL:%.+]] = fptosi x86_fp80 [[DIV]] to i32 747 // CHECK: [[BF_LD:%.+]] = load i32, i32* [[TEMP1]], 748 // CHECK: [[BF_AND:%.+]] = and i32 [[NEW_VAL]], 16383 749 // CHECK: [[BF_VALUE:%.+]] = shl i32 [[BF_AND]], 11 750 // CHECK: [[BF_CLEAR:%.+]] = and i32 %{{.+}}, -33552385 751 // CHECK: or i32 [[BF_CLEAR]], [[BF_VALUE]] 752 // CHECK: store i32 %{{.+}}, i32* [[TEMP1]] 753 // CHECK: [[NEW_BF_VALUE:%.+]] = load i32, i32* [[TEMP1]] 754 // CHECK: [[RES:%.+]] = cmpxchg i32* getelementptr inbounds (%struct.BitFields3, %struct.BitFields3* @{{.+}}, i32 0, i32 0), i32 [[OLD_BF_VALUE]], i32 [[NEW_BF_VALUE]] monotonic monotonic 755 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i32, i1 } [[RES]], 0 756 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i32, i1 } [[RES]], 1 757 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 758 // CHECK: [[EXIT]] 759 #pragma omp atomic 760 bfx3.a /= ldv; 761 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 762 // CHECK: [[LDTEMP:%.+]] = bitcast i32* %{{.+}} to i24* 763 // CHECK: [[BITCAST:%.+]] = bitcast i24* %{{.+}} to i8* 764 // CHECK: call void @__atomic_load(i64 3, i8* getelementptr (i8, i8* bitcast (%struct.BitFields3_packed* @{{.+}} to i8*), i64 1), i8* [[BITCAST]], i32 0) 765 // CHECK: br label %[[CONT:.+]] 766 // CHECK: [[CONT]] 767 // CHECK: [[PREV_VALUE:%.+]] = load i24, i24* [[LDTEMP]] 768 // CHECK: store i24 [[PREV_VALUE]], i24* [[TEMP1:%.+]], 769 // CHECK: [[PREV_VALUE:%.+]] = load i24, i24* [[LDTEMP]] 770 // CHECK: store i24 [[PREV_VALUE]], i24* [[TEMP:%.+]], 771 // CHECK: [[A_LD:%.+]] = load i24, i24* [[TEMP]], 772 // CHECK: [[A_SHL:%.+]] = shl i24 [[A_LD]], 7 773 // CHECK: [[A_ASHR:%.+]] = ashr i24 [[A_SHL]], 10 774 // CHECK: [[CAST:%.+]] = sext i24 [[A_ASHR]] to i32 775 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CAST]] to x86_fp80 776 // CHECK: [[ADD:%.+]] = fadd x86_fp80 [[X_RVAL]], [[EXPR]] 777 // CHECK: [[NEW_VAL:%.+]] = fptosi x86_fp80 [[ADD]] to i32 778 // CHECK: [[TRUNC:%.+]] = trunc i32 [[NEW_VAL]] to i24 779 // CHECK: [[BF_LD:%.+]] = load i24, i24* [[TEMP1]], 780 // CHECK: [[BF_AND:%.+]] = and i24 [[TRUNC]], 16383 781 // CHECK: [[BF_VALUE:%.+]] = shl i24 [[BF_AND]], 3 782 // CHECK: [[BF_CLEAR:%.+]] = and i24 [[BF_LD]], -131065 783 // CHECK: or i24 [[BF_CLEAR]], [[BF_VALUE]] 784 // CHECK: store i24 %{{.+}}, i24* [[TEMP1]] 785 // CHECK: [[BITCAST_TEMP_OLD_BF_ADDR:%.+]] = bitcast i24* [[LDTEMP]] to i8* 786 // CHECK: [[BITCAST_TEMP_NEW_BF_ADDR:%.+]] = bitcast i24* [[TEMP1]] to i8* 787 // CHECK: [[FAIL_SUCCESS:%.+]] = call zeroext i1 @__atomic_compare_exchange(i64 3, i8* getelementptr (i8, i8* bitcast (%struct.BitFields3_packed* @{{.+}} to i8*), i64 1), i8* [[BITCAST_TEMP_OLD_BF_ADDR]], i8* [[BITCAST_TEMP_NEW_BF_ADDR]], i32 0, i32 0) 788 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 789 // CHECK: [[EXIT]] 790 #pragma omp atomic update 791 bfx3_packed.a += ldv; 792 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 793 // CHECK: [[PREV_VALUE:%.+]] = load atomic i64, i64* bitcast (%struct.BitFields4* @{{.+}} to i64*) monotonic 794 // CHECK: br label %[[CONT:.+]] 795 // CHECK: [[CONT]] 796 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i64 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 797 // CHECK: store i64 [[OLD_BF_VALUE]], i64* [[TEMP1:%.+]], 798 // CHECK: store i64 [[OLD_BF_VALUE]], i64* [[TEMP:%.+]], 799 // CHECK: [[A_LD:%.+]] = load i64, i64* [[TEMP]], 800 // CHECK: [[A_SHL:%.+]] = shl i64 [[A_LD]], 47 801 // CHECK: [[A_ASHR:%.+]] = ashr i64 [[A_SHL:%.+]], 63 802 // CHECK: [[A_CAST:%.+]] = trunc i64 [[A_ASHR:%.+]] to i32 803 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[CAST:%.+]] to x86_fp80 804 // CHECK: [[MUL:%.+]] = fmul x86_fp80 [[X_RVAL]], [[EXPR]] 805 // CHECK: [[NEW_VAL:%.+]] = fptosi x86_fp80 [[MUL]] to i32 806 // CHECK: [[ZEXT:%.+]] = zext i32 [[NEW_VAL]] to i64 807 // CHECK: [[BF_LD:%.+]] = load i64, i64* [[TEMP1]], 808 // CHECK: [[BF_AND:%.+]] = and i64 [[ZEXT]], 1 809 // CHECK: [[BF_VALUE:%.+]] = shl i64 [[BF_AND]], 16 810 // CHECK: [[BF_CLEAR:%.+]] = and i64 [[BF_LD]], -65537 811 // CHECK: or i64 [[BF_CLEAR]], [[BF_VALUE]] 812 // CHECK: store i64 %{{.+}}, i64* [[TEMP1]] 813 // CHECK: [[NEW_BF_VALUE:%.+]] = load i64, i64* [[TEMP1]] 814 // CHECK: [[RES:%.+]] = cmpxchg i64* bitcast (%struct.BitFields4* @{{.+}} to i64*), i64 [[OLD_BF_VALUE]], i64 [[NEW_BF_VALUE]] monotonic monotonic 815 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i64, i1 } [[RES]], 0 816 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i64, i1 } [[RES]], 1 817 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 818 // CHECK: [[EXIT]] 819 #pragma omp atomic 820 bfx4.a = bfx4.a * ldv; 821 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 822 // CHECK: [[PREV_VALUE:%.+]] = load atomic i8, i8* getelementptr inbounds (%struct.BitFields4_packed, %struct.BitFields4_packed* @{{.+}}, i32 0, i32 0, i64 2) monotonic 823 // CHECK: br label %[[CONT:.+]] 824 // CHECK: [[CONT]] 825 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i8 [ [[PREV_VALUE]], %{{.+}} ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 826 // CHECK: [[BITCAST1:%.+]] = bitcast i32* %{{.+}} to i8* 827 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST1]], 828 // CHECK: [[BITCAST:%.+]] = bitcast i32* %{{.+}} to i8* 829 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST]], 830 // CHECK: [[A_LD:%.+]] = load i8, i8* [[BITCAST]], 831 // CHECK: [[A_SHL:%.+]] = shl i8 [[A_LD]], 7 832 // CHECK: [[A_ASHR:%.+]] = ashr i8 [[A_SHL:%.+]], 7 833 // CHECK: [[CAST:%.+]] = sext i8 [[A_ASHR:%.+]] to i32 834 // CHECK: [[CONV:%.+]] = sitofp i32 [[CAST]] to x86_fp80 835 // CHECK: [[SUB: %.+]] = fsub x86_fp80 [[CONV]], [[EXPR]] 836 // CHECK: [[CONV:%.+]] = fptosi x86_fp80 [[SUB:%.+]] to i32 837 // CHECK: [[NEW_VAL:%.+]] = trunc i32 [[CONV]] to i8 838 // CHECK: [[BF_LD:%.+]] = load i8, i8* [[BITCAST1]], 839 // CHECK: [[BF_VALUE:%.+]] = and i8 [[NEW_VAL]], 1 840 // CHECK: [[BF_CLEAR:%.+]] = and i8 [[BF_LD]], -2 841 // CHECK: or i8 [[BF_CLEAR]], [[BF_VALUE]] 842 // CHECK: store i8 %{{.+}}, i8* [[BITCAST1]] 843 // CHECK: [[NEW_BF_VALUE:%.+]] = load i8, i8* [[BITCAST1]] 844 // CHECK: [[RES:%.+]] = cmpxchg i8* getelementptr inbounds (%struct.BitFields4_packed, %struct.BitFields4_packed* @{{.+}}, i32 0, i32 0, i64 2), i8 [[OLD_BF_VALUE]], i8 [[NEW_BF_VALUE]] monotonic monotonic 845 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i8, i1 } [[RES]], 0 846 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i8, i1 } [[RES]], 1 847 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 848 // CHECK: [[EXIT]] 849 #pragma omp atomic update 850 bfx4_packed.a -= ldv; 851 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 852 // CHECK: [[PREV_VALUE:%.+]] = load atomic i64, i64* bitcast (%struct.BitFields4* @{{.+}} to i64*) monotonic 853 // CHECK: br label %[[CONT:.+]] 854 // CHECK: [[CONT]] 855 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i64 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 856 // CHECK: store i64 [[OLD_BF_VALUE]], i64* [[TEMP1:%.+]], 857 // CHECK: store i64 [[OLD_BF_VALUE]], i64* [[TEMP:%.+]], 858 // CHECK: [[A_LD:%.+]] = load i64, i64* [[TEMP]], 859 // CHECK: [[A_SHL:%.+]] = shl i64 [[A_LD]], 40 860 // CHECK: [[A_ASHR:%.+]] = ashr i64 [[A_SHL:%.+]], 57 861 // CHECK: [[CONV:%.+]] = sitofp i64 [[A_ASHR]] to x86_fp80 862 // CHECK: [[DIV:%.+]] = fdiv x86_fp80 [[CONV]], [[EXPR]] 863 // CHECK: [[CONV:%.+]] = fptosi x86_fp80 [[DIV]] to i64 864 // CHECK: [[BF_LD:%.+]] = load i64, i64* [[TEMP1]], 865 // CHECK: [[BF_AND:%.+]] = and i64 [[CONV]], 127 866 // CHECK: [[BF_VALUE:%.+]] = shl i64 [[BF_AND:%.+]], 17 867 // CHECK: [[BF_CLEAR:%.+]] = and i64 [[BF_LD]], -16646145 868 // CHECK: [[VAL:%.+]] = or i64 [[BF_CLEAR]], [[BF_VALUE]] 869 // CHECK: store i64 [[VAL]], i64* [[TEMP1]] 870 // CHECK: [[NEW_BF_VALUE:%.+]] = load i64, i64* [[TEMP1]] 871 // CHECK: [[RES:%.+]] = cmpxchg i64* bitcast (%struct.BitFields4* @{{.+}} to i64*), i64 [[OLD_BF_VALUE]], i64 [[NEW_BF_VALUE]] monotonic monotonic 872 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i64, i1 } [[RES]], 0 873 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i64, i1 } [[RES]], 1 874 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 875 // CHECK: [[EXIT]] 876 #pragma omp atomic 877 bfx4.b /= ldv; 878 // CHECK: [[EXPR:%.+]] = load x86_fp80, x86_fp80* @{{.+}} 879 // CHECK: [[PREV_VALUE:%.+]] = load atomic i8, i8* getelementptr inbounds (%struct.BitFields4_packed, %struct.BitFields4_packed* @{{.+}}, i32 0, i32 0, i64 2) monotonic 880 // CHECK: br label %[[CONT:.+]] 881 // CHECK: [[CONT]] 882 // CHECK: [[OLD_BF_VALUE:%.+]] = phi i8 [ [[PREV_VALUE]], %[[EXIT]] ], [ [[FAILED_OLD_VAL:%.+]], %[[CONT]] ] 883 // CHECK: [[BITCAST1:%.+]] = bitcast i64* %{{.+}} to i8* 884 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST1]], 885 // CHECK: [[BITCAST:%.+]] = bitcast i64* %{{.+}} to i8* 886 // CHECK: store i8 [[OLD_BF_VALUE]], i8* [[BITCAST]], 887 // CHECK: [[A_LD:%.+]] = load i8, i8* [[BITCAST]], 888 // CHECK: [[A_ASHR:%.+]] = ashr i8 [[A_LD]], 1 889 // CHECK: [[CAST:%.+]] = sext i8 [[A_ASHR]] to i64 890 // CHECK: [[CONV:%.+]] = sitofp i64 [[CAST]] to x86_fp80 891 // CHECK: [[ADD:%.+]] = fadd x86_fp80 [[CONV]], [[EXPR]] 892 // CHECK: [[NEW_VAL:%.+]] = fptosi x86_fp80 [[ADD]] to i64 893 // CHECK: [[TRUNC:%.+]] = trunc i64 [[NEW_VAL]] to i8 894 // CHECK: [[BF_LD:%.+]] = load i8, i8* [[BITCAST1]], 895 // CHECK: [[BF_AND:%.+]] = and i8 [[TRUNC]], 127 896 // CHECK: [[BF_VALUE:%.+]] = shl i8 [[BF_AND]], 1 897 // CHECK: [[BF_CLEAR:%.+]] = and i8 [[BF_LD]], 1 898 // CHECK: or i8 [[BF_CLEAR]], [[BF_VALUE]] 899 // CHECK: store i8 %{{.+}}, i8* [[BITCAST1]] 900 // CHECK: [[NEW_BF_VALUE:%.+]] = load i8, i8* [[BITCAST1]] 901 // CHECK: [[RES:%.+]] = cmpxchg i8* getelementptr inbounds (%struct.BitFields4_packed, %struct.BitFields4_packed* @{{.+}}, i32 0, i32 0, i64 2), i8 [[OLD_BF_VALUE]], i8 [[NEW_BF_VALUE]] monotonic monotonic 902 // CHECK: [[FAILED_OLD_VAL]] = extractvalue { i8, i1 } [[RES]], 0 903 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i8, i1 } [[RES]], 1 904 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 905 // CHECK: [[EXIT]] 906 #pragma omp atomic update 907 bfx4_packed.b += ldv; 908 // CHECK: load i64, i64* 909 // CHECK: [[EXPR:%.+]] = uitofp i64 %{{.+}} to float 910 // CHECK: [[I64VAL:%.+]] = load atomic i64, i64* bitcast (<2 x float>* [[DEST:@.+]] to i64*) monotonic 911 // CHECK: br label %[[CONT:.+]] 912 // CHECK: [[CONT]] 913 // CHECK: [[OLD_I64:%.+]] = phi i64 [ [[I64VAL]], %{{.+}} ], [ [[FAILED_I64_OLD_VAL:%.+]], %[[CONT]] ] 914 // CHECK: [[BITCAST:%.+]] = bitcast <2 x float>* [[TEMP:%.+]] to i64* 915 // CHECK: store i64 [[OLD_I64]], i64* [[BITCAST]], 916 // CHECK: [[OLD_VEC_VAL:%.+]] = bitcast i64 [[OLD_I64]] to <2 x float> 917 // CHECK: store <2 x float> [[OLD_VEC_VAL]], <2 x float>* [[LDTEMP:%.+]], 918 // CHECK: [[VEC_VAL:%.+]] = load <2 x float>, <2 x float>* [[LDTEMP]] 919 // CHECK: [[X:%.+]] = extractelement <2 x float> [[VEC_VAL]], i64 0 920 // CHECK: [[VEC_ITEM_VAL:%.+]] = fsub float [[EXPR]], [[X]] 921 // CHECK: [[VEC_VAL:%.+]] = load <2 x float>, <2 x float>* [[TEMP]], 922 // CHECK: [[NEW_VEC_VAL:%.+]] = insertelement <2 x float> [[VEC_VAL]], float [[VEC_ITEM_VAL]], i64 0 923 // CHECK: store <2 x float> [[NEW_VEC_VAL]], <2 x float>* [[TEMP]] 924 // CHECK: [[NEW_I64:%.+]] = load i64, i64* [[BITCAST]] 925 // CHECK: [[RES:%.+]] = cmpxchg i64* bitcast (<2 x float>* [[DEST]] to i64*), i64 [[OLD_I64]], i64 [[NEW_I64]] monotonic monotonic 926 // CHECK: [[FAILED_I64_OLD_VAL:%.+]] = extractvalue { i64, i1 } [[RES]], 0 927 // CHECK: [[FAIL_SUCCESS:%.+]] = extractvalue { i64, i1 } [[RES]], 1 928 // CHECK: br i1 [[FAIL_SUCCESS]], label %[[EXIT:.+]], label %[[CONT]] 929 // CHECK: [[EXIT]] 930 #pragma omp atomic 931 float2x.x = ulv - float2x.x; 932 // CHECK: [[EXPR:%.+]] = load double, double* @{{.+}}, 933 // CHECK: [[OLD_VAL:%.+]] = call i32 @llvm.read_register.i32([[REG:metadata ![0-9]+]]) 934 // CHECK: [[X_RVAL:%.+]] = sitofp i32 [[OLD_VAL]] to double 935 // CHECK: [[DIV:%.+]] = fdiv double [[EXPR]], [[X_RVAL]] 936 // CHECK: [[NEW_VAL:%.+]] = fptosi double [[DIV]] to i32 937 // CHECK: call void @llvm.write_register.i32([[REG]], i32 [[NEW_VAL]]) 938 // CHECK: call{{.*}} @__kmpc_flush( 939 #pragma omp atomic seq_cst 940 rix = dv / rix; 941 return 0; 942 } 943 944 #endif 945