1//===--- OpenMPKinds.h - OpenMP enums ---------------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8///
9/// \file
10/// Defines some OpenMP-specific enums and functions.
11///
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_BASIC_OPENMPKINDS_H
15#define LLVM_CLANG_BASIC_OPENMPKINDS_H
16
17#include "llvm/ADT/StringRef.h"
18#include "llvm/Frontend/OpenMP/OMPConstants.h"
19
20namespace clang {
21
22/// OpenMP context selector sets.
23enum OpenMPContextSelectorSetKind {
24#define OPENMP_CONTEXT_SELECTOR_SET(Name) OMP_CTX_SET_##Name,
25#include "clang/Basic/OpenMPKinds.def"
26  OMP_CTX_SET_unknown,
27};
28
29/// OpenMP context selectors.
30enum OpenMPContextSelectorKind {
31#define OPENMP_CONTEXT_SELECTOR(Name) OMP_CTX_##Name,
32#include "clang/Basic/OpenMPKinds.def"
33  OMP_CTX_unknown,
34};
35
36OpenMPContextSelectorSetKind getOpenMPContextSelectorSet(llvm::StringRef Str);
37llvm::StringRef
38getOpenMPContextSelectorSetName(OpenMPContextSelectorSetKind Kind);
39OpenMPContextSelectorKind getOpenMPContextSelector(llvm::StringRef Str);
40llvm::StringRef getOpenMPContextSelectorName(OpenMPContextSelectorKind Kind);
41
42/// Struct to store the context selectors info.
43template <typename VectorType, typename ScoreT> struct OpenMPCtxSelectorData {
44  OpenMPContextSelectorSetKind CtxSet = OMP_CTX_SET_unknown;
45  OpenMPContextSelectorKind Ctx = OMP_CTX_unknown;
46  ScoreT Score;
47  VectorType Names;
48  explicit OpenMPCtxSelectorData() = default;
49  explicit OpenMPCtxSelectorData(OpenMPContextSelectorSetKind CtxSet,
50                                 OpenMPContextSelectorKind Ctx,
51                                 const ScoreT &Score, VectorType &&Names)
52      : CtxSet(CtxSet), Ctx(Ctx), Score(Score), Names(Names) {}
53  template <typename U>
54  explicit OpenMPCtxSelectorData(OpenMPContextSelectorSetKind CtxSet,
55                                 OpenMPContextSelectorKind Ctx,
56                                 const ScoreT &Score, const U &Names)
57      : CtxSet(CtxSet), Ctx(Ctx), Score(Score),
58        Names(Names.begin(), Names.end()) {}
59};
60
61/// OpenMP directives.
62using OpenMPDirectiveKind = llvm::omp::Directive;
63
64/// OpenMP clauses.
65enum OpenMPClauseKind {
66#define OPENMP_CLAUSE(Name, Class) \
67  OMPC_##Name,
68#include "clang/Basic/OpenMPKinds.def"
69  OMPC_threadprivate,
70  OMPC_uniform,
71  OMPC_device_type,
72  OMPC_match,
73  OMPC_unknown
74};
75
76/// OpenMP attributes for 'default' clause.
77enum OpenMPDefaultClauseKind {
78#define OPENMP_DEFAULT_KIND(Name) \
79  OMPC_DEFAULT_##Name,
80#include "clang/Basic/OpenMPKinds.def"
81  OMPC_DEFAULT_unknown
82};
83
84/// OpenMP attributes for 'schedule' clause.
85enum OpenMPScheduleClauseKind {
86#define OPENMP_SCHEDULE_KIND(Name) \
87  OMPC_SCHEDULE_##Name,
88#include "clang/Basic/OpenMPKinds.def"
89  OMPC_SCHEDULE_unknown
90};
91
92/// OpenMP modifiers for 'schedule' clause.
93enum OpenMPScheduleClauseModifier {
94  OMPC_SCHEDULE_MODIFIER_unknown = OMPC_SCHEDULE_unknown,
95#define OPENMP_SCHEDULE_MODIFIER(Name) \
96  OMPC_SCHEDULE_MODIFIER_##Name,
97#include "clang/Basic/OpenMPKinds.def"
98  OMPC_SCHEDULE_MODIFIER_last
99};
100
101/// OpenMP attributes for 'depend' clause.
102enum OpenMPDependClauseKind {
103#define OPENMP_DEPEND_KIND(Name) \
104  OMPC_DEPEND_##Name,
105#include "clang/Basic/OpenMPKinds.def"
106  OMPC_DEPEND_unknown
107};
108
109/// OpenMP attributes for 'linear' clause.
110enum OpenMPLinearClauseKind {
111#define OPENMP_LINEAR_KIND(Name) \
112  OMPC_LINEAR_##Name,
113#include "clang/Basic/OpenMPKinds.def"
114  OMPC_LINEAR_unknown
115};
116
117/// OpenMP mapping kind for 'map' clause.
118enum OpenMPMapClauseKind {
119#define OPENMP_MAP_KIND(Name) \
120  OMPC_MAP_##Name,
121#include "clang/Basic/OpenMPKinds.def"
122  OMPC_MAP_unknown
123};
124
125/// OpenMP modifier kind for 'map' clause.
126enum OpenMPMapModifierKind {
127  OMPC_MAP_MODIFIER_unknown = OMPC_MAP_unknown,
128#define OPENMP_MAP_MODIFIER_KIND(Name) \
129  OMPC_MAP_MODIFIER_##Name,
130#include "clang/Basic/OpenMPKinds.def"
131  OMPC_MAP_MODIFIER_last
132};
133
134/// OpenMP modifier kind for 'to' clause.
135enum OpenMPToModifierKind {
136#define OPENMP_TO_MODIFIER_KIND(Name) \
137  OMPC_TO_MODIFIER_##Name,
138#include "clang/Basic/OpenMPKinds.def"
139  OMPC_TO_MODIFIER_unknown
140};
141
142/// OpenMP modifier kind for 'from' clause.
143enum OpenMPFromModifierKind {
144#define OPENMP_FROM_MODIFIER_KIND(Name) \
145  OMPC_FROM_MODIFIER_##Name,
146#include "clang/Basic/OpenMPKinds.def"
147  OMPC_FROM_MODIFIER_unknown
148};
149
150/// OpenMP attributes for 'dist_schedule' clause.
151enum OpenMPDistScheduleClauseKind {
152#define OPENMP_DIST_SCHEDULE_KIND(Name) OMPC_DIST_SCHEDULE_##Name,
153#include "clang/Basic/OpenMPKinds.def"
154  OMPC_DIST_SCHEDULE_unknown
155};
156
157/// OpenMP attributes for 'defaultmap' clause.
158enum OpenMPDefaultmapClauseKind {
159#define OPENMP_DEFAULTMAP_KIND(Name) \
160  OMPC_DEFAULTMAP_##Name,
161#include "clang/Basic/OpenMPKinds.def"
162  OMPC_DEFAULTMAP_unknown
163};
164
165/// OpenMP modifiers for 'defaultmap' clause.
166enum OpenMPDefaultmapClauseModifier {
167  OMPC_DEFAULTMAP_MODIFIER_unknown = OMPC_DEFAULTMAP_unknown,
168#define OPENMP_DEFAULTMAP_MODIFIER(Name) \
169  OMPC_DEFAULTMAP_MODIFIER_##Name,
170#include "clang/Basic/OpenMPKinds.def"
171  OMPC_DEFAULTMAP_MODIFIER_last
172};
173
174/// OpenMP attributes for 'atomic_default_mem_order' clause.
175enum OpenMPAtomicDefaultMemOrderClauseKind {
176#define OPENMP_ATOMIC_DEFAULT_MEM_ORDER_KIND(Name)  \
177  OMPC_ATOMIC_DEFAULT_MEM_ORDER_##Name,
178#include "clang/Basic/OpenMPKinds.def"
179  OMPC_ATOMIC_DEFAULT_MEM_ORDER_unknown
180};
181
182/// OpenMP device type for 'device_type' clause.
183enum OpenMPDeviceType {
184#define OPENMP_DEVICE_TYPE_KIND(Name) \
185  OMPC_DEVICE_TYPE_##Name,
186#include "clang/Basic/OpenMPKinds.def"
187  OMPC_DEVICE_TYPE_unknown
188};
189
190/// OpenMP 'lastprivate' clause modifier.
191enum OpenMPLastprivateModifier {
192#define OPENMP_LASTPRIVATE_KIND(Name) OMPC_LASTPRIVATE_##Name,
193#include "clang/Basic/OpenMPKinds.def"
194  OMPC_LASTPRIVATE_unknown,
195};
196
197/// Scheduling data for loop-based OpenMP directives.
198struct OpenMPScheduleTy final {
199  OpenMPScheduleClauseKind Schedule = OMPC_SCHEDULE_unknown;
200  OpenMPScheduleClauseModifier M1 = OMPC_SCHEDULE_MODIFIER_unknown;
201  OpenMPScheduleClauseModifier M2 = OMPC_SCHEDULE_MODIFIER_unknown;
202};
203
204OpenMPClauseKind getOpenMPClauseKind(llvm::StringRef Str);
205const char *getOpenMPClauseName(OpenMPClauseKind Kind);
206
207unsigned getOpenMPSimpleClauseType(OpenMPClauseKind Kind, llvm::StringRef Str);
208const char *getOpenMPSimpleClauseTypeName(OpenMPClauseKind Kind, unsigned Type);
209
210bool isAllowedClauseForDirective(OpenMPDirectiveKind DKind,
211                                 OpenMPClauseKind CKind,
212                                 unsigned OpenMPVersion);
213
214/// Checks if the specified directive is a directive with an associated
215/// loop construct.
216/// \param DKind Specified directive.
217/// \return true - the directive is a loop-associated directive like 'omp simd'
218/// or 'omp for' directive, otherwise - false.
219bool isOpenMPLoopDirective(OpenMPDirectiveKind DKind);
220
221/// Checks if the specified directive is a worksharing directive.
222/// \param DKind Specified directive.
223/// \return true - the directive is a worksharing directive like 'omp for',
224/// otherwise - false.
225bool isOpenMPWorksharingDirective(OpenMPDirectiveKind DKind);
226
227/// Checks if the specified directive is a taskloop directive.
228/// \param DKind Specified directive.
229/// \return true - the directive is a worksharing directive like 'omp taskloop',
230/// otherwise - false.
231bool isOpenMPTaskLoopDirective(OpenMPDirectiveKind DKind);
232
233/// Checks if the specified directive is a parallel-kind directive.
234/// \param DKind Specified directive.
235/// \return true - the directive is a parallel-like directive like 'omp
236/// parallel', otherwise - false.
237bool isOpenMPParallelDirective(OpenMPDirectiveKind DKind);
238
239/// Checks if the specified directive is a target code offload directive.
240/// \param DKind Specified directive.
241/// \return true - the directive is a target code offload directive like
242/// 'omp target', 'omp target parallel', 'omp target xxx'
243/// otherwise - false.
244bool isOpenMPTargetExecutionDirective(OpenMPDirectiveKind DKind);
245
246/// Checks if the specified directive is a target data offload directive.
247/// \param DKind Specified directive.
248/// \return true - the directive is a target data offload directive like
249/// 'omp target data', 'omp target update', 'omp target enter data',
250/// 'omp target exit data'
251/// otherwise - false.
252bool isOpenMPTargetDataManagementDirective(OpenMPDirectiveKind DKind);
253
254/// Checks if the specified composite/combined directive constitutes a teams
255/// directive in the outermost nest.  For example
256/// 'omp teams distribute' or 'omp teams distribute parallel for'.
257/// \param DKind Specified directive.
258/// \return true - the directive has teams on the outermost nest, otherwise -
259/// false.
260bool isOpenMPNestingTeamsDirective(OpenMPDirectiveKind DKind);
261
262/// Checks if the specified directive is a teams-kind directive.  For example,
263/// 'omp teams distribute' or 'omp target teams'.
264/// \param DKind Specified directive.
265/// \return true - the directive is a teams-like directive, otherwise - false.
266bool isOpenMPTeamsDirective(OpenMPDirectiveKind DKind);
267
268/// Checks if the specified directive is a simd directive.
269/// \param DKind Specified directive.
270/// \return true - the directive is a simd directive like 'omp simd',
271/// otherwise - false.
272bool isOpenMPSimdDirective(OpenMPDirectiveKind DKind);
273
274/// Checks if the specified directive is a distribute directive.
275/// \param DKind Specified directive.
276/// \return true - the directive is a distribute-directive like 'omp
277/// distribute',
278/// otherwise - false.
279bool isOpenMPDistributeDirective(OpenMPDirectiveKind DKind);
280
281/// Checks if the specified composite/combined directive constitutes a
282/// distribute directive in the outermost nest.  For example,
283/// 'omp distribute parallel for' or 'omp distribute'.
284/// \param DKind Specified directive.
285/// \return true - the directive has distribute on the outermost nest.
286/// otherwise - false.
287bool isOpenMPNestingDistributeDirective(OpenMPDirectiveKind DKind);
288
289/// Checks if the specified clause is one of private clauses like
290/// 'private', 'firstprivate', 'reduction' etc..
291/// \param Kind Clause kind.
292/// \return true - the clause is a private clause, otherwise - false.
293bool isOpenMPPrivate(OpenMPClauseKind Kind);
294
295/// Checks if the specified clause is one of threadprivate clauses like
296/// 'threadprivate', 'copyin' or 'copyprivate'.
297/// \param Kind Clause kind.
298/// \return true - the clause is a threadprivate clause, otherwise - false.
299bool isOpenMPThreadPrivate(OpenMPClauseKind Kind);
300
301/// Checks if the specified directive kind is one of tasking directives - task,
302/// taskloop, taksloop simd, master taskloop, parallel master taskloop, master
303/// taskloop simd, or parallel master taskloop simd.
304bool isOpenMPTaskingDirective(OpenMPDirectiveKind Kind);
305
306/// Checks if the specified directive kind is one of the composite or combined
307/// directives that need loop bound sharing across loops outlined in nested
308/// functions
309bool isOpenMPLoopBoundSharingDirective(OpenMPDirectiveKind Kind);
310
311/// Return the captured regions of an OpenMP directive.
312void getOpenMPCaptureRegions(
313    llvm::SmallVectorImpl<OpenMPDirectiveKind> &CaptureRegions,
314    OpenMPDirectiveKind DKind);
315}
316
317#endif
318
319