From 3279a9a5a9a2e4e17175678cb7b15613495e306e Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 19 Mar 2021 22:54:31 +0100 Subject: c: Fix up -Wunused-but-set-* warnings for _Atomics [PR99588] As the following testcases show, compared to -D_Atomic= case we have many -Wunused-but-set-* warning false positives. When an _Atomic variable/parameter is read, we call mark_exp_read on it in convert_lvalue_to_rvalue, but build_atomic_assign does not. For consistency with the non-_Atomic case where we mark_exp_read the lhs for lhs op= ... but not for lhs = ..., this patch does that too. But furthermore we need to pattern match the trees emitted by _Atomic store, so that _Atomic store itself is not marked as being a variable read, but when the result of the store is used, we mark it. 2021-03-19 Jakub Jelinek PR c/99588 * c-typeck.c (mark_exp_read): Recognize what build_atomic_assign with modifycode NOP_EXPR produces and mark the _Atomic var as read if found. (build_atomic_assign): For modifycode of NOP_EXPR, use COMPOUND_EXPRs rather than STATEMENT_LIST. Otherwise call mark_exp_read on lhs. Set TREE_SIDE_EFFECTS on the TARGET_EXPR. * gcc.dg/Wunused-var-5.c: New test. * gcc.dg/Wunused-var-6.c: New test. --- gcc/c/c-typeck.c | 66 ++++++++++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 60 insertions(+), 6 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 4e6d369..2685afb 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -1968,6 +1968,50 @@ mark_exp_read (tree exp) mark_exp_read (TREE_OPERAND (exp, 0)); break; case COMPOUND_EXPR: + /* Pattern match what build_atomic_assign produces with modifycode + NOP_EXPR. */ + if (VAR_P (TREE_OPERAND (exp, 1)) + && DECL_ARTIFICIAL (TREE_OPERAND (exp, 1)) + && TREE_CODE (TREE_OPERAND (exp, 0)) == COMPOUND_EXPR) + { + tree t1 = TREE_OPERAND (TREE_OPERAND (exp, 0), 0); + tree t2 = TREE_OPERAND (TREE_OPERAND (exp, 0), 1); + if (TREE_CODE (t1) == TARGET_EXPR + && TARGET_EXPR_SLOT (t1) == TREE_OPERAND (exp, 1) + && TREE_CODE (t2) == CALL_EXPR) + { + tree fndecl = get_callee_fndecl (t2); + tree arg = NULL_TREE; + if (fndecl + && TREE_CODE (fndecl) == FUNCTION_DECL + && fndecl_built_in_p (fndecl, BUILT_IN_NORMAL) + && call_expr_nargs (t2) >= 2) + switch (DECL_FUNCTION_CODE (fndecl)) + { + case BUILT_IN_ATOMIC_STORE: + arg = CALL_EXPR_ARG (t2, 1); + break; + case BUILT_IN_ATOMIC_STORE_1: + case BUILT_IN_ATOMIC_STORE_2: + case BUILT_IN_ATOMIC_STORE_4: + case BUILT_IN_ATOMIC_STORE_8: + case BUILT_IN_ATOMIC_STORE_16: + arg = CALL_EXPR_ARG (t2, 0); + break; + default: + break; + } + if (arg) + { + STRIP_NOPS (arg); + if (TREE_CODE (arg) == ADDR_EXPR + && DECL_P (TREE_OPERAND (arg, 0)) + && TYPE_ATOMIC (TREE_TYPE (TREE_OPERAND (arg, 0)))) + mark_exp_read (TREE_OPERAND (arg, 0)); + } + } + } + /* FALLTHRU */ case C_MAYBE_CONST_EXPR: mark_exp_read (TREE_OPERAND (exp, 1)); break; @@ -4065,7 +4109,7 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, vec *params; tree val, nonatomic_lhs_type, nonatomic_rhs_type, newval, newval_addr; tree old, old_addr; - tree compound_stmt; + tree compound_stmt = NULL_TREE; tree stmt, goto_stmt; tree loop_label, loop_decl, done_label, done_decl; @@ -4086,7 +4130,15 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, /* Create a compound statement to hold the sequence of statements with a loop. */ - compound_stmt = c_begin_compound_stmt (false); + if (modifycode != NOP_EXPR) + { + compound_stmt = c_begin_compound_stmt (false); + + /* For consistency with build_modify_expr on non-_Atomic, + mark the lhs as read. Also, it would be very hard to match + such expressions in mark_exp_read. */ + mark_exp_read (lhs); + } /* Remove any excess precision (which is only present here in the case of compound assignments). */ @@ -4112,13 +4164,16 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, TREE_NO_WARNING (val) = 1; rhs = build4 (TARGET_EXPR, nonatomic_rhs_type, val, rhs, NULL_TREE, NULL_TREE); + TREE_SIDE_EFFECTS (rhs) = 1; SET_EXPR_LOCATION (rhs, loc); - add_stmt (rhs); + if (modifycode != NOP_EXPR) + add_stmt (rhs); /* NOP_EXPR indicates it's a straight store of the RHS. Simply issue an atomic_store. */ if (modifycode == NOP_EXPR) { + compound_stmt = rhs; /* Build __atomic_store (&lhs, &val, SEQ_CST) */ rhs = build_unary_op (loc, ADDR_EXPR, val, false); fndecl = builtin_decl_explicit (BUILT_IN_ATOMIC_STORE); @@ -4126,10 +4181,9 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, params->quick_push (rhs); params->quick_push (seq_cst); func_call = c_build_function_call_vec (loc, vNULL, fndecl, params, NULL); - add_stmt (func_call); - /* Finish the compound statement. */ - compound_stmt = c_end_compound_stmt (loc, compound_stmt, false); + compound_stmt = build2 (COMPOUND_EXPR, void_type_node, + compound_stmt, func_call); /* VAL is the value which was stored, return a COMPOUND_STMT of the statement and that value. */ -- cgit v1.1 From 5f256a70a05fcfc5a1caf56678ceb12b4f87f781 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 20 Mar 2021 00:16:24 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index e1da067..5a3e934 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,13 @@ +2021-03-19 Jakub Jelinek + + PR c/99588 + * c-typeck.c (mark_exp_read): Recognize what build_atomic_assign + with modifycode NOP_EXPR produces and mark the _Atomic var as read + if found. + (build_atomic_assign): For modifycode of NOP_EXPR, use COMPOUND_EXPRs + rather than STATEMENT_LIST. Otherwise call mark_exp_read on lhs. + Set TREE_SIDE_EFFECTS on the TARGET_EXPR. + 2021-03-15 Tobias Burnus PR c++/99509 -- cgit v1.1 From 660eb7e9dee46ef1c986d5a4fa5cbd182b435518 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 25 Mar 2021 11:33:35 +0100 Subject: c-family: Fix up -Wduplicated-branches for union members [PR99565] Honza has fairly recently changed operand_equal_p to compare DECL_FIELD_OFFSET for COMPONENT_REFs when comparing addresses. As the first testcase in this patch shows, while that is very nice for optimizations, for the -Wduplicated-branches warning it causes regressions. Pedantically a union in both C and C++ has only one active member at a time, so using some other union member even if it has the same type is UB, so I think the warning shouldn't warn when it sees access to different fields that happen to have the same offset and should consider them different. In my first attempt to fix this I've keyed the old behavior on OEP_LEXICOGRAPHIC, but unfortunately that has various problems, the warning has a quick non-lexicographic compare in build_conditional_expr* and another lexicographic more expensive one later during genericization and turning the first one into lexicographic would mean wasting compile time on large conditionals. So, this patch instead introduces a new OEP_ flag and makes sure to pass it to operand_equal_p in all -Wduplicated-branches cases. The cvt.c changes are because on the other testcase we were warning with UNKNOWN_LOCATION, so the user wouldn't really know where the questionable code is. 2021-03-25 Jakub Jelinek PR c++/99565 * tree-core.h (enum operand_equal_flag): Add OEP_ADDRESS_OF_SAME_FIELD. * fold-const.c (operand_compare::operand_equal_p): Don't compare field offsets if OEP_ADDRESS_OF_SAME_FIELD. * c-warn.c (do_warn_duplicated_branches): Pass also OEP_ADDRESS_OF_SAME_FIELD to operand_equal_p. * c-typeck.c (build_conditional_expr): Pass OEP_ADDRESS_OF_SAME_FIELD to operand_equal_p. * call.c (build_conditional_expr_1): Pass OEP_ADDRESS_OF_SAME_FIELD to operand_equal_p. * cvt.c (convert_to_void): Preserve location_t on COND_EXPR or or COMPOUND_EXPR. * g++.dg/warn/Wduplicated-branches6.C: New test. * g++.dg/warn/Wduplicated-branches7.C: New test. --- gcc/c/c-typeck.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 2685afb..21eab00 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -5544,7 +5544,7 @@ build_conditional_expr (location_t colon_loc, tree ifexp, bool ifexp_bcp, warn here, because the COND_EXPR will be turned into OP1. */ if (warn_duplicated_branches && TREE_CODE (ret) == COND_EXPR - && (op1 == op2 || operand_equal_p (op1, op2, 0))) + && (op1 == op2 || operand_equal_p (op1, op2, OEP_ADDRESS_OF_SAME_FIELD))) warning_at (EXPR_LOCATION (ret), OPT_Wduplicated_branches, "this condition has identical branches"); -- cgit v1.1 From 4493b1c1ad7e2b2a60ad70563b81f51173115471 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 26 Mar 2021 00:16:25 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 5a3e934..c4d4605 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-03-25 Jakub Jelinek + + PR c++/99565 + * c-typeck.c (build_conditional_expr): Pass OEP_ADDRESS_OF_SAME_FIELD + to operand_equal_p. + 2021-03-19 Jakub Jelinek PR c/99588 -- cgit v1.1 From 9f7d77bd6d65aa1cf2e195d3776052705c6e636b Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Sat, 10 Apr 2021 17:01:54 +0200 Subject: c: Avoid clobbering TREE_TYPE (error_mark_node) [PR99990] The following testcase ICEs during error recovery, because finish_decl overwrites TREE_TYPE (error_mark_node), which better should stay always to be error_mark_node. 2021-04-10 Jakub Jelinek PR c/99990 * c-decl.c (finish_decl): Don't overwrite TREE_TYPE of error_mark_node. * gcc.dg/pr99990.c: New test. --- gcc/c/c-decl.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 3b2241b..3c25451 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -5402,7 +5402,7 @@ finish_decl (tree decl, location_t init_loc, tree init, gcc_unreachable (); } - if (DECL_INITIAL (decl)) + if (DECL_INITIAL (decl) && DECL_INITIAL (decl) != error_mark_node) TREE_TYPE (DECL_INITIAL (decl)) = type; relayout_decl (decl); -- cgit v1.1 From 1d54b13841774aa40f5d0a5ab87b19e7e1276d42 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sun, 11 Apr 2021 00:16:24 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index c4d4605..a11dc24 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-04-10 Jakub Jelinek + + PR c/99990 + * c-decl.c (finish_decl): Don't overwrite TREE_TYPE of + error_mark_node. + 2021-03-25 Jakub Jelinek PR c++/99565 -- cgit v1.1 From a3317f7b3c02907a122f89879e5b6e90c386e64d Mon Sep 17 00:00:00 2001 From: Richard Sandiford Date: Thu, 15 Apr 2021 11:37:38 +0100 Subject: c: Don't drop vector attributes that affect type identity [PR98852] types are distinct from GNU vector types in at least their mangling. However, there used to be nothing explicit in the VECTOR_TYPE itself to indicate the difference: we simply treated them as distinct TYPE_MAIN_VARIANTs. This caused problems like the ones reported in PR95726. The fix for that PR was to add type attributes to the types, in order to maintain the distinction between them and GNU vectors. However, this in turn caused PR98852, where c_common_type would unconditionally drop the attributes on the source types. This meant that: vector + vector had a GNU vector type rather than an vector type. See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96377#c2 for Jakub's analysis of the history of this c_common_type code. TBH I'm not sure which case the build_type_attribute_variant code is handling, but I think we should at least avoid dropping attributes that affect type identity. I've tried to audit the C and target-specific attributes to look for other types that might be affected by this, but I couldn't see any. We are only dealing with: gcc_assert (code1 == VECTOR_TYPE || code1 == COMPLEX_TYPE || code1 == FIXED_POINT_TYPE || code1 == REAL_TYPE || code1 == INTEGER_TYPE); which excludes most affects_type_identity attributes. The closest was s390_vector_bool, but the handler for that attribute changes the type node and drops the attribute itself (*no_add_attrs = true). I put the main list handling into a separate function (remove_attributes_matching) because a later patch will need it for something else. gcc/ PR c/98852 * attribs.h (affects_type_identity_attributes): Declare. * attribs.c (remove_attributes_matching): New function. (affects_type_identity_attributes): Likewise. gcc/c/ PR c/98852 * c-typeck.c (c_common_type): Do not drop attributes that affect type identity. gcc/testsuite/ PR c/98852 * gcc.target/aarch64/advsimd-intrinsics/pr98852.c: New test. --- gcc/c/c-typeck.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 21eab00..51a62c8 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -740,10 +740,16 @@ c_common_type (tree t1, tree t2) t2 = TYPE_MAIN_VARIANT (t2); if (TYPE_ATTRIBUTES (t1) != NULL_TREE) - t1 = build_type_attribute_variant (t1, NULL_TREE); + { + tree attrs = affects_type_identity_attributes (TYPE_ATTRIBUTES (t1)); + t1 = build_type_attribute_variant (t1, attrs); + } if (TYPE_ATTRIBUTES (t2) != NULL_TREE) - t2 = build_type_attribute_variant (t2, NULL_TREE); + { + tree attrs = affects_type_identity_attributes (TYPE_ATTRIBUTES (t2)); + t2 = build_type_attribute_variant (t2, attrs); + } /* Save time if the two types are the same. */ -- cgit v1.1 From da879e01ecd35737c18be1da3324f4560aba1961 Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Thu, 15 Apr 2021 15:49:30 -0600 Subject: Propagate type attribute when merging extern declarations at local scope. Resolves: PR c/99420 - bogus -Warray-parameter on a function redeclaration in function scope PR c/99972 - missing -Wunused-result on a call to a locally redeclared warn_unused_result function gcc/c/ChangeLog: PR c/99420 PR c/99972 * c-decl.c (pushdecl): Always propagate type attribute. gcc/testsuite/ChangeLog: PR c/99420 PR c/99972 * gcc.dg/Warray-parameter-9.c: New test. * gcc.dg/Wnonnull-6.c: New test. * gcc.dg/Wreturn-type3.c: New test. * gcc.dg/Wunused-result.c: New test. * gcc.dg/attr-noreturn.c: New test. * gcc.dg/attr-returns-nonnull.c: New test. --- gcc/c/c-decl.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 3c25451..3ea4708 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -3263,11 +3263,10 @@ pushdecl (tree x) else thistype = type; b->u.type = TREE_TYPE (b->decl); - if (TREE_CODE (b->decl) == FUNCTION_DECL - && fndecl_built_in_p (b->decl)) - thistype - = build_type_attribute_variant (thistype, - TYPE_ATTRIBUTES (b->u.type)); + /* Propagate the type attributes to the decl. */ + thistype + = build_type_attribute_variant (thistype, + TYPE_ATTRIBUTES (b->u.type)); TREE_TYPE (b->decl) = thistype; bind (name, b->decl, scope, /*invisible=*/false, /*nested=*/true, locus); -- cgit v1.1 From ee351f7fdbd82f8947fe9a0e74cea65d216a8549 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 16 Apr 2021 00:16:23 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 12 ++++++++++++ 1 file changed, 12 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index a11dc24..cf7415b 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,15 @@ +2021-04-15 Martin Sebor + + PR c/99420 + PR c/99972 + * c-decl.c (pushdecl): Always propagate type attribute. + +2021-04-15 Richard Sandiford + + PR c/98852 + * c-typeck.c (c_common_type): Do not drop attributes that + affect type identity. + 2021-04-10 Jakub Jelinek PR c/99990 -- cgit v1.1 From cc806126215c3f4dc187eff3bf923458d8cc6b4f Mon Sep 17 00:00:00 2001 From: Joseph Myers Date: Thu, 29 Apr 2021 00:50:35 +0000 Subject: c: C2x changes to function type compatibility WG14 N2432, the C2x removal of old-style function definitions, also changed the function type compatibility rules so that an unprototyped declaration can be compatible with a non-variadic prototyped declaration even if some function arguments are changed by the default argument promotions. I missed that change in the initial implementation for GCC of the rest of the N2432 changes, but discussion on the WG14 reflector in February suggests that this is indeed an intended change. Implement this in the C front end. Note that while this may be of use in some cases for use of pointers to unprototyped function types as a kind of generic function pointer, it's *not* possible to call such a function without a prototype visible, without getting runtime undefined behavior from the (promoted) type used in the call being incompatible with the (unpromoted) type in the prototype. Note also that GCC has a longstanding extension to allow compatibility of such a prototype with an old-style definition specifying the same type as in the prototype (which is not valid in ISO C, before old-style definitions were removed in C2x). Bootstrapped with no regressions for x86_64-pc-linux-gnu. gcc/c/ * c-typeck.c (function_types_compatible_p): For C2X, treat unprototyped function as compatible with non-variadic prototyped function even if some argument types are changed by the default argument promotions. gcc/testsuite/ * gcc.dg/c11-unproto-1.c, gcc.dg/c11-unproto-2.c, gcc.dg/c2x-unproto-1.c, gcc.dg/c2x-unproto-2.c: New tests. --- gcc/c/c-typeck.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 51a62c8..3b45cfd 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -1692,7 +1692,7 @@ function_types_compatible_p (const_tree f1, const_tree f2, if (args1 == NULL_TREE) { - if (!self_promoting_args_p (args2)) + if (flag_isoc2x ? stdarg_p (f2) : !self_promoting_args_p (args2)) return 0; /* If one of these types comes from a non-prototype fn definition, compare that with the other type's arglist. @@ -1705,7 +1705,7 @@ function_types_compatible_p (const_tree f1, const_tree f2, } if (args2 == NULL_TREE) { - if (!self_promoting_args_p (args1)) + if (flag_isoc2x ? stdarg_p (f1) : !self_promoting_args_p (args1)) return 0; if (TYPE_ACTUAL_ARG_TYPES (f2) && type_lists_compatible_p (args1, TYPE_ACTUAL_ARG_TYPES (f2), -- cgit v1.1 From 3c8e539dcfd955b24af44b95a1a900dc0a5dc4c9 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 30 Apr 2021 00:16:37 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index cf7415b..e61ec5d 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,10 @@ +2021-04-29 Joseph Myers + + * c-typeck.c (function_types_compatible_p): For C2X, treat + unprototyped function as compatible with non-variadic prototyped + function even if some argument types are changed by the default + argument promotions. + 2021-04-15 Martin Sebor PR c/99420 -- cgit v1.1 From 1580fc764423bf89e9b853aaa8c65999e37ccb8b Mon Sep 17 00:00:00 2001 From: Tobias Burnus Date: Tue, 4 May 2021 13:38:03 +0200 Subject: OpenMP: Support complex/float in && and || reduction C/C++ permit logical AND and logical OR also with floating-point or complex arguments by doing an unequal zero comparison; the result is an 'int' with value one or zero. Hence, those are also permitted as reduction variable, even though it is not the most sensible thing to do. gcc/c/ChangeLog: * c-typeck.c (c_finish_omp_clauses): Accept float + complex for || and && reductions. gcc/cp/ChangeLog: * semantics.c (finish_omp_reduction_clause): Accept float + complex for || and && reductions. gcc/ChangeLog: * omp-low.c (lower_rec_input_clauses, lower_reduction_clauses): Handle && and || with floating-point and complex arguments. gcc/testsuite/ChangeLog: * gcc.dg/gomp/clause-1.c: Use 'reduction(&:..)' instead of '...(&&:..)'. libgomp/ChangeLog: * testsuite/libgomp.c-c++-common/reduction-1.c: New test. * testsuite/libgomp.c-c++-common/reduction-2.c: New test. * testsuite/libgomp.c-c++-common/reduction-3.c: New test. --- gcc/c/c-typeck.c | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 3b45cfd..fdc7bb6 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -14097,6 +14097,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) case PLUS_EXPR: case MULT_EXPR: case MINUS_EXPR: + case TRUTH_ANDIF_EXPR: + case TRUTH_ORIF_EXPR: break; case MIN_EXPR: if (TREE_CODE (type) == COMPLEX_TYPE) @@ -14115,14 +14117,6 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) case BIT_IOR_EXPR: r_name = "|"; break; - case TRUTH_ANDIF_EXPR: - if (FLOAT_TYPE_P (type)) - r_name = "&&"; - break; - case TRUTH_ORIF_EXPR: - if (FLOAT_TYPE_P (type)) - r_name = "||"; - break; default: gcc_unreachable (); } -- cgit v1.1 From 99e8df7a4cc0bb1bfa49e69ccb0f7e02c9755e3c Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 5 May 2021 00:16:54 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index e61ec5d..29499d7 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-05-04 Tobias Burnus + + * c-typeck.c (c_finish_omp_clauses): Accept float + complex + for || and && reductions. + 2021-04-29 Joseph Myers * c-typeck.c (function_types_compatible_p): For C2X, treat -- cgit v1.1 From e2bc5b6c04df820017c497a2578bd3c4c7b6c89b Mon Sep 17 00:00:00 2001 From: Eric Botcazou Date: Fri, 7 May 2021 20:44:36 +0200 Subject: Do not apply scalar storage order to pointer fields Pointer fields (and vector fields originally) were not really considered when the scalar_storage_order attribute, so they are swapped as well. As pointed out, this is problematic to describe in DWARF and probably not very useful in any case, so this pulls them out. gcc/ * doc/extend.texi (scalar_storage_order): Mention effect on pointer and vector fields. * tree.h (reverse_storage_order_for_component_p): Return false if the type is a pointer. gcc/c/ * c-typeck.c (build_unary_op) : Do not issue an error on the address of a pointer field in a record with reverse SSO. gcc/testsuite/ * gcc.dg/sso-12.c: New test. --- gcc/c/c-typeck.c | 1 + 1 file changed, 1 insertion(+) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index fdc7bb6..5bdc673 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -4866,6 +4866,7 @@ build_unary_op (location_t location, enum tree_code code, tree xarg, if (TYPE_REVERSE_STORAGE_ORDER (TREE_TYPE (TREE_OPERAND (arg, 0)))) { if (!AGGREGATE_TYPE_P (TREE_TYPE (arg)) + && !POINTER_TYPE_P (TREE_TYPE (arg)) && !VECTOR_TYPE_P (TREE_TYPE (arg))) { error_at (location, "cannot take address of scalar with " -- cgit v1.1 From 62d87a321b29f9febdacc6220367021d98db3057 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 8 May 2021 00:16:27 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 29499d7..d5750cf 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-05-07 Eric Botcazou + + * c-typeck.c (build_unary_op) : Do not issue an error + on the address of a pointer field in a record with reverse SSO. + 2021-05-04 Tobias Burnus * c-typeck.c (c_finish_omp_clauses): Accept float + complex -- cgit v1.1 From 6ba3079dce89d9b63bf5dbd5e320ea2bf96f196b Mon Sep 17 00:00:00 2001 From: Martin Liska Date: Wed, 17 Mar 2021 16:36:44 +0100 Subject: Come up with startswith function. gcc/ada/ChangeLog: * gcc-interface/utils.c (def_builtin_1): Use startswith function instead of strncmp. gcc/analyzer/ChangeLog: * sm-file.cc (is_file_using_fn_p): Use startswith function instead of strncmp. gcc/ChangeLog: * builtins.c (is_builtin_name): Use startswith function instead of strncmp. * collect2.c (main): Likewise. (has_lto_section): Likewise. (scan_libraries): Likewise. * coverage.c (coverage_checksum_string): Likewise. (coverage_init): Likewise. * dwarf2out.c (is_cxx): Likewise. (gen_compile_unit_die): Likewise. * gcc-ar.c (main): Likewise. * gcc.c (init_spec): Likewise. (read_specs): Likewise. (execute): Likewise. (check_live_switch): Likewise. * genattrtab.c (write_attr_case): Likewise. (IS_ATTR_GROUP): Likewise. * gencfn-macros.c (main): Likewise. * gengtype.c (type_for_name): Likewise. (gen_rtx_next): Likewise. (get_file_langdir): Likewise. (write_local): Likewise. * genmatch.c (get_operator): Likewise. (get_operand_type): Likewise. (expr::gen_transform): Likewise. * genoutput.c (validate_optab_operands): Likewise. * incpath.c (add_sysroot_to_chain): Likewise. * langhooks.c (lang_GNU_C): Likewise. (lang_GNU_CXX): Likewise. (lang_GNU_Fortran): Likewise. (lang_GNU_OBJC): Likewise. * lto-wrapper.c (run_gcc): Likewise. * omp-general.c (omp_max_simt_vf): Likewise. * omp-low.c (omp_runtime_api_call): Likewise. * opts-common.c (parse_options_from_collect_gcc_options): Likewise. * read-rtl-function.c (function_reader::read_rtx_operand_r): Likewise. * real.c (real_from_string): Likewise. * selftest.c (assert_str_startswith): Likewise. * timevar.c (timer::validate_phases): Likewise. * tree.c (get_file_function_name): Likewise. * ubsan.c (ubsan_use_new_style_p): Likewise. * varasm.c (default_function_rodata_section): Likewise. (incorporeal_function_p): Likewise. (default_section_type_flags): Likewise. * system.h (startswith): Define startswith. gcc/c-family/ChangeLog: * c-ada-spec.c (print_destructor): Use startswith function instead of strncmp. (dump_ada_declaration): Likewise. * c-common.c (disable_builtin_function): Likewise. (def_builtin_1): Likewise. * c-format.c (check_tokens): Likewise. (check_plain): Likewise. (convert_format_name_to_system_name): Likewise. gcc/c/ChangeLog: * c-aux-info.c (affix_data_type): Use startswith function instead of strncmp. * c-typeck.c (build_function_call_vec): Likewise. * gimple-parser.c (c_parser_gimple_parse_bb_spec): Likewise. gcc/cp/ChangeLog: * decl.c (duplicate_decls): Use startswith function instead of strncmp. (cxx_builtin_function): Likewise. (omp_declare_variant_finalize_one): Likewise. (grokfndecl): Likewise. * error.c (dump_decl_name): Likewise. * mangle.c (find_decomp_unqualified_name): Likewise. (write_guarded_var_name): Likewise. (decl_tls_wrapper_p): Likewise. * parser.c (cp_parser_simple_type_specifier): Likewise. (cp_parser_tx_qualifier_opt): Likewise. * pt.c (template_parm_object_p): Likewise. (dguide_name_p): Likewise. gcc/d/ChangeLog: * d-builtins.cc (do_build_builtin_fn): Use startswith function instead of strncmp. * dmd/dinterpret.c (evaluateIfBuiltin): Likewise. * dmd/dmangle.c: Likewise. * dmd/hdrgen.c: Likewise. * dmd/identifier.c (Identifier::toHChars2): Likewise. gcc/fortran/ChangeLog: * decl.c (variable_decl): Use startswith function instead of strncmp. (gfc_match_end): Likewise. * gfortran.h (gfc_str_startswith): Likewise. * module.c (load_omp_udrs): Likewise. (read_module): Likewise. * options.c (gfc_handle_runtime_check_option): Likewise. * primary.c (match_arg_list_function): Likewise. * trans-decl.c (gfc_get_symbol_decl): Likewise. * trans-expr.c (gfc_conv_procedure_call): Likewise. * trans-intrinsic.c (gfc_conv_ieee_arithmetic_function): Likewise. gcc/go/ChangeLog: * gofrontend/runtime.cc (Runtime::name_to_code): Use startswith function instead of strncmp. gcc/objc/ChangeLog: * objc-act.c (objc_string_ref_type_p): Use startswith function instead of strncmp. * objc-encoding.c (encode_type): Likewise. * objc-next-runtime-abi-02.c (has_load_impl): Likewise. --- gcc/c/c-aux-info.c | 4 ++-- gcc/c/c-typeck.c | 4 ++-- gcc/c/gimple-parser.c | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-aux-info.c b/gcc/c/c-aux-info.c index bae5757..81860cb 100644 --- a/gcc/c/c-aux-info.c +++ b/gcc/c/c-aux-info.c @@ -67,12 +67,12 @@ affix_data_type (const char *param) for (;;) { - if (!strncmp (p, "volatile ", 9)) + if (startswith (p, "volatile ")) { p += 9; continue; } - if (!strncmp (p, "const ", 6)) + if (startswith (p, "const ")) { p += 6; continue; diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 5bdc673..c3b85da 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -3113,7 +3113,7 @@ build_function_call_vec (location_t loc, vec arg_loc, orig_fundecl = fundecl; /* Atomic functions have type checking/casting already done. They are often rewritten and don't match the original parameter list. */ - if (name && !strncmp (IDENTIFIER_POINTER (name), "__atomic_", 9)) + if (name && startswith (IDENTIFIER_POINTER (name), "__atomic_")) origtypes = NULL; } if (TREE_CODE (TREE_TYPE (function)) == FUNCTION_TYPE) @@ -3199,7 +3199,7 @@ build_function_call_vec (location_t loc, vec arg_loc, nargs, argarray, &arg_loc); if (name != NULL_TREE - && !strncmp (IDENTIFIER_POINTER (name), "__builtin_", 10)) + && startswith (IDENTIFIER_POINTER (name), "__builtin_")) { if (require_constant_value) result diff --git a/gcc/c/gimple-parser.c b/gcc/c/gimple-parser.c index 58b161b..3a6e72e 100644 --- a/gcc/c/gimple-parser.c +++ b/gcc/c/gimple-parser.c @@ -131,7 +131,7 @@ static void c_parser_gimple_expr_list (gimple_parser &, vec *); static bool c_parser_gimple_parse_bb_spec (tree val, int *index) { - if (strncmp (IDENTIFIER_POINTER (val), "__BB", 4) != 0) + if (!startswith (IDENTIFIER_POINTER (val), "__BB")) return false; for (const char *p = IDENTIFIER_POINTER (val) + 4; *p; ++p) if (!ISDIGIT (*p)) -- cgit v1.1 From aa891c56f25baac94db004e309d1b6e40b770a95 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 11 May 2021 00:16:36 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index d5750cf..d003883 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,10 @@ +2021-05-10 Martin Liska + + * c-aux-info.c (affix_data_type): Use startswith + function instead of strncmp. + * c-typeck.c (build_function_call_vec): Likewise. + * gimple-parser.c (c_parser_gimple_parse_bb_spec): Likewise. + 2021-05-07 Eric Botcazou * c-typeck.c (build_unary_op) : Do not issue an error -- cgit v1.1 From fa6894ec9ce25f5aff10ec176212383f5c88b1ec Mon Sep 17 00:00:00 2001 From: Marcel Vollweiler Date: Wed, 12 May 2021 09:31:58 -0700 Subject: OpenMP: Add support for 'close' in map clause gcc/c/ChangeLog: * c-parser.c (c_parser_omp_clause_map): Support map-type-modifier 'close'. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_clause_map): Support map-type-modifier 'close'. gcc/testsuite/ChangeLog: * c-c++-common/gomp/map-6.c: New test. * c-c++-common/gomp/map-7.c: New test. --- gcc/c/c-parser.c | 116 +++++++++++++++++++++++++++---------------------------- 1 file changed, 58 insertions(+), 58 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 5cdeb21..f79b839 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -15643,54 +15643,83 @@ c_parser_omp_clause_depend (c_parser *parser, tree list) map-kind: alloc | to | from | tofrom | release | delete - map ( always [,] map-kind: variable-list ) */ + map ( always [,] map-kind: variable-list ) + + OpenMP 5.0: + map ( [map-type-modifier[,] ...] map-kind: variable-list ) + + map-type-modifier: + always | close */ static tree c_parser_omp_clause_map (c_parser *parser, tree list) { location_t clause_loc = c_parser_peek_token (parser)->location; enum gomp_map_kind kind = GOMP_MAP_TOFROM; - int always = 0; - enum c_id_kind always_id_kind = C_ID_NONE; - location_t always_loc = UNKNOWN_LOCATION; - tree always_id = NULL_TREE; tree nl, c; matching_parens parens; if (!parens.require_open (parser)) return list; - if (c_parser_next_token_is (parser, CPP_NAME)) + int pos = 1; + int map_kind_pos = 0; + while (c_parser_peek_nth_token_raw (parser, pos)->type == CPP_NAME) + { + if (c_parser_peek_nth_token_raw (parser, pos + 1)->type == CPP_COLON) + { + map_kind_pos = pos; + break; + } + + if (c_parser_peek_nth_token_raw (parser, pos + 1)->type == CPP_COMMA) + pos++; + pos++; + } + + int always_modifier = 0; + int close_modifier = 0; + for (int pos = 1; pos < map_kind_pos; ++pos) { c_token *tok = c_parser_peek_token (parser); + + if (tok->type == CPP_COMMA) + { + c_parser_consume_token (parser); + continue; + } + const char *p = IDENTIFIER_POINTER (tok->value); - always_id_kind = tok->id_kind; - always_loc = tok->location; - always_id = tok->value; if (strcmp ("always", p) == 0) { - c_token *sectok = c_parser_peek_2nd_token (parser); - if (sectok->type == CPP_COMMA) + if (always_modifier) { - c_parser_consume_token (parser); - c_parser_consume_token (parser); - always = 2; + c_parser_error (parser, "too many % modifiers"); + parens.skip_until_found_close (parser); + return list; } - else if (sectok->type == CPP_NAME) + always_modifier++; + } + else if (strcmp ("close", p) == 0) + { + if (close_modifier) { - p = IDENTIFIER_POINTER (sectok->value); - if (strcmp ("alloc", p) == 0 - || strcmp ("to", p) == 0 - || strcmp ("from", p) == 0 - || strcmp ("tofrom", p) == 0 - || strcmp ("release", p) == 0 - || strcmp ("delete", p) == 0) - { - c_parser_consume_token (parser); - always = 1; - } + c_parser_error (parser, "too many % modifiers"); + parens.skip_until_found_close (parser); + return list; } + close_modifier++; } + else + { + c_parser_error (parser, "%<#pragma omp target%> with " + "modifier other than % or %" + "on % clause"); + parens.skip_until_found_close (parser); + return list; + } + + c_parser_consume_token (parser); } if (c_parser_next_token_is (parser, CPP_NAME) @@ -15700,11 +15729,11 @@ c_parser_omp_clause_map (c_parser *parser, tree list) if (strcmp ("alloc", p) == 0) kind = GOMP_MAP_ALLOC; else if (strcmp ("to", p) == 0) - kind = always ? GOMP_MAP_ALWAYS_TO : GOMP_MAP_TO; + kind = always_modifier ? GOMP_MAP_ALWAYS_TO : GOMP_MAP_TO; else if (strcmp ("from", p) == 0) - kind = always ? GOMP_MAP_ALWAYS_FROM : GOMP_MAP_FROM; + kind = always_modifier ? GOMP_MAP_ALWAYS_FROM : GOMP_MAP_FROM; else if (strcmp ("tofrom", p) == 0) - kind = always ? GOMP_MAP_ALWAYS_TOFROM : GOMP_MAP_TOFROM; + kind = always_modifier ? GOMP_MAP_ALWAYS_TOFROM : GOMP_MAP_TOFROM; else if (strcmp ("release", p) == 0) kind = GOMP_MAP_RELEASE; else if (strcmp ("delete", p) == 0) @@ -15719,35 +15748,6 @@ c_parser_omp_clause_map (c_parser *parser, tree list) c_parser_consume_token (parser); c_parser_consume_token (parser); } - else if (always) - { - if (always_id_kind != C_ID_ID) - { - c_parser_error (parser, "expected identifier"); - parens.skip_until_found_close (parser); - return list; - } - - tree t = lookup_name (always_id); - if (t == NULL_TREE) - { - undeclared_variable (always_loc, always_id); - t = error_mark_node; - } - if (t != error_mark_node) - { - tree u = build_omp_clause (clause_loc, OMP_CLAUSE_MAP); - OMP_CLAUSE_DECL (u) = t; - OMP_CLAUSE_CHAIN (u) = list; - OMP_CLAUSE_SET_MAP_KIND (u, kind); - list = u; - } - if (always == 1) - { - parens.skip_until_found_close (parser); - return list; - } - } nl = c_parser_omp_variable_list (parser, clause_loc, OMP_CLAUSE_MAP, list); -- cgit v1.1 From 0ff3a0f2b9d5cbea70d134cda2e74b674f8be9c9 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 13 May 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index d003883..0690d93 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-05-12 Marcel Vollweiler + + * c-parser.c (c_parser_omp_clause_map): Support map-type-modifier + 'close'. + 2021-05-10 Martin Liska * c-aux-info.c (affix_data_type): Use startswith -- cgit v1.1 From 957c437363f139313b2c0b2c93ca985df1d98ad2 Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Thu, 13 May 2021 10:38:09 -0600 Subject: PR c/100550 - ICE: in fold_convert_loc with function call VLA argument gcc/c/ChangeLog: PR c/100550 * c-decl.c (get_parm_array_spec): Avoid erroneous VLA bounds. gcc/testsuite/ChangeLog: PR c/100550 * gcc.dg/Wvla-parameter-9.c: New test. --- gcc/c/c-decl.c | 3 +++ 1 file changed, 3 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 3ea4708..53b2b5b 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -5856,6 +5856,9 @@ get_parm_array_spec (const struct c_parm *parm, tree attrs) spec += buf; break; } + else if (!INTEGRAL_TYPE_P (TREE_TYPE (nelts))) + /* Avoid invalid NELTS. */ + return attrs; /* Each variable VLA bound is represented by a dollar sign. */ spec += "$"; -- cgit v1.1 From f9af11c7f156bede9aa28410073acbab7b0fa0fe Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 14 May 2021 00:16:30 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 0690d93..a75832b 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-05-13 Martin Sebor + + PR c/100550 + * c-decl.c (get_parm_array_spec): Avoid erroneous VLA bounds. + 2021-05-12 Marcel Vollweiler * c-parser.c (c_parser_omp_clause_map): Support map-type-modifier -- cgit v1.1 From 086882b1c8faa8f99f98a9219ccec42d89db50c2 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Mon, 17 May 2021 14:47:08 +0200 Subject: c/100625 - avoid building invalid labels in the GIMPLE FE When duplicate labes are diagnosed, avoid building a GIMPLE_LABEL. 2021-05-17 Richard Biener PR c/100625 gcc/c/ * gimple-parser.c (c_parser_gimple_label): Avoid building a GIMPLE label with NULL label decl. gcc/testsuite/ * gcc.dg/gimplefe-error-9.c: New testcase. --- gcc/c/gimple-parser.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/gimple-parser.c b/gcc/c/gimple-parser.c index 3a6e72e..398e216 100644 --- a/gcc/c/gimple-parser.c +++ b/gcc/c/gimple-parser.c @@ -1887,7 +1887,8 @@ c_parser_gimple_label (gimple_parser &parser, gimple_seq *seq) gcc_assert (c_parser_next_token_is (parser, CPP_COLON)); c_parser_consume_token (parser); tree label = define_label (loc1, name); - gimple_seq_add_stmt_without_update (seq, gimple_build_label (label)); + if (label) + gimple_seq_add_stmt_without_update (seq, gimple_build_label (label)); return; } -- cgit v1.1 From a7ffc1ef6e38c01037c8894a6bc1889d6f875444 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 18 May 2021 00:16:40 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index a75832b..7d34f7c 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-05-17 Richard Biener + + PR c/100625 + * gimple-parser.c (c_parser_gimple_label): Avoid building + a GIMPLE label with NULL label decl. + 2021-05-13 Martin Sebor PR c/100550 -- cgit v1.1 From 414fe08a352eac69168f4fb3671246c84a1ac5aa Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Tue, 18 May 2021 08:41:43 +0200 Subject: c/100522 - avoid invalid GIMPLE in GIMPLE parsing This plugs a few easy holes avoiding ICEs down the route. 2021-05-18 Richard Biener PR c/100522 gcc/c/ * gimple-parser.c (c_parser_gimple_postfix_expression_after_primary): Diagnose calls to non-functions. (c_parser_gimple_statement): Diagnose unexpected assignment RHS. gcc/testsuite/ * gcc.dg/gimplefe-error-10.c: New testcase. --- gcc/c/gimple-parser.c | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/gimple-parser.c b/gcc/c/gimple-parser.c index 398e216..dfacf23 100644 --- a/gcc/c/gimple-parser.c +++ b/gcc/c/gimple-parser.c @@ -877,6 +877,11 @@ c_parser_gimple_statement (gimple_parser &parser, gimple_seq *seq) rhs.value = build3_loc (loc, COND_EXPR, TREE_TYPE (trueval.value), rhs.value, trueval.value, falseval.value); } + if (get_gimple_rhs_class (TREE_CODE (rhs.value)) == GIMPLE_INVALID_RHS) + { + c_parser_error (parser, "unexpected RHS for assignment"); + return; + } assign = gimple_build_assign (lhs.value, rhs.value); gimple_seq_add_stmt_without_update (seq, assign); gimple_set_location (assign, loc); @@ -1754,6 +1759,12 @@ c_parser_gimple_postfix_expression_after_primary (gimple_parser &parser, c_parser_gimple_expr_list (parser, &exprlist); c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, "expected %<)%>"); + if (!FUNC_OR_METHOD_TYPE_P (TREE_TYPE (expr.value))) + { + c_parser_error (parser, "invalid call to non-function"); + expr.set_error (); + break; + } expr.value = build_call_array_loc (expr_loc, TREE_TYPE (TREE_TYPE (expr.value)), expr.value, exprlist.length (), exprlist.address ()); -- cgit v1.1 From a8daf9a19a5eae6b98acede14bb6c27b2e0038e0 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 19 May 2021 00:16:45 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 7d34f7c..8832602 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,10 @@ +2021-05-18 Richard Biener + + PR c/100522 + * gimple-parser.c (c_parser_gimple_postfix_expression_after_primary): + Diagnose calls to non-functions. + (c_parser_gimple_statement): Diagnose unexpected assignment RHS. + 2021-05-17 Richard Biener PR c/100625 -- cgit v1.1 From 780e5d4a2bac6eb7566c966a265961c99449cb55 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Wed, 19 May 2021 09:21:09 +0200 Subject: openmp: Handle lastprivate on combined target correctly [PR99928] This patch deals with 2 issues: 1) the gimplifier couldn't differentiate between #pragma omp parallel master #pragma omp taskloop simd and #pragma omp parallel master taskloop simd when there is a significant difference for clause handling between the two; as master construct doesn't have any clauses, we don't currently represent it during gimplification by an gimplification omp context at all, so this patch makes sure we don't set OMP_PARALLEL_COMBINED on parallel master when not combined further. If we ever add a separate master context during gimplification, we'd use ORT_COMBINED_MASTER vs. ORT_MASTER (or MASKED probably). 2) lastprivate when combined with target should be map(tofrom:) on the target, this change handles it only when not combined with firstprivate though, that will need further work (similarly to linear or reduction). 2021-05-19 Jakub Jelinek PR middle-end/99928 gcc/ * tree.h (OMP_MASTER_COMBINED): Define. * gimplify.c (gimplify_scan_omp_clauses): Rewrite lastprivate handling for outer combined/composite constructs to a loop. Handle lastprivate on combined target. (gimplify_expr): Formatting fix. gcc/c/ * c-parser.c (c_parser_omp_master): Set OMP_MASTER_COMBINED on master when combined with taskloop. (c_parser_omp_parallel): Don't set OMP_PARALLEL_COMBINED on parallel master when not combined with taskloop. gcc/cp/ * parser.c (cp_parser_omp_master): Set OMP_MASTER_COMBINED on master when combined with taskloop. (cp_parser_omp_parallel): Don't set OMP_PARALLEL_COMBINED on parallel master when not combined with taskloop. gcc/testsuite/ * c-c++-common/gomp/pr99928-2.c: Remove all xfails. * c-c++-common/gomp/pr99928-12.c: New test. --- gcc/c/c-parser.c | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index f79b839..b9930d4 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -18826,6 +18826,7 @@ c_parser_omp_master (location_t loc, c_parser *parser, if (ret == NULL_TREE) return ret; ret = c_finish_omp_master (loc, block); + OMP_MASTER_COMBINED (ret) = 1; return ret; } } @@ -19126,7 +19127,16 @@ c_parser_omp_parallel (location_t loc, c_parser *parser, block); if (ret == NULL) return ret; - OMP_PARALLEL_COMBINED (stmt) = 1; + /* master doesn't have any clauses and during gimplification + isn't represented by a gimplification omp context, so for + #pragma omp parallel master don't set OMP_PARALLEL_COMBINED, + so that + #pragma omp parallel master + #pragma omp taskloop simd lastprivate (x) + isn't confused with + #pragma omp parallel master taskloop simd lastprivate (x) */ + if (OMP_MASTER_COMBINED (ret)) + OMP_PARALLEL_COMBINED (stmt) = 1; return stmt; } else if (strcmp (p, "loop") == 0) -- cgit v1.1 From 65f32e5d6bbeb93a7d8d121fd56af6555e16d747 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 20 May 2021 00:16:40 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 8832602..305d816 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,11 @@ +2021-05-19 Jakub Jelinek + + PR middle-end/99928 + * c-parser.c (c_parser_omp_master): Set OMP_MASTER_COMBINED on + master when combined with taskloop. + (c_parser_omp_parallel): Don't set OMP_PARALLEL_COMBINED on + parallel master when not combined with taskloop. + 2021-05-18 Richard Biener PR c/100522 -- cgit v1.1 From b5c1c7a96bc8d7062d2c35675f48131667498182 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 21 May 2021 21:16:21 +0200 Subject: openmp: Fix up firstprivate+lastprivate clause handling [PR99928] The C/C++ clause splitting happens very early during construct parsing, but only the FEs later on handle possible instantiations, non-static member handling and array section lowering. In the OpenMP 5.0/5.1 rules, whether firstprivate is added to combined target depends on whether it isn't also mentioned in lastprivate or map clauses, but unfortunately I think such checks are much better done only when the FEs perform all the above mentioned changes. So, this patch arranges for the firstprivate clause to be copied or moved to combined target construct (as before), but sets flags on that clause, which tell the FE *finish_omp_clauses and the gimplifier it has been added only conditionally and let the FEs and gimplifier DTRT for these. 2021-05-21 Jakub Jelinek PR middle-end/99928 gcc/ * tree.h (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET): Define. * gimplify.c (enum gimplify_omp_var_data): Fix up GOVD_MAP_HAS_ATTACHMENTS value, add GOVD_FIRSTPRIVATE_IMPLICIT. (omp_lastprivate_for_combined_outer_constructs): If combined target has GOVD_FIRSTPRIVATE_IMPLICIT set for the decl, change it to GOVD_MAP | GOVD_SEEN. (gimplify_scan_omp_clauses): Set GOVD_FIRSTPRIVATE_IMPLICIT for firstprivate clauses with OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT. (gimplify_adjust_omp_clauses): For firstprivate clauses with OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT either clear that bit and OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET too, or remove it and let it be replaced by implicit map clause. gcc/c-family/ * c-omp.c (c_omp_split_clauses): Set OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT on firstprivate clause copy going to target construct, and for target simd set also OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET bit. gcc/c/ * c-typeck.c (c_finish_omp_clauses): Move firstprivate clauses with OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT to the end of the chain. Don't error if a decl is mentioned both in map clause and in such firstprivate clause unless OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET is also set. gcc/cp/ * semantics.c (finish_omp_clauses): Move firstprivate clauses with OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT to the end of the chain. Don't error if a decl is mentioned both in map clause and in such firstprivate clause unless OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET is also set. gcc/testsuite/ * c-c++-common/gomp/pr99928-3.c: Remove all xfails. * c-c++-common/gomp/pr99928-15.c: New test. --- gcc/c/c-typeck.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index c3b85da..fc64ef9 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -13936,6 +13936,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) has been seen, -2 if mixed inscan/normal reduction diagnosed. */ int reduction_seen = 0; bool allocate_seen = false; + bool firstprivate_implicit_moved = false; bitmap_obstack_initialize (NULL); bitmap_initialize (&generic_head, &bitmap_default_obstack); @@ -14377,6 +14378,29 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) break; case OMP_CLAUSE_FIRSTPRIVATE: + if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) + && !firstprivate_implicit_moved) + { + firstprivate_implicit_moved = true; + /* Move firstprivate clauses with + OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT set to the end of + clauses chain. */ + tree cl = NULL, *pc1 = pc, *pc2 = &cl; + while (*pc1) + if (OMP_CLAUSE_CODE (*pc1) == OMP_CLAUSE_FIRSTPRIVATE + && OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (*pc1)) + { + *pc2 = *pc1; + pc2 = &OMP_CLAUSE_CHAIN (*pc2); + *pc1 = OMP_CLAUSE_CHAIN (*pc1); + } + else + pc1 = &OMP_CLAUSE_CHAIN (*pc1); + *pc2 = NULL; + *pc1 = cl; + if (pc1 != pc) + continue; + } t = OMP_CLAUSE_DECL (c); need_complete = true; need_implicitly_determined = true; @@ -14398,6 +14422,9 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) if (ort == C_ORT_ACC) error_at (OMP_CLAUSE_LOCATION (c), "%qD appears more than once in data clauses", t); + else if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) + && !OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET (c)) + /* Silently drop the clause. */; else error_at (OMP_CLAUSE_LOCATION (c), "%qD appears both in data and map clauses", t); -- cgit v1.1 From 2832d51b383392e961373fb7067a73c6dfdc7cb1 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 22 May 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 305d816..7780539 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,11 @@ +2021-05-21 Jakub Jelinek + + PR middle-end/99928 + * c-typeck.c (c_finish_omp_clauses): Move firstprivate clauses with + OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT to the end of the chain. Don't error + if a decl is mentioned both in map clause and in such firstprivate + clause unless OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET is also set. + 2021-05-19 Jakub Jelinek PR middle-end/99928 -- cgit v1.1 From 401bd4adcfda9965363b1ac3ba7e1580f15d6883 Mon Sep 17 00:00:00 2001 From: Eric Botcazou Date: Wed, 26 May 2021 19:12:05 +0200 Subject: Warn on type punning that toggles scalar storage order As documented in the manual, we do not support type punning that toggles the scalar storage order, so this adds a warning for the case of unions. gcc/c/ PR c/100653 * c-decl.c (finish_struct): Warn for a union containing an aggregate field with a differing scalar storage order. gcc/testsuite/ * gcc.dg/sso-13.c: New test. --- gcc/c/c-decl.c | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 53b2b5b..3c7b306 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -8853,6 +8853,13 @@ finish_struct (location_t loc, tree t, tree fieldlist, tree attributes, = c_build_qualified_type (fmain_type, TYPE_QUALS (ftype)); } } + + if (TREE_CODE (t) == UNION_TYPE + && AGGREGATE_TYPE_P (TREE_TYPE (field)) + && TYPE_REVERSE_STORAGE_ORDER (t) + != TYPE_REVERSE_STORAGE_ORDER (TREE_TYPE (field))) + warning_at (DECL_SOURCE_LOCATION (field), OPT_Wscalar_storage_order, + "type punning toggles scalar storage order"); } /* Now we have the truly final field list. -- cgit v1.1 From 01c59ef2e5a59b44d2b662361196abb6be872a20 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 27 May 2021 00:16:53 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 7780539..669a818 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-05-26 Eric Botcazou + + PR c/100653 + * c-decl.c (finish_struct): Warn for a union containing an aggregate + field with a differing scalar storage order. + 2021-05-21 Jakub Jelinek PR middle-end/99928 -- cgit v1.1 From 9a5de4d5af1c10a8c097de30ee4c71457216e975 Mon Sep 17 00:00:00 2001 From: Tobias Burnus Date: Fri, 28 May 2021 10:01:19 +0200 Subject: OpenMP: Add iterator support to Fortran's depend; add affinity clause gcc/c-family/ChangeLog: * c-pragma.h (enum pragma_omp_clause): Add PRAGMA_OMP_CLAUSE_AFFINITY. gcc/c/ChangeLog: * c-parser.c (c_parser_omp_clause_affinity): New. (c_parser_omp_clause_name, c_parser_omp_variable_list, c_parser_omp_all_clauses, OMP_TASK_CLAUSE_MASK): Handle affinity clause. * c-typeck.c (handle_omp_array_sections_1, handle_omp_array_sections, c_finish_omp_clauses): Likewise. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_clause_affinity): New. (cp_parser_omp_clause_name, cp_parser_omp_var_list_no_open, cp_parser_omp_all_clauses, OMP_TASK_CLAUSE_MASK): Handle affinity clause. * semantics.c (handle_omp_array_sections_1, handle_omp_array_sections, finish_omp_clauses): Likewise. gcc/fortran/ChangeLog: * dump-parse-tree.c (show_iterator): New. (show_omp_namelist): Handle iterators. (show_omp_clauses): Handle affinity. * gfortran.h (gfc_free_omp_namelist): New union with 'udr' and new 'ns'. * match.c (gfc_free_omp_namelist): Add are to choose union element. * openmp.c (gfc_free_omp_clauses, gfc_match_omp_detach, gfc_match_omp_clause_reduction, gfc_match_omp_flush): Update call to gfc_free_omp_namelist. (gfc_match_omp_variable_list): Likewise; permit preceeding whitespace. (enum omp_mask1): Add OMP_CLAUSE_AFFINITY. (gfc_match_iterator): New. (gfc_match_omp_clauses): Use it; update call to gfc_free_omp_namelist. (OMP_TASK_CLAUSES): Add OMP_CLAUSE_AFFINITY. (gfc_match_omp_taskwait): Match depend clause. (resolve_omp_clauses): Handle affinity; update for udr/union change. (gfc_resolve_omp_directive): Resolve clauses of taskwait. * st.c (gfc_free_statement): Update gfc_free_omp_namelist call. * trans-openmp.c (gfc_trans_omp_array_reduction_or_udr): Likewise (handle_iterator): New. (gfc_trans_omp_clauses): Handle iterators for depend/affinity clause. (gfc_trans_omp_taskwait): Handle depend clause. (gfc_trans_omp_directive): Update call. gcc/ChangeLog: * gimplify.c (gimplify_omp_affinity): New. (gimplify_scan_omp_clauses): Call it; remove affinity clause afterwards. * tree-core.h (enum omp_clause_code): Add OMP_CLAUSE_AFFINITY. * tree-pretty-print.c (dump_omp_clause): Handle OMP_CLAUSE_AFFINITY. * tree.c (omp_clause_num_ops, omp_clause_code_name): Add clause. (walk_tree_1): Handle OMP_CLAUSE_AFFINITY. libgomp/ChangeLog: * testsuite/libgomp.fortran/depend-iterator-2.f90: New test. gcc/testsuite/ChangeLog: * c-c++-common/gomp/affinity-1.c: New test. * c-c++-common/gomp/affinity-2.c: New test. * c-c++-common/gomp/affinity-3.c: New test. * c-c++-common/gomp/affinity-4.c: New test. * c-c++-common/gomp/affinity-5.c: New test. * c-c++-common/gomp/affinity-6.c: New test. * c-c++-common/gomp/affinity-7.c: New test. * gfortran.dg/gomp/affinity-clause-1.f90: New test. * gfortran.dg/gomp/affinity-clause-2.f90: New test. * gfortran.dg/gomp/affinity-clause-3.f90: New test. * gfortran.dg/gomp/affinity-clause-4.f90: New test. * gfortran.dg/gomp/affinity-clause-5.f90: New test. * gfortran.dg/gomp/affinity-clause-6.f90: New test. * gfortran.dg/gomp/depend-iterator-1.f90: New test. * gfortran.dg/gomp/depend-iterator-2.f90: New test. * gfortran.dg/gomp/depend-iterator-3.f90: New test. * gfortran.dg/gomp/taskwait.f90: New test. --- gcc/c/c-parser.c | 81 ++++++++++++++++++++++++++++++++++++++++++++++++++++---- gcc/c/c-typeck.c | 52 +++++++++++++++++++++++++----------- 2 files changed, 112 insertions(+), 21 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index b9930d4..d71fd0a 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -12601,7 +12601,9 @@ c_parser_omp_clause_name (c_parser *parser) switch (p[0]) { case 'a': - if (!strcmp ("aligned", p)) + if (!strcmp ("affinity", p)) + result = PRAGMA_OMP_CLAUSE_AFFINITY; + else if (!strcmp ("aligned", p)) result = PRAGMA_OMP_CLAUSE_ALIGNED; else if (!strcmp ("allocate", p)) result = PRAGMA_OMP_CLAUSE_ALLOCATE; @@ -12900,7 +12902,7 @@ c_parser_omp_variable_list (c_parser *parser, while (1) { bool array_section_p = false; - if (kind == OMP_CLAUSE_DEPEND) + if (kind == OMP_CLAUSE_DEPEND || kind == OMP_CLAUSE_AFFINITY) { if (c_parser_next_token_is_not (parser, CPP_NAME) || c_parser_peek_token (parser)->id_kind != C_ID_ID) @@ -13040,6 +13042,7 @@ c_parser_omp_variable_list (c_parser *parser, t = build_component_ref (op_loc, t, ident, comp_loc); } /* FALLTHROUGH */ + case OMP_CLAUSE_AFFINITY: case OMP_CLAUSE_DEPEND: case OMP_CLAUSE_REDUCTION: case OMP_CLAUSE_IN_REDUCTION: @@ -13090,7 +13093,7 @@ c_parser_omp_variable_list (c_parser *parser, t = tree_cons (low_bound, length, t); } - if (kind == OMP_CLAUSE_DEPEND + if ((kind == OMP_CLAUSE_DEPEND || kind == OMP_CLAUSE_AFFINITY) && t != error_mark_node && parser->tokens_avail != 2) { @@ -13130,7 +13133,7 @@ c_parser_omp_variable_list (c_parser *parser, else list = tree_cons (t, NULL_TREE, list); - if (kind == OMP_CLAUSE_DEPEND) + if (kind == OMP_CLAUSE_DEPEND || kind == OMP_CLAUSE_AFFINITY) { parser->tokens = &parser->tokens_buf[0]; parser->tokens_avail = tokens_avail; @@ -15508,6 +15511,69 @@ c_parser_omp_iterators (c_parser *parser) return ret ? ret : error_mark_node; } +/* OpenMP 5.0: + affinity ( [aff-modifier :] variable-list ) + aff-modifier: + iterator ( iterators-definition ) */ + +static tree +c_parser_omp_clause_affinity (c_parser *parser, tree list) +{ + location_t clause_loc = c_parser_peek_token (parser)->location; + tree nl, iterators = NULL_TREE; + + matching_parens parens; + if (!parens.require_open (parser)) + return list; + + if (c_parser_next_token_is (parser, CPP_NAME)) + { + const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); + bool parse_iter = ((strcmp ("iterator", p) == 0) + && (c_parser_peek_2nd_token (parser)->type + == CPP_OPEN_PAREN)); + if (parse_iter) + { + unsigned n = 3; + parse_iter = (c_parser_check_balanced_raw_token_sequence (parser, &n) + && (c_parser_peek_nth_token_raw (parser, n)->type + == CPP_CLOSE_PAREN) + && (c_parser_peek_nth_token_raw (parser, n + 1)->type + == CPP_COLON)); + } + if (parse_iter) + { + iterators = c_parser_omp_iterators (parser); + if (!c_parser_require (parser, CPP_COLON, "expected %<:%>")) + { + if (iterators) + pop_scope (); + parens.skip_until_found_close (parser); + return list; + } + } + } + nl = c_parser_omp_variable_list (parser, clause_loc, OMP_CLAUSE_AFFINITY, + list); + if (iterators) + { + tree block = pop_scope (); + if (iterators == error_mark_node) + iterators = NULL_TREE; + else + { + TREE_VEC_ELT (iterators, 5) = block; + for (tree c = nl; c != list; c = OMP_CLAUSE_CHAIN (c)) + OMP_CLAUSE_DECL (c) = build_tree_list (iterators, + OMP_CLAUSE_DECL (c)); + } + } + + parens.skip_until_found_close (parser); + return nl; +} + + /* OpenMP 4.0: depend ( depend-kind: variable-list ) @@ -16474,6 +16540,10 @@ c_parser_omp_all_clauses (c_parser *parser, omp_clause_mask mask, clauses = c_parser_omp_clause_linear (parser, clauses); c_name = "linear"; break; + case PRAGMA_OMP_CLAUSE_AFFINITY: + clauses = c_parser_omp_clause_affinity (parser, clauses); + c_name = "affinity"; + break; case PRAGMA_OMP_CLAUSE_DEPEND: clauses = c_parser_omp_clause_depend (parser, clauses); c_name = "depend"; @@ -19249,7 +19319,8 @@ c_parser_omp_single (location_t loc, c_parser *parser, bool *if_p) | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIORITY) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ALLOCATE) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IN_REDUCTION) \ - | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DETACH)) + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DETACH) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_AFFINITY)) static tree c_parser_omp_task (location_t loc, c_parser *parser, bool *if_p) diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index fc64ef9..bee01df 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -13064,7 +13064,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, if (error_operand_p (t)) return error_mark_node; ret = t; - if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND && TYPE_ATOMIC (strip_array_types (TREE_TYPE (t)))) { error_at (OMP_CLAUSE_LOCATION (c), "%<_Atomic%> %qE in %qs clause", @@ -13115,14 +13116,16 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, omp_clause_code_name[OMP_CLAUSE_CODE (c)]); return error_mark_node; } - else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND && TYPE_ATOMIC (TREE_TYPE (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%<_Atomic%> %qD in %qs clause", t, omp_clause_code_name[OMP_CLAUSE_CODE (c)]); return error_mark_node; } - else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND && VAR_P (t) && DECL_THREAD_LOCAL_P (t)) { @@ -13131,7 +13134,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, omp_clause_code_name[OMP_CLAUSE_CODE (c)]); return error_mark_node; } - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND) && TYPE_ATOMIC (TREE_TYPE (t)) && POINTER_TYPE_P (TREE_TYPE (t))) { @@ -13202,7 +13206,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, { if (!integer_nonzerop (length)) { - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION) @@ -13270,7 +13275,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, } if (tree_int_cst_equal (size, low_bound)) { - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION) @@ -13291,7 +13297,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, } else if (length == NULL_TREE) { - if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_IN_REDUCTION && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_TASK_REDUCTION) @@ -13329,7 +13336,8 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, } else if (length == NULL_TREE) { - if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_IN_REDUCTION && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_TASK_REDUCTION) @@ -13374,6 +13382,7 @@ handle_omp_array_sections_1 (tree c, tree t, vec &types, /* If there is a pointer type anywhere but in the very first array-section-subscript, the array section can't be contiguous. */ if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND + && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY && TREE_CODE (TREE_CHAIN (t)) == TREE_LIST) { error_at (OMP_CLAUSE_LOCATION (c), @@ -13410,7 +13419,8 @@ handle_omp_array_sections (tree c, enum c_omp_region_type ort) unsigned int first_non_one = 0; auto_vec types; tree *tp = &OMP_CLAUSE_DECL (c); - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY) && TREE_CODE (*tp) == TREE_LIST && TREE_PURPOSE (*tp) && TREE_CODE (TREE_PURPOSE (*tp)) == TREE_VEC) @@ -13422,7 +13432,8 @@ handle_omp_array_sections (tree c, enum c_omp_region_type ort) return true; if (first == NULL_TREE) return false; - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND) + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY) { tree t = *tp; tree tem = NULL_TREE; @@ -14531,6 +14542,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) } break; + case OMP_CLAUSE_AFFINITY: case OMP_CLAUSE_DEPEND: t = OMP_CLAUSE_DECL (c); if (t == NULL_TREE) @@ -14539,7 +14551,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) == OMP_CLAUSE_DEPEND_SOURCE); break; } - if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK) + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK) { gcc_assert (TREE_CODE (t) == TREE_LIST); for (; t; t = TREE_CHAIN (t)) @@ -14585,7 +14598,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) { if (handle_omp_array_sections (c, ort)) remove = true; - else if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_DEPOBJ) + else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_DEPOBJ) { error_at (OMP_CLAUSE_LOCATION (c), "% clause with % dependence " @@ -14600,17 +14614,22 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) { error_at (OMP_CLAUSE_LOCATION (c), "%qE is not lvalue expression nor array section in " - "% clause", t); + "%qs clause", t, + omp_clause_code_name[OMP_CLAUSE_CODE (c)]); remove = true; } else if (TREE_CODE (t) == COMPONENT_REF && DECL_C_BIT_FIELD (TREE_OPERAND (t, 1))) { + gcc_assert (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY); error_at (OMP_CLAUSE_LOCATION (c), - "bit-field %qE in %qs clause", t, "depend"); + "bit-field %qE in %qs clause", t, + omp_clause_code_name[OMP_CLAUSE_CODE (c)]); remove = true; } - else if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_DEPOBJ) + else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_DEPOBJ) { if (!c_omp_depend_t_p (TREE_TYPE (t))) { @@ -14621,7 +14640,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) remove = true; } } - else if (c_omp_depend_t_p (TREE_TYPE (t))) + else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND + && c_omp_depend_t_p (TREE_TYPE (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%qE should not have % type in " -- cgit v1.1 From c94424b0ed786ec92b6904da69af8b5243b34fdc Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 28 May 2021 11:26:48 +0200 Subject: openmp: Fix up handling of reduction clause on constructs combined with target [PR99928] The reduction clause should be copied as map (tofrom: ) to combined target if present, but as we need different handling of array sections between map and reduction, doing that during gimplification would be harder. So, this patch adds them during splitting, and similarly to firstprivate adds them with a new flag that they should be just ignored/removed if an explicit map clause of the same list item is present. The exact rules are to be decided in https://github.com/OpenMP/spec/issues/2766 so this patch just implements something that is IMHO reasonable and exact detailed testcases for the cornercases will follow once it is clarified. 2021-05-28 Jakub Jelinek PR middle-end/99928 gcc/ * tree.h (OMP_CLAUSE_MAP_IMPLICIT): Define. gcc/c-family/ * c-omp.c (c_omp_split_clauses): For reduction clause if combined with target add a map tofrom clause with OMP_CLAUSE_MAP_IMPLICIT. gcc/c/ * c-typeck.c (handle_omp_array_sections): Copy OMP_CLAUSE_MAP_IMPLICIT. (c_finish_omp_clauses): Move not just OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT marked clauses last, but also OMP_CLAUSE_MAP_IMPLICIT. Add map_firstprivate_head bitmap, set it for GOMP_MAP_FIRSTPRIVATE_POINTER maps and silently remove OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT if it is present too. For OMP_CLAUSE_MAP_IMPLICIT silently remove the clause if present in map_head, map_field_head or map_firstprivate_head bitmaps. gcc/cp/ * semantics.c (handle_omp_array_sections): Copy OMP_CLAUSE_MAP_IMPLICIT. (finish_omp_clauses): Move not just OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT marked clauses last, but also OMP_CLAUSE_MAP_IMPLICIT. Add map_firstprivate_head bitmap, set it for GOMP_MAP_FIRSTPRIVATE_POINTER maps and silently remove OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT if it is present too. For OMP_CLAUSE_MAP_IMPLICIT silently remove the clause if present in map_head, map_field_head or map_firstprivate_head bitmaps. gcc/testsuite/ * c-c++-common/gomp/pr99928-8.c: Remove all xfails. * c-c++-common/gomp/pr99928-9.c: Likewise. * c-c++-common/gomp/pr99928-10.c: Likewise. * c-c++-common/gomp/pr99928-16.c: New test. --- gcc/c/c-typeck.c | 63 ++++++++++++++++++++++++++++++++++++++++++++------------ 1 file changed, 50 insertions(+), 13 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index bee01df..5f32287 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -13657,6 +13657,7 @@ handle_omp_array_sections (tree c, enum c_omp_region_type ort) OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_ATTACH_DETACH); else OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_FIRSTPRIVATE_POINTER); + OMP_CLAUSE_MAP_IMPLICIT (c2) = OMP_CLAUSE_MAP_IMPLICIT (c); if (OMP_CLAUSE_MAP_KIND (c2) != GOMP_MAP_FIRSTPRIVATE_POINTER && !c_mark_addressable (t)) return false; @@ -13927,7 +13928,8 @@ tree c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) { bitmap_head generic_head, firstprivate_head, lastprivate_head; - bitmap_head aligned_head, map_head, map_field_head, oacc_reduction_head; + bitmap_head aligned_head, map_head, map_field_head, map_firstprivate_head; + bitmap_head oacc_reduction_head; tree c, t, type, *pc; tree simdlen = NULL_TREE, safelen = NULL_TREE; bool branch_seen = false; @@ -13947,7 +13949,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) has been seen, -2 if mixed inscan/normal reduction diagnosed. */ int reduction_seen = 0; bool allocate_seen = false; - bool firstprivate_implicit_moved = false; + bool implicit_moved = false; bitmap_obstack_initialize (NULL); bitmap_initialize (&generic_head, &bitmap_default_obstack); @@ -13957,6 +13959,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) /* If ort == C_ORT_OMP_DECLARE_SIMD used as uniform_head instead. */ bitmap_initialize (&map_head, &bitmap_default_obstack); bitmap_initialize (&map_field_head, &bitmap_default_obstack); + bitmap_initialize (&map_firstprivate_head, &bitmap_default_obstack); /* If ort == C_ORT_OMP used as nontemporal_head or use_device_xxx_head instead. */ bitmap_initialize (&oacc_reduction_head, &bitmap_default_obstack); @@ -14389,28 +14392,36 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) break; case OMP_CLAUSE_FIRSTPRIVATE: - if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) - && !firstprivate_implicit_moved) + if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) && !implicit_moved) { - firstprivate_implicit_moved = true; - /* Move firstprivate clauses with - OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT set to the end of + move_implicit: + implicit_moved = true; + /* Move firstprivate and map clauses with + OMP_CLAUSE_{FIRSTPRIVATE,MAP}_IMPLICIT set to the end of clauses chain. */ - tree cl = NULL, *pc1 = pc, *pc2 = &cl; + tree cl1 = NULL_TREE, cl2 = NULL_TREE; + tree *pc1 = pc, *pc2 = &cl1, *pc3 = &cl2; while (*pc1) if (OMP_CLAUSE_CODE (*pc1) == OMP_CLAUSE_FIRSTPRIVATE && OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (*pc1)) { + *pc3 = *pc1; + pc3 = &OMP_CLAUSE_CHAIN (*pc3); + *pc1 = OMP_CLAUSE_CHAIN (*pc1); + } + else if (OMP_CLAUSE_CODE (*pc1) == OMP_CLAUSE_MAP + && OMP_CLAUSE_MAP_IMPLICIT (*pc1)) + { *pc2 = *pc1; pc2 = &OMP_CLAUSE_CHAIN (*pc2); *pc1 = OMP_CLAUSE_CHAIN (*pc1); } else pc1 = &OMP_CLAUSE_CHAIN (*pc1); - *pc2 = NULL; - *pc1 = cl; - if (pc1 != pc) - continue; + *pc3 = NULL; + *pc2 = cl2; + *pc1 = cl1; + continue; } t = OMP_CLAUSE_DECL (c); need_complete = true; @@ -14421,6 +14432,10 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) "%qE is not a variable in clause %", t); remove = true; } + else if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) + && !OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET (c) + && bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))) + remove = true; else if (bitmap_bit_p (&generic_head, DECL_UID (t)) || bitmap_bit_p (&firstprivate_head, DECL_UID (t))) { @@ -14673,6 +14688,9 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) break; case OMP_CLAUSE_MAP: + if (OMP_CLAUSE_MAP_IMPLICIT (c) && !implicit_moved) + goto move_implicit; + /* FALLTHRU */ case OMP_CLAUSE_TO: case OMP_CLAUSE_FROM: case OMP_CLAUSE__CACHE_: @@ -14706,6 +14724,16 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) { while (TREE_CODE (t) == COMPONENT_REF) t = TREE_OPERAND (t, 0); + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP + && OMP_CLAUSE_MAP_IMPLICIT (c) + && (bitmap_bit_p (&map_head, DECL_UID (t)) + || bitmap_bit_p (&map_field_head, DECL_UID (t)) + || bitmap_bit_p (&map_firstprivate_head, + DECL_UID (t)))) + { + remove = true; + break; + } if (bitmap_bit_p (&map_field_head, DECL_UID (t))) break; if (bitmap_bit_p (&map_head, DECL_UID (t))) @@ -14860,6 +14888,12 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) remove = true; } else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP + && OMP_CLAUSE_MAP_IMPLICIT (c) + && (bitmap_bit_p (&map_head, DECL_UID (t)) + || bitmap_bit_p (&map_field_head, DECL_UID (t)) + || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t)))) + remove = true; + else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER) { if (bitmap_bit_p (&generic_head, DECL_UID (t)) @@ -14880,7 +14914,10 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) remove = true; } else - bitmap_set_bit (&generic_head, DECL_UID (t)); + { + bitmap_set_bit (&generic_head, DECL_UID (t)); + bitmap_set_bit (&map_firstprivate_head, DECL_UID (t)); + } } else if (bitmap_bit_p (&map_head, DECL_UID (t)) && (ort != C_ORT_OMP -- cgit v1.1 From 8b2b32ab2d8cff4eb0dad0ef4e72e33257574cb6 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Fri, 28 May 2021 13:05:39 +0200 Subject: c/100803 - diagnose invalid GIMPLE condition another easy fix for GIMPLE FE parser robustness. 2021-05-28 Richard Biener PR c/100803 gcc/c/ * gimple-parser.c (c_parser_gimple_paren_condition): Diagnose invalid if conditions. gcc/testsuite/ * gcc.dg/gimplefe-error-11.c: New testcase. --- gcc/c/gimple-parser.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/gimple-parser.c b/gcc/c/gimple-parser.c index dfacf23..c8d9db6 100644 --- a/gcc/c/gimple-parser.c +++ b/gcc/c/gimple-parser.c @@ -2112,6 +2112,14 @@ c_parser_gimple_paren_condition (gimple_parser &parser) if (! c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>")) return error_mark_node; tree cond = c_parser_gimple_binary_expression (parser).value; + if (cond != error_mark_node + && ! COMPARISON_CLASS_P (cond) + && ! CONSTANT_CLASS_P (cond) + && ! SSA_VAR_P (cond)) + { + c_parser_error (parser, "comparison required"); + cond = error_mark_node; + } if (! c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>")) return error_mark_node; return cond; -- cgit v1.1 From 48166757dcf46d92cf1795dd7333dda7030179c8 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 29 May 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 669a818..411058f 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,29 @@ +2021-05-28 Richard Biener + + PR c/100803 + * gimple-parser.c (c_parser_gimple_paren_condition): Diagnose + invalid if conditions. + +2021-05-28 Jakub Jelinek + + PR middle-end/99928 + * c-typeck.c (handle_omp_array_sections): Copy OMP_CLAUSE_MAP_IMPLICIT. + (c_finish_omp_clauses): Move not just OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT + marked clauses last, but also OMP_CLAUSE_MAP_IMPLICIT. Add + map_firstprivate_head bitmap, set it for GOMP_MAP_FIRSTPRIVATE_POINTER + maps and silently remove OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT if it is + present too. For OMP_CLAUSE_MAP_IMPLICIT silently remove the clause + if present in map_head, map_field_head or map_firstprivate_head + bitmaps. + +2021-05-28 Tobias Burnus + + * c-parser.c (c_parser_omp_clause_affinity): New. + (c_parser_omp_clause_name, c_parser_omp_variable_list, + c_parser_omp_all_clauses, OMP_TASK_CLAUSE_MASK): Handle affinity clause. + * c-typeck.c (handle_omp_array_sections_1, handle_omp_array_sections, + c_finish_omp_clauses): Likewise. + 2021-05-26 Eric Botcazou PR c/100653 -- cgit v1.1 From ef8176e0fac935c095cc39f4ecdfd43cdb8cb3f3 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Fri, 21 May 2021 11:33:30 +0200 Subject: c++/88601 - [C/C++] __builtin_shufflevector support This adds support for the clang __builtin_shufflevector extension to the C and C++ frontends. The builtin is lowered to VEC_PERM_EXPR. Because VEC_PERM_EXPR does not support different sized vector inputs or result or the special permute index of -1 (don't-care) c_build_shufflevector applies lowering by widening inputs and output to the widest vector, replacing -1 by a defined index and subsetting the final vector if we produced a wider result than desired. Code generation thus can be sub-optimal, followup patches will aim to fix that by recovering from part of the missing features during RTL expansion and by relaxing the constraints of the GIMPLE IL with regard to VEC_PERM_EXPR. 2021-05-21 Richard Biener PR c++/88601 gcc/c-family/ * c-common.c: Include tree-vector-builder.h and vec-perm-indices.h. (c_common_reswords): Add __builtin_shufflevector. (c_build_shufflevector): New funtion. * c-common.h (enum rid): Add RID_BUILTIN_SHUFFLEVECTOR. (c_build_shufflevector): Declare. gcc/c/ * c-decl.c (names_builtin_p): Handle RID_BUILTIN_SHUFFLEVECTOR. * c-parser.c (c_parser_postfix_expression): Likewise. gcc/cp/ * cp-objcp-common.c (names_builtin_p): Handle RID_BUILTIN_SHUFFLEVECTOR. * cp-tree.h (build_x_shufflevector): Declare. * parser.c (cp_parser_postfix_expression): Handle RID_BUILTIN_SHUFFLEVECTOR. * pt.c (tsubst_copy_and_build): Handle IFN_SHUFFLEVECTOR. * typeck.c (build_x_shufflevector): Build either a lowered VEC_PERM_EXPR or an unlowered shufflevector via a temporary internal function IFN_SHUFFLEVECTOR. gcc/ * internal-fn.c (expand_SHUFFLEVECTOR): Define. * internal-fn.def (SHUFFLEVECTOR): New. * internal-fn.h (expand_SHUFFLEVECTOR): Declare. * doc/extend.texi: Document __builtin_shufflevector. gcc/testsuite/ * c-c++-common/builtin-shufflevector-2.c: New testcase. * c-c++-common/torture/builtin-shufflevector-1.c: Likewise. * g++.dg/ext/builtin-shufflevector-1.C: Likewise. * g++.dg/ext/builtin-shufflevector-2.C: Likewise. --- gcc/c/c-decl.c | 1 + gcc/c/c-parser.c | 38 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 39 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 3c7b306..28f851b 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -10547,6 +10547,7 @@ names_builtin_p (const char *name) case RID_BUILTIN_CONVERTVECTOR: case RID_BUILTIN_HAS_ATTRIBUTE: case RID_BUILTIN_SHUFFLE: + case RID_BUILTIN_SHUFFLEVECTOR: case RID_CHOOSE_EXPR: case RID_OFFSETOF: case RID_TYPES_COMPATIBLE_P: diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index d71fd0a..c491b12 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -10000,6 +10000,44 @@ c_parser_postfix_expression (c_parser *parser) set_c_expr_source_range (&expr, loc, close_paren_loc); break; } + case RID_BUILTIN_SHUFFLEVECTOR: + { + vec *cexpr_list; + unsigned int i; + c_expr_t *p; + location_t close_paren_loc; + + c_parser_consume_token (parser); + if (!c_parser_get_builtin_args (parser, + "__builtin_shufflevector", + &cexpr_list, false, + &close_paren_loc)) + { + expr.set_error (); + break; + } + + FOR_EACH_VEC_SAFE_ELT (cexpr_list, i, p) + *p = convert_lvalue_to_rvalue (loc, *p, true, true); + + if (vec_safe_length (cexpr_list) < 3) + { + error_at (loc, "wrong number of arguments to " + "%<__builtin_shuffle%>"); + expr.set_error (); + } + else + { + auto_vec mask; + for (i = 2; i < cexpr_list->length (); ++i) + mask.safe_push ((*cexpr_list)[i].value); + expr.value = c_build_shufflevector (loc, (*cexpr_list)[0].value, + (*cexpr_list)[1].value, + mask); + } + set_c_expr_source_range (&expr, loc, close_paren_loc); + break; + } case RID_BUILTIN_CONVERTVECTOR: { location_t start_loc = loc; -- cgit v1.1 From ee682192755bb88af0ee10852e7c873b844d449f Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 1 Jun 2021 00:16:37 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 411058f..b6f76b3 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-05-31 Richard Biener + + PR c++/88601 + * c-decl.c (names_builtin_p): Handle RID_BUILTIN_SHUFFLEVECTOR. + * c-parser.c (c_parser_postfix_expression): Likewise. + 2021-05-28 Richard Biener PR c/100803 -- cgit v1.1 From 098f4e989beb1a1be1157430c56ea4f158c1d538 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 3 Jun 2021 10:38:08 +0200 Subject: openmp: Assorted depend/affinity/iterator related fixes [PR100859] The depend-iterator-3.C testcases shows various bugs. 1) tsubst_omp_clauses didn't handle OMP_CLAUSE_AFFINITY (should be handled like OMP_CLAUSE_DEPEND) 2) because locators can be arbitrary lvalue expressions, we need to allow for C++ array section base (especially when array section is just an array reference) FIELD_DECLs, handle them as this->member, but don't need to privatize in any way 3) similarly for this as base 4) depend(inout: this) is invalid, but for different reason than the reported one, again this is an expression, but not lvalue expression, so that should be reported 5) the ctor/dtor cloning in the C++ FE (which is using walk_tree with copy_tree_body_r) didn't handle iterators correctly, walk_tree normally doesn't walk TREE_PURPOSE of TREE_LIST, and in the iterator case that TREE_VEC contains also a BLOCK that needs special handling during copy_tree_body_r 2021-06-03 Jakub Jelinek PR c++/100859 gcc/ * tree-inline.c (copy_tree_body_r): Handle iterators on OMP_CLAUSE_AFFINITY or OMP_CLAUSE_DEPEND. gcc/c/ * c-typeck.c (c_finish_omp_clauses): Move OMP_CLAUSE_AFFINITY after depend only cases. gcc/cp/ * semantics.c (handle_omp_array_sections_1): For OMP_CLAUSE_{AFFINITY,DEPEND} handle FIELD_DECL base using finish_non_static_data_member and allow this as base. (finish_omp_clauses): Move OMP_CLAUSE_AFFINITY after depend only cases. Let this be diagnosed by !lvalue_p case for OMP_CLAUSE_{AFFINITY,DEPEND} and remove useless assert. * pt.c (tsubst_omp_clauses): Handle OMP_CLAUSE_AFFINITY. gcc/testsuite/ * g++.dg/gomp/depend-iterator-3.C: New test. * g++.dg/gomp/this-1.C: Don't expect any diagnostics for this as base expression of depend array section, expect a different error wording for this as depend locator and add testcases for affinity clauses. --- gcc/c/c-typeck.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 5f32287..be3f4f0 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -14557,7 +14557,6 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) } break; - case OMP_CLAUSE_AFFINITY: case OMP_CLAUSE_DEPEND: t = OMP_CLAUSE_DECL (c); if (t == NULL_TREE) @@ -14566,8 +14565,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) == OMP_CLAUSE_DEPEND_SOURCE); break; } - if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND - && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK) + if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK) { gcc_assert (TREE_CODE (t) == TREE_LIST); for (; t; t = TREE_CHAIN (t)) @@ -14595,6 +14593,9 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) } break; } + /* FALLTHRU */ + case OMP_CLAUSE_AFFINITY: + t = OMP_CLAUSE_DECL (c); if (TREE_CODE (t) == TREE_LIST && TREE_PURPOSE (t) && TREE_CODE (TREE_PURPOSE (t)) == TREE_VEC) -- cgit v1.1 From 440c8a0a91b7ea1603e3e1eaae64fc0e12f0c4f1 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 4 Jun 2021 00:16:24 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index b6f76b3..3a7e3d4 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-06-03 Jakub Jelinek + + PR c++/100859 + * c-typeck.c (c_finish_omp_clauses): Move OMP_CLAUSE_AFFINITY + after depend only cases. + 2021-05-31 Richard Biener PR c++/88601 -- cgit v1.1 From 5328cad24f7460a39b2def12bb9b62be36c92a54 Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Fri, 4 Jun 2021 11:21:51 -0600 Subject: PR c/100783 - ICE on -Wnonnull and erroneous type gcc/c-family/ChangeLog: PR c/100783 * c-attribs.c (positional_argument): Bail on erroneous types. gcc/c/ChangeLog: PR c/100783 * c-objc-common.c (print_type): Handle erroneous types. gcc/testsuite/ChangeLog: PR c/100783 * gcc.dg/nonnull-6.c: New test. --- gcc/c/c-objc-common.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-objc-common.c b/gcc/c/c-objc-common.c index a68249d..b945de1 100644 --- a/gcc/c/c-objc-common.c +++ b/gcc/c/c-objc-common.c @@ -185,6 +185,12 @@ get_aka_type (tree type) static void print_type (c_pretty_printer *cpp, tree t, bool *quoted) { + if (t == error_mark_node) + { + pp_string (cpp, _("{erroneous}")); + return; + } + gcc_assert (TYPE_P (t)); struct obstack *ob = pp_buffer (cpp)->obstack; char *p = (char *) obstack_base (ob); -- cgit v1.1 From 600f90cbbbf2f1e4511d72a23a5d637d11e9f28b Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 5 Jun 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 3a7e3d4..747f53f 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-06-04 Martin Sebor + + PR c/100783 + * c-objc-common.c (print_type): Handle erroneous types. + 2021-06-03 Jakub Jelinek PR c++/100859 -- cgit v1.1 From a589877a0036fc2f66b7a957859940c53efdc7c9 Mon Sep 17 00:00:00 2001 From: Eric Botcazou Date: Sun, 6 Jun 2021 11:37:45 +0200 Subject: Fix thinko in new warning on type punning for storage order purposes In C, unlike in Ada, the storage order of arrays is that of their component type, so you need to look at it when deciding to warn. And the PR complains about a bogus warning on the assignment of a pointer returned by alloca or malloc, so this also fixes that. gcc/c PR c/100920 * c-decl.c (finish_struct): Fix thinko in previous change. * c-typeck.c (convert_for_assignment): Do not warn on pointer assignment and initialization for storage order purposes if the RHS is a call to a DECL_IS_MALLOC function. gcc/testsuite/ * gcc.dg/sso-14.c: New test. --- gcc/c/c-decl.c | 19 ++++++++++++++----- gcc/c/c-typeck.c | 23 +++++++++++++++++------ 2 files changed, 31 insertions(+), 11 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 28f851b..a86792b 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -8854,12 +8854,21 @@ finish_struct (location_t loc, tree t, tree fieldlist, tree attributes, } } + /* Warn on problematic type punning for storage order purposes. */ if (TREE_CODE (t) == UNION_TYPE - && AGGREGATE_TYPE_P (TREE_TYPE (field)) - && TYPE_REVERSE_STORAGE_ORDER (t) - != TYPE_REVERSE_STORAGE_ORDER (TREE_TYPE (field))) - warning_at (DECL_SOURCE_LOCATION (field), OPT_Wscalar_storage_order, - "type punning toggles scalar storage order"); + && TREE_CODE (field) == FIELD_DECL + && AGGREGATE_TYPE_P (TREE_TYPE (field))) + { + tree ftype = TREE_TYPE (field); + if (TREE_CODE (ftype) == ARRAY_TYPE) + ftype = strip_array_types (ftype); + if (RECORD_OR_UNION_TYPE_P (ftype) + && TYPE_REVERSE_STORAGE_ORDER (ftype) + != TYPE_REVERSE_STORAGE_ORDER (t)) + warning_at (DECL_SOURCE_LOCATION (field), + OPT_Wscalar_storage_order, + "type punning toggles scalar storage order"); + } } /* Now we have the truly final field list. diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index be3f4f0..daa2e12 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -7295,6 +7295,8 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, && (AGGREGATE_TYPE_P (ttl) && TYPE_REVERSE_STORAGE_ORDER (ttl)) != (AGGREGATE_TYPE_P (ttr) && TYPE_REVERSE_STORAGE_ORDER (ttr))) { + tree t; + switch (errtype) { case ic_argpass: @@ -7307,14 +7309,23 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, "scalar storage order", parmnum, rname); break; case ic_assign: - warning_at (location, OPT_Wscalar_storage_order, - "assignment to %qT from pointer type %qT with " - "incompatible scalar storage order", type, rhstype); + /* Do not warn if the RHS is a call to a function that returns a + pointer that is not an alias. */ + if (TREE_CODE (rhs) != CALL_EXPR + || (t = get_callee_fndecl (rhs)) == NULL_TREE + || !DECL_IS_MALLOC (t)) + warning_at (location, OPT_Wscalar_storage_order, + "assignment to %qT from pointer type %qT with " + "incompatible scalar storage order", type, rhstype); break; case ic_init: - warning_at (location, OPT_Wscalar_storage_order, - "initialization of %qT from pointer type %qT with " - "incompatible scalar storage order", type, rhstype); + /* Likewise. */ + if (TREE_CODE (rhs) != CALL_EXPR + || (t = get_callee_fndecl (rhs)) == NULL_TREE + || !DECL_IS_MALLOC (t)) + warning_at (location, OPT_Wscalar_storage_order, + "initialization of %qT from pointer type %qT with " + "incompatible scalar storage order", type, rhstype); break; case ic_return: warning_at (location, OPT_Wscalar_storage_order, -- cgit v1.1 From 7fa4db39b6bcd207bd2bffff52023ff6b155bd15 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Sun, 6 Jun 2021 19:37:06 +0200 Subject: openmp: Call c_omp_adjust_map_clauses even for combined target [PR100902] When looking at in_reduction support for target, I've noticed that c_omp_adjust_map_clauses is not called for the combined target case. The following patch fixes it. Unfortunately, there are other issues. One is (also mentioned in the PR) that currently the pointer attachment stuff seems to be clause ordering dependent (the standard says that clause ordering on the same construct does not matter), the baz and qux cases in the PR are rejected while when swapped it is accepted. Note, the order of clauses in GCC really is treated as insignificant initially and only later on the compiler can adjust the ordering (e.g. when we sort map clauses based on what they refer to etc.) and in particular, clauses from parsing is reverse of the order in user code, while c_omp_split_clauses performed for combined/composite constructs typically reverses that ordering, i.e. makes it follow the user code ordering. And another one is I'm slightly afraid c_omp_adjust_map_clauses might misbehave in templates, though haven't tried to verify it with testcases. When processing_template_decl, the non-dependent clauses will be handled usually the same as when not in a template, but dependent clauses aren't processed or only limited processing is done there, and rest is deferred till later. From quick skimming of c_omp_adjust_map_clauses, it seems it might not be very happy about non-processed map clauses that might still have the TREE_LIST representation of array sections, or might not have finalized decls or base decls etc. So, for this I wonder if cp_parser_omp_target (and other cp/parser.c callers of c_omp_adjust_map_clauses) shouldn't call it only if (!processing_template_decl) - perhaps you could add cp_omp_adjust_map_clauses wrapper that would be if (!processing_template_decl) c_omp_adjust_map_clauses (...); - and call c_omp_adjust_map_clauses from within pt.c after the clauses are tsubsted and finish_omp_clauses is called again. 2021-06-06 Jakub Jelinek PR c/100902 * c-parser.c (c_parser_omp_target): Call c_omp_adjust_map_clauses even when target is combined with other constructs. * parser.c (cp_parser_omp_target): Call c_omp_adjust_map_clauses even when target is combined with other constructs. * c-c++-common/gomp/pr100902-1.c: New test. --- gcc/c/c-parser.c | 1 + 1 file changed, 1 insertion(+) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index c491b12..add3353 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -20133,6 +20133,7 @@ c_parser_omp_target (c_parser *parser, enum pragma_context context, bool *if_p) tree stmt = make_node (OMP_TARGET); TREE_TYPE (stmt) = void_type_node; OMP_TARGET_CLAUSES (stmt) = cclauses[C_OMP_CLAUSE_SPLIT_TARGET]; + c_omp_adjust_map_clauses (OMP_TARGET_CLAUSES (stmt), true); OMP_TARGET_BODY (stmt) = block; OMP_TARGET_COMBINED (stmt) = 1; SET_EXPR_LOCATION (stmt, loc); -- cgit v1.1 From 7d6987e90d1181de8dc51f9ba2313052faea080e Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Mon, 7 Jun 2021 00:16:23 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 747f53f..ff665e3 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,17 @@ +2021-06-06 Jakub Jelinek + + PR c/100902 + * c-parser.c (c_parser_omp_target): Call c_omp_adjust_map_clauses + even when target is combined with other constructs. + +2021-06-06 Eric Botcazou + + PR c/100920 + * c-decl.c (finish_struct): Fix thinko in previous change. + * c-typeck.c (convert_for_assignment): Do not warn on pointer + assignment and initialization for storage order purposes if the + RHS is a call to a DECL_IS_MALLOC function. + 2021-06-04 Martin Sebor PR c/100783 -- cgit v1.1 From 97d83259b91fb558f5b09bfb09529900f585c4c9 Mon Sep 17 00:00:00 2001 From: Eric Botcazou Date: Mon, 7 Jun 2021 18:17:31 +0200 Subject: Fix old thinko in warning on pointer for storage order purposes gcc/c PR c/100920 * c-typeck.c (convert_for_assignment): Test fndecl_built_in_p to spot built-in functions. gcc/testsuite/ * gcc.dg/sso-14.c: Adjust. --- gcc/c/c-typeck.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index daa2e12..845d50f 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -7303,7 +7303,7 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, /* Do not warn for built-in functions, for example memcpy, since we control how they behave and they can be useful in this area. */ if (TREE_CODE (rname) != FUNCTION_DECL - || !DECL_IS_UNDECLARED_BUILTIN (rname)) + || !fndecl_built_in_p (rname)) warning_at (location, OPT_Wscalar_storage_order, "passing argument %d of %qE from incompatible " "scalar storage order", parmnum, rname); -- cgit v1.1 From 438aac594e1c5ad32b787e8753b3893044ecf26f Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 8 Jun 2021 00:16:44 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index ff665e3..27f8838 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-06-07 Eric Botcazou + + PR c/100920 + * c-typeck.c (convert_for_assignment): Test fndecl_built_in_p to + spot built-in functions. + 2021-06-06 Jakub Jelinek PR c/100902 -- cgit v1.1 From 12d13cf50fe68c898ee65d71d1ba9cdb3ea07996 Mon Sep 17 00:00:00 2001 From: Tobias Burnus Date: Mon, 14 Jun 2021 16:49:24 +0200 Subject: C/C++: Fix unused set var warning with omp_clause_affinity [PR100913] PR c/100913 gcc/c/ChangeLog: * c-parser.c (c_parser_omp_clause_affinity): No need to set iterator var in the error case. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_clause_affinity): No need to set iterator var in the error case. --- gcc/c/c-parser.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index add3353..b90710c 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -15596,9 +15596,7 @@ c_parser_omp_clause_affinity (c_parser *parser, tree list) if (iterators) { tree block = pop_scope (); - if (iterators == error_mark_node) - iterators = NULL_TREE; - else + if (iterators != error_mark_node) { TREE_VEC_ELT (iterators, 5) = block; for (tree c = nl; c != list; c = OMP_CLAUSE_CHAIN (c)) -- cgit v1.1 From 8dc48181affa1d03ec8d47e513d1c62bd16da6f3 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 15 Jun 2021 00:16:37 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 27f8838..665fcd8 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-06-14 Tobias Burnus + + PR c/100913 + * c-parser.c (c_parser_omp_clause_affinity): No need to set iterator + var in the error case. + 2021-06-07 Eric Botcazou PR c/100920 -- cgit v1.1 From ba2eef033e59d80fde35d0cc3acf4d82f7706e60 Mon Sep 17 00:00:00 2001 From: Robin Dapp Date: Tue, 15 Jun 2021 09:06:02 +0200 Subject: c-family: Copy DECL_USER_ALIGN even if DECL_ALIGN is similar. When re-declaring a function with differing attributes DECL_USER_ALIGN is usually not merged/copied when DECL_ALIGN is similar. On s390 this will cause a warning message not to be shown. Similarly, we warned about the wrong alignment when short-circuiting an alignment initialization in common_handle_aligned_attribute (). Fix this by copying DECL_USER_ALIGN even if DECL_ALIGN is similar as well as getting rid of the short-circuited initialization. gcc/c-family/ChangeLog: * c-attribs.c (common_handle_aligned_attribute): Remove short circuit and dead code. gcc/c/ChangeLog: * c-decl.c (merge_decls): Copy DECL_USER_ALIGN if DECL_ALIGN is similar. gcc/cp/ChangeLog: * decl.c (duplicate_decls): Likewise. --- gcc/c/c-decl.c | 3 +++ 1 file changed, 3 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index a86792b..7cd13a5 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -2620,6 +2620,9 @@ merge_decls (tree newdecl, tree olddecl, tree newtype, tree oldtype) SET_DECL_ALIGN (newdecl, DECL_ALIGN (olddecl)); DECL_USER_ALIGN (newdecl) |= DECL_USER_ALIGN (olddecl); } + else if (DECL_ALIGN (olddecl) == DECL_ALIGN (newdecl) + && DECL_USER_ALIGN (olddecl) != DECL_USER_ALIGN (newdecl)) + DECL_USER_ALIGN (newdecl) = 1; if (DECL_WARN_IF_NOT_ALIGN (olddecl) > DECL_WARN_IF_NOT_ALIGN (newdecl)) SET_DECL_WARN_IF_NOT_ALIGN (newdecl, -- cgit v1.1 From ede6c3568f383f62df7bf9234212ee80763fdf6b Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 16 Jun 2021 00:17:05 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 665fcd8..2deedba 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-06-15 Robin Dapp + + * c-decl.c (merge_decls): Copy DECL_USER_ALIGN if DECL_ALIGN is + similar. + 2021-06-14 Tobias Burnus PR c/100913 -- cgit v1.1 From 644c2cc5f2c09506a7bfef293a7f90efa8d7e5fa Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Mon, 21 Jun 2021 13:30:42 +0200 Subject: inline-asm: Fix ICE with bitfields in "m" operands [PR100785] Bitfields, while they live in memory, aren't something inline-asm can easily operate on. For C and "=m" or "+m", we were diagnosing bitfields in the past in the FE, where c_mark_addressable had: case COMPONENT_REF: if (DECL_C_BIT_FIELD (TREE_OPERAND (x, 1))) { error ("cannot take address of bit-field %qD", TREE_OPERAND (x, 1)); return false; } but that check got moved in GCC 6 to build_unary_op instead and now we emit an error during expansion and ICE afterwards (i.e. error-recovery). For "m" it used to be diagnosed in c_mark_addressable too, but since GCC 6 it is ice-on-invalid. For C++, this was never diagnosed in the FE, but used to be diagnosed in the gimplifier and/or during expansion before 4.8. The following patch does multiple things: 1) diagnoses it in the FEs 2) stops emitting a redundant diagnostic in the gimplifier using the usual way, if we already see error_mark_node, we assume error has been emitted already and only diagnose if it wasn't error_mark_node; this helps diagnosing the same bug with multiple different errors 3) simplifies during expansion the inline asm if any errors have been reported (similarly how e.g. vregs pass if it detects errors on inline-asm either deletes them or simplifies to bare minimum - just labels), so that we don't have error-recovery ICEs there 2021-06-11 Jakub Jelinek PR inline-asm/100785 gcc/ * gimplify.c (gimplify_asm_expr): Don't diagnose errors if output or input operands were already error_mark_node. * cfgexpand.c (expand_asm_stmt): If errors are emitted, remove all inputs, outputs and clobbers from the asm and set template to "". gcc/c/ * c-typeck.c (c_mark_addressable): Diagnose trying to make bit-fields addressable. gcc/cp/ * typeck.c (cxx_mark_addressable): Diagnose trying to make bit-fields addressable. gcc/testsuite/ * c-c++-common/pr100785.c: New test. * gcc.dg/pr48552-1.c: Don't expect invalid lvalue errors. * gcc.dg/pr48552-2.c: Likewise. --- gcc/c/c-typeck.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 845d50f..77de881 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -5034,8 +5034,17 @@ c_mark_addressable (tree exp, bool array_ref_p) && TREE_CODE (TREE_TYPE (x)) == ARRAY_TYPE && VECTOR_TYPE_P (TREE_TYPE (TREE_OPERAND (x, 0)))) return true; - /* FALLTHRU */ + x = TREE_OPERAND (x, 0); + break; + case COMPONENT_REF: + if (DECL_C_BIT_FIELD (TREE_OPERAND (x, 1))) + { + error ("cannot take address of bit-field %qD", + TREE_OPERAND (x, 1)); + return false; + } + /* FALLTHRU */ case ADDR_EXPR: case ARRAY_REF: case REALPART_EXPR: -- cgit v1.1 From 2f080224cfa9de0e215324c6ac242d6ee3f27172 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 22 Jun 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 2deedba..5751a37 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-06-21 Jakub Jelinek + + PR inline-asm/100785 + * c-typeck.c (c_mark_addressable): Diagnose trying to make + bit-fields addressable. + 2021-06-15 Robin Dapp * c-decl.c (merge_decls): Copy DECL_USER_ALIGN if DECL_ALIGN is -- cgit v1.1 From 7619d33471c10fe3d149dcbb701d99ed3dd23528 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 24 Jun 2021 11:25:34 +0200 Subject: openmp: in_reduction clause support on target construct This patch adds support for in_reduction clause on target construct, though for now only for synchronous targets (without nowait clause). The encountering thread in that case runs the target task and blocks until the target region ends, so it is implemented by remapping it before entering the target, initializing the private copy if not yet initialized for the current thread and then using the remapped addresses for the mapping addresses. For nowait combined with in_reduction the patch contains a hack where the nowait clause is ignored. To implement it correctly, I think we would need to create a new private variable for the in_reduction and initialize it before doing the async target and adjust the map addresses to that private variable and then pass a function pointer to the library routine with code where the callback would remap the address to the current threads private variable and use in_reduction combiner to combine the private variable we've created into the thread's copy. The library would then need to make sure that the routine is called in some thread participating in the parallel (and not in an unshackeled thread). 2021-06-24 Jakub Jelinek gcc/ * tree.h (OMP_CLAUSE_MAP_IN_REDUCTION): Document meaning for OpenMP. * gimplify.c (gimplify_scan_omp_clauses): For OpenMP map clauses with OMP_CLAUSE_MAP_IN_REDUCTION flag partially defer gimplification of non-decl OMP_CLAUSE_DECL. For OMP_CLAUSE_IN_REDUCTION on OMP_TARGET user outer_ctx instead of ctx for placeholders and initializer/combiner gimplification. * omp-low.c (scan_sharing_clauses): Handle OMP_CLAUSE_MAP_IN_REDUCTION on target constructs. (lower_rec_input_clauses): Likewise. (lower_omp_target): Likewise. * omp-expand.c (expand_omp_target): Temporarily ignore nowait clause on target if in_reduction is present. gcc/c-family/ * c-common.h (enum c_omp_region_type): Add C_ORT_TARGET and C_ORT_OMP_TARGET. * c-omp.c (c_omp_split_clauses): For OMP_CLAUSE_IN_REDUCTION on combined target constructs also add map (always, tofrom:) clause. gcc/c/ * c-parser.c (omp_split_clauses): Pass C_ORT_OMP_TARGET instead of C_ORT_OMP for clauses on target construct. (OMP_TARGET_CLAUSE_MASK): Add in_reduction clause. (c_parser_omp_target): For non-combined target add map (always, tofrom:) clauses for OMP_CLAUSE_IN_REDUCTION. Pass C_ORT_OMP_TARGET to c_finish_omp_clauses. * c-typeck.c (handle_omp_array_sections): Adjust ort handling for addition of C_ORT_OMP_TARGET and simplify, mapping clauses are never present on C_ORT_*DECLARE_SIMD. (c_finish_omp_clauses): Likewise. Handle OMP_CLAUSE_IN_REDUCTION on C_ORT_OMP_TARGET, set OMP_CLAUSE_MAP_IN_REDUCTION on corresponding map clauses. gcc/cp/ * parser.c (cp_omp_split_clauses): Pass C_ORT_OMP_TARGET instead of C_ORT_OMP for clauses on target construct. (OMP_TARGET_CLAUSE_MASK): Add in_reduction clause. (cp_parser_omp_target): For non-combined target add map (always, tofrom:) clauses for OMP_CLAUSE_IN_REDUCTION. Pass C_ORT_OMP_TARGET to finish_omp_clauses. * semantics.c (handle_omp_array_sections_1): Adjust ort handling for addition of C_ORT_OMP_TARGET and simplify, mapping clauses are never present on C_ORT_*DECLARE_SIMD. (handle_omp_array_sections): Likewise. (finish_omp_clauses): Likewise. Handle OMP_CLAUSE_IN_REDUCTION on C_ORT_OMP_TARGET, set OMP_CLAUSE_MAP_IN_REDUCTION on corresponding map clauses. * pt.c (tsubst_expr): Pass C_ORT_OMP_TARGET instead of C_ORT_OMP for clauses on target construct. gcc/testsuite/ * c-c++-common/gomp/target-in-reduction-1.c: New test. * c-c++-common/gomp/clauses-1.c: Add in_reduction clauses on target or combined target constructs. libgomp/ * testsuite/libgomp.c-c++-common/target-in-reduction-1.c: New test. * testsuite/libgomp.c-c++-common/target-in-reduction-2.c: New test. * testsuite/libgomp.c++/target-in-reduction-1.C: New test. * testsuite/libgomp.c++/target-in-reduction-2.C: New test. --- gcc/c/c-parser.c | 18 ++++++++- gcc/c/c-typeck.c | 109 +++++++++++++++++++++++++++++++++++-------------------- 2 files changed, 85 insertions(+), 42 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index b90710c..c0f7020 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -18701,7 +18701,9 @@ omp_split_clauses (location_t loc, enum tree_code code, c_omp_split_clauses (loc, code, mask, clauses, cclauses); for (i = 0; i < C_OMP_CLAUSE_SPLIT_COUNT; i++) if (cclauses[i]) - cclauses[i] = c_finish_omp_clauses (cclauses[i], C_ORT_OMP); + cclauses[i] = c_finish_omp_clauses (cclauses[i], + i == C_OMP_CLAUSE_SPLIT_TARGET + ? C_ORT_OMP_TARGET : C_ORT_OMP); } /* OpenMP 5.0: @@ -20013,6 +20015,7 @@ c_parser_omp_target_exit_data (location_t loc, c_parser *parser, | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ALLOCATE) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULTMAP) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IN_REDUCTION) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR)) static bool @@ -20179,7 +20182,18 @@ c_parser_omp_target (c_parser *parser, enum pragma_context context, bool *if_p) OMP_TARGET_CLAUSES (stmt) = c_parser_omp_all_clauses (parser, OMP_TARGET_CLAUSE_MASK, - "#pragma omp target"); + "#pragma omp target", false); + for (tree c = OMP_TARGET_CLAUSES (stmt); c; c = OMP_CLAUSE_CHAIN (c)) + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION) + { + tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_MAP); + OMP_CLAUSE_DECL (nc) = OMP_CLAUSE_DECL (c); + OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_ALWAYS_TOFROM); + OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (c); + OMP_CLAUSE_CHAIN (c) = nc; + } + OMP_TARGET_CLAUSES (stmt) + = c_finish_omp_clauses (OMP_TARGET_CLAUSES (stmt), C_ORT_OMP_TARGET); c_omp_adjust_map_clauses (OMP_TARGET_CLAUSES (stmt), true); pc = &OMP_TARGET_CLAUSES (stmt); diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 77de881..d0d36c3 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -13648,32 +13648,29 @@ handle_omp_array_sections (tree c, enum c_omp_region_type ort) && TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)) return false; gcc_assert (OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FORCE_DEVICEPTR); - if (ort == C_ORT_OMP || ort == C_ORT_ACC) - switch (OMP_CLAUSE_MAP_KIND (c)) - { - case GOMP_MAP_ALLOC: - case GOMP_MAP_IF_PRESENT: - case GOMP_MAP_TO: - case GOMP_MAP_FROM: - case GOMP_MAP_TOFROM: - case GOMP_MAP_ALWAYS_TO: - case GOMP_MAP_ALWAYS_FROM: - case GOMP_MAP_ALWAYS_TOFROM: - case GOMP_MAP_RELEASE: - case GOMP_MAP_DELETE: - case GOMP_MAP_FORCE_TO: - case GOMP_MAP_FORCE_FROM: - case GOMP_MAP_FORCE_TOFROM: - case GOMP_MAP_FORCE_PRESENT: - OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1; - break; - default: - break; - } + switch (OMP_CLAUSE_MAP_KIND (c)) + { + case GOMP_MAP_ALLOC: + case GOMP_MAP_IF_PRESENT: + case GOMP_MAP_TO: + case GOMP_MAP_FROM: + case GOMP_MAP_TOFROM: + case GOMP_MAP_ALWAYS_TO: + case GOMP_MAP_ALWAYS_FROM: + case GOMP_MAP_ALWAYS_TOFROM: + case GOMP_MAP_RELEASE: + case GOMP_MAP_DELETE: + case GOMP_MAP_FORCE_TO: + case GOMP_MAP_FORCE_FROM: + case GOMP_MAP_FORCE_TOFROM: + case GOMP_MAP_FORCE_PRESENT: + OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1; + break; + default: + break; + } tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_MAP); - if (ort != C_ORT_OMP && ort != C_ORT_ACC) - OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_POINTER); - else if (TREE_CODE (t) == COMPONENT_REF) + if (TREE_CODE (t) == COMPONENT_REF) OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_ATTACH_DETACH); else OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_FIRSTPRIVATE_POINTER); @@ -13970,6 +13967,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) int reduction_seen = 0; bool allocate_seen = false; bool implicit_moved = false; + bool target_in_reduction_seen = false; bitmap_obstack_initialize (NULL); bitmap_initialize (&generic_head, &bitmap_default_obstack); @@ -13981,7 +13979,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) bitmap_initialize (&map_field_head, &bitmap_default_obstack); bitmap_initialize (&map_firstprivate_head, &bitmap_default_obstack); /* If ort == C_ORT_OMP used as nontemporal_head or use_device_xxx_head - instead. */ + instead and for ort == C_ORT_OMP_TARGET used as in_reduction_head. */ bitmap_initialize (&oacc_reduction_head, &bitmap_default_obstack); if (ort & C_ORT_ACC) @@ -14374,8 +14372,22 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) || (ort == C_ORT_OMP && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR || (OMP_CLAUSE_CODE (c) - == OMP_CLAUSE_USE_DEVICE_ADDR)))) + == OMP_CLAUSE_USE_DEVICE_ADDR))) + || (ort == C_ORT_OMP_TARGET + && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION)) { + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION + && (bitmap_bit_p (&generic_head, DECL_UID (t)) + || bitmap_bit_p (&firstprivate_head, DECL_UID (t)))) + { + error_at (OMP_CLAUSE_LOCATION (c), + "%qD appears more than once in data-sharing " + "clauses", t); + remove = true; + break; + } + if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION) + target_in_reduction_seen = true; if (bitmap_bit_p (&oacc_reduction_head, DECL_UID (t))) { error_at (OMP_CLAUSE_LOCATION (c), @@ -14390,7 +14402,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) } else if (bitmap_bit_p (&generic_head, DECL_UID (t)) || bitmap_bit_p (&firstprivate_head, DECL_UID (t)) - || bitmap_bit_p (&lastprivate_head, DECL_UID (t))) + || bitmap_bit_p (&lastprivate_head, DECL_UID (t)) + || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%qE appears more than once in data clauses", t); @@ -14457,7 +14470,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) && bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))) remove = true; else if (bitmap_bit_p (&generic_head, DECL_UID (t)) - || bitmap_bit_p (&firstprivate_head, DECL_UID (t))) + || bitmap_bit_p (&firstprivate_head, DECL_UID (t)) + || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%qE appears more than once in data clauses", t); @@ -14861,7 +14875,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) if (VAR_P (t) || TREE_CODE (t) == PARM_DECL) { if (bitmap_bit_p (&map_field_head, DECL_UID (t)) - || (ort == C_ORT_OMP + || (ort != C_ORT_ACC && bitmap_bit_p (&map_head, DECL_UID (t)))) break; } @@ -14918,7 +14932,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER) { if (bitmap_bit_p (&generic_head, DECL_UID (t)) - || bitmap_bit_p (&firstprivate_head, DECL_UID (t))) + || bitmap_bit_p (&firstprivate_head, DECL_UID (t)) + || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%qD appears more than once in data clauses", t); @@ -14935,13 +14950,10 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) remove = true; } else - { - bitmap_set_bit (&generic_head, DECL_UID (t)); - bitmap_set_bit (&map_firstprivate_head, DECL_UID (t)); - } + bitmap_set_bit (&map_firstprivate_head, DECL_UID (t)); } else if (bitmap_bit_p (&map_head, DECL_UID (t)) - && (ort != C_ORT_OMP + && (ort == C_ORT_ACC || !bitmap_bit_p (&map_field_head, DECL_UID (t)))) { if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP) @@ -14955,8 +14967,8 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) "%qD appears more than once in map clauses", t); remove = true; } - else if (bitmap_bit_p (&generic_head, DECL_UID (t)) - && ort == C_ORT_ACC) + else if (ort == C_ORT_ACC + && bitmap_bit_p (&generic_head, DECL_UID (t))) { error_at (OMP_CLAUSE_LOCATION (c), "%qD appears more than once in data clauses", t); @@ -15050,7 +15062,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) if (TREE_CODE (TREE_TYPE (t)) != POINTER_TYPE) { if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR - && ort == C_ORT_OMP) + && ort != C_ORT_ACC) { error_at (OMP_CLAUSE_LOCATION (c), "%qs variable is not a pointer", @@ -15335,7 +15347,10 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) reduction_seen = -2; } - if (linear_variable_step_check || reduction_seen == -2 || allocate_seen) + if (linear_variable_step_check + || reduction_seen == -2 + || allocate_seen + || target_in_reduction_seen) for (pc = &clauses, c = clauses; c ; c = *pc) { bool remove = false; @@ -15383,6 +15398,20 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION && reduction_seen == -2) OMP_CLAUSE_REDUCTION_INSCAN (c) = 0; + if (target_in_reduction_seen + && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP) + { + tree t = OMP_CLAUSE_DECL (c); + while (handled_component_p (t) + || TREE_CODE (t) == INDIRECT_REF + || TREE_CODE (t) == ADDR_EXPR + || TREE_CODE (t) == MEM_REF + || TREE_CODE (t) == NON_LVALUE_EXPR) + t = TREE_OPERAND (t, 0); + if (DECL_P (t) + && bitmap_bit_p (&oacc_reduction_head, DECL_UID (t))) + OMP_CLAUSE_MAP_IN_REDUCTION (c) = 1; + } if (remove) *pc = OMP_CLAUSE_CHAIN (c); -- cgit v1.1 From fdc5522fb04b4a820b28c4d1f16f54897f5978de Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 24 Jun 2021 15:55:28 +0200 Subject: c: Fix C cast error-recovery [PR101171] The following testcase ICEs during error-recovery, as build_c_cast calls note_integer_operands on error_mark_node and that wraps it into C_MAYBE_CONST_EXPR which is unexpected and causes ICE later on. Seems most other callers of note_integer_operands check early if something is error_mark_node and return before calling note_integer_operands on it. The following patch fixes it by not calling on error_mark_node, another possibility would be to handle error_mark_node in note_integer_operands and just return it. 2021-06-24 Jakub Jelinek PR c/101171 * c-typeck.c (build_c_cast): Don't call note_integer_operands on error_mark_node. * gcc.dg/pr101171.c: New test. --- gcc/c/c-typeck.c | 1 + 1 file changed, 1 insertion(+) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index d0d36c3..d079ce4 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -6131,6 +6131,7 @@ build_c_cast (location_t loc, tree type, tree expr) return value reflects this. */ if (int_operands && INTEGRAL_TYPE_P (type) + && value != error_mark_node && !EXPR_INT_CONST_OPERANDS (value)) value = note_integer_operands (value); -- cgit v1.1 From 178fb8df9315f2f8f45b7fe5faf11a9c2912cc28 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 24 Jun 2021 15:58:02 +0200 Subject: c: Fix up c_parser_has_attribute_expression [PR101176] This function keeps src_range member of the result uninitialized, which at least under valgrind can show up later when those uninitialized location_t's can make it into the IL or location_t hash tables. 2021-06-24 Jakub Jelinek PR c/101176 * c-parser.c (c_parser_has_attribute_expression): Set source range for the result. --- gcc/c/c-parser.c | 3 +++ 1 file changed, 3 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index c0f7020..27034f8 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -8406,6 +8406,7 @@ c_parser_has_attribute_expression (c_parser *parser) { gcc_assert (c_parser_next_token_is_keyword (parser, RID_BUILTIN_HAS_ATTRIBUTE)); + location_t start = c_parser_peek_token (parser)->location; c_parser_consume_token (parser); c_inhibit_evaluation_warnings++; @@ -8484,6 +8485,7 @@ c_parser_has_attribute_expression (c_parser *parser) parser->translate_strings_p = save_translate_strings_p; + location_t finish = c_parser_peek_token (parser)->location; if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN)) c_parser_consume_token (parser); else @@ -8512,6 +8514,7 @@ c_parser_has_attribute_expression (c_parser *parser) else result.value = boolean_false_node; + set_c_expr_source_range (&result, start, finish); return result; } -- cgit v1.1 From 9aa8327e86eba9a5ad6dacb4db505e3451854976 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 25 Jun 2021 00:16:53 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 5751a37..c38b665 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,30 @@ +2021-06-24 Jakub Jelinek + + PR c/101176 + * c-parser.c (c_parser_has_attribute_expression): Set source range for + the result. + +2021-06-24 Jakub Jelinek + + PR c/101171 + * c-typeck.c (build_c_cast): Don't call note_integer_operands on + error_mark_node. + +2021-06-24 Jakub Jelinek + + * c-parser.c (omp_split_clauses): Pass C_ORT_OMP_TARGET instead of + C_ORT_OMP for clauses on target construct. + (OMP_TARGET_CLAUSE_MASK): Add in_reduction clause. + (c_parser_omp_target): For non-combined target add + map (always, tofrom:) clauses for OMP_CLAUSE_IN_REDUCTION. Pass + C_ORT_OMP_TARGET to c_finish_omp_clauses. + * c-typeck.c (handle_omp_array_sections): Adjust ort handling + for addition of C_ORT_OMP_TARGET and simplify, mapping clauses are + never present on C_ORT_*DECLARE_SIMD. + (c_finish_omp_clauses): Likewise. Handle OMP_CLAUSE_IN_REDUCTION + on C_ORT_OMP_TARGET, set OMP_CLAUSE_MAP_IN_REDUCTION on + corresponding map clauses. + 2021-06-21 Jakub Jelinek PR inline-asm/100785 -- cgit v1.1 From 1ebd2b2c9407796cd526137038b9b885f68ffb4d Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Thu, 24 Jun 2021 15:35:20 -0600 Subject: c: add support for per-location warning groups. gcc/ChangeLog: * tree.h (warning_suppressed_at, copy_warning, warning_suppressed_p, suppress_warning): New functions. gcc/c/ChangeLog: * c-decl.c (pop_scope): Replace direct uses of TREE_NO_WARNING with warning_suppressed_p, suppress_warning, and copy_no_warning. (diagnose_mismatched_decls): Same. (duplicate_decls): Same. (grokdeclarator): Same. (finish_function): Same. (c_write_global_declarations_1): Same. * c-fold.c (c_fully_fold_internal): Same. * c-parser.c (c_parser_expr_no_commas): Same. (c_parser_postfix_expression): Same. * c-typeck.c (array_to_pointer_conversion): Same. (function_to_pointer_conversion): Same. (default_function_array_conversion): Same. (convert_lvalue_to_rvalue): Same. (default_conversion): Same. (build_indirect_ref): Same. (build_function_call_vec): Same. (build_atomic_assign): Same. (build_unary_op): Same. (c_finish_return): Same. (emit_side_effect_warnings): Same. (c_finish_stmt_expr): Same. (c_omp_clause_copy_ctor): Same. --- gcc/c/c-decl.c | 24 +++++++++++------------- gcc/c/c-fold.c | 8 ++++---- gcc/c/c-parser.c | 4 ++-- gcc/c/c-typeck.c | 43 ++++++++++++++++++++----------------------- 4 files changed, 37 insertions(+), 42 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 7cd13a5..983d65e 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -1295,7 +1295,7 @@ pop_scope (void) case VAR_DECL: /* Warnings for unused variables. */ if ((!TREE_USED (p) || !DECL_READ_P (p)) - && !TREE_NO_WARNING (p) + && !warning_suppressed_p (p, OPT_Wunused_but_set_variable) && !DECL_IN_SYSTEM_HEADER (p) && DECL_NAME (p) && !DECL_ARTIFICIAL (p) @@ -2159,8 +2159,8 @@ diagnose_mismatched_decls (tree newdecl, tree olddecl, if (DECL_IN_SYSTEM_HEADER (newdecl) || DECL_IN_SYSTEM_HEADER (olddecl) - || TREE_NO_WARNING (newdecl) - || TREE_NO_WARNING (olddecl)) + || warning_suppressed_p (newdecl, OPT_Wpedantic) + || warning_suppressed_p (olddecl, OPT_Wpedantic)) return true; /* Allow OLDDECL to continue in use. */ if (variably_modified_type_p (newtype, NULL)) @@ -2956,7 +2956,7 @@ duplicate_decls (tree newdecl, tree olddecl) if (!diagnose_mismatched_decls (newdecl, olddecl, &newtype, &oldtype)) { /* Avoid `unused variable' and other warnings for OLDDECL. */ - TREE_NO_WARNING (olddecl) = 1; + suppress_warning (olddecl, OPT_Wunused); return false; } @@ -7543,10 +7543,7 @@ grokdeclarator (const struct c_declarator *declarator, FIELD_DECL, declarator->u.id.id, type); DECL_NONADDRESSABLE_P (decl) = bitfield; if (bitfield && !declarator->u.id.id) - { - TREE_NO_WARNING (decl) = 1; - DECL_PADDING_P (decl) = 1; - } + DECL_PADDING_P (decl) = 1; if (size_varies) C_DECL_VARIABLE_SIZE (decl) = 1; @@ -10244,7 +10241,7 @@ finish_function (location_t end_loc) && targetm.warn_func_return (fndecl) && warning (OPT_Wreturn_type, "no return statement in function returning non-void")) - TREE_NO_WARNING (fndecl) = 1; + suppress_warning (fndecl, OPT_Wreturn_type); /* Complain about parameters that are only set, but never otherwise used. */ if (warn_unused_but_set_parameter) @@ -10259,7 +10256,7 @@ finish_function (location_t end_loc) && !DECL_READ_P (decl) && DECL_NAME (decl) && !DECL_ARTIFICIAL (decl) - && !TREE_NO_WARNING (decl)) + && !warning_suppressed_p (decl, OPT_Wunused_but_set_parameter)) warning_at (DECL_SOURCE_LOCATION (decl), OPT_Wunused_but_set_parameter, "parameter %qD set but not used", decl); @@ -12126,19 +12123,20 @@ c_write_global_declarations_1 (tree globals) { if (C_DECL_USED (decl)) { + /* TODO: Add OPT_Wundefined-inline. */ if (pedwarn (input_location, 0, "%q+F used but never defined", decl)) - TREE_NO_WARNING (decl) = 1; + suppress_warning (decl /* OPT_Wundefined-inline. */); } /* For -Wunused-function warn about unused static prototypes. */ else if (warn_unused_function && ! DECL_ARTIFICIAL (decl) - && ! TREE_NO_WARNING (decl)) + && ! warning_suppressed_p (decl, OPT_Wunused_function)) { if (warning (OPT_Wunused_function, "%q+F declared % but never defined", decl)) - TREE_NO_WARNING (decl) = 1; + suppress_warning (decl, OPT_Wunused_function); } } diff --git a/gcc/c/c-fold.c b/gcc/c/c-fold.c index 68c74cc..0ebcb46 100644 --- a/gcc/c/c-fold.c +++ b/gcc/c/c-fold.c @@ -154,7 +154,7 @@ c_fully_fold_internal (tree expr, bool in_init, bool *maybe_const_operands, tree orig_op0, orig_op1, orig_op2; bool op0_const = true, op1_const = true, op2_const = true; bool op0_const_self = true, op1_const_self = true, op2_const_self = true; - bool nowarning = TREE_NO_WARNING (expr); + bool nowarning = warning_suppressed_p (expr, OPT_Woverflow); bool unused_p; bool op0_lval = false; source_range old_range; @@ -670,13 +670,13 @@ c_fully_fold_internal (tree expr, bool in_init, bool *maybe_const_operands, out: /* Some folding may introduce NON_LVALUE_EXPRs; all lvalue checks have been done by this point, so remove them again. */ - nowarning |= TREE_NO_WARNING (ret); + nowarning |= warning_suppressed_p (ret, OPT_Woverflow); STRIP_TYPE_NOPS (ret); - if (nowarning && !TREE_NO_WARNING (ret)) + if (nowarning && !warning_suppressed_p (ret, OPT_Woverflow)) { if (!CAN_HAVE_LOCATION_P (ret)) ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret); - TREE_NO_WARNING (ret) = 1; + suppress_warning (ret, OPT_Woverflow); } if (ret != expr) { diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 27034f8..3922b56 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -7558,7 +7558,7 @@ c_parser_expr_no_commas (c_parser *parser, struct c_expr *after, ret.original_code = MODIFY_EXPR; else { - TREE_NO_WARNING (ret.value) = 1; + suppress_warning (ret.value, OPT_Wparentheses); ret.original_code = ERROR_MARK; } ret.original_type = NULL; @@ -9088,7 +9088,7 @@ c_parser_postfix_expression (c_parser *parser) c_parser_consume_token (parser); expr = c_parser_expression (parser); if (TREE_CODE (expr.value) == MODIFY_EXPR) - TREE_NO_WARNING (expr.value) = 1; + suppress_warning (expr.value, OPT_Wparentheses); if (expr.original_code != C_MAYBE_CONST_EXPR && expr.original_code != SIZEOF_EXPR) expr.original_code = ERROR_MARK; diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index d079ce4..5349ef1 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -1911,8 +1911,7 @@ array_to_pointer_conversion (location_t loc, tree exp) STRIP_TYPE_NOPS (exp); - if (TREE_NO_WARNING (orig_exp)) - TREE_NO_WARNING (exp) = 1; + copy_warning (exp, orig_exp); ptrtype = build_pointer_type (restype); @@ -1945,8 +1944,7 @@ function_to_pointer_conversion (location_t loc, tree exp) STRIP_TYPE_NOPS (exp); - if (TREE_NO_WARNING (orig_exp)) - TREE_NO_WARNING (exp) = 1; + copy_warning (exp, orig_exp); return build_unary_op (loc, ADDR_EXPR, exp, false); } @@ -2055,8 +2053,7 @@ default_function_array_conversion (location_t loc, struct c_expr exp) exp.value = TREE_OPERAND (exp.value, 0); } - if (TREE_NO_WARNING (orig_exp)) - TREE_NO_WARNING (exp.value) = 1; + copy_warning (exp.value, orig_exp); lvalue_array_p = !not_lvalue && lvalue_p (exp.value); if (!flag_isoc99 && !lvalue_array_p) @@ -2154,7 +2151,8 @@ convert_lvalue_to_rvalue (location_t loc, struct c_expr exp, tmp = create_tmp_var_raw (nonatomic_type); tmp_addr = build_unary_op (loc, ADDR_EXPR, tmp, false); TREE_ADDRESSABLE (tmp) = 1; - TREE_NO_WARNING (tmp) = 1; + /* Do not disable warnings for TMP even though it's artificial. + -Winvalid-memory-model depends on it. */ /* Issue __atomic_load (&expr, &tmp, SEQ_CST); */ fndecl = builtin_decl_explicit (BUILT_IN_ATOMIC_LOAD); @@ -2251,8 +2249,7 @@ default_conversion (tree exp) orig_exp = exp; STRIP_TYPE_NOPS (exp); - if (TREE_NO_WARNING (orig_exp)) - TREE_NO_WARNING (exp) = 1; + copy_warning (exp, orig_exp); if (code == VOID_TYPE) { @@ -2616,7 +2613,7 @@ build_indirect_ref (location_t loc, tree ptr, ref_operator errstring) if (warn_strict_aliasing > 2) if (strict_aliasing_warning (EXPR_LOCATION (pointer), type, TREE_OPERAND (pointer, 0))) - TREE_NO_WARNING (pointer) = 1; + suppress_warning (pointer, OPT_Wstrict_aliasing_); } if (TREE_CODE (pointer) == ADDR_EXPR @@ -3218,7 +3215,7 @@ build_function_call_vec (location_t loc, vec arg_loc, /* If -Wnonnull warning has been diagnosed, avoid diagnosing it again later. */ if (warned_p && TREE_CODE (result) == CALL_EXPR) - TREE_NO_WARNING (result) = 1; + suppress_warning (result, OPT_Wnonnull); /* In this improbable scenario, a nested function returns a VM type. Create a TARGET_EXPR so that the call always has a LHS, much as @@ -4167,7 +4164,7 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, TYPE_UNQUALIFIED); val = create_tmp_var_raw (nonatomic_rhs_type); TREE_ADDRESSABLE (val) = 1; - TREE_NO_WARNING (val) = 1; + suppress_warning (val); rhs = build4 (TARGET_EXPR, nonatomic_rhs_type, val, rhs, NULL_TREE, NULL_TREE); TREE_SIDE_EFFECTS (rhs) = 1; @@ -4268,7 +4265,7 @@ build_atomic_assign (location_t loc, tree lhs, enum tree_code modifycode, newval = create_tmp_var_raw (nonatomic_lhs_type); TREE_ADDRESSABLE (newval) = 1; - TREE_NO_WARNING (newval) = 1; + suppress_warning (newval); rhs = build4 (TARGET_EXPR, nonatomic_lhs_type, newval, func_call, NULL_TREE, NULL_TREE); SET_EXPR_LOCATION (rhs, loc); @@ -4287,12 +4284,12 @@ cas_loop: old = create_tmp_var_raw (nonatomic_lhs_type); old_addr = build_unary_op (loc, ADDR_EXPR, old, false); TREE_ADDRESSABLE (old) = 1; - TREE_NO_WARNING (old) = 1; + suppress_warning (old); newval = create_tmp_var_raw (nonatomic_lhs_type); newval_addr = build_unary_op (loc, ADDR_EXPR, newval, false); TREE_ADDRESSABLE (newval) = 1; - TREE_NO_WARNING (newval) = 1; + suppress_warning (newval); loop_decl = create_artificial_label (loc); loop_label = build1 (LABEL_EXPR, void_type_node, loop_decl); @@ -4781,8 +4778,6 @@ build_unary_op (location_t location, enum tree_code code, tree xarg, else val = build2 (code, TREE_TYPE (arg), arg, inc); TREE_SIDE_EFFECTS (val) = 1; - if (TREE_CODE (val) != code) - TREE_NO_WARNING (val) = 1; ret = val; goto return_build_unary_op; } @@ -10962,7 +10957,8 @@ c_finish_return (location_t loc, tree retval, tree origtype) } ret_stmt = build_stmt (loc, RETURN_EXPR, retval); - TREE_NO_WARNING (ret_stmt) |= no_warning; + if (no_warning) + suppress_warning (ret_stmt, OPT_Wreturn_type); return add_stmt (ret_stmt); } @@ -11238,7 +11234,8 @@ emit_side_effect_warnings (location_t loc, tree expr) ; else if (!TREE_SIDE_EFFECTS (expr)) { - if (!VOID_TYPE_P (TREE_TYPE (expr)) && !TREE_NO_WARNING (expr)) + if (!VOID_TYPE_P (TREE_TYPE (expr)) + && !warning_suppressed_p (expr, OPT_Wunused_value)) warning_at (loc, OPT_Wunused_value, "statement with no effect"); } else if (TREE_CODE (expr) == COMPOUND_EXPR) @@ -11254,8 +11251,8 @@ emit_side_effect_warnings (location_t loc, tree expr) if (!TREE_SIDE_EFFECTS (r) && !VOID_TYPE_P (TREE_TYPE (r)) && !CONVERT_EXPR_P (r) - && !TREE_NO_WARNING (r) - && !TREE_NO_WARNING (expr)) + && !warning_suppressed_p (r, OPT_Wunused_value) + && !warning_suppressed_p (expr, OPT_Wunused_value)) warning_at (cloc, OPT_Wunused_value, "right-hand operand of comma expression has no effect"); } @@ -11424,7 +11421,7 @@ c_finish_stmt_expr (location_t loc, tree body) last = c_wrap_maybe_const (last, true); /* Do not warn if the return value of a statement expression is unused. */ - TREE_NO_WARNING (last) = 1; + suppress_warning (last, OPT_Wunused); return last; } @@ -15503,7 +15500,7 @@ c_omp_clause_copy_ctor (tree clause, tree dst, tree src) tree tmp = create_tmp_var (nonatomic_type); tree tmp_addr = build_fold_addr_expr (tmp); TREE_ADDRESSABLE (tmp) = 1; - TREE_NO_WARNING (tmp) = 1; + suppress_warning (tmp); tree src_addr = build_fold_addr_expr (src); tree dst_addr = build_fold_addr_expr (dst); tree seq_cst = build_int_cst (integer_type_node, MEMMODEL_SEQ_CST); -- cgit v1.1 From 90708f87b8d13da61f7d5cba7c6597fee0025bb1 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 26 Jun 2021 00:16:39 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index c38b665..ba53da8 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,29 @@ +2021-06-25 Martin Sebor + + * c-decl.c (pop_scope): Replace direct uses of TREE_NO_WARNING with + warning_suppressed_p, suppress_warning, and copy_no_warning. + (diagnose_mismatched_decls): Same. + (duplicate_decls): Same. + (grokdeclarator): Same. + (finish_function): Same. + (c_write_global_declarations_1): Same. + * c-fold.c (c_fully_fold_internal): Same. + * c-parser.c (c_parser_expr_no_commas): Same. + (c_parser_postfix_expression): Same. + * c-typeck.c (array_to_pointer_conversion): Same. + (function_to_pointer_conversion): Same. + (default_function_array_conversion): Same. + (convert_lvalue_to_rvalue): Same. + (default_conversion): Same. + (build_indirect_ref): Same. + (build_function_call_vec): Same. + (build_atomic_assign): Same. + (build_unary_op): Same. + (c_finish_return): Same. + (emit_side_effect_warnings): Same. + (c_finish_stmt_expr): Same. + (c_omp_clause_copy_ctor): Same. + 2021-06-24 Jakub Jelinek PR c/101176 -- cgit v1.1 From 2ca89394280da4afad6074ec3cb7136b6142af7b Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 2 Jul 2021 21:57:24 +0200 Subject: openmp: Reject #pragma omp atomic update, [PR101297] I've noticed that we allow a trailing comma on OpenMP atomic construct if there is at least one clause. Commas should be only allowed to separate the clauses (or in OpenMP 5.1 to separate directive name from the clauses). 2021-07-02 Jakub Jelinek PR c/101297 * c-parser.c (c_parser_omp_atomic): Consume comma only if it appears before a CPP_NAME. * parser.c (cp_parser_omp_atomic): Consume comma only if it appears before a CPP_NAME. * c-c++-common/gomp/atomic-24.c: New test. --- gcc/c/c-parser.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 3922b56..9a56e0c 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -17533,7 +17533,9 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL)) { - if (!first && c_parser_next_token_is (parser, CPP_COMMA)) + if (!first + && c_parser_next_token_is (parser, CPP_COMMA) + && c_parser_peek_2nd_token (parser)->type == CPP_NAME) c_parser_consume_token (parser); first = false; -- cgit v1.1 From 7a60a6e8b36dec960939494baef0f1f15dbfc450 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 3 Jul 2021 00:16:31 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index ba53da8..27d6e89 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-07-02 Jakub Jelinek + + PR c/101297 + * c-parser.c (c_parser_omp_atomic): Consume comma only if it + appears before a CPP_NAME. + 2021-06-25 Martin Sebor * c-decl.c (pop_scope): Replace direct uses of TREE_NO_WARNING with -- cgit v1.1 From 4f6e181181a48c341e524653cae0885fd170131e Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Tue, 6 Jul 2021 14:13:31 -0600 Subject: Remove support for %G and %K. gcc/c-family/ChangeLog: * c-format.c (gcc_tdiag_char_table): Remove support for %G and %K. (gcc_cdiag_char_table): Same. (gcc_cxxdiag_char_table): Same. gcc/c/ChangeLog: * c-objc-common.c (c_tree_printer): Remove support for %G and %K. gcc/cp/ChangeLog: * error.c (cp_printer): Remove support for %G and %K. gcc/ChangeLog: * gimple-pretty-print.c (percent_G_format): Remove. * tree-diagnostic.c (default_tree_printer): Remove calls. * tree-pretty-print.c (percent_K_format): Remove. * tree-pretty-print.h (percent_K_format): Remove. gcc/testsuite/ChangeLog: * gcc.dg/format/gcc_diag-10.c: Update expected warnings. * gcc.dg/plugin/diagnostic_plugin_test_inlining.c: Remove %G. --- gcc/c/c-objc-common.c | 15 --------------- 1 file changed, 15 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-objc-common.c b/gcc/c/c-objc-common.c index b945de1..cdb2242 100644 --- a/gcc/c/c-objc-common.c +++ b/gcc/c/c-objc-common.c @@ -247,8 +247,6 @@ print_type (c_pretty_printer *cpp, tree t, bool *quoted) %D: a general decl, %E: an identifier or expression, %F: a function declaration, - %G: a Gimple statement, - %K: a CALL_EXPR, %T: a type. %V: a list of type qualifiers from a tree. %v: an explicit list of type qualifiers @@ -269,19 +267,6 @@ c_tree_printer (pretty_printer *pp, text_info *text, const char *spec, if (precision != 0 || wide) return false; - if (*spec == 'G') - { - percent_G_format (text); - return true; - } - - if (*spec == 'K') - { - t = va_arg (*text->args_ptr, tree); - percent_K_format (text, EXPR_LOCATION (t), TREE_BLOCK (t)); - return true; - } - if (*spec != 'v') { t = va_arg (*text->args_ptr, tree); -- cgit v1.1 From 6fba0eea8d6464966ac6d37af98a7487a9a03d19 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 7 Jul 2021 00:17:12 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 27d6e89..ef6f4ad 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,7 @@ +2021-07-06 Martin Sebor + + * c-objc-common.c (c_tree_printer): Remove support for %G and %K. + 2021-07-02 Jakub Jelinek PR c/101297 -- cgit v1.1 From 98f1f9f38c45218c06200feb1939c9433a2ab6ca Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Thu, 15 Jul 2021 10:11:23 -0600 Subject: Avoid -Wvla-parameter for nontrivial bounds [PR97548]. Resolves: PR c/101289 - bogus -Wvla-paramater warning when using const for vla param PR c/97548 - bogus -Wvla-parameter on a bound expression involving a parameter gcc/c-family/ChangeLog: PR c/101289 PR c/97548 * c-warn.c (warn_parm_array_mismatch): Use OEP_DECL_NAME. gcc/c/ChangeLog: PR c/101289 PR c/97548 * c-decl.c (get_parm_array_spec): Strip nops. gcc/ChangeLog: PR c/101289 PR c/97548 * fold-const.c (operand_compare::operand_equal_p): Handle OEP_DECL_NAME. (operand_compare::verify_hash_value): Same. * tree-core.h (OEP_DECL_NAME): New. gcc/testsuite/ChangeLog: * gcc.dg/Wvla-parameter-12.c: New test. --- gcc/c/c-decl.c | 1 + 1 file changed, 1 insertion(+) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 983d65e..234ee16 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -5865,6 +5865,7 @@ get_parm_array_spec (const struct c_parm *parm, tree attrs) /* Each variable VLA bound is represented by a dollar sign. */ spec += "$"; + STRIP_NOPS (nelts); vbchain = tree_cons (NULL_TREE, nelts, vbchain); } -- cgit v1.1 From d97d71a1989e9ee8e1b8563b351c42b7732da108 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 16 Jul 2021 00:16:25 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index ef6f4ad..a190806 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-07-15 Martin Sebor + + PR c/101289 + PR c/97548 + * c-decl.c (get_parm_array_spec): Strip nops. + 2021-07-06 Martin Sebor * c-objc-common.c (c_tree_printer): Remove support for %G and %K. -- cgit v1.1 From 00dcc88a0ed7bd148ea86d900b6c93574a2e1f26 Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Tue, 20 Jul 2021 11:14:19 -0600 Subject: Adjust by-value function vec arguments to by-reference. gcc/c-family/ChangeLog: * c-common.c (c_build_shufflevector): Adjust by-value argument to by-const-reference. * c-common.h (c_build_shufflevector): Same. gcc/c/ChangeLog: * c-tree.h (c_build_function_call_vec): Adjust by-value argument to by-const-reference. * c-typeck.c (c_build_function_call_vec): Same. gcc/ChangeLog: * cfgloop.h (single_likely_exit): Adjust by-value argument to by-const-reference. * cfgloopanal.c (single_likely_exit): Same. * cgraph.h (struct cgraph_node): Same. * cgraphclones.c (cgraph_node::create_virtual_clone): Same. * genautomata.c (merge_states): Same. * genextract.c (VEC_char_to_string): Same. * genmatch.c (dt_node::gen_kids_1): Same. (walk_captures): Adjust by-value argument to by-reference. * gimple-ssa-store-merging.c (check_no_overlap): Adjust by-value argument to by-const-reference. * gimple.c (gimple_build_call_vec): Same. (gimple_build_call_internal_vec): Same. (gimple_build_switch): Same. (sort_case_labels): Same. (preprocess_case_label_vec_for_gimple): Adjust by-value argument to by-reference. * gimple.h (gimple_build_call_vec): Adjust by-value argument to by-const-reference. (gimple_build_call_internal_vec): Same. (gimple_build_switch): Same. (sort_case_labels): Same. (preprocess_case_label_vec_for_gimple): Adjust by-value argument to by-reference. * haifa-sched.c (calc_priorities): Adjust by-value argument to by-const-reference. (sched_init_luids): Same. (haifa_init_h_i_d): Same. * ipa-cp.c (ipa_get_indirect_edge_target_1): Same. (adjust_callers_for_value_intersection): Adjust by-value argument to by-reference. (find_more_scalar_values_for_callers_subset): Adjust by-value argument to by-const-reference. (find_more_contexts_for_caller_subset): Same. (find_aggregate_values_for_callers_subset): Same. (copy_useful_known_contexts): Same. * ipa-fnsummary.c (remap_edge_summaries): Same. (remap_freqcounting_predicate): Same. * ipa-inline.c (add_new_edges_to_heap): Adjust by-value argument to by-reference. * ipa-predicate.c (predicate::remap_after_inlining): Adjust by-value argument to by-const-reference. * ipa-predicate.h (predicate::remap_after_inlining): Same. * ipa-prop.c (ipa_find_agg_cst_for_param): Same. * ipa-prop.h (ipa_find_agg_cst_for_param): Same. * ira-build.c (ira_loop_tree_body_rev_postorder): Same. * read-rtl.c (add_overload_instance): Same. * rtl.h (native_decode_rtx): Same. (native_decode_vector_rtx): Same. * sched-int.h (sched_init_luids): Same. (haifa_init_h_i_d): Same. * simplify-rtx.c (native_decode_vector_rtx): Same. (native_decode_rtx): Same. * tree-call-cdce.c (gen_shrink_wrap_conditions): Same. (shrink_wrap_one_built_in_call_with_conds): Same. (shrink_wrap_conditional_dead_built_in_calls): Same. * tree-data-ref.c (create_runtime_alias_checks): Same. (compute_all_dependences): Same. * tree-data-ref.h (compute_all_dependences): Same. (create_runtime_alias_checks): Same. (index_in_loop_nest): Same. * tree-if-conv.c (mask_exists): Same. * tree-loop-distribution.c (class loop_distribution): Same. (loop_distribution::create_rdg_vertices): Same. (dump_rdg_partitions): Same. (debug_rdg_partitions): Same. (partition_contains_all_rw): Same. (loop_distribution::distribute_loop): Same. * tree-parloops.c (oacc_entry_exit_ok_1): Same. (oacc_entry_exit_single_gang): Same. * tree-ssa-loop-im.c (hoist_memory_references): Same. (loop_suitable_for_sm): Same. * tree-ssa-loop-niter.c (bound_index): Same. * tree-ssa-reassoc.c (update_ops): Same. (swap_ops_for_binary_stmt): Same. (rewrite_expr_tree): Same. (rewrite_expr_tree_parallel): Same. * tree-ssa-sccvn.c (ao_ref_init_from_vn_reference): Same. * tree-ssa-sccvn.h (ao_ref_init_from_vn_reference): Same. * tree-ssa-structalias.c (process_all_all_constraints): Same. (make_constraints_to): Same. (handle_lhs_call): Same. (find_func_aliases_for_builtin_call): Same. (sort_fieldstack): Same. (check_for_overlaps): Same. * tree-vect-loop-manip.c (vect_create_cond_for_align_checks): Same. (vect_create_cond_for_unequal_addrs): Same. (vect_create_cond_for_lower_bounds): Same. (vect_create_cond_for_alias_checks): Same. * tree-vect-slp-patterns.c (vect_validate_multiplication): Same. * tree-vect-slp.c (vect_analyze_slp_instance): Same. (vect_make_slp_decision): Same. (vect_slp_bbs): Same. (duplicate_and_interleave): Same. (vect_transform_slp_perm_load): Same. (vect_schedule_slp): Same. * tree-vectorizer.h (vect_transform_slp_perm_load): Same. (vect_schedule_slp): Same. (duplicate_and_interleave): Same. * tree.c (build_vector_from_ctor): Same. (build_vector): Same. (check_vector_cst): Same. (check_vector_cst_duplicate): Same. (check_vector_cst_fill): Same. (check_vector_cst_stepped): Same. * tree.h (build_vector_from_ctor): Same. --- gcc/c/c-tree.h | 5 +++-- gcc/c/c-typeck.c | 2 +- 2 files changed, 4 insertions(+), 3 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h index a671a3e..ab6db38 100644 --- a/gcc/c/c-tree.h +++ b/gcc/c/c-tree.h @@ -759,8 +759,9 @@ extern tree c_finish_omp_clauses (tree, enum c_omp_region_type); extern tree c_build_va_arg (location_t, tree, location_t, tree); extern tree c_finish_transaction (location_t, tree, int); extern bool c_tree_equal (tree, tree); -extern tree c_build_function_call_vec (location_t, vec, tree, - vec *, vec *); +extern tree c_build_function_call_vec (location_t, const vec&, + tree, vec *, + vec *); extern tree c_omp_clause_copy_ctor (tree, tree, tree); /* Set to 0 at beginning of a function definition, set to 1 if diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 5349ef1..4f7ed67 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -3240,7 +3240,7 @@ build_function_call_vec (location_t loc, vec arg_loc, /* Like build_function_call_vec, but call also resolve_overloaded_builtin. */ tree -c_build_function_call_vec (location_t loc, vec arg_loc, +c_build_function_call_vec (location_t loc, const vec &arg_loc, tree function, vec *params, vec *origtypes) { -- cgit v1.1 From 92d4550991de7e0970a38939422b31e9dc07dd11 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 21 Jul 2021 00:16:54 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index a190806..9cd1dd6 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-07-20 Martin Sebor + + * c-tree.h (c_build_function_call_vec): Adjust by-value argument to + by-const-reference. + * c-typeck.c (c_build_function_call_vec): Same. + 2021-07-15 Martin Sebor PR c/101289 -- cgit v1.1 From a61f6afbee370785cf091fe46e2e022748528307 Mon Sep 17 00:00:00 2001 From: Thomas Schwinge Date: Wed, 21 Jul 2021 18:30:00 +0200 Subject: OpenACC 'nohost' clause Do not "compile a version of this procedure for the host". gcc/ * tree-core.h (omp_clause_code): Add 'OMP_CLAUSE_NOHOST'. * tree.c (omp_clause_num_ops, omp_clause_code_name, walk_tree_1): Handle it. * tree-pretty-print.c (dump_omp_clause): Likewise. * omp-general.c (oacc_verify_routine_clauses): Likewise. * gimplify.c (gimplify_scan_omp_clauses) (gimplify_adjust_omp_clauses): Likewise. * tree-nested.c (convert_nonlocal_omp_clauses) (convert_local_omp_clauses): Likewise. * omp-low.c (scan_sharing_clauses): Likewise. * omp-offload.c (execute_oacc_device_lower): Update. gcc/c-family/ * c-pragma.h (pragma_omp_clause): Add 'PRAGMA_OACC_CLAUSE_NOHOST'. gcc/c/ * c-parser.c (c_parser_omp_clause_name): Handle 'nohost'. (c_parser_oacc_all_clauses): Handle 'PRAGMA_OACC_CLAUSE_NOHOST'. (OACC_ROUTINE_CLAUSE_MASK): Add 'PRAGMA_OACC_CLAUSE_NOHOST'. * c-typeck.c (c_finish_omp_clauses): Handle 'OMP_CLAUSE_NOHOST'. gcc/cp/ * parser.c (cp_parser_omp_clause_name): Handle 'nohost'. (cp_parser_oacc_all_clauses): Handle 'PRAGMA_OACC_CLAUSE_NOHOST'. (OACC_ROUTINE_CLAUSE_MASK): Add 'PRAGMA_OACC_CLAUSE_NOHOST'. * pt.c (tsubst_omp_clauses): Handle 'OMP_CLAUSE_NOHOST'. * semantics.c (finish_omp_clauses): Likewise. gcc/fortran/ * dump-parse-tree.c (show_attr): Update. * gfortran.h (symbol_attribute): Add 'oacc_routine_nohost' member. (gfc_omp_clauses): Add 'nohost' member. * module.c (ab_attribute): Add 'AB_OACC_ROUTINE_NOHOST'. (attr_bits, mio_symbol_attribute): Update. * openmp.c (omp_mask2): Add 'OMP_CLAUSE_NOHOST'. (gfc_match_omp_clauses): Handle 'OMP_CLAUSE_NOHOST'. (OACC_ROUTINE_CLAUSES): Add 'OMP_CLAUSE_NOHOST'. (gfc_match_oacc_routine): Update. * trans-decl.c (add_attributes_to_decl): Update. * trans-openmp.c (gfc_trans_omp_clauses): Likewise. gcc/testsuite/ * c-c++-common/goacc/classify-routine-nohost.c: New file. * c-c++-common/goacc/classify-routine.c: Update. * c-c++-common/goacc/routine-2.c: Likewise. * c-c++-common/goacc/routine-nohost-1.c: New file. * c-c++-common/goacc/routine-nohost-2.c: Likewise. * g++.dg/goacc/template.C: Update. * gfortran.dg/goacc/classify-routine-nohost.f95: New file. * gfortran.dg/goacc/classify-routine.f95: Update. * gfortran.dg/goacc/pure-elemental-procedures-2.f90: Likewise. * gfortran.dg/goacc/routine-6.f90: Likewise. * gfortran.dg/goacc/routine-intrinsic-2.f: Likewise. * gfortran.dg/goacc/routine-module-1.f90: Likewise. * gfortran.dg/goacc/routine-module-2.f90: Likewise. * gfortran.dg/goacc/routine-module-3.f90: Likewise. * gfortran.dg/goacc/routine-module-mod-1.f90: Likewise. * gfortran.dg/goacc/routine-multiple-directives-1.f90: Likewise. * gfortran.dg/goacc/routine-multiple-directives-2.f90: Likewise. libgomp/ * testsuite/libgomp.oacc-c-c++-common/routine-nohost-1.c: New file. * testsuite/libgomp.oacc-c-c++-common/routine-nohost-2.c: Likewise. * testsuite/libgomp.oacc-c-c++-common/routine-nohost-2_2.c: Likewise. * testsuite/libgomp.oacc-fortran/routine-nohost-1.f90: Likewise. Co-Authored-By: Joseph Myers Co-Authored-By: Cesar Philippidis --- gcc/c/c-parser.c | 10 +++++++++- gcc/c/c-typeck.c | 1 + 2 files changed, 10 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 9a56e0c..92d22d1 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -12744,6 +12744,8 @@ c_parser_omp_clause_name (c_parser *parser) result = PRAGMA_OACC_CLAUSE_NO_CREATE; else if (!strcmp ("nogroup", p)) result = PRAGMA_OMP_CLAUSE_NOGROUP; + else if (!strcmp ("nohost", p)) + result = PRAGMA_OACC_CLAUSE_NOHOST; else if (!strcmp ("nontemporal", p)) result = PRAGMA_OMP_CLAUSE_NONTEMPORAL; else if (!strcmp ("notinbranch", p)) @@ -16248,6 +16250,11 @@ c_parser_oacc_all_clauses (c_parser *parser, omp_clause_mask mask, clauses = c_parser_oacc_data_clause (parser, c_kind, clauses); c_name = "no_create"; break; + case PRAGMA_OACC_CLAUSE_NOHOST: + clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_NOHOST, + clauses); + c_name = "nohost"; + break; case PRAGMA_OACC_CLAUSE_NUM_GANGS: clauses = c_parser_oacc_single_int_clause (parser, OMP_CLAUSE_NUM_GANGS, @@ -17179,7 +17186,8 @@ c_parser_oacc_compute (location_t loc, c_parser *parser, ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_GANG) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WORKER) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_VECTOR) \ - | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_SEQ) ) + | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_SEQ) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NOHOST) ) /* Parse an OpenACC routine directive. For named directives, we apply immediately to the named function. For unnamed ones we then parse diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 4f7ed67..5d6565b 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -15168,6 +15168,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) case OMP_CLAUSE_TILE: case OMP_CLAUSE_IF_PRESENT: case OMP_CLAUSE_FINALIZE: + case OMP_CLAUSE_NOHOST: pc = &OMP_CLAUSE_CHAIN (c); continue; -- cgit v1.1 From 419c6c68e60adc8801b44dab72ebcd680cfe1d97 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 22 Jul 2021 00:16:46 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 9cd1dd6..367c9c7 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,12 @@ +2021-07-21 Thomas Schwinge + Joseph Myers + Cesar Philippidis + + * c-parser.c (c_parser_omp_clause_name): Handle 'nohost'. + (c_parser_oacc_all_clauses): Handle 'PRAGMA_OACC_CLAUSE_NOHOST'. + (OACC_ROUTINE_CLAUSE_MASK): Add 'PRAGMA_OACC_CLAUSE_NOHOST'. + * c-typeck.c (c_finish_omp_clauses): Handle 'OMP_CLAUSE_NOHOST'. + 2021-07-20 Martin Sebor * c-tree.h (c_build_function_call_vec): Adjust by-value argument to -- cgit v1.1 From a3d3e8c362c2d850543eb2e2631128e1efc368f0 Mon Sep 17 00:00:00 2001 From: Martin Sebor Date: Thu, 5 Aug 2021 19:50:35 -0600 Subject: Adjust by-value function vec arguments to by-reference. gcc/c/ChangeLog: * c-parser.c (c_parser_declaration_or_fndef): Adjust by-value function vec arguments to by-reference. (c_finish_omp_declare_simd): Same. (c_parser_compound_statement_nostart): Same. (c_parser_for_statement): Same. (c_parser_objc_methodprotolist): Same. (c_parser_oacc_routine): Same. (c_parser_omp_for_loop): Same. (c_parser_omp_declare_simd): Same. gcc/ChangeLog: * dominance.c (prune_bbs_to_update_dominators): Adjust by-value vec arguments to by-reference. (iterate_fix_dominators): Same. * dominance.h (iterate_fix_dominators): Same. * ipa-prop.h: Call auto_vec::to_vec_legacy. * tree-data-ref.c (dump_data_dependence_relation): Adjust by-value vec arguments to by-reference. (debug_data_dependence_relation): Same. (dump_data_dependence_relations): Same. * tree-data-ref.h (debug_data_dependence_relation): Same. (dump_data_dependence_relations): Same. * tree-predcom.c (dump_chains): Same. (initialize_root_vars_lm): Same. (determine_unroll_factor): Same. (replace_phis_by_defined_names): Same. (insert_init_seqs): Same. (pcom_worker::tree_predictive_commoning_loop): Call auto_vec::to_vec_legacy. * tree-ssa-pre.c (insert_into_preds_of_block): Adjust by-value vec arguments to by-reference. * tree-ssa-threadbackward.c (populate_worklist): Same. (back_threader::resolve_def): Same. * tree-vect-data-refs.c (vect_check_nonzero_value): Same. (vect_enhance_data_refs_alignment): Same. (vect_check_lower_bound): Same. (vect_prune_runtime_alias_test_list): Same. (vect_permute_store_chain): Same. * tree-vect-slp-patterns.c (vect_normalize_conj_loc): Same. * tree-vect-stmts.c (vect_create_vectorized_demotion_stmts): Same. * tree-vectorizer.h (vect_permute_store_chain): Same. * vec.c (test_init): New function. (vec_c_tests): Call new function. * vec.h (vec): Declare ctors, dtor, and assignment. (auto_vec::vec_to_legacy): New function. (vec::copy): Adjust initialization. --- gcc/c/c-parser.c | 63 ++++++++++++++++++++++++++++++-------------------------- 1 file changed, 34 insertions(+), 29 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 92d22d1..d24bfdb 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -1489,7 +1489,8 @@ static tree c_parser_std_attribute_specifier_sequence (c_parser *); static void c_parser_external_declaration (c_parser *); static void c_parser_asm_definition (c_parser *); static void c_parser_declaration_or_fndef (c_parser *, bool, bool, bool, - bool, bool, tree *, vec, + bool, bool, tree * = NULL, + vec * = NULL, bool have_attrs = false, tree attrs = NULL, struct oacc_routine_data * = NULL, @@ -1774,13 +1775,12 @@ c_parser_external_declaration (c_parser *parser) an @interface or @protocol with prefix attributes). We can only tell which after parsing the declaration specifiers, if any, and the first declarator. */ - c_parser_declaration_or_fndef (parser, true, true, true, false, true, - NULL, vNULL); + c_parser_declaration_or_fndef (parser, true, true, true, false, true); break; } } -static void c_finish_omp_declare_simd (c_parser *, tree, tree, vec); +static void c_finish_omp_declare_simd (c_parser *, tree, tree, vec *); static void c_finish_oacc_routine (struct oacc_routine_data *, tree, bool); /* Build and add a DEBUG_BEGIN_STMT statement with location LOC. */ @@ -1890,11 +1890,15 @@ static void c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, bool static_assert_ok, bool empty_ok, bool nested, bool start_attr_ok, - tree *objc_foreach_object_declaration, - vec omp_declare_simd_clauses, - bool have_attrs, tree attrs, - struct oacc_routine_data *oacc_routine_data, - bool *fallthru_attr_p) + tree *objc_foreach_object_declaration + /* = NULL */, + vec *omp_declare_simd_clauses + /* = NULL */, + bool have_attrs /* = false */, + tree attrs /* = NULL_TREE */, + struct oacc_routine_data *oacc_routine_data + /* = NULL */, + bool *fallthru_attr_p /* = NULL */) { struct c_declspecs *specs; tree prefix_attrs; @@ -2150,7 +2154,7 @@ c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, C_DTR_NORMAL, &dummy); if (declarator == NULL) { - if (omp_declare_simd_clauses.exists ()) + if (omp_declare_simd_clauses) c_finish_omp_declare_simd (parser, NULL_TREE, NULL_TREE, omp_declare_simd_clauses); if (oacc_routine_data) @@ -2250,7 +2254,7 @@ c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, chainon (postfix_attrs, all_prefix_attrs)); if (!d) d = error_mark_node; - if (omp_declare_simd_clauses.exists ()) + if (omp_declare_simd_clauses) c_finish_omp_declare_simd (parser, d, NULL_TREE, omp_declare_simd_clauses); } @@ -2262,7 +2266,7 @@ c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, chainon (postfix_attrs, all_prefix_attrs)); if (!d) d = error_mark_node; - if (omp_declare_simd_clauses.exists ()) + if (omp_declare_simd_clauses) c_finish_omp_declare_simd (parser, d, NULL_TREE, omp_declare_simd_clauses); init_loc = c_parser_peek_token (parser)->location; @@ -2342,7 +2346,7 @@ c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, warn_parm_array_mismatch (lastloc, d, parms); } } - if (omp_declare_simd_clauses.exists ()) + if (omp_declare_simd_clauses) { tree parms = NULL_TREE; if (d && TREE_CODE (d) == FUNCTION_DECL) @@ -2496,9 +2500,9 @@ c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok, while (c_parser_next_token_is_not (parser, CPP_EOF) && c_parser_next_token_is_not (parser, CPP_OPEN_BRACE)) c_parser_declaration_or_fndef (parser, false, false, false, - true, false, NULL, vNULL); + true, false); store_parm_decls (); - if (omp_declare_simd_clauses.exists ()) + if (omp_declare_simd_clauses) c_finish_omp_declare_simd (parser, current_function_decl, NULL_TREE, omp_declare_simd_clauses); if (oacc_routine_data) @@ -5699,7 +5703,7 @@ c_parser_compound_statement_nostart (c_parser *parser) bool fallthru_attr_p = false; c_parser_declaration_or_fndef (parser, true, !have_std_attrs, true, true, true, NULL, - vNULL, have_std_attrs, std_attrs, + NULL, have_std_attrs, std_attrs, NULL, &fallthru_attr_p); if (last_stmt && !fallthru_attr_p) @@ -5731,7 +5735,7 @@ c_parser_compound_statement_nostart (c_parser *parser) last_label = false; mark_valid_location_for_stdc_pragma (false); c_parser_declaration_or_fndef (parser, true, true, true, true, - true, NULL, vNULL); + true); /* Following the old parser, __extension__ does not disable this diagnostic. */ restore_extension_diagnostics (ext); @@ -6782,7 +6786,7 @@ c_parser_for_statement (c_parser *parser, bool ivdep, unsigned short unroll, || c_parser_nth_token_starts_std_attributes (parser, 1)) { c_parser_declaration_or_fndef (parser, true, true, true, true, true, - &object_expression, vNULL); + &object_expression); parser->objc_could_be_foreach_context = false; if (c_parser_next_token_is_keyword (parser, RID_IN)) @@ -6813,7 +6817,7 @@ c_parser_for_statement (c_parser *parser, bool ivdep, unsigned short unroll, ext = disable_extension_diagnostics (); c_parser_consume_token (parser); c_parser_declaration_or_fndef (parser, true, true, true, true, - true, &object_expression, vNULL); + true, &object_expression); parser->objc_could_be_foreach_context = false; restore_extension_diagnostics (ext); @@ -11277,7 +11281,7 @@ c_parser_objc_methodprotolist (c_parser *parser) } else c_parser_declaration_or_fndef (parser, false, false, true, - false, true, NULL, vNULL); + false, true); break; } } @@ -17281,12 +17285,12 @@ c_parser_oacc_routine (c_parser *parser, enum pragma_context context) while (c_parser_next_token_is (parser, CPP_KEYWORD) && c_parser_peek_token (parser)->keyword == RID_EXTENSION); c_parser_declaration_or_fndef (parser, true, true, true, false, true, - NULL, vNULL, false, NULL, &data); + NULL, NULL, false, NULL, &data); restore_extension_diagnostics (ext); } else c_parser_declaration_or_fndef (parser, true, true, true, false, true, - NULL, vNULL, false, NULL, &data); + NULL, NULL, false, NULL, &data); } } @@ -18393,8 +18397,7 @@ c_parser_omp_for_loop (location_t loc, c_parser *parser, enum tree_code code, vec_safe_push (for_block, c_begin_compound_stmt (true)); this_pre_body = push_stmt_list (); c_in_omp_for = true; - c_parser_declaration_or_fndef (parser, true, true, true, true, true, - NULL, vNULL); + c_parser_declaration_or_fndef (parser, true, true, true, true, true); c_in_omp_for = false; if (this_pre_body) { @@ -20335,12 +20338,12 @@ c_parser_omp_declare_simd (c_parser *parser, enum pragma_context context) while (c_parser_next_token_is (parser, CPP_KEYWORD) && c_parser_peek_token (parser)->keyword == RID_EXTENSION); c_parser_declaration_or_fndef (parser, true, true, true, false, true, - NULL, clauses); + NULL, &clauses); restore_extension_diagnostics (ext); } else c_parser_declaration_or_fndef (parser, true, true, true, false, true, - NULL, clauses); + NULL, &clauses); break; case pragma_struct: case pragma_param: @@ -20361,7 +20364,7 @@ c_parser_omp_declare_simd (c_parser *parser, enum pragma_context context) if (c_parser_next_tokens_start_declaration (parser)) { c_parser_declaration_or_fndef (parser, true, true, true, true, - true, NULL, clauses); + true, NULL, &clauses); restore_extension_diagnostics (ext); break; } @@ -20370,7 +20373,7 @@ c_parser_omp_declare_simd (c_parser *parser, enum pragma_context context) else if (c_parser_next_tokens_start_declaration (parser)) { c_parser_declaration_or_fndef (parser, true, true, true, true, true, - NULL, clauses); + NULL, &clauses); break; } error ("%<#pragma omp declare %s%> must be followed by " @@ -20851,8 +20854,10 @@ c_finish_omp_declare_variant (c_parser *parser, tree fndecl, tree parms) static void c_finish_omp_declare_simd (c_parser *parser, tree fndecl, tree parms, - vec clauses) + vec *pclauses) { + vec &clauses = *pclauses; + /* Normally first token is CPP_NAME "simd" or "variant". CPP_EOF there indicates error has been reported and CPP_PRAGMA that c_finish_omp_declare_simd has already processed the tokens. */ -- cgit v1.1 From 6b0bde7eef492843426c3f6b2da229b3c1526eaa Mon Sep 17 00:00:00 2001 From: Tamar Christina Date: Fri, 6 Aug 2021 12:21:05 +0100 Subject: middle-end/AArch64: Fix bootstrap after vec changes The build is broken since a3d3e8c362c2 since it's deleted the ability to pass vec<> by value and now must be past by reference. However some language hooks used by AArch64 were not updated and breaks the build on AArch64. This patch updates these hooks. gcc/c/ChangeLog: * c-decl.c (c_simulate_enum_decl): Pass vec<> by pointer. * c-tree.h (c_simulate_enum_decl): Likewise. gcc/ChangeLog: * config/aarch64/aarch64-sve-builtins.cc (register_svpattern, register_svprfop): Pass vec<> by pointer. * langhooks-def.h (lhd_simulate_enum_decl): Likewise. * langhooks.c (lhd_simulate_enum_decl): Likewise. * langhooks.h (struct lang_hooks_for_types): Likewise. gcc/cp/ChangeLog: * cp-objcp-common.h (cxx_simulate_enum_decl): Pass vec<> by pointer. * decl.c (cxx_simulate_enum_decl): Likewise. --- gcc/c/c-decl.c | 3 ++- gcc/c/c-tree.h | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 234ee16..221a67f 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -9379,7 +9379,7 @@ build_enumerator (location_t decl_loc, location_t loc, tree c_simulate_enum_decl (location_t loc, const char *name, - vec values) + vec *values_ptr) { location_t saved_loc = input_location; input_location = loc; @@ -9389,6 +9389,7 @@ c_simulate_enum_decl (location_t loc, const char *name, tree value_chain = NULL_TREE; string_int_pair *value; + vec values = *values_ptr; unsigned int i; FOR_EACH_VEC_ELT (values, i, value) { diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h index ab6db38..a8a90ea 100644 --- a/gcc/c/c-tree.h +++ b/gcc/c/c-tree.h @@ -595,7 +595,7 @@ extern void finish_function (location_t = input_location); extern tree finish_struct (location_t, tree, tree, tree, class c_struct_parse_info *); extern tree c_simulate_enum_decl (location_t, const char *, - vec); + vec *); extern struct c_arg_info *build_arg_info (void); extern struct c_arg_info *get_parm_info (bool, tree); extern tree grokfield (location_t, struct c_declarator *, -- cgit v1.1 From f92f47785201d44cef91e2c4a9742fb503ce5316 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 7 Aug 2021 00:16:39 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 367c9c7..6f15b0f 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,20 @@ +2021-08-06 Tamar Christina + + * c-decl.c (c_simulate_enum_decl): Pass vec<> by pointer. + * c-tree.h (c_simulate_enum_decl): Likewise. + +2021-08-06 Martin Sebor + + * c-parser.c (c_parser_declaration_or_fndef): Adjust by-value function + vec arguments to by-reference. + (c_finish_omp_declare_simd): Same. + (c_parser_compound_statement_nostart): Same. + (c_parser_for_statement): Same. + (c_parser_objc_methodprotolist): Same. + (c_parser_oacc_routine): Same. + (c_parser_omp_for_loop): Same. + (c_parser_omp_declare_simd): Same. + 2021-07-21 Thomas Schwinge Joseph Myers Cesar Philippidis -- cgit v1.1 From 0631faf87a197145acd833249bf8f20a1c4aaabf Mon Sep 17 00:00:00 2001 From: Martin Uecker Date: Tue, 10 Aug 2021 07:42:51 +0200 Subject: Evaluate arguments of sizeof that are structs of variable size. Evaluate arguments of sizeof for all types of variable size and not just for VLAs. This fixes some issues related to [PR29970] where statement expressions need to be evaluated so that the size is well defined. 2021-08-10 Martin Uecker gcc/c/ PR c/29970 * c-typeck.c (c_expr_sizeof_expr): Evaluate size expressions for structs of variable size. gcc/testsuite/ PR c/29970 * gcc.dg/vla-stexp-1.c: New test. --- gcc/c/c-typeck.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 5d6565b..c5bf337 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -2992,7 +2992,7 @@ c_expr_sizeof_expr (location_t loc, struct c_expr expr) c_last_sizeof_loc = loc; ret.original_code = SIZEOF_EXPR; ret.original_type = NULL; - if (c_vla_type_p (TREE_TYPE (folded_expr))) + if (C_TYPE_VARIABLE_SIZE (TREE_TYPE (folded_expr))) { /* sizeof is evaluated when given a vla (C99 6.5.3.4p2). */ ret.value = build2 (C_MAYBE_CONST_EXPR, TREE_TYPE (ret.value), -- cgit v1.1 From 3ae564ea7410e99e533bc87f999a04b2647c831d Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 11 Aug 2021 00:16:27 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 6f15b0f..74ab186 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-08-10 Martin Uecker + + PR c/29970 + * c-typeck.c (c_expr_sizeof_expr): Evaluate + size expressions for structs of variable size. + 2021-08-06 Tamar Christina * c-decl.c (c_simulate_enum_decl): Pass vec<> by pointer. -- cgit v1.1 From 432de08498142d2266c0fb05f2c555a7f1e10ddd Mon Sep 17 00:00:00 2001 From: Tobias Burnus Date: Thu, 12 Aug 2021 15:48:28 +0200 Subject: OpenMP 5.1: Add proc-bind 'primary' support In OpenMP 5.1 "master thread" was changed to "primary thread" and the proc_bind clause and the OMP_PROC_BIND environment variable now take 'primary' as argument as alias for 'master', while the latter is deprecated. This commit accepts 'primary' and adds the named constant omp_proc_bind_primary and changes 'master thread' in the documentation; however, given that not even OpenMP 5.0 is fully supported, omp_display_env and the dumps currently still output 'master' and there is no deprecation warning when using the 'master' in the proc_bind clause. gcc/c/ChangeLog: * c-parser.c (c_parser_omp_clause_proc_bind): Accept 'primary' as alias for 'master'. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_clause_proc_bind): Accept 'primary' as alias for 'master'. gcc/fortran/ChangeLog: * gfortran.h (gfc_omp_proc_bind_kind): Add OMP_PROC_BIND_PRIMARY. * dump-parse-tree.c (show_omp_clauses): Add TODO comment to change 'master' to 'primary' in proc_bind for OpenMP 5.1. * intrinsic.texi (OMP_LIB): Mention OpenMP 5.1; add omp_proc_bind_primary. * openmp.c (gfc_match_omp_clauses): Accept 'primary' as alias for 'master'. * trans-openmp.c (gfc_trans_omp_clauses): Handle OMP_PROC_BIND_PRIMARY. gcc/ChangeLog: * tree-core.h (omp_clause_proc_bind_kind): Add OMP_CLAUSE_PROC_BIND_PRIMARY. * tree-pretty-print.c (dump_omp_clause): Add TODO comment to change 'master' to 'primary' in proc_bind for OpenMP 5.1. libgomp/ChangeLog: * env.c (parse_bind_var): Accept 'primary' as alias for 'master'. (omp_display_env): Add TODO comment to change 'master' to 'primary' in proc_bind for OpenMP 5.1. * libgomp.texi: Change 'master thread' to 'primary thread' in line with OpenMP 5.1. (omp_get_proc_bind): Add omp_proc_bind_primary and note that omp_proc_bind_master is an alias of it. (OMP_PROC_BIND): Mention 'PRIMARY'. * omp.h.in (__GOMP_DEPRECATED_5_1): Define. (omp_proc_bind_primary): Add. (omp_proc_bind_master): Deprecate for OpenMP 5.1. * omp_lib.f90.in (omp_proc_bind_primary): Add. (omp_proc_bind_master): Deprecate for OpenMP 5.1. * omp_lib.h.in (omp_proc_bind_primary): Add. * testsuite/libgomp.c/affinity-1.c: Check that 'primary' works and is identical to 'master'. gcc/testsuite/ChangeLog: * c-c++-common/gomp/pr61486-2.c: Duplicate one proc_bind(master) testcase and test proc_bind(primary) instead. * gfortran.dg/gomp/affinity-1.f90: Likewise. --- gcc/c/c-parser.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index d24bfdb..195c137 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -15959,7 +15959,8 @@ c_parser_omp_clause_dist_schedule (c_parser *parser, tree list) proc_bind ( proc-bind-kind ) proc-bind-kind: - master | close | spread */ + primary | master | close | spread + where OpenMP 5.1 added 'primary' and deprecated the alias 'master'. */ static tree c_parser_omp_clause_proc_bind (c_parser *parser, tree list) @@ -15975,7 +15976,9 @@ c_parser_omp_clause_proc_bind (c_parser *parser, tree list) if (c_parser_next_token_is (parser, CPP_NAME)) { const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); - if (strcmp ("master", p) == 0) + if (strcmp ("primary", p) == 0) + kind = OMP_CLAUSE_PROC_BIND_PRIMARY; + else if (strcmp ("master", p) == 0) kind = OMP_CLAUSE_PROC_BIND_MASTER; else if (strcmp ("close", p) == 0) kind = OMP_CLAUSE_PROC_BIND_CLOSE; -- cgit v1.1 From d2ba65ab6010f0d507bf5512a0223692e6653b23 Mon Sep 17 00:00:00 2001 From: Martin Uecker Date: Thu, 12 Aug 2021 20:32:16 +0200 Subject: Evaluate type arguments of sizeof that are structs of variable size [PR101838] Evaluate type arguments of sizeof for all types of variable size and not just for VLAs. This fixes PR101838 and some issues related to PR29970 where statement expressions need to be evaluated so that the size is well defined. 2021-08-12 Martin Uecker gcc/c/ PR c/101838 PR c/29970 * c-typeck.c (c_expr_sizeof_type): Evaluate size expressions for structs of variable size. gcc/testsuite/ PR c/101838 * gcc.dg/vla-stexp-2.c: New test. --- gcc/c/c-typeck.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index c5bf337..eb5c87d 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -3022,8 +3022,14 @@ c_expr_sizeof_type (location_t loc, struct c_type_name *t) c_last_sizeof_loc = loc; ret.original_code = SIZEOF_EXPR; ret.original_type = NULL; + if (type == error_mark_node) + { + ret.value = error_mark_node; + ret.original_code = ERROR_MARK; + } + else if ((type_expr || TREE_CODE (ret.value) == INTEGER_CST) - && c_vla_type_p (type)) + && C_TYPE_VARIABLE_SIZE (type)) { /* If the type is a [*] array, it is a VLA but is represented as having a size of zero. In such a case we must ensure that -- cgit v1.1 From d0befed793b94f3f407be44e6f69f81a02f5f073 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 12 Aug 2021 22:41:17 +0200 Subject: openmp: Add support for OpenMP 5.1 masked construct This construct has been introduced as a replacement for master construct, but unlike that construct is slightly more general, has an optional clause which allows to choose which thread will be the one running the region, it can be some other thread than the master (primary) thread with number 0, or it could be no threads or multiple threads (then of course one needs to be careful about data races). It is way too early to deprecate the master construct though, we don't even have OpenMP 5.0 fully implemented, it has been deprecated in 5.1, will be also in 5.2 and removed in 6.0. But even then it will likely be a good idea to just -Wdeprecated warn about it and still accept it. The patch also contains something I should have done much earlier, for clauses that accept some integral expression where we only care about the value, forces during gimplification that value into either a min invariant (as before), SSA_NAME or a fresh temporary, but never e.g. a user VAR_DECL, so that for those clauses we don't need to worry about adjusting it. 2021-08-12 Jakub Jelinek gcc/ * tree.def (OMP_MASKED): New tree code. * tree-core.h (enum omp_clause_code): Add OMP_CLAUSE_FILTER. * tree.h (OMP_MASKED_BODY, OMP_MASKED_CLAUSES, OMP_MASKED_COMBINED, OMP_CLAUSE_FILTER_EXPR): Define. * tree.c (omp_clause_num_ops): Add OMP_CLAUSE_FILTER entry. (omp_clause_code_name): Likewise. (walk_tree_1): Handle OMP_CLAUSE_FILTER. * tree-nested.c (convert_nonlocal_omp_clauses, convert_local_omp_clauses): Handle OMP_CLAUSE_FILTER. (convert_nonlocal_reference_stmt, convert_local_reference_stmt, convert_gimple_call): Handle GIMPLE_OMP_MASTER. * tree-pretty-print.c (dump_omp_clause): Handle OMP_CLAUSE_FILTER. (dump_generic_node): Handle OMP_MASTER. * gimple.def (GIMPLE_OMP_MASKED): New gimple code. * gimple.c (gimple_build_omp_masked): New function. (gimple_copy): Handle GIMPLE_OMP_MASKED. * gimple.h (gimple_build_omp_masked): Declare. (gimple_has_substatements): Handle GIMPLE_OMP_MASKED. (gimple_omp_masked_clauses, gimple_omp_masked_clauses_ptr, gimple_omp_masked_set_clauses): New inline functions. (CASE_GIMPLE_OMP): Add GIMPLE_OMP_MASKED. * gimple-pretty-print.c (dump_gimple_omp_masked): New function. (pp_gimple_stmt_1): Handle GIMPLE_OMP_MASKED. * gimple-walk.c (walk_gimple_stmt): Likewise. * gimple-low.c (lower_stmt): Likewise. * gimplify.c (is_gimple_stmt): Handle OMP_MASTER. (gimplify_scan_omp_clauses): Handle OMP_CLAUSE_FILTER. For clauses that take one expression rather than decl or constant, force gimplification of that into a SSA_NAME or temporary unless min invariant. (gimplify_adjust_omp_clauses): Handle OMP_CLAUSE_FILTER. (gimplify_expr): Handle OMP_MASKED. * tree-inline.c (remap_gimple_stmt): Handle GIMPLE_OMP_MASKED. (estimate_num_insns): Likewise. * omp-low.c (scan_sharing_clauses): Handle OMP_CLAUSE_FILTER. (check_omp_nesting_restrictions): Handle GIMPLE_OMP_MASKED. Adjust diagnostics for existence of masked construct. (scan_omp_1_stmt, lower_omp_master, lower_omp_1, diagnose_sb_1, diagnose_sb_2): Handle GIMPLE_OMP_MASKED. * omp-expand.c (expand_omp_synch, expand_omp, omp_make_gimple_edges): Likewise. gcc/c-family/ * c-pragma.h (enum pragma_kind): Add PRAGMA_OMP_MASKED. (enum pragma_omp_clause): Add PRAGMA_OMP_CLAUSE_FILTER. * c-pragma.c (omp_pragmas_simd): Add masked construct. * c-common.h (enum c_omp_clause_split): Add C_OMP_CLAUSE_SPLIT_MASKED enumerator. (c_finish_omp_masked): Declare. * c-omp.c (c_finish_omp_masked): New function. (c_omp_split_clauses): Handle combined masked constructs. gcc/c/ * c-parser.c (c_parser_omp_clause_name): Parse filter clause name. (c_parser_omp_clause_filter): New function. (c_parser_omp_all_clauses): Handle PRAGMA_OMP_CLAUSE_FILTER. (OMP_MASKED_CLAUSE_MASK): Define. (c_parser_omp_masked): New function. (c_parser_omp_parallel): Handle parallel masked. (c_parser_omp_construct): Handle PRAGMA_OMP_MASKED. * c-typeck.c (c_finish_omp_clauses): Handle OMP_CLAUSE_FILTER. gcc/cp/ * parser.c (cp_parser_omp_clause_name): Parse filter clause name. (cp_parser_omp_clause_filter): New function. (cp_parser_omp_all_clauses): Handle PRAGMA_OMP_CLAUSE_FILTER. (OMP_MASKED_CLAUSE_MASK): Define. (cp_parser_omp_masked): New function. (cp_parser_omp_parallel): Handle parallel masked. (cp_parser_omp_construct, cp_parser_pragma): Handle PRAGMA_OMP_MASKED. * semantics.c (finish_omp_clauses): Handle OMP_CLAUSE_FILTER. * pt.c (tsubst_omp_clauses): Likewise. (tsubst_expr): Handle OMP_MASKED. gcc/testsuite/ * c-c++-common/gomp/clauses-1.c (bar): Add tests for combined masked constructs with clauses. * c-c++-common/gomp/clauses-5.c (foo): Add testcase for filter clause. * c-c++-common/gomp/clause-dups-1.c (f1): Likewise. * c-c++-common/gomp/masked-1.c: New test. * c-c++-common/gomp/masked-2.c: New test. * c-c++-common/gomp/masked-combined-1.c: New test. * c-c++-common/gomp/masked-combined-2.c: New test. * c-c++-common/goacc/uninit-if-clause.c: Remove xfails. * g++.dg/gomp/block-11.C: New test. * g++.dg/gomp/tpl-masked-1.C: New test. * g++.dg/gomp/attrs-1.C (bar): Add tests for masked construct and combined masked constructs with clauses in attribute syntax. * g++.dg/gomp/attrs-2.C (bar): Likewise. * gcc.dg/gomp/nesting-1.c (f1, f2): Add tests for masked construct nesting. * gfortran.dg/goacc/host_data-tree.f95: Allow also SSA_NAMEs in if clause. * gfortran.dg/goacc/kernels-tree.f95: Likewise. libgomp/ * testsuite/libgomp.c-c++-common/masked-1.c: New test. --- gcc/c/c-parser.c | 139 ++++++++++++++++++++++++++++++++++++++++++++++++++++++- gcc/c/c-typeck.c | 1 + 2 files changed, 138 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 195c137..ca6e56a 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -12696,7 +12696,9 @@ c_parser_omp_clause_name (c_parser *parser) result = PRAGMA_OMP_CLAUSE_DIST_SCHEDULE; break; case 'f': - if (!strcmp ("final", p)) + if (!strcmp ("filter", p)) + result = PRAGMA_OMP_CLAUSE_FILTER; + else if (!strcmp ("final", p)) result = PRAGMA_OMP_CLAUSE_FINAL; else if (!strcmp ("finalize", p)) result = PRAGMA_OACC_CLAUSE_FINALIZE; @@ -13948,6 +13950,38 @@ c_parser_omp_clause_hint (c_parser *parser, tree list) return list; } +/* OpenMP 5.1: + filter ( integer-expression ) */ + +static tree +c_parser_omp_clause_filter (c_parser *parser, tree list) +{ + location_t hint_loc = c_parser_peek_token (parser)->location; + matching_parens parens; + if (parens.require_open (parser)) + { + location_t expr_loc = c_parser_peek_token (parser)->location; + c_expr expr = c_parser_expr_no_commas (parser, NULL); + expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true); + tree c, t = expr.value; + t = c_fully_fold (t, false, NULL); + if (!INTEGRAL_TYPE_P (TREE_TYPE (t))) + { + c_parser_error (parser, "expected integer expression"); + return list; + } + parens.skip_until_found_close (parser); + check_no_duplicate_clause (list, OMP_CLAUSE_FILTER, "filter"); + + c = build_omp_clause (hint_loc, OMP_CLAUSE_FILTER); + OMP_CLAUSE_FILTER_EXPR (c) = t; + OMP_CLAUSE_CHAIN (c) = list; + list = c; + } + + return list; +} + /* OpenMP 4.5: defaultmap ( tofrom : scalar ) @@ -16410,6 +16444,10 @@ c_parser_omp_all_clauses (c_parser *parser, omp_clause_mask mask, clauses = c_parser_omp_clause_detach (parser, clauses); c_name = "detach"; break; + case PRAGMA_OMP_CLAUSE_FILTER: + clauses = c_parser_omp_clause_filter (parser, clauses); + c_name = "filter"; + break; case PRAGMA_OMP_CLAUSE_FIRSTPRIVATE: clauses = c_parser_omp_clause_firstprivate (parser, clauses); c_name = "firstprivate"; @@ -18975,6 +19013,70 @@ c_parser_omp_master (location_t loc, c_parser *parser, if_p)); } +/* OpenMP 5.1: + # pragma omp masked masked-clauses new-line + structured-block + + LOC is the location of the #pragma token. +*/ + +#define OMP_MASKED_CLAUSE_MASK \ + (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FILTER) + +static tree +c_parser_omp_masked (location_t loc, c_parser *parser, + char *p_name, omp_clause_mask mask, tree *cclauses, + bool *if_p) +{ + tree block, clauses, ret; + + strcat (p_name, " masked"); + mask |= OMP_MASKED_CLAUSE_MASK; + + if (c_parser_next_token_is (parser, CPP_NAME)) + { + const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); + + if (strcmp (p, "taskloop") == 0) + { + tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT]; + if (cclauses == NULL) + cclauses = cclauses_buf; + + c_parser_consume_token (parser); + if (!flag_openmp) /* flag_openmp_simd */ + return c_parser_omp_taskloop (loc, parser, p_name, mask, cclauses, + if_p); + block = c_begin_compound_stmt (true); + ret = c_parser_omp_taskloop (loc, parser, p_name, mask, cclauses, + if_p); + block = c_end_compound_stmt (loc, block, true); + if (ret == NULL_TREE) + return ret; + ret = c_finish_omp_masked (loc, block, + cclauses[C_OMP_CLAUSE_SPLIT_MASKED]); + OMP_MASKED_COMBINED (ret) = 1; + return ret; + } + } + if (!flag_openmp) /* flag_openmp_simd */ + { + c_parser_skip_to_pragma_eol (parser, false); + return NULL_TREE; + } + + clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL); + if (cclauses) + { + omp_split_clauses (loc, OMP_MASKED, mask, clauses, cclauses); + clauses = cclauses[C_OMP_CLAUSE_SPLIT_MASKED]; + } + + return c_finish_omp_masked (loc, c_parser_omp_structured_block (parser, + if_p), + clauses); +} + /* OpenMP 2.5: # pragma omp ordered new-line structured-block @@ -19237,7 +19339,36 @@ c_parser_omp_parallel (location_t loc, c_parser *parser, else if (c_parser_next_token_is (parser, CPP_NAME)) { const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); - if (cclauses == NULL && strcmp (p, "master") == 0) + if (cclauses == NULL && strcmp (p, "masked") == 0) + { + tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT]; + cclauses = cclauses_buf; + + c_parser_consume_token (parser); + if (!flag_openmp) /* flag_openmp_simd */ + return c_parser_omp_masked (loc, parser, p_name, mask, cclauses, + if_p); + block = c_begin_omp_parallel (); + tree ret = c_parser_omp_masked (loc, parser, p_name, mask, cclauses, + if_p); + stmt = c_finish_omp_parallel (loc, + cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL], + block); + if (ret == NULL) + return ret; + /* masked does have just filter clause, but during gimplification + isn't represented by a gimplification omp context, so for + #pragma omp parallel masked don't set OMP_PARALLEL_COMBINED, + so that + #pragma omp parallel masked + #pragma omp taskloop simd lastprivate (x) + isn't confused with + #pragma omp parallel masked taskloop simd lastprivate (x) */ + if (OMP_MASKED_COMBINED (ret)) + OMP_PARALLEL_COMBINED (stmt) = 1; + return stmt; + } + else if (cclauses == NULL && strcmp (p, "master") == 0) { tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT]; cclauses = cclauses_buf; @@ -21815,6 +21946,10 @@ c_parser_omp_construct (c_parser *parser, bool *if_p) strcpy (p_name, "#pragma omp"); stmt = c_parser_omp_loop (loc, parser, p_name, mask, NULL, if_p); break; + case PRAGMA_OMP_MASKED: + strcpy (p_name, "#pragma omp"); + stmt = c_parser_omp_masked (loc, parser, p_name, mask, NULL, if_p); + break; case PRAGMA_OMP_MASTER: strcpy (p_name, "#pragma omp"); stmt = c_parser_omp_master (loc, parser, p_name, mask, NULL, if_p); diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index eb5c87d..0c07af61 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -15158,6 +15158,7 @@ c_finish_omp_clauses (tree clauses, enum c_omp_region_type ort) case OMP_CLAUSE_THREADS: case OMP_CLAUSE_SIMD: case OMP_CLAUSE_HINT: + case OMP_CLAUSE_FILTER: case OMP_CLAUSE_DEFAULTMAP: case OMP_CLAUSE_BIND: case OMP_CLAUSE_NUM_GANGS: -- cgit v1.1 From 72be20e20299ec57b4bc9ba03d5b7d6bf10e97cc Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 13 Aug 2021 00:16:43 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 74ab186..ab61ac0 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,26 @@ +2021-08-12 Jakub Jelinek + + * c-parser.c (c_parser_omp_clause_name): Parse filter clause name. + (c_parser_omp_clause_filter): New function. + (c_parser_omp_all_clauses): Handle PRAGMA_OMP_CLAUSE_FILTER. + (OMP_MASKED_CLAUSE_MASK): Define. + (c_parser_omp_masked): New function. + (c_parser_omp_parallel): Handle parallel masked. + (c_parser_omp_construct): Handle PRAGMA_OMP_MASKED. + * c-typeck.c (c_finish_omp_clauses): Handle OMP_CLAUSE_FILTER. + +2021-08-12 Martin Uecker + + PR c/101838 + PR c/29970 + * c-typeck.c (c_expr_sizeof_type): Evaluate + size expressions for structs of variable size. + +2021-08-12 Tobias Burnus + + * c-parser.c (c_parser_omp_clause_proc_bind): Accept + 'primary' as alias for 'master'. + 2021-08-10 Martin Uecker PR c/29970 -- cgit v1.1 From e45483c7c4badc4bf2d6ced22360ce1ab172967f Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Tue, 17 Aug 2021 09:30:09 +0200 Subject: openmp: Implement OpenMP 5.1 scope construct This patch implements the OpenMP 5.1 scope construct, which is similar to worksharing constructs in many regards, but isn't one of them. The body of the construct is encountered by all threads though, it can be nested in itself or intermixed with taskgroup and worksharing etc. constructs can appear inside of it (but it can't be nested in worksharing etc. constructs). The main purpose of the construct is to allow reductions (normal and task ones) without the need to close the parallel and reopen another one. If it doesn't have task reductions, it can be implemented without any new library support, with nowait it just does the privatizations at the start if any and reductions before the end of the body, with without nowait emits a normal GOMP_barrier{,_cancel} at the end too. For task reductions, we need to ensure only one thread initializes the task reduction library data structures and other threads copy from that, so a new GOMP_scope_start routine is added to the library for that. It acts as if the start of the scope construct is a nowait worksharing construct (that is ok, it can't be nested in other worksharing constructs and all threads need to encounter the start in the same order) which does the task reduction initialization, but as the body can have other scope constructs and/or worksharing constructs, that is all where we use this dummy worksharing construct. With task reductions, the construct must not have nowait and ends with a GOMP_barrier{,_cancel}, followed by task reductions followed by GOMP_workshare_task_reduction_unregister. Only C/C++ FE support is done. 2021-08-17 Jakub Jelinek gcc/ * tree.def (OMP_SCOPE): New tree code. * tree.h (OMP_SCOPE_BODY, OMP_SCOPE_CLAUSES): Define. * tree-nested.c (convert_nonlocal_reference_stmt, convert_local_reference_stmt, convert_gimple_call): Handle GIMPLE_OMP_SCOPE. * tree-pretty-print.c (dump_generic_node): Handle OMP_SCOPE. * gimple.def (GIMPLE_OMP_SCOPE): New gimple code. * gimple.c (gimple_build_omp_scope): New function. (gimple_copy): Handle GIMPLE_OMP_SCOPE. * gimple.h (gimple_build_omp_scope): Declare. (gimple_has_substatements): Handle GIMPLE_OMP_SCOPE. (gimple_omp_scope_clauses, gimple_omp_scope_clauses_ptr, gimple_omp_scope_set_clauses): New inline functions. (CASE_GIMPLE_OMP): Add GIMPLE_OMP_SCOPE. * gimple-pretty-print.c (dump_gimple_omp_scope): New function. (pp_gimple_stmt_1): Handle GIMPLE_OMP_SCOPE. * gimple-walk.c (walk_gimple_stmt): Likewise. * gimple-low.c (lower_stmt): Likewise. * gimplify.c (is_gimple_stmt): Handle OMP_MASTER. (gimplify_scan_omp_clauses): For task reductions, handle OMP_SCOPE like ORT_WORKSHARE constructs. Adjust diagnostics for % allowing task reductions. Reject inscan reductions on scope. (omp_find_stores_stmt): Handle GIMPLE_OMP_SCOPE. (gimplify_omp_workshare, gimplify_expr): Handle OMP_SCOPE. * tree-inline.c (remap_gimple_stmt): Handle GIMPLE_OMP_SCOPE. (estimate_num_insns): Likewise. * omp-low.c (build_outer_var_ref): Look through GIMPLE_OMP_SCOPE contexts if var isn't privatized there. (check_omp_nesting_restrictions): Handle GIMPLE_OMP_SCOPE. (scan_omp_1_stmt): Likewise. (maybe_add_implicit_barrier_cancel): Look through outer scope constructs. (lower_omp_scope): New function. (lower_omp_task_reductions): Handle OMP_SCOPE. (lower_omp_1): Handle GIMPLE_OMP_SCOPE. (diagnose_sb_1, diagnose_sb_2): Likewise. * omp-expand.c (expand_omp_single): Support also GIMPLE_OMP_SCOPE. (expand_omp): Handle GIMPLE_OMP_SCOPE. (omp_make_gimple_edges): Likewise. * omp-builtins.def (BUILT_IN_GOMP_SCOPE_START): New built-in. gcc/c-family/ * c-pragma.h (enum pragma_kind): Add PRAGMA_OMP_SCOPE. * c-pragma.c (omp_pragmas): Add scope construct. * c-omp.c (omp_directives): Uncomment scope directive entry. gcc/c/ * c-parser.c (OMP_SCOPE_CLAUSE_MASK): Define. (c_parser_omp_scope): New function. (c_parser_omp_construct): Handle PRAGMA_OMP_SCOPE. gcc/cp/ * parser.c (OMP_SCOPE_CLAUSE_MASK): Define. (cp_parser_omp_scope): New function. (cp_parser_omp_construct, cp_parser_pragma): Handle PRAGMA_OMP_SCOPE. * pt.c (tsubst_expr): Handle OMP_SCOPE. gcc/testsuite/ * c-c++-common/gomp/nesting-2.c (foo): Add scope and masked construct tests. * c-c++-common/gomp/scan-1.c (f3): Add scope construct test.. * c-c++-common/gomp/cancel-1.c (f2): Add scope and masked construct tests. * c-c++-common/gomp/reduction-task-2.c (bar): Add scope construct test. Adjust diagnostics for the addition of scope. * c-c++-common/gomp/loop-1.c (f5): Add master, masked and scope construct tests. * c-c++-common/gomp/clause-dups-1.c (f1): Add scope construct test. * gcc.dg/gomp/nesting-1.c (f1, f2, f3): Add scope construct tests. * c-c++-common/gomp/scope-1.c: New test. * c-c++-common/gomp/scope-2.c: New test. * g++.dg/gomp/attrs-1.C (bar): Add scope construct tests. * g++.dg/gomp/attrs-2.C (bar): Likewise. * gfortran.dg/gomp/reduction4.f90: Adjust expected diagnostics. * gfortran.dg/gomp/reduction7.f90: Likewise. libgomp/ * Makefile.am (libgomp_la_SOURCES): Add scope.c * Makefile.in: Regenerated. * libgomp_g.h (GOMP_scope_start): Declare. * libgomp.map: Add GOMP_scope_start@@GOMP_5.1. * scope.c: New file. * testsuite/libgomp.c-c++-common/scope-1.c: New test. * testsuite/libgomp.c-c++-common/task-reduction-16.c: New test. --- gcc/c/c-parser.c | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index ca6e56a..33aeb09 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -19488,6 +19488,33 @@ c_parser_omp_single (location_t loc, c_parser *parser, bool *if_p) return add_stmt (stmt); } +/* OpenMP 5.1: + # pragma omp scope scope-clause[optseq] new-line + structured-block + + LOC is the location of the #pragma. +*/ + +#define OMP_SCOPE_CLAUSE_MASK \ + ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \ + | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT)) + +static tree +c_parser_omp_scope (location_t loc, c_parser *parser, bool *if_p) +{ + tree stmt = make_node (OMP_SCOPE); + SET_EXPR_LOCATION (stmt, loc); + TREE_TYPE (stmt) = void_type_node; + + OMP_SCOPE_CLAUSES (stmt) + = c_parser_omp_all_clauses (parser, OMP_SCOPE_CLAUSE_MASK, + "#pragma omp scope"); + OMP_SCOPE_BODY (stmt) = c_parser_omp_structured_block (parser, if_p); + + return add_stmt (stmt); +} + /* OpenMP 3.0: # pragma omp task task-clause[optseq] new-line @@ -21958,6 +21985,9 @@ c_parser_omp_construct (c_parser *parser, bool *if_p) strcpy (p_name, "#pragma omp"); stmt = c_parser_omp_parallel (loc, parser, p_name, mask, NULL, if_p); break; + case PRAGMA_OMP_SCOPE: + stmt = c_parser_omp_scope (loc, parser, if_p); + break; case PRAGMA_OMP_SECTIONS: strcpy (p_name, "#pragma omp"); stmt = c_parser_omp_sections (loc, parser, p_name, mask, NULL); -- cgit v1.1 From 2d14d64bf2d42a87ec58dd3760be12aeaa4a4279 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 18 Aug 2021 00:16:48 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index ab61ac0..caeac5b 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-08-17 Jakub Jelinek + + * c-parser.c (OMP_SCOPE_CLAUSE_MASK): Define. + (c_parser_omp_scope): New function. + (c_parser_omp_construct): Handle PRAGMA_OMP_SCOPE. + 2021-08-12 Jakub Jelinek * c-parser.c (c_parser_omp_clause_name): Parse filter clause name. -- cgit v1.1 From 1bf976a5de69ecd9b1e10eb7515357b98e78faf7 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Wed, 18 Aug 2021 10:20:50 +0200 Subject: openmp: Actually ignore pragma_stmt pragmas for which c_parser_pragma returns false Unlike the C++ FE, the C FE ignored pragmas (as if they weren't there) in pragma_stmt contexts if c*_parser_pragma returns false only when after labels, not inside of substatements of selection or loop statements. After making just that change, several gomp/goacc testcases started failing, because extra diagnostics has been emitted (in C, in C++ it was emitted already before). Say void foo (int x) { if (x) #pragma omp barrier } used to in C emit just an error that the pragma is not allowed in such contexts, but in C++ emitted both that and a parsing error that if (x) } is invalid. So, the rest of this patch is mostly about returning true after we report that that certain pragma is not allowed in pragma_stmt contexts, because for error-recovery it seems better to treat the pragma in that case as something that is the substatement of such if etc. c*_parser_pragma return value is only ever used for pragma_stmt context, in which false means act as if the pragma isn't there (e.g. has been handled already by preprocessor etc.), and true which means it was there. 2021-08-18 Jakub Jelinek gcc/c/ * c-parser.c (c_parser_statement_after_labels): Add restart label near the start of the function. If c_parser_pragma returns false, goto restart. (c_parser_pragma): For PRAGMA_OMP_CANCELLATION_POINT return what c_parser_omp_cancellation_point returned. For PRAGMA_OMP_DECLARE return what c_parser_omp_declare returned. Return true instead of false after emitting errors that the directive is not allowed in pragma_stmt context. (c_parser_omp_ordered): Return true instead of false after emitting errors that the directive is not allowed in pragma_stmt context. (c_parser_omp_target_update): Likewise. (c_parser_omp_target_enter_data, c_parser_omp_target_exit_data): Change return type from tree to bool, return false if the directive should be ignored in pragma_stmt contexts. (c_parser_omp_target): Adjust callers of c_parser_omp_target_*_data, return their result directly. (c_parser_omp_cancellation_point): Change return type from void to bool, return false if the directive should be ignored in pragma_stmt contexts. (c_parser_omp_declare): Likewise. gcc/cp/ * parser.c (cp_parser_omp_ordered): Return true instead of false after emitting errors that the directive is not allowed in pragma_stmt context. (cp_parser_omp_target_update): Likewise. (cp_parser_omp_cancellation_point): Change return type from void to bool, return false if the directive should be ignored in pragma_stmt contexts. (cp_parser_omp_target_enter_data, cp_parser_omp_target_exit_data): Change return type from tree to bool, return false if the directive should be ignored in pragma_stmt contexts. (cp_parser_omp_target): Adjust callers of cp_parser_omp_target_*_data, return their result directly. (cp_parser_pragma): For PRAGMA_OMP_CANCELLATION_POINT return what cp_parser_omp_cancellation_point returned. Return true instead of false after emitting errors that the directive is not allowed in pragma_stmt context. gcc/testsuite/ * c-c++-common/gomp/pr63326.c: Don't expect extra "before" errors in C++. * g++.dg/gomp/attrs-7.C: Don't expect one extra error. * g++.dg/gomp/barrier-2.C: Likewise. * gcc.dg/gomp/declare-simd-5.c: Likewise. * gcc.dg/gomp/barrier-2.c: Likewise. * gcc.dg/gomp/declare-variant-2.c: Likewise. --- gcc/c/c-parser.c | 70 ++++++++++++++++++++++++++++---------------------------- 1 file changed, 35 insertions(+), 35 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 33aeb09..565efc4 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -1582,10 +1582,10 @@ static void c_parser_omp_cancel (c_parser *); enum pragma_context { pragma_external, pragma_struct, pragma_param, pragma_stmt, pragma_compound }; static bool c_parser_pragma (c_parser *, enum pragma_context, bool *); -static void c_parser_omp_cancellation_point (c_parser *, enum pragma_context); +static bool c_parser_omp_cancellation_point (c_parser *, enum pragma_context); static bool c_parser_omp_target (c_parser *, enum pragma_context, bool *); static void c_parser_omp_end_declare_target (c_parser *); -static void c_parser_omp_declare (c_parser *, enum pragma_context); +static bool c_parser_omp_declare (c_parser *, enum pragma_context); static void c_parser_omp_requires (c_parser *); static bool c_parser_omp_ordered (c_parser *, enum pragma_context, bool *); static void c_parser_oacc_routine (c_parser *, enum pragma_context); @@ -6100,6 +6100,7 @@ c_parser_statement_after_labels (c_parser *parser, bool *if_p, if (c_parser_peek_token (parser)->type != CPP_OPEN_BRACE) add_debug_begin_stmt (loc); + restart: switch (c_parser_peek_token (parser)->type) { case CPP_OPEN_BRACE: @@ -6246,7 +6247,8 @@ c_parser_statement_after_labels (c_parser *parser, bool *if_p, c_parser_consume_token (parser); break; case CPP_PRAGMA: - c_parser_pragma (parser, pragma_stmt, if_p); + if (!c_parser_pragma (parser, pragma_stmt, if_p)) + goto restart; break; default: expr_stmt: @@ -12346,7 +12348,7 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) "%<#pragma %s%> may only be used in compound " "statements", construct); c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL); - return false; + return true; } goto bad_stmt; } @@ -12437,8 +12439,7 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) return false; case PRAGMA_OMP_CANCELLATION_POINT: - c_parser_omp_cancellation_point (parser, context); - return false; + return c_parser_omp_cancellation_point (parser, context); case PRAGMA_OMP_THREADPRIVATE: c_parser_omp_threadprivate (parser); @@ -12466,8 +12467,7 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) return false; case PRAGMA_OMP_DECLARE: - c_parser_omp_declare (parser, context); - return false; + return c_parser_omp_declare (parser, context); case PRAGMA_OMP_REQUIRES: if (context != pragma_external) @@ -12505,7 +12505,7 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) else c_parser_do_statement (parser, ivdep, unroll); } - return false; + return true; case PRAGMA_UNROLL: { @@ -12529,7 +12529,7 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) else c_parser_do_statement (parser, ivdep, unroll); } - return false; + return true; case PRAGMA_GCC_PCH_PREPROCESS: c_parser_error (parser, "%<#pragma GCC pch_preprocess%> must be first"); @@ -19125,7 +19125,7 @@ c_parser_omp_ordered (c_parser *parser, enum pragma_context context, "%<#pragma omp ordered%> with % clause may " "only be used in compound statements"); c_parser_skip_to_pragma_eol (parser, false); - return false; + return true; } tree clauses @@ -19655,7 +19655,7 @@ c_parser_omp_cancel (c_parser *parser) | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SECTIONS) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TASKGROUP)) -static void +static bool c_parser_omp_cancellation_point (c_parser *parser, enum pragma_context context) { location_t loc = c_parser_peek_token (parser)->location; @@ -19676,7 +19676,7 @@ c_parser_omp_cancellation_point (c_parser *parser, enum pragma_context context) { c_parser_error (parser, "expected %"); c_parser_skip_to_pragma_eol (parser); - return; + return false; } if (context != pragma_compound) @@ -19688,7 +19688,7 @@ c_parser_omp_cancellation_point (c_parser *parser, enum pragma_context context) else c_parser_error (parser, "expected declaration specifiers"); c_parser_skip_to_pragma_eol (parser, false); - return; + return true; } clauses @@ -19696,6 +19696,7 @@ c_parser_omp_cancellation_point (c_parser *parser, enum pragma_context context) "#pragma omp cancellation point"); c_finish_omp_cancellation_point (loc, clauses); + return true; } /* OpenMP 4.0: @@ -19981,7 +19982,7 @@ c_parser_omp_target_update (location_t loc, c_parser *parser, error_at (loc, "%<#pragma %s%> may only be used in compound statements", "omp target update"); c_parser_skip_to_pragma_eol (parser, false); - return false; + return true; } tree clauses @@ -20014,7 +20015,7 @@ c_parser_omp_target_update (location_t loc, c_parser *parser, | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT)) -static tree +static bool c_parser_omp_target_enter_data (location_t loc, c_parser *parser, enum pragma_context context) { @@ -20032,7 +20033,7 @@ c_parser_omp_target_enter_data (location_t loc, c_parser *parser, { c_parser_error (parser, "expected %"); c_parser_skip_to_pragma_eol (parser); - return NULL_TREE; + return false; } if (context == pragma_stmt) @@ -20040,7 +20041,7 @@ c_parser_omp_target_enter_data (location_t loc, c_parser *parser, error_at (loc, "%<#pragma %s%> may only be used in compound statements", "omp target enter data"); c_parser_skip_to_pragma_eol (parser, false); - return NULL_TREE; + return true; } tree clauses @@ -20079,7 +20080,7 @@ c_parser_omp_target_enter_data (location_t loc, c_parser *parser, error_at (loc, "%<#pragma omp target enter data%> must contain at least " "one % clause"); - return NULL_TREE; + return true; } tree stmt = make_node (OMP_TARGET_ENTER_DATA); @@ -20087,7 +20088,7 @@ c_parser_omp_target_enter_data (location_t loc, c_parser *parser, OMP_TARGET_ENTER_DATA_CLAUSES (stmt) = clauses; SET_EXPR_LOCATION (stmt, loc); add_stmt (stmt); - return stmt; + return true; } /* OpenMP 4.5: @@ -20100,7 +20101,7 @@ c_parser_omp_target_enter_data (location_t loc, c_parser *parser, | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \ | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT)) -static tree +static bool c_parser_omp_target_exit_data (location_t loc, c_parser *parser, enum pragma_context context) { @@ -20118,7 +20119,7 @@ c_parser_omp_target_exit_data (location_t loc, c_parser *parser, { c_parser_error (parser, "expected %"); c_parser_skip_to_pragma_eol (parser); - return NULL_TREE; + return false; } if (context == pragma_stmt) @@ -20126,7 +20127,7 @@ c_parser_omp_target_exit_data (location_t loc, c_parser *parser, error_at (loc, "%<#pragma %s%> may only be used in compound statements", "omp target exit data"); c_parser_skip_to_pragma_eol (parser, false); - return NULL_TREE; + return true; } tree clauses @@ -20167,7 +20168,7 @@ c_parser_omp_target_exit_data (location_t loc, c_parser *parser, error_at (loc, "%<#pragma omp target exit data%> must contain at least one " "% clause"); - return NULL_TREE; + return true; } tree stmt = make_node (OMP_TARGET_EXIT_DATA); @@ -20175,7 +20176,7 @@ c_parser_omp_target_exit_data (location_t loc, c_parser *parser, OMP_TARGET_EXIT_DATA_CLAUSES (stmt) = clauses; SET_EXPR_LOCATION (stmt, loc); add_stmt (stmt); - return stmt; + return true; } /* OpenMP 4.0: @@ -20333,14 +20334,12 @@ c_parser_omp_target (c_parser *parser, enum pragma_context context, bool *if_p) else if (strcmp (p, "enter") == 0) { c_parser_consume_token (parser); - c_parser_omp_target_enter_data (loc, parser, context); - return false; + return c_parser_omp_target_enter_data (loc, parser, context); } else if (strcmp (p, "exit") == 0) { c_parser_consume_token (parser); - c_parser_omp_target_exit_data (loc, parser, context); - return false; + return c_parser_omp_target_exit_data (loc, parser, context); } else if (strcmp (p, "update") == 0) { @@ -21599,7 +21598,7 @@ c_parser_omp_declare_reduction (c_parser *parser, enum pragma_context context) OpenMP 5.0 #pragma omp declare variant (identifier) match (context-selector) */ -static void +static bool c_parser_omp_declare (c_parser *parser, enum pragma_context context) { c_parser_consume_pragma (parser); @@ -21611,37 +21610,38 @@ c_parser_omp_declare (c_parser *parser, enum pragma_context context) /* c_parser_consume_token (parser); done in c_parser_omp_declare_simd. */ c_parser_omp_declare_simd (parser, context); - return; + return true; } if (strcmp (p, "reduction") == 0) { c_parser_consume_token (parser); c_parser_omp_declare_reduction (parser, context); - return; + return false; } if (!flag_openmp) /* flag_openmp_simd */ { c_parser_skip_to_pragma_eol (parser, false); - return; + return false; } if (strcmp (p, "target") == 0) { c_parser_consume_token (parser); c_parser_omp_declare_target (parser); - return; + return false; } if (strcmp (p, "variant") == 0) { /* c_parser_consume_token (parser); done in c_parser_omp_declare_simd. */ c_parser_omp_declare_simd (parser, context); - return; + return true; } } c_parser_error (parser, "expected %, %, " "% or %"); c_parser_skip_to_pragma_eol (parser); + return false; } /* OpenMP 5.0 -- cgit v1.1 From 5079b7781a2c506dcdfb241347d74c7891268225 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Wed, 18 Aug 2021 11:10:43 +0200 Subject: openmp: Add nothing directive support As has been clarified, it is intentional that nothing directive is accepted in substatements of selection and looping statements and after labels and is handled as if the directive just isn't there, so that void foo (int x) { if (x) #pragma omp metadirective when (...:nothing) when (...:parallel) bar (); } behaves consistently; declarative and stand-alone directives aren't allowed at that point, but constructs are parsed with the following statement as the construct body and nothing or missing default on metadirective therefore should handle the following statement as part of the if substatement instead of having nothing as the substatement and bar done unconditionally after the if. 2021-08-18 Jakub Jelinek gcc/c-family/ * c-pragma.h (enum pragma_kind): Add PRAGMA_OMP_NOTHING. * c-pragma.c (omp_pragmas): Add nothing directive. * c-omp.c (omp_directives): Uncomment nothing directive entry. gcc/c/ * c-parser.c (c_parser_omp_nothing): New function. (c_parser_pragma): Handle PRAGMA_OMP_NOTHING. gcc/cp/ * parser.c (cp_parser_omp_nothing): New function. (cp_parser_pragma): Handle PRAGMA_OMP_NOTHING. gcc/testsuite/ * c-c++-common/gomp/nothing-1.c: New test. * g++.dg/gomp/attrs-1.C (bar): Add nothing directive test. * g++.dg/gomp/attrs-2.C (bar): Likewise. * g++.dg/gomp/attrs-9.C: Likewise. libgomp/ * testsuite/libgomp.c-c++-common/nothing-1.c: New test. --- gcc/c/c-parser.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 565efc4..d5f51b1 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -1578,6 +1578,7 @@ static tree c_parser_omp_for_loop (location_t, c_parser *, enum tree_code, static void c_parser_omp_taskwait (c_parser *); static void c_parser_omp_taskyield (c_parser *); static void c_parser_omp_cancel (c_parser *); +static void c_parser_omp_nothing (c_parser *); enum pragma_context { pragma_external, pragma_struct, pragma_param, pragma_stmt, pragma_compound }; @@ -12480,6 +12481,10 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) c_parser_omp_requires (parser); return false; + case PRAGMA_OMP_NOTHING: + c_parser_omp_nothing (parser); + return false; + case PRAGMA_OMP_ORDERED: return c_parser_omp_ordered (parser, context, if_p); @@ -21908,6 +21913,16 @@ c_parser_omp_taskloop (location_t loc, c_parser *parser, return ret; } +/* OpenMP 5.1 + #pragma omp nothing new-line */ + +static void +c_parser_omp_nothing (c_parser *parser) +{ + c_parser_consume_pragma (parser); + c_parser_skip_to_pragma_eol (parser); +} + /* Main entry point to parsing most OpenMP pragmas. */ static void -- cgit v1.1 From 6e529985d8956f74492e3176026fc02dc8f01b6c Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 19 Aug 2021 00:16:42 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index caeac5b..53abd1a 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,32 @@ +2021-08-18 Jakub Jelinek + + * c-parser.c (c_parser_omp_nothing): New function. + (c_parser_pragma): Handle PRAGMA_OMP_NOTHING. + +2021-08-18 Jakub Jelinek + + * c-parser.c (c_parser_statement_after_labels): Add restart label + near the start of the function. If c_parser_pragma returns false, + goto restart. + (c_parser_pragma): For PRAGMA_OMP_CANCELLATION_POINT return what + c_parser_omp_cancellation_point returned. For PRAGMA_OMP_DECLARE + return what c_parser_omp_declare returned. Return true instead of + false after emitting errors that the directive is not allowed in + pragma_stmt context. + (c_parser_omp_ordered): Return true instead of + false after emitting errors that the directive is not allowed in + pragma_stmt context. + (c_parser_omp_target_update): Likewise. + (c_parser_omp_target_enter_data, c_parser_omp_target_exit_data): + Change return type from tree to bool, return false if the + directive should be ignored in pragma_stmt contexts. + (c_parser_omp_target): Adjust callers of c_parser_omp_target_*_data, + return their result directly. + (c_parser_omp_cancellation_point): Change return type from void to + bool, return false if the directive should be ignored in pragma_stmt + contexts. + (c_parser_omp_declare): Likewise. + 2021-08-17 Jakub Jelinek * c-parser.c (OMP_SCOPE_CLAUSE_MASK): Define. -- cgit v1.1 From c04d766942274da89b236c4cb7e954b26da397c7 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 19 Aug 2021 10:38:19 +0200 Subject: openmp: Fix ICE on requires clause with atomic_default_mem_order ( When working on error directive, I've noticed the C FE ICEs on #pragma omp requires atomic_default_mem_order ( where it tries to peek 2nd token after the CPP_PRAGMA_EOL (or CPP_EOF) in there in order to improve error-recovery on say atomic_default_mem_order (acquire) or atomic_default_mem_order (seqcst) etc. The C++ FE didn't ICE, but it is better to follow the same thing there. 2021-08-19 Jakub Jelinek gcc/c/ * c-parser.c (c_parser_omp_requires): Don't call c_parser_peek_2nd_token and optionally consume token if current token is CPP_EOF, CPP_PRAGMA_EOL or CPP_CLOSE_PAREN. gcc/cp/ * parser.c (cp_parser_omp_requires): Don't call cp_lexer_nth_token_is and optionally consume token if current token is CPP_EOF, CPP_PRAGMA_EOL or CPP_CLOSE_PAREN. gcc/testsuite/ * c-c++-common/gomp/requires-3.c: Add testcase for atomic_default_mem_order ( at the end of line without corresponding ). --- gcc/c/c-parser.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index d5f51b1..407f279 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -21710,9 +21710,18 @@ c_parser_omp_requires (c_parser *parser) error_at (c_parser_peek_token (parser)->location, "expected %, % or " "%"); - if (c_parser_peek_2nd_token (parser)->type - == CPP_CLOSE_PAREN) - c_parser_consume_token (parser); + switch (c_parser_peek_token (parser)->type) + { + case CPP_EOF: + case CPP_PRAGMA_EOL: + case CPP_CLOSE_PAREN: + break; + default: + if (c_parser_peek_2nd_token (parser)->type + == CPP_CLOSE_PAREN) + c_parser_consume_token (parser); + break; + } } else c_parser_consume_token (parser); -- cgit v1.1 From b57fba5e376c7277168c14e207979e1505e6fe1d Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Fri, 20 Aug 2021 00:16:28 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 53abd1a..1b13446 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,9 @@ +2021-08-19 Jakub Jelinek + + * c-parser.c (c_parser_omp_requires): Don't call + c_parser_peek_2nd_token and optionally consume token if current + token is CPP_EOF, CPP_PRAGMA_EOL or CPP_CLOSE_PAREN. + 2021-08-18 Jakub Jelinek * c-parser.c (c_parser_omp_nothing): New function. -- cgit v1.1 From f9400e4e4705845f2b0cdc4eab30c214e0e4cbe0 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 20 Aug 2021 11:29:48 +0200 Subject: openmp: Diagnose some superfluous commas in OpenMP parsing While working on error directive, I've noticed a few spots in OpenMP parsing where we consume and don't diagnose superfluous commas at the end (either of depend sink arguments or at the end of requires pragma). 2021-08-20 Jakub Jelinek gcc/c/ * c-parser.c (c_parser_omp_clause_depend_sink): Reject spurious comma at the end of list. (c_parser_omp_requires): Likewise. gcc/cp/ * parser.c (cp_parser_omp_clause_depend_sink): Reject spurious comma at the end of list. Don't parse closing paren here... (cp_parser_omp_clause_depend): ... but here instead. gcc/testsuite/ * c-c++-common/gomp/sink-5.c: New test. * c-c++-common/gomp/requires-3.c: Add test for spurious comma at the end of pragma line. --- gcc/c/c-parser.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 407f279..ab79e9c 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -15481,7 +15481,9 @@ c_parser_omp_clause_depend_sink (c_parser *parser, location_t clause_loc, OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1; } - if (c_parser_next_token_is_not (parser, CPP_COMMA)) + if (c_parser_next_token_is_not (parser, CPP_COMMA) + || c_parser_peek_2nd_token (parser)->type != CPP_NAME + || c_parser_peek_2nd_token (parser)->id_kind != C_ID_ID) break; c_parser_consume_token (parser); @@ -21663,7 +21665,9 @@ c_parser_omp_requires (c_parser *parser) location_t loc = c_parser_peek_token (parser)->location; while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL)) { - if (!first && c_parser_next_token_is (parser, CPP_COMMA)) + if (!first + && c_parser_next_token_is (parser, CPP_COMMA) + && c_parser_peek_2nd_token (parser)->type == CPP_NAME) c_parser_consume_token (parser); first = false; -- cgit v1.1 From 0d973c0a0d90a0a302e7eda1a4d9709be3c5b102 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 20 Aug 2021 11:36:52 +0200 Subject: openmp: Implement the error directive This patch implements the error directive. Depending on clauses it is either a compile time diagnostics (in that case diagnosed right away) or runtime diagnostics (libgomp API call that diagnoses at runtime), and either fatal or warning (error or warning at compile time or fatal error vs. error at runtime) and either has no message or user supplied message (this kind of e.g. deprecated attribute). The directive is also stand-alone directive when at runtime while utility (thus disappears from the IL as if it wasn't there for parsing like nothing directive) at compile time. There are some clarifications in the works ATM, so this patch doesn't yet require that for compile time diagnostics the user message must be a constant string literal, there are uncertainities on what exactly is valid argument of message clause (whether just const char * type, convertible to const char *, qualified/unqualified const char * or char * or what else) and what to do in templates. Currently even in templates it is diagnosed right away for compile time diagnostics, if we'll need to substitute it, we'd need to queue something into the IL, have pt.c handle it and diagnose only later. 2021-08-20 Jakub Jelinek gcc/ * omp-builtins.def (BUILT_IN_GOMP_WARNING, BUILT_IN_GOMP_ERROR): New builtins. gcc/c-family/ * c-pragma.h (enum pragma_kind): Add PRAGMA_OMP_ERROR. * c-pragma.c (omp_pragmas): Add error directive. * c-omp.c (omp_directives): Uncomment error directive entry. gcc/c/ * c-parser.c (c_parser_omp_error): New function. (c_parser_pragma): Handle PRAGMA_OMP_ERROR. gcc/cp/ * parser.c (cp_parser_handle_statement_omp_attributes): Determine if PRAGMA_OMP_ERROR directive is C_OMP_DIR_STANDALONE. (cp_parser_omp_error): New function. (cp_parser_pragma): Handle PRAGMA_OMP_ERROR. gcc/fortran/ * types.def (BT_FN_VOID_CONST_PTR_SIZE): New DEF_FUNCTION_TYPE_2. * f95-lang.c (ATTR_COLD_NORETURN_NOTHROW_LEAF_LIST): Define. gcc/testsuite/ * c-c++-common/gomp/error-1.c: New test. * c-c++-common/gomp/error-2.c: New test. * c-c++-common/gomp/error-3.c: New test. * g++.dg/gomp/attrs-1.C (bar): Add error directive test. * g++.dg/gomp/attrs-2.C (bar): Add error directive test. * g++.dg/gomp/attrs-13.C: New test. * g++.dg/gomp/error-1.C: New test. libgomp/ * libgomp.map (GOMP_5.1): Add GOMP_error and GOMP_warning. * libgomp_g.h (GOMP_warning, GOMP_error): Declare. * error.c (GOMP_warning, GOMP_error): New functions. * testsuite/libgomp.c-c++-common/error-1.c: New test. --- gcc/c/c-parser.c | 171 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 171 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index ab79e9c..c578307 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -1588,6 +1588,7 @@ static bool c_parser_omp_target (c_parser *, enum pragma_context, bool *); static void c_parser_omp_end_declare_target (c_parser *); static bool c_parser_omp_declare (c_parser *, enum pragma_context); static void c_parser_omp_requires (c_parser *); +static bool c_parser_omp_error (c_parser *, enum pragma_context); static bool c_parser_omp_ordered (c_parser *, enum pragma_context, bool *); static void c_parser_oacc_routine (c_parser *, enum pragma_context); @@ -12485,6 +12486,9 @@ c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p) c_parser_omp_nothing (parser); return false; + case PRAGMA_OMP_ERROR: + return c_parser_omp_error (parser, context); + case PRAGMA_OMP_ORDERED: return c_parser_omp_ordered (parser, context, if_p); @@ -21936,6 +21940,173 @@ c_parser_omp_nothing (c_parser *parser) c_parser_skip_to_pragma_eol (parser); } +/* OpenMP 5.1 + #pragma omp error clauses[optseq] new-line */ + +static bool +c_parser_omp_error (c_parser *parser, enum pragma_context context) +{ + int at_compilation = -1; + int severity_fatal = -1; + tree message = NULL_TREE; + bool first = true; + bool bad = false; + location_t loc = c_parser_peek_token (parser)->location; + + c_parser_consume_pragma (parser); + + while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL)) + { + if (!first + && c_parser_next_token_is (parser, CPP_COMMA) + && c_parser_peek_2nd_token (parser)->type == CPP_NAME) + c_parser_consume_token (parser); + + first = false; + + if (!c_parser_next_token_is (parser, CPP_NAME)) + break; + + const char *p + = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); + location_t cloc = c_parser_peek_token (parser)->location; + static const char *args[] = { + "execution", "compilation", "warning", "fatal" + }; + int *v = NULL; + int idx = 0, n = -1; + tree m = NULL_TREE; + + if (!strcmp (p, "at")) + v = &at_compilation; + else if (!strcmp (p, "severity")) + { + v = &severity_fatal; + idx += 2; + } + else if (strcmp (p, "message")) + { + error_at (cloc, + "expected %, % or % clause"); + c_parser_skip_to_pragma_eol (parser, false); + return false; + } + + c_parser_consume_token (parser); + + matching_parens parens; + if (parens.require_open (parser)) + { + if (v == NULL) + { + location_t expr_loc = c_parser_peek_token (parser)->location; + c_expr expr = c_parser_expr_no_commas (parser, NULL); + expr = convert_lvalue_to_rvalue (expr_loc, expr, true, true); + m = convert (const_string_type_node, expr.value); + m = c_fully_fold (m, false, NULL); + } + else + { + if (c_parser_next_token_is (parser, CPP_NAME)) + { + tree val = c_parser_peek_token (parser)->value; + const char *q = IDENTIFIER_POINTER (val); + + if (!strcmp (q, args[idx])) + n = 0; + else if (!strcmp (q, args[idx + 1])) + n = 1; + } + if (n == -1) + { + error_at (c_parser_peek_token (parser)->location, + "expected %qs or %qs", args[idx], args[idx + 1]); + bad = true; + switch (c_parser_peek_token (parser)->type) + { + case CPP_EOF: + case CPP_PRAGMA_EOL: + case CPP_CLOSE_PAREN: + break; + default: + if (c_parser_peek_2nd_token (parser)->type + == CPP_CLOSE_PAREN) + c_parser_consume_token (parser); + break; + } + } + else + c_parser_consume_token (parser); + } + + parens.skip_until_found_close (parser); + + if (v == NULL) + { + if (message) + { + error_at (cloc, "too many %qs clauses", p); + bad = true; + } + else + message = m; + } + else if (n != -1) + { + if (*v != -1) + { + error_at (cloc, "too many %qs clauses", p); + bad = true; + } + else + *v = n; + } + } + else + bad = true; + } + c_parser_skip_to_pragma_eol (parser); + if (bad) + return true; + + if (at_compilation == -1) + at_compilation = 1; + if (severity_fatal == -1) + severity_fatal = 1; + if (!at_compilation) + { + if (context != pragma_compound) + { + error_at (loc, "%<#pragma omp error%> with % clause " + "may only be used in compound statements"); + return true; + } + tree fndecl + = builtin_decl_explicit (severity_fatal ? BUILT_IN_GOMP_ERROR + : BUILT_IN_GOMP_WARNING); + if (!message) + message = build_zero_cst (const_string_type_node); + tree stmt = build_call_expr_loc (loc, fndecl, 2, message, + build_all_ones_cst (size_type_node)); + add_stmt (stmt); + return true; + } + const char *msg = NULL; + if (message) + { + msg = c_getstr (message); + if (msg == NULL) + msg = _(""); + } + if (msg) + emit_diagnostic (severity_fatal ? DK_ERROR : DK_WARNING, loc, 0, + "% encountered: %s", msg); + else + emit_diagnostic (severity_fatal ? DK_ERROR : DK_WARNING, loc, 0, + "% encountered"); + return false; +} + /* Main entry point to parsing most OpenMP pragmas. */ static void -- cgit v1.1 From 7c9e1645836d7746838acebb7018b1774490ab5c Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 21 Aug 2021 00:16:29 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 1b13446..e5e12b3 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,14 @@ +2021-08-20 Jakub Jelinek + + * c-parser.c (c_parser_omp_error): New function. + (c_parser_pragma): Handle PRAGMA_OMP_ERROR. + +2021-08-20 Jakub Jelinek + + * c-parser.c (c_parser_omp_clause_depend_sink): Reject spurious + comma at the end of list. + (c_parser_omp_requires): Likewise. + 2021-08-19 Jakub Jelinek * c-parser.c (c_parser_omp_requires): Don't call -- cgit v1.1 From 972eab51f53d1db26864ec7d62d40c2ff83407ec Mon Sep 17 00:00:00 2001 From: Martin Uecker Date: Sun, 22 Aug 2021 23:47:58 +0200 Subject: Correct treatment of qualifiers for pointers to arrays for C2X [PR98397] 2021-08-22 Martin Uecker gcc/c/ PR c/98397 * c-typeck.c (comp_target_types): Change pedwarn to pedwarn_c11 for pointers to arrays with qualifiers. (build_conditional_expr): For C23 don't lose qualifiers for pointers to arrays when the other pointer is a void pointer. Update warnings. (convert_for_assignment): Update warnings for C2X when converting from void* with qualifiers to a pointer to array with the same qualifiers. gcc/testsuite/ PR c/98397 * gcc.dg/c11-qual-1.c: New test. * gcc.dg/c2x-qual-1.c: New test. * gcc.dg/c2x-qual-2.c: New test. * gcc.dg/c2x-qual-3.c: New test. * gcc.dg/c2x-qual-4.c: New test. * gcc.dg/c2x-qual-5.c: New test. * gcc.dg/c2x-qual-6.c: New test. * gcc.dg/c2x-qual-7.c: New test. * gcc.dg/pointer-array-quals-1.c: Remove unnecessary flag. * gcc.dg/pointer-array-quals-2.c: Remove unnecessary flag. --- gcc/c/c-typeck.c | 188 +++++++++++++++++++++++++++---------------------------- 1 file changed, 93 insertions(+), 95 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 0c07af61..d9f26d6 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -1328,8 +1328,8 @@ comp_target_types (location_t location, tree ttl, tree ttr) val = comptypes_check_enum_int (mvl, mvr, &enum_and_int_p); if (val == 1 && val_ped != 1) - pedwarn (location, OPT_Wpedantic, "pointers to arrays with different qualifiers " - "are incompatible in ISO C"); + pedwarn_c11 (location, OPT_Wpedantic, "invalid use of pointers to arrays with different qualifiers " + "in ISO C before C2X"); if (val == 2) pedwarn (location, OPT_Wpedantic, "types are not quite compatible"); @@ -5406,39 +5406,41 @@ build_conditional_expr (location_t colon_loc, tree ifexp, bool ifexp_bcp, "used in conditional expression"); return error_mark_node; } - else if (VOID_TYPE_P (TREE_TYPE (type1)) - && !TYPE_ATOMIC (TREE_TYPE (type1))) - { - if ((TREE_CODE (TREE_TYPE (type2)) == ARRAY_TYPE) - && (TYPE_QUALS (strip_array_types (TREE_TYPE (type2))) - & ~TYPE_QUALS (TREE_TYPE (type1)))) - warning_at (colon_loc, OPT_Wdiscarded_array_qualifiers, - "pointer to array loses qualifier " - "in conditional expression"); - - if (TREE_CODE (TREE_TYPE (type2)) == FUNCTION_TYPE) + else if ((VOID_TYPE_P (TREE_TYPE (type1)) + && !TYPE_ATOMIC (TREE_TYPE (type1))) + || (VOID_TYPE_P (TREE_TYPE (type2)) + && !TYPE_ATOMIC (TREE_TYPE (type2)))) + { + tree t1 = TREE_TYPE (type1); + tree t2 = TREE_TYPE (type2); + if (!(VOID_TYPE_P (t1) + && !TYPE_ATOMIC (t1))) + { + /* roles are swapped */ + t1 = t2; + t2 = TREE_TYPE (type1); + } + tree t2_stripped = strip_array_types (t2); + if ((TREE_CODE (t2) == ARRAY_TYPE) + && (TYPE_QUALS (t2_stripped) & ~TYPE_QUALS (t1))) + { + if (!flag_isoc2x) + warning_at (colon_loc, OPT_Wdiscarded_array_qualifiers, + "pointer to array loses qualifier " + "in conditional expression"); + else if (warn_c11_c2x_compat > 0) + warning_at (colon_loc, OPT_Wc11_c2x_compat, + "pointer to array loses qualifier " + "in conditional expression in ISO C before C2X"); + } + if (TREE_CODE (t2) == FUNCTION_TYPE) pedwarn (colon_loc, OPT_Wpedantic, "ISO C forbids conditional expr between " "% and function pointer"); - result_type = build_pointer_type (qualify_type (TREE_TYPE (type1), - TREE_TYPE (type2))); - } - else if (VOID_TYPE_P (TREE_TYPE (type2)) - && !TYPE_ATOMIC (TREE_TYPE (type2))) - { - if ((TREE_CODE (TREE_TYPE (type1)) == ARRAY_TYPE) - && (TYPE_QUALS (strip_array_types (TREE_TYPE (type1))) - & ~TYPE_QUALS (TREE_TYPE (type2)))) - warning_at (colon_loc, OPT_Wdiscarded_array_qualifiers, - "pointer to array loses qualifier " - "in conditional expression"); - - if (TREE_CODE (TREE_TYPE (type1)) == FUNCTION_TYPE) - pedwarn (colon_loc, OPT_Wpedantic, - "ISO C forbids conditional expr between " - "% and function pointer"); - result_type = build_pointer_type (qualify_type (TREE_TYPE (type2), - TREE_TYPE (type1))); + /* for array, use qualifiers of element type */ + if (flag_isoc2x) + t2 = t2_stripped; + result_type = build_pointer_type (qualify_type (t1, t2)); } /* Objective-C pointer comparisons are a bit more lenient. */ else if (objc_have_common_type (type1, type2, -3, NULL_TREE)) @@ -6797,27 +6799,40 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, /* This macro is used to emit diagnostics to ensure that all format strings are complete sentences, visible to gettext and checked at - compile time. It is the same as PEDWARN_FOR_ASSIGNMENT but with an - extra parameter to enumerate qualifiers. */ -#define PEDWARN_FOR_QUALIFIERS(LOCATION, PLOC, OPT, AR, AS, IN, RE, QUALS) \ + compile time. It can be called with 'pedwarn' or 'warning_at'. */ +#define WARNING_FOR_QUALIFIERS(PEDWARN, LOCATION, PLOC, OPT, AR, AS, IN, RE, QUALS) \ do { \ switch (errtype) \ { \ case ic_argpass: \ - { \ - auto_diagnostic_group d; \ - if (pedwarn (PLOC, OPT, AR, parmnum, rname, QUALS)) \ - inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \ - } \ + { \ + auto_diagnostic_group d; \ + if (PEDWARN) { \ + if (pedwarn (PLOC, OPT, AR, parmnum, rname, QUALS)) \ + inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \ + } else { \ + if (warning_at (PLOC, OPT, AR, parmnum, rname, QUALS)) \ + inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \ + } \ + } \ break; \ case ic_assign: \ - pedwarn (LOCATION, OPT, AS, QUALS); \ + if (PEDWARN) \ + pedwarn (LOCATION, OPT, AS, QUALS); \ + else \ + warning_at (LOCATION, OPT, AS, QUALS); \ break; \ case ic_init: \ - pedwarn (LOCATION, OPT, IN, QUALS); \ + if (PEDWARN) \ + pedwarn (LOCATION, OPT, IN, QUALS); \ + else \ + warning_at (LOCATION, OPT, IN, QUALS); \ break; \ case ic_return: \ - pedwarn (LOCATION, OPT, RE, QUALS); \ + if (PEDWARN) \ + pedwarn (LOCATION, OPT, RE, QUALS); \ + else \ + warning_at (LOCATION, OPT, RE, QUALS); \ break; \ default: \ gcc_unreachable (); \ @@ -6826,32 +6841,11 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, /* This macro is used to emit diagnostics to ensure that all format strings are complete sentences, visible to gettext and checked at - compile time. It is the same as PEDWARN_FOR_QUALIFIERS but uses - warning_at instead of pedwarn. */ -#define WARNING_FOR_QUALIFIERS(LOCATION, PLOC, OPT, AR, AS, IN, RE, QUALS) \ - do { \ - switch (errtype) \ - { \ - case ic_argpass: \ - { \ - auto_diagnostic_group d; \ - if (warning_at (PLOC, OPT, AR, parmnum, rname, QUALS)) \ - inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \ - } \ - break; \ - case ic_assign: \ - warning_at (LOCATION, OPT, AS, QUALS); \ - break; \ - case ic_init: \ - warning_at (LOCATION, OPT, IN, QUALS); \ - break; \ - case ic_return: \ - warning_at (LOCATION, OPT, RE, QUALS); \ - break; \ - default: \ - gcc_unreachable (); \ - } \ - } while (0) + compile time. It is the same as PEDWARN_FOR_ASSIGNMENT but with an + extra parameter to enumerate qualifiers. */ +#define PEDWARN_FOR_QUALIFIERS(LOCATION, PLOC, OPT, AR, AS, IN, RE, QUALS) \ + WARNING_FOR_QUALIFIERS (true, LOCATION, PLOC, OPT, AR, AS, IN, RE, QUALS) + if (TREE_CODE (rhs) == EXCESS_PRECISION_EXPR) rhs = TREE_OPERAND (rhs, 0); @@ -7370,17 +7364,18 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, if (TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttr) & ~TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttl)) - WARNING_FOR_QUALIFIERS (location, expr_loc, - OPT_Wdiscarded_array_qualifiers, - G_("passing argument %d of %qE discards " + WARNING_FOR_QUALIFIERS (flag_isoc2x, + location, expr_loc, + OPT_Wdiscarded_array_qualifiers, + G_("passing argument %d of %qE discards " "%qv qualifier from pointer target type"), - G_("assignment discards %qv qualifier " + G_("assignment discards %qv qualifier " "from pointer target type"), - G_("initialization discards %qv qualifier " + G_("initialization discards %qv qualifier " "from pointer target type"), - G_("return discards %qv qualifier from " + G_("return discards %qv qualifier from " "pointer target type"), - TYPE_QUALS (ttr) & ~TYPE_QUALS (ttl)); + TYPE_QUALS (ttr) & ~TYPE_QUALS (ttl)); } else if (pedantic && ((VOID_TYPE_P (ttl) && TREE_CODE (ttr) == FUNCTION_TYPE) @@ -7403,28 +7398,31 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, else if (TREE_CODE (ttr) != FUNCTION_TYPE && TREE_CODE (ttl) != FUNCTION_TYPE) { + /* Assignments between atomic and non-atomic objects are OK. */ + bool warn_quals_ped = TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttr) + & ~TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttl); + bool warn_quals = TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttr) + & ~TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (strip_array_types (ttl)); + /* Don't warn about loss of qualifier for conversions from qualified void* to pointers to arrays with corresponding - qualifier on the element type. */ - if (!pedantic) - ttl = strip_array_types (ttl); + qualifier on the element type (except for pedantic before C23). */ + if (warn_quals || (warn_quals_ped && pedantic && !flag_isoc2x)) + PEDWARN_FOR_QUALIFIERS (location, expr_loc, + OPT_Wdiscarded_qualifiers, + G_("passing argument %d of %qE discards " + "%qv qualifier from pointer target type"), + G_("assignment discards %qv qualifier " + "from pointer target type"), + G_("initialization discards %qv qualifier " + "from pointer target type"), + G_("return discards %qv qualifier from " + "pointer target type"), + TYPE_QUALS (ttr) & ~TYPE_QUALS (ttl)); + else if (warn_quals_ped) + pedwarn_c11 (location, OPT_Wc11_c2x_compat, + "array with qualifier on the element is not qualified before C2X"); - /* Assignments between atomic and non-atomic objects are OK. */ - if (TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttr) - & ~TYPE_QUALS_NO_ADDR_SPACE_NO_ATOMIC (ttl)) - { - PEDWARN_FOR_QUALIFIERS (location, expr_loc, - OPT_Wdiscarded_qualifiers, - G_("passing argument %d of %qE discards " - "%qv qualifier from pointer target type"), - G_("assignment discards %qv qualifier " - "from pointer target type"), - G_("initialization discards %qv qualifier " - "from pointer target type"), - G_("return discards %qv qualifier from " - "pointer target type"), - TYPE_QUALS (ttr) & ~TYPE_QUALS (ttl)); - } /* If this is not a case of ignoring a mismatch in signedness, no warning. */ else if (VOID_TYPE_P (ttl) || VOID_TYPE_P (ttr) -- cgit v1.1 From 5b2876f96c16f43c7b4810237ac92bb8f9d18c01 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Mon, 23 Aug 2021 00:16:28 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index e5e12b3..6ca524b 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,13 @@ +2021-08-22 Martin Uecker + + PR c/98397 + * c-typeck.c (comp_target_types): Change pedwarn to pedwarn_c11 + for pointers to arrays with qualifiers. + (build_conditional_expr): For C23 don't lose qualifiers for pointers + to arrays when the other pointer is a void pointer. Update warnings. + (convert_for_assignment): Update warnings for C2X when converting from + void* with qualifiers to a pointer to array with the same qualifiers. + 2021-08-20 Jakub Jelinek * c-parser.c (c_parser_omp_error): New function. -- cgit v1.1 From 3bc75533d1f87f0617be6c1af98804f9127ec637 Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Mon, 23 Aug 2021 10:16:24 +0200 Subject: openmp: Add support for strict modifier on grainsize/num_tasks clauses With strict: modifier on these clauses, the standard is explicit about how many iterations (and which) each generated task of taskloop directive should contain. For num_tasks it actually matches what we were already implementing, but for grainsize it does not (and even violates the old rule - without strict it requires that the number of iterations (unspecified which exactly) handled by each generated task is >= grainsize argument and < 2 * grainsize argument, with strict: it requires that each generated task handles exactly == grainsize argument iterations, except for the generated task handling the last iteration which can handles <= grainsize iterations). The following patch implements it for C and C++. 2021-08-23 Jakub Jelinek gcc/ * tree.h (OMP_CLAUSE_GRAINSIZE_STRICT): Define. (OMP_CLAUSE_NUM_TASKS_STRICT): Define. * tree-pretty-print.c (dump_omp_clause) : Print strict: modifier. * omp-expand.c (expand_task_call): Use GOMP_TASK_FLAG_STRICT in iflags if either grainsize or num_tasks clause has the strict modifier. gcc/c/ * c-parser.c (c_parser_omp_clause_num_tasks, c_parser_omp_clause_grainsize): Parse the optional strict: modifier. gcc/cp/ * parser.c (cp_parser_omp_clause_num_tasks, cp_parser_omp_clause_grainsize): Parse the optional strict: modifier. include/ * gomp-constants.h (GOMP_TASK_FLAG_STRICT): Define. libgomp/ * taskloop.c (GOMP_taskloop): Handle GOMP_TASK_FLAG_STRICT. * testsuite/libgomp.c-c++-common/taskloop-4.c (main): Fix up comment. * testsuite/libgomp.c-c++-common/taskloop-5.c: New test. --- gcc/c/c-parser.c | 34 ++++++++++++++++++++++++++++++++-- 1 file changed, 32 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index c578307..356cf25 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -13786,7 +13786,10 @@ c_parser_omp_clause_num_threads (c_parser *parser, tree list) } /* OpenMP 4.5: - num_tasks ( expression ) */ + num_tasks ( expression ) + + OpenMP 5.1: + num_tasks ( strict : expression ) */ static tree c_parser_omp_clause_num_tasks (c_parser *parser, tree list) @@ -13795,6 +13798,17 @@ c_parser_omp_clause_num_tasks (c_parser *parser, tree list) matching_parens parens; if (parens.require_open (parser)) { + bool strict = false; + if (c_parser_next_token_is (parser, CPP_NAME) + && c_parser_peek_2nd_token (parser)->type == CPP_COLON + && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value), + "strict") == 0) + { + strict = true; + c_parser_consume_token (parser); + c_parser_consume_token (parser); + } + location_t expr_loc = c_parser_peek_token (parser)->location; c_expr expr = c_parser_expr_no_commas (parser, NULL); expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true); @@ -13824,6 +13838,7 @@ c_parser_omp_clause_num_tasks (c_parser *parser, tree list) c = build_omp_clause (num_tasks_loc, OMP_CLAUSE_NUM_TASKS); OMP_CLAUSE_NUM_TASKS_EXPR (c) = t; + OMP_CLAUSE_NUM_TASKS_STRICT (c) = strict; OMP_CLAUSE_CHAIN (c) = list; list = c; } @@ -13832,7 +13847,10 @@ c_parser_omp_clause_num_tasks (c_parser *parser, tree list) } /* OpenMP 4.5: - grainsize ( expression ) */ + grainsize ( expression ) + + OpenMP 5.1: + grainsize ( strict : expression ) */ static tree c_parser_omp_clause_grainsize (c_parser *parser, tree list) @@ -13841,6 +13859,17 @@ c_parser_omp_clause_grainsize (c_parser *parser, tree list) matching_parens parens; if (parens.require_open (parser)) { + bool strict = false; + if (c_parser_next_token_is (parser, CPP_NAME) + && c_parser_peek_2nd_token (parser)->type == CPP_COLON + && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value), + "strict") == 0) + { + strict = true; + c_parser_consume_token (parser); + c_parser_consume_token (parser); + } + location_t expr_loc = c_parser_peek_token (parser)->location; c_expr expr = c_parser_expr_no_commas (parser, NULL); expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true); @@ -13870,6 +13899,7 @@ c_parser_omp_clause_grainsize (c_parser *parser, tree list) c = build_omp_clause (grainsize_loc, OMP_CLAUSE_GRAINSIZE); OMP_CLAUSE_GRAINSIZE_EXPR (c) = t; + OMP_CLAUSE_GRAINSIZE_STRICT (c) = strict; OMP_CLAUSE_CHAIN (c) = list; list = c; } -- cgit v1.1 From 38b19c5b0805f9acfcf52430cebca025fc3cdea6 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Tue, 24 Aug 2021 00:17:00 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 6ca524b..27ccc32 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-08-23 Jakub Jelinek + + * c-parser.c (c_parser_omp_clause_num_tasks, + c_parser_omp_clause_grainsize): Parse the optional strict: modifier. + 2021-08-22 Martin Uecker PR c/98397 -- cgit v1.1 From 03be3cfeef7b3811acb6c4a8da2fc5c1e25d3e4c Mon Sep 17 00:00:00 2001 From: Marcel Vollweiler Date: Tue, 31 Aug 2021 06:09:40 -0700 Subject: Add support for device-modifiers for 'omp target device'. 'device_num' and 'ancestor' are now parsed on target device constructs for C, C++, and Fortran (see OpenMP specification 5.0, p. 170). When 'ancestor' is used, then 'sorry, not supported' is output. Moreover, the restrictions for 'ancestor' are implemented (see OpenMP specification 5.0, p. 174f). gcc/c/ChangeLog: * c-parser.c (c_parser_omp_clause_device): Parse device-modifiers 'device_num' and 'ancestor' in 'target device' clauses. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_clause_device): Parse device-modifiers 'device_num' and 'ancestor' in 'target device' clauses. * semantics.c (finish_omp_clauses): Error handling. Constant device ids must evaluate to '1' if 'ancestor' is used. gcc/fortran/ChangeLog: * gfortran.h: Add variable for 'ancestor' in struct gfc_omp_clauses. * openmp.c (gfc_match_omp_clauses): Parse device-modifiers 'device_num' and 'ancestor' in 'target device' clauses. * trans-openmp.c (gfc_trans_omp_clauses): Set OMP_CLAUSE_DEVICE_ANCESTOR. gcc/ChangeLog: * gimplify.c (gimplify_scan_omp_clauses): Error handling. 'ancestor' only allowed on target constructs and only with particular other clauses. * omp-expand.c (expand_omp_target): Output of 'sorry, not supported' if 'ancestor' is used. * omp-low.c (check_omp_nesting_restrictions): Error handling. No nested OpenMP structs when 'ancestor' is used. (scan_omp_1_stmt): No usage of OpenMP runtime routines in a target region when 'ancestor' is used. * tree-pretty-print.c (dump_omp_clause): Append 'ancestor'. * tree.h (OMP_CLAUSE_DEVICE_ANCESTOR): Define macro. gcc/testsuite/ChangeLog: * c-c++-common/gomp/target-device-1.c: New test. * c-c++-common/gomp/target-device-2.c: New test. * c-c++-common/gomp/target-device-ancestor-1.c: New test. * c-c++-common/gomp/target-device-ancestor-2.c: New test. * c-c++-common/gomp/target-device-ancestor-3.c: New test. * c-c++-common/gomp/target-device-ancestor-4.c: New test. * gfortran.dg/gomp/target-device-1.f90: New test. * gfortran.dg/gomp/target-device-2.f90: New test. * gfortran.dg/gomp/target-device-ancestor-1.f90: New test. * gfortran.dg/gomp/target-device-ancestor-2.f90: New test. * gfortran.dg/gomp/target-device-ancestor-3.f90: New test. * gfortran.dg/gomp/target-device-ancestor-4.f90: New test. --- gcc/c/c-parser.c | 84 ++++++++++++++++++++++++++++++++++++++++++++------------ 1 file changed, 67 insertions(+), 17 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 356cf25..3b1d10f 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -15945,37 +15945,87 @@ c_parser_omp_clause_map (c_parser *parser, tree list) } /* OpenMP 4.0: - device ( expression ) */ + device ( expression ) + + OpenMP 5.0: + device ( [device-modifier :] integer-expression ) + + device-modifier: + ancestor | device_num */ static tree c_parser_omp_clause_device (c_parser *parser, tree list) { location_t clause_loc = c_parser_peek_token (parser)->location; - matching_parens parens; - if (parens.require_open (parser)) - { - location_t expr_loc = c_parser_peek_token (parser)->location; - c_expr expr = c_parser_expr_no_commas (parser, NULL); - expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true); - tree c, t = expr.value; - t = c_fully_fold (t, false, NULL); + location_t expr_loc; + c_expr expr; + tree c, t; + bool ancestor = false; - parens.skip_until_found_close (parser); + matching_parens parens; + if (!parens.require_open (parser)) + return list; - if (!INTEGRAL_TYPE_P (TREE_TYPE (t))) + if (c_parser_next_token_is (parser, CPP_NAME) + && c_parser_peek_2nd_token (parser)->type == CPP_COLON) + { + c_token *tok = c_parser_peek_token (parser); + const char *p = IDENTIFIER_POINTER (tok->value); + if (strcmp ("ancestor", p) == 0) { - c_parser_error (parser, "expected integer expression"); + /* A requires directive with the reverse_offload clause must be + specified. */ + if ((omp_requires_mask & OMP_REQUIRES_REVERSE_OFFLOAD) == 0) + { + error_at (tok->location, "% device modifier not " + "preceded by % directive " + "with % clause"); + parens.skip_until_found_close (parser); + return list; + } + ancestor = true; + } + else if (strcmp ("device_num", p) == 0) + ; + else + { + error_at (tok->location, "expected % or %"); + parens.skip_until_found_close (parser); return list; } + c_parser_consume_token (parser); + c_parser_consume_token (parser); + } - check_no_duplicate_clause (list, OMP_CLAUSE_DEVICE, "device"); + expr_loc = c_parser_peek_token (parser)->location; + expr = c_parser_expr_no_commas (parser, NULL); + expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true); + t = expr.value; + t = c_fully_fold (t, false, NULL); - c = build_omp_clause (clause_loc, OMP_CLAUSE_DEVICE); - OMP_CLAUSE_DEVICE_ID (c) = t; - OMP_CLAUSE_CHAIN (c) = list; - list = c; + parens.skip_until_found_close (parser); + + if (!INTEGRAL_TYPE_P (TREE_TYPE (t))) + { + c_parser_error (parser, "expected integer expression"); + return list; } + if (ancestor && TREE_CODE (t) == INTEGER_CST && !integer_onep (t)) + { + error_at (expr_loc, "the % clause expression must evaluate to " + "%<1%>"); + return list; + } + + check_no_duplicate_clause (list, OMP_CLAUSE_DEVICE, "device"); + + c = build_omp_clause (clause_loc, OMP_CLAUSE_DEVICE); + OMP_CLAUSE_DEVICE_ID (c) = t; + OMP_CLAUSE_CHAIN (c) = list; + OMP_CLAUSE_DEVICE_ANCESTOR (c) = ancestor; + + list = c; return list; } -- cgit v1.1 From 6d51ee4321605c704aa238d039b47bfcf59b1005 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 1 Sep 2021 00:16:58 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 27ccc32..a175f36 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-08-31 Marcel Vollweiler + + * c-parser.c (c_parser_omp_clause_device): Parse device-modifiers 'device_num' + and 'ancestor' in 'target device' clauses. + 2021-08-23 Jakub Jelinek * c-parser.c (c_parser_omp_clause_num_tasks, -- cgit v1.1 From 823685221de986afb729910a6f2237f07a377f17 Mon Sep 17 00:00:00 2001 From: Roger Sayle Date: Wed, 1 Sep 2021 08:38:39 +0100 Subject: C: PR c/79412: Poison decls with error_mark_node after type mismatch This patch fixes an ICE during error-recovery regression in the C front-end. The symptom is that the middle-end's sanity checking assertions fail during gimplification when being asked to increment an array, which is non-sense. The issue is that the C-front end has detected the type mismatch and reported an error to the user, but hasn't provided any indication of this to the middle-end, simply passing bogus trees that the optimizers recognize as invalid. This appears to be a frequently reported ICE with 94730, 94731, 101036 and 101365 all marked as duplicates. I believe the correct (polite) fix is to mark the mismatched types as problematic/dubious in the front-end, when the error is spotted, so that the middle-end has a heads-up and can be a little more forgiving. This patch to c-decl.c's duplicate_decls sets (both) mismatched types to error_mark_node if they are significantly different, and we've issued an error message. Alas, this is too punitive for FUNCTION_DECLs where we store return types, parameter lists, parameter types and attributes in the type, but fortunately the middle-end is already more cautious about trusting possibly suspect function types. This fix required one minor change to the testsuite, typedef-var-2.c where after conflicting type definitions, we now no longer assume that the (first or) second definition is the correct one. This change only affects the behaviour after seen_error(), so should be relatively safe. 2021-09-01 Roger Sayle Joseph Myers gcc/c/ChangeLog PR c/79412 * c-decl.c (duplicate_decls): On significant mismatches, mark the types of both (non-function) decls as error_mark_node, so that the middle-end can see the code is malformed. (free_attr_access_data): Don't process if the type has been set to error_mark_node. gcc/testsuite/ChangeLog PR c/79412 * gcc.dg/pr79412.c: New test case. * gcc.dg/typedef-var-2.c: Update expeted errors. --- gcc/c/c-decl.c | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 221a67f..3482d82 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -2957,6 +2957,17 @@ duplicate_decls (tree newdecl, tree olddecl) { /* Avoid `unused variable' and other warnings for OLDDECL. */ suppress_warning (olddecl, OPT_Wunused); + /* If the types are completely different, poison them both with + error_mark_node. */ + if (TREE_CODE (TREE_TYPE (newdecl)) != TREE_CODE (TREE_TYPE (olddecl)) + && olddecl != error_mark_node + && seen_error ()) + { + if (TREE_CODE (olddecl) != FUNCTION_DECL) + TREE_TYPE (olddecl) = error_mark_node; + if (TREE_CODE (newdecl) != FUNCTION_DECL) + TREE_TYPE (newdecl) = error_mark_node; + } return false; } @@ -12209,7 +12220,7 @@ free_attr_access_data () attr_access::free_lang_data (attrs); tree fntype = TREE_TYPE (n->decl); - if (!fntype) + if (!fntype || fntype == error_mark_node) continue; tree attrs = TYPE_ATTRIBUTES (fntype); if (!attrs) -- cgit v1.1 From 8433baadec88e5f31fa141b6d78094e91256079d Mon Sep 17 00:00:00 2001 From: Iain Sandoe Date: Sun, 8 Nov 2020 09:04:07 +0000 Subject: C-family: Add attribute 'unavailable'. If an interface is marked 'deprecated' then, presumably, at some point it will be withdrawn and no longer available. The 'unavailable' attribute makes it possible to mark up interfaces to indicate this status. It is used quite extensively in some codebases where a single set of headers can be used to permit code generation for multiple system versions. From a configuration perspective, it also allows a compile test to determine that an interface is missing - rather than requiring a link test. The implementation follows the pattern of attribute deprecated, but produces an error (where deprecation produces a warning). This attribute has been implemented in clang for some years. Signed-off-by: Iain Sandoe gcc/c-family/ChangeLog: * c-attribs.c (handle_unavailable_attribute): New. gcc/c/ChangeLog: * c-decl.c (enum deprecated_states): Add unavailable state. (merge_decls): Copy unavailability. (quals_from_declspecs): Handle unavailable case. (start_decl): Amend the logic handling suppression of nested deprecation states to include unavailability. (smallest_type_quals_location): Amend comment. (grokdeclarator): Handle the unavailable deprecation state. (declspecs_add_type): Set TREE_UNAVAILABLE from the decl specs. * c-tree.h (struct c_declspecs): Add unavailable_p. * c-typeck.c (build_component_ref): Handle unavailability. (build_external_ref): Likewise. gcc/cp/ChangeLog: * call.c (build_over_call): Handle unavailable state in addition to deprecation. * class.c (type_build_ctor_call): Likewise. (type_build_dtor_call): Likewise. * cp-tree.h: Rename cp_warn_deprecated_use to cp_handle_deprecated_or_unavailable. * decl.c (duplicate_decls): Merge unavailability. (grokdeclarator): Handle unavailability in addition to deprecation. (type_is_unavailable): New. (grokparms): Handle unavailability in addition to deprecation. * decl.h (enum deprecated_states): Add UNAVAILABLE_DEPRECATED_SUPPRESS. * decl2.c (cplus_decl_attributes): Propagate unavailability to templates. (cp_warn_deprecated_use): Rename to ... (cp_handle_deprecated_or_unavailable): ... this and amend to handle the unavailable case. It remains a warning in the case of deprecation but becomes an error in the case of unavailability. (cp_warn_deprecated_use_scopes): Handle unavailability. (mark_used): Likewise. * parser.c (cp_parser_template_name): Likewise. (cp_parser_template_argument): Likewise. (cp_parser_parameter_declaration_list): Likewise. * typeck.c (build_class_member_access_expr): Likewise. (finish_class_member_access_expr): Likewise. * typeck2.c (build_functional_cast_1): Likewise. gcc/ChangeLog: * doc/extend.texi: Document unavailable attribute. * print-tree.c (print_node): Handle unavailable attribute. * tree-core.h (struct tree_base): Add a bit to carry unavailability. * tree.c (error_unavailable_use): New. * tree.h (TREE_UNAVAILABLE): New. (error_unavailable_use): New. gcc/objc/ChangeLog: * objc-act.c (objc_add_property_declaration): Register unavailable attribute. (maybe_make_artificial_property_decl): Set available. (objc_maybe_build_component_ref): Generalise to the method prototype to count availability. (objc_build_class_component_ref): Likewise. (build_private_template): Likewise. (objc_decl_method_attributes): Handle unavailable attribute. (lookup_method_in_hash_lists): Amend comments. (objc_finish_message_expr): Handle unavailability in addition to deprecation. (start_class): Likewise. (finish_class): Likewise. (lookup_protocol): Likewise. (objc_declare_protocol): Likewise. (start_protocol): Register unavailable attribute. (really_start_method): Likewise. (objc_gimplify_property_ref): Emit error on encountering an unavailable entity (and a warning for a deprecated one). gcc/testsuite/ChangeLog: * g++.dg/ext/attr-unavailable-1.C: New test. * g++.dg/ext/attr-unavailable-2.C: New test. * g++.dg/ext/attr-unavailable-3.C: New test. * g++.dg/ext/attr-unavailable-4.C: New test. * g++.dg/ext/attr-unavailable-5.C: New test. * g++.dg/ext/attr-unavailable-6.C: New test. * g++.dg/ext/attr-unavailable-7.C: New test. * g++.dg/ext/attr-unavailable-8.C: New test. * g++.dg/ext/attr-unavailable-9.C: New test. * gcc.dg/attr-unavailable-1.c: New test. * gcc.dg/attr-unavailable-2.c: New test. * gcc.dg/attr-unavailable-3.c: New test. * gcc.dg/attr-unavailable-4.c: New test. * gcc.dg/attr-unavailable-5.c: New test. * gcc.dg/attr-unavailable-6.c: New test. * obj-c++.dg/attributes/method-unavailable-1.mm: New test. * obj-c++.dg/attributes/method-unavailable-2.mm: New test. * obj-c++.dg/attributes/method-unavailable-3.mm: New test. * obj-c++.dg/property/at-property-unavailable-1.mm: New test. * obj-c++.dg/property/at-property-unavailable-2.mm: New test. * obj-c++.dg/property/dotsyntax-unavailable-1.mm: New test. * objc.dg/attributes/method-unavailable-1.m: New test. * objc.dg/attributes/method-unavailable-2.m: New test. * objc.dg/attributes/method-unavailable-3.m: New test. * objc.dg/property/at-property-unavailable-1.m: New test. * objc.dg/property/at-property-unavailable-2.m: New test. * objc.dg/property/dotsyntax-unavailable-1.m: New test. --- gcc/c/c-decl.c | 39 ++++++++++++++++++++++++++++++--------- gcc/c/c-tree.h | 2 ++ gcc/c/c-typeck.c | 8 ++++++-- 3 files changed, 38 insertions(+), 11 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index 3482d82..771efa3 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -73,13 +73,16 @@ enum decl_context TYPENAME}; /* Typename (inside cast or sizeof) */ /* States indicating how grokdeclarator() should handle declspecs marked - with __attribute__((deprecated)). An object declared as - __attribute__((deprecated)) suppresses warnings of uses of other - deprecated items. */ + with __attribute__((deprecated)) or __attribute__((unavailable)). + An object declared as __attribute__((unavailable)) should suppress + any reports of being declared with unavailable or deprecated items. + An object declared as __attribute__((deprecated)) should suppress + warnings of uses of other deprecated items. */ enum deprecated_states { DEPRECATED_NORMAL, - DEPRECATED_SUPPRESS + DEPRECATED_SUPPRESS, + UNAVAILABLE_DEPRECATED_SUPPRESS }; @@ -2644,6 +2647,10 @@ merge_decls (tree newdecl, tree olddecl, tree newtype, tree oldtype) if (TREE_DEPRECATED (newdecl)) TREE_DEPRECATED (olddecl) = 1; + /* Merge unavailability. */ + if (TREE_UNAVAILABLE (newdecl)) + TREE_UNAVAILABLE (olddecl) = 1; + /* If a decl is in a system header and the other isn't, keep the one on the system header. Otherwise, keep source location of definition rather than declaration and of prototype rather than non-prototype unless that @@ -4892,6 +4899,7 @@ quals_from_declspecs (const struct c_declspecs *specs) && !specs->typedef_p && !specs->explicit_signed_p && !specs->deprecated_p + && !specs->unavailable_p && !specs->long_p && !specs->long_long_p && !specs->short_p @@ -5094,9 +5102,14 @@ start_decl (struct c_declarator *declarator, struct c_declspecs *declspecs, tree expr = NULL_TREE; enum deprecated_states deprecated_state = DEPRECATED_NORMAL; - /* An object declared as __attribute__((deprecated)) suppresses + /* An object declared as __attribute__((unavailable)) suppresses + warnings and errors from __attribute__((deprecated/unavailable)) + components. + An object declared as __attribute__((deprecated)) suppresses warnings of uses of other deprecated items. */ - if (lookup_attribute ("deprecated", attributes)) + if (lookup_attribute ("unavailable", attributes)) + deprecated_state = UNAVAILABLE_DEPRECATED_SUPPRESS; + else if (lookup_attribute ("deprecated", attributes)) deprecated_state = DEPRECATED_SUPPRESS; decl = grokdeclarator (declarator, declspecs, @@ -6233,7 +6246,7 @@ smallest_type_quals_location (const location_t *locations, set to indicate whether operands in *EXPR can be used in constant expressions. DEPRECATED_STATE is a deprecated_states value indicating whether - deprecation warnings should be suppressed. + deprecation/unavailability warnings should be suppressed. In the TYPENAME case, DECLARATOR is really an absolute declarator. It may also be so in the PARM case, for a prototype where the @@ -6363,8 +6376,14 @@ grokdeclarator (const struct c_declarator *declarator, if (decl_context == NORMAL && !funcdef_flag && current_scope->parm_flag) decl_context = PARM; - if (declspecs->deprecated_p && deprecated_state != DEPRECATED_SUPPRESS) - warn_deprecated_use (declspecs->type, declspecs->decl_attr); + if (deprecated_state != UNAVAILABLE_DEPRECATED_SUPPRESS) + { + if (declspecs->unavailable_p) + error_unavailable_use (declspecs->type, declspecs->decl_attr); + else if (declspecs->deprecated_p + && deprecated_state != DEPRECATED_SUPPRESS) + warn_deprecated_use (declspecs->type, declspecs->decl_attr); + } if ((decl_context == NORMAL || decl_context == FIELD) && current_scope == file_scope @@ -10814,6 +10833,8 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs, specs->typespec_kind = spec.kind; if (TREE_DEPRECATED (type)) specs->deprecated_p = true; + if (TREE_UNAVAILABLE (type)) + specs->unavailable_p = true; /* Handle type specifier keywords. */ if (TREE_CODE (type) == IDENTIFIER_NODE diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h index a8a90ea..d50d0cb 100644 --- a/gcc/c/c-tree.h +++ b/gcc/c/c-tree.h @@ -370,6 +370,8 @@ struct c_declspecs { BOOL_BITFIELD explicit_signed_p : 1; /* Whether the specifiers include a deprecated typedef. */ BOOL_BITFIELD deprecated_p : 1; + /* Whether the specifiers include an unavailable typedef. */ + BOOL_BITFIELD unavailable_p : 1; /* Whether the type defaulted to "int" because there were no type specifiers. */ BOOL_BITFIELD default_int_p : 1; diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index d9f26d6..5849c5a 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -2558,7 +2558,9 @@ build_component_ref (location_t loc, tree datum, tree component, || (use_datum_quals && TREE_THIS_VOLATILE (datum))) TREE_THIS_VOLATILE (ref) = 1; - if (TREE_DEPRECATED (subdatum)) + if (TREE_UNAVAILABLE (subdatum)) + error_unavailable_use (subdatum, NULL_TREE); + else if (TREE_DEPRECATED (subdatum)) warn_deprecated_use (subdatum, NULL_TREE); datum = ref; @@ -2843,7 +2845,9 @@ build_external_ref (location_t loc, tree id, bool fun, tree *type) if (TREE_TYPE (ref) == error_mark_node) return error_mark_node; - if (TREE_DEPRECATED (ref)) + if (TREE_UNAVAILABLE (ref)) + error_unavailable_use (ref, NULL_TREE); + else if (TREE_DEPRECATED (ref)) warn_deprecated_use (ref, NULL_TREE); /* Recursive call does not count as usage. */ -- cgit v1.1 From e11c6046f9c8bc891a67f37f0260ef4ece482f5d Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Thu, 2 Sep 2021 00:16:59 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index a175f36..e501dc9 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,27 @@ +2021-09-01 Iain Sandoe + + * c-decl.c (enum deprecated_states): Add unavailable state. + (merge_decls): Copy unavailability. + (quals_from_declspecs): Handle unavailable case. + (start_decl): Amend the logic handling suppression of nested + deprecation states to include unavailability. + (smallest_type_quals_location): Amend comment. + (grokdeclarator): Handle the unavailable deprecation state. + (declspecs_add_type): Set TREE_UNAVAILABLE from the decl specs. + * c-tree.h (struct c_declspecs): Add unavailable_p. + * c-typeck.c (build_component_ref): Handle unavailability. + (build_external_ref): Likewise. + +2021-09-01 Roger Sayle + Joseph Myers + + PR c/79412 + * c-decl.c (duplicate_decls): On significant mismatches, mark the + types of both (non-function) decls as error_mark_node, so that the + middle-end can see the code is malformed. + (free_attr_access_data): Don't process if the type has been set to + error_mark_node. + 2021-08-31 Marcel Vollweiler * c-parser.c (c_parser_omp_clause_device): Parse device-modifiers 'device_num' -- cgit v1.1 From ba1cc6956b956eb5b92c45af79a8b1fe426ec4d3 Mon Sep 17 00:00:00 2001 From: Marcel Vollweiler Date: Tue, 7 Sep 2021 03:46:28 -0700 Subject: C, C++, Fortran, OpenMP: Add support for 'flush seq_cst' construct. This patch adds support for the 'seq_cst' memory order clause on the 'flush' directive which was introduced in OpenMP 5.1. gcc/c-family/ChangeLog: * c-omp.c (c_finish_omp_flush): Handle MEMMODEL_SEQ_CST. gcc/c/ChangeLog: * c-parser.c (c_parser_omp_flush): Parse 'seq_cst' clause on 'flush' directive. gcc/cp/ChangeLog: * parser.c (cp_parser_omp_flush): Parse 'seq_cst' clause on 'flush' directive. * semantics.c (finish_omp_flush): Handle MEMMODEL_SEQ_CST. gcc/fortran/ChangeLog: * openmp.c (gfc_match_omp_flush): Parse 'seq_cst' clause on 'flush' directive. * trans-openmp.c (gfc_trans_omp_flush): Handle OMP_MEMORDER_SEQ_CST. gcc/testsuite/ChangeLog: * c-c++-common/gomp/flush-1.c: Add test case for 'seq_cst'. * c-c++-common/gomp/flush-2.c: Add test case for 'seq_cst'. * g++.dg/gomp/attrs-1.C: Adapt test to handle all flush clauses. * g++.dg/gomp/attrs-2.C: Adapt test to handle all flush clauses. * gfortran.dg/gomp/flush-1.f90: Add test case for 'seq_cst'. * gfortran.dg/gomp/flush-2.f90: Add test case for 'seq_cst'. --- gcc/c/c-parser.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 3b1d10f..4d074ec 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -18339,7 +18339,9 @@ c_parser_omp_flush (c_parser *parser) const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); - if (!strcmp (p, "acq_rel")) + if (!strcmp (p, "seq_cst")) + mo = MEMMODEL_SEQ_CST; + else if (!strcmp (p, "acq_rel")) mo = MEMMODEL_ACQ_REL; else if (!strcmp (p, "release")) mo = MEMMODEL_RELEASE; @@ -18347,7 +18349,8 @@ c_parser_omp_flush (c_parser *parser) mo = MEMMODEL_ACQUIRE; else error_at (c_parser_peek_token (parser)->location, - "expected %, % or %"); + "expected %, %, % or " + "%"); c_parser_consume_token (parser); } if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)) -- cgit v1.1 From b2748138c05c6fba1a34f54980b6382bc6332f56 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Wed, 8 Sep 2021 00:16:23 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index e501dc9..9deeb0e 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,8 @@ +2021-09-07 Marcel Vollweiler + + * c-parser.c (c_parser_omp_flush): Parse 'seq_cst' clause on 'flush' + directive. + 2021-09-01 Iain Sandoe * c-decl.c (enum deprecated_states): Add unavailable state. -- cgit v1.1 From 8122fbff770bcff183a9c3c72e8092c0ca32150b Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Fri, 10 Sep 2021 20:41:33 +0200 Subject: openmp: Implement OpenMP 5.1 atomics, so far for C only This patch implements OpenMP 5.1 atomics (with clarifications from upcoming 5.2). The most important changes are that it is now possible to write (for C/C++, for Fortran it was possible before already) min/max atomics and more importantly compare and exchange in various forms. Also, acq_rel is now allowed on read/write and acq_rel/acquire are allowed on update, and there are new compare, weak and fail clauses. 2021-09-10 Jakub Jelinek gcc/ * tree-core.h (enum omp_memory_order): Add OMP_MEMORY_ORDER_MASK, OMP_FAIL_MEMORY_ORDER_UNSPECIFIED, OMP_FAIL_MEMORY_ORDER_RELAXED, OMP_FAIL_MEMORY_ORDER_ACQUIRE, OMP_FAIL_MEMORY_ORDER_RELEASE, OMP_FAIL_MEMORY_ORDER_ACQ_REL, OMP_FAIL_MEMORY_ORDER_SEQ_CST and OMP_FAIL_MEMORY_ORDER_MASK enumerators. (OMP_FAIL_MEMORY_ORDER_SHIFT): Define. * gimple-pretty-print.c (dump_gimple_omp_atomic_load, dump_gimple_omp_atomic_store): Print [weak] for weak atomic load/store. * gimple.h (enum gf_mask): Change GF_OMP_ATOMIC_MEMORY_ORDER to 6-bit mask, adjust GF_OMP_ATOMIC_NEED_VALUE value and add GF_OMP_ATOMIC_WEAK. (gimple_omp_atomic_weak_p, gimple_omp_atomic_set_weak): New inline functions. * tree.h (OMP_ATOMIC_WEAK): Define. * tree-pretty-print.c (dump_omp_atomic_memory_order): Adjust for fail memory order being encoded in the same enum and also print fail clause if present. (dump_generic_node): Print weak clause if OMP_ATOMIC_WEAK. * gimplify.c (goa_stabilize_expr): Add target_expr and rhs arguments, handle pre_p == NULL case as a test mode that only returns value but doesn't change gimplify nor change anything otherwise, adjust recursive calls, add MODIFY_EXPR, ADDR_EXPR, COND_EXPR, TARGET_EXPR and CALL_EXPR handling, adjust COMPOUND_EXPR handling for __builtin_clear_padding calls, for !rhs gimplify as lvalue rather than rvalue. (gimplify_omp_atomic): Adjust goa_stabilize_expr caller. Handle COND_EXPR rhs. Set weak flag on gimple load/store for OMP_ATOMIC_WEAK. * omp-expand.c (omp_memory_order_to_fail_memmodel): New function. (omp_memory_order_to_memmodel): Adjust for fail clause encoded in the same enum. (expand_omp_atomic_cas): New function. (expand_omp_atomic_pipeline): Use omp_memory_order_to_fail_memmodel function. (expand_omp_atomic): Attempt to optimize atomic compare and exchange using expand_omp_atomic_cas. gcc/c-family/ * c-common.h (c_finish_omp_atomic): Add r and weak arguments. * c-omp.c: Include gimple-fold.h. (c_finish_omp_atomic): Add r and weak arguments. Add support for OpenMP 5.1 atomics. gcc/c/ * c-parser.c (c_parser_conditional_expression): If omp_atomic_lhs and cond.value is >, < or == with omp_atomic_lhs as one of the operands, don't call build_conditional_expr, instead build a COND_EXPR directly. (c_parser_binary_expression): Avoid calling parser_build_binary_op if omp_atomic_lhs even in more cases for >, < or ==. (c_parser_omp_atomic): Update function comment for OpenMP 5.1 atomics, parse OpenMP 5.1 atomics and fail, compare and weak clauses, allow acq_rel on atomic read/write and acq_rel/acquire clauses on update. * c-typeck.c (build_binary_op): For flag_openmp only handle MIN_EXPR/MAX_EXPR. gcc/cp/ * parser.c (cp_parser_omp_atomic): Allow acq_rel on atomic read/write and acq_rel/acquire clauses on update. * semantics.c (finish_omp_atomic): Adjust c_finish_omp_atomic caller. gcc/testsuite/ * c-c++-common/gomp/atomic-17.c (foo): Add tests for atomic read, write or update with acq_rel clause and atomic update with acquire clause. * c-c++-common/gomp/atomic-18.c (foo): Adjust expected diagnostics wording, remove tests moved to atomic-17.c. * c-c++-common/gomp/atomic-21.c: Expect only 2 omp atomic release and 2 omp atomic acq_rel directives instead of 4 omp atomic release. * c-c++-common/gomp/atomic-25.c: New test. * c-c++-common/gomp/atomic-26.c: New test. * c-c++-common/gomp/atomic-27.c: New test. * c-c++-common/gomp/atomic-28.c: New test. * c-c++-common/gomp/atomic-29.c: New test. * c-c++-common/gomp/atomic-30.c: New test. * c-c++-common/goacc-gomp/atomic.c: Expect 1 omp atomic release and 1 omp atomic_acq_rel instead of 2 omp atomic release directives. * gcc.dg/gomp/atomic-5.c: Adjust expected error diagnostic wording. * g++.dg/gomp/atomic-18.C:Expect 4 omp atomic release and 1 omp atomic_acq_rel instead of 5 omp atomic release directives. libgomp/ * testsuite/libgomp.c-c++-common/atomic-19.c: New test. * testsuite/libgomp.c-c++-common/atomic-20.c: New test. * testsuite/libgomp.c-c++-common/atomic-21.c: New test. --- gcc/c/c-parser.c | 504 ++++++++++++++++++++++++++++++++++++++++++++++++++----- gcc/c/c-typeck.c | 7 + 2 files changed, 473 insertions(+), 38 deletions(-) (limited to 'gcc/c') diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 4d074ec..d82c042 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -7663,10 +7663,21 @@ c_parser_conditional_expression (c_parser *parser, struct c_expr *after, c_inhibit_evaluation_warnings -= cond.value == truthvalue_true_node; location_t loc1 = make_location (exp1.get_start (), exp1.src_range); location_t loc2 = make_location (exp2.get_start (), exp2.src_range); - ret.value = build_conditional_expr (colon_loc, cond.value, - cond.original_code == C_MAYBE_CONST_EXPR, - exp1.value, exp1.original_type, loc1, - exp2.value, exp2.original_type, loc2); + if (__builtin_expect (omp_atomic_lhs != NULL, 0) + && (TREE_CODE (cond.value) == GT_EXPR + || TREE_CODE (cond.value) == LT_EXPR + || TREE_CODE (cond.value) == EQ_EXPR) + && c_tree_equal (exp2.value, omp_atomic_lhs) + && (c_tree_equal (TREE_OPERAND (cond.value, 0), omp_atomic_lhs) + || c_tree_equal (TREE_OPERAND (cond.value, 1), omp_atomic_lhs))) + ret.value = build3_loc (colon_loc, COND_EXPR, TREE_TYPE (omp_atomic_lhs), + cond.value, exp1.value, exp2.value); + else + ret.value + = build_conditional_expr (colon_loc, cond.value, + cond.original_code == C_MAYBE_CONST_EXPR, + exp1.value, exp1.original_type, loc1, + exp2.value, exp2.original_type, loc2); ret.original_code = ERROR_MARK; if (exp1.value == error_mark_node || exp2.value == error_mark_node) ret.original_type = NULL; @@ -7849,15 +7860,27 @@ c_parser_binary_expression (c_parser *parser, struct c_expr *after, = convert_lvalue_to_rvalue (stack[sp].loc, \ stack[sp].expr, true, true); \ if (__builtin_expect (omp_atomic_lhs != NULL_TREE, 0) && sp == 1 \ - && c_parser_peek_token (parser)->type == CPP_SEMICOLON \ - && ((1 << stack[sp].prec) \ - & ((1 << PREC_BITOR) | (1 << PREC_BITXOR) | (1 << PREC_BITAND) \ - | (1 << PREC_SHIFT) | (1 << PREC_ADD) | (1 << PREC_MULT))) \ + && ((c_parser_next_token_is (parser, CPP_SEMICOLON) \ + && ((1 << stack[sp].prec) \ + & ((1 << PREC_BITOR) | (1 << PREC_BITXOR) \ + | (1 << PREC_BITAND) | (1 << PREC_SHIFT) \ + | (1 << PREC_ADD) | (1 << PREC_MULT) \ + | (1 << PREC_EQ)))) \ + || ((c_parser_next_token_is (parser, CPP_QUERY) \ + || (omp_atomic_lhs == void_list_node \ + && c_parser_next_token_is (parser, CPP_CLOSE_PAREN))) \ + && (stack[sp].prec == PREC_REL || stack[sp].prec == PREC_EQ)))\ && stack[sp].op != TRUNC_MOD_EXPR \ + && stack[sp].op != GE_EXPR \ + && stack[sp].op != LE_EXPR \ + && stack[sp].op != NE_EXPR \ && stack[0].expr.value != error_mark_node \ && stack[1].expr.value != error_mark_node \ - && (c_tree_equal (stack[0].expr.value, omp_atomic_lhs) \ - || c_tree_equal (stack[1].expr.value, omp_atomic_lhs))) \ + && (omp_atomic_lhs == void_list_node \ + || c_tree_equal (stack[0].expr.value, omp_atomic_lhs) \ + || c_tree_equal (stack[1].expr.value, omp_atomic_lhs) \ + || (stack[sp].op == EQ_EXPR \ + && c_parser_peek_2nd_token (parser)->keyword == RID_IF))) \ { \ tree t = make_node (stack[1].op); \ TREE_TYPE (t) = TREE_TYPE (stack[0].expr.value); \ @@ -17655,14 +17678,45 @@ c_parser_omp_allocate (location_t loc, c_parser *parser) capture-block: { v = x; update-stmt; } | { update-stmt; v = x; } | { v = x; x = expr; } - where x and v are lvalue expressions with scalar type. + OpenMP 5.1: + # pragma omp atomic compare new-line + conditional-update-atomic + + # pragma omp atomic compare capture new-line + conditional-update-capture-atomic + + conditional-update-atomic: + cond-expr-stmt | cond-update-stmt + cond-expr-stmt: + x = expr ordop x ? expr : x; + x = x ordop expr ? expr : x; + x = x == e ? d : x; + cond-update-stmt: + if (expr ordop x) { x = expr; } + if (x ordop expr) { x = expr; } + if (x == e) { x = d; } + ordop: + <, > + conditional-update-capture-atomic: + v = cond-expr-stmt + { v = x; cond-expr-stmt } + { cond-expr-stmt v = x; } + { v = x; cond-update-stmt } + { cond-update-stmt v = x; } + if (x == e) { x = d; } else { v = x; } + { r = x == e; if (r) { x = d; } } + { r = x == e; if (r) { x = d; } else { v = x; } } + + where x, r and v are lvalue expressions with scalar type, + expr, e and d are expressions with scalar type and e might be + the same as v. LOC is the location of the #pragma token. */ static void c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) { - tree lhs = NULL_TREE, rhs = NULL_TREE, v = NULL_TREE; + tree lhs = NULL_TREE, rhs = NULL_TREE, v = NULL_TREE, r = NULL_TREE; tree lhs1 = NULL_TREE, rhs1 = NULL_TREE; tree stmt, orig_lhs, unfolded_lhs = NULL_TREE, unfolded_lhs1 = NULL_TREE; enum tree_code code = ERROR_MARK, opcode = NOP_EXPR; @@ -17674,6 +17728,12 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) bool non_lvalue_p; bool first = true; tree clauses = NULL_TREE; + bool capture = false; + bool compare = false; + bool weak = false; + enum omp_memory_order fail = OMP_MEMORY_ORDER_UNSPECIFIED; + bool no_semicolon = false; + bool extra_scope = false; while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL)) { @@ -17692,6 +17752,10 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) enum tree_code new_code = ERROR_MARK; enum omp_memory_order new_memory_order = OMP_MEMORY_ORDER_UNSPECIFIED; + bool new_capture = false; + bool new_compare = false; + bool new_weak = false; + enum omp_memory_order new_fail = OMP_MEMORY_ORDER_UNSPECIFIED; if (!strcmp (p, "read")) new_code = OMP_ATOMIC_READ; @@ -17699,7 +17763,7 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) new_code = NOP_EXPR; else if (!strcmp (p, "update")) new_code = OMP_ATOMIC; - else if (!strcmp (p, "capture")) + else if (openacc && !strcmp (p, "capture")) new_code = OMP_ATOMIC_CAPTURE_NEW; else if (openacc) { @@ -17707,6 +17771,47 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) error_at (cloc, "expected %, %, %, " "or % clause"); } + else if (!strcmp (p, "capture")) + new_capture = true; + else if (!strcmp (p, "compare")) + new_compare = true; + else if (!strcmp (p, "weak")) + new_weak = true; + else if (!strcmp (p, "fail")) + { + matching_parens parens; + + c_parser_consume_token (parser); + if (!parens.require_open (parser)) + continue; + + if (c_parser_next_token_is (parser, CPP_NAME)) + { + const char *q + = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value); + + if (!strcmp (q, "seq_cst")) + new_fail = OMP_MEMORY_ORDER_SEQ_CST; + else if (!strcmp (q, "acquire")) + new_fail = OMP_MEMORY_ORDER_ACQUIRE; + else if (!strcmp (q, "relaxed")) + new_fail = OMP_MEMORY_ORDER_RELAXED; + } + + if (new_fail != OMP_MEMORY_ORDER_UNSPECIFIED) + { + c_parser_consume_token (parser); + if (fail != OMP_MEMORY_ORDER_UNSPECIFIED) + error_at (cloc, "too many %qs clauses", "fail"); + else + fail = new_fail; + } + else + c_parser_error (parser, "expected %, % " + "or %"); + parens.skip_until_found_close (parser); + continue; + } else if (!strcmp (p, "seq_cst")) new_memory_order = OMP_MEMORY_ORDER_SEQ_CST; else if (!strcmp (p, "acq_rel")) @@ -17727,8 +17832,9 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) { p = NULL; error_at (cloc, "expected %, %, %, " - "%, %, %, " - "%, % or % clause"); + "%, %, %, %, " + "%, %, %, " + "% or % clause"); } if (p) { @@ -17751,6 +17857,27 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) else memory_order = new_memory_order; } + else if (new_capture) + { + if (capture) + error_at (cloc, "too many %qs clauses", "capture"); + else + capture = true; + } + else if (new_compare) + { + if (compare) + error_at (cloc, "too many %qs clauses", "compare"); + else + compare = true; + } + else if (new_weak) + { + if (weak) + error_at (cloc, "too many %qs clauses", "weak"); + else + weak = true; + } c_parser_consume_token (parser); continue; } @@ -17761,6 +17888,30 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) if (code == ERROR_MARK) code = OMP_ATOMIC; + if (capture) + { + if (code != OMP_ATOMIC) + error_at (loc, "%qs clause is incompatible with % or % " + "clauses", "capture"); + else + code = OMP_ATOMIC_CAPTURE_NEW; + } + if (compare && code != OMP_ATOMIC && code != OMP_ATOMIC_CAPTURE_NEW) + { + error_at (loc, "%qs clause is incompatible with % or % " + "clauses", "compare"); + compare = false; + } + if (fail != OMP_MEMORY_ORDER_UNSPECIFIED && !compare) + { + error_at (loc, "%qs clause requires %qs clause", "fail", "compare"); + fail = OMP_MEMORY_ORDER_UNSPECIFIED; + } + if (weak && !compare) + { + error_at (loc, "%qs clause requires %qs clause", "weak", "compare"); + weak = false; + } if (openacc) memory_order = OMP_MEMORY_ORDER_RELAXED; else if (memory_order == OMP_MEMORY_ORDER_UNSPECIFIED) @@ -17785,7 +17936,6 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) memory_order = OMP_MEMORY_ORDER_ACQUIRE; break; case NOP_EXPR: /* atomic write */ - case OMP_ATOMIC: memory_order = OMP_MEMORY_ORDER_RELEASE; break; default: @@ -17801,36 +17951,32 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) switch (code) { case OMP_ATOMIC_READ: - if (memory_order == OMP_MEMORY_ORDER_ACQ_REL - || memory_order == OMP_MEMORY_ORDER_RELEASE) + if (memory_order == OMP_MEMORY_ORDER_RELEASE) { error_at (loc, "%<#pragma omp atomic read%> incompatible with " - "% or % clauses"); + "% clause"); memory_order = OMP_MEMORY_ORDER_SEQ_CST; } + else if (memory_order == OMP_MEMORY_ORDER_ACQ_REL) + memory_order = OMP_MEMORY_ORDER_ACQUIRE; break; case NOP_EXPR: /* atomic write */ - if (memory_order == OMP_MEMORY_ORDER_ACQ_REL - || memory_order == OMP_MEMORY_ORDER_ACQUIRE) + if (memory_order == OMP_MEMORY_ORDER_ACQUIRE) { error_at (loc, "%<#pragma omp atomic write%> incompatible with " - "% or % clauses"); - memory_order = OMP_MEMORY_ORDER_SEQ_CST; - } - break; - case OMP_ATOMIC: - /* case OMP_ATOMIC_CAPTURE_NEW: - or update to OpenMP 5.1 */ - if (memory_order == OMP_MEMORY_ORDER_ACQ_REL - || memory_order == OMP_MEMORY_ORDER_ACQUIRE) - { - error_at (loc, "%<#pragma omp atomic update%> incompatible with " - "% or % clauses"); + "% clause"); memory_order = OMP_MEMORY_ORDER_SEQ_CST; } + else if (memory_order == OMP_MEMORY_ORDER_ACQ_REL) + memory_order = OMP_MEMORY_ORDER_RELEASE; break; default: break; } + if (fail != OMP_MEMORY_ORDER_UNSPECIFIED) + memory_order + = (enum omp_memory_order) (memory_order + | (fail << OMP_FAIL_MEMORY_ORDER_SHIFT)); switch (code) { @@ -17879,6 +18025,9 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) c_parser_consume_token (parser); structured_block = true; } + else if (compare + && c_parser_next_token_is_keyword (parser, RID_IF)) + break; else { v = c_parser_cast_expression (parser, NULL).value; @@ -17890,6 +18039,12 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) v = non_lvalue (v); if (!c_parser_require (parser, CPP_EQ, "expected %<=%>")) goto saw_error; + if (compare && c_parser_next_token_is_keyword (parser, RID_IF)) + { + eloc = c_parser_peek_token (parser)->location; + error_at (eloc, "expected expression"); + goto saw_error; + } } break; default: @@ -17899,6 +18054,179 @@ c_parser_omp_atomic (location_t loc, c_parser *parser, bool openacc) /* For structured_block case we don't know yet whether old or new x should be captured. */ restart: + if (compare && c_parser_next_token_is_keyword (parser, RID_IF)) + { + c_parser_consume_token (parser); + + matching_parens parens; + if (!parens.require_open (parser)) + goto saw_error; + eloc = c_parser_peek_token (parser)->location; + c_expr cmp_expr; + if (r) + { + cmp_expr = c_parser_cast_expression (parser, NULL); + cmp_expr = default_function_array_conversion (eloc, cmp_expr); + } + else + cmp_expr = c_parser_binary_expression (parser, NULL, void_list_node); + parens.skip_until_found_close (parser); + if (cmp_expr.value == error_mark_node) + goto saw_error; + if (r) + { + if (!c_tree_equal (cmp_expr.value, unfolded_lhs)) + goto bad_if; + cmp_expr.value = rhs1; + rhs1 = NULL_TREE; + gcc_assert (TREE_CODE (cmp_expr.value) == EQ_EXPR); + } + if (TREE_CODE (cmp_expr.value) == EQ_EXPR) + ; + else if (!structured_block && code == OMP_ATOMIC_CAPTURE_NEW) + { + error_at (EXPR_LOC_OR_LOC (cmp_expr.value, eloc), + "expected %<==%> comparison in % condition"); + goto saw_error; + } + else if (TREE_CODE (cmp_expr.value) != GT_EXPR + && TREE_CODE (cmp_expr.value) != LT_EXPR) + { + error_at (EXPR_LOC_OR_LOC (cmp_expr.value, eloc), + "expected %<==%>, %<<%> or %<>%> comparison in % " + "condition"); + goto saw_error; + } + if (!c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>")) + goto saw_error; + + extra_scope = true; + eloc = c_parser_peek_token (parser)->location; + expr = c_parser_cast_expression (parser, NULL); + lhs = expr.value; + expr = default_function_array_conversion (eloc, expr); + unfolded_lhs = expr.value; + lhs = c_fully_fold (lhs, false, NULL, true); + orig_lhs = lhs; + if (lhs == error_mark_node) + goto saw_error; + if (!lvalue_p (unfolded_lhs)) + lhs = non_lvalue (lhs); + if (!c_parser_next_token_is (parser, CPP_EQ)) + { + c_parser_error (parser, "expected %<=%>"); + goto saw_error; + } + c_parser_consume_token (parser); + eloc = c_parser_peek_token (parser)->location; + expr = c_parser_expr_no_commas (parser, NULL); + rhs1 = expr.value; + + if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>")) + goto saw_error; + + if (!c_parser_require (parser, CPP_CLOSE_BRACE, "expected %<}%>")) + goto saw_error; + + extra_scope = false; + no_semicolon = true; + + if (c_tree_equal (TREE_OPERAND (cmp_expr.value, 0), unfolded_lhs)) + { + if (TREE_CODE (cmp_expr.value) == EQ_EXPR) + { + opcode = COND_EXPR; + rhs = c_fully_fold (TREE_OPERAND (cmp_expr.value, 1), + false, NULL, true); + rhs1 = c_fully_fold (rhs1, false, NULL, true); + } + else if (c_tree_equal (TREE_OPERAND (cmp_expr.value, 1), rhs1)) + { + opcode = (TREE_CODE (cmp_expr.value) == GT_EXPR + ? MIN_EXPR : MAX_EXPR); + rhs = c_fully_fold (rhs1, false, NULL, true); + rhs1 = c_fully_fold (TREE_OPERAND (cmp_expr.value, 0), + false, NULL, true); + } + else + goto bad_if; + } + else if (TREE_CODE (cmp_expr.value) == EQ_EXPR) + goto bad_if; + else if (c_tree_equal (TREE_OPERAND (cmp_expr.value, 1), unfolded_lhs) + && c_tree_equal (TREE_OPERAND (cmp_expr.value, 0), rhs1)) + { + opcode = (TREE_CODE (cmp_expr.value) == GT_EXPR + ? MAX_EXPR : MIN_EXPR); + rhs = c_fully_fold (rhs1, false, NULL, true); + rhs1 = c_fully_fold (TREE_OPERAND (cmp_expr.value, 1), + false, NULL, true); + } + else + { + bad_if: + c_parser_error (parser, + "invalid form of %<#pragma omp atomic compare%>"); + goto saw_error; + } + + if (c_parser_next_token_is_keyword (parser, RID_ELSE)) + { + if (code != OMP_ATOMIC_CAPTURE_NEW + || (structured_block && r == NULL_TREE) + || TREE_CODE (cmp_expr.value) != EQ_EXPR) + { + eloc = c_parser_peek_token (parser)->location; + error_at (eloc, "unexpected %"); + goto saw_error; + } + + c_parser_consume_token (parser); + + if (!c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>")) + goto saw_error; + + extra_scope = true; + v = c_parser_cast_expression (parser, NULL).value; + non_lvalue_p = !lvalue_p (v); + v = c_fully_fold (v, false, NULL, true); + if (v == error_mark_node) + goto saw_error; + if (non_lvalue_p) + v = non_lvalue (v); + if (!c_parser_require (parser, CPP_EQ, "expected %<=%>")) + goto saw_error; + + expr = c_parser_expr_no_commas (parser, NULL); + + if (!c_tree_equal (expr.value, unfolded_lhs)) + goto bad_if; + + if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>")) + goto saw_error; + + if (!c_parser_require (parser, CPP_CLOSE_BRACE, "expected %<}%>")) + goto saw_error; + + extra_scope = false; + code = OMP_ATOMIC_CAPTURE_OLD; + if (r == NULL_TREE) + /* Signal to c_finish_omp_atomic that in + if (x == e) { x = d; } else { v = x; } + case the store to v should be conditional. */ + r = void_list_node; + } + else if (code == OMP_ATOMIC_CAPTURE_NEW && !structured_block) + { + c_parser_require_keyword (parser, RID_ELSE, "expected %"); + goto saw_error; + } + else if (code == OMP_ATOMIC_CAPTURE_NEW + && r != NULL_TREE + && v == NULL_TREE) + code = OMP_ATOMIC; + goto stmt_done; + } eloc = c_parser_peek_token (parser)->location; expr = c_parser_cast_expression (parser, NULL); lhs = expr.value; @@ -17908,9 +18236,14 @@ restart: orig_lhs = lhs; switch (TREE_CODE (lhs)) { + invalid_compare: + error_at (eloc, "invalid form of %"); + /* FALLTHRU */ case ERROR_MARK: saw_error: c_parser_skip_to_end_of_block_or_statement (parser); + if (extra_scope && c_parser_next_token_is (parser, CPP_CLOSE_BRACE)) + c_parser_consume_token (parser); if (structured_block) { if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE)) @@ -17933,6 +18266,8 @@ restart: unfolded_lhs = NULL_TREE; opcode = PLUS_EXPR; rhs = integer_one_node; + if (compare) + goto invalid_compare; break; case POSTDECREMENT_EXPR: @@ -17944,6 +18279,8 @@ restart: unfolded_lhs = NULL_TREE; opcode = MINUS_EXPR; rhs = integer_one_node; + if (compare) + goto invalid_compare; break; case COMPOUND_EXPR: @@ -17973,6 +18310,8 @@ restart: && !structured_block && TREE_CODE (orig_lhs) == COMPOUND_EXPR) code = OMP_ATOMIC_CAPTURE_OLD; + if (compare) + goto invalid_compare; break; } if (TREE_CODE (TREE_OPERAND (lhs, 1)) == TRUTH_NOT_EXPR @@ -17988,6 +18327,8 @@ restart: && !structured_block && TREE_CODE (orig_lhs) == COMPOUND_EXPR) code = OMP_ATOMIC_CAPTURE_OLD; + if (compare) + goto invalid_compare; break; } } @@ -17995,6 +18336,11 @@ restart: default: if (!lvalue_p (unfolded_lhs)) lhs = non_lvalue (lhs); + if (compare && !c_parser_next_token_is (parser, CPP_EQ)) + { + c_parser_error (parser, "expected %<=%>"); + goto saw_error; + } switch (c_parser_peek_token (parser)->type) { case CPP_MULT_EQ: @@ -18041,6 +18387,8 @@ restart: case BIT_AND_EXPR: case BIT_IOR_EXPR: case BIT_XOR_EXPR: + if (compare) + break; if (c_tree_equal (TREE_OPERAND (rhs1, 0), unfolded_lhs)) { opcode = TREE_CODE (rhs1); @@ -18061,6 +18409,78 @@ restart: goto stmt_done; } break; + case COND_EXPR: + if (!compare) + break; + if (TREE_CODE (TREE_OPERAND (rhs1, 0)) != GT_EXPR + && TREE_CODE (TREE_OPERAND (rhs1, 0)) != LT_EXPR + && TREE_CODE (TREE_OPERAND (rhs1, 0)) != EQ_EXPR) + break; + if (!TREE_OPERAND (rhs1, 1)) + break; + if (!c_tree_equal (TREE_OPERAND (rhs1, 2), unfolded_lhs)) + break; + if (c_tree_equal (TREE_OPERAND (TREE_OPERAND (rhs1, 0), 0), + unfolded_lhs)) + { + if (TREE_CODE (TREE_OPERAND (rhs1, 0)) == EQ_EXPR) + { + opcode = COND_EXPR; + rhs = c_fully_fold (TREE_OPERAND (TREE_OPERAND (rhs1, + 0), 1), + false, NULL, true); + rhs1 = c_fully_fold (TREE_OPERAND (rhs1, 1), false, + NULL, true); + goto stmt_done; + } + if (c_tree_equal (TREE_OPERAND (TREE_OPERAND (rhs1, 0), 1), + TREE_OPERAND (rhs1, 1))) + { + opcode = (TREE_CODE (TREE_OPERAND (rhs1, 0)) == GT_EXPR + ? MIN_EXPR : MAX_EXPR); + rhs = c_fully_fold (TREE_OPERAND (rhs1, 1), false, NULL, + true); + rhs1 = c_fully_fold (TREE_OPERAND (TREE_OPERAND (rhs1, + 0), 0), + false, NULL, true); + goto stmt_done; + } + } + else if (TREE_CODE (TREE_OPERAND (rhs1, 0)) == EQ_EXPR) + break; + else if (c_tree_equal (TREE_OPERAND (TREE_OPERAND (rhs1, 0), 1), + unfolded_lhs)) + { + if (c_tree_equal (TREE_OPERAND (TREE_OPERAND (rhs1, 0), 0), + TREE_OPERAND (rhs1, 1))) + { + opcode = (TREE_CODE (TREE_OPERAND (rhs1, 0)) == GT_EXPR + ? MAX_EXPR : MIN_EXPR); + rhs = c_fully_fold (TREE_OPERAND (rhs1, 1), false, NULL, + true); + rhs1 = c_fully_fold (TREE_OPERAND (TREE_OPERAND (rhs1, + 0), 1), + false, NULL, true); + goto stmt_done; + } + } + break; + case EQ_EXPR: + if (!compare + || code != OMP_ATOMIC_CAPTURE_NEW + || !structured_block + || v + || r) + break; + if (c_parser_next_token_is (parser, CPP_SEMICOLON) + && c_parser_peek_2nd_token (parser)->keyword == RID_IF) + { + r = lhs; + lhs = NULL_TREE; + c_parser_consume_token (parser); + goto restart; + } + break; case ERROR_MARK: goto saw_error; default: @@ -18109,10 +18529,12 @@ restart: break; } stmt_done: - if (structured_block && code == OMP_ATOMIC_CAPTURE_NEW) + if (structured_block && code == OMP_ATOMIC_CAPTURE_NEW && r == NULL_TREE) { - if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>")) + if (!no_semicolon + && !c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>")) goto saw_error; + no_semicolon = false; v = c_parser_cast_expression (parser, NULL).value; non_lvalue_p = !lvalue_p (v); v = c_fully_fold (v, false, NULL, true); @@ -18135,10 +18557,16 @@ stmt_done: } if (structured_block) { - c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>"); + if (!no_semicolon) + c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>"); c_parser_require (parser, CPP_CLOSE_BRACE, "expected %<}%>"); } done: + if (weak && opcode != COND_EXPR) + { + error_at (loc, "% clause requires atomic equality comparison"); + weak = false; + } if (unfolded_lhs && unfolded_lhs1 && !c_tree_equal (unfolded_lhs, unfolded_lhs1)) { @@ -18147,12 +18575,12 @@ done: stmt = error_mark_node; } else - stmt = c_finish_omp_atomic (loc, code, opcode, lhs, rhs, v, lhs1, rhs1, - swapped, memory_order); + stmt = c_finish_omp_atomic (loc, code, opcode, lhs, rhs, v, lhs1, rhs1, r, + swapped, memory_order, weak); if (stmt != error_mark_node) add_stmt (stmt); - if (!structured_block) + if (!structured_block && !no_semicolon) c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>"); } diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 5849c5a..49d1bb0 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -12426,6 +12426,13 @@ build_binary_op (location_t location, enum tree_code code, maybe_warn_bool_compare (location, code, orig_op0, orig_op1); break; + case MIN_EXPR: + case MAX_EXPR: + /* Used for OpenMP atomics. */ + gcc_assert (flag_openmp); + common = 1; + break; + default: gcc_unreachable (); } -- cgit v1.1 From a26206ec7b8f8c60747c25d009ea7f9b94184215 Mon Sep 17 00:00:00 2001 From: GCC Administrator Date: Sat, 11 Sep 2021 00:16:27 +0000 Subject: Daily bump. --- gcc/c/ChangeLog | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'gcc/c') diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 9deeb0e..28fe7bc 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,16 @@ +2021-09-10 Jakub Jelinek + + * c-parser.c (c_parser_conditional_expression): If omp_atomic_lhs and + cond.value is >, < or == with omp_atomic_lhs as one of the operands, + don't call build_conditional_expr, instead build a COND_EXPR directly. + (c_parser_binary_expression): Avoid calling parser_build_binary_op + if omp_atomic_lhs even in more cases for >, < or ==. + (c_parser_omp_atomic): Update function comment for OpenMP 5.1 atomics, + parse OpenMP 5.1 atomics and fail, compare and weak clauses, allow + acq_rel on atomic read/write and acq_rel/acquire clauses on update. + * c-typeck.c (build_binary_op): For flag_openmp only handle + MIN_EXPR/MAX_EXPR. + 2021-09-07 Marcel Vollweiler * c-parser.c (c_parser_omp_flush): Parse 'seq_cst' clause on 'flush' -- cgit v1.1