2010-05-19 Jason Merrill <jason@redhat.com>
+ * decl.c (grokdeclarator): Don't check quals on fn type.
+ * typeck.c (cp_apply_type_quals_to_decl): Likewise.
+ * tree.c (cp_build_qualified_type_real): Simplify qualifier checking.
+
PR c++/44193
* typeck.c (type_memfn_quals): New fn.
(apply_memfn_quals): New fn.
error ("qualifiers are not allowed on declaration of %<operator %T%>",
ctor_return_type);
- if (TREE_CODE (type) == FUNCTION_TYPE
- && type_quals != TYPE_UNQUALIFIED)
- {
- /* This was an error in C++98 (cv-qualifiers cannot be added to
- a function type), but DR 295 makes the code well-formed by
- dropping the extra qualifiers. */
- if (pedantic && cxx_dialect == cxx98)
- {
- tree bad_type = build_qualified_type (type, type_quals);
- pedwarn (input_location, OPT_pedantic,
- "ignoring %qV qualifiers added to function type %qT",
- bad_type, type);
- }
- type_quals = TYPE_UNQUALIFIED;
- }
type_quals |= cp_type_quals (type);
type = cp_build_qualified_type_real
(type, type_quals, ((typedef_decl && !DECL_ARTIFICIAL (typedef_decl)
{
/* Although a CVR qualifier is ignored when being applied to a
substituted template parameter ([8.3.2]/1 for example), that
- does not apply during deduction [14.8.2.4]/1, (even though
- that is not explicitly mentioned, [14.8.2.4]/9 indicates
- this). Except when we're allowing additional CV qualifiers
+ does not allow us to unify "const T" with "int&" because both
+ types are not of the form "cv-list T" [14.8.2.5 temp.deduct.type].
+ It is ok when we're allowing additional CV qualifiers
at the outer level [14.8.2.1]/3,1st bullet. */
if ((TREE_CODE (arg) == REFERENCE_TYPE
|| TREE_CODE (arg) == FUNCTION_TYPE
}
/* A reference or method type shall not be cv-qualified.
- [dcl.ref], [dcl.fct] */
+ [dcl.ref], [dcl.fct]. This used to be an error, but as of DR 295
+ (in CD1) we always ignore extra cv-quals on functions. */
if (type_quals & (TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE)
&& (TREE_CODE (type) == REFERENCE_TYPE
|| TREE_CODE (type) == FUNCTION_TYPE
|| TREE_CODE (type) == METHOD_TYPE))
{
- bad_quals |= type_quals & (TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE);
+ if (TREE_CODE (type) == REFERENCE_TYPE)
+ bad_quals |= type_quals & (TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE);
type_quals &= ~(TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE);
}
type_quals &= ~TYPE_QUAL_RESTRICT;
}
- if (bad_quals == TYPE_UNQUALIFIED)
+ if (bad_quals == TYPE_UNQUALIFIED
+ || (complain & tf_ignore_bad_quals))
/*OK*/;
- else if (!(complain & (tf_error | tf_ignore_bad_quals)))
+ else if (!(complain & tf_error))
return error_mark_node;
else
{
- if (complain & tf_ignore_bad_quals)
- /* We're not going to warn about constifying things that can't
- be constified. */
- bad_quals &= ~TYPE_QUAL_CONST;
- if (bad_quals)
- {
- tree bad_type = build_qualified_type (ptr_type_node, bad_quals);
-
- if (!(complain & tf_ignore_bad_quals))
- error ("%qV qualifiers cannot be applied to %qT",
- bad_type, type);
- }
+ tree bad_type = build_qualified_type (ptr_type_node, bad_quals);
+ error ("%qV qualifiers cannot be applied to %qT",
+ bad_type, type);
}
/* Retrieve (or create) the appropriately qualified variant. */
if (TREE_CODE (decl) == TYPE_DECL)
return;
- if (TREE_CODE (type) == FUNCTION_TYPE
- && type_quals != TYPE_UNQUALIFIED)
- {
- /* This was an error in C++98 (cv-qualifiers cannot be added to
- a function type), but DR 295 makes the code well-formed by
- dropping the extra qualifiers. */
- if (pedantic)
- {
- tree bad_type = build_qualified_type (type, type_quals);
- pedwarn (input_location, OPT_pedantic,
- "ignoring %qV qualifiers added to function type %qT",
- bad_type, type);
- }
-
- TREE_TYPE (decl) = TYPE_MAIN_VARIANT (type);
- return;
- }
+ gcc_assert (!(TREE_CODE (type) == FUNCTION_TYPE
+ && type_quals != TYPE_UNQUALIFIED));
/* Avoid setting TREE_READONLY incorrectly. */
if (/* If the object has a constructor, the constructor may modify
2010-05-19 Jason Merrill <jason@redhat.com>
+ * g++.dg/other/cv_func.C: Don't expect errors about cv-qualified
+ function type.
+
PR c++/44193
* g++.dg/template/fntype1.C: New.
// { dg-do compile }
-// { dg-options "-pedantic -pedantic-errors" }
+
typedef int FIC(int) const;
typedef int FI(int);
struct S {
FIC f; // OK
- const FI g; // { dg-error "qualifier" }
+ const FI g;
int h(int) const;
};
FIC S::*pm = &S::f;
-const FI S::*pm2 = &S::f; // { dg-error "qualifier" }
-// { dg-error "cannot convert" "cannot convert" { target *-*-* } 16 }
-const FIC S::*pm3 = &S::f; // { dg-error "qualifier" }
+const FI S::*pm2 = &S::f; // { dg-error "cannot convert" }
+const FIC S::*pm3 = &S::f;
int S::f(int) const
{