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

📄 objc-act.c

📁 gcc的组件
💻 C
📖 第 1 页 / 共 5 页
字号:
  tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);  tree fields = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);  tree field = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);  TREE_CHAIN (field) = fields; fields = field;  field = build_decl (FIELD_DECL, NULL_TREE, unsigned_type_node);  TREE_CHAIN (field) = fields; fields = field;  /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in     reverse order!  */  finish_builtin_struct (type, "__builtin_ObjCString",			 fields, NULL_TREE);  return type;}/* Custom build_string which sets TREE_TYPE!  */static treemy_build_string (int len, const char *str){  return fix_string_type (build_string (len, str));}/* Build a string with contents STR and length LEN and convert it to a   pointer.  */static treemy_build_string_pointer (int len, const char *str){  tree string = my_build_string (len, str);  tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));  return build1 (ADDR_EXPR, ptrtype, string);}static hashval_tstring_hash (const void *ptr){  tree str = ((struct string_descriptor *)ptr)->literal;  const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);  int i, len = TREE_STRING_LENGTH (str);  hashval_t h = len;  for (i = 0; i < len; i++)    h = ((h * 613) + p[i]);  return h;}static intstring_eq (const void *ptr1, const void *ptr2){  tree str1 = ((struct string_descriptor *)ptr1)->literal;  tree str2 = ((struct string_descriptor *)ptr2)->literal;  int len1 = TREE_STRING_LENGTH (str1);  return (len1 == TREE_STRING_LENGTH (str2)	  && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),		      len1));}/* Given a chain of STRING_CST's, build a static instance of   NXConstantString which points at the concatenation of those   strings.  We place the string object in the __string_objects   section of the __OBJC segment.  The Objective-C runtime will   initialize the isa pointers of the string objects to point at the   NXConstantString class object.  */treeobjc_build_string_object (tree string){  tree initlist, constructor, constant_string_class;  int length;  tree fields, addr;  struct string_descriptor *desc, key;  void **loc;  /* Prep the string argument.  */  string = fix_string_type (string);  TREE_SET_CODE (string, STRING_CST);  length = TREE_STRING_LENGTH (string) - 1;  /* Check whether the string class being used actually exists and has the     correct ivar layout.  */  if (!string_layout_checked)    {      string_layout_checked = -1;      constant_string_class = lookup_interface (constant_string_id);      internal_const_str_type = objc_build_internal_const_str_type ();      if (!constant_string_class	  || !(constant_string_type	       = CLASS_STATIC_TEMPLATE (constant_string_class)))	error ("cannot find interface declaration for %qs",	       IDENTIFIER_POINTER (constant_string_id));      /* The NSConstantString/NXConstantString ivar layout is now known.  */      else if (!check_string_class_template ())	error ("interface %qs does not have valid constant string layout",	       IDENTIFIER_POINTER (constant_string_id));      /* For the NeXT runtime, we can generate a literal reference	 to the string class, don't need to run a constructor.  */      else if (flag_next_runtime && !setup_string_decl ())	error ("cannot find reference tag for class %qs",	       IDENTIFIER_POINTER (constant_string_id));      else	{	  string_layout_checked = 1;  /* Success!  */	  add_class_reference (constant_string_id);	}    }  if (string_layout_checked == -1)    return error_mark_node;  /* Perhaps we already constructed a constant string just like this one? */  key.literal = string;  loc = htab_find_slot (string_htab, &key, INSERT);  desc = *loc;  if (!desc)    {      tree var;      *loc = desc = ggc_alloc (sizeof (*desc));      desc->literal = string;      /* GNU:    (NXConstantString *) & ((__builtin_ObjCString) { NULL, string, length })  */      /* NeXT:   (NSConstantString *) & ((__builtin_ObjCString) { isa, string, length })   */      fields = TYPE_FIELDS (internal_const_str_type);      initlist	= build_tree_list (fields,			   flag_next_runtime			   ? build_unary_op (ADDR_EXPR, string_class_decl, 0)			   : build_int_cst (NULL_TREE, 0));      fields = TREE_CHAIN (fields);      initlist = tree_cons (fields, build_unary_op (ADDR_EXPR, string, 1),			    initlist);      fields = TREE_CHAIN (fields);      initlist = tree_cons (fields, build_int_cst (NULL_TREE, length), 			    initlist);      constructor = objc_build_constructor (internal_const_str_type,					    nreverse (initlist));      TREE_INVARIANT (constructor) = true;      if (!flag_next_runtime)	constructor	  = objc_add_static_instance (constructor, constant_string_type);      else        {	  var = build_decl (CONST_DECL, NULL, TREE_TYPE (constructor));	  DECL_INITIAL (var) = constructor;	  TREE_STATIC (var) = 1;	  pushdecl_top_level (var);	  constructor = var;	}      desc->constructor = constructor;    }  addr = convert (build_pointer_type (constant_string_type),		  build_unary_op (ADDR_EXPR, desc->constructor, 1));  return addr;}/* Declare a static instance of CLASS_DECL initialized by CONSTRUCTOR.  */static GTY(()) int num_static_inst;static treeobjc_add_static_instance (tree constructor, tree class_decl){  tree *chain, decl;  char buf[256];  /* Find the list of static instances for the CLASS_DECL.  Create one if     not found.  */  for (chain = &objc_static_instances;       *chain && TREE_VALUE (*chain) != class_decl;       chain = &TREE_CHAIN (*chain));  if (!*chain)    {      *chain = tree_cons (NULL_TREE, class_decl, NULL_TREE);      add_objc_string (OBJC_TYPE_NAME (class_decl), class_names);    }  sprintf (buf, "_OBJC_INSTANCE_%d", num_static_inst++);  decl = build_decl (VAR_DECL, get_identifier (buf), class_decl);  DECL_COMMON (decl) = 1;  TREE_STATIC (decl) = 1;  DECL_ARTIFICIAL (decl) = 1;  DECL_INITIAL (decl) = constructor;  /* We may be writing something else just now.     Postpone till end of input.  */  DECL_DEFER_OUTPUT (decl) = 1;  pushdecl_top_level (decl);  rest_of_decl_compilation (decl, 1, 0);  /* Add the DECL to the head of this CLASS' list.  */  TREE_PURPOSE (*chain) = tree_cons (NULL_TREE, decl, TREE_PURPOSE (*chain));  return decl;}/* Build a static constant CONSTRUCTOR   with type TYPE and elements ELTS.  */static treeobjc_build_constructor (tree type, tree elts){  tree constructor = build_constructor_from_list (type, elts);  TREE_CONSTANT (constructor) = 1;  TREE_STATIC (constructor) = 1;  TREE_READONLY (constructor) = 1;#ifdef OBJCPLUS  /* Adjust for impedance mismatch.  We should figure out how to build     CONSTRUCTORs that consistently please both the C and C++ gods.  */  if (!TREE_PURPOSE (elts))    TREE_TYPE (constructor) = NULL_TREE;  TREE_HAS_CONSTRUCTOR (constructor) = 1;#endif  return constructor;}/* Take care of defining and initializing _OBJC_SYMBOLS.  *//* Predefine the following data type:   struct _objc_symtab   {     long sel_ref_cnt;     SEL *refs;     short cls_def_cnt;     short cat_def_cnt;     void *defs[cls_def_cnt + cat_def_cnt];   }; */static voidbuild_objc_symtab_template (void){  tree field_decl, field_decl_chain;  objc_symtab_template    = start_struct (RECORD_TYPE, get_identifier (UTAG_SYMTAB));  /* long sel_ref_cnt; */  field_decl = create_field_decl (long_integer_type_node, "sel_ref_cnt");  field_decl_chain = field_decl;  /* SEL *refs; */  field_decl = create_field_decl (build_pointer_type (objc_selector_type),				  "refs");  chainon (field_decl_chain, field_decl);  /* short cls_def_cnt; */  field_decl = create_field_decl (short_integer_type_node, "cls_def_cnt");  chainon (field_decl_chain, field_decl);  /* short cat_def_cnt; */  field_decl = create_field_decl (short_integer_type_node,				  "cat_def_cnt");  chainon (field_decl_chain, field_decl);  if (imp_count || cat_count || !flag_next_runtime)    {      /* void *defs[imp_count + cat_count (+ 1)]; */      /* NB: The index is one less than the size of the array.  */      int index = imp_count + cat_count		+ (flag_next_runtime? -1: 0);      field_decl = create_field_decl		   (build_array_type		    (ptr_type_node,		     build_index_type (build_int_cst (NULL_TREE, index))),		    "defs");      chainon (field_decl_chain, field_decl);    }  finish_struct (objc_symtab_template, field_decl_chain, NULL_TREE);}/* Create the initial value for the `defs' field of _objc_symtab.   This is a CONSTRUCTOR.  */static treeinit_def_list (tree type){  tree expr, initlist = NULL_TREE;  struct imp_entry *impent;  if (imp_count)    for (impent = imp_list; impent; impent = impent->next)      {	if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)	  {	    expr = build_unary_op (ADDR_EXPR, impent->class_decl, 0);	    initlist = tree_cons (NULL_TREE, expr, initlist);	  }      }  if (cat_count)    for (impent = imp_list; impent; impent = impent->next)      {	if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)	  {	    expr = build_unary_op (ADDR_EXPR, impent->class_decl, 0);	    initlist = tree_cons (NULL_TREE, expr, initlist);	  }      }  if (!flag_next_runtime)    {      /* statics = { ..., _OBJC_STATIC_INSTANCES, ... }  */      tree expr;      if (static_instances_decl)	expr = build_unary_op (ADDR_EXPR, static_instances_decl, 0);      else	expr = build_int_cst (NULL_TREE, 0);      initlist = tree_cons (NULL_TREE, expr, initlist);    }  return objc_build_constructor (type, nreverse (initlist));}/* Construct the initial value for all of _objc_symtab.  */static treeinit_objc_symtab (tree type){  tree initlist;  /* sel_ref_cnt = { ..., 5, ... } */  initlist = build_tree_list (NULL_TREE,			      build_int_cst (long_integer_type_node, 0));  /* refs = { ..., _OBJC_SELECTOR_TABLE, ... } */  if (flag_next_runtime || ! sel_ref_chain)    initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);  else    initlist      = tree_cons (NULL_TREE,		   convert (build_pointer_type (objc_selector_type),			    build_unary_op (ADDR_EXPR,					    UOBJC_SELECTOR_TABLE_decl, 1)),		   initlist);  /* cls_def_cnt = { ..., 5, ... } */  initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, imp_count), initlist);  /* cat_def_cnt = { ..., 5, ... } */  initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, cat_count), initlist);  /* cls_def = { ..., { &Foo, &Bar, ...}, ... } */  if (imp_count || cat_count || !flag_next_runtime)    {      tree field = TYPE_FIELDS (type);      field = TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (field))));      initlist = tree_cons (NULL_TREE, init_def_list (TREE_TYPE (field)),			    initlist);    }  return objc_build_constructor (type, nreverse (initlist));}/* Generate forward declarations for metadata such as  'OBJC_CLASS_...'.  */static treebuild_metadata_decl (const char *name, tree type){  tree decl;  /* struct TYPE NAME_<name>; */  decl = start_var_decl (type, synth_id_with_class_suffix			       (name,				objc_implementation_context));  return decl;}/* Push forward-declarations of all the categories so that   init_def_list can use them in a CONSTRUCTOR.  */static voidforward_declare_categories (void){  struct imp_entry *impent;  tree sav = objc_implementation_context;  for (impent = imp_list; impent; impent = impent->next)    {      if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)	{	  /* Set an invisible arg to synth_id_with_class_suffix.  */	  objc_implementation_context = impent->imp_context;	  /* extern struct objc_category _OBJC_CATEGORY_<name>; */	  impent->class_decl = build_metadata_decl ("_OBJC_CATEGORY",						    objc_category_template);	}    }  objc_implementation_context = sav;}/* Create the declaration of _OBJC_SYMBOLS, with type `struct _objc_symtab'   and initialized appropriately.  */static voidgenerate_objc_symtab_decl (void){  /* forward declare categories */  if (cat_count)    forward_declare_categories ();  build_objc_symtab_template ();  UOBJC_SYMBOLS_decl = start_var_decl (objc_symtab_template, "_OBJC_SYMBOLS");  finish_var_decl (UOBJC_SYMBOLS_decl,		   init_objc_symtab (TREE_TYPE (UOBJC_SYMBOLS_decl)));}static treeinit_module_descriptor (tree type){  tree initlist, expr;  /* version = { 1, ... } */  expr = build_int_cst (long_integer_type_node, OBJC_VERSION);  initlist = build_tree_list (NULL_TREE, expr);  /* size = { ..., sizeof (struct _objc_module), ... } */  expr = convert (long_integer_type_node,		  size_in_bytes (objc_module_template));  initlist = tree_cons (NULL_TREE, expr, initlist);  /* name = { ..., "foo.m", ... } */  expr = add_objc_string (get_identifier (input_filename), class_names);  initlist = tree_cons (NULL_TREE, expr, initlist);  /* symtab = { ..., _OBJC_SYMBOLS, ... } */  if (UOBJC_SYMBOLS_decl)    expr = build_unary_op (ADDR_EXPR, UOBJC_SYMBOLS_dec

⌨️ 快捷键说明

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