1 /* Implement classes and message passing for Objective C.
2 Copyright (C) 1992, 1993, 1994, 1995, 1997, 1998, 1999, 2000,
3 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
4 Contributed by Steve Naroff.
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
13 GCC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING. If not, write to
20 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA. */
23 /* Purpose: This module implements the Objective-C 4.0 language.
25 compatibility issues (with the Stepstone translator):
27 - does not recognize the following 3.3 constructs.
28 @requires, @classes, @messages, = (...)
29 - methods with variable arguments must conform to ANSI standard.
30 - tagged structure definitions that appear in BOTH the interface
31 and implementation are not allowed.
32 - public/private: all instance variables are public within the
33 context of the implementation...I consider this to be a bug in
35 - statically allocated objects are not supported. the user will
36 receive an error if this service is requested.
38 code generation `options':
44 #include "coretypes.h"
60 #include "langhooks.h"
71 #include "diagnostic.h"
73 #include "tree-iterator.h"
76 #include "langhooks-def.h"
78 #define OBJC_VOID_AT_END void_list_node
80 static unsigned int should_call_super_dealloc = 0;
82 /* When building Objective-C++, we are not linking against the C front-end
83 and so need to replicate the C tree-construction functions in some way. */
85 #define OBJCP_REMAP_FUNCTIONS
86 #include "objcp-decl.h"
89 /* This is the default way of generating a method name. */
90 /* I am not sure it is really correct.
91 Perhaps there's a danger that it will make name conflicts
92 if method names contain underscores. -- rms. */
93 #ifndef OBJC_GEN_METHOD_LABEL
94 #define OBJC_GEN_METHOD_LABEL(BUF, IS_INST, CLASS_NAME, CAT_NAME, SEL_NAME, NUM) \
97 sprintf ((BUF), "_%s_%s_%s_%s", \
98 ((IS_INST) ? "i" : "c"), \
100 ((CAT_NAME)? (CAT_NAME) : ""), \
102 for (temp = (BUF); *temp; temp++) \
103 if (*temp == ':') *temp = '_'; \
107 /* These need specifying. */
108 #ifndef OBJC_FORWARDING_STACK_OFFSET
109 #define OBJC_FORWARDING_STACK_OFFSET 0
112 #ifndef OBJC_FORWARDING_MIN_OFFSET
113 #define OBJC_FORWARDING_MIN_OFFSET 0
116 /* Set up for use of obstacks. */
120 /* This obstack is used to accumulate the encoding of a data type. */
121 static struct obstack util_obstack;
123 /* This points to the beginning of obstack contents, so we can free
124 the whole contents. */
127 /* The version identifies which language generation and runtime
128 the module (file) was compiled for, and is recorded in the
129 module descriptor. */
131 #define OBJC_VERSION (flag_next_runtime ? 6 : 8)
132 #define PROTOCOL_VERSION 2
134 /* (Decide if these can ever be validly changed.) */
135 #define OBJC_ENCODE_INLINE_DEFS 0
136 #define OBJC_ENCODE_DONT_INLINE_DEFS 1
138 /*** Private Interface (procedures) ***/
140 /* Used by compile_file. */
142 static void init_objc (void);
143 static void finish_objc (void);
145 /* Code generation. */
147 static tree objc_build_constructor (tree, tree);
148 static tree build_objc_method_call (int, tree, tree, tree, tree);
149 static tree get_proto_encoding (tree);
150 static tree lookup_interface (tree);
151 static tree objc_add_static_instance (tree, tree);
153 static tree start_class (enum tree_code, tree, tree, tree);
154 static tree continue_class (tree);
155 static void finish_class (tree);
156 static void start_method_def (tree);
158 static void objc_start_function (tree, tree, tree, tree);
160 static void objc_start_function (tree, tree, tree, struct c_arg_info *);
162 static tree start_protocol (enum tree_code, tree, tree);
163 static tree build_method_decl (enum tree_code, tree, tree, tree, bool);
164 static tree objc_add_method (tree, tree, int);
165 static tree add_instance_variable (tree, int, tree);
166 static tree build_ivar_reference (tree);
167 static tree is_ivar (tree, tree);
169 static void build_objc_exception_stuff (void);
170 static void build_next_objc_exception_stuff (void);
172 /* We only need the following for ObjC; ObjC++ will use C++'s definition
173 of DERIVED_FROM_P. */
175 static bool objc_derived_from_p (tree, tree);
176 #define DERIVED_FROM_P(PARENT, CHILD) objc_derived_from_p (PARENT, CHILD)
178 static void objc_xref_basetypes (tree, tree);
180 static void build_class_template (void);
181 static void build_selector_template (void);
182 static void build_category_template (void);
183 static void build_super_template (void);
184 static tree build_protocol_initializer (tree, tree, tree, tree, tree);
185 static tree get_class_ivars (tree, bool);
186 static tree generate_protocol_list (tree);
187 static void build_protocol_reference (tree);
190 static void objc_generate_cxx_cdtors (void);
193 static const char *synth_id_with_class_suffix (const char *, tree);
195 /* Hash tables to manage the global pool of method prototypes. */
197 hash *nst_method_hash_list = 0;
198 hash *cls_method_hash_list = 0;
200 static hash hash_lookup (hash *, tree);
201 static tree lookup_method (tree, tree);
202 static tree lookup_method_static (tree, tree, int);
206 class_names, /* class, category, protocol, module names */
207 meth_var_names, /* method and variable names */
208 meth_var_types /* method and variable type descriptors */
211 static tree add_objc_string (tree, enum string_section);
212 static tree build_objc_string_decl (enum string_section);
213 static void build_selector_table_decl (void);
215 /* Protocol additions. */
217 static tree lookup_protocol (tree);
218 static tree lookup_and_install_protocols (tree);
222 static void encode_type_qualifiers (tree);
223 static void encode_type (tree, int, int);
224 static void encode_field_decl (tree, int, int);
227 static void really_start_method (tree, tree);
229 static void really_start_method (tree, struct c_arg_info *);
231 static int comp_proto_with_proto (tree, tree, int);
232 static void objc_push_parm (tree);
234 static tree objc_get_parm_info (int);
236 static struct c_arg_info *objc_get_parm_info (int);
239 /* Utilities for debugging and error diagnostics. */
241 static void warn_with_method (const char *, int, tree);
242 static char *gen_type_name (tree);
243 static char *gen_type_name_0 (tree);
244 static char *gen_method_decl (tree);
245 static char *gen_declaration (tree);
247 /* Everything else. */
249 static tree create_field_decl (tree, const char *);
250 static void add_class_reference (tree);
251 static void build_protocol_template (void);
252 static tree encode_method_prototype (tree);
253 static void generate_classref_translation_entry (tree);
254 static void handle_class_ref (tree);
255 static void generate_struct_by_value_array (void)
257 static void mark_referenced_methods (void);
258 static void generate_objc_image_info (void);
260 /*** Private Interface (data) ***/
262 /* Reserved tag definitions. */
264 #define OBJECT_TYPEDEF_NAME "id"
265 #define CLASS_TYPEDEF_NAME "Class"
267 #define TAG_OBJECT "objc_object"
268 #define TAG_CLASS "objc_class"
269 #define TAG_SUPER "objc_super"
270 #define TAG_SELECTOR "objc_selector"
272 #define UTAG_CLASS "_objc_class"
273 #define UTAG_IVAR "_objc_ivar"
274 #define UTAG_IVAR_LIST "_objc_ivar_list"
275 #define UTAG_METHOD "_objc_method"
276 #define UTAG_METHOD_LIST "_objc_method_list"
277 #define UTAG_CATEGORY "_objc_category"
278 #define UTAG_MODULE "_objc_module"
279 #define UTAG_SYMTAB "_objc_symtab"
280 #define UTAG_SUPER "_objc_super"
281 #define UTAG_SELECTOR "_objc_selector"
283 #define UTAG_PROTOCOL "_objc_protocol"
284 #define UTAG_METHOD_PROTOTYPE "_objc_method_prototype"
285 #define UTAG_METHOD_PROTOTYPE_LIST "_objc__method_prototype_list"
287 /* Note that the string object global name is only needed for the
289 #define STRING_OBJECT_GLOBAL_FORMAT "_%sClassReference"
291 #define PROTOCOL_OBJECT_CLASS_NAME "Protocol"
293 static const char *TAG_GETCLASS;
294 static const char *TAG_GETMETACLASS;
295 static const char *TAG_MSGSEND;
296 static const char *TAG_MSGSENDSUPER;
297 /* The NeXT Objective-C messenger may have two extra entry points, for use
298 when returning a structure. */
299 static const char *TAG_MSGSEND_STRET;
300 static const char *TAG_MSGSENDSUPER_STRET;
301 static const char *default_constant_string_class_name;
303 /* Runtime metadata flags. */
304 #define CLS_FACTORY 0x0001L
305 #define CLS_META 0x0002L
306 #define CLS_HAS_CXX_STRUCTORS 0x2000L
308 #define OBJC_MODIFIER_STATIC 0x00000001
309 #define OBJC_MODIFIER_FINAL 0x00000002
310 #define OBJC_MODIFIER_PUBLIC 0x00000004
311 #define OBJC_MODIFIER_PRIVATE 0x00000008
312 #define OBJC_MODIFIER_PROTECTED 0x00000010
313 #define OBJC_MODIFIER_NATIVE 0x00000020
314 #define OBJC_MODIFIER_SYNCHRONIZED 0x00000040
315 #define OBJC_MODIFIER_ABSTRACT 0x00000080
316 #define OBJC_MODIFIER_VOLATILE 0x00000100
317 #define OBJC_MODIFIER_TRANSIENT 0x00000200
318 #define OBJC_MODIFIER_NONE_SPECIFIED 0x80000000
320 /* NeXT-specific tags. */
322 #define TAG_MSGSEND_NONNIL "objc_msgSendNonNil"
323 #define TAG_MSGSEND_NONNIL_STRET "objc_msgSendNonNil_stret"
324 #define TAG_EXCEPTIONEXTRACT "objc_exception_extract"
325 #define TAG_EXCEPTIONTRYENTER "objc_exception_try_enter"
326 #define TAG_EXCEPTIONTRYEXIT "objc_exception_try_exit"
327 #define TAG_EXCEPTIONMATCH "objc_exception_match"
328 #define TAG_EXCEPTIONTHROW "objc_exception_throw"
329 #define TAG_SYNCENTER "objc_sync_enter"
330 #define TAG_SYNCEXIT "objc_sync_exit"
331 #define TAG_SETJMP "_setjmp"
332 #define UTAG_EXCDATA "_objc_exception_data"
334 #define TAG_ASSIGNIVAR "objc_assign_ivar"
335 #define TAG_ASSIGNGLOBAL "objc_assign_global"
336 #define TAG_ASSIGNSTRONGCAST "objc_assign_strongCast"
338 /* Branch entry points. All that matters here are the addresses;
339 functions with these names do not really exist in libobjc. */
341 #define TAG_MSGSEND_FAST "objc_msgSend_Fast"
342 #define TAG_ASSIGNIVAR_FAST "objc_assign_ivar_Fast"
344 #define TAG_CXX_CONSTRUCT ".cxx_construct"
345 #define TAG_CXX_DESTRUCT ".cxx_destruct"
347 /* GNU-specific tags. */
349 #define TAG_EXECCLASS "__objc_exec_class"
350 #define TAG_GNUINIT "__objc_gnu_init"
352 /* Flags for lookup_method_static(). */
353 #define OBJC_LOOKUP_CLASS 1 /* Look for class methods. */
354 #define OBJC_LOOKUP_NO_SUPER 2 /* Do not examine superclasses. */
356 /* The OCTI_... enumeration itself is in objc/objc-act.h. */
357 tree objc_global_trees[OCTI_MAX];
359 static void handle_impent (struct imp_entry *);
361 struct imp_entry *imp_list = 0;
362 int imp_count = 0; /* `@implementation' */
363 int cat_count = 0; /* `@category' */
365 enum tree_code objc_inherit_code;
366 int objc_public_flag;
368 /* Use to generate method labels. */
369 static int method_slot = 0;
373 static char *errbuf; /* Buffer for error diagnostics */
375 /* Data imported from tree.c. */
377 extern enum debug_info_type write_symbols;
379 /* Data imported from toplev.c. */
381 extern const char *dump_base_name;
383 static int flag_typed_selectors;
385 /* Store all constructed constant strings in a hash table so that
386 they get uniqued properly. */
388 struct string_descriptor GTY(())
390 /* The literal argument . */
393 /* The resulting constant string. */
397 static GTY((param_is (struct string_descriptor))) htab_t string_htab;
399 /* Store the EH-volatilized types in a hash table, for easy retrieval. */
400 struct volatilized_type GTY(())
405 static GTY((param_is (struct volatilized_type))) htab_t volatilized_htab;
407 FILE *gen_declaration_file;
409 /* Tells "encode_pointer/encode_aggregate" whether we are generating
410 type descriptors for instance variables (as opposed to methods).
411 Type descriptors for instance variables contain more information
412 than methods (for static typing and embedded structures). */
414 static int generating_instance_variables = 0;
416 /* Some platforms pass small structures through registers versus
417 through an invisible pointer. Determine at what size structure is
418 the transition point between the two possibilities. */
421 generate_struct_by_value_array (void)
424 tree field_decl, field_decl_chain;
426 int aggregate_in_mem[32];
429 /* Presumably no platform passes 32 byte structures in a register. */
430 for (i = 1; i < 32; i++)
434 /* Create an unnamed struct that has `i' character components */
435 type = start_struct (RECORD_TYPE, NULL_TREE);
437 strcpy (buffer, "c1");
438 field_decl = create_field_decl (char_type_node,
440 field_decl_chain = field_decl;
442 for (j = 1; j < i; j++)
444 sprintf (buffer, "c%d", j + 1);
445 field_decl = create_field_decl (char_type_node,
447 chainon (field_decl_chain, field_decl);
449 finish_struct (type, field_decl_chain, NULL_TREE);
451 aggregate_in_mem[i] = aggregate_value_p (type, 0);
452 if (!aggregate_in_mem[i])
456 /* We found some structures that are returned in registers instead of memory
457 so output the necessary data. */
460 for (i = 31; i >= 0; i--)
461 if (!aggregate_in_mem[i])
463 printf ("#define OBJC_MAX_STRUCT_BY_VALUE %d\n\n", i);
465 /* The first member of the structure is always 0 because we don't handle
466 structures with 0 members */
467 printf ("static int struct_forward_array[] = {\n 0");
469 for (j = 1; j <= i; j++)
470 printf (", %d", aggregate_in_mem[j]);
481 if (cxx_init () == false)
483 if (c_objc_common_init () == false)
487 #ifndef USE_MAPPED_LOCATION
488 /* Force the line number back to 0; check_newline will have
489 raised it to 1, which will make the builtin functions appear
490 not to be built in. */
494 /* If gen_declaration desired, open the output file. */
495 if (flag_gen_declaration)
497 register char * const dumpname = concat (dump_base_name, ".decl", NULL);
498 gen_declaration_file = fopen (dumpname, "w");
499 if (gen_declaration_file == 0)
500 fatal_error ("can't open %s: %m", dumpname);
504 if (flag_next_runtime)
506 TAG_GETCLASS = "objc_getClass";
507 TAG_GETMETACLASS = "objc_getMetaClass";
508 TAG_MSGSEND = "objc_msgSend";
509 TAG_MSGSENDSUPER = "objc_msgSendSuper";
510 TAG_MSGSEND_STRET = "objc_msgSend_stret";
511 TAG_MSGSENDSUPER_STRET = "objc_msgSendSuper_stret";
512 default_constant_string_class_name = "NSConstantString";
516 TAG_GETCLASS = "objc_get_class";
517 TAG_GETMETACLASS = "objc_get_meta_class";
518 TAG_MSGSEND = "objc_msg_lookup";
519 TAG_MSGSENDSUPER = "objc_msg_lookup_super";
520 /* GNU runtime does not provide special functions to support
521 structure-returning methods. */
522 default_constant_string_class_name = "NXConstantString";
523 flag_typed_selectors = 1;
528 if (print_struct_values)
529 generate_struct_by_value_array ();
535 objc_finish_file (void)
537 mark_referenced_methods ();
540 /* We need to instantiate templates _before_ we emit ObjC metadata;
541 if we do not, some metadata (such as selectors) may go missing. */
543 instantiate_pending_templates (0);
546 /* Finalize Objective-C runtime data. No need to generate tables
547 and code if only checking syntax, or if generating a PCH file. */
548 if (!flag_syntax_only && !pch_file)
551 if (gen_declaration_file)
552 fclose (gen_declaration_file);
559 /* Return the first occurrence of a method declaration corresponding
560 to sel_name in rproto_list. Search rproto_list recursively.
561 If is_class is 0, search for instance methods, otherwise for class
564 lookup_method_in_protocol_list (tree rproto_list, tree sel_name,
570 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
572 p = TREE_VALUE (rproto);
574 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
576 if ((fnd = lookup_method (is_class
577 ? PROTOCOL_CLS_METHODS (p)
578 : PROTOCOL_NST_METHODS (p), sel_name)))
580 else if (PROTOCOL_LIST (p))
581 fnd = lookup_method_in_protocol_list (PROTOCOL_LIST (p),
586 ; /* An identifier...if we could not find a protocol. */
597 lookup_protocol_in_reflist (tree rproto_list, tree lproto)
601 /* Make sure the protocol is supported by the object on the rhs. */
602 if (TREE_CODE (lproto) == PROTOCOL_INTERFACE_TYPE)
605 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
607 p = TREE_VALUE (rproto);
609 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
614 else if (PROTOCOL_LIST (p))
615 fnd = lookup_protocol_in_reflist (PROTOCOL_LIST (p), lproto);
624 ; /* An identifier...if we could not find a protocol. */
631 objc_start_class_interface (tree class, tree super_class, tree protos)
633 objc_interface_context
635 = start_class (CLASS_INTERFACE_TYPE, class, super_class, protos);
636 objc_public_flag = 0;
640 objc_start_category_interface (tree class, tree categ, tree protos)
642 objc_interface_context
643 = start_class (CATEGORY_INTERFACE_TYPE, class, categ, protos);
645 = continue_class (objc_interface_context);
649 objc_start_protocol (tree name, tree protos)
651 objc_interface_context
652 = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos);
656 objc_continue_interface (void)
659 = continue_class (objc_interface_context);
663 objc_finish_interface (void)
665 finish_class (objc_interface_context);
666 objc_interface_context = NULL_TREE;
670 objc_start_class_implementation (tree class, tree super_class)
672 objc_implementation_context
674 = start_class (CLASS_IMPLEMENTATION_TYPE, class, super_class, NULL_TREE);
675 objc_public_flag = 0;
679 objc_start_category_implementation (tree class, tree categ)
681 objc_implementation_context
682 = start_class (CATEGORY_IMPLEMENTATION_TYPE, class, categ, NULL_TREE);
684 = continue_class (objc_implementation_context);
688 objc_continue_implementation (void)
691 = continue_class (objc_implementation_context);
695 objc_finish_implementation (void)
698 if (flag_objc_call_cxx_cdtors)
699 objc_generate_cxx_cdtors ();
702 if (objc_implementation_context)
704 finish_class (objc_implementation_context);
705 objc_ivar_chain = NULL_TREE;
706 objc_implementation_context = NULL_TREE;
709 warning (0, "%<@end%> must appear in an @implementation context");
713 objc_set_visibility (int visibility)
715 objc_public_flag = visibility;
719 objc_set_method_type (enum tree_code type)
721 objc_inherit_code = (type == PLUS_EXPR
723 : INSTANCE_METHOD_DECL);
727 objc_build_method_signature (tree rettype, tree selector,
728 tree optparms, bool ellipsis)
730 return build_method_decl (objc_inherit_code, rettype, selector,
735 objc_add_method_declaration (tree decl)
737 if (!objc_interface_context)
738 fatal_error ("method declaration not in @interface context");
740 objc_add_method (objc_interface_context,
742 objc_inherit_code == CLASS_METHOD_DECL);
746 objc_start_method_definition (tree decl)
748 if (!objc_implementation_context)
749 fatal_error ("method definition not in @implementation context");
751 objc_add_method (objc_implementation_context,
753 objc_inherit_code == CLASS_METHOD_DECL);
754 start_method_def (decl);
758 objc_add_instance_variable (tree decl)
760 (void) add_instance_variable (objc_ivar_context,
765 /* Return 1 if IDENT is an ObjC/ObjC++ reserved keyword in the context of
769 objc_is_reserved_word (tree ident)
771 unsigned char code = C_RID_CODE (ident);
773 return (OBJC_IS_AT_KEYWORD (code)
775 || code == RID_CLASS || code == RID_PUBLIC
776 || code == RID_PROTECTED || code == RID_PRIVATE
777 || code == RID_TRY || code == RID_THROW || code == RID_CATCH
782 /* Return true if TYPE is 'id'. */
785 objc_is_object_id (tree type)
787 return OBJC_TYPE_NAME (type) == objc_object_id;
791 objc_is_class_id (tree type)
793 return OBJC_TYPE_NAME (type) == objc_class_id;
796 /* Construct a C struct with same name as CLASS, a base struct with tag
797 SUPER_NAME (if any), and FIELDS indicated. */
800 objc_build_struct (tree class, tree fields, tree super_name)
802 tree name = CLASS_NAME (class);
803 tree s = start_struct (RECORD_TYPE, name);
804 tree super = (super_name ? xref_tag (RECORD_TYPE, super_name) : NULL_TREE);
805 tree t, objc_info = NULL_TREE;
809 /* Prepend a packed variant of the base class into the layout. This
810 is necessary to preserve ObjC ABI compatibility. */
811 tree base = build_decl (FIELD_DECL, NULL_TREE, super);
812 tree field = TYPE_FIELDS (super);
814 while (field && TREE_CHAIN (field)
815 && TREE_CODE (TREE_CHAIN (field)) == FIELD_DECL)
816 field = TREE_CHAIN (field);
818 /* For ObjC ABI purposes, the "packed" size of a base class is the
819 the sum of the offset and the size (in bits) of the last field
822 = (field && TREE_CODE (field) == FIELD_DECL
823 ? size_binop (PLUS_EXPR,
824 size_binop (PLUS_EXPR,
827 convert (bitsizetype,
828 DECL_FIELD_OFFSET (field)),
829 bitsize_int (BITS_PER_UNIT)),
830 DECL_FIELD_BIT_OFFSET (field)),
832 : bitsize_zero_node);
833 DECL_SIZE_UNIT (base)
834 = size_binop (FLOOR_DIV_EXPR, convert (sizetype, DECL_SIZE (base)),
835 size_int (BITS_PER_UNIT));
836 DECL_ARTIFICIAL (base) = 1;
837 DECL_ALIGN (base) = 1;
838 DECL_FIELD_CONTEXT (base) = s;
840 DECL_FIELD_IS_BASE (base) = 1;
843 TREE_NO_WARNING (fields) = 1; /* Suppress C++ ABI warnings -- we */
844 #endif /* are following the ObjC ABI here. */
845 TREE_CHAIN (base) = fields;
849 /* NB: Calling finish_struct() may cause type TYPE_LANG_SPECIFIC fields
850 in all variants of this RECORD_TYPE to be clobbered, but it is therein
851 that we store protocol conformance info (e.g., 'NSObject <MyProtocol>').
852 Hence, we must squirrel away the ObjC-specific information before calling
853 finish_struct(), and then reinstate it afterwards. */
855 for (t = TYPE_NEXT_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t))
857 = chainon (objc_info,
858 build_tree_list (NULL_TREE, TYPE_OBJC_INFO (t)));
860 /* Point the struct at its related Objective-C class. */
861 INIT_TYPE_OBJC_INFO (s);
862 TYPE_OBJC_INTERFACE (s) = class;
864 s = finish_struct (s, fields, NULL_TREE);
866 for (t = TYPE_NEXT_VARIANT (s); t;
867 t = TYPE_NEXT_VARIANT (t), objc_info = TREE_CHAIN (objc_info))
869 TYPE_OBJC_INFO (t) = TREE_VALUE (objc_info);
870 /* Replace the IDENTIFIER_NODE with an actual @interface. */
871 TYPE_OBJC_INTERFACE (t) = class;
874 /* Use TYPE_BINFO structures to point at the super class, if any. */
875 objc_xref_basetypes (s, super);
877 /* Mark this struct as a class template. */
878 CLASS_STATIC_TEMPLATE (class) = s;
883 /* Build a type differing from TYPE only in that TYPE_VOLATILE is set.
884 Unlike tree.c:build_qualified_type(), preserve TYPE_LANG_SPECIFIC in the
887 objc_build_volatilized_type (tree type)
891 /* Check if we have not constructed the desired variant already. */
892 for (t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
894 /* The type qualifiers must (obviously) match up. */
895 if (!TYPE_VOLATILE (t)
896 || (TYPE_READONLY (t) != TYPE_READONLY (type))
897 || (TYPE_RESTRICT (t) != TYPE_RESTRICT (type)))
900 /* For pointer types, the pointees (and hence their TYPE_LANG_SPECIFIC
901 info, if any) must match up. */
902 if (POINTER_TYPE_P (t)
903 && (TREE_TYPE (t) != TREE_TYPE (type)))
906 /* Everything matches up! */
910 /* Ok, we could not re-use any of the pre-existing variants. Create
912 t = build_variant_type_copy (type);
913 TYPE_VOLATILE (t) = 1;
918 /* Mark DECL as being 'volatile' for purposes of Darwin
919 _setjmp()/_longjmp() exception handling. Called from
920 objc_mark_locals_volatile(). */
922 objc_volatilize_decl (tree decl)
924 /* Do not mess with variables that are 'static' or (already)
926 if (!TREE_THIS_VOLATILE (decl) && !TREE_STATIC (decl)
927 && (TREE_CODE (decl) == VAR_DECL
928 || TREE_CODE (decl) == PARM_DECL))
930 tree t = TREE_TYPE (decl);
931 struct volatilized_type key;
934 t = objc_build_volatilized_type (t);
936 loc = htab_find_slot (volatilized_htab, &key, INSERT);
940 *loc = ggc_alloc (sizeof (key));
941 ((struct volatilized_type *) *loc)->type = t;
944 TREE_TYPE (decl) = t;
945 TREE_THIS_VOLATILE (decl) = 1;
946 TREE_SIDE_EFFECTS (decl) = 1;
947 DECL_REGISTER (decl) = 0;
949 C_DECL_REGISTER (decl) = 0;
954 /* Check if protocol PROTO is adopted (directly or indirectly) by class CLS
955 (including its categoreis and superclasses) or by object type TYP.
956 Issue a warning if PROTO is not adopted anywhere and WARN is set. */
959 objc_lookup_protocol (tree proto, tree cls, tree typ, bool warn)
961 bool class_type = (cls != NULL_TREE);
967 /* Check protocols adopted by the class and its categories. */
968 for (c = cls; c; c = CLASS_CATEGORY_LIST (c))
970 if (lookup_protocol_in_reflist (CLASS_PROTOCOL_LIST (c), proto))
974 /* Repeat for superclasses. */
975 cls = lookup_interface (CLASS_SUPER_NAME (cls));
978 /* Check for any protocols attached directly to the object type. */
979 if (TYPE_HAS_OBJC_INFO (typ))
981 if (lookup_protocol_in_reflist (TYPE_OBJC_PROTOCOL_LIST (typ), proto))
987 strcpy (errbuf, class_type ? "class \'" : "type \'");
988 gen_type_name_0 (class_type ? typ : TYPE_POINTER_TO (typ));
989 strcat (errbuf, "\' does not ");
990 /* NB: Types 'id' and 'Class' cannot reasonably be described as
991 "implementing" a given protocol, since they do not have an
993 strcat (errbuf, class_type ? "implement" : "conform to");
994 strcat (errbuf, " the \'");
995 strcat (errbuf, IDENTIFIER_POINTER (PROTOCOL_NAME (proto)));
996 strcat (errbuf, "\' protocol");
1003 /* Check if class RCLS and instance struct type RTYP conform to at least the
1004 same protocols that LCLS and LTYP conform to. */
1007 objc_compare_protocols (tree lcls, tree ltyp, tree rcls, tree rtyp, bool warn)
1010 bool have_lproto = false;
1014 /* NB: We do _not_ look at categories defined for LCLS; these may or
1015 may not get loaded in, and therefore it is unreasonable to require
1016 that RCLS/RTYP must implement any of their protocols. */
1017 for (p = CLASS_PROTOCOL_LIST (lcls); p; p = TREE_CHAIN (p))
1021 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1025 /* Repeat for superclasses. */
1026 lcls = lookup_interface (CLASS_SUPER_NAME (lcls));
1029 /* Check for any protocols attached directly to the object type. */
1030 if (TYPE_HAS_OBJC_INFO (ltyp))
1032 for (p = TYPE_OBJC_PROTOCOL_LIST (ltyp); p; p = TREE_CHAIN (p))
1036 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1041 /* NB: If LTYP and LCLS have no protocols to search for, return 'true'
1042 vacuously, _unless_ RTYP is a protocol-qualified 'id'. We can get
1043 away with simply checking for 'id' or 'Class' (!RCLS), since this
1044 routine will not get called in other cases. */
1045 return have_lproto || (rcls != NULL_TREE);
1048 /* Determine if it is permissible to assign (if ARGNO is greater than -3)
1049 an instance of RTYP to an instance of LTYP or to compare the two
1050 (if ARGNO is equal to -3), per ObjC type system rules. Before
1051 returning 'true', this routine may issue warnings related to, e.g.,
1052 protocol conformance. When returning 'false', the routine must
1053 produce absolutely no warnings; the C or C++ front-end will do so
1054 instead, if needed. If either LTYP or RTYP is not an Objective-C type,
1055 the routine must return 'false'.
1057 The ARGNO parameter is encoded as follows:
1058 >= 1 Parameter number (CALLEE contains function being called);
1062 -3 Comparison (LTYP and RTYP may match in either direction). */
1065 objc_compare_types (tree ltyp, tree rtyp, int argno, tree callee)
1067 tree lcls, rcls, lproto, rproto;
1068 bool pointers_compatible;
1070 /* We must be dealing with pointer types */
1071 if (!POINTER_TYPE_P (ltyp) || !POINTER_TYPE_P (rtyp))
1076 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
1077 rtyp = TREE_TYPE (rtyp);
1079 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
1081 /* Past this point, we are only interested in ObjC class instances,
1082 or 'id' or 'Class'. */
1083 if (TREE_CODE (ltyp) != RECORD_TYPE || TREE_CODE (rtyp) != RECORD_TYPE)
1086 if (!objc_is_object_id (ltyp) && !objc_is_class_id (ltyp)
1087 && !TYPE_HAS_OBJC_INFO (ltyp))
1090 if (!objc_is_object_id (rtyp) && !objc_is_class_id (rtyp)
1091 && !TYPE_HAS_OBJC_INFO (rtyp))
1094 /* Past this point, we are committed to returning 'true' to the caller.
1095 However, we can still warn about type and/or protocol mismatches. */
1097 if (TYPE_HAS_OBJC_INFO (ltyp))
1099 lcls = TYPE_OBJC_INTERFACE (ltyp);
1100 lproto = TYPE_OBJC_PROTOCOL_LIST (ltyp);
1103 lcls = lproto = NULL_TREE;
1105 if (TYPE_HAS_OBJC_INFO (rtyp))
1107 rcls = TYPE_OBJC_INTERFACE (rtyp);
1108 rproto = TYPE_OBJC_PROTOCOL_LIST (rtyp);
1111 rcls = rproto = NULL_TREE;
1113 /* If we could not find an @interface declaration, we must have
1114 only seen a @class declaration; for purposes of type comparison,
1115 treat it as a stand-alone (root) class. */
1117 if (lcls && TREE_CODE (lcls) == IDENTIFIER_NODE)
1120 if (rcls && TREE_CODE (rcls) == IDENTIFIER_NODE)
1123 /* If either type is an unqualified 'id', we're done. */
1124 if ((!lproto && objc_is_object_id (ltyp))
1125 || (!rproto && objc_is_object_id (rtyp)))
1128 pointers_compatible = (TYPE_MAIN_VARIANT (ltyp) == TYPE_MAIN_VARIANT (rtyp));
1130 /* If the underlying types are the same, and at most one of them has
1131 a protocol list, we do not need to issue any diagnostics. */
1132 if (pointers_compatible && (!lproto || !rproto))
1135 /* If exactly one of the types is 'Class', issue a diagnostic; any
1136 exceptions of this rule have already been handled. */
1137 if (objc_is_class_id (ltyp) ^ objc_is_class_id (rtyp))
1138 pointers_compatible = false;
1139 /* Otherwise, check for inheritance relations. */
1142 if (!pointers_compatible)
1144 = (objc_is_object_id (ltyp) || objc_is_object_id (rtyp));
1146 if (!pointers_compatible)
1147 pointers_compatible = DERIVED_FROM_P (ltyp, rtyp);
1149 if (!pointers_compatible && argno == -3)
1150 pointers_compatible = DERIVED_FROM_P (rtyp, ltyp);
1153 /* If the pointers match modulo protocols, check for protocol conformance
1155 if (pointers_compatible)
1157 pointers_compatible = objc_compare_protocols (lcls, ltyp, rcls, rtyp,
1160 if (!pointers_compatible && argno == -3)
1161 pointers_compatible = objc_compare_protocols (rcls, rtyp, lcls, ltyp,
1165 if (!pointers_compatible)
1167 /* NB: For the time being, we shall make our warnings look like their
1168 C counterparts. In the future, we may wish to make them more
1173 warning (0, "comparison of distinct Objective-C types lacks a cast");
1177 warning (0, "initialization from distinct Objective-C type");
1181 warning (0, "assignment from distinct Objective-C type");
1185 warning (0, "distinct Objective-C type in return");
1189 warning (0, "passing argument %d of %qE from distinct "
1190 "Objective-C type", argno, callee);
1198 /* Check if LTYP and RTYP have the same type qualifiers. If either type
1199 lives in the volatilized hash table, ignore the 'volatile' bit when
1200 making the comparison. */
1203 objc_type_quals_match (tree ltyp, tree rtyp)
1205 int lquals = TYPE_QUALS (ltyp), rquals = TYPE_QUALS (rtyp);
1206 struct volatilized_type key;
1210 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1211 lquals &= ~TYPE_QUAL_VOLATILE;
1215 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1216 rquals &= ~TYPE_QUAL_VOLATILE;
1218 return (lquals == rquals);
1222 /* Determine if CHILD is derived from PARENT. The routine assumes that
1223 both parameters are RECORD_TYPEs, and is non-reflexive. */
1226 objc_derived_from_p (tree parent, tree child)
1228 parent = TYPE_MAIN_VARIANT (parent);
1230 for (child = TYPE_MAIN_VARIANT (child);
1231 TYPE_BINFO (child) && BINFO_N_BASE_BINFOS (TYPE_BINFO (child));)
1233 child = TYPE_MAIN_VARIANT (BINFO_TYPE (BINFO_BASE_BINFO
1234 (TYPE_BINFO (child),
1237 if (child == parent)
1246 objc_build_component_ref (tree datum, tree component)
1248 /* If COMPONENT is NULL, the caller is referring to the anonymous
1249 base class field. */
1252 tree base = TYPE_FIELDS (TREE_TYPE (datum));
1254 return build3 (COMPONENT_REF, TREE_TYPE (base), datum, base, NULL_TREE);
1257 /* The 'build_component_ref' routine has been removed from the C++
1258 front-end, but 'finish_class_member_access_expr' seems to be
1259 a worthy substitute. */
1261 return finish_class_member_access_expr (datum, component, false);
1263 return build_component_ref (datum, component);
1267 /* Recursively copy inheritance information rooted at BINFO. To do this,
1268 we emulate the song and dance performed by cp/tree.c:copy_binfo(). */
1271 objc_copy_binfo (tree binfo)
1273 tree btype = BINFO_TYPE (binfo);
1274 tree binfo2 = make_tree_binfo (BINFO_N_BASE_BINFOS (binfo));
1278 BINFO_TYPE (binfo2) = btype;
1279 BINFO_OFFSET (binfo2) = BINFO_OFFSET (binfo);
1280 BINFO_BASE_ACCESSES (binfo2) = BINFO_BASE_ACCESSES (binfo);
1282 /* Recursively copy base binfos of BINFO. */
1283 for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
1285 tree base_binfo2 = objc_copy_binfo (base_binfo);
1287 BINFO_INHERITANCE_CHAIN (base_binfo2) = binfo2;
1288 BINFO_BASE_APPEND (binfo2, base_binfo2);
1294 /* Record superclass information provided in BASETYPE for ObjC class REF.
1295 This is loosely based on cp/decl.c:xref_basetypes(). */
1298 objc_xref_basetypes (tree ref, tree basetype)
1300 tree binfo = make_tree_binfo (basetype ? 1 : 0);
1302 TYPE_BINFO (ref) = binfo;
1303 BINFO_OFFSET (binfo) = size_zero_node;
1304 BINFO_TYPE (binfo) = ref;
1308 tree base_binfo = objc_copy_binfo (TYPE_BINFO (basetype));
1310 BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
1311 BINFO_BASE_ACCESSES (binfo) = VEC_alloc (tree, gc, 1);
1312 BINFO_BASE_APPEND (binfo, base_binfo);
1313 BINFO_BASE_ACCESS_APPEND (binfo, access_public_node);
1318 volatilized_hash (const void *ptr)
1320 tree typ = ((struct volatilized_type *)ptr)->type;
1322 return htab_hash_pointer(typ);
1326 volatilized_eq (const void *ptr1, const void *ptr2)
1328 tree typ1 = ((struct volatilized_type *)ptr1)->type;
1329 tree typ2 = ((struct volatilized_type *)ptr2)->type;
1331 return typ1 == typ2;
1334 /* Called from finish_decl. */
1337 objc_check_decl (tree decl)
1339 tree type = TREE_TYPE (decl);
1341 if (TREE_CODE (type) != RECORD_TYPE)
1343 if (OBJC_TYPE_NAME (type) && (type = objc_is_class_name (OBJC_TYPE_NAME (type))))
1344 error ("statically allocated instance of Objective-C class %qs",
1345 IDENTIFIER_POINTER (type));
1348 /* Construct a PROTOCOLS-qualified variant of INTERFACE, where INTERFACE may
1349 either name an Objective-C class, or refer to the special 'id' or 'Class'
1350 types. If INTERFACE is not a valid ObjC type, just return it unchanged. */
1353 objc_get_protocol_qualified_type (tree interface, tree protocols)
1355 /* If INTERFACE is not provided, default to 'id'. */
1356 tree type = (interface ? objc_is_id (interface) : objc_object_type);
1357 bool is_ptr = (type != NULL_TREE);
1361 type = objc_is_class_name (interface);
1364 type = xref_tag (RECORD_TYPE, type);
1371 type = build_variant_type_copy (type);
1373 /* For pointers (i.e., 'id' or 'Class'), attach the protocol(s)
1377 TREE_TYPE (type) = build_variant_type_copy (TREE_TYPE (type));
1378 TYPE_POINTER_TO (TREE_TYPE (type)) = type;
1379 type = TREE_TYPE (type);
1382 /* Look up protocols and install in lang specific list. */
1383 DUP_TYPE_OBJC_INFO (type, TYPE_MAIN_VARIANT (type));
1384 TYPE_OBJC_PROTOCOL_LIST (type) = lookup_and_install_protocols (protocols);
1386 /* For RECORD_TYPEs, point to the @interface; for 'id' and 'Class',
1387 return the pointer to the new pointee variant. */
1389 type = TYPE_POINTER_TO (type);
1391 TYPE_OBJC_INTERFACE (type)
1392 = TYPE_OBJC_INTERFACE (TYPE_MAIN_VARIANT (type));
1398 /* Check for circular dependencies in protocols. The arguments are
1399 PROTO, the protocol to check, and LIST, a list of protocol it
1403 check_protocol_recursively (tree proto, tree list)
1407 for (p = list; p; p = TREE_CHAIN (p))
1409 tree pp = TREE_VALUE (p);
1411 if (TREE_CODE (pp) == IDENTIFIER_NODE)
1412 pp = lookup_protocol (pp);
1415 fatal_error ("protocol %qs has circular dependency",
1416 IDENTIFIER_POINTER (PROTOCOL_NAME (pp)));
1418 check_protocol_recursively (proto, PROTOCOL_LIST (pp));
1422 /* Look up PROTOCOLS, and return a list of those that are found.
1423 If none are found, return NULL. */
1426 lookup_and_install_protocols (tree protocols)
1429 tree return_value = NULL_TREE;
1431 for (proto = protocols; proto; proto = TREE_CHAIN (proto))
1433 tree ident = TREE_VALUE (proto);
1434 tree p = lookup_protocol (ident);
1437 return_value = chainon (return_value,
1438 build_tree_list (NULL_TREE, p));
1439 else if (ident != error_mark_node)
1440 error ("cannot find protocol declaration for %qs",
1441 IDENTIFIER_POINTER (ident));
1444 return return_value;
1447 /* Create a declaration for field NAME of a given TYPE. */
1450 create_field_decl (tree type, const char *name)
1452 return build_decl (FIELD_DECL, get_identifier (name), type);
1455 /* Create a global, static declaration for variable NAME of a given TYPE. The
1456 finish_var_decl() routine will need to be called on it afterwards. */
1459 start_var_decl (tree type, const char *name)
1461 tree var = build_decl (VAR_DECL, get_identifier (name), type);
1463 TREE_STATIC (var) = 1;
1464 DECL_INITIAL (var) = error_mark_node; /* A real initializer is coming... */
1465 DECL_IGNORED_P (var) = 1;
1466 DECL_ARTIFICIAL (var) = 1;
1467 DECL_CONTEXT (var) = NULL_TREE;
1469 DECL_THIS_STATIC (var) = 1; /* squash redeclaration errors */
1475 /* Finish off the variable declaration created by start_var_decl(). */
1478 finish_var_decl (tree var, tree initializer)
1480 finish_decl (var, initializer, NULL_TREE);
1481 /* Ensure that the variable actually gets output. */
1482 mark_decl_referenced (var);
1483 /* Mark the decl to avoid "defined but not used" warning. */
1484 TREE_USED (var) = 1;
1487 /* Find the decl for the constant string class reference. This is only
1488 used for the NeXT runtime. */
1491 setup_string_decl (void)
1496 /* %s in format will provide room for terminating null */
1497 length = strlen (STRING_OBJECT_GLOBAL_FORMAT)
1498 + strlen (constant_string_class_name);
1499 name = xmalloc (length);
1500 sprintf (name, STRING_OBJECT_GLOBAL_FORMAT,
1501 constant_string_class_name);
1502 constant_string_global_id = get_identifier (name);
1503 string_class_decl = lookup_name (constant_string_global_id);
1505 return string_class_decl;
1508 /* Purpose: "play" parser, creating/installing representations
1509 of the declarations that are required by Objective-C.
1513 type_spec--------->sc_spec
1514 (tree_list) (tree_list)
1517 identifier_node identifier_node */
1520 synth_module_prologue (void)
1523 enum debug_info_type save_write_symbols = write_symbols;
1524 const struct gcc_debug_hooks *const save_hooks = debug_hooks;
1526 /* Suppress outputting debug symbols, because
1527 dbxout_init hasn'r been called yet. */
1528 write_symbols = NO_DEBUG;
1529 debug_hooks = &do_nothing_debug_hooks;
1532 push_lang_context (lang_name_c); /* extern "C" */
1535 /* The following are also defined in <objc/objc.h> and friends. */
1537 objc_object_id = get_identifier (TAG_OBJECT);
1538 objc_class_id = get_identifier (TAG_CLASS);
1540 objc_object_reference = xref_tag (RECORD_TYPE, objc_object_id);
1541 objc_class_reference = xref_tag (RECORD_TYPE, objc_class_id);
1543 objc_object_type = build_pointer_type (objc_object_reference);
1544 objc_class_type = build_pointer_type (objc_class_reference);
1546 objc_object_name = get_identifier (OBJECT_TYPEDEF_NAME);
1547 objc_class_name = get_identifier (CLASS_TYPEDEF_NAME);
1549 /* Declare the 'id' and 'Class' typedefs. */
1551 type = lang_hooks.decls.pushdecl (build_decl (TYPE_DECL,
1554 DECL_IN_SYSTEM_HEADER (type) = 1;
1555 type = lang_hooks.decls.pushdecl (build_decl (TYPE_DECL,
1558 DECL_IN_SYSTEM_HEADER (type) = 1;
1560 /* Forward-declare '@interface Protocol'. */
1562 type = get_identifier (PROTOCOL_OBJECT_CLASS_NAME);
1563 objc_declare_class (tree_cons (NULL_TREE, type, NULL_TREE));
1564 objc_protocol_type = build_pointer_type (xref_tag (RECORD_TYPE,
1567 /* Declare type of selector-objects that represent an operation name. */
1569 if (flag_next_runtime)
1570 /* `struct objc_selector *' */
1572 = build_pointer_type (xref_tag (RECORD_TYPE,
1573 get_identifier (TAG_SELECTOR)));
1575 /* `const struct objc_selector *' */
1577 = build_pointer_type
1578 (build_qualified_type (xref_tag (RECORD_TYPE,
1579 get_identifier (TAG_SELECTOR)),
1582 /* Declare receiver type used for dispatching messages to 'super'. */
1584 /* `struct objc_super *' */
1585 objc_super_type = build_pointer_type (xref_tag (RECORD_TYPE,
1586 get_identifier (TAG_SUPER)));
1588 /* Declare pointers to method and ivar lists. */
1589 objc_method_list_ptr = build_pointer_type
1590 (xref_tag (RECORD_TYPE,
1591 get_identifier (UTAG_METHOD_LIST)));
1592 objc_method_proto_list_ptr
1593 = build_pointer_type (xref_tag (RECORD_TYPE,
1594 get_identifier (UTAG_METHOD_PROTOTYPE_LIST)));
1595 objc_ivar_list_ptr = build_pointer_type
1596 (xref_tag (RECORD_TYPE,
1597 get_identifier (UTAG_IVAR_LIST)));
1599 /* TREE_NOTHROW is cleared for the message-sending functions,
1600 because the function that gets called can throw in Obj-C++, or
1601 could itself call something that can throw even in Obj-C. */
1603 if (flag_next_runtime)
1605 /* NB: In order to call one of the ..._stret (struct-returning)
1606 functions, the function *MUST* first be cast to a signature that
1607 corresponds to the actual ObjC method being invoked. This is
1608 what is done by the build_objc_method_call() routine below. */
1610 /* id objc_msgSend (id, SEL, ...); */
1611 /* id objc_msgSendNonNil (id, SEL, ...); */
1612 /* id objc_msgSend_stret (id, SEL, ...); */
1613 /* id objc_msgSendNonNil_stret (id, SEL, ...); */
1615 = build_function_type (objc_object_type,
1616 tree_cons (NULL_TREE, objc_object_type,
1617 tree_cons (NULL_TREE, objc_selector_type,
1619 umsg_decl = builtin_function (TAG_MSGSEND,
1620 type, 0, NOT_BUILT_IN,
1622 umsg_nonnil_decl = builtin_function (TAG_MSGSEND_NONNIL,
1623 type, 0, NOT_BUILT_IN,
1625 umsg_stret_decl = builtin_function (TAG_MSGSEND_STRET,
1626 type, 0, NOT_BUILT_IN,
1628 umsg_nonnil_stret_decl = builtin_function (TAG_MSGSEND_NONNIL_STRET,
1629 type, 0, NOT_BUILT_IN,
1632 /* These can throw, because the function that gets called can throw
1633 in Obj-C++, or could itself call something that can throw even
1635 TREE_NOTHROW (umsg_decl) = 0;
1636 TREE_NOTHROW (umsg_nonnil_decl) = 0;
1637 TREE_NOTHROW (umsg_stret_decl) = 0;
1638 TREE_NOTHROW (umsg_nonnil_stret_decl) = 0;
1640 /* id objc_msgSend_Fast (id, SEL, ...)
1641 __attribute__ ((hard_coded_address (OFFS_MSGSEND_FAST))); */
1642 #ifdef OFFS_MSGSEND_FAST
1643 umsg_fast_decl = builtin_function (TAG_MSGSEND_FAST,
1644 type, 0, NOT_BUILT_IN,
1646 TREE_NOTHROW (umsg_fast_decl) = 0;
1647 DECL_ATTRIBUTES (umsg_fast_decl)
1648 = tree_cons (get_identifier ("hard_coded_address"),
1649 build_int_cst (NULL_TREE, OFFS_MSGSEND_FAST),
1652 /* No direct dispatch availible. */
1653 umsg_fast_decl = umsg_decl;
1656 /* id objc_msgSendSuper (struct objc_super *, SEL, ...); */
1657 /* id objc_msgSendSuper_stret (struct objc_super *, SEL, ...); */
1659 = build_function_type (objc_object_type,
1660 tree_cons (NULL_TREE, objc_super_type,
1661 tree_cons (NULL_TREE, objc_selector_type,
1663 umsg_super_decl = builtin_function (TAG_MSGSENDSUPER,
1664 type, 0, NOT_BUILT_IN,
1666 umsg_super_stret_decl = builtin_function (TAG_MSGSENDSUPER_STRET,
1667 type, 0, NOT_BUILT_IN, 0,
1669 TREE_NOTHROW (umsg_super_decl) = 0;
1670 TREE_NOTHROW (umsg_super_stret_decl) = 0;
1674 /* GNU runtime messenger entry points. */
1676 /* typedef id (*IMP)(id, SEL, ...); */
1678 = build_pointer_type
1679 (build_function_type (objc_object_type,
1680 tree_cons (NULL_TREE, objc_object_type,
1681 tree_cons (NULL_TREE, objc_selector_type,
1684 /* IMP objc_msg_lookup (id, SEL); */
1686 = build_function_type (IMP_type,
1687 tree_cons (NULL_TREE, objc_object_type,
1688 tree_cons (NULL_TREE, objc_selector_type,
1689 OBJC_VOID_AT_END)));
1690 umsg_decl = builtin_function (TAG_MSGSEND,
1691 type, 0, NOT_BUILT_IN,
1693 TREE_NOTHROW (umsg_decl) = 0;
1695 /* IMP objc_msg_lookup_super (struct objc_super *, SEL); */
1697 = build_function_type (IMP_type,
1698 tree_cons (NULL_TREE, objc_super_type,
1699 tree_cons (NULL_TREE, objc_selector_type,
1700 OBJC_VOID_AT_END)));
1701 umsg_super_decl = builtin_function (TAG_MSGSENDSUPER,
1702 type, 0, NOT_BUILT_IN,
1704 TREE_NOTHROW (umsg_super_decl) = 0;
1706 /* The following GNU runtime entry point is called to initialize
1709 __objc_exec_class (void *); */
1711 = build_function_type (void_type_node,
1712 tree_cons (NULL_TREE, ptr_type_node,
1714 execclass_decl = builtin_function (TAG_EXECCLASS,
1715 type, 0, NOT_BUILT_IN,
1719 /* id objc_getClass (const char *); */
1721 type = build_function_type (objc_object_type,
1722 tree_cons (NULL_TREE,
1723 const_string_type_node,
1727 = builtin_function (TAG_GETCLASS, type, 0, NOT_BUILT_IN,
1730 /* id objc_getMetaClass (const char *); */
1732 objc_get_meta_class_decl
1733 = builtin_function (TAG_GETMETACLASS, type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
1735 build_class_template ();
1736 build_super_template ();
1737 build_protocol_template ();
1738 build_category_template ();
1739 build_objc_exception_stuff ();
1741 if (flag_next_runtime)
1742 build_next_objc_exception_stuff ();
1744 /* static SEL _OBJC_SELECTOR_TABLE[]; */
1746 if (! flag_next_runtime)
1747 build_selector_table_decl ();
1749 /* Forward declare constant_string_id and constant_string_type. */
1750 if (!constant_string_class_name)
1751 constant_string_class_name = default_constant_string_class_name;
1753 constant_string_id = get_identifier (constant_string_class_name);
1754 objc_declare_class (tree_cons (NULL_TREE, constant_string_id, NULL_TREE));
1756 /* Pre-build the following entities - for speed/convenience. */
1757 self_id = get_identifier ("self");
1758 ucmd_id = get_identifier ("_cmd");
1761 pop_lang_context ();
1764 write_symbols = save_write_symbols;
1765 debug_hooks = save_hooks;
1768 /* Ensure that the ivar list for NSConstantString/NXConstantString
1769 (or whatever was specified via `-fconstant-string-class')
1770 contains fields at least as large as the following three, so that
1771 the runtime can stomp on them with confidence:
1773 struct STRING_OBJECT_CLASS_NAME
1777 unsigned int length;
1781 check_string_class_template (void)
1783 tree field_decl = objc_get_class_ivars (constant_string_id);
1785 #define AT_LEAST_AS_LARGE_AS(F, T) \
1786 (F && TREE_CODE (F) == FIELD_DECL \
1787 && (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (F))) \
1788 >= TREE_INT_CST_LOW (TYPE_SIZE (T))))
1790 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
1793 field_decl = TREE_CHAIN (field_decl);
1794 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
1797 field_decl = TREE_CHAIN (field_decl);
1798 return AT_LEAST_AS_LARGE_AS (field_decl, unsigned_type_node);
1800 #undef AT_LEAST_AS_LARGE_AS
1803 /* Avoid calling `check_string_class_template ()' more than once. */
1804 static GTY(()) int string_layout_checked;
1806 /* Construct an internal string layout to be used as a template for
1807 creating NSConstantString/NXConstantString instances. */
1810 objc_build_internal_const_str_type (void)
1812 tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);
1813 tree fields = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);
1814 tree field = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);
1816 TREE_CHAIN (field) = fields; fields = field;
1817 field = build_decl (FIELD_DECL, NULL_TREE, unsigned_type_node);
1818 TREE_CHAIN (field) = fields; fields = field;
1819 /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in
1821 finish_builtin_struct (type, "__builtin_ObjCString",
1827 /* Custom build_string which sets TREE_TYPE! */
1830 my_build_string (int len, const char *str)
1832 return fix_string_type (build_string (len, str));
1835 /* Build a string with contents STR and length LEN and convert it to a
1839 my_build_string_pointer (int len, const char *str)
1841 tree string = my_build_string (len, str);
1842 tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));
1843 return build1 (ADDR_EXPR, ptrtype, string);
1847 string_hash (const void *ptr)
1849 tree str = ((struct string_descriptor *)ptr)->literal;
1850 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);
1851 int i, len = TREE_STRING_LENGTH (str);
1854 for (i = 0; i < len; i++)
1855 h = ((h * 613) + p[i]);
1861 string_eq (const void *ptr1, const void *ptr2)
1863 tree str1 = ((struct string_descriptor *)ptr1)->literal;
1864 tree str2 = ((struct string_descriptor *)ptr2)->literal;
1865 int len1 = TREE_STRING_LENGTH (str1);
1867 return (len1 == TREE_STRING_LENGTH (str2)
1868 && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),
1872 /* Given a chain of STRING_CST's, build a static instance of
1873 NXConstantString which points at the concatenation of those
1874 strings. We place the string object in the __string_objects
1875 section of the __OBJC segment. The Objective-C runtime will
1876 initialize the isa pointers of the string objects to point at the
1877 NXConstantString class object. */
1880 objc_build_string_object (tree string)
1882 tree initlist, constructor, constant_string_class;
1885 struct string_descriptor *desc, key;
1888 /* Prep the string argument. */
1889 string = fix_string_type (string);
1890 TREE_SET_CODE (string, STRING_CST);
1891 length = TREE_STRING_LENGTH (string) - 1;
1893 /* Check whether the string class being used actually exists and has the
1894 correct ivar layout. */
1895 if (!string_layout_checked)
1897 string_layout_checked = -1;
1898 constant_string_class = lookup_interface (constant_string_id);
1899 internal_const_str_type = objc_build_internal_const_str_type ();
1901 if (!constant_string_class
1902 || !(constant_string_type
1903 = CLASS_STATIC_TEMPLATE (constant_string_class)))
1904 error ("cannot find interface declaration for %qs",
1905 IDENTIFIER_POINTER (constant_string_id));
1906 /* The NSConstantString/NXConstantString ivar layout is now known. */
1907 else if (!check_string_class_template ())
1908 error ("interface %qs does not have valid constant string layout",
1909 IDENTIFIER_POINTER (constant_string_id));
1910 /* For the NeXT runtime, we can generate a literal reference
1911 to the string class, don't need to run a constructor. */
1912 else if (flag_next_runtime && !setup_string_decl ())
1913 error ("cannot find reference tag for class %qs",
1914 IDENTIFIER_POINTER (constant_string_id));
1917 string_layout_checked = 1; /* Success! */
1918 add_class_reference (constant_string_id);
1922 if (string_layout_checked == -1)
1923 return error_mark_node;
1925 /* Perhaps we already constructed a constant string just like this one? */
1926 key.literal = string;
1927 loc = htab_find_slot (string_htab, &key, INSERT);
1933 *loc = desc = ggc_alloc (sizeof (*desc));
1934 desc->literal = string;
1936 /* GNU: (NXConstantString *) & ((__builtin_ObjCString) { NULL, string, length }) */
1937 /* NeXT: (NSConstantString *) & ((__builtin_ObjCString) { isa, string, length }) */
1938 fields = TYPE_FIELDS (internal_const_str_type);
1940 = build_tree_list (fields,
1942 ? build_unary_op (ADDR_EXPR, string_class_decl, 0)
1943 : build_int_cst (NULL_TREE, 0));
1944 fields = TREE_CHAIN (fields);
1945 initlist = tree_cons (fields, build_unary_op (ADDR_EXPR, string, 1),
1947 fields = TREE_CHAIN (fields);
1948 initlist = tree_cons (fields, build_int_cst (NULL_TREE, length),
1950 constructor = objc_build_constructor (internal_const_str_type,
1951 nreverse (initlist));
1952 TREE_INVARIANT (constructor) = true;
1954 if (!flag_next_runtime)
1956 = objc_add_static_instance (constructor, constant_string_type);
1959 var = build_decl (CONST_DECL, NULL, TREE_TYPE (constructor));
1960 DECL_INITIAL (var) = constructor;
1961 TREE_STATIC (var) = 1;
1962 pushdecl_top_level (var);
1965 desc->constructor = constructor;
1968 addr = convert (build_pointer_type (constant_string_type),
1969 build_unary_op (ADDR_EXPR, desc->constructor, 1));
1974 /* Declare a static instance of CLASS_DECL initialized by CONSTRUCTOR. */
1976 static GTY(()) int num_static_inst;
1979 objc_add_static_instance (tree constructor, tree class_decl)
1984 /* Find the list of static instances for the CLASS_DECL. Create one if
1986 for (chain = &objc_static_instances;
1987 *chain && TREE_VALUE (*chain) != class_decl;
1988 chain = &TREE_CHAIN (*chain));
1991 *chain = tree_cons (NULL_TREE, class_decl, NULL_TREE);
1992 add_objc_string (OBJC_TYPE_NAME (class_decl), class_names);
1995 sprintf (buf, "_OBJC_INSTANCE_%d", num_static_inst++);
1996 decl = build_decl (VAR_DECL, get_identifier (buf), class_decl);
1997 DECL_COMMON (decl) = 1;
1998 TREE_STATIC (decl) = 1;
1999 DECL_ARTIFICIAL (decl) = 1;
2000 DECL_INITIAL (decl) = constructor;
2002 /* We may be writing something else just now.
2003 Postpone till end of input. */
2004 DECL_DEFER_OUTPUT (decl) = 1;
2005 pushdecl_top_level (decl);
2006 rest_of_decl_compilation (decl, 1, 0);
2008 /* Add the DECL to the head of this CLASS' list. */
2009 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE, decl, TREE_PURPOSE (*chain));
2014 /* Build a static constant CONSTRUCTOR
2015 with type TYPE and elements ELTS. */
2018 objc_build_constructor (tree type, tree elts)
2020 tree constructor = build_constructor_from_list (type, elts);
2022 TREE_CONSTANT (constructor) = 1;
2023 TREE_STATIC (constructor) = 1;
2024 TREE_READONLY (constructor) = 1;
2027 /* Adjust for impedance mismatch. We should figure out how to build
2028 CONSTRUCTORs that consistently please both the C and C++ gods. */
2029 if (!TREE_PURPOSE (elts))
2030 TREE_TYPE (constructor) = NULL_TREE;
2031 TREE_HAS_CONSTRUCTOR (constructor) = 1;
2037 /* Take care of defining and initializing _OBJC_SYMBOLS. */
2039 /* Predefine the following data type:
2047 void *defs[cls_def_cnt + cat_def_cnt];
2051 build_objc_symtab_template (void)
2053 tree field_decl, field_decl_chain;
2055 objc_symtab_template
2056 = start_struct (RECORD_TYPE, get_identifier (UTAG_SYMTAB));
2058 /* long sel_ref_cnt; */
2059 field_decl = create_field_decl (long_integer_type_node, "sel_ref_cnt");
2060 field_decl_chain = field_decl;
2063 field_decl = create_field_decl (build_pointer_type (objc_selector_type),
2065 chainon (field_decl_chain, field_decl);
2067 /* short cls_def_cnt; */
2068 field_decl = create_field_decl (short_integer_type_node, "cls_def_cnt");
2069 chainon (field_decl_chain, field_decl);
2071 /* short cat_def_cnt; */
2072 field_decl = create_field_decl (short_integer_type_node,
2074 chainon (field_decl_chain, field_decl);
2076 if (imp_count || cat_count || !flag_next_runtime)
2078 /* void *defs[imp_count + cat_count (+ 1)]; */
2079 /* NB: The index is one less than the size of the array. */
2080 int index = imp_count + cat_count
2081 + (flag_next_runtime? -1: 0);
2082 field_decl = create_field_decl
2085 build_index_type (build_int_cst (NULL_TREE, index))),
2087 chainon (field_decl_chain, field_decl);
2090 finish_struct (objc_symtab_template, field_decl_chain, NULL_TREE);
2093 /* Create the initial value for the `defs' field of _objc_symtab.
2094 This is a CONSTRUCTOR. */
2097 init_def_list (tree type)
2099 tree expr, initlist = NULL_TREE;
2100 struct imp_entry *impent;
2103 for (impent = imp_list; impent; impent = impent->next)
2105 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
2107 expr = build_unary_op (ADDR_EXPR, impent->class_decl, 0);
2108 initlist = tree_cons (NULL_TREE, expr, initlist);
2113 for (impent = imp_list; impent; impent = impent->next)
2115 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2117 expr = build_unary_op (ADDR_EXPR, impent->class_decl, 0);
2118 initlist = tree_cons (NULL_TREE, expr, initlist);
2122 if (!flag_next_runtime)
2124 /* statics = { ..., _OBJC_STATIC_INSTANCES, ... } */
2127 if (static_instances_decl)
2128 expr = build_unary_op (ADDR_EXPR, static_instances_decl, 0);
2130 expr = build_int_cst (NULL_TREE, 0);
2132 initlist = tree_cons (NULL_TREE, expr, initlist);
2135 return objc_build_constructor (type, nreverse (initlist));
2138 /* Construct the initial value for all of _objc_symtab. */
2141 init_objc_symtab (tree type)
2145 /* sel_ref_cnt = { ..., 5, ... } */
2147 initlist = build_tree_list (NULL_TREE,
2148 build_int_cst (long_integer_type_node, 0));
2150 /* refs = { ..., _OBJC_SELECTOR_TABLE, ... } */
2152 if (flag_next_runtime || ! sel_ref_chain)
2153 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
2156 = tree_cons (NULL_TREE,
2157 convert (build_pointer_type (objc_selector_type),
2158 build_unary_op (ADDR_EXPR,
2159 UOBJC_SELECTOR_TABLE_decl, 1)),
2162 /* cls_def_cnt = { ..., 5, ... } */
2164 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, imp_count), initlist);
2166 /* cat_def_cnt = { ..., 5, ... } */
2168 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, cat_count), initlist);
2170 /* cls_def = { ..., { &Foo, &Bar, ...}, ... } */
2172 if (imp_count || cat_count || !flag_next_runtime)
2175 tree field = TYPE_FIELDS (type);
2176 field = TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (field))));
2178 initlist = tree_cons (NULL_TREE, init_def_list (TREE_TYPE (field)),
2182 return objc_build_constructor (type, nreverse (initlist));
2185 /* Generate forward declarations for metadata such as
2186 'OBJC_CLASS_...'. */
2189 build_metadata_decl (const char *name, tree type)
2193 /* struct TYPE NAME_<name>; */
2194 decl = start_var_decl (type, synth_id_with_class_suffix
2196 objc_implementation_context));
2201 /* Push forward-declarations of all the categories so that
2202 init_def_list can use them in a CONSTRUCTOR. */
2205 forward_declare_categories (void)
2207 struct imp_entry *impent;
2208 tree sav = objc_implementation_context;
2210 for (impent = imp_list; impent; impent = impent->next)
2212 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2214 /* Set an invisible arg to synth_id_with_class_suffix. */
2215 objc_implementation_context = impent->imp_context;
2216 /* extern struct objc_category _OBJC_CATEGORY_<name>; */
2217 impent->class_decl = build_metadata_decl ("_OBJC_CATEGORY",
2218 objc_category_template);
2221 objc_implementation_context = sav;
2224 /* Create the declaration of _OBJC_SYMBOLS, with type `struct _objc_symtab'
2225 and initialized appropriately. */
2228 generate_objc_symtab_decl (void)
2230 /* forward declare categories */
2232 forward_declare_categories ();
2234 build_objc_symtab_template ();
2235 UOBJC_SYMBOLS_decl = start_var_decl (objc_symtab_template, "_OBJC_SYMBOLS");
2236 finish_var_decl (UOBJC_SYMBOLS_decl,
2237 init_objc_symtab (TREE_TYPE (UOBJC_SYMBOLS_decl)));
2241 init_module_descriptor (tree type)
2243 tree initlist, expr;
2245 /* version = { 1, ... } */
2247 expr = build_int_cst (long_integer_type_node, OBJC_VERSION);
2248 initlist = build_tree_list (NULL_TREE, expr);
2250 /* size = { ..., sizeof (struct _objc_module), ... } */
2252 expr = convert (long_integer_type_node,
2253 size_in_bytes (objc_module_template));
2254 initlist = tree_cons (NULL_TREE, expr, initlist);
2256 /* Don't provide any file name for security reasons. */
2257 /* name = { ..., "", ... } */
2259 expr = add_objc_string (get_identifier (""), class_names);
2260 initlist = tree_cons (NULL_TREE, expr, initlist);
2262 /* symtab = { ..., _OBJC_SYMBOLS, ... } */
2264 if (UOBJC_SYMBOLS_decl)
2265 expr = build_unary_op (ADDR_EXPR, UOBJC_SYMBOLS_decl, 0);
2267 expr = build_int_cst (NULL_TREE, 0);
2268 initlist = tree_cons (NULL_TREE, expr, initlist);
2270 return objc_build_constructor (type, nreverse (initlist));
2273 /* Write out the data structures to describe Objective C classes defined.
2275 struct _objc_module { ... } _OBJC_MODULE = { ... }; */
2278 build_module_descriptor (void)
2280 tree field_decl, field_decl_chain;
2283 push_lang_context (lang_name_c); /* extern "C" */
2286 objc_module_template
2287 = start_struct (RECORD_TYPE, get_identifier (UTAG_MODULE));
2290 field_decl = create_field_decl (long_integer_type_node, "version");
2291 field_decl_chain = field_decl;
2294 field_decl = create_field_decl (long_integer_type_node, "size");
2295 chainon (field_decl_chain, field_decl);
2298 field_decl = create_field_decl (string_type_node, "name");
2299 chainon (field_decl_chain, field_decl);
2301 /* struct _objc_symtab *symtab; */
2303 = create_field_decl (build_pointer_type
2304 (xref_tag (RECORD_TYPE,
2305 get_identifier (UTAG_SYMTAB))),
2307 chainon (field_decl_chain, field_decl);
2309 finish_struct (objc_module_template, field_decl_chain, NULL_TREE);
2311 /* Create an instance of "_objc_module". */
2312 UOBJC_MODULES_decl = start_var_decl (objc_module_template, "_OBJC_MODULES");
2313 finish_var_decl (UOBJC_MODULES_decl,
2314 init_module_descriptor (TREE_TYPE (UOBJC_MODULES_decl)));
2317 pop_lang_context ();
2321 /* The GNU runtime requires us to provide a static initializer function
2324 static void __objc_gnu_init (void) {
2325 __objc_exec_class (&L_OBJC_MODULES);
2329 build_module_initializer_routine (void)
2334 push_lang_context (lang_name_c); /* extern "C" */
2337 objc_push_parm (build_decl (PARM_DECL, NULL_TREE, void_type_node));
2338 objc_start_function (get_identifier (TAG_GNUINIT),
2339 build_function_type (void_type_node,
2341 NULL_TREE, objc_get_parm_info (0));
2343 body = c_begin_compound_stmt (true);
2344 add_stmt (build_function_call
2348 build_unary_op (ADDR_EXPR,
2349 UOBJC_MODULES_decl, 0))));
2350 add_stmt (c_end_compound_stmt (body, true));
2352 TREE_PUBLIC (current_function_decl) = 0;
2355 /* For Objective-C++, we will need to call __objc_gnu_init
2356 from objc_generate_static_init_call() below. */
2357 DECL_STATIC_CONSTRUCTOR (current_function_decl) = 1;
2360 GNU_INIT_decl = current_function_decl;
2364 pop_lang_context ();
2369 /* Return 1 if the __objc_gnu_init function has been synthesized and needs
2370 to be called by the module initializer routine. */
2373 objc_static_init_needed_p (void)
2375 return (GNU_INIT_decl != NULL_TREE);
2378 /* Generate a call to the __objc_gnu_init initializer function. */
2381 objc_generate_static_init_call (tree ctors ATTRIBUTE_UNUSED)
2383 add_stmt (build_stmt (EXPR_STMT,
2384 build_function_call (GNU_INIT_decl, NULL_TREE)));
2388 #endif /* OBJCPLUS */
2390 /* Return the DECL of the string IDENT in the SECTION. */
2393 get_objc_string_decl (tree ident, enum string_section section)
2397 if (section == class_names)
2398 chain = class_names_chain;
2399 else if (section == meth_var_names)
2400 chain = meth_var_names_chain;
2401 else if (section == meth_var_types)
2402 chain = meth_var_types_chain;
2406 for (; chain != 0; chain = TREE_CHAIN (chain))
2407 if (TREE_VALUE (chain) == ident)
2408 return (TREE_PURPOSE (chain));
2414 /* Output references to all statically allocated objects. Return the DECL
2415 for the array built. */
2418 generate_static_references (void)
2420 tree decls = NULL_TREE, expr = NULL_TREE;
2421 tree class_name, class, decl, initlist;
2422 tree cl_chain, in_chain, type
2423 = build_array_type (build_pointer_type (void_type_node), NULL_TREE);
2424 int num_inst, num_class;
2427 if (flag_next_runtime)
2430 for (cl_chain = objc_static_instances, num_class = 0;
2431 cl_chain; cl_chain = TREE_CHAIN (cl_chain), num_class++)
2433 for (num_inst = 0, in_chain = TREE_PURPOSE (cl_chain);
2434 in_chain; num_inst++, in_chain = TREE_CHAIN (in_chain));
2436 sprintf (buf, "_OBJC_STATIC_INSTANCES_%d", num_class);
2437 decl = start_var_decl (type, buf);
2439 /* Output {class_name, ...}. */
2440 class = TREE_VALUE (cl_chain);
2441 class_name = get_objc_string_decl (OBJC_TYPE_NAME (class), class_names);
2442 initlist = build_tree_list (NULL_TREE,
2443 build_unary_op (ADDR_EXPR, class_name, 1));
2445 /* Output {..., instance, ...}. */
2446 for (in_chain = TREE_PURPOSE (cl_chain);
2447 in_chain; in_chain = TREE_CHAIN (in_chain))
2449 expr = build_unary_op (ADDR_EXPR, TREE_VALUE (in_chain), 1);
2450 initlist = tree_cons (NULL_TREE, expr, initlist);
2453 /* Output {..., NULL}. */
2454 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
2456 expr = objc_build_constructor (TREE_TYPE (decl), nreverse (initlist));
2457 finish_var_decl (decl, expr);
2459 = tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, decl, 1), decls);
2462 decls = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), decls);
2463 expr = objc_build_constructor (type, nreverse (decls));
2464 static_instances_decl = start_var_decl (type, "_OBJC_STATIC_INSTANCES");
2465 finish_var_decl (static_instances_decl, expr);
2468 static GTY(()) int selector_reference_idx;
2471 build_selector_reference_decl (void)
2476 sprintf (buf, "_OBJC_SELECTOR_REFERENCES_%d", selector_reference_idx++);
2477 decl = start_var_decl (objc_selector_type, buf);
2483 build_selector_table_decl (void)
2487 if (flag_typed_selectors)
2489 build_selector_template ();
2490 temp = build_array_type (objc_selector_template, NULL_TREE);
2493 temp = build_array_type (objc_selector_type, NULL_TREE);
2495 UOBJC_SELECTOR_TABLE_decl = start_var_decl (temp, "_OBJC_SELECTOR_TABLE");
2498 /* Just a handy wrapper for add_objc_string. */
2501 build_selector (tree ident)
2503 return convert (objc_selector_type,
2504 add_objc_string (ident, meth_var_names));
2508 build_selector_translation_table (void)
2510 tree chain, initlist = NULL_TREE;
2512 tree decl = NULL_TREE;
2514 for (chain = sel_ref_chain; chain; chain = TREE_CHAIN (chain))
2518 if (warn_selector && objc_implementation_context)
2522 for (method_chain = meth_var_names_chain;
2524 method_chain = TREE_CHAIN (method_chain))
2526 if (TREE_VALUE (method_chain) == TREE_VALUE (chain))
2535 if (flag_next_runtime && TREE_PURPOSE (chain))
2536 loc = &DECL_SOURCE_LOCATION (TREE_PURPOSE (chain));
2538 loc = &input_location;
2539 warning (0, "%Hcreating selector for nonexistent method %qE",
2540 loc, TREE_VALUE (chain));
2544 expr = build_selector (TREE_VALUE (chain));
2545 /* add one for the '\0' character */
2546 offset += IDENTIFIER_LENGTH (TREE_VALUE (chain)) + 1;
2548 if (flag_next_runtime)
2550 decl = TREE_PURPOSE (chain);
2551 finish_var_decl (decl, expr);
2555 if (flag_typed_selectors)
2557 tree eltlist = NULL_TREE;
2558 tree encoding = get_proto_encoding (TREE_PURPOSE (chain));
2559 eltlist = tree_cons (NULL_TREE, expr, NULL_TREE);
2560 eltlist = tree_cons (NULL_TREE, encoding, eltlist);
2561 expr = objc_build_constructor (objc_selector_template,
2562 nreverse (eltlist));
2565 initlist = tree_cons (NULL_TREE, expr, initlist);
2569 if (! flag_next_runtime)
2571 /* Cause the selector table (previously forward-declared)
2572 to be actually output. */
2573 initlist = tree_cons (NULL_TREE,
2574 flag_typed_selectors
2575 ? objc_build_constructor
2576 (objc_selector_template,
2577 tree_cons (NULL_TREE,
2578 build_int_cst (NULL_TREE, 0),
2579 tree_cons (NULL_TREE,
2580 build_int_cst (NULL_TREE, 0),
2582 : build_int_cst (NULL_TREE, 0), initlist);
2583 initlist = objc_build_constructor (TREE_TYPE (UOBJC_SELECTOR_TABLE_decl),
2584 nreverse (initlist));
2585 finish_var_decl (UOBJC_SELECTOR_TABLE_decl, initlist);
2590 get_proto_encoding (tree proto)
2595 if (! METHOD_ENCODING (proto))
2597 encoding = encode_method_prototype (proto);
2598 METHOD_ENCODING (proto) = encoding;
2601 encoding = METHOD_ENCODING (proto);
2603 return add_objc_string (encoding, meth_var_types);
2606 return build_int_cst (NULL_TREE, 0);
2609 /* sel_ref_chain is a list whose "value" fields will be instances of
2610 identifier_node that represent the selector. */
2613 build_typed_selector_reference (tree ident, tree prototype)
2615 tree *chain = &sel_ref_chain;
2621 if (TREE_PURPOSE (*chain) == prototype && TREE_VALUE (*chain) == ident)
2622 goto return_at_index;
2625 chain = &TREE_CHAIN (*chain);
2628 *chain = tree_cons (prototype, ident, NULL_TREE);
2631 expr = build_unary_op (ADDR_EXPR,
2632 build_array_ref (UOBJC_SELECTOR_TABLE_decl,
2633 build_int_cst (NULL_TREE, index)),
2635 return convert (objc_selector_type, expr);
2639 build_selector_reference (tree ident)
2641 tree *chain = &sel_ref_chain;
2647 if (TREE_VALUE (*chain) == ident)
2648 return (flag_next_runtime
2649 ? TREE_PURPOSE (*chain)
2650 : build_array_ref (UOBJC_SELECTOR_TABLE_decl,
2651 build_int_cst (NULL_TREE, index)));
2654 chain = &TREE_CHAIN (*chain);
2657 expr = (flag_next_runtime ? build_selector_reference_decl (): NULL_TREE);
2659 *chain = tree_cons (expr, ident, NULL_TREE);
2661 return (flag_next_runtime
2663 : build_array_ref (UOBJC_SELECTOR_TABLE_decl,
2664 build_int_cst (NULL_TREE, index)));
2667 static GTY(()) int class_reference_idx;
2670 build_class_reference_decl (void)
2675 sprintf (buf, "_OBJC_CLASS_REFERENCES_%d", class_reference_idx++);
2676 decl = start_var_decl (objc_class_type, buf);
2681 /* Create a class reference, but don't create a variable to reference
2685 add_class_reference (tree ident)
2689 if ((chain = cls_ref_chain))
2694 if (ident == TREE_VALUE (chain))
2698 chain = TREE_CHAIN (chain);
2702 /* Append to the end of the list */
2703 TREE_CHAIN (tail) = tree_cons (NULL_TREE, ident, NULL_TREE);
2706 cls_ref_chain = tree_cons (NULL_TREE, ident, NULL_TREE);
2709 /* Get a class reference, creating it if necessary. Also create the
2710 reference variable. */
2713 objc_get_class_reference (tree ident)
2715 tree orig_ident = (DECL_P (ident)
2718 ? OBJC_TYPE_NAME (ident)
2720 bool local_scope = false;
2723 if (processing_template_decl)
2724 /* Must wait until template instantiation time. */
2725 return build_min_nt (CLASS_REFERENCE_EXPR, ident);
2728 if (TREE_CODE (ident) == TYPE_DECL)
2729 ident = (DECL_ORIGINAL_TYPE (ident)
2730 ? DECL_ORIGINAL_TYPE (ident)
2731 : TREE_TYPE (ident));
2734 if (TYPE_P (ident) && TYPE_CONTEXT (ident)
2735 && TYPE_CONTEXT (ident) != global_namespace)
2739 if (local_scope || !(ident = objc_is_class_name (ident)))
2741 error ("%qs is not an Objective-C class name or alias",
2742 IDENTIFIER_POINTER (orig_ident));
2743 return error_mark_node;
2746 if (flag_next_runtime && !flag_zero_link)
2751 for (chain = &cls_ref_chain; *chain; chain = &TREE_CHAIN (*chain))
2752 if (TREE_VALUE (*chain) == ident)
2754 if (! TREE_PURPOSE (*chain))
2755 TREE_PURPOSE (*chain) = build_class_reference_decl ();
2757 return TREE_PURPOSE (*chain);
2760 decl = build_class_reference_decl ();
2761 *chain = tree_cons (decl, ident, NULL_TREE);
2768 add_class_reference (ident);
2770 params = build_tree_list (NULL_TREE,
2771 my_build_string_pointer
2772 (IDENTIFIER_LENGTH (ident) + 1,
2773 IDENTIFIER_POINTER (ident)));
2775 assemble_external (objc_get_class_decl);
2776 return build_function_call (objc_get_class_decl, params);
2780 /* For each string section we have a chain which maps identifier nodes
2781 to decls for the strings. */
2784 add_objc_string (tree ident, enum string_section section)
2786 tree *chain, decl, type, string_expr;
2788 if (section == class_names)
2789 chain = &class_names_chain;
2790 else if (section == meth_var_names)
2791 chain = &meth_var_names_chain;
2792 else if (section == meth_var_types)
2793 chain = &meth_var_types_chain;
2799 if (TREE_VALUE (*chain) == ident)
2800 return convert (string_type_node,
2801 build_unary_op (ADDR_EXPR, TREE_PURPOSE (*chain), 1));
2803 chain = &TREE_CHAIN (*chain);
2806 decl = build_objc_string_decl (section);
2808 type = build_array_type
2811 (build_int_cst (NULL_TREE,
2812 IDENTIFIER_LENGTH (ident))));
2813 decl = start_var_decl (type, IDENTIFIER_POINTER (DECL_NAME (decl)));
2814 string_expr = my_build_string (IDENTIFIER_LENGTH (ident) + 1,
2815 IDENTIFIER_POINTER (ident));
2816 finish_var_decl (decl, string_expr);
2818 *chain = tree_cons (decl, ident, NULL_TREE);
2820 return convert (string_type_node, build_unary_op (ADDR_EXPR, decl, 1));
2823 static GTY(()) int class_names_idx;
2824 static GTY(()) int meth_var_names_idx;
2825 static GTY(()) int meth_var_types_idx;
2828 build_objc_string_decl (enum string_section section)
2833 if (section == class_names)
2834 sprintf (buf, "_OBJC_CLASS_NAME_%d", class_names_idx++);
2835 else if (section == meth_var_names)
2836 sprintf (buf, "_OBJC_METH_VAR_NAME_%d", meth_var_names_idx++);
2837 else if (section == meth_var_types)
2838 sprintf (buf, "_OBJC_METH_VAR_TYPE_%d", meth_var_types_idx++);
2840 ident = get_identifier (buf);
2842 decl = build_decl (VAR_DECL, ident, build_array_type (char_type_node, 0));
2843 DECL_EXTERNAL (decl) = 1;
2844 TREE_PUBLIC (decl) = 0;
2845 TREE_USED (decl) = 1;
2846 TREE_CONSTANT (decl) = 1;
2847 DECL_CONTEXT (decl) = 0;
2848 DECL_ARTIFICIAL (decl) = 1;
2850 DECL_THIS_STATIC (decl) = 1; /* squash redeclaration errors */
2853 make_decl_rtl (decl);
2854 pushdecl_top_level (decl);
2861 objc_declare_alias (tree alias_ident, tree class_ident)
2863 tree underlying_class;
2866 if (current_namespace != global_namespace) {
2867 error ("Objective-C declarations may only appear in global scope");
2869 #endif /* OBJCPLUS */
2871 if (!(underlying_class = objc_is_class_name (class_ident)))
2872 warning (0, "cannot find class %qs", IDENTIFIER_POINTER (class_ident));
2873 else if (objc_is_class_name (alias_ident))
2874 warning (0, "class %qs already exists", IDENTIFIER_POINTER (alias_ident));
2877 /* Implement @compatibility_alias as a typedef. */
2879 push_lang_context (lang_name_c); /* extern "C" */
2881 lang_hooks.decls.pushdecl (build_decl
2884 xref_tag (RECORD_TYPE, underlying_class)));
2886 pop_lang_context ();
2888 alias_chain = tree_cons (underlying_class, alias_ident, alias_chain);
2893 objc_declare_class (tree ident_list)
2897 if (current_namespace != global_namespace) {
2898 error ("Objective-C declarations may only appear in global scope");
2900 #endif /* OBJCPLUS */
2902 for (list = ident_list; list; list = TREE_CHAIN (list))
2904 tree ident = TREE_VALUE (list);
2906 if (! objc_is_class_name (ident))
2908 tree record = lookup_name (ident), type = record;
2912 if (TREE_CODE (record) == TYPE_DECL)
2913 type = DECL_ORIGINAL_TYPE (record);
2915 if (!TYPE_HAS_OBJC_INFO (type)
2916 || !TYPE_OBJC_INTERFACE (type))
2918 error ("%qs redeclared as different kind of symbol",
2919 IDENTIFIER_POINTER (ident));
2920 error ("previous declaration of %q+D",
2925 record = xref_tag (RECORD_TYPE, ident);
2926 INIT_TYPE_OBJC_INFO (record);
2927 TYPE_OBJC_INTERFACE (record) = ident;
2928 class_chain = tree_cons (NULL_TREE, ident, class_chain);
2934 objc_is_class_name (tree ident)
2938 if (ident && TREE_CODE (ident) == IDENTIFIER_NODE
2939 && identifier_global_value (ident))
2940 ident = identifier_global_value (ident);
2941 while (ident && TREE_CODE (ident) == TYPE_DECL && DECL_ORIGINAL_TYPE (ident))
2942 ident = OBJC_TYPE_NAME (DECL_ORIGINAL_TYPE (ident));
2944 if (ident && TREE_CODE (ident) == RECORD_TYPE)
2945 ident = OBJC_TYPE_NAME (ident);
2947 if (ident && TREE_CODE (ident) == TYPE_DECL)
2948 ident = DECL_NAME (ident);
2950 if (!ident || TREE_CODE (ident) != IDENTIFIER_NODE)
2953 if (lookup_interface (ident))
2956 for (chain = class_chain; chain; chain = TREE_CHAIN (chain))
2958 if (ident == TREE_VALUE (chain))
2962 for (chain = alias_chain; chain; chain = TREE_CHAIN (chain))
2964 if (ident == TREE_VALUE (chain))
2965 return TREE_PURPOSE (chain);
2971 /* Check whether TYPE is either 'id' or 'Class'. */
2974 objc_is_id (tree type)
2976 if (type && TREE_CODE (type) == IDENTIFIER_NODE
2977 && identifier_global_value (type))
2978 type = identifier_global_value (type);
2980 if (type && TREE_CODE (type) == TYPE_DECL)
2981 type = TREE_TYPE (type);
2983 /* NB: This function may be called before the ObjC front-end has
2984 been initialized, in which case OBJC_OBJECT_TYPE will (still) be NULL. */
2985 return (objc_object_type && type
2986 && (IS_ID (type) || IS_CLASS (type) || IS_SUPER (type))
2991 /* Check whether TYPE is either 'id', 'Class', or a pointer to an ObjC
2992 class instance. This is needed by other parts of the compiler to
2993 handle ObjC types gracefully. */
2996 objc_is_object_ptr (tree type)
3000 type = TYPE_MAIN_VARIANT (type);
3001 if (!POINTER_TYPE_P (type))
3004 ret = objc_is_id (type);
3006 ret = objc_is_class_name (TREE_TYPE (type));
3012 objc_is_gcable_type (tree type, int or_strong_p)
3018 if (objc_is_id (TYPE_MAIN_VARIANT (type)))
3020 if (or_strong_p && lookup_attribute ("objc_gc", TYPE_ATTRIBUTES (type)))
3022 if (TREE_CODE (type) != POINTER_TYPE && TREE_CODE (type) != INDIRECT_REF)
3024 type = TREE_TYPE (type);
3025 if (TREE_CODE (type) != RECORD_TYPE)
3027 name = TYPE_NAME (type);
3028 return (objc_is_class_name (name) != NULL_TREE);
3032 objc_substitute_decl (tree expr, tree oldexpr, tree newexpr)
3034 if (expr == oldexpr)
3037 switch (TREE_CODE (expr))
3040 return objc_build_component_ref
3041 (objc_substitute_decl (TREE_OPERAND (expr, 0),
3044 DECL_NAME (TREE_OPERAND (expr, 1)));
3046 return build_array_ref (objc_substitute_decl (TREE_OPERAND (expr, 0),
3049 TREE_OPERAND (expr, 1));
3051 return build_indirect_ref (objc_substitute_decl (TREE_OPERAND (expr, 0),
3060 objc_build_ivar_assignment (tree outervar, tree lhs, tree rhs)
3063 /* The LHS parameter contains the expression 'outervar->memberspec';
3064 we need to transform it into '&((typeof(outervar) *) 0)->memberspec',
3065 where memberspec may be arbitrarily complex (e.g., 'g->f.d[2].g[3]').
3068 = objc_substitute_decl
3069 (lhs, outervar, convert (TREE_TYPE (outervar), integer_zero_node));
3071 = (flag_objc_direct_dispatch
3072 ? objc_assign_ivar_fast_decl
3073 : objc_assign_ivar_decl);
3075 offs = convert (integer_type_node, build_unary_op (ADDR_EXPR, offs, 0));
3077 func_params = tree_cons (NULL_TREE,
3078 convert (objc_object_type, rhs),
3079 tree_cons (NULL_TREE, convert (objc_object_type, outervar),
3080 tree_cons (NULL_TREE, offs,
3083 assemble_external (func);
3084 return build_function_call (func, func_params);
3088 objc_build_global_assignment (tree lhs, tree rhs)
3090 tree func_params = tree_cons (NULL_TREE,
3091 convert (objc_object_type, rhs),
3092 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3093 build_unary_op (ADDR_EXPR, lhs, 0)),
3096 assemble_external (objc_assign_global_decl);
3097 return build_function_call (objc_assign_global_decl, func_params);
3101 objc_build_strong_cast_assignment (tree lhs, tree rhs)
3103 tree func_params = tree_cons (NULL_TREE,
3104 convert (objc_object_type, rhs),
3105 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3106 build_unary_op (ADDR_EXPR, lhs, 0)),
3109 assemble_external (objc_assign_strong_cast_decl);
3110 return build_function_call (objc_assign_strong_cast_decl, func_params);
3114 objc_is_gcable_p (tree expr)
3116 return (TREE_CODE (expr) == COMPONENT_REF
3117 ? objc_is_gcable_p (TREE_OPERAND (expr, 1))
3118 : TREE_CODE (expr) == ARRAY_REF
3119 ? (objc_is_gcable_p (TREE_TYPE (expr))
3120 || objc_is_gcable_p (TREE_OPERAND (expr, 0)))
3121 : TREE_CODE (expr) == ARRAY_TYPE
3122 ? objc_is_gcable_p (TREE_TYPE (expr))
3124 ? objc_is_gcable_type (expr, 1)
3125 : (objc_is_gcable_p (TREE_TYPE (expr))
3127 && lookup_attribute ("objc_gc", DECL_ATTRIBUTES (expr)))));
3131 objc_is_ivar_reference_p (tree expr)
3133 return (TREE_CODE (expr) == ARRAY_REF
3134 ? objc_is_ivar_reference_p (TREE_OPERAND (expr, 0))
3135 : TREE_CODE (expr) == COMPONENT_REF
3136 ? TREE_CODE (TREE_OPERAND (expr, 1)) == FIELD_DECL
3141 objc_is_global_reference_p (tree expr)
3143 return (TREE_CODE (expr) == INDIRECT_REF || TREE_CODE (expr) == PLUS_EXPR
3144 ? objc_is_global_reference_p (TREE_OPERAND (expr, 0))
3146 ? (!DECL_CONTEXT (expr) || TREE_STATIC (expr))
3151 objc_generate_write_barrier (tree lhs, enum tree_code modifycode, tree rhs)
3153 tree result = NULL_TREE, outer;
3154 int strong_cast_p = 0, outer_gc_p = 0, indirect_p = 0;
3156 /* See if we have any lhs casts, and strip them out. NB: The lvalue casts
3157 will have been transformed to the form '*(type *)&expr'. */
3158 if (TREE_CODE (lhs) == INDIRECT_REF)
3160 outer = TREE_OPERAND (lhs, 0);
3162 while (!strong_cast_p
3163 && (TREE_CODE (outer) == CONVERT_EXPR
3164 || TREE_CODE (outer) == NOP_EXPR
3165 || TREE_CODE (outer) == NON_LVALUE_EXPR))
3167 tree lhstype = TREE_TYPE (outer);
3169 /* Descend down the cast chain, and record the first objc_gc
3171 if (POINTER_TYPE_P (lhstype))
3174 = lookup_attribute ("objc_gc",
3175 TYPE_ATTRIBUTES (TREE_TYPE (lhstype)));
3181 outer = TREE_OPERAND (outer, 0);
3185 /* If we have a __strong cast, it trumps all else. */
3188 if (modifycode != NOP_EXPR)
3189 goto invalid_pointer_arithmetic;
3191 if (warn_assign_intercept)
3192 warning (0, "strong-cast assignment has been intercepted");
3194 result = objc_build_strong_cast_assignment (lhs, rhs);
3199 /* the lhs must be of a suitable type, regardless of its underlying
3201 if (!objc_is_gcable_p (lhs))
3207 && (TREE_CODE (outer) == COMPONENT_REF
3208 || TREE_CODE (outer) == ARRAY_REF))
3209 outer = TREE_OPERAND (outer, 0);
3211 if (TREE_CODE (outer) == INDIRECT_REF)
3213 outer = TREE_OPERAND (outer, 0);
3217 outer_gc_p = objc_is_gcable_p (outer);
3219 /* Handle ivar assignments. */
3220 if (objc_is_ivar_reference_p (lhs))
3222 /* if the struct to the left of the ivar is not an Objective-C object (__strong
3223 doesn't cut it here), the best we can do here is suggest a cast. */
3224 if (!objc_is_gcable_type (TREE_TYPE (outer), 0))
3226 /* We may still be able to use the global write barrier... */
3227 if (!indirect_p && objc_is_global_reference_p (outer))
3228 goto global_reference;
3231 if (modifycode == NOP_EXPR)
3233 if (warn_assign_intercept)
3234 warning (0, "strong-cast may possibly be needed");
3240 if (modifycode != NOP_EXPR)
3241 goto invalid_pointer_arithmetic;
3243 if (warn_assign_intercept)
3244 warning (0, "instance variable assignment has been intercepted");
3246 result = objc_build_ivar_assignment (outer, lhs, rhs);
3251 /* Likewise, intercept assignment to global/static variables if their type is
3253 if (objc_is_global_reference_p (outer))
3259 if (modifycode != NOP_EXPR)
3261 invalid_pointer_arithmetic:
3263 warning (0, "pointer arithmetic for garbage-collected objects not allowed");
3268 if (warn_assign_intercept)
3269 warning (0, "global/static variable assignment has been intercepted");
3271 result = objc_build_global_assignment (lhs, rhs);
3274 /* In all other cases, fall back to the normal mechanism. */
3279 struct interface_tuple GTY(())
3285 static GTY ((param_is (struct interface_tuple))) htab_t interface_htab;
3288 hash_interface (const void *p)
3290 const struct interface_tuple *d = p;
3291 return htab_hash_pointer (d->id);
3295 eq_interface (const void *p1, const void *p2)
3297 const struct interface_tuple *d = p1;
3302 lookup_interface (tree ident)
3305 if (ident && TREE_CODE (ident) == TYPE_DECL)
3306 ident = DECL_NAME (ident);
3309 if (ident == NULL_TREE || TREE_CODE (ident) != IDENTIFIER_NODE)
3313 struct interface_tuple **slot;
3318 slot = (struct interface_tuple **)
3319 htab_find_slot_with_hash (interface_htab, ident,
3320 htab_hash_pointer (ident),
3323 i = (*slot)->class_name;
3329 /* Implement @defs (<classname>) within struct bodies. */
3332 objc_get_class_ivars (tree class_name)
3334 tree interface = lookup_interface (class_name);
3337 return get_class_ivars (interface, true);
3339 error ("cannot find interface declaration for %qs",
3340 IDENTIFIER_POINTER (class_name));
3342 return error_mark_node;
3345 /* Used by: build_private_template, continue_class,
3346 and for @defs constructs. */
3349 get_class_ivars (tree interface, bool inherited)
3351 tree ivar_chain = copy_list (CLASS_RAW_IVARS (interface));
3353 /* Both CLASS_RAW_IVARS and CLASS_IVARS contain a list of ivars declared
3354 by the current class (i.e., they do not include super-class ivars).
3355 However, the CLASS_IVARS list will be side-effected by a call to
3356 finish_struct(), which will fill in field offsets. */
3357 if (!CLASS_IVARS (interface))
3358 CLASS_IVARS (interface) = ivar_chain;
3363 while (CLASS_SUPER_NAME (interface))
3365 /* Prepend super-class ivars. */
3366 interface = lookup_interface (CLASS_SUPER_NAME (interface));
3367 ivar_chain = chainon (copy_list (CLASS_RAW_IVARS (interface)),
3375 objc_create_temporary_var (tree type)
3379 decl = build_decl (VAR_DECL, NULL_TREE, type);
3380 TREE_USED (decl) = 1;
3381 DECL_ARTIFICIAL (decl) = 1;
3382 DECL_IGNORED_P (decl) = 1;
3383 DECL_CONTEXT (decl) = current_function_decl;
3388 /* Exception handling constructs. We begin by having the parser do most
3389 of the work and passing us blocks. What we do next depends on whether
3390 we're doing "native" exception handling or legacy Darwin setjmp exceptions.
3391 We abstract all of this in a handful of appropriately named routines. */
3393 /* Stack of open try blocks. */
3395 struct objc_try_context
3397 struct objc_try_context *outer;
3399 /* Statements (or statement lists) as processed by the parser. */
3403 /* Some file position locations. */
3404 location_t try_locus;
3405 location_t end_try_locus;
3406 location_t end_catch_locus;
3407 location_t finally_locus;
3408 location_t end_finally_locus;
3410 /* A STATEMENT_LIST of CATCH_EXPRs, appropriate for sticking into op1
3411 of a TRY_CATCH_EXPR. Even when doing Darwin setjmp. */
3414 /* The CATCH_EXPR of an open @catch clause. */
3417 /* The VAR_DECL holding the Darwin equivalent of EXC_PTR_EXPR. */
3423 static struct objc_try_context *cur_try_context;
3425 /* This hook, called via lang_eh_runtime_type, generates a runtime object
3426 that represents TYPE. For Objective-C, this is just the class name. */
3427 /* ??? Isn't there a class object or some such? Is it easy to get? */
3431 objc_eh_runtime_type (tree type)
3433 return add_objc_string (OBJC_TYPE_NAME (TREE_TYPE (type)), class_names);
3437 /* Initialize exception handling. */
3440 objc_init_exceptions (void)
3442 static bool done = false;
3447 if (flag_objc_sjlj_exceptions)
3449 /* On Darwin, ObjC exceptions require a sufficiently recent
3450 version of the runtime, so the user must ask for them explicitly. */
3451 if (!flag_objc_exceptions)
3452 warning (0, "use %<-fobjc-exceptions%> to enable Objective-C "
3453 "exception syntax");
3458 c_eh_initialized_p = true;
3459 eh_personality_libfunc
3460 = init_one_libfunc (USING_SJLJ_EXCEPTIONS
3461 ? "__gnu_objc_personality_sj0"
3462 : "__gnu_objc_personality_v0");
3463 default_init_unwind_resume_libfunc ();
3464 using_eh_for_cleanups ();
3465 lang_eh_runtime_type = objc_eh_runtime_type;
3470 /* Build an EXC_PTR_EXPR, or the moral equivalent. In the case of Darwin,
3471 we'll arrange for it to be initialized (and associated with a binding)
3475 objc_build_exc_ptr (void)
3477 if (flag_objc_sjlj_exceptions)
3479 tree var = cur_try_context->caught_decl;
3482 var = objc_create_temporary_var (objc_object_type);
3483 cur_try_context->caught_decl = var;
3488 return build0 (EXC_PTR_EXPR, objc_object_type);
3491 /* Build "objc_exception_try_exit(&_stack)". */
3494 next_sjlj_build_try_exit (void)
3497 t = build_fold_addr_expr (cur_try_context->stack_decl);
3498 t = tree_cons (NULL, t, NULL);
3499 t = build_function_call (objc_exception_try_exit_decl, t);
3504 objc_exception_try_enter (&_stack);
3505 if (_setjmp(&_stack.buf))
3509 Return the COND_EXPR. Note that the THEN and ELSE fields are left
3510 empty, ready for the caller to fill them in. */
3513 next_sjlj_build_enter_and_setjmp (void)
3515 tree t, enter, sj, cond;
3517 t = build_fold_addr_expr (cur_try_context->stack_decl);
3518 t = tree_cons (NULL, t, NULL);
3519 enter = build_function_call (objc_exception_try_enter_decl, t);
3521 t = objc_build_component_ref (cur_try_context->stack_decl,
3522 get_identifier ("buf"));
3523 t = build_fold_addr_expr (t);
3525 /* Convert _setjmp argument to type that is expected. */
3526 if (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl)))
3527 t = convert (TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl))), t);
3529 t = convert (ptr_type_node, t);
3531 t = convert (ptr_type_node, t);
3533 t = tree_cons (NULL, t, NULL);
3534 sj = build_function_call (objc_setjmp_decl, t);
3536 cond = build2 (COMPOUND_EXPR, TREE_TYPE (sj), enter, sj);
3537 cond = c_common_truthvalue_conversion (cond);
3539 return build3 (COND_EXPR, void_type_node, cond, NULL, NULL);
3544 DECL = objc_exception_extract(&_stack); */
3547 next_sjlj_build_exc_extract (tree decl)
3551 t = build_fold_addr_expr (cur_try_context->stack_decl);
3552 t = tree_cons (NULL, t, NULL);
3553 t = build_function_call (objc_exception_extract_decl, t);
3554 t = convert (TREE_TYPE (decl), t);
3555 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
3561 if (objc_exception_match(obj_get_class(TYPE), _caught)
3568 objc_exception_try_exit(&_stack);
3570 from the sequence of CATCH_EXPRs in the current try context. */
3573 next_sjlj_build_catch_list (void)
3575 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
3577 tree *last = &catch_seq;
3578 bool saw_id = false;
3580 for (; !tsi_end_p (i); tsi_next (&i))
3582 tree stmt = tsi_stmt (i);
3583 tree type = CATCH_TYPES (stmt);
3584 tree body = CATCH_BODY (stmt);
3596 if (type == error_mark_node)
3597 cond = error_mark_node;
3600 args = tree_cons (NULL, cur_try_context->caught_decl, NULL);
3601 t = objc_get_class_reference (OBJC_TYPE_NAME (TREE_TYPE (type)));
3602 args = tree_cons (NULL, t, args);
3603 t = build_function_call (objc_exception_match_decl, args);
3604 cond = c_common_truthvalue_conversion (t);
3606 t = build3 (COND_EXPR, void_type_node, cond, body, NULL);
3607 SET_EXPR_LOCUS (t, EXPR_LOCUS (stmt));
3610 last = &COND_EXPR_ELSE (t);
3616 t = build2 (MODIFY_EXPR, void_type_node, cur_try_context->rethrow_decl,
3617 cur_try_context->caught_decl);
3618 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3619 append_to_statement_list (t, last);
3621 t = next_sjlj_build_try_exit ();
3622 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3623 append_to_statement_list (t, last);
3629 /* Build a complete @try-@catch-@finally block for legacy Darwin setjmp
3630 exception handling. We aim to build:
3633 struct _objc_exception_data _stack;
3634 id volatile _rethrow = 0;
3637 objc_exception_try_enter (&_stack);
3638 if (_setjmp(&_stack.buf))
3640 id _caught = objc_exception_extract(&_stack);
3641 objc_exception_try_enter (&_stack);
3642 if (_setjmp(&_stack.buf))
3643 _rethrow = objc_exception_extract(&_stack);
3653 objc_exception_try_exit(&_stack);
3656 objc_exception_throw(_rethrow);
3660 If CATCH-LIST is empty, we can omit all of the block containing
3661 "_caught" except for the setting of _rethrow. Note the use of
3662 a real TRY_FINALLY_EXPR here, which is not involved in EH per-se,
3663 but handles goto and other exits from the block. */
3666 next_sjlj_build_try_catch_finally (void)
3668 tree rethrow_decl, stack_decl, t;
3669 tree catch_seq, try_fin, bind;
3671 /* Create the declarations involved. */
3672 t = xref_tag (RECORD_TYPE, get_identifier (UTAG_EXCDATA));
3673 stack_decl = objc_create_temporary_var (t);
3674 cur_try_context->stack_decl = stack_decl;
3676 rethrow_decl = objc_create_temporary_var (objc_object_type);
3677 cur_try_context->rethrow_decl = rethrow_decl;
3678 TREE_THIS_VOLATILE (rethrow_decl) = 1;
3679 TREE_CHAIN (rethrow_decl) = stack_decl;
3681 /* Build the outermost variable binding level. */
3682 bind = build3 (BIND_EXPR, void_type_node, rethrow_decl, NULL, NULL);
3683 SET_EXPR_LOCATION (bind, cur_try_context->try_locus);
3684 TREE_SIDE_EFFECTS (bind) = 1;
3686 /* Initialize rethrow_decl. */
3687 t = build2 (MODIFY_EXPR, void_type_node, rethrow_decl,
3688 convert (objc_object_type, null_pointer_node));
3689 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3690 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
3692 /* Build the outermost TRY_FINALLY_EXPR. */
3693 try_fin = build2 (TRY_FINALLY_EXPR, void_type_node, NULL, NULL);
3694 SET_EXPR_LOCATION (try_fin, cur_try_context->try_locus);
3695 TREE_SIDE_EFFECTS (try_fin) = 1;
3696 append_to_statement_list (try_fin, &BIND_EXPR_BODY (bind));
3698 /* Create the complete catch sequence. */
3699 if (cur_try_context->catch_list)
3701 tree caught_decl = objc_build_exc_ptr ();
3702 catch_seq = build_stmt (BIND_EXPR, caught_decl, NULL, NULL);
3703 TREE_SIDE_EFFECTS (catch_seq) = 1;
3705 t = next_sjlj_build_exc_extract (caught_decl);
3706 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3708 t = next_sjlj_build_enter_and_setjmp ();
3709 COND_EXPR_THEN (t) = next_sjlj_build_exc_extract (rethrow_decl);
3710 COND_EXPR_ELSE (t) = next_sjlj_build_catch_list ();
3711 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3714 catch_seq = next_sjlj_build_exc_extract (rethrow_decl);
3715 SET_EXPR_LOCATION (catch_seq, cur_try_context->end_try_locus);
3717 /* Build the main register-and-try if statement. */
3718 t = next_sjlj_build_enter_and_setjmp ();
3719 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3720 COND_EXPR_THEN (t) = catch_seq;
3721 COND_EXPR_ELSE (t) = cur_try_context->try_body;
3722 TREE_OPERAND (try_fin, 0) = t;
3724 /* Build the complete FINALLY statement list. */
3725 t = next_sjlj_build_try_exit ();
3726 t = build_stmt (COND_EXPR,
3727 c_common_truthvalue_conversion (rethrow_decl),
3729 SET_EXPR_LOCATION (t, cur_try_context->finally_locus);
3730 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3732 append_to_statement_list (cur_try_context->finally_body,
3733 &TREE_OPERAND (try_fin, 1));
3735 t = tree_cons (NULL, rethrow_decl, NULL);
3736 t = build_function_call (objc_exception_throw_decl, t);
3737 t = build_stmt (COND_EXPR,
3738 c_common_truthvalue_conversion (rethrow_decl),
3740 SET_EXPR_LOCATION (t, cur_try_context->end_finally_locus);
3741 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3746 /* Called just after parsing the @try and its associated BODY. We now
3747 must prepare for the tricky bits -- handling the catches and finally. */
3750 objc_begin_try_stmt (location_t try_locus, tree body)
3752 struct objc_try_context *c = xcalloc (1, sizeof (*c));
3753 c->outer = cur_try_context;
3755 c->try_locus = try_locus;
3756 c->end_try_locus = input_location;
3757 cur_try_context = c;
3759 objc_init_exceptions ();
3761 if (flag_objc_sjlj_exceptions)
3762 objc_mark_locals_volatile (NULL);
3765 /* Called just after parsing "@catch (parm)". Open a binding level,
3766 enter DECL into the binding level, and initialize it. Leave the
3767 binding level open while the body of the compound statement is parsed. */
3770 objc_begin_catch_clause (tree decl)
3772 tree compound, type, t;
3774 /* Begin a new scope that the entire catch clause will live in. */
3775 compound = c_begin_compound_stmt (true);
3777 /* The parser passed in a PARM_DECL, but what we really want is a VAR_DECL. */
3778 decl = build_decl (VAR_DECL, DECL_NAME (decl), TREE_TYPE (decl));
3779 lang_hooks.decls.pushdecl (decl);
3781 /* Since a decl is required here by syntax, don't warn if its unused. */
3782 /* ??? As opposed to __attribute__((unused))? Anyway, this appears to
3783 be what the previous objc implementation did. */
3784 TREE_USED (decl) = 1;
3786 /* Verify that the type of the catch is valid. It must be a pointer
3787 to an Objective-C class, or "id" (which is catch-all). */
3788 type = TREE_TYPE (decl);
3790 if (POINTER_TYPE_P (type) && objc_is_object_id (TREE_TYPE (type)))
3792 else if (!POINTER_TYPE_P (type) || !TYPED_OBJECT (TREE_TYPE (type)))
3794 error ("@catch parameter is not a known Objective-C class type");
3795 type = error_mark_node;
3797 else if (cur_try_context->catch_list)
3799 /* Examine previous @catch clauses and see if we've already
3800 caught the type in question. */
3801 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
3802 for (; !tsi_end_p (i); tsi_next (&i))
3804 tree stmt = tsi_stmt (i);
3805 t = CATCH_TYPES (stmt);
3806 if (t == error_mark_node)
3808 if (!t || DERIVED_FROM_P (TREE_TYPE (t), TREE_TYPE (type)))
3810 warning (0, "exception of type %<%T%> will be caught",
3812 warning (0, "%H by earlier handler for %<%T%>",
3813 EXPR_LOCUS (stmt), TREE_TYPE (t ? t : objc_object_type));
3819 /* Record the data for the catch in the try context so that we can
3820 finalize it later. */
3821 t = build_stmt (CATCH_EXPR, type, compound);
3822 cur_try_context->current_catch = t;
3824 /* Initialize the decl from the EXC_PTR_EXPR we get from the runtime. */
3825 t = objc_build_exc_ptr ();
3826 t = convert (TREE_TYPE (decl), t);
3827 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
3831 /* Called just after parsing the closing brace of a @catch clause. Close
3832 the open binding level, and record a CATCH_EXPR for it. */
3835 objc_finish_catch_clause (void)
3837 tree c = cur_try_context->current_catch;
3838 cur_try_context->current_catch = NULL;
3839 cur_try_context->end_catch_locus = input_location;
3841 CATCH_BODY (c) = c_end_compound_stmt (CATCH_BODY (c), 1);
3842 append_to_statement_list (c, &cur_try_context->catch_list);
3845 /* Called after parsing a @finally clause and its associated BODY.
3846 Record the body for later placement. */
3849 objc_build_finally_clause (location_t finally_locus, tree body)
3851 cur_try_context->finally_body = body;
3852 cur_try_context->finally_locus = finally_locus;
3853 cur_try_context->end_finally_locus = input_location;
3856 /* Called to finalize a @try construct. */
3859 objc_finish_try_stmt (void)
3861 struct objc_try_context *c = cur_try_context;
3864 if (c->catch_list == NULL && c->finally_body == NULL)
3865 error ("%<@try%> without %<@catch%> or %<@finally%>");
3867 /* If we're doing Darwin setjmp exceptions, build the big nasty. */
3868 if (flag_objc_sjlj_exceptions)
3870 if (!cur_try_context->finally_body)
3872 cur_try_context->finally_locus = input_location;
3873 cur_try_context->end_finally_locus = input_location;
3875 stmt = next_sjlj_build_try_catch_finally ();
3879 /* Otherwise, nest the CATCH inside a FINALLY. */
3883 stmt = build_stmt (TRY_CATCH_EXPR, stmt, c->catch_list);
3884 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
3886 if (c->finally_body)
3888 stmt = build_stmt (TRY_FINALLY_EXPR, stmt, c->finally_body);
3889 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
3894 cur_try_context = c->outer;
3900 objc_build_throw_stmt (tree throw_expr)
3904 objc_init_exceptions ();
3906 if (throw_expr == NULL)
3908 /* If we're not inside a @catch block, there is no "current
3909 exception" to be rethrown. */
3910 if (cur_try_context == NULL
3911 || cur_try_context->current_catch == NULL)
3913 error ("%<@throw%> (rethrow) used outside of a @catch block");
3917 /* Otherwise the object is still sitting in the EXC_PTR_EXPR
3918 value that we get from the runtime. */
3919 throw_expr = objc_build_exc_ptr ();
3922 /* A throw is just a call to the runtime throw function with the
3923 object as a parameter. */
3924 args = tree_cons (NULL, throw_expr, NULL);
3925 return add_stmt (build_function_call (objc_exception_throw_decl, args));
3929 objc_build_synchronized (location_t start_locus, tree mutex, tree body)
3933 /* First lock the mutex. */
3934 mutex = save_expr (mutex);
3935 args = tree_cons (NULL, mutex, NULL);
3936 call = build_function_call (objc_sync_enter_decl, args);
3937 SET_EXPR_LOCATION (call, start_locus);
3940 /* Build the mutex unlock. */
3941 args = tree_cons (NULL, mutex, NULL);
3942 call = build_function_call (objc_sync_exit_decl, args);
3943 SET_EXPR_LOCATION (call, input_location);
3945 /* Put the that and the body in a TRY_FINALLY. */
3946 objc_begin_try_stmt (start_locus, body);
3947 objc_build_finally_clause (input_location, call);
3948 return objc_finish_try_stmt ();
3952 /* Predefine the following data type:
3954 struct _objc_exception_data
3960 /* The following yuckiness should prevent users from having to #include
3961 <setjmp.h> in their code... */
3963 #ifdef TARGET_POWERPC
3964 /* snarfed from /usr/include/ppc/setjmp.h */
3965 #define JBLEN (26 + 36 + 129 + 1)
3967 /* snarfed from /usr/include/i386/{setjmp,signal}.h */
3972 build_next_objc_exception_stuff (void)
3974 tree field_decl, field_decl_chain, index, temp_type;
3976 objc_exception_data_template
3977 = start_struct (RECORD_TYPE, get_identifier (UTAG_EXCDATA));
3979 /* int buf[JBLEN]; */
3981 index = build_index_type (build_int_cst (NULL_TREE, JBLEN - 1));
3982 field_decl = create_field_decl (build_array_type (integer_type_node, index),
3984 field_decl_chain = field_decl;
3986 /* void *pointers[4]; */
3988 index = build_index_type (build_int_cst (NULL_TREE, 4 - 1));
3989 field_decl = create_field_decl (build_array_type (ptr_type_node, index),
3991 chainon (field_decl_chain, field_decl);
3993 finish_struct (objc_exception_data_template, field_decl_chain, NULL_TREE);
3995 /* int _setjmp(...); */
3996 /* If the user includes <setjmp.h>, this shall be superseded by
3997 'int _setjmp(jmp_buf);' */
3998 temp_type = build_function_type (integer_type_node, NULL_TREE);
4000 = builtin_function (TAG_SETJMP, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4002 /* id objc_exception_extract(struct _objc_exception_data *); */
4004 = build_function_type (objc_object_type,
4005 tree_cons (NULL_TREE,
4006 build_pointer_type (objc_exception_data_template),
4008 objc_exception_extract_decl
4009 = builtin_function (TAG_EXCEPTIONEXTRACT, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4010 /* void objc_exception_try_enter(struct _objc_exception_data *); */
4011 /* void objc_exception_try_exit(struct _objc_exception_data *); */
4013 = build_function_type (void_type_node,
4014 tree_cons (NULL_TREE,
4015 build_pointer_type (objc_exception_data_template),
4017 objc_exception_try_enter_decl
4018 = builtin_function (TAG_EXCEPTIONTRYENTER, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4019 objc_exception_try_exit_decl
4020 = builtin_function (TAG_EXCEPTIONTRYEXIT, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4022 /* int objc_exception_match(id, id); */
4024 = build_function_type (integer_type_node,
4025 tree_cons (NULL_TREE, objc_object_type,
4026 tree_cons (NULL_TREE, objc_object_type,
4027 OBJC_VOID_AT_END)));
4028 objc_exception_match_decl
4029 = builtin_function (TAG_EXCEPTIONMATCH, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4031 /* id objc_assign_ivar (id, id, unsigned int); */
4032 /* id objc_assign_ivar_Fast (id, id, unsigned int)
4033 __attribute__ ((hard_coded_address (OFFS_ASSIGNIVAR_FAST))); */
4035 = build_function_type (objc_object_type,
4037 (NULL_TREE, objc_object_type,
4038 tree_cons (NULL_TREE, objc_object_type,
4039 tree_cons (NULL_TREE,
4041 OBJC_VOID_AT_END))));
4042 objc_assign_ivar_decl
4043 = builtin_function (TAG_ASSIGNIVAR, temp_type, 0, NOT_BUILT_IN,
4045 #ifdef OFFS_ASSIGNIVAR_FAST
4046 objc_assign_ivar_fast_decl
4047 = builtin_function (TAG_ASSIGNIVAR_FAST, temp_type, 0,
4048 NOT_BUILT_IN, NULL, NULL_TREE);
4049 DECL_ATTRIBUTES (objc_assign_ivar_fast_decl)
4050 = tree_cons (get_identifier ("hard_coded_address"),
4051 build_int_cst (NULL_TREE, OFFS_ASSIGNIVAR_FAST),
4054 /* Default to slower ivar method. */
4055 objc_assign_ivar_fast_decl = objc_assign_ivar_decl;
4058 /* id objc_assign_global (id, id *); */
4059 /* id objc_assign_strongCast (id, id *); */
4060 temp_type = build_function_type (objc_object_type,
4061 tree_cons (NULL_TREE, objc_object_type,
4062 tree_cons (NULL_TREE, build_pointer_type (objc_object_type),
4063 OBJC_VOID_AT_END)));
4064 objc_assign_global_decl
4065 = builtin_function (TAG_ASSIGNGLOBAL, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4066 objc_assign_strong_cast_decl
4067 = builtin_function (TAG_ASSIGNSTRONGCAST, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4071 build_objc_exception_stuff (void)
4073 tree noreturn_list, nothrow_list, temp_type;
4075 noreturn_list = tree_cons (get_identifier ("noreturn"), NULL, NULL);
4076 nothrow_list = tree_cons (get_identifier ("nothrow"), NULL, NULL);
4078 /* void objc_exception_throw(id) __attribute__((noreturn)); */
4079 /* void objc_sync_enter(id); */
4080 /* void objc_sync_exit(id); */
4081 temp_type = build_function_type (void_type_node,
4082 tree_cons (NULL_TREE, objc_object_type,
4084 objc_exception_throw_decl
4085 = builtin_function (TAG_EXCEPTIONTHROW, temp_type, 0, NOT_BUILT_IN, NULL,
4087 objc_sync_enter_decl
4088 = builtin_function (TAG_SYNCENTER, temp_type, 0, NOT_BUILT_IN,
4089 NULL, nothrow_list);
4091 = builtin_function (TAG_SYNCEXIT, temp_type, 0, NOT_BUILT_IN,
4092 NULL, nothrow_list);
4095 /* Construct a C struct corresponding to ObjC class CLASS, with the same
4098 struct <classname> {
4099 struct _objc_class *isa;
4104 build_private_template (tree class)
4106 if (!CLASS_STATIC_TEMPLATE (class))
4108 tree record = objc_build_struct (class,
4109 get_class_ivars (class, false),
4110 CLASS_SUPER_NAME (class));
4112 /* Set the TREE_USED bit for this struct, so that stab generator
4113 can emit stabs for this struct type. */
4114 if (flag_debug_only_used_symbols && TYPE_STUB_DECL (record))
4115 TREE_USED (TYPE_STUB_DECL (record)) = 1;
4119 /* Begin code generation for protocols... */
4121 /* struct _objc_protocol {
4122 struct _objc_class *isa;
4123 char *protocol_name;
4124 struct _objc_protocol **protocol_list;
4125 struct _objc__method_prototype_list *instance_methods;
4126 struct _objc__method_prototype_list *class_methods;
4130 build_protocol_template (void)
4132 tree field_decl, field_decl_chain;
4134 objc_protocol_template = start_struct (RECORD_TYPE,
4135 get_identifier (UTAG_PROTOCOL));
4137 /* struct _objc_class *isa; */
4138 field_decl = create_field_decl (build_pointer_type
4139 (xref_tag (RECORD_TYPE,
4140 get_identifier (UTAG_CLASS))),
4142 field_decl_chain = field_decl;
4144 /* char *protocol_name; */
4145 field_decl = create_field_decl (string_type_node, "protocol_name");
4146 chainon (field_decl_chain, field_decl);
4148 /* struct _objc_protocol **protocol_list; */
4149 field_decl = create_field_decl (build_pointer_type
4151 (objc_protocol_template)),
4153 chainon (field_decl_chain, field_decl);
4155 /* struct _objc__method_prototype_list *instance_methods; */
4156 field_decl = create_field_decl (objc_method_proto_list_ptr,
4157 "instance_methods");
4158 chainon (field_decl_chain, field_decl);
4160 /* struct _objc__method_prototype_list *class_methods; */
4161 field_decl = create_field_decl (objc_method_proto_list_ptr,
4163 chainon (field_decl_chain, field_decl);
4165 finish_struct (objc_protocol_template, field_decl_chain, NULL_TREE);
4169 build_descriptor_table_initializer (tree type, tree entries)
4171 tree initlist = NULL_TREE;
4175 tree eltlist = NULL_TREE;
4178 = tree_cons (NULL_TREE,
4179 build_selector (METHOD_SEL_NAME (entries)), NULL_TREE);
4181 = tree_cons (NULL_TREE,
4182 add_objc_string (METHOD_ENCODING (entries),
4187 = tree_cons (NULL_TREE,
4188 objc_build_constructor (type, nreverse (eltlist)),
4191 entries = TREE_CHAIN (entries);
4195 return objc_build_constructor (build_array_type (type, 0),
4196 nreverse (initlist));
4199 /* struct objc_method_prototype_list {
4201 struct objc_method_prototype {
4208 build_method_prototype_list_template (tree list_type, int size)
4210 tree objc_ivar_list_record;
4211 tree field_decl, field_decl_chain;
4213 /* Generate an unnamed struct definition. */
4215 objc_ivar_list_record = start_struct (RECORD_TYPE, NULL_TREE);
4217 /* int method_count; */
4218 field_decl = create_field_decl (integer_type_node, "method_count");
4219 field_decl_chain = field_decl;
4221 /* struct objc_method method_list[]; */
4222 field_decl = create_field_decl (build_array_type
4225 (build_int_cst (NULL_TREE, size - 1))),
4227 chainon (field_decl_chain, field_decl);
4229 finish_struct (objc_ivar_list_record, field_decl_chain, NULL_TREE);
4231 return objc_ivar_list_record;
4235 build_method_prototype_template (void)
4238 tree field_decl, field_decl_chain;
4241 = start_struct (RECORD_TYPE, get_identifier (UTAG_METHOD_PROTOTYPE));
4244 field_decl = create_field_decl (objc_selector_type, "_cmd");
4245 field_decl_chain = field_decl;
4247 /* char *method_types; */
4248 field_decl = create_field_decl (string_type_node, "method_types");
4249 chainon (field_decl_chain, field_decl);
4251 finish_struct (proto_record, field_decl_chain, NULL_TREE);
4253 return proto_record;
4257 objc_method_parm_type (tree type)
4259 type = TREE_VALUE (TREE_TYPE (type));
4260 if (TREE_CODE (type) == TYPE_DECL)
4261 type = TREE_TYPE (type);
4266 objc_encoded_type_size (tree type)
4268 int sz = int_size_in_bytes (type);
4270 /* Make all integer and enum types at least as large
4272 if (sz > 0 && INTEGRAL_TYPE_P (type))
4273 sz = MAX (sz, int_size_in_bytes (integer_type_node));
4274 /* Treat arrays as pointers, since that's how they're
4276 else if (TREE_CODE (type) == ARRAY_TYPE)
4277 sz = int_size_in_bytes (ptr_type_node);
4282 encode_method_prototype (tree method_decl)
4289 /* ONEWAY and BYCOPY, for remote object are the only method qualifiers. */
4290 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (method_decl)));
4292 /* Encode return type. */
4293 encode_type (objc_method_parm_type (method_decl),
4294 obstack_object_size (&util_obstack),
4295 OBJC_ENCODE_INLINE_DEFS);
4298 /* The first two arguments (self and _cmd) are pointers; account for
4300 i = int_size_in_bytes (ptr_type_node);
4301 parm_offset = 2 * i;
4302 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4303 parms = TREE_CHAIN (parms))
4305 tree type = objc_method_parm_type (parms);
4306 int sz = objc_encoded_type_size (type);
4308 /* If a type size is not known, bail out. */
4311 error ("type %q+D does not have a known size",
4313 /* Pretend that the encoding succeeded; the compilation will
4314 fail nevertheless. */
4315 goto finish_encoding;
4320 sprintf (buf, "%d@0:%d", parm_offset, i);
4321 obstack_grow (&util_obstack, buf, strlen (buf));
4323 /* Argument types. */
4324 parm_offset = 2 * i;
4325 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4326 parms = TREE_CHAIN (parms))
4328 tree type = objc_method_parm_type (parms);
4330 /* Process argument qualifiers for user supplied arguments. */
4331 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (parms)));
4334 encode_type (type, obstack_object_size (&util_obstack),
4335 OBJC_ENCODE_INLINE_DEFS);
4337 /* Compute offset. */
4338 sprintf (buf, "%d", parm_offset);
4339 parm_offset += objc_encoded_type_size (type);
4341 obstack_grow (&util_obstack, buf, strlen (buf));
4345 obstack_1grow (&util_obstack, '\0');
4346 result = get_identifier (obstack_finish (&util_obstack));
4347 obstack_free (&util_obstack, util_firstobj);
4352 generate_descriptor_table (tree type, const char *name, int size, tree list,
4355 tree decl, initlist;
4357 decl = start_var_decl (type, synth_id_with_class_suffix (name, proto));
4359 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, size));
4360 initlist = tree_cons (NULL_TREE, list, initlist);
4362 finish_var_decl (decl, objc_build_constructor (type, nreverse (initlist)));
4368 generate_method_descriptors (tree protocol)
4370 tree initlist, chain, method_list_template;
4373 if (!objc_method_prototype_template)
4374 objc_method_prototype_template = build_method_prototype_template ();
4376 chain = PROTOCOL_CLS_METHODS (protocol);
4379 size = list_length (chain);
4381 method_list_template
4382 = build_method_prototype_list_template (objc_method_prototype_template,
4386 = build_descriptor_table_initializer (objc_method_prototype_template,
4389 UOBJC_CLASS_METHODS_decl
4390 = generate_descriptor_table (method_list_template,
4391 "_OBJC_PROTOCOL_CLASS_METHODS",
4392 size, initlist, protocol);
4395 UOBJC_CLASS_METHODS_decl = 0;
4397 chain = PROTOCOL_NST_METHODS (protocol);
4400 size = list_length (chain);
4402 method_list_template
4403 = build_method_prototype_list_template (objc_method_prototype_template,
4406 = build_descriptor_table_initializer (objc_method_prototype_template,
4409 UOBJC_INSTANCE_METHODS_decl
4410 = generate_descriptor_table (method_list_template,
4411 "_OBJC_PROTOCOL_INSTANCE_METHODS",
4412 size, initlist, protocol);
4415 UOBJC_INSTANCE_METHODS_decl = 0;
4419 generate_protocol_references (tree plist)
4423 /* Forward declare protocols referenced. */
4424 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
4426 tree proto = TREE_VALUE (lproto);
4428 if (TREE_CODE (proto) == PROTOCOL_INTERFACE_TYPE
4429 && PROTOCOL_NAME (proto))
4431 if (! PROTOCOL_FORWARD_DECL (proto))
4432 build_protocol_reference (proto);
4434 if (PROTOCOL_LIST (proto))
4435 generate_protocol_references (PROTOCOL_LIST (proto));
4440 /* Generate either '- .cxx_construct' or '- .cxx_destruct' for the
4444 objc_generate_cxx_ctor_or_dtor (bool dtor)
4446 tree fn, body, compound_stmt, ivar;
4448 /* - (id) .cxx_construct { ... return self; } */
4449 /* - (void) .cxx_construct { ... } */
4451 objc_set_method_type (MINUS_EXPR);
4452 objc_start_method_definition
4453 (objc_build_method_signature (build_tree_list (NULL_TREE,
4456 : objc_object_type),
4457 get_identifier (dtor
4459 : TAG_CXX_CONSTRUCT),
4460 make_node (TREE_LIST),
4462 body = begin_function_body ();
4463 compound_stmt = begin_compound_stmt (0);
4465 ivar = CLASS_IVARS (implementation_template);
4466 /* Destroy ivars in reverse order. */
4468 ivar = nreverse (copy_list (ivar));
4470 for (; ivar; ivar = TREE_CHAIN (ivar))
4472 if (TREE_CODE (ivar) == FIELD_DECL)
4474 tree type = TREE_TYPE (ivar);
4476 /* Call the ivar's default constructor or destructor. Do not
4477 call the destructor unless a corresponding constructor call
4478 has also been made (or is not needed). */
4479 if (IS_AGGR_TYPE (type)
4481 ? (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4482 && (!TYPE_NEEDS_CONSTRUCTING (type)
4483 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4484 : (TYPE_NEEDS_CONSTRUCTING (type)
4485 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))))
4487 (build_special_member_call
4488 (build_ivar_reference (DECL_NAME (ivar)),
4489 dtor ? complete_dtor_identifier : complete_ctor_identifier,
4490 NULL_TREE, type, LOOKUP_NORMAL));
4494 /* The constructor returns 'self'. */
4496 finish_return_stmt (self_decl);
4498 finish_compound_stmt (compound_stmt);
4499 finish_function_body (body);
4500 fn = current_function_decl;
4502 objc_finish_method_definition (fn);
4505 /* The following routine will examine the current @interface for any
4506 non-POD C++ ivars requiring non-trivial construction and/or
4507 destruction, and then synthesize special '- .cxx_construct' and/or
4508 '- .cxx_destruct' methods which will run the appropriate
4509 construction or destruction code. Note that ivars inherited from
4510 super-classes are _not_ considered. */
4512 objc_generate_cxx_cdtors (void)
4514 bool need_ctor = false, need_dtor = false;
4517 /* We do not want to do this for categories, since they do not have
4520 if (TREE_CODE (objc_implementation_context) != CLASS_IMPLEMENTATION_TYPE)
4523 /* First, determine if we even need a constructor and/or destructor. */
4525 for (ivar = CLASS_IVARS (implementation_template); ivar;
4526 ivar = TREE_CHAIN (ivar))
4528 if (TREE_CODE (ivar) == FIELD_DECL)
4530 tree type = TREE_TYPE (ivar);
4532 if (IS_AGGR_TYPE (type))
4534 if (TYPE_NEEDS_CONSTRUCTING (type)
4535 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
4536 /* NB: If a default constructor is not available, we will not
4537 be able to initialize this ivar; the add_instance_variable()
4538 routine will already have warned about this. */
4541 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4542 && (!TYPE_NEEDS_CONSTRUCTING (type)
4543 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4544 /* NB: If a default constructor is not available, we will not
4545 call the destructor either, for symmetry. */
4551 /* Generate '- .cxx_construct' if needed. */
4554 objc_generate_cxx_ctor_or_dtor (false);
4556 /* Generate '- .cxx_destruct' if needed. */
4559 objc_generate_cxx_ctor_or_dtor (true);
4561 /* The 'imp_list' variable points at an imp_entry record for the current
4562 @implementation. Record the existence of '- .cxx_construct' and/or
4563 '- .cxx_destruct' methods therein; it will be included in the
4564 metadata for the class. */
4565 if (flag_next_runtime)
4566 imp_list->has_cxx_cdtors = (need_ctor || need_dtor);
4570 /* For each protocol which was referenced either from a @protocol()
4571 expression, or because a class/category implements it (then a
4572 pointer to the protocol is stored in the struct describing the
4573 class/category), we create a statically allocated instance of the
4574 Protocol class. The code is written in such a way as to generate
4575 as few Protocol objects as possible; we generate a unique Protocol
4576 instance for each protocol, and we don't generate a Protocol
4577 instance if the protocol is never referenced (either from a
4578 @protocol() or from a class/category implementation). These
4579 statically allocated objects can be referred to via the static
4580 (that is, private to this module) symbols _OBJC_PROTOCOL_n.
4582 The statically allocated Protocol objects that we generate here
4583 need to be fixed up at runtime in order to be used: the 'isa'
4584 pointer of the objects need to be set up to point to the 'Protocol'
4585 class, as known at runtime.
4587 The NeXT runtime fixes up all protocols at program startup time,
4588 before main() is entered. It uses a low-level trick to look up all
4589 those symbols, then loops on them and fixes them up.
4591 The GNU runtime as well fixes up all protocols before user code
4592 from the module is executed; it requires pointers to those symbols
4593 to be put in the objc_symtab (which is then passed as argument to
4594 the function __objc_exec_class() which the compiler sets up to be
4595 executed automatically when the module is loaded); setup of those
4596 Protocol objects happen in two ways in the GNU runtime: all
4597 Protocol objects referred to by a class or category implementation
4598 are fixed up when the class/category is loaded; all Protocol
4599 objects referred to by a @protocol() expression are added by the
4600 compiler to the list of statically allocated instances to fixup
4601 (the same list holding the statically allocated constant string
4602 objects). Because, as explained above, the compiler generates as
4603 few Protocol objects as possible, some Protocol object might end up
4604 being referenced multiple times when compiled with the GNU runtime,
4605 and end up being fixed up multiple times at runtime initialization.
4606 But that doesn't hurt, it's just a little inefficient. */
4609 generate_protocols (void)
4613 tree initlist, protocol_name_expr, refs_decl, refs_expr;
4615 /* If a protocol was directly referenced, pull in indirect references. */
4616 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4617 if (PROTOCOL_FORWARD_DECL (p) && PROTOCOL_LIST (p))
4618 generate_protocol_references (PROTOCOL_LIST (p));
4620 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4622 tree nst_methods = PROTOCOL_NST_METHODS (p);
4623 tree cls_methods = PROTOCOL_CLS_METHODS (p);
4625 /* If protocol wasn't referenced, don't generate any code. */
4626 decl = PROTOCOL_FORWARD_DECL (p);
4631 /* Make sure we link in the Protocol class. */
4632 add_class_reference (get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
4636 if (! METHOD_ENCODING (nst_methods))
4638 encoding = encode_method_prototype (nst_methods);
4639 METHOD_ENCODING (nst_methods) = encoding;
4641 nst_methods = TREE_CHAIN (nst_methods);
4646 if (! METHOD_ENCODING (cls_methods))
4648 encoding = encode_method_prototype (cls_methods);
4649 METHOD_ENCODING (cls_methods) = encoding;
4652 cls_methods = TREE_CHAIN (cls_methods);
4654 generate_method_descriptors (p);
4656 if (PROTOCOL_LIST (p))
4657 refs_decl = generate_protocol_list (p);
4661 /* static struct objc_protocol _OBJC_PROTOCOL_<mumble>; */
4662 protocol_name_expr = add_objc_string (PROTOCOL_NAME (p), class_names);
4665 refs_expr = convert (build_pointer_type (build_pointer_type
4666 (objc_protocol_template)),
4667 build_unary_op (ADDR_EXPR, refs_decl, 0));
4669 refs_expr = build_int_cst (NULL_TREE, 0);
4671 /* UOBJC_INSTANCE_METHODS_decl/UOBJC_CLASS_METHODS_decl are set
4672 by generate_method_descriptors, which is called above. */
4673 initlist = build_protocol_initializer (TREE_TYPE (decl),
4674 protocol_name_expr, refs_expr,
4675 UOBJC_INSTANCE_METHODS_decl,
4676 UOBJC_CLASS_METHODS_decl);
4677 finish_var_decl (decl, initlist);
4682 build_protocol_initializer (tree type, tree protocol_name,
4683 tree protocol_list, tree instance_methods,
4686 tree initlist = NULL_TREE, expr;
4687 tree cast_type = build_pointer_type
4688 (xref_tag (RECORD_TYPE,
4689 get_identifier (UTAG_CLASS)));
4691 /* Filling the "isa" in with one allows the runtime system to
4692 detect that the version change...should remove before final release. */
4694 expr = build_int_cst (cast_type, PROTOCOL_VERSION);
4695 initlist = tree_cons (NULL_TREE, expr, initlist);
4696 initlist = tree_cons (NULL_TREE, protocol_name, initlist);
4697 initlist = tree_cons (NULL_TREE, protocol_list, initlist);
4699 if (!instance_methods)
4700 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
4703 expr = convert (objc_method_proto_list_ptr,
4704 build_unary_op (ADDR_EXPR, instance_methods, 0));
4705 initlist = tree_cons (NULL_TREE, expr, initlist);
4709 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
4712 expr = convert (objc_method_proto_list_ptr,
4713 build_unary_op (ADDR_EXPR, class_methods, 0));
4714 initlist = tree_cons (NULL_TREE, expr, initlist);
4717 return objc_build_constructor (type, nreverse (initlist));
4720 /* struct _objc_category {
4721 char *category_name;
4723 struct _objc_method_list *instance_methods;
4724 struct _objc_method_list *class_methods;
4725 struct _objc_protocol_list *protocols;
4729 build_category_template (void)
4731 tree field_decl, field_decl_chain;
4733 objc_category_template = start_struct (RECORD_TYPE,
4734 get_identifier (UTAG_CATEGORY));
4736 /* char *category_name; */
4737 field_decl = create_field_decl (string_type_node, "category_name");
4738 field_decl_chain = field_decl;
4740 /* char *class_name; */
4741 field_decl = create_field_decl (string_type_node, "class_name");
4742 chainon (field_decl_chain, field_decl);
4744 /* struct _objc_method_list *instance_methods; */
4745 field_decl = create_field_decl (objc_method_list_ptr,
4746 "instance_methods");
4747 chainon (field_decl_chain, field_decl);
4749 /* struct _objc_method_list *class_methods; */
4750 field_decl = create_field_decl (objc_method_list_ptr,
4752 chainon (field_decl_chain, field_decl);
4754 /* struct _objc_protocol **protocol_list; */
4755 field_decl = create_field_decl (build_pointer_type
4757 (objc_protocol_template)),
4759 chainon (field_decl_chain, field_decl);
4761 finish_struct (objc_category_template, field_decl_chain, NULL_TREE);
4764 /* struct _objc_selector {
4770 build_selector_template (void)
4773 tree field_decl, field_decl_chain;
4775 objc_selector_template
4776 = start_struct (RECORD_TYPE, get_identifier (UTAG_SELECTOR));
4779 field_decl = create_field_decl (objc_selector_type, "sel_id");
4780 field_decl_chain = field_decl;
4782 /* char *sel_type; */
4783 field_decl = create_field_decl (string_type_node, "sel_type");
4784 chainon (field_decl_chain, field_decl);
4786 finish_struct (objc_selector_template, field_decl_chain, NULL_TREE);
4789 /* struct _objc_class {
4790 struct _objc_class *isa;
4791 struct _objc_class *super_class;
4796 struct _objc_ivar_list *ivars;
4797 struct _objc_method_list *methods;
4798 #ifdef __NEXT_RUNTIME__
4799 struct objc_cache *cache;
4801 struct sarray *dtable;
4802 struct _objc_class *subclass_list;
4803 struct _objc_class *sibling_class;
4805 struct _objc_protocol_list *protocols;
4806 #ifdef __NEXT_RUNTIME__
4809 void *gc_object_type;
4812 /* NB: The 'sel_id' and 'gc_object_type' fields are not being used by
4813 the NeXT/Apple runtime; still, the compiler must generate them to
4814 maintain backward binary compatibility (and to allow for future
4818 build_class_template (void)
4820 tree field_decl, field_decl_chain;
4823 = start_struct (RECORD_TYPE, get_identifier (UTAG_CLASS));
4825 /* struct _objc_class *isa; */
4826 field_decl = create_field_decl (build_pointer_type (objc_class_template),
4828 field_decl_chain = field_decl;
4830 /* struct _objc_class *super_class; */
4831 field_decl = create_field_decl (build_pointer_type (objc_class_template),
4833 chainon (field_decl_chain, field_decl);
4836 field_decl = create_field_decl (string_type_node, "name");
4837 chainon (field_decl_chain, field_decl);
4840 field_decl = create_field_decl (long_integer_type_node, "version");
4841 chainon (field_decl_chain, field_decl);
4844 field_decl = create_field_decl (long_integer_type_node, "info");
4845 chainon (field_decl_chain, field_decl);
4847 /* long instance_size; */
4848 field_decl = create_field_decl (long_integer_type_node, "instance_size");
4849 chainon (field_decl_chain, field_decl);
4851 /* struct _objc_ivar_list *ivars; */
4852 field_decl = create_field_decl (objc_ivar_list_ptr,
4854 chainon (field_decl_chain, field_decl);
4856 /* struct _objc_method_list *methods; */
4857 field_decl = create_field_decl (objc_method_list_ptr,
4859 chainon (field_decl_chain, field_decl);
4861 if (flag_next_runtime)
4863 /* struct objc_cache *cache; */
4864 field_decl = create_field_decl (build_pointer_type
4865 (xref_tag (RECORD_TYPE,
4869 chainon (field_decl_chain, field_decl);
4873 /* struct sarray *dtable; */
4874 field_decl = create_field_decl (build_pointer_type
4875 (xref_tag (RECORD_TYPE,
4879 chainon (field_decl_chain, field_decl);
4881 /* struct objc_class *subclass_list; */
4882 field_decl = create_field_decl (build_pointer_type
4883 (objc_class_template),
4885 chainon (field_decl_chain, field_decl);
4887 /* struct objc_class *sibling_class; */
4888 field_decl = create_field_decl (build_pointer_type
4889 (objc_class_template),
4891 chainon (field_decl_chain, field_decl);
4894 /* struct _objc_protocol **protocol_list; */
4895 field_decl = create_field_decl (build_pointer_type
4897 (xref_tag (RECORD_TYPE,
4901 chainon (field_decl_chain, field_decl);
4903 if (flag_next_runtime)
4906 field_decl = create_field_decl (build_pointer_type (void_type_node),
4908 chainon (field_decl_chain, field_decl);
4911 /* void *gc_object_type; */
4912 field_decl = create_field_decl (build_pointer_type (void_type_node),
4914 chainon (field_decl_chain, field_decl);
4916 finish_struct (objc_class_template, field_decl_chain, NULL_TREE);
4919 /* Generate appropriate forward declarations for an implementation. */
4922 synth_forward_declarations (void)
4926 /* static struct objc_class _OBJC_CLASS_<my_name>; */
4927 UOBJC_CLASS_decl = build_metadata_decl ("_OBJC_CLASS",
4928 objc_class_template);
4930 /* static struct objc_class _OBJC_METACLASS_<my_name>; */
4931 UOBJC_METACLASS_decl = build_metadata_decl ("_OBJC_METACLASS",
4932 objc_class_template);
4934 /* Pre-build the following entities - for speed/convenience. */
4936 an_id = get_identifier ("super_class");
4937 ucls_super_ref = objc_build_component_ref (UOBJC_CLASS_decl, an_id);
4938 uucls_super_ref = objc_build_component_ref (UOBJC_METACLASS_decl, an_id);
4942 error_with_ivar (const char *message, tree decl)
4944 error ("%J%s %qs", decl,
4945 message, gen_declaration (decl));
4950 check_ivars (tree inter, tree imp)
4952 tree intdecls = CLASS_RAW_IVARS (inter);
4953 tree impdecls = CLASS_RAW_IVARS (imp);
4960 if (intdecls && TREE_CODE (intdecls) == TYPE_DECL)
4961 intdecls = TREE_CHAIN (intdecls);
4963 if (intdecls == 0 && impdecls == 0)
4965 if (intdecls == 0 || impdecls == 0)
4967 error ("inconsistent instance variable specification");
4971 t1 = TREE_TYPE (intdecls); t2 = TREE_TYPE (impdecls);
4973 if (!comptypes (t1, t2)
4974 || !tree_int_cst_equal (DECL_INITIAL (intdecls),
4975 DECL_INITIAL (impdecls)))
4977 if (DECL_NAME (intdecls) == DECL_NAME (impdecls))
4979 error_with_ivar ("conflicting instance variable type",
4981 error_with_ivar ("previous declaration of",
4984 else /* both the type and the name don't match */
4986 error ("inconsistent instance variable specification");
4991 else if (DECL_NAME (intdecls) != DECL_NAME (impdecls))
4993 error_with_ivar ("conflicting instance variable name",
4995 error_with_ivar ("previous declaration of",
4999 intdecls = TREE_CHAIN (intdecls);
5000 impdecls = TREE_CHAIN (impdecls);
5004 /* Set 'objc_super_template' to the data type node for 'struct _objc_super'.
5005 This needs to be done just once per compilation. */
5007 /* struct _objc_super {
5008 struct _objc_object *self;
5009 struct _objc_class *super_class;
5013 build_super_template (void)
5015 tree field_decl, field_decl_chain;
5017 objc_super_template = start_struct (RECORD_TYPE, get_identifier (UTAG_SUPER));
5019 /* struct _objc_object *self; */
5020 field_decl = create_field_decl (objc_object_type, "self");
5021 field_decl_chain = field_decl;
5023 /* struct _objc_class *super_class; */
5024 field_decl = create_field_decl (build_pointer_type (objc_class_template),
5026 chainon (field_decl_chain, field_decl);
5028 finish_struct (objc_super_template, field_decl_chain, NULL_TREE);
5031 /* struct _objc_ivar {
5038 build_ivar_template (void)
5040 tree objc_ivar_id, objc_ivar_record;
5041 tree field_decl, field_decl_chain;
5043 objc_ivar_id = get_identifier (UTAG_IVAR);
5044 objc_ivar_record = start_struct (RECORD_TYPE, objc_ivar_id);
5046 /* char *ivar_name; */
5047 field_decl = create_field_decl (string_type_node, "ivar_name");
5048 field_decl_chain = field_decl;
5050 /* char *ivar_type; */
5051 field_decl = create_field_decl (string_type_node, "ivar_type");
5052 chainon (field_decl_chain, field_decl);
5054 /* int ivar_offset; */
5055 field_decl = create_field_decl (integer_type_node, "ivar_offset");
5056 chainon (field_decl_chain, field_decl);
5058 finish_struct (objc_ivar_record, field_decl_chain, NULL_TREE);
5060 return objc_ivar_record;
5065 struct objc_ivar ivar_list[ivar_count];
5069 build_ivar_list_template (tree list_type, int size)
5071 tree objc_ivar_list_record;
5072 tree field_decl, field_decl_chain;
5074 objc_ivar_list_record = start_struct (RECORD_TYPE, NULL_TREE);
5076 /* int ivar_count; */
5077 field_decl = create_field_decl (integer_type_node, "ivar_count");
5078 field_decl_chain = field_decl;
5080 /* struct objc_ivar ivar_list[]; */
5081 field_decl = create_field_decl (build_array_type
5084 (build_int_cst (NULL_TREE, size - 1))),
5086 chainon (field_decl_chain, field_decl);
5088 finish_struct (objc_ivar_list_record, field_decl_chain, NULL_TREE);
5090 return objc_ivar_list_record;
5094 struct _objc__method_prototype_list *method_next;
5096 struct objc_method method_list[method_count];
5100 build_method_list_template (tree list_type, int size)
5102 tree objc_ivar_list_record;
5103 tree field_decl, field_decl_chain;
5105 objc_ivar_list_record = start_struct (RECORD_TYPE, NULL_TREE);
5107 /* struct _objc__method_prototype_list *method_next; */
5108 field_decl = create_field_decl (objc_method_proto_list_ptr,
5110 field_decl_chain = field_decl;
5112 /* int method_count; */
5113 field_decl = create_field_decl (integer_type_node, "method_count");
5114 chainon (field_decl_chain, field_decl);
5116 /* struct objc_method method_list[]; */
5117 field_decl = create_field_decl (build_array_type
5120 (build_int_cst (NULL_TREE, size - 1))),
5122 chainon (field_decl_chain, field_decl);
5124 finish_struct (objc_ivar_list_record, field_decl_chain, NULL_TREE);
5126 return objc_ivar_list_record;
5130 build_ivar_list_initializer (tree type, tree field_decl)
5132 tree initlist = NULL_TREE;
5136 tree ivar = NULL_TREE;
5139 if (DECL_NAME (field_decl))
5140 ivar = tree_cons (NULL_TREE,
5141 add_objc_string (DECL_NAME (field_decl),
5145 /* Unnamed bit-field ivar (yuck). */
5146 ivar = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), ivar);
5149 encode_field_decl (field_decl,
5150 obstack_object_size (&util_obstack),
5151 OBJC_ENCODE_DONT_INLINE_DEFS);
5153 /* Null terminate string. */
5154 obstack_1grow (&util_obstack, 0);
5158 add_objc_string (get_identifier (obstack_finish (&util_obstack)),
5161 obstack_free (&util_obstack, util_firstobj);
5164 ivar = tree_cons (NULL_TREE, byte_position (field_decl), ivar);
5165 initlist = tree_cons (NULL_TREE,
5166 objc_build_constructor (type, nreverse (ivar)),
5169 field_decl = TREE_CHAIN (field_decl);
5170 while (field_decl && TREE_CODE (field_decl) != FIELD_DECL);
5174 return objc_build_constructor (build_array_type (type, 0),
5175 nreverse (initlist));
5179 generate_ivars_list (tree type, const char *name, int size, tree list)
5181 tree decl, initlist;
5183 decl = start_var_decl (type, synth_id_with_class_suffix
5184 (name, objc_implementation_context));
5186 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, size));
5187 initlist = tree_cons (NULL_TREE, list, initlist);
5189 finish_var_decl (decl,
5190 objc_build_constructor (TREE_TYPE (decl),
5191 nreverse (initlist)));
5196 /* Count only the fields occurring in T. */
5199 ivar_list_length (tree t)
5203 for (; t; t = TREE_CHAIN (t))
5204 if (TREE_CODE (t) == FIELD_DECL)
5211 generate_ivar_lists (void)
5213 tree initlist, ivar_list_template, chain;
5216 generating_instance_variables = 1;
5218 if (!objc_ivar_template)
5219 objc_ivar_template = build_ivar_template ();
5221 /* Only generate class variables for the root of the inheritance
5222 hierarchy since these will be the same for every class. */
5224 if (CLASS_SUPER_NAME (implementation_template) == NULL_TREE
5225 && (chain = TYPE_FIELDS (objc_class_template)))
5227 size = ivar_list_length (chain);
5229 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5230 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5232 UOBJC_CLASS_VARIABLES_decl
5233 = generate_ivars_list (ivar_list_template, "_OBJC_CLASS_VARIABLES",
5237 UOBJC_CLASS_VARIABLES_decl = 0;
5239 chain = CLASS_IVARS (implementation_template);
5242 size = ivar_list_length (chain);
5243 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5244 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5246 UOBJC_INSTANCE_VARIABLES_decl
5247 = generate_ivars_list (ivar_list_template, "_OBJC_INSTANCE_VARIABLES",
5251 UOBJC_INSTANCE_VARIABLES_decl = 0;
5253 generating_instance_variables = 0;
5257 build_dispatch_table_initializer (tree type, tree entries)
5259 tree initlist = NULL_TREE;
5263 tree elemlist = NULL_TREE;
5265 elemlist = tree_cons (NULL_TREE,
5266 build_selector (METHOD_SEL_NAME (entries)),
5269 /* Generate the method encoding if we don't have one already. */
5270 if (! METHOD_ENCODING (entries))
5271 METHOD_ENCODING (entries) =
5272 encode_method_prototype (entries);
5274 elemlist = tree_cons (NULL_TREE,
5275 add_objc_string (METHOD_ENCODING (entries),
5280 = tree_cons (NULL_TREE,
5281 convert (ptr_type_node,
5282 build_unary_op (ADDR_EXPR,
5283 METHOD_DEFINITION (entries), 1)),
5286 initlist = tree_cons (NULL_TREE,
5287 objc_build_constructor (type, nreverse (elemlist)),
5290 entries = TREE_CHAIN (entries);
5294 return objc_build_constructor (build_array_type (type, 0),
5295 nreverse (initlist));
5298 /* To accomplish method prototyping without generating all kinds of
5299 inane warnings, the definition of the dispatch table entries were
5302 struct objc_method { SEL _cmd; ...; id (*_imp)(); };
5304 struct objc_method { SEL _cmd; ...; void *_imp; }; */
5307 build_method_template (void)
5310 tree field_decl, field_decl_chain;
5312 _SLT_record = start_struct (RECORD_TYPE, get_identifier (UTAG_METHOD));
5315 field_decl = create_field_decl (objc_selector_type, "_cmd");
5316 field_decl_chain = field_decl;
5318 /* char *method_types; */
5319 field_decl = create_field_decl (string_type_node, "method_types");
5320 chainon (field_decl_chain, field_decl);
5323 field_decl = create_field_decl (build_pointer_type (void_type_node),
5325 chainon (field_decl_chain, field_decl);
5327 finish_struct (_SLT_record, field_decl_chain, NULL_TREE);
5334 generate_dispatch_table (tree type, const char *name, int size, tree list)
5336 tree decl, initlist;
5338 decl = start_var_decl (type, synth_id_with_class_suffix
5339 (name, objc_implementation_context));
5341 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, 0));
5342 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, size), initlist);
5343 initlist = tree_cons (NULL_TREE, list, initlist);
5345 finish_var_decl (decl,
5346 objc_build_constructor (TREE_TYPE (decl),
5347 nreverse (initlist)));
5353 mark_referenced_methods (void)
5355 struct imp_entry *impent;
5358 for (impent = imp_list; impent; impent = impent->next)
5360 chain = CLASS_CLS_METHODS (impent->imp_context);
5363 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5364 chain = TREE_CHAIN (chain);
5367 chain = CLASS_NST_METHODS (impent->imp_context);
5370 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5371 chain = TREE_CHAIN (chain);
5377 generate_dispatch_tables (void)
5379 tree initlist, chain, method_list_template;
5382 if (!objc_method_template)
5383 objc_method_template = build_method_template ();
5385 chain = CLASS_CLS_METHODS (objc_implementation_context);
5388 size = list_length (chain);
5390 method_list_template
5391 = build_method_list_template (objc_method_template, size);
5393 = build_dispatch_table_initializer (objc_method_template, chain);
5395 UOBJC_CLASS_METHODS_decl
5396 = generate_dispatch_table (method_list_template,
5397 ((TREE_CODE (objc_implementation_context)
5398 == CLASS_IMPLEMENTATION_TYPE)
5399 ? "_OBJC_CLASS_METHODS"
5400 : "_OBJC_CATEGORY_CLASS_METHODS"),
5404 UOBJC_CLASS_METHODS_decl = 0;
5406 chain = CLASS_NST_METHODS (objc_implementation_context);
5409 size = list_length (chain);
5411 method_list_template
5412 = build_method_list_template (objc_method_template, size);
5414 = build_dispatch_table_initializer (objc_method_template, chain);
5416 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
5417 UOBJC_INSTANCE_METHODS_decl
5418 = generate_dispatch_table (method_list_template,
5419 "_OBJC_INSTANCE_METHODS",
5422 /* We have a category. */
5423 UOBJC_INSTANCE_METHODS_decl
5424 = generate_dispatch_table (method_list_template,
5425 "_OBJC_CATEGORY_INSTANCE_METHODS",
5429 UOBJC_INSTANCE_METHODS_decl = 0;
5433 generate_protocol_list (tree i_or_p)
5436 tree refs_decl, lproto, e, plist;
5438 const char *ref_name;
5440 if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE
5441 || TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5442 plist = CLASS_PROTOCOL_LIST (i_or_p);
5443 else if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5444 plist = PROTOCOL_LIST (i_or_p);
5449 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5450 if (TREE_CODE (TREE_VALUE (lproto)) == PROTOCOL_INTERFACE_TYPE
5451 && PROTOCOL_FORWARD_DECL (TREE_VALUE (lproto)))
5454 /* Build initializer. */
5455 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), NULL_TREE);
5456 e = build_int_cst (build_pointer_type (objc_protocol_template), size);
5457 initlist = tree_cons (NULL_TREE, e, initlist);
5459 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5461 tree pval = TREE_VALUE (lproto);
5463 if (TREE_CODE (pval) == PROTOCOL_INTERFACE_TYPE
5464 && PROTOCOL_FORWARD_DECL (pval))
5466 e = build_unary_op (ADDR_EXPR, PROTOCOL_FORWARD_DECL (pval), 0);
5467 initlist = tree_cons (NULL_TREE, e, initlist);
5471 /* static struct objc_protocol *refs[n]; */
5473 if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5474 ref_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL_REFS", i_or_p);
5475 else if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE)
5476 ref_name = synth_id_with_class_suffix ("_OBJC_CLASS_PROTOCOLS", i_or_p);
5477 else if (TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5478 ref_name = synth_id_with_class_suffix ("_OBJC_CATEGORY_PROTOCOLS", i_or_p);
5482 refs_decl = start_var_decl
5484 (build_pointer_type (objc_protocol_template),
5485 build_index_type (build_int_cst (NULL_TREE, size + 2))),
5488 finish_var_decl (refs_decl, objc_build_constructor (TREE_TYPE (refs_decl),
5489 nreverse (initlist)));
5495 build_category_initializer (tree type, tree cat_name, tree class_name,
5496 tree instance_methods, tree class_methods,
5499 tree initlist = NULL_TREE, expr;
5501 initlist = tree_cons (NULL_TREE, cat_name, initlist);
5502 initlist = tree_cons (NULL_TREE, class_name, initlist);
5504 if (!instance_methods)
5505 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5508 expr = convert (objc_method_list_ptr,
5509 build_unary_op (ADDR_EXPR, instance_methods, 0));
5510 initlist = tree_cons (NULL_TREE, expr, initlist);
5513 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5516 expr = convert (objc_method_list_ptr,
5517 build_unary_op (ADDR_EXPR, class_methods, 0));
5518 initlist = tree_cons (NULL_TREE, expr, initlist);
5521 /* protocol_list = */
5523 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5526 expr = convert (build_pointer_type
5528 (objc_protocol_template)),
5529 build_unary_op (ADDR_EXPR, protocol_list, 0));
5530 initlist = tree_cons (NULL_TREE, expr, initlist);
5533 return objc_build_constructor (type, nreverse (initlist));
5536 /* struct _objc_class {
5537 struct objc_class *isa;
5538 struct objc_class *super_class;
5543 struct objc_ivar_list *ivars;
5544 struct objc_method_list *methods;
5545 if (flag_next_runtime)
5546 struct objc_cache *cache;
5548 struct sarray *dtable;
5549 struct objc_class *subclass_list;
5550 struct objc_class *sibling_class;
5552 struct objc_protocol_list *protocols;
5553 if (flag_next_runtime)
5555 void *gc_object_type;
5559 build_shared_structure_initializer (tree type, tree isa, tree super,
5560 tree name, tree size, int status,
5561 tree dispatch_table, tree ivar_list,
5564 tree initlist = NULL_TREE, expr;
5567 initlist = tree_cons (NULL_TREE, isa, initlist);
5570 initlist = tree_cons (NULL_TREE, super, initlist);
5573 initlist = tree_cons (NULL_TREE, default_conversion (name), initlist);
5576 initlist = tree_cons (NULL_TREE, build_int_cst (long_integer_type_node, 0),
5580 initlist = tree_cons (NULL_TREE,
5581 build_int_cst (long_integer_type_node, status),
5584 /* instance_size = */
5585 initlist = tree_cons (NULL_TREE, convert (long_integer_type_node, size),
5588 /* objc_ivar_list = */
5590 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5593 expr = convert (objc_ivar_list_ptr,
5594 build_unary_op (ADDR_EXPR, ivar_list, 0));
5595 initlist = tree_cons (NULL_TREE, expr, initlist);
5598 /* objc_method_list = */
5599 if (!dispatch_table)
5600 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5603 expr = convert (objc_method_list_ptr,
5604 build_unary_op (ADDR_EXPR, dispatch_table, 0));
5605 initlist = tree_cons (NULL_TREE, expr, initlist);
5608 if (flag_next_runtime)
5609 /* method_cache = */
5610 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5614 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5616 /* subclass_list = */
5617 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5619 /* sibling_class = */
5620 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5623 /* protocol_list = */
5624 if (! protocol_list)
5625 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5628 expr = convert (build_pointer_type
5630 (objc_protocol_template)),
5631 build_unary_op (ADDR_EXPR, protocol_list, 0));
5632 initlist = tree_cons (NULL_TREE, expr, initlist);
5635 if (flag_next_runtime)
5637 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5639 /* gc_object_type = NULL */
5640 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5642 return objc_build_constructor (type, nreverse (initlist));
5645 /* Retrieve category interface CAT_NAME (if any) associated with CLASS. */
5648 lookup_category (tree class, tree cat_name)
5650 tree category = CLASS_CATEGORY_LIST (class);
5652 while (category && CLASS_SUPER_NAME (category) != cat_name)
5653 category = CLASS_CATEGORY_LIST (category);
5657 /* static struct objc_category _OBJC_CATEGORY_<name> = { ... }; */
5660 generate_category (tree cat)
5663 tree initlist, cat_name_expr, class_name_expr;
5664 tree protocol_decl, category;
5666 add_class_reference (CLASS_NAME (cat));
5667 cat_name_expr = add_objc_string (CLASS_SUPER_NAME (cat), class_names);
5669 class_name_expr = add_objc_string (CLASS_NAME (cat), class_names);
5671 category = lookup_category (implementation_template,
5672 CLASS_SUPER_NAME (cat));
5674 if (category && CLASS_PROTOCOL_LIST (category))
5676 generate_protocol_references (CLASS_PROTOCOL_LIST (category));
5677 protocol_decl = generate_protocol_list (category);
5682 decl = start_var_decl (objc_category_template,
5683 synth_id_with_class_suffix
5684 ("_OBJC_CATEGORY", objc_implementation_context));
5686 initlist = build_category_initializer (TREE_TYPE (decl),
5687 cat_name_expr, class_name_expr,
5688 UOBJC_INSTANCE_METHODS_decl,
5689 UOBJC_CLASS_METHODS_decl,
5692 finish_var_decl (decl, initlist);
5695 /* static struct objc_class _OBJC_METACLASS_Foo={ ... };
5696 static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5699 generate_shared_structures (int cls_flags)
5701 tree sc_spec, decl_specs, decl;
5702 tree name_expr, super_expr, root_expr;
5703 tree my_root_id = NULL_TREE, my_super_id = NULL_TREE;
5704 tree cast_type, initlist, protocol_decl;
5706 my_super_id = CLASS_SUPER_NAME (implementation_template);
5709 add_class_reference (my_super_id);
5711 /* Compute "my_root_id" - this is required for code generation.
5712 the "isa" for all meta class structures points to the root of
5713 the inheritance hierarchy (e.g. "__Object")... */
5714 my_root_id = my_super_id;
5717 tree my_root_int = lookup_interface (my_root_id);
5719 if (my_root_int && CLASS_SUPER_NAME (my_root_int))
5720 my_root_id = CLASS_SUPER_NAME (my_root_int);
5727 /* No super class. */
5728 my_root_id = CLASS_NAME (implementation_template);
5730 cast_type = build_pointer_type (objc_class_template);
5731 name_expr = add_objc_string (CLASS_NAME (implementation_template),
5734 /* Install class `isa' and `super' pointers at runtime. */
5737 super_expr = add_objc_string (my_super_id, class_names);
5738 super_expr = build_c_cast (cast_type, super_expr); /* cast! */
5741 super_expr = build_int_cst (NULL_TREE, 0);
5743 root_expr = add_objc_string (my_root_id, class_names);
5744 root_expr = build_c_cast (cast_type, root_expr); /* cast! */
5746 if (CLASS_PROTOCOL_LIST (implementation_template))
5748 generate_protocol_references
5749 (CLASS_PROTOCOL_LIST (implementation_template));
5750 protocol_decl = generate_protocol_list (implementation_template);
5755 /* static struct objc_class _OBJC_METACLASS_Foo = { ... }; */
5757 sc_spec = build_tree_list (NULL_TREE, ridpointers[(int) RID_STATIC]);
5758 decl_specs = tree_cons (NULL_TREE, objc_class_template, sc_spec);
5760 decl = start_var_decl (objc_class_template,
5762 (DECL_NAME (UOBJC_METACLASS_decl)));
5765 = build_shared_structure_initializer
5767 root_expr, super_expr, name_expr,
5768 convert (integer_type_node, TYPE_SIZE_UNIT (objc_class_template)),
5770 UOBJC_CLASS_METHODS_decl,
5771 UOBJC_CLASS_VARIABLES_decl,
5774 finish_var_decl (decl, initlist);
5776 /* static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5778 decl = start_var_decl (objc_class_template,
5780 (DECL_NAME (UOBJC_CLASS_decl)));
5783 = build_shared_structure_initializer
5785 build_unary_op (ADDR_EXPR, UOBJC_METACLASS_decl, 0),
5786 super_expr, name_expr,
5787 convert (integer_type_node,
5788 TYPE_SIZE_UNIT (CLASS_STATIC_TEMPLATE
5789 (implementation_template))),
5790 1 /*CLS_FACTORY*/ | cls_flags,
5791 UOBJC_INSTANCE_METHODS_decl,
5792 UOBJC_INSTANCE_VARIABLES_decl,
5795 finish_var_decl (decl, initlist);
5800 synth_id_with_class_suffix (const char *preamble, tree ctxt)
5802 static char string[BUFSIZE];
5804 if (TREE_CODE (ctxt) == CLASS_IMPLEMENTATION_TYPE
5805 || TREE_CODE (ctxt) == CLASS_INTERFACE_TYPE)
5807 sprintf (string, "%s_%s", preamble,
5808 IDENTIFIER_POINTER (CLASS_NAME (ctxt)));
5810 else if (TREE_CODE (ctxt) == CATEGORY_IMPLEMENTATION_TYPE
5811 || TREE_CODE (ctxt) == CATEGORY_INTERFACE_TYPE)
5813 /* We have a category. */
5814 const char *const class_name
5815 = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
5816 const char *const class_super_name
5817 = IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context));
5818 sprintf (string, "%s_%s_%s", preamble, class_name, class_super_name);
5820 else if (TREE_CODE (ctxt) == PROTOCOL_INTERFACE_TYPE)
5822 const char *protocol_name = IDENTIFIER_POINTER (PROTOCOL_NAME (ctxt));
5823 sprintf (string, "%s_%s", preamble, protocol_name);
5831 /* If type is empty or only type qualifiers are present, add default
5832 type of id (otherwise grokdeclarator will default to int). */
5835 adjust_type_for_id_default (tree type)
5838 type = make_node (TREE_LIST);
5840 if (!TREE_VALUE (type))
5841 TREE_VALUE (type) = objc_object_type;
5842 else if (TREE_CODE (TREE_VALUE (type)) == RECORD_TYPE
5843 && TYPED_OBJECT (TREE_VALUE (type)))
5844 error ("can not use an object as parameter to a method");
5851 selector ':' '(' typename ')' identifier
5854 Transform an Objective-C keyword argument into
5855 the C equivalent parameter declarator.
5857 In: key_name, an "identifier_node" (optional).
5858 arg_type, a "tree_list" (optional).
5859 arg_name, an "identifier_node".
5861 Note: It would be really nice to strongly type the preceding
5862 arguments in the function prototype; however, then I
5863 could not use the "accessor" macros defined in "tree.h".
5865 Out: an instance of "keyword_decl". */
5868 objc_build_keyword_decl (tree key_name, tree arg_type, tree arg_name)
5872 /* If no type is specified, default to "id". */
5873 arg_type = adjust_type_for_id_default (arg_type);
5875 keyword_decl = make_node (KEYWORD_DECL);
5877 TREE_TYPE (keyword_decl) = arg_type;
5878 KEYWORD_ARG_NAME (keyword_decl) = arg_name;
5879 KEYWORD_KEY_NAME (keyword_decl) = key_name;
5881 return keyword_decl;
5884 /* Given a chain of keyword_decl's, synthesize the full keyword selector. */
5887 build_keyword_selector (tree selector)
5890 tree key_chain, key_name;
5893 /* Scan the selector to see how much space we'll need. */
5894 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
5896 if (TREE_CODE (selector) == KEYWORD_DECL)
5897 key_name = KEYWORD_KEY_NAME (key_chain);
5898 else if (TREE_CODE (selector) == TREE_LIST)
5899 key_name = TREE_PURPOSE (key_chain);
5904 len += IDENTIFIER_LENGTH (key_name) + 1;
5906 /* Just a ':' arg. */
5910 buf = (char *) alloca (len + 1);
5911 /* Start the buffer out as an empty string. */
5914 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
5916 if (TREE_CODE (selector) == KEYWORD_DECL)
5917 key_name = KEYWORD_KEY_NAME (key_chain);
5918 else if (TREE_CODE (selector) == TREE_LIST)
5920 key_name = TREE_PURPOSE (key_chain);
5921 /* The keyword decl chain will later be used as a function argument
5922 chain. Unhook the selector itself so as to not confuse other
5923 parts of the compiler. */
5924 TREE_PURPOSE (key_chain) = NULL_TREE;
5930 strcat (buf, IDENTIFIER_POINTER (key_name));
5934 return get_identifier (buf);
5937 /* Used for declarations and definitions. */
5940 build_method_decl (enum tree_code code, tree ret_type, tree selector,
5941 tree add_args, bool ellipsis)
5945 /* If no type is specified, default to "id". */
5946 ret_type = adjust_type_for_id_default (ret_type);
5948 method_decl = make_node (code);
5949 TREE_TYPE (method_decl) = ret_type;
5951 /* If we have a keyword selector, create an identifier_node that
5952 represents the full selector name (`:' included)... */
5953 if (TREE_CODE (selector) == KEYWORD_DECL)
5955 METHOD_SEL_NAME (method_decl) = build_keyword_selector (selector);
5956 METHOD_SEL_ARGS (method_decl) = selector;
5957 METHOD_ADD_ARGS (method_decl) = add_args;
5958 METHOD_ADD_ARGS_ELLIPSIS_P (method_decl) = ellipsis;
5962 METHOD_SEL_NAME (method_decl) = selector;
5963 METHOD_SEL_ARGS (method_decl) = NULL_TREE;
5964 METHOD_ADD_ARGS (method_decl) = NULL_TREE;
5970 #define METHOD_DEF 0
5971 #define METHOD_REF 1
5973 /* Used by `build_objc_method_call' and `comp_proto_with_proto'. Return
5974 an argument list for method METH. CONTEXT is either METHOD_DEF or
5975 METHOD_REF, saying whether we are trying to define a method or call
5976 one. SUPERFLAG says this is for a send to super; this makes a
5977 difference for the NeXT calling sequence in which the lookup and
5978 the method call are done together. If METH is null, user-defined
5979 arguments (i.e., beyond self and _cmd) shall be represented by `...'. */
5982 get_arg_type_list (tree meth, int context, int superflag)
5986 /* Receiver type. */
5987 if (flag_next_runtime && superflag)
5988 arglist = build_tree_list (NULL_TREE, objc_super_type);
5989 else if (context == METHOD_DEF && TREE_CODE (meth) == INSTANCE_METHOD_DECL)
5990 arglist = build_tree_list (NULL_TREE, objc_instance_type);
5992 arglist = build_tree_list (NULL_TREE, objc_object_type);
5994 /* Selector type - will eventually change to `int'. */
5995 chainon (arglist, build_tree_list (NULL_TREE, objc_selector_type));
5997 /* No actual method prototype given -- assume that remaining arguments
6002 /* Build a list of argument types. */
6003 for (akey = METHOD_SEL_ARGS (meth); akey; akey = TREE_CHAIN (akey))
6005 tree arg_type = TREE_VALUE (TREE_TYPE (akey));
6007 /* Decay arrays and functions into pointers. */
6008 if (TREE_CODE (arg_type) == ARRAY_TYPE)
6009 arg_type = build_pointer_type (TREE_TYPE (arg_type));
6010 else if (TREE_CODE (arg_type) == FUNCTION_TYPE)
6011 arg_type = build_pointer_type (arg_type);
6013 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6016 if (METHOD_ADD_ARGS (meth))
6018 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (meth));
6019 akey; akey = TREE_CHAIN (akey))
6021 tree arg_type = TREE_TYPE (TREE_VALUE (akey));
6023 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6026 if (!METHOD_ADD_ARGS_ELLIPSIS_P (meth))
6027 goto lack_of_ellipsis;
6032 chainon (arglist, OBJC_VOID_AT_END);
6039 check_duplicates (hash hsh, int methods, int is_class)
6041 tree meth = NULL_TREE;
6049 /* We have two or more methods with the same name but
6053 /* But just how different are those types? If
6054 -Wno-strict-selector-match is specified, we shall not
6055 complain if the differences are solely among types with
6056 identical size and alignment. */
6057 if (!warn_strict_selector_match)
6059 for (loop = hsh->list; loop; loop = loop->next)
6060 if (!comp_proto_with_proto (meth, loop->value, 0))
6067 warning (0, "multiple %s named %<%c%s%> found",
6068 methods ? "methods" : "selectors",
6069 (is_class ? '+' : '-'),
6070 IDENTIFIER_POINTER (METHOD_SEL_NAME (meth)));
6072 warn_with_method (methods ? "using" : "found",
6073 ((TREE_CODE (meth) == INSTANCE_METHOD_DECL)
6077 for (loop = hsh->list; loop; loop = loop->next)
6078 warn_with_method ("also found",
6079 ((TREE_CODE (loop->value) == INSTANCE_METHOD_DECL)
6088 /* If RECEIVER is a class reference, return the identifier node for
6089 the referenced class. RECEIVER is created by objc_get_class_reference,
6090 so we check the exact form created depending on which runtimes are
6094 receiver_is_class_object (tree receiver, int self, int super)
6096 tree chain, exp, arg;
6098 /* The receiver is 'self' or 'super' in the context of a class method. */
6099 if (objc_method_context
6100 && TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
6103 ? CLASS_SUPER_NAME (implementation_template)
6104 : CLASS_NAME (implementation_template));
6106 if (flag_next_runtime)
6108 /* The receiver is a variable created by
6109 build_class_reference_decl. */
6110 if (TREE_CODE (receiver) == VAR_DECL && IS_CLASS (TREE_TYPE (receiver)))
6111 /* Look up the identifier. */
6112 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
6113 if (TREE_PURPOSE (chain) == receiver)
6114 return TREE_VALUE (chain);
6117 /* The receiver is a function call that returns an id. Check if
6118 it is a call to objc_getClass, if so, pick up the class name. */
6119 if (TREE_CODE (receiver) == CALL_EXPR
6120 && (exp = TREE_OPERAND (receiver, 0))
6121 && TREE_CODE (exp) == ADDR_EXPR
6122 && (exp = TREE_OPERAND (exp, 0))
6123 && TREE_CODE (exp) == FUNCTION_DECL
6124 /* For some reason, we sometimes wind up with multiple FUNCTION_DECL
6125 prototypes for objc_get_class(). Thankfully, they seem to share the
6126 same function type. */
6127 && TREE_TYPE (exp) == TREE_TYPE (objc_get_class_decl)
6128 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (exp)), TAG_GETCLASS)
6129 /* We have a call to objc_get_class/objc_getClass! */
6130 && (arg = TREE_OPERAND (receiver, 1))
6131 && TREE_CODE (arg) == TREE_LIST
6132 && (arg = TREE_VALUE (arg)))
6135 if (TREE_CODE (arg) == ADDR_EXPR
6136 && (arg = TREE_OPERAND (arg, 0))
6137 && TREE_CODE (arg) == STRING_CST)
6138 /* Finally, we have the class name. */
6139 return get_identifier (TREE_STRING_POINTER (arg));
6144 /* If we are currently building a message expr, this holds
6145 the identifier of the selector of the message. This is
6146 used when printing warnings about argument mismatches. */
6148 static tree current_objc_message_selector = 0;
6151 objc_message_selector (void)
6153 return current_objc_message_selector;
6156 /* Construct an expression for sending a message.
6157 MESS has the object to send to in TREE_PURPOSE
6158 and the argument list (including selector) in TREE_VALUE.
6160 (*(<abstract_decl>(*)())_msg)(receiver, selTransTbl[n], ...);
6161 (*(<abstract_decl>(*)())_msgSuper)(receiver, selTransTbl[n], ...); */
6164 objc_build_message_expr (tree mess)
6166 tree receiver = TREE_PURPOSE (mess);
6169 tree args = TREE_PURPOSE (TREE_VALUE (mess));
6171 tree args = TREE_VALUE (mess);
6173 tree method_params = NULL_TREE;
6175 if (TREE_CODE (receiver) == ERROR_MARK)
6176 return error_mark_node;
6178 /* Obtain the full selector name. */
6179 if (TREE_CODE (args) == IDENTIFIER_NODE)
6180 /* A unary selector. */
6182 else if (TREE_CODE (args) == TREE_LIST)
6183 sel_name = build_keyword_selector (args);
6187 /* Build the parameter list to give to the method. */
6188 if (TREE_CODE (args) == TREE_LIST)
6190 method_params = chainon (args, TREE_VALUE (TREE_VALUE (mess)));
6193 tree chain = args, prev = NULL_TREE;
6195 /* We have a keyword selector--check for comma expressions. */
6198 tree element = TREE_VALUE (chain);
6200 /* We have a comma expression, must collapse... */
6201 if (TREE_CODE (element) == TREE_LIST)
6204 TREE_CHAIN (prev) = element;
6209 chain = TREE_CHAIN (chain);
6211 method_params = args;
6216 if (processing_template_decl)
6217 /* Must wait until template instantiation time. */
6218 return build_min_nt (MESSAGE_SEND_EXPR, receiver, sel_name,
6222 return objc_finish_message_expr (receiver, sel_name, method_params);
6225 /* Look up method SEL_NAME that would be suitable for receiver
6226 of type 'id' (if IS_CLASS is zero) or 'Class' (if IS_CLASS is
6227 nonzero), and report on any duplicates. */
6230 lookup_method_in_hash_lists (tree sel_name, int is_class)
6232 hash method_prototype = NULL;
6235 method_prototype = hash_lookup (nst_method_hash_list,
6238 if (!method_prototype)
6240 method_prototype = hash_lookup (cls_method_hash_list,
6245 return check_duplicates (method_prototype, 1, is_class);
6248 /* The 'objc_finish_message_expr' routine is called from within
6249 'objc_build_message_expr' for non-template functions. In the case of
6250 C++ template functions, it is called from 'build_expr_from_tree'
6251 (in decl2.c) after RECEIVER and METHOD_PARAMS have been expanded. */
6254 objc_finish_message_expr (tree receiver, tree sel_name, tree method_params)
6256 tree method_prototype = NULL_TREE, rprotos = NULL_TREE, rtype;
6257 tree selector, retval, class_tree;
6258 int self, super, have_cast;
6260 /* Extract the receiver of the message, as well as its type
6261 (where the latter may take the form of a cast or be inferred
6262 from the implementation context). */
6264 while (TREE_CODE (rtype) == COMPOUND_EXPR
6265 || TREE_CODE (rtype) == MODIFY_EXPR
6266 || TREE_CODE (rtype) == NOP_EXPR
6267 || TREE_CODE (rtype) == CONVERT_EXPR
6268 || TREE_CODE (rtype) == COMPONENT_REF)
6269 rtype = TREE_OPERAND (rtype, 0);
6270 self = (rtype == self_decl);
6271 super = (rtype == UOBJC_SUPER_decl);
6272 rtype = TREE_TYPE (receiver);
6273 have_cast = (TREE_CODE (receiver) == NOP_EXPR
6274 || (TREE_CODE (receiver) == COMPOUND_EXPR
6275 && !IS_SUPER (rtype)));
6277 /* If we are calling [super dealloc], reset our warning flag. */
6278 if (super && !strcmp ("dealloc", IDENTIFIER_POINTER (sel_name)))
6279 should_call_super_dealloc = 0;
6281 /* If the receiver is a class object, retrieve the corresponding
6282 @interface, if one exists. */
6283 class_tree = receiver_is_class_object (receiver, self, super);
6285 /* Now determine the receiver type (if an explicit cast has not been
6290 rtype = lookup_interface (class_tree);
6291 /* Handle `self' and `super'. */
6294 if (!CLASS_SUPER_NAME (implementation_template))
6296 error ("no super class declared in @interface for %qs",
6297 IDENTIFIER_POINTER (CLASS_NAME (implementation_template)));
6298 return error_mark_node;
6300 rtype = lookup_interface (CLASS_SUPER_NAME (implementation_template));
6303 rtype = lookup_interface (CLASS_NAME (implementation_template));
6306 /* If receiver is of type `id' or `Class' (or if the @interface for a
6307 class is not visible), we shall be satisfied with the existence of
6308 any instance or class method. */
6309 if (objc_is_id (rtype))
6311 class_tree = (IS_CLASS (rtype) ? objc_class_name : NULL_TREE);
6312 rprotos = (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype))
6313 ? TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype))
6319 /* If messaging 'id <Protos>' or 'Class <Proto>', first search
6320 in protocols themselves for the method prototype. */
6322 = lookup_method_in_protocol_list (rprotos, sel_name,
6323 class_tree != NULL_TREE);
6325 /* If messaging 'Class <Proto>' but did not find a class method
6326 prototype, search for an instance method instead, and warn
6327 about having done so. */
6328 if (!method_prototype && !rtype && class_tree != NULL_TREE)
6331 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
6333 if (method_prototype)
6334 warning (0, "found %<-%s%> instead of %<+%s%> in protocol(s)",
6335 IDENTIFIER_POINTER (sel_name),
6336 IDENTIFIER_POINTER (sel_name));
6342 tree orig_rtype = rtype, saved_rtype;
6344 if (TREE_CODE (rtype) == POINTER_TYPE)
6345 rtype = TREE_TYPE (rtype);
6346 /* Traverse typedef aliases */
6347 while (TREE_CODE (rtype) == RECORD_TYPE && OBJC_TYPE_NAME (rtype)
6348 && TREE_CODE (OBJC_TYPE_NAME (rtype)) == TYPE_DECL
6349 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype)))
6350 rtype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype));
6351 saved_rtype = rtype;
6352 if (TYPED_OBJECT (rtype))
6354 rprotos = TYPE_OBJC_PROTOCOL_LIST (rtype);
6355 rtype = TYPE_OBJC_INTERFACE (rtype);
6357 /* If we could not find an @interface declaration, we must have
6358 only seen a @class declaration; so, we cannot say anything
6359 more intelligent about which methods the receiver will
6361 if (!rtype || TREE_CODE (rtype) == IDENTIFIER_NODE)
6363 else if (TREE_CODE (rtype) == CLASS_INTERFACE_TYPE
6364 || TREE_CODE (rtype) == CLASS_IMPLEMENTATION_TYPE)
6366 /* We have a valid ObjC class name. Look up the method name
6367 in the published @interface for the class (and its
6370 = lookup_method_static (rtype, sel_name, class_tree != NULL_TREE);
6372 /* If the method was not found in the @interface, it may still
6373 exist locally as part of the @implementation. */
6374 if (!method_prototype && objc_implementation_context
6375 && CLASS_NAME (objc_implementation_context)
6376 == OBJC_TYPE_NAME (rtype))
6380 ? CLASS_CLS_METHODS (objc_implementation_context)
6381 : CLASS_NST_METHODS (objc_implementation_context)),
6384 /* If we haven't found a candidate method by now, try looking for
6385 it in the protocol list. */
6386 if (!method_prototype && rprotos)
6388 = lookup_method_in_protocol_list (rprotos, sel_name,
6389 class_tree != NULL_TREE);
6393 warning (0, "invalid receiver type %qs",
6394 gen_type_name (orig_rtype));
6395 /* After issuing the "invalid receiver" warning, perform method
6396 lookup as if we were messaging 'id'. */
6397 rtype = rprotos = NULL_TREE;
6402 /* For 'id' or 'Class' receivers, search in the global hash table
6403 as a last resort. For all receivers, warn if protocol searches
6405 if (!method_prototype)
6408 warning (0, "%<%c%s%> not found in protocol(s)",
6409 (class_tree ? '+' : '-'),
6410 IDENTIFIER_POINTER (sel_name));
6414 = lookup_method_in_hash_lists (sel_name, class_tree != NULL_TREE);
6417 if (!method_prototype)
6419 static bool warn_missing_methods = false;
6422 warning (0, "%qs may not respond to %<%c%s%>",
6423 IDENTIFIER_POINTER (OBJC_TYPE_NAME (rtype)),
6424 (class_tree ? '+' : '-'),
6425 IDENTIFIER_POINTER (sel_name));
6426 /* If we are messaging an 'id' or 'Class' object and made it here,
6427 then we have failed to find _any_ instance or class method,
6430 warning (0, "no %<%c%s%> method found",
6431 (class_tree ? '+' : '-'),
6432 IDENTIFIER_POINTER (sel_name));
6434 if (!warn_missing_methods)
6436 warning (0, "(Messages without a matching method signature");
6437 warning (0, "will be assumed to return %<id%> and accept");
6438 warning (0, "%<...%> as arguments.)");
6439 warn_missing_methods = true;
6443 /* Save the selector name for printing error messages. */
6444 current_objc_message_selector = sel_name;
6446 /* Build the parameters list for looking up the method.
6447 These are the object itself and the selector. */
6449 if (flag_typed_selectors)
6450 selector = build_typed_selector_reference (sel_name, method_prototype);
6452 selector = build_selector_reference (sel_name);
6454 retval = build_objc_method_call (super, method_prototype,
6456 selector, method_params);
6458 current_objc_message_selector = 0;
6463 /* Build a tree expression to send OBJECT the operation SELECTOR,
6464 looking up the method on object LOOKUP_OBJECT (often same as OBJECT),
6465 assuming the method has prototype METHOD_PROTOTYPE.
6466 (That is an INSTANCE_METHOD_DECL or CLASS_METHOD_DECL.)
6467 Use METHOD_PARAMS as list of args to pass to the method.
6468 If SUPER_FLAG is nonzero, we look up the superclass's method. */
6471 build_objc_method_call (int super_flag, tree method_prototype,
6472 tree lookup_object, tree selector,
6475 tree sender = (super_flag ? umsg_super_decl :
6476 (!flag_next_runtime || flag_nil_receivers
6477 ? (flag_objc_direct_dispatch
6480 : umsg_nonnil_decl));
6481 tree rcv_p = (super_flag ? objc_super_type : objc_object_type);
6483 /* If a prototype for the method to be called exists, then cast
6484 the sender's return type and arguments to match that of the method.
6485 Otherwise, leave sender as is. */
6488 ? TREE_VALUE (TREE_TYPE (method_prototype))
6489 : objc_object_type);
6491 = build_pointer_type
6492 (build_function_type
6495 (method_prototype, METHOD_REF, super_flag)));
6498 lookup_object = build_c_cast (rcv_p, lookup_object);
6500 /* Use SAVE_EXPR to avoid evaluating the receiver twice. */
6501 lookup_object = save_expr (lookup_object);
6503 if (flag_next_runtime)
6505 /* If we are returning a struct in memory, and the address
6506 of that memory location is passed as a hidden first
6507 argument, then change which messenger entry point this
6508 expr will call. NB: Note that sender_cast remains
6509 unchanged (it already has a struct return type). */
6510 if (!targetm.calls.struct_value_rtx (0, 0)
6511 && (TREE_CODE (ret_type) == RECORD_TYPE
6512 || TREE_CODE (ret_type) == UNION_TYPE)
6513 && targetm.calls.return_in_memory (ret_type, 0))
6514 sender = (super_flag ? umsg_super_stret_decl :
6515 flag_nil_receivers ? umsg_stret_decl : umsg_nonnil_stret_decl);
6517 method_params = tree_cons (NULL_TREE, lookup_object,
6518 tree_cons (NULL_TREE, selector,
6520 method = build_fold_addr_expr (sender);
6524 /* This is the portable (GNU) way. */
6527 /* First, call the lookup function to get a pointer to the method,
6528 then cast the pointer, then call it with the method arguments. */
6530 object = (super_flag ? self_decl : lookup_object);
6532 t = tree_cons (NULL_TREE, selector, NULL_TREE);
6533 t = tree_cons (NULL_TREE, lookup_object, t);
6534 method = build_function_call (sender, t);
6536 /* Pass the object to the method. */
6537 method_params = tree_cons (NULL_TREE, object,
6538 tree_cons (NULL_TREE, selector,
6542 /* ??? Selector is not at this point something we can use inside
6543 the compiler itself. Set it to garbage for the nonce. */
6544 t = build3 (OBJ_TYPE_REF, sender_cast, method, lookup_object, size_zero_node);
6545 return build_function_call (t, method_params);
6549 build_protocol_reference (tree p)
6552 const char *proto_name;
6554 /* static struct _objc_protocol _OBJC_PROTOCOL_<mumble>; */
6556 proto_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL", p);
6557 decl = start_var_decl (objc_protocol_template, proto_name);
6559 PROTOCOL_FORWARD_DECL (p) = decl;
6562 /* This function is called by the parser when (and only when) a
6563 @protocol() expression is found, in order to compile it. */
6565 objc_build_protocol_expr (tree protoname)
6568 tree p = lookup_protocol (protoname);
6572 error ("cannot find protocol declaration for %qs",
6573 IDENTIFIER_POINTER (protoname));
6574 return error_mark_node;
6577 if (!PROTOCOL_FORWARD_DECL (p))
6578 build_protocol_reference (p);
6580 expr = build_unary_op (ADDR_EXPR, PROTOCOL_FORWARD_DECL (p), 0);
6582 /* ??? Ideally we'd build the reference with objc_protocol_type directly,
6583 if we have it, rather than converting it here. */
6584 expr = convert (objc_protocol_type, expr);
6586 /* The @protocol() expression is being compiled into a pointer to a
6587 statically allocated instance of the Protocol class. To become
6588 usable at runtime, the 'isa' pointer of the instance need to be
6589 fixed up at runtime by the runtime library, to point to the
6590 actual 'Protocol' class. */
6592 /* For the GNU runtime, put the static Protocol instance in the list
6593 of statically allocated instances, so that we make sure that its
6594 'isa' pointer is fixed up at runtime by the GNU runtime library
6595 to point to the Protocol class (at runtime, when loading the
6596 module, the GNU runtime library loops on the statically allocated
6597 instances (as found in the defs field in objc_symtab) and fixups
6598 all the 'isa' pointers of those objects). */
6599 if (! flag_next_runtime)
6601 /* This type is a struct containing the fields of a Protocol
6602 object. (Cfr. objc_protocol_type instead is the type of a pointer
6603 to such a struct). */
6604 tree protocol_struct_type = xref_tag
6605 (RECORD_TYPE, get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
6608 /* Look for the list of Protocol statically allocated instances
6609 to fixup at runtime. Create a new list to hold Protocol
6610 statically allocated instances, if the list is not found. At
6611 present there is only another list, holding NSConstantString
6612 static instances to be fixed up at runtime. */
6613 for (chain = &objc_static_instances;
6614 *chain && TREE_VALUE (*chain) != protocol_struct_type;
6615 chain = &TREE_CHAIN (*chain));
6618 *chain = tree_cons (NULL_TREE, protocol_struct_type, NULL_TREE);
6619 add_objc_string (OBJC_TYPE_NAME (protocol_struct_type),
6623 /* Add this statically allocated instance to the Protocol list. */
6624 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE,
6625 PROTOCOL_FORWARD_DECL (p),
6626 TREE_PURPOSE (*chain));
6633 /* This function is called by the parser when a @selector() expression
6634 is found, in order to compile it. It is only called by the parser
6635 and only to compile a @selector(). */
6637 objc_build_selector_expr (tree selnamelist)
6641 /* Obtain the full selector name. */
6642 if (TREE_CODE (selnamelist) == IDENTIFIER_NODE)
6643 /* A unary selector. */
6644 selname = selnamelist;
6645 else if (TREE_CODE (selnamelist) == TREE_LIST)
6646 selname = build_keyword_selector (selnamelist);
6650 /* If we are required to check @selector() expressions as they
6651 are found, check that the selector has been declared. */
6652 if (warn_undeclared_selector)
6654 /* Look the selector up in the list of all known class and
6655 instance methods (up to this line) to check that the selector
6659 /* First try with instance methods. */
6660 hsh = hash_lookup (nst_method_hash_list, selname);
6662 /* If not found, try with class methods. */
6665 hsh = hash_lookup (cls_method_hash_list, selname);
6668 /* If still not found, print out a warning. */
6671 warning (0, "undeclared selector %qs", IDENTIFIER_POINTER (selname));
6676 if (flag_typed_selectors)
6677 return build_typed_selector_reference (selname, 0);
6679 return build_selector_reference (selname);
6683 objc_build_encode_expr (tree type)
6688 encode_type (type, obstack_object_size (&util_obstack),
6689 OBJC_ENCODE_INLINE_DEFS);
6690 obstack_1grow (&util_obstack, 0); /* null terminate string */
6691 string = obstack_finish (&util_obstack);
6693 /* Synthesize a string that represents the encoded struct/union. */
6694 result = my_build_string (strlen (string) + 1, string);
6695 obstack_free (&util_obstack, util_firstobj);
6700 build_ivar_reference (tree id)
6702 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
6704 /* Historically, a class method that produced objects (factory
6705 method) would assign `self' to the instance that it
6706 allocated. This would effectively turn the class method into
6707 an instance method. Following this assignment, the instance
6708 variables could be accessed. That practice, while safe,
6709 violates the simple rule that a class method should not refer
6710 to an instance variable. It's better to catch the cases
6711 where this is done unknowingly than to support the above
6713 warning (0, "instance variable %qs accessed in class method",
6714 IDENTIFIER_POINTER (id));
6715 self_decl = convert (objc_instance_type, self_decl); /* cast */
6718 return objc_build_component_ref (build_indirect_ref (self_decl, "->"), id);
6721 /* Compute a hash value for a given method SEL_NAME. */
6724 hash_func (tree sel_name)
6726 const unsigned char *s
6727 = (const unsigned char *)IDENTIFIER_POINTER (sel_name);
6731 h = h * 67 + *s++ - 113;
6738 nst_method_hash_list
6739 = (hash *) ggc_alloc_cleared (SIZEHASHTABLE * sizeof (hash));
6740 cls_method_hash_list
6741 = (hash *) ggc_alloc_cleared (SIZEHASHTABLE * sizeof (hash));
6743 /* Initialize the hash table used to hold the constant string objects. */
6744 string_htab = htab_create_ggc (31, string_hash,
6747 /* Initialize the hash table used to hold EH-volatilized types. */
6748 volatilized_htab = htab_create_ggc (31, volatilized_hash,
6749 volatilized_eq, NULL);
6752 /* WARNING!!!! hash_enter is called with a method, and will peek
6753 inside to find its selector! But hash_lookup is given a selector
6754 directly, and looks for the selector that's inside the found
6755 entry's key (method) for comparison. */
6758 hash_enter (hash *hashlist, tree method)
6761 int slot = hash_func (METHOD_SEL_NAME (method)) % SIZEHASHTABLE;
6763 obj = (hash) ggc_alloc (sizeof (struct hashed_entry));
6765 obj->next = hashlist[slot];
6768 hashlist[slot] = obj; /* append to front */
6772 hash_lookup (hash *hashlist, tree sel_name)
6776 target = hashlist[hash_func (sel_name) % SIZEHASHTABLE];
6780 if (sel_name == METHOD_SEL_NAME (target->key))
6783 target = target->next;
6789 hash_add_attr (hash entry, tree value)
6793 obj = (attr) ggc_alloc (sizeof (struct hashed_attribute));
6794 obj->next = entry->list;
6797 entry->list = obj; /* append to front */
6801 lookup_method (tree mchain, tree method)
6805 if (TREE_CODE (method) == IDENTIFIER_NODE)
6808 key = METHOD_SEL_NAME (method);
6812 if (METHOD_SEL_NAME (mchain) == key)
6815 mchain = TREE_CHAIN (mchain);
6820 /* Look up a class (if OBJC_LOOKUP_CLASS is set in FLAGS) or instance method
6821 in INTERFACE, along with any categories and protocols attached thereto.
6822 If method is not found, and the OBJC_LOOKUP_NO_SUPER is _not_ set in FLAGS,
6823 recursively examine the INTERFACE's superclass. If OBJC_LOOKUP_CLASS is
6824 set, OBJC_LOOKUP_NO_SUPER is cleared, and no suitable class method could
6825 be found in INTERFACE or any of its superclasses, look for an _instance_
6826 method of the same name in the root class as a last resort.
6828 If a suitable method cannot be found, return NULL_TREE. */
6831 lookup_method_static (tree interface, tree ident, int flags)
6833 tree meth = NULL_TREE, root_inter = NULL_TREE;
6834 tree inter = interface;
6835 int is_class = (flags & OBJC_LOOKUP_CLASS);
6836 int no_superclasses = (flags & OBJC_LOOKUP_NO_SUPER);
6840 tree chain = is_class ? CLASS_CLS_METHODS (inter) : CLASS_NST_METHODS (inter);
6841 tree category = inter;
6843 /* First, look up the method in the class itself. */
6844 if ((meth = lookup_method (chain, ident)))
6847 /* Failing that, look for the method in each category of the class. */
6848 while ((category = CLASS_CATEGORY_LIST (category)))
6850 chain = is_class ? CLASS_CLS_METHODS (category) : CLASS_NST_METHODS (category);
6852 /* Check directly in each category. */
6853 if ((meth = lookup_method (chain, ident)))
6856 /* Failing that, check in each category's protocols. */
6857 if (CLASS_PROTOCOL_LIST (category))
6859 if ((meth = (lookup_method_in_protocol_list
6860 (CLASS_PROTOCOL_LIST (category), ident, is_class))))
6865 /* If not found in categories, check in protocols of the main class. */
6866 if (CLASS_PROTOCOL_LIST (inter))
6868 if ((meth = (lookup_method_in_protocol_list
6869 (CLASS_PROTOCOL_LIST (inter), ident, is_class))))
6873 /* If we were instructed not to look in superclasses, don't. */
6874 if (no_superclasses)
6877 /* Failing that, climb up the inheritance hierarchy. */
6879 inter = lookup_interface (CLASS_SUPER_NAME (inter));
6883 /* If no class (factory) method was found, check if an _instance_
6884 method of the same name exists in the root class. This is what
6885 the Objective-C runtime will do. If an instance method was not
6887 return is_class ? lookup_method_static (root_inter, ident, 0): NULL_TREE;
6890 /* Add the method to the hash list if it doesn't contain an identical
6894 add_method_to_hash_list (hash *hash_list, tree method)
6898 if (!(hsh = hash_lookup (hash_list, METHOD_SEL_NAME (method))))
6900 /* Install on a global chain. */
6901 hash_enter (hash_list, method);
6905 /* Check types against those; if different, add to a list. */
6907 int already_there = comp_proto_with_proto (method, hsh->key, 1);
6908 for (loop = hsh->list; !already_there && loop; loop = loop->next)
6909 already_there |= comp_proto_with_proto (method, loop->value, 1);
6911 hash_add_attr (hsh, method);
6916 objc_add_method (tree class, tree method, int is_class)
6920 if (!(mth = lookup_method (is_class
6921 ? CLASS_CLS_METHODS (class)
6922 : CLASS_NST_METHODS (class), method)))
6924 /* put method on list in reverse order */
6927 TREE_CHAIN (method) = CLASS_CLS_METHODS (class);
6928 CLASS_CLS_METHODS (class) = method;
6932 TREE_CHAIN (method) = CLASS_NST_METHODS (class);
6933 CLASS_NST_METHODS (class) = method;
6938 /* When processing an @interface for a class or category, give hard
6939 errors on methods with identical selectors but differing argument
6940 and/or return types. We do not do this for @implementations, because
6941 C/C++ will do it for us (i.e., there will be duplicate function
6942 definition errors). */
6943 if ((TREE_CODE (class) == CLASS_INTERFACE_TYPE
6944 || TREE_CODE (class) == CATEGORY_INTERFACE_TYPE)
6945 && !comp_proto_with_proto (method, mth, 1))
6946 error ("duplicate declaration of method %<%c%s%>",
6947 is_class ? '+' : '-',
6948 IDENTIFIER_POINTER (METHOD_SEL_NAME (mth)));
6952 add_method_to_hash_list (cls_method_hash_list, method);
6955 add_method_to_hash_list (nst_method_hash_list, method);
6957 /* Instance methods in root classes (and categories thereof)
6958 may act as class methods as a last resort. We also add
6959 instance methods listed in @protocol declarations to
6960 the class hash table, on the assumption that @protocols
6961 may be adopted by root classes or categories. */
6962 if (TREE_CODE (class) == CATEGORY_INTERFACE_TYPE
6963 || TREE_CODE (class) == CATEGORY_IMPLEMENTATION_TYPE)
6964 class = lookup_interface (CLASS_NAME (class));
6966 if (TREE_CODE (class) == PROTOCOL_INTERFACE_TYPE
6967 || !CLASS_SUPER_NAME (class))
6968 add_method_to_hash_list (cls_method_hash_list, method);
6975 add_class (tree class_name, tree name)
6977 struct interface_tuple **slot;
6979 /* Put interfaces on list in reverse order. */
6980 TREE_CHAIN (class_name) = interface_chain;
6981 interface_chain = class_name;
6983 if (interface_htab == NULL)
6984 interface_htab = htab_create_ggc (31, hash_interface, eq_interface, NULL);
6985 slot = (struct interface_tuple **)
6986 htab_find_slot_with_hash (interface_htab, name,
6987 htab_hash_pointer (name),
6991 *slot = (struct interface_tuple *) ggc_alloc_cleared (sizeof (struct interface_tuple));
6994 (*slot)->class_name = class_name;
6996 return interface_chain;
7000 add_category (tree class, tree category)
7002 /* Put categories on list in reverse order. */
7003 tree cat = lookup_category (class, CLASS_SUPER_NAME (category));
7007 warning (0, "duplicate interface declaration for category %<%s(%s)%>",
7008 IDENTIFIER_POINTER (CLASS_NAME (class)),
7009 IDENTIFIER_POINTER (CLASS_SUPER_NAME (category)));
7013 CLASS_CATEGORY_LIST (category) = CLASS_CATEGORY_LIST (class);
7014 CLASS_CATEGORY_LIST (class) = category;
7018 /* Called after parsing each instance variable declaration. Necessary to
7019 preserve typedefs and implement public/private...
7021 PUBLIC is 1 for public, 0 for protected, and 2 for private. */
7024 add_instance_variable (tree class, int public, tree field_decl)
7026 tree field_type = TREE_TYPE (field_decl);
7027 const char *ivar_name = DECL_NAME (field_decl)
7028 ? IDENTIFIER_POINTER (DECL_NAME (field_decl))
7032 if (TREE_CODE (field_type) == REFERENCE_TYPE)
7034 error ("illegal reference type specified for instance variable %qs",
7036 /* Return class as is without adding this ivar. */
7041 if (field_type == error_mark_node || !TYPE_SIZE (field_type)
7042 || TYPE_SIZE (field_type) == error_mark_node)
7043 /* 'type[0]' is allowed, but 'type[]' is not! */
7045 error ("instance variable %qs has unknown size", ivar_name);
7046 /* Return class as is without adding this ivar. */
7051 /* Check if the ivar being added has a non-POD C++ type. If so, we will
7052 need to either (1) warn the user about it or (2) generate suitable
7053 constructor/destructor call from '- .cxx_construct' or '- .cxx_destruct'
7054 methods (if '-fobjc-call-cxx-cdtors' was specified). */
7055 if (IS_AGGR_TYPE (field_type)
7056 && (TYPE_NEEDS_CONSTRUCTING (field_type)
7057 || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type)
7058 || TYPE_POLYMORPHIC_P (field_type)))
7060 const char *type_name = IDENTIFIER_POINTER (OBJC_TYPE_NAME (field_type));
7062 if (flag_objc_call_cxx_cdtors)
7064 /* Since the ObjC runtime will be calling the constructors and
7065 destructors for us, the only thing we can't handle is the lack
7066 of a default constructor. */
7067 if (TYPE_NEEDS_CONSTRUCTING (field_type)
7068 && !TYPE_HAS_DEFAULT_CONSTRUCTOR (field_type))
7070 warning (0, "type %qs has no default constructor to call",
7073 /* If we cannot call a constructor, we should also avoid
7074 calling the destructor, for symmetry. */
7075 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7076 warning (0, "destructor for %qs shall not be run either",
7082 static bool warn_cxx_ivars = false;
7084 if (TYPE_POLYMORPHIC_P (field_type))
7086 /* Vtable pointers are Real Bad(tm), since Obj-C cannot
7088 error ("type %qs has virtual member functions", type_name);
7089 error ("illegal aggregate type %qs specified "
7090 "for instance variable %qs",
7091 type_name, ivar_name);
7092 /* Return class as is without adding this ivar. */
7096 /* User-defined constructors and destructors are not known to Obj-C
7097 and hence will not be called. This may or may not be a problem. */
7098 if (TYPE_NEEDS_CONSTRUCTING (field_type))
7099 warning (0, "type %qs has a user-defined constructor", type_name);
7100 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7101 warning (0, "type %qs has a user-defined destructor", type_name);
7103 if (!warn_cxx_ivars)
7105 warning (0, "C++ constructors and destructors will not "
7106 "be invoked for Objective-C fields");
7107 warn_cxx_ivars = true;
7113 /* Overload the public attribute, it is not used for FIELD_DECLs. */
7117 TREE_PUBLIC (field_decl) = 0;
7118 TREE_PRIVATE (field_decl) = 0;
7119 TREE_PROTECTED (field_decl) = 1;
7123 TREE_PUBLIC (field_decl) = 1;
7124 TREE_PRIVATE (field_decl) = 0;
7125 TREE_PROTECTED (field_decl) = 0;
7129 TREE_PUBLIC (field_decl) = 0;
7130 TREE_PRIVATE (field_decl) = 1;
7131 TREE_PROTECTED (field_decl) = 0;
7136 CLASS_RAW_IVARS (class) = chainon (CLASS_RAW_IVARS (class), field_decl);
7142 is_ivar (tree decl_chain, tree ident)
7144 for ( ; decl_chain; decl_chain = TREE_CHAIN (decl_chain))
7145 if (DECL_NAME (decl_chain) == ident)
7150 /* True if the ivar is private and we are not in its implementation. */
7153 is_private (tree decl)
7155 return (TREE_PRIVATE (decl)
7156 && ! is_ivar (CLASS_IVARS (implementation_template),
7160 /* We have an instance variable reference;, check to see if it is public. */
7163 objc_is_public (tree expr, tree identifier)
7165 tree basetype, decl;
7168 if (processing_template_decl)
7172 if (TREE_TYPE (expr) == error_mark_node)
7175 basetype = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
7177 if (basetype && TREE_CODE (basetype) == RECORD_TYPE)
7179 if (TYPE_HAS_OBJC_INFO (basetype) && TYPE_OBJC_INTERFACE (basetype))
7181 tree class = lookup_interface (OBJC_TYPE_NAME (basetype));
7185 error ("cannot find interface declaration for %qs",
7186 IDENTIFIER_POINTER (OBJC_TYPE_NAME (basetype)));
7190 if ((decl = is_ivar (get_class_ivars (class, true), identifier)))
7192 if (TREE_PUBLIC (decl))
7195 /* Important difference between the Stepstone translator:
7196 all instance variables should be public within the context
7197 of the implementation. */
7198 if (objc_implementation_context
7199 && ((TREE_CODE (objc_implementation_context)
7200 == CLASS_IMPLEMENTATION_TYPE)
7201 || (TREE_CODE (objc_implementation_context)
7202 == CATEGORY_IMPLEMENTATION_TYPE)))
7204 tree curtype = TYPE_MAIN_VARIANT
7205 (CLASS_STATIC_TEMPLATE
7206 (implementation_template));
7208 if (basetype == curtype
7209 || DERIVED_FROM_P (basetype, curtype))
7211 int private = is_private (decl);
7214 error ("instance variable %qs is declared private",
7215 IDENTIFIER_POINTER (DECL_NAME (decl)));
7221 /* The 2.95.2 compiler sometimes allowed C functions to access
7222 non-@public ivars. We will let this slide for now... */
7223 if (!objc_method_context)
7225 warning (0, "instance variable %qs is %s; "
7226 "this will be a hard error in the future",
7227 IDENTIFIER_POINTER (identifier),
7228 TREE_PRIVATE (decl) ? "@private" : "@protected");
7232 error ("instance variable %qs is declared %s",
7233 IDENTIFIER_POINTER (identifier),
7234 TREE_PRIVATE (decl) ? "private" : "protected");
7243 /* Make sure all entries in CHAIN are also in LIST. */
7246 check_methods (tree chain, tree list, int mtype)
7252 if (!lookup_method (list, chain))
7256 if (TREE_CODE (objc_implementation_context)
7257 == CLASS_IMPLEMENTATION_TYPE)
7258 warning (0, "incomplete implementation of class %qs",
7259 IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context)));
7260 else if (TREE_CODE (objc_implementation_context)
7261 == CATEGORY_IMPLEMENTATION_TYPE)
7262 warning (0, "incomplete implementation of category %qs",
7263 IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
7267 warning (0, "method definition for %<%c%s%> not found",
7268 mtype, IDENTIFIER_POINTER (METHOD_SEL_NAME (chain)));
7271 chain = TREE_CHAIN (chain);
7277 /* Check if CLASS, or its superclasses, explicitly conforms to PROTOCOL. */
7280 conforms_to_protocol (tree class, tree protocol)
7282 if (TREE_CODE (protocol) == PROTOCOL_INTERFACE_TYPE)
7284 tree p = CLASS_PROTOCOL_LIST (class);
7285 while (p && TREE_VALUE (p) != protocol)
7290 tree super = (CLASS_SUPER_NAME (class)
7291 ? lookup_interface (CLASS_SUPER_NAME (class))
7293 int tmp = super ? conforms_to_protocol (super, protocol) : 0;
7302 /* Make sure all methods in CHAIN are accessible as MTYPE methods in
7303 CONTEXT. This is one of two mechanisms to check protocol integrity. */
7306 check_methods_accessible (tree chain, tree context, int mtype)
7310 tree base_context = context;
7314 context = base_context;
7318 list = CLASS_CLS_METHODS (context);
7320 list = CLASS_NST_METHODS (context);
7322 if (lookup_method (list, chain))
7325 else if (TREE_CODE (context) == CLASS_IMPLEMENTATION_TYPE
7326 || TREE_CODE (context) == CLASS_INTERFACE_TYPE)
7327 context = (CLASS_SUPER_NAME (context)
7328 ? lookup_interface (CLASS_SUPER_NAME (context))
7331 else if (TREE_CODE (context) == CATEGORY_IMPLEMENTATION_TYPE
7332 || TREE_CODE (context) == CATEGORY_INTERFACE_TYPE)
7333 context = (CLASS_NAME (context)
7334 ? lookup_interface (CLASS_NAME (context))
7340 if (context == NULL_TREE)
7344 if (TREE_CODE (objc_implementation_context)
7345 == CLASS_IMPLEMENTATION_TYPE)
7346 warning (0, "incomplete implementation of class %qs",
7348 (CLASS_NAME (objc_implementation_context)));
7349 else if (TREE_CODE (objc_implementation_context)
7350 == CATEGORY_IMPLEMENTATION_TYPE)
7351 warning (0, "incomplete implementation of category %qs",
7353 (CLASS_SUPER_NAME (objc_implementation_context)));
7356 warning (0, "method definition for %<%c%s%> not found",
7357 mtype, IDENTIFIER_POINTER (METHOD_SEL_NAME (chain)));
7360 chain = TREE_CHAIN (chain); /* next method... */
7365 /* Check whether the current interface (accessible via
7366 'objc_implementation_context') actually implements protocol P, along
7367 with any protocols that P inherits. */
7370 check_protocol (tree p, const char *type, const char *name)
7372 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
7376 /* Ensure that all protocols have bodies! */
7379 f1 = check_methods (PROTOCOL_CLS_METHODS (p),
7380 CLASS_CLS_METHODS (objc_implementation_context),
7382 f2 = check_methods (PROTOCOL_NST_METHODS (p),
7383 CLASS_NST_METHODS (objc_implementation_context),
7388 f1 = check_methods_accessible (PROTOCOL_CLS_METHODS (p),
7389 objc_implementation_context,
7391 f2 = check_methods_accessible (PROTOCOL_NST_METHODS (p),
7392 objc_implementation_context,
7397 warning (0, "%s %qs does not fully implement the %qs protocol",
7398 type, name, IDENTIFIER_POINTER (PROTOCOL_NAME (p)));
7401 /* Check protocols recursively. */
7402 if (PROTOCOL_LIST (p))
7404 tree subs = PROTOCOL_LIST (p);
7406 lookup_interface (CLASS_SUPER_NAME (implementation_template));
7410 tree sub = TREE_VALUE (subs);
7412 /* If the superclass does not conform to the protocols
7413 inherited by P, then we must! */
7414 if (!super_class || !conforms_to_protocol (super_class, sub))
7415 check_protocol (sub, type, name);
7416 subs = TREE_CHAIN (subs);
7421 /* Check whether the current interface (accessible via
7422 'objc_implementation_context') actually implements the protocols listed
7426 check_protocols (tree proto_list, const char *type, const char *name)
7428 for ( ; proto_list; proto_list = TREE_CHAIN (proto_list))
7430 tree p = TREE_VALUE (proto_list);
7432 check_protocol (p, type, name);
7436 /* Make sure that the class CLASS_NAME is defined
7437 CODE says which kind of thing CLASS_NAME ought to be.
7438 It can be CLASS_INTERFACE_TYPE, CLASS_IMPLEMENTATION_TYPE,
7439 CATEGORY_INTERFACE_TYPE, or CATEGORY_IMPLEMENTATION_TYPE. */
7442 start_class (enum tree_code code, tree class_name, tree super_name,
7448 if (current_namespace != global_namespace) {
7449 error ("Objective-C declarations may only appear in global scope");
7451 #endif /* OBJCPLUS */
7453 if (objc_implementation_context)
7455 warning (0, "%<@end%> missing in implementation context");
7456 finish_class (objc_implementation_context);
7457 objc_ivar_chain = NULL_TREE;
7458 objc_implementation_context = NULL_TREE;
7461 class = make_node (code);
7462 TYPE_LANG_SLOT_1 (class) = make_tree_vec (CLASS_LANG_SLOT_ELTS);
7464 /* Check for existence of the super class, if one was specified. Note
7465 that we must have seen an @interface, not just a @class. If we
7466 are looking at a @compatibility_alias, traverse it first. */
7467 if ((code == CLASS_INTERFACE_TYPE || code == CLASS_IMPLEMENTATION_TYPE)
7470 tree super = objc_is_class_name (super_name);
7472 if (!super || !lookup_interface (super))
7474 error ("cannot find interface declaration for %qs, superclass of %qs",
7475 IDENTIFIER_POINTER (super ? super : super_name),
7476 IDENTIFIER_POINTER (class_name));
7477 super_name = NULL_TREE;
7483 CLASS_NAME (class) = class_name;
7484 CLASS_SUPER_NAME (class) = super_name;
7485 CLASS_CLS_METHODS (class) = NULL_TREE;
7487 if (! objc_is_class_name (class_name)
7488 && (decl = lookup_name (class_name)))
7490 error ("%qs redeclared as different kind of symbol",
7491 IDENTIFIER_POINTER (class_name));
7492 error ("previous declaration of %q+D",
7496 if (code == CLASS_IMPLEMENTATION_TYPE)
7501 for (chain = implemented_classes; chain; chain = TREE_CHAIN (chain))
7502 if (TREE_VALUE (chain) == class_name)
7504 error ("reimplementation of class %qs",
7505 IDENTIFIER_POINTER (class_name));
7506 return error_mark_node;
7508 implemented_classes = tree_cons (NULL_TREE, class_name,
7509 implemented_classes);
7512 /* Reset for multiple classes per file. */
7515 objc_implementation_context = class;
7517 /* Lookup the interface for this implementation. */
7519 if (!(implementation_template = lookup_interface (class_name)))
7521 warning (0, "cannot find interface declaration for %qs",
7522 IDENTIFIER_POINTER (class_name));
7523 add_class (implementation_template = objc_implementation_context,
7527 /* If a super class has been specified in the implementation,
7528 insure it conforms to the one specified in the interface. */
7531 && (super_name != CLASS_SUPER_NAME (implementation_template)))
7533 tree previous_name = CLASS_SUPER_NAME (implementation_template);
7534 const char *const name =
7535 previous_name ? IDENTIFIER_POINTER (previous_name) : "";
7536 error ("conflicting super class name %qs",
7537 IDENTIFIER_POINTER (super_name));
7538 error ("previous declaration of %qs", name);
7541 else if (! super_name)
7543 CLASS_SUPER_NAME (objc_implementation_context)
7544 = CLASS_SUPER_NAME (implementation_template);
7548 else if (code == CLASS_INTERFACE_TYPE)
7550 if (lookup_interface (class_name))
7552 error ("duplicate interface declaration for class %qs",
7554 warning (0, "duplicate interface declaration for class %qs",
7556 IDENTIFIER_POINTER (class_name));
7558 add_class (class, class_name);
7561 CLASS_PROTOCOL_LIST (class)
7562 = lookup_and_install_protocols (protocol_list);
7565 else if (code == CATEGORY_INTERFACE_TYPE)
7567 tree class_category_is_assoc_with;
7569 /* For a category, class_name is really the name of the class that
7570 the following set of methods will be associated with. We must
7571 find the interface so that can derive the objects template. */
7573 if (!(class_category_is_assoc_with = lookup_interface (class_name)))
7575 error ("cannot find interface declaration for %qs",
7576 IDENTIFIER_POINTER (class_name));
7577 exit (FATAL_EXIT_CODE);
7580 add_category (class_category_is_assoc_with, class);
7583 CLASS_PROTOCOL_LIST (class)
7584 = lookup_and_install_protocols (protocol_list);
7587 else if (code == CATEGORY_IMPLEMENTATION_TYPE)
7589 /* Reset for multiple classes per file. */
7592 objc_implementation_context = class;
7594 /* For a category, class_name is really the name of the class that
7595 the following set of methods will be associated with. We must
7596 find the interface so that can derive the objects template. */
7598 if (!(implementation_template = lookup_interface (class_name)))
7600 error ("cannot find interface declaration for %qs",
7601 IDENTIFIER_POINTER (class_name));
7602 exit (FATAL_EXIT_CODE);
7609 continue_class (tree class)
7611 if (TREE_CODE (class) == CLASS_IMPLEMENTATION_TYPE
7612 || TREE_CODE (class) == CATEGORY_IMPLEMENTATION_TYPE)
7614 struct imp_entry *imp_entry;
7616 /* Check consistency of the instance variables. */
7618 if (CLASS_RAW_IVARS (class))
7619 check_ivars (implementation_template, class);
7621 /* code generation */
7624 push_lang_context (lang_name_c);
7627 build_private_template (implementation_template);
7628 uprivate_record = CLASS_STATIC_TEMPLATE (implementation_template);
7629 objc_instance_type = build_pointer_type (uprivate_record);
7631 imp_entry = (struct imp_entry *) ggc_alloc (sizeof (struct imp_entry));
7633 imp_entry->next = imp_list;
7634 imp_entry->imp_context = class;
7635 imp_entry->imp_template = implementation_template;
7637 synth_forward_declarations ();
7638 imp_entry->class_decl = UOBJC_CLASS_decl;
7639 imp_entry->meta_decl = UOBJC_METACLASS_decl;
7640 imp_entry->has_cxx_cdtors = 0;
7642 /* Append to front and increment count. */
7643 imp_list = imp_entry;
7644 if (TREE_CODE (class) == CLASS_IMPLEMENTATION_TYPE)
7650 pop_lang_context ();
7651 #endif /* OBJCPLUS */
7653 return get_class_ivars (implementation_template, true);
7656 else if (TREE_CODE (class) == CLASS_INTERFACE_TYPE)
7659 push_lang_context (lang_name_c);
7660 #endif /* OBJCPLUS */
7662 build_private_template (class);
7665 pop_lang_context ();
7666 #endif /* OBJCPLUS */
7672 return error_mark_node;
7675 /* This is called once we see the "@end" in an interface/implementation. */
7678 finish_class (tree class)
7680 if (TREE_CODE (class) == CLASS_IMPLEMENTATION_TYPE)
7682 /* All code generation is done in finish_objc. */
7684 if (implementation_template != objc_implementation_context)
7686 /* Ensure that all method listed in the interface contain bodies. */
7687 check_methods (CLASS_CLS_METHODS (implementation_template),
7688 CLASS_CLS_METHODS (objc_implementation_context), '+');
7689 check_methods (CLASS_NST_METHODS (implementation_template),
7690 CLASS_NST_METHODS (objc_implementation_context), '-');
7692 if (CLASS_PROTOCOL_LIST (implementation_template))
7693 check_protocols (CLASS_PROTOCOL_LIST (implementation_template),
7695 IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context)));
7699 else if (TREE_CODE (class) == CATEGORY_IMPLEMENTATION_TYPE)
7701 tree category = lookup_category (implementation_template, CLASS_SUPER_NAME (class));
7705 /* Ensure all method listed in the interface contain bodies. */
7706 check_methods (CLASS_CLS_METHODS (category),
7707 CLASS_CLS_METHODS (objc_implementation_context), '+');
7708 check_methods (CLASS_NST_METHODS (category),
7709 CLASS_NST_METHODS (objc_implementation_context), '-');
7711 if (CLASS_PROTOCOL_LIST (category))
7712 check_protocols (CLASS_PROTOCOL_LIST (category),
7714 IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
7720 add_protocol (tree protocol)
7722 /* Put protocol on list in reverse order. */
7723 TREE_CHAIN (protocol) = protocol_chain;
7724 protocol_chain = protocol;
7725 return protocol_chain;
7729 lookup_protocol (tree ident)
7733 for (chain = protocol_chain; chain; chain = TREE_CHAIN (chain))
7734 if (ident == PROTOCOL_NAME (chain))
7740 /* This function forward declares the protocols named by NAMES. If
7741 they are already declared or defined, the function has no effect. */
7744 objc_declare_protocols (tree names)
7749 if (current_namespace != global_namespace) {
7750 error ("Objective-C declarations may only appear in global scope");
7752 #endif /* OBJCPLUS */
7754 for (list = names; list; list = TREE_CHAIN (list))
7756 tree name = TREE_VALUE (list);
7758 if (lookup_protocol (name) == NULL_TREE)
7760 tree protocol = make_node (PROTOCOL_INTERFACE_TYPE);
7762 TYPE_LANG_SLOT_1 (protocol)
7763 = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
7764 PROTOCOL_NAME (protocol) = name;
7765 PROTOCOL_LIST (protocol) = NULL_TREE;
7766 add_protocol (protocol);
7767 PROTOCOL_DEFINED (protocol) = 0;
7768 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
7774 start_protocol (enum tree_code code, tree name, tree list)
7779 if (current_namespace != global_namespace) {
7780 error ("Objective-C declarations may only appear in global scope");
7782 #endif /* OBJCPLUS */
7784 protocol = lookup_protocol (name);
7788 protocol = make_node (code);
7789 TYPE_LANG_SLOT_1 (protocol) = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
7791 PROTOCOL_NAME (protocol) = name;
7792 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
7793 add_protocol (protocol);
7794 PROTOCOL_DEFINED (protocol) = 1;
7795 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
7797 check_protocol_recursively (protocol, list);
7799 else if (! PROTOCOL_DEFINED (protocol))
7801 PROTOCOL_DEFINED (protocol) = 1;
7802 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
7804 check_protocol_recursively (protocol, list);
7808 warning (0, "duplicate declaration for protocol %qs",
7809 IDENTIFIER_POINTER (name));
7815 /* "Encode" a data type into a string, which grows in util_obstack.
7816 ??? What is the FORMAT? Someone please document this! */
7819 encode_type_qualifiers (tree declspecs)
7823 for (spec = declspecs; spec; spec = TREE_CHAIN (spec))
7825 if (ridpointers[(int) RID_IN] == TREE_VALUE (spec))
7826 obstack_1grow (&util_obstack, 'n');
7827 else if (ridpointers[(int) RID_INOUT] == TREE_VALUE (spec))
7828 obstack_1grow (&util_obstack, 'N');
7829 else if (ridpointers[(int) RID_OUT] == TREE_VALUE (spec))
7830 obstack_1grow (&util_obstack, 'o');
7831 else if (ridpointers[(int) RID_BYCOPY] == TREE_VALUE (spec))
7832 obstack_1grow (&util_obstack, 'O');
7833 else if (ridpointers[(int) RID_BYREF] == TREE_VALUE (spec))
7834 obstack_1grow (&util_obstack, 'R');
7835 else if (ridpointers[(int) RID_ONEWAY] == TREE_VALUE (spec))
7836 obstack_1grow (&util_obstack, 'V');
7840 /* Encode a pointer type. */
7843 encode_pointer (tree type, int curtype, int format)
7845 tree pointer_to = TREE_TYPE (type);
7847 if (TREE_CODE (pointer_to) == RECORD_TYPE)
7849 if (OBJC_TYPE_NAME (pointer_to)
7850 && TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE)
7852 const char *name = IDENTIFIER_POINTER (OBJC_TYPE_NAME (pointer_to));
7854 if (strcmp (name, TAG_OBJECT) == 0) /* '@' */
7856 obstack_1grow (&util_obstack, '@');
7859 else if (TYPE_HAS_OBJC_INFO (pointer_to)
7860 && TYPE_OBJC_INTERFACE (pointer_to))
7862 if (generating_instance_variables)
7864 obstack_1grow (&util_obstack, '@');
7865 obstack_1grow (&util_obstack, '"');
7866 obstack_grow (&util_obstack, name, strlen (name));
7867 obstack_1grow (&util_obstack, '"');
7872 obstack_1grow (&util_obstack, '@');
7876 else if (strcmp (name, TAG_CLASS) == 0) /* '#' */
7878 obstack_1grow (&util_obstack, '#');
7881 else if (strcmp (name, TAG_SELECTOR) == 0) /* ':' */
7883 obstack_1grow (&util_obstack, ':');
7888 else if (TREE_CODE (pointer_to) == INTEGER_TYPE
7889 && TYPE_MODE (pointer_to) == QImode)
7891 tree pname = TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE
7892 ? OBJC_TYPE_NAME (pointer_to)
7893 : DECL_NAME (OBJC_TYPE_NAME (pointer_to));
7895 if (!flag_next_runtime || strcmp (IDENTIFIER_POINTER (pname), "BOOL"))
7897 /* It appears that "r*" means "const char *" rather than
7899 if (TYPE_READONLY (pointer_to))
7900 obstack_1grow (&util_obstack, 'r');
7902 obstack_1grow (&util_obstack, '*');
7907 /* We have a type that does not get special treatment. */
7909 /* NeXT extension */
7910 obstack_1grow (&util_obstack, '^');
7911 encode_type (pointer_to, curtype, format);
7915 encode_array (tree type, int curtype, int format)
7917 tree an_int_cst = TYPE_SIZE (type);
7918 tree array_of = TREE_TYPE (type);
7921 /* An incomplete array is treated like a pointer. */
7922 if (an_int_cst == NULL)
7924 encode_pointer (type, curtype, format);
7928 if (TREE_INT_CST_LOW (TYPE_SIZE (array_of)) == 0)
7929 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT)0);
7931 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC,
7932 TREE_INT_CST_LOW (an_int_cst)
7933 / TREE_INT_CST_LOW (TYPE_SIZE (array_of)));
7935 obstack_grow (&util_obstack, buffer, strlen (buffer));
7936 encode_type (array_of, curtype, format);
7937 obstack_1grow (&util_obstack, ']');
7942 encode_aggregate_fields (tree type, int pointed_to, int curtype, int format)
7944 tree field = TYPE_FIELDS (type);
7946 for (; field; field = TREE_CHAIN (field))
7949 /* C++ static members, and things that are not field at all,
7950 should not appear in the encoding. */
7951 if (TREE_CODE (field) != FIELD_DECL || TREE_STATIC (field))
7955 /* Recursively encode fields of embedded base classes. */
7956 if (DECL_ARTIFICIAL (field) && !DECL_NAME (field)
7957 && TREE_CODE (TREE_TYPE (field)) == RECORD_TYPE)
7959 encode_aggregate_fields (TREE_TYPE (field),
7960 pointed_to, curtype, format);
7964 if (generating_instance_variables && !pointed_to)
7966 tree fname = DECL_NAME (field);
7968 obstack_1grow (&util_obstack, '"');
7970 if (fname && TREE_CODE (fname) == IDENTIFIER_NODE)
7971 obstack_grow (&util_obstack,
7972 IDENTIFIER_POINTER (fname),
7973 strlen (IDENTIFIER_POINTER (fname)));
7975 obstack_1grow (&util_obstack, '"');
7978 encode_field_decl (field, curtype, format);
7983 encode_aggregate_within (tree type, int curtype, int format, int left,
7987 /* NB: aggregates that are pointed to have slightly different encoding
7988 rules in that you never encode the names of instance variables. */
7989 int ob_size = obstack_object_size (&util_obstack);
7990 char c1 = ob_size > 1 ? *(obstack_next_free (&util_obstack) - 2) : 0;
7991 char c0 = ob_size > 0 ? *(obstack_next_free (&util_obstack) - 1) : 0;
7992 int pointed_to = (c0 == '^' || (c1 == '^' && c0 == 'r'));
7994 = ((format == OBJC_ENCODE_INLINE_DEFS || generating_instance_variables)
7995 && (!pointed_to || ob_size - curtype == (c1 == 'r' ? 2 : 1)));
7997 /* Traverse struct aliases; it is important to get the
7998 original struct and its tag name (if any). */
7999 type = TYPE_MAIN_VARIANT (type);
8000 name = OBJC_TYPE_NAME (type);
8001 /* Open parenth/bracket. */
8002 obstack_1grow (&util_obstack, left);
8004 /* Encode the struct/union tag name, or '?' if a tag was
8005 not provided. Typedef aliases do not qualify. */
8006 if (name && TREE_CODE (name) == IDENTIFIER_NODE
8008 /* Did this struct have a tag? */
8009 && !TYPE_WAS_ANONYMOUS (type)
8012 obstack_grow (&util_obstack,
8013 IDENTIFIER_POINTER (name),
8014 strlen (IDENTIFIER_POINTER (name)));
8016 obstack_1grow (&util_obstack, '?');
8018 /* Encode the types (and possibly names) of the inner fields,
8020 if (inline_contents)
8022 obstack_1grow (&util_obstack, '=');
8023 encode_aggregate_fields (type, pointed_to, curtype, format);
8025 /* Close parenth/bracket. */
8026 obstack_1grow (&util_obstack, right);
8030 encode_aggregate (tree type, int curtype, int format)
8032 enum tree_code code = TREE_CODE (type);
8038 encode_aggregate_within (type, curtype, format, '{', '}');
8043 encode_aggregate_within (type, curtype, format, '(', ')');
8048 obstack_1grow (&util_obstack, 'i');
8056 /* Encode a bitfield NeXT-style (i.e., without a bit offset or the underlying
8060 encode_next_bitfield (int width)
8063 sprintf (buffer, "b%d", width);
8064 obstack_grow (&util_obstack, buffer, strlen (buffer));
8067 /* FORMAT will be OBJC_ENCODE_INLINE_DEFS or OBJC_ENCODE_DONT_INLINE_DEFS. */
8069 encode_type (tree type, int curtype, int format)
8071 enum tree_code code = TREE_CODE (type);
8074 if (TYPE_READONLY (type))
8075 obstack_1grow (&util_obstack, 'r');
8077 if (code == INTEGER_TYPE)
8079 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8081 case 8: c = TYPE_UNSIGNED (type) ? 'C' : 'c'; break;
8082 case 16: c = TYPE_UNSIGNED (type) ? 'S' : 's'; break;
8084 if (type == long_unsigned_type_node
8085 || type == long_integer_type_node)
8086 c = TYPE_UNSIGNED (type) ? 'L' : 'l';
8088 c = TYPE_UNSIGNED (type) ? 'I' : 'i';
8090 case 64: c = TYPE_UNSIGNED (type) ? 'Q' : 'q'; break;
8093 obstack_1grow (&util_obstack, c);
8096 else if (code == REAL_TYPE)
8098 /* Floating point types. */
8099 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8101 case 32: c = 'f'; break;
8104 case 128: c = 'd'; break;
8107 obstack_1grow (&util_obstack, c);
8110 else if (code == VOID_TYPE)
8111 obstack_1grow (&util_obstack, 'v');
8113 else if (code == BOOLEAN_TYPE)
8114 obstack_1grow (&util_obstack, 'B');
8116 else if (code == ARRAY_TYPE)
8117 encode_array (type, curtype, format);
8119 else if (code == POINTER_TYPE)
8120 encode_pointer (type, curtype, format);
8122 else if (code == RECORD_TYPE || code == UNION_TYPE || code == ENUMERAL_TYPE)
8123 encode_aggregate (type, curtype, format);
8125 else if (code == FUNCTION_TYPE) /* '?' */
8126 obstack_1grow (&util_obstack, '?');
8128 else if (code == COMPLEX_TYPE)
8130 obstack_1grow (&util_obstack, 'j');
8131 encode_type (TREE_TYPE (type), curtype, format);
8136 encode_gnu_bitfield (int position, tree type, int size)
8138 enum tree_code code = TREE_CODE (type);
8140 char charType = '?';
8142 if (code == INTEGER_TYPE)
8144 if (integer_zerop (TYPE_MIN_VALUE (type)))
8146 /* Unsigned integer types. */
8148 if (TYPE_MODE (type) == QImode)
8150 else if (TYPE_MODE (type) == HImode)
8152 else if (TYPE_MODE (type) == SImode)
8154 if (type == long_unsigned_type_node)
8159 else if (TYPE_MODE (type) == DImode)
8164 /* Signed integer types. */
8166 if (TYPE_MODE (type) == QImode)
8168 else if (TYPE_MODE (type) == HImode)
8170 else if (TYPE_MODE (type) == SImode)
8172 if (type == long_integer_type_node)
8178 else if (TYPE_MODE (type) == DImode)
8182 else if (code == ENUMERAL_TYPE)
8187 sprintf (buffer, "b%d%c%d", position, charType, size);
8188 obstack_grow (&util_obstack, buffer, strlen (buffer));
8192 encode_field_decl (tree field_decl, int curtype, int format)
8197 /* C++ static members, and things that are not fields at all,
8198 should not appear in the encoding. */
8199 if (TREE_CODE (field_decl) != FIELD_DECL || TREE_STATIC (field_decl))
8203 type = TREE_TYPE (field_decl);
8205 /* Generate the bitfield typing information, if needed. Note the difference
8206 between GNU and NeXT runtimes. */
8207 if (DECL_BIT_FIELD_TYPE (field_decl))
8209 int size = tree_low_cst (DECL_SIZE (field_decl), 1);
8211 if (flag_next_runtime)
8212 encode_next_bitfield (size);
8214 encode_gnu_bitfield (int_bit_position (field_decl),
8215 DECL_BIT_FIELD_TYPE (field_decl), size);
8218 encode_type (TREE_TYPE (field_decl), curtype, format);
8221 static GTY(()) tree objc_parmlist = NULL_TREE;
8223 /* Append PARM to a list of formal parameters of a method, making a necessary
8224 array-to-pointer adjustment along the way. */
8227 objc_push_parm (tree parm)
8229 /* Decay arrays and functions into pointers. */
8230 if (TREE_CODE (TREE_TYPE (parm)) == ARRAY_TYPE)
8231 TREE_TYPE (parm) = build_pointer_type (TREE_TYPE (TREE_TYPE (parm)));
8232 else if (TREE_CODE (TREE_TYPE (parm)) == FUNCTION_TYPE)
8233 TREE_TYPE (parm) = build_pointer_type (TREE_TYPE (parm));
8235 DECL_ARG_TYPE (parm)
8236 = lang_hooks.types.type_promotes_to (TREE_TYPE (parm));
8238 /* Record constancy and volatility. */
8239 c_apply_type_quals_to_decl
8240 ((TYPE_READONLY (TREE_TYPE (parm)) ? TYPE_QUAL_CONST : 0)
8241 | (TYPE_RESTRICT (TREE_TYPE (parm)) ? TYPE_QUAL_RESTRICT : 0)
8242 | (TYPE_VOLATILE (TREE_TYPE (parm)) ? TYPE_QUAL_VOLATILE : 0), parm);
8244 objc_parmlist = chainon (objc_parmlist, parm);
8247 /* Retrieve the formal parameter list constructed via preceding calls to
8248 objc_push_parm(). */
8252 objc_get_parm_info (int have_ellipsis ATTRIBUTE_UNUSED)
8254 static struct c_arg_info *
8255 objc_get_parm_info (int have_ellipsis)
8259 tree parm_info = objc_parmlist;
8260 objc_parmlist = NULL_TREE;
8264 tree parm_info = objc_parmlist;
8265 struct c_arg_info *arg_info;
8266 /* The C front-end requires an elaborate song and dance at
8269 declare_parm_level ();
8272 tree next = TREE_CHAIN (parm_info);
8274 TREE_CHAIN (parm_info) = NULL_TREE;
8275 parm_info = pushdecl (parm_info);
8276 finish_decl (parm_info, NULL_TREE, NULL_TREE);
8279 arg_info = get_parm_info (have_ellipsis);
8281 objc_parmlist = NULL_TREE;
8286 /* Synthesize the formal parameters 'id self' and 'SEL _cmd' needed for ObjC
8287 method definitions. In the case of instance methods, we can be more
8288 specific as to the type of 'self'. */
8291 synth_self_and_ucmd_args (void)
8295 if (objc_method_context
8296 && TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL)
8297 self_type = objc_instance_type;
8299 /* Really a `struct objc_class *'. However, we allow people to
8300 assign to self, which changes its type midstream. */
8301 self_type = objc_object_type;
8304 objc_push_parm (build_decl (PARM_DECL, self_id, self_type));
8307 objc_push_parm (build_decl (PARM_DECL, ucmd_id, objc_selector_type));
8310 /* Transform an Objective-C method definition into a static C function
8311 definition, synthesizing the first two arguments, "self" and "_cmd",
8315 start_method_def (tree method)
8321 struct c_arg_info *parm_info;
8323 int have_ellipsis = 0;
8325 /* If we are defining a "dealloc" method in a non-root class, we
8326 will need to check if a [super dealloc] is missing, and warn if
8328 if(CLASS_SUPER_NAME (objc_implementation_context)
8329 && !strcmp ("dealloc", IDENTIFIER_POINTER (METHOD_SEL_NAME (method))))
8330 should_call_super_dealloc = 1;
8332 should_call_super_dealloc = 0;
8334 /* Required to implement _msgSuper. */
8335 objc_method_context = method;
8336 UOBJC_SUPER_decl = NULL_TREE;
8338 /* Generate prototype declarations for arguments..."new-style". */
8339 synth_self_and_ucmd_args ();
8341 /* Generate argument declarations if a keyword_decl. */
8342 parmlist = METHOD_SEL_ARGS (method);
8345 tree type = TREE_VALUE (TREE_TYPE (parmlist)), parm;
8347 parm = build_decl (PARM_DECL, KEYWORD_ARG_NAME (parmlist), type);
8348 objc_push_parm (parm);
8349 parmlist = TREE_CHAIN (parmlist);
8352 if (METHOD_ADD_ARGS (method))
8356 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (method));
8357 akey; akey = TREE_CHAIN (akey))
8359 objc_push_parm (TREE_VALUE (akey));
8362 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8366 parm_info = objc_get_parm_info (have_ellipsis);
8368 really_start_method (objc_method_context, parm_info);
8372 warn_with_method (const char *message, int mtype, tree method)
8374 /* Add a readable method name to the warning. */
8375 warning (0, "%J%s %<%c%s%>", method,
8376 message, mtype, gen_method_decl (method));
8379 /* Return 1 if TYPE1 is equivalent to TYPE2
8380 for purposes of method overloading. */
8383 objc_types_are_equivalent (tree type1, tree type2)
8388 /* Strip away indirections. */
8389 while ((TREE_CODE (type1) == ARRAY_TYPE || TREE_CODE (type1) == POINTER_TYPE)
8390 && (TREE_CODE (type1) == TREE_CODE (type2)))
8391 type1 = TREE_TYPE (type1), type2 = TREE_TYPE (type2);
8392 if (TYPE_MAIN_VARIANT (type1) != TYPE_MAIN_VARIANT (type2))
8395 type1 = (TYPE_HAS_OBJC_INFO (type1)
8396 ? TYPE_OBJC_PROTOCOL_LIST (type1)
8398 type2 = (TYPE_HAS_OBJC_INFO (type2)
8399 ? TYPE_OBJC_PROTOCOL_LIST (type2)
8402 if (list_length (type1) == list_length (type2))
8404 for (; type2; type2 = TREE_CHAIN (type2))
8405 if (!lookup_protocol_in_reflist (type1, TREE_VALUE (type2)))
8412 /* Return 1 if TYPE1 has the same size and alignment as TYPE2. */
8415 objc_types_share_size_and_alignment (tree type1, tree type2)
8417 return (simple_cst_equal (TYPE_SIZE (type1), TYPE_SIZE (type2))
8418 && TYPE_ALIGN (type1) == TYPE_ALIGN (type2));
8421 /* Return 1 if PROTO1 is equivalent to PROTO2
8422 for purposes of method overloading. Ordinarily, the type signatures
8423 should match up exactly, unless STRICT is zero, in which case we
8424 shall allow differences in which the size and alignment of a type
8428 comp_proto_with_proto (tree proto1, tree proto2, int strict)
8432 /* The following test is needed in case there are hashing
8434 if (METHOD_SEL_NAME (proto1) != METHOD_SEL_NAME (proto2))
8437 /* Compare return types. */
8438 type1 = TREE_VALUE (TREE_TYPE (proto1));
8439 type2 = TREE_VALUE (TREE_TYPE (proto2));
8441 if (!objc_types_are_equivalent (type1, type2)
8442 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8445 /* Compare argument types. */
8446 for (type1 = get_arg_type_list (proto1, METHOD_REF, 0),
8447 type2 = get_arg_type_list (proto2, METHOD_REF, 0);
8449 type1 = TREE_CHAIN (type1), type2 = TREE_CHAIN (type2))
8451 if (!objc_types_are_equivalent (TREE_VALUE (type1), TREE_VALUE (type2))
8453 || !objc_types_share_size_and_alignment (TREE_VALUE (type1),
8454 TREE_VALUE (type2))))
8458 return (!type1 && !type2);
8461 /* Fold an OBJ_TYPE_REF expression for ObjC method dispatches, where
8462 this occurs. ObjC method dispatches are _not_ like C++ virtual
8463 member function dispatches, and we account for the difference here. */
8466 objc_fold_obj_type_ref (tree ref, tree known_type)
8468 objc_fold_obj_type_ref (tree ref ATTRIBUTE_UNUSED,
8469 tree known_type ATTRIBUTE_UNUSED)
8473 tree v = BINFO_VIRTUALS (TYPE_BINFO (known_type));
8475 /* If the receiver does not have virtual member functions, there
8476 is nothing we can (or need to) do here. */
8480 /* Let C++ handle C++ virtual functions. */
8481 return cp_fold_obj_type_ref (ref, known_type);
8483 /* For plain ObjC, we currently do not need to do anything. */
8489 objc_start_function (tree name, tree type, tree attrs,
8493 struct c_arg_info *params
8497 tree fndecl = build_decl (FUNCTION_DECL, name, type);
8500 DECL_ARGUMENTS (fndecl) = params;
8501 DECL_INITIAL (fndecl) = error_mark_node;
8502 DECL_EXTERNAL (fndecl) = 0;
8503 TREE_STATIC (fndecl) = 1;
8504 retrofit_lang_decl (fndecl);
8505 cplus_decl_attributes (&fndecl, attrs, 0);
8506 start_preparsed_function (fndecl, attrs, /*flags=*/SF_DEFAULT);
8508 struct c_label_context_se *nstack_se;
8509 struct c_label_context_vm *nstack_vm;
8510 nstack_se = XOBNEW (&parser_obstack, struct c_label_context_se);
8511 nstack_se->labels_def = NULL;
8512 nstack_se->labels_used = NULL;
8513 nstack_se->next = label_context_stack_se;
8514 label_context_stack_se = nstack_se;
8515 nstack_vm = XOBNEW (&parser_obstack, struct c_label_context_vm);
8516 nstack_vm->labels_def = NULL;
8517 nstack_vm->labels_used = NULL;
8518 nstack_vm->scope = 0;
8519 nstack_vm->next = label_context_stack_vm;
8520 label_context_stack_vm = nstack_vm;
8521 current_function_returns_value = 0; /* Assume, until we see it does. */
8522 current_function_returns_null = 0;
8524 decl_attributes (&fndecl, attrs, 0);
8525 announce_function (fndecl);
8526 DECL_INITIAL (fndecl) = error_mark_node;
8527 DECL_EXTERNAL (fndecl) = 0;
8528 TREE_STATIC (fndecl) = 1;
8529 current_function_decl = pushdecl (fndecl);
8531 declare_parm_level ();
8532 DECL_RESULT (current_function_decl)
8533 = build_decl (RESULT_DECL, NULL_TREE,
8534 TREE_TYPE (TREE_TYPE (current_function_decl)));
8535 DECL_ARTIFICIAL (DECL_RESULT (current_function_decl)) = 1;
8536 DECL_IGNORED_P (DECL_RESULT (current_function_decl)) = 1;
8537 start_fname_decls ();
8538 store_parm_decls_from (params);
8541 TREE_USED (current_function_decl) = 1;
8544 /* - Generate an identifier for the function. the format is "_n_cls",
8545 where 1 <= n <= nMethods, and cls is the name the implementation we
8547 - Install the return type from the method declaration.
8548 - If we have a prototype, check for type consistency. */
8551 really_start_method (tree method,
8555 struct c_arg_info *parmlist
8559 tree ret_type, meth_type;
8561 const char *sel_name, *class_name, *cat_name;
8564 /* Synth the storage class & assemble the return type. */
8565 ret_type = TREE_VALUE (TREE_TYPE (method));
8567 sel_name = IDENTIFIER_POINTER (METHOD_SEL_NAME (method));
8568 class_name = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
8569 cat_name = ((TREE_CODE (objc_implementation_context)
8570 == CLASS_IMPLEMENTATION_TYPE)
8572 : IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
8575 /* Make sure this is big enough for any plausible method label. */
8576 buf = (char *) alloca (50 + strlen (sel_name) + strlen (class_name)
8577 + (cat_name ? strlen (cat_name) : 0));
8579 OBJC_GEN_METHOD_LABEL (buf, TREE_CODE (method) == INSTANCE_METHOD_DECL,
8580 class_name, cat_name, sel_name, method_slot);
8582 method_id = get_identifier (buf);
8585 /* Objective-C methods cannot be overloaded, so we don't need
8586 the type encoding appended. It looks bad anyway... */
8587 push_lang_context (lang_name_c);
8591 = build_function_type (ret_type,
8592 get_arg_type_list (method, METHOD_DEF, 0));
8593 objc_start_function (method_id, meth_type, NULL_TREE, parmlist);
8595 /* Set self_decl from the first argument. */
8596 self_decl = DECL_ARGUMENTS (current_function_decl);
8598 /* Suppress unused warnings. */
8599 TREE_USED (self_decl) = 1;
8600 TREE_USED (TREE_CHAIN (self_decl)) = 1;
8602 pop_lang_context ();
8605 METHOD_DEFINITION (method) = current_function_decl;
8607 /* Check consistency...start_function, pushdecl, duplicate_decls. */
8609 if (implementation_template != objc_implementation_context)
8612 = lookup_method_static (implementation_template,
8613 METHOD_SEL_NAME (method),
8614 ((TREE_CODE (method) == CLASS_METHOD_DECL)
8615 | OBJC_LOOKUP_NO_SUPER));
8619 if (!comp_proto_with_proto (method, proto, 1))
8621 char type = (TREE_CODE (method) == INSTANCE_METHOD_DECL ? '-' : '+');
8623 warn_with_method ("conflicting types for", type, method);
8624 warn_with_method ("previous declaration of", type, proto);
8629 /* We have a method @implementation even though we did not
8630 see a corresponding @interface declaration (which is allowed
8631 by Objective-C rules). Go ahead and place the method in
8632 the @interface anyway, so that message dispatch lookups
8634 tree interface = implementation_template;
8636 if (TREE_CODE (objc_implementation_context)
8637 == CATEGORY_IMPLEMENTATION_TYPE)
8638 interface = lookup_category
8640 CLASS_SUPER_NAME (objc_implementation_context));
8643 objc_add_method (interface, copy_node (method),
8644 TREE_CODE (method) == CLASS_METHOD_DECL);
8649 static void *UOBJC_SUPER_scope = 0;
8651 /* _n_Method (id self, SEL sel, ...)
8653 struct objc_super _S;
8654 _msgSuper ((_S.self = self, _S.class = _cls, &_S), ...);
8658 get_super_receiver (void)
8660 if (objc_method_context)
8662 tree super_expr, super_expr_list;
8664 if (!UOBJC_SUPER_decl)
8666 UOBJC_SUPER_decl = build_decl (VAR_DECL, get_identifier (TAG_SUPER),
8667 objc_super_template);
8668 /* This prevents `unused variable' warnings when compiling with -Wall. */
8669 TREE_USED (UOBJC_SUPER_decl) = 1;
8670 lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
8671 finish_decl (UOBJC_SUPER_decl, NULL_TREE, NULL_TREE);
8672 UOBJC_SUPER_scope = objc_get_current_scope ();
8675 /* Set receiver to self. */
8676 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
8677 super_expr = build_modify_expr (super_expr, NOP_EXPR, self_decl);
8678 super_expr_list = super_expr;
8680 /* Set class to begin searching. */
8681 super_expr = objc_build_component_ref (UOBJC_SUPER_decl,
8682 get_identifier ("super_class"));
8684 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
8686 /* [_cls, __cls]Super are "pre-built" in
8687 synth_forward_declarations. */
8689 super_expr = build_modify_expr (super_expr, NOP_EXPR,
8690 ((TREE_CODE (objc_method_context)
8691 == INSTANCE_METHOD_DECL)
8693 : uucls_super_ref));
8697 /* We have a category. */
8699 tree super_name = CLASS_SUPER_NAME (implementation_template);
8702 /* Barf if super used in a category of Object. */
8705 error ("no super class declared in interface for %qs",
8706 IDENTIFIER_POINTER (CLASS_NAME (implementation_template)));
8707 return error_mark_node;
8710 if (flag_next_runtime && !flag_zero_link)
8712 super_class = objc_get_class_reference (super_name);
8713 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
8714 /* If we are in a class method, we must retrieve the
8715 _metaclass_ for the current class, pointed at by
8716 the class's "isa" pointer. The following assumes that
8717 "isa" is the first ivar in a class (which it must be). */
8719 = build_indirect_ref
8720 (build_c_cast (build_pointer_type (objc_class_type),
8721 super_class), "unary *");
8725 add_class_reference (super_name);
8726 super_class = (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
8727 ? objc_get_class_decl : objc_get_meta_class_decl);
8728 assemble_external (super_class);
8730 = build_function_call
8734 my_build_string_pointer
8735 (IDENTIFIER_LENGTH (super_name) + 1,
8736 IDENTIFIER_POINTER (super_name))));
8740 = build_modify_expr (super_expr, NOP_EXPR,
8741 build_c_cast (TREE_TYPE (super_expr),
8745 super_expr_list = build_compound_expr (super_expr_list, super_expr);
8747 super_expr = build_unary_op (ADDR_EXPR, UOBJC_SUPER_decl, 0);
8748 super_expr_list = build_compound_expr (super_expr_list, super_expr);
8750 return super_expr_list;
8754 error ("[super ...] must appear in a method context");
8755 return error_mark_node;
8759 /* When exiting a scope, sever links to a 'super' declaration (if any)
8760 therein contained. */
8763 objc_clear_super_receiver (void)
8765 if (objc_method_context
8766 && UOBJC_SUPER_scope == objc_get_current_scope ()) {
8767 UOBJC_SUPER_decl = 0;
8768 UOBJC_SUPER_scope = 0;
8773 objc_finish_method_definition (tree fndecl)
8775 /* We cannot validly inline ObjC methods, at least not without a language
8776 extension to declare that a method need not be dynamically
8777 dispatched, so suppress all thoughts of doing so. */
8778 DECL_INLINE (fndecl) = 0;
8779 DECL_UNINLINABLE (fndecl) = 1;
8782 /* The C++ front-end will have called finish_function() for us. */
8786 METHOD_ENCODING (objc_method_context)
8787 = encode_method_prototype (objc_method_context);
8789 /* Required to implement _msgSuper. This must be done AFTER finish_function,
8790 since the optimizer may find "may be used before set" errors. */
8791 objc_method_context = NULL_TREE;
8793 if (should_call_super_dealloc)
8794 warning (0, "method possibly missing a [super dealloc] call");
8799 lang_report_error_function (tree decl)
8801 if (objc_method_context)
8803 fprintf (stderr, "In method %qs\n",
8804 IDENTIFIER_POINTER (METHOD_SEL_NAME (objc_method_context)));
8813 /* Given a tree DECL node, produce a printable description of it in the given
8814 buffer, overwriting the buffer. */
8817 gen_declaration (tree decl)
8823 gen_type_name_0 (TREE_TYPE (decl));
8825 if (DECL_NAME (decl))
8827 if (!POINTER_TYPE_P (TREE_TYPE (decl)))
8828 strcat (errbuf, " ");
8830 strcat (errbuf, IDENTIFIER_POINTER (DECL_NAME (decl)));
8833 if (DECL_INITIAL (decl)
8834 && TREE_CODE (DECL_INITIAL (decl)) == INTEGER_CST)
8835 sprintf (errbuf + strlen (errbuf), ": " HOST_WIDE_INT_PRINT_DEC,
8836 TREE_INT_CST_LOW (DECL_INITIAL (decl)));
8842 /* Given a tree TYPE node, produce a printable description of it in the given
8843 buffer, overwriting the buffer. */
8846 gen_type_name_0 (tree type)
8848 tree orig = type, proto;
8850 if (TYPE_P (type) && TYPE_NAME (type))
8851 type = TYPE_NAME (type);
8852 else if (POINTER_TYPE_P (type) || TREE_CODE (type) == ARRAY_TYPE)
8854 tree inner = TREE_TYPE (type);
8856 while (TREE_CODE (inner) == ARRAY_TYPE)
8857 inner = TREE_TYPE (inner);
8859 gen_type_name_0 (inner);
8861 if (!POINTER_TYPE_P (inner))
8862 strcat (errbuf, " ");
8864 if (POINTER_TYPE_P (type))
8865 strcat (errbuf, "*");
8867 while (type != inner)
8869 strcat (errbuf, "[");
8871 if (TYPE_DOMAIN (type))
8875 sprintf (sz, HOST_WIDE_INT_PRINT_DEC,
8877 (TYPE_MAX_VALUE (TYPE_DOMAIN (type))) + 1));
8878 strcat (errbuf, sz);
8881 strcat (errbuf, "]");
8882 type = TREE_TYPE (type);
8888 if (TREE_CODE (type) == TYPE_DECL && DECL_NAME (type))
8889 type = DECL_NAME (type);
8891 strcat (errbuf, TREE_CODE (type) == IDENTIFIER_NODE
8892 ? IDENTIFIER_POINTER (type)
8895 /* For 'id' and 'Class', adopted protocols are stored in the pointee. */
8896 if (objc_is_id (orig))
8897 orig = TREE_TYPE (orig);
8899 proto = TYPE_HAS_OBJC_INFO (orig) ? TYPE_OBJC_PROTOCOL_LIST (orig) : NULL_TREE;
8903 strcat (errbuf, " <");
8907 IDENTIFIER_POINTER (PROTOCOL_NAME (TREE_VALUE (proto))));
8908 proto = TREE_CHAIN (proto);
8909 strcat (errbuf, proto ? ", " : ">");
8918 gen_type_name (tree type)
8922 return gen_type_name_0 (type);
8925 /* Given a method tree, put a printable description into the given
8926 buffer (overwriting) and return a pointer to the buffer. */
8929 gen_method_decl (tree method)
8933 strcpy (errbuf, "("); /* NB: Do _not_ call strcat() here. */
8934 gen_type_name_0 (TREE_VALUE (TREE_TYPE (method)));
8935 strcat (errbuf, ")");
8936 chain = METHOD_SEL_ARGS (method);
8940 /* We have a chain of keyword_decls. */
8943 if (KEYWORD_KEY_NAME (chain))
8944 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_KEY_NAME (chain)));
8946 strcat (errbuf, ":(");
8947 gen_type_name_0 (TREE_VALUE (TREE_TYPE (chain)));
8948 strcat (errbuf, ")");
8950 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_ARG_NAME (chain)));
8951 if ((chain = TREE_CHAIN (chain)))
8952 strcat (errbuf, " ");
8956 if (METHOD_ADD_ARGS (method))
8958 chain = TREE_CHAIN (METHOD_ADD_ARGS (method));
8960 /* Know we have a chain of parm_decls. */
8963 strcat (errbuf, ", ");
8964 gen_type_name_0 (TREE_TYPE (TREE_VALUE (chain)));
8965 chain = TREE_CHAIN (chain);
8968 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8969 strcat (errbuf, ", ...");
8974 /* We have a unary selector. */
8975 strcat (errbuf, IDENTIFIER_POINTER (METHOD_SEL_NAME (method)));
8983 /* Dump an @interface declaration of the supplied class CHAIN to the
8984 supplied file FP. Used to implement the -gen-decls option (which
8985 prints out an @interface declaration of all classes compiled in
8986 this run); potentially useful for debugging the compiler too. */
8988 dump_interface (FILE *fp, tree chain)
8990 /* FIXME: A heap overflow here whenever a method (or ivar)
8991 declaration is so long that it doesn't fit in the buffer. The
8992 code and all the related functions should be rewritten to avoid
8993 using fixed size buffers. */
8994 const char *my_name = IDENTIFIER_POINTER (CLASS_NAME (chain));
8995 tree ivar_decls = CLASS_RAW_IVARS (chain);
8996 tree nst_methods = CLASS_NST_METHODS (chain);
8997 tree cls_methods = CLASS_CLS_METHODS (chain);
8999 fprintf (fp, "\n@interface %s", my_name);
9001 /* CLASS_SUPER_NAME is used to store the superclass name for
9002 classes, and the category name for categories. */
9003 if (CLASS_SUPER_NAME (chain))
9005 const char *name = IDENTIFIER_POINTER (CLASS_SUPER_NAME (chain));
9007 if (TREE_CODE (chain) == CATEGORY_IMPLEMENTATION_TYPE
9008 || TREE_CODE (chain) == CATEGORY_INTERFACE_TYPE)
9010 fprintf (fp, " (%s)\n", name);
9014 fprintf (fp, " : %s\n", name);
9020 /* FIXME - the following doesn't seem to work at the moment. */
9023 fprintf (fp, "{\n");
9026 fprintf (fp, "\t%s;\n", gen_declaration (ivar_decls));
9027 ivar_decls = TREE_CHAIN (ivar_decls);
9030 fprintf (fp, "}\n");
9035 fprintf (fp, "- %s;\n", gen_method_decl (nst_methods));
9036 nst_methods = TREE_CHAIN (nst_methods);
9041 fprintf (fp, "+ %s;\n", gen_method_decl (cls_methods));
9042 cls_methods = TREE_CHAIN (cls_methods);
9045 fprintf (fp, "@end\n");
9048 /* Demangle function for Objective-C */
9050 objc_demangle (const char *mangled)
9052 char *demangled, *cp;
9054 if (mangled[0] == '_' &&
9055 (mangled[1] == 'i' || mangled[1] == 'c') &&
9058 cp = demangled = XNEWVEC (char, strlen(mangled) + 2);
9059 if (mangled[1] == 'i')
9060 *cp++ = '-'; /* for instance method */
9062 *cp++ = '+'; /* for class method */
9063 *cp++ = '['; /* opening left brace */
9064 strcpy(cp, mangled+3); /* tack on the rest of the mangled name */
9065 while (*cp && *cp == '_')
9066 cp++; /* skip any initial underbars in class name */
9067 cp = strchr(cp, '_'); /* find first non-initial underbar */
9070 free(demangled); /* not mangled name */
9073 if (cp[1] == '_') /* easy case: no category name */
9075 *cp++ = ' '; /* replace two '_' with one ' ' */
9076 strcpy(cp, mangled + (cp - demangled) + 2);
9080 *cp++ = '('; /* less easy case: category name */
9081 cp = strchr(cp, '_');
9084 free(demangled); /* not mangled name */
9088 *cp++ = ' '; /* overwriting 1st char of method name... */
9089 strcpy(cp, mangled + (cp - demangled)); /* get it back */
9091 while (*cp && *cp == '_')
9092 cp++; /* skip any initial underbars in method name */
9095 *cp = ':'; /* replace remaining '_' with ':' */
9096 *cp++ = ']'; /* closing right brace */
9097 *cp++ = 0; /* string terminator */
9101 return mangled; /* not an objc mangled name */
9105 objc_printable_name (tree decl, int kind ATTRIBUTE_UNUSED)
9107 return objc_demangle (IDENTIFIER_POINTER (DECL_NAME (decl)));
9113 gcc_obstack_init (&util_obstack);
9114 util_firstobj = (char *) obstack_finish (&util_obstack);
9116 errbuf = XNEWVEC (char, 1024 * 10);
9118 synth_module_prologue ();
9124 struct imp_entry *impent;
9126 /* The internally generated initializers appear to have missing braces.
9127 Don't warn about this. */
9128 int save_warn_missing_braces = warn_missing_braces;
9129 warn_missing_braces = 0;
9131 /* A missing @end may not be detected by the parser. */
9132 if (objc_implementation_context)
9134 warning (0, "%<@end%> missing in implementation context");
9135 finish_class (objc_implementation_context);
9136 objc_ivar_chain = NULL_TREE;
9137 objc_implementation_context = NULL_TREE;
9140 /* Process the static instances here because initialization of objc_symtab
9142 if (objc_static_instances)
9143 generate_static_references ();
9145 if (imp_list || class_names_chain
9146 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9147 generate_objc_symtab_decl ();
9149 for (impent = imp_list; impent; impent = impent->next)
9151 objc_implementation_context = impent->imp_context;
9152 implementation_template = impent->imp_template;
9154 UOBJC_CLASS_decl = impent->class_decl;
9155 UOBJC_METACLASS_decl = impent->meta_decl;
9157 /* Dump the @interface of each class as we compile it, if the
9158 -gen-decls option is in use. TODO: Dump the classes in the
9159 order they were found, rather than in reverse order as we
9161 if (flag_gen_declaration)
9163 dump_interface (gen_declaration_file, objc_implementation_context);
9166 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
9168 /* all of the following reference the string pool... */
9169 generate_ivar_lists ();
9170 generate_dispatch_tables ();
9171 generate_shared_structures (impent->has_cxx_cdtors
9172 ? CLS_HAS_CXX_STRUCTORS
9177 generate_dispatch_tables ();
9178 generate_category (objc_implementation_context);
9182 /* If we are using an array of selectors, we must always
9183 finish up the array decl even if no selectors were used. */
9184 if (! flag_next_runtime || sel_ref_chain)
9185 build_selector_translation_table ();
9188 generate_protocols ();
9190 if ((flag_replace_objc_classes && imp_list) || flag_objc_gc)
9191 generate_objc_image_info ();
9193 /* Arrange for ObjC data structures to be initialized at run time. */
9194 if (objc_implementation_context || class_names_chain || objc_static_instances
9195 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9197 build_module_descriptor ();
9199 if (!flag_next_runtime)
9200 build_module_initializer_routine ();
9203 /* Dump the class references. This forces the appropriate classes
9204 to be linked into the executable image, preserving unix archive
9205 semantics. This can be removed when we move to a more dynamically
9206 linked environment. */
9208 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
9210 handle_class_ref (chain);
9211 if (TREE_PURPOSE (chain))
9212 generate_classref_translation_entry (chain);
9215 for (impent = imp_list; impent; impent = impent->next)
9216 handle_impent (impent);
9223 /* Run through the selector hash tables and print a warning for any
9224 selector which has multiple methods. */
9226 for (slot = 0; slot < SIZEHASHTABLE; slot++)
9228 for (hsh = cls_method_hash_list[slot]; hsh; hsh = hsh->next)
9229 check_duplicates (hsh, 0, 1);
9230 for (hsh = nst_method_hash_list[slot]; hsh; hsh = hsh->next)
9231 check_duplicates (hsh, 0, 1);
9235 warn_missing_braces = save_warn_missing_braces;
9238 /* Subroutines of finish_objc. */
9241 generate_classref_translation_entry (tree chain)
9243 tree expr, decl, type;
9245 decl = TREE_PURPOSE (chain);
9246 type = TREE_TYPE (decl);
9248 expr = add_objc_string (TREE_VALUE (chain), class_names);
9249 expr = convert (type, expr); /* cast! */
9251 /* The decl that is the one that we
9252 forward declared in build_class_reference. */
9253 finish_var_decl (decl, expr);
9258 handle_class_ref (tree chain)
9260 const char *name = IDENTIFIER_POINTER (TREE_VALUE (chain));
9261 char *string = (char *) alloca (strlen (name) + 30);
9265 sprintf (string, "%sobjc_class_name_%s",
9266 (flag_next_runtime ? "." : "__"), name);
9268 #ifdef ASM_DECLARE_UNRESOLVED_REFERENCE
9269 if (flag_next_runtime)
9271 ASM_DECLARE_UNRESOLVED_REFERENCE (asm_out_file, string);
9276 /* Make a decl for this name, so we can use its address in a tree. */
9277 decl = build_decl (VAR_DECL, get_identifier (string), char_type_node);
9278 DECL_EXTERNAL (decl) = 1;
9279 TREE_PUBLIC (decl) = 1;
9282 rest_of_decl_compilation (decl, 0, 0);
9284 /* Make a decl for the address. */
9285 sprintf (string, "%sobjc_class_ref_%s",
9286 (flag_next_runtime ? "." : "__"), name);
9287 exp = build1 (ADDR_EXPR, string_type_node, decl);
9288 decl = build_decl (VAR_DECL, get_identifier (string), string_type_node);
9289 DECL_INITIAL (decl) = exp;
9290 TREE_STATIC (decl) = 1;
9291 TREE_USED (decl) = 1;
9292 /* Force the output of the decl as this forces the reference of the class. */
9293 mark_decl_referenced (decl);
9296 rest_of_decl_compilation (decl, 0, 0);
9300 handle_impent (struct imp_entry *impent)
9304 objc_implementation_context = impent->imp_context;
9305 implementation_template = impent->imp_template;
9307 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
9309 const char *const class_name =
9310 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9312 string = (char *) alloca (strlen (class_name) + 30);
9314 sprintf (string, "%sobjc_class_name_%s",
9315 (flag_next_runtime ? "." : "__"), class_name);
9317 else if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
9319 const char *const class_name =
9320 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9321 const char *const class_super_name =
9322 IDENTIFIER_POINTER (CLASS_SUPER_NAME (impent->imp_context));
9324 string = (char *) alloca (strlen (class_name)
9325 + strlen (class_super_name) + 30);
9327 /* Do the same for categories. Even though no references to
9328 these symbols are generated automatically by the compiler, it
9329 gives you a handle to pull them into an archive by hand. */
9330 sprintf (string, "*%sobjc_category_name_%s_%s",
9331 (flag_next_runtime ? "." : "__"), class_name, class_super_name);
9336 #ifdef ASM_DECLARE_CLASS_REFERENCE
9337 if (flag_next_runtime)
9339 ASM_DECLARE_CLASS_REFERENCE (asm_out_file, string);
9347 init = build_int_cst (c_common_type_for_size (BITS_PER_WORD, 1), 0);
9348 decl = build_decl (VAR_DECL, get_identifier (string), TREE_TYPE (init));
9349 TREE_PUBLIC (decl) = 1;
9350 TREE_READONLY (decl) = 1;
9351 TREE_USED (decl) = 1;
9352 TREE_CONSTANT (decl) = 1;
9353 DECL_CONTEXT (decl) = 0;
9354 DECL_ARTIFICIAL (decl) = 1;
9355 DECL_INITIAL (decl) = init;
9356 assemble_variable (decl, 1, 0, 0);
9360 /* The Fix-and-Continue functionality available in Mac OS X 10.3 and
9361 later requires that ObjC translation units participating in F&C be
9362 specially marked. The following routine accomplishes this. */
9364 /* static int _OBJC_IMAGE_INFO[2] = { 0, 1 }; */
9367 generate_objc_image_info (void)
9369 tree decl, initlist;
9371 = ((flag_replace_objc_classes && imp_list ? 1 : 0)
9372 | (flag_objc_gc ? 2 : 0));
9374 decl = start_var_decl (build_array_type
9376 build_index_type (build_int_cst (NULL_TREE, 2 - 1))),
9377 "_OBJC_IMAGE_INFO");
9379 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, 0));
9380 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, flags), initlist);
9381 initlist = objc_build_constructor (TREE_TYPE (decl), nreverse (initlist));
9383 finish_var_decl (decl, initlist);
9386 /* Look up ID as an instance variable. OTHER contains the result of
9387 the C or C++ lookup, which we may want to use instead. */
9390 objc_lookup_ivar (tree other, tree id)
9394 /* If we are not inside of an ObjC method, ivar lookup makes no sense. */
9395 if (!objc_method_context)
9398 if (!strcmp (IDENTIFIER_POINTER (id), "super"))
9399 /* We have a message to super. */
9400 return get_super_receiver ();
9402 /* In a class method, look up an instance variable only as a last
9404 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
9405 && other && other != error_mark_node)
9408 /* Look up the ivar, but do not use it if it is not accessible. */
9409 ivar = is_ivar (objc_ivar_chain, id);
9411 if (!ivar || is_private (ivar))
9414 /* In an instance method, a local variable (or parameter) may hide the
9415 instance variable. */
9416 if (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9417 && other && other != error_mark_node
9419 && CP_DECL_CONTEXT (other) != global_namespace)
9421 && !DECL_FILE_SCOPE_P (other))
9424 warning (0, "local declaration of %qs hides instance variable",
9425 IDENTIFIER_POINTER (id));
9430 /* At this point, we are either in an instance method with no obscuring
9431 local definitions, or in a class method with no alternate definitions
9433 return build_ivar_reference (id);
9436 /* Possibly rewrite a function CALL into an OBJ_TYPE_REF expression. This
9437 needs to be done if we are calling a function through a cast. */
9440 objc_rewrite_function_call (tree function, tree params)
9442 if (TREE_CODE (function) == NOP_EXPR
9443 && TREE_CODE (TREE_OPERAND (function, 0)) == ADDR_EXPR
9444 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (function, 0), 0))
9447 function = build3 (OBJ_TYPE_REF, TREE_TYPE (function),
9448 TREE_OPERAND (function, 0),
9449 TREE_VALUE (params), size_zero_node);
9455 /* Look for the special case of OBJC_TYPE_REF with the address of
9456 a function in OBJ_TYPE_REF_EXPR (presumably objc_msgSend or one
9459 enum gimplify_status
9460 objc_gimplify_expr (tree *expr_p, tree *pre_p, tree *post_p)
9462 enum gimplify_status r0, r1;
9463 if (TREE_CODE (*expr_p) == OBJ_TYPE_REF
9464 && TREE_CODE (OBJ_TYPE_REF_EXPR (*expr_p)) == ADDR_EXPR
9465 && TREE_CODE (TREE_OPERAND (OBJ_TYPE_REF_EXPR (*expr_p), 0))
9468 /* Postincrements in OBJ_TYPE_REF_OBJECT don't affect the
9469 value of the OBJ_TYPE_REF, so force them to be emitted
9470 during subexpression evaluation rather than after the
9471 OBJ_TYPE_REF. This permits objc_msgSend calls in Objective
9472 C to use direct rather than indirect calls when the
9473 object expression has a postincrement. */
9474 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p, NULL,
9475 is_gimple_val, fb_rvalue);
9476 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p, post_p,
9477 is_gimple_val, fb_rvalue);
9479 return MIN (r0, r1);
9483 return cp_gimplify_expr (expr_p, pre_p, post_p);
9485 return c_gimplify_expr (expr_p, pre_p, post_p);
9489 /* Given a CALL expression, find the function being called. The ObjC
9490 version looks for the OBJ_TYPE_REF_EXPR which is used for objc_msgSend. */
9493 objc_get_callee_fndecl (tree call_expr)
9495 tree addr = TREE_OPERAND (call_expr, 0);
9496 if (TREE_CODE (addr) != OBJ_TYPE_REF)
9499 addr = OBJ_TYPE_REF_EXPR (addr);
9501 /* If the address is just `&f' for some function `f', then we know
9502 that `f' is being called. */
9503 if (TREE_CODE (addr) == ADDR_EXPR
9504 && TREE_CODE (TREE_OPERAND (addr, 0)) == FUNCTION_DECL)
9505 return TREE_OPERAND (addr, 0);
9510 #include "gt-objc-objc-act.h"