r255001 - Add parse and sema for OpenMP distribute directive and all its clauses excluding dist_schedule.

Carlo Bertolli via cfe-commits cfe-commits at lists.llvm.org
Thu Dec 10 11:54:06 PST 2015


Hi Hans

It was already reverted.

In the meantime Jonas found the problem - attached his patch that applies
on top of the distribute one.. We were finally able to replicate the
problem by compiling clang with the address sanitizer.
Apologies it took so long (traveling got in the way).

(See attached file: FixOMPDistribute.diff)

I am adapting the whole distribute patch to build on top of the latest
revision and we will re-run tests with the sanitizer before committing.


Many thanks!

-- Carlo



From:	Hans Wennborg <hans at chromium.org>
To:	Carlo Bertolli/Watson/IBM at IBMUS
Cc:	Alexey Samsonov <vonosmas at gmail.com>, cfe-commits
            <cfe-commits at lists.llvm.org>
Date:	12/10/2015 01:45 PM
Subject:	Re: r255001 - Add parse and sema for OpenMP distribute
            directive and all its clauses excluding dist_schedule.
Sent by:	hwennborg at google.com



It fails on Windows too. I was using a 32-bit build on Windows
with -DCMAKE_BUILD_TYPE=Release -DLLVM_ENABLE_ASSERTIONS=ON.

If you need more time for fixing this, please consider reverting it in the
meantime.

Thanks,
Hans

