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 to attribute handling


This is pretty much a quick hack to allow attributes to apply to types in
casts and to parameter declarations; a more thorough attribute overhaul
should wait for the new parser.

Tested i686-pc-linux-gnu; test in g++.dg/ext/attrib3.C.

2002-01-31  Jason Merrill  <jason@redhat.com>

	Allow attributes in parms and casts.
	* parse.y (named_parm): Don't strip attrs.
	(declmods): Remove 'attributes' production.
	(nonempty_cv_qualifiers): Accept attributes.
	(ATTRIBUTE): Give precedence.
	* decl.c (groktypename): Handle attributes.
	(grokparms): Likewise.

*** parse.y.~1~	Thu Jan 31 16:59:01 2002
--- parse.y	Thu Jan 31 17:48:58 2002
*************** cp_parse_init ()
*** 301,307 ****
  %nonassoc IF
  %nonassoc ELSE
  
! %left IDENTIFIER PFUNCNAME TYPENAME SELFNAME PTYPENAME SCSPEC TYPESPEC CV_QUALIFIER ENUM AGGR ELLIPSIS TYPEOF SIGOF OPERATOR NSNAME TYPENAME_KEYWORD
  
  %left '{' ',' ';'
  
--- 301,307 ----
  %nonassoc IF
  %nonassoc ELSE
  
! %left IDENTIFIER PFUNCNAME TYPENAME SELFNAME PTYPENAME SCSPEC TYPESPEC CV_QUALIFIER ENUM AGGR ELLIPSIS TYPEOF SIGOF OPERATOR NSNAME TYPENAME_KEYWORD ATTRIBUTE
  
  %left '{' ',' ';'
  
*************** declmods:
*** 1938,1948 ****
  		}
  	| declmods attributes
  		{ $$.t = hash_tree_cons ($2, NULL_TREE, $1.t); }
- 	| attributes  %prec EMPTY
- 		{
- 		  $$.t = hash_tree_cons ($1, NULL_TREE, NULL_TREE);
- 		  $$.new_type_flag = 0; $$.lookups = NULL_TREE;
- 		}
  	;
  
  /* Used instead of declspecs where storage classes are not allowed
--- 1938,1943 ----
*************** nonempty_cv_qualifiers:
*** 2819,2824 ****
--- 2814,2825 ----
  	| nonempty_cv_qualifiers CV_QUALIFIER
  		{ $$.t = hash_tree_cons (NULL_TREE, $2, $1.t); 
  		  $$.new_type_flag = $1.new_type_flag; }
+ 	| attributes %prec EMPTY
+ 		{ $$.t = hash_tree_cons ($1, NULL_TREE, NULL_TREE); 
+ 		  $$.new_type_flag = 0; }
+ 	| nonempty_cv_qualifiers attributes %prec EMPTY
+ 		{ $$.t = hash_tree_cons ($2, NULL_TREE, $1.t); 
+ 		  $$.new_type_flag = $1.new_type_flag; }
  	;
  
  /* These rules must follow the rules for function declarations
*************** named_parm:
*** 3718,3726 ****
  	/* Here we expand typed_declspecs inline to avoid mis-parsing of
  	   TYPESPEC IDENTIFIER.  */
  	  typed_declspecs1 declarator
! 		{ tree specs = strip_attrs ($1.t);
! 		  $$.new_type_flag = $1.new_type_flag;
! 		  $$.t = build_tree_list (specs, $2); }
  	| typed_typespecs declarator
  		{ $$.t = build_tree_list ($1.t, $2); 
  		  $$.new_type_flag = $1.new_type_flag; }
--- 3719,3726 ----
  	/* Here we expand typed_declspecs inline to avoid mis-parsing of
  	   TYPESPEC IDENTIFIER.  */
  	  typed_declspecs1 declarator
! 		{ $$.new_type_flag = $1.new_type_flag;
! 		  $$.t = build_tree_list ($1.t, $2); }
  	| typed_typespecs declarator
  		{ $$.t = build_tree_list ($1.t, $2); 
  		  $$.new_type_flag = $1.new_type_flag; }
*************** named_parm:
*** 3729,3744 ****
  					  $2); 
  		  $$.new_type_flag = $1.new_type_flag; }
  	| typed_declspecs1 absdcl
! 		{ tree specs = strip_attrs ($1.t);
! 		  $$.t = build_tree_list (specs, $2);
  		  $$.new_type_flag = $1.new_type_flag; }
  	| typed_declspecs1  %prec EMPTY
! 		{ tree specs = strip_attrs ($1.t);
! 		  $$.t = build_tree_list (specs, NULL_TREE); 
  		  $$.new_type_flag = $1.new_type_flag; }
  	| declmods notype_declarator
! 		{ tree specs = strip_attrs ($1.t);
! 		  $$.t = build_tree_list (specs, $2); 
  		  $$.new_type_flag = 0; }
  	;
  
--- 3729,3741 ----
  					  $2); 
  		  $$.new_type_flag = $1.new_type_flag; }
  	| typed_declspecs1 absdcl
! 		{ $$.t = build_tree_list ($1.t, $2);
  		  $$.new_type_flag = $1.new_type_flag; }
  	| typed_declspecs1  %prec EMPTY
! 		{ $$.t = build_tree_list ($1.t, NULL_TREE); 
  		  $$.new_type_flag = $1.new_type_flag; }
  	| declmods notype_declarator
! 		{ $$.t = build_tree_list ($1.t, $2); 
  		  $$.new_type_flag = 0; }
  	;
  
*** decl.c.~1~	Thu Jan 31 16:59:01 2002
--- decl.c	Thu Jan 31 18:51:32 2002
*************** tree
*** 7127,7137 ****
  groktypename (typename)
       tree typename;
  {
    if (TREE_CODE (typename) != TREE_LIST)
      return typename;
!   return grokdeclarator (TREE_VALUE (typename),
! 			 TREE_PURPOSE (typename),
! 			 TYPENAME, 0, NULL);
  }
  
  /* Decode a declarator in an ordinary declaration or data definition.
--- 7127,7142 ----
  groktypename (typename)
       tree typename;
  {
+   tree specs, attrs;
+   tree type;
    if (TREE_CODE (typename) != TREE_LIST)
      return typename;
!   split_specs_attrs (TREE_PURPOSE (typename), &specs, &attrs);
!   type = grokdeclarator (TREE_VALUE (typename), specs,
! 			 TYPENAME, 0, &attrs);
!   if (attrs)
!     cplus_decl_attributes (&type, attrs, 0);
!   return type;
  }
  
  /* Decode a declarator in an ordinary declaration or data definition.
*************** grokparms (first_parm)
*** 11997,12004 ****
    for (parm = first_parm; parm != NULL_TREE; parm = chain)
      {
        tree type = NULL_TREE;
!       register tree decl = TREE_VALUE (parm);
        tree init = TREE_PURPOSE (parm);
  
        chain = TREE_CHAIN (parm);
        /* @@ weak defense against parse errors.  */
--- 12002,12010 ----
    for (parm = first_parm; parm != NULL_TREE; parm = chain)
      {
        tree type = NULL_TREE;
!       tree decl = TREE_VALUE (parm);
        tree init = TREE_PURPOSE (parm);
+       tree specs, attrs;
  
        chain = TREE_CHAIN (parm);
        /* @@ weak defense against parse errors.  */
*************** grokparms (first_parm)
*** 12016,12026 ****
        if (parm == void_list_node)
          break;
  
!       decl = grokdeclarator (TREE_VALUE (decl), TREE_PURPOSE (decl),
! 		     PARM, init != NULL_TREE, NULL);
        if (! decl || TREE_TYPE (decl) == error_mark_node)
          continue;
  
        type = TREE_TYPE (decl);
        if (VOID_TYPE_P (type))
          {
--- 12022,12036 ----
        if (parm == void_list_node)
          break;
  
!       split_specs_attrs (TREE_PURPOSE (decl), &specs, &attrs);
!       decl = grokdeclarator (TREE_VALUE (decl), specs,
! 			     PARM, init != NULL_TREE, &attrs);
        if (! decl || TREE_TYPE (decl) == error_mark_node)
          continue;
  
+       if (attrs)
+ 	cplus_decl_attributes (&decl, attrs, 0);
+ 
        type = TREE_TYPE (decl);
        if (VOID_TYPE_P (type))
          {

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