re PR c++/35546 (__attribute__(format...) broken for members of template classes?)

PR c++/35546
	* pt.c (apply_late_template_attributes): Don't call tsubst on
	first attribute argument if it is IDENTIFIER_NODE.

	* g++.dg/ext/attrib33.C: New test.

From-SVN: r133615
This commit is contained in:
Jakub Jelinek 2008-03-26 21:34:14 +01:00 committed by Jakub Jelinek
parent 33558d947c
commit ff2f1c5f22
4 changed files with 50 additions and 3 deletions

View File

@ -1,5 +1,9 @@
2008-03-26 Jakub Jelinek <jakub@redhat.com>
PR c++/35546
* pt.c (apply_late_template_attributes): Don't call tsubst on
first attribute argument if it is IDENTIFIER_NODE.
PR c++/35332
* error.c (dump_expr): Pass {,UN}ORDERED_EXPR, UN{LT,LE,GT,GE,EQ}_EXPR
and LTGT_EXPR to pp_expression.

View File

@ -6791,9 +6791,29 @@ apply_late_template_attributes (tree *decl_p, tree attributes, int attr_flags,
{
*p = TREE_CHAIN (t);
TREE_CHAIN (t) = NULL_TREE;
TREE_VALUE (t)
= tsubst_expr (TREE_VALUE (t), args, complain, in_decl,
/*integral_constant_expression_p=*/false);
/* If the first attribute argument is an identifier, don't
pass it through tsubst. Attributes like mode, format,
cleanup and several target specific attributes expect it
unmodified. */
if (TREE_VALUE (t)
&& TREE_CODE (TREE_VALUE (t)) == TREE_LIST
&& TREE_VALUE (TREE_VALUE (t))
&& (TREE_CODE (TREE_VALUE (TREE_VALUE (t)))
== IDENTIFIER_NODE))
{
tree chain
= tsubst_expr (TREE_CHAIN (TREE_VALUE (t)), args, complain,
in_decl,
/*integral_constant_expression_p=*/false);
if (chain != TREE_CHAIN (TREE_VALUE (t)))
TREE_VALUE (t)
= tree_cons (NULL_TREE, TREE_VALUE (TREE_VALUE (t)),
chain);
}
else
TREE_VALUE (t)
= tsubst_expr (TREE_VALUE (t), args, complain, in_decl,
/*integral_constant_expression_p=*/false);
*q = t;
q = &TREE_CHAIN (t);
}

View File

@ -1,3 +1,8 @@
2008-03-26 Jakub Jelinek <jakub@redhat.com>
PR c++/35546
* g++.dg/ext/attrib33.C: New test.
2008-03-26 Richard Guenther <rguenther@suse.de>
Revert

View File

@ -0,0 +1,18 @@
// PR c++/35546
// { dg-do compile }
template <int N>
struct T
{
void foo (char const * ...) __attribute__ ((format (printf,2,3)));
};
template struct T<3>;
template <typename T>
struct U
{
typedef T __attribute__((mode (SI))) V;
};
U<int>::V v;