@@ -1334,12 +1334,15 @@ cp_check_const_attributes (tree attribut
}
/* Return true if TYPE is an OpenMP mappable type. */
-static bool
+bool
cp_omp_mappable_type (tree type)
{
/* Mappable type has to be complete. */
if (type == error_mark_node || !COMPLETE_TYPE_P (type))
return false;
+ /* Arrays have mappable type if the elements have mappable type. */
+ while (TREE_CODE (type) == ARRAY_TYPE)
+ type = TREE_TYPE (type);
/* A mappable type cannot contain virtual members. */
if (CLASS_TYPE_P (type) && CLASSTYPE_VTABLES (type))
return false;
@@ -1350,6 +1353,10 @@ cp_omp_mappable_type (tree type)
for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
if (TREE_CODE (field) == VAR_DECL)
return false;
+ /* All fields must have mappable types. */
+ else if (TREE_CODE (field) == FIELD_DECL
+ && !cp_omp_mappable_type (TREE_TYPE (field)))
+ return false;
}
return true;
}
@@ -4122,11 +4122,11 @@ handle_omp_array_sections_1 (tree c, tre
omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
return error_mark_node;
}
+ t = convert_from_reference (t);
if (!processing_template_decl
&& POINTER_TYPE_P (TREE_TYPE (t))
&& OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP)
pointer_based_p = true;
- t = convert_from_reference (t);
return t;
}
@@ -4921,6 +4921,18 @@ finish_omp_clauses (tree clauses)
{
if (handle_omp_array_sections (c))
remove = true;
+ else
+ {
+ t = OMP_CLAUSE_DECL (c);
+ if (!cp_omp_mappable_type (TREE_TYPE (t)))
+ {
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "array section does not have mappable type "
+ "in %qs clause",
+ omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
+ remove = true;
+ }
+ }
break;
}
if (t == error_mark_node)
@@ -4947,6 +4959,16 @@ finish_omp_clauses (tree clauses)
&& TREE_CODE (TREE_TYPE (t)) != REFERENCE_TYPE
&& !cxx_mark_addressable (t))
remove = true;
+ else if (!cp_omp_mappable_type ((TREE_CODE (TREE_TYPE (t))
+ == REFERENCE_TYPE)
+ ? TREE_TYPE (TREE_TYPE (t))
+ : TREE_TYPE (t)))
+ {
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%qD does not have a mappable type in %qs clause", t,
+ omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
+ remove = true;
+ }
else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP)
break;
else if (bitmap_bit_p (&generic_head, DECL_UID (t)))
@@ -5297,6 +5296,7 @@ extern void note_vague_linkage_fn (tree
extern tree build_artificial_parm (tree, tree);
extern bool possibly_inlined_p (tree);
extern int parm_index (tree);
+extern bool cp_omp_mappable_type (tree);
/* in error.c */
extern void init_error (void);