[clang] [Clang][OpenMP 6.0] Support positional arguments in `adjust_args` clause (PR #225081)
via cfe-commits
cfe-commits at lists.llvm.org
Wed Sep 23 09:47:10 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-clang-static-analyzer-1
Author: ykhatav (ykhatav)
<details>
<summary>Changes</summary>
Extends the `adjust_args` to accept positional arguments as specified in OpenMP 6.0 spec, in addition to the existing named-parameter form.This PR adds parsing, Sema, AST, and serialization support for it.
---
Patch is 76.79 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/225081.diff
36 Files Affected:
- (modified) clang/bindings/python/clang/cindex.py (+6)
- (modified) clang/include/clang-c/Index.h (+13-1)
- (modified) clang/include/clang/AST/ComputeDependence.h (+4)
- (modified) clang/include/clang/AST/ExprOpenMP.h (+140)
- (modified) clang/include/clang/AST/OpenMPClause.h (+23)
- (modified) clang/include/clang/AST/RecursiveASTVisitor.h (+2)
- (modified) clang/include/clang/AST/TextNodeDumper.h (+1)
- (modified) clang/include/clang/Basic/DiagnosticParseKinds.td (+4)
- (modified) clang/include/clang/Basic/DiagnosticSemaKinds.td (+3)
- (modified) clang/include/clang/Basic/StmtNodes.td (+2)
- (modified) clang/include/clang/Parse/Parser.h (+11)
- (modified) clang/include/clang/Sema/SemaOpenMP.h (+14)
- (modified) clang/include/clang/Serialization/ASTBitCodes.h (+2)
- (modified) clang/lib/AST/AttrImpl.cpp (+12-5)
- (modified) clang/lib/AST/ComputeDependence.cpp (+20)
- (modified) clang/lib/AST/Expr.cpp (+2)
- (modified) clang/lib/AST/ExprClassification.cpp (+2)
- (modified) clang/lib/AST/ExprConstant.cpp (+2)
- (modified) clang/lib/AST/ItaniumMangle.cpp (+2)
- (modified) clang/lib/AST/OpenMPClause.cpp (+85)
- (modified) clang/lib/AST/StmtPrinter.cpp (+18)
- (modified) clang/lib/AST/StmtProfile.cpp (+13)
- (modified) clang/lib/AST/TextNodeDumper.cpp (+6)
- (modified) clang/lib/Parse/ParseOpenMP.cpp (+110-3)
- (modified) clang/lib/Sema/SemaExceptionSpec.cpp (+2)
- (modified) clang/lib/Sema/SemaOpenMP.cpp (+164-19)
- (modified) clang/lib/Sema/TreeTransform.h (+64)
- (modified) clang/lib/Serialization/ASTReaderStmt.cpp (+23)
- (modified) clang/lib/Serialization/ASTWriterStmt.cpp (+17)
- (modified) clang/lib/StaticAnalyzer/Core/ExprEngine.cpp (+2)
- (added) clang/test/OpenMP/declare_variant_adjust_args_positional_ast_print.cpp (+175)
- (added) clang/test/OpenMP/declare_variant_adjust_args_positional_messages.cpp (+228)
- (added) clang/test/OpenMP/declare_variant_adjust_args_positional_template.cpp (+62)
- (modified) clang/test/OpenMP/declare_variant_clauses_messages.cpp (+9-7)
- (modified) clang/tools/libclang/CIndex.cpp (+4)
- (modified) clang/tools/libclang/CXCursor.cpp (+8)
``````````diff
diff --git a/clang/bindings/python/clang/cindex.py b/clang/bindings/python/clang/cindex.py
index bc00dd770ce3b5..a21eb9e9d543f4 100644
--- a/clang/bindings/python/clang/cindex.py
+++ b/clang/bindings/python/clang/cindex.py
@@ -1113,6 +1113,12 @@ def is_unexposed(self):
# Represents a C++26 pack indexing expression.
PACK_INDEXING_EXPR = 156
+ # OpenMP 6.0 [5.2.1] 'omp_num_args [+/- logical_offset]' bound expression.
+ OMP_NUM_ARGS_EXPR = 157
+
+ # OpenMP 6.0 [5.2.1] parameter range 'lb:ub' expression.
+ OMP_ARGUMENT_RANGE_EXPR = 158
+
# A statement whose specific kind is not exposed via this interface.
#
# Unexposed statements have the same operations as any other kind of
diff --git a/clang/include/clang-c/Index.h b/clang/include/clang-c/Index.h
index 1c8d097f1beab4..1ab3635f2ea3a3 100644
--- a/clang/include/clang-c/Index.h
+++ b/clang/include/clang-c/Index.h
@@ -1691,7 +1691,19 @@ enum CXCursorKind {
*/
CXCursor_PackIndexingExpr = 156,
- CXCursor_LastExpr = CXCursor_PackIndexingExpr,
+ /**
+ * OpenMP 6.0 [5.2.1, Parameter List Items]
+ * The 'omp_num_args' identifier with an optional logical offset.
+ */
+ CXCursor_OMPNumArgsExpr = 157,
+
+ /**
+ * OpenMP 6.0 [5.2.1, Parameter List Items]
+ * A parameter range 'lb:ub', either bound of which may be omitted.
+ */
+ CXCursor_OMPArgumentRangeExpr = 158,
+
+ CXCursor_LastExpr = CXCursor_OMPArgumentRangeExpr,
/* Statements */
CXCursor_FirstStmt = 200,
diff --git a/clang/include/clang/AST/ComputeDependence.h b/clang/include/clang/AST/ComputeDependence.h
index 6430081a40350d..4a36588d399e17 100644
--- a/clang/include/clang/AST/ComputeDependence.h
+++ b/clang/include/clang/AST/ComputeDependence.h
@@ -100,6 +100,8 @@ class AtomicExpr;
class ArraySectionExpr;
class OMPArrayShapingExpr;
class OMPIteratorExpr;
+class OMPNumArgsExpr;
+class OMPArgumentRangeExpr;
class ObjCArrayLiteral;
class ObjCDictionaryLiteral;
class ObjCBoxedExpr;
@@ -200,6 +202,8 @@ ExprDependence computeDependence(AtomicExpr *E);
ExprDependence computeDependence(ArraySectionExpr *E);
ExprDependence computeDependence(OMPArrayShapingExpr *E);
ExprDependence computeDependence(OMPIteratorExpr *E);
+ExprDependence computeDependence(OMPNumArgsExpr *E);
+ExprDependence computeDependence(OMPArgumentRangeExpr *E);
ExprDependence computeDependence(ObjCArrayLiteral *E);
ExprDependence computeDependence(ObjCDictionaryLiteral *E);
diff --git a/clang/include/clang/AST/ExprOpenMP.h b/clang/include/clang/AST/ExprOpenMP.h
index 4d3c5f54ad7dde..bc293465e3ff80 100644
--- a/clang/include/clang/AST/ExprOpenMP.h
+++ b/clang/include/clang/AST/ExprOpenMP.h
@@ -296,6 +296,146 @@ class OMPIteratorExpr final
}
};
+/// OpenMP 6.0 [5.2.1, Parameter List Items]
+/// Represents the 'omp_num_args' identifier used as a bound of a parameter
+/// range, together with an optional logical offset:
+/// \code
+/// omp_num_args [ ('+' | '-') logical_offset ]
+/// \endcode
+class OMPNumArgsExpr final : public Expr {
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
+
+ /// The logical offset, or null if none was written.
+ Stmt *Offset = nullptr;
+ /// Location of the 'omp_num_args' identifier.
+ SourceLocation NumArgsLoc;
+ /// Location of the '+' or '-'; invalid if there is no offset.
+ SourceLocation OpLoc;
+ /// True if the offset was written with '-'.
+ bool IsSubtraction = false;
+
+public:
+ OMPNumArgsExpr(QualType Type, SourceLocation NumArgsLoc, SourceLocation OpLoc,
+ bool IsSubtraction, Expr *Offset)
+ : Expr(OMPNumArgsExprClass, Type, VK_PRValue, OK_Ordinary),
+ Offset(Offset), NumArgsLoc(NumArgsLoc), OpLoc(OpLoc),
+ IsSubtraction(IsSubtraction) {
+ setDependence(computeDependence(this));
+ }
+
+ /// Create an empty 'omp_num_args' expression.
+ explicit OMPNumArgsExpr(EmptyShell Shell)
+ : Expr(OMPNumArgsExprClass, Shell) {}
+
+ /// Gets the logical offset, or null if none was written.
+ Expr *getOffset() { return cast_or_null<Expr>(Offset); }
+ const Expr *getOffset() const { return cast_or_null<Expr>(Offset); }
+ void setOffset(Expr *E) { Offset = E; }
+
+ /// True if the offset was written with '-' rather than '+'.
+ bool isSubtraction() const { return IsSubtraction; }
+ void setIsSubtraction(bool IS) { IsSubtraction = IS; }
+
+ SourceLocation getNumArgsLoc() const { return NumArgsLoc; }
+ void setNumArgsLoc(SourceLocation L) { NumArgsLoc = L; }
+
+ SourceLocation getOperatorLoc() const { return OpLoc; }
+ void setOperatorLoc(SourceLocation L) { OpLoc = L; }
+
+ SourceLocation getBeginLoc() const LLVM_READONLY { return NumArgsLoc; }
+ SourceLocation getEndLoc() const LLVM_READONLY {
+ return Offset ? Offset->getEndLoc() : NumArgsLoc;
+ }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == OMPNumArgsExprClass;
+ }
+
+ // Iterators
+ child_range children() { return child_range(&Offset, &Offset + 1); }
+ const_child_range children() const {
+ return const_child_range(&Offset, &Offset + 1);
+ }
+};
+
+/// OpenMP 6.0 [5.2.1, Parameter List Items]
+/// Represents a parameter range, one list item that stands for every parameter
+/// position from a lower to an upper bound:
+/// \code
+/// [ lb ] ':' [ ub ]
+/// \endcode
+/// Either bound may be omitted: an omitted \c lb defaults to 1 and an omitted
+/// \c ub defaults to 'omp_num_args'. A bound may be an 'omp_num_args'
+/// expression, which is why this node's children are general expressions rather
+/// than integer literals.
+///
+/// The type is 'void': a range is never a value, it only ever appears as an
+/// item of an 'adjust_args' parameter list in \c OMPDeclareVariantAttr.
+class OMPArgumentRangeExpr final : public Expr {
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
+
+ enum { LOWER_BOUND, UPPER_BOUND, NUM_SUBEXPRS };
+
+ /// The two bounds; either may be null when the bound was omitted.
+ Stmt *SubExprs[NUM_SUBEXPRS] = {nullptr, nullptr};
+ /// Location of the ':' separating the bounds.
+ SourceLocation ColonLoc;
+
+public:
+ OMPArgumentRangeExpr(QualType Type, Expr *LowerBound, SourceLocation ColonLoc,
+ Expr *UpperBound)
+ : Expr(OMPArgumentRangeExprClass, Type, VK_PRValue, OK_Ordinary),
+ ColonLoc(ColonLoc) {
+ SubExprs[LOWER_BOUND] = LowerBound;
+ SubExprs[UPPER_BOUND] = UpperBound;
+ setDependence(computeDependence(this));
+ }
+
+ /// Create an empty parameter range expression.
+ explicit OMPArgumentRangeExpr(EmptyShell Shell)
+ : Expr(OMPArgumentRangeExprClass, Shell) {}
+
+ /// Gets the lower bound, or null if it was omitted (meaning 1).
+ Expr *getLowerBound() { return cast_or_null<Expr>(SubExprs[LOWER_BOUND]); }
+ const Expr *getLowerBound() const {
+ return cast_or_null<Expr>(SubExprs[LOWER_BOUND]);
+ }
+ void setLowerBound(Expr *E) { SubExprs[LOWER_BOUND] = E; }
+
+ /// Gets the upper bound, or null if it was omitted (meaning 'omp_num_args').
+ Expr *getUpperBound() { return cast_or_null<Expr>(SubExprs[UPPER_BOUND]); }
+ const Expr *getUpperBound() const {
+ return cast_or_null<Expr>(SubExprs[UPPER_BOUND]);
+ }
+ void setUpperBound(Expr *E) { SubExprs[UPPER_BOUND] = E; }
+
+ SourceLocation getColonLoc() const { return ColonLoc; }
+ void setColonLoc(SourceLocation L) { ColonLoc = L; }
+
+ SourceLocation getBeginLoc() const LLVM_READONLY {
+ return SubExprs[LOWER_BOUND] ? SubExprs[LOWER_BOUND]->getBeginLoc()
+ : ColonLoc;
+ }
+ SourceLocation getEndLoc() const LLVM_READONLY {
+ return SubExprs[UPPER_BOUND] ? SubExprs[UPPER_BOUND]->getEndLoc()
+ : ColonLoc;
+ }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == OMPArgumentRangeExprClass;
+ }
+
+ // Iterators
+ child_range children() {
+ return child_range(&SubExprs[LOWER_BOUND], &SubExprs[NUM_SUBEXPRS]);
+ }
+ const_child_range children() const {
+ return const_child_range(&SubExprs[LOWER_BOUND], &SubExprs[NUM_SUBEXPRS]);
+ }
+};
+
} // end namespace clang
#endif
diff --git a/clang/include/clang/AST/OpenMPClause.h b/clang/include/clang/AST/OpenMPClause.h
index 9e9295e1a0c549..f79c9b2c12ce69 100644
--- a/clang/include/clang/AST/OpenMPClause.h
+++ b/clang/include/clang/AST/OpenMPClause.h
@@ -10566,6 +10566,29 @@ class OMPXBareClause : public OMPNoChildClause<llvm::omp::OMPC_ompx_bare> {
OMPXBareClause() = default;
};
+/// Resolve one 'adjust_args' parameter-list item to the 1-based argument
+/// positions it identifies (OpenMP 6.0 [5.2.1]).
+///
+/// \param Item A named item (\c DeclRefExpr to a \c ParmVarDecl of \p FD),
+/// a positional item (a constant integer expression), or an
+/// \c OMPArgumentRangeExpr. Callers pass IgnoreParenImpCasts().
+/// \param FD The base function the OMPDeclareVariantAttr is attached to.
+/// \param NumArgs The value of 'omp_num_args' at the point of resolution:
+/// \c max(FD->getNumParams(), Call->getNumArgs()) at a call
+/// site, or \c FD->getNumParams() with no call site available
+/// (OpenMP 6.0 [20.1]).
+/// \param Positions Resolved positions are appended here, ascending. Positions
+/// outside [1, NumArgs] are silently dropped
+/// (OpenMP 6.0 [9.6.2]).
+/// \returns false if \p Item is not a resolvable item shape, or if a bound is
+/// dependent or not a constant expression.
+///
+/// Emits no diagnostics: it lives in the AST library so it can later be
+/// shared with CodeGen. Sema diagnoses separately, before calling this.
+bool resolveOMPAdjustArgsItem(const Expr *Item, const FunctionDecl *FD,
+ unsigned NumArgs, const ASTContext &Ctx,
+ SmallVectorImpl<unsigned> &Positions);
+
} // namespace clang
#endif // LLVM_CLANG_AST_OPENMPCLAUSE_H
diff --git a/clang/include/clang/AST/RecursiveASTVisitor.h b/clang/include/clang/AST/RecursiveASTVisitor.h
index 1f7c8d762e1b52..5a66c147ac8cab 100644
--- a/clang/include/clang/AST/RecursiveASTVisitor.h
+++ b/clang/include/clang/AST/RecursiveASTVisitor.h
@@ -2954,6 +2954,8 @@ DEF_TRAVERSE_STMT(MatrixSubscriptExpr, {})
DEF_TRAVERSE_STMT(ArraySectionExpr, {})
DEF_TRAVERSE_STMT(OMPArrayShapingExpr, {})
DEF_TRAVERSE_STMT(OMPIteratorExpr, {})
+DEF_TRAVERSE_STMT(OMPNumArgsExpr, {})
+DEF_TRAVERSE_STMT(OMPArgumentRangeExpr, {})
DEF_TRAVERSE_STMT(BlockExpr, {
TRY_TO(TraverseDecl(S->getBlockDecl()));
diff --git a/clang/include/clang/AST/TextNodeDumper.h b/clang/include/clang/AST/TextNodeDumper.h
index 1cdd8c37c7fc63..f2fd730d34c5d1 100644
--- a/clang/include/clang/AST/TextNodeDumper.h
+++ b/clang/include/clang/AST/TextNodeDumper.h
@@ -328,6 +328,7 @@ class TextNodeDumper
void VisitObjCIvarRefExpr(const ObjCIvarRefExpr *Node);
void VisitObjCBoolLiteralExpr(const ObjCBoolLiteralExpr *Node);
void VisitOMPIteratorExpr(const OMPIteratorExpr *Node);
+ void VisitOMPNumArgsExpr(const OMPNumArgsExpr *Node);
void VisitConceptSpecializationExpr(const ConceptSpecializationExpr *Node);
void VisitRequiresExpr(const RequiresExpr *Node);
diff --git a/clang/include/clang/Basic/DiagnosticParseKinds.td b/clang/include/clang/Basic/DiagnosticParseKinds.td
index 6a48d74079f4ed..5c826aba1c200f 100644
--- a/clang/include/clang/Basic/DiagnosticParseKinds.td
+++ b/clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1623,6 +1623,10 @@ def err_omp_unknown_adjust_args_op
: Error<
"incorrect 'adjust_args' type, expected 'need_device_ptr'%select{|, "
"'need_device_addr',}0 or 'nothing'">;
+def err_omp_num_args_invalid_form
+ : Error<"'omp_num_args' %select{is only allowed as a bound of a parameter "
+ "range|may only be followed by '+' or '-' and a constant logical "
+ "offset}0">;
def err_omp_declare_variant_wrong_clause : Error<
"expected %select{'match'|'match', 'adjust_args', or 'append_args'}0 clause "
"on 'omp declare variant' directive">;
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 3a910c9c3f2b92..090acdfa4cac84 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -12815,6 +12815,9 @@ def err_omp_instantiation_not_supported
: Error<"instantiation of '%0' not supported yet">;
def err_omp_adjust_arg_multiple_clauses : Error<
"'adjust_arg' argument %0 used in multiple clauses">;
+def err_omp_adjust_args_invalid_item : Error<
+ "expected a parameter name, a parameter position, or a parameter range in "
+ "'adjust_args' clause">;
def err_omp_clause_requires_dispatch_construct : Error<
"'%0' clause requires 'dispatch' context selector">;
def err_omp_append_args_with_varargs : Error<
diff --git a/clang/include/clang/Basic/StmtNodes.td b/clang/include/clang/Basic/StmtNodes.td
index 84804d6705d2b9..e9f64565677e9d 100644
--- a/clang/include/clang/Basic/StmtNodes.td
+++ b/clang/include/clang/Basic/StmtNodes.td
@@ -85,6 +85,8 @@ def MatrixSingleSubscriptExpr : StmtNode<Expr>;
def MatrixSubscriptExpr : StmtNode<Expr>;
def ArraySectionExpr : StmtNode<Expr>;
def OMPIteratorExpr : StmtNode<Expr>;
+def OMPNumArgsExpr : StmtNode<Expr>;
+def OMPArgumentRangeExpr : StmtNode<Expr>;
def CallExpr : StmtNode<Expr>;
def MemberExpr : StmtNode<Expr>;
def CastExpr : StmtNode<Expr, 1>;
diff --git a/clang/include/clang/Parse/Parser.h b/clang/include/clang/Parse/Parser.h
index 163aa483a84e3f..832835b27edc51 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -7053,6 +7053,17 @@ class Parser : public CodeCompletionHandler {
bool ParseOpenMPReservedLocator(OpenMPClauseKind Kind,
SemaOpenMP::OpenMPVarListDataTy &Data,
const LangOptions &LangOpts);
+
+ /// Parses one bound of an OpenMP 6.0 'adjust_args' parameter range, which may
+ /// be 'omp_num_args' with an optional logical offset, or the whole
+ /// parameter-list item when no range colon follows it.
+ ExprResult ParseOpenMPAdjustArgsBound();
+
+ /// Parses an OpenMP 6.0 'adjust_args' parameter list, whose items may be
+ /// parameter names, positions, or ranges with optional bounds.
+ /// Returns true on error.
+ bool ParseOpenMPAdjustArgsList(SmallVectorImpl<Expr *> &Vars);
+
/// Parses clauses with list.
bool ParseOpenMPVarList(OpenMPDirectiveKind DKind, OpenMPClauseKind Kind,
SmallVectorImpl<Expr *> &Vars,
diff --git a/clang/include/clang/Sema/SemaOpenMP.h b/clang/include/clang/Sema/SemaOpenMP.h
index 361473140e2364..99199ac06c2a23 100644
--- a/clang/include/clang/Sema/SemaOpenMP.h
+++ b/clang/include/clang/Sema/SemaOpenMP.h
@@ -1491,6 +1491,20 @@ class SemaOpenMP : public SemaBase {
SourceLocation LLoc, SourceLocation RLoc,
ArrayRef<OMPIteratorData> Data);
+ /// Called on a well-formed 'omp_num_args' expression appearing as a bound of
+ /// an 'adjust_args' parameter range. \a Offset is null if no logical offset
+ /// was written, in which case \a OpLoc is invalid.
+ ExprResult ActOnOMPNumArgsExpr(SourceLocation NumArgsLoc,
+ SourceLocation OpLoc, bool IsSubtraction,
+ Expr *Offset);
+
+ /// Called on a well-formed 'adjust_args' parameter range 'lb:ub'. Either
+ /// bound may be null, meaning 1 for \a LowerBound and 'omp_num_args' for
+ /// \a UpperBound.
+ ExprResult ActOnOMPArgumentRangeExpr(Expr *LowerBound,
+ SourceLocation ColonLoc,
+ Expr *UpperBound);
+
ExprResult ActOnOpenMPDimsModifier(OpenMPClauseKind Kind, int Modifier,
Expr *ModifierExpr,
SourceLocation ModifierLoc,
diff --git a/clang/include/clang/Serialization/ASTBitCodes.h b/clang/include/clang/Serialization/ASTBitCodes.h
index 6a52a9e4fa780f..678b17b63a9ffc 100644
--- a/clang/include/clang/Serialization/ASTBitCodes.h
+++ b/clang/include/clang/Serialization/ASTBitCodes.h
@@ -2057,6 +2057,8 @@ enum StmtCode {
EXPR_ARRAY_SECTION,
EXPR_OMP_ARRAY_SHAPING,
EXPR_OMP_ITERATOR,
+ EXPR_OMP_NUM_ARGS,
+ EXPR_OMP_ARGUMENT_RANGE,
// ARC
EXPR_OBJC_BRIDGED_CAST, // ObjCBridgedCastExpr
diff --git a/clang/lib/AST/AttrImpl.cpp b/clang/lib/AST/AttrImpl.cpp
index 7272ad0de9a2cc..09165226152af6 100644
--- a/clang/lib/AST/AttrImpl.cpp
+++ b/clang/lib/AST/AttrImpl.cpp
@@ -14,6 +14,7 @@
#include "clang/AST/ASTStructuralEquivalence.h"
#include "clang/AST/Attr.h"
#include "clang/AST/Expr.h"
+#include "clang/AST/ExprOpenMP.h"
#include "clang/AST/Type.h"
#include <optional>
#include <type_traits>
@@ -209,12 +210,18 @@ void OMPDeclareVariantAttr::printPrettyPragma(
OS << " match(" << traitInfos << ")";
auto PrintExprs = [&OS, &Policy](Expr **Begin, Expr **End) {
- for (Expr **I = Begin; I != End; ++I) {
- assert(*I && "Expected non-null Stmt");
- if (I != Begin)
- OS << ",";
- (*I)->printPretty(OS, nullptr, Policy);
+ if (Begin != End) {
+ if (const auto *Range = dyn_cast<OMPArgumentRangeExpr>(*Begin);
+ Range && !Range->getLowerBound())
+ OS << " ";
}
+ llvm::interleave(
+ Begin, End,
+ [&](Expr *E) {
+ assert(E && "Expected non-null Stmt");
+ E->printPretty(OS, nullptr, Policy);
+ },
+ [&OS] { OS << ","; });
};
if (adjustArgsNothing_size()) {
OS << " adjust_args(nothing:";
diff --git a/clang/lib/AST/ComputeDependence.cpp b/clang/lib/AST/ComputeDependence.cpp
index 0fc9da18b93940..4f33ed8beca4e3 100644
--- a/clang/lib/AST/ComputeDependence.cpp
+++ b/clang/lib/AST/ComputeDependence.cpp
@@ -500,6 +500,26 @@ ExprDependence clang::computeDependence(OMPIteratorExpr *E) {
return D;
}
+ExprDependence clang::computeDependence(OMPNumArgsExpr *E) {
+ // The type is always 'int', so the expression is never type-dependent; only
+ // the logical offset can make it value- or instantiation-dependent.
+ if (Expr *Offset = E->getOffset())
+ return Offset->getDependence() & ~ExprDependence::Type;
+ return ExprDependence::None;
+}
+
+ExprDependence clang::computeDependence(OMPArgumentRangeExpr *E) {
+ // The type is always 'void', so the expression is never type-dependent.
+ // Either bound may be omitted, meaning 1 for the lower bound and
+ // 'omp_num_args' for the upper bound.
+ auto D = ExprDependence::None;
+ if (Expr *LB = E->getLowerBound())
+ D |= LB->getDependence();
+ if (Expr *UB = E->getUpperBound())
+ D |= UB->getDependence();
+ return D & ~ExprDependence::Type;
+}
+
/// Compute the type-, value-, and instantiation-dependence of a
/// declaration reference
/// based on the declaration being referenced.
diff --git a/clang/lib/AST/Expr.cpp b/clang/lib/AST/Expr.cpp
index e501527ed9b04b..90622bde37beda 100644
--- a/clang/lib/AST/Expr.cpp
+++ b/clang/lib/AST/Expr.cpp
@@ -3831,6 +3831,8 @@ bool Expr::HasSideEffects(const ASTContext &Ctx,
case ArraySectionExprClass:
case OMPArrayShapingExprClass:
case OMPIteratorExprClass:
+ case OMPNumArgsExprClass:
+ case OMPArgumentRangeExprClass:
case MemberExprClass:
case ConditionalOperatorClass:
case BinaryConditionalOperatorClass:
diff --git a/clang/lib/AST/ExprClassification.cpp b/clang/lib/AST/ExprClassification.cpp
index eebae17d7b948b..6f3cd087b2660b 100644
--- a/clang/lib/AST/ExprClassification.cpp
+++ b/clang/lib/AST/ExprClassification.cpp
@@ -220,6 +220,8 @@ static Cl::Kinds ClassifyInternal(ASTContext &Ctx, const Expr *E) {
case Expr::RequiresExprClass:
case Expr::CXXReflectExprClass:
case Expr::CXXExpansionSelectExprClass:
+ case Expr::OMPNumArgsExprClass:
+ case Expr::OMPArgumentRangeExprClass:
return Cl::CL_PRValue;
case Expr::EmbedExprClass:
diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp
index d55749100658f7..034142aac4c706 100644
--- a/clang/lib/AST/ExprConstant.cpp
+++ b/clang/lib/AST/ExprConstant.cpp
@@ -22398,6 +22398,8 @@ static ICEDiag CheckICE(const Expr* E, const ASTContext &Ctx) {
case Expr::ArraySectionExprClass:
case Expr::OMPArrayShapingExprClass:
case Expr::OMPIteratorExprClass:
+ case...
[truncated]
``````````
</details>
https://github.com/llvm/llvm-project/pull/225081
More information about the cfe-commits
mailing list