}
void VisitStmt(Stmt *S) {
for (Stmt *C : S->children()) {
- if (C && !isa<OMPExecutableDirective>(C))
- Visit(C);
+ if (C) {
+ if (auto *OED = dyn_cast<OMPExecutableDirective>(C)) {
+ // Check implicitly captured vriables in the task-based directives to
+ // check if they must be firstprivatized.
+ if (!OED->hasAssociatedStmt())
+ continue;
+ const Stmt *AS = OED->getAssociatedStmt();
+ if (!AS)
+ continue;
+ for (const CapturedStmt::Capture &Cap :
+ cast<CapturedStmt>(AS)->captures()) {
+ if (Cap.capturesVariable()) {
+ DeclRefExpr *DRE = buildDeclRefExpr(
+ SemaRef, Cap.getCapturedVar(),
+ Cap.getCapturedVar()->getType().getNonLValueExprType(
+ SemaRef.Context),
+ Cap.getLocation(),
+ /*RefersToCapture=*/true);
+ Visit(DRE);
+ }
+ }
+ } else {
+ Visit(C);
+ }
+ }
}
}
// CHECK: call i32 @__kmpc_omp_task([[IDENT_T]]* @{{.+}}, i32 [[GTID]], i8* [[ORIG_TASK_PTR]])
#pragma omp task untied
{
+#pragma omp critical
a = 1;
}
// CHECK: [[ORIG_TASK_PTR:%.+]] = call i8* @__kmpc_omp_task_alloc([[IDENT_T]]* @{{.+}}, i32 [[GTID]], i32 0, i64 40, i64 1,