1 /* Implement classes and message passing for Objective C.
2 Copyright (C) 1992, 1993, 1994, 1995, 1997, 1998, 1999, 2000, 2001,
3 2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010
4 Free Software Foundation, Inc.
5 Contributed by Steve Naroff.
7 This file is part of GCC.
9 GCC is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3, or (at your option)
14 GCC is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3. If not see
21 <http://www.gnu.org/licenses/>. */
25 #include "coretypes.h"
36 #include "c-family/c-common.h"
37 #include "c-family/c-pragma.h"
39 #include "langhooks.h"
48 #include "diagnostic-core.h"
51 #include "tree-iterator.h"
53 #include "langhooks-def.h"
55 /* For enum gimplify_status */
58 #define OBJC_VOID_AT_END void_list_node
60 static unsigned int should_call_super_dealloc = 0;
62 /* When building Objective-C++, we need in_late_binary_op. */
64 bool in_late_binary_op = false;
67 /* When building Objective-C++, we are not linking against the C front-end
68 and so need to replicate the C tree-construction functions in some way. */
70 #define OBJCP_REMAP_FUNCTIONS
71 #include "objcp-decl.h"
74 /* This is the default way of generating a method name. */
75 /* I am not sure it is really correct.
76 Perhaps there's a danger that it will make name conflicts
77 if method names contain underscores. -- rms. */
78 #ifndef OBJC_GEN_METHOD_LABEL
79 #define OBJC_GEN_METHOD_LABEL(BUF, IS_INST, CLASS_NAME, CAT_NAME, SEL_NAME, NUM) \
82 sprintf ((BUF), "_%s_%s_%s_%s", \
83 ((IS_INST) ? "i" : "c"), \
85 ((CAT_NAME)? (CAT_NAME) : ""), \
87 for (temp = (BUF); *temp; temp++) \
88 if (*temp == ':') *temp = '_'; \
92 /* These need specifying. */
93 #ifndef OBJC_FORWARDING_STACK_OFFSET
94 #define OBJC_FORWARDING_STACK_OFFSET 0
97 #ifndef OBJC_FORWARDING_MIN_OFFSET
98 #define OBJC_FORWARDING_MIN_OFFSET 0
101 /* Set up for use of obstacks. */
105 /* This obstack is used to accumulate the encoding of a data type. */
106 static struct obstack util_obstack;
108 /* This points to the beginning of obstack contents, so we can free
109 the whole contents. */
112 /* The version identifies which language generation and runtime
113 the module (file) was compiled for, and is recorded in the
114 module descriptor. */
116 #define OBJC_VERSION (flag_next_runtime ? 6 : 8)
117 #define PROTOCOL_VERSION 2
119 /* (Decide if these can ever be validly changed.) */
120 #define OBJC_ENCODE_INLINE_DEFS 0
121 #define OBJC_ENCODE_DONT_INLINE_DEFS 1
123 /*** Private Interface (procedures) ***/
125 /* Used by compile_file. */
127 static void init_objc (void);
128 static void finish_objc (void);
130 /* Code generation. */
132 static tree objc_build_constructor (tree, VEC(constructor_elt,gc) *);
133 static tree build_objc_method_call (location_t, int, tree, tree, tree, tree);
134 static tree get_proto_encoding (tree);
135 static tree lookup_interface (tree);
136 static tree objc_add_static_instance (tree, tree);
138 static tree start_class (enum tree_code, tree, tree, tree);
139 static tree continue_class (tree);
140 static void finish_class (tree);
141 static void start_method_def (tree);
143 static void objc_start_function (tree, tree, tree, tree);
145 static void objc_start_function (tree, tree, tree, struct c_arg_info *);
147 static tree start_protocol (enum tree_code, tree, tree);
148 static tree build_method_decl (enum tree_code, tree, tree, tree, bool);
149 static tree objc_add_method (tree, tree, int, bool);
150 static tree add_instance_variable (tree, int, tree);
151 static tree build_ivar_reference (tree);
152 static tree is_ivar (tree, tree);
154 static void build_objc_exception_stuff (void);
155 static void build_next_objc_exception_stuff (void);
157 /* We only need the following for ObjC; ObjC++ will use C++'s definition
158 of DERIVED_FROM_P. */
160 static bool objc_derived_from_p (tree, tree);
161 #define DERIVED_FROM_P(PARENT, CHILD) objc_derived_from_p (PARENT, CHILD)
163 static void objc_xref_basetypes (tree, tree);
165 static void build_class_template (void);
166 static void build_selector_template (void);
167 static void build_category_template (void);
168 static void build_super_template (void);
169 static tree build_protocol_initializer (tree, tree, tree, tree, tree);
170 static tree get_class_ivars (tree, bool);
171 static tree generate_protocol_list (tree);
172 static void build_protocol_reference (tree);
174 static void build_fast_enumeration_state_template (void);
177 static void objc_generate_cxx_cdtors (void);
180 static const char *synth_id_with_class_suffix (const char *, tree);
182 /* Hash tables to manage the global pool of method prototypes. */
184 hash *nst_method_hash_list = 0;
185 hash *cls_method_hash_list = 0;
187 static hash hash_lookup (hash *, tree);
188 static tree lookup_method (tree, tree);
189 static tree lookup_method_static (tree, tree, int);
193 class_names, /* class, category, protocol, module names */
194 meth_var_names, /* method and variable names */
195 meth_var_types /* method and variable type descriptors */
198 static tree add_objc_string (tree, enum string_section);
199 static void build_selector_table_decl (void);
201 /* Protocol additions. */
203 static tree lookup_protocol (tree);
204 static tree lookup_and_install_protocols (tree);
208 static void encode_type_qualifiers (tree);
209 static void encode_type (tree, int, int);
210 static void encode_field_decl (tree, int, int);
213 static void really_start_method (tree, tree);
215 static void really_start_method (tree, struct c_arg_info *);
217 static int comp_proto_with_proto (tree, tree, int);
218 static tree objc_decay_parm_type (tree);
219 static void objc_push_parm (tree);
221 static tree objc_get_parm_info (int);
223 static struct c_arg_info *objc_get_parm_info (int);
226 /* Utilities for debugging and error diagnostics. */
228 static char *gen_type_name (tree);
229 static char *gen_type_name_0 (tree);
230 static char *gen_method_decl (tree);
231 static char *gen_declaration (tree);
233 /* Everything else. */
235 static tree create_field_decl (tree, const char *);
236 static void add_class_reference (tree);
237 static void build_protocol_template (void);
238 static tree encode_method_prototype (tree);
239 static void generate_classref_translation_entry (tree);
240 static void handle_class_ref (tree);
241 static void generate_struct_by_value_array (void)
243 static void mark_referenced_methods (void);
244 static void generate_objc_image_info (void);
245 static bool objc_type_valid_for_messaging (tree typ);
247 /*** Private Interface (data) ***/
249 /* Reserved tag definitions. */
251 #define OBJECT_TYPEDEF_NAME "id"
252 #define CLASS_TYPEDEF_NAME "Class"
254 #define TAG_OBJECT "objc_object"
255 #define TAG_CLASS "objc_class"
256 #define TAG_SUPER "objc_super"
257 #define TAG_SELECTOR "objc_selector"
259 #define UTAG_CLASS "_objc_class"
260 #define UTAG_IVAR "_objc_ivar"
261 #define UTAG_IVAR_LIST "_objc_ivar_list"
262 #define UTAG_METHOD "_objc_method"
263 #define UTAG_METHOD_LIST "_objc_method_list"
264 #define UTAG_CATEGORY "_objc_category"
265 #define UTAG_MODULE "_objc_module"
266 #define UTAG_SYMTAB "_objc_symtab"
267 #define UTAG_SUPER "_objc_super"
268 #define UTAG_SELECTOR "_objc_selector"
270 #define UTAG_PROTOCOL "_objc_protocol"
271 #define UTAG_METHOD_PROTOTYPE "_objc_method_prototype"
272 #define UTAG_METHOD_PROTOTYPE_LIST "_objc__method_prototype_list"
274 /* Note that the string object global name is only needed for the
276 #define STRING_OBJECT_GLOBAL_FORMAT "_%sClassReference"
278 #define PROTOCOL_OBJECT_CLASS_NAME "Protocol"
280 #define TAG_ENUMERATION_MUTATION "objc_enumerationMutation"
281 #define TAG_FAST_ENUMERATION_STATE "__objcFastEnumerationState"
283 static const char *TAG_GETCLASS;
284 static const char *TAG_GETMETACLASS;
285 static const char *TAG_MSGSEND;
286 static const char *TAG_MSGSENDSUPER;
287 /* The NeXT Objective-C messenger may have two extra entry points, for use
288 when returning a structure. */
289 static const char *TAG_MSGSEND_STRET;
290 static const char *TAG_MSGSENDSUPER_STRET;
291 static const char *default_constant_string_class_name;
293 /* Runtime metadata flags. */
294 #define CLS_FACTORY 0x0001L
295 #define CLS_META 0x0002L
296 #define CLS_HAS_CXX_STRUCTORS 0x2000L
298 #define OBJC_MODIFIER_STATIC 0x00000001
299 #define OBJC_MODIFIER_FINAL 0x00000002
300 #define OBJC_MODIFIER_PUBLIC 0x00000004
301 #define OBJC_MODIFIER_PRIVATE 0x00000008
302 #define OBJC_MODIFIER_PROTECTED 0x00000010
303 #define OBJC_MODIFIER_NATIVE 0x00000020
304 #define OBJC_MODIFIER_SYNCHRONIZED 0x00000040
305 #define OBJC_MODIFIER_ABSTRACT 0x00000080
306 #define OBJC_MODIFIER_VOLATILE 0x00000100
307 #define OBJC_MODIFIER_TRANSIENT 0x00000200
308 #define OBJC_MODIFIER_NONE_SPECIFIED 0x80000000
310 /* NeXT-specific tags. */
312 #define TAG_MSGSEND_NONNIL "objc_msgSendNonNil"
313 #define TAG_MSGSEND_NONNIL_STRET "objc_msgSendNonNil_stret"
314 #define TAG_EXCEPTIONEXTRACT "objc_exception_extract"
315 #define TAG_EXCEPTIONTRYENTER "objc_exception_try_enter"
316 #define TAG_EXCEPTIONTRYEXIT "objc_exception_try_exit"
317 #define TAG_EXCEPTIONMATCH "objc_exception_match"
318 #define TAG_EXCEPTIONTHROW "objc_exception_throw"
319 #define TAG_SYNCENTER "objc_sync_enter"
320 #define TAG_SYNCEXIT "objc_sync_exit"
321 #define TAG_SETJMP "_setjmp"
322 #define UTAG_EXCDATA "_objc_exception_data"
324 #define TAG_ASSIGNIVAR "objc_assign_ivar"
325 #define TAG_ASSIGNGLOBAL "objc_assign_global"
326 #define TAG_ASSIGNSTRONGCAST "objc_assign_strongCast"
328 /* Branch entry points. All that matters here are the addresses;
329 functions with these names do not really exist in libobjc. */
331 #define TAG_MSGSEND_FAST "objc_msgSend_Fast"
332 #define TAG_ASSIGNIVAR_FAST "objc_assign_ivar_Fast"
334 #define TAG_CXX_CONSTRUCT ".cxx_construct"
335 #define TAG_CXX_DESTRUCT ".cxx_destruct"
337 /* GNU-specific tags. */
339 #define TAG_EXECCLASS "__objc_exec_class"
340 #define TAG_GNUINIT "__objc_gnu_init"
342 /* Flags for lookup_method_static(). */
343 #define OBJC_LOOKUP_CLASS 1 /* Look for class methods. */
344 #define OBJC_LOOKUP_NO_SUPER 2 /* Do not examine superclasses. */
346 /* The OCTI_... enumeration itself is in objc/objc-act.h. */
347 tree objc_global_trees[OCTI_MAX];
349 static void handle_impent (struct imp_entry *);
351 struct imp_entry *imp_list = 0;
352 int imp_count = 0; /* `@implementation' */
353 int cat_count = 0; /* `@category' */
355 enum tree_code objc_inherit_code;
356 int objc_public_flag;
358 /* Use to generate method labels. */
359 static int method_slot = 0;
361 /* Flag to say whether methods in a protocol are optional or
363 static bool objc_method_optional_flag = false;
365 static int objc_collecting_ivars = 0;
369 static char *errbuf; /* Buffer for error diagnostics */
371 /* Data imported from tree.c. */
373 extern enum debug_info_type write_symbols;
375 /* Data imported from toplev.c. */
377 extern const char *dump_base_name;
379 static int flag_typed_selectors;
381 /* Store all constructed constant strings in a hash table so that
382 they get uniqued properly. */
384 struct GTY(()) string_descriptor {
385 /* The literal argument . */
388 /* The resulting constant string. */
392 static GTY((param_is (struct string_descriptor))) htab_t string_htab;
394 /* Store the EH-volatilized types in a hash table, for easy retrieval. */
395 struct GTY(()) volatilized_type {
399 static GTY((param_is (struct volatilized_type))) htab_t volatilized_htab;
401 FILE *gen_declaration_file;
403 /* Tells "encode_pointer/encode_aggregate" whether we are generating
404 type descriptors for instance variables (as opposed to methods).
405 Type descriptors for instance variables contain more information
406 than methods (for static typing and embedded structures). */
408 static int generating_instance_variables = 0;
410 /* For building an objc struct. These may not be used when this file
411 is compiled as part of obj-c++. */
413 static bool objc_building_struct;
414 static struct c_struct_parse_info *objc_struct_info ATTRIBUTE_UNUSED;
416 /* Start building a struct for objc. */
419 objc_start_struct (tree name)
421 gcc_assert (!objc_building_struct);
422 objc_building_struct = true;
423 return start_struct (input_location, RECORD_TYPE, name, &objc_struct_info);
426 /* Finish building a struct for objc. */
429 objc_finish_struct (tree type, tree fieldlist)
431 gcc_assert (objc_building_struct);
432 objc_building_struct = false;
433 return finish_struct (input_location, type, fieldlist, NULL_TREE,
438 build_sized_array_type (tree base_type, int size)
440 tree index_type = build_index_type (build_int_cst (NULL_TREE, size - 1));
441 return build_array_type (base_type, index_type);
445 add_field_decl (tree type, const char *name, tree **chain)
447 tree field = create_field_decl (type, name);
451 *chain = &DECL_CHAIN (field);
456 /* Some platforms pass small structures through registers versus
457 through an invisible pointer. Determine at what size structure is
458 the transition point between the two possibilities. */
461 generate_struct_by_value_array (void)
466 int aggregate_in_mem[32];
469 /* Presumably no platform passes 32 byte structures in a register. */
470 for (i = 1; i < 32; i++)
475 /* Create an unnamed struct that has `i' character components */
476 type = objc_start_struct (NULL_TREE);
478 strcpy (buffer, "c1");
479 decls = add_field_decl (char_type_node, buffer, &chain);
481 for (j = 1; j < i; j++)
483 sprintf (buffer, "c%d", j + 1);
484 add_field_decl (char_type_node, buffer, &chain);
486 objc_finish_struct (type, decls);
488 aggregate_in_mem[i] = aggregate_value_p (type, 0);
489 if (!aggregate_in_mem[i])
493 /* We found some structures that are returned in registers instead of memory
494 so output the necessary data. */
497 for (i = 31; i >= 0; i--)
498 if (!aggregate_in_mem[i])
500 printf ("#define OBJC_MAX_STRUCT_BY_VALUE %d\n\n", i);
502 /* The first member of the structure is always 0 because we don't handle
503 structures with 0 members */
504 printf ("static int struct_forward_array[] = {\n 0");
506 for (j = 1; j <= i; j++)
507 printf (", %d", aggregate_in_mem[j]);
518 if (cxx_init () == false)
520 if (c_objc_common_init () == false)
524 /* If gen_declaration desired, open the output file. */
525 if (flag_gen_declaration)
527 register char * const dumpname = concat (dump_base_name, ".decl", NULL);
528 gen_declaration_file = fopen (dumpname, "w");
529 if (gen_declaration_file == 0)
530 fatal_error ("can't open %s: %m", dumpname);
534 if (flag_next_runtime)
536 TAG_GETCLASS = "objc_getClass";
537 TAG_GETMETACLASS = "objc_getMetaClass";
538 TAG_MSGSEND = "objc_msgSend";
539 TAG_MSGSENDSUPER = "objc_msgSendSuper";
540 TAG_MSGSEND_STRET = "objc_msgSend_stret";
541 TAG_MSGSENDSUPER_STRET = "objc_msgSendSuper_stret";
542 default_constant_string_class_name = "NSConstantString";
546 TAG_GETCLASS = "objc_get_class";
547 TAG_GETMETACLASS = "objc_get_meta_class";
548 TAG_MSGSEND = "objc_msg_lookup";
549 TAG_MSGSENDSUPER = "objc_msg_lookup_super";
550 /* GNU runtime does not provide special functions to support
551 structure-returning methods. */
552 default_constant_string_class_name = "NXConstantString";
553 flag_typed_selectors = 1;
554 /* GNU runtime does not need the compiler to change code
555 in order to do GC. */
558 warning_at (0, 0, "%<-fobjc-gc%> is ignored for %<-fgnu-runtime%>");
565 if (print_struct_values && !flag_compare_debug)
566 generate_struct_by_value_array ();
572 objc_finish_file (void)
574 mark_referenced_methods ();
577 /* We need to instantiate templates _before_ we emit ObjC metadata;
578 if we do not, some metadata (such as selectors) may go missing. */
580 instantiate_pending_templates (0);
583 /* Finalize Objective-C runtime data. No need to generate tables
584 and code if only checking syntax, or if generating a PCH file. */
585 if (!flag_syntax_only && !pch_file)
588 if (gen_declaration_file)
589 fclose (gen_declaration_file);
592 /* Return the first occurrence of a method declaration corresponding
593 to sel_name in rproto_list. Search rproto_list recursively.
594 If is_class is 0, search for instance methods, otherwise for class
597 lookup_method_in_protocol_list (tree rproto_list, tree sel_name,
603 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
605 p = TREE_VALUE (rproto);
607 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
609 if ((fnd = lookup_method (is_class
610 ? PROTOCOL_CLS_METHODS (p)
611 : PROTOCOL_NST_METHODS (p), sel_name)))
613 else if (PROTOCOL_LIST (p))
614 fnd = lookup_method_in_protocol_list (PROTOCOL_LIST (p),
619 ; /* An identifier...if we could not find a protocol. */
630 lookup_protocol_in_reflist (tree rproto_list, tree lproto)
634 /* Make sure the protocol is supported by the object on the rhs. */
635 if (TREE_CODE (lproto) == PROTOCOL_INTERFACE_TYPE)
638 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
640 p = TREE_VALUE (rproto);
642 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
647 else if (PROTOCOL_LIST (p))
648 fnd = lookup_protocol_in_reflist (PROTOCOL_LIST (p), lproto);
657 ; /* An identifier...if we could not find a protocol. */
664 objc_start_class_interface (tree klass, tree super_class,
665 tree protos, tree attributes)
668 warning_at (input_location, OPT_Wattributes,
669 "class attributes are not available in this version"
670 " of the compiler, (ignored)");
671 objc_interface_context
673 = start_class (CLASS_INTERFACE_TYPE, klass, super_class, protos);
674 objc_public_flag = 0;
678 objc_start_category_interface (tree klass, tree categ,
679 tree protos, tree attributes)
682 warning_at (input_location, OPT_Wattributes,
683 "category attributes are not available in this version"
684 " of the compiler, (ignored)");
685 objc_interface_context
686 = start_class (CATEGORY_INTERFACE_TYPE, klass, categ, protos);
688 = continue_class (objc_interface_context);
692 objc_start_protocol (tree name, tree protos, tree attributes)
695 warning_at (input_location, OPT_Wattributes,
696 "protocol attributes are not available in this version"
697 " of the compiler, (ignored)");
698 objc_interface_context
699 = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos);
700 objc_method_optional_flag = false;
704 objc_continue_interface (void)
707 = continue_class (objc_interface_context);
711 objc_finish_interface (void)
713 finish_class (objc_interface_context);
714 objc_interface_context = NULL_TREE;
715 objc_method_optional_flag = false;
719 objc_start_class_implementation (tree klass, tree super_class)
721 objc_implementation_context
723 = start_class (CLASS_IMPLEMENTATION_TYPE, klass, super_class, NULL_TREE);
724 objc_public_flag = 0;
728 objc_start_category_implementation (tree klass, tree categ)
730 objc_implementation_context
731 = start_class (CATEGORY_IMPLEMENTATION_TYPE, klass, categ, NULL_TREE);
733 = continue_class (objc_implementation_context);
737 objc_continue_implementation (void)
740 = continue_class (objc_implementation_context);
744 objc_finish_implementation (void)
747 if (flag_objc_call_cxx_cdtors)
748 objc_generate_cxx_cdtors ();
751 if (objc_implementation_context)
753 finish_class (objc_implementation_context);
754 objc_ivar_chain = NULL_TREE;
755 objc_implementation_context = NULL_TREE;
758 warning (0, "%<@end%> must appear in an @implementation context");
762 objc_set_visibility (int visibility)
764 objc_public_flag = visibility;
768 objc_set_method_opt (bool optional)
770 objc_method_optional_flag = optional;
771 if (!objc_interface_context
772 || TREE_CODE (objc_interface_context) != PROTOCOL_INTERFACE_TYPE)
774 error ("@optional/@required is allowed in @protocol context only.");
775 objc_method_optional_flag = false;
780 objc_set_method_type (enum tree_code type)
782 objc_inherit_code = (type == PLUS_EXPR
784 : INSTANCE_METHOD_DECL);
788 objc_build_method_signature (tree rettype, tree selector,
789 tree optparms, bool ellipsis)
791 return build_method_decl (objc_inherit_code, rettype, selector,
796 objc_add_method_declaration (tree decl, tree attributes)
798 if (!objc_interface_context)
800 /* PS: At the moment, due to how the parser works, it should be
801 impossible to get here. But it's good to have the check in
802 case the parser changes.
804 fatal_error ("method declaration not in @interface context");
808 warning_at (input_location, OPT_Wattributes,
809 "method attributes are not available in this version"
810 " of the compiler, (ignored)");
812 objc_add_method (objc_interface_context,
814 objc_inherit_code == CLASS_METHOD_DECL,
815 objc_method_optional_flag);
818 /* Return 'true' if the method definition could be started, and
819 'false' if not (because we are outside an @implementation context).
822 objc_start_method_definition (tree decl, tree attributes)
824 if (!objc_implementation_context)
826 error ("method definition not in @implementation context");
830 if (decl != NULL_TREE && METHOD_SEL_NAME (decl) == error_mark_node)
834 warning_at (input_location, OPT_Wattributes,
835 "method attributes are not available in this version"
836 " of the compiler, (ignored)");
839 /* Indicate no valid break/continue context by setting these variables
840 to some non-null, non-label value. We'll notice and emit the proper
841 error message in c_finish_bc_stmt. */
842 c_break_label = c_cont_label = size_zero_node;
845 objc_add_method (objc_implementation_context,
847 objc_inherit_code == CLASS_METHOD_DECL,
848 /* is optional */ false);
849 start_method_def (decl);
854 objc_add_instance_variable (tree decl)
856 (void) add_instance_variable (objc_ivar_context,
861 /* Return true if TYPE is 'id'. */
864 objc_is_object_id (tree type)
866 return OBJC_TYPE_NAME (type) == objc_object_id;
870 objc_is_class_id (tree type)
872 return OBJC_TYPE_NAME (type) == objc_class_id;
875 /* Construct a C struct with same name as KLASS, a base struct with tag
876 SUPER_NAME (if any), and FIELDS indicated. */
879 objc_build_struct (tree klass, tree fields, tree super_name)
881 tree name = CLASS_NAME (klass);
882 tree s = objc_start_struct (name);
883 tree super = (super_name ? xref_tag (RECORD_TYPE, super_name) : NULL_TREE);
885 VEC(tree,heap) *objc_info = NULL;
890 /* Prepend a packed variant of the base class into the layout. This
891 is necessary to preserve ObjC ABI compatibility. */
892 tree base = build_decl (input_location,
893 FIELD_DECL, NULL_TREE, super);
894 tree field = TYPE_FIELDS (super);
896 while (field && DECL_CHAIN (field)
897 && TREE_CODE (DECL_CHAIN (field)) == FIELD_DECL)
898 field = DECL_CHAIN (field);
900 /* For ObjC ABI purposes, the "packed" size of a base class is
901 the sum of the offset and the size (in bits) of the last field
904 = (field && TREE_CODE (field) == FIELD_DECL
905 ? size_binop (PLUS_EXPR,
906 size_binop (PLUS_EXPR,
909 convert (bitsizetype,
910 DECL_FIELD_OFFSET (field)),
911 bitsize_int (BITS_PER_UNIT)),
912 DECL_FIELD_BIT_OFFSET (field)),
914 : bitsize_zero_node);
915 DECL_SIZE_UNIT (base)
916 = size_binop (FLOOR_DIV_EXPR, convert (sizetype, DECL_SIZE (base)),
917 size_int (BITS_PER_UNIT));
918 DECL_ARTIFICIAL (base) = 1;
919 DECL_ALIGN (base) = 1;
920 DECL_FIELD_CONTEXT (base) = s;
922 DECL_FIELD_IS_BASE (base) = 1;
925 TREE_NO_WARNING (fields) = 1; /* Suppress C++ ABI warnings -- we */
926 #endif /* are following the ObjC ABI here. */
927 DECL_CHAIN (base) = fields;
931 /* NB: Calling finish_struct() may cause type TYPE_LANG_SPECIFIC fields
932 in all variants of this RECORD_TYPE to be clobbered, but it is therein
933 that we store protocol conformance info (e.g., 'NSObject <MyProtocol>').
934 Hence, we must squirrel away the ObjC-specific information before calling
935 finish_struct(), and then reinstate it afterwards. */
937 for (t = TYPE_NEXT_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t))
939 if (!TYPE_HAS_OBJC_INFO (t))
941 INIT_TYPE_OBJC_INFO (t);
942 TYPE_OBJC_INTERFACE (t) = klass;
944 VEC_safe_push (tree, heap, objc_info, TYPE_OBJC_INFO (t));
947 /* Point the struct at its related Objective-C class. */
948 INIT_TYPE_OBJC_INFO (s);
949 TYPE_OBJC_INTERFACE (s) = klass;
951 s = objc_finish_struct (s, fields);
953 for (i = 0, t = TYPE_NEXT_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t), i++)
955 TYPE_OBJC_INFO (t) = VEC_index (tree, objc_info, i);
956 /* Replace the IDENTIFIER_NODE with an actual @interface. */
957 TYPE_OBJC_INTERFACE (t) = klass;
959 VEC_free (tree, heap, objc_info);
961 /* Use TYPE_BINFO structures to point at the super class, if any. */
962 objc_xref_basetypes (s, super);
964 /* Mark this struct as a class template. */
965 CLASS_STATIC_TEMPLATE (klass) = s;
970 /* Build a type differing from TYPE only in that TYPE_VOLATILE is set.
971 Unlike tree.c:build_qualified_type(), preserve TYPE_LANG_SPECIFIC in the
974 objc_build_volatilized_type (tree type)
978 /* Check if we have not constructed the desired variant already. */
979 for (t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
981 /* The type qualifiers must (obviously) match up. */
982 if (!TYPE_VOLATILE (t)
983 || (TYPE_READONLY (t) != TYPE_READONLY (type))
984 || (TYPE_RESTRICT (t) != TYPE_RESTRICT (type)))
987 /* For pointer types, the pointees (and hence their TYPE_LANG_SPECIFIC
988 info, if any) must match up. */
989 if (POINTER_TYPE_P (t)
990 && (TREE_TYPE (t) != TREE_TYPE (type)))
993 /* Everything matches up! */
997 /* Ok, we could not re-use any of the pre-existing variants. Create
999 t = build_variant_type_copy (type);
1000 TYPE_VOLATILE (t) = 1;
1002 /* Set up the canonical type information. */
1003 if (TYPE_STRUCTURAL_EQUALITY_P (type))
1004 SET_TYPE_STRUCTURAL_EQUALITY (t);
1005 else if (TYPE_CANONICAL (type) != type)
1006 TYPE_CANONICAL (t) = objc_build_volatilized_type (TYPE_CANONICAL (type));
1008 TYPE_CANONICAL (t) = t;
1013 /* Mark DECL as being 'volatile' for purposes of Darwin
1014 _setjmp()/_longjmp() exception handling. Called from
1015 objc_mark_locals_volatile(). */
1017 objc_volatilize_decl (tree decl)
1019 /* Do not mess with variables that are 'static' or (already)
1021 if (!TREE_THIS_VOLATILE (decl) && !TREE_STATIC (decl)
1022 && (TREE_CODE (decl) == VAR_DECL
1023 || TREE_CODE (decl) == PARM_DECL))
1025 tree t = TREE_TYPE (decl);
1026 struct volatilized_type key;
1029 t = objc_build_volatilized_type (t);
1031 loc = htab_find_slot (volatilized_htab, &key, INSERT);
1035 *loc = ggc_alloc_volatilized_type ();
1036 ((struct volatilized_type *) *loc)->type = t;
1039 TREE_TYPE (decl) = t;
1040 TREE_THIS_VOLATILE (decl) = 1;
1041 TREE_SIDE_EFFECTS (decl) = 1;
1042 DECL_REGISTER (decl) = 0;
1044 C_DECL_REGISTER (decl) = 0;
1049 /* Check if protocol PROTO is adopted (directly or indirectly) by class CLS
1050 (including its categories and superclasses) or by object type TYP.
1051 Issue a warning if PROTO is not adopted anywhere and WARN is set. */
1054 objc_lookup_protocol (tree proto, tree cls, tree typ, bool warn)
1056 bool class_type = (cls != NULL_TREE);
1062 /* Check protocols adopted by the class and its categories. */
1063 for (c = cls; c; c = CLASS_CATEGORY_LIST (c))
1065 if (lookup_protocol_in_reflist (CLASS_PROTOCOL_LIST (c), proto))
1069 /* Repeat for superclasses. */
1070 cls = lookup_interface (CLASS_SUPER_NAME (cls));
1073 /* Check for any protocols attached directly to the object type. */
1074 if (TYPE_HAS_OBJC_INFO (typ))
1076 if (lookup_protocol_in_reflist (TYPE_OBJC_PROTOCOL_LIST (typ), proto))
1083 gen_type_name_0 (class_type ? typ : TYPE_POINTER_TO (typ));
1084 /* NB: Types 'id' and 'Class' cannot reasonably be described as
1085 "implementing" a given protocol, since they do not have an
1088 warning (0, "class %qs does not implement the %qE protocol",
1089 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
1091 warning (0, "type %qs does not conform to the %qE protocol",
1092 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
1098 /* Check if class RCLS and instance struct type RTYP conform to at least the
1099 same protocols that LCLS and LTYP conform to. */
1102 objc_compare_protocols (tree lcls, tree ltyp, tree rcls, tree rtyp, bool warn)
1105 bool have_lproto = false;
1109 /* NB: We do _not_ look at categories defined for LCLS; these may or
1110 may not get loaded in, and therefore it is unreasonable to require
1111 that RCLS/RTYP must implement any of their protocols. */
1112 for (p = CLASS_PROTOCOL_LIST (lcls); p; p = TREE_CHAIN (p))
1116 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1120 /* Repeat for superclasses. */
1121 lcls = lookup_interface (CLASS_SUPER_NAME (lcls));
1124 /* Check for any protocols attached directly to the object type. */
1125 if (TYPE_HAS_OBJC_INFO (ltyp))
1127 for (p = TYPE_OBJC_PROTOCOL_LIST (ltyp); p; p = TREE_CHAIN (p))
1131 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1136 /* NB: If LTYP and LCLS have no protocols to search for, return 'true'
1137 vacuously, _unless_ RTYP is a protocol-qualified 'id'. We can get
1138 away with simply checking for 'id' or 'Class' (!RCLS), since this
1139 routine will not get called in other cases. */
1140 return have_lproto || (rcls != NULL_TREE);
1143 /* Given two types TYPE1 and TYPE2, return their least common ancestor.
1144 Both TYPE1 and TYPE2 must be pointers, and already determined to be
1145 compatible by objc_compare_types() below. */
1148 objc_common_type (tree type1, tree type2)
1150 tree inner1 = TREE_TYPE (type1), inner2 = TREE_TYPE (type2);
1152 while (POINTER_TYPE_P (inner1))
1154 inner1 = TREE_TYPE (inner1);
1155 inner2 = TREE_TYPE (inner2);
1158 /* If one type is derived from another, return the base type. */
1159 if (DERIVED_FROM_P (inner1, inner2))
1161 else if (DERIVED_FROM_P (inner2, inner1))
1164 /* If both types are 'Class', return 'Class'. */
1165 if (objc_is_class_id (inner1) && objc_is_class_id (inner2))
1166 return objc_class_type;
1168 /* Otherwise, return 'id'. */
1169 return objc_object_type;
1172 /* Determine if it is permissible to assign (if ARGNO is greater than -3)
1173 an instance of RTYP to an instance of LTYP or to compare the two
1174 (if ARGNO is equal to -3), per ObjC type system rules. Before
1175 returning 'true', this routine may issue warnings related to, e.g.,
1176 protocol conformance. When returning 'false', the routine must
1177 produce absolutely no warnings; the C or C++ front-end will do so
1178 instead, if needed. If either LTYP or RTYP is not an Objective-C type,
1179 the routine must return 'false'.
1181 The ARGNO parameter is encoded as follows:
1182 >= 1 Parameter number (CALLEE contains function being called);
1186 -3 Comparison (LTYP and RTYP may match in either direction);
1187 -4 Silent comparison (for C++ overload resolution).
1191 objc_compare_types (tree ltyp, tree rtyp, int argno, tree callee)
1193 tree lcls, rcls, lproto, rproto;
1194 bool pointers_compatible;
1196 /* We must be dealing with pointer types */
1197 if (!POINTER_TYPE_P (ltyp) || !POINTER_TYPE_P (rtyp))
1202 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
1203 rtyp = TREE_TYPE (rtyp);
1205 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
1207 /* We must also handle function pointers, since ObjC is a bit more
1208 lenient than C or C++ on this. */
1209 if (TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE)
1211 /* Return types must be covariant. */
1212 if (!comptypes (TREE_TYPE (ltyp), TREE_TYPE (rtyp))
1213 && !objc_compare_types (TREE_TYPE (ltyp), TREE_TYPE (rtyp),
1217 /* Argument types must be contravariant. */
1218 for (ltyp = TYPE_ARG_TYPES (ltyp), rtyp = TYPE_ARG_TYPES (rtyp);
1219 ltyp && rtyp; ltyp = TREE_CHAIN (ltyp), rtyp = TREE_CHAIN (rtyp))
1221 if (!comptypes (TREE_VALUE (rtyp), TREE_VALUE (ltyp))
1222 && !objc_compare_types (TREE_VALUE (rtyp), TREE_VALUE (ltyp),
1227 return (ltyp == rtyp);
1230 /* Past this point, we are only interested in ObjC class instances,
1231 or 'id' or 'Class'. */
1232 if (TREE_CODE (ltyp) != RECORD_TYPE || TREE_CODE (rtyp) != RECORD_TYPE)
1235 if (!objc_is_object_id (ltyp) && !objc_is_class_id (ltyp)
1236 && !TYPE_HAS_OBJC_INFO (ltyp))
1239 if (!objc_is_object_id (rtyp) && !objc_is_class_id (rtyp)
1240 && !TYPE_HAS_OBJC_INFO (rtyp))
1243 /* Past this point, we are committed to returning 'true' to the caller
1244 (unless performing a silent comparison; see below). However, we can
1245 still warn about type and/or protocol mismatches. */
1247 if (TYPE_HAS_OBJC_INFO (ltyp))
1249 lcls = TYPE_OBJC_INTERFACE (ltyp);
1250 lproto = TYPE_OBJC_PROTOCOL_LIST (ltyp);
1253 lcls = lproto = NULL_TREE;
1255 if (TYPE_HAS_OBJC_INFO (rtyp))
1257 rcls = TYPE_OBJC_INTERFACE (rtyp);
1258 rproto = TYPE_OBJC_PROTOCOL_LIST (rtyp);
1261 rcls = rproto = NULL_TREE;
1263 /* If we could not find an @interface declaration, we must have
1264 only seen a @class declaration; for purposes of type comparison,
1265 treat it as a stand-alone (root) class. */
1267 if (lcls && TREE_CODE (lcls) == IDENTIFIER_NODE)
1270 if (rcls && TREE_CODE (rcls) == IDENTIFIER_NODE)
1273 /* If either type is an unqualified 'id', we're done. */
1274 if ((!lproto && objc_is_object_id (ltyp))
1275 || (!rproto && objc_is_object_id (rtyp)))
1278 pointers_compatible = (TYPE_MAIN_VARIANT (ltyp) == TYPE_MAIN_VARIANT (rtyp));
1280 /* If the underlying types are the same, and at most one of them has
1281 a protocol list, we do not need to issue any diagnostics. */
1282 if (pointers_compatible && (!lproto || !rproto))
1285 /* If exactly one of the types is 'Class', issue a diagnostic; any
1286 exceptions of this rule have already been handled. */
1287 if (objc_is_class_id (ltyp) ^ objc_is_class_id (rtyp))
1288 pointers_compatible = false;
1289 /* Otherwise, check for inheritance relations. */
1292 if (!pointers_compatible)
1294 = (objc_is_object_id (ltyp) || objc_is_object_id (rtyp));
1296 if (!pointers_compatible)
1297 pointers_compatible = DERIVED_FROM_P (ltyp, rtyp);
1299 if (!pointers_compatible && argno <= -3)
1300 pointers_compatible = DERIVED_FROM_P (rtyp, ltyp);
1303 /* If the pointers match modulo protocols, check for protocol conformance
1305 if (pointers_compatible)
1307 pointers_compatible = objc_compare_protocols (lcls, ltyp, rcls, rtyp,
1310 if (!pointers_compatible && argno == -3)
1311 pointers_compatible = objc_compare_protocols (rcls, rtyp, lcls, ltyp,
1315 if (!pointers_compatible)
1317 /* The two pointers are not exactly compatible. Issue a warning, unless
1318 we are performing a silent comparison, in which case return 'false'
1320 /* NB: For the time being, we shall make our warnings look like their
1321 C counterparts. In the future, we may wish to make them more
1329 warning (0, "comparison of distinct Objective-C types lacks a cast");
1333 warning (0, "initialization from distinct Objective-C type");
1337 warning (0, "assignment from distinct Objective-C type");
1341 warning (0, "distinct Objective-C type in return");
1345 warning (0, "passing argument %d of %qE from distinct "
1346 "Objective-C type", argno, callee);
1354 /* This routine is similar to objc_compare_types except that function-pointers are
1355 excluded. This is because, caller assumes that common types are of (id, Object*)
1356 variety and calls objc_common_type to obtain a common type. There is no commonolty
1357 between two function-pointers in this regard. */
1360 objc_have_common_type (tree ltyp, tree rtyp, int argno, tree callee)
1362 if (objc_compare_types (ltyp, rtyp, argno, callee))
1364 /* exclude function-pointer types. */
1367 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
1368 rtyp = TREE_TYPE (rtyp);
1370 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
1371 return !(TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE);
1376 /* Check if LTYP and RTYP have the same type qualifiers. If either type
1377 lives in the volatilized hash table, ignore the 'volatile' bit when
1378 making the comparison. */
1381 objc_type_quals_match (tree ltyp, tree rtyp)
1383 int lquals = TYPE_QUALS (ltyp), rquals = TYPE_QUALS (rtyp);
1384 struct volatilized_type key;
1388 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1389 lquals &= ~TYPE_QUAL_VOLATILE;
1393 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1394 rquals &= ~TYPE_QUAL_VOLATILE;
1396 return (lquals == rquals);
1400 /* Determine if CHILD is derived from PARENT. The routine assumes that
1401 both parameters are RECORD_TYPEs, and is non-reflexive. */
1404 objc_derived_from_p (tree parent, tree child)
1406 parent = TYPE_MAIN_VARIANT (parent);
1408 for (child = TYPE_MAIN_VARIANT (child);
1409 TYPE_BINFO (child) && BINFO_N_BASE_BINFOS (TYPE_BINFO (child));)
1411 child = TYPE_MAIN_VARIANT (BINFO_TYPE (BINFO_BASE_BINFO
1412 (TYPE_BINFO (child),
1415 if (child == parent)
1424 objc_build_component_ref (tree datum, tree component)
1426 /* If COMPONENT is NULL, the caller is referring to the anonymous
1427 base class field. */
1430 tree base = TYPE_FIELDS (TREE_TYPE (datum));
1432 return build3 (COMPONENT_REF, TREE_TYPE (base), datum, base, NULL_TREE);
1435 /* The 'build_component_ref' routine has been removed from the C++
1436 front-end, but 'finish_class_member_access_expr' seems to be
1437 a worthy substitute. */
1439 return finish_class_member_access_expr (datum, component, false,
1440 tf_warning_or_error);
1442 return build_component_ref (input_location, datum, component);
1446 /* Recursively copy inheritance information rooted at BINFO. To do this,
1447 we emulate the song and dance performed by cp/tree.c:copy_binfo(). */
1450 objc_copy_binfo (tree binfo)
1452 tree btype = BINFO_TYPE (binfo);
1453 tree binfo2 = make_tree_binfo (BINFO_N_BASE_BINFOS (binfo));
1457 BINFO_TYPE (binfo2) = btype;
1458 BINFO_OFFSET (binfo2) = BINFO_OFFSET (binfo);
1459 BINFO_BASE_ACCESSES (binfo2) = BINFO_BASE_ACCESSES (binfo);
1461 /* Recursively copy base binfos of BINFO. */
1462 for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
1464 tree base_binfo2 = objc_copy_binfo (base_binfo);
1466 BINFO_INHERITANCE_CHAIN (base_binfo2) = binfo2;
1467 BINFO_BASE_APPEND (binfo2, base_binfo2);
1473 /* Record superclass information provided in BASETYPE for ObjC class REF.
1474 This is loosely based on cp/decl.c:xref_basetypes(). */
1477 objc_xref_basetypes (tree ref, tree basetype)
1479 tree binfo = make_tree_binfo (basetype ? 1 : 0);
1481 TYPE_BINFO (ref) = binfo;
1482 BINFO_OFFSET (binfo) = size_zero_node;
1483 BINFO_TYPE (binfo) = ref;
1487 tree base_binfo = objc_copy_binfo (TYPE_BINFO (basetype));
1489 BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
1490 BINFO_BASE_ACCESSES (binfo) = VEC_alloc (tree, gc, 1);
1491 BINFO_BASE_APPEND (binfo, base_binfo);
1492 BINFO_BASE_ACCESS_APPEND (binfo, access_public_node);
1497 volatilized_hash (const void *ptr)
1499 const_tree const typ = ((const struct volatilized_type *)ptr)->type;
1501 return htab_hash_pointer(typ);
1505 volatilized_eq (const void *ptr1, const void *ptr2)
1507 const_tree const typ1 = ((const struct volatilized_type *)ptr1)->type;
1508 const_tree const typ2 = ((const struct volatilized_type *)ptr2)->type;
1510 return typ1 == typ2;
1513 /* Called from finish_decl. */
1516 objc_check_decl (tree decl)
1518 tree type = TREE_TYPE (decl);
1520 if (TREE_CODE (type) != RECORD_TYPE)
1522 if (OBJC_TYPE_NAME (type) && (type = objc_is_class_name (OBJC_TYPE_NAME (type))))
1523 error ("statically allocated instance of Objective-C class %qE",
1528 objc_check_global_decl (tree decl)
1530 tree id = DECL_NAME (decl);
1531 if (objc_is_class_name (id) && global_bindings_p())
1532 error ("redeclaration of Objective-C class %qs", IDENTIFIER_POINTER (id));
1535 /* Construct a PROTOCOLS-qualified variant of INTERFACE, where INTERFACE may
1536 either name an Objective-C class, or refer to the special 'id' or 'Class'
1537 types. If INTERFACE is not a valid ObjC type, just return it unchanged. */
1540 objc_get_protocol_qualified_type (tree interface, tree protocols)
1542 /* If INTERFACE is not provided, default to 'id'. */
1543 tree type = (interface ? objc_is_id (interface) : objc_object_type);
1544 bool is_ptr = (type != NULL_TREE);
1548 type = objc_is_class_name (interface);
1552 /* If looking at a typedef, retrieve the precise type it
1554 if (TREE_CODE (interface) == IDENTIFIER_NODE)
1555 interface = identifier_global_value (interface);
1557 type = ((interface && TREE_CODE (interface) == TYPE_DECL
1558 && DECL_ORIGINAL_TYPE (interface))
1559 ? DECL_ORIGINAL_TYPE (interface)
1560 : xref_tag (RECORD_TYPE, type));
1568 type = build_variant_type_copy (type);
1570 /* For pointers (i.e., 'id' or 'Class'), attach the protocol(s)
1574 tree orig_pointee_type = TREE_TYPE (type);
1575 TREE_TYPE (type) = build_variant_type_copy (orig_pointee_type);
1577 /* Set up the canonical type information. */
1578 TYPE_CANONICAL (type)
1579 = TYPE_CANONICAL (TYPE_POINTER_TO (orig_pointee_type));
1581 TYPE_POINTER_TO (TREE_TYPE (type)) = type;
1582 type = TREE_TYPE (type);
1585 /* Look up protocols and install in lang specific list. */
1586 DUP_TYPE_OBJC_INFO (type, TYPE_MAIN_VARIANT (type));
1587 TYPE_OBJC_PROTOCOL_LIST (type) = lookup_and_install_protocols (protocols);
1589 /* For RECORD_TYPEs, point to the @interface; for 'id' and 'Class',
1590 return the pointer to the new pointee variant. */
1592 type = TYPE_POINTER_TO (type);
1594 TYPE_OBJC_INTERFACE (type)
1595 = TYPE_OBJC_INTERFACE (TYPE_MAIN_VARIANT (type));
1601 /* Check for circular dependencies in protocols. The arguments are
1602 PROTO, the protocol to check, and LIST, a list of protocol it
1606 check_protocol_recursively (tree proto, tree list)
1610 for (p = list; p; p = TREE_CHAIN (p))
1612 tree pp = TREE_VALUE (p);
1614 if (TREE_CODE (pp) == IDENTIFIER_NODE)
1615 pp = lookup_protocol (pp);
1618 fatal_error ("protocol %qE has circular dependency",
1619 PROTOCOL_NAME (pp));
1621 check_protocol_recursively (proto, PROTOCOL_LIST (pp));
1625 /* Look up PROTOCOLS, and return a list of those that are found.
1626 If none are found, return NULL. */
1629 lookup_and_install_protocols (tree protocols)
1632 tree return_value = NULL_TREE;
1634 for (proto = protocols; proto; proto = TREE_CHAIN (proto))
1636 tree ident = TREE_VALUE (proto);
1637 tree p = lookup_protocol (ident);
1640 return_value = chainon (return_value,
1641 build_tree_list (NULL_TREE, p));
1642 else if (ident != error_mark_node)
1643 error ("cannot find protocol declaration for %qE",
1647 return return_value;
1650 /* Create a declaration for field NAME of a given TYPE. */
1653 create_field_decl (tree type, const char *name)
1655 return build_decl (input_location,
1656 FIELD_DECL, get_identifier (name), type);
1659 /* Create a global, static declaration for variable NAME of a given TYPE. The
1660 finish_var_decl() routine will need to be called on it afterwards. */
1663 start_var_decl (tree type, const char *name)
1665 tree var = build_decl (input_location,
1666 VAR_DECL, get_identifier (name), type);
1668 TREE_STATIC (var) = 1;
1669 DECL_INITIAL (var) = error_mark_node; /* A real initializer is coming... */
1670 DECL_IGNORED_P (var) = 1;
1671 DECL_ARTIFICIAL (var) = 1;
1672 DECL_CONTEXT (var) = NULL_TREE;
1674 DECL_THIS_STATIC (var) = 1; /* squash redeclaration errors */
1680 /* Finish off the variable declaration created by start_var_decl(). */
1683 finish_var_decl (tree var, tree initializer)
1685 finish_decl (var, input_location, initializer, NULL_TREE, NULL_TREE);
1688 /* Find the decl for the constant string class reference. This is only
1689 used for the NeXT runtime. */
1692 setup_string_decl (void)
1697 /* %s in format will provide room for terminating null */
1698 length = strlen (STRING_OBJECT_GLOBAL_FORMAT)
1699 + strlen (constant_string_class_name);
1700 name = XNEWVEC (char, length);
1701 sprintf (name, STRING_OBJECT_GLOBAL_FORMAT,
1702 constant_string_class_name);
1703 constant_string_global_id = get_identifier (name);
1704 string_class_decl = lookup_name (constant_string_global_id);
1706 return string_class_decl;
1709 /* Purpose: "play" parser, creating/installing representations
1710 of the declarations that are required by Objective-C.
1714 type_spec--------->sc_spec
1715 (tree_list) (tree_list)
1718 identifier_node identifier_node */
1721 synth_module_prologue (void)
1724 enum debug_info_type save_write_symbols = write_symbols;
1725 const struct gcc_debug_hooks *const save_hooks = debug_hooks;
1727 /* Suppress outputting debug symbols, because
1728 dbxout_init hasn't been called yet. */
1729 write_symbols = NO_DEBUG;
1730 debug_hooks = &do_nothing_debug_hooks;
1733 push_lang_context (lang_name_c); /* extern "C" */
1736 /* The following are also defined in <objc/objc.h> and friends. */
1738 objc_object_id = get_identifier (TAG_OBJECT);
1739 objc_class_id = get_identifier (TAG_CLASS);
1741 objc_object_reference = xref_tag (RECORD_TYPE, objc_object_id);
1742 objc_class_reference = xref_tag (RECORD_TYPE, objc_class_id);
1744 objc_object_type = build_pointer_type (objc_object_reference);
1745 objc_class_type = build_pointer_type (objc_class_reference);
1747 objc_object_name = get_identifier (OBJECT_TYPEDEF_NAME);
1748 objc_class_name = get_identifier (CLASS_TYPEDEF_NAME);
1750 /* Declare the 'id' and 'Class' typedefs. */
1752 type = lang_hooks.decls.pushdecl (build_decl (input_location,
1756 TREE_NO_WARNING (type) = 1;
1757 type = lang_hooks.decls.pushdecl (build_decl (input_location,
1761 TREE_NO_WARNING (type) = 1;
1763 /* Forward-declare '@interface Protocol'. */
1765 type = get_identifier (PROTOCOL_OBJECT_CLASS_NAME);
1766 objc_declare_class (tree_cons (NULL_TREE, type, NULL_TREE));
1767 objc_protocol_type = build_pointer_type (xref_tag (RECORD_TYPE,
1770 /* Declare type of selector-objects that represent an operation name. */
1772 if (flag_next_runtime)
1773 /* `struct objc_selector *' */
1775 = build_pointer_type (xref_tag (RECORD_TYPE,
1776 get_identifier (TAG_SELECTOR)));
1778 /* `const struct objc_selector *' */
1780 = build_pointer_type
1781 (build_qualified_type (xref_tag (RECORD_TYPE,
1782 get_identifier (TAG_SELECTOR)),
1785 /* Declare receiver type used for dispatching messages to 'super'. */
1787 /* `struct objc_super *' */
1788 objc_super_type = build_pointer_type (xref_tag (RECORD_TYPE,
1789 get_identifier (TAG_SUPER)));
1791 /* Declare pointers to method and ivar lists. */
1792 objc_method_list_ptr = build_pointer_type
1793 (xref_tag (RECORD_TYPE,
1794 get_identifier (UTAG_METHOD_LIST)));
1795 objc_method_proto_list_ptr
1796 = build_pointer_type (xref_tag (RECORD_TYPE,
1797 get_identifier (UTAG_METHOD_PROTOTYPE_LIST)));
1798 objc_ivar_list_ptr = build_pointer_type
1799 (xref_tag (RECORD_TYPE,
1800 get_identifier (UTAG_IVAR_LIST)));
1802 /* TREE_NOTHROW is cleared for the message-sending functions,
1803 because the function that gets called can throw in Obj-C++, or
1804 could itself call something that can throw even in Obj-C. */
1806 if (flag_next_runtime)
1808 /* NB: In order to call one of the ..._stret (struct-returning)
1809 functions, the function *MUST* first be cast to a signature that
1810 corresponds to the actual ObjC method being invoked. This is
1811 what is done by the build_objc_method_call() routine below. */
1813 /* id objc_msgSend (id, SEL, ...); */
1814 /* id objc_msgSendNonNil (id, SEL, ...); */
1815 /* id objc_msgSend_stret (id, SEL, ...); */
1816 /* id objc_msgSendNonNil_stret (id, SEL, ...); */
1818 = build_varargs_function_type_list (objc_object_type,
1822 umsg_decl = add_builtin_function (TAG_MSGSEND,
1823 type, 0, NOT_BUILT_IN,
1825 umsg_nonnil_decl = add_builtin_function (TAG_MSGSEND_NONNIL,
1826 type, 0, NOT_BUILT_IN,
1828 umsg_stret_decl = add_builtin_function (TAG_MSGSEND_STRET,
1829 type, 0, NOT_BUILT_IN,
1831 umsg_nonnil_stret_decl = add_builtin_function (TAG_MSGSEND_NONNIL_STRET,
1832 type, 0, NOT_BUILT_IN,
1835 /* These can throw, because the function that gets called can throw
1836 in Obj-C++, or could itself call something that can throw even
1838 TREE_NOTHROW (umsg_decl) = 0;
1839 TREE_NOTHROW (umsg_nonnil_decl) = 0;
1840 TREE_NOTHROW (umsg_stret_decl) = 0;
1841 TREE_NOTHROW (umsg_nonnil_stret_decl) = 0;
1843 /* id objc_msgSend_Fast (id, SEL, ...)
1844 __attribute__ ((hard_coded_address (OFFS_MSGSEND_FAST))); */
1845 #ifdef OFFS_MSGSEND_FAST
1846 umsg_fast_decl = add_builtin_function (TAG_MSGSEND_FAST,
1847 type, 0, NOT_BUILT_IN,
1849 TREE_NOTHROW (umsg_fast_decl) = 0;
1850 DECL_ATTRIBUTES (umsg_fast_decl)
1851 = tree_cons (get_identifier ("hard_coded_address"),
1852 build_int_cst (NULL_TREE, OFFS_MSGSEND_FAST),
1855 /* No direct dispatch available. */
1856 umsg_fast_decl = umsg_decl;
1859 /* id objc_msgSendSuper (struct objc_super *, SEL, ...); */
1860 /* id objc_msgSendSuper_stret (struct objc_super *, SEL, ...); */
1862 = build_varargs_function_type_list (objc_object_type,
1866 umsg_super_decl = add_builtin_function (TAG_MSGSENDSUPER,
1867 type, 0, NOT_BUILT_IN,
1869 umsg_super_stret_decl = add_builtin_function (TAG_MSGSENDSUPER_STRET,
1870 type, 0, NOT_BUILT_IN, 0,
1872 TREE_NOTHROW (umsg_super_decl) = 0;
1873 TREE_NOTHROW (umsg_super_stret_decl) = 0;
1877 /* GNU runtime messenger entry points. */
1879 /* typedef id (*IMP)(id, SEL, ...); */
1881 build_varargs_function_type_list (objc_object_type,
1885 tree IMP_type = build_pointer_type (ftype);
1887 /* IMP objc_msg_lookup (id, SEL); */
1888 type = build_function_type_list (IMP_type,
1892 umsg_decl = add_builtin_function (TAG_MSGSEND,
1893 type, 0, NOT_BUILT_IN,
1895 TREE_NOTHROW (umsg_decl) = 0;
1897 /* IMP objc_msg_lookup_super (struct objc_super *, SEL); */
1899 = build_function_type_list (IMP_type,
1903 umsg_super_decl = add_builtin_function (TAG_MSGSENDSUPER,
1904 type, 0, NOT_BUILT_IN,
1906 TREE_NOTHROW (umsg_super_decl) = 0;
1908 /* The following GNU runtime entry point is called to initialize
1911 __objc_exec_class (void *); */
1913 = build_function_type_list (void_type_node,
1916 execclass_decl = add_builtin_function (TAG_EXECCLASS,
1917 type, 0, NOT_BUILT_IN,
1921 /* id objc_getClass (const char *); */
1923 type = build_function_type_list (objc_object_type,
1924 const_string_type_node,
1928 = add_builtin_function (TAG_GETCLASS, type, 0, NOT_BUILT_IN,
1931 /* id objc_getMetaClass (const char *); */
1933 objc_get_meta_class_decl
1934 = add_builtin_function (TAG_GETMETACLASS, type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
1936 build_class_template ();
1937 build_super_template ();
1938 build_protocol_template ();
1939 build_category_template ();
1940 build_objc_exception_stuff ();
1942 if (flag_next_runtime)
1943 build_next_objc_exception_stuff ();
1945 /* static SEL _OBJC_SELECTOR_TABLE[]; */
1947 if (! flag_next_runtime)
1948 build_selector_table_decl ();
1950 /* Forward declare constant_string_id and constant_string_type. */
1951 if (!constant_string_class_name)
1952 constant_string_class_name = default_constant_string_class_name;
1954 constant_string_id = get_identifier (constant_string_class_name);
1955 objc_declare_class (tree_cons (NULL_TREE, constant_string_id, NULL_TREE));
1957 /* Pre-build the following entities - for speed/convenience. */
1958 self_id = get_identifier ("self");
1959 ucmd_id = get_identifier ("_cmd");
1961 /* Declare struct _objc_fast_enumeration_state { ... }; */
1962 build_fast_enumeration_state_template ();
1964 /* void objc_enumeration_mutation (id) */
1965 type = build_function_type (void_type_node,
1966 tree_cons (NULL_TREE, objc_object_type, NULL_TREE));
1967 objc_enumeration_mutation_decl
1968 = add_builtin_function (TAG_ENUMERATION_MUTATION, type, 0, NOT_BUILT_IN,
1970 TREE_NOTHROW (objc_enumeration_mutation_decl) = 0;
1973 pop_lang_context ();
1976 write_symbols = save_write_symbols;
1977 debug_hooks = save_hooks;
1980 /* Ensure that the ivar list for NSConstantString/NXConstantString
1981 (or whatever was specified via `-fconstant-string-class')
1982 contains fields at least as large as the following three, so that
1983 the runtime can stomp on them with confidence:
1985 struct STRING_OBJECT_CLASS_NAME
1989 unsigned int length;
1993 check_string_class_template (void)
1995 tree field_decl = objc_get_class_ivars (constant_string_id);
1997 #define AT_LEAST_AS_LARGE_AS(F, T) \
1998 (F && TREE_CODE (F) == FIELD_DECL \
1999 && (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (F))) \
2000 >= TREE_INT_CST_LOW (TYPE_SIZE (T))))
2002 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
2005 field_decl = DECL_CHAIN (field_decl);
2006 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
2009 field_decl = DECL_CHAIN (field_decl);
2010 return AT_LEAST_AS_LARGE_AS (field_decl, unsigned_type_node);
2012 #undef AT_LEAST_AS_LARGE_AS
2015 /* Avoid calling `check_string_class_template ()' more than once. */
2016 static GTY(()) int string_layout_checked;
2018 /* Construct an internal string layout to be used as a template for
2019 creating NSConstantString/NXConstantString instances. */
2022 objc_build_internal_const_str_type (void)
2024 tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);
2025 tree fields = build_decl (input_location,
2026 FIELD_DECL, NULL_TREE, ptr_type_node);
2027 tree field = build_decl (input_location,
2028 FIELD_DECL, NULL_TREE, ptr_type_node);
2030 DECL_CHAIN (field) = fields; fields = field;
2031 field = build_decl (input_location,
2032 FIELD_DECL, NULL_TREE, unsigned_type_node);
2033 DECL_CHAIN (field) = fields; fields = field;
2034 /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in
2036 finish_builtin_struct (type, "__builtin_ObjCString",
2042 /* Custom build_string which sets TREE_TYPE! */
2045 my_build_string (int len, const char *str)
2047 return fix_string_type (build_string (len, str));
2050 /* Build a string with contents STR and length LEN and convert it to a
2054 my_build_string_pointer (int len, const char *str)
2056 tree string = my_build_string (len, str);
2057 tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));
2058 return build1 (ADDR_EXPR, ptrtype, string);
2062 string_hash (const void *ptr)
2064 const_tree const str = ((const struct string_descriptor *)ptr)->literal;
2065 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);
2066 int i, len = TREE_STRING_LENGTH (str);
2069 for (i = 0; i < len; i++)
2070 h = ((h * 613) + p[i]);
2076 string_eq (const void *ptr1, const void *ptr2)
2078 const_tree const str1 = ((const struct string_descriptor *)ptr1)->literal;
2079 const_tree const str2 = ((const struct string_descriptor *)ptr2)->literal;
2080 int len1 = TREE_STRING_LENGTH (str1);
2082 return (len1 == TREE_STRING_LENGTH (str2)
2083 && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),
2087 /* Given a chain of STRING_CST's, build a static instance of
2088 NXConstantString which points at the concatenation of those
2089 strings. We place the string object in the __string_objects
2090 section of the __OBJC segment. The Objective-C runtime will
2091 initialize the isa pointers of the string objects to point at the
2092 NXConstantString class object. */
2095 objc_build_string_object (tree string)
2097 tree constructor, constant_string_class;
2100 struct string_descriptor *desc, key;
2103 /* Prep the string argument. */
2104 string = fix_string_type (string);
2105 TREE_SET_CODE (string, STRING_CST);
2106 length = TREE_STRING_LENGTH (string) - 1;
2108 /* Check whether the string class being used actually exists and has the
2109 correct ivar layout. */
2110 if (!string_layout_checked)
2112 string_layout_checked = -1;
2113 constant_string_class = lookup_interface (constant_string_id);
2114 internal_const_str_type = objc_build_internal_const_str_type ();
2116 if (!constant_string_class
2117 || !(constant_string_type
2118 = CLASS_STATIC_TEMPLATE (constant_string_class)))
2119 error ("cannot find interface declaration for %qE",
2120 constant_string_id);
2121 /* The NSConstantString/NXConstantString ivar layout is now known. */
2122 else if (!check_string_class_template ())
2123 error ("interface %qE does not have valid constant string layout",
2124 constant_string_id);
2125 /* For the NeXT runtime, we can generate a literal reference
2126 to the string class, don't need to run a constructor. */
2127 else if (flag_next_runtime && !setup_string_decl ())
2128 error ("cannot find reference tag for class %qE",
2129 constant_string_id);
2132 string_layout_checked = 1; /* Success! */
2133 add_class_reference (constant_string_id);
2137 if (string_layout_checked == -1)
2138 return error_mark_node;
2140 /* Perhaps we already constructed a constant string just like this one? */
2141 key.literal = string;
2142 loc = htab_find_slot (string_htab, &key, INSERT);
2143 desc = (struct string_descriptor *) *loc;
2148 VEC(constructor_elt,gc) *v = NULL;
2149 *loc = desc = ggc_alloc_string_descriptor ();
2150 desc->literal = string;
2152 /* GNU: (NXConstantString *) & ((__builtin_ObjCString) { NULL, string, length }) */
2153 /* NeXT: (NSConstantString *) & ((__builtin_ObjCString) { isa, string, length }) */
2154 fields = TYPE_FIELDS (internal_const_str_type);
2155 CONSTRUCTOR_APPEND_ELT (v, fields,
2157 ? build_unary_op (input_location,
2158 ADDR_EXPR, string_class_decl, 0)
2159 : build_int_cst (NULL_TREE, 0));
2160 fields = DECL_CHAIN (fields);
2161 CONSTRUCTOR_APPEND_ELT (v, fields,
2162 build_unary_op (input_location,
2163 ADDR_EXPR, string, 1));
2164 fields = DECL_CHAIN (fields);
2165 CONSTRUCTOR_APPEND_ELT (v, fields, build_int_cst (NULL_TREE, length));
2166 constructor = objc_build_constructor (internal_const_str_type, v);
2168 if (!flag_next_runtime)
2170 = objc_add_static_instance (constructor, constant_string_type);
2173 var = build_decl (input_location,
2174 CONST_DECL, NULL, TREE_TYPE (constructor));
2175 DECL_INITIAL (var) = constructor;
2176 TREE_STATIC (var) = 1;
2177 pushdecl_top_level (var);
2180 desc->constructor = constructor;
2183 addr = convert (build_pointer_type (constant_string_type),
2184 build_unary_op (input_location,
2185 ADDR_EXPR, desc->constructor, 1));
2190 /* Declare a static instance of CLASS_DECL initialized by CONSTRUCTOR. */
2192 static GTY(()) int num_static_inst;
2195 objc_add_static_instance (tree constructor, tree class_decl)
2200 /* Find the list of static instances for the CLASS_DECL. Create one if
2202 for (chain = &objc_static_instances;
2203 *chain && TREE_VALUE (*chain) != class_decl;
2204 chain = &TREE_CHAIN (*chain));
2207 *chain = tree_cons (NULL_TREE, class_decl, NULL_TREE);
2208 add_objc_string (OBJC_TYPE_NAME (class_decl), class_names);
2211 sprintf (buf, "_OBJC_INSTANCE_%d", num_static_inst++);
2212 decl = build_decl (input_location,
2213 VAR_DECL, get_identifier (buf), class_decl);
2214 TREE_STATIC (decl) = 1;
2215 DECL_ARTIFICIAL (decl) = 1;
2216 TREE_USED (decl) = 1;
2217 DECL_INITIAL (decl) = constructor;
2219 /* We may be writing something else just now.
2220 Postpone till end of input. */
2221 DECL_DEFER_OUTPUT (decl) = 1;
2222 pushdecl_top_level (decl);
2223 rest_of_decl_compilation (decl, 1, 0);
2225 /* Add the DECL to the head of this CLASS' list. */
2226 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE, decl, TREE_PURPOSE (*chain));
2231 /* Build a static constant CONSTRUCTOR
2232 with type TYPE and elements ELTS. */
2235 objc_build_constructor (tree type, VEC(constructor_elt,gc) *elts)
2237 tree constructor = build_constructor (type, elts);
2239 TREE_CONSTANT (constructor) = 1;
2240 TREE_STATIC (constructor) = 1;
2241 TREE_READONLY (constructor) = 1;
2244 /* Adjust for impedance mismatch. We should figure out how to build
2245 CONSTRUCTORs that consistently please both the C and C++ gods. */
2246 if (!VEC_index (constructor_elt, elts, 0)->index)
2247 TREE_TYPE (constructor) = init_list_type_node;
2253 /* Take care of defining and initializing _OBJC_SYMBOLS. */
2255 /* Predefine the following data type:
2263 void *defs[cls_def_cnt + cat_def_cnt];
2267 build_objc_symtab_template (void)
2269 tree fields, *chain = NULL;
2271 objc_symtab_template = objc_start_struct (get_identifier (UTAG_SYMTAB));
2273 /* long sel_ref_cnt; */
2274 fields = add_field_decl (long_integer_type_node, "sel_ref_cnt", &chain);
2277 add_field_decl (build_pointer_type (objc_selector_type), "refs", &chain);
2279 /* short cls_def_cnt; */
2280 add_field_decl (short_integer_type_node, "cls_def_cnt", &chain);
2282 /* short cat_def_cnt; */
2283 add_field_decl (short_integer_type_node, "cat_def_cnt", &chain);
2285 if (imp_count || cat_count || !flag_next_runtime)
2287 /* void *defs[imp_count + cat_count (+ 1)]; */
2288 /* NB: The index is one less than the size of the array. */
2289 int index = imp_count + cat_count + (flag_next_runtime ? -1: 0);
2290 tree array_type = build_sized_array_type (ptr_type_node, index + 1);
2291 add_field_decl (array_type, "defs", &chain);
2294 objc_finish_struct (objc_symtab_template, fields);
2297 /* Create the initial value for the `defs' field of _objc_symtab.
2298 This is a CONSTRUCTOR. */
2301 init_def_list (tree type)
2304 struct imp_entry *impent;
2305 VEC(constructor_elt,gc) *v = NULL;
2308 for (impent = imp_list; impent; impent = impent->next)
2310 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
2312 expr = build_unary_op (input_location,
2313 ADDR_EXPR, impent->class_decl, 0);
2314 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2319 for (impent = imp_list; impent; impent = impent->next)
2321 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2323 expr = build_unary_op (input_location,
2324 ADDR_EXPR, impent->class_decl, 0);
2325 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2329 if (!flag_next_runtime)
2331 /* statics = { ..., _OBJC_STATIC_INSTANCES, ... } */
2332 if (static_instances_decl)
2333 expr = build_unary_op (input_location,
2334 ADDR_EXPR, static_instances_decl, 0);
2336 expr = integer_zero_node;
2338 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2341 return objc_build_constructor (type, v);
2344 /* Construct the initial value for all of _objc_symtab. */
2347 init_objc_symtab (tree type)
2349 VEC(constructor_elt,gc) *v = NULL;
2351 /* sel_ref_cnt = { ..., 5, ... } */
2353 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
2354 build_int_cst (long_integer_type_node, 0));
2356 /* refs = { ..., _OBJC_SELECTOR_TABLE, ... } */
2358 if (flag_next_runtime || ! sel_ref_chain)
2359 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, convert (
2360 build_pointer_type (objc_selector_type),
2361 integer_zero_node));
2364 tree expr = build_unary_op (input_location, ADDR_EXPR,
2365 UOBJC_SELECTOR_TABLE_decl, 1);
2367 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
2368 convert (build_pointer_type (objc_selector_type),
2372 /* cls_def_cnt = { ..., 5, ... } */
2374 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
2375 build_int_cst (short_integer_type_node, imp_count));
2377 /* cat_def_cnt = { ..., 5, ... } */
2379 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
2380 build_int_cst (short_integer_type_node, cat_count));
2382 /* cls_def = { ..., { &Foo, &Bar, ...}, ... } */
2384 if (imp_count || cat_count || !flag_next_runtime)
2387 tree field = TYPE_FIELDS (type);
2388 field = DECL_CHAIN (DECL_CHAIN (DECL_CHAIN (DECL_CHAIN (field))));
2390 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, init_def_list (TREE_TYPE (field)));
2393 return objc_build_constructor (type, v);
2396 /* Generate forward declarations for metadata such as
2397 'OBJC_CLASS_...'. */
2400 build_metadata_decl (const char *name, tree type)
2404 /* struct TYPE NAME_<name>; */
2405 decl = start_var_decl (type, synth_id_with_class_suffix
2407 objc_implementation_context));
2412 /* Push forward-declarations of all the categories so that
2413 init_def_list can use them in a CONSTRUCTOR. */
2416 forward_declare_categories (void)
2418 struct imp_entry *impent;
2419 tree sav = objc_implementation_context;
2421 for (impent = imp_list; impent; impent = impent->next)
2423 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2425 /* Set an invisible arg to synth_id_with_class_suffix. */
2426 objc_implementation_context = impent->imp_context;
2427 /* extern struct objc_category _OBJC_CATEGORY_<name>; */
2428 impent->class_decl = build_metadata_decl ("_OBJC_CATEGORY",
2429 objc_category_template);
2432 objc_implementation_context = sav;
2435 /* Create the declaration of _OBJC_SYMBOLS, with type `struct _objc_symtab'
2436 and initialized appropriately. */
2439 generate_objc_symtab_decl (void)
2442 build_objc_symtab_template ();
2443 UOBJC_SYMBOLS_decl = start_var_decl (objc_symtab_template, "_OBJC_SYMBOLS");
2444 finish_var_decl (UOBJC_SYMBOLS_decl,
2445 init_objc_symtab (TREE_TYPE (UOBJC_SYMBOLS_decl)));
2449 init_module_descriptor (tree type)
2452 VEC(constructor_elt,gc) *v = NULL;
2454 /* version = { 1, ... } */
2456 expr = build_int_cst (long_integer_type_node, OBJC_VERSION);
2457 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2459 /* size = { ..., sizeof (struct _objc_module), ... } */
2461 expr = convert (long_integer_type_node,
2462 size_in_bytes (objc_module_template));
2463 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2465 /* Don't provide any file name for security reasons. */
2466 /* name = { ..., "", ... } */
2468 expr = add_objc_string (get_identifier (""), class_names);
2469 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2471 /* symtab = { ..., _OBJC_SYMBOLS, ... } */
2473 if (UOBJC_SYMBOLS_decl)
2474 expr = build_unary_op (input_location,
2475 ADDR_EXPR, UOBJC_SYMBOLS_decl, 0);
2477 expr = null_pointer_node;
2478 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2480 return objc_build_constructor (type, v);
2483 /* Write out the data structures to describe Objective C classes defined.
2485 struct _objc_module { ... } _OBJC_MODULE = { ... }; */
2488 build_module_descriptor (void)
2490 tree decls, *chain = NULL;
2493 push_lang_context (lang_name_c); /* extern "C" */
2496 objc_module_template = objc_start_struct (get_identifier (UTAG_MODULE));
2499 decls = add_field_decl (long_integer_type_node, "version", &chain);
2502 add_field_decl (long_integer_type_node, "size", &chain);
2505 add_field_decl (string_type_node, "name", &chain);
2507 /* struct _objc_symtab *symtab; */
2508 add_field_decl (build_pointer_type (xref_tag (RECORD_TYPE,
2509 get_identifier (UTAG_SYMTAB))),
2512 objc_finish_struct (objc_module_template, decls);
2514 /* Create an instance of "_objc_module". */
2515 UOBJC_MODULES_decl = start_var_decl (objc_module_template, "_OBJC_MODULES");
2516 /* This is the root of the metadata for defined classes and categories, it
2517 is referenced by the runtime and, therefore, needed. */
2518 DECL_PRESERVE_P (UOBJC_MODULES_decl) = 1;
2519 finish_var_decl (UOBJC_MODULES_decl,
2520 init_module_descriptor (TREE_TYPE (UOBJC_MODULES_decl)));
2523 pop_lang_context ();
2527 /* The GNU runtime requires us to provide a static initializer function
2530 static void __objc_gnu_init (void) {
2531 __objc_exec_class (&L_OBJC_MODULES);
2535 build_module_initializer_routine (void)
2540 push_lang_context (lang_name_c); /* extern "C" */
2543 objc_push_parm (build_decl (input_location,
2544 PARM_DECL, NULL_TREE, void_type_node));
2546 objc_start_function (get_identifier (TAG_GNUINIT),
2547 build_function_type_list (void_type_node, NULL_TREE),
2548 NULL_TREE, NULL_TREE);
2550 objc_start_function (get_identifier (TAG_GNUINIT),
2551 build_function_type_list (void_type_node, NULL_TREE),
2552 NULL_TREE, objc_get_parm_info (0));
2554 body = c_begin_compound_stmt (true);
2555 add_stmt (build_function_call
2560 build_unary_op (input_location, ADDR_EXPR,
2561 UOBJC_MODULES_decl, 0))));
2562 add_stmt (c_end_compound_stmt (input_location, body, true));
2564 TREE_PUBLIC (current_function_decl) = 0;
2567 /* For Objective-C++, we will need to call __objc_gnu_init
2568 from objc_generate_static_init_call() below. */
2569 DECL_STATIC_CONSTRUCTOR (current_function_decl) = 1;
2572 GNU_INIT_decl = current_function_decl;
2576 pop_lang_context ();
2581 /* Return 1 if the __objc_gnu_init function has been synthesized and needs
2582 to be called by the module initializer routine. */
2585 objc_static_init_needed_p (void)
2587 return (GNU_INIT_decl != NULL_TREE);
2590 /* Generate a call to the __objc_gnu_init initializer function. */
2593 objc_generate_static_init_call (tree ctors ATTRIBUTE_UNUSED)
2595 add_stmt (build_stmt (input_location, EXPR_STMT,
2596 build_function_call (input_location,
2597 GNU_INIT_decl, NULL_TREE)));
2601 #endif /* OBJCPLUS */
2603 /* Return the DECL of the string IDENT in the SECTION. */
2606 get_objc_string_decl (tree ident, enum string_section section)
2610 if (section == class_names)
2611 chain = class_names_chain;
2612 else if (section == meth_var_names)
2613 chain = meth_var_names_chain;
2614 else if (section == meth_var_types)
2615 chain = meth_var_types_chain;
2619 for (; chain != 0; chain = TREE_CHAIN (chain))
2620 if (TREE_VALUE (chain) == ident)
2621 return (TREE_PURPOSE (chain));
2627 /* Output references to all statically allocated objects. Return the DECL
2628 for the array built. */
2631 generate_static_references (void)
2633 tree expr = NULL_TREE;
2634 tree class_name, klass, decl;
2635 tree cl_chain, in_chain, type
2636 = build_array_type (build_pointer_type (void_type_node), NULL_TREE);
2637 int num_inst, num_class;
2639 VEC(constructor_elt,gc) *decls = NULL;
2641 if (flag_next_runtime)
2644 for (cl_chain = objc_static_instances, num_class = 0;
2645 cl_chain; cl_chain = TREE_CHAIN (cl_chain), num_class++)
2647 VEC(constructor_elt,gc) *v = NULL;
2649 for (num_inst = 0, in_chain = TREE_PURPOSE (cl_chain);
2650 in_chain; num_inst++, in_chain = TREE_CHAIN (in_chain));
2652 sprintf (buf, "_OBJC_STATIC_INSTANCES_%d", num_class);
2653 decl = start_var_decl (type, buf);
2655 /* Output {class_name, ...}. */
2656 klass = TREE_VALUE (cl_chain);
2657 class_name = get_objc_string_decl (OBJC_TYPE_NAME (klass), class_names);
2658 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
2659 build_unary_op (input_location,
2660 ADDR_EXPR, class_name, 1));
2662 /* Output {..., instance, ...}. */
2663 for (in_chain = TREE_PURPOSE (cl_chain);
2664 in_chain; in_chain = TREE_CHAIN (in_chain))
2666 expr = build_unary_op (input_location,
2667 ADDR_EXPR, TREE_VALUE (in_chain), 1);
2668 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2671 /* Output {..., NULL}. */
2672 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
2674 expr = objc_build_constructor (TREE_TYPE (decl), v);
2675 finish_var_decl (decl, expr);
2676 CONSTRUCTOR_APPEND_ELT (decls, NULL_TREE,
2677 build_unary_op (input_location,
2678 ADDR_EXPR, decl, 1));
2681 CONSTRUCTOR_APPEND_ELT (decls, NULL_TREE, build_int_cst (NULL_TREE, 0));
2682 expr = objc_build_constructor (type, decls);
2683 static_instances_decl = start_var_decl (type, "_OBJC_STATIC_INSTANCES");
2684 finish_var_decl (static_instances_decl, expr);
2687 static GTY(()) int selector_reference_idx;
2690 build_selector_reference_decl (void)
2695 sprintf (buf, "_OBJC_SELECTOR_REFERENCES_%d", selector_reference_idx++);
2696 decl = start_var_decl (objc_selector_type, buf);
2702 build_selector_table_decl (void)
2706 if (flag_typed_selectors)
2708 build_selector_template ();
2709 temp = build_array_type (objc_selector_template, NULL_TREE);
2712 temp = build_array_type (objc_selector_type, NULL_TREE);
2714 UOBJC_SELECTOR_TABLE_decl = start_var_decl (temp, "_OBJC_SELECTOR_TABLE");
2717 /* Just a handy wrapper for add_objc_string. */
2720 build_selector (tree ident)
2722 return convert (objc_selector_type,
2723 add_objc_string (ident, meth_var_names));
2726 /* Used only by build_*_selector_translation_table (). */
2728 diagnose_missing_method (tree meth, location_t here)
2732 for (method_chain = meth_var_names_chain;
2734 method_chain = TREE_CHAIN (method_chain))
2736 if (TREE_VALUE (method_chain) == meth)
2744 warning_at (here, 0, "creating selector for nonexistent method %qE",
2749 build_next_selector_translation_table (void)
2752 for (chain = sel_ref_chain; chain; chain = TREE_CHAIN (chain))
2755 tree decl = TREE_PURPOSE (chain);
2756 if (warn_selector && objc_implementation_context)
2760 loc = DECL_SOURCE_LOCATION (decl);
2762 loc = input_location;
2763 diagnose_missing_method (TREE_VALUE (chain), loc);
2766 expr = build_selector (TREE_VALUE (chain));
2770 /* Entries of this form are used for references to methods.
2771 The runtime re-writes these on start-up, but the compiler can't see
2772 that and optimizes it away unless we force it. */
2773 DECL_PRESERVE_P (decl) = 1;
2774 finish_var_decl (decl, expr);
2780 build_gnu_selector_translation_table (void)
2784 tree decl = NULL_TREE;*/
2785 VEC(constructor_elt,gc) *inits = NULL;
2787 for (chain = sel_ref_chain; chain; chain = TREE_CHAIN (chain))
2791 if (warn_selector && objc_implementation_context)
2792 diagnose_missing_method (TREE_VALUE (chain), input_location);
2794 expr = build_selector (TREE_VALUE (chain));
2795 /* add one for the '\0' character
2796 offset += IDENTIFIER_LENGTH (TREE_VALUE (chain)) + 1;*/
2799 if (flag_typed_selectors)
2801 VEC(constructor_elt,gc) *v = NULL;
2802 tree encoding = get_proto_encoding (TREE_PURPOSE (chain));
2803 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
2804 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, encoding);
2805 expr = objc_build_constructor (objc_selector_template, v);
2808 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, expr);
2810 } /* each element in the chain */
2813 /* Cause the selector table (previously forward-declared)
2814 to be actually output. */
2817 if (flag_typed_selectors)
2819 VEC(constructor_elt,gc) *v = NULL;
2820 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, integer_zero_node);
2821 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, integer_zero_node);
2822 expr = objc_build_constructor (objc_selector_template, v);
2825 expr = integer_zero_node;
2827 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, expr);
2828 expr = objc_build_constructor (TREE_TYPE (UOBJC_SELECTOR_TABLE_decl),
2830 finish_var_decl (UOBJC_SELECTOR_TABLE_decl, expr);
2835 get_proto_encoding (tree proto)
2840 if (! METHOD_ENCODING (proto))
2842 encoding = encode_method_prototype (proto);
2843 METHOD_ENCODING (proto) = encoding;
2846 encoding = METHOD_ENCODING (proto);
2848 return add_objc_string (encoding, meth_var_types);
2851 return build_int_cst (NULL_TREE, 0);
2854 /* sel_ref_chain is a list whose "value" fields will be instances of
2855 identifier_node that represent the selector. LOC is the location of
2859 build_typed_selector_reference (location_t loc, tree ident, tree prototype)
2861 tree *chain = &sel_ref_chain;
2867 if (TREE_PURPOSE (*chain) == prototype && TREE_VALUE (*chain) == ident)
2868 goto return_at_index;
2871 chain = &TREE_CHAIN (*chain);
2874 *chain = tree_cons (prototype, ident, NULL_TREE);
2877 expr = build_unary_op (loc, ADDR_EXPR,
2878 build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2879 build_int_cst (NULL_TREE, index)),
2881 return convert (objc_selector_type, expr);
2885 build_selector_reference (location_t loc, tree ident)
2887 tree *chain = &sel_ref_chain;
2893 if (TREE_VALUE (*chain) == ident)
2894 return (flag_next_runtime
2895 ? TREE_PURPOSE (*chain)
2896 : build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2897 build_int_cst (NULL_TREE, index)));
2900 chain = &TREE_CHAIN (*chain);
2903 expr = (flag_next_runtime ? build_selector_reference_decl (): NULL_TREE);
2905 *chain = tree_cons (expr, ident, NULL_TREE);
2907 return (flag_next_runtime
2909 : build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2910 build_int_cst (NULL_TREE, index)));
2913 static GTY(()) int class_reference_idx;
2916 build_class_reference_decl (void)
2921 sprintf (buf, "_OBJC_CLASS_REFERENCES_%d", class_reference_idx++);
2922 decl = start_var_decl (objc_class_type, buf);
2927 /* Create a class reference, but don't create a variable to reference
2931 add_class_reference (tree ident)
2935 if ((chain = cls_ref_chain))
2940 if (ident == TREE_VALUE (chain))
2944 chain = TREE_CHAIN (chain);
2948 /* Append to the end of the list */
2949 TREE_CHAIN (tail) = tree_cons (NULL_TREE, ident, NULL_TREE);
2952 cls_ref_chain = tree_cons (NULL_TREE, ident, NULL_TREE);
2955 /* Get a class reference, creating it if necessary. Also create the
2956 reference variable. */
2959 objc_get_class_reference (tree ident)
2961 tree orig_ident = (DECL_P (ident)
2964 ? OBJC_TYPE_NAME (ident)
2966 bool local_scope = false;
2969 if (processing_template_decl)
2970 /* Must wait until template instantiation time. */
2971 return build_min_nt (CLASS_REFERENCE_EXPR, ident);
2974 if (TREE_CODE (ident) == TYPE_DECL)
2975 ident = (DECL_ORIGINAL_TYPE (ident)
2976 ? DECL_ORIGINAL_TYPE (ident)
2977 : TREE_TYPE (ident));
2981 && CP_TYPE_CONTEXT (ident) != global_namespace)
2985 if (local_scope || !(ident = objc_is_class_name (ident)))
2987 error ("%qE is not an Objective-C class name or alias",
2989 return error_mark_node;
2992 if (flag_next_runtime && !flag_zero_link)
2997 for (chain = &cls_ref_chain; *chain; chain = &TREE_CHAIN (*chain))
2998 if (TREE_VALUE (*chain) == ident)
3000 if (! TREE_PURPOSE (*chain))
3001 TREE_PURPOSE (*chain) = build_class_reference_decl ();
3003 return TREE_PURPOSE (*chain);
3006 decl = build_class_reference_decl ();
3007 *chain = tree_cons (decl, ident, NULL_TREE);
3014 add_class_reference (ident);
3016 params = build_tree_list (NULL_TREE,
3017 my_build_string_pointer
3018 (IDENTIFIER_LENGTH (ident) + 1,
3019 IDENTIFIER_POINTER (ident)));
3021 assemble_external (objc_get_class_decl);
3022 return build_function_call (input_location, objc_get_class_decl, params);
3026 /* For each string section we have a chain which maps identifier nodes
3027 to decls for the strings. */
3029 static GTY(()) int class_names_idx;
3030 static GTY(()) int meth_var_names_idx;
3031 static GTY(()) int meth_var_types_idx;
3034 add_objc_string (tree ident, enum string_section section)
3036 tree *chain, decl, type, string_expr;
3040 if (section == class_names)
3042 chain = &class_names_chain;
3043 sprintf (buf, "_OBJC_CLASS_NAME_%d", class_names_idx++);
3045 else if (section == meth_var_names)
3047 chain = &meth_var_names_chain;
3048 sprintf (buf, "_OBJC_METH_VAR_NAME_%d", meth_var_names_idx++);
3050 else if (section == meth_var_types)
3052 chain = &meth_var_types_chain;
3053 sprintf (buf, "_OBJC_METH_VAR_TYPE_%d", meth_var_types_idx++);
3060 if (TREE_VALUE (*chain) == ident)
3061 return convert (string_type_node,
3062 build_unary_op (input_location,
3063 ADDR_EXPR, TREE_PURPOSE (*chain), 1));
3065 chain = &TREE_CHAIN (*chain);
3068 type = build_sized_array_type (char_type_node, IDENTIFIER_LENGTH (ident) + 1);
3069 decl = start_var_decl (type, buf);
3070 string_expr = my_build_string (IDENTIFIER_LENGTH (ident) + 1,
3071 IDENTIFIER_POINTER (ident));
3072 TREE_CONSTANT (decl) = 1;
3073 finish_var_decl (decl, string_expr);
3075 *chain = tree_cons (decl, ident, NULL_TREE);
3077 return convert (string_type_node, build_unary_op (input_location,
3078 ADDR_EXPR, decl, 1));
3082 objc_declare_alias (tree alias_ident, tree class_ident)
3084 tree underlying_class;
3087 if (current_namespace != global_namespace) {
3088 error ("Objective-C declarations may only appear in global scope");
3090 #endif /* OBJCPLUS */
3092 if (!(underlying_class = objc_is_class_name (class_ident)))
3093 warning (0, "cannot find class %qE", class_ident);
3094 else if (objc_is_class_name (alias_ident))
3095 warning (0, "class %qE already exists", alias_ident);
3098 /* Implement @compatibility_alias as a typedef. */
3100 push_lang_context (lang_name_c); /* extern "C" */
3102 lang_hooks.decls.pushdecl (build_decl
3106 xref_tag (RECORD_TYPE, underlying_class)));
3108 pop_lang_context ();
3110 alias_chain = tree_cons (underlying_class, alias_ident, alias_chain);
3115 objc_declare_class (tree ident_list)
3119 if (current_namespace != global_namespace) {
3120 error ("Objective-C declarations may only appear in global scope");
3122 #endif /* OBJCPLUS */
3124 for (list = ident_list; list; list = TREE_CHAIN (list))
3126 tree ident = TREE_VALUE (list);
3128 if (! objc_is_class_name (ident))
3130 tree record = lookup_name (ident), type = record;
3134 if (TREE_CODE (record) == TYPE_DECL)
3135 type = DECL_ORIGINAL_TYPE (record) ?
3136 DECL_ORIGINAL_TYPE (record) :
3139 if (!TYPE_HAS_OBJC_INFO (type)
3140 || !TYPE_OBJC_INTERFACE (type))
3142 error ("%qE redeclared as different kind of symbol",
3144 error ("previous declaration of %q+D",
3149 record = xref_tag (RECORD_TYPE, ident);
3150 INIT_TYPE_OBJC_INFO (record);
3151 TYPE_OBJC_INTERFACE (record) = ident;
3152 class_chain = tree_cons (NULL_TREE, ident, class_chain);
3158 objc_is_class_name (tree ident)
3162 if (ident && TREE_CODE (ident) == IDENTIFIER_NODE
3163 && identifier_global_value (ident))
3164 ident = identifier_global_value (ident);
3165 while (ident && TREE_CODE (ident) == TYPE_DECL && DECL_ORIGINAL_TYPE (ident))
3166 ident = OBJC_TYPE_NAME (DECL_ORIGINAL_TYPE (ident));
3168 if (ident && TREE_CODE (ident) == RECORD_TYPE)
3169 ident = OBJC_TYPE_NAME (ident);
3171 if (ident && TREE_CODE (ident) == TYPE_DECL)
3172 ident = DECL_NAME (ident);
3174 if (!ident || TREE_CODE (ident) != IDENTIFIER_NODE)
3177 if (lookup_interface (ident))
3180 for (chain = class_chain; chain; chain = TREE_CHAIN (chain))
3182 if (ident == TREE_VALUE (chain))
3186 for (chain = alias_chain; chain; chain = TREE_CHAIN (chain))
3188 if (ident == TREE_VALUE (chain))
3189 return TREE_PURPOSE (chain);
3195 /* Check whether TYPE is either 'id' or 'Class'. */
3198 objc_is_id (tree type)
3200 if (type && TREE_CODE (type) == IDENTIFIER_NODE
3201 && identifier_global_value (type))
3202 type = identifier_global_value (type);
3204 if (type && TREE_CODE (type) == TYPE_DECL)
3205 type = TREE_TYPE (type);
3207 /* NB: This function may be called before the ObjC front-end has
3208 been initialized, in which case OBJC_OBJECT_TYPE will (still) be NULL. */
3209 return (objc_object_type && type
3210 && (IS_ID (type) || IS_CLASS (type) || IS_SUPER (type))
3215 /* Check whether TYPE is either 'id', 'Class', or a pointer to an ObjC
3216 class instance. This is needed by other parts of the compiler to
3217 handle ObjC types gracefully. */
3220 objc_is_object_ptr (tree type)
3224 type = TYPE_MAIN_VARIANT (type);
3225 if (!POINTER_TYPE_P (type))
3228 ret = objc_is_id (type);
3230 ret = objc_is_class_name (TREE_TYPE (type));
3236 objc_is_gcable_type (tree type, int or_strong_p)
3242 if (objc_is_id (TYPE_MAIN_VARIANT (type)))
3244 if (or_strong_p && lookup_attribute ("objc_gc", TYPE_ATTRIBUTES (type)))
3246 if (TREE_CODE (type) != POINTER_TYPE && TREE_CODE (type) != INDIRECT_REF)
3248 type = TREE_TYPE (type);
3249 if (TREE_CODE (type) != RECORD_TYPE)
3251 name = TYPE_NAME (type);
3252 return (objc_is_class_name (name) != NULL_TREE);
3256 objc_substitute_decl (tree expr, tree oldexpr, tree newexpr)
3258 if (expr == oldexpr)
3261 switch (TREE_CODE (expr))
3264 return objc_build_component_ref
3265 (objc_substitute_decl (TREE_OPERAND (expr, 0),
3268 DECL_NAME (TREE_OPERAND (expr, 1)));
3270 return build_array_ref (input_location,
3271 objc_substitute_decl (TREE_OPERAND (expr, 0),
3274 TREE_OPERAND (expr, 1));
3276 return build_indirect_ref (input_location,
3277 objc_substitute_decl (TREE_OPERAND (expr, 0),
3279 newexpr), RO_ARROW);
3286 objc_build_ivar_assignment (tree outervar, tree lhs, tree rhs)
3289 /* The LHS parameter contains the expression 'outervar->memberspec';
3290 we need to transform it into '&((typeof(outervar) *) 0)->memberspec',
3291 where memberspec may be arbitrarily complex (e.g., 'g->f.d[2].g[3]').
3294 = objc_substitute_decl
3295 (lhs, outervar, convert (TREE_TYPE (outervar), integer_zero_node));
3297 = (flag_objc_direct_dispatch
3298 ? objc_assign_ivar_fast_decl
3299 : objc_assign_ivar_decl);
3301 offs = convert (integer_type_node, build_unary_op (input_location,
3302 ADDR_EXPR, offs, 0));
3304 func_params = tree_cons (NULL_TREE,
3305 convert (objc_object_type, rhs),
3306 tree_cons (NULL_TREE, convert (objc_object_type, outervar),
3307 tree_cons (NULL_TREE, offs,
3310 assemble_external (func);
3311 return build_function_call (input_location, func, func_params);
3315 objc_build_global_assignment (tree lhs, tree rhs)
3317 tree func_params = tree_cons (NULL_TREE,
3318 convert (objc_object_type, rhs),
3319 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3320 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3323 assemble_external (objc_assign_global_decl);
3324 return build_function_call (input_location,
3325 objc_assign_global_decl, func_params);
3329 objc_build_strong_cast_assignment (tree lhs, tree rhs)
3331 tree func_params = tree_cons (NULL_TREE,
3332 convert (objc_object_type, rhs),
3333 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3334 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3337 assemble_external (objc_assign_strong_cast_decl);
3338 return build_function_call (input_location,
3339 objc_assign_strong_cast_decl, func_params);
3343 objc_is_gcable_p (tree expr)
3345 return (TREE_CODE (expr) == COMPONENT_REF
3346 ? objc_is_gcable_p (TREE_OPERAND (expr, 1))
3347 : TREE_CODE (expr) == ARRAY_REF
3348 ? (objc_is_gcable_p (TREE_TYPE (expr))
3349 || objc_is_gcable_p (TREE_OPERAND (expr, 0)))
3350 : TREE_CODE (expr) == ARRAY_TYPE
3351 ? objc_is_gcable_p (TREE_TYPE (expr))
3353 ? objc_is_gcable_type (expr, 1)
3354 : (objc_is_gcable_p (TREE_TYPE (expr))
3356 && lookup_attribute ("objc_gc", DECL_ATTRIBUTES (expr)))));
3360 objc_is_ivar_reference_p (tree expr)
3362 return (TREE_CODE (expr) == ARRAY_REF
3363 ? objc_is_ivar_reference_p (TREE_OPERAND (expr, 0))
3364 : TREE_CODE (expr) == COMPONENT_REF
3365 ? TREE_CODE (TREE_OPERAND (expr, 1)) == FIELD_DECL
3370 objc_is_global_reference_p (tree expr)
3372 return (TREE_CODE (expr) == INDIRECT_REF || TREE_CODE (expr) == PLUS_EXPR
3373 ? objc_is_global_reference_p (TREE_OPERAND (expr, 0))
3375 ? (DECL_FILE_SCOPE_P (expr) || TREE_STATIC (expr))
3380 objc_generate_write_barrier (tree lhs, enum tree_code modifycode, tree rhs)
3382 tree result = NULL_TREE, outer;
3383 int strong_cast_p = 0, outer_gc_p = 0, indirect_p = 0;
3385 /* See if we have any lhs casts, and strip them out. NB: The lvalue casts
3386 will have been transformed to the form '*(type *)&expr'. */
3387 if (TREE_CODE (lhs) == INDIRECT_REF)
3389 outer = TREE_OPERAND (lhs, 0);
3391 while (!strong_cast_p
3392 && (CONVERT_EXPR_P (outer)
3393 || TREE_CODE (outer) == NON_LVALUE_EXPR))
3395 tree lhstype = TREE_TYPE (outer);
3397 /* Descend down the cast chain, and record the first objc_gc
3399 if (POINTER_TYPE_P (lhstype))
3402 = lookup_attribute ("objc_gc",
3403 TYPE_ATTRIBUTES (TREE_TYPE (lhstype)));
3409 outer = TREE_OPERAND (outer, 0);
3413 /* If we have a __strong cast, it trumps all else. */
3416 if (modifycode != NOP_EXPR)
3417 goto invalid_pointer_arithmetic;
3419 if (warn_assign_intercept)
3420 warning (0, "strong-cast assignment has been intercepted");
3422 result = objc_build_strong_cast_assignment (lhs, rhs);
3427 /* the lhs must be of a suitable type, regardless of its underlying
3429 if (!objc_is_gcable_p (lhs))
3435 && (TREE_CODE (outer) == COMPONENT_REF
3436 || TREE_CODE (outer) == ARRAY_REF))
3437 outer = TREE_OPERAND (outer, 0);
3439 if (TREE_CODE (outer) == INDIRECT_REF)
3441 outer = TREE_OPERAND (outer, 0);
3445 outer_gc_p = objc_is_gcable_p (outer);
3447 /* Handle ivar assignments. */
3448 if (objc_is_ivar_reference_p (lhs))
3450 /* if the struct to the left of the ivar is not an Objective-C object (__strong
3451 doesn't cut it here), the best we can do here is suggest a cast. */
3452 if (!objc_is_gcable_type (TREE_TYPE (outer), 0))
3454 /* We may still be able to use the global write barrier... */
3455 if (!indirect_p && objc_is_global_reference_p (outer))
3456 goto global_reference;
3459 if (modifycode == NOP_EXPR)
3461 if (warn_assign_intercept)
3462 warning (0, "strong-cast may possibly be needed");
3468 if (modifycode != NOP_EXPR)
3469 goto invalid_pointer_arithmetic;
3471 if (warn_assign_intercept)
3472 warning (0, "instance variable assignment has been intercepted");
3474 result = objc_build_ivar_assignment (outer, lhs, rhs);
3479 /* Likewise, intercept assignment to global/static variables if their type is
3481 if (objc_is_global_reference_p (outer))
3487 if (modifycode != NOP_EXPR)
3489 invalid_pointer_arithmetic:
3491 warning (0, "pointer arithmetic for garbage-collected objects not allowed");
3496 if (warn_assign_intercept)
3497 warning (0, "global/static variable assignment has been intercepted");
3499 result = objc_build_global_assignment (lhs, rhs);
3502 /* In all other cases, fall back to the normal mechanism. */
3507 struct GTY(()) interface_tuple {
3512 static GTY ((param_is (struct interface_tuple))) htab_t interface_htab;
3515 hash_interface (const void *p)
3517 const struct interface_tuple *d = (const struct interface_tuple *) p;
3518 return IDENTIFIER_HASH_VALUE (d->id);
3522 eq_interface (const void *p1, const void *p2)
3524 const struct interface_tuple *d = (const struct interface_tuple *) p1;
3529 lookup_interface (tree ident)
3532 if (ident && TREE_CODE (ident) == TYPE_DECL)
3533 ident = DECL_NAME (ident);
3536 if (ident == NULL_TREE || TREE_CODE (ident) != IDENTIFIER_NODE)
3540 struct interface_tuple **slot;
3545 slot = (struct interface_tuple **)
3546 htab_find_slot_with_hash (interface_htab, ident,
3547 IDENTIFIER_HASH_VALUE (ident),
3550 i = (*slot)->class_name;
3556 /* Implement @defs (<classname>) within struct bodies. */
3559 objc_get_class_ivars (tree class_name)
3561 tree interface = lookup_interface (class_name);
3564 return get_class_ivars (interface, true);
3566 error ("cannot find interface declaration for %qE",
3569 return error_mark_node;
3572 /* Called when checking the variables in a struct. If we are not
3573 doing the ivars list inside an @interface context, then returns
3574 fieldlist unchanged. Else, returns the list of class ivars.
3577 objc_get_interface_ivars (tree fieldlist)
3579 if (!objc_collecting_ivars || !objc_interface_context
3580 || TREE_CODE (objc_interface_context) != CLASS_INTERFACE_TYPE
3581 || CLASS_SUPER_NAME (objc_interface_context) == NULL_TREE)
3584 return get_class_ivars (objc_interface_context, true);
3587 /* Used by: build_private_template, continue_class,
3588 and for @defs constructs. */
3591 get_class_ivars (tree interface, bool inherited)
3593 tree ivar_chain = copy_list (CLASS_RAW_IVARS (interface));
3595 /* Both CLASS_RAW_IVARS and CLASS_IVARS contain a list of ivars declared
3596 by the current class (i.e., they do not include super-class ivars).
3597 However, the CLASS_IVARS list will be side-effected by a call to
3598 finish_struct(), which will fill in field offsets. */
3599 if (!CLASS_IVARS (interface))
3600 CLASS_IVARS (interface) = ivar_chain;
3605 while (CLASS_SUPER_NAME (interface))
3607 /* Prepend super-class ivars. */
3608 interface = lookup_interface (CLASS_SUPER_NAME (interface));
3609 ivar_chain = chainon (copy_list (CLASS_RAW_IVARS (interface)),
3616 /* Create a temporary variable of type 'type'. If 'name' is set, uses
3617 the specified name, else use no name. Returns the declaration of
3618 the type. The 'name' is mostly useful for debugging.
3621 objc_create_temporary_var (tree type, const char *name)
3627 decl = build_decl (input_location,
3628 VAR_DECL, get_identifier (name), type);
3632 decl = build_decl (input_location,
3633 VAR_DECL, NULL_TREE, type);
3635 TREE_USED (decl) = 1;
3636 DECL_ARTIFICIAL (decl) = 1;
3637 DECL_IGNORED_P (decl) = 1;
3638 DECL_CONTEXT (decl) = current_function_decl;
3643 /* Exception handling constructs. We begin by having the parser do most
3644 of the work and passing us blocks. What we do next depends on whether
3645 we're doing "native" exception handling or legacy Darwin setjmp exceptions.
3646 We abstract all of this in a handful of appropriately named routines. */
3648 /* Stack of open try blocks. */
3650 struct objc_try_context
3652 struct objc_try_context *outer;
3654 /* Statements (or statement lists) as processed by the parser. */
3658 /* Some file position locations. */
3659 location_t try_locus;
3660 location_t end_try_locus;
3661 location_t end_catch_locus;
3662 location_t finally_locus;
3663 location_t end_finally_locus;
3665 /* A STATEMENT_LIST of CATCH_EXPRs, appropriate for sticking into op1
3666 of a TRY_CATCH_EXPR. Even when doing Darwin setjmp. */
3669 /* The CATCH_EXPR of an open @catch clause. */
3672 /* The VAR_DECL holding the Darwin equivalent of __builtin_eh_pointer. */
3678 static struct objc_try_context *cur_try_context;
3680 static GTY(()) tree objc_eh_personality_decl;
3682 /* This hook, called via lang_eh_runtime_type, generates a runtime object
3683 that represents TYPE. For Objective-C, this is just the class name. */
3684 /* ??? Isn't there a class object or some such? Is it easy to get? */
3688 objc_eh_runtime_type (tree type)
3690 return add_objc_string (OBJC_TYPE_NAME (TREE_TYPE (type)), class_names);
3694 objc_eh_personality (void)
3696 if (!flag_objc_sjlj_exceptions
3697 && !objc_eh_personality_decl)
3698 objc_eh_personality_decl
3699 = build_personality_function (targetm.except_unwind_info () == UI_SJLJ
3700 ? "__gnu_objc_personality_sj0"
3701 : "__gnu_objc_personality_v0");
3703 return objc_eh_personality_decl;
3707 /* Build __builtin_eh_pointer, or the moral equivalent. In the case
3708 of Darwin, we'll arrange for it to be initialized (and associated
3709 with a binding) later. */
3712 objc_build_exc_ptr (void)
3714 if (flag_objc_sjlj_exceptions)
3716 tree var = cur_try_context->caught_decl;
3719 var = objc_create_temporary_var (objc_object_type, NULL);
3720 cur_try_context->caught_decl = var;
3727 t = built_in_decls[BUILT_IN_EH_POINTER];
3728 t = build_call_expr (t, 1, integer_zero_node);
3729 return fold_convert (objc_object_type, t);
3733 /* Build "objc_exception_try_exit(&_stack)". */
3736 next_sjlj_build_try_exit (void)
3739 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3740 t = tree_cons (NULL, t, NULL);
3741 t = build_function_call (input_location,
3742 objc_exception_try_exit_decl, t);
3747 objc_exception_try_enter (&_stack);
3748 if (_setjmp(&_stack.buf))
3752 Return the COND_EXPR. Note that the THEN and ELSE fields are left
3753 empty, ready for the caller to fill them in. */
3756 next_sjlj_build_enter_and_setjmp (void)
3758 tree t, enter, sj, cond;
3760 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3761 t = tree_cons (NULL, t, NULL);
3762 enter = build_function_call (input_location,
3763 objc_exception_try_enter_decl, t);
3765 t = objc_build_component_ref (cur_try_context->stack_decl,
3766 get_identifier ("buf"));
3767 t = build_fold_addr_expr_loc (input_location, t);
3769 /* Convert _setjmp argument to type that is expected. */
3770 if (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl)))
3771 t = convert (TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl))), t);
3773 t = convert (ptr_type_node, t);
3775 t = convert (ptr_type_node, t);
3777 t = tree_cons (NULL, t, NULL);
3778 sj = build_function_call (input_location,
3779 objc_setjmp_decl, t);
3781 cond = build2 (COMPOUND_EXPR, TREE_TYPE (sj), enter, sj);
3782 cond = c_common_truthvalue_conversion (input_location, cond);
3784 return build3 (COND_EXPR, void_type_node, cond, NULL, NULL);
3789 DECL = objc_exception_extract(&_stack); */
3792 next_sjlj_build_exc_extract (tree decl)
3796 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3797 t = tree_cons (NULL, t, NULL);
3798 t = build_function_call (input_location,
3799 objc_exception_extract_decl, t);
3800 t = convert (TREE_TYPE (decl), t);
3801 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
3807 if (objc_exception_match(obj_get_class(TYPE), _caught)
3814 objc_exception_try_exit(&_stack);
3816 from the sequence of CATCH_EXPRs in the current try context. */
3819 next_sjlj_build_catch_list (void)
3821 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
3823 tree *last = &catch_seq;
3824 bool saw_id = false;
3826 for (; !tsi_end_p (i); tsi_next (&i))
3828 tree stmt = tsi_stmt (i);
3829 tree type = CATCH_TYPES (stmt);
3830 tree body = CATCH_BODY (stmt);
3842 if (type == error_mark_node)
3843 cond = error_mark_node;
3846 args = tree_cons (NULL, cur_try_context->caught_decl, NULL);
3847 t = objc_get_class_reference (OBJC_TYPE_NAME (TREE_TYPE (type)));
3848 args = tree_cons (NULL, t, args);
3849 t = build_function_call (input_location,
3850 objc_exception_match_decl, args);
3851 cond = c_common_truthvalue_conversion (input_location, t);
3853 t = build3 (COND_EXPR, void_type_node, cond, body, NULL);
3854 SET_EXPR_LOCATION (t, EXPR_LOCATION (stmt));
3857 last = &COND_EXPR_ELSE (t);
3863 t = build2 (MODIFY_EXPR, void_type_node, cur_try_context->rethrow_decl,
3864 cur_try_context->caught_decl);
3865 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3866 append_to_statement_list (t, last);
3868 t = next_sjlj_build_try_exit ();
3869 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3870 append_to_statement_list (t, last);
3876 /* Build a complete @try-@catch-@finally block for legacy Darwin setjmp
3877 exception handling. We aim to build:
3880 struct _objc_exception_data _stack;
3884 objc_exception_try_enter (&_stack);
3885 if (_setjmp(&_stack.buf))
3887 id _caught = objc_exception_extract(&_stack);
3888 objc_exception_try_enter (&_stack);
3889 if (_setjmp(&_stack.buf))
3890 _rethrow = objc_exception_extract(&_stack);
3900 objc_exception_try_exit(&_stack);
3903 objc_exception_throw(_rethrow);
3907 If CATCH-LIST is empty, we can omit all of the block containing
3908 "_caught" except for the setting of _rethrow. Note the use of
3909 a real TRY_FINALLY_EXPR here, which is not involved in EH per-se,
3910 but handles goto and other exits from the block. */
3913 next_sjlj_build_try_catch_finally (void)
3915 tree rethrow_decl, stack_decl, t;
3916 tree catch_seq, try_fin, bind;
3918 /* Create the declarations involved. */
3919 t = xref_tag (RECORD_TYPE, get_identifier (UTAG_EXCDATA));
3920 stack_decl = objc_create_temporary_var (t, NULL);
3921 cur_try_context->stack_decl = stack_decl;
3923 rethrow_decl = objc_create_temporary_var (objc_object_type, NULL);
3924 cur_try_context->rethrow_decl = rethrow_decl;
3925 TREE_CHAIN (rethrow_decl) = stack_decl;
3927 /* Build the outermost variable binding level. */
3928 bind = build3 (BIND_EXPR, void_type_node, rethrow_decl, NULL, NULL);
3929 SET_EXPR_LOCATION (bind, cur_try_context->try_locus);
3930 TREE_SIDE_EFFECTS (bind) = 1;
3932 /* Initialize rethrow_decl. */
3933 t = build2 (MODIFY_EXPR, void_type_node, rethrow_decl,
3934 convert (objc_object_type, null_pointer_node));
3935 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3936 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
3938 /* Build the outermost TRY_FINALLY_EXPR. */
3939 try_fin = build2 (TRY_FINALLY_EXPR, void_type_node, NULL, NULL);
3940 SET_EXPR_LOCATION (try_fin, cur_try_context->try_locus);
3941 TREE_SIDE_EFFECTS (try_fin) = 1;
3942 append_to_statement_list (try_fin, &BIND_EXPR_BODY (bind));
3944 /* Create the complete catch sequence. */
3945 if (cur_try_context->catch_list)
3947 tree caught_decl = objc_build_exc_ptr ();
3948 catch_seq = build_stmt (input_location, BIND_EXPR, caught_decl, NULL, NULL);
3949 TREE_SIDE_EFFECTS (catch_seq) = 1;
3951 t = next_sjlj_build_exc_extract (caught_decl);
3952 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3954 t = next_sjlj_build_enter_and_setjmp ();
3955 COND_EXPR_THEN (t) = next_sjlj_build_exc_extract (rethrow_decl);
3956 COND_EXPR_ELSE (t) = next_sjlj_build_catch_list ();
3957 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3960 catch_seq = next_sjlj_build_exc_extract (rethrow_decl);
3961 SET_EXPR_LOCATION (catch_seq, cur_try_context->end_try_locus);
3963 /* Build the main register-and-try if statement. */
3964 t = next_sjlj_build_enter_and_setjmp ();
3965 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3966 COND_EXPR_THEN (t) = catch_seq;
3967 COND_EXPR_ELSE (t) = cur_try_context->try_body;
3968 TREE_OPERAND (try_fin, 0) = t;
3970 /* Build the complete FINALLY statement list. */
3971 t = next_sjlj_build_try_exit ();
3972 t = build_stmt (input_location, COND_EXPR,
3973 c_common_truthvalue_conversion
3974 (input_location, rethrow_decl),
3976 SET_EXPR_LOCATION (t, cur_try_context->finally_locus);
3977 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3979 append_to_statement_list (cur_try_context->finally_body,
3980 &TREE_OPERAND (try_fin, 1));
3982 t = tree_cons (NULL, rethrow_decl, NULL);
3983 t = build_function_call (input_location,
3984 objc_exception_throw_decl, t);
3985 t = build_stmt (input_location, COND_EXPR,
3986 c_common_truthvalue_conversion (input_location,
3989 SET_EXPR_LOCATION (t, cur_try_context->end_finally_locus);
3990 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3995 /* Called just after parsing the @try and its associated BODY. We now
3996 must prepare for the tricky bits -- handling the catches and finally. */
3999 objc_begin_try_stmt (location_t try_locus, tree body)
4001 struct objc_try_context *c = XCNEW (struct objc_try_context);
4002 c->outer = cur_try_context;
4004 c->try_locus = try_locus;
4005 c->end_try_locus = input_location;
4006 cur_try_context = c;
4008 /* -fobjc-exceptions is required to enable Objective-C exceptions.
4009 For example, on Darwin, ObjC exceptions require a sufficiently
4010 recent version of the runtime, so the user must ask for them
4011 explicitly. On other platforms, at the moment -fobjc-exceptions
4012 triggers -fexceptions which again is required for exceptions to
4015 if (!flag_objc_exceptions)
4017 error_at (try_locus, "%<-fobjc-exceptions%> is required to enable Objective-C exception syntax");
4020 if (flag_objc_sjlj_exceptions)
4021 objc_mark_locals_volatile (NULL);
4024 /* Called just after parsing "@catch (parm)". Open a binding level,
4025 enter DECL into the binding level, and initialize it. Leave the
4026 binding level open while the body of the compound statement is parsed. */
4029 objc_begin_catch_clause (tree decl)
4031 tree compound, type, t;
4033 /* Begin a new scope that the entire catch clause will live in. */
4034 compound = c_begin_compound_stmt (true);
4036 /* The parser passed in a PARM_DECL, but what we really want is a VAR_DECL. */
4037 decl = build_decl (input_location,
4038 VAR_DECL, DECL_NAME (decl), TREE_TYPE (decl));
4039 lang_hooks.decls.pushdecl (decl);
4041 /* Since a decl is required here by syntax, don't warn if its unused. */
4042 /* ??? As opposed to __attribute__((unused))? Anyway, this appears to
4043 be what the previous objc implementation did. */
4044 TREE_USED (decl) = 1;
4045 DECL_READ_P (decl) = 1;
4047 /* Verify that the type of the catch is valid. It must be a pointer
4048 to an Objective-C class, or "id" (which is catch-all). */
4049 type = TREE_TYPE (decl);
4051 if (POINTER_TYPE_P (type) && objc_is_object_id (TREE_TYPE (type)))
4053 else if (!POINTER_TYPE_P (type) || !TYPED_OBJECT (TREE_TYPE (type)))
4055 error ("@catch parameter is not a known Objective-C class type");
4056 type = error_mark_node;
4058 else if (cur_try_context->catch_list)
4060 /* Examine previous @catch clauses and see if we've already
4061 caught the type in question. */
4062 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
4063 for (; !tsi_end_p (i); tsi_next (&i))
4065 tree stmt = tsi_stmt (i);
4066 t = CATCH_TYPES (stmt);
4067 if (t == error_mark_node)
4069 if (!t || DERIVED_FROM_P (TREE_TYPE (t), TREE_TYPE (type)))
4071 warning (0, "exception of type %<%T%> will be caught",
4073 warning_at (EXPR_LOCATION (stmt), 0, " by earlier handler for %<%T%>",
4074 TREE_TYPE (t ? t : objc_object_type));
4080 /* Record the data for the catch in the try context so that we can
4081 finalize it later. */
4082 t = build_stmt (input_location, CATCH_EXPR, type, compound);
4083 cur_try_context->current_catch = t;
4085 /* Initialize the decl from the EXC_PTR_EXPR we get from the runtime. */
4086 t = objc_build_exc_ptr ();
4087 t = convert (TREE_TYPE (decl), t);
4088 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
4092 /* Called just after parsing the closing brace of a @catch clause. Close
4093 the open binding level, and record a CATCH_EXPR for it. */
4096 objc_finish_catch_clause (void)
4098 tree c = cur_try_context->current_catch;
4099 cur_try_context->current_catch = NULL;
4100 cur_try_context->end_catch_locus = input_location;
4102 CATCH_BODY (c) = c_end_compound_stmt (input_location, CATCH_BODY (c), 1);
4103 append_to_statement_list (c, &cur_try_context->catch_list);
4106 /* Called after parsing a @finally clause and its associated BODY.
4107 Record the body for later placement. */
4110 objc_build_finally_clause (location_t finally_locus, tree body)
4112 cur_try_context->finally_body = body;
4113 cur_try_context->finally_locus = finally_locus;
4114 cur_try_context->end_finally_locus = input_location;
4117 /* Called to finalize a @try construct. */
4120 objc_finish_try_stmt (void)
4122 struct objc_try_context *c = cur_try_context;
4125 if (c->catch_list == NULL && c->finally_body == NULL)
4126 error ("%<@try%> without %<@catch%> or %<@finally%>");
4128 /* If we're doing Darwin setjmp exceptions, build the big nasty. */
4129 if (flag_objc_sjlj_exceptions)
4131 bool save = in_late_binary_op;
4132 in_late_binary_op = true;
4133 if (!cur_try_context->finally_body)
4135 cur_try_context->finally_locus = input_location;
4136 cur_try_context->end_finally_locus = input_location;
4138 stmt = next_sjlj_build_try_catch_finally ();
4139 in_late_binary_op = save;
4143 /* Otherwise, nest the CATCH inside a FINALLY. */
4147 stmt = build_stmt (input_location, TRY_CATCH_EXPR, stmt, c->catch_list);
4148 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
4150 if (c->finally_body)
4152 stmt = build_stmt (input_location, TRY_FINALLY_EXPR, stmt, c->finally_body);
4153 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
4158 cur_try_context = c->outer;
4164 objc_build_throw_stmt (location_t loc, tree throw_expr)
4168 if (!flag_objc_exceptions)
4170 error_at (loc, "%<-fobjc-exceptions%> is required to enable Objective-C exception syntax");
4173 if (throw_expr == NULL)
4175 /* If we're not inside a @catch block, there is no "current
4176 exception" to be rethrown. */
4177 if (cur_try_context == NULL
4178 || cur_try_context->current_catch == NULL)
4180 error_at (loc, "%<@throw%> (rethrow) used outside of a @catch block");
4184 /* Otherwise the object is still sitting in the EXC_PTR_EXPR
4185 value that we get from the runtime. */
4186 throw_expr = objc_build_exc_ptr ();
4189 /* A throw is just a call to the runtime throw function with the
4190 object as a parameter. */
4191 args = tree_cons (NULL, throw_expr, NULL);
4192 return add_stmt (build_function_call (loc,
4193 objc_exception_throw_decl, args));
4197 objc_build_synchronized (location_t start_locus, tree mutex, tree body)
4201 /* First lock the mutex. */
4202 mutex = save_expr (mutex);
4203 args = tree_cons (NULL, mutex, NULL);
4204 call = build_function_call (input_location,
4205 objc_sync_enter_decl, args);
4206 SET_EXPR_LOCATION (call, start_locus);
4209 /* Build the mutex unlock. */
4210 args = tree_cons (NULL, mutex, NULL);
4211 call = build_function_call (input_location,
4212 objc_sync_exit_decl, args);
4213 SET_EXPR_LOCATION (call, input_location);
4215 /* Put the that and the body in a TRY_FINALLY. */
4216 objc_begin_try_stmt (start_locus, body);
4217 objc_build_finally_clause (input_location, call);
4218 return objc_finish_try_stmt ();
4222 /* Predefine the following data type:
4224 struct _objc_exception_data
4226 int buf[OBJC_JBLEN];
4230 /* The following yuckiness should prevent users from having to #include
4231 <setjmp.h> in their code... */
4233 /* Define to a harmless positive value so the below code doesn't die. */
4235 #define OBJC_JBLEN 18
4239 build_next_objc_exception_stuff (void)
4241 tree decls, temp_type, *chain = NULL;
4243 objc_exception_data_template
4244 = objc_start_struct (get_identifier (UTAG_EXCDATA));
4246 /* int buf[OBJC_JBLEN]; */
4248 temp_type = build_sized_array_type (integer_type_node, OBJC_JBLEN);
4249 decls = add_field_decl (temp_type, "buf", &chain);
4251 /* void *pointers[4]; */
4253 temp_type = build_sized_array_type (ptr_type_node, 4);
4254 add_field_decl (temp_type, "pointers", &chain);
4256 objc_finish_struct (objc_exception_data_template, decls);
4258 /* int _setjmp(...); */
4259 /* If the user includes <setjmp.h>, this shall be superseded by
4260 'int _setjmp(jmp_buf);' */
4261 temp_type = build_varargs_function_type_list (integer_type_node, NULL_TREE);
4263 = add_builtin_function (TAG_SETJMP, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4265 /* id objc_exception_extract(struct _objc_exception_data *); */
4267 = build_function_type_list (objc_object_type,
4268 build_pointer_type (objc_exception_data_template),
4270 objc_exception_extract_decl
4271 = add_builtin_function (TAG_EXCEPTIONEXTRACT, temp_type, 0, NOT_BUILT_IN, NULL,
4273 /* void objc_exception_try_enter(struct _objc_exception_data *); */
4274 /* void objc_exception_try_exit(struct _objc_exception_data *); */
4276 = build_function_type_list (void_type_node,
4277 build_pointer_type (objc_exception_data_template),
4279 objc_exception_try_enter_decl
4280 = add_builtin_function (TAG_EXCEPTIONTRYENTER, temp_type, 0, NOT_BUILT_IN, NULL,
4282 objc_exception_try_exit_decl
4283 = add_builtin_function (TAG_EXCEPTIONTRYEXIT, temp_type, 0, NOT_BUILT_IN, NULL,
4286 /* int objc_exception_match(id, id); */
4288 = build_function_type_list (integer_type_node,
4289 objc_object_type, objc_object_type, NULL_TREE);
4290 objc_exception_match_decl
4291 = add_builtin_function (TAG_EXCEPTIONMATCH, temp_type, 0, NOT_BUILT_IN, NULL,
4294 /* id objc_assign_ivar (id, id, unsigned int); */
4295 /* id objc_assign_ivar_Fast (id, id, unsigned int)
4296 __attribute__ ((hard_coded_address (OFFS_ASSIGNIVAR_FAST))); */
4298 = build_function_type_list (objc_object_type,
4303 objc_assign_ivar_decl
4304 = add_builtin_function (TAG_ASSIGNIVAR, temp_type, 0, NOT_BUILT_IN,
4306 #ifdef OFFS_ASSIGNIVAR_FAST
4307 objc_assign_ivar_fast_decl
4308 = add_builtin_function (TAG_ASSIGNIVAR_FAST, temp_type, 0,
4309 NOT_BUILT_IN, NULL, NULL_TREE);
4310 DECL_ATTRIBUTES (objc_assign_ivar_fast_decl)
4311 = tree_cons (get_identifier ("hard_coded_address"),
4312 build_int_cst (NULL_TREE, OFFS_ASSIGNIVAR_FAST),
4315 /* Default to slower ivar method. */
4316 objc_assign_ivar_fast_decl = objc_assign_ivar_decl;
4319 /* id objc_assign_global (id, id *); */
4320 /* id objc_assign_strongCast (id, id *); */
4321 temp_type = build_function_type_list (objc_object_type,
4323 build_pointer_type (objc_object_type),
4325 objc_assign_global_decl
4326 = add_builtin_function (TAG_ASSIGNGLOBAL, temp_type, 0, NOT_BUILT_IN, NULL,
4328 objc_assign_strong_cast_decl
4329 = add_builtin_function (TAG_ASSIGNSTRONGCAST, temp_type, 0, NOT_BUILT_IN, NULL,
4334 build_objc_exception_stuff (void)
4336 tree noreturn_list, nothrow_list, temp_type;
4338 noreturn_list = tree_cons (get_identifier ("noreturn"), NULL, NULL);
4339 nothrow_list = tree_cons (get_identifier ("nothrow"), NULL, NULL);
4341 /* void objc_exception_throw(id) __attribute__((noreturn)); */
4342 /* void objc_sync_enter(id); */
4343 /* void objc_sync_exit(id); */
4344 temp_type = build_function_type_list (void_type_node,
4347 objc_exception_throw_decl
4348 = add_builtin_function (TAG_EXCEPTIONTHROW, temp_type, 0, NOT_BUILT_IN, NULL,
4350 objc_sync_enter_decl
4351 = add_builtin_function (TAG_SYNCENTER, temp_type, 0, NOT_BUILT_IN,
4352 NULL, nothrow_list);
4354 = add_builtin_function (TAG_SYNCEXIT, temp_type, 0, NOT_BUILT_IN,
4355 NULL, nothrow_list);
4358 /* Construct a C struct corresponding to ObjC class CLASS, with the same
4361 struct <classname> {
4362 struct _objc_class *isa;
4367 build_private_template (tree klass)
4369 if (!CLASS_STATIC_TEMPLATE (klass))
4371 tree record = objc_build_struct (klass,
4372 get_class_ivars (klass, false),
4373 CLASS_SUPER_NAME (klass));
4375 /* Set the TREE_USED bit for this struct, so that stab generator
4376 can emit stabs for this struct type. */
4377 if (flag_debug_only_used_symbols && TYPE_STUB_DECL (record))
4378 TREE_USED (TYPE_STUB_DECL (record)) = 1;
4382 /* Begin code generation for protocols... */
4384 /* struct _objc_protocol {
4385 struct _objc_class *isa;
4386 char *protocol_name;
4387 struct _objc_protocol **protocol_list;
4388 struct _objc__method_prototype_list *instance_methods;
4389 struct _objc__method_prototype_list *class_methods;
4393 build_protocol_template (void)
4395 tree ptype, decls, *chain = NULL;
4397 objc_protocol_template = objc_start_struct (get_identifier (UTAG_PROTOCOL));
4399 /* struct _objc_class *isa; */
4400 ptype = build_pointer_type (xref_tag (RECORD_TYPE,
4401 get_identifier (UTAG_CLASS)));
4402 decls = add_field_decl (ptype, "isa", &chain);
4404 /* char *protocol_name; */
4405 add_field_decl (string_type_node, "protocol_name", &chain);
4407 /* struct _objc_protocol **protocol_list; */
4408 ptype = build_pointer_type (build_pointer_type (objc_protocol_template));
4409 add_field_decl (ptype, "protocol_list", &chain);
4411 /* struct _objc__method_prototype_list *instance_methods; */
4412 add_field_decl (objc_method_proto_list_ptr, "instance_methods", &chain);
4414 /* struct _objc__method_prototype_list *class_methods; */
4415 add_field_decl (objc_method_proto_list_ptr, "class_methods", &chain);
4417 objc_finish_struct (objc_protocol_template, decls);
4421 build_descriptor_table_initializer (tree type, tree entries)
4423 VEC(constructor_elt,gc) *inits = NULL;
4427 VEC(constructor_elt,gc) *elts = NULL;
4429 CONSTRUCTOR_APPEND_ELT (elts, NULL_TREE,
4430 build_selector (METHOD_SEL_NAME (entries)));
4431 CONSTRUCTOR_APPEND_ELT (elts, NULL_TREE,
4432 add_objc_string (METHOD_ENCODING (entries),
4435 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE,
4436 objc_build_constructor (type, elts));
4438 entries = DECL_CHAIN (entries);
4442 return objc_build_constructor (build_array_type (type, 0), inits);
4445 /* struct objc_method_prototype_list {
4447 struct objc_method_prototype {
4454 build_method_prototype_list_template (tree list_type, int size)
4456 tree objc_ivar_list_record;
4457 tree array_type, decls, *chain = NULL;
4459 /* Generate an unnamed struct definition. */
4461 objc_ivar_list_record = objc_start_struct (NULL_TREE);
4463 /* int method_count; */
4464 decls = add_field_decl (integer_type_node, "method_count", &chain);
4466 /* struct objc_method method_list[]; */
4467 array_type = build_sized_array_type (list_type, size);
4468 add_field_decl (array_type, "method_list", &chain);
4470 objc_finish_struct (objc_ivar_list_record, decls);
4472 return objc_ivar_list_record;
4476 build_method_prototype_template (void)
4479 tree decls, *chain = NULL;
4481 proto_record = objc_start_struct (get_identifier (UTAG_METHOD_PROTOTYPE));
4484 decls = add_field_decl (objc_selector_type, "_cmd", &chain);
4486 /* char *method_types; */
4487 add_field_decl (string_type_node, "method_types", &chain);
4489 objc_finish_struct (proto_record, decls);
4491 return proto_record;
4495 objc_method_parm_type (tree type)
4497 type = TREE_VALUE (TREE_TYPE (type));
4498 if (TREE_CODE (type) == TYPE_DECL)
4499 type = TREE_TYPE (type);
4504 objc_encoded_type_size (tree type)
4506 int sz = int_size_in_bytes (type);
4508 /* Make all integer and enum types at least as large
4510 if (sz > 0 && INTEGRAL_TYPE_P (type))
4511 sz = MAX (sz, int_size_in_bytes (integer_type_node));
4512 /* Treat arrays as pointers, since that's how they're
4514 else if (TREE_CODE (type) == ARRAY_TYPE)
4515 sz = int_size_in_bytes (ptr_type_node);
4519 /* Encode a method prototype.
4521 The format is described in gcc/doc/objc.texi, section 'Method
4525 encode_method_prototype (tree method_decl)
4532 /* ONEWAY and BYCOPY, for remote object are the only method qualifiers. */
4533 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (method_decl)));
4535 /* Encode return type. */
4536 encode_type (objc_method_parm_type (method_decl),
4537 obstack_object_size (&util_obstack),
4538 OBJC_ENCODE_INLINE_DEFS);
4541 /* The first two arguments (self and _cmd) are pointers; account for
4543 i = int_size_in_bytes (ptr_type_node);
4544 parm_offset = 2 * i;
4545 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4546 parms = DECL_CHAIN (parms))
4548 tree type = objc_method_parm_type (parms);
4549 int sz = objc_encoded_type_size (type);
4551 /* If a type size is not known, bail out. */
4554 error ("type %q+D does not have a known size",
4556 /* Pretend that the encoding succeeded; the compilation will
4557 fail nevertheless. */
4558 goto finish_encoding;
4563 sprintf (buf, "%d@0:%d", parm_offset, i);
4564 obstack_grow (&util_obstack, buf, strlen (buf));
4566 /* Argument types. */
4567 parm_offset = 2 * i;
4568 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4569 parms = DECL_CHAIN (parms))
4571 tree type = objc_method_parm_type (parms);
4573 /* Process argument qualifiers for user supplied arguments. */
4574 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (parms)));
4577 encode_type (type, obstack_object_size (&util_obstack),
4578 OBJC_ENCODE_INLINE_DEFS);
4580 /* Compute offset. */
4581 sprintf (buf, "%d", parm_offset);
4582 parm_offset += objc_encoded_type_size (type);
4584 obstack_grow (&util_obstack, buf, strlen (buf));
4588 obstack_1grow (&util_obstack, '\0');
4589 result = get_identifier (XOBFINISH (&util_obstack, char *));
4590 obstack_free (&util_obstack, util_firstobj);
4595 generate_descriptor_table (tree type, const char *name, int size, tree list,
4599 VEC(constructor_elt,gc) *v = NULL;
4601 decl = start_var_decl (type, synth_id_with_class_suffix (name, proto));
4603 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, size));
4604 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, list);
4606 finish_var_decl (decl, objc_build_constructor (type, v));
4612 generate_method_descriptors (tree protocol)
4614 tree initlist, chain, method_list_template;
4617 if (!objc_method_prototype_template)
4618 objc_method_prototype_template = build_method_prototype_template ();
4620 chain = PROTOCOL_CLS_METHODS (protocol);
4623 size = list_length (chain);
4625 method_list_template
4626 = build_method_prototype_list_template (objc_method_prototype_template,
4630 = build_descriptor_table_initializer (objc_method_prototype_template,
4633 UOBJC_CLASS_METHODS_decl
4634 = generate_descriptor_table (method_list_template,
4635 "_OBJC_PROTOCOL_CLASS_METHODS",
4636 size, initlist, protocol);
4639 UOBJC_CLASS_METHODS_decl = 0;
4641 chain = PROTOCOL_NST_METHODS (protocol);
4644 size = list_length (chain);
4646 method_list_template
4647 = build_method_prototype_list_template (objc_method_prototype_template,
4650 = build_descriptor_table_initializer (objc_method_prototype_template,
4653 UOBJC_INSTANCE_METHODS_decl
4654 = generate_descriptor_table (method_list_template,
4655 "_OBJC_PROTOCOL_INSTANCE_METHODS",
4656 size, initlist, protocol);
4659 UOBJC_INSTANCE_METHODS_decl = 0;
4663 generate_protocol_references (tree plist)
4667 /* Forward declare protocols referenced. */
4668 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
4670 tree proto = TREE_VALUE (lproto);
4672 if (TREE_CODE (proto) == PROTOCOL_INTERFACE_TYPE
4673 && PROTOCOL_NAME (proto))
4675 if (! PROTOCOL_FORWARD_DECL (proto))
4676 build_protocol_reference (proto);
4678 if (PROTOCOL_LIST (proto))
4679 generate_protocol_references (PROTOCOL_LIST (proto));
4684 /* Generate either '- .cxx_construct' or '- .cxx_destruct' for the
4688 objc_generate_cxx_ctor_or_dtor (bool dtor)
4690 tree fn, body, compound_stmt, ivar;
4692 /* - (id) .cxx_construct { ... return self; } */
4693 /* - (void) .cxx_construct { ... } */
4695 objc_set_method_type (MINUS_EXPR);
4696 objc_start_method_definition
4697 (objc_build_method_signature (build_tree_list (NULL_TREE,
4700 : objc_object_type),
4701 get_identifier (dtor
4703 : TAG_CXX_CONSTRUCT),
4704 make_node (TREE_LIST),
4706 body = begin_function_body ();
4707 compound_stmt = begin_compound_stmt (0);
4709 ivar = CLASS_IVARS (implementation_template);
4710 /* Destroy ivars in reverse order. */
4712 ivar = nreverse (copy_list (ivar));
4714 for (; ivar; ivar = TREE_CHAIN (ivar))
4716 if (TREE_CODE (ivar) == FIELD_DECL)
4718 tree type = TREE_TYPE (ivar);
4720 /* Call the ivar's default constructor or destructor. Do not
4721 call the destructor unless a corresponding constructor call
4722 has also been made (or is not needed). */
4723 if (MAYBE_CLASS_TYPE_P (type)
4725 ? (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4726 && (!TYPE_NEEDS_CONSTRUCTING (type)
4727 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4728 : (TYPE_NEEDS_CONSTRUCTING (type)
4729 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))))
4731 (build_special_member_call
4732 (build_ivar_reference (DECL_NAME (ivar)),
4733 dtor ? complete_dtor_identifier : complete_ctor_identifier,
4734 NULL, type, LOOKUP_NORMAL, tf_warning_or_error));
4738 /* The constructor returns 'self'. */
4740 finish_return_stmt (self_decl);
4742 finish_compound_stmt (compound_stmt);
4743 finish_function_body (body);
4744 fn = current_function_decl;
4746 objc_finish_method_definition (fn);
4749 /* The following routine will examine the current @interface for any
4750 non-POD C++ ivars requiring non-trivial construction and/or
4751 destruction, and then synthesize special '- .cxx_construct' and/or
4752 '- .cxx_destruct' methods which will run the appropriate
4753 construction or destruction code. Note that ivars inherited from
4754 super-classes are _not_ considered. */
4756 objc_generate_cxx_cdtors (void)
4758 bool need_ctor = false, need_dtor = false;
4761 /* We do not want to do this for categories, since they do not have
4764 if (TREE_CODE (objc_implementation_context) != CLASS_IMPLEMENTATION_TYPE)
4767 /* First, determine if we even need a constructor and/or destructor. */
4769 for (ivar = CLASS_IVARS (implementation_template); ivar;
4770 ivar = TREE_CHAIN (ivar))
4772 if (TREE_CODE (ivar) == FIELD_DECL)
4774 tree type = TREE_TYPE (ivar);
4776 if (MAYBE_CLASS_TYPE_P (type))
4778 if (TYPE_NEEDS_CONSTRUCTING (type)
4779 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
4780 /* NB: If a default constructor is not available, we will not
4781 be able to initialize this ivar; the add_instance_variable()
4782 routine will already have warned about this. */
4785 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4786 && (!TYPE_NEEDS_CONSTRUCTING (type)
4787 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4788 /* NB: If a default constructor is not available, we will not
4789 call the destructor either, for symmetry. */
4795 /* Generate '- .cxx_construct' if needed. */
4798 objc_generate_cxx_ctor_or_dtor (false);
4800 /* Generate '- .cxx_destruct' if needed. */
4803 objc_generate_cxx_ctor_or_dtor (true);
4805 /* The 'imp_list' variable points at an imp_entry record for the current
4806 @implementation. Record the existence of '- .cxx_construct' and/or
4807 '- .cxx_destruct' methods therein; it will be included in the
4808 metadata for the class. */
4809 if (flag_next_runtime)
4810 imp_list->has_cxx_cdtors = (need_ctor || need_dtor);
4814 /* For each protocol which was referenced either from a @protocol()
4815 expression, or because a class/category implements it (then a
4816 pointer to the protocol is stored in the struct describing the
4817 class/category), we create a statically allocated instance of the
4818 Protocol class. The code is written in such a way as to generate
4819 as few Protocol objects as possible; we generate a unique Protocol
4820 instance for each protocol, and we don't generate a Protocol
4821 instance if the protocol is never referenced (either from a
4822 @protocol() or from a class/category implementation). These
4823 statically allocated objects can be referred to via the static
4824 (that is, private to this module) symbols _OBJC_PROTOCOL_n.
4826 The statically allocated Protocol objects that we generate here
4827 need to be fixed up at runtime in order to be used: the 'isa'
4828 pointer of the objects need to be set up to point to the 'Protocol'
4829 class, as known at runtime.
4831 The NeXT runtime fixes up all protocols at program startup time,
4832 before main() is entered. It uses a low-level trick to look up all
4833 those symbols, then loops on them and fixes them up.
4835 The GNU runtime as well fixes up all protocols before user code
4836 from the module is executed; it requires pointers to those symbols
4837 to be put in the objc_symtab (which is then passed as argument to
4838 the function __objc_exec_class() which the compiler sets up to be
4839 executed automatically when the module is loaded); setup of those
4840 Protocol objects happen in two ways in the GNU runtime: all
4841 Protocol objects referred to by a class or category implementation
4842 are fixed up when the class/category is loaded; all Protocol
4843 objects referred to by a @protocol() expression are added by the
4844 compiler to the list of statically allocated instances to fixup
4845 (the same list holding the statically allocated constant string
4846 objects). Because, as explained above, the compiler generates as
4847 few Protocol objects as possible, some Protocol object might end up
4848 being referenced multiple times when compiled with the GNU runtime,
4849 and end up being fixed up multiple times at runtime initialization.
4850 But that doesn't hurt, it's just a little inefficient. */
4853 generate_protocols (void)
4857 tree initlist, protocol_name_expr, refs_decl, refs_expr;
4859 /* If a protocol was directly referenced, pull in indirect references. */
4860 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4861 if (PROTOCOL_FORWARD_DECL (p) && PROTOCOL_LIST (p))
4862 generate_protocol_references (PROTOCOL_LIST (p));
4864 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4866 tree nst_methods = PROTOCOL_NST_METHODS (p);
4867 tree cls_methods = PROTOCOL_CLS_METHODS (p);
4869 /* If protocol wasn't referenced, don't generate any code. */
4870 decl = PROTOCOL_FORWARD_DECL (p);
4875 /* Make sure we link in the Protocol class. */
4876 add_class_reference (get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
4880 if (! METHOD_ENCODING (nst_methods))
4882 encoding = encode_method_prototype (nst_methods);
4883 METHOD_ENCODING (nst_methods) = encoding;
4885 nst_methods = DECL_CHAIN (nst_methods);
4890 if (! METHOD_ENCODING (cls_methods))
4892 encoding = encode_method_prototype (cls_methods);
4893 METHOD_ENCODING (cls_methods) = encoding;
4896 cls_methods = DECL_CHAIN (cls_methods);
4898 generate_method_descriptors (p);
4900 if (PROTOCOL_LIST (p))
4901 refs_decl = generate_protocol_list (p);
4905 /* static struct objc_protocol _OBJC_PROTOCOL_<mumble>; */
4906 protocol_name_expr = add_objc_string (PROTOCOL_NAME (p), class_names);
4909 refs_expr = convert (build_pointer_type (build_pointer_type
4910 (objc_protocol_template)),
4911 build_unary_op (input_location,
4912 ADDR_EXPR, refs_decl, 0));
4914 refs_expr = build_int_cst (NULL_TREE, 0);
4916 /* UOBJC_INSTANCE_METHODS_decl/UOBJC_CLASS_METHODS_decl are set
4917 by generate_method_descriptors, which is called above. */
4918 initlist = build_protocol_initializer (TREE_TYPE (decl),
4919 protocol_name_expr, refs_expr,
4920 UOBJC_INSTANCE_METHODS_decl,
4921 UOBJC_CLASS_METHODS_decl);
4922 finish_var_decl (decl, initlist);
4927 build_protocol_initializer (tree type, tree protocol_name,
4928 tree protocol_list, tree instance_methods,
4932 tree cast_type = build_pointer_type
4933 (xref_tag (RECORD_TYPE,
4934 get_identifier (UTAG_CLASS)));
4935 VEC(constructor_elt,gc) *inits = NULL;
4937 /* Filling the "isa" in with one allows the runtime system to
4938 detect that the version change...should remove before final release. */
4940 expr = build_int_cst (cast_type, PROTOCOL_VERSION);
4941 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, expr);
4942 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, protocol_name);
4943 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, protocol_list);
4945 if (!instance_methods)
4946 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, build_int_cst (NULL_TREE, 0));
4949 expr = convert (objc_method_proto_list_ptr,
4950 build_unary_op (input_location,
4951 ADDR_EXPR, instance_methods, 0));
4952 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, expr);
4956 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, build_int_cst (NULL_TREE, 0));
4959 expr = convert (objc_method_proto_list_ptr,
4960 build_unary_op (input_location,
4961 ADDR_EXPR, class_methods, 0));
4962 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, expr);
4965 return objc_build_constructor (type, inits);
4968 /* struct _objc_category {
4969 char *category_name;
4971 struct _objc_method_list *instance_methods;
4972 struct _objc_method_list *class_methods;
4973 struct _objc_protocol_list *protocols;
4977 build_category_template (void)
4979 tree ptype, decls, *chain = NULL;
4981 objc_category_template = objc_start_struct (get_identifier (UTAG_CATEGORY));
4983 /* char *category_name; */
4984 decls = add_field_decl (string_type_node, "category_name", &chain);
4986 /* char *class_name; */
4987 add_field_decl (string_type_node, "class_name", &chain);
4989 /* struct _objc_method_list *instance_methods; */
4990 add_field_decl (objc_method_list_ptr, "instance_methods", &chain);
4992 /* struct _objc_method_list *class_methods; */
4993 add_field_decl (objc_method_list_ptr, "class_methods", &chain);
4995 /* struct _objc_protocol **protocol_list; */
4996 ptype = build_pointer_type (build_pointer_type (objc_protocol_template));
4997 add_field_decl (ptype, "protocol_list", &chain);
4999 objc_finish_struct (objc_category_template, decls);
5002 /* struct _objc_selector {
5008 build_selector_template (void)
5010 tree decls, *chain = NULL;
5012 objc_selector_template = objc_start_struct (get_identifier (UTAG_SELECTOR));
5015 decls = add_field_decl (objc_selector_type, "sel_id", &chain);
5017 /* char *sel_type; */
5018 add_field_decl (string_type_node, "sel_type", &chain);
5020 objc_finish_struct (objc_selector_template, decls);
5023 /* struct _objc_class {
5024 struct _objc_class *isa;
5025 struct _objc_class *super_class;
5030 struct _objc_ivar_list *ivars;
5031 struct _objc_method_list *methods;
5032 #ifdef __NEXT_RUNTIME__
5033 struct objc_cache *cache;
5035 struct sarray *dtable;
5036 struct _objc_class *subclass_list;
5037 struct _objc_class *sibling_class;
5039 struct _objc_protocol_list *protocols;
5040 #ifdef __NEXT_RUNTIME__
5043 void *gc_object_type;
5046 /* NB: The 'sel_id' and 'gc_object_type' fields are not being used by
5047 the NeXT/Apple runtime; still, the compiler must generate them to
5048 maintain backward binary compatibility (and to allow for future
5052 build_class_template (void)
5054 tree ptype, decls, *chain = NULL;
5056 objc_class_template = objc_start_struct (get_identifier (UTAG_CLASS));
5058 /* struct _objc_class *isa; */
5059 decls = add_field_decl (build_pointer_type (objc_class_template),
5062 /* struct _objc_class *super_class; */
5063 add_field_decl (build_pointer_type (objc_class_template),
5064 "super_class", &chain);
5067 add_field_decl (string_type_node, "name", &chain);
5070 add_field_decl (long_integer_type_node, "version", &chain);
5073 add_field_decl (long_integer_type_node, "info", &chain);
5075 /* long instance_size; */
5076 add_field_decl (long_integer_type_node, "instance_size", &chain);
5078 /* struct _objc_ivar_list *ivars; */
5079 add_field_decl (objc_ivar_list_ptr,"ivars", &chain);
5081 /* struct _objc_method_list *methods; */
5082 add_field_decl (objc_method_list_ptr, "methods", &chain);
5084 if (flag_next_runtime)
5086 /* struct objc_cache *cache; */
5087 ptype = build_pointer_type (xref_tag (RECORD_TYPE,
5088 get_identifier ("objc_cache")));
5089 add_field_decl (ptype, "cache", &chain);
5093 /* struct sarray *dtable; */
5094 ptype = build_pointer_type(xref_tag (RECORD_TYPE,
5095 get_identifier ("sarray")));
5096 add_field_decl (ptype, "dtable", &chain);
5098 /* struct objc_class *subclass_list; */
5099 ptype = build_pointer_type (objc_class_template);
5100 add_field_decl (ptype, "subclass_list", &chain);
5102 /* struct objc_class *sibling_class; */
5103 ptype = build_pointer_type (objc_class_template);
5104 add_field_decl (ptype, "sibling_class", &chain);
5107 /* struct _objc_protocol **protocol_list; */
5108 ptype = build_pointer_type (build_pointer_type
5109 (xref_tag (RECORD_TYPE,
5110 get_identifier (UTAG_PROTOCOL))));
5111 add_field_decl (ptype, "protocol_list", &chain);
5113 if (flag_next_runtime)
5116 add_field_decl (build_pointer_type (void_type_node), "sel_id", &chain);
5119 /* void *gc_object_type; */
5120 add_field_decl (build_pointer_type (void_type_node),
5121 "gc_object_type", &chain);
5123 objc_finish_struct (objc_class_template, decls);
5126 /* Generate appropriate forward declarations for an implementation. */
5129 synth_forward_declarations (void)
5133 /* static struct objc_class _OBJC_CLASS_<my_name>; */
5134 UOBJC_CLASS_decl = build_metadata_decl ("_OBJC_CLASS",
5135 objc_class_template);
5137 /* static struct objc_class _OBJC_METACLASS_<my_name>; */
5138 UOBJC_METACLASS_decl = build_metadata_decl ("_OBJC_METACLASS",
5139 objc_class_template);
5141 /* Pre-build the following entities - for speed/convenience. */
5143 an_id = get_identifier ("super_class");
5144 ucls_super_ref = objc_build_component_ref (UOBJC_CLASS_decl, an_id);
5145 uucls_super_ref = objc_build_component_ref (UOBJC_METACLASS_decl, an_id);
5149 error_with_ivar (const char *message, tree decl)
5151 error_at (DECL_SOURCE_LOCATION (decl), "%s %qs",
5152 message, identifier_to_locale (gen_declaration (decl)));
5157 check_ivars (tree inter, tree imp)
5159 tree intdecls = CLASS_RAW_IVARS (inter);
5160 tree impdecls = CLASS_RAW_IVARS (imp);
5167 if (intdecls && TREE_CODE (intdecls) == TYPE_DECL)
5168 intdecls = TREE_CHAIN (intdecls);
5170 if (intdecls == 0 && impdecls == 0)
5172 if (intdecls == 0 || impdecls == 0)
5174 error ("inconsistent instance variable specification");
5178 t1 = TREE_TYPE (intdecls); t2 = TREE_TYPE (impdecls);
5180 if (!comptypes (t1, t2)
5181 || !tree_int_cst_equal (DECL_INITIAL (intdecls),
5182 DECL_INITIAL (impdecls)))
5184 if (DECL_NAME (intdecls) == DECL_NAME (impdecls))
5186 error_with_ivar ("conflicting instance variable type",
5188 error_with_ivar ("previous declaration of",
5191 else /* both the type and the name don't match */
5193 error ("inconsistent instance variable specification");
5198 else if (DECL_NAME (intdecls) != DECL_NAME (impdecls))
5200 error_with_ivar ("conflicting instance variable name",
5202 error_with_ivar ("previous declaration of",
5206 intdecls = DECL_CHAIN (intdecls);
5207 impdecls = DECL_CHAIN (impdecls);
5211 /* Set 'objc_super_template' to the data type node for 'struct _objc_super'.
5212 This needs to be done just once per compilation. */
5214 /* struct _objc_super {
5215 struct _objc_object *self;
5216 struct _objc_class *super_class;
5220 build_super_template (void)
5222 tree decls, *chain = NULL;
5224 objc_super_template = objc_start_struct (get_identifier (UTAG_SUPER));
5226 /* struct _objc_object *self; */
5227 decls = add_field_decl (objc_object_type, "self", &chain);
5229 /* struct _objc_class *super_class; */
5230 add_field_decl (build_pointer_type (objc_class_template),
5231 "super_class", &chain);
5233 objc_finish_struct (objc_super_template, decls);
5236 /* struct _objc_ivar {
5243 build_ivar_template (void)
5245 tree objc_ivar_id, objc_ivar_record;
5246 tree decls, *chain = NULL;
5248 objc_ivar_id = get_identifier (UTAG_IVAR);
5249 objc_ivar_record = objc_start_struct (objc_ivar_id);
5251 /* char *ivar_name; */
5252 decls = add_field_decl (string_type_node, "ivar_name", &chain);
5254 /* char *ivar_type; */
5255 add_field_decl (string_type_node, "ivar_type", &chain);
5257 /* int ivar_offset; */
5258 add_field_decl (integer_type_node, "ivar_offset", &chain);
5260 objc_finish_struct (objc_ivar_record, decls);
5262 return objc_ivar_record;
5267 struct objc_ivar ivar_list[ivar_count];
5271 build_ivar_list_template (tree list_type, int size)
5273 tree objc_ivar_list_record;
5274 tree array_type, decls, *chain = NULL;
5276 objc_ivar_list_record = objc_start_struct (NULL_TREE);
5278 /* int ivar_count; */
5279 decls = add_field_decl (integer_type_node, "ivar_count", &chain);
5281 /* struct objc_ivar ivar_list[]; */
5282 array_type = build_sized_array_type (list_type, size);
5283 add_field_decl (array_type, "ivar_list", &chain);
5285 objc_finish_struct (objc_ivar_list_record, decls);
5287 return objc_ivar_list_record;
5291 struct _objc__method_prototype_list *method_next;
5293 struct objc_method method_list[method_count];
5297 build_method_list_template (tree list_type, int size)
5299 tree objc_ivar_list_record;
5300 tree array_type, decls, *chain = NULL;
5302 objc_ivar_list_record = objc_start_struct (NULL_TREE);
5304 /* struct _objc__method_prototype_list *method_next; */
5305 decls = add_field_decl (objc_method_proto_list_ptr, "method_next", &chain);
5307 /* int method_count; */
5308 add_field_decl (integer_type_node, "method_count", &chain);
5310 /* struct objc_method method_list[]; */
5311 array_type = build_sized_array_type (list_type, size);
5312 add_field_decl (array_type, "method_list", &chain);
5314 objc_finish_struct (objc_ivar_list_record, decls);
5316 return objc_ivar_list_record;
5320 build_ivar_list_initializer (tree type, tree field_decl)
5322 VEC(constructor_elt,gc) *inits = NULL;
5326 VEC(constructor_elt,gc) *ivar = NULL;
5330 if (DECL_NAME (field_decl))
5331 CONSTRUCTOR_APPEND_ELT (ivar, NULL_TREE,
5332 add_objc_string (DECL_NAME (field_decl),
5335 /* Unnamed bit-field ivar (yuck). */
5336 CONSTRUCTOR_APPEND_ELT (ivar, NULL_TREE, build_int_cst (NULL_TREE, 0));
5339 encode_field_decl (field_decl,
5340 obstack_object_size (&util_obstack),
5341 OBJC_ENCODE_DONT_INLINE_DEFS);
5343 /* Null terminate string. */
5344 obstack_1grow (&util_obstack, 0);
5345 id = add_objc_string (get_identifier (XOBFINISH (&util_obstack, char *)),
5347 CONSTRUCTOR_APPEND_ELT (ivar, NULL_TREE, id);
5348 obstack_free (&util_obstack, util_firstobj);
5351 CONSTRUCTOR_APPEND_ELT (ivar, NULL_TREE, byte_position (field_decl));
5352 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE,
5353 objc_build_constructor (type, ivar));
5355 field_decl = DECL_CHAIN (field_decl);
5356 while (field_decl && TREE_CODE (field_decl) != FIELD_DECL);
5360 return objc_build_constructor (build_array_type (type, 0), inits);
5364 generate_ivars_list (tree type, const char *name, int size, tree list)
5367 VEC(constructor_elt,gc) *inits = NULL;
5369 decl = start_var_decl (type, synth_id_with_class_suffix
5370 (name, objc_implementation_context));
5372 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, build_int_cst (NULL_TREE, size));
5373 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE, list);
5375 finish_var_decl (decl,
5376 objc_build_constructor (TREE_TYPE (decl), inits));
5381 /* Count only the fields occurring in T. */
5384 ivar_list_length (tree t)
5388 for (; t; t = DECL_CHAIN (t))
5389 if (TREE_CODE (t) == FIELD_DECL)
5396 generate_ivar_lists (void)
5398 tree initlist, ivar_list_template, chain;
5401 generating_instance_variables = 1;
5403 if (!objc_ivar_template)
5404 objc_ivar_template = build_ivar_template ();
5406 /* Only generate class variables for the root of the inheritance
5407 hierarchy since these will be the same for every class. */
5409 if (CLASS_SUPER_NAME (implementation_template) == NULL_TREE
5410 && (chain = TYPE_FIELDS (objc_class_template)))
5412 size = ivar_list_length (chain);
5414 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5415 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5417 UOBJC_CLASS_VARIABLES_decl
5418 = generate_ivars_list (ivar_list_template, "_OBJC_CLASS_VARIABLES",
5422 UOBJC_CLASS_VARIABLES_decl = 0;
5424 chain = CLASS_IVARS (implementation_template);
5427 size = ivar_list_length (chain);
5428 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5429 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5431 UOBJC_INSTANCE_VARIABLES_decl
5432 = generate_ivars_list (ivar_list_template, "_OBJC_INSTANCE_VARIABLES",
5436 UOBJC_INSTANCE_VARIABLES_decl = 0;
5438 generating_instance_variables = 0;
5442 build_dispatch_table_initializer (tree type, tree entries)
5444 VEC(constructor_elt,gc) *inits = NULL;
5448 VEC(constructor_elt,gc) *elems = NULL;
5451 CONSTRUCTOR_APPEND_ELT (elems, NULL_TREE,
5452 build_selector (METHOD_SEL_NAME (entries)));
5454 /* Generate the method encoding if we don't have one already. */
5455 if (! METHOD_ENCODING (entries))
5456 METHOD_ENCODING (entries) =
5457 encode_method_prototype (entries);
5459 CONSTRUCTOR_APPEND_ELT (elems, NULL_TREE,
5460 add_objc_string (METHOD_ENCODING (entries),
5463 expr = convert (ptr_type_node,
5464 build_unary_op (input_location, ADDR_EXPR,
5465 METHOD_DEFINITION (entries), 1));
5466 CONSTRUCTOR_APPEND_ELT (elems, NULL_TREE, expr);
5468 CONSTRUCTOR_APPEND_ELT (inits, NULL_TREE,
5469 objc_build_constructor (type, elems));
5471 entries = DECL_CHAIN (entries);
5475 return objc_build_constructor (build_array_type (type, 0), inits);
5478 /* To accomplish method prototyping without generating all kinds of
5479 inane warnings, the definition of the dispatch table entries were
5482 struct objc_method { SEL _cmd; ...; id (*_imp)(); };
5484 struct objc_method { SEL _cmd; ...; void *_imp; }; */
5487 build_method_template (void)
5490 tree decls, *chain = NULL;
5492 _SLT_record = objc_start_struct (get_identifier (UTAG_METHOD));
5495 decls = add_field_decl (objc_selector_type, "_cmd", &chain);
5497 /* char *method_types; */
5498 add_field_decl (string_type_node, "method_types", &chain);
5501 add_field_decl (build_pointer_type (void_type_node), "_imp", &chain);
5503 objc_finish_struct (_SLT_record, decls);
5510 generate_dispatch_table (tree type, const char *name, int size, tree list)
5513 VEC(constructor_elt,gc) *v = NULL;
5515 decl = start_var_decl (type, synth_id_with_class_suffix
5516 (name, objc_implementation_context));
5518 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, integer_zero_node);
5519 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (integer_type_node, size));
5520 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, list);
5522 finish_var_decl (decl,
5523 objc_build_constructor (TREE_TYPE (decl), v));
5529 mark_referenced_methods (void)
5531 struct imp_entry *impent;
5534 for (impent = imp_list; impent; impent = impent->next)
5536 chain = CLASS_CLS_METHODS (impent->imp_context);
5539 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5540 chain = DECL_CHAIN (chain);
5543 chain = CLASS_NST_METHODS (impent->imp_context);
5546 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5547 chain = DECL_CHAIN (chain);
5553 generate_dispatch_tables (void)
5555 tree initlist, chain, method_list_template;
5558 if (!objc_method_template)
5559 objc_method_template = build_method_template ();
5561 chain = CLASS_CLS_METHODS (objc_implementation_context);
5564 size = list_length (chain);
5566 method_list_template
5567 = build_method_list_template (objc_method_template, size);
5569 = build_dispatch_table_initializer (objc_method_template, chain);
5571 UOBJC_CLASS_METHODS_decl
5572 = generate_dispatch_table (method_list_template,
5573 ((TREE_CODE (objc_implementation_context)
5574 == CLASS_IMPLEMENTATION_TYPE)
5575 ? "_OBJC_CLASS_METHODS"
5576 : "_OBJC_CATEGORY_CLASS_METHODS"),
5580 UOBJC_CLASS_METHODS_decl = 0;
5582 chain = CLASS_NST_METHODS (objc_implementation_context);
5585 size = list_length (chain);
5587 method_list_template
5588 = build_method_list_template (objc_method_template, size);
5590 = build_dispatch_table_initializer (objc_method_template, chain);
5592 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
5593 UOBJC_INSTANCE_METHODS_decl
5594 = generate_dispatch_table (method_list_template,
5595 "_OBJC_INSTANCE_METHODS",
5598 /* We have a category. */
5599 UOBJC_INSTANCE_METHODS_decl
5600 = generate_dispatch_table (method_list_template,
5601 "_OBJC_CATEGORY_INSTANCE_METHODS",
5605 UOBJC_INSTANCE_METHODS_decl = 0;
5609 generate_protocol_list (tree i_or_p)
5611 tree array_type, ptype, refs_decl, lproto, e, plist;
5613 const char *ref_name;
5614 VEC(constructor_elt,gc) *v = NULL;
5616 if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE
5617 || TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5618 plist = CLASS_PROTOCOL_LIST (i_or_p);
5619 else if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5620 plist = PROTOCOL_LIST (i_or_p);
5625 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5626 if (TREE_CODE (TREE_VALUE (lproto)) == PROTOCOL_INTERFACE_TYPE
5627 && PROTOCOL_FORWARD_DECL (TREE_VALUE (lproto)))
5630 /* Build initializer. */
5631 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5632 e = build_int_cst (build_pointer_type (objc_protocol_template), size);
5633 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, e);
5635 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5637 tree pval = TREE_VALUE (lproto);
5639 if (TREE_CODE (pval) == PROTOCOL_INTERFACE_TYPE
5640 && PROTOCOL_FORWARD_DECL (pval))
5642 e = build_unary_op (input_location, ADDR_EXPR,
5643 PROTOCOL_FORWARD_DECL (pval), 0);
5644 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, e);
5648 /* static struct objc_protocol *refs[n]; */
5650 if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5651 ref_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL_REFS", i_or_p);
5652 else if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE)
5653 ref_name = synth_id_with_class_suffix ("_OBJC_CLASS_PROTOCOLS", i_or_p);
5654 else if (TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5655 ref_name = synth_id_with_class_suffix ("_OBJC_CATEGORY_PROTOCOLS", i_or_p);
5659 ptype = build_pointer_type (objc_protocol_template);
5660 array_type = build_sized_array_type (ptype, size + 3);
5661 refs_decl = start_var_decl (array_type, ref_name);
5663 finish_var_decl (refs_decl,
5664 objc_build_constructor (TREE_TYPE (refs_decl), v));
5670 build_category_initializer (tree type, tree cat_name, tree class_name,
5671 tree instance_methods, tree class_methods,
5675 VEC(constructor_elt,gc) *v = NULL;
5677 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, cat_name);
5678 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, class_name);
5680 if (!instance_methods)
5681 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5684 expr = convert (objc_method_list_ptr,
5685 build_unary_op (input_location, ADDR_EXPR,
5686 instance_methods, 0));
5687 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5690 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5693 expr = convert (objc_method_list_ptr,
5694 build_unary_op (input_location, ADDR_EXPR,
5696 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5699 /* protocol_list = */
5701 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5704 expr = convert (build_pointer_type
5706 (objc_protocol_template)),
5707 build_unary_op (input_location, ADDR_EXPR,
5709 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5712 return objc_build_constructor (type, v);
5715 /* struct _objc_class {
5716 struct objc_class *isa;
5717 struct objc_class *super_class;
5722 struct objc_ivar_list *ivars;
5723 struct objc_method_list *methods;
5724 if (flag_next_runtime)
5725 struct objc_cache *cache;
5727 struct sarray *dtable;
5728 struct objc_class *subclass_list;
5729 struct objc_class *sibling_class;
5731 struct objc_protocol_list *protocols;
5732 if (flag_next_runtime)
5734 void *gc_object_type;
5738 build_shared_structure_initializer (tree type, tree isa, tree super,
5739 tree name, tree size, int status,
5740 tree dispatch_table, tree ivar_list,
5744 VEC(constructor_elt,gc) *v = NULL;
5747 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, isa);
5750 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, super);
5753 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, default_conversion (name));
5756 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5757 build_int_cst (long_integer_type_node, 0));
5760 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5761 build_int_cst (long_integer_type_node, status));
5763 /* instance_size = */
5764 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5765 convert (long_integer_type_node, size));
5767 /* objc_ivar_list = */
5769 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5772 expr = convert (objc_ivar_list_ptr,
5773 build_unary_op (input_location, ADDR_EXPR,
5775 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5778 /* objc_method_list = */
5779 if (!dispatch_table)
5780 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5783 expr = convert (objc_method_list_ptr,
5784 build_unary_op (input_location, ADDR_EXPR,
5785 dispatch_table, 0));
5786 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5789 if (flag_next_runtime)
5790 /* method_cache = */
5791 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5795 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5797 /* subclass_list = */
5798 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5800 /* sibling_class = */
5801 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5804 /* protocol_list = */
5805 if (! protocol_list)
5806 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5809 expr = convert (build_pointer_type
5811 (objc_protocol_template)),
5812 build_unary_op (input_location, ADDR_EXPR,
5814 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, expr);
5817 if (flag_next_runtime)
5819 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5821 /* gc_object_type = NULL */
5822 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (NULL_TREE, 0));
5824 return objc_build_constructor (type, v);
5827 /* Retrieve category interface CAT_NAME (if any) associated with CLASS. */
5830 lookup_category (tree klass, tree cat_name)
5832 tree category = CLASS_CATEGORY_LIST (klass);
5834 while (category && CLASS_SUPER_NAME (category) != cat_name)
5835 category = CLASS_CATEGORY_LIST (category);
5839 /* static struct objc_category _OBJC_CATEGORY_<name> = { ... }; */
5842 generate_category (struct imp_entry *impent)
5844 tree initlist, cat_name_expr, class_name_expr;
5845 tree protocol_decl, category;
5846 tree cat = impent->imp_context;
5848 implementation_template = impent->imp_template;
5849 UOBJC_CLASS_decl = impent->class_decl;
5850 UOBJC_METACLASS_decl = impent->meta_decl;
5852 add_class_reference (CLASS_NAME (cat));
5853 cat_name_expr = add_objc_string (CLASS_SUPER_NAME (cat), class_names);
5855 class_name_expr = add_objc_string (CLASS_NAME (cat), class_names);
5857 category = lookup_category (implementation_template,
5858 CLASS_SUPER_NAME (cat));
5860 if (category && CLASS_PROTOCOL_LIST (category))
5862 generate_protocol_references (CLASS_PROTOCOL_LIST (category));
5863 protocol_decl = generate_protocol_list (category);
5868 initlist = build_category_initializer (TREE_TYPE (UOBJC_CLASS_decl),
5869 cat_name_expr, class_name_expr,
5870 UOBJC_INSTANCE_METHODS_decl,
5871 UOBJC_CLASS_METHODS_decl,
5873 /* Finish and initialize the forward decl. */
5874 finish_var_decl (UOBJC_CLASS_decl, initlist);
5877 /* static struct objc_class _OBJC_METACLASS_Foo={ ... };
5878 static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5881 generate_shared_structures (struct imp_entry *impent)
5883 tree name_expr, super_expr, root_expr;
5884 tree my_root_id, my_super_id;
5885 tree cast_type, initlist, protocol_decl;
5888 objc_implementation_context = impent->imp_context;
5889 implementation_template = impent->imp_template;
5890 UOBJC_CLASS_decl = impent->class_decl;
5891 UOBJC_METACLASS_decl = impent->meta_decl;
5892 cls_flags = impent->has_cxx_cdtors ? CLS_HAS_CXX_STRUCTORS : 0 ;
5894 my_super_id = CLASS_SUPER_NAME (implementation_template);
5897 add_class_reference (my_super_id);
5899 /* Compute "my_root_id" - this is required for code generation.
5900 the "isa" for all meta class structures points to the root of
5901 the inheritance hierarchy (e.g. "__Object")... */
5902 my_root_id = my_super_id;
5905 tree my_root_int = lookup_interface (my_root_id);
5907 if (my_root_int && CLASS_SUPER_NAME (my_root_int))
5908 my_root_id = CLASS_SUPER_NAME (my_root_int);
5915 /* No super class. */
5916 my_root_id = CLASS_NAME (implementation_template);
5918 cast_type = build_pointer_type (objc_class_template);
5919 name_expr = add_objc_string (CLASS_NAME (implementation_template),
5922 /* Install class `isa' and `super' pointers at runtime. */
5924 super_expr = add_objc_string (my_super_id, class_names);
5926 super_expr = integer_zero_node;
5928 super_expr = build_c_cast (input_location,
5929 cast_type, super_expr); /* cast! */
5931 root_expr = add_objc_string (my_root_id, class_names);
5932 root_expr = build_c_cast (input_location, cast_type, root_expr); /* cast! */
5934 if (CLASS_PROTOCOL_LIST (implementation_template))
5936 generate_protocol_references
5937 (CLASS_PROTOCOL_LIST (implementation_template));
5938 protocol_decl = generate_protocol_list (implementation_template);
5943 /* static struct objc_class _OBJC_METACLASS_Foo = { ... }; */
5946 = build_shared_structure_initializer
5947 (TREE_TYPE (UOBJC_METACLASS_decl),
5948 root_expr, super_expr, name_expr,
5949 convert (integer_type_node, TYPE_SIZE_UNIT (objc_class_template)),
5951 UOBJC_CLASS_METHODS_decl,
5952 UOBJC_CLASS_VARIABLES_decl,
5955 finish_var_decl (UOBJC_METACLASS_decl, initlist);
5957 /* static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5960 = build_shared_structure_initializer
5961 (TREE_TYPE (UOBJC_CLASS_decl),
5962 build_unary_op (input_location, ADDR_EXPR, UOBJC_METACLASS_decl, 0),
5963 super_expr, name_expr,
5964 convert (integer_type_node,
5965 TYPE_SIZE_UNIT (CLASS_STATIC_TEMPLATE
5966 (implementation_template))),
5967 1 /*CLS_FACTORY*/ | cls_flags,
5968 UOBJC_INSTANCE_METHODS_decl,
5969 UOBJC_INSTANCE_VARIABLES_decl,
5972 finish_var_decl (UOBJC_CLASS_decl, initlist);
5977 synth_id_with_class_suffix (const char *preamble, tree ctxt)
5979 static char string[BUFSIZE];
5981 if (TREE_CODE (ctxt) == CLASS_IMPLEMENTATION_TYPE
5982 || TREE_CODE (ctxt) == CLASS_INTERFACE_TYPE)
5984 sprintf (string, "%s_%s", preamble,
5985 IDENTIFIER_POINTER (CLASS_NAME (ctxt)));
5987 else if (TREE_CODE (ctxt) == CATEGORY_IMPLEMENTATION_TYPE
5988 || TREE_CODE (ctxt) == CATEGORY_INTERFACE_TYPE)
5990 /* We have a category. */
5991 const char *const class_name
5992 = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
5993 const char *const class_super_name
5994 = IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context));
5995 sprintf (string, "%s_%s_%s", preamble, class_name, class_super_name);
5997 else if (TREE_CODE (ctxt) == PROTOCOL_INTERFACE_TYPE)
5999 const char *protocol_name = IDENTIFIER_POINTER (PROTOCOL_NAME (ctxt));
6000 sprintf (string, "%s_%s", preamble, protocol_name);
6008 /* If type is empty or only type qualifiers are present, add default
6009 type of id (otherwise grokdeclarator will default to int). */
6012 adjust_type_for_id_default (tree type)
6015 type = make_node (TREE_LIST);
6017 if (!TREE_VALUE (type))
6018 TREE_VALUE (type) = objc_object_type;
6019 else if (TREE_CODE (TREE_VALUE (type)) == RECORD_TYPE
6020 && TYPED_OBJECT (TREE_VALUE (type)))
6021 error ("can not use an object as parameter to a method");
6028 selector ':' '(' typename ')' identifier
6031 Transform an Objective-C keyword argument into
6032 the C equivalent parameter declarator.
6034 In: key_name, an "identifier_node" (optional).
6035 arg_type, a "tree_list" (optional).
6036 arg_name, an "identifier_node".
6037 attributes, a optional tree containing param attributes.
6039 Note: It would be really nice to strongly type the preceding
6040 arguments in the function prototype; however, then I
6041 could not use the "accessor" macros defined in "tree.h".
6043 Out: an instance of "keyword_decl". */
6046 objc_build_keyword_decl (tree key_name, tree arg_type,
6047 tree arg_name, tree attributes)
6052 warning_at (input_location, OPT_Wattributes,
6053 "method parameter attributes are not available in this "
6054 "version of the compiler, (ignored)");
6056 /* If no type is specified, default to "id". */
6057 arg_type = adjust_type_for_id_default (arg_type);
6059 keyword_decl = make_node (KEYWORD_DECL);
6061 TREE_TYPE (keyword_decl) = arg_type;
6062 KEYWORD_ARG_NAME (keyword_decl) = arg_name;
6063 KEYWORD_KEY_NAME (keyword_decl) = key_name;
6065 return keyword_decl;
6068 /* Given a chain of keyword_decl's, synthesize the full keyword selector. */
6071 build_keyword_selector (tree selector)
6074 tree key_chain, key_name;
6077 /* Scan the selector to see how much space we'll need. */
6078 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
6080 if (TREE_CODE (selector) == KEYWORD_DECL)
6081 key_name = KEYWORD_KEY_NAME (key_chain);
6082 else if (TREE_CODE (selector) == TREE_LIST)
6083 key_name = TREE_PURPOSE (key_chain);
6088 len += IDENTIFIER_LENGTH (key_name) + 1;
6090 /* Just a ':' arg. */
6094 buf = (char *) alloca (len + 1);
6095 /* Start the buffer out as an empty string. */
6098 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
6100 if (TREE_CODE (selector) == KEYWORD_DECL)
6101 key_name = KEYWORD_KEY_NAME (key_chain);
6102 else if (TREE_CODE (selector) == TREE_LIST)
6104 key_name = TREE_PURPOSE (key_chain);
6105 /* The keyword decl chain will later be used as a function argument
6106 chain. Unhook the selector itself so as to not confuse other
6107 parts of the compiler. */
6108 TREE_PURPOSE (key_chain) = NULL_TREE;
6114 strcat (buf, IDENTIFIER_POINTER (key_name));
6118 return get_identifier (buf);
6121 /* Used for declarations and definitions. */
6124 build_method_decl (enum tree_code code, tree ret_type, tree selector,
6125 tree add_args, bool ellipsis)
6129 /* If no type is specified, default to "id". */
6130 ret_type = adjust_type_for_id_default (ret_type);
6132 method_decl = make_node (code);
6133 TREE_TYPE (method_decl) = ret_type;
6135 /* If we have a keyword selector, create an identifier_node that
6136 represents the full selector name (`:' included)... */
6137 if (TREE_CODE (selector) == KEYWORD_DECL)
6139 METHOD_SEL_NAME (method_decl) = build_keyword_selector (selector);
6140 METHOD_SEL_ARGS (method_decl) = selector;
6141 METHOD_ADD_ARGS (method_decl) = add_args;
6142 METHOD_ADD_ARGS_ELLIPSIS_P (method_decl) = ellipsis;
6146 METHOD_SEL_NAME (method_decl) = selector;
6147 METHOD_SEL_ARGS (method_decl) = NULL_TREE;
6148 METHOD_ADD_ARGS (method_decl) = NULL_TREE;
6154 #define METHOD_DEF 0
6155 #define METHOD_REF 1
6157 /* Used by `build_objc_method_call' and `comp_proto_with_proto'. Return
6158 an argument list for method METH. CONTEXT is either METHOD_DEF or
6159 METHOD_REF, saying whether we are trying to define a method or call
6160 one. SUPERFLAG says this is for a send to super; this makes a
6161 difference for the NeXT calling sequence in which the lookup and
6162 the method call are done together. If METH is null, user-defined
6163 arguments (i.e., beyond self and _cmd) shall be represented by `...'. */
6166 get_arg_type_list (tree meth, int context, int superflag)
6170 /* Receiver type. */
6171 if (flag_next_runtime && superflag)
6172 arglist = build_tree_list (NULL_TREE, objc_super_type);
6173 else if (context == METHOD_DEF && TREE_CODE (meth) == INSTANCE_METHOD_DECL)
6174 arglist = build_tree_list (NULL_TREE, objc_instance_type);
6176 arglist = build_tree_list (NULL_TREE, objc_object_type);
6178 /* Selector type - will eventually change to `int'. */
6179 chainon (arglist, build_tree_list (NULL_TREE, objc_selector_type));
6181 /* No actual method prototype given -- assume that remaining arguments
6186 /* Build a list of argument types. */
6187 for (akey = METHOD_SEL_ARGS (meth); akey; akey = DECL_CHAIN (akey))
6189 tree arg_type = TREE_VALUE (TREE_TYPE (akey));
6191 /* Decay argument types for the underlying C function as appropriate. */
6192 arg_type = objc_decay_parm_type (arg_type);
6194 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6197 if (METHOD_ADD_ARGS (meth))
6199 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (meth));
6200 akey; akey = TREE_CHAIN (akey))
6202 tree arg_type = TREE_TYPE (TREE_VALUE (akey));
6204 arg_type = objc_decay_parm_type (arg_type);
6206 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6209 if (!METHOD_ADD_ARGS_ELLIPSIS_P (meth))
6210 goto lack_of_ellipsis;
6215 chainon (arglist, OBJC_VOID_AT_END);
6222 check_duplicates (hash hsh, int methods, int is_class)
6224 tree meth = NULL_TREE;
6232 /* We have two or more methods with the same name but
6236 /* But just how different are those types? If
6237 -Wno-strict-selector-match is specified, we shall not
6238 complain if the differences are solely among types with
6239 identical size and alignment. */
6240 if (!warn_strict_selector_match)
6242 for (loop = hsh->list; loop; loop = loop->next)
6243 if (!comp_proto_with_proto (meth, loop->value, 0))
6252 bool type = TREE_CODE (meth) == INSTANCE_METHOD_DECL;
6254 warning_at (input_location, 0,
6255 "multiple methods named %<%c%E%> found",
6256 (is_class ? '+' : '-'),
6257 METHOD_SEL_NAME (meth));
6258 inform (DECL_SOURCE_LOCATION (meth), "using %<%c%s%>",
6260 identifier_to_locale (gen_method_decl (meth)));
6264 bool type = TREE_CODE (meth) == INSTANCE_METHOD_DECL;
6266 warning_at (input_location, 0,
6267 "multiple selectors named %<%c%E%> found",
6268 (is_class ? '+' : '-'),
6269 METHOD_SEL_NAME (meth));
6270 inform (DECL_SOURCE_LOCATION (meth), "found %<%c%s%>",
6272 identifier_to_locale (gen_method_decl (meth)));
6275 for (loop = hsh->list; loop; loop = loop->next)
6277 bool type = TREE_CODE (loop->value) == INSTANCE_METHOD_DECL;
6279 inform (DECL_SOURCE_LOCATION (loop->value), "also found %<%c%s%>",
6281 identifier_to_locale (gen_method_decl (loop->value)));
6288 /* If RECEIVER is a class reference, return the identifier node for
6289 the referenced class. RECEIVER is created by objc_get_class_reference,
6290 so we check the exact form created depending on which runtimes are
6294 receiver_is_class_object (tree receiver, int self, int super)
6296 tree chain, exp, arg;
6298 /* The receiver is 'self' or 'super' in the context of a class method. */
6299 if (objc_method_context
6300 && TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
6303 ? CLASS_SUPER_NAME (implementation_template)
6304 : CLASS_NAME (implementation_template));
6306 if (flag_next_runtime)
6308 /* The receiver is a variable created by
6309 build_class_reference_decl. */
6310 if (TREE_CODE (receiver) == VAR_DECL && IS_CLASS (TREE_TYPE (receiver)))
6311 /* Look up the identifier. */
6312 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
6313 if (TREE_PURPOSE (chain) == receiver)
6314 return TREE_VALUE (chain);
6317 /* The receiver is a function call that returns an id. Check if
6318 it is a call to objc_getClass, if so, pick up the class name. */
6319 if (TREE_CODE (receiver) == CALL_EXPR
6320 && (exp = CALL_EXPR_FN (receiver))
6321 && TREE_CODE (exp) == ADDR_EXPR
6322 && (exp = TREE_OPERAND (exp, 0))
6323 && TREE_CODE (exp) == FUNCTION_DECL
6324 /* For some reason, we sometimes wind up with multiple FUNCTION_DECL
6325 prototypes for objc_get_class(). Thankfully, they seem to share the
6326 same function type. */
6327 && TREE_TYPE (exp) == TREE_TYPE (objc_get_class_decl)
6328 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (exp)), TAG_GETCLASS)
6329 /* We have a call to objc_get_class/objc_getClass! */
6330 && (arg = CALL_EXPR_ARG (receiver, 0)))
6333 if (TREE_CODE (arg) == ADDR_EXPR
6334 && (arg = TREE_OPERAND (arg, 0))
6335 && TREE_CODE (arg) == STRING_CST)
6336 /* Finally, we have the class name. */
6337 return get_identifier (TREE_STRING_POINTER (arg));
6342 /* If we are currently building a message expr, this holds
6343 the identifier of the selector of the message. This is
6344 used when printing warnings about argument mismatches. */
6346 static tree current_objc_message_selector = 0;
6349 objc_message_selector (void)
6351 return current_objc_message_selector;
6354 /* Construct an expression for sending a message.
6355 MESS has the object to send to in TREE_PURPOSE
6356 and the argument list (including selector) in TREE_VALUE.
6358 (*(<abstract_decl>(*)())_msg)(receiver, selTransTbl[n], ...);
6359 (*(<abstract_decl>(*)())_msgSuper)(receiver, selTransTbl[n], ...); */
6362 objc_build_message_expr (tree mess)
6364 tree receiver = TREE_PURPOSE (mess);
6367 tree args = TREE_PURPOSE (TREE_VALUE (mess));
6369 tree args = TREE_VALUE (mess);
6371 tree method_params = NULL_TREE;
6373 if (TREE_CODE (receiver) == ERROR_MARK || TREE_CODE (args) == ERROR_MARK)
6374 return error_mark_node;
6376 /* Obtain the full selector name. */
6377 if (TREE_CODE (args) == IDENTIFIER_NODE)
6378 /* A unary selector. */
6380 else if (TREE_CODE (args) == TREE_LIST)
6381 sel_name = build_keyword_selector (args);
6385 /* Build the parameter list to give to the method. */
6386 if (TREE_CODE (args) == TREE_LIST)
6388 method_params = chainon (args, TREE_VALUE (TREE_VALUE (mess)));
6391 tree chain = args, prev = NULL_TREE;
6393 /* We have a keyword selector--check for comma expressions. */
6396 tree element = TREE_VALUE (chain);
6398 /* We have a comma expression, must collapse... */
6399 if (TREE_CODE (element) == TREE_LIST)
6402 TREE_CHAIN (prev) = element;
6407 chain = TREE_CHAIN (chain);
6409 method_params = args;
6414 if (processing_template_decl)
6415 /* Must wait until template instantiation time. */
6416 return build_min_nt (MESSAGE_SEND_EXPR, receiver, sel_name,
6420 return objc_finish_message_expr (receiver, sel_name, method_params);
6423 /* Look up method SEL_NAME that would be suitable for receiver
6424 of type 'id' (if IS_CLASS is zero) or 'Class' (if IS_CLASS is
6425 nonzero), and report on any duplicates. */
6428 lookup_method_in_hash_lists (tree sel_name, int is_class)
6430 hash method_prototype = NULL;
6433 method_prototype = hash_lookup (nst_method_hash_list,
6436 if (!method_prototype)
6438 method_prototype = hash_lookup (cls_method_hash_list,
6443 return check_duplicates (method_prototype, 1, is_class);
6446 /* The 'objc_finish_message_expr' routine is called from within
6447 'objc_build_message_expr' for non-template functions. In the case of
6448 C++ template functions, it is called from 'build_expr_from_tree'
6449 (in decl2.c) after RECEIVER and METHOD_PARAMS have been expanded. */
6452 objc_finish_message_expr (tree receiver, tree sel_name, tree method_params)
6454 tree method_prototype = NULL_TREE, rprotos = NULL_TREE, rtype;
6455 tree selector, retval, class_tree;
6456 int self, super, have_cast;
6458 /* We have used the receiver, so mark it as read. */
6459 mark_exp_read (receiver);
6461 /* Extract the receiver of the message, as well as its type
6462 (where the latter may take the form of a cast or be inferred
6463 from the implementation context). */
6465 while (TREE_CODE (rtype) == COMPOUND_EXPR
6466 || TREE_CODE (rtype) == MODIFY_EXPR
6467 || CONVERT_EXPR_P (rtype)
6468 || TREE_CODE (rtype) == COMPONENT_REF)
6469 rtype = TREE_OPERAND (rtype, 0);
6470 self = (rtype == self_decl);
6471 super = (rtype == UOBJC_SUPER_decl);
6472 rtype = TREE_TYPE (receiver);
6473 have_cast = (TREE_CODE (receiver) == NOP_EXPR
6474 || (TREE_CODE (receiver) == COMPOUND_EXPR
6475 && !IS_SUPER (rtype)));
6477 /* If we are calling [super dealloc], reset our warning flag. */
6478 if (super && !strcmp ("dealloc", IDENTIFIER_POINTER (sel_name)))
6479 should_call_super_dealloc = 0;
6481 /* If the receiver is a class object, retrieve the corresponding
6482 @interface, if one exists. */
6483 class_tree = receiver_is_class_object (receiver, self, super);
6485 /* Now determine the receiver type (if an explicit cast has not been
6490 rtype = lookup_interface (class_tree);
6491 /* Handle `self' and `super'. */
6494 if (!CLASS_SUPER_NAME (implementation_template))
6496 error ("no super class declared in @interface for %qE",
6497 CLASS_NAME (implementation_template));
6498 return error_mark_node;
6500 rtype = lookup_interface (CLASS_SUPER_NAME (implementation_template));
6503 rtype = lookup_interface (CLASS_NAME (implementation_template));
6506 /* If receiver is of type `id' or `Class' (or if the @interface for a
6507 class is not visible), we shall be satisfied with the existence of
6508 any instance or class method. */
6509 if (objc_is_id (rtype))
6511 class_tree = (IS_CLASS (rtype) ? objc_class_name : NULL_TREE);
6512 rprotos = (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype))
6513 ? TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype))
6519 /* If messaging 'id <Protos>' or 'Class <Proto>', first search
6520 in protocols themselves for the method prototype. */
6522 = lookup_method_in_protocol_list (rprotos, sel_name,
6523 class_tree != NULL_TREE);
6525 /* If messaging 'Class <Proto>' but did not find a class method
6526 prototype, search for an instance method instead, and warn
6527 about having done so. */
6528 if (!method_prototype && !rtype && class_tree != NULL_TREE)
6531 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
6533 if (method_prototype)
6534 warning (0, "found %<-%E%> instead of %<+%E%> in protocol(s)",
6535 sel_name, sel_name);
6541 tree orig_rtype = rtype;
6543 if (TREE_CODE (rtype) == POINTER_TYPE)
6544 rtype = TREE_TYPE (rtype);
6545 /* Traverse typedef aliases */
6546 while (TREE_CODE (rtype) == RECORD_TYPE && OBJC_TYPE_NAME (rtype)
6547 && TREE_CODE (OBJC_TYPE_NAME (rtype)) == TYPE_DECL
6548 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype)))
6549 rtype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype));
6550 if (TYPED_OBJECT (rtype))
6552 rprotos = TYPE_OBJC_PROTOCOL_LIST (rtype);
6553 rtype = TYPE_OBJC_INTERFACE (rtype);
6555 /* If we could not find an @interface declaration, we must have
6556 only seen a @class declaration; so, we cannot say anything
6557 more intelligent about which methods the receiver will
6559 if (!rtype || TREE_CODE (rtype) == IDENTIFIER_NODE)
6562 /* We could not find an @interface declaration, yet Message maybe in a
6563 @class's protocol. */
6564 if (!method_prototype && rprotos)
6566 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
6568 else if (TREE_CODE (rtype) == CLASS_INTERFACE_TYPE
6569 || TREE_CODE (rtype) == CLASS_IMPLEMENTATION_TYPE)
6571 /* We have a valid ObjC class name. Look up the method name
6572 in the published @interface for the class (and its
6575 = lookup_method_static (rtype, sel_name, class_tree != NULL_TREE);
6577 /* If the method was not found in the @interface, it may still
6578 exist locally as part of the @implementation. */
6579 if (!method_prototype && objc_implementation_context
6580 && CLASS_NAME (objc_implementation_context)
6581 == OBJC_TYPE_NAME (rtype))
6585 ? CLASS_CLS_METHODS (objc_implementation_context)
6586 : CLASS_NST_METHODS (objc_implementation_context)),
6589 /* If we haven't found a candidate method by now, try looking for
6590 it in the protocol list. */
6591 if (!method_prototype && rprotos)
6593 = lookup_method_in_protocol_list (rprotos, sel_name,
6594 class_tree != NULL_TREE);
6598 warning (0, "invalid receiver type %qs",
6599 identifier_to_locale (gen_type_name (orig_rtype)));
6600 /* After issuing the "invalid receiver" warning, perform method
6601 lookup as if we were messaging 'id'. */
6602 rtype = rprotos = NULL_TREE;
6607 /* For 'id' or 'Class' receivers, search in the global hash table
6608 as a last resort. For all receivers, warn if protocol searches
6610 if (!method_prototype)
6613 warning (0, "%<%c%E%> not found in protocol(s)",
6614 (class_tree ? '+' : '-'),
6619 = lookup_method_in_hash_lists (sel_name, class_tree != NULL_TREE);
6622 if (!method_prototype)
6624 static bool warn_missing_methods = false;
6627 warning (0, "%qE may not respond to %<%c%E%>",
6628 OBJC_TYPE_NAME (rtype),
6629 (class_tree ? '+' : '-'),
6631 /* If we are messaging an 'id' or 'Class' object and made it here,
6632 then we have failed to find _any_ instance or class method,
6635 warning (0, "no %<%c%E%> method found",
6636 (class_tree ? '+' : '-'),
6639 if (!warn_missing_methods)
6641 warning_at (input_location,
6642 0, "(Messages without a matching method signature");
6643 warning_at (input_location,
6644 0, "will be assumed to return %<id%> and accept");
6645 warning_at (input_location,
6646 0, "%<...%> as arguments.)");
6647 warn_missing_methods = true;
6651 /* Save the selector name for printing error messages. */
6652 current_objc_message_selector = sel_name;
6654 /* Build the parameters list for looking up the method.
6655 These are the object itself and the selector. */
6657 if (flag_typed_selectors)
6658 selector = build_typed_selector_reference (input_location,
6659 sel_name, method_prototype);
6661 selector = build_selector_reference (input_location, sel_name);
6663 retval = build_objc_method_call (input_location, super, method_prototype,
6665 selector, method_params);
6667 current_objc_message_selector = 0;
6672 /* Build a tree expression to send OBJECT the operation SELECTOR,
6673 looking up the method on object LOOKUP_OBJECT (often same as OBJECT),
6674 assuming the method has prototype METHOD_PROTOTYPE.
6675 (That is an INSTANCE_METHOD_DECL or CLASS_METHOD_DECL.)
6676 LOC is the location of the expression to build.
6677 Use METHOD_PARAMS as list of args to pass to the method.
6678 If SUPER_FLAG is nonzero, we look up the superclass's method. */
6681 build_objc_method_call (location_t loc, int super_flag, tree method_prototype,
6682 tree lookup_object, tree selector,
6685 tree sender = (super_flag ? umsg_super_decl :
6686 (!flag_next_runtime || flag_nil_receivers
6687 ? (flag_objc_direct_dispatch
6690 : umsg_nonnil_decl));
6691 tree rcv_p = (super_flag ? objc_super_type : objc_object_type);
6692 VEC(tree, gc) *parms = NULL;
6693 unsigned nparm = (method_params ? list_length (method_params) : 0);
6695 /* If a prototype for the method to be called exists, then cast
6696 the sender's return type and arguments to match that of the method.
6697 Otherwise, leave sender as is. */
6700 ? TREE_VALUE (TREE_TYPE (method_prototype))
6701 : objc_object_type);
6703 = build_pointer_type
6704 (build_function_type
6707 (method_prototype, METHOD_REF, super_flag)));
6710 lookup_object = build_c_cast (loc, rcv_p, lookup_object);
6712 /* Use SAVE_EXPR to avoid evaluating the receiver twice. */
6713 lookup_object = save_expr (lookup_object);
6715 /* Param list + 2 slots for object and selector. */
6716 parms = VEC_alloc (tree, gc, nparm + 2);
6718 if (flag_next_runtime)
6720 /* If we are returning a struct in memory, and the address
6721 of that memory location is passed as a hidden first
6722 argument, then change which messenger entry point this
6723 expr will call. NB: Note that sender_cast remains
6724 unchanged (it already has a struct return type). */
6725 if (!targetm.calls.struct_value_rtx (0, 0)
6726 && (TREE_CODE (ret_type) == RECORD_TYPE
6727 || TREE_CODE (ret_type) == UNION_TYPE)
6728 && targetm.calls.return_in_memory (ret_type, 0))
6729 sender = (super_flag ? umsg_super_stret_decl :
6730 flag_nil_receivers ? umsg_stret_decl : umsg_nonnil_stret_decl);
6732 method = build_fold_addr_expr_loc (input_location, sender);
6733 /* Pass the object to the method. */
6734 VEC_quick_push (tree, parms, lookup_object);
6738 /* This is the portable (GNU) way. */
6739 /* First, call the lookup function to get a pointer to the method,
6740 then cast the pointer, then call it with the method arguments. */
6741 VEC(tree, gc) *tv = VEC_alloc (tree, gc, 2);
6742 VEC_quick_push (tree, tv, lookup_object);
6743 VEC_quick_push (tree, tv, selector);
6744 method = build_function_call_vec (loc, sender, tv, NULL);
6745 VEC_free (tree, gc, tv);
6747 /* Pass the appropriate object to the method. */
6748 VEC_quick_push (tree, parms, (super_flag ? self_decl : lookup_object));
6751 /* Pass the selector to the method. */
6752 VEC_quick_push (tree, parms, selector);
6753 /* Now append the remainder of the parms. */
6755 for (; method_params; method_params = TREE_CHAIN (method_params))
6756 VEC_quick_push (tree, parms, TREE_VALUE (method_params));
6758 /* Build an obj_type_ref, with the correct cast for the method call. */
6759 t = build3 (OBJ_TYPE_REF, sender_cast, method,
6760 lookup_object, size_zero_node);
6761 t = build_function_call_vec (loc, t, parms, NULL);\
6762 VEC_free (tree, gc, parms);
6767 build_protocol_reference (tree p)
6770 const char *proto_name;
6772 /* static struct _objc_protocol _OBJC_PROTOCOL_<mumble>; */
6774 proto_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL", p);
6775 decl = start_var_decl (objc_protocol_template, proto_name);
6777 PROTOCOL_FORWARD_DECL (p) = decl;
6780 /* This function is called by the parser when (and only when) a
6781 @protocol() expression is found, in order to compile it. */
6783 objc_build_protocol_expr (tree protoname)
6786 tree p = lookup_protocol (protoname);
6790 error ("cannot find protocol declaration for %qE",
6792 return error_mark_node;
6795 if (!PROTOCOL_FORWARD_DECL (p))
6796 build_protocol_reference (p);
6798 expr = build_unary_op (input_location,
6799 ADDR_EXPR, PROTOCOL_FORWARD_DECL (p), 0);
6801 /* ??? Ideally we'd build the reference with objc_protocol_type directly,
6802 if we have it, rather than converting it here. */
6803 expr = convert (objc_protocol_type, expr);
6805 /* The @protocol() expression is being compiled into a pointer to a
6806 statically allocated instance of the Protocol class. To become
6807 usable at runtime, the 'isa' pointer of the instance need to be
6808 fixed up at runtime by the runtime library, to point to the
6809 actual 'Protocol' class. */
6811 /* For the GNU runtime, put the static Protocol instance in the list
6812 of statically allocated instances, so that we make sure that its
6813 'isa' pointer is fixed up at runtime by the GNU runtime library
6814 to point to the Protocol class (at runtime, when loading the
6815 module, the GNU runtime library loops on the statically allocated
6816 instances (as found in the defs field in objc_symtab) and fixups
6817 all the 'isa' pointers of those objects). */
6818 if (! flag_next_runtime)
6820 /* This type is a struct containing the fields of a Protocol
6821 object. (Cfr. objc_protocol_type instead is the type of a pointer
6822 to such a struct). */
6823 tree protocol_struct_type = xref_tag
6824 (RECORD_TYPE, get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
6827 /* Look for the list of Protocol statically allocated instances
6828 to fixup at runtime. Create a new list to hold Protocol
6829 statically allocated instances, if the list is not found. At
6830 present there is only another list, holding NSConstantString
6831 static instances to be fixed up at runtime. */
6832 for (chain = &objc_static_instances;
6833 *chain && TREE_VALUE (*chain) != protocol_struct_type;
6834 chain = &TREE_CHAIN (*chain));
6837 *chain = tree_cons (NULL_TREE, protocol_struct_type, NULL_TREE);
6838 add_objc_string (OBJC_TYPE_NAME (protocol_struct_type),
6842 /* Add this statically allocated instance to the Protocol list. */
6843 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE,
6844 PROTOCOL_FORWARD_DECL (p),
6845 TREE_PURPOSE (*chain));
6852 /* This function is called by the parser when a @selector() expression
6853 is found, in order to compile it. It is only called by the parser
6854 and only to compile a @selector(). LOC is the location of the
6857 objc_build_selector_expr (location_t loc, tree selnamelist)
6861 /* Obtain the full selector name. */
6862 if (TREE_CODE (selnamelist) == IDENTIFIER_NODE)
6863 /* A unary selector. */
6864 selname = selnamelist;
6865 else if (TREE_CODE (selnamelist) == TREE_LIST)
6866 selname = build_keyword_selector (selnamelist);
6870 /* If we are required to check @selector() expressions as they
6871 are found, check that the selector has been declared. */
6872 if (warn_undeclared_selector)
6874 /* Look the selector up in the list of all known class and
6875 instance methods (up to this line) to check that the selector
6879 /* First try with instance methods. */
6880 hsh = hash_lookup (nst_method_hash_list, selname);
6882 /* If not found, try with class methods. */
6885 hsh = hash_lookup (cls_method_hash_list, selname);
6888 /* If still not found, print out a warning. */
6891 warning (0, "undeclared selector %qE", selname);
6896 if (flag_typed_selectors)
6897 return build_typed_selector_reference (loc, selname, 0);
6899 return build_selector_reference (loc, selname);
6902 /* This is used to implement @encode(). See gcc/doc/objc.texi,
6903 section '@encode'. */
6905 objc_build_encode_expr (tree type)
6910 encode_type (type, obstack_object_size (&util_obstack),
6911 OBJC_ENCODE_INLINE_DEFS);
6912 obstack_1grow (&util_obstack, 0); /* null terminate string */
6913 string = XOBFINISH (&util_obstack, const char *);
6915 /* Synthesize a string that represents the encoded struct/union. */
6916 result = my_build_string (strlen (string) + 1, string);
6917 obstack_free (&util_obstack, util_firstobj);
6922 build_ivar_reference (tree id)
6924 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
6926 /* Historically, a class method that produced objects (factory
6927 method) would assign `self' to the instance that it
6928 allocated. This would effectively turn the class method into
6929 an instance method. Following this assignment, the instance
6930 variables could be accessed. That practice, while safe,
6931 violates the simple rule that a class method should not refer
6932 to an instance variable. It's better to catch the cases
6933 where this is done unknowingly than to support the above
6935 warning (0, "instance variable %qE accessed in class method",
6937 self_decl = convert (objc_instance_type, self_decl); /* cast */
6940 return objc_build_component_ref (build_indirect_ref (input_location,
6941 self_decl, RO_ARROW),
6945 /* Compute a hash value for a given method SEL_NAME. */
6948 hash_func (tree sel_name)
6950 const unsigned char *s
6951 = (const unsigned char *)IDENTIFIER_POINTER (sel_name);
6955 h = h * 67 + *s++ - 113;
6962 nst_method_hash_list = ggc_alloc_cleared_vec_hash (SIZEHASHTABLE);
6963 cls_method_hash_list = ggc_alloc_cleared_vec_hash (SIZEHASHTABLE);
6965 /* Initialize the hash table used to hold the constant string objects. */
6966 string_htab = htab_create_ggc (31, string_hash,
6969 /* Initialize the hash table used to hold EH-volatilized types. */
6970 volatilized_htab = htab_create_ggc (31, volatilized_hash,
6971 volatilized_eq, NULL);
6974 /* WARNING!!!! hash_enter is called with a method, and will peek
6975 inside to find its selector! But hash_lookup is given a selector
6976 directly, and looks for the selector that's inside the found
6977 entry's key (method) for comparison. */
6980 hash_enter (hash *hashlist, tree method)
6983 int slot = hash_func (METHOD_SEL_NAME (method)) % SIZEHASHTABLE;
6985 obj = ggc_alloc_hashed_entry ();
6987 obj->next = hashlist[slot];
6990 hashlist[slot] = obj; /* append to front */
6994 hash_lookup (hash *hashlist, tree sel_name)
6998 target = hashlist[hash_func (sel_name) % SIZEHASHTABLE];
7002 if (sel_name == METHOD_SEL_NAME (target->key))
7005 target = target->next;
7011 hash_add_attr (hash entry, tree value)
7015 obj = ggc_alloc_hashed_attribute ();
7016 obj->next = entry->list;
7019 entry->list = obj; /* append to front */
7023 lookup_method (tree mchain, tree method)
7027 if (TREE_CODE (method) == IDENTIFIER_NODE)
7030 key = METHOD_SEL_NAME (method);
7034 if (METHOD_SEL_NAME (mchain) == key)
7037 mchain = DECL_CHAIN (mchain);
7042 /* Look up a class (if OBJC_LOOKUP_CLASS is set in FLAGS) or instance method
7043 in INTERFACE, along with any categories and protocols attached thereto.
7044 If method is not found, and the OBJC_LOOKUP_NO_SUPER is _not_ set in FLAGS,
7045 recursively examine the INTERFACE's superclass. If OBJC_LOOKUP_CLASS is
7046 set, OBJC_LOOKUP_NO_SUPER is cleared, and no suitable class method could
7047 be found in INTERFACE or any of its superclasses, look for an _instance_
7048 method of the same name in the root class as a last resort.
7050 If a suitable method cannot be found, return NULL_TREE. */
7053 lookup_method_static (tree interface, tree ident, int flags)
7055 tree meth = NULL_TREE, root_inter = NULL_TREE;
7056 tree inter = interface;
7057 int is_class = (flags & OBJC_LOOKUP_CLASS);
7058 int no_superclasses = (flags & OBJC_LOOKUP_NO_SUPER);
7062 tree chain = is_class ? CLASS_CLS_METHODS (inter) : CLASS_NST_METHODS (inter);
7063 tree category = inter;
7065 /* First, look up the method in the class itself. */
7066 if ((meth = lookup_method (chain, ident)))
7069 /* Failing that, look for the method in each category of the class. */
7070 while ((category = CLASS_CATEGORY_LIST (category)))
7072 chain = is_class ? CLASS_CLS_METHODS (category) : CLASS_NST_METHODS (category);
7074 /* Check directly in each category. */
7075 if ((meth = lookup_method (chain, ident)))
7078 /* Failing that, check in each category's protocols. */
7079 if (CLASS_PROTOCOL_LIST (category))
7081 if ((meth = (lookup_method_in_protocol_list
7082 (CLASS_PROTOCOL_LIST (category), ident, is_class))))
7087 /* If not found in categories, check in protocols of the main class. */
7088 if (CLASS_PROTOCOL_LIST (inter))
7090 if ((meth = (lookup_method_in_protocol_list
7091 (CLASS_PROTOCOL_LIST (inter), ident, is_class))))
7095 /* If we were instructed not to look in superclasses, don't. */
7096 if (no_superclasses)
7099 /* Failing that, climb up the inheritance hierarchy. */
7101 inter = lookup_interface (CLASS_SUPER_NAME (inter));
7105 /* If no class (factory) method was found, check if an _instance_
7106 method of the same name exists in the root class. This is what
7107 the Objective-C runtime will do. If an instance method was not
7109 return is_class ? lookup_method_static (root_inter, ident, 0): NULL_TREE;
7112 /* Add the method to the hash list if it doesn't contain an identical
7116 add_method_to_hash_list (hash *hash_list, tree method)
7120 if (!(hsh = hash_lookup (hash_list, METHOD_SEL_NAME (method))))
7122 /* Install on a global chain. */
7123 hash_enter (hash_list, method);
7127 /* Check types against those; if different, add to a list. */
7129 int already_there = comp_proto_with_proto (method, hsh->key, 1);
7130 for (loop = hsh->list; !already_there && loop; loop = loop->next)
7131 already_there |= comp_proto_with_proto (method, loop->value, 1);
7133 hash_add_attr (hsh, method);
7138 objc_add_method (tree klass, tree method, int is_class, bool is_optional)
7142 /* @optional methods are added to protocol's OPTIONAL list */
7145 gcc_assert (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE);
7146 if (!(mth = lookup_method (is_class
7147 ? PROTOCOL_OPTIONAL_CLS_METHODS (klass)
7148 : PROTOCOL_OPTIONAL_NST_METHODS (klass),
7153 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_CLS_METHODS (klass);
7154 PROTOCOL_OPTIONAL_CLS_METHODS (klass) = method;
7158 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_NST_METHODS (klass);
7159 PROTOCOL_OPTIONAL_NST_METHODS (klass) = method;
7163 else if (!(mth = lookup_method (is_class
7164 ? CLASS_CLS_METHODS (klass)
7165 : CLASS_NST_METHODS (klass), method)))
7167 /* put method on list in reverse order */
7170 DECL_CHAIN (method) = CLASS_CLS_METHODS (klass);
7171 CLASS_CLS_METHODS (klass) = method;
7175 DECL_CHAIN (method) = CLASS_NST_METHODS (klass);
7176 CLASS_NST_METHODS (klass) = method;
7181 /* When processing an @interface for a class or category, give hard
7182 errors on methods with identical selectors but differing argument
7183 and/or return types. We do not do this for @implementations, because
7184 C/C++ will do it for us (i.e., there will be duplicate function
7185 definition errors). */
7186 if ((TREE_CODE (klass) == CLASS_INTERFACE_TYPE
7187 || TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE)
7188 && !comp_proto_with_proto (method, mth, 1))
7189 error ("duplicate declaration of method %<%c%E%>",
7190 is_class ? '+' : '-',
7191 METHOD_SEL_NAME (mth));
7195 add_method_to_hash_list (cls_method_hash_list, method);
7198 add_method_to_hash_list (nst_method_hash_list, method);
7200 /* Instance methods in root classes (and categories thereof)
7201 may act as class methods as a last resort. We also add
7202 instance methods listed in @protocol declarations to
7203 the class hash table, on the assumption that @protocols
7204 may be adopted by root classes or categories. */
7205 if (TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
7206 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7207 klass = lookup_interface (CLASS_NAME (klass));
7209 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE
7210 || !CLASS_SUPER_NAME (klass))
7211 add_method_to_hash_list (cls_method_hash_list, method);
7218 add_class (tree class_name, tree name)
7220 struct interface_tuple **slot;
7222 /* Put interfaces on list in reverse order. */
7223 TREE_CHAIN (class_name) = interface_chain;
7224 interface_chain = class_name;
7226 if (interface_htab == NULL)
7227 interface_htab = htab_create_ggc (31, hash_interface, eq_interface, NULL);
7228 slot = (struct interface_tuple **)
7229 htab_find_slot_with_hash (interface_htab, name,
7230 IDENTIFIER_HASH_VALUE (name),
7234 *slot = ggc_alloc_cleared_interface_tuple ();
7237 (*slot)->class_name = class_name;
7239 return interface_chain;
7243 add_category (tree klass, tree category)
7245 /* Put categories on list in reverse order. */
7246 tree cat = lookup_category (klass, CLASS_SUPER_NAME (category));
7250 warning (0, "duplicate interface declaration for category %<%E(%E)%>",
7252 CLASS_SUPER_NAME (category));
7256 CLASS_CATEGORY_LIST (category) = CLASS_CATEGORY_LIST (klass);
7257 CLASS_CATEGORY_LIST (klass) = category;
7261 /* Called after parsing each instance variable declaration. Necessary to
7262 preserve typedefs and implement public/private...
7264 VISIBILITY is 1 for public, 0 for protected, and 2 for private. */
7267 add_instance_variable (tree klass, int visibility, tree field_decl)
7269 tree field_type = TREE_TYPE (field_decl);
7270 const char *ivar_name = DECL_NAME (field_decl)
7271 ? identifier_to_locale (IDENTIFIER_POINTER (DECL_NAME (field_decl)))
7275 if (TREE_CODE (field_type) == REFERENCE_TYPE)
7277 error ("illegal reference type specified for instance variable %qs",
7279 /* Return class as is without adding this ivar. */
7284 if (field_type == error_mark_node || !TYPE_SIZE (field_type)
7285 || TYPE_SIZE (field_type) == error_mark_node)
7286 /* 'type[0]' is allowed, but 'type[]' is not! */
7288 error ("instance variable %qs has unknown size", ivar_name);
7289 /* Return class as is without adding this ivar. */
7294 /* Check if the ivar being added has a non-POD C++ type. If so, we will
7295 need to either (1) warn the user about it or (2) generate suitable
7296 constructor/destructor call from '- .cxx_construct' or '- .cxx_destruct'
7297 methods (if '-fobjc-call-cxx-cdtors' was specified). */
7298 if (MAYBE_CLASS_TYPE_P (field_type)
7299 && (TYPE_NEEDS_CONSTRUCTING (field_type)
7300 || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type)
7301 || TYPE_POLYMORPHIC_P (field_type)))
7303 tree type_name = OBJC_TYPE_NAME (field_type);
7305 if (flag_objc_call_cxx_cdtors)
7307 /* Since the ObjC runtime will be calling the constructors and
7308 destructors for us, the only thing we can't handle is the lack
7309 of a default constructor. */
7310 if (TYPE_NEEDS_CONSTRUCTING (field_type)
7311 && !TYPE_HAS_DEFAULT_CONSTRUCTOR (field_type))
7313 warning (0, "type %qE has no default constructor to call",
7316 /* If we cannot call a constructor, we should also avoid
7317 calling the destructor, for symmetry. */
7318 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7319 warning (0, "destructor for %qE shall not be run either",
7325 static bool warn_cxx_ivars = false;
7327 if (TYPE_POLYMORPHIC_P (field_type))
7329 /* Vtable pointers are Real Bad(tm), since Obj-C cannot
7331 error ("type %qE has virtual member functions", type_name);
7332 error ("illegal aggregate type %qE specified "
7333 "for instance variable %qs",
7334 type_name, ivar_name);
7335 /* Return class as is without adding this ivar. */
7339 /* User-defined constructors and destructors are not known to Obj-C
7340 and hence will not be called. This may or may not be a problem. */
7341 if (TYPE_NEEDS_CONSTRUCTING (field_type))
7342 warning (0, "type %qE has a user-defined constructor", type_name);
7343 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7344 warning (0, "type %qE has a user-defined destructor", type_name);
7346 if (!warn_cxx_ivars)
7348 warning (0, "C++ constructors and destructors will not "
7349 "be invoked for Objective-C fields");
7350 warn_cxx_ivars = true;
7356 /* Overload the public attribute, it is not used for FIELD_DECLs. */
7360 TREE_PUBLIC (field_decl) = 0;
7361 TREE_PRIVATE (field_decl) = 0;
7362 TREE_PROTECTED (field_decl) = 1;
7366 TREE_PUBLIC (field_decl) = 1;
7367 TREE_PRIVATE (field_decl) = 0;
7368 TREE_PROTECTED (field_decl) = 0;
7372 TREE_PUBLIC (field_decl) = 0;
7373 TREE_PRIVATE (field_decl) = 1;
7374 TREE_PROTECTED (field_decl) = 0;
7379 CLASS_RAW_IVARS (klass) = chainon (CLASS_RAW_IVARS (klass), field_decl);
7385 is_ivar (tree decl_chain, tree ident)
7387 for ( ; decl_chain; decl_chain = DECL_CHAIN (decl_chain))
7388 if (DECL_NAME (decl_chain) == ident)
7393 /* True if the ivar is private and we are not in its implementation. */
7396 is_private (tree decl)
7398 return (TREE_PRIVATE (decl)
7399 && ! is_ivar (CLASS_IVARS (implementation_template),
7403 /* We have an instance variable reference;, check to see if it is public. */
7406 objc_is_public (tree expr, tree identifier)
7408 tree basetype, decl;
7411 if (processing_template_decl)
7415 if (TREE_TYPE (expr) == error_mark_node)
7418 basetype = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
7420 if (basetype && TREE_CODE (basetype) == RECORD_TYPE)
7422 if (TYPE_HAS_OBJC_INFO (basetype) && TYPE_OBJC_INTERFACE (basetype))
7424 tree klass = lookup_interface (OBJC_TYPE_NAME (basetype));
7428 error ("cannot find interface declaration for %qE",
7429 OBJC_TYPE_NAME (basetype));
7433 if ((decl = is_ivar (get_class_ivars (klass, true), identifier)))
7435 if (TREE_PUBLIC (decl))
7438 /* Important difference between the Stepstone translator:
7439 all instance variables should be public within the context
7440 of the implementation. */
7441 if (objc_implementation_context
7442 && ((TREE_CODE (objc_implementation_context)
7443 == CLASS_IMPLEMENTATION_TYPE)
7444 || (TREE_CODE (objc_implementation_context)
7445 == CATEGORY_IMPLEMENTATION_TYPE)))
7447 tree curtype = TYPE_MAIN_VARIANT
7448 (CLASS_STATIC_TEMPLATE
7449 (implementation_template));
7451 if (basetype == curtype
7452 || DERIVED_FROM_P (basetype, curtype))
7454 int priv = is_private (decl);
7457 error ("instance variable %qE is declared private",
7464 /* The 2.95.2 compiler sometimes allowed C functions to access
7465 non-@public ivars. We will let this slide for now... */
7466 if (!objc_method_context)
7468 warning (0, "instance variable %qE is %s; "
7469 "this will be a hard error in the future",
7471 TREE_PRIVATE (decl) ? "@private" : "@protected");
7475 error ("instance variable %qE is declared %s",
7477 TREE_PRIVATE (decl) ? "private" : "protected");
7486 /* Make sure all entries in CHAIN are also in LIST. */
7489 check_methods (tree chain, tree list, int mtype)
7495 if (!lookup_method (list, chain))
7499 if (TREE_CODE (objc_implementation_context)
7500 == CLASS_IMPLEMENTATION_TYPE)
7501 warning (0, "incomplete implementation of class %qE",
7502 CLASS_NAME (objc_implementation_context));
7503 else if (TREE_CODE (objc_implementation_context)
7504 == CATEGORY_IMPLEMENTATION_TYPE)
7505 warning (0, "incomplete implementation of category %qE",
7506 CLASS_SUPER_NAME (objc_implementation_context));
7510 warning (0, "method definition for %<%c%E%> not found",
7511 mtype, METHOD_SEL_NAME (chain));
7514 chain = DECL_CHAIN (chain);
7520 /* Check if KLASS, or its superclasses, explicitly conforms to PROTOCOL. */
7523 conforms_to_protocol (tree klass, tree protocol)
7525 if (TREE_CODE (protocol) == PROTOCOL_INTERFACE_TYPE)
7527 tree p = CLASS_PROTOCOL_LIST (klass);
7528 while (p && TREE_VALUE (p) != protocol)
7533 tree super = (CLASS_SUPER_NAME (klass)
7534 ? lookup_interface (CLASS_SUPER_NAME (klass))
7536 int tmp = super ? conforms_to_protocol (super, protocol) : 0;
7545 /* Make sure all methods in CHAIN are accessible as MTYPE methods in
7546 CONTEXT. This is one of two mechanisms to check protocol integrity. */
7549 check_methods_accessible (tree chain, tree context, int mtype)
7553 tree base_context = context;
7557 context = base_context;
7561 list = CLASS_CLS_METHODS (context);
7563 list = CLASS_NST_METHODS (context);
7565 if (lookup_method (list, chain))
7568 else if (TREE_CODE (context) == CLASS_IMPLEMENTATION_TYPE
7569 || TREE_CODE (context) == CLASS_INTERFACE_TYPE)
7570 context = (CLASS_SUPER_NAME (context)
7571 ? lookup_interface (CLASS_SUPER_NAME (context))
7574 else if (TREE_CODE (context) == CATEGORY_IMPLEMENTATION_TYPE
7575 || TREE_CODE (context) == CATEGORY_INTERFACE_TYPE)
7576 context = (CLASS_NAME (context)
7577 ? lookup_interface (CLASS_NAME (context))
7583 if (context == NULL_TREE)
7587 if (TREE_CODE (objc_implementation_context)
7588 == CLASS_IMPLEMENTATION_TYPE)
7589 warning (0, "incomplete implementation of class %qE",
7590 CLASS_NAME (objc_implementation_context));
7591 else if (TREE_CODE (objc_implementation_context)
7592 == CATEGORY_IMPLEMENTATION_TYPE)
7593 warning (0, "incomplete implementation of category %qE",
7594 CLASS_SUPER_NAME (objc_implementation_context));
7597 warning (0, "method definition for %<%c%E%> not found",
7598 mtype, METHOD_SEL_NAME (chain));
7601 chain = TREE_CHAIN (chain); /* next method... */
7606 /* Check whether the current interface (accessible via
7607 'objc_implementation_context') actually implements protocol P, along
7608 with any protocols that P inherits. */
7611 check_protocol (tree p, const char *type, tree name)
7613 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
7617 /* Ensure that all protocols have bodies! */
7620 f1 = check_methods (PROTOCOL_CLS_METHODS (p),
7621 CLASS_CLS_METHODS (objc_implementation_context),
7623 f2 = check_methods (PROTOCOL_NST_METHODS (p),
7624 CLASS_NST_METHODS (objc_implementation_context),
7629 f1 = check_methods_accessible (PROTOCOL_CLS_METHODS (p),
7630 objc_implementation_context,
7632 f2 = check_methods_accessible (PROTOCOL_NST_METHODS (p),
7633 objc_implementation_context,
7638 warning (0, "%s %qE does not fully implement the %qE protocol",
7639 type, name, PROTOCOL_NAME (p));
7642 /* Check protocols recursively. */
7643 if (PROTOCOL_LIST (p))
7645 tree subs = PROTOCOL_LIST (p);
7647 lookup_interface (CLASS_SUPER_NAME (implementation_template));
7651 tree sub = TREE_VALUE (subs);
7653 /* If the superclass does not conform to the protocols
7654 inherited by P, then we must! */
7655 if (!super_class || !conforms_to_protocol (super_class, sub))
7656 check_protocol (sub, type, name);
7657 subs = TREE_CHAIN (subs);
7662 /* Check whether the current interface (accessible via
7663 'objc_implementation_context') actually implements the protocols listed
7667 check_protocols (tree proto_list, const char *type, tree name)
7669 for ( ; proto_list; proto_list = TREE_CHAIN (proto_list))
7671 tree p = TREE_VALUE (proto_list);
7673 check_protocol (p, type, name);
7677 /* Make sure that the class CLASS_NAME is defined
7678 CODE says which kind of thing CLASS_NAME ought to be.
7679 It can be CLASS_INTERFACE_TYPE, CLASS_IMPLEMENTATION_TYPE,
7680 CATEGORY_INTERFACE_TYPE, or CATEGORY_IMPLEMENTATION_TYPE. */
7683 start_class (enum tree_code code, tree class_name, tree super_name,
7689 if (current_namespace != global_namespace) {
7690 error ("Objective-C declarations may only appear in global scope");
7692 #endif /* OBJCPLUS */
7694 if (objc_implementation_context)
7696 warning (0, "%<@end%> missing in implementation context");
7697 finish_class (objc_implementation_context);
7698 objc_ivar_chain = NULL_TREE;
7699 objc_implementation_context = NULL_TREE;
7702 klass = make_node (code);
7703 TYPE_LANG_SLOT_1 (klass) = make_tree_vec (CLASS_LANG_SLOT_ELTS);
7705 /* Check for existence of the super class, if one was specified. Note
7706 that we must have seen an @interface, not just a @class. If we
7707 are looking at a @compatibility_alias, traverse it first. */
7708 if ((code == CLASS_INTERFACE_TYPE || code == CLASS_IMPLEMENTATION_TYPE)
7711 tree super = objc_is_class_name (super_name);
7713 if (!super || !lookup_interface (super))
7715 error ("cannot find interface declaration for %qE, superclass of %qE",
7716 super ? super : super_name,
7718 super_name = NULL_TREE;
7724 CLASS_NAME (klass) = class_name;
7725 CLASS_SUPER_NAME (klass) = super_name;
7726 CLASS_CLS_METHODS (klass) = NULL_TREE;
7728 if (! objc_is_class_name (class_name)
7729 && (decl = lookup_name (class_name)))
7731 error ("%qE redeclared as different kind of symbol",
7733 error ("previous declaration of %q+D",
7737 if (code == CLASS_IMPLEMENTATION_TYPE)
7742 for (chain = implemented_classes; chain; chain = TREE_CHAIN (chain))
7743 if (TREE_VALUE (chain) == class_name)
7745 error ("reimplementation of class %qE",
7747 return error_mark_node;
7749 implemented_classes = tree_cons (NULL_TREE, class_name,
7750 implemented_classes);
7753 /* Reset for multiple classes per file. */
7756 objc_implementation_context = klass;
7758 /* Lookup the interface for this implementation. */
7760 if (!(implementation_template = lookup_interface (class_name)))
7762 warning (0, "cannot find interface declaration for %qE",
7764 add_class (implementation_template = objc_implementation_context,
7768 /* If a super class has been specified in the implementation,
7769 insure it conforms to the one specified in the interface. */
7772 && (super_name != CLASS_SUPER_NAME (implementation_template)))
7774 tree previous_name = CLASS_SUPER_NAME (implementation_template);
7775 error ("conflicting super class name %qE",
7778 error ("previous declaration of %qE", previous_name);
7780 error ("previous declaration");
7783 else if (! super_name)
7785 CLASS_SUPER_NAME (objc_implementation_context)
7786 = CLASS_SUPER_NAME (implementation_template);
7790 else if (code == CLASS_INTERFACE_TYPE)
7792 if (lookup_interface (class_name))
7794 error ("duplicate interface declaration for class %qE",
7796 warning (0, "duplicate interface declaration for class %qE",
7800 add_class (klass, class_name);
7803 CLASS_PROTOCOL_LIST (klass)
7804 = lookup_and_install_protocols (protocol_list);
7807 else if (code == CATEGORY_INTERFACE_TYPE)
7809 tree class_category_is_assoc_with;
7811 /* For a category, class_name is really the name of the class that
7812 the following set of methods will be associated with. We must
7813 find the interface so that can derive the objects template. */
7815 if (!(class_category_is_assoc_with = lookup_interface (class_name)))
7817 error ("cannot find interface declaration for %qE",
7819 exit (FATAL_EXIT_CODE);
7822 add_category (class_category_is_assoc_with, klass);
7825 CLASS_PROTOCOL_LIST (klass)
7826 = lookup_and_install_protocols (protocol_list);
7829 else if (code == CATEGORY_IMPLEMENTATION_TYPE)
7831 /* Reset for multiple classes per file. */
7834 objc_implementation_context = klass;
7836 /* For a category, class_name is really the name of the class that
7837 the following set of methods will be associated with. We must
7838 find the interface so that can derive the objects template. */
7840 if (!(implementation_template = lookup_interface (class_name)))
7842 error ("cannot find interface declaration for %qE",
7844 exit (FATAL_EXIT_CODE);
7851 continue_class (tree klass)
7853 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE
7854 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7856 struct imp_entry *imp_entry;
7858 /* Check consistency of the instance variables. */
7860 if (CLASS_RAW_IVARS (klass))
7861 check_ivars (implementation_template, klass);
7863 /* code generation */
7866 push_lang_context (lang_name_c);
7869 build_private_template (implementation_template);
7870 uprivate_record = CLASS_STATIC_TEMPLATE (implementation_template);
7871 objc_instance_type = build_pointer_type (uprivate_record);
7873 imp_entry = ggc_alloc_imp_entry ();
7875 imp_entry->next = imp_list;
7876 imp_entry->imp_context = klass;
7877 imp_entry->imp_template = implementation_template;
7879 synth_forward_declarations ();
7880 imp_entry->class_decl = UOBJC_CLASS_decl;
7881 imp_entry->meta_decl = UOBJC_METACLASS_decl;
7882 imp_entry->has_cxx_cdtors = 0;
7884 /* Append to front and increment count. */
7885 imp_list = imp_entry;
7886 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7892 pop_lang_context ();
7893 #endif /* OBJCPLUS */
7895 return get_class_ivars (implementation_template, true);
7898 else if (TREE_CODE (klass) == CLASS_INTERFACE_TYPE)
7901 push_lang_context (lang_name_c);
7902 #endif /* OBJCPLUS */
7904 objc_collecting_ivars = 1;
7905 build_private_template (klass);
7906 objc_collecting_ivars = 0;
7909 pop_lang_context ();
7910 #endif /* OBJCPLUS */
7916 return error_mark_node;
7919 /* This is called once we see the "@end" in an interface/implementation. */
7922 finish_class (tree klass)
7924 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7926 /* All code generation is done in finish_objc. */
7928 if (implementation_template != objc_implementation_context)
7930 /* Ensure that all method listed in the interface contain bodies. */
7931 check_methods (CLASS_CLS_METHODS (implementation_template),
7932 CLASS_CLS_METHODS (objc_implementation_context), '+');
7933 check_methods (CLASS_NST_METHODS (implementation_template),
7934 CLASS_NST_METHODS (objc_implementation_context), '-');
7936 if (CLASS_PROTOCOL_LIST (implementation_template))
7937 check_protocols (CLASS_PROTOCOL_LIST (implementation_template),
7939 CLASS_NAME (objc_implementation_context));
7943 else if (TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7945 tree category = lookup_category (implementation_template, CLASS_SUPER_NAME (klass));
7949 /* Ensure all method listed in the interface contain bodies. */
7950 check_methods (CLASS_CLS_METHODS (category),
7951 CLASS_CLS_METHODS (objc_implementation_context), '+');
7952 check_methods (CLASS_NST_METHODS (category),
7953 CLASS_NST_METHODS (objc_implementation_context), '-');
7955 if (CLASS_PROTOCOL_LIST (category))
7956 check_protocols (CLASS_PROTOCOL_LIST (category),
7958 CLASS_SUPER_NAME (objc_implementation_context));
7964 add_protocol (tree protocol)
7966 /* Put protocol on list in reverse order. */
7967 TREE_CHAIN (protocol) = protocol_chain;
7968 protocol_chain = protocol;
7969 return protocol_chain;
7973 lookup_protocol (tree ident)
7977 for (chain = protocol_chain; chain; chain = TREE_CHAIN (chain))
7978 if (ident == PROTOCOL_NAME (chain))
7984 /* This function forward declares the protocols named by NAMES. If
7985 they are already declared or defined, the function has no effect. */
7988 objc_declare_protocols (tree names)
7993 if (current_namespace != global_namespace) {
7994 error ("Objective-C declarations may only appear in global scope");
7996 #endif /* OBJCPLUS */
7998 for (list = names; list; list = TREE_CHAIN (list))
8000 tree name = TREE_VALUE (list);
8002 if (lookup_protocol (name) == NULL_TREE)
8004 tree protocol = make_node (PROTOCOL_INTERFACE_TYPE);
8006 TYPE_LANG_SLOT_1 (protocol)
8007 = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8008 PROTOCOL_NAME (protocol) = name;
8009 PROTOCOL_LIST (protocol) = NULL_TREE;
8010 add_protocol (protocol);
8011 PROTOCOL_DEFINED (protocol) = 0;
8012 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8018 start_protocol (enum tree_code code, tree name, tree list)
8023 if (current_namespace != global_namespace) {
8024 error ("Objective-C declarations may only appear in global scope");
8026 #endif /* OBJCPLUS */
8028 protocol = lookup_protocol (name);
8032 protocol = make_node (code);
8033 TYPE_LANG_SLOT_1 (protocol) = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8035 PROTOCOL_NAME (protocol) = name;
8036 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
8037 add_protocol (protocol);
8038 PROTOCOL_DEFINED (protocol) = 1;
8039 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8041 check_protocol_recursively (protocol, list);
8043 else if (! PROTOCOL_DEFINED (protocol))
8045 PROTOCOL_DEFINED (protocol) = 1;
8046 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
8048 check_protocol_recursively (protocol, list);
8052 warning (0, "duplicate declaration for protocol %qE",
8059 /* "Encode" a data type into a string, which grows in util_obstack.
8061 The format is described in gcc/doc/objc.texi, section 'Type
8064 Most of the encode_xxx functions have a 'type' argument, which is
8065 the type to encode, and an integer 'curtype' argument, which is the
8066 index in the encoding string of the beginning of the encoding of
8067 the current type, and allows you to find what characters have
8068 already been written for the current type (they are the ones in the
8069 current encoding string starting from 'curtype').
8071 For example, if we are encoding a method which returns 'int' and
8072 takes a 'char **' argument, then when we get to the point of
8073 encoding the 'char **' argument, the encoded string already
8074 contains 'i12@0:4' (assuming a pointer size of 4 bytes). So,
8075 'curtype' will be set to 7 when starting to encode 'char **'.
8076 During the whole of the encoding of 'char **', 'curtype' will be
8077 fixed at 7, so the routine encoding the second pointer can find out
8078 that it's actually encoding a pointer to a pointer by looking
8079 backwards at what has already been encoded for the current type,
8080 and seeing there is a "^" (meaning a pointer) in there.
8084 /* Encode type qualifiers encodes one of the "PQ" Objective-C
8085 keywords, ie 'in', 'out', 'inout', 'bycopy', 'byref', 'oneway'.
8086 'const', instead, is encoded directly as part of the type.
8090 encode_type_qualifiers (tree declspecs)
8094 for (spec = declspecs; spec; spec = TREE_CHAIN (spec))
8096 /* FIXME: Shouldn't we use token->keyword here ? */
8097 if (ridpointers[(int) RID_IN] == TREE_VALUE (spec))
8098 obstack_1grow (&util_obstack, 'n');
8099 else if (ridpointers[(int) RID_INOUT] == TREE_VALUE (spec))
8100 obstack_1grow (&util_obstack, 'N');
8101 else if (ridpointers[(int) RID_OUT] == TREE_VALUE (spec))
8102 obstack_1grow (&util_obstack, 'o');
8103 else if (ridpointers[(int) RID_BYCOPY] == TREE_VALUE (spec))
8104 obstack_1grow (&util_obstack, 'O');
8105 else if (ridpointers[(int) RID_BYREF] == TREE_VALUE (spec))
8106 obstack_1grow (&util_obstack, 'R');
8107 else if (ridpointers[(int) RID_ONEWAY] == TREE_VALUE (spec))
8108 obstack_1grow (&util_obstack, 'V');
8112 /* Determine if a pointee is marked read-only. Only used by the NeXT
8113 runtime to be compatible with gcc-3.3. */
8116 pointee_is_readonly (tree pointee)
8118 while (POINTER_TYPE_P (pointee))
8119 pointee = TREE_TYPE (pointee);
8121 return TYPE_READONLY (pointee);
8124 /* Encode a pointer type. */
8127 encode_pointer (tree type, int curtype, int format)
8129 tree pointer_to = TREE_TYPE (type);
8131 if (flag_next_runtime)
8133 /* This code is used to be compatible with gcc-3.3. */
8134 /* For historical/compatibility reasons, the read-only qualifier
8135 of the pointee gets emitted _before_ the '^'. The read-only
8136 qualifier of the pointer itself gets ignored, _unless_ we are
8137 looking at a typedef! Also, do not emit the 'r' for anything
8138 but the outermost type! */
8139 if (!generating_instance_variables
8140 && (obstack_object_size (&util_obstack) - curtype <= 1)
8141 && (TYPE_NAME (type) && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
8142 ? TYPE_READONLY (type)
8143 : pointee_is_readonly (pointer_to)))
8144 obstack_1grow (&util_obstack, 'r');
8147 if (TREE_CODE (pointer_to) == RECORD_TYPE)
8149 if (OBJC_TYPE_NAME (pointer_to)
8150 && TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE)
8152 const char *name = IDENTIFIER_POINTER (OBJC_TYPE_NAME (pointer_to));
8154 if (strcmp (name, TAG_OBJECT) == 0) /* '@' */
8156 obstack_1grow (&util_obstack, '@');
8159 else if (TYPE_HAS_OBJC_INFO (pointer_to)
8160 && TYPE_OBJC_INTERFACE (pointer_to))
8162 if (generating_instance_variables)
8164 obstack_1grow (&util_obstack, '@');
8165 obstack_1grow (&util_obstack, '"');
8166 obstack_grow (&util_obstack, name, strlen (name));
8167 obstack_1grow (&util_obstack, '"');
8172 obstack_1grow (&util_obstack, '@');
8176 else if (strcmp (name, TAG_CLASS) == 0) /* '#' */
8178 obstack_1grow (&util_obstack, '#');
8181 else if (strcmp (name, TAG_SELECTOR) == 0) /* ':' */
8183 obstack_1grow (&util_obstack, ':');
8188 else if (TREE_CODE (pointer_to) == INTEGER_TYPE
8189 && TYPE_MODE (pointer_to) == QImode)
8191 tree pname = TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE
8192 ? OBJC_TYPE_NAME (pointer_to)
8193 : DECL_NAME (OBJC_TYPE_NAME (pointer_to));
8195 /* (BOOL *) are an exception and are encoded as ^c, while all
8196 other pointers to char are encoded as *. */
8197 if (strcmp (IDENTIFIER_POINTER (pname), "BOOL"))
8199 if (!flag_next_runtime)
8201 /* The NeXT runtime adds the 'r' before getting here. */
8203 /* It appears that "r*" means "const char *" rather than
8204 "char *const". "char *const" is encoded as "*",
8205 which is identical to "char *", so the "const" is
8206 unfortunately lost. */
8207 if (TYPE_READONLY (pointer_to))
8208 obstack_1grow (&util_obstack, 'r');
8211 obstack_1grow (&util_obstack, '*');
8216 /* We have a normal pointer type that does not get special treatment. */
8217 obstack_1grow (&util_obstack, '^');
8218 encode_type (pointer_to, curtype, format);
8222 encode_array (tree type, int curtype, int format)
8224 tree an_int_cst = TYPE_SIZE (type);
8225 tree array_of = TREE_TYPE (type);
8228 if (an_int_cst == NULL)
8230 /* We are trying to encode an incomplete array. An incomplete
8231 array is forbidden as part of an instance variable. */
8232 if (generating_instance_variables)
8234 /* TODO: Detect this error earlier. */
8235 error ("instance variable has unknown size");
8239 /* So the only case in which an incomplete array could occur is
8240 if we are encoding the arguments or return value of a method.
8241 In that case, an incomplete array argument or return value
8242 (eg, -(void)display: (char[])string) is treated like a
8243 pointer because that is how the compiler does the function
8244 call. A special, more complicated case, is when the
8245 incomplete array is the last member of a struct (eg, if we
8246 are encoding "struct { unsigned long int a;double b[];}"),
8247 which is again part of a method argument/return value. In
8248 that case, we really need to communicate to the runtime that
8249 there is an incomplete array (not a pointer!) there. So, we
8250 detect that special case and encode it as a zero-length
8253 Try to detect that we are part of a struct. We do this by
8254 searching for '=' in the type encoding for the current type.
8255 NB: This hack assumes that you can't use '=' as part of a C
8259 char *enc = obstack_base (&util_obstack) + curtype;
8260 if (memchr (enc, '=',
8261 obstack_object_size (&util_obstack) - curtype) == NULL)
8263 /* We are not inside a struct. Encode the array as a
8265 encode_pointer (type, curtype, format);
8270 /* Else, we are in a struct, and we encode it as a zero-length
8272 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT)0);
8274 else if (TREE_INT_CST_LOW (TYPE_SIZE (array_of)) == 0)
8275 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT)0);
8277 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC,
8278 TREE_INT_CST_LOW (an_int_cst)
8279 / TREE_INT_CST_LOW (TYPE_SIZE (array_of)));
8281 obstack_grow (&util_obstack, buffer, strlen (buffer));
8282 encode_type (array_of, curtype, format);
8283 obstack_1grow (&util_obstack, ']');
8287 /* Encode a vector. The vector type is a GCC extension to C. */
8289 encode_vector (tree type, int curtype, int format)
8291 tree vector_of = TREE_TYPE (type);
8294 /* Vectors are like simple fixed-size arrays. */
8296 /* Output ![xx,yy,<code>] where xx is the vector_size, yy is the
8297 alignment of the vector, and <code> is the base type. Eg, int
8298 __attribute__ ((vector_size (16))) gets encoded as ![16,32,i]
8299 assuming that the alignment is 32 bytes. We include size and
8300 alignment in bytes so that the runtime does not have to have any
8301 knowledge of the actual types.
8303 sprintf (buffer, "![" HOST_WIDE_INT_PRINT_DEC ",%d",
8304 /* We want to compute the equivalent of sizeof (<vector>).
8305 Code inspired by c_sizeof_or_alignof_type. */
8306 ((TREE_INT_CST_LOW (TYPE_SIZE_UNIT (type))
8307 / (TYPE_PRECISION (char_type_node) / BITS_PER_UNIT))),
8308 /* We want to compute the equivalent of __alignof__
8309 (<vector>). Code inspired by
8310 c_sizeof_or_alignof_type. */
8311 TYPE_ALIGN_UNIT (type));
8312 obstack_grow (&util_obstack, buffer, strlen (buffer));
8313 encode_type (vector_of, curtype, format);
8314 obstack_1grow (&util_obstack, ']');
8319 encode_aggregate_fields (tree type, bool pointed_to, int curtype, int format)
8321 tree field = TYPE_FIELDS (type);
8323 for (; field; field = DECL_CHAIN (field))
8326 /* C++ static members, and things that are not field at all,
8327 should not appear in the encoding. */
8328 if (TREE_CODE (field) != FIELD_DECL || TREE_STATIC (field))
8332 /* Recursively encode fields of embedded base classes. */
8333 if (DECL_ARTIFICIAL (field) && !DECL_NAME (field)
8334 && TREE_CODE (TREE_TYPE (field)) == RECORD_TYPE)
8336 encode_aggregate_fields (TREE_TYPE (field),
8337 pointed_to, curtype, format);
8341 if (generating_instance_variables && !pointed_to)
8343 tree fname = DECL_NAME (field);
8345 obstack_1grow (&util_obstack, '"');
8347 if (fname && TREE_CODE (fname) == IDENTIFIER_NODE)
8348 obstack_grow (&util_obstack,
8349 IDENTIFIER_POINTER (fname),
8350 strlen (IDENTIFIER_POINTER (fname)));
8352 obstack_1grow (&util_obstack, '"');
8355 encode_field_decl (field, curtype, format);
8360 encode_aggregate_within (tree type, int curtype, int format, int left,
8364 /* NB: aggregates that are pointed to have slightly different encoding
8365 rules in that you never encode the names of instance variables. */
8366 int ob_size = obstack_object_size (&util_obstack);
8367 bool inline_contents = false;
8368 bool pointed_to = false;
8370 if (flag_next_runtime)
8372 if (ob_size > 0 && *(obstack_next_free (&util_obstack) - 1) == '^')
8375 if ((format == OBJC_ENCODE_INLINE_DEFS || generating_instance_variables)
8376 && (!pointed_to || ob_size - curtype == 1
8377 || (ob_size - curtype == 2
8378 && *(obstack_next_free (&util_obstack) - 2) == 'r')))
8379 inline_contents = true;
8383 /* c0 and c1 are the last two characters in the encoding of the
8384 current type; if the last two characters were '^' or '^r',
8385 then we are encoding an aggregate that is "pointed to". The
8386 comment above applies: in that case we should avoid encoding
8387 the names of instance variables.
8389 char c1 = ob_size > 1 ? *(obstack_next_free (&util_obstack) - 2) : 0;
8390 char c0 = ob_size > 0 ? *(obstack_next_free (&util_obstack) - 1) : 0;
8392 if (c0 == '^' || (c1 == '^' && c0 == 'r'))
8395 if (format == OBJC_ENCODE_INLINE_DEFS || generating_instance_variables)
8398 inline_contents = true;
8401 /* Note that the check (ob_size - curtype < 2) prevents
8402 infinite recursion when encoding a structure which is
8403 a linked list (eg, struct node { struct node *next;
8404 }). Each time we follow a pointer, we add one
8405 character to ob_size, and curtype is fixed, so after
8406 at most two pointers we stop inlining contents and
8409 The other case where we don't inline is "^r", which
8410 is a pointer to a constant struct.
8412 if ((ob_size - curtype <= 2) && !(c0 == 'r'))
8413 inline_contents = true;
8418 /* Traverse struct aliases; it is important to get the
8419 original struct and its tag name (if any). */
8420 type = TYPE_MAIN_VARIANT (type);
8421 name = OBJC_TYPE_NAME (type);
8422 /* Open parenth/bracket. */
8423 obstack_1grow (&util_obstack, left);
8425 /* Encode the struct/union tag name, or '?' if a tag was
8426 not provided. Typedef aliases do not qualify. */
8428 /* For compatibility with the NeXT runtime, ObjC++ encodes template
8429 args as a composite struct tag name. */
8430 if (name && TREE_CODE (name) == IDENTIFIER_NODE
8431 /* Did this struct have a tag? */
8432 && !TYPE_WAS_ANONYMOUS (type))
8433 obstack_grow (&util_obstack,
8434 decl_as_string (type, TFF_DECL_SPECIFIERS | TFF_UNQUALIFIED_NAME),
8435 strlen (decl_as_string (type, TFF_DECL_SPECIFIERS | TFF_UNQUALIFIED_NAME)));
8437 if (name && TREE_CODE (name) == IDENTIFIER_NODE)
8438 obstack_grow (&util_obstack,
8439 IDENTIFIER_POINTER (name),
8440 strlen (IDENTIFIER_POINTER (name)));
8443 obstack_1grow (&util_obstack, '?');
8445 /* Encode the types (and possibly names) of the inner fields,
8447 if (inline_contents)
8449 obstack_1grow (&util_obstack, '=');
8450 encode_aggregate_fields (type, pointed_to, curtype, format);
8452 /* Close parenth/bracket. */
8453 obstack_1grow (&util_obstack, right);
8456 /* Encode a bitfield NeXT-style (i.e., without a bit offset or the underlying
8460 encode_next_bitfield (int width)
8463 sprintf (buffer, "b%d", width);
8464 obstack_grow (&util_obstack, buffer, strlen (buffer));
8468 /* Encodes 'type', ignoring type qualifiers (which you should encode
8469 beforehand if needed) with the exception of 'const', which is
8470 encoded by encode_type. See above for the explanation of
8471 'curtype'. 'format' can be OBJC_ENCODE_INLINE_DEFS or
8472 OBJC_ENCODE_DONT_INLINE_DEFS.
8475 encode_type (tree type, int curtype, int format)
8477 enum tree_code code = TREE_CODE (type);
8479 /* Ignore type qualifiers other than 'const' when encoding a
8482 if (type == error_mark_node)
8485 if (!flag_next_runtime)
8487 if (TYPE_READONLY (type))
8488 obstack_1grow (&util_obstack, 'r');
8494 if (flag_next_runtime)
8496 /* Kludge for backwards-compatibility with gcc-3.3: enums
8497 are always encoded as 'i' no matter what type they
8498 actually are (!). */
8499 obstack_1grow (&util_obstack, 'i');
8502 /* Else, they are encoded exactly like the integer type that is
8503 used by the compiler to store them. */
8507 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8509 case 8: c = TYPE_UNSIGNED (type) ? 'C' : 'c'; break;
8510 case 16: c = TYPE_UNSIGNED (type) ? 'S' : 's'; break;
8512 if (flag_next_runtime)
8515 /* Another legacy kludge for compatiblity with
8516 gcc-3.3: 32-bit longs are encoded as 'l' or 'L',
8517 but not always. For typedefs, we need to use 'i'
8518 or 'I' instead if encoding a struct field, or a
8520 int_type = ((!generating_instance_variables
8521 && (obstack_object_size (&util_obstack)
8522 == (unsigned) curtype))
8523 ? TYPE_MAIN_VARIANT (type)
8526 if (int_type == long_unsigned_type_node
8527 || int_type == long_integer_type_node)
8528 c = TYPE_UNSIGNED (type) ? 'L' : 'l';
8530 c = TYPE_UNSIGNED (type) ? 'I' : 'i';
8534 if (type == long_unsigned_type_node
8535 || type == long_integer_type_node)
8536 c = TYPE_UNSIGNED (type) ? 'L' : 'l';
8538 c = TYPE_UNSIGNED (type) ? 'I' : 'i';
8541 case 64: c = TYPE_UNSIGNED (type) ? 'Q' : 'q'; break;
8542 case 128: c = TYPE_UNSIGNED (type) ? 'T' : 't'; break;
8545 obstack_1grow (&util_obstack, c);
8551 /* Floating point types. */
8552 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8554 case 32: c = 'f'; break;
8555 case 64: c = 'd'; break;
8557 case 128: c = 'D'; break;
8560 obstack_1grow (&util_obstack, c);
8564 obstack_1grow (&util_obstack, 'v');
8568 obstack_1grow (&util_obstack, 'B');
8572 encode_array (type, curtype, format);
8577 case REFERENCE_TYPE:
8579 encode_pointer (type, curtype, format);
8583 encode_aggregate_within (type, curtype, format, '{', '}');
8587 encode_aggregate_within (type, curtype, format, '(', ')');
8590 case FUNCTION_TYPE: /* '?' means an unknown type. */
8591 obstack_1grow (&util_obstack, '?');
8595 /* A complex is encoded as 'j' followed by the inner type (eg,
8596 "_Complex int" is encoded as 'ji'). */
8597 obstack_1grow (&util_obstack, 'j');
8598 encode_type (TREE_TYPE (type), curtype, format);
8602 encode_vector (type, curtype, format);
8606 warning (0, "unknown type %s found during Objective-C encoding",
8607 gen_type_name (type));
8608 obstack_1grow (&util_obstack, '?');
8612 if (flag_next_runtime)
8614 /* Super-kludge. Some ObjC qualifier and type combinations need
8615 to be rearranged for compatibility with gcc-3.3. */
8616 if (code == POINTER_TYPE && obstack_object_size (&util_obstack) >= 3)
8618 char *enc = obstack_base (&util_obstack) + curtype;
8620 /* Rewrite "in const" from "nr" to "rn". */
8621 if (curtype >= 1 && !strncmp (enc - 1, "nr", 2))
8622 strncpy (enc - 1, "rn", 2);
8628 encode_gnu_bitfield (int position, tree type, int size)
8630 enum tree_code code = TREE_CODE (type);
8632 char charType = '?';
8634 /* This code is only executed for the GNU runtime, so we can ignore
8635 the NeXT runtime kludge of always encoding enums as 'i' no matter
8636 what integers they actually are. */
8637 if (code == INTEGER_TYPE || code == ENUMERAL_TYPE)
8639 if (integer_zerop (TYPE_MIN_VALUE (type)))
8640 /* Unsigned integer types. */
8642 if (TYPE_MODE (type) == QImode)
8644 else if (TYPE_MODE (type) == HImode)
8646 else if (TYPE_MODE (type) == SImode)
8648 if (type == long_unsigned_type_node)
8653 else if (TYPE_MODE (type) == DImode)
8657 /* Signed integer types. */
8659 if (TYPE_MODE (type) == QImode)
8661 else if (TYPE_MODE (type) == HImode)
8663 else if (TYPE_MODE (type) == SImode)
8665 if (type == long_integer_type_node)
8671 else if (TYPE_MODE (type) == DImode)
8677 /* Do not do any encoding, produce an error and keep going. */
8678 error ("trying to encode non-integer type as a bitfield");
8682 sprintf (buffer, "b%d%c%d", position, charType, size);
8683 obstack_grow (&util_obstack, buffer, strlen (buffer));
8687 encode_field_decl (tree field_decl, int curtype, int format)
8690 /* C++ static members, and things that are not fields at all,
8691 should not appear in the encoding. */
8692 if (TREE_CODE (field_decl) != FIELD_DECL || TREE_STATIC (field_decl))
8696 /* Generate the bitfield typing information, if needed. Note the difference
8697 between GNU and NeXT runtimes. */
8698 if (DECL_BIT_FIELD_TYPE (field_decl))
8700 int size = tree_low_cst (DECL_SIZE (field_decl), 1);
8702 if (flag_next_runtime)
8703 encode_next_bitfield (size);
8705 encode_gnu_bitfield (int_bit_position (field_decl),
8706 DECL_BIT_FIELD_TYPE (field_decl), size);
8709 encode_type (TREE_TYPE (field_decl), curtype, format);
8712 /* Decay array and function parameters into pointers. */
8715 objc_decay_parm_type (tree type)
8717 if (TREE_CODE (type) == ARRAY_TYPE || TREE_CODE (type) == FUNCTION_TYPE)
8718 type = build_pointer_type (TREE_CODE (type) == ARRAY_TYPE
8725 static GTY(()) tree objc_parmlist = NULL_TREE;
8727 /* Append PARM to a list of formal parameters of a method, making a necessary
8728 array-to-pointer adjustment along the way. */
8731 objc_push_parm (tree parm)
8735 if (TREE_TYPE (parm) == error_mark_node)
8737 objc_parmlist = chainon (objc_parmlist, parm);
8741 /* Decay arrays and functions into pointers. */
8742 type = objc_decay_parm_type (TREE_TYPE (parm));
8744 /* If the parameter type has been decayed, a new PARM_DECL needs to be
8746 if (type != TREE_TYPE (parm))
8747 parm = build_decl (input_location, PARM_DECL, DECL_NAME (parm), type);
8749 DECL_ARG_TYPE (parm)
8750 = lang_hooks.types.type_promotes_to (TREE_TYPE (parm));
8752 /* Record constancy and volatility. */
8753 c_apply_type_quals_to_decl
8754 ((TYPE_READONLY (TREE_TYPE (parm)) ? TYPE_QUAL_CONST : 0)
8755 | (TYPE_RESTRICT (TREE_TYPE (parm)) ? TYPE_QUAL_RESTRICT : 0)
8756 | (TYPE_VOLATILE (TREE_TYPE (parm)) ? TYPE_QUAL_VOLATILE : 0), parm);
8758 objc_parmlist = chainon (objc_parmlist, parm);
8761 /* Retrieve the formal parameter list constructed via preceding calls to
8762 objc_push_parm(). */
8766 objc_get_parm_info (int have_ellipsis ATTRIBUTE_UNUSED)
8768 static struct c_arg_info *
8769 objc_get_parm_info (int have_ellipsis)
8773 tree parm_info = objc_parmlist;
8774 objc_parmlist = NULL_TREE;
8778 tree parm_info = objc_parmlist;
8779 struct c_arg_info *arg_info;
8780 /* The C front-end requires an elaborate song and dance at
8783 declare_parm_level ();
8786 tree next = DECL_CHAIN (parm_info);
8788 DECL_CHAIN (parm_info) = NULL_TREE;
8789 parm_info = pushdecl (parm_info);
8790 finish_decl (parm_info, input_location, NULL_TREE, NULL_TREE, NULL_TREE);
8793 arg_info = get_parm_info (have_ellipsis);
8795 objc_parmlist = NULL_TREE;
8800 /* Synthesize the formal parameters 'id self' and 'SEL _cmd' needed for ObjC
8801 method definitions. In the case of instance methods, we can be more
8802 specific as to the type of 'self'. */
8805 synth_self_and_ucmd_args (void)
8809 if (objc_method_context
8810 && TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL)
8811 self_type = objc_instance_type;
8813 /* Really a `struct objc_class *'. However, we allow people to
8814 assign to self, which changes its type midstream. */
8815 self_type = objc_object_type;
8818 objc_push_parm (build_decl (input_location,
8819 PARM_DECL, self_id, self_type));
8822 objc_push_parm (build_decl (input_location,
8823 PARM_DECL, ucmd_id, objc_selector_type));
8826 /* Transform an Objective-C method definition into a static C function
8827 definition, synthesizing the first two arguments, "self" and "_cmd",
8831 start_method_def (tree method)
8837 struct c_arg_info *parm_info;
8839 int have_ellipsis = 0;
8841 /* If we are defining a "dealloc" method in a non-root class, we
8842 will need to check if a [super dealloc] is missing, and warn if
8844 if(CLASS_SUPER_NAME (objc_implementation_context)
8845 && !strcmp ("dealloc", IDENTIFIER_POINTER (METHOD_SEL_NAME (method))))
8846 should_call_super_dealloc = 1;
8848 should_call_super_dealloc = 0;
8850 /* Required to implement _msgSuper. */
8851 objc_method_context = method;
8852 UOBJC_SUPER_decl = NULL_TREE;
8854 /* Generate prototype declarations for arguments..."new-style". */
8855 synth_self_and_ucmd_args ();
8857 /* Generate argument declarations if a keyword_decl. */
8858 parmlist = METHOD_SEL_ARGS (method);
8861 tree type = TREE_VALUE (TREE_TYPE (parmlist)), parm;
8863 parm = build_decl (input_location,
8864 PARM_DECL, KEYWORD_ARG_NAME (parmlist), type);
8865 objc_push_parm (parm);
8866 parmlist = DECL_CHAIN (parmlist);
8869 if (METHOD_ADD_ARGS (method))
8873 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (method));
8874 akey; akey = TREE_CHAIN (akey))
8876 objc_push_parm (TREE_VALUE (akey));
8879 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8883 parm_info = objc_get_parm_info (have_ellipsis);
8885 really_start_method (objc_method_context, parm_info);
8888 /* Return 1 if TYPE1 is equivalent to TYPE2
8889 for purposes of method overloading. */
8892 objc_types_are_equivalent (tree type1, tree type2)
8897 /* Strip away indirections. */
8898 while ((TREE_CODE (type1) == ARRAY_TYPE || TREE_CODE (type1) == POINTER_TYPE)
8899 && (TREE_CODE (type1) == TREE_CODE (type2)))
8900 type1 = TREE_TYPE (type1), type2 = TREE_TYPE (type2);
8901 if (TYPE_MAIN_VARIANT (type1) != TYPE_MAIN_VARIANT (type2))
8904 type1 = (TYPE_HAS_OBJC_INFO (type1)
8905 ? TYPE_OBJC_PROTOCOL_LIST (type1)
8907 type2 = (TYPE_HAS_OBJC_INFO (type2)
8908 ? TYPE_OBJC_PROTOCOL_LIST (type2)
8911 if (list_length (type1) == list_length (type2))
8913 for (; type2; type2 = TREE_CHAIN (type2))
8914 if (!lookup_protocol_in_reflist (type1, TREE_VALUE (type2)))
8921 /* Return 1 if TYPE1 has the same size and alignment as TYPE2. */
8924 objc_types_share_size_and_alignment (tree type1, tree type2)
8926 return (simple_cst_equal (TYPE_SIZE (type1), TYPE_SIZE (type2))
8927 && TYPE_ALIGN (type1) == TYPE_ALIGN (type2));
8930 /* Return 1 if PROTO1 is equivalent to PROTO2
8931 for purposes of method overloading. Ordinarily, the type signatures
8932 should match up exactly, unless STRICT is zero, in which case we
8933 shall allow differences in which the size and alignment of a type
8937 comp_proto_with_proto (tree proto1, tree proto2, int strict)
8941 /* The following test is needed in case there are hashing
8943 if (METHOD_SEL_NAME (proto1) != METHOD_SEL_NAME (proto2))
8946 /* Compare return types. */
8947 type1 = TREE_VALUE (TREE_TYPE (proto1));
8948 type2 = TREE_VALUE (TREE_TYPE (proto2));
8950 if (!objc_types_are_equivalent (type1, type2)
8951 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8954 /* Compare argument types. */
8955 for (type1 = get_arg_type_list (proto1, METHOD_REF, 0),
8956 type2 = get_arg_type_list (proto2, METHOD_REF, 0);
8958 type1 = TREE_CHAIN (type1), type2 = TREE_CHAIN (type2))
8960 if (!objc_types_are_equivalent (TREE_VALUE (type1), TREE_VALUE (type2))
8962 || !objc_types_share_size_and_alignment (TREE_VALUE (type1),
8963 TREE_VALUE (type2))))
8967 return (!type1 && !type2);
8970 /* Fold an OBJ_TYPE_REF expression for ObjC method dispatches, where
8971 this occurs. ObjC method dispatches are _not_ like C++ virtual
8972 member function dispatches, and we account for the difference here. */
8975 objc_fold_obj_type_ref (tree ref, tree known_type)
8977 objc_fold_obj_type_ref (tree ref ATTRIBUTE_UNUSED,
8978 tree known_type ATTRIBUTE_UNUSED)
8982 tree v = BINFO_VIRTUALS (TYPE_BINFO (known_type));
8984 /* If the receiver does not have virtual member functions, there
8985 is nothing we can (or need to) do here. */
8989 /* Let C++ handle C++ virtual functions. */
8990 return cp_fold_obj_type_ref (ref, known_type);
8992 /* For plain ObjC, we currently do not need to do anything. */
8998 objc_start_function (tree name, tree type, tree attrs,
9002 struct c_arg_info *params
9006 tree fndecl = build_decl (input_location,
9007 FUNCTION_DECL, name, type);
9010 DECL_ARGUMENTS (fndecl) = params;
9011 DECL_INITIAL (fndecl) = error_mark_node;
9012 DECL_EXTERNAL (fndecl) = 0;
9013 TREE_STATIC (fndecl) = 1;
9014 retrofit_lang_decl (fndecl);
9015 cplus_decl_attributes (&fndecl, attrs, 0);
9016 start_preparsed_function (fndecl, attrs, /*flags=*/SF_DEFAULT);
9018 current_function_returns_value = 0; /* Assume, until we see it does. */
9019 current_function_returns_null = 0;
9021 decl_attributes (&fndecl, attrs, 0);
9022 announce_function (fndecl);
9023 DECL_INITIAL (fndecl) = error_mark_node;
9024 DECL_EXTERNAL (fndecl) = 0;
9025 TREE_STATIC (fndecl) = 1;
9026 current_function_decl = pushdecl (fndecl);
9028 declare_parm_level ();
9029 DECL_RESULT (current_function_decl)
9030 = build_decl (input_location,
9031 RESULT_DECL, NULL_TREE,
9032 TREE_TYPE (TREE_TYPE (current_function_decl)));
9033 DECL_ARTIFICIAL (DECL_RESULT (current_function_decl)) = 1;
9034 DECL_IGNORED_P (DECL_RESULT (current_function_decl)) = 1;
9035 start_fname_decls ();
9036 store_parm_decls_from (params);
9039 TREE_USED (current_function_decl) = 1;
9042 /* - Generate an identifier for the function. the format is "_n_cls",
9043 where 1 <= n <= nMethods, and cls is the name the implementation we
9045 - Install the return type from the method declaration.
9046 - If we have a prototype, check for type consistency. */
9049 really_start_method (tree method,
9053 struct c_arg_info *parmlist
9057 tree ret_type, meth_type;
9059 const char *sel_name, *class_name, *cat_name;
9062 /* Synth the storage class & assemble the return type. */
9063 ret_type = TREE_VALUE (TREE_TYPE (method));
9065 sel_name = IDENTIFIER_POINTER (METHOD_SEL_NAME (method));
9066 class_name = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
9067 cat_name = ((TREE_CODE (objc_implementation_context)
9068 == CLASS_IMPLEMENTATION_TYPE)
9070 : IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
9073 /* Make sure this is big enough for any plausible method label. */
9074 buf = (char *) alloca (50 + strlen (sel_name) + strlen (class_name)
9075 + (cat_name ? strlen (cat_name) : 0));
9077 OBJC_GEN_METHOD_LABEL (buf, TREE_CODE (method) == INSTANCE_METHOD_DECL,
9078 class_name, cat_name, sel_name, method_slot);
9080 method_id = get_identifier (buf);
9083 /* Objective-C methods cannot be overloaded, so we don't need
9084 the type encoding appended. It looks bad anyway... */
9085 push_lang_context (lang_name_c);
9089 = build_function_type (ret_type,
9090 get_arg_type_list (method, METHOD_DEF, 0));
9091 objc_start_function (method_id, meth_type, NULL_TREE, parmlist);
9093 /* Set self_decl from the first argument. */
9094 self_decl = DECL_ARGUMENTS (current_function_decl);
9096 /* Suppress unused warnings. */
9097 TREE_USED (self_decl) = 1;
9098 DECL_READ_P (self_decl) = 1;
9099 TREE_USED (DECL_CHAIN (self_decl)) = 1;
9100 DECL_READ_P (DECL_CHAIN (self_decl)) = 1;
9102 pop_lang_context ();
9105 METHOD_DEFINITION (method) = current_function_decl;
9107 /* Check consistency...start_function, pushdecl, duplicate_decls. */
9109 if (implementation_template != objc_implementation_context)
9112 = lookup_method_static (implementation_template,
9113 METHOD_SEL_NAME (method),
9114 ((TREE_CODE (method) == CLASS_METHOD_DECL)
9115 | OBJC_LOOKUP_NO_SUPER));
9119 if (!comp_proto_with_proto (method, proto, 1))
9121 bool type = TREE_CODE (method) == INSTANCE_METHOD_DECL;
9123 warning_at (DECL_SOURCE_LOCATION (method), 0,
9124 "conflicting types for %<%c%s%>",
9126 identifier_to_locale (gen_method_decl (method)));
9127 inform (DECL_SOURCE_LOCATION (proto),
9128 "previous declaration of %<%c%s%>",
9130 identifier_to_locale (gen_method_decl (proto)));
9135 /* We have a method @implementation even though we did not
9136 see a corresponding @interface declaration (which is allowed
9137 by Objective-C rules). Go ahead and place the method in
9138 the @interface anyway, so that message dispatch lookups
9140 tree interface = implementation_template;
9142 if (TREE_CODE (objc_implementation_context)
9143 == CATEGORY_IMPLEMENTATION_TYPE)
9144 interface = lookup_category
9146 CLASS_SUPER_NAME (objc_implementation_context));
9149 objc_add_method (interface, copy_node (method),
9150 TREE_CODE (method) == CLASS_METHOD_DECL,
9151 /* is_optional= */ false);
9156 static void *UOBJC_SUPER_scope = 0;
9158 /* _n_Method (id self, SEL sel, ...)
9160 struct objc_super _S;
9161 _msgSuper ((_S.self = self, _S.class = _cls, &_S), ...);
9165 get_super_receiver (void)
9167 if (objc_method_context)
9169 tree super_expr, super_expr_list;
9171 if (!UOBJC_SUPER_decl)
9173 UOBJC_SUPER_decl = build_decl (input_location,
9174 VAR_DECL, get_identifier (TAG_SUPER),
9175 objc_super_template);
9176 /* This prevents `unused variable' warnings when compiling with -Wall. */
9177 TREE_USED (UOBJC_SUPER_decl) = 1;
9178 DECL_READ_P (UOBJC_SUPER_decl) = 1;
9179 lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
9180 finish_decl (UOBJC_SUPER_decl, input_location, NULL_TREE, NULL_TREE,
9182 UOBJC_SUPER_scope = objc_get_current_scope ();
9185 /* Set receiver to self. */
9186 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
9187 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
9188 NOP_EXPR, input_location, self_decl,
9190 super_expr_list = super_expr;
9192 /* Set class to begin searching. */
9193 super_expr = objc_build_component_ref (UOBJC_SUPER_decl,
9194 get_identifier ("super_class"));
9196 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
9198 /* [_cls, __cls]Super are "pre-built" in
9199 synth_forward_declarations. */
9201 super_expr = build_modify_expr (input_location, super_expr,
9202 NULL_TREE, NOP_EXPR,
9204 ((TREE_CODE (objc_method_context)
9205 == INSTANCE_METHOD_DECL)
9212 /* We have a category. */
9214 tree super_name = CLASS_SUPER_NAME (implementation_template);
9217 /* Barf if super used in a category of Object. */
9220 error ("no super class declared in interface for %qE",
9221 CLASS_NAME (implementation_template));
9222 return error_mark_node;
9225 if (flag_next_runtime && !flag_zero_link)
9227 super_class = objc_get_class_reference (super_name);
9228 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
9229 /* If we are in a class method, we must retrieve the
9230 _metaclass_ for the current class, pointed at by
9231 the class's "isa" pointer. The following assumes that
9232 "isa" is the first ivar in a class (which it must be). */
9234 = build_indirect_ref
9236 build_c_cast (input_location,
9237 build_pointer_type (objc_class_type),
9238 super_class), RO_UNARY_STAR);
9242 add_class_reference (super_name);
9243 super_class = (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9244 ? objc_get_class_decl : objc_get_meta_class_decl);
9245 assemble_external (super_class);
9247 = build_function_call
9252 my_build_string_pointer
9253 (IDENTIFIER_LENGTH (super_name) + 1,
9254 IDENTIFIER_POINTER (super_name))));
9258 = build_modify_expr (input_location, super_expr, NULL_TREE,
9261 build_c_cast (input_location,
9262 TREE_TYPE (super_expr),
9267 super_expr_list = build_compound_expr (input_location,
9268 super_expr_list, super_expr);
9270 super_expr = build_unary_op (input_location,
9271 ADDR_EXPR, UOBJC_SUPER_decl, 0);
9272 super_expr_list = build_compound_expr (input_location,
9273 super_expr_list, super_expr);
9275 return super_expr_list;
9279 error ("[super ...] must appear in a method context");
9280 return error_mark_node;
9284 /* When exiting a scope, sever links to a 'super' declaration (if any)
9285 therein contained. */
9288 objc_clear_super_receiver (void)
9290 if (objc_method_context
9291 && UOBJC_SUPER_scope == objc_get_current_scope ()) {
9292 UOBJC_SUPER_decl = 0;
9293 UOBJC_SUPER_scope = 0;
9298 objc_finish_method_definition (tree fndecl)
9300 /* We cannot validly inline ObjC methods, at least not without a language
9301 extension to declare that a method need not be dynamically
9302 dispatched, so suppress all thoughts of doing so. */
9303 DECL_UNINLINABLE (fndecl) = 1;
9306 /* The C++ front-end will have called finish_function() for us. */
9310 METHOD_ENCODING (objc_method_context)
9311 = encode_method_prototype (objc_method_context);
9313 /* Required to implement _msgSuper. This must be done AFTER finish_function,
9314 since the optimizer may find "may be used before set" errors. */
9315 objc_method_context = NULL_TREE;
9317 if (should_call_super_dealloc)
9318 warning (0, "method possibly missing a [super dealloc] call");
9321 /* Given a tree DECL node, produce a printable description of it in the given
9322 buffer, overwriting the buffer. */
9325 gen_declaration (tree decl)
9331 gen_type_name_0 (TREE_TYPE (decl));
9333 if (DECL_NAME (decl))
9335 if (!POINTER_TYPE_P (TREE_TYPE (decl)))
9336 strcat (errbuf, " ");
9338 strcat (errbuf, IDENTIFIER_POINTER (DECL_NAME (decl)));
9341 if (DECL_INITIAL (decl)
9342 && TREE_CODE (DECL_INITIAL (decl)) == INTEGER_CST)
9343 sprintf (errbuf + strlen (errbuf), ": " HOST_WIDE_INT_PRINT_DEC,
9344 TREE_INT_CST_LOW (DECL_INITIAL (decl)));
9350 /* Given a tree TYPE node, produce a printable description of it in the given
9351 buffer, overwriting the buffer. */
9354 gen_type_name_0 (tree type)
9356 tree orig = type, proto;
9358 if (TYPE_P (type) && TYPE_NAME (type))
9359 type = TYPE_NAME (type);
9360 else if (POINTER_TYPE_P (type) || TREE_CODE (type) == ARRAY_TYPE)
9362 tree inner = TREE_TYPE (type);
9364 while (TREE_CODE (inner) == ARRAY_TYPE)
9365 inner = TREE_TYPE (inner);
9367 gen_type_name_0 (inner);
9369 if (!POINTER_TYPE_P (inner))
9370 strcat (errbuf, " ");
9372 if (POINTER_TYPE_P (type))
9373 strcat (errbuf, "*");
9375 while (type != inner)
9377 strcat (errbuf, "[");
9379 if (TYPE_DOMAIN (type))
9383 sprintf (sz, HOST_WIDE_INT_PRINT_DEC,
9385 (TYPE_MAX_VALUE (TYPE_DOMAIN (type))) + 1));
9386 strcat (errbuf, sz);
9389 strcat (errbuf, "]");
9390 type = TREE_TYPE (type);
9396 if (TREE_CODE (type) == TYPE_DECL && DECL_NAME (type))
9397 type = DECL_NAME (type);
9399 strcat (errbuf, TREE_CODE (type) == IDENTIFIER_NODE
9400 ? IDENTIFIER_POINTER (type)
9403 /* For 'id' and 'Class', adopted protocols are stored in the pointee. */
9404 if (objc_is_id (orig))
9405 orig = TREE_TYPE (orig);
9407 proto = TYPE_HAS_OBJC_INFO (orig) ? TYPE_OBJC_PROTOCOL_LIST (orig) : NULL_TREE;
9411 strcat (errbuf, " <");
9415 IDENTIFIER_POINTER (PROTOCOL_NAME (TREE_VALUE (proto))));
9416 proto = TREE_CHAIN (proto);
9417 strcat (errbuf, proto ? ", " : ">");
9426 gen_type_name (tree type)
9430 return gen_type_name_0 (type);
9433 /* Given a method tree, put a printable description into the given
9434 buffer (overwriting) and return a pointer to the buffer. */
9437 gen_method_decl (tree method)
9441 strcpy (errbuf, "("); /* NB: Do _not_ call strcat() here. */
9442 gen_type_name_0 (TREE_VALUE (TREE_TYPE (method)));
9443 strcat (errbuf, ")");
9444 chain = METHOD_SEL_ARGS (method);
9448 /* We have a chain of keyword_decls. */
9451 if (KEYWORD_KEY_NAME (chain))
9452 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_KEY_NAME (chain)));
9454 strcat (errbuf, ":(");
9455 gen_type_name_0 (TREE_VALUE (TREE_TYPE (chain)));
9456 strcat (errbuf, ")");
9458 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_ARG_NAME (chain)));
9459 if ((chain = DECL_CHAIN (chain)))
9460 strcat (errbuf, " ");
9464 if (METHOD_ADD_ARGS (method))
9466 chain = TREE_CHAIN (METHOD_ADD_ARGS (method));
9468 /* Know we have a chain of parm_decls. */
9471 strcat (errbuf, ", ");
9472 gen_type_name_0 (TREE_TYPE (TREE_VALUE (chain)));
9473 chain = TREE_CHAIN (chain);
9476 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
9477 strcat (errbuf, ", ...");
9482 /* We have a unary selector. */
9483 strcat (errbuf, IDENTIFIER_POINTER (METHOD_SEL_NAME (method)));
9491 /* Dump an @interface declaration of the supplied class CHAIN to the
9492 supplied file FP. Used to implement the -gen-decls option (which
9493 prints out an @interface declaration of all classes compiled in
9494 this run); potentially useful for debugging the compiler too. */
9496 dump_interface (FILE *fp, tree chain)
9498 /* FIXME: A heap overflow here whenever a method (or ivar)
9499 declaration is so long that it doesn't fit in the buffer. The
9500 code and all the related functions should be rewritten to avoid
9501 using fixed size buffers. */
9502 const char *my_name = IDENTIFIER_POINTER (CLASS_NAME (chain));
9503 tree ivar_decls = CLASS_RAW_IVARS (chain);
9504 tree nst_methods = CLASS_NST_METHODS (chain);
9505 tree cls_methods = CLASS_CLS_METHODS (chain);
9507 fprintf (fp, "\n@interface %s", my_name);
9509 /* CLASS_SUPER_NAME is used to store the superclass name for
9510 classes, and the category name for categories. */
9511 if (CLASS_SUPER_NAME (chain))
9513 const char *name = IDENTIFIER_POINTER (CLASS_SUPER_NAME (chain));
9515 if (TREE_CODE (chain) == CATEGORY_IMPLEMENTATION_TYPE
9516 || TREE_CODE (chain) == CATEGORY_INTERFACE_TYPE)
9518 fprintf (fp, " (%s)\n", name);
9522 fprintf (fp, " : %s\n", name);
9528 /* FIXME - the following doesn't seem to work at the moment. */
9531 fprintf (fp, "{\n");
9534 fprintf (fp, "\t%s;\n", gen_declaration (ivar_decls));
9535 ivar_decls = TREE_CHAIN (ivar_decls);
9538 fprintf (fp, "}\n");
9543 fprintf (fp, "- %s;\n", gen_method_decl (nst_methods));
9544 nst_methods = TREE_CHAIN (nst_methods);
9549 fprintf (fp, "+ %s;\n", gen_method_decl (cls_methods));
9550 cls_methods = TREE_CHAIN (cls_methods);
9553 fprintf (fp, "@end\n");
9556 /* Demangle function for Objective-C */
9558 objc_demangle (const char *mangled)
9560 char *demangled, *cp;
9562 if (mangled[0] == '_' &&
9563 (mangled[1] == 'i' || mangled[1] == 'c') &&
9566 cp = demangled = XNEWVEC (char, strlen(mangled) + 2);
9567 if (mangled[1] == 'i')
9568 *cp++ = '-'; /* for instance method */
9570 *cp++ = '+'; /* for class method */
9571 *cp++ = '['; /* opening left brace */
9572 strcpy(cp, mangled+3); /* tack on the rest of the mangled name */
9573 while (*cp && *cp == '_')
9574 cp++; /* skip any initial underbars in class name */
9575 cp = strchr(cp, '_'); /* find first non-initial underbar */
9578 free(demangled); /* not mangled name */
9581 if (cp[1] == '_') /* easy case: no category name */
9583 *cp++ = ' '; /* replace two '_' with one ' ' */
9584 strcpy(cp, mangled + (cp - demangled) + 2);
9588 *cp++ = '('; /* less easy case: category name */
9589 cp = strchr(cp, '_');
9592 free(demangled); /* not mangled name */
9596 *cp++ = ' '; /* overwriting 1st char of method name... */
9597 strcpy(cp, mangled + (cp - demangled)); /* get it back */
9599 while (*cp && *cp == '_')
9600 cp++; /* skip any initial underbars in method name */
9603 *cp = ':'; /* replace remaining '_' with ':' */
9604 *cp++ = ']'; /* closing right brace */
9605 *cp++ = 0; /* string terminator */
9609 return mangled; /* not an objc mangled name */
9613 objc_printable_name (tree decl, int kind ATTRIBUTE_UNUSED)
9615 return objc_demangle (IDENTIFIER_POINTER (DECL_NAME (decl)));
9621 gcc_obstack_init (&util_obstack);
9622 util_firstobj = (char *) obstack_finish (&util_obstack);
9624 errbuf = XNEWVEC (char, 1024 * 10);
9626 synth_module_prologue ();
9632 struct imp_entry *impent;
9634 /* The internally generated initializers appear to have missing braces.
9635 Don't warn about this. */
9636 int save_warn_missing_braces = warn_missing_braces;
9637 warn_missing_braces = 0;
9639 /* A missing @end may not be detected by the parser. */
9640 if (objc_implementation_context)
9642 warning (0, "%<@end%> missing in implementation context");
9643 finish_class (objc_implementation_context);
9644 objc_ivar_chain = NULL_TREE;
9645 objc_implementation_context = NULL_TREE;
9648 /* Process the static instances here because initialization of objc_symtab
9650 if (objc_static_instances)
9651 generate_static_references ();
9653 /* forward declare categories */
9655 forward_declare_categories ();
9657 for (impent = imp_list; impent; impent = impent->next)
9659 objc_implementation_context = impent->imp_context;
9660 implementation_template = impent->imp_template;
9662 /* FIXME: This needs reworking to be more obvious. */
9664 UOBJC_CLASS_decl = impent->class_decl;
9665 UOBJC_METACLASS_decl = impent->meta_decl;
9667 /* Dump the @interface of each class as we compile it, if the
9668 -gen-decls option is in use. TODO: Dump the classes in the
9669 order they were found, rather than in reverse order as we
9671 if (flag_gen_declaration)
9673 dump_interface (gen_declaration_file, objc_implementation_context);
9676 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
9678 /* all of the following reference the string pool... */
9679 generate_ivar_lists ();
9680 generate_dispatch_tables ();
9681 generate_shared_structures (impent);
9685 generate_dispatch_tables ();
9686 generate_category (impent);
9689 impent->class_decl = UOBJC_CLASS_decl;
9690 impent->meta_decl = UOBJC_METACLASS_decl;
9693 /* If we are using an array of selectors, we must always
9694 finish up the array decl even if no selectors were used. */
9695 if (flag_next_runtime)
9696 build_next_selector_translation_table ();
9698 build_gnu_selector_translation_table ();
9701 generate_protocols ();
9703 if (flag_next_runtime)
9704 generate_objc_image_info ();
9706 if (imp_list || class_names_chain
9707 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9708 generate_objc_symtab_decl ();
9710 /* Arrange for ObjC data structures to be initialized at run time. */
9711 if (objc_implementation_context || class_names_chain || objc_static_instances
9712 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9714 build_module_descriptor ();
9716 if (!flag_next_runtime)
9717 build_module_initializer_routine ();
9720 /* Dump the class references. This forces the appropriate classes
9721 to be linked into the executable image, preserving unix archive
9722 semantics. This can be removed when we move to a more dynamically
9723 linked environment. */
9725 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
9727 handle_class_ref (chain);
9728 if (TREE_PURPOSE (chain))
9729 generate_classref_translation_entry (chain);
9732 for (impent = imp_list; impent; impent = impent->next)
9733 handle_impent (impent);
9740 /* Run through the selector hash tables and print a warning for any
9741 selector which has multiple methods. */
9743 for (slot = 0; slot < SIZEHASHTABLE; slot++)
9745 for (hsh = cls_method_hash_list[slot]; hsh; hsh = hsh->next)
9746 check_duplicates (hsh, 0, 1);
9747 for (hsh = nst_method_hash_list[slot]; hsh; hsh = hsh->next)
9748 check_duplicates (hsh, 0, 1);
9752 warn_missing_braces = save_warn_missing_braces;
9755 /* Subroutines of finish_objc. */
9758 generate_classref_translation_entry (tree chain)
9760 tree expr, decl, type;
9762 decl = TREE_PURPOSE (chain);
9763 type = TREE_TYPE (decl);
9765 expr = add_objc_string (TREE_VALUE (chain), class_names);
9766 expr = convert (type, expr); /* cast! */
9768 /* This is a class reference. It is re-written by the runtime,
9769 but will be optimized away unless we force it. */
9770 DECL_PRESERVE_P (decl) = 1;
9771 finish_var_decl (decl, expr);
9776 handle_class_ref (tree chain)
9778 const char *name = IDENTIFIER_POINTER (TREE_VALUE (chain));
9779 char *string = (char *) alloca (strlen (name) + 30);
9783 sprintf (string, "%sobjc_class_name_%s",
9784 (flag_next_runtime ? "." : "__"), name);
9786 #ifdef ASM_DECLARE_UNRESOLVED_REFERENCE
9787 if (flag_next_runtime)
9789 ASM_DECLARE_UNRESOLVED_REFERENCE (asm_out_file, string);
9794 /* Make a decl for this name, so we can use its address in a tree. */
9795 decl = build_decl (input_location,
9796 VAR_DECL, get_identifier (string), TREE_TYPE (integer_zero_node));
9797 DECL_EXTERNAL (decl) = 1;
9798 TREE_PUBLIC (decl) = 1;
9800 finish_var_decl (decl, 0);
9802 /* Make a decl for the address. */
9803 sprintf (string, "%sobjc_class_ref_%s",
9804 (flag_next_runtime ? "." : "__"), name);
9805 exp = build1 (ADDR_EXPR, string_type_node, decl);
9806 decl = build_decl (input_location,
9807 VAR_DECL, get_identifier (string), string_type_node);
9808 TREE_STATIC (decl) = 1;
9809 TREE_USED (decl) = 1;
9810 DECL_READ_P (decl) = 1;
9811 DECL_ARTIFICIAL (decl) = 1;
9812 DECL_INITIAL (decl) = error_mark_node;
9814 /* We must force the reference. */
9815 DECL_PRESERVE_P (decl) = 1;
9818 finish_var_decl (decl, exp);
9822 handle_impent (struct imp_entry *impent)
9826 objc_implementation_context = impent->imp_context;
9827 implementation_template = impent->imp_template;
9829 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
9831 const char *const class_name =
9832 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9834 string = (char *) alloca (strlen (class_name) + 30);
9836 sprintf (string, "%sobjc_class_name_%s",
9837 (flag_next_runtime ? "." : "__"), class_name);
9839 else if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
9841 const char *const class_name =
9842 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9843 const char *const class_super_name =
9844 IDENTIFIER_POINTER (CLASS_SUPER_NAME (impent->imp_context));
9846 string = (char *) alloca (strlen (class_name)
9847 + strlen (class_super_name) + 30);
9849 /* Do the same for categories. Even though no references to
9850 these symbols are generated automatically by the compiler, it
9851 gives you a handle to pull them into an archive by hand. */
9852 sprintf (string, "*%sobjc_category_name_%s_%s",
9853 (flag_next_runtime ? "." : "__"), class_name, class_super_name);
9858 #ifdef ASM_DECLARE_CLASS_REFERENCE
9859 if (flag_next_runtime)
9861 ASM_DECLARE_CLASS_REFERENCE (asm_out_file, string);
9869 init = integer_zero_node;
9870 decl = build_decl (input_location,
9871 VAR_DECL, get_identifier (string), TREE_TYPE (init));
9872 TREE_PUBLIC (decl) = 1;
9873 TREE_READONLY (decl) = 1;
9874 TREE_USED (decl) = 1;
9875 TREE_CONSTANT (decl) = 1;
9876 DECL_CONTEXT (decl) = NULL_TREE;
9877 DECL_ARTIFICIAL (decl) = 1;
9878 TREE_STATIC (decl) = 1;
9879 DECL_INITIAL (decl) = error_mark_node; /* A real initializer is coming... */
9880 /* We must force the reference. */
9881 DECL_PRESERVE_P (decl) = 1;
9883 finish_var_decl(decl, init) ;
9887 /* The Fix-and-Continue functionality available in Mac OS X 10.3 and
9888 later requires that ObjC translation units participating in F&C be
9889 specially marked. The following routine accomplishes this. */
9891 /* static int _OBJC_IMAGE_INFO[2] = { 0, 1 }; */
9894 generate_objc_image_info (void)
9898 = ((flag_replace_objc_classes && imp_count ? 1 : 0)
9899 | (flag_objc_gc ? 2 : 0));
9900 VEC(constructor_elt,gc) *v = NULL;
9904 return; /* No need for an image_info entry. */
9906 array_type = build_sized_array_type (integer_type_node, 2);
9908 decl = start_var_decl (array_type, "_OBJC_IMAGE_INFO");
9910 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, integer_zero_node);
9911 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, build_int_cst (integer_type_node, flags));
9912 /* If we need this (determined above) it is because the runtime wants to
9913 refer to it in a manner hidden from the compiler. So we must force the
9915 DECL_PRESERVE_P (decl) = 1;
9916 finish_var_decl (decl, objc_build_constructor (TREE_TYPE (decl), v));
9919 /* Look up ID as an instance variable. OTHER contains the result of
9920 the C or C++ lookup, which we may want to use instead. */
9923 objc_lookup_ivar (tree other, tree id)
9927 /* If we are not inside of an ObjC method, ivar lookup makes no sense. */
9928 if (!objc_method_context)
9931 if (!strcmp (IDENTIFIER_POINTER (id), "super"))
9932 /* We have a message to super. */
9933 return get_super_receiver ();
9935 /* In a class method, look up an instance variable only as a last
9937 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
9938 && other && other != error_mark_node)
9941 /* Look up the ivar, but do not use it if it is not accessible. */
9942 ivar = is_ivar (objc_ivar_chain, id);
9944 if (!ivar || is_private (ivar))
9947 /* In an instance method, a local variable (or parameter) may hide the
9948 instance variable. */
9949 if (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9950 && other && other != error_mark_node
9952 && CP_DECL_CONTEXT (other) != global_namespace)
9954 && !DECL_FILE_SCOPE_P (other))
9957 warning (0, "local declaration of %qE hides instance variable",
9963 /* At this point, we are either in an instance method with no obscuring
9964 local definitions, or in a class method with no alternate definitions
9966 return build_ivar_reference (id);
9969 /* Possibly rewrite a function CALL into an OBJ_TYPE_REF expression. This
9970 needs to be done if we are calling a function through a cast. */
9973 objc_rewrite_function_call (tree function, tree first_param)
9975 if (TREE_CODE (function) == NOP_EXPR
9976 && TREE_CODE (TREE_OPERAND (function, 0)) == ADDR_EXPR
9977 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (function, 0), 0))
9980 function = build3 (OBJ_TYPE_REF, TREE_TYPE (function),
9981 TREE_OPERAND (function, 0),
9982 first_param, size_zero_node);
9988 /* Look for the special case of OBJC_TYPE_REF with the address of
9989 a function in OBJ_TYPE_REF_EXPR (presumably objc_msgSend or one
9993 objc_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
9995 enum gimplify_status r0, r1;
9996 if (TREE_CODE (*expr_p) == OBJ_TYPE_REF
9997 && TREE_CODE (OBJ_TYPE_REF_EXPR (*expr_p)) == ADDR_EXPR
9998 && TREE_CODE (TREE_OPERAND (OBJ_TYPE_REF_EXPR (*expr_p), 0))
10001 /* Postincrements in OBJ_TYPE_REF_OBJECT don't affect the
10002 value of the OBJ_TYPE_REF, so force them to be emitted
10003 during subexpression evaluation rather than after the
10004 OBJ_TYPE_REF. This permits objc_msgSend calls in Objective
10005 C to use direct rather than indirect calls when the
10006 object expression has a postincrement. */
10007 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p, NULL,
10008 is_gimple_val, fb_rvalue);
10009 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p, post_p,
10010 is_gimple_val, fb_rvalue);
10012 return MIN (r0, r1);
10016 return (enum gimplify_status) cp_gimplify_expr (expr_p, pre_p, post_p);
10018 return (enum gimplify_status) c_gimplify_expr (expr_p, pre_p, post_p);
10022 /* This routine returns true if TYP is a valid objc object type,
10023 suitable for messaging; false otherwise.
10027 objc_type_valid_for_messaging (tree typ)
10029 if (!POINTER_TYPE_P (typ))
10033 typ = TREE_TYPE (typ); /* Remove indirections. */
10034 while (POINTER_TYPE_P (typ));
10036 if (TREE_CODE (typ) != RECORD_TYPE)
10039 return objc_is_object_id (typ) || TYPE_HAS_OBJC_INFO (typ);
10042 /* Begin code generation for fast enumeration (foreach) ... */
10046 struct __objcFastEnumerationState
10048 unsigned long state;
10050 unsigned long *mutationsPtr;
10051 unsigned long extra[5];
10054 Confusingly enough, NSFastEnumeration is then defined by libraries
10055 to be the same structure.
10059 build_fast_enumeration_state_template (void)
10061 tree decls, *chain = NULL;
10064 objc_fast_enumeration_state_template = objc_start_struct (get_identifier
10065 (TAG_FAST_ENUMERATION_STATE));
10067 /* unsigned long state; */
10068 decls = add_field_decl (long_unsigned_type_node, "state", &chain);
10070 /* id *itemsPtr; */
10071 add_field_decl (build_pointer_type (objc_object_type),
10072 "itemsPtr", &chain);
10074 /* unsigned long *mutationsPtr; */
10075 add_field_decl (build_pointer_type (long_unsigned_type_node),
10076 "mutationsPtr", &chain);
10078 /* unsigned long extra[5]; */
10079 add_field_decl (build_sized_array_type (long_unsigned_type_node, 5),
10083 objc_finish_struct (objc_fast_enumeration_state_template, decls);
10087 'objc_finish_foreach_loop()' generates the code for an Objective-C
10088 foreach loop. The 'location' argument is the location of the 'for'
10089 that starts the loop. The 'object_expression' is the expression of
10090 the 'object' that iterates; the 'collection_expression' is the
10091 expression of the collection that we iterate over (we need to make
10092 sure we evaluate this only once); the 'for_body' is the set of
10093 statements to be executed in each iteration; 'break_label' and
10094 'continue_label' are the break and continue labels which we need to
10095 emit since the <statements> may be jumping to 'break_label' (if they
10096 contain 'break') or to 'continue_label' (if they contain
10101 for (<object expression> in <collection expression>)
10104 which is compiled into the following blurb:
10107 id __objc_foreach_collection;
10108 __objc_fast_enumeration_state __objc_foreach_enum_state;
10109 unsigned long __objc_foreach_batchsize;
10110 id __objc_foreach_items[16];
10111 __objc_foreach_collection = <collection expression>;
10112 __objc_foreach_enum_state = { 0 };
10113 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
10115 if (__objc_foreach_batchsize == 0)
10116 <object expression> = nil;
10119 unsigned long __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr;
10122 unsigned long __objc_foreach_index;
10123 __objc_foreach_index = 0;
10126 if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>);
10127 <object expression> = enumState.itemsPtr[__objc_foreach_index];
10128 <statements> [PS: inside <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label]
10131 __objc_foreach_index++;
10132 if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object;
10133 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
10135 if (__objc_foreach_batchsize != 0) goto next_batch;
10136 <object expression> = nil;
10141 'statements' may contain a 'continue' or 'break' instruction, which
10142 the user expects to 'continue' or 'break' the entire foreach loop.
10143 We are provided the labels that 'break' and 'continue' jump to, so
10144 we place them where we want them to jump to when they pick them.
10146 Optimization TODO: we could cache the IMP of
10147 countByEnumeratingWithState:objects:count:.
10150 /* If you need to debug objc_finish_foreach_loop(), uncomment the following line. */
10151 /* #define DEBUG_OBJC_FINISH_FOREACH_LOOP 1 */
10153 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
10154 #include "tree-pretty-print.h"
10158 objc_finish_foreach_loop (location_t location, tree object_expression, tree collection_expression, tree for_body,
10159 tree break_label, tree continue_label)
10161 /* A tree representing the __objcFastEnumerationState struct type,
10162 or NSFastEnumerationState struct, whatever we are using. */
10163 tree objc_fast_enumeration_state_type;
10165 /* The trees representing the declarations of each of the local variables. */
10166 tree objc_foreach_collection_decl;
10167 tree objc_foreach_enum_state_decl;
10168 tree objc_foreach_items_decl;
10169 tree objc_foreach_batchsize_decl;
10170 tree objc_foreach_mutations_pointer_decl;
10171 tree objc_foreach_index_decl;
10173 /* A tree representing the selector countByEnumeratingWithState:objects:count:. */
10174 tree selector_name;
10176 /* A tree representing the local bind. */
10179 /* A tree representing the external 'if (__objc_foreach_batchsize)' */
10182 /* A tree representing the 'else' part of 'first_if' */
10185 /* A tree representing the 'next_batch' label. */
10186 tree next_batch_label_decl;
10188 /* A tree representing the binding after the 'next_batch' label. */
10189 tree next_batch_bind;
10191 /* A tree representing the 'next_object' label. */
10192 tree next_object_label_decl;
10194 /* Temporary variables. */
10198 if (object_expression == error_mark_node)
10201 if (collection_expression == error_mark_node)
10204 if (!objc_type_valid_for_messaging (TREE_TYPE (object_expression)))
10206 error ("iterating variable in fast enumeration is not an object");
10210 if (!objc_type_valid_for_messaging (TREE_TYPE (collection_expression)))
10212 error ("collection in fast enumeration is not an object");
10216 /* TODO: Check that object_expression is either a variable
10217 declaration, or an lvalue. */
10219 /* This kludge is an idea from apple. We use the
10220 __objcFastEnumerationState struct implicitly defined by the
10221 compiler, unless a NSFastEnumerationState struct has been defined
10222 (by a Foundation library such as GNUstep Base) in which case, we
10225 objc_fast_enumeration_state_type = objc_fast_enumeration_state_template;
10227 tree objc_NSFastEnumeration_type = lookup_name (get_identifier ("NSFastEnumerationState"));
10229 if (objc_NSFastEnumeration_type)
10231 /* TODO: We really need to check that
10232 objc_NSFastEnumeration_type is the same as ours! */
10233 if (TREE_CODE (objc_NSFastEnumeration_type) == TYPE_DECL)
10235 /* If it's a typedef, use the original type. */
10236 if (DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type))
10237 objc_fast_enumeration_state_type = DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type);
10239 objc_fast_enumeration_state_type = TREE_TYPE (objc_NSFastEnumeration_type);
10245 /* Done by c-parser.c. */
10248 /* Done by c-parser.c. */
10250 /* id __objc_foreach_collection */
10251 objc_foreach_collection_decl = objc_create_temporary_var (objc_object_type, "__objc_foreach_collection");
10253 /* __objcFastEnumerationState __objc_foreach_enum_state; */
10254 objc_foreach_enum_state_decl = objc_create_temporary_var (objc_fast_enumeration_state_type, "__objc_foreach_enum_state");
10255 TREE_CHAIN (objc_foreach_enum_state_decl) = objc_foreach_collection_decl;
10257 /* id __objc_foreach_items[16]; */
10258 objc_foreach_items_decl = objc_create_temporary_var (build_sized_array_type (objc_object_type, 16), "__objc_foreach_items");
10259 TREE_CHAIN (objc_foreach_items_decl) = objc_foreach_enum_state_decl;
10261 /* unsigned long __objc_foreach_batchsize; */
10262 objc_foreach_batchsize_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_batchsize");
10263 TREE_CHAIN (objc_foreach_batchsize_decl) = objc_foreach_items_decl;
10265 /* Generate the local variable binding. */
10266 bind = build3 (BIND_EXPR, void_type_node, objc_foreach_batchsize_decl, NULL, NULL);
10267 SET_EXPR_LOCATION (bind, location);
10268 TREE_SIDE_EFFECTS (bind) = 1;
10270 /* __objc_foreach_collection = <collection expression>; */
10271 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_collection_decl, collection_expression);
10272 SET_EXPR_LOCATION (t, location);
10273 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10275 /* __objc_foreach_enum_state.state = 0; */
10276 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10277 get_identifier ("state")),
10278 build_int_cst (long_unsigned_type_node, 0));
10279 SET_EXPR_LOCATION (t, location);
10280 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10282 /* __objc_foreach_enum_state.itemsPtr = NULL; */
10283 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10284 get_identifier ("itemsPtr")),
10285 null_pointer_node);
10286 SET_EXPR_LOCATION (t, location);
10287 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10289 /* __objc_foreach_enum_state.mutationsPtr = NULL; */
10290 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10291 get_identifier ("mutationsPtr")),
10292 null_pointer_node);
10293 SET_EXPR_LOCATION (t, location);
10294 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10296 /* __objc_foreach_enum_state.extra[0] = 0; */
10297 /* __objc_foreach_enum_state.extra[1] = 0; */
10298 /* __objc_foreach_enum_state.extra[2] = 0; */
10299 /* __objc_foreach_enum_state.extra[3] = 0; */
10300 /* __objc_foreach_enum_state.extra[4] = 0; */
10301 for (i = 0; i < 5 ; i++)
10303 t = build2 (MODIFY_EXPR, void_type_node,
10304 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10305 get_identifier ("extra")),
10306 build_int_cst (NULL_TREE, i)),
10307 build_int_cst (long_unsigned_type_node, 0));
10308 SET_EXPR_LOCATION (t, location);
10309 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10312 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
10313 selector_name = get_identifier ("countByEnumeratingWithState:objects:count:");
10315 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10317 tree_cons /* &__objc_foreach_enum_state */
10318 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10319 tree_cons /* __objc_foreach_items */
10320 (NULL_TREE, objc_foreach_items_decl,
10322 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))));
10324 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
10326 struct c_expr array;
10327 array.value = objc_foreach_items_decl;
10328 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10330 tree_cons /* &__objc_foreach_enum_state */
10331 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10332 tree_cons /* __objc_foreach_items */
10333 (NULL_TREE, default_function_array_conversion (location, array).value,
10335 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))));
10338 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
10339 convert (long_unsigned_type_node, t));
10340 SET_EXPR_LOCATION (t, location);
10341 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10343 /* if (__objc_foreach_batchsize == 0) */
10344 first_if = build3 (COND_EXPR, void_type_node,
10347 (c_common_truthvalue_conversion
10349 build_binary_op (location,
10351 objc_foreach_batchsize_decl,
10352 build_int_cst (long_unsigned_type_node, 0), 1)),
10354 /* Then block (we fill it in later). */
10356 /* Else block (we fill it in later). */
10358 SET_EXPR_LOCATION (first_if, location);
10359 append_to_statement_list (first_if, &BIND_EXPR_BODY (bind));
10361 /* then <object expression> = nil; */
10362 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
10363 SET_EXPR_LOCATION (t, location);
10364 COND_EXPR_THEN (first_if) = t;
10366 /* Now we build the 'else' part of the if; once we finish building
10367 it, we attach it to first_if as the 'else' part. */
10372 /* unsigned long __objc_foreach_mutations_pointer; */
10373 objc_foreach_mutations_pointer_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_mutations_pointer");
10375 /* Generate the local variable binding. */
10376 first_else = build3 (BIND_EXPR, void_type_node, objc_foreach_mutations_pointer_decl, NULL, NULL);
10377 SET_EXPR_LOCATION (first_else, location);
10378 TREE_SIDE_EFFECTS (first_else) = 1;
10380 /* __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr; */
10381 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_mutations_pointer_decl,
10382 build_indirect_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10383 get_identifier ("mutationsPtr")),
10385 SET_EXPR_LOCATION (t, location);
10386 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10389 next_batch_label_decl = create_artificial_label (location);
10390 t = build1 (LABEL_EXPR, void_type_node, next_batch_label_decl);
10391 SET_EXPR_LOCATION (t, location);
10392 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10396 /* unsigned long __objc_foreach_index; */
10397 objc_foreach_index_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_index");
10399 /* Generate the local variable binding. */
10400 next_batch_bind = build3 (BIND_EXPR, void_type_node, objc_foreach_index_decl, NULL, NULL);
10401 SET_EXPR_LOCATION (next_batch_bind, location);
10402 TREE_SIDE_EFFECTS (next_batch_bind) = 1;
10403 append_to_statement_list (next_batch_bind, &BIND_EXPR_BODY (first_else));
10405 /* __objc_foreach_index = 0; */
10406 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
10407 build_int_cst (long_unsigned_type_node, 0));
10408 SET_EXPR_LOCATION (t, location);
10409 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10412 next_object_label_decl = create_artificial_label (location);
10413 t = build1 (LABEL_EXPR, void_type_node, next_object_label_decl);
10414 SET_EXPR_LOCATION (t, location);
10415 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10417 /* if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>); */
10418 t = build3 (COND_EXPR, void_type_node,
10421 (c_common_truthvalue_conversion
10426 objc_foreach_mutations_pointer_decl,
10427 build_indirect_ref (location,
10428 objc_build_component_ref (objc_foreach_enum_state_decl,
10429 get_identifier ("mutationsPtr")),
10430 RO_UNARY_STAR), 1)),
10433 build_function_call (input_location,
10434 objc_enumeration_mutation_decl,
10435 tree_cons (NULL, collection_expression, NULL)),
10438 SET_EXPR_LOCATION (t, location);
10439 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10441 /* <object expression> = enumState.itemsPtr[__objc_foreach_index]; */
10442 t = build2 (MODIFY_EXPR, void_type_node, object_expression,
10443 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10444 get_identifier ("itemsPtr")),
10445 objc_foreach_index_decl));
10446 SET_EXPR_LOCATION (t, location);
10447 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10449 /* <statements> [PS: in <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label] */
10450 append_to_statement_list (for_body, &BIND_EXPR_BODY (next_batch_bind));
10452 /* continue_label: */
10453 if (continue_label)
10455 t = build1 (LABEL_EXPR, void_type_node, continue_label);
10456 SET_EXPR_LOCATION (t, location);
10457 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10460 /* __objc_foreach_index++; */
10461 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
10462 build_binary_op (location,
10464 objc_foreach_index_decl,
10465 build_int_cst (long_unsigned_type_node, 1), 1));
10466 SET_EXPR_LOCATION (t, location);
10467 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10469 /* if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object; */
10470 t = build3 (COND_EXPR, void_type_node,
10473 (c_common_truthvalue_conversion
10475 build_binary_op (location,
10477 objc_foreach_index_decl,
10478 objc_foreach_batchsize_decl, 1)),
10481 build1 (GOTO_EXPR, void_type_node, next_object_label_decl),
10484 SET_EXPR_LOCATION (t, location);
10485 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10487 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
10489 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10491 tree_cons /* &__objc_foreach_enum_state */
10492 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10493 tree_cons /* __objc_foreach_items */
10494 (NULL_TREE, objc_foreach_items_decl,
10496 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))));
10498 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
10500 struct c_expr array;
10501 array.value = objc_foreach_items_decl;
10502 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10504 tree_cons /* &__objc_foreach_enum_state */
10505 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10506 tree_cons /* __objc_foreach_items */
10507 (NULL_TREE, default_function_array_conversion (location, array).value,
10509 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))));
10512 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
10513 convert (long_unsigned_type_node, t));
10514 SET_EXPR_LOCATION (t, location);
10515 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10519 /* if (__objc_foreach_batchsize != 0) goto next_batch; */
10520 t = build3 (COND_EXPR, void_type_node,
10523 (c_common_truthvalue_conversion
10525 build_binary_op (location,
10527 objc_foreach_batchsize_decl,
10528 build_int_cst (long_unsigned_type_node, 0), 1)),
10531 build1 (GOTO_EXPR, void_type_node, next_batch_label_decl),
10534 SET_EXPR_LOCATION (t, location);
10535 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10537 /* <object expression> = nil; */
10538 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
10539 SET_EXPR_LOCATION (t, location);
10540 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10545 t = build1 (LABEL_EXPR, void_type_node, break_label);
10546 SET_EXPR_LOCATION (t, location);
10547 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10551 COND_EXPR_ELSE (first_if) = first_else;
10553 /* Do the whole thing. */
10556 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
10557 /* This will print to stderr the whole blurb generated by the
10558 compiler while compiling (assuming the compiler doesn't crash
10559 before getting here).
10561 debug_generic_stmt (bind);
10565 /* Done by c-parser.c */
10568 #include "gt-objc-objc-act.h"