re PR c++/21336 (Internal compiler error when using custom new operators)
PR c++/21336 * cp-tree.h (grok_op_properties): Remove friendp parameter. * decl.c (grokfndecl): Adjust call. (grok_op_properties): Determine the class of which the function is a member by looking at its DECL_CONTEXT, not current_class_type. * pt.c (tsubst_decl): Adjust call to grok_op_properties. PR c++/21336 * g++.dg/template/new2.C: New test. From-SVN: r100541
This commit is contained in:
parent
83cd747fd9
commit
7e45bd18da
6 changed files with 77 additions and 44 deletions
|
@ -1,3 +1,12 @@
|
|||
2005-06-03 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/21336
|
||||
* cp-tree.h (grok_op_properties): Remove friendp parameter.
|
||||
* decl.c (grokfndecl): Adjust call.
|
||||
(grok_op_properties): Determine the class of which the function is
|
||||
a member by looking at its DECL_CONTEXT, not current_class_type.
|
||||
* pt.c (tsubst_decl): Adjust call to grok_op_properties.
|
||||
|
||||
2005-06-02 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
* method.c (synthesize_method): Add addtional arg to warning call.
|
||||
|
|
|
@ -3766,7 +3766,7 @@ extern int copy_fn_p (tree);
|
|||
extern tree get_scope_of_declarator (const cp_declarator *);
|
||||
extern void grok_special_member_properties (tree);
|
||||
extern int grok_ctor_properties (tree, tree);
|
||||
extern void grok_op_properties (tree, int, bool);
|
||||
extern void grok_op_properties (tree, bool);
|
||||
extern tree xref_tag (enum tag_types, tree, tag_scope, bool);
|
||||
extern tree xref_tag_from_type (tree, tree, tag_scope);
|
||||
extern void xref_basetypes (tree, tree);
|
||||
|
|
|
@ -5610,7 +5610,7 @@ grokfndecl (tree ctype,
|
|||
}
|
||||
|
||||
if (IDENTIFIER_OPNAME_P (DECL_NAME (decl)))
|
||||
grok_op_properties (decl, friendp, /*complain=*/true);
|
||||
grok_op_properties (decl, /*complain=*/true);
|
||||
|
||||
if (ctype && decl_function_context (decl))
|
||||
DECL_NO_STATIC_CHAIN (decl) = 1;
|
||||
|
@ -8608,7 +8608,7 @@ unary_op_p (enum tree_code code)
|
|||
errors are issued for invalid declarations. */
|
||||
|
||||
void
|
||||
grok_op_properties (tree decl, int friendp, bool complain)
|
||||
grok_op_properties (tree decl, bool complain)
|
||||
{
|
||||
tree argtypes = TYPE_ARG_TYPES (TREE_TYPE (decl));
|
||||
tree argtype;
|
||||
|
@ -8616,6 +8616,7 @@ grok_op_properties (tree decl, int friendp, bool complain)
|
|||
tree name = DECL_NAME (decl);
|
||||
enum tree_code operator_code;
|
||||
int arity;
|
||||
tree class_type;
|
||||
|
||||
/* Count the number of arguments. */
|
||||
for (argtype = argtypes, arity = 0;
|
||||
|
@ -8623,8 +8624,9 @@ grok_op_properties (tree decl, int friendp, bool complain)
|
|||
argtype = TREE_CHAIN (argtype))
|
||||
++arity;
|
||||
|
||||
if (current_class_type == NULL_TREE)
|
||||
friendp = 1;
|
||||
class_type = DECL_CONTEXT (decl);
|
||||
if (class_type && !CLASS_TYPE_P (class_type))
|
||||
class_type = NULL_TREE;
|
||||
|
||||
if (DECL_CONV_FN_P (decl))
|
||||
operator_code = TYPE_EXPR;
|
||||
|
@ -8653,30 +8655,28 @@ grok_op_properties (tree decl, int friendp, bool complain)
|
|||
gcc_assert (operator_code != LAST_CPLUS_TREE_CODE);
|
||||
SET_OVERLOADED_OPERATOR_CODE (decl, operator_code);
|
||||
|
||||
if (! friendp)
|
||||
{
|
||||
switch (operator_code)
|
||||
{
|
||||
case NEW_EXPR:
|
||||
TYPE_HAS_NEW_OPERATOR (current_class_type) = 1;
|
||||
break;
|
||||
if (class_type)
|
||||
switch (operator_code)
|
||||
{
|
||||
case NEW_EXPR:
|
||||
TYPE_HAS_NEW_OPERATOR (class_type) = 1;
|
||||
break;
|
||||
|
||||
case DELETE_EXPR:
|
||||
TYPE_GETS_DELETE (current_class_type) |= 1;
|
||||
break;
|
||||
case DELETE_EXPR:
|
||||
TYPE_GETS_DELETE (class_type) |= 1;
|
||||
break;
|
||||
|
||||
case VEC_NEW_EXPR:
|
||||
TYPE_HAS_ARRAY_NEW_OPERATOR (current_class_type) = 1;
|
||||
break;
|
||||
case VEC_NEW_EXPR:
|
||||
TYPE_HAS_ARRAY_NEW_OPERATOR (class_type) = 1;
|
||||
break;
|
||||
|
||||
case VEC_DELETE_EXPR:
|
||||
TYPE_GETS_DELETE (current_class_type) |= 2;
|
||||
break;
|
||||
case VEC_DELETE_EXPR:
|
||||
TYPE_GETS_DELETE (class_type) |= 2;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* [basic.std.dynamic.allocation]/1:
|
||||
|
||||
|
@ -8755,32 +8755,38 @@ grok_op_properties (tree decl, int friendp, bool complain)
|
|||
if (operator_code == CALL_EXPR)
|
||||
return;
|
||||
|
||||
if (IDENTIFIER_TYPENAME_P (name) && ! DECL_TEMPLATE_INFO (decl))
|
||||
/* Warn about conversion operators that will never be used. */
|
||||
if (IDENTIFIER_TYPENAME_P (name)
|
||||
&& ! DECL_TEMPLATE_INFO (decl)
|
||||
&& warn_conversion
|
||||
/* Warn only declaring the function; there is no need to
|
||||
warn again about out-of-class definitions. */
|
||||
&& class_type == current_class_type)
|
||||
{
|
||||
tree t = TREE_TYPE (name);
|
||||
if (! friendp)
|
||||
int ref = (TREE_CODE (t) == REFERENCE_TYPE);
|
||||
const char *what = 0;
|
||||
|
||||
if (ref)
|
||||
t = TYPE_MAIN_VARIANT (TREE_TYPE (t));
|
||||
|
||||
if (TREE_CODE (t) == VOID_TYPE)
|
||||
what = "void";
|
||||
else if (class_type)
|
||||
{
|
||||
int ref = (TREE_CODE (t) == REFERENCE_TYPE);
|
||||
const char *what = 0;
|
||||
|
||||
if (ref)
|
||||
t = TYPE_MAIN_VARIANT (TREE_TYPE (t));
|
||||
|
||||
if (TREE_CODE (t) == VOID_TYPE)
|
||||
what = "void";
|
||||
else if (t == current_class_type)
|
||||
if (t == class_type)
|
||||
what = "the same type";
|
||||
/* Don't force t to be complete here. */
|
||||
else if (IS_AGGR_TYPE (t)
|
||||
&& COMPLETE_TYPE_P (t)
|
||||
&& DERIVED_FROM_P (t, current_class_type))
|
||||
&& DERIVED_FROM_P (t, class_type))
|
||||
what = "a base class";
|
||||
|
||||
if (what && warn_conversion)
|
||||
warning (0, "conversion to %s%s will never use a type "
|
||||
"conversion operator",
|
||||
ref ? "a reference to " : "", what);
|
||||
}
|
||||
|
||||
if (what)
|
||||
warning (0, "conversion to %s%s will never use a type "
|
||||
"conversion operator",
|
||||
ref ? "a reference to " : "", what);
|
||||
}
|
||||
if (operator_code == COND_EXPR)
|
||||
{
|
||||
|
|
|
@ -6494,8 +6494,7 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
|
|||
clone_function_decl (r, /*update_method_vec_p=*/0);
|
||||
}
|
||||
else if (IDENTIFIER_OPNAME_P (DECL_NAME (r)))
|
||||
grok_op_properties (r, DECL_FRIEND_P (r),
|
||||
(complain & tf_error) != 0);
|
||||
grok_op_properties (r, (complain & tf_error) != 0);
|
||||
|
||||
if (DECL_FRIEND_P (t) && DECL_FRIEND_CONTEXT (t))
|
||||
SET_DECL_FRIEND_CONTEXT (r,
|
||||
|
|
|
@ -1,3 +1,8 @@
|
|||
2005-06-03 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/21336
|
||||
* g++.dg/template/new2.C: New test.
|
||||
|
||||
2005-06-03 Josh Conner <jconner@apple.com>
|
||||
|
||||
* gcc.dg/ppc-vector-memcpy.c (foo): Use non-zero values for
|
||||
|
|
14
gcc/testsuite/g++.dg/template/new2.C
Normal file
14
gcc/testsuite/g++.dg/template/new2.C
Normal file
|
@ -0,0 +1,14 @@
|
|||
// PR c++/21336
|
||||
|
||||
typedef __SIZE_TYPE__ size_t;
|
||||
template<class _T> void* operator new( size_t Size, _T&);
|
||||
struct B {
|
||||
int a;
|
||||
int* m() {
|
||||
return new(a) int;
|
||||
}
|
||||
};
|
||||
B* n() {
|
||||
return new B();
|
||||
}
|
||||
|
Loading…
Add table
Reference in a new issue