aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2020-10-30 09:16:45 +0100
committerJakub Jelinek <jakub@redhat.com>2020-10-30 09:16:45 +0100
commit5a6b1d8ef4218a1a2ed6d43c6ee058db9c417bc8 (patch)
treecb6feb912772a61d80a954d525c48a08da8aa7c4 /gcc
parent973574465ca250ed9af5c229a8a3a6b05fde9ca0 (diff)
downloadgcc-5a6b1d8ef4218a1a2ed6d43c6ee058db9c417bc8.zip
gcc-5a6b1d8ef4218a1a2ed6d43c6ee058db9c417bc8.tar.gz
gcc-5a6b1d8ef4218a1a2ed6d43c6ee058db9c417bc8.tar.bz2
openmp: Handle non-static data members in allocate clause and other C++ allocate fixes
This allows specification of non-static data members in allocate clause like it can be specified in other privatization clauses and adds a new testcase that covers also handling of that clause in templates. 2020-10-30 Jakub Jelinek <jakub@redhat.com> * semantics.c (finish_omp_clauses) <case OMP_CLAUSE_ALLOCATE>: Handle non-static members in methods. * pt.c (tsubst_omp_clauses): Handle OMP_CLAUSE_ALLOCATE. * c-c++-common/gomp/allocate-1.c (qux): Add another test. * g++.dg/gomp/allocate-1.C: New test.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/cp/pt.c1
-rw-r--r--gcc/cp/semantics.c33
-rw-r--r--gcc/testsuite/c-c++-common/gomp/allocate-1.c8
-rw-r--r--gcc/testsuite/g++.dg/gomp/allocate-1.C88
4 files changed, 117 insertions, 13 deletions
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index b569644..aa162d2 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -17390,6 +17390,7 @@ tsubst_omp_clauses (tree clauses, enum c_omp_region_type ort,
case OMP_CLAUSE_IS_DEVICE_PTR:
case OMP_CLAUSE_INCLUSIVE:
case OMP_CLAUSE_EXCLUSIVE:
+ case OMP_CLAUSE_ALLOCATE:
/* tsubst_expr on SCOPE_REF results in returning
finish_non_static_data_member result. Undo that here. */
if (TREE_CODE (OMP_CLAUSE_DECL (oc)) == SCOPE_REF
diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c
index d8d3baf92..352ebe0 100644
--- a/gcc/cp/semantics.c
+++ b/gcc/cp/semantics.c
@@ -7200,7 +7200,11 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort)
break;
case OMP_CLAUSE_ALLOCATE:
- t = OMP_CLAUSE_DECL (c);
+ t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
+ if (t)
+ omp_note_field_privatization (t, OMP_CLAUSE_DECL (c));
+ else
+ t = OMP_CLAUSE_DECL (c);
if (t == current_class_ptr)
{
error_at (OMP_CLAUSE_LOCATION (c),
@@ -7208,7 +7212,9 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort)
remove = true;
break;
}
- if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL)
+ if (!VAR_P (t)
+ && TREE_CODE (t) != PARM_DECL
+ && TREE_CODE (t) != FIELD_DECL)
{
if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
break;
@@ -7232,17 +7238,18 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort)
bitmap_set_bit (&aligned_head, DECL_UID (t));
allocate_seen = true;
}
- t = OMP_CLAUSE_ALLOCATE_ALLOCATOR (c);
- if (error_operand_p (t))
+ tree allocator;
+ allocator = OMP_CLAUSE_ALLOCATE_ALLOCATOR (c);
+ if (error_operand_p (allocator))
{
remove = true;
break;
}
- if (t == NULL_TREE)
- break;
+ if (allocator == NULL_TREE)
+ goto handle_field_decl;
tree allocatort;
- allocatort = TYPE_MAIN_VARIANT (TREE_TYPE (t));
- if (!type_dependent_expression_p (t)
+ allocatort = TYPE_MAIN_VARIANT (TREE_TYPE (allocator));
+ if (!type_dependent_expression_p (allocator)
&& (TREE_CODE (allocatort) != ENUMERAL_TYPE
|| TYPE_NAME (allocatort) == NULL_TREE
|| TREE_CODE (TYPE_NAME (allocatort)) != TYPE_DECL
@@ -7254,17 +7261,17 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort)
error_at (OMP_CLAUSE_LOCATION (c),
"%<allocate%> clause allocator expression has "
"type %qT rather than %<omp_allocator_handle_t%>",
- TREE_TYPE (t));
+ TREE_TYPE (allocator));
remove = true;
}
else
{
- t = mark_rvalue_use (t);
+ allocator = mark_rvalue_use (allocator);
if (!processing_template_decl)
- t = maybe_constant_value (t);
- OMP_CLAUSE_ALLOCATE_ALLOCATOR (c) = t;
+ allocator = maybe_constant_value (allocator);
+ OMP_CLAUSE_ALLOCATE_ALLOCATOR (c) = allocator;
}
- break;
+ goto handle_field_decl;
case OMP_CLAUSE_DEPEND:
t = OMP_CLAUSE_DECL (c);
diff --git a/gcc/testsuite/c-c++-common/gomp/allocate-1.c b/gcc/testsuite/c-c++-common/gomp/allocate-1.c
index 29ebdf1..5630dac 100644
--- a/gcc/testsuite/c-c++-common/gomp/allocate-1.c
+++ b/gcc/testsuite/c-c++-common/gomp/allocate-1.c
@@ -74,3 +74,11 @@ foo (int x, int z)
r += bar (x, &r, 0);
#pragma omp taskwait
}
+
+void
+qux (const omp_allocator_handle_t h)
+{
+ int x = 0;
+ #pragma omp parallel firstprivate (x) allocate (h: x)
+ x = 1;
+}
diff --git a/gcc/testsuite/g++.dg/gomp/allocate-1.C b/gcc/testsuite/g++.dg/gomp/allocate-1.C
new file mode 100644
index 0000000..e70c65e
--- /dev/null
+++ b/gcc/testsuite/g++.dg/gomp/allocate-1.C
@@ -0,0 +1,88 @@
+// { dg-do compile }
+// { dg-additional-options "-std=c++11" }
+
+typedef enum omp_allocator_handle_t
+#if __cplusplus >= 201103L
+: __UINTPTR_TYPE__
+#endif
+{
+ omp_null_allocator = 0,
+ omp_default_mem_alloc = 1,
+ omp_large_cap_mem_alloc = 2,
+ omp_const_mem_alloc = 3,
+ omp_high_bw_mem_alloc = 4,
+ omp_low_lat_mem_alloc = 5,
+ omp_cgroup_mem_alloc = 6,
+ omp_pteam_mem_alloc = 7,
+ omp_thread_mem_alloc = 8,
+ __omp_allocator_handle_t_max__ = __UINTPTR_MAX__
+} omp_allocator_handle_t;
+
+namespace N1
+{
+ using ::omp_allocator_handle_t;
+ void
+ foo (const omp_allocator_handle_t h)
+ {
+ int x = 0;
+ #pragma omp parallel allocate (h: x) private (x)
+ x = 1;
+ }
+}
+
+namespace N2
+{
+ typedef enum omp_allocator_handle_t { my = 0 } omp_allocator_handle_t;
+ void
+ foo (omp_allocator_handle_t h)
+ {
+ int x = 0;
+ #pragma omp parallel allocate (h: x) private (x) // { dg-error "'allocate' clause allocator expression has type 'N2::omp_allocator_handle_t' rather than 'omp_allocator_handle_t'" }
+ x = 1;
+ }
+}
+
+struct S
+{
+ void foo ()
+ {
+ #pragma omp parallel allocate (omp_default_mem_alloc:s) firstprivate (s)
+ s++;
+ }
+ int s;
+};
+
+template <typename T>
+struct U
+{
+ int foo ()
+ {
+ #pragma omp parallel allocate (omp_default_mem_alloc:s) firstprivate (s)
+ s++;
+ return 1;
+ }
+ T s;
+};
+
+template <typename T>
+int foo (T t)
+{
+ int x = 0;
+ #pragma omp parallel firstprivate (x) allocate (t: x)
+ x = 1;
+ return 0;
+}
+
+template <typename T>
+int bar (T t)
+{
+ int x = 0;
+ #pragma omp parallel firstprivate (x) allocate (t: x) // { dg-error "'allocate' clause allocator expression has type 'int' rather than 'omp_allocator_handle_t'" }
+ x = 1;
+ return 0;
+}
+
+omp_allocator_handle_t h;
+int a = foo (h);
+int b = bar (0);
+int c = U<int> ().foo ();