1// Check that omp atomic compare handles signedness of integer comparisons
2// correctly.
3//
4// At one time, a bug sometimes reversed the signedness.
5
6// RUN: %libomptarget-compile-generic
7// RUN: %libomptarget-run-generic | %fcheck-generic
8// RUN: %libomptarget-compileopt-generic -fopenmp-version=51
9// RUN: %libomptarget-run-generic | %fcheck-generic
10
11// High parallelism increases our chances of detecting a lack of atomicity.
12#define NUM_THREADS_TRY 256
13
14#include <limits.h>
15#include <omp.h>
16#include <stdio.h>
17
18int main() {
19 // CHECK: signed: num_threads=[[#NUM_THREADS:]]{{$}}
20 // CHECK-NEXT: signed: xs=[[#NUM_THREADS-1]]{{$}}
21 int xs = -1;
22 int numThreads;
23#pragma omp target parallel for num_threads(NUM_THREADS_TRY) \
24 map(tofrom : xs, numThreads)
25 for (int i = 0; i < omp_get_num_threads(); ++i) {
26#pragma omp atomic compare
27 if (xs < i) {
28 xs = i;
29 }
30 if (i == 0)
31 numThreads = omp_get_num_threads();
32 }
33 printf(format: "signed: num_threads=%d\n", numThreads);
34 printf(format: "signed: xs=%d\n", xs);
35
36 // CHECK-NEXT: unsigned: xu=0x0{{$}}
37 unsigned xu = UINT_MAX;
38#pragma omp target parallel for num_threads(NUM_THREADS_TRY) map(tofrom : xu)
39 for (int i = 0; i < omp_get_num_threads(); ++i) {
40#pragma omp atomic compare
41 if (xu > i) {
42 xu = i;
43 }
44 }
45 printf(format: "unsigned: xu=0x%x\n", xu);
46 return 0;
47}
48

source code of offload/test/offloading/atomic-compare-signedness.c