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] Backport to 3.4


This patch backports 3 regression fixes to 3.4.

built & 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

Index: cp/ChangeLog
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/ChangeLog,v
retrieving revision 1.3892.2.223
diff -c -3 -p -r1.3892.2.223 ChangeLog
*** cp/ChangeLog	8 Jun 2005 11:25:51 -0000	1.3892.2.223
--- cp/ChangeLog	8 Jun 2005 14:48:49 -0000
***************
*** 1,3 ****
--- 1,23 ----
+ 2005-06-08  Nathan Sidwell  <nathan@codesourcery.com>
+ 
+ 	PR c+++/21903
+ 	* cp-tree.def (DEFAULT_ARG): Document TREE_CHAIN use.
+ 	* parser.c (cp_parser_late_parsing_default_args): Propagate parsed
+ 	argument to any early instantiations.
+ 	* pt.c (tsubst_arg_types): Chain early instantiation of default
+ 	arg.
+ 
+ 	PR c++/19884
+ 	* pt.c (check_explicit_specialization): Make sure namespace
+ 	binding lookup found an overloaded function.
+ 	(lookup_template_function): Just assert FNS is an overloaded
+ 	function.
+ 
+ 	PR c++/19608
+ 	* parser.c (cp_parser_late_parsing_for_member): Use
+ 	current_function_decl as scope to push to and from.
+ 	testsuite:
+ 
  2005-06-08  Volker Reichelt  <reichelt@igpm.rwth-aachen.de>
  
  	PR c++/20563
Index: testsuite/ChangeLog
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/ChangeLog,v
retrieving revision 1.3389.2.402
diff -c -3 -p -r1.3389.2.402 ChangeLog
*** testsuite/ChangeLog	8 Jun 2005 11:25:57 -0000	1.3389.2.402
--- testsuite/ChangeLog	8 Jun 2005 14:58:42 -0000
***************
*** 1,3 ****
--- 1,15 ----
+ 2005-06-08  Nathan Sidwell  <nathan@codesourcery.com>
+ 
+ 	PR c++/21903
+ 	* g++.dg/parse/defarg9.C: New.
+ 
+ 	PR c++/19884
+ 	* g++.old-deja/g++.oliva/template6.C: Add another case.
+ 	* g++.dg/template/explicit6.C: New.
+ 
+ 	PR c++/19608
+ 	* g++.dg/parse/local-class1.C: New.
+ 
  2005-06-08  Volker Reichelt  <reichelt@igpm.rwth-aachen.de>
  
  	PR c++/20563
