diff options
Diffstat (limited to 'gcc/c')
| -rw-r--r-- | gcc/c/ChangeLog | 7 | ||||
| -rw-r--r-- | gcc/c/c-decl.cc | 38 | ||||
| -rw-r--r-- | gcc/c/c-typeck.cc | 5 |
3 files changed, 45 insertions, 5 deletions
diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 89a1bbe..3c37ba0 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,10 @@ +2025-10-27 H.J. Lu <hjl.tools@gmail.com> + + PR c/122427 + * c-decl.cc (diagnose_mismatched_decls): For FUNCTION_DECL, if + OLDDECL has TYPE_ATTRIBUTES and NEWDECL doesn't, try the type + with the OLDDECL attributes. + 2025-10-24 Joseph Myers <josmyers@redhat.com> * c-parser.cc (c_parser_next_tokens_start_typename) diff --git a/gcc/c/c-decl.cc b/gcc/c/c-decl.cc index 061892a..2b31a43 100644 --- a/gcc/c/c-decl.cc +++ b/gcc/c/c-decl.cc @@ -2337,10 +2337,40 @@ diagnose_mismatched_decls (tree newdecl, tree olddecl, error ("conflicting type qualifiers for %q+D", newdecl); } else - error ("conflicting types for %q+D; have %qT", newdecl, newtype); - diagnose_arglist_conflict (newdecl, olddecl, newtype, oldtype); - locate_old_decl (olddecl); - return false; + { + if (TREE_CODE (olddecl) == FUNCTION_DECL) + { + tree attrs = TYPE_ATTRIBUTES (TREE_TYPE (olddecl)); + if (attrs && !TYPE_ATTRIBUTES (TREE_TYPE (newdecl))) + { + /* Similar to the C++ front-end, for FUNCTION_DECL, + if OLDDECL has attributes and NEWDECL doesn't, + try the type with OLDDECL attributes. */ + tree rettype = TREE_TYPE (newtype); + tree tryargs = TYPE_ARG_TYPES (newtype); + tree trytype = c_build_function_type (rettype, + tryargs); + trytype = c_build_type_attribute_variant (trytype, + attrs); + if (comptypes (oldtype, trytype)) + { + *newtypep = newtype = trytype; + comptypes_result = 1; + } + } + } + + if (!comptypes_result) + error ("conflicting types for %q+D; have %qT", newdecl, + newtype); + } + if (!comptypes_result) + { + diagnose_arglist_conflict (newdecl, olddecl, newtype, + oldtype); + locate_old_decl (olddecl); + return false; + } } } /* Warn about enum/integer type mismatches. They are compatible types diff --git a/gcc/c/c-typeck.cc b/gcc/c/c-typeck.cc index 371583b..bc0fb6b 100644 --- a/gcc/c/c-typeck.cc +++ b/gcc/c/c-typeck.cc @@ -3179,7 +3179,10 @@ build_access_with_size_for_counted_by (location_t loc, tree ref, tree result_type = is_fam ? c_build_pointer_type (TREE_TYPE (ref)) : TREE_TYPE (ref); - tree element_size = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (ref))); + tree element_type = TREE_TYPE (TREE_TYPE (ref)); + tree element_size = VOID_TYPE_P (element_type) + ? build_one_cst (size_type_node) + : TYPE_SIZE_UNIT (element_type); tree first_param = is_fam ? c_fully_fold (array_to_pointer_conversion (loc, ref), |
