https://gcc.gnu.org/g:3002e1f69abbb45a570b66383f5d2ad562190807
commit 3002e1f69abbb45a570b66383f5d2ad562190807 Author: Tobias Burnus <tbur...@baylibre.com> Date: Mon Jan 27 12:35:53 2025 +0100 OpenMP: Add 'interop' clause to 'dispatch' for C/C++ Will fail with an error if/as no suitable 'append_args' has been specified, given that 'append_args' is not yet implemented. gcc/c-family/ChangeLog: * c-pragma.h (enum pragma_omp_clause): Add PRAGMA_OMP_CLAUSE_INTEROP. gcc/c/ChangeLog: * c-parser.cc (c_parser_omp_clause_interop): New. (c_parser_omp_clause_name, c_parser_omp_all_clauses, c_parser_omp_dispatch_body): Handle 'interop' clause. * c-typeck.cc (c_finish_omp_clauses): Likewise. gcc/cp/ChangeLog: * parser.cc (cp_parser_omp_clause_name, cp_parser_omp_all_clauses, cp_parser_omp_dispatch_body): Handle 'interop' clause. * pt.cc (tsubst_omp_clauses): Likewise. * semantics.cc (finish_omp_clauses): Likewise. gcc/ChangeLog: * gimplify.cc (gimplify_call_expr): Add initial support for dispatch's 'interop' clause. (gimplify_scan_omp_clauses): Handle interop clause. * tree-pretty-print.cc (dump_omp_clause): Likewise. * tree-core.h (enum omp_clause_code): Add OMP_CLAUSE_INTEROP. * tree.cc (omp_clause_num_ops, omp_clause_code_name): Add interop. gcc/testsuite/ChangeLog: * c-c++-common/gomp/dispatch-11.c: New test. * c-c++-common/gomp/dispatch-12.c: New test. (cherry picked from commit f34422e06c38eb1f69c301ad5d8e2114c46a2796) Diff: --- gcc/ChangeLog.omp | 12 ++++ gcc/c-family/ChangeLog.omp | 7 +++ gcc/c-family/c-pragma.h | 1 + gcc/c/ChangeLog.omp | 10 ++++ gcc/c/c-parser.cc | 17 ++++++ gcc/c/c-typeck.cc | 23 ++++++-- gcc/cp/ChangeLog.omp | 10 ++++ gcc/cp/parser.cc | 10 ++++ gcc/cp/pt.cc | 1 + gcc/cp/semantics.cc | 29 ++++++--- gcc/gimplify.cc | 15 +++++ gcc/testsuite/ChangeLog.omp | 8 +++ gcc/testsuite/c-c++-common/gomp/dispatch-11.c | 84 +++++++++++++++++++++++++++ gcc/testsuite/c-c++-common/gomp/dispatch-12.c | 53 +++++++++++++++++ gcc/tree-core.h | 3 + gcc/tree-pretty-print.cc | 6 +- gcc/tree.cc | 2 + 17 files changed, 275 insertions(+), 16 deletions(-) diff --git a/gcc/ChangeLog.omp b/gcc/ChangeLog.omp index cf11ac6d3242..e83fe6afebb4 100644 --- a/gcc/ChangeLog.omp +++ b/gcc/ChangeLog.omp @@ -1,3 +1,15 @@ +2025-01-27 Tobias Burnus <tbur...@baylibre.com> + + Backported from master: + 2024-11-22 Tobias Burnus <tbur...@baylibre.com> + + * gimplify.cc (gimplify_call_expr): Add initial support for + dispatch's 'interop' clause. + (gimplify_scan_omp_clauses): Handle interop clause. + * tree-pretty-print.cc (dump_omp_clause): Likewise. + * tree-core.h (enum omp_clause_code): Add OMP_CLAUSE_INTEROP. + * tree.cc (omp_clause_num_ops, omp_clause_code_name): Add interop. + 2025-01-27 Tobias Burnus <tbur...@baylibre.com> Backported from master: diff --git a/gcc/c-family/ChangeLog.omp b/gcc/c-family/ChangeLog.omp index 852acb8a2039..cf966f7be0f4 100644 --- a/gcc/c-family/ChangeLog.omp +++ b/gcc/c-family/ChangeLog.omp @@ -1,3 +1,10 @@ +2025-01-27 Tobias Burnus <tbur...@baylibre.com> + + Backported from master: + 2024-11-22 Tobias Burnus <tbur...@baylibre.com> + + * c-pragma.h (enum pragma_omp_clause): Add PRAGMA_OMP_CLAUSE_INTEROP. + 2025-01-27 Tobias Burnus <tbur...@baylibre.com> Backported from master: diff --git a/gcc/c-family/c-pragma.h b/gcc/c-family/c-pragma.h index bea0d9121cb2..ef452fc102ca 100644 --- a/gcc/c-family/c-pragma.h +++ b/gcc/c-family/c-pragma.h @@ -135,6 +135,7 @@ enum pragma_omp_clause { PRAGMA_OMP_CLAUSE_INDIRECT, PRAGMA_OMP_CLAUSE_INIT, PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR, + PRAGMA_OMP_CLAUSE_INTEROP, PRAGMA_OMP_CLAUSE_LASTPRIVATE, PRAGMA_OMP_CLAUSE_LINEAR, PRAGMA_OMP_CLAUSE_LINK, diff --git a/gcc/c/ChangeLog.omp b/gcc/c/ChangeLog.omp index 4323cd1b239d..a19c27f82634 100644 --- a/gcc/c/ChangeLog.omp +++ b/gcc/c/ChangeLog.omp @@ -1,3 +1,13 @@ +2025-01-27 Tobias Burnus <tbur...@baylibre.com> + + Backported from master: + 2024-11-22 Tobias Burnus <tbur...@baylibre.com> + + * c-parser.cc (c_parser_omp_clause_interop): New. + (c_parser_omp_clause_name, c_parser_omp_all_clauses, + c_parser_omp_dispatch_body): Handle 'interop' clause. + * c-typeck.cc (c_finish_omp_clauses): Likewise. + 2025-01-27 Tobias Burnus <tbur...@baylibre.com> Backported from master: diff --git a/gcc/c/c-parser.cc b/gcc/c/c-parser.cc index df369a7090f3..4c1cead30248 100644 --- a/gcc/c/c-parser.cc +++ b/gcc/c/c-parser.cc @@ -15158,6 +15158,8 @@ c_parser_omp_clause_name (c_parser *parser) result = PRAGMA_OMP_CLAUSE_INIT; else if (!strcmp ("is_device_ptr", p)) result = PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR; + else if (!strcmp ("interop", p)) + result = PRAGMA_OMP_CLAUSE_INTEROP; break; case 'l': if (!strcmp ("lastprivate", p)) @@ -20526,6 +20528,16 @@ c_parser_omp_clause_use (c_parser *parser, tree list) return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_USE, list); } +/* OpenMP 6.0: + interop ( variable-list ) */ + +static tree +c_parser_omp_clause_interop (c_parser *parser, tree list) +{ + check_no_duplicate_clause (list, OMP_CLAUSE_INTEROP, "interop"); + return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_INTEROP, list); +} + /* Parse all OpenACC clauses. The set clauses allowed by the directive is a bitmask in MASK. Return the list of clauses found. */ @@ -21037,6 +21049,10 @@ c_parser_omp_all_clauses (c_parser *parser, omp_clause_mask mask, clauses = c_parser_omp_clause_use (parser, clauses); c_name = "use"; break; + case PRAGMA_OMP_CLAUSE_INTEROP: + clauses = c_parser_omp_clause_interop (parser, clauses); + c_name = "interop"; + break; case PRAGMA_OMP_CLAUSE_MAP: clauses = c_parser_omp_clause_map (parser, clauses, GOMP_MAP_TOFROM); c_name = "map"; @@ -25033,6 +25049,7 @@ c_parser_omp_dispatch_body (c_parser *parser) | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOVARIANTS) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOCONTEXT) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_INTEROP) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT)) diff --git a/gcc/c/c-typeck.cc b/gcc/c/c-typeck.cc index 018ba344d892..9e444b4f009f 100644 --- a/gcc/c/c-typeck.cc +++ b/gcc/c/c-typeck.cc @@ -16517,16 +16517,27 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) error_at (OMP_CLAUSE_LOCATION (c), "%qD appears more than once in action clauses", t); remove = true; + break; } - else if (/* ort == C_ORT_OMP_INTEROP [uncomment for depobj init] */ + bitmap_set_bit (&generic_head, DECL_UID (t)); + /* FALLTHRU */ + case OMP_CLAUSE_INTEROP: + if (/* ort == C_ORT_OMP_INTEROP [uncomment for depobj init] */ !c_omp_interop_t_p (TREE_TYPE (OMP_CLAUSE_DECL (c)))) - error_at (OMP_CLAUSE_LOCATION (c), - "%qD must be of %<omp_interop_t%>", OMP_CLAUSE_DECL (c)); - else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_USE + { + error_at (OMP_CLAUSE_LOCATION (c), + "%qD must be of %<omp_interop_t%>", + OMP_CLAUSE_DECL (c)); + remove = true; + } + else if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_INIT + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DESTROY) && TREE_READONLY (OMP_CLAUSE_DECL (c))) - error_at (OMP_CLAUSE_LOCATION (c), + { + error_at (OMP_CLAUSE_LOCATION (c), "%qD shall not be const", OMP_CLAUSE_DECL (c)); - bitmap_set_bit (&generic_head, DECL_UID (t)); + remove = true; + } pc = &OMP_CLAUSE_CHAIN (c); break; default: diff --git a/gcc/cp/ChangeLog.omp b/gcc/cp/ChangeLog.omp index 41d2eb6f157a..feb5fbb0b09d 100644 --- a/gcc/cp/ChangeLog.omp +++ b/gcc/cp/ChangeLog.omp @@ -1,3 +1,13 @@ +2025-01-27 Tobias Burnus <tbur...@baylibre.com> + + Backported from master: + 2024-11-22 Tobias Burnus <tbur...@baylibre.com> + + * parser.cc (cp_parser_omp_clause_name, cp_parser_omp_all_clauses, + cp_parser_omp_dispatch_body): Handle 'interop' clause. + * pt.cc (tsubst_omp_clauses): Likewise. + * semantics.cc (finish_omp_clauses): Likewise. + 2025-01-27 Tobias Burnus <tbur...@baylibre.com> Backported from master: diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc index e23aaf1c5a12..7d65fc2fa674 100644 --- a/gcc/cp/parser.cc +++ b/gcc/cp/parser.cc @@ -38127,6 +38127,8 @@ cp_parser_omp_clause_name (cp_parser *parser) result = PRAGMA_OMP_CLAUSE_INDIRECT; else if (!strcmp ("init", p)) result = PRAGMA_OMP_CLAUSE_INIT; + else if (!strcmp ("interop", p)) + result = PRAGMA_OMP_CLAUSE_INTEROP; else if (!strcmp ("is_device_ptr", p)) result = PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR; break; @@ -43724,6 +43726,13 @@ cp_parser_omp_all_clauses (cp_parser *parser, omp_clause_mask mask, clauses = cp_parser_omp_var_list (parser, OMP_CLAUSE_USE, clauses); c_name = "use"; break; + case PRAGMA_OMP_CLAUSE_INTEROP: + check_no_duplicate_clause (clauses, OMP_CLAUSE_INTEROP, "interop", + token->location); + clauses = cp_parser_omp_var_list (parser, OMP_CLAUSE_INTEROP, + clauses); + c_name = "interop"; + break; case PRAGMA_OMP_CLAUSE_DETACH: clauses = cp_parser_omp_clause_detach (parser, clauses); c_name = "detach"; @@ -50182,6 +50191,7 @@ cp_parser_omp_dispatch_body (cp_parser *parser) | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOVARIANTS) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOCONTEXT) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_INTEROP) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT)) diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc index 5c9aff0f1c1d..2dcdebcc0219 100644 --- a/gcc/cp/pt.cc +++ b/gcc/cp/pt.cc @@ -17863,6 +17863,7 @@ tsubst_omp_clauses (tree clauses, enum c_omp_region_type ort, /* FALLTHRU */ case OMP_CLAUSE_DESTROY: case OMP_CLAUSE_USE: + case OMP_CLAUSE_INTEROP: OMP_CLAUSE_OPERAND (nc, 0) = tsubst_stmt (OMP_CLAUSE_OPERAND (oc, 0), args, complain, in_decl); break; diff --git a/gcc/cp/semantics.cc b/gcc/cp/semantics.cc index 600f90ba4c4b..f0a6d464538f 100644 --- a/gcc/cp/semantics.cc +++ b/gcc/cp/semantics.cc @@ -9730,20 +9730,31 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort) error_at (OMP_CLAUSE_LOCATION (c), "%qD appears more than once in action clauses", t); remove = true; + break; } + bitmap_set_bit (&generic_head, DECL_UID (t)); + /* FALLTHRU */ + case OMP_CLAUSE_INTEROP: if (!processing_template_decl) { - if (/* ort == C_ORT_OMP_INTEROP [uncomment for depobj init] */ - !c_omp_interop_t_p (TREE_TYPE (OMP_CLAUSE_DECL (c)))) - error_at (OMP_CLAUSE_LOCATION (c), - "%qD must be of %<omp_interop_t%>", - OMP_CLAUSE_DECL (c)); - else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_USE + if (/* (ort == C_ORT_OMP_INTEROP [uncomment for depobj init] + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_INTEROP) && */ + !c_omp_interop_t_p (TREE_TYPE (OMP_CLAUSE_DECL (c)))) + { + error_at (OMP_CLAUSE_LOCATION (c), + "%qD must be of %<omp_interop_t%>", + OMP_CLAUSE_DECL (c)); + remove = true; + } + else if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_INIT + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DESTROY) && TREE_READONLY (OMP_CLAUSE_DECL (c))) - error_at (OMP_CLAUSE_LOCATION (c), - "%qD shall not be const", OMP_CLAUSE_DECL (c)); + { + error_at (OMP_CLAUSE_LOCATION (c), + "%qD shall not be const", OMP_CLAUSE_DECL (c)); + remove = true; + } } - bitmap_set_bit (&generic_head, DECL_UID (t)); pc = &OMP_CLAUSE_CHAIN (c); break; default: diff --git a/gcc/gimplify.cc b/gcc/gimplify.cc index 99b227e41f26..cd9bb8d701e1 100644 --- a/gcc/gimplify.cc +++ b/gcc/gimplify.cc @@ -4341,6 +4341,20 @@ gimplify_call_expr (tree *expr_p, gimple_seq *pre_p, fallback_t fallback) vars there. */ bool returns_twice = call_expr_flags (*expr_p) & ECF_RETURNS_TWICE; + tree dispatch_interop = NULL_TREE; + if (flag_openmp + && gimplify_omp_ctxp != NULL + && gimplify_omp_ctxp->code == OMP_DISPATCH + && gimplify_omp_ctxp->clauses + && (dispatch_interop = omp_find_clause (gimplify_omp_ctxp->clauses, + OMP_CLAUSE_INTEROP)) != NULL_TREE) + /* FIXME: When implementing 'append_args, use the 'device_num' of + the argument. */ + error_at (OMP_CLAUSE_LOCATION (dispatch_interop), + "number of list items in %<interop%> clause exceeds number of " + "%<append_args%> items for %<declare variant%> candidate %qD", + fndecl); + /* Gimplify the function arguments. */ if (nargs > 0) { @@ -14133,6 +14147,7 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p, case OMP_CLAUSE_BIND: case OMP_CLAUSE_IF_PRESENT: case OMP_CLAUSE_FINALIZE: + case OMP_CLAUSE_INTEROP: break; case OMP_CLAUSE__OMPACC_: diff --git a/gcc/testsuite/ChangeLog.omp b/gcc/testsuite/ChangeLog.omp index f5b97f749c7d..bd3d806ad08a 100644 --- a/gcc/testsuite/ChangeLog.omp +++ b/gcc/testsuite/ChangeLog.omp @@ -1,3 +1,11 @@ +2025-01-27 Tobias Burnus <tbur...@baylibre.com> + + Backported from master: + 2024-11-22 Tobias Burnus <tbur...@baylibre.com> + + * c-c++-common/gomp/dispatch-11.c: New test. + * c-c++-common/gomp/dispatch-12.c: New test. + 2025-01-27 Tobias Burnus <tbur...@baylibre.com> Backported from master: diff --git a/gcc/testsuite/c-c++-common/gomp/dispatch-11.c b/gcc/testsuite/c-c++-common/gomp/dispatch-11.c new file mode 100644 index 000000000000..7f1d8062f25c --- /dev/null +++ b/gcc/testsuite/c-c++-common/gomp/dispatch-11.c @@ -0,0 +1,84 @@ +/* { dg-additional-options "-fdump-tree-original" } */ + +/* The following definitions are in omp_lib, which cannot be included + in gcc/testsuite/ */ + +#if __cplusplus >= 201103L +# define __GOMP_UINTPTR_T_ENUM : __UINTPTR_TYPE__ +#else +# define __GOMP_UINTPTR_T_ENUM +#endif + +typedef enum omp_interop_t __GOMP_UINTPTR_T_ENUM +{ + omp_interop_none = 0, + __omp_interop_t_max__ = __UINTPTR_MAX__ +} omp_interop_t; + + +float repl1(); +#pragma omp declare variant(repl1) match(construct={dispatch}) +float base1(); + +void repl2(int *, int *); +#pragma omp declare variant(repl2) match(construct={dispatch}) adjust_args(need_device_ptr : y) +void base2(int *x, int *y); + + +float +dupl (int *a, int *b) +{ + omp_interop_t obj1, obj2; + float x; + + #pragma omp dispatch interop ( obj1 ) interop(obj2) /* { dg-error "too many 'interop' clauses" } */ + x = base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'float repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( obj1) nocontext(1) interop (obj2 ) /* { dg-error "too many 'interop' clauses" } */ + base2 (a, b); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'base2'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void base2\\(int\\*, int\\*\\)'" "" { target c++ } .-3 } */ + return x; +} + + +float +test (int *a, int *b) +{ + omp_interop_t obj1, obj2; + float x, y; + + #pragma omp dispatch interop ( obj1 ) + x = base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'float repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( obj1, obj1 ) /* Twice the same - should be fine. */ + x = base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'float repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch novariants(1) interop(obj2, obj1) + y = base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'base1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'float base1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop(obj2, obj1) + base2 (a, b); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl2'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl2\\(int\\*, int\\*\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop(obj2) nocontext(1) + base2 (a, b); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'base2'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void base2\\(int\\*, int\\*\\)'" "" { target c++ } .-3 } */ + return x + y; +} + +/* { dg-final { scan-tree-dump-times "#pragma omp dispatch interop\\(obj1\\)\[\\n\\r\]" 1 "original" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp dispatch interop\\(obj1\\) interop\\(obj1\\)\[\\n\\r\]" 1 "original" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp dispatch interop\\(obj1\\) interop\\(obj2\\) novariants\\(1\\)\[\\n\\r\]" 1 "original" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp dispatch interop\\(obj1\\) interop\\(obj2\\)\[\\n\\r\]" 1 "original" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp dispatch nocontext\\(1\\) interop\\(obj2\\)\[\\n\\r\]" 1 "original" } } */ diff --git a/gcc/testsuite/c-c++-common/gomp/dispatch-12.c b/gcc/testsuite/c-c++-common/gomp/dispatch-12.c new file mode 100644 index 000000000000..ea190c74e84f --- /dev/null +++ b/gcc/testsuite/c-c++-common/gomp/dispatch-12.c @@ -0,0 +1,53 @@ +/* The following definitions are in omp_lib, which cannot be included + in gcc/testsuite/ */ + +#if __cplusplus >= 201103L +# define __GOMP_UINTPTR_T_ENUM : __UINTPTR_TYPE__ +#else +# define __GOMP_UINTPTR_T_ENUM +#endif + +typedef enum omp_interop_t __GOMP_UINTPTR_T_ENUM +{ + omp_interop_none = 0, + __omp_interop_t_max__ = __UINTPTR_MAX__ +} omp_interop_t; + + +void repl1(); +#pragma omp declare variant(repl1) match(construct={dispatch}) +void base1(); + +void +test () +{ + const omp_interop_t obj1 = omp_interop_none; + omp_interop_t obj2[2]; + const omp_interop_t *obj3; + short x; + + #pragma omp dispatch interop ( obj1, obj2, obj1 ) /* { dg-error "'obj2' must be of 'omp_interop_t'" } */ + base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( obj3 ) /* { dg-error "'obj3' must be of 'omp_interop_t'" } */ + base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( obj1 ) + base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( obj2 ) /* { dg-error "'obj2' must be of 'omp_interop_t'" } */ + base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl1\\(\\)'" "" { target c++ } .-3 } */ + + #pragma omp dispatch interop ( x ) /* { dg-error "'x' must be of 'omp_interop_t'" } */ + base1 (); + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'repl1'" "" { target c } .-2 } */ + /* { dg-error "number of list items in 'interop' clause exceeds number of 'append_args' items for 'declare variant' candidate 'void repl1\\(\\)'" "" { target c++ } .-3 } */ +} diff --git a/gcc/tree-core.h b/gcc/tree-core.h index e94f0d2896bd..a9e26ada1077 100644 --- a/gcc/tree-core.h +++ b/gcc/tree-core.h @@ -393,6 +393,9 @@ enum omp_clause_code { /* OpenMP clause: use (variable-list ). */ OMP_CLAUSE_USE, + /* OpenMP clause: interop (variable-list). */ + OMP_CLAUSE_INTEROP, + /* OpenACC clause: gang [(gang-argument-list)]. Where gang-argument-list: [gang-argument-list, ] gang-argument diff --git a/gcc/tree-pretty-print.cc b/gcc/tree-pretty-print.cc index 3bb684609ba7..4535b924edae 100644 --- a/gcc/tree-pretty-print.cc +++ b/gcc/tree-pretty-print.cc @@ -1680,7 +1680,11 @@ dump_omp_clause (pretty_printer *pp, tree clause, int spc, dump_flags_t flags) spc, flags, false); pp_right_paren (pp); break; - + case OMP_CLAUSE_INTEROP: + pp_string (pp, "interop("); + dump_generic_node (pp, OMP_CLAUSE_DECL (clause), spc, flags, false); + pp_right_paren (pp); + break; case OMP_CLAUSE_IF_PRESENT: pp_string (pp, "if_present"); break; diff --git a/gcc/tree.cc b/gcc/tree.cc index fae1e920e9c2..445ed7520550 100644 --- a/gcc/tree.cc +++ b/gcc/tree.cc @@ -274,6 +274,7 @@ unsigned const char omp_clause_num_ops[] = 1, /* OMP_CLAUSE_DESTROY */ 2, /* OMP_CLAUSE_INIT */ 1, /* OMP_CLAUSE_USE */ + 1, /* OMP_CLAUSE_INTEROP */ 2, /* OMP_CLAUSE_GANG */ 1, /* OMP_CLAUSE_ASYNC */ 1, /* OMP_CLAUSE_WAIT */ @@ -378,6 +379,7 @@ const char * const omp_clause_code_name[] = "destroy", "init", "use", + "interop", "gang", "async", "wait",