Index: cp/cp-tree.def
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/cp-tree.def,v
retrieving revision 1.80
diff -c -3 -p -r1.80 cp-tree.def
*** cp/cp-tree.def	15 Aug 2003 12:15:56 -0000	1.80
--- cp/cp-tree.def	8 Jun 2005 14:48:50 -0000
*************** DEFTREECODE (USING_DECL, "using_decl", '
*** 203,209 ****
  /* A using directive. The operand is USING_STMT_NAMESPACE. */     
  DEFTREECODE (USING_STMT, "using_directive", 'e', 1)
  
! /* An un-parsed default argument.  Looks like an IDENTIFIER_NODE.  */
  DEFTREECODE (DEFAULT_ARG, "default_arg", 'x', 0)
  
  /* A template-id, like foo<int>.  The first operand is the template.
--- 203,211 ----
  /* A using directive. The operand is USING_STMT_NAMESPACE. */     
  DEFTREECODE (USING_STMT, "using_directive", 'e', 1)
  
! /* An un-parsed default argument.
!    TREE_CHAIN is used to hold instantiations of functions that had to
!    be instantiated before the argument was parsed.  */
  DEFTREECODE (DEFAULT_ARG, "default_arg", 'x', 0)
  
  /* A template-id, like foo<int>.  The first operand is the template.
Index: cp/parser.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/parser.c,v
retrieving revision 1.157.2.56
diff -c -3 -p -r1.157.2.56 parser.c
*** cp/parser.c	8 Jun 2005 11:25:55 -0000	1.157.2.56
--- cp/parser.c	8 Jun 2005 14:49:10 -0000
*************** cp_parser_late_parsing_for_member (cp_pa
*** 14771,14779 ****
        tokens = DECL_PENDING_INLINE_INFO (member_function);
        DECL_PENDING_INLINE_INFO (member_function) = NULL;
        DECL_PENDING_INLINE_P (member_function) = 0;
!       /* If this was an inline function in a local class, enter the scope
! 	 of the containing function.  */
!       function_scope = decl_function_context (member_function);
        if (function_scope)
  	push_function_context_to (function_scope);
        
--- 14771,14780 ----
        tokens = DECL_PENDING_INLINE_INFO (member_function);
        DECL_PENDING_INLINE_INFO (member_function) = NULL;
        DECL_PENDING_INLINE_P (member_function) = 0;
!       
!       /* If this is a local class, enter the scope of the containing
! 	 function.  */
!       function_scope = current_function_decl;
        if (function_scope)
  	push_function_context_to (function_scope);
        
*************** cp_parser_late_parsing_default_args (cp_
*** 14854,14886 ****
         parameters;
         parameters = TREE_CHAIN (parameters))
      {
!       if (!TREE_PURPOSE (parameters)
! 	  || TREE_CODE (TREE_PURPOSE (parameters)) != DEFAULT_ARG)
  	continue;
    
!        /* Save away the current lexer.  */
        saved_lexer = parser->lexer;
!        /* Create a new one, using the tokens we have saved.  */
!       tokens =  DEFARG_TOKENS (TREE_PURPOSE (parameters));
        parser->lexer = cp_lexer_new_from_tokens (tokens);
  
!        /* Set the current source position to be the location of the
!      	  first token in the default argument.  */
        cp_lexer_peek_token (parser->lexer);
  
!        /* Local variable names (and the `this' keyword) may not appear
!      	  in a default argument.  */
        saved_local_variables_forbidden_p = parser->local_variables_forbidden_p;
        parser->local_variables_forbidden_p = true;
!        /* Parse the assignment-expression.  */
        if (DECL_FRIEND_CONTEXT (fn))
  	push_nested_class (DECL_FRIEND_CONTEXT (fn));
        else if (DECL_CLASS_SCOPE_P (fn))
  	push_nested_class (DECL_CONTEXT (fn));
!       TREE_PURPOSE (parameters) = cp_parser_assignment_expression (parser);
        if (DECL_FRIEND_CONTEXT (fn) || DECL_CLASS_SCOPE_P (fn))
  	pop_nested_class ();
! 
        /* If the token stream has not been completely used up, then
  	 there was extra junk after the end of the default
  	 argument.  */
--- 14855,14903 ----
         parameters;
         parameters = TREE_CHAIN (parameters))
      {
!       tree default_arg = TREE_PURPOSE (parameters);
!       tree parsed_arg;
! 
!       if (!default_arg)
! 	continue;
! 
!       if (TREE_CODE (default_arg) != DEFAULT_ARG)
! 	/* This can happen for a friend declaration for a function
! 	   already declared with default arguments.  */
  	continue;
    
!       /* Save away the current lexer.  */
        saved_lexer = parser->lexer;
!       /* Create a new one, using the tokens we have saved.  */
!       tokens =  DEFARG_TOKENS (default_arg);
        parser->lexer = cp_lexer_new_from_tokens (tokens);
  
!       /* Set the current source position to be the location of the
!          first token in the default argument.  */
        cp_lexer_peek_token (parser->lexer);
  
!       /* Local variable names (and the `this' keyword) may not appear
!      	 in a default argument.  */
        saved_local_variables_forbidden_p = parser->local_variables_forbidden_p;
        parser->local_variables_forbidden_p = true;
!       
!       /* Parse the assignment-expression.  */
        if (DECL_FRIEND_CONTEXT (fn))
  	push_nested_class (DECL_FRIEND_CONTEXT (fn));
        else if (DECL_CLASS_SCOPE_P (fn))
  	push_nested_class (DECL_CONTEXT (fn));
!       parsed_arg = cp_parser_assignment_expression (parser);
        if (DECL_FRIEND_CONTEXT (fn) || DECL_CLASS_SCOPE_P (fn))
  	pop_nested_class ();
!       
!       TREE_PURPOSE (parameters) = parsed_arg;
!       
!       /* Update any instantiations we've already created.  */
!       for (default_arg = TREE_CHAIN (default_arg);
! 	   default_arg;
! 	   default_arg = TREE_CHAIN (default_arg))
! 	TREE_PURPOSE (TREE_PURPOSE (default_arg)) = parsed_arg;
!      
        /* If the token stream has not been completely used up, then
  	 there was extra junk after the end of the default
  	 argument.  */
Index: cp/pt.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/pt.c,v
retrieving revision 1.816.2.54
diff -c -3 -p -r1.816.2.54 pt.c
*** cp/pt.c	3 Jun 2005 16:29:25 -0000	1.816.2.54
--- cp/pt.c	8 Jun 2005 14:49:17 -0000
*************** check_explicit_specialization (tree decl
*** 1779,1784 ****
--- 1779,1789 ----
  	      /* Find the namespace binding, using the declaration
                   context.  */
  	      fns = namespace_binding (dname, CP_DECL_CONTEXT (decl));
+ 	      if (!fns || !is_overloaded_fn (fns))
+ 		{
+ 		  error ("`%D' is not a template function", dname);
+ 		  fns = error_mark_node;
+ 		}
  	    }
  
  	  declarator = lookup_template_function (fns, NULL_TREE);
*************** lookup_template_function (tree fns, tree
*** 4066,4083 ****
      return error_mark_node;
  
    my_friendly_assert (!arglist || TREE_CODE (arglist) == TREE_VEC, 20030726);
!   if (fns == NULL_TREE 
!       || TREE_CODE (fns) == FUNCTION_DECL)
!     {
!       error ("non-template used as template");
!       return error_mark_node;
!     }
! 
!   my_friendly_assert (TREE_CODE (fns) == TEMPLATE_DECL
! 		      || TREE_CODE (fns) == OVERLOAD
! 		      || BASELINK_P (fns)
! 		      || TREE_CODE (fns) == IDENTIFIER_NODE,
! 		      20020730);
  
    if (BASELINK_P (fns))
      {
--- 4071,4079 ----
      return error_mark_node;
  
    my_friendly_assert (!arglist || TREE_CODE (arglist) == TREE_VEC, 20030726);
!   my_friendly_assert (fns && (is_overloaded_fn (fns)
! 			      || TREE_CODE (fns) == IDENTIFIER_NODE),
! 		      20050608);
  
    if (BASELINK_P (fns))
      {
*************** tsubst_arg_types (tree arg_types, 
*** 6484,6489 ****
--- 6480,6487 ----
  {
    tree remaining_arg_types;
    tree type;
+   tree default_arg;
+   tree result = NULL_TREE;
  
    if (!arg_types || arg_types == void_list_node)
      return arg_types;
*************** tsubst_arg_types (tree arg_types, 
*** 6511,6522 ****
       top-level qualifiers as required.  */
    type = TYPE_MAIN_VARIANT (type_decays_to (type));
  
!   /* Note that we do not substitute into default arguments here.  The
!      standard mandates that they be instantiated only when needed,
!      which is done in build_over_call.  */
!   return hash_tree_cons (TREE_PURPOSE (arg_types), type,
! 			 remaining_arg_types);
! 			 
  }
  
  /* Substitute into a FUNCTION_TYPE or METHOD_TYPE.  This routine does
--- 6509,6533 ----
       top-level qualifiers as required.  */
    type = TYPE_MAIN_VARIANT (type_decays_to (type));
  
!   /* We do not substitute into default arguments here.  The standard
!      mandates that they be instantiated only when needed, which is
!      done in build_over_call.  */
!   default_arg = TREE_PURPOSE (arg_types);
!   
!   if (default_arg && TREE_CODE (default_arg) == DEFAULT_ARG)
!     {
!       /* We've instantiated a template before its default arguments
!  	 have been parsed.  This can happen for a nested template
!  	 class, and is not an error unless we require the default
!  	 argument in a call of this function.  */
!       result = tree_cons (default_arg, type, remaining_arg_types);
!       TREE_CHAIN (default_arg) = tree_cons (result, NULL_TREE,
! 					    TREE_CHAIN (default_arg));
!     }
!   else
!     result = hash_tree_cons (default_arg, type, remaining_arg_types);
!   
!   return result;
  }
  
  /* Substitute into a FUNCTION_TYPE or METHOD_TYPE.  This routine does
Index: testsuite/g++.dg/parse/local-class1.C
===================================================================
RCS file: testsuite/g++.dg/parse/local-class1.C
diff -N testsuite/g++.dg/parse/local-class1.C
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- testsuite/g++.dg/parse/local-class1.C	8 Jun 2005 14:49:18 -0000
***************
*** 0 ****
--- 1,14 ----
+  // Copyright (C) 2005 Free Software Foundation, Inc.
+ // Contributed by Nathan Sidwell 14 Feb 2005 <nathan@codesourcery.com>
+ 
+ // Origin: Jorn Wolfgang Rennecke <amylaar@gcc.gnu.org>
+ // Bug 19608: ICE on invalid
+ 
+ 
+ void f ()
+ {
+   class c
+     {
+       friend void g () { } // { dg-error "local class definition" "" }
+     };
+ }
Index: testsuite/g++.dg/template/explicit6.C
===================================================================
RCS file: testsuite/g++.dg/template/explicit6.C
diff -N testsuite/g++.dg/template/explicit6.C
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- testsuite/g++.dg/template/explicit6.C	8 Jun 2005 14:49:18 -0000
***************
*** 0 ****
--- 1,8 ----
+ // Copyright (C) 2005 Free Software Foundation, Inc.
+ // Contributed by Nathan Sidwell 14 Feb 2005 <nathan@codesourcery.com>
+ 
+ // Origin: Volker Reichelt <reichelt@gcc.gnu.org>
+ // Bug 19895: ICE on invalid
+ 
+ struct A;
+ template A<>::A(); // { dg-error "(not a template)|(explicit qualification)" "" }
Index: testsuite/g++.old-deja/g++.oliva/template6.C
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/g++.old-deja/g++.oliva/template6.C,v
retrieving revision 1.3
diff -c -3 -p -r1.3 template6.C
*** testsuite/g++.old-deja/g++.oliva/template6.C	1 May 2003 02:02:47 -0000	1.3
--- testsuite/g++.old-deja/g++.oliva/template6.C	8 Jun 2005 14:49:20 -0000
***************
*** 6,9 ****
  // simplified from bug report by Meenaradchagan Vishnu <mvishnu@fore.com>
  
  template <typename> struct foo {};
! template <> void foo(); // { dg-error "" } bad specialization
--- 6,12 ----
  // simplified from bug report by Meenaradchagan Vishnu <mvishnu@fore.com>
  
  template <typename> struct foo {};
! template <> void foo(); // { dg-error "not a template function" } bad specialization
! 
! struct baz {};
! template <> void baz (); // { dg-error "not a template function" } bad specialization
Index: testsuite/g++.dg/parse/defarg9.C
===================================================================
RCS file: testsuite/g++.dg/parse/defarg9.C
diff -N testsuite/g++.dg/parse/defarg9.C
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- testsuite/g++.dg/parse/defarg9.C	8 Jun 2005 15:22:45 -0000
***************
*** 0 ****
--- 1,20 ----
+ // Copyright (C) 2005 Free Software Foundation, Inc.
+ // Contributed by Nathan Sidwell 6 Jun 2005 <nathan@codesourcery.com>
+ 
+ // PR 21903:Reject legal with default arg confusion
+ // Origin:  Wolfgang Bangerth <bangerth@dealii.org>
+ 
+ 
+ struct O { 
+   template<typename T> struct B { 
+     void set (T, bool=true); 
+   }; 
+   
+   struct D : public B<int> {}; 
+ }; 
+ 
+ void x () 
+ { 
+   O::D d; 
+   d.set(1); 
+ }

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