On Tue, Dec 8, 2015 at 12:58 PM, Carlo Bertolli via cfe-commits <
cfe-commits at lists.llvm.org> wrote:
  Hi

  I was unable to replicate the errors. This is what I tried:

  - Run check-clang on ppc64le linux ubuntu 14.04, debug mode, llvm and
  clang compiled with clang 3.7.

  - Run check-clang on x86-64 linux, debug and release modes, llvm and
  clang compiled with both clang 3.7 and gcc 4.8.2

  I am using cmake+ninja,

  Can you please advise on how to replicate the errors that you see,
  including platform, flags, etc?

  Many thanks!

  -- Carlo

  Inactive hide details for Alexey Samsonov ---12/08/2015 12:36:39
  PM---ASan bootstrap provides an error report as well: http://lAlexey
  Samsonov ---12/08/2015 12:36:39 PM---ASan bootstrap provides an error
  report as well: http://lab.llvm.org:8011/builders/sanitizer-x86_64-

  From: Alexey Samsonov <vonosmas at gmail.com>
  To: NAKAMURA Takumi <geek4civic at gmail.com>
  Cc: Carlo Bertolli/Watson/IBM at IBMUS, cfe-commits <
  cfe-commits at lists.llvm.org>
  Date: 12/08/2015 12:36 PM
  Subject: Re: r255001 - Add parse and sema for OpenMP distribute directive
  and all its clauses excluding dist_schedule.




  ASan bootstrap provides an error report as well:

  http://lab.llvm.org:8011/builders/sanitizer-x86_64-linux-fast/builds/8407/steps/check-clang%20asan/logs/stdio

  Please investigate or revert.

  On Tue, Dec 8, 2015 at 6:06 AM, NAKAMURA Takumi via cfe-commits <
  cfe-commits at lists.llvm.org> wrote:
        It crashes on i686-clang. See
        http://bb.pgr.jp/builders/clang-3stage-i686-linux/builds/4055
        Investigating.

        #6  0xf7ea482f in operator delete(void*) () from /usr/lib32/libstdc
        ++.so.6
        #7  0x0bef8cce in llvm::DenseMap<clang::VarDecl*,
        llvm::detail::DenseSetEmpty, llvm::DenseMapInfo<clang::VarDecl*>,
        llvm::detail::DenseSetPair<clang::VarDecl*> >::~DenseMap
        (this=0xf2419d8)
            at llvm/include/llvm/ADT/DenseMap.h:575
        #8  0x0bef8c86 in llvm::DenseSet<clang::VarDecl*,
        llvm::DenseMapInfo<clang::VarDecl*> >::~DenseSet (this=0xf2419d8)
            at llvm/include/llvm/ADT/DenseSet.h:39
        #9  0x0cf988a4 in (anonymous
        namespace)::DSAStackTy::SharingMapTy::~SharingMapTy
        (this=0xf2412c0)
            at clang/lib/Sema/SemaOpenMP.cpp:95
        #10 0x0cf9e24b in llvm::SmallVectorTemplateBase<(anonymous
        namespace)::DSAStackTy::SharingMapTy, false>::pop_back
        (this=0xf23fca0)
            at llvm/include/llvm/ADT/SmallVector.h:245
        #11 0x0cf68ed2 in (anonymous namespace)::DSAStackTy::pop
        (this=0xf23fca0)
            at clang/lib/Sema/SemaOpenMP.cpp:163
        #12 0x0cf68a50 in clang::Sema::EndOpenMPDSABlock (this=0xf23e188,
            CurDirective=0xf2901a0)
            at clang/lib/Sema/SemaOpenMP.cpp:957
        #13 0x0c603bf0 in
        clang::Parser::ParseOpenMPDeclarativeOrExecutableDirective (
            this=0xf25d3c0, StandAloneAllowed=false)
            at clang/lib/Parse/ParseOpenMP.cpp:314
        #14 0x0c61c641 in
        clang::Parser::ParseStatementOrDeclarationAfterAttributes (
            this=0xf25d3c0, Stmts=..., OnlyStatement=true,
        TrailingElseLoc=0x0,
            Attrs=...)
            at clang/lib/Parse/ParseStmt.cpp:349
        #15 0x0c61b1e9 in clang::Parser::ParseStatementOrDeclaration
        (this=0xf25d3c0,
            Stmts=..., OnlyStatement=true, TrailingElseLoc=0x0)
            at clang/lib/Parse/ParseStmt.cpp:106
        #16 0x0c61b064 in clang::Parser::ParseStatement (this=0xf25d3c0,
            TrailingElseLoc=0x0)
            at clang/lib/Parse/ParseStmt.cpp:42
        #17 0x0c6039ff in
        clang::Parser::ParseOpenMPDeclarativeOrExecutableDirective (
            this=0xf25d3c0, StandAloneAllowed=false)
            at clang/lib/Parse/ParseOpenMP.cpp:305
        #18 0x0c61c641 in
        clang::Parser::ParseStatementOrDeclarationAfterAttributes (
            this=0xf25d3c0, Stmts=..., OnlyStatement=true,
        TrailingElseLoc=0x0,
            Attrs=...)
            at clang/lib/Parse/ParseStmt.cpp:349
        #19 0x0c61b1e9 in clang::Parser::ParseStatementOrDeclaration
        (this=0xf25d3c0,
            Stmts=..., OnlyStatement=true, TrailingElseLoc=0x0)
            at clang/lib/Parse/ParseStmt.cpp:106
        #20 0x0c61b064 in clang::Parser::ParseStatement (this=0xf25d3c0,
            TrailingElseLoc=0x0)
            at clang/lib/Parse/ParseStmt.cpp:42
        #21 0x0c6039ff in
        clang::Parser::ParseOpenMPDeclarativeOrExecutableDirective (
            this=0xf25d3c0, StandAloneAllowed=true)
            at clang/lib/Parse/ParseOpenMP.cpp:305
        #22 0x0c61c641 in
        clang::Parser::ParseStatementOrDeclarationAfterAttributes (
            this=0xf25d3c0, Stmts=..., OnlyStatement=false,
        TrailingElseLoc=0x0,
            Attrs=...)
            at clang/lib/Parse/ParseStmt.cpp:349
        #23 0x0c61b1e9 in clang::Parser::ParseStatementOrDeclaration
        (this=0xf25d3c0,
            Stmts=..., OnlyStatement=false, TrailingElseLoc=0x0)
            at clang/lib/Parse/ParseStmt.cpp:106
        #24 0x0c625955 in clang::Parser::ParseCompoundStatementBody
        (this=0xf25d3c0,
            isStmtExpr=false)
            at clang/lib/Parse/ParseStmt.cpp:968
        #25 0x0c62692d in clang::Parser::ParseFunctionStatementBody
        (this=0xf25d3c0,
            Decl=0xf27a948, BodyScope=...)
            at clang/lib/Parse/ParseStmt.cpp:1914
        #26 0x0c53f639 in clang::Parser::ParseFunctionDefinition
        (this=0xf25d3c0,
            D=..., TemplateInfo=..., LateParsedAttrs=0xffffb630)
            at clang/lib/Parse/Parser.cpp:1147
        #27 0x0c56c1ca in clang::Parser::ParseDeclGroup (this=0xf25d3c0,
        DS=...,
            Context=0, DeclEnd=0x0, FRI=0x0)
            at clang/lib/Parse/ParseDecl.cpp:1757
        #28 0x0c53e13b in clang::Parser::ParseDeclOrFunctionDefInternal (
            this=0xf25d3c0, attrs=..., DS=..., AS=clang::AS_none)
            at clang/lib/Parse/Parser.cpp:927
        #29 0x0c53d527 in
        clang::Parser::ParseDeclarationOrFunctionDefinition (
            this=0xf25d3c0, attrs=..., DS=0x0, AS=clang::AS_none)
            at clang/lib/Parse/Parser.cpp:943
        #30 0x0c53c9c4 in clang::Parser::ParseExternalDeclaration
        (this=0xf25d3c0,
            attrs=..., DS=0x0)
            at clang/lib/Parse/Parser.cpp:801
        #31 0x0c53b4af in clang::Parser::ParseTopLevelDecl (this=0xf25d3c0,
        Result=...)
            at clang/lib/Parse/Parser.cpp:593
        #32 0x0c535b0d in clang::ParseAST (S=..., PrintStats=false,
            SkipFunctionBodies=false)
            at clang/lib/Parse/ParseAST.cpp:161
        #33 0x0b3bec76 in clang::ASTFrontendAction::ExecuteAction
        (this=0xf200980)
            at clang/lib/Frontend/FrontendAction.cpp:538
        #34 0x0b3be581 in clang::FrontendAction::Execute (this=0xf200980)
            at clang/lib/Frontend/FrontendAction.cpp:439
        #35 0x0b355071 in clang::CompilerInstance::ExecuteAction
        (this=0xf1ff128,
            Act=...)
            at clang/lib/Frontend/CompilerInstance.cpp:841
        #36 0x0b52d118 in clang::ExecuteCompilerInvocation
        (Clang=0xf1ff128)
            at clang/lib/FrontendTool/ExecuteCompilerInvocation.cpp:222
        #37 0x086e8734 in cc1_main (Argv=...,
            Argv0=0xffffd7c0 "/home/tnakamura/llvm/2-32/bin/clang",
            MainAddr=0x86d7820 <GetExecutablePath(char const*, bool)>)
            at clang/tools/driver/cc1_main.cpp:116
        #38 0x086d9823 in ExecuteCC1Tool (argv=..., Tool=...)
            at clang/tools/driver/driver.cpp:301
        #39 0x086d8316 in main (argc_=8, argv_=0xffffd684)
            at clang/tools/driver/driver.cpp:366


        On Tue, Dec 8, 2015 at 1:24 PM Carlo Bertolli via cfe-commits <
        cfe-commits at lists.llvm.org> wrote:
        Author: cbertol
        Date: Mon Dec  7 22:21:03 2015
        New Revision: 255001

        URL: http://llvm.org/viewvc/llvm-project?rev=255001&view=rev
        Log:
        Add parse and sema for OpenMP distribute directive and all its
        clauses excluding dist_schedule.

        Added:
            cfe/trunk/test/OpenMP/distribute_ast_print.cpp
            cfe/trunk/test/OpenMP/distribute_collapse_messages.cpp
            cfe/trunk/test/OpenMP/distribute_firstprivate_messages.cpp
            cfe/trunk/test/OpenMP/distribute_private_messages.cpp
        Modified:
            cfe/trunk/include/clang-c/Index.h
            cfe/trunk/include/clang/AST/RecursiveASTVisitor.h
            cfe/trunk/include/clang/AST/StmtOpenMP.h
            cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
            cfe/trunk/include/clang/Basic/OpenMPKinds.def
            cfe/trunk/include/clang/Basic/OpenMPKinds.h
            cfe/trunk/include/clang/Basic/StmtNodes.td
            cfe/trunk/include/clang/Sema/Sema.h
            cfe/trunk/include/clang/Serialization/ASTBitCodes.h
            cfe/trunk/lib/AST/StmtOpenMP.cpp
            cfe/trunk/lib/AST/StmtPrinter.cpp
            cfe/trunk/lib/AST/StmtProfile.cpp
            cfe/trunk/lib/Basic/OpenMPKinds.cpp
            cfe/trunk/lib/CodeGen/CGStmt.cpp
            cfe/trunk/lib/CodeGen/CGStmtOpenMP.cpp
            cfe/trunk/lib/CodeGen/CodeGenFunction.h
            cfe/trunk/lib/Parse/ParseOpenMP.cpp
            cfe/trunk/lib/Sema/SemaOpenMP.cpp
            cfe/trunk/lib/Sema/TreeTransform.h
            cfe/trunk/lib/Serialization/ASTReaderStmt.cpp
            cfe/trunk/lib/Serialization/ASTWriterStmt.cpp
            cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp
            cfe/trunk/test/OpenMP/nesting_of_regions.cpp
            cfe/trunk/tools/libclang/CIndex.cpp
            cfe/trunk/tools/libclang/CXCursor.cpp

        Modified: cfe/trunk/include/clang-c/Index.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang-c/Index.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang-c/Index.h (original)
        +++ cfe/trunk/include/clang-c/Index.h Mon Dec  7 22:21:03 2015
        @@ -2264,7 +2264,11 @@ enum CXCursorKind {
            */
           CXCursor_OMPTaskLoopSimdDirective      = 259,

        -  CXCursor_LastStmt                      =
        CXCursor_OMPTaskLoopSimdDirective,
        +   /** \brief OpenMP distribute directive.
        +   */
        +  CXCursor_OMPDistributeDirective        = 260,
        +
        +  CXCursor_LastStmt                      =
        CXCursor_OMPDistributeDirective,

           /**
            * \brief Cursor that represents the translation unit itself.

        Modified: cfe/trunk/include/clang/AST/RecursiveASTVisitor.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/RecursiveASTVisitor.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/AST/RecursiveASTVisitor.h (original)
        +++ cfe/trunk/include/clang/AST/RecursiveASTVisitor.h Mon Dec  7
        22:21:03 2015
        @@ -2439,6 +2439,9 @@ DEF_TRAVERSE_STMT(OMPTaskLoopDirective,
         DEF_TRAVERSE_STMT(OMPTaskLoopSimdDirective,
                           { TRY_TO(TraverseOMPExecutableDirective(S)); })

        +DEF_TRAVERSE_STMT(OMPDistributeDirective,
        +                  { TRY_TO(TraverseOMPExecutableDirective(S)); })
        +
         // OpenMP clauses.
         template <typename Derived>
         bool RecursiveASTVisitor<Derived>::TraverseOMPClause(OMPClause *C)
        {

        Modified: cfe/trunk/include/clang/AST/StmtOpenMP.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/StmtOpenMP.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/AST/StmtOpenMP.h (original)
        +++ cfe/trunk/include/clang/AST/StmtOpenMP.h Mon Dec  7 22:21:03
        2015
        @@ -424,43 +424,50 @@ protected:
           void setInc(Expr *Inc) { *std::next(child_begin(), IncOffset) =
        Inc; }
           void setIsLastIterVariable(Expr *IL) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), IsLastIterVariableOffset) = IL;
           }
           void setLowerBoundVariable(Expr *LB) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), LowerBoundVariableOffset) = LB;
           }
           void setUpperBoundVariable(Expr *UB) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), UpperBoundVariableOffset) = UB;
           }
           void setStrideVariable(Expr *ST) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), StrideVariableOffset) = ST;
           }
           void setEnsureUpperBound(Expr *EUB) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), EnsureUpperBoundOffset) = EUB;
           }
           void setNextLowerBound(Expr *NLB) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), NextLowerBoundOffset) = NLB;
           }
           void setNextUpperBound(Expr *NUB) {
             assert((isOpenMPWorksharingDirective(getDirectiveKind()) ||
        -            isOpenMPTaskLoopDirective(getDirectiveKind())) &&
        +            isOpenMPTaskLoopDirective(getDirectiveKind()) ||
        +            isOpenMPDistributeDirective(getDirectiveKind())) &&
                    "expected worksharing loop directive");
             *std::next(child_begin(), NextUpperBoundOffset) = NUB;
           }
        @@ -683,7 +690,8 @@ public:
                    T->getStmtClass() == OMPParallelForDirectiveClass ||
                    T->getStmtClass() == OMPParallelForSimdDirectiveClass
        ||
                    T->getStmtClass() == OMPTaskLoopDirectiveClass ||
        -           T->getStmtClass() == OMPTaskLoopSimdDirectiveClass;
        +           T->getStmtClass() == OMPTaskLoopSimdDirectiveClass ||
        +           T->getStmtClass() == OMPDistributeDirectiveClass;
           }
         };

        @@ -2333,6 +2341,73 @@ public:
           }
         };

        +/// \brief This represents '#pragma omp distribute' directive.
        +///
        +/// \code
        +/// #pragma omp distribute private(a,b)
        +/// \endcode
        +/// In this example directive '#pragma omp distribute' has clauses
        'private'
        +/// with the variables 'a' and 'b'
        +///
        +class OMPDistributeDirective : public OMPLoopDirective {
        +  friend class ASTStmtReader;
        +
        +  /// \brief Build directive with the given start and end
        location.
        +  ///
        +  /// \param StartLoc Starting location of the directive kind.
        +  /// \param EndLoc Ending location of the directive.
        +  /// \param CollapsedNum Number of collapsed nested loops.
        +  /// \param NumClauses Number of clauses.
        +  ///
        +  OMPDistributeDirective(SourceLocation StartLoc, SourceLocation
        EndLoc,
        +                         unsigned CollapsedNum, unsigned
        NumClauses)
        +      : OMPLoopDirective(this, OMPDistributeDirectiveClass,
        OMPD_distribute,
        +                         StartLoc, EndLoc, CollapsedNum,
        NumClauses)
        +        {}
        +
        +  /// \brief Build an empty directive.
        +  ///
        +  /// \param CollapsedNum Number of collapsed nested loops.
        +  /// \param NumClauses Number of clauses.
        +  ///
        +  explicit OMPDistributeDirective(unsigned CollapsedNum, unsigned
        NumClauses)
        +      : OMPLoopDirective(this, OMPDistributeDirectiveClass,
        OMPD_distribute,
        +                         SourceLocation(), SourceLocation(),
        CollapsedNum,
        +                         NumClauses)
        +        {}
        +
        +public:
        +  /// \brief Creates directive with a list of \a Clauses.
        +  ///
        +  /// \param C AST context.
        +  /// \param StartLoc Starting location of the directive kind.
        +  /// \param EndLoc Ending Location of the directive.
        +  /// \param CollapsedNum Number of collapsed loops.
        +  /// \param Clauses List of clauses.
        +  /// \param AssociatedStmt Statement, associated with the
        directive.
        +  /// \param Exprs Helper expressions for CodeGen.
        +    ///
        +  static OMPDistributeDirective *
        +  Create(const ASTContext &C, SourceLocation StartLoc,
        SourceLocation EndLoc,
        +         unsigned CollapsedNum, ArrayRef<OMPClause *> Clauses,
        +         Stmt *AssociatedStmt, const HelperExprs &Exprs);
        +
        +  /// \brief Creates an empty directive with the place
        +  /// for \a NumClauses clauses.
        +  ///
        +  /// \param C AST context.
        +  /// \param CollapsedNum Number of collapsed nested loops.
        +  /// \param NumClauses Number of clauses.
        +  ///
        +  static OMPDistributeDirective *CreateEmpty(const ASTContext &C,
        +                                             unsigned NumClauses,
        +                                             unsigned
        CollapsedNum, EmptyShell);
        +
        +  static bool classof(const Stmt *T) {
        +    return T->getStmtClass() == OMPDistributeDirectiveClass;
        +  }
        +};
        +
         } // end namespace clang

         #endif

        Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td (original)
        +++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td Mon Dec  7
        22:21:03 2015
        @@ -7801,7 +7801,8 @@ def err_omp_prohibited_region : Error<
           "region cannot be%select{| closely}0 nested inside '%1' region"
           "%select{|; perhaps you forget to enclose 'omp %3' directive
        into a parallel region?|"
           "; perhaps you forget to enclose 'omp %3' directive into a for
        or a parallel for region with 'ordered' clause?|"
        -  "; perhaps you forget to enclose 'omp %3' directive into a
        target region?}2">;
        +  "; perhaps you forget to enclose 'omp %3' directive into a
        target region?|"
        +  "; perhaps you forget to enclose 'omp %3' directive into a teams
        region?}2">;
         def err_omp_prohibited_region_simd : Error<
           "OpenMP constructs may not be nested inside a simd region">;
         def err_omp_prohibited_region_atomic : Error<
        @@ -7920,6 +7921,12 @@ def err_omp_wrong_ordered_loop_count : E
           "the parameter of the 'ordered' clause must be greater than or
        equal to the parameter of the 'collapse' clause">;
         def note_collapse_loop_count : Note<
           "parameter of the 'collapse' clause">;
        +def err_omp_firstprivate_distribute_private_teams : Error<
        +  "private variable in '#pragma omp teams' cannot be firstprivate
        in '#pragma omp distribute'">;
        +def err_omp_firstprivate_and_lastprivate_in_distribute : Error<
        +  "lastprivate variable cannot be firstprivate in '#pragma omp
        distribute'">;
        +def err_omp_firstprivate_distribute_in_teams_reduction : Error<
        +  "reduction variable in '#pragma omp teams' cannot be
        firstprivate in '#pragma omp distribute'">;
         } // end of OpenMP category

         let CategoryName = "Related Result Type Issue" in {

        Modified: cfe/trunk/include/clang/Basic/OpenMPKinds.def
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/OpenMPKinds.def?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Basic/OpenMPKinds.def (original)
        +++ cfe/trunk/include/clang/Basic/OpenMPKinds.def Mon Dec  7
        22:21:03 2015
        @@ -75,6 +75,9 @@
         #ifndef OPENMP_TASKLOOP_SIMD_CLAUSE
         #  define OPENMP_TASKLOOP_SIMD_CLAUSE(Name)
         #endif
        +#ifndef OPENMP_DISTRIBUTE_CLAUSE
        +#define OPENMP_DISTRIBUTE_CLAUSE(Name)
        +#endif
         #ifndef OPENMP_DEFAULT_KIND
         #  define OPENMP_DEFAULT_KIND(Name)
         #endif
        @@ -123,6 +126,7 @@ OPENMP_DIRECTIVE_EXT(for_simd, "for simd
         OPENMP_DIRECTIVE_EXT(cancellation_point, "cancellation point")
         OPENMP_DIRECTIVE(taskloop)
         OPENMP_DIRECTIVE_EXT(taskloop_simd, "taskloop simd")
        +OPENMP_DIRECTIVE(distribute)

         // OpenMP clauses.
         OPENMP_CLAUSE(if, OMPIfClause)
        @@ -388,6 +392,12 @@ OPENMP_TASKLOOP_SIMD_CLAUSE(simdlen)
         OPENMP_TASKLOOP_SIMD_CLAUSE(grainsize)
         OPENMP_TASKLOOP_SIMD_CLAUSE(nogroup)

        +// Clauses allowed for OpenMP directive 'distribute'
        +OPENMP_DISTRIBUTE_CLAUSE(private)
        +OPENMP_DISTRIBUTE_CLAUSE(firstprivate)
        +OPENMP_DISTRIBUTE_CLAUSE(lastprivate)
        +OPENMP_DISTRIBUTE_CLAUSE(collapse)
        +
         #undef OPENMP_TASKLOOP_SIMD_CLAUSE
         #undef OPENMP_TASKLOOP_CLAUSE
         #undef OPENMP_LINEAR_KIND
        @@ -415,3 +425,4 @@ OPENMP_TASKLOOP_SIMD_CLAUSE(nogroup)
         #undef OPENMP_FOR_CLAUSE
         #undef OPENMP_FOR_SIMD_CLAUSE
         #undef OPENMP_MAP_KIND
        +#undef OPENMP_DISTRIBUTE_CLAUSE

        Modified: cfe/trunk/include/clang/Basic/OpenMPKinds.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/OpenMPKinds.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Basic/OpenMPKinds.h (original)
        +++ cfe/trunk/include/clang/Basic/OpenMPKinds.h Mon Dec  7 22:21:03
        2015
        @@ -141,6 +141,13 @@ bool isOpenMPTeamsDirective(OpenMPDirect
         /// otherwise - false.
         bool isOpenMPSimdDirective(OpenMPDirectiveKind DKind);

        +/// \brief Checks if the specified directive is a distribute
        directive.
        +/// \param DKind Specified directive.
        +/// \return true - the directive is a distribute-directive like
        'omp
        +/// distribute',
        +/// otherwise - false.
        +bool isOpenMPDistributeDirective(OpenMPDirectiveKind DKind);
        +
         /// \brief Checks if the specified clause is one of private
        clauses like
         /// 'private', 'firstprivate', 'reduction' etc..
         /// \param Kind Clause kind.

        Modified: cfe/trunk/include/clang/Basic/StmtNodes.td
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/StmtNodes.td?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Basic/StmtNodes.td (original)
        +++ cfe/trunk/include/clang/Basic/StmtNodes.td Mon Dec  7 22:21:03
        2015
        @@ -221,4 +221,4 @@ def OMPCancellationPointDirective : DStm
         def OMPCancelDirective : DStmt<OMPExecutableDirective>;
         def OMPTaskLoopDirective : DStmt<OMPLoopDirective>;
         def OMPTaskLoopSimdDirective : DStmt<OMPLoopDirective>;
        -
        +def OMPDistributeDirective : DStmt<OMPLoopDirective>;

        Modified: cfe/trunk/include/clang/Sema/Sema.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Sema/Sema.h (original)
        +++ cfe/trunk/include/clang/Sema/Sema.h Mon Dec  7 22:21:03 2015
        @@ -7961,6 +7961,12 @@ public:
               ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation
        StartLoc,
               SourceLocation EndLoc,
               llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA);
        +  /// \brief Called on well-formed '\#pragma omp distribute' after
        parsing
        +  /// of the associated statement.
        +  StmtResult ActOnOpenMPDistributeDirective(
        +      ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation
        StartLoc,
        +      SourceLocation EndLoc,
        +      llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA);

           OMPClause *ActOnOpenMPSingleExprClause(OpenMPClauseKind Kind,
                                                  Expr *Expr,

        Modified: cfe/trunk/include/clang/Serialization/ASTBitCodes.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTBitCodes.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/include/clang/Serialization/ASTBitCodes.h (original)
        +++ cfe/trunk/include/clang/Serialization/ASTBitCodes.h Mon Dec  7
        22:21:03 2015
        @@ -1449,6 +1449,7 @@ namespace clang {
               STMT_OMP_CANCEL_DIRECTIVE,
               STMT_OMP_TASKLOOP_DIRECTIVE,
               STMT_OMP_TASKLOOP_SIMD_DIRECTIVE,
        +      STMT_OMP_DISTRIBUTE_DIRECTIVE,
               EXPR_OMP_ARRAY_SECTION,

               // ARC

        Modified: cfe/trunk/lib/AST/StmtOpenMP.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtOpenMP.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/AST/StmtOpenMP.cpp (original)
        +++ cfe/trunk/lib/AST/StmtOpenMP.cpp Mon Dec  7 22:21:03 2015
        @@ -832,3 +832,48 @@ OMPTaskLoopSimdDirective::CreateEmpty(co
           return new (Mem) OMPTaskLoopSimdDirective(CollapsedNum,
        NumClauses);
         }

        +OMPDistributeDirective *OMPDistributeDirective::Create(
        +    const ASTContext &C, SourceLocation StartLoc, SourceLocation
        EndLoc,
        +    unsigned CollapsedNum, ArrayRef<OMPClause *> Clauses, Stmt
        *AssociatedStmt,
        +    const HelperExprs &Exprs) {
        +  unsigned Size = llvm::RoundUpToAlignment(sizeof
        (OMPDistributeDirective),
        +                                           llvm::alignOf<OMPClause
        *>());
        +  void *Mem = C.Allocate(Size + sizeof(OMPClause *) * Clauses.size
        () +
        +                         sizeof(Stmt *) *
        +                             numLoopChildren(CollapsedNum,
        OMPD_distribute));
        +  OMPDistributeDirective *Dir = new (Mem)
        +      OMPDistributeDirective(StartLoc, EndLoc, CollapsedNum,
        Clauses.size());
        +  Dir->setClauses(Clauses);
        +  Dir->setAssociatedStmt(AssociatedStmt);
        +  Dir->setIterationVariable(Exprs.IterationVarRef);
        +  Dir->setLastIteration(Exprs.LastIteration);
        +  Dir->setCalcLastIteration(Exprs.CalcLastIteration);
        +  Dir->setPreCond(Exprs.PreCond);
        +  Dir->setCond(Exprs.Cond);
        +  Dir->setInit(Exprs.Init);
        +  Dir->setInc(Exprs.Inc);
        +  Dir->setIsLastIterVariable(Exprs.IL);
        +  Dir->setLowerBoundVariable(Exprs.LB);
        +  Dir->setUpperBoundVariable(Exprs.UB);
        +  Dir->setStrideVariable(Exprs.ST);
        +  Dir->setEnsureUpperBound(Exprs.EUB);
        +  Dir->setNextLowerBound(Exprs.NLB);
        +  Dir->setNextUpperBound(Exprs.NUB);
        +  Dir->setCounters(Exprs.Counters);
        +  Dir->setPrivateCounters(Exprs.PrivateCounters);
        +  Dir->setInits(Exprs.Inits);
        +  Dir->setUpdates(Exprs.Updates);
        +  Dir->setFinals(Exprs.Finals);
        +  return Dir;
        +}
        +
        +OMPDistributeDirective *
        +OMPDistributeDirective::CreateEmpty(const ASTContext &C, unsigned
        NumClauses,
        +                                    unsigned CollapsedNum,
        EmptyShell) {
        +  unsigned Size = llvm::RoundUpToAlignment(sizeof
        (OMPDistributeDirective),
        +                                           llvm::alignOf<OMPClause
        *>());
        +  void *Mem = C.Allocate(Size + sizeof(OMPClause *) * NumClauses +
        +                         sizeof(Stmt *) *
        +                             numLoopChildren(CollapsedNum,
        OMPD_distribute));
        +  return new (Mem) OMPDistributeDirective(CollapsedNum,
        NumClauses);
        +}

        Modified: cfe/trunk/lib/AST/StmtPrinter.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtPrinter.cpp?rev=255001&r1=255000&r2=255001&view=diff

        
==============================================================================

        --- cfe/trunk/lib/AST/StmtPrinter.cpp (original)
        +++ cfe/trunk/lib/AST/StmtPrinter.cpp Mon Dec  7 22:21:03 2015
        @@ -1057,6 +1057,11 @@ void StmtPrinter::VisitOMPTaskLoopSimdDi
           PrintOMPExecutableDirective(Node);
         }

        +void StmtPrinter::VisitOMPDistributeDirective
        (OMPDistributeDirective *Node) {
        +  Indent() << "#pragma omp distribute ";
        +  PrintOMPExecutableDirective(Node);
        +}
        +

        //===----------------------------------------------------------------------===//

         //  Expr printing methods.

        //===----------------------------------------------------------------------===//


        Modified: cfe/trunk/lib/AST/StmtProfile.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtProfile.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/AST/StmtProfile.cpp (original)
        +++ cfe/trunk/lib/AST/StmtProfile.cpp Mon Dec  7 22:21:03 2015
        @@ -599,6 +599,11 @@ void StmtProfiler::VisitOMPTaskLoopSimdD
           VisitOMPLoopDirective(S);
         }

        +void StmtProfiler::VisitOMPDistributeDirective(
        +    const OMPDistributeDirective *S) {
        +  VisitOMPLoopDirective(S);
        +}
        +
         void StmtProfiler::VisitExpr(const Expr *S) {
           VisitStmt(S);
         }

        Modified: cfe/trunk/lib/Basic/OpenMPKinds.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Basic/OpenMPKinds.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Basic/OpenMPKinds.cpp (original)
        +++ cfe/trunk/lib/Basic/OpenMPKinds.cpp Mon Dec  7 22:21:03 2015
        @@ -436,6 +436,16 @@ bool clang::isAllowedClauseForDirective(
               break;
             }
             break;
        +  case OMPD_distribute:
        +    switch (CKind) {
        +#define OPENMP_DISTRIBUTE_CLAUSE(Name)
        \
        +  case OMPC_##Name:
        \
        +    return true;
        +#include "clang/Basic/OpenMPKinds.def"
        +    default:
        +      break;
        +    }
        +    break;
           case OMPD_unknown:
           case OMPD_threadprivate:
           case OMPD_section:
        @@ -455,7 +465,8 @@ bool clang::isOpenMPLoopDirective(OpenMP
           return DKind == OMPD_simd || DKind == OMPD_for || DKind ==
        OMPD_for_simd ||
                  DKind == OMPD_parallel_for || DKind ==
        OMPD_parallel_for_simd ||
                  DKind == OMPD_taskloop ||
        -         DKind == OMPD_taskloop_simd; // TODO add next directives.
        +         DKind == OMPD_taskloop_simd ||
        +         DKind == OMPD_distribute; // TODO add next directives.
         }

         bool clang::isOpenMPWorksharingDirective(OpenMPDirectiveKind
        DKind) {
        @@ -490,6 +501,10 @@ bool clang::isOpenMPSimdDirective(OpenMP
                  DKind == OMPD_taskloop_simd; // TODO add next directives.
         }

        +bool clang::isOpenMPDistributeDirective(OpenMPDirectiveKind Kind)
        {
        +  return Kind == OMPD_distribute; // TODO add next directives.
        +}
        +
         bool clang::isOpenMPPrivate(OpenMPClauseKind Kind) {
           return Kind == OMPC_private || Kind == OMPC_firstprivate ||
                  Kind == OMPC_lastprivate || Kind == OMPC_linear ||

        Modified: cfe/trunk/lib/CodeGen/CGStmt.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGStmt.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/CodeGen/CGStmt.cpp (original)
        +++ cfe/trunk/lib/CodeGen/CGStmt.cpp Mon Dec  7 22:21:03 2015
        @@ -262,6 +262,9 @@ void CodeGenFunction::EmitStmt(const Stm
           case Stmt::OMPTaskLoopSimdDirectiveClass:
             EmitOMPTaskLoopSimdDirective(cast<OMPTaskLoopSimdDirective>
        (*S));
             break;
        +case Stmt::OMPDistributeDirectiveClass:
        +    EmitOMPDistributeDirective(cast<OMPDistributeDirective>(*S));
        +       break;
           }
         }


        Modified: cfe/trunk/lib/CodeGen/CGStmtOpenMP.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGStmtOpenMP.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/CodeGen/CGStmtOpenMP.cpp (original)
        +++ cfe/trunk/lib/CodeGen/CGStmtOpenMP.cpp Mon Dec  7 22:21:03 2015
        @@ -2045,6 +2045,11 @@ void CodeGenFunction::EmitOMPFlushDirect
           }(), S.getLocStart());
         }

        +void CodeGenFunction::EmitOMPDistributeDirective(
        +    const OMPDistributeDirective &S) {
        +  llvm_unreachable("CodeGen for 'omp distribute' is not supported
        yet.");
        +}
        +
         static llvm::Function *emitOutlinedOrderedFunction(CodeGenModule
        &CGM,
                                                          const
        CapturedStmt *S) {
           CodeGenFunction CGF(CGM, /*suppressNewContext=*/true);

        Modified: cfe/trunk/lib/CodeGen/CodeGenFunction.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenFunction.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/CodeGen/CodeGenFunction.h (original)
        +++ cfe/trunk/lib/CodeGen/CodeGenFunction.h Mon Dec  7 22:21:03
        2015
        @@ -2339,6 +2339,7 @@ public:
           void EmitOMPCancelDirective(const OMPCancelDirective &S);
           void EmitOMPTaskLoopDirective(const OMPTaskLoopDirective &S);
           void EmitOMPTaskLoopSimdDirective(const OMPTaskLoopSimdDirective
        &S);
        +  void EmitOMPDistributeDirective(const OMPDistributeDirective
        &S);

           /// \brief Emit inner loop of the worksharing/simd construct.
           ///

        Modified: cfe/trunk/lib/Parse/ParseOpenMP.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseOpenMP.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Parse/ParseOpenMP.cpp (original)
        +++ cfe/trunk/lib/Parse/ParseOpenMP.cpp Mon Dec  7 22:21:03 2015
        @@ -140,6 +140,7 @@ Parser::DeclGroupPtrTy Parser::ParseOpen
           case OMPD_target_data:
           case OMPD_taskloop:
           case OMPD_taskloop_simd:
        +  case OMPD_distribute:
             Diag(Tok, diag::err_omp_unexpected_directive)
                 << getOpenMPDirectiveName(DKind);
             break;
        @@ -160,7 +161,8 @@ Parser::DeclGroupPtrTy Parser::ParseOpen
         ///         'parallel for' | 'parallel sections' | 'task' |
        'taskyi eld' |
         ///         'barrier' | 'taskwait' | 'flush' | 'ordered' |
        'atomic' |
         ///         'for simd' | 'parallel for simd' | 'target' | 'target
        data' |
        -///         'taskgroup' | 'teams' | 'taskloop' | 'taskloop
        simd' {clause}
        +///         'taskgroup' | 'teams' | 'taskloop' | 'taskloop
        simd' {clause} |
        +///         'distribute'
         ///         annot_pragma_openmp_end
         ///
         StmtResult
        @@ -237,7 +239,8 @@ Parser::ParseOpenMPDeclarativeOrExecutab
           case OMPD_taskgroup:
           case OMPD_target_data:
           case OMPD_taskloop:
        -  case OMPD_taskloop_simd: {
        +  case OMPD_taskloop_simd:
        +  case OMPD_distribute: {
             ConsumeToken();
             // Parse directive name of the 'critical' directive if any.
             if (DKind == OMPD_critical) {

        Modified: cfe/trunk/lib/Sema/SemaOpenMP.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaOpenMP.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Sema/SemaOpenMP.cpp (original)
        +++ cfe/trunk/lib/Sema/SemaOpenMP.cpp Mon Dec  7 22:21:03 2015
        @@ -1568,6 +1568,14 @@ void Sema::ActOnOpenMPRegionStart(OpenMP
                                      Params);
             break;
           }
        +  case OMPD_distribute: {
        +    Sema::CapturedParamNameType Params[] = {
        +        std::make_pair(StringRef(), QualType()) // __context with
        shared vars
        +    };
        +    ActOnCapturedRegionStart(DSAStack->getConstructLoc(),
        CurScope, CR_OpenMP,
        +                             Params);
        +    break;
        +  }
           case OMPD_threadprivate:
           case OMPD_taskyield:
           case OMPD_barrier:
        @@ -1652,6 +1660,7 @@ static bool CheckNestingOfRegions(Sema &
           // | parallel         | cancel          | !
        |
           // | parallel         | taskloop        | *
        |
           // | parallel         | taskloop simd   | *
        |
        +  // | parallel         | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | for              | parallel        | *
        |
           // | for              | for             | +
        |
        @@ -1680,6 +1689,7 @@ static bool CheckNestingOfRegions(Sema &
           // | for              | cancel          | !
        |
           // | for              | taskloop        | *
        |
           // | for              | taskloop simd   | *
        |
        +  // | for              | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | master           | parallel        | *
        |
           // | master           | for             | +
        |
        @@ -1708,6 +1718,7 @@ static bool CheckNestingOfRegions(Sema &
           // | master           | cancel          |
        |
           // | master           | taskloop        | *
        |
           // | master           | taskloop simd   | *
        |
        +  // | master           | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | critical         | parallel        | *
        |
           // | critical         | for             | +
        |
        @@ -1735,6 +1746,7 @@ static bool CheckNestingOfRegions(Sema &
           // | critical         | cancel          |
        |
           // | critical         | taskloop        | *
        |
           // | critical         | taskloop simd   | *
        |
        +  // | critical         | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | simd             | parallel        |
        |
           // | simd             | for             |
        |
        @@ -1763,6 +1775,7 @@ static bool CheckNestingOfRegions(Sema &
           // | simd             | cancel          |
        |
           // | simd             | taskloop        |
        |
           // | simd             | taskloop simd   |
        |
        +  // | simd             | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | for simd         | parallel        |
        |
           // | for simd         | for             |
        |
        @@ -1791,6 +1804,7 @@ static bool CheckNestingOfRegions(Sema &
           // | for simd         | cancel          |
        |
           // | for simd         | taskloop        |
        |
           // | for simd         | taskloop simd   |
        |
        +  // | for simd         | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | parallel for simd| parallel        |
        |
           // | parallel for simd| for             |
        |
        @@ -1819,6 +1833,7 @@ static bool CheckNestingOfRegions(Sema &
           // | parallel for simd| cancel          |
        |
           // | parallel for simd| taskloop        |
        |
           // | parallel for simd| taskloop simd   |
        |
        +  // | parallel for simd| distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | sections         | parallel        | *
        |
           // | sections         | for             | +
        |
        @@ -1847,6 +1862,7 @@ static bool CheckNestingOfRegions(Sema &
           // | sections         | cancel          | !
        |
           // | sections         | taskloop        | *
        |
           // | sections         | taskloop simd   | *
        |
        +  // | sections         | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | section          | parallel        | *
        |
           // | section          | for             | +
        |
        @@ -1875,6 +1891,7 @@ static bool CheckNestingOfRegions(Sema &
           // | section          | cancel          | !
        |
           // | section          | taskloop        | *
        |
           // | section          | taskloop simd   | *
        |
        +  // | section          | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | single           | parallel        | *
        |
           // | single           | for             | +
        |
        @@ -1903,6 +1920,7 @@ static bool CheckNestingOfRegions(Sema &
           // | single           | cancel          |
        |
           // | single           | taskloop        | *
        |
           // | single           | taskloop simd   | *
        |
        +  // | single           | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | parallel for     | parallel        | *
        |
           // | parallel for     | for             | +
        |
        @@ -1931,6 +1949,7 @@ static bool CheckNestingOfRegions(Sema &
           // | parallel for     | cancel          | !
        |
           // | parallel for     | taskloop        | *
        |
           // | parallel for     | taskloop simd   | *
        |
        +  // | parallel for     | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | parallel sections| parallel        | *
        |
           // | parallel sections| for             | +
        |
        @@ -1959,6 +1978,7 @@ static bool CheckNestingOfRegions(Sema &
           // | parallel sections| cancel          | !
        |
           // | parallel sections| taskloop        | *
        |
           // | parallel sections| taskloop simd   | *
        |
        +  // | parallel sections| distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | task             | parallel        | *
        |
           // | task             | for             | +
        |
        @@ -1987,6 +2007,7 @@ static bool CheckNestingOfRegions(Sema &
           // | task             | cancel          | !
        |
           // | task             | taskloop        | *
        |
           // | task             | taskloop simd   | *
        |
        +  // | task             | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | ordered          | parallel        | *
        |
           // | ordered          | for             | +
        |
        @@ -2015,6 +2036,7 @@ static bool CheckNestingOfRegions(Sema &
           // | ordered          | cancel          |
        |
           // | ordered          | taskloop        | *
        |
           // | ordered          | taskloop simd   | *
        |
        +  // | ordered          | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | atomic           | parallel        |
        |
           // | atomic           | for             |
        |
        @@ -2043,6 +2065,7 @@ static bool CheckNestingOfRegions(Sema &
           // | atomic           | cancel          |
        |
           // | atomic           | taskloop        |
        |
           // | atomic           | taskloop simd   |
        |
        +  // | atomic           | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | target           | parallel        | *
        |
           // | target           | for             | *
        |
        @@ -2071,6 +2094,7 @@ static bool CheckNestingOfRegions(Sema &
           // | target           | cancel          |
        |
           // | target           | taskloop        | *
        |
           // | target           | taskloop simd   | *
        |
        +  // | target           | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | teams            | parallel        | *
        |
           // | teams            | for             | +
        |
        @@ -2099,6 +2123,7 @@ static bool CheckNestingOfRegions(Sema &
           // | teams            | cancel          |
        |
           // | teams            | taskloop        | +
        |
           // | teams            | taskloop simd   | +
        |
        +  // | teams            | distribute      | !
        |
           //
        +------------------+-----------------+------------------------------------+

           // | taskloop         | parallel        | *
        |
           // | taskloop         | for             | +
        |
        @@ -2126,6 +2151,7 @@ static bool CheckNestingOfRegions(Sema &
           // |                  | point           |
        |
           // | taskloop         | cancel          |
        |
           // | taskloop         | taskloop        | *
        |
        +  // | taskloop         | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           // | taskloop simd    | parallel        |
        |
           // | taskloop simd    | for             |
        |
        @@ -2154,6 +2180,36 @@ static bool CheckNestingOfRegions(Sema &
           // | taskloop simd    | cancel          |
        |
           // | taskloop simd    | taskloop        |
        |
           // | taskloop simd    | taskloop simd   |
        |
        +  // | taskloop simd    | distribute      |
        |
        +  //
        +------------------+-----------------+------------------------------------+

        +  // | distribute       | parallel        | *
        |
        +  // | distribute       | for             | *
        |
        +  // | distribute       | for simd        | *
        |
        +  // | distribute       | master          | *
        |
        +  // | distribute       | critical        | *
        |
        +  // | distribute       | simd            | *
        |
        +  // | distribute       | sections        | *
        |
        +  // | distribute       | section         | *
        |
        +  // | distribute       | single          | *
        |
        +  // | distribute       | parallel for    | *
        |
        +  // | distribute       |parallel for simd| *
        |
        +  // | distribute       |parallel sections| *
        |
        +  // | distribute       | task            | *
        |
        +  // | distribute       | taskyield       | *
        |
        +  // | distribute       | barrier         | *
        |
        +  // | distribute       | taskwait        | *
        |
        +  // | distribute       | taskgroup       | *
        |
        +  // | distribute       | flush           | *
        |
        +  // | distribute       | ordered         | +
        |
        +  // | distribute       | atomic          | *
        |
        +  // | distribute       | target          |
        |
        +  // | distribute       | teams           |
        |
        +  // | distribute       | cancellation    | +
        |
        +  // |                  | point           |
        |
        +  // | distribute       | cancel          | +
        |
        +  // | distribute       | taskloop        | *
        |
        +  // | distribute       | taskloop simd   | *
        |
        +  // | distribute       | distribute      |
        |
           //
        +------------------+-----------------+------------------------------------+

           if (Stack->getCurScope()) {
             auto ParentRegion = Stack->getParentDirective();
        @@ -2163,7 +2219,8 @@ static bool CheckNestingOfRegions(Sema &
               NoRecommend,
               ShouldBeInParallelRegion,
             ShouldBeInOrderedRegion,
        -      ShouldBeInTargetRegion
        +      ShouldBeInTargetRegion,
        +      ShouldBeInTeamsRegion
             } Recommend = NoRecommend;
             if (isOpenMPSimdDirective(ParentRegion) && CurrentRegion !=
        OMPD_ordered) {
               // OpenMP [2.16, Nesting of Regions]
        @@ -2303,10 +2360,17 @@ static bool CheckNestingOfRegions(Sema &
               // distribute, parallel, parallel sections, parallel
        workshare, and the
               // parallel loop and parallel loop SIMD constructs are the
        only OpenMP
               // constructs that can be closely nested in the teams
        region.
        -      // TODO: add distribute directive.
        -      NestingProhibited = !isOpenMPParallelDirective
        (CurrentRegion);
        +      NestingProhibited = !isOpenMPParallelDirective
        (CurrentRegion) &&
        +                          !isOpenMPDistributeDirective
        (CurrentRegion);
               Recommend = ShouldBeInParallelRegion;
             }
        +    if (!NestingProhibited && isOpenMPDistributeDirective
        (CurrentRegion)) {
        +      // OpenMP 4.5 [2.17 Nesting of Regions]
        +      // The region associated with the distribute construct must
        be strictly
        +      // nested inside a teams region
        +      NestingProhibited = !isOpenMPTeamsDirective(ParentRegion);
        +      Recommend = ShouldBeInTeamsRegion;
        +    }
             if (NestingProhibited) {
               SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region)
                   << CloseNesting << getOpenMPDirectiveName(ParentRegion)
        << Recommend
        @@ -2574,6 +2638,10 @@ StmtResult Sema::ActOnOpenMPExecutableDi
                                                    EndLoc,
        VarsWithInheritedDSA);
             AllowedNameModifiers.push_back(OMPD_taskloop);
             break;
        +  case OMPD_distribute:
        +    Res = ActOnOpenMPDistributeDirective(ClausesWithImplicit,
        AStmt, StartLoc,
        +                                         EndLoc,
        VarsWithInheritedDSA);
        +    break;
           case OMPD_threadprivate:
             llvm_unreachable("OpenMP Directive is not allowed");
           case OMPD_unknown:
        @@ -3402,7 +3470,8 @@ static bool CheckOpenMPIterationSpace(
                   : OMPC_private;
           if (((isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown
        &&
                 DVar.CKind != OMPC_threadprivate && DVar.CKind !=
        PredeterminedCKind) ||
        -       ((isOpenMPWorksharingDirective(DKind) || DKind ==
        OMPD_taskloop) &&
        +       ((isOpenMPWorksharingDirective(DKind) || DKind ==
        OMPD_taskloop ||
        +        isOpenMPDistributeDirective(DKind)) &&
                 !isOpenMPSimdDirective(DKind) && DVar.CKind !=
        OMPC_unknown &&
                 DVar.CKind != OMPC_private && DVar.CKind !=
        OMPC_lastprivate &&
                 DVar.CKind != OMPC_threadprivate)) &&
        @@ -3441,7 +3510,8 @@ static bool CheckOpenMPIterationSpace(
           ResultIterSpace.PreCond = ISC.BuildPreCond(DSA.getCurScope(),
        For->getCond());
           ResultIterSpace.NumIterations = ISC.BuildNumIterations(
               DSA.getCurScope(), (isOpenMPWorksharingDirective(DKind) ||
        -                          isOpenMPTaskLoopDirective(DKind)));
        +                          isOpenMPTaskLoopDirective(DKind) ||
        +                          isOpenMPDistributeDirective(DKind)));
           ResultIterSpace.CounterVar = ISC.BuildCounterVar();
           ResultIterSpace.PrivateCounterVar = ISC.BuildPrivateCounterVar
        ();
           ResultIterSpace.CounterInit = ISC.BuildCounterInit();
        @@ -3749,7 +3819,8 @@ CheckOpenMPLoop(OpenMPDirectiveKind DKin
           QualType VType = LastIteration.get()->getType();
           // Build variables passed into runtime, nesessary for
        worksharing directives.
           ExprResult LB, UB, IL, ST, EUB;
        -  if (isOpenMPWorksharingDirective(DKind) ||
        isOpenMPTaskLoopDirective(DKind)) {
        +  if (isOpenMPWorksharingDirective(DKind) ||
        isOpenMPTaskLoopDirective(DKind) ||
        +      isOpenMPDistributeDirective(DKind)) {
             // Lower bound variable, initialized with zero.
             VarDecl *LBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".
        omp.lb");
             LB = buildDeclRefExpr(SemaRef, LBDecl, VType, InitLoc);
        @@ -3798,7 +3869,8 @@ CheckOpenMPLoop(OpenMPDirectiveKind DKin
             VarDecl *IVDecl = buildVarDecl(SemaRef, InitLoc, VType,
        ".omp.iv");
             IV = buildDeclRefExpr(SemaRef, IVDecl, VType, InitLoc);
             Expr *RHS = (isOpenMPWorksharingDirective(DKind) ||
        -                 isOpenMPTaskLoopDirective(DKind))
        +                 isOpenMPTaskLoopDirective(DKind) ||
        +                 isOpenMPDistributeDirective(DKind))
                             ? LB.get()
                             : SemaRef.ActOnIntegerConstant(SourceLocation
        (), 0).get();
             Init = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get
        (), RHS);
        @@ -3808,7 +3880,8 @@ CheckOpenMPLoop(OpenMPDirectiveKind DKin
           // Loop condition (IV < NumIterations) or (IV <= UB) for
        worksharing loops.
           SourceLocation CondLoc;
           ExprResult Cond =
        -      (isOpenMPWorksharingDirective(DKind) ||
        isOpenMPTaskLoopDirective(DKind))
        +      (isOpenMPWorksharingDirective(DKind) ||
        +       isOpenMPTaskLoopDirective(DKind) ||
        isOpenMPDistributeDirective(DKind))
                   ? SemaRef.BuildBinOp(CurScope, CondLoc, BO_LE, IV.get(),
        UB.get())
                   : SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
                                        NumIterations.get());
        @@ -3828,7 +3901,8 @@ CheckOpenMPLoop(OpenMPDirectiveKind DKin
           // Increments for worksharing loops (LB = LB + ST; UB = UB +
        ST).
           // Used for directives with static scheduling.
           ExprResult NextLB, NextUB;
        -  if (isOpenMPWorksharingDirective(DKind) ||
        isOpenMPTaskLoopDirective(DKind)) {
        +  if (isOpenMPWorksharingDirective(DKind) ||
        isOpenMPTaskLoopDirective(DKind) ||
        +      isOpenMPDistributeDirective(DKind)) {
             // LB + ST
             NextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, LB.get
        (), ST.get());
             if (!NextLB.isUsable())
        @@ -5345,6 +5419,32 @@ StmtResult Sema::ActOnOpenMPTaskLoopSimd
                                                   NestedLoopCount,
        Clauses, AStmt, B);
         }

        +StmtResult Sema::ActOnOpenMPDistributeDirective(
        +    ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation
        StartLoc,
        +    SourceLocation EndLoc,
        +    llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) {
        +  if (!AStmt)
        +    return StmtError();
        +
        +  assert(isa<CapturedStmt>(AStmt) && "Captured statement
        expected");
        +  OMPLoopDirective::HelperExprs B;
        +  // In presence of clause 'collapse' with number of loops, it
        will
        +  // define the nested loops number.
        +  unsigned NestedLoopCount =
        +      CheckOpenMPLoop(OMPD_distribute, getCollapseNumberExpr
        (Clauses),
        +                      nullptr /*ordered not a clause on
        distribute*/, AStmt,
        +                      *this, *DSAStack, VarsWithImplicitDSA, B);
        +  if (NestedLoopCount == 0)
        +    return StmtError();
        +
        +  assert((CurContext->isDependentContext() || B.builtAll()) &&
        +         "omp for loop exprs were not built");
        +
        +  getCurFunction()->setHasBranchProtectedScope();
        +  return OMPDistributeDirective::Create(Context, StartLoc, EndLoc,
        +                                        NestedLoopCount, Clauses,
        AStmt, B);
        +}
        +
         OMPClause *Sema::ActOnOpenMPSingleExprClause(OpenMPClauseKind
        Kind, Expr *Expr,
                                                      SourceLocation
        StartLoc,
                                                      SourceLocation
        LParenLoc,
        @@ -6381,6 +6481,49 @@ OMPClause *Sema::ActOnOpenMPFirstprivate
                   continue;
                 }
               }
        +
        +      // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
        +      // A list item that is private within a teams region must
        not appear in a
        +      // firstprivate clause on a distribute construct if any of
        the distribute
        +      // regions arising from the distribute construct ever bind
        to any of the
        +      // teams regions arising from the teams construct.
        +      // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
        +      // A list item that appears in a reduction clause of a teams
        construct
        +      // must not appear in a firstprivate clause on a distribute
        construct if
        +      // any of the distribute regions arising from the distribute
        construct
        +      // ever bind to any of the teams regions arising from the
        teams construct.
        +      // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
        +      // A list item may appear in a firstprivate or lastprivate
        clause but not
        +      // both.
        +      if (CurrDir == OMPD_distribute) {
        +        DVar = DSAStack->hasInnermostDSA(VD, MatchesAnyClause
        (OMPC_private),
        +                                         [](OpenMPDirectiveKind K)
        -> bool {
        +                                           return
        isOpenMPTeamsDirective(K);
        +                                         },
        +                                         false);
        +        if (DVar.CKind == OMPC_private && isOpenMPTeamsDirective
        (DVar.DKind)) {
        +          Diag(ELoc,
        diag::err_omp_firstprivate_distribute_private_teams);
        +          ReportOriginalDSA(*this, DSAStack, VD, DVar);
        +          continue;
        +        }
        +        DVar = DSAStack->hasInnermostDSA(VD, MatchesAnyClause
        (OMPC_reduction),
        +                                         [](OpenMPDirectiveKind K)
        -> bool {
        +                                           return
        isOpenMPTeamsDirective(K);
        +                                         },
        +                                         false);
        +        if (DVar.CKind == OMPC_reduction &&
        +            isOpenMPTeamsDirective(DVar.DKind)) {
        +          Diag(ELoc,
        diag::err_omp_firstprivate_distribute_in_teams_reduction);
        +          ReportOriginalDSA(*this, DSAStack, VD, DVar);
        +          continue;
        +        }
        +        DVar = DSAStack->getTopDSA(VD, false);
        +        if (DVar.CKind == OMPC_lastprivate) {
        +          Diag(ELoc,
        diag::err_omp_firstprivate_and_lastprivate_in_distribute);
        +          ReportOriginalDSA(*this, DSAStack, VD, DVar);
        +          continue;
        +        }
        +      }
             }

             // Variably modified types are not supported for tasks.
        @@ -6577,6 +6720,18 @@ OMPClause *Sema::ActOnOpenMPLastprivateC
             if (AssignmentOp.isInvalid())
               continue;

        +    // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
        +    // A list item may appear in a firstprivate or lastprivate
        clause but not
        +    // both.
        +    if (CurrDir == OMPD_distribute) {
        +      DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD,
        false);
        +      if (DVar.CKind == OMPC_firstprivate) {
        +        Diag(ELoc,
        diag::err_omp_firstprivate_and_lastprivate_in_distribute);
        +        ReportOriginalDSA(*this, DSAStack, VD, DVar);
        +        continue;
        +      }
        +    }
        +
             if (TopDVar.CKind != OMPC_firstprivate)
               DSAStack->addDSA(VD, DE, OMPC_lastprivate);
             Vars.push_back(DE);

        Modified: cfe/trunk/lib/Sema/TreeTransform.h
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/TreeTransform.h?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Sema/TreeTransform.h (original)
        +++ cfe/trunk/lib/Sema/TreeTransform.h Mon Dec  7 22:21:03 2015
        @@ -7386,6 +7386,17 @@ StmtResult TreeTransform<Derived>::Trans
           return Res;
         }

        +template <typename Derived>
        +StmtResult TreeTransform<Derived>::TransformOMPDistributeDirective
        (
        +    OMPDistributeDirective *D) {
        +  DeclarationNameInfo DirName;
        +  getDerived().getSema().StartOpenMPDSABlock(OMPD_distribute,
        DirName, nullptr,
        +                                             D->getLocStart());
        +  StmtResult Res = getDerived().TransformOMPExecutableDirective
        (D);
        +  getDerived().getSema().EndOpenMPDSABlock(Res.get());
        +  return Res;
        +}
        +

        //===----------------------------------------------------------------------===//

         // OpenMP clause transformation

        //===----------------------------------------------------------------------===//


        Modified: cfe/trunk/lib/Serialization/ASTReaderStmt.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTReaderStmt.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Serialization/ASTReaderStmt.cpp (original)
        +++ cfe/trunk/lib/Serialization/ASTReaderStmt.cpp Mon Dec  7
        22:21:03 2015
        @@ -2441,6 +2441,10 @@ void ASTStmtReader::VisitOMPTaskLoopSimd
           VisitOMPLoopDirective(D);
         }

        +void ASTStmtReader::VisitOMPDistributeDirective
        (OMPDistributeDirective *D) {
        +  VisitOMPLoopDirective(D);
        +}
        +

        //===----------------------------------------------------------------------===//

         // ASTReader Implementation

        //===----------------------------------------------------------------------===//

        @@ -3079,6 +3083,14 @@ Stmt *ASTReader::ReadStmtFromStream(Modu
               break;
             }

        +    case STMT_OMP_DISTRIBUTE_DIRECTIVE: {
        +      unsigned NumClauses = Record[ASTStmtReader::NumStmtFields];
        +      unsigned CollapsedNum = Record[ASTStmtReader::NumStmtFields
        + 1];
        +      S = OMPDistributeDirective::CreateEmpty(Context, NumClauses,
        CollapsedNum,
        +                                              Empty);
        +      break;
        +    }
        +
             case EXPR_CXX_OPERATOR_CALL:
               S = new (Context) CXXOperatorCallExpr(Context, Empty);
               break;

        Modified: cfe/trunk/lib/Serialization/ASTWriterStmt.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriterStmt.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/Serialization/ASTWriterStmt.cpp (original)
        +++ cfe/trunk/lib/Serialization/ASTWriterStmt.cpp Mon Dec  7
        22:21:03 2015
        @@ -2261,6 +2261,11 @@ void ASTStmtWriter::VisitOMPTaskLoopSimd
           Code = serialization::STMT_OMP_TASKLOOP_SIMD_DIRECTIVE;
         }

        +void ASTStmtWriter::VisitOMPDistributeDirective
        (OMPDistributeDirective *D) {
        +  VisitOMPLoopDirective(D);
        +  Code = serialization::STMT_OMP_DISTRIBUTE_DIRECTIVE;
        +}
        +

        //===----------------------------------------------------------------------===//

         // ASTWriter Implementation

        //===----------------------------------------------------------------------===//


        Modified: cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp
        URL:
        http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp?rev=255001&r1=255000&r2=255001&view=diff

        ==============================================================================

        --- cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp (original)
        +++ cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp Mon Dec  7
        22:21:03 2015
        @@ -831,6 +831,7 @@ void ExprEngine::Visit(const Stmt *S, Ex
             case Stmt::OMPCancelDirectiveClass:
             case Stmt::OMPTaskLoopDirectiveClass:
             case Stmt::OMPTaskLoopSimdDirectiveClass:
        +    case Stmt::OMPDist

        _______________________________________________
        cfe-commits mailing list
        cfe-commits at lists.llvm.org
        http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits



  --
  Alexey Samsonov
  vonosmas at gmail.com



  _______________________________________________
  cfe-commits mailing list
  cfe-commits at lists.llvm.org
  http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits



-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20151210/07a177e5/attachment-0001.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: graycol.gif
Type: image/gif
Size: 105 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20151210/07a177e5/attachment-0001.gif>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: FixOMPDistribute.diff
Type: application/octet-stream
Size: 601 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20151210/07a177e5/attachment-0001.obj>


More information about the cfe-commits mailing list