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
Tue Dec 8 09:37:26 PST 2015


I am investigating.

Thanks

-- Carlo



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' | 'taskyield'
   |
    ///         '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

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20151208/58459f19/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/20151208/58459f19/attachment-0001.gif>


More information about the cfe-commits mailing list