FLANG
check-omp-structure.h
1//===-- lib/Semantics/check-omp-structure.h ---------------------*- 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// OpenMP structure validity check list
10// 1. invalid clauses on directive
11// 2. invalid repeated clauses on directive
12// 3. TODO: invalid nesting of regions
13
14#ifndef FORTRAN_SEMANTICS_CHECK_OMP_STRUCTURE_H_
15#define FORTRAN_SEMANTICS_CHECK_OMP_STRUCTURE_H_
16
17#include "check-directive-structure.h"
18#include "flang/Common/enum-set.h"
19#include "flang/Parser/parse-tree.h"
20#include "flang/Semantics/openmp-directive-sets.h"
21#include "flang/Semantics/semantics.h"
22
23using OmpClauseSet =
25
26#define GEN_FLANG_DIRECTIVE_CLAUSE_SETS
27#include "llvm/Frontend/OpenMP/OMP.inc"
28
29namespace llvm {
30namespace omp {
31static OmpClauseSet privateSet{
32 Clause::OMPC_private, Clause::OMPC_firstprivate, Clause::OMPC_lastprivate};
33static OmpClauseSet privateReductionSet{
34 OmpClauseSet{Clause::OMPC_reduction} | privateSet};
35} // namespace omp
36} // namespace llvm
37
38namespace Fortran::semantics {
39struct AnalyzedCondStmt;
40
41namespace omp {
42struct LoopSequence;
43}
44
45// Mapping from 'Symbol' to 'Source' to keep track of the variables
46// used in multiple clauses
47using SymbolSourceMap = std::multimap<const Symbol *, parser::CharBlock>;
48// Multimap to check the triple <current_dir, enclosing_dir, enclosing_clause>
49using DirectivesClauseTriple = std::multimap<llvm::omp::Directive,
50 std::pair<llvm::omp::Directive, const OmpClauseSet>>;
51
52using OmpStructureCheckerBase = DirectiveStructureChecker<llvm::omp::Directive,
53 llvm::omp::Clause, parser::OmpClause, llvm::omp::Clause_enumSize>;
54
55class OmpStructureChecker : public OmpStructureCheckerBase {
56public:
57 using Base = OmpStructureCheckerBase;
58
59 OmpStructureChecker(SemanticsContext &context);
60
61 void Enter(const parser::ProgramUnit &);
62 void Enter(const parser::MainProgram &);
63 void Leave(const parser::MainProgram &);
64 void Enter(const parser::BlockData &);
65 void Leave(const parser::BlockData &);
66 void Enter(const parser::Module &);
67 void Leave(const parser::Module &);
68 void Enter(const parser::Submodule &);
69 void Leave(const parser::Submodule &);
70 void Enter(const parser::SubroutineStmt &);
71 void Enter(const parser::EndSubroutineStmt &);
72 void Enter(const parser::FunctionStmt &);
73 void Enter(const parser::EndFunctionStmt &);
74 void Enter(const parser::MpSubprogramStmt &);
75 void Enter(const parser::EndMpSubprogramStmt &);
76 void Enter(const parser::BlockConstruct &);
77 void Leave(const parser::BlockConstruct &);
78 void Enter(const parser::InternalSubprogram &);
79 void Enter(const parser::ModuleSubprogram &);
80
81 void Enter(const parser::SpecificationPart &);
82 void Leave(const parser::SpecificationPart &);
83 void Enter(const parser::ExecutionPart &);
84 void Leave(const parser::ExecutionPart &);
85
86 void Enter(const parser::OpenMPConstruct &);
87 void Leave(const parser::OpenMPConstruct &);
88 void Enter(const parser::OpenMPDeclarativeConstruct &);
89 void Leave(const parser::OpenMPDeclarativeConstruct &);
90
91 void Enter(const parser::OpenMPMisplacedEndDirective &);
92 void Leave(const parser::OpenMPMisplacedEndDirective &);
93 void Enter(const parser::OpenMPInvalidDirective &);
94 void Leave(const parser::OpenMPInvalidDirective &);
95
96 void Enter(const parser::OpenMPLoopConstruct &);
97 void Leave(const parser::OpenMPLoopConstruct &);
98
99 void Enter(const parser::OpenMPInteropConstruct &);
100 void Enter(const parser::OmpBlockConstruct &);
101 void Leave(const parser::OmpBlockConstruct &);
102 void Enter(const parser::OmpBeginDirective &);
103 void Leave(const parser::OmpBeginDirective &);
104 void Enter(const parser::OmpEndDirective &);
105 void Leave(const parser::OmpEndDirective &);
106
107 void Enter(const parser::OpenMPSectionsConstruct &);
108 void Enter(const parser::OmpEndSectionsDirective &);
109 void Leave(const parser::OmpEndSectionsDirective &);
110
111 void Enter(const parser::OmpDeclareVariantDirective &);
112 void Enter(const parser::OmpDeclareSimdDirective &);
113 void Enter(const parser::OmpAllocateDirective &);
114 void Leave(const parser::OmpAllocateDirective &);
115 void Enter(const parser::OmpDeclareMapperDirective &);
116 void Enter(const parser::OmpDeclareReductionDirective &);
117 void Enter(const parser::OmpDeclareTargetDirective &);
118 void Leave(const parser::OmpDeclareTargetDirective &);
119 void Enter(const parser::OpenMPDepobjConstruct &);
120 void Enter(const parser::OpenMPDispatchConstruct &);
121 void Enter(const parser::OpenMPAllocatorsConstruct &);
122 void Enter(const parser::OmpRequiresDirective &);
123 void Enter(const parser::OmpGroupprivateDirective &);
124 void Leave(const parser::OmpThreadprivateDirective &);
125
126 void Enter(const parser::OpenMPSimpleStandaloneConstruct &);
127 void Leave(const parser::OpenMPSimpleStandaloneConstruct &);
128 void Leave(const parser::OpenMPFlushConstruct &);
129 void Enter(const parser::OpenMPCancelConstruct &);
131 void Enter(const parser::OpenMPCriticalConstruct &);
132 void Enter(const parser::OpenMPAtomicConstruct &);
133
134 void Leave(const parser::OmpClauseList &);
135 void Enter(const parser::OmpClause &);
136
137 void Enter(const parser::DoConstruct &);
138 void Leave(const parser::DoConstruct &);
139
140 void Enter(const parser::OmpDirectiveSpecification &);
141 void Leave(const parser::OmpDirectiveSpecification &);
142
143 void Enter(const parser::OmpMetadirectiveDirective &);
144 void Leave(const parser::OmpMetadirectiveDirective &);
145
146 void Enter(const parser::OmpContextSelector &);
147 void Leave(const parser::OmpContextSelector &);
148
149 template <typename A> void Enter(const parser::Statement<A> &);
150 void Leave(const parser::GotoStmt &);
151 void Leave(const parser::ComputedGotoStmt &);
152 void Leave(const parser::ArithmeticIfStmt &);
153 void Leave(const parser::AssignedGotoStmt &);
154 void Leave(const parser::AltReturnSpec &);
155 void Leave(const parser::ErrLabel &);
156 void Leave(const parser::EndLabel &);
157 void Leave(const parser::EorLabel &);
158
159#define GEN_FLANG_CLAUSE_CHECK_ENTER
160#include "llvm/Frontend/OpenMP/OMP.inc"
161
162private:
163 using LoopOrConstruct = std::variant<const parser::DoConstruct *,
165
166 // Most of these functions are defined in check-omp-structure.cpp, but
167 // some groups have their own files.
168
169 // check-omp-atomic.cpp
170 void CheckStorageOverlap(const evaluate::Expr<evaluate::SomeType> &,
172 void ErrorShouldBeVariable(const MaybeExpr &expr, parser::CharBlock source);
173 void CheckAtomicType(SymbolRef sym, parser::CharBlock source,
174 std::string_view name, bool checkTypeOnPointer = true);
175 void CheckAtomicVariable(const evaluate::Expr<evaluate::SomeType> &,
176 parser::CharBlock, bool checkTypeOnPointer = true);
177 std::pair<const parser::ExecutionPartConstruct *,
179 CheckUpdateCapture(const parser::ExecutionPartConstruct *ec1,
181 void CheckAtomicCaptureAssignment(const evaluate::Assignment &capture,
182 const SomeExpr &atom, parser::CharBlock source);
183 void CheckAtomicReadAssignment(
184 const evaluate::Assignment &read, parser::CharBlock source);
185 void CheckAtomicWriteAssignment(
186 const evaluate::Assignment &write, parser::CharBlock source);
187 std::optional<evaluate::Assignment> CheckAtomicUpdateAssignment(
188 const evaluate::Assignment &update, parser::CharBlock source);
189 std::pair<bool, bool> CheckAtomicUpdateAssignmentRhs(const SomeExpr &atom,
190 const SomeExpr &rhs, parser::CharBlock source, bool suppressDiagnostics);
191 void CheckAtomicConditionalUpdateAssignment(const SomeExpr &cond,
192 parser::CharBlock condSource, const evaluate::Assignment &assign,
193 parser::CharBlock assignSource);
194 void CheckAtomicConditionalUpdateStmt(
195 const AnalyzedCondStmt &update, parser::CharBlock source);
196 void CheckAtomicUpdateOnly(const parser::OpenMPAtomicConstruct &x,
197 const parser::Block &body, parser::CharBlock source);
198 void CheckAtomicConditionalUpdate(const parser::OpenMPAtomicConstruct &x,
199 const parser::Block &body, parser::CharBlock source);
200 void CheckAtomicUpdateCapture(const parser::OpenMPAtomicConstruct &x,
201 const parser::Block &body, parser::CharBlock source);
202 void CheckAtomicConditionalUpdateCapture(
203 const parser::OpenMPAtomicConstruct &x, const parser::Block &body,
204 parser::CharBlock source);
205 void CheckAtomicRead(const parser::OpenMPAtomicConstruct &x);
206 void CheckAtomicWrite(const parser::OpenMPAtomicConstruct &x);
207 void CheckAtomicUpdate(const parser::OpenMPAtomicConstruct &x);
208
209 // check-omp-loop.cpp
210 void HasInvalidDistributeNesting(const parser::OpenMPLoopConstruct &x);
211 void HasInvalidLoopBinding(const parser::OpenMPLoopConstruct &x);
212 void CheckSIMDNest(const parser::OpenMPConstruct &x);
213 void CheckRectangularNest(const parser::OmpDirectiveSpecification &spec,
214 const omp::LoopSequence &nest);
215 void CheckNestedConstruct(const parser::OpenMPLoopConstruct &x);
216 const parser::Name GetLoopIndex(const parser::DoConstruct *x);
217 void CheckIterationVariables(const parser::OpenMPLoopConstruct &x);
218 std::int64_t GetOrdCollapseLevel(const parser::OpenMPLoopConstruct &x);
219 void CheckAssociatedLoopConstraints(const parser::OpenMPLoopConstruct &x);
220 void CheckScanModifier(const parser::OmpClause::Reduction &x);
221 void CheckDistLinear(const parser::OpenMPLoopConstruct &x);
222
223 // check-omp-variant.cpp
224 void CheckOmpDeclareVariantDirective(
226 void CheckDeclareVariantUserConditions(const parser::OmpContextSelector &);
227 const std::list<parser::OmpTraitProperty> &GetTraitPropertyList(
229 std::optional<llvm::omp::Clause> GetClauseFromProperty(
231
232 void CheckTraitSelectorList(const std::list<parser::OmpTraitSelector> &);
233 void CheckContextSelectorSpecification(const parser::OmpContextSelector &);
234 void CheckTraitSetSelector(const parser::OmpTraitSetSelector &);
235 void CheckTraitScore(const parser::OmpTraitScore &);
236 bool VerifyTraitPropertyLists(
238 void CheckTraitSelector(
240 void CheckTraitADMO(
242 void CheckTraitCondition(
244 void CheckTraitDeviceNum(
246 void CheckTraitRequires(
248 void CheckTraitSimd(
250
251 // check-omp-structure.cpp
252 bool IsAllowedClause(llvm::omp::Clause clauseId);
253 bool CheckAllowedClause(llvm::omp::Clause clause);
254 void CheckArgumentObjectKind(const parser::OmpClause &x);
255 void CheckDirectiveSpelling(
256 parser::CharBlock spelling, llvm::omp::Directive id);
257 void CheckDirectiveDeprecation(const parser::OpenMPConstruct &x);
258 void AnalyzeObject(const parser::OmpObject &object);
259
260 const parser::OpenMPConstruct *GetCurrentConstruct() const;
261 void CheckSourceLabel(const parser::Label &);
262 void CheckLabelContext(const parser::CharBlock, const parser::CharBlock,
264 void ClearLabels();
265 void CheckMultipleOccurrence(semantics::UnorderedSymbolSet &listVars,
266 const std::list<parser::Name> &nameList, const parser::CharBlock &item,
267 const std::string &clauseName);
268 void CheckMultListItems();
269 void CheckStructureComponent(
270 const parser::OmpObject &object, llvm::omp::Clause clauseId);
271 void CheckStructureComponent(
272 const parser::OmpObjectList &objects, llvm::omp::Clause clauseId);
273 bool HasInvalidWorksharingNesting(
274 const parser::OmpDirectiveName &name, const OmpDirectiveSet &);
275
276 bool IsCloselyNestedRegion(const OmpDirectiveSet &set);
277 bool IsNestedInDirective(llvm::omp::Directive directive);
278 bool IsCombinedParallelWorksharing(llvm::omp::Directive directive) const;
279 bool InTargetRegion();
280 void HasInvalidTeamsNesting(
281 const llvm::omp::Directive &dir, const parser::CharBlock &source);
282 bool HasRequires(llvm::omp::Clause req);
283 void CheckAllowedMapTypes(
284 parser::OmpMapType::Value, llvm::ArrayRef<parser::OmpMapType::Value>);
285
286 llvm::StringRef getClauseName(llvm::omp::Clause clause) override;
287 llvm::StringRef getDirectiveName(llvm::omp::Directive directive) override;
288
289 template < //
290 typename LessTy, typename RangeTy,
291 typename IterTy = decltype(std::declval<RangeTy>().begin())>
292 std::optional<IterTy> FindDuplicate(RangeTy &&);
293
294 void CheckDependList(const parser::DataRef &);
295 void CheckDoacross(const parser::OmpDoacross &doa);
296 void CheckDimsModifier(parser::CharBlock source, size_t numValues,
297 const parser::OmpDimsModifier &x);
298 void CheckTypeParamInquiry(const parser::CharBlock &source,
299 const parser::OmpObject &object, llvm::omp::Directive dirId);
300 void CheckTypeParamInquiry(const parser::CharBlock &source,
301 const parser::OmpObject &object, llvm::omp::Clause clauseId);
302 void CheckVarIsNotPartOfAnotherVar(const parser::CharBlock &source,
303 const parser::OmpObject &object, llvm::StringRef clause = "");
304 void CheckVarIsNotPartOfAnotherVar(const parser::CharBlock &source,
305 const parser::OmpObjectList &objList, llvm::StringRef clause = "");
306 void CheckThreadprivateOrDeclareTargetVar(const parser::Designator &);
307 void CheckThreadprivateOrDeclareTargetVar(const parser::Name &);
308 void CheckThreadprivateOrDeclareTargetVar(const parser::OmpObject &);
309 void CheckThreadprivateOrDeclareTargetVar(const parser::OmpObjectList &);
310 void CheckIntentInPointer(SymbolSourceMap &, const llvm::omp::Clause);
311 void CheckProcedurePointer(SymbolSourceMap &, const llvm::omp::Clause);
312 void CheckCrayPointee(const parser::OmpObjectList &objectList,
313 llvm::StringRef clause, bool suggestToUseCrayPointer = true);
314 void GetSymbolsInObjectList(const parser::OmpObjectList &, SymbolSourceMap &);
315 void CheckDefinableObjects(SymbolSourceMap &, const llvm::omp::Clause);
316 void CheckCopyingPolymorphicAllocatable(
317 SymbolSourceMap &, const llvm::omp::Clause);
318 void CheckPrivateSymbolsInOuterCxt(
319 SymbolSourceMap &, DirectivesClauseTriple &, const llvm::omp::Clause);
320 bool CheckTargetBlockOnlyTeams(const parser::Block &);
321 void CheckWorkshareBlockStmts(const parser::Block &, parser::CharBlock);
322 void CheckWorkdistributeBlockStmts(const parser::Block &, parser::CharBlock);
323 void CheckIndividualAllocateDirective(
324 const parser::OmpAllocateDirective &x, bool isExecutable);
325 void CheckExecutableAllocateDirective(const parser::OmpAllocateDirective &x);
326
327 void CheckIteratorRange(const parser::OmpIteratorSpecifier &x);
328 void CheckIteratorModifier(const parser::OmpIterator &x);
329
330 void CheckTargetNest(const parser::OpenMPConstruct &x);
331 void CheckTargetUpdate();
332 void CheckTaskgraph(const parser::OmpBlockConstruct &x);
333 void CheckDependenceType(const parser::OmpDependenceType::Value &x);
334 void CheckTaskDependenceType(const parser::OmpTaskDependenceType::Value &x);
335 std::optional<llvm::omp::Directive> GetCancelType(
336 llvm::omp::Directive cancelDir, const parser::CharBlock &cancelSource,
337 const std::optional<parser::OmpClauseList> &maybeClauses);
338 void CheckCancellationNest(
339 const parser::CharBlock &source, llvm::omp::Directive type);
340 void CheckReductionObjects(
341 const parser::OmpObjectList &objects, llvm::omp::Clause clauseId);
342 bool CheckReductionOperator(const parser::OmpReductionIdentifier &ident,
343 parser::CharBlock source, llvm::omp::Clause clauseId);
344 void CheckReductionObjectTypes(const parser::OmpObjectList &objects,
345 const parser::OmpReductionIdentifier &ident);
346 void CheckReductionModifier(const parser::OmpReductionModifier &);
347 void CheckLastprivateModifier(const parser::OmpLastprivateModifier &);
348 void CheckSingleConstruct(const parser::OmpBlockConstruct &x);
349 void CheckMasterNesting(const parser::OmpBlockConstruct &x);
350 void ChecksOnOrderedAsBlock();
351 void CheckBarrierNesting(const parser::OpenMPSimpleStandaloneConstruct &x);
352 void CheckScan(const parser::OpenMPSimpleStandaloneConstruct &x);
353 void ChecksOnOrderedAsStandalone();
354 void CheckOrderedDependClause(std::optional<std::int64_t> orderedValue);
355 void CheckReductionArraySection(
356 const parser::OmpObjectList &ompObjectList, llvm::omp::Clause clauseId);
357 void CheckArraySection(const parser::ArrayElement &arrayElement,
358 const parser::Name &name, const llvm::omp::Clause clause);
359 void CheckLastPartRefForArraySection(
360 const parser::Designator &designator, llvm::omp::Clause clauseId);
361 void CheckSharedBindingInOuterContext(
362 const parser::OmpObjectList &ompObjectList);
363 void CheckIfContiguous(const parser::OmpObject &object);
364 const parser::Name *GetObjectName(const parser::OmpObject &object);
365 void CheckInitOnDepobj(const parser::OpenMPDepobjConstruct &depobj,
366 const parser::OmpClause &initClause);
367 void CheckAllowedRequiresClause(llvm::omp::Clause clause);
368 void AddEndDirectiveClauses(const parser::OmpClauseList &clauses);
369
370 void EnterDirectiveNest(const int index) { directiveNest_[index]++; }
371 void ExitDirectiveNest(const int index) { directiveNest_[index]--; }
372 int GetDirectiveNest(const int index) { return directiveNest_[index]; }
373
374 bool deviceConstructFound_{false};
375 enum directiveNestType : int {
376 SIMDNest,
377 TargetBlockOnlyTeams,
378 TargetNest,
379 DeclarativeNest,
380 ContextSelectorNest,
381 MetadirectiveNest,
382 LastType = MetadirectiveNest,
383 };
384 int directiveNest_[LastType + 1] = {0};
385
386 std::set<std::pair<const Symbol *, const Symbol *>> declareVariantPairs_;
387
388 int allocateDirectiveLevel_{0};
389 parser::CharBlock visitedAtomicSource_;
390
391 // Stack of nested DO loops and OpenMP constructs.
392 // This is used to verify DO loop nest for DOACROSS, and branches into
393 // and out of OpenMP constructs.
394 std::vector<LoopOrConstruct> constructStack_;
395 // Scopes for scoping units.
396 std::vector<const Scope *> scopeStack_;
397 // Stack of directive specifications (except for SECTION).
398 // This is to allow visitor functions to see all specified clauses, since
399 // they are only recorded in DirectiveContext as they are processed.
400 std::vector<const parser::OmpDirectiveSpecification *> dirStack_;
401
402 enum class PartKind : int {
403 // There are also other "parts", such as internal-subprogram-part, etc,
404 // but we're keeping track of these two for now.
405 SpecificationPart,
406 ExecutionPart,
407 };
408 std::vector<PartKind> partStack_;
409
410 std::multimap<const parser::Label,
411 std::pair<parser::CharBlock, const parser::OpenMPConstruct *>>
412 sourceLabels_;
413 std::map<const parser::Label,
414 std::pair<parser::CharBlock, const parser::OpenMPConstruct *>>
415 targetLabels_;
416 parser::CharBlock currentStatementSource_;
417};
418
419template <typename A>
420void OmpStructureChecker::Enter(const parser::Statement<A> &statement) {
421 currentStatementSource_ = statement.source;
422 // Keep track of the labels in all the labelled statements
423 if (statement.label) {
424 auto label{statement.label.value()};
425 // Get the context to check if the labelled statement is in an
426 // enclosing OpenMP construct
427 auto *thisConstruct{GetCurrentConstruct()};
428 targetLabels_.emplace(
429 label, std::make_pair(currentStatementSource_, thisConstruct));
430 // Check if a statement that causes a jump to the 'label'
431 // has already been encountered
432 auto range{sourceLabels_.equal_range(label)};
433 for (auto it{range.first}; it != range.second; ++it) {
434 // Check if both the statement with 'label' and the statement that
435 // causes a jump to the 'label' are in the same scope
436 CheckLabelContext(it->second.first, currentStatementSource_,
437 it->second.second, thisConstruct);
438 }
439 }
440}
441
444template <typename LessTy, typename RangeTy, typename IterTy>
445std::optional<IterTy> OmpStructureChecker::FindDuplicate(RangeTy &&range) {
446 // Deal with iterators, since the actual elements may be rvalues (i.e.
447 // have no addresses), for example with custom-constructed ranges that
448 // are not simple c.begin()..c.end().
449 std::set<IterTy, LessTy> uniq;
450 for (auto it{range.begin()}, end{range.end()}; it != end; ++it) {
451 if (!uniq.insert(it).second) {
452 return it;
453 }
454 }
455 return std::nullopt;
456}
457
458} // namespace Fortran::semantics
459#endif // FORTRAN_SEMANTICS_CHECK_OMP_STRUCTURE_H_
Definition enum-set.h:28
Definition expression.h:921
Definition common.h:215
Definition char-block.h:28
Definition check-directive-structure.h:208
Definition semantics.h:68
Definition FIRType.h:103
Definition parse-tree.h:3537
Definition parse-tree.h:1939
Definition parse-tree.h:3547
Definition parse-tree.h:2223
Definition parse-tree.h:3061
Definition parse-tree.h:2551
Definition parse-tree.h:1849
Definition parse-tree.h:1888
Definition parse-tree.h:2366
Definition parse-tree.h:559
Definition parse-tree.h:3181
Definition parse-tree.h:468
Definition parse-tree.h:2970
Definition parse-tree.h:2984
Definition parse-tree.h:3005
Definition parse-tree.h:592
Definition parse-tree.h:5364
Definition parse-tree.h:5153
Definition parse-tree.h:5163
Definition parse-tree.h:5122
Definition parse-tree.h:5106
Definition parse-tree.h:5291
Definition parse-tree.h:5308
Definition parse-tree.h:5283
Definition parse-tree.h:3573
Definition parse-tree.h:5129
Definition parse-tree.h:4553
Definition parse-tree.h:5158
Definition parse-tree.h:5233
Definition parse-tree.h:5317
Definition parse-tree.h:5176
Definition parse-tree.h:3618
Definition parse-tree.h:3606
Definition parse-tree.h:3662
Definition parse-tree.h:5324
Definition parse-tree.h:5330
Definition parse-tree.h:5390
Definition parse-tree.h:5395
Definition parse-tree.h:5432
Definition parse-tree.h:5516
Definition parse-tree.h:5380
Definition parse-tree.h:5443
Definition parse-tree.h:5457
Definition parse-tree.h:5473
Definition parse-tree.h:5481
Definition parse-tree.h:5534
Definition parse-tree.h:5502
Definition parse-tree.h:5248
Definition parse-tree.h:576
Definition parse-tree.h:456
Definition parse-tree.h:362
Definition parse-tree.h:3047
Definition parse-tree.h:3200
Definition parse-tree.h:4055
Definition parse-tree.h:4121
Definition parse-tree.h:4131
Definition parse-tree.h:4139
Definition parse-tree.h:4280
Definition parse-tree.h:3808
Definition parse-tree.h:3774
Definition parse-tree.h:3847
Definition parse-tree.h:3869
Definition check-omp-atomic.cpp:242
Definition openmp-utils.h:303