https://gcc.gnu.org/g:d0efbc9d9e155c94768701749420a0dd690c151b
commit d0efbc9d9e155c94768701749420a0dd690c151b Author: Waffl3x <[email protected]> Date: Tue May 5 09:02:04 2026 -0600 OpenMP/C++: Sorry for allocate directive in omp::decl attribute At least one of the diagnostics in cp_parser_omp_allocate expects each decl to have been pushed into the current binding level. Due to when attributes are parsed this assumption does not hold for an allocate directive specified in an omp::decl attribute. The broken diagnostic checks that the vars listed in an allocate directive are in the same scope as the directive. Obviously we can assume that is the case when using omp::decl, but it is not obvious how to detect that we in an omp::decl in a robust way so this case is simply not supported for now. This patch also adds a check for TREE_PUBLIC in cp_maybe_parse_omp_decl. During investigation of this issue it was noticed that TREE_PUBLIC denotes an omp::decl attribute as opposed to an omp::directive attribute, thus it is also a precondition in that function. gcc/cp/ChangeLog: * parser.cc (cp_maybe_parse_omp_decl): Sorry for allocate directive. libgomp/ChangeLog: * testsuite/libgomp.c-c++-common/allocate-7.c: Disable for C++. gcc/testsuite/ChangeLog: * g++.dg/gomp/omp-constexpr.C: Add sorry for allocate directive. * g++.dg/gomp/allocate-24.C: New test. Signed-off-by: Waffl3x <[email protected]> Diff: --- gcc/cp/parser.cc | 10 ++++++++- gcc/testsuite/g++.dg/gomp/allocate-24.C | 26 ++++++++++++++++++++++ gcc/testsuite/g++.dg/gomp/omp-constexpr.C | 3 ++- .../testsuite/libgomp.c-c++-common/allocate-7.c | 5 ++++- 4 files changed, 41 insertions(+), 3 deletions(-) diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc index 826ff368c92a..31944b3bf941 100644 --- a/gcc/cp/parser.cc +++ b/gcc/cp/parser.cc @@ -54763,7 +54763,8 @@ cp_parser_late_parsing_omp_declare_simd (cp_parser *parser, tree attrs, bool cp_maybe_parse_omp_decl (tree decl, tree d) { - gcc_assert (TREE_CODE (d) == DEFERRED_PARSE); + gcc_assert (TREE_CODE (d) == DEFERRED_PARSE + && TREE_PUBLIC (d)); cp_token *first = DEFPARSE_TOKENS (d)->first; cp_token *last = DEFPARSE_TOKENS (d)->last; const char *directive[3] = {}; @@ -54801,6 +54802,13 @@ cp_maybe_parse_omp_decl (tree decl, tree d) if (!flag_openmp && !dir->simd) return true; + if (dir->id == PRAGMA_OMP_ALLOCATE) + { + sorry_at (first->location, + "allocate directive not supported in %<omp::decl%>"); + return true; + } + cp_parser *parser = the_parser; cp_lexer *lexer = cp_lexer_alloc (); lexer->debugging_p = parser->lexer->debugging_p; diff --git a/gcc/testsuite/g++.dg/gomp/allocate-24.C b/gcc/testsuite/g++.dg/gomp/allocate-24.C new file mode 100644 index 000000000000..114231c8a54d --- /dev/null +++ b/gcc/testsuite/g++.dg/gomp/allocate-24.C @@ -0,0 +1,26 @@ +/* { dg-do compile { target c++11 } } */ + +#include "allocate-allocator-handle.h" + +/* TODO: Add scan-tree-dump checks once support for omp::decl is added. */ + +int AAA [[omp::decl(allocate,allocator(omp_low_lat_mem_alloc),align(4096))]]; +/* { dg-message "allocate directive not supported in 'omp::decl'" "" { target *-*-* } .-1 } */ + +static_assert (alignof(AAA) == alignof(int), "wrong alignment"); + +void f () +{ + /* This applies to A1 and B1. + (C++23 N4950 ยง9.1.3, sentence 5) + The attribute-specifier-seq appertains to each of the entities declared by + the declarators of the init-declarator-list. */ + [[omp::decl(allocate, align(4096))]] int A1[5], B1; + /* { dg-message "allocate directive not supported in 'omp::decl'" "" { target *-*-* } .-1 } */ + + static_assert (alignof(A1) == alignof(int[5]), "wrong alignment"); + static_assert (alignof(B1) == alignof(int), "wrong alignment"); + + static int BBB [[omp::decl(allocate,allocator(omp_low_lat_mem_alloc),align(4096))]]; + /* { dg-message "allocate directive not supported in 'omp::decl'" "" { target *-*-* } .-1 } */ +} diff --git a/gcc/testsuite/g++.dg/gomp/omp-constexpr.C b/gcc/testsuite/g++.dg/gomp/omp-constexpr.C index 0d984d8609b5..85b1157201c0 100644 --- a/gcc/testsuite/g++.dg/gomp/omp-constexpr.C +++ b/gcc/testsuite/g++.dg/gomp/omp-constexpr.C @@ -31,7 +31,8 @@ h () constexpr int i () { - int a [[omp::decl(allocate, align(128))]] = 42; /* { dg-error "OpenMP directives may not appear in 'constexpr' functions" } */ + int a [[omp::decl(allocate, align(128))]] = 42; /* { dg-error "OpenMP directives may not appear in 'constexpr' functions" "" { xfail *-*-* } } */ + /* { dg-message "allocate directive not supported in 'omp::decl'" "" { target *-*-* } .-1 } */ return a; } // { dg-error "not a return-statement" "" { target c++11_down } } diff --git a/libgomp/testsuite/libgomp.c-c++-common/allocate-7.c b/libgomp/testsuite/libgomp.c-c++-common/allocate-7.c index 9968eb190050..8d5429b0eb3b 100644 --- a/libgomp/testsuite/libgomp.c-c++-common/allocate-7.c +++ b/libgomp/testsuite/libgomp.c-c++-common/allocate-7.c @@ -1,9 +1,12 @@ -/* { dg-do run } */ +/* { dg-do run { target c } } */ + +/* In C++, omp allocate in an omp::decl attribute is not currently supported. */ #include <omp.h> int AAA [[omp::decl(allocate,allocator(omp_low_lat_mem_alloc),align(4096))]]; + #ifndef __cplusplus _Static_assert (_Alignof(AAA) == _Alignof(int), "wrong alignment"); #elif __cplusplus >= 201103L
