summaryrefslogtreecommitdiffstats
path: root/clang/lib/CodeGen/CGStmtOpenMP.cpp
diff options
context:
space:
mode:
authorAlexey Bataev <a.bataev@hotmail.com>2019-11-04 09:59:11 -0500
committerAlexey Bataev <a.bataev@hotmail.com>2019-11-04 16:09:25 -0500
commit8bbf2e37167d9ac08fa9d3c772d48ca7d9a6f8f6 (patch)
treeb953ffda0932338af7cebd3e04afa6282a88ac19 /clang/lib/CodeGen/CGStmtOpenMP.cpp
parentadbf64ccc9e18278600ebaeadd8f0117eb8e64b1 (diff)
downloadbcm5719-llvm-8bbf2e37167d9ac08fa9d3c772d48ca7d9a6f8f6.tar.gz
bcm5719-llvm-8bbf2e37167d9ac08fa9d3c772d48ca7d9a6f8f6.zip
[OPENMP50]Support for imperfectly nested loops.
Added support for imperfectly nested loops introduced in OpenMP 5.0.
Diffstat (limited to 'clang/lib/CodeGen/CGStmtOpenMP.cpp')
-rw-r--r--clang/lib/CodeGen/CGStmtOpenMP.cpp57
1 files changed, 43 insertions, 14 deletions
diff --git a/clang/lib/CodeGen/CGStmtOpenMP.cpp b/clang/lib/CodeGen/CGStmtOpenMP.cpp
index df4b69e4986..4406fbc4144 100644
--- a/clang/lib/CodeGen/CGStmtOpenMP.cpp
+++ b/clang/lib/CodeGen/CGStmtOpenMP.cpp
@@ -18,6 +18,7 @@
#include "clang/AST/Stmt.h"
#include "clang/AST/StmtOpenMP.h"
#include "clang/AST/DeclOpenMP.h"
+#include "clang/Basic/PrettyStackTrace.h"
using namespace clang;
using namespace CodeGen;
@@ -146,7 +147,8 @@ class OMPLoopScope : public CodeGenFunction::RunCleanupsScope {
const Stmt *Body =
S.getInnermostCapturedStmt()->getCapturedStmt()->IgnoreContainers();
for (unsigned Cnt = 0; Cnt < S.getCollapsedNumber(); ++Cnt) {
- Body = Body->IgnoreContainers();
+ Body = OMPLoopDirective::tryToFindNextInnerLoop(
+ Body, /*TryImperfectlyNestedLoops=*/true);
if (auto *For = dyn_cast<ForStmt>(Body)) {
Body = For->getBody();
} else {
@@ -1339,6 +1341,41 @@ void CodeGenFunction::EmitOMPParallelDirective(const OMPParallelDirective &S) {
[](CodeGenFunction &) { return nullptr; });
}
+static void emitBody(CodeGenFunction &CGF, const Stmt *S, const Stmt *NextLoop,
+ int MaxLevel, int Level = 0) {
+ assert(Level < MaxLevel && "Too deep lookup during loop body codegen.");
+ const Stmt *SimplifiedS = S->IgnoreContainers();
+ if (const auto *CS = dyn_cast<CompoundStmt>(SimplifiedS)) {
+ PrettyStackTraceLoc CrashInfo(
+ CGF.getContext().getSourceManager(), CS->getLBracLoc(),
+ "LLVM IR generation of compound statement ('{}')");
+
+ // Keep track of the current cleanup stack depth, including debug scopes.
+ CodeGenFunction::LexicalScope Scope(CGF, S->getSourceRange());
+ for (const Stmt *CurStmt : CS->body())
+ emitBody(CGF, CurStmt, NextLoop, MaxLevel, Level);
+ return;
+ }
+ if (SimplifiedS == NextLoop) {
+ if (const auto *For = dyn_cast<ForStmt>(SimplifiedS)) {
+ S = For->getBody();
+ } else {
+ assert(isa<CXXForRangeStmt>(SimplifiedS) &&
+ "Expected canonical for loop or range-based for loop.");
+ const auto *CXXFor = cast<CXXForRangeStmt>(SimplifiedS);
+ CGF.EmitStmt(CXXFor->getLoopVarStmt());
+ S = CXXFor->getBody();
+ }
+ if (Level + 1 < MaxLevel) {
+ NextLoop = OMPLoopDirective::tryToFindNextInnerLoop(
+ S, /*TryImperfectlyNestedLoops=*/true);
+ emitBody(CGF, S, NextLoop, MaxLevel, Level + 1);
+ return;
+ }
+ }
+ CGF.EmitStmt(S);
+}
+
void CodeGenFunction::EmitOMPLoopBody(const OMPLoopDirective &D,
JumpDest LoopExit) {
RunCleanupsScope BodyScope(*this);
@@ -1371,20 +1408,12 @@ void CodeGenFunction::EmitOMPLoopBody(const OMPLoopDirective &D,
// Emit loop variables for C++ range loops.
const Stmt *Body =
D.getInnermostCapturedStmt()->getCapturedStmt()->IgnoreContainers();
- for (unsigned Cnt = 0; Cnt < D.getCollapsedNumber(); ++Cnt) {
- Body = Body->IgnoreContainers();
- if (auto *For = dyn_cast<ForStmt>(Body)) {
- Body = For->getBody();
- } else {
- assert(isa<CXXForRangeStmt>(Body) &&
- "Expected canonical for loop or range-based for loop.");
- auto *CXXFor = cast<CXXForRangeStmt>(Body);
- EmitStmt(CXXFor->getLoopVarStmt());
- Body = CXXFor->getBody();
- }
- }
// Emit loop body.
- EmitStmt(D.getBody());
+ emitBody(*this, Body,
+ OMPLoopDirective::tryToFindNextInnerLoop(
+ Body, /*TryImperfectlyNestedLoops=*/true),
+ D.getCollapsedNumber());
+
// The end (updates/cleanups).
EmitBlock(Continue.getBlock());
BreakContinueStack.pop_back();
OpenPOWER on IntegriCloud