[clang] 553fa20 - [OpenACC] Implement 'at least one of' restriction for 'update'

via cfe-commits cfe-commits at lists.llvm.org
Thu Jan 9 09:29:06 PST 2025


Author: erichkeane
Date: 2025-01-09T09:28:58-08:00
New Revision: 553fa204ed5ab4c48bc6080451df24310c00e69c

URL: https://github.com/llvm/llvm-project/commit/553fa204ed5ab4c48bc6080451df24310c00e69c
DIFF: https://github.com/llvm/llvm-project/commit/553fa204ed5ab4c48bc6080451df24310c00e69c.diff

LOG: [OpenACC] Implement 'at least one of' restriction for 'update'

This completes the implementation of 'update' by implementing its last
restriction. This restriction requires at least 1 of the 'self', 'host',
  or 'device' clauses.

Added: 
    

Modified: 
    clang/lib/Sema/SemaOpenACC.cpp
    clang/test/AST/ast-print-openacc-update-construct.cpp
    clang/test/ParserOpenACC/parse-clauses.c
    clang/test/ParserOpenACC/parse-constructs.c
    clang/test/SemaOpenACC/update-construct-ast.cpp
    clang/test/SemaOpenACC/update-construct.cpp

Removed: 
    


################################################################################
diff  --git a/clang/lib/Sema/SemaOpenACC.cpp b/clang/lib/Sema/SemaOpenACC.cpp
index a2973f1f99b2cf..9ded913638fb3e 100644
--- a/clang/lib/Sema/SemaOpenACC.cpp
+++ b/clang/lib/Sema/SemaOpenACC.cpp
@@ -3732,8 +3732,17 @@ bool SemaOpenACC::ActOnStartStmtDirective(
                                 OpenACCClauseKind::DeviceType,
                                 OpenACCClauseKind::If});
 
-  // TODO: OpenACC: 'Update' construct needs to have one of 'self', 'host', or
-  // 'device'.  Implement here.
+  // OpenACC3.3 2.14.4: At least one self, host, or device clause must appear on
+  // an update directive.
+  if (K == OpenACCDirectiveKind::Update &&
+      llvm::find_if(Clauses, llvm::IsaPred<OpenACCSelfClause, OpenACCHostClause,
+                                           OpenACCDeviceClause>) ==
+          Clauses.end())
+    return Diag(StartLoc, diag::err_acc_construct_one_clause_of)
+           << K
+           << GetListOfClauses({OpenACCClauseKind::Self,
+                                OpenACCClauseKind::Host,
+                                OpenACCClauseKind::Device});
 
   return diagnoseConstructAppertainment(*this, K, StartLoc, /*IsStmt=*/true);
 }

