⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cp-method.c

📁 早期freebsd实现
💻 C
📖 第 1 页 / 共 5 页
字号:
/* Handle the hair of processing (but not expanding) inline functions.   Also manage function and variable name overloading.   Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.   Contributed by Michael Tiemann (tiemann@cygnus.com)   This file is part of GNU CC.   GNU CC is free software; you can redistribute it and/or modifyit under the terms of the GNU General Public License as published bythe Free Software Foundation; either version 2, or (at your option)any later version.GNU CC is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty ofMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See theGNU General Public License for more details.You should have received a copy of the GNU General Public Licensealong with GNU CC; see the file COPYING.  If not, write tothe Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */#ifndef PARM_CAN_BE_ARRAY_TYPE#define PARM_CAN_BE_ARRAY_TYPE 1#endif/* Handle method declarations.  */#include <stdio.h>#include "config.h"#include "tree.h"#include "cp-tree.h"#include "cp-class.h"#include "obstack.h"#define obstack_chunk_alloc xmalloc#define obstack_chunk_free free/* TREE_LIST of the current inline functions that need to be   processed.  */struct pending_inline *pending_inlines;/* Obstack where we build text strings for overloading, etc.  */static struct obstack scratch_obstack;static char *scratch_firstobj;# define OB_INIT() (scratch_firstobj ? (obstack_free (&scratch_obstack, scratch_firstobj), 0) : 0)# define OB_PUTC(C) (obstack_1grow (&scratch_obstack, (C)))# define OB_PUTC2(C1,C2)	\  (obstack_1grow (&scratch_obstack, (C1)), obstack_1grow (&scratch_obstack, (C2)))# define OB_PUTS(S) (obstack_grow (&scratch_obstack, (S), sizeof (S) - 1))# define OB_PUTID(ID)  \  (obstack_grow (&scratch_obstack, IDENTIFIER_POINTER (ID),	\		 IDENTIFIER_LENGTH (ID)))# define OB_PUTCP(S) (obstack_grow (&scratch_obstack, (S), strlen (S)))# define OB_FINISH() (obstack_1grow (&scratch_obstack, '\0'))/* Counter to help build parameter names in case they were omitted.  */static int dummy_name;static int in_parmlist;/* This points to a safe place to resume processing in case an expression   generates an error while we're trying to format it.  */static int scratch_error_offset;static void dump_type (), dump_decl ();static void dump_init (), dump_unary_op (), dump_binary_op ();#ifdef NO_AUTO_OVERLOADint is_overloaded ();#endifvoidinit_method (){  gcc_obstack_init (&scratch_obstack);  scratch_firstobj = (char *)obstack_alloc (&scratch_obstack, 0);}treemake_anon_parm_name (){  char buf[32];  sprintf (buf, ANON_PARMNAME_FORMAT, dummy_name++);  return get_identifier (buf);}voidclear_anon_parm_name (){  /* recycle these names.  */  dummy_name = 0;}static voiddump_readonly_or_volatile (t)     tree t;{  if (TYPE_READONLY (t))    OB_PUTS ("const ");  if (TYPE_VOLATILE (t))    OB_PUTS ("volatile ");}static voiddump_aggr_type (t)     tree t;{  tree name;  char *aggr_string;  char *context_string = 0;  if (TYPE_READONLY (t))    OB_PUTS ("const ");  if (TYPE_VOLATILE (t))    OB_PUTS ("volatile ");  if (TREE_CODE (t) == ENUMERAL_TYPE)    aggr_string = "enum";  else if (TREE_CODE (t) == UNION_TYPE)    aggr_string = "union";  else if (TYPE_LANG_SPECIFIC (t) && CLASSTYPE_DECLARED_CLASS (t))    aggr_string = "class";  else    aggr_string = "struct";  name = TYPE_NAME (t);  if (TREE_CODE (name) == TYPE_DECL)    {#if 0 /* not yet, should get fixed properly later */      if (DECL_CONTEXT (name))	context_string = TYPE_NAME_STRING (DECL_CONTEXT (name));#else      if (DECL_LANG_SPECIFIC (name) && DECL_CLASS_CONTEXT (name))	context_string = TYPE_NAME_STRING (DECL_CLASS_CONTEXT (name));#endif      name = DECL_NAME (name);    }  obstack_grow (&scratch_obstack, aggr_string, strlen (aggr_string));  OB_PUTC (' ');  if (context_string)    {      obstack_grow (&scratch_obstack, context_string, strlen (context_string));      OB_PUTC2 (':', ':');    }  OB_PUTID (name);}/* This must be large enough to hold any anonymous parm name.  */static char anon_buffer[sizeof (ANON_PARMNAME_FORMAT) + 20];/* This must be large enough to hold any printed integer or floatingpoint value.  */static char digit_buffer[128];static voiddump_type_prefix (t, p)     tree t;     int *p;{  int old_p = 0;  if (t == NULL_TREE)    return;  switch (TREE_CODE (t))    {    case ERROR_MARK:      sprintf (anon_buffer, ANON_PARMNAME_FORMAT, dummy_name++);      OB_PUTCP (anon_buffer);      break;    case UNKNOWN_TYPE:      OB_PUTS ("<unknown type>");      return;    case TREE_LIST:      dump_type (TREE_VALUE (t), &old_p);      if (TREE_CHAIN (t))	{	  if (TREE_CHAIN (t) != void_list_node)	    {	      OB_PUTC (',');	      dump_type (TREE_CHAIN (t), &old_p);	    }	}      else OB_PUTS ("...");      return;    case POINTER_TYPE:      *p += 1;      dump_type_prefix (TREE_TYPE (t), p);      while (*p)	{	  OB_PUTC ('*');	  *p -= 1;	}      if (TYPE_READONLY (t))	OB_PUTS ("const ");      if (TYPE_VOLATILE (t))	OB_PUTS ("volatile ");      return;    case OFFSET_TYPE:      {	tree type = TREE_TYPE (t);	if (TREE_CODE (type) == FUNCTION_TYPE)	  {	    type = TREE_TYPE (type);	    if (in_parmlist)	      OB_PUTS ("auto ");	  }	dump_type_prefix (type, &old_p);	OB_PUTC ('(');	dump_type (TYPE_OFFSET_BASETYPE (t), &old_p);	OB_PUTC2 (':', ':');	while (*p)	  {	    OB_PUTC ('*');	    *p -= 1;	  }	if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	  dump_readonly_or_volatile (t);	return;      }    case METHOD_TYPE:      {	tree type = TREE_TYPE (t);	if (in_parmlist)	  OB_PUTS ("auto ");	dump_type_prefix (type, &old_p);	OB_PUTC ('(');	dump_type (TYPE_METHOD_BASETYPE (t), &old_p);	OB_PUTC2 (':', ':');	while (*p)	  {	    OB_PUTC ('*');	    *p -= 1;	  }	if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	  dump_readonly_or_volatile (t);	return;      }    case REFERENCE_TYPE:      dump_type_prefix (TREE_TYPE (t), p);      OB_PUTC ('&');      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      return;    case ARRAY_TYPE:      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      dump_type_prefix (TREE_TYPE (t), p);      return;    case FUNCTION_TYPE:      if (in_parmlist)	OB_PUTS ("auto ");      dump_type_prefix (TREE_TYPE (t), &old_p);      OB_PUTC ('(');      while (*p)	{	  OB_PUTC ('*');	  *p -= 1;	}      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      return;    case IDENTIFIER_NODE:      OB_PUTID (t);      OB_PUTC (' ');      break;    case RECORD_TYPE:    case UNION_TYPE:    case ENUMERAL_TYPE:      dump_aggr_type (t);      break;    case TYPE_DECL:      if (TYPE_READONLY (t))	OB_PUTS ("const ");      if (TYPE_VOLATILE (t))	OB_PUTS ("volatile ");      OB_PUTID (DECL_NAME (t));      OB_PUTC (' ');      break;    case INTEGER_TYPE:#if 0      /* Normally, `unsigned' is part of the deal.  Not so if it comes	 with `const' or `volatile'.  */      if (TYPE_MAIN_VARIANT (t) == unsigned_type (TYPE_MAIN_VARIANT (t))	  && (TYPE_READONLY (t) || TYPE_VOLATILE (t)))	OB_PUTS ("unsigned ");#endif      /* fall through.  */    case REAL_TYPE:    case VOID_TYPE:      if (TYPE_READONLY (t))	OB_PUTS ("const ");      if (TYPE_VOLATILE (t))	OB_PUTS ("volatile ");      OB_PUTID (TYPE_IDENTIFIER (t));      OB_PUTC (' ');      break;    default:      my_friendly_abort (65);    }}static voiddump_type_suffix (t, p)     tree t;     int *p;{  int old_p = 0;  if (t == NULL_TREE)    return;  switch (TREE_CODE (t))    {    case ERROR_MARK:      sprintf (anon_buffer, ANON_PARMNAME_FORMAT, dummy_name++);      OB_PUTCP (anon_buffer);      break;    case UNKNOWN_TYPE:      return;    case POINTER_TYPE:      dump_type_suffix (TREE_TYPE (t), p);      return;    case OFFSET_TYPE:      {	tree type = TREE_TYPE (t);	OB_PUTC (')');	if (TREE_CODE (type) == FUNCTION_TYPE)	  {#if 0	    tree next_arg = TREE_CHAIN (TYPE_ARG_TYPES (type));	    OB_PUTC ('(');	    if (next_arg)	      {		if (next_arg != void_list_node)		  {		    in_parmlist++;		    dump_type (next_arg, &old_p);		    in_parmlist--;		  }	      }	    else OB_PUTS ("...");	    OB_PUTC (')');	    dump_type_suffix (TREE_TYPE (type), p);#else	    my_friendly_abort (66);#endif	  }	return;      }    case METHOD_TYPE:      {	tree next_arg;	OB_PUTC (')');	next_arg = TREE_CHAIN (TYPE_ARG_TYPES (t));	OB_PUTC ('(');	if (next_arg)	  {	    if (next_arg != void_list_node)	      {		in_parmlist++;		dump_type (next_arg, &old_p);		in_parmlist--;	      }	  }	else OB_PUTS ("...");	OB_PUTC (')');	dump_readonly_or_volatile (TREE_TYPE (TREE_VALUE (TYPE_ARG_TYPES (t))));	dump_type_suffix (TREE_TYPE (t), p);	return;      }    case REFERENCE_TYPE:      dump_type_suffix (TREE_TYPE (t), p);      return;    case ARRAY_TYPE:      dump_type_suffix (TREE_TYPE (t), p);      OB_PUTC2 ('[', ']');      return;    case FUNCTION_TYPE:      OB_PUTC2 (')', '(');      if (TYPE_ARG_TYPES (t) && TYPE_ARG_TYPES (t) != void_list_node)	{	  in_parmlist++;	  dump_type (TYPE_ARG_TYPES (t), &old_p);	  in_parmlist--;	}      OB_PUTC (')');      dump_type_suffix (TREE_TYPE (t), p);      return;    case IDENTIFIER_NODE:    case RECORD_TYPE:    case UNION_TYPE:    case ENUMERAL_TYPE:    case TYPE_DECL:    case INTEGER_TYPE:    case REAL_TYPE:    case VOID_TYPE:      return;    default:      my_friendly_abort (67);    }}static voiddump_type (t, p)     tree t;     int *p;{  int old_p = 0;  if (t == NULL_TREE)    return;  switch (TREE_CODE (t))    {    case ERROR_MARK:      sprintf (anon_buffer, ANON_PARMNAME_FORMAT, dummy_name++);      OB_PUTCP (anon_buffer);      break;    case UNKNOWN_TYPE:      OB_PUTS ("<unknown type>");      return;    case TREE_LIST:      dump_type (TREE_VALUE (t), &old_p);      if (TREE_CHAIN (t))	{	  if (TREE_CHAIN (t) != void_list_node)	    {	      OB_PUTC (',');	      dump_type (TREE_CHAIN (t), &old_p);	    }	}      else OB_PUTS ("...");      return;    case POINTER_TYPE:      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      *p += 1;      dump_type (TREE_TYPE (t), p);      while (*p)	{	  OB_PUTC ('*');	  *p -= 1;	}      return;    case REFERENCE_TYPE:      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      dump_type (TREE_TYPE (t), p);      OB_PUTC ('&');      return;    case ARRAY_TYPE:      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      dump_type (TREE_TYPE (t), p);      OB_PUTC2 ('[', ']');      return;    case OFFSET_TYPE:    case METHOD_TYPE:    case FUNCTION_TYPE:      dump_type_prefix (t, p);      dump_type_suffix (t, p);      return;    case IDENTIFIER_NODE:      OB_PUTID (t);      OB_PUTC (' ');      break;    case RECORD_TYPE:    case UNION_TYPE:    case ENUMERAL_TYPE:      dump_aggr_type (t);      break;    case TYPE_DECL:      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);      OB_PUTID (DECL_NAME (t));      OB_PUTC (' ');      break;    case INTEGER_TYPE:      /* Normally, `unsigned' is part of the deal.  Not so if it comes	 with `const' or `volatile'.  */      if (TYPE_READONLY (t) | TYPE_VOLATILE (t))	dump_readonly_or_volatile (t);#if 0      if (TYPE_MAIN_VARIANT (t) == unsigned_type (TYPE_MAIN_VARIANT (t))	  && (TYPE_READONLY (t) | TYPE_VOLATILE (t)))	OB_PUTS ("unsigned ");#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -