enable-checking: error_mark accessed as type

Martin v. Loewis martin@mira.isdn.cs.tu-berlin.de
Mon Mar 15 00:54:00 GMT 1999


> Yes, so long as it can't get there normally.  How about using
> void_zero_node instead?

Yes, that appears to work.

> Yep; that's what it means other places, too.  I'd rather just fix the
> places that don't currently check for TREE_TYPE == error_mark_node.

Ok. This is what the patch below does. There are still some places
left where error marks are incorrectly accessed, but the majority is
fixed with this patch.

Regards,
Martin

1999-03-15  Martin von Löwis  <loewis@informatik.hu-berlin.de>

	* parse.y (named_complex_class_head_sans_basetype): 
	Push std_node for error_mark_node.
	(maybe_base_class_list): Likewise.

	* decl.c (start_decl): Check for error_mark_node as a type.
	Detected by g++.brendan/array-refs.C.
	(start_decl_1): Likewise. Detected by g++.bugs/900322_01.C.
	(maybe_build_cleanup_1): Likewise. Detected by
	g++.jason/incomplete1.C.

	* tree.c (build_dummy_object): Build ERROR_MARK with proper type.
	(is_dummy_object): Check for such a node.
	Detected by g++.bob/inherit1.C

	* expr.c (cplus_expand_expr): Expand 0 if new is in error.
	Detected by g++.brendan/crash19.C