diff  --git a/clang/test/AST/ast-print-openacc-update-construct.cpp b/clang/test/AST/ast-print-openacc-update-construct.cpp
index 0d09c829929dc7..f999e1037e904b 100644
--- a/clang/test/AST/ast-print-openacc-update-construct.cpp
+++ b/clang/test/AST/ast-print-openacc-update-construct.cpp
@@ -3,38 +3,38 @@ void uses(bool cond) {
   int I;
   int *iPtr;
   int array[5];
-  // CHECK: #pragma acc update
-#pragma acc update
+  // CHECK: #pragma acc update self(I)
+#pragma acc update self(I)
 
-// CHECK: #pragma acc update if_present
-#pragma acc update if_present
-// CHECK: #pragma acc update if(cond)
-#pragma acc update if(cond)
+// CHECK: #pragma acc update self(I) if_present
+#pragma acc update self(I) if_present
+// CHECK: #pragma acc update self(I) if(cond)
+#pragma acc update self(I) if(cond)
 
-// CHECK: #pragma acc update async
-#pragma acc update async
-// CHECK: #pragma acc update async(*iPtr)
-#pragma acc update async(*iPtr)
-// CHECK: #pragma acc update async(I)
-#pragma acc update async(I)
+// CHECK: #pragma acc update self(I) async
+#pragma acc update self(I) async
+// CHECK: #pragma acc update self(I) async(*iPtr)
+#pragma acc update self(I) async(*iPtr)
+// CHECK: #pragma acc update self(I) async(I)
+#pragma acc update self(I) async(I)
 
-// CHECK: #pragma acc update wait(*iPtr, I) async
-#pragma acc update wait(*iPtr, I) async
+// CHECK: #pragma acc update self(I) wait(*iPtr, I) async
+#pragma acc update self(I) wait(*iPtr, I) async
 
-// CHECK: #pragma acc update wait(queues: *iPtr, I) async(*iPtr)
-#pragma acc update wait(queues:*iPtr, I) async(*iPtr)
+// CHECK: #pragma acc update self(I) wait(queues: *iPtr, I) async(*iPtr)
+#pragma acc update self(I) wait(queues:*iPtr, I) async(*iPtr)
 
-// CHECK: #pragma acc update wait(devnum: I : *iPtr, I) async(I)
-#pragma acc update wait(devnum:I:*iPtr, I) async(I)
+// CHECK: #pragma acc update self(I) wait(devnum: I : *iPtr, I) async(I)
+#pragma acc update self(I) wait(devnum:I:*iPtr, I) async(I)
 
-// CHECK: #pragma acc update wait(devnum: I : queues: *iPtr, I) if(I == array[I]) async(I)
-#pragma acc update wait(devnum:I:queues:*iPtr, I) if(I == array[I]) async(I)
+// CHECK: #pragma acc update self(I) wait(devnum: I : queues: *iPtr, I) if(I == array[I]) async(I)
+#pragma acc update self(I) wait(devnum:I:queues:*iPtr, I) if(I == array[I]) async(I)
 
-// CHECK: #pragma acc update device_type(I) dtype(H)
-#pragma acc update device_type(I) dtype(H)
+// CHECK: #pragma acc update self(I) device_type(I) dtype(H)
+#pragma acc update self(I) device_type(I) dtype(H)
 
-// CHECK: #pragma acc update device_type(J) dtype(K)
-#pragma acc update device_type(J) dtype(K)
+// CHECK: #pragma acc update self(I) device_type(J) dtype(K)
+#pragma acc update self(I) device_type(J) dtype(K)
 
 // CHECK: #pragma acc update self(I, iPtr, array, array[1], array[1:2])
 #pragma acc update self(I, iPtr, array, array[1], array[1:2])

diff  --git a/clang/test/ParserOpenACC/parse-clauses.c b/clang/test/ParserOpenACC/parse-clauses.c
index 930cc1e4c0353a..b871624b6e9431 100644
--- a/clang/test/ParserOpenACC/parse-clauses.c
+++ b/clang/test/ParserOpenACC/parse-clauses.c
@@ -344,7 +344,7 @@ void SelfUpdate() {
   struct Members s;
 
   // expected-error at +1{{expected '('}}
-#pragma acc update self
+#pragma acc update host(s) self
   for(int i = 0; i < 5;++i) {}
 
   // expected-error at +3{{use of undeclared identifier 'zero'}}

diff  --git a/clang/test/ParserOpenACC/parse-constructs.c b/clang/test/ParserOpenACC/parse-constructs.c
index 9948e33ac94d1c..886a912713c58b 100644
--- a/clang/test/ParserOpenACC/parse-constructs.c
+++ b/clang/test/ParserOpenACC/parse-constructs.c
@@ -151,6 +151,7 @@ void func() {
   // expected-error at +1{{OpenACC 'set' construct must have at least one 'default_async', 'device_num', 'device_type' or 'if' clause}}
 #pragma acc set clause list
   for(;;){}
+  // expected-error at +2{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
   // expected-error at +1{{invalid OpenACC clause 'clause'}}
 #pragma acc update clause list
   for(;;){}

diff  --git a/clang/test/SemaOpenACC/update-construct-ast.cpp b/clang/test/SemaOpenACC/update-construct-ast.cpp
index 5582bde7a64c2d..4238f93d90a346 100644
--- a/clang/test/SemaOpenACC/update-construct-ast.cpp
+++ b/clang/test/SemaOpenACC/update-construct-ast.cpp
@@ -18,8 +18,10 @@ void NormalFunc() {
   // CHECK-LABEL: NormalFunc
   // CHECK-NEXT: CompoundStmt
 
-#pragma acc update if_present if (some_int() < some_long())
+#pragma acc update self(Global) if_present if (some_int() < some_long())
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: if_present clause
   // CHECK-NEXT: if clause
   // CHECK-NEXT: BinaryOperator{{.*}}'bool' '<'
@@ -31,15 +33,19 @@ void NormalFunc() {
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'some_long' 'long ()'
 
-#pragma acc update wait async device_type(A) dtype(B)
+#pragma acc update self(Global) wait async device_type(A) dtype(B)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: async clause
   // CHECK-NEXT: device_type(A)
   // CHECK-NEXT: dtype(B)
-#pragma acc update wait(some_int(), some_long()) async(some_int())
+#pragma acc update self(Global) wait(some_int(), some_long()) async(some_int())
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: CallExpr{{.*}}'int'
@@ -52,8 +58,10 @@ void NormalFunc() {
   // CHECK-NEXT: CallExpr{{.*}}'int'
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'some_int' 'int ()'
-#pragma acc update wait(queues:some_int(), some_long())
+#pragma acc update self(Global) wait(queues:some_int(), some_long())
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: CallExpr{{.*}}'int'
@@ -62,8 +70,10 @@ void NormalFunc() {
   // CHECK-NEXT: CallExpr{{.*}}'long'
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'some_long' 'long ()'
-#pragma acc update wait(devnum: some_int() :some_int(), some_long())
+#pragma acc update self(Global) wait(devnum: some_int() :some_int(), some_long())
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: CallExpr{{.*}}'int'
   // CHECK-NEXT: ImplicitCastExpr
@@ -83,12 +93,12 @@ void NormalFunc() {
   // CHECK-NEXT: ArraySubscriptExpr{{.*}} 'short' lvalue
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
-  // CHECK-NEXT: IntegerLiteral{{.*}} 1
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 1
 
 #pragma acc update host(Global, GlobalArray, GlobalArray[0], GlobalArray[0:1]) device(Global, GlobalArray, GlobalArray[0], GlobalArray[0:1])
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
@@ -98,24 +108,24 @@ void NormalFunc() {
   // CHECK-NEXT: ArraySubscriptExpr{{.*}} 'short' lvalue
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
-  // CHECK-NEXT: IntegerLiteral{{.*}} 1
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 1
   // CHECK-NEXT: device clause
   // CHECK-NEXT: DeclRefExpr{{.*}}'Global' 'int'
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
   // CHECK-NEXT: ArraySubscriptExpr{{.*}} 'short' lvalue
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}}'GlobalArray' 'short[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}} 0
-  // CHECK-NEXT: IntegerLiteral{{.*}} 1
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}} 'int' 1
 }
 
 template<typename T>
@@ -126,8 +136,10 @@ void TemplFunc(T t) {
   // CHECK-NEXT: ParmVarDecl{{.*}} t 'T'
   // CHECK-NEXT: CompoundStmt
 
-#pragma acc update if_present if (T::value < t)
+#pragma acc update self(t) if_present if (T::value < t)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: if_present clause
   // CHECK-NEXT: if clause
   // CHECK-NEXT: BinaryOperator{{.*}}'<dependent type>' '<'
@@ -135,15 +147,19 @@ void TemplFunc(T t) {
   // CHECK-NEXT: NestedNameSpecifier TypeSpec 'T'
   // CHECK-NEXT: DeclRefExpr{{.*}}'t' 'T'
 
-#pragma acc update wait async device_type(T) dtype(U)
+#pragma acc update self(t) wait async device_type(T) dtype(U)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: async clause
   // CHECK-NEXT: device_type(T)
   // CHECK-NEXT: dtype(U)
-#pragma acc update wait(T::value, t) async(T::value)
+#pragma acc update self(t) wait(T::value, t) async(T::value)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: DependentScopeDeclRefExpr{{.*}}'<dependent type>'
@@ -152,8 +168,10 @@ void TemplFunc(T t) {
   // CHECK-NEXT: async clause
   // CHECK-NEXT: DependentScopeDeclRefExpr{{.*}}'<dependent type>'
   // CHECK-NEXT: NestedNameSpecifier TypeSpec 'T'
-#pragma acc update wait(queues:T::value, t) async(t)
+#pragma acc update self(t) wait(queues:T::value, t) async(t)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: DependentScopeDeclRefExpr{{.*}}'<dependent type>'
@@ -161,8 +179,10 @@ void TemplFunc(T t) {
   // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: async clause
   // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
-#pragma acc update wait(devnum: T::value:t, T::value)
+#pragma acc update self(t) wait(devnum: T::value:t, T::value)
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'T'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: DependentScopeDeclRefExpr{{.*}}'<dependent type>'
   // CHECK-NEXT: NestedNameSpecifier TypeSpec 'T'
@@ -184,11 +204,11 @@ void TemplFunc(T t) {
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
 
 #pragma acc update host(Local, LocalArray, LocalArray[0], LocalArray[0:1]) device(Local, LocalArray, LocalArray[0], LocalArray[0:1])
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
@@ -197,21 +217,21 @@ void TemplFunc(T t) {
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
   // CHECK-NEXT: device clause
   // CHECK-NEXT: DeclRefExpr{{.*}} 'Local' 'decltype(T::value)'
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(T::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
 
   // Instantiation:
   // CHECK-NEXT: FunctionDecl{{.*}} TemplFunc 'void (SomeStruct)' implicit_instantiation
@@ -222,6 +242,8 @@ void TemplFunc(T t) {
   // CHECK-NEXT: CompoundStmt
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'SomeStruct'
   // CHECK-NEXT: if_present clause
   // CHECK-NEXT: if clause
   // CHECK-NEXT: BinaryOperator{{.*}}'bool' '<'
@@ -234,6 +256,8 @@ void TemplFunc(T t) {
   // CHECK-NEXT: DeclRefExpr{{.*}}'t' 'SomeStruct'
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'SomeStruct'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: async clause
@@ -241,6 +265,8 @@ void TemplFunc(T t) {
   // CHECK-NEXT: dtype(U)
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'SomeStruct'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: ImplicitCastExpr{{.*}}'unsigned int'
@@ -256,6 +282,8 @@ void TemplFunc(T t) {
   // CHECK-NEXT: NestedNameSpecifier TypeSpec 'SomeStruct'
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'SomeStruct'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: <<<NULL>>>
   // CHECK-NEXT: ImplicitCastExpr{{.*}}'unsigned int'
@@ -272,6 +300,8 @@ void TemplFunc(T t) {
   // CHECK-NEXT: DeclRefExpr{{.*}}'t' 'SomeStruct'
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
+  // CHECK-NEXT: self clause
+  // CHECK-NEXT: DeclRefExpr{{.*}} 't' 'SomeStruct'
   // CHECK-NEXT: wait clause
   // CHECK-NEXT: ImplicitCastExpr{{.*}}'unsigned int'
   // CHECK-NEXT: DeclRefExpr{{.*}}'value' 'const unsigned int'
@@ -299,12 +329,12 @@ void TemplFunc(T t) {
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
 
   // CHECK-NEXT: OpenACCUpdateConstruct{{.*}}update
   // CHECK-NEXT: host clause
@@ -313,24 +343,24 @@ void TemplFunc(T t) {
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
   // CHECK-NEXT: device clause
   // CHECK-NEXT: DeclRefExpr{{.*}} 'Local' 'decltype(SomeStruct::value)':'const unsigned int'
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
   // CHECK-NEXT: ArraySubscriptExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
   // CHECK-NEXT: ArraySectionExpr
   // CHECK-NEXT: ImplicitCastExpr
   // CHECK-NEXT: DeclRefExpr{{.*}} 'LocalArray' 'decltype(SomeStruct::value)[5]'
-  // CHECK-NEXT: IntegerLiteral{{.*}}0
-  // CHECK-NEXT: IntegerLiteral{{.*}}1
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 0
+  // CHECK-NEXT: IntegerLiteral{{.*}}'int' 1
 }
 
 struct SomeStruct{

diff  --git a/clang/test/SemaOpenACC/update-construct.cpp b/clang/test/SemaOpenACC/update-construct.cpp
index 8b65da69e42b9f..30c079c8befd4e 100644
--- a/clang/test/SemaOpenACC/update-construct.cpp
+++ b/clang/test/SemaOpenACC/update-construct.cpp
@@ -21,36 +21,38 @@ void uses() {
 #pragma acc update self(Var) device_type(I) if_present
   // expected-error at +2{{OpenACC clause 'self' may not follow a 'device_type' clause in a 'update' construct}}
   // expected-note at +1{{previous clause is here}}
-#pragma acc update device_type(I) self(Var)
+#pragma acc update self(Var) device_type(I) self(Var)
   // expected-error at +2{{OpenACC clause 'host' may not follow a 'device_type' clause in a 'update' construct}}
   // expected-note at +1{{previous clause is here}}
-#pragma acc update device_type(I) host(Var)
+#pragma acc update self(Var) device_type(I) host(Var)
   // expected-error at +2{{OpenACC clause 'device' may not follow a 'device_type' clause in a 'update' construct}}
   // expected-note at +1{{previous clause is here}}
-#pragma acc update device_type(I) device(Var)
+#pragma acc update self(Var) device_type(I) device(Var)
   // These 2 are OK.
 #pragma acc update self(Var) device_type(I) async
 #pragma acc update self(Var) device_type(I) wait
   // Unless otherwise specified, we assume 'device_type' can happen after itself.
 #pragma acc update self(Var) device_type(I) device_type(I)
 
-  // TODO: OpenACC: These should diagnose because there isn't at least 1 of
-  // 'self', 'host', or 'device'.
+  // These diagnose because there isn't at least 1 of 'self', 'host', or
+  // 'device'.
+  // expected-error at +1{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
 #pragma acc update async
+  // expected-error at +1{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
 #pragma acc update wait
+  // expected-error at +1{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
 #pragma acc update device_type(I)
+  // expected-error at +1{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
 #pragma acc update if(true)
+  // expected-error at +1{{OpenACC 'update' construct must have at least one 'self', 'host' or 'device' clause}}
 #pragma acc update if_present
 
   // expected-error at +1{{value of type 'struct NotConvertible' is not contextually convertible to 'bool'}}
-#pragma acc update if (NC) device_type(I)
+#pragma acc update self(Var) if (NC) device_type(I)
 
   // expected-error at +2{{OpenACC 'if' clause cannot appear more than once on a 'update' directive}}
   // expected-note at +1{{previous clause is here}}
-#pragma acc update if(true) if (false)
-
-  // TODO: OpenACC: There is restrictions on the contents of a 'varlist', so
-  // those should be checked here too.
+#pragma acc update self(Var) if(true) if (false)
 
   // Cannot be the body of an 'if', 'while', 'do', 'switch', or
   // 'label'.
@@ -80,34 +82,34 @@ void uses() {
 #pragma acc update device(Var)
 
   // Checking for 'async', which requires an 'int' expression.
-#pragma acc update async
+#pragma acc update self(Var) async
 
-#pragma acc update async(getI())
+#pragma acc update self(Var) async(getI())
   // expected-error at +2{{expected ')'}}
   // expected-note at +1{{to match this '('}}
-#pragma acc update async(getI(), getI())
+#pragma acc update self(Var) async(getI(), getI())
   // expected-error at +2{{OpenACC 'async' clause cannot appear more than once on a 'update' directive}}
   // expected-note at +1{{previous clause is here}}
-#pragma acc update async(getI()) async(getI())
+#pragma acc update self(Var) async(getI()) async(getI())
   // expected-error at +1{{OpenACC clause 'async' requires expression of integer type ('struct NotConvertible' invalid)}}
-#pragma acc update async(NC)
+#pragma acc update self(Var) async(NC)
 
   // Checking for 'wait', which has a complicated set arguments.
-#pragma acc update wait
-#pragma acc update wait()
-#pragma acc update wait(getI(), getI())
-#pragma acc update wait(devnum: getI():  getI())
-#pragma acc update wait(devnum: getI(): queues: getI(), getI())
+#pragma acc update self(Var) wait
+#pragma acc update self(Var) wait()
+#pragma acc update self(Var) wait(getI(), getI())
+#pragma acc update self(Var) wait(devnum: getI():  getI())
+#pragma acc update self(Var) wait(devnum: getI(): queues: getI(), getI())
   // expected-error at +1{{OpenACC clause 'wait' requires expression of integer type ('struct NotConvertible' invalid)}}
-#pragma acc update wait(devnum:NC : 5)
+#pragma acc update self(Var) wait(devnum:NC : 5)
   // expected-error at +1{{OpenACC clause 'wait' requires expression of integer type ('struct NotConvertible' invalid)}}
-#pragma acc update wait(devnum:5 : NC)
+#pragma acc update self(Var) wait(devnum:5 : NC)
 
     int arr[5];
   // expected-error at +3{{OpenACC clause 'wait' requires expression of integer type ('int[5]' invalid)}}
   // expected-error at +2{{OpenACC clause 'wait' requires expression of integer type ('int[5]' invalid)}}
   // expected-error at +1{{OpenACC clause 'wait' requires expression of integer type ('struct NotConvertible' invalid)}}
-#pragma acc update wait(devnum:arr : queues: arr, NC, 5)
+#pragma acc update self(Var) wait(devnum:arr : queues: arr, NC, 5)
 }
 
 struct SomeS {


        


More information about the cfe-commits mailing list