Commit 93e1ddcf by Jason Merrill Committed by Jason Merrill

decl.c (grokdeclarator): Don't check quals on fn type.

	* 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.

From-SVN: r159597
parent 2872152c
2010-05-19 Jason Merrill <jason@redhat.com> 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 PR c++/44193
* typeck.c (type_memfn_quals): New fn. * typeck.c (type_memfn_quals): New fn.
(apply_memfn_quals): New fn. (apply_memfn_quals): New fn.
......
...@@ -8224,21 +8224,6 @@ grokdeclarator (const cp_declarator *declarator, ...@@ -8224,21 +8224,6 @@ grokdeclarator (const cp_declarator *declarator,
error ("qualifiers are not allowed on declaration of %<operator %T%>", error ("qualifiers are not allowed on declaration of %<operator %T%>",
ctor_return_type); 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_quals |= cp_type_quals (type);
type = cp_build_qualified_type_real type = cp_build_qualified_type_real
(type, type_quals, ((typedef_decl && !DECL_ARTIFICIAL (typedef_decl) (type, type_quals, ((typedef_decl && !DECL_ARTIFICIAL (typedef_decl)
......
...@@ -14099,9 +14099,9 @@ check_cv_quals_for_unify (int strict, tree arg, tree parm) ...@@ -14099,9 +14099,9 @@ check_cv_quals_for_unify (int strict, tree arg, tree parm)
{ {
/* Although a CVR qualifier is ignored when being applied to a /* Although a CVR qualifier is ignored when being applied to a
substituted template parameter ([8.3.2]/1 for example), that substituted template parameter ([8.3.2]/1 for example), that
does not apply during deduction [14.8.2.4]/1, (even though does not allow us to unify "const T" with "int&" because both
that is not explicitly mentioned, [14.8.2.4]/9 indicates types are not of the form "cv-list T" [14.8.2.5 temp.deduct.type].
this). Except when we're allowing additional CV qualifiers It is ok when we're allowing additional CV qualifiers
at the outer level [14.8.2.1]/3,1st bullet. */ at the outer level [14.8.2.1]/3,1st bullet. */
if ((TREE_CODE (arg) == REFERENCE_TYPE if ((TREE_CODE (arg) == REFERENCE_TYPE
|| TREE_CODE (arg) == FUNCTION_TYPE || TREE_CODE (arg) == FUNCTION_TYPE
......
...@@ -865,13 +865,15 @@ cp_build_qualified_type_real (tree type, ...@@ -865,13 +865,15 @@ cp_build_qualified_type_real (tree type,
} }
/* A reference or method type shall not be cv-qualified. /* 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) if (type_quals & (TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE)
&& (TREE_CODE (type) == REFERENCE_TYPE && (TREE_CODE (type) == REFERENCE_TYPE
|| TREE_CODE (type) == FUNCTION_TYPE || TREE_CODE (type) == FUNCTION_TYPE
|| TREE_CODE (type) == METHOD_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_CONST | TYPE_QUAL_VOLATILE);
} }
...@@ -890,24 +892,16 @@ cp_build_qualified_type_real (tree type, ...@@ -890,24 +892,16 @@ cp_build_qualified_type_real (tree type,
type_quals &= ~TYPE_QUAL_RESTRICT; type_quals &= ~TYPE_QUAL_RESTRICT;
} }
if (bad_quals == TYPE_UNQUALIFIED) if (bad_quals == TYPE_UNQUALIFIED
|| (complain & tf_ignore_bad_quals))
/*OK*/; /*OK*/;
else if (!(complain & (tf_error | tf_ignore_bad_quals))) else if (!(complain & tf_error))
return error_mark_node; return error_mark_node;
else else
{ {
if (complain & tf_ignore_bad_quals) tree bad_type = build_qualified_type (ptr_type_node, bad_quals);
/* We're not going to warn about constifying things that can't error ("%qV qualifiers cannot be applied to %qT",
be constified. */ bad_type, type);
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);
}
} }
/* Retrieve (or create) the appropriately qualified variant. */ /* Retrieve (or create) the appropriately qualified variant. */
......
...@@ -7952,23 +7952,8 @@ cp_apply_type_quals_to_decl (int type_quals, tree decl) ...@@ -7952,23 +7952,8 @@ cp_apply_type_quals_to_decl (int type_quals, tree decl)
if (TREE_CODE (decl) == TYPE_DECL) if (TREE_CODE (decl) == TYPE_DECL)
return; return;
if (TREE_CODE (type) == FUNCTION_TYPE gcc_assert (!(TREE_CODE (type) == FUNCTION_TYPE
&& type_quals != TYPE_UNQUALIFIED) && 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;
}
/* Avoid setting TREE_READONLY incorrectly. */ /* Avoid setting TREE_READONLY incorrectly. */
if (/* If the object has a constructor, the constructor may modify if (/* If the object has a constructor, the constructor may modify
......
2010-05-19 Jason Merrill <jason@redhat.com> 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 PR c++/44193
* g++.dg/template/fntype1.C: New. * g++.dg/template/fntype1.C: New.
......
// { dg-do compile } // { dg-do compile }
// { dg-options "-pedantic -pedantic-errors" }
typedef int FIC(int) const; typedef int FIC(int) const;
typedef int FI(int); typedef int FI(int);
...@@ -7,15 +7,14 @@ FIC f; // { dg-error "qualified" } ...@@ -7,15 +7,14 @@ FIC f; // { dg-error "qualified" }
struct S { struct S {
FIC f; // OK FIC f; // OK
const FI g; // { dg-error "qualifier" } const FI g;
int h(int) const; int h(int) const;
}; };
FIC S::*pm = &S::f; FIC S::*pm = &S::f;
const FI S::*pm2 = &S::f; // { dg-error "qualifier" } const FI S::*pm2 = &S::f; // { dg-error "cannot convert" }
// { dg-error "cannot convert" "cannot convert" { target *-*-* } 16 } const FIC S::*pm3 = &S::f;
const FIC S::*pm3 = &S::f; // { dg-error "qualifier" }
int S::f(int) const int S::f(int) const
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment