Commit c112e941 authored by Alexey Bataev's avatar Alexey Bataev
Browse files

[OPENMP50]Add basic support for depobj construct.

Added basic parsing/sema/serialization support for depobj directive.
parent 5c83bede
Loading
Loading
Loading
Loading
+5 −1
Original line number Diff line number Diff line
@@ -2574,7 +2574,11 @@ enum CXCursorKind {
   */
  CXCursor_OMPParallelMasterDirective      = 285,

  CXCursor_LastStmt = CXCursor_OMPParallelMasterDirective,
  /** OpenMP depobj directive.
   */
  CXCursor_OMPDepobjDirective             = 286,

  CXCursor_LastStmt = CXCursor_OMPDepobjDirective,

  /**
   * Cursor that represents the translation unit itself.
+86 −0
Original line number Diff line number Diff line
@@ -4108,6 +4108,92 @@ public:
  }
};

/// This represents implicit clause 'depobj' for the '#pragma omp depobj'
/// directive.
/// This clause does not exist by itself, it can be only as a part of 'omp
/// depobj' directive. This clause is introduced to keep the original structure
/// of \a OMPExecutableDirective class and its derivatives and to use the
/// existing infrastructure of clauses with the list of variables.
///
/// \code
/// #pragma omp depobj(a) destroy
/// \endcode
/// In this example directive '#pragma omp depobj' has implicit clause 'depobj'
/// with the depobj 'a'.
class OMPDepobjClause final : public OMPClause {
  friend class OMPClauseReader;

  /// Location of '('.
  SourceLocation LParenLoc;

  /// Chunk size.
  Expr *Depobj = nullptr;

  /// Build clause with number of variables \a N.
  ///
  /// \param StartLoc Starting location of the clause.
  /// \param LParenLoc Location of '('.
  /// \param EndLoc Ending location of the clause.
  OMPDepobjClause(SourceLocation StartLoc, SourceLocation LParenLoc,
                  SourceLocation EndLoc)
      : OMPClause(OMPC_depobj, StartLoc, EndLoc), LParenLoc(LParenLoc) {}

  /// Build an empty clause.
  ///
  explicit OMPDepobjClause()
      : OMPClause(OMPC_depobj, SourceLocation(), SourceLocation()) {}

  void setDepobj(Expr *E) { Depobj = E; }

  /// Sets the location of '('.
  void setLParenLoc(SourceLocation Loc) { LParenLoc = Loc; }

public:
  /// Creates clause.
  ///
  /// \param C AST context.
  /// \param StartLoc Starting location of the clause.
  /// \param LParenLoc Location of '('.
  /// \param EndLoc Ending location of the clause.
  /// \param Depobj depobj expression associated with the 'depobj' directive.
  static OMPDepobjClause *Create(const ASTContext &C, SourceLocation StartLoc,
                                 SourceLocation LParenLoc,
                                 SourceLocation EndLoc, Expr *Depobj);

  /// Creates an empty clause.
  ///
  /// \param C AST context.
  static OMPDepobjClause *CreateEmpty(const ASTContext &C);

  /// Returns depobj expression associated with the clause.
  Expr *getDepobj() { return Depobj; }
  const Expr *getDepobj() const { return Depobj; }

  /// Returns the location of '('.
  SourceLocation getLParenLoc() const { return LParenLoc; }

  child_range children() {
    return child_range(reinterpret_cast<Stmt **>(&Depobj),
                       reinterpret_cast<Stmt **>(&Depobj) + 1);
  }

  const_child_range children() const {
    auto Children = const_cast<OMPDepobjClause *>(this)->children();
    return const_child_range(Children.begin(), Children.end());
  }

  child_range used_children() {
    return child_range(child_iterator(), child_iterator());
  }
  const_child_range used_children() const {
    return const_child_range(const_child_iterator(), const_child_iterator());
  }

  static bool classof(const OMPClause *T) {
    return T->getClauseKind() == OMPC_depobj;
  }
};

/// This represents implicit clause 'depend' for the '#pragma omp task'
/// directive.
///
+9 −0
Original line number Diff line number Diff line
@@ -2842,6 +2842,9 @@ DEF_TRAVERSE_STMT(OMPCancelDirective,
DEF_TRAVERSE_STMT(OMPFlushDirective,
                  { TRY_TO(TraverseOMPExecutableDirective(S)); })

DEF_TRAVERSE_STMT(OMPDepobjDirective,
                  { TRY_TO(TraverseOMPExecutableDirective(S)); })

DEF_TRAVERSE_STMT(OMPOrderedDirective,
                  { TRY_TO(TraverseOMPExecutableDirective(S)); })

@@ -3347,6 +3350,12 @@ bool RecursiveASTVisitor<Derived>::VisitOMPFlushClause(OMPFlushClause *C) {
  return true;
}

template <typename Derived>
bool RecursiveASTVisitor<Derived>::VisitOMPDepobjClause(OMPDepobjClause *C) {
  TRY_TO(TraverseStmt(C->getDepobj()));
  return true;
}

template <typename Derived>
bool RecursiveASTVisitor<Derived>::VisitOMPDependClause(OMPDependClause *C) {
  TRY_TO(VisitOMPClauseList(C));
+58 −0
Original line number Diff line number Diff line
@@ -2314,6 +2314,64 @@ public:
  }
};

/// This represents '#pragma omp depobj' directive.
///
/// \code
/// #pragma omp depobj(a) depend(in:x,y)
/// \endcode
/// In this example directive '#pragma omp  depobj' initializes a depobj object
/// 'a' with dependence type 'in' and a list with 'x' and 'y' locators.
class OMPDepobjDirective final : public OMPExecutableDirective {
  friend class ASTStmtReader;

  /// 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 NumClauses Number of clauses.
  ///
  OMPDepobjDirective(SourceLocation StartLoc, SourceLocation EndLoc,
                     unsigned NumClauses)
      : OMPExecutableDirective(this, OMPDepobjDirectiveClass,
                               llvm::omp::OMPD_depobj, StartLoc, EndLoc,
                               NumClauses, 0) {}

  /// Build an empty directive.
  ///
  /// \param NumClauses Number of clauses.
  ///
  explicit OMPDepobjDirective(unsigned NumClauses)
      : OMPExecutableDirective(this, OMPDepobjDirectiveClass,
                               llvm::omp::OMPD_depobj, SourceLocation(),
                               SourceLocation(), NumClauses, 0) {}

public:
  /// 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 Clauses List of clauses.
  ///
  static OMPDepobjDirective *Create(const ASTContext &C,
                                    SourceLocation StartLoc,
                                    SourceLocation EndLoc,
                                    ArrayRef<OMPClause *> Clauses);

  /// Creates an empty directive with the place for \a NumClauses
  /// clauses.
  ///
  /// \param C AST context.
  /// \param NumClauses Number of clauses.
  ///
  static OMPDepobjDirective *CreateEmpty(const ASTContext &C,
                                         unsigned NumClauses, EmptyShell);

  static bool classof(const Stmt *T) {
    return T->getStmtClass() == OMPDepobjDirectiveClass;
  }
};

/// This represents '#pragma omp ordered' directive.
///
/// \code
+8 −2
Original line number Diff line number Diff line
@@ -10031,8 +10031,14 @@ def note_omp_invalid_subscript_on_this_ptr_map : Note <
  "expected 'this' subscript expression on map clause to be 'this[0]'">;
def err_omp_invalid_map_this_expr : Error <
  "invalid 'this' expression on 'map' clause">;
def err_implied_omp_allocator_handle_t_not_found : Error<
  "omp_allocator_handle_t type not found; include <omp.h>">;
def err_omp_implied_type_not_found : Error<
  "'%0' type not found; include <omp.h>">;
def err_omp_expected_omp_depend_t_lvalue : Error<
  "expected lvalue expression%select{ of 'omp_depend_t' type, not %1|}0">;
def err_omp_depobj_expected : Error<
  "expected depobj expression">;
def err_omp_depobj_single_clause_expected : Error<
  "exactly one of 'depend', 'destroy', or 'update' clauses is expected">;
def err_omp_expected_predefined_allocator : Error<
  "expected one of the predefined allocators for the variables with the static "
  "storage: 'omp_default_mem_alloc', 'omp_large_cap_mem_alloc', "
Loading