aboutsummaryrefslogtreecommitdiff
path: root/gcc/c-family
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/c-family')
-rw-r--r--gcc/c-family/ChangeLog151
-rw-r--r--gcc/c-family/c-attribs.cc13
-rw-r--r--gcc/c-family/c-common.cc115
-rw-r--r--gcc/c-family/c-common.def3
-rw-r--r--gcc/c-family/c-common.h7
-rw-r--r--gcc/c-family/c-cppbuiltin.cc1
-rw-r--r--gcc/c-family/c-format.cc4
-rw-r--r--gcc/c-family/c-omp.cc309
-rw-r--r--gcc/c-family/c-opts.cc44
-rw-r--r--gcc/c-family/c-pragma.cc4
-rw-r--r--gcc/c-family/c.opt14
-rw-r--r--gcc/c-family/c.opt.urls9
12 files changed, 620 insertions, 54 deletions
diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog
index 1572c8b..54dcb52 100644
--- a/gcc/c-family/ChangeLog
+++ b/gcc/c-family/ChangeLog
@@ -1,3 +1,154 @@
+2025-07-07 Qing Zhao <qing.zhao@oracle.com>
+
+ Revert:
+ 2025-07-01 Qing Zhao <qing.zhao@oracle.com>
+
+ * c-attribs.cc (handle_counted_by_attribute): Accept counted_by
+ attribute for pointer fields.
+
+2025-07-07 Qing Zhao <qing.zhao@oracle.com>
+
+ Revert:
+ 2025-07-01 Qing Zhao <qing.zhao@oracle.com>
+
+ * c-gimplify.cc (is_address_with_access_with_size): New function.
+ (ubsan_walk_array_refs_r): Instrument an INDIRECT_REF whose base
+ address is .ACCESS_WITH_SIZE or an address computation whose base
+ address is .ACCESS_WITH_SIZE.
+ * c-ubsan.cc (ubsan_instrument_bounds_pointer_address): New function.
+ (struct factor_t): New structure.
+ (get_factors_from_mul_expr): New function.
+ (get_index_from_offset): New function.
+ (get_index_from_pointer_addr_expr): New function.
+ (is_instrumentable_pointer_array_address): New function.
+ (ubsan_array_ref_instrumented_p): Change prototype.
+ Handle MEM_REF in addtional to ARRAY_REF.
+ (ubsan_maybe_instrument_array_ref): Handle MEM_REF in addtional
+ to ARRAY_REF.
+
+2025-07-07 Jason Merrill <jason@redhat.com>
+
+ PR c++/120917
+ * c.opt: Add -Wno-abbreviated-auto-in-template-arg.
+ * c.opt.urls: Regenerate.
+
+2025-07-04 Jakub Jelinek <jakub@redhat.com>
+
+ PR c/120837
+ * c-common.cc (pointer_int_sum): Rewrite the intop PLUS_EXPR or
+ MINUS_EXPR optimization into extension of both intop operands,
+ their separate multiplication and then addition/subtraction followed
+ by rest of pointer_int_sum handling after the multiplication.
+
+2025-07-01 Qing Zhao <qing.zhao@oracle.com>
+
+ * c-gimplify.cc (is_address_with_access_with_size): New function.
+ (ubsan_walk_array_refs_r): Instrument an INDIRECT_REF whose base
+ address is .ACCESS_WITH_SIZE or an address computation whose base
+ address is .ACCESS_WITH_SIZE.
+ * c-ubsan.cc (ubsan_instrument_bounds_pointer_address): New function.
+ (struct factor_t): New structure.
+ (get_factors_from_mul_expr): New function.
+ (get_index_from_offset): New function.
+ (get_index_from_pointer_addr_expr): New function.
+ (is_instrumentable_pointer_array_address): New function.
+ (ubsan_array_ref_instrumented_p): Change prototype.
+ Handle MEM_REF in addtional to ARRAY_REF.
+ (ubsan_maybe_instrument_array_ref): Handle MEM_REF in addtional
+ to ARRAY_REF.
+
+2025-07-01 Qing Zhao <qing.zhao@oracle.com>
+
+ * c-attribs.cc (handle_counted_by_attribute): Accept counted_by
+ attribute for pointer fields.
+
+2025-06-30 Jakub Jelinek <jakub@redhat.com>
+
+ PR c/120520
+ PR c/117023
+ * c-attribs.cc (c_common_gnu_attributes): Allow 2 or 3 arguments for
+ nonnull_if_nonzero attribute instead of only 2.
+ (handle_nonnull_if_nonzero_attribute): Handle 3 argument
+ nonnull_if_nonzero.
+ * c-common.cc (struct nonnull_arg_ctx): Rename other member to other1,
+ add other2 member.
+ (check_function_nonnull): Clear a if nonnull attribute has an
+ argument. Adjust for nonnull_arg_ctx changes. Handle 3 argument
+ nonnull_if_nonzero attribute.
+ (check_nonnull_arg): Adjust for nonnull_arg_ctx changes, emit different
+ diagnostics for 3 argument nonnull_if_nonzero attributes.
+ (check_function_arguments): Adjust ctx var initialization.
+
+2025-06-27 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/120777
+ * c-cppbuiltin.cc (c_cpp_builtins): Predefine
+ __cpp_constexpr_virtual_inheritance=202506L for C++26.
+
+2025-06-26 David Malcolm <dmalcolm@redhat.com>
+
+ * c-opts.cc (c_common_diagnostics_set_defaults): Use
+ diagnostic_context::set_permissive_option.
+
+2025-06-23 Tobias Burnus <tburnus@baylibre.com>
+
+ * c-omp.cc (c_finish_oacc_wait): Handle if clause.
+
+2025-06-16 Jason Merrill <jason@redhat.com>
+
+ * c.opt: Add -Wsfinae-incomplete.
+ * c.opt.urls: Regenerate.
+
+2025-06-12 Gwenole Beauchesne <gb.devel@gmail.com>
+ Andrew Pinski <quic_apinski@quicinc.com>
+
+ PR c++/41201
+ PR c++/48026
+ * c-pragma.cc (init_pragma): Use c_register_pragma_with_early_handler
+ instead of c_register_pragma for `#pragma GCC optimize`.
+
+2025-06-03 Martin Uecker <uecker@tugraz.at>
+
+ PR c/120078
+ * c.opt (Wjump-misses-init): Fix typo.
+
+2025-05-30 Julian Brown <julian@codesourcery.com>
+ Tobias Burnus <tburnus@baylibre.com>
+
+ * c-common.h (c_omp_region_type): Add C_ORT_DECLARE_MAPPER and
+ C_ORT_OMP_DECLARE_MAPPER codes.
+ (omp_mapper_list): Add forward declaration.
+ (c_omp_find_nested_mappers, c_omp_instantiate_mappers): Add prototypes.
+ * c-omp.cc (c_omp_find_nested_mappers): New function.
+ (remap_mapper_decl_info): New struct.
+ (remap_mapper_decl_1, omp_instantiate_mapper,
+ c_omp_instantiate_mappers): New functions.
+
+2025-05-27 Alejandro Colomar <alx@kernel.org>
+ Martin Uecker <uecker@tugraz.at>
+
+ PR c/117025
+ * c-common.h (enum rid): Add RID_COUNTOF.
+ (c_countof_type): New function prototype.
+ * c-common.def (COUNTOF_EXPR): New tree.
+ * c-common.cc (c_common_reswords): Add RID_COUNTOF entry.
+ (c_countof_type): New function.
+
+2025-05-23 Jason Merrill <jason@redhat.com>
+
+ * c-format.cc (flag_chars_t::validate): Control quoting warnings
+ with -Wformat-diag.
+
+2025-05-15 Jason Merrill <jason@redhat.com>
+
+ * c-opts.cc (c_common_post_options): Set flag_coroutines.
+ (set_std_cxx20, set_std_cxx23, set_std_cxx26): Not here.
+
+2025-05-03 Jason Merrill <jason@redhat.com>
+
+ * c-opts.cc (c_common_post_options): Let plain -Wabi warn
+ about changes in a future version.
+
2025-04-28 David Malcolm <dmalcolm@redhat.com>
* c-pretty-print.cc: Drop include of "make-unique.h".
diff --git a/gcc/c-family/c-attribs.cc b/gcc/c-family/c-attribs.cc
index 5a0e3d3..5d7a31f 100644
--- a/gcc/c-family/c-attribs.cc
+++ b/gcc/c-family/c-attribs.cc
@@ -489,7 +489,7 @@ const struct attribute_spec c_common_gnu_attributes[] =
handle_tls_model_attribute, NULL },
{ "nonnull", 0, -1, false, true, true, false,
handle_nonnull_attribute, NULL },
- { "nonnull_if_nonzero", 2, 2, false, true, true, false,
+ { "nonnull_if_nonzero", 2, 3, false, true, true, false,
handle_nonnull_if_nonzero_attribute, NULL },
{ "nonstring", 0, 0, true, false, false, false,
handle_nonstring_attribute, NULL },
@@ -5034,12 +5034,21 @@ handle_nonnull_if_nonzero_attribute (tree *node, tree name,
tree type = *node;
tree pos = TREE_VALUE (args);
tree pos2 = TREE_VALUE (TREE_CHAIN (args));
+ tree chain2 = TREE_CHAIN (TREE_CHAIN (args));
+ tree pos3 = NULL_TREE;
+ if (chain2)
+ pos3 = TREE_VALUE (chain2);
tree val = positional_argument (type, name, pos, POINTER_TYPE, 1);
tree val2 = positional_argument (type, name, pos2, INTEGER_TYPE, 2);
- if (val && val2)
+ tree val3 = NULL_TREE;
+ if (chain2)
+ val3 = positional_argument (type, name, pos3, INTEGER_TYPE, 3);
+ if (val && val2 && (!chain2 || val3))
{
TREE_VALUE (args) = val;
TREE_VALUE (TREE_CHAIN (args)) = val2;
+ if (chain2)
+ TREE_VALUE (chain2) = val3;
}
else
*no_add_attrs = true;
diff --git a/gcc/c-family/c-common.cc b/gcc/c-family/c-common.cc
index 587d764..362dc50 100644
--- a/gcc/c-family/c-common.cc
+++ b/gcc/c-family/c-common.cc
@@ -394,6 +394,7 @@ const struct c_common_resword c_common_reswords[] =
{
{ "_Alignas", RID_ALIGNAS, D_CONLY },
{ "_Alignof", RID_ALIGNOF, D_CONLY },
+ { "_Countof", RID_COUNTOF, D_CONLY },
{ "_Atomic", RID_ATOMIC, D_CONLY },
{ "_BitInt", RID_BITINT, D_CONLY },
{ "_Bool", RID_BOOL, D_CONLY },
@@ -3437,20 +3438,41 @@ pointer_int_sum (location_t loc, enum tree_code resultcode,
an overflow error if the constant is negative but INTOP is not. */
&& (TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (intop))
|| (TYPE_PRECISION (TREE_TYPE (intop))
- == TYPE_PRECISION (TREE_TYPE (ptrop)))))
- {
- enum tree_code subcode = resultcode;
- tree int_type = TREE_TYPE (intop);
- if (TREE_CODE (intop) == MINUS_EXPR)
- subcode = (subcode == PLUS_EXPR ? MINUS_EXPR : PLUS_EXPR);
- /* Convert both subexpression types to the type of intop,
- because weird cases involving pointer arithmetic
- can result in a sum or difference with different type args. */
- ptrop = build_binary_op (EXPR_LOCATION (TREE_OPERAND (intop, 1)),
- subcode, ptrop,
- convert (int_type, TREE_OPERAND (intop, 1)),
- true);
- intop = convert (int_type, TREE_OPERAND (intop, 0));
+ == TYPE_PRECISION (TREE_TYPE (ptrop))))
+ && TYPE_PRECISION (TREE_TYPE (intop)) <= TYPE_PRECISION (sizetype))
+ {
+ tree intop0 = TREE_OPERAND (intop, 0);
+ tree intop1 = TREE_OPERAND (intop, 1);
+ if (TYPE_PRECISION (TREE_TYPE (intop)) != TYPE_PRECISION (sizetype)
+ || TYPE_UNSIGNED (TREE_TYPE (intop)) != TYPE_UNSIGNED (sizetype))
+ {
+ tree optype = c_common_type_for_size (TYPE_PRECISION (sizetype),
+ TYPE_UNSIGNED (sizetype));
+ intop0 = convert (optype, intop0);
+ intop1 = convert (optype, intop1);
+ }
+ tree t = fold_build2_loc (loc, MULT_EXPR, TREE_TYPE (intop0), intop0,
+ convert (TREE_TYPE (intop0), size_exp));
+ intop0 = convert (sizetype, t);
+ if (TREE_OVERFLOW_P (intop0) && !TREE_OVERFLOW (t))
+ intop0 = wide_int_to_tree (TREE_TYPE (intop0), wi::to_wide (intop0));
+ t = fold_build2_loc (loc, MULT_EXPR, TREE_TYPE (intop1), intop1,
+ convert (TREE_TYPE (intop1), size_exp));
+ intop1 = convert (sizetype, t);
+ if (TREE_OVERFLOW_P (intop1) && !TREE_OVERFLOW (t))
+ intop1 = wide_int_to_tree (TREE_TYPE (intop1), wi::to_wide (intop1));
+ intop = build_binary_op (EXPR_LOCATION (intop), TREE_CODE (intop),
+ intop0, intop1, true);
+
+ /* Create the sum or difference. */
+ if (resultcode == MINUS_EXPR)
+ intop = fold_build1_loc (loc, NEGATE_EXPR, sizetype, intop);
+
+ ret = fold_build_pointer_plus_loc (loc, ptrop, intop);
+
+ fold_undefer_and_ignore_overflow_warnings ();
+
+ return ret;
}
/* Convert the integer argument to a type the same size as sizetype
@@ -4080,6 +4102,31 @@ c_alignof_expr (location_t loc, tree expr)
return fold_convert_loc (loc, size_type_node, t);
}
+
+/* Implement the _Countof keyword:
+ Return the number of elements of an array. */
+
+tree
+c_countof_type (location_t loc, tree type)
+{
+ enum tree_code type_code;
+
+ type_code = TREE_CODE (type);
+ if (type_code != ARRAY_TYPE)
+ {
+ error_at (loc, "invalid application of %<_Countof%> to type %qT", type);
+ return error_mark_node;
+ }
+ if (!COMPLETE_TYPE_P (type))
+ {
+ error_at (loc,
+ "invalid application of %<_Countof%> to incomplete type %qT",
+ type);
+ return error_mark_node;
+ }
+
+ return array_type_nelts_top (type);
+}
/* Handle C and C++ default attributes. */
@@ -5723,8 +5770,8 @@ struct nonnull_arg_ctx
/* The function whose arguments are being checked and its type (used
for calls through function pointers). */
const_tree fndecl, fntype;
- /* For nonnull_if_nonzero, index of the other argument. */
- unsigned HOST_WIDE_INT other;
+ /* For nonnull_if_nonzero, index of the other arguments. */
+ unsigned HOST_WIDE_INT other1, other2;
/* True if a warning has been issued. */
bool warned_p;
};
@@ -5792,6 +5839,7 @@ check_function_nonnull (nonnull_arg_ctx &ctx, int nargs, tree *argarray)
check_function_arguments_recurse (check_nonnull_arg, &ctx,
argarray[i], i + 1,
OPT_Wnonnull);
+ a = NULL_TREE;
}
}
if (a == NULL_TREE)
@@ -5803,17 +5851,25 @@ check_function_nonnull (nonnull_arg_ctx &ctx, int nargs, tree *argarray)
unsigned int idx = TREE_INT_CST_LOW (TREE_VALUE (args)) - 1;
unsigned int idx2
= TREE_INT_CST_LOW (TREE_VALUE (TREE_CHAIN (args))) - 1;
+ unsigned int idx3 = idx2;
+ if (tree chain2 = TREE_CHAIN (TREE_CHAIN (args)))
+ idx3 = TREE_INT_CST_LOW (TREE_VALUE (chain2)) - 1;
if (idx < (unsigned) nargs - firstarg
&& idx2 < (unsigned) nargs - firstarg
+ && idx3 < (unsigned) nargs - firstarg
&& INTEGRAL_TYPE_P (TREE_TYPE (argarray[firstarg + idx2]))
- && integer_nonzerop (argarray[firstarg + idx2]))
+ && integer_nonzerop (argarray[firstarg + idx2])
+ && INTEGRAL_TYPE_P (TREE_TYPE (argarray[firstarg + idx3]))
+ && integer_nonzerop (argarray[firstarg + idx3]))
{
- ctx.other = firstarg + idx2 + 1;
+ ctx.other1 = firstarg + idx2 + 1;
+ ctx.other2 = firstarg + idx3 + 1;
check_function_arguments_recurse (check_nonnull_arg, &ctx,
argarray[firstarg + idx],
firstarg + idx + 1,
OPT_Wnonnull);
- ctx.other = 0;
+ ctx.other1 = 0;
+ ctx.other2 = 0;
}
}
return ctx.warned_p;
@@ -5997,14 +6053,25 @@ check_nonnull_arg (void *ctx, tree param, unsigned HOST_WIDE_INT param_num)
}
else
{
- if (pctx->other)
+ if (pctx->other1 && pctx->other2 != pctx->other1)
+ warned = warning_at (loc, OPT_Wnonnull,
+ "argument %u null where non-null expected "
+ "because arguments %u and %u are nonzero",
+ (unsigned) param_num,
+ TREE_CODE (pctx->fntype) == METHOD_TYPE
+ ? (unsigned) pctx->other1 - 1
+ : (unsigned) pctx->other1,
+ TREE_CODE (pctx->fntype) == METHOD_TYPE
+ ? (unsigned) pctx->other2 - 1
+ : (unsigned) pctx->other2);
+ else if (pctx->other1)
warned = warning_at (loc, OPT_Wnonnull,
"argument %u null where non-null expected "
"because argument %u is nonzero",
(unsigned) param_num,
TREE_CODE (pctx->fntype) == METHOD_TYPE
- ? (unsigned) pctx->other - 1
- : (unsigned) pctx->other);
+ ? (unsigned) pctx->other1 - 1
+ : (unsigned) pctx->other1);
else
warned = warning_at (loc, OPT_Wnonnull,
"argument %u null where non-null expected",
@@ -6013,7 +6080,7 @@ check_nonnull_arg (void *ctx, tree param, unsigned HOST_WIDE_INT param_num)
inform (DECL_SOURCE_LOCATION (pctx->fndecl),
"in a call to function %qD declared %qs",
pctx->fndecl,
- pctx->other ? "nonnull_if_nonzero" : "nonnull");
+ pctx->other1 ? "nonnull_if_nonzero" : "nonnull");
}
if (warned)
@@ -6269,7 +6336,7 @@ check_function_arguments (location_t loc, const_tree fndecl, const_tree fntype,
to do this if format checking is enabled. */
if (warn_nonnull)
{
- nonnull_arg_ctx ctx = { loc, fndecl, fntype, 0, false };
+ nonnull_arg_ctx ctx = { loc, fndecl, fntype, 0, 0, false };
warned_p = check_function_nonnull (ctx, nargs, argarray);
}
diff --git a/gcc/c-family/c-common.def b/gcc/c-family/c-common.def
index cf22282..0bcc499 100644
--- a/gcc/c-family/c-common.def
+++ b/gcc/c-family/c-common.def
@@ -50,6 +50,9 @@ DEFTREECODE (EXCESS_PRECISION_EXPR, "excess_precision_expr", tcc_expression, 1)
number. */
DEFTREECODE (USERDEF_LITERAL, "userdef_literal", tcc_exceptional, 3)
+/* Represents a 'countof' expression. */
+DEFTREECODE (COUNTOF_EXPR, "countof_expr", tcc_expression, 1)
+
/* Represents a 'sizeof' expression during C++ template expansion,
or for the purpose of -Wsizeof-pointer-memaccess warning. */
DEFTREECODE (SIZEOF_EXPR, "sizeof_expr", tcc_expression, 1)
diff --git a/gcc/c-family/c-common.h b/gcc/c-family/c-common.h
index ea6c297..675708d 100644
--- a/gcc/c-family/c-common.h
+++ b/gcc/c-family/c-common.h
@@ -105,6 +105,7 @@ enum rid
/* C extensions */
RID_ASM, RID_TYPEOF, RID_TYPEOF_UNQUAL, RID_ALIGNOF, RID_ATTRIBUTE,
+ RID_COUNTOF,
RID_C23_VA_START, RID_VA_ARG,
RID_EXTENSION, RID_IMAGPART, RID_REALPART, RID_LABEL, RID_CHOOSE_EXPR,
RID_TYPES_COMPATIBLE_P, RID_BUILTIN_COMPLEX, RID_BUILTIN_SHUFFLE,
@@ -890,6 +891,7 @@ extern tree c_common_truthvalue_conversion (location_t, tree);
extern void c_apply_type_quals_to_decl (int, tree);
extern tree c_sizeof_or_alignof_type (location_t, tree, bool, bool, int);
extern tree c_alignof_expr (location_t, tree);
+extern tree c_countof_type (location_t, tree);
/* Print an error message for invalid operands to arith operation CODE.
NOP_EXPR is used as a special case (see truthvalue_conversion). */
extern void binary_op_error (rich_location *, enum tree_code, tree, tree);
@@ -1301,10 +1303,12 @@ enum c_omp_region_type
C_ORT_TARGET = 1 << 3,
C_ORT_EXIT_DATA = 1 << 4,
C_ORT_INTEROP = 1 << 5,
+ C_ORT_DECLARE_MAPPER = 1 << 6,
C_ORT_OMP_DECLARE_SIMD = C_ORT_OMP | C_ORT_DECLARE_SIMD,
C_ORT_OMP_TARGET = C_ORT_OMP | C_ORT_TARGET,
C_ORT_OMP_EXIT_DATA = C_ORT_OMP | C_ORT_EXIT_DATA,
C_ORT_OMP_INTEROP = C_ORT_OMP | C_ORT_INTEROP,
+ C_ORT_OMP_DECLARE_MAPPER = C_ORT_OMP | C_ORT_DECLARE_MAPPER,
C_ORT_ACC_TARGET = C_ORT_ACC | C_ORT_TARGET
};
@@ -1343,6 +1347,9 @@ extern enum omp_clause_defaultmap_kind c_omp_predetermined_mapping (tree);
extern tree c_omp_check_context_selector (location_t, tree);
extern void c_omp_mark_declare_variant (location_t, tree, tree);
extern void c_omp_adjust_map_clauses (tree, bool);
+template<typename T> struct omp_mapper_list;
+extern void c_omp_find_nested_mappers (struct omp_mapper_list<tree> *, tree);
+extern tree c_omp_instantiate_mappers (tree);
namespace omp_addr_tokenizer { struct omp_addr_token; }
typedef omp_addr_tokenizer::omp_addr_token omp_addr_token;
diff --git a/gcc/c-family/c-cppbuiltin.cc b/gcc/c-family/c-cppbuiltin.cc
index 4589ee4..459fd86 100644
--- a/gcc/c-family/c-cppbuiltin.cc
+++ b/gcc/c-family/c-cppbuiltin.cc
@@ -1094,6 +1094,7 @@ c_cpp_builtins (cpp_reader *pfile)
cpp_define (pfile, "__cpp_variadic_friend=202403L");
cpp_define (pfile, "__cpp_pack_indexing=202311L");
cpp_define (pfile, "__cpp_pp_embed=202502L");
+ cpp_define (pfile, "__cpp_constexpr_virtual_inheritance=202506L");
}
if (flag_concepts && cxx_dialect > cxx14)
cpp_define (pfile, "__cpp_concepts=202002L");
diff --git a/gcc/c-family/c-format.cc b/gcc/c-family/c-format.cc
index 211d20d..a44249a 100644
--- a/gcc/c-family/c-format.cc
+++ b/gcc/c-family/c-format.cc
@@ -2124,7 +2124,7 @@ flag_chars_t::validate (const format_kind_info *fki,
{
format_warning_at_char (format_string_loc, format_string_cst,
format_chars - orig_format_chars - 1,
- OPT_Wformat_,
+ OPT_Wformat_diag,
"%s used within a quoted sequence",
_(s->name));
}
@@ -2137,7 +2137,7 @@ flag_chars_t::validate (const format_kind_info *fki,
{
format_warning_at_char (format_string_loc, format_string_cst,
format_chars - orig_format_chars,
- OPT_Wformat_,
+ OPT_Wformat_diag,
"%qc conversion used unquoted",
format_char);
}
diff --git a/gcc/c-family/c-omp.cc b/gcc/c-family/c-omp.cc
index a92c6e3..4352214 100644
--- a/gcc/c-family/c-omp.cc
+++ b/gcc/c-family/c-omp.cc
@@ -52,8 +52,8 @@ c_finish_oacc_wait (location_t loc, tree parms, tree clauses)
vec_alloc (args, nparms + 2);
stmt = builtin_decl_explicit (BUILT_IN_GOACC_WAIT);
- if (omp_find_clause (clauses, OMP_CLAUSE_ASYNC))
- t = OMP_CLAUSE_ASYNC_EXPR (clauses);
+ if ((t = omp_find_clause (clauses, OMP_CLAUSE_ASYNC)))
+ t = OMP_CLAUSE_ASYNC_EXPR (t);
else
t = build_int_cst (integer_type_node, GOMP_ASYNC_SYNC);
@@ -71,6 +71,11 @@ c_finish_oacc_wait (location_t loc, tree parms, tree clauses)
stmt = build_call_expr_loc_vec (loc, stmt, args);
+ t = omp_find_clause (clauses, OMP_CLAUSE_IF);
+ if (t)
+ stmt = build3_loc (input_location, COND_EXPR, void_type_node,
+ OMP_CLAUSE_IF_EXPR (t), stmt, NULL_TREE);
+
vec_free (args);
return stmt;
@@ -4282,6 +4287,306 @@ c_omp_address_inspector::expand_map_clause (tree c, tree expr,
return error_mark_node;
}
+/* Given a mapper function MAPPER_FN, recursively scan through the map clauses
+ for that mapper, and if any of those should use a (named or unnamed) mapper
+ themselves, add it to MLIST. */
+
+void
+c_omp_find_nested_mappers (omp_mapper_list<tree> *mlist, tree mapper_fn)
+{
+ tree mapper = lang_hooks.decls.omp_extract_mapper_directive (mapper_fn);
+ tree mapper_name = NULL_TREE;
+
+ if (mapper == error_mark_node)
+ return;
+
+ gcc_assert (TREE_CODE (mapper) == OMP_DECLARE_MAPPER);
+
+ for (tree clause = OMP_DECLARE_MAPPER_CLAUSES (mapper);
+ clause;
+ clause = OMP_CLAUSE_CHAIN (clause))
+ {
+ tree expr = OMP_CLAUSE_DECL (clause);
+ enum gomp_map_kind clause_kind = OMP_CLAUSE_MAP_KIND (clause);
+ tree elem_type;
+
+ if (clause_kind == GOMP_MAP_PUSH_MAPPER_NAME)
+ {
+ mapper_name = expr;
+ continue;
+ }
+ else if (clause_kind == GOMP_MAP_POP_MAPPER_NAME)
+ {
+ mapper_name = NULL_TREE;
+ continue;
+ }
+
+ gcc_assert (TREE_CODE (expr) != TREE_LIST);
+ if (TREE_CODE (expr) == OMP_ARRAY_SECTION)
+ {
+ while (TREE_CODE (expr) == OMP_ARRAY_SECTION)
+ expr = TREE_OPERAND (expr, 0);
+
+ elem_type = TREE_TYPE (expr);
+ }
+ else
+ elem_type = TREE_TYPE (expr);
+
+ /* This might be too much... or not enough? */
+ while (TREE_CODE (elem_type) == ARRAY_TYPE
+ || TREE_CODE (elem_type) == POINTER_TYPE
+ || TREE_CODE (elem_type) == REFERENCE_TYPE)
+ elem_type = TREE_TYPE (elem_type);
+
+ elem_type = TYPE_MAIN_VARIANT (elem_type);
+
+ if (RECORD_OR_UNION_TYPE_P (elem_type)
+ && !mlist->contains (mapper_name, elem_type))
+ {
+ tree nested_mapper_fn
+ = lang_hooks.decls.omp_mapper_lookup (mapper_name, elem_type);
+
+ if (nested_mapper_fn)
+ {
+ mlist->add_mapper (mapper_name, elem_type, nested_mapper_fn);
+ c_omp_find_nested_mappers (mlist, nested_mapper_fn);
+ }
+ else if (mapper_name)
+ {
+ error ("mapper %qE not found for type %qT", mapper_name,
+ elem_type);
+ continue;
+ }
+ }
+ }
+}
+
+struct remap_mapper_decl_info
+{
+ tree dummy_var;
+ tree expr;
+};
+
+/* Helper for rewriting DUMMY_VAR into EXPR in a map clause decl. */
+
+static tree
+remap_mapper_decl_1 (tree *tp, int *walk_subtrees, void *data)
+{
+ remap_mapper_decl_info *map_info = (remap_mapper_decl_info *) data;
+
+ if (operand_equal_p (*tp, map_info->dummy_var))
+ {
+ *tp = map_info->expr;
+ *walk_subtrees = 0;
+ }
+
+ return NULL_TREE;
+}
+
+/* Instantiate a mapper MAPPER for expression EXPR, adding new clauses to
+ OUTLIST. OUTER_KIND is the mapping kind to use if not already specified in
+ the mapper declaration. */
+
+static tree *
+omp_instantiate_mapper (tree *outlist, tree mapper, tree expr,
+ enum gomp_map_kind outer_kind)
+{
+ tree clauses = OMP_DECLARE_MAPPER_CLAUSES (mapper);
+ tree dummy_var = OMP_DECLARE_MAPPER_DECL (mapper);
+ tree mapper_name = NULL_TREE;
+
+ remap_mapper_decl_info map_info;
+ map_info.dummy_var = dummy_var;
+ map_info.expr = expr;
+
+ for (tree c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
+ {
+ tree unshared = unshare_expr (c);
+ enum gomp_map_kind clause_kind = OMP_CLAUSE_MAP_KIND (c);
+ tree t = OMP_CLAUSE_DECL (unshared);
+ tree type = NULL_TREE;
+ bool nonunit_array_with_mapper = false;
+
+ if (clause_kind == GOMP_MAP_PUSH_MAPPER_NAME)
+ {
+ mapper_name = t;
+ continue;
+ }
+ else if (clause_kind == GOMP_MAP_POP_MAPPER_NAME)
+ {
+ mapper_name = NULL_TREE;
+ continue;
+ }
+
+ if (TREE_CODE (t) == OMP_ARRAY_SECTION)
+ {
+ location_t loc = OMP_CLAUSE_LOCATION (c);
+ tree t2 = lang_hooks.decls.omp_map_array_section (loc, t);
+
+ if (t2 == t)
+ {
+ nonunit_array_with_mapper = true;
+ /* We'd want use the mapper for the element type if this worked:
+ look that one up. */
+ type = TREE_TYPE (TREE_TYPE (t));
+ }
+ else
+ {
+ t = t2;
+ type = TREE_TYPE (t);
+ }
+ }
+ else
+ type = TREE_TYPE (t);
+
+ gcc_assert (type);
+
+ if (type == error_mark_node)
+ continue;
+
+ walk_tree (&unshared, remap_mapper_decl_1, &map_info, NULL);
+
+ if (OMP_CLAUSE_MAP_KIND (unshared) == GOMP_MAP_UNSET)
+ OMP_CLAUSE_SET_MAP_KIND (unshared, outer_kind);
+
+ type = TYPE_MAIN_VARIANT (type);
+
+ tree mapper_fn = lang_hooks.decls.omp_mapper_lookup (mapper_name, type);
+
+ if (mapper_fn && nonunit_array_with_mapper)
+ {
+ sorry ("user-defined mapper with non-unit length array section");
+ continue;
+ }
+ else if (mapper_fn)
+ {
+ tree nested_mapper
+ = lang_hooks.decls.omp_extract_mapper_directive (mapper_fn);
+ if (nested_mapper != mapper)
+ {
+ if (clause_kind == GOMP_MAP_UNSET)
+ clause_kind = outer_kind;
+
+ outlist = omp_instantiate_mapper (outlist, nested_mapper,
+ t, clause_kind);
+ continue;
+ }
+ }
+ else if (mapper_name)
+ {
+ error ("mapper %qE not found for type %qT", mapper_name, type);
+ continue;
+ }
+
+ *outlist = unshared;
+ outlist = &OMP_CLAUSE_CHAIN (unshared);
+ }
+
+ return outlist;
+}
+
+/* Given a list of CLAUSES, scan each clause and invoke a user-defined mapper
+ appropriate to the type of the data in that clause, if such a mapper is
+ visible in the current parsing context. */
+
+tree
+c_omp_instantiate_mappers (tree clauses)
+{
+ tree c, *pc, mapper_name = NULL_TREE;
+
+ for (pc = &clauses, c = clauses; c; c = *pc)
+ {
+ bool using_mapper = false;
+
+ switch (OMP_CLAUSE_CODE (c))
+ {
+ case OMP_CLAUSE_MAP:
+ {
+ tree t = OMP_CLAUSE_DECL (c);
+ tree type = NULL_TREE;
+ bool nonunit_array_with_mapper = false;
+
+ if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_PUSH_MAPPER_NAME
+ || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_POP_MAPPER_NAME)
+ {
+ if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_PUSH_MAPPER_NAME)
+ mapper_name = OMP_CLAUSE_DECL (c);
+ else
+ mapper_name = NULL_TREE;
+ pc = &OMP_CLAUSE_CHAIN (c);
+ continue;
+ }
+
+ if (TREE_CODE (t) == OMP_ARRAY_SECTION)
+ {
+ location_t loc = OMP_CLAUSE_LOCATION (c);
+ tree t2 = lang_hooks.decls.omp_map_array_section (loc, t);
+
+ if (t2 == t)
+ {
+ /* !!! Array sections of size >1 with mappers for elements
+ are hard to support. Do something here. */
+ nonunit_array_with_mapper = true;
+ type = TREE_TYPE (TREE_TYPE (t));
+ }
+ else
+ {
+ t = t2;
+ type = TREE_TYPE (t);
+ }
+ }
+ else
+ type = TREE_TYPE (t);
+
+ if (type == NULL_TREE || type == error_mark_node)
+ {
+ pc = &OMP_CLAUSE_CHAIN (c);
+ continue;
+ }
+
+ enum gomp_map_kind kind = OMP_CLAUSE_MAP_KIND (c);
+ if (kind == GOMP_MAP_UNSET)
+ kind = GOMP_MAP_TOFROM;
+
+ type = TYPE_MAIN_VARIANT (type);
+
+ tree mapper_fn
+ = lang_hooks.decls.omp_mapper_lookup (mapper_name, type);
+
+ if (mapper_fn && nonunit_array_with_mapper)
+ {
+ sorry ("user-defined mapper with non-unit length "
+ "array section");
+ using_mapper = true;
+ }
+ else if (mapper_fn)
+ {
+ tree mapper
+ = lang_hooks.decls.omp_extract_mapper_directive (mapper_fn);
+ pc = omp_instantiate_mapper (pc, mapper, t, kind);
+ using_mapper = true;
+ }
+ else if (mapper_name)
+ {
+ error ("mapper %qE not found for type %qT", mapper_name, type);
+ using_mapper = true;
+ }
+ }
+ break;
+
+ default:
+ ;
+ }
+
+ if (using_mapper)
+ *pc = OMP_CLAUSE_CHAIN (c);
+ else
+ pc = &OMP_CLAUSE_CHAIN (c);
+ }
+
+ return clauses;
+}
+
const struct c_omp_directive c_omp_directives[] = {
/* Keep this alphabetically sorted by the first word. Non-null second/third
if any should precede null ones. */
diff --git a/gcc/c-family/c-opts.cc b/gcc/c-family/c-opts.cc
index 4016382..3ee9444 100644
--- a/gcc/c-family/c-opts.cc
+++ b/gcc/c-family/c-opts.cc
@@ -192,7 +192,7 @@ void
c_common_diagnostics_set_defaults (diagnostic_context *context)
{
diagnostic_text_finalizer (context) = c_diagnostic_text_finalizer;
- context->m_opt_permissive = OPT_fpermissive;
+ context->set_permissive_option (OPT_fpermissive);
}
/* Input charset configuration for diagnostics. */
@@ -1085,12 +1085,21 @@ c_common_post_options (const char **pfilename)
/* Change flag_abi_version to be the actual current ABI level, for the
benefit of c_cpp_builtins, and to make comparison simpler. */
const int latest_abi_version = 21;
+ /* Possibly different for non-default ABI fixes within a release. */
+ const int default_abi_version = latest_abi_version;
/* Generate compatibility aliases for ABI v18 (GCC 13) by default. */
const int abi_compat_default = 18;
+ if (flag_abi_version > latest_abi_version)
+ warning (0, "%<-fabi-version=%d%> is not supported, using =%d",
+ flag_abi_version, latest_abi_version);
+
+ SET_OPTION_IF_UNSET (&global_options, &global_options_set,
+ flag_abi_version, default_abi_version);
+
#define clamp(X) if (X == 0 || X > latest_abi_version) X = latest_abi_version
clamp (flag_abi_version);
- clamp (warn_abi_version);
+ /* Don't clamp warn_abi_version, let it be 0 or out of bounds. */
clamp (flag_abi_compat_version);
#undef clamp
@@ -1101,24 +1110,17 @@ c_common_post_options (const char **pfilename)
flag_abi_compat_version = warn_abi_version;
else if (warn_abi_version == -1 && flag_abi_compat_version == -1)
{
- warn_abi_version = latest_abi_version;
- if (flag_abi_version == latest_abi_version)
- {
- auto_diagnostic_group d;
- if (warning (OPT_Wabi, "%<-Wabi%> won%'t warn about anything"))
- {
- inform (input_location, "%<-Wabi%> warns about differences "
- "from the most up-to-date ABI, which is also used "
- "by default");
- inform (input_location, "use e.g. %<-Wabi=11%> to warn about "
- "changes from GCC 7");
- }
- flag_abi_compat_version = abi_compat_default;
- }
+ warn_abi_version = 0;
+ if (flag_abi_version == default_abi_version)
+ flag_abi_compat_version = abi_compat_default;
else
flag_abi_compat_version = latest_abi_version;
}
+ /* Allow warnings vs ABI versions beyond what we currently support. */
+ if (warn_abi_version == 0)
+ warn_abi_version = 1000;
+
/* By default, enable the new inheriting constructor semantics along with ABI
11. New and old should coexist fine, but it is a change in what
artificial symbols are generated. */
@@ -1213,6 +1215,10 @@ c_common_post_options (const char **pfilename)
if (cxx_dialect >= cxx20)
flag_concepts = 1;
+ /* Coroutines are also a C++20 feature. */
+ SET_OPTION_IF_UNSET (&global_options, &global_options_set,
+ flag_coroutines, cxx_dialect >= cxx20);
+
/* Enable lifetime extension of range based for temporaries for C++23. */
SET_OPTION_IF_UNSET (&global_options, &global_options_set,
flag_range_for_ext_temps, cxx_dialect >= cxx23);
@@ -2007,8 +2013,6 @@ set_std_cxx20 (int iso)
flag_isoc94 = 1;
flag_isoc99 = 1;
flag_isoc11 = 1;
- /* C++20 includes coroutines. */
- flag_coroutines = true;
cxx_dialect = cxx20;
lang_hooks.name = "GNU C++20";
}
@@ -2025,8 +2029,6 @@ set_std_cxx23 (int iso)
flag_isoc94 = 1;
flag_isoc99 = 1;
flag_isoc11 = 1;
- /* C++23 includes coroutines. */
- flag_coroutines = true;
cxx_dialect = cxx23;
lang_hooks.name = "GNU C++23";
}
@@ -2043,8 +2045,6 @@ set_std_cxx26 (int iso)
flag_isoc94 = 1;
flag_isoc99 = 1;
flag_isoc11 = 1;
- /* C++26 includes coroutines. */
- flag_coroutines = true;
cxx_dialect = cxx26;
lang_hooks.name = "GNU C++26";
}
diff --git a/gcc/c-family/c-pragma.cc b/gcc/c-family/c-pragma.cc
index 8b5cdcc..137b83bf 100644
--- a/gcc/c-family/c-pragma.cc
+++ b/gcc/c-family/c-pragma.cc
@@ -1847,7 +1847,9 @@ init_pragma (void)
c_register_pragma_with_early_handler ("GCC", "target",
handle_pragma_target,
handle_pragma_target);
- c_register_pragma ("GCC", "optimize", handle_pragma_optimize);
+ c_register_pragma_with_early_handler ("GCC", "optimize",
+ handle_pragma_optimize,
+ handle_pragma_optimize);
c_register_pragma_with_early_handler ("GCC", "push_options",
handle_pragma_push_options,
handle_pragma_push_options);
diff --git a/gcc/c-family/c.opt b/gcc/c-family/c.opt
index 75b6531..6a55e71 100644
--- a/gcc/c-family/c.opt
+++ b/gcc/c-family/c.opt
@@ -397,6 +397,10 @@ Wassign-intercept
ObjC ObjC++ Var(warn_assign_intercept) Warning
Warn whenever an Objective-C assignment is being intercepted by the garbage collector.
+Wabbreviated-auto-in-template-arg
+C++ ObjC++ Warning Var(warn_abbev_auto_targ) Init(1)
+Diagnose a placeholder type in a template argument in a function parameter type.
+
Wbad-function-cast
C ObjC Var(warn_bad_function_cast) Warning
Warn about casting functions to incompatible types.
@@ -938,7 +942,7 @@ C ObjC C++ ObjC++ CPP(cpp_warn_invalid_utf8) CppReason(CPP_W_INVALID_UTF8) Var(w
Warn about invalid UTF-8 characters.
Wjump-misses-init
-C ObjC Var(warn_jump_misses_init) Warning LangEnabledby(C ObjC,Wc++-compat)
+C ObjC Var(warn_jump_misses_init) Warning LangEnabledBy(C ObjC,Wc++-compat)
Warn when a jump misses a variable initialization.
Enum
@@ -1319,6 +1323,14 @@ Wsequence-point
C ObjC C++ ObjC++ Var(warn_sequence_point) Warning LangEnabledBy(C ObjC C++ ObjC++,Wall)
Warn about possible violations of sequence point rules.
+Wsfinae-incomplete=
+C++ ObjC++ Var(warn_sfinae_incomplete) Warning Init(1) Joined RejectNegative UInteger IntegerRange(0, 2)
+Warn about an incomplete type affecting semantics in a non-error context.
+
+Wsfinae-incomplete
+C++ ObjC++ Warning Alias(Wsfinae-incomplete=, 1, 0)
+Warn about an incomplete type affecting semantics in a non-error context.
+
Wshadow-ivar
ObjC ObjC++ Var(warn_shadow_ivar) EnabledBy(Wshadow) Init(1) Warning
Warn if a local declaration hides an instance variable.
diff --git a/gcc/c-family/c.opt.urls b/gcc/c-family/c.opt.urls
index ad6d8a0..401e6e7 100644
--- a/gcc/c-family/c.opt.urls
+++ b/gcc/c-family/c.opt.urls
@@ -139,6 +139,9 @@ UrlSuffix(gcc/Warning-Options.html#index-Warray-parameter)
Wassign-intercept
UrlSuffix(gcc/Objective-C-and-Objective-C_002b_002b-Dialect-Options.html#index-Wassign-intercept)
+Wabbreviated-auto-in-template-arg
+UrlSuffix(gcc/C_002b_002b-Dialect-Options.html#index-Wabbreviated-auto-in-template-arg)
+
Wbad-function-cast
UrlSuffix(gcc/Warning-Options.html#index-Wbad-function-cast)
@@ -756,6 +759,12 @@ UrlSuffix(gcc/Warning-Options.html#index-Wno-self-move)
Wsequence-point
UrlSuffix(gcc/Warning-Options.html#index-Wno-sequence-point)
+Wsfinae-incomplete=
+UrlSuffix(gcc/C_002b_002b-Dialect-Options.html#index-Wno-sfinae-incomplete)
+
+Wsfinae-incomplete
+UrlSuffix(gcc/C_002b_002b-Dialect-Options.html#index-Wno-sfinae-incomplete)
+
Wshadow-ivar
UrlSuffix(gcc/Warning-Options.html#index-Wno-shadow-ivar)