This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[C++ PATCH] Fix 23797


I've installed this patch to fix 23797.

The problem was a latent bug in type_dependent_expression_p, (which would accept a TYPE_DECL) was hiding a bug in cp_parser_functional_cast (which presumed the TYPE was a TYPE_DECL).

Note, we do not issue an error on the testcase, even though it uses typename outside of a template. DR 382 (http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#382), which is in ready status, will allow such uses, so it seems silly to me to become strict only to have to remove the strictness later.

booted & tested on i686-pc-linux-gnu

nathan
--
Nathan Sidwell    ::   http://www.codesourcery.com   ::     CodeSourcery LLC
nathan@codesourcery.com    ::     http://www.planetfall.pwp.blueyonder.co.uk

2005-10-12  Nathan Sidwell  <nathan@codesourcery.com>

	PR c++/23797
	* parser.c (cp_parser_functional_cast): Cope when TYPE is not a
	TYPE_DECL.  Use dependent_type_p to check type.
	* pt.c (uses_template_parms_p): Use dependent_type_p for a
	TYPE_DECL.
	(type_dependent_expression_p): Assert we've not been given a
	TYPE_DECL.

Index: cp/parser.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/parser.c,v
retrieving revision 1.363
diff -c -3 -p -r1.363 parser.c
*** cp/parser.c	11 Oct 2005 16:38:51 -0000	1.363
--- cp/parser.c	12 Oct 2005 16:53:37 -0000
*************** cp_parser_postfix_expression (cp_parser 
*** 3956,3961 ****
--- 3956,3962 ----
  
  	/* Consume the `typename' token.  */
  	cp_lexer_consume_token (parser->lexer);
+ 
  	/* Look for the optional `::' operator.  */
  	cp_parser_global_scope_opt (parser,
  				    /*current_scope_valid_p=*/false);
*************** cp_parser_functional_cast (cp_parser* pa
*** 15355,15362 ****
    cast = build_functional_cast (type, expression_list);
    /* [expr.const]/1: In an integral constant expression "only type
       conversions to integral or enumeration type can be used".  */
!   if (cast != error_mark_node && !type_dependent_expression_p (type)
!       && !INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (type)))
      {
        if (cp_parser_non_integral_constant_expression
  	  (parser, "a call to a constructor"))
--- 15356,15365 ----
    cast = build_functional_cast (type, expression_list);
    /* [expr.const]/1: In an integral constant expression "only type
       conversions to integral or enumeration type can be used".  */
!   if (TREE_CODE (type) == TYPE_DECL)
!     type = TREE_TYPE (type);
!   if (cast != error_mark_node && !dependent_type_p (type)
!       && !INTEGRAL_OR_ENUMERATION_TYPE_P (type))
      {
        if (cp_parser_non_integral_constant_expression
  	  (parser, "a call to a constructor"))
Index: cp/pt.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/pt.c,v
retrieving revision 1.1043
diff -c -3 -p -r1.1043 pt.c
*** cp/pt.c	11 Oct 2005 06:26:04 -0000	1.1043
--- cp/pt.c	12 Oct 2005 16:53:43 -0000
*************** uses_template_parms (tree t)
*** 4982,4987 ****
--- 4982,4989 ----
    else if (TREE_CODE (t) == TREE_LIST)
      dependent_p = (uses_template_parms (TREE_VALUE (t))
  		   || uses_template_parms (TREE_CHAIN (t)));
+   else if (TREE_CODE (t) == TYPE_DECL)
+     dependent_p = dependent_type_p (TREE_TYPE (t));
    else if (DECL_P (t)
  	   || EXPR_P (t)
  	   || TREE_CODE (t) == TEMPLATE_PARM_INDEX
*************** type_dependent_expression_p (tree expres
*** 12442,12447 ****
--- 12444,12451 ----
        return false;
      }
  
+   gcc_assert (TREE_CODE (expression) != TYPE_DECL);
+   
    return (dependent_type_p (TREE_TYPE (expression)));
  }
  
// Copyright (C) 2005 Free Software Foundation, Inc.
// Contributed by Nathan Sidwell 12 Oct 2005 <nathan@codesourcery.com>

// PR 23797:ICE
// Origin:  Volker Reichelt <reichelt@gcc.gnu.org>

struct A { typedef int X; };

int i = typename A::X();

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]