Index: decl.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/cp/decl.c,v
retrieving revision 1.322
diff -c -p -r1.322 decl.c
*** decl.c	1999/03/13 01:16:31	1.322
--- decl.c	1999/03/15 08:44:57
*************** start_decl (declarator, declspecs, initi
*** 6875,6880 ****
--- 6875,6881 ----
  
    /* Don't lose if destructors must be executed at file-level.  */
    if (! processing_template_decl && TREE_STATIC (decl)
+       && type != error_mark_node
        && TYPE_NEEDS_DESTRUCTOR (complete_type (type))
        && !TREE_PERMANENT (decl))
      {
*************** start_decl_1 (decl)
*** 7122,7128 ****
    /* If this type of object needs a cleanup, and control may
       jump past it, make a new binding level so that it is cleaned
       up only when it is initialized first.  */
!   if (TYPE_NEEDS_DESTRUCTOR (type)
        && current_binding_level->more_cleanups_ok == 0)
      pushlevel_temporary (1);
  
--- 7123,7130 ----
    /* If this type of object needs a cleanup, and control may
       jump past it, make a new binding level so that it is cleaned
       up only when it is initialized first.  */
!   if (type != error_mark_node
!       && TYPE_NEEDS_DESTRUCTOR (type)
        && current_binding_level->more_cleanups_ok == 0)
      pushlevel_temporary (1);
  
*************** start_decl_1 (decl)
*** 7156,7161 ****
--- 7158,7164 ----
    if (!initialized
        && TREE_CODE (decl) != TYPE_DECL
        && TREE_CODE (decl) != TEMPLATE_DECL
+       && type != error_mark_node
        && IS_AGGR_TYPE (type) && ! DECL_EXTERNAL (decl))
      {
        if ((! processing_template_decl || ! uses_template_parms (type))
*************** maybe_build_cleanup_1 (decl, auto_delete
*** 14317,14323 ****
       tree decl, auto_delete;
  {
    tree type = TREE_TYPE (decl);
!   if (TYPE_NEEDS_DESTRUCTOR (type))
      {
        int temp = 0, flags = LOOKUP_NORMAL|LOOKUP_DESTRUCTOR;
        tree rval;
--- 14320,14326 ----
       tree decl, auto_delete;
  {
    tree type = TREE_TYPE (decl);
!   if (type != error_mark_node && TYPE_NEEDS_DESTRUCTOR (type))
      {
        int temp = 0, flags = LOOKUP_NORMAL|LOOKUP_DESTRUCTOR;
        tree rval;
Index: expr.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/cp/expr.c,v
retrieving revision 1.20
diff -c -p -r1.20 expr.c
*** expr.c	1998/12/16 21:15:23	1.20
--- expr.c	1999/03/15 08:44:57
*************** cplus_expand_expr (exp, target, tmode, m
*** 217,223 ****
  	  TREE_OPERAND (exp, 1), 0), target, tmode, modifier);
  
      case NEW_EXPR:
!       return expand_expr (build_new_1 (exp), target, tmode, modifier);
  
      default:
        break;
--- 217,229 ----
  	  TREE_OPERAND (exp, 1), 0), target, tmode, modifier);
  
      case NEW_EXPR:
!       {
! 	tree new_expr = build_new_1 (exp);
! 	if (new_expr != error_mark_node)
! 	  return expand_expr (new_expr, target, tmode, modifier);
! 	else
! 	  return expand_expr (integer_zero_node, target, tmode, modifier);
!       }
  
      default:
        break;
Index: parse.y
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/cp/parse.y,v
retrieving revision 1.108
diff -c -p -r1.108 parse.y
*** parse.y	1999/03/09 23:02:38	1.108
--- parse.y	1999/03/15 08:45:10
***************
*** 1,5 ****
  /* YACC parser for C++ syntax.
!    Copyright (C) 1988, 89, 93-97, 1998 Free Software Foundation, Inc.
     Hacked by Michael Tiemann (tiemann@cygnus.com)
  
  This file is part of GNU CC.
--- 1,5 ----
  /* YACC parser for C++ syntax.
!    Copyright (C) 1988, 89, 93-98, 1999 Free Software Foundation, Inc.
     Hacked by Michael Tiemann (tiemann@cygnus.com)
  
  This file is part of GNU CC.
*************** named_class_head:
*** 2243,2269 ****
                      xref_basetypes (current_aggr, $1, $<ttype>2, $3); 
  		}
  	| named_complex_class_head_sans_basetype 
!                 { push_scope (CP_DECL_CONTEXT ($1)); }
  	  maybe_base_class_list
  		{ 
!                   pop_scope (CP_DECL_CONTEXT ($1));
! 		  $$ = TREE_TYPE ($1);
! 		  if (current_aggr == union_type_node
! 		      && TREE_CODE ($$) != UNION_TYPE)
! 		    cp_pedwarn ("`union' tag used in declaring `%#T'", $$);
! 		  else if (TREE_CODE ($$) == UNION_TYPE
! 			   && current_aggr != union_type_node)
! 		    cp_pedwarn ("non-`union' tag used in declaring `%#T'", $$);
! 		  else if (TREE_CODE ($$) == RECORD_TYPE)
! 		    /* We might be specializing a template with a different
! 		       class-key; deal.  */
! 		    CLASSTYPE_DECLARED_CLASS ($$) = (current_aggr
! 						     == class_type_node);
! 		  if ($3)
  		    {
! 		      maybe_process_partial_specialization ($$);
! 		      xref_basetypes (current_aggr, $1, $$, $3); 
  		    }
  		}
  	;
  
--- 2243,2280 ----
                      xref_basetypes (current_aggr, $1, $<ttype>2, $3); 
  		}
  	| named_complex_class_head_sans_basetype 
!                 { 
! 		  if ($1 != error_mark_node)
! 		    push_scope (CP_DECL_CONTEXT ($1)); 
! 		  else
! 		    /* We enter a scope here, but have none to push. */
! 		    push_scope (std_node);
! 		}
  	  maybe_base_class_list
  		{ 
! 		  if ($1 != error_mark_node)
  		    {
! 		      pop_scope (CP_DECL_CONTEXT ($1));
! 		      $$ = TREE_TYPE ($1);
! 		      if (current_aggr == union_type_node
! 			  && TREE_CODE ($$) != UNION_TYPE)
! 			cp_pedwarn ("`union' tag used in declaring `%#T'", $$);
! 		      else if (TREE_CODE ($$) == UNION_TYPE
! 			       && current_aggr != union_type_node)
! 			cp_pedwarn ("non-`union' tag used in declaring `%#T'", $$);
! 		      else if (TREE_CODE ($$) == RECORD_TYPE)
! 			/* We might be specializing a template with a different
! 			   class-key; deal.  */
! 			CLASSTYPE_DECLARED_CLASS ($$) = (current_aggr
! 							 == class_type_node);
! 		      if ($3)
! 			{
! 			  maybe_process_partial_specialization ($$);
! 			  xref_basetypes (current_aggr, $1, $$, $3); 
! 			}
  		    }
+ 		  else
+ 		    pop_scope (std_node);
  		}
  	;
  
Index: tree.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/cp/tree.c,v
retrieving revision 1.98
diff -c -p -r1.98 tree.c
*** tree.c	1999/03/06 17:41:36	1.98
--- tree.c	1999/03/15 08:45:13
*************** tree
*** 2700,2706 ****
  build_dummy_object (type)
       tree type;
  {
!   tree decl = build1 (NOP_EXPR, build_pointer_type (type), error_mark_node);
    return build_indirect_ref (decl, NULL_PTR);
  }
  
--- 2700,2706 ----
  build_dummy_object (type)
       tree type;
  {
!   tree decl = build1 (NOP_EXPR, build_pointer_type (type), void_zero_node);
    return build_indirect_ref (decl, NULL_PTR);
  }
  
*************** is_dummy_object (ob)
*** 2743,2749 ****
    if (TREE_CODE (ob) == INDIRECT_REF)
      ob = TREE_OPERAND (ob, 0);
    return (TREE_CODE (ob) == NOP_EXPR
! 	  && TREE_OPERAND (ob, 0) == error_mark_node);
  }
  
  /* Returns 1 iff type T is a POD type, as defined in [basic.types].  */
--- 2743,2749 ----
    if (TREE_CODE (ob) == INDIRECT_REF)
      ob = TREE_OPERAND (ob, 0);
    return (TREE_CODE (ob) == NOP_EXPR
! 	  && TREE_OPERAND (ob, 0) == void_zero_node);
  }
  
  /* Returns 1 iff type T is a POD type, as defined in [basic.types].  */




More information about the Gcc-patches mailing list