LLVM OpenMP
omp_scan_inscan_template.cpp
Go to the documentation of this file.
1// RUN: %libomp-cxx-compile-and-run | FileCheck %s
2
3// Regression test for https://github.com/llvm/llvm-project/issues/191549
4// Inscan reductions with non-dependent types inside function templates were
5// rejected by Clang because the DSA stack was not populated in dependent
6// contexts. This test verifies runtime correctness of both exclusive and
7// inclusive scans in template functions.
8
9#include <cstdlib>
10#include <numeric>
11#include <stdio.h>
12
13#define N 100
14
15template <typename T> bool test_exclusive(T *a, const T *b) {
16 int sum = 0;
17#pragma omp parallel for reduction(inscan, + : sum)
18 for (int i = 0; i < N; i++) {
19 a[i] = sum;
20#pragma omp scan exclusive(sum)
21 sum += b[i];
22 }
23
24 for (int i = 0, prefix = 0; i < N; i++) {
25 if (a[i] != prefix)
26 return false;
27 prefix += b[i];
28 }
29 return true;
30}
31
32template <typename T> bool test_inclusive(T *a, const T *b) {
33 int sum = 0;
34#pragma omp parallel for reduction(inscan, + : sum)
35 for (int i = 0; i < N; i++) {
36 sum += b[i];
37#pragma omp scan inclusive(sum)
38 a[i] = sum;
39 }
40
41 for (int i = 0, prefix = 0; i < N; i++) {
42 prefix += b[i];
43 if (a[i] != prefix)
44 return false;
45 }
46 return true;
47}
48
49int main() {
50 bool success = true;
51
52 int a[N], b[N];
53 std::iota(b, b + N, 1);
54
55 if (test_exclusive<int>(a, b)) {
56 printf("exclusive: PASS\n");
57 } else {
58 printf("exclusive: FAIL\n");
59 success = false;
60 }
61
62 if (test_inclusive<int>(a, b)) {
63 printf("inclusive: PASS\n");
64 } else {
65 printf("inclusive: FAIL\n");
66 success = false;
67 }
68
69 return success ? EXIT_SUCCESS : EXIT_FAILURE;
70}
71
72// CHECK: exclusive: PASS
73// CHECK: inclusive: PASS
#define N
Definition bug54082.c:13
#define i
Definition kmp_stub.cpp:87
int a
bool test_inclusive(T *a, const T *b)
bool test_exclusive(T *a, const T *b)