1 /* Implement classes and message passing for Objective C.
2 Copyright (C) 1992, 1993, 1994, 1995, 1997, 1998, 1999, 2000, 2001,
3 2002, 2003, 2004, 2005, 2007, 2008, 2009 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 3, 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 COPYING3. If not see
20 <http://www.gnu.org/licenses/>. */
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"
61 #include "langhooks.h"
72 #include "diagnostic.h"
75 #include "tree-iterator.h"
78 #include "langhooks-def.h"
80 #define OBJC_VOID_AT_END void_list_node
82 static unsigned int should_call_super_dealloc = 0;
84 /* When building Objective-C++, we need in_late_binary_op. */
86 bool in_late_binary_op = false;
89 /* When building Objective-C++, we are not linking against the C front-end
90 and so need to replicate the C tree-construction functions in some way. */
92 #define OBJCP_REMAP_FUNCTIONS
93 #include "objcp-decl.h"
96 /* This is the default way of generating a method name. */
97 /* I am not sure it is really correct.
98 Perhaps there's a danger that it will make name conflicts
99 if method names contain underscores. -- rms. */
100 #ifndef OBJC_GEN_METHOD_LABEL
101 #define OBJC_GEN_METHOD_LABEL(BUF, IS_INST, CLASS_NAME, CAT_NAME, SEL_NAME, NUM) \
104 sprintf ((BUF), "_%s_%s_%s_%s", \
105 ((IS_INST) ? "i" : "c"), \
107 ((CAT_NAME)? (CAT_NAME) : ""), \
109 for (temp = (BUF); *temp; temp++) \
110 if (*temp == ':') *temp = '_'; \
114 /* These need specifying. */
115 #ifndef OBJC_FORWARDING_STACK_OFFSET
116 #define OBJC_FORWARDING_STACK_OFFSET 0
119 #ifndef OBJC_FORWARDING_MIN_OFFSET
120 #define OBJC_FORWARDING_MIN_OFFSET 0
123 /* Set up for use of obstacks. */
127 /* This obstack is used to accumulate the encoding of a data type. */
128 static struct obstack util_obstack;
130 /* This points to the beginning of obstack contents, so we can free
131 the whole contents. */
134 /* The version identifies which language generation and runtime
135 the module (file) was compiled for, and is recorded in the
136 module descriptor. */
138 #define OBJC_VERSION (flag_next_runtime ? 6 : 8)
139 #define PROTOCOL_VERSION 2
141 /* (Decide if these can ever be validly changed.) */
142 #define OBJC_ENCODE_INLINE_DEFS 0
143 #define OBJC_ENCODE_DONT_INLINE_DEFS 1
145 /*** Private Interface (procedures) ***/
147 /* Used by compile_file. */
149 static void init_objc (void);
150 static void finish_objc (void);
152 /* Code generation. */
154 static tree objc_build_constructor (tree, tree);
155 static tree build_objc_method_call (location_t, int, tree, tree, tree, tree);
156 static tree get_proto_encoding (tree);
157 static tree lookup_interface (tree);
158 static tree objc_add_static_instance (tree, tree);
160 static tree start_class (enum tree_code, tree, tree, tree);
161 static tree continue_class (tree);
162 static void finish_class (tree);
163 static void start_method_def (tree);
165 static void objc_start_function (tree, tree, tree, tree);
167 static void objc_start_function (tree, tree, tree, struct c_arg_info *);
169 static tree start_protocol (enum tree_code, tree, tree);
170 static tree build_method_decl (enum tree_code, tree, tree, tree, bool);
171 static tree objc_add_method (tree, tree, int);
172 static tree add_instance_variable (tree, int, tree);
173 static tree build_ivar_reference (tree);
174 static tree is_ivar (tree, tree);
176 static void build_objc_exception_stuff (void);
177 static void build_next_objc_exception_stuff (void);
179 /* We only need the following for ObjC; ObjC++ will use C++'s definition
180 of DERIVED_FROM_P. */
182 static bool objc_derived_from_p (tree, tree);
183 #define DERIVED_FROM_P(PARENT, CHILD) objc_derived_from_p (PARENT, CHILD)
185 static void objc_xref_basetypes (tree, tree);
187 static void build_class_template (void);
188 static void build_selector_template (void);
189 static void build_category_template (void);
190 static void build_super_template (void);
191 static tree build_protocol_initializer (tree, tree, tree, tree, tree);
192 static tree get_class_ivars (tree, bool);
193 static tree generate_protocol_list (tree);
194 static void build_protocol_reference (tree);
197 static void objc_generate_cxx_cdtors (void);
200 static const char *synth_id_with_class_suffix (const char *, tree);
202 /* Hash tables to manage the global pool of method prototypes. */
204 hash *nst_method_hash_list = 0;
205 hash *cls_method_hash_list = 0;
207 static hash hash_lookup (hash *, tree);
208 static tree lookup_method (tree, tree);
209 static tree lookup_method_static (tree, tree, int);
213 class_names, /* class, category, protocol, module names */
214 meth_var_names, /* method and variable names */
215 meth_var_types /* method and variable type descriptors */
218 static tree add_objc_string (tree, enum string_section);
219 static tree build_objc_string_decl (enum string_section);
220 static void build_selector_table_decl (void);
222 /* Protocol additions. */
224 static tree lookup_protocol (tree);
225 static tree lookup_and_install_protocols (tree);
229 static void encode_type_qualifiers (tree);
230 static void encode_type (tree, int, int);
231 static void encode_field_decl (tree, int, int);
234 static void really_start_method (tree, tree);
236 static void really_start_method (tree, struct c_arg_info *);
238 static int comp_proto_with_proto (tree, tree, int);
239 static void objc_push_parm (tree);
241 static tree objc_get_parm_info (int);
243 static struct c_arg_info *objc_get_parm_info (int);
246 /* Utilities for debugging and error diagnostics. */
248 static char *gen_type_name (tree);
249 static char *gen_type_name_0 (tree);
250 static char *gen_method_decl (tree);
251 static char *gen_declaration (tree);
253 /* Everything else. */
255 static tree create_field_decl (tree, const char *);
256 static void add_class_reference (tree);
257 static void build_protocol_template (void);
258 static tree encode_method_prototype (tree);
259 static void generate_classref_translation_entry (tree);
260 static void handle_class_ref (tree);
261 static void generate_struct_by_value_array (void)
263 static void mark_referenced_methods (void);
264 static void generate_objc_image_info (void);
266 /*** Private Interface (data) ***/
268 /* Reserved tag definitions. */
270 #define OBJECT_TYPEDEF_NAME "id"
271 #define CLASS_TYPEDEF_NAME "Class"
273 #define TAG_OBJECT "objc_object"
274 #define TAG_CLASS "objc_class"
275 #define TAG_SUPER "objc_super"
276 #define TAG_SELECTOR "objc_selector"
278 #define UTAG_CLASS "_objc_class"
279 #define UTAG_IVAR "_objc_ivar"
280 #define UTAG_IVAR_LIST "_objc_ivar_list"
281 #define UTAG_METHOD "_objc_method"
282 #define UTAG_METHOD_LIST "_objc_method_list"
283 #define UTAG_CATEGORY "_objc_category"
284 #define UTAG_MODULE "_objc_module"
285 #define UTAG_SYMTAB "_objc_symtab"
286 #define UTAG_SUPER "_objc_super"
287 #define UTAG_SELECTOR "_objc_selector"
289 #define UTAG_PROTOCOL "_objc_protocol"
290 #define UTAG_METHOD_PROTOTYPE "_objc_method_prototype"
291 #define UTAG_METHOD_PROTOTYPE_LIST "_objc__method_prototype_list"
293 /* Note that the string object global name is only needed for the
295 #define STRING_OBJECT_GLOBAL_FORMAT "_%sClassReference"
297 #define PROTOCOL_OBJECT_CLASS_NAME "Protocol"
299 static const char *TAG_GETCLASS;
300 static const char *TAG_GETMETACLASS;
301 static const char *TAG_MSGSEND;
302 static const char *TAG_MSGSENDSUPER;
303 /* The NeXT Objective-C messenger may have two extra entry points, for use
304 when returning a structure. */
305 static const char *TAG_MSGSEND_STRET;
306 static const char *TAG_MSGSENDSUPER_STRET;
307 static const char *default_constant_string_class_name;
309 /* Runtime metadata flags. */
310 #define CLS_FACTORY 0x0001L
311 #define CLS_META 0x0002L
312 #define CLS_HAS_CXX_STRUCTORS 0x2000L
314 #define OBJC_MODIFIER_STATIC 0x00000001
315 #define OBJC_MODIFIER_FINAL 0x00000002
316 #define OBJC_MODIFIER_PUBLIC 0x00000004
317 #define OBJC_MODIFIER_PRIVATE 0x00000008
318 #define OBJC_MODIFIER_PROTECTED 0x00000010
319 #define OBJC_MODIFIER_NATIVE 0x00000020
320 #define OBJC_MODIFIER_SYNCHRONIZED 0x00000040
321 #define OBJC_MODIFIER_ABSTRACT 0x00000080
322 #define OBJC_MODIFIER_VOLATILE 0x00000100
323 #define OBJC_MODIFIER_TRANSIENT 0x00000200
324 #define OBJC_MODIFIER_NONE_SPECIFIED 0x80000000
326 /* NeXT-specific tags. */
328 #define TAG_MSGSEND_NONNIL "objc_msgSendNonNil"
329 #define TAG_MSGSEND_NONNIL_STRET "objc_msgSendNonNil_stret"
330 #define TAG_EXCEPTIONEXTRACT "objc_exception_extract"
331 #define TAG_EXCEPTIONTRYENTER "objc_exception_try_enter"
332 #define TAG_EXCEPTIONTRYEXIT "objc_exception_try_exit"
333 #define TAG_EXCEPTIONMATCH "objc_exception_match"
334 #define TAG_EXCEPTIONTHROW "objc_exception_throw"
335 #define TAG_SYNCENTER "objc_sync_enter"
336 #define TAG_SYNCEXIT "objc_sync_exit"
337 #define TAG_SETJMP "_setjmp"
338 #define UTAG_EXCDATA "_objc_exception_data"
340 #define TAG_ASSIGNIVAR "objc_assign_ivar"
341 #define TAG_ASSIGNGLOBAL "objc_assign_global"
342 #define TAG_ASSIGNSTRONGCAST "objc_assign_strongCast"
344 /* Branch entry points. All that matters here are the addresses;
345 functions with these names do not really exist in libobjc. */
347 #define TAG_MSGSEND_FAST "objc_msgSend_Fast"
348 #define TAG_ASSIGNIVAR_FAST "objc_assign_ivar_Fast"
350 #define TAG_CXX_CONSTRUCT ".cxx_construct"
351 #define TAG_CXX_DESTRUCT ".cxx_destruct"
353 /* GNU-specific tags. */
355 #define TAG_EXECCLASS "__objc_exec_class"
356 #define TAG_GNUINIT "__objc_gnu_init"
358 /* Flags for lookup_method_static(). */
359 #define OBJC_LOOKUP_CLASS 1 /* Look for class methods. */
360 #define OBJC_LOOKUP_NO_SUPER 2 /* Do not examine superclasses. */
362 /* The OCTI_... enumeration itself is in objc/objc-act.h. */
363 tree objc_global_trees[OCTI_MAX];
365 static void handle_impent (struct imp_entry *);
367 struct imp_entry *imp_list = 0;
368 int imp_count = 0; /* `@implementation' */
369 int cat_count = 0; /* `@category' */
371 enum tree_code objc_inherit_code;
372 int objc_public_flag;
374 /* Use to generate method labels. */
375 static int method_slot = 0;
379 static char *errbuf; /* Buffer for error diagnostics */
381 /* Data imported from tree.c. */
383 extern enum debug_info_type write_symbols;
385 /* Data imported from toplev.c. */
387 extern const char *dump_base_name;
389 static int flag_typed_selectors;
391 /* Store all constructed constant strings in a hash table so that
392 they get uniqued properly. */
394 struct GTY(()) string_descriptor {
395 /* The literal argument . */
398 /* The resulting constant string. */
402 static GTY((param_is (struct string_descriptor))) htab_t string_htab;
404 /* Store the EH-volatilized types in a hash table, for easy retrieval. */
405 struct GTY(()) volatilized_type {
409 static GTY((param_is (struct volatilized_type))) htab_t volatilized_htab;
411 FILE *gen_declaration_file;
413 /* Tells "encode_pointer/encode_aggregate" whether we are generating
414 type descriptors for instance variables (as opposed to methods).
415 Type descriptors for instance variables contain more information
416 than methods (for static typing and embedded structures). */
418 static int generating_instance_variables = 0;
420 /* For building an objc struct. These may not be used when this file
421 is compiled as part of obj-c++. */
423 static bool objc_building_struct;
424 static struct c_struct_parse_info *objc_struct_info ATTRIBUTE_UNUSED;
426 /* Start building a struct for objc. */
429 objc_start_struct (tree name)
431 gcc_assert (!objc_building_struct);
432 objc_building_struct = true;
433 return start_struct (input_location, RECORD_TYPE, name, &objc_struct_info);
436 /* Finish building a struct for objc. */
439 objc_finish_struct (tree type, tree fieldlist)
441 gcc_assert (objc_building_struct);
442 objc_building_struct = false;
443 return finish_struct (input_location, type, fieldlist, NULL_TREE,
447 /* Some platforms pass small structures through registers versus
448 through an invisible pointer. Determine at what size structure is
449 the transition point between the two possibilities. */
452 generate_struct_by_value_array (void)
455 tree field_decl, field_decl_chain;
457 int aggregate_in_mem[32];
460 /* Presumably no platform passes 32 byte structures in a register. */
461 for (i = 1; i < 32; i++)
465 /* Create an unnamed struct that has `i' character components */
466 type = objc_start_struct (NULL_TREE);
468 strcpy (buffer, "c1");
469 field_decl = create_field_decl (char_type_node,
471 field_decl_chain = field_decl;
473 for (j = 1; j < i; j++)
475 sprintf (buffer, "c%d", j + 1);
476 field_decl = create_field_decl (char_type_node,
478 chainon (field_decl_chain, field_decl);
480 objc_finish_struct (type, field_decl_chain);
482 aggregate_in_mem[i] = aggregate_value_p (type, 0);
483 if (!aggregate_in_mem[i])
487 /* We found some structures that are returned in registers instead of memory
488 so output the necessary data. */
491 for (i = 31; i >= 0; i--)
492 if (!aggregate_in_mem[i])
494 printf ("#define OBJC_MAX_STRUCT_BY_VALUE %d\n\n", i);
496 /* The first member of the structure is always 0 because we don't handle
497 structures with 0 members */
498 printf ("static int struct_forward_array[] = {\n 0");
500 for (j = 1; j <= i; j++)
501 printf (", %d", aggregate_in_mem[j]);
512 if (cxx_init () == false)
514 if (c_objc_common_init () == false)
518 /* If gen_declaration desired, open the output file. */
519 if (flag_gen_declaration)
521 register char * const dumpname = concat (dump_base_name, ".decl", NULL);
522 gen_declaration_file = fopen (dumpname, "w");
523 if (gen_declaration_file == 0)
524 fatal_error ("can't open %s: %m", dumpname);
528 if (flag_next_runtime)
530 TAG_GETCLASS = "objc_getClass";
531 TAG_GETMETACLASS = "objc_getMetaClass";
532 TAG_MSGSEND = "objc_msgSend";
533 TAG_MSGSENDSUPER = "objc_msgSendSuper";
534 TAG_MSGSEND_STRET = "objc_msgSend_stret";
535 TAG_MSGSENDSUPER_STRET = "objc_msgSendSuper_stret";
536 default_constant_string_class_name = "NSConstantString";
540 TAG_GETCLASS = "objc_get_class";
541 TAG_GETMETACLASS = "objc_get_meta_class";
542 TAG_MSGSEND = "objc_msg_lookup";
543 TAG_MSGSENDSUPER = "objc_msg_lookup_super";
544 /* GNU runtime does not provide special functions to support
545 structure-returning methods. */
546 default_constant_string_class_name = "NXConstantString";
547 flag_typed_selectors = 1;
552 if (print_struct_values && !flag_compare_debug)
553 generate_struct_by_value_array ();
559 objc_finish_file (void)
561 mark_referenced_methods ();
564 /* We need to instantiate templates _before_ we emit ObjC metadata;
565 if we do not, some metadata (such as selectors) may go missing. */
567 instantiate_pending_templates (0);
570 /* Finalize Objective-C runtime data. No need to generate tables
571 and code if only checking syntax, or if generating a PCH file. */
572 if (!flag_syntax_only && !pch_file)
575 if (gen_declaration_file)
576 fclose (gen_declaration_file);
579 /* Return the first occurrence of a method declaration corresponding
580 to sel_name in rproto_list. Search rproto_list recursively.
581 If is_class is 0, search for instance methods, otherwise for class
584 lookup_method_in_protocol_list (tree rproto_list, tree sel_name,
590 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
592 p = TREE_VALUE (rproto);
594 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
596 if ((fnd = lookup_method (is_class
597 ? PROTOCOL_CLS_METHODS (p)
598 : PROTOCOL_NST_METHODS (p), sel_name)))
600 else if (PROTOCOL_LIST (p))
601 fnd = lookup_method_in_protocol_list (PROTOCOL_LIST (p),
606 ; /* An identifier...if we could not find a protocol. */
617 lookup_protocol_in_reflist (tree rproto_list, tree lproto)
621 /* Make sure the protocol is supported by the object on the rhs. */
622 if (TREE_CODE (lproto) == PROTOCOL_INTERFACE_TYPE)
625 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
627 p = TREE_VALUE (rproto);
629 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
634 else if (PROTOCOL_LIST (p))
635 fnd = lookup_protocol_in_reflist (PROTOCOL_LIST (p), lproto);
644 ; /* An identifier...if we could not find a protocol. */
651 objc_start_class_interface (tree klass, tree super_class, tree protos)
653 objc_interface_context
655 = start_class (CLASS_INTERFACE_TYPE, klass, super_class, protos);
656 objc_public_flag = 0;
660 objc_start_category_interface (tree klass, tree categ, tree protos)
662 objc_interface_context
663 = start_class (CATEGORY_INTERFACE_TYPE, klass, categ, protos);
665 = continue_class (objc_interface_context);
669 objc_start_protocol (tree name, tree protos)
671 objc_interface_context
672 = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos);
676 objc_continue_interface (void)
679 = continue_class (objc_interface_context);
683 objc_finish_interface (void)
685 finish_class (objc_interface_context);
686 objc_interface_context = NULL_TREE;
690 objc_start_class_implementation (tree klass, tree super_class)
692 objc_implementation_context
694 = start_class (CLASS_IMPLEMENTATION_TYPE, klass, super_class, NULL_TREE);
695 objc_public_flag = 0;
699 objc_start_category_implementation (tree klass, tree categ)
701 objc_implementation_context
702 = start_class (CATEGORY_IMPLEMENTATION_TYPE, klass, categ, NULL_TREE);
704 = continue_class (objc_implementation_context);
708 objc_continue_implementation (void)
711 = continue_class (objc_implementation_context);
715 objc_finish_implementation (void)
718 if (flag_objc_call_cxx_cdtors)
719 objc_generate_cxx_cdtors ();
722 if (objc_implementation_context)
724 finish_class (objc_implementation_context);
725 objc_ivar_chain = NULL_TREE;
726 objc_implementation_context = NULL_TREE;
729 warning (0, "%<@end%> must appear in an @implementation context");
733 objc_set_visibility (int visibility)
735 objc_public_flag = visibility;
739 objc_set_method_type (enum tree_code type)
741 objc_inherit_code = (type == PLUS_EXPR
743 : INSTANCE_METHOD_DECL);
747 objc_build_method_signature (tree rettype, tree selector,
748 tree optparms, bool ellipsis)
750 return build_method_decl (objc_inherit_code, rettype, selector,
755 objc_add_method_declaration (tree decl)
757 if (!objc_interface_context)
758 fatal_error ("method declaration not in @interface context");
760 objc_add_method (objc_interface_context,
762 objc_inherit_code == CLASS_METHOD_DECL);
766 objc_start_method_definition (tree decl)
768 if (!objc_implementation_context)
769 fatal_error ("method definition not in @implementation context");
771 objc_add_method (objc_implementation_context,
773 objc_inherit_code == CLASS_METHOD_DECL);
774 start_method_def (decl);
778 objc_add_instance_variable (tree decl)
780 (void) add_instance_variable (objc_ivar_context,
785 /* Return 1 if IDENT is an ObjC/ObjC++ reserved keyword in the context of
789 objc_is_reserved_word (tree ident)
791 unsigned char code = C_RID_CODE (ident);
793 return (OBJC_IS_AT_KEYWORD (code)
794 || code == RID_CLASS || code == RID_PUBLIC
795 || code == RID_PROTECTED || code == RID_PRIVATE
796 || code == RID_TRY || code == RID_THROW || code == RID_CATCH);
799 /* Return true if TYPE is 'id'. */
802 objc_is_object_id (tree type)
804 return OBJC_TYPE_NAME (type) == objc_object_id;
808 objc_is_class_id (tree type)
810 return OBJC_TYPE_NAME (type) == objc_class_id;
813 /* Construct a C struct with same name as KLASS, a base struct with tag
814 SUPER_NAME (if any), and FIELDS indicated. */
817 objc_build_struct (tree klass, tree fields, tree super_name)
819 tree name = CLASS_NAME (klass);
820 tree s = objc_start_struct (name);
821 tree super = (super_name ? xref_tag (RECORD_TYPE, super_name) : NULL_TREE);
822 tree t, objc_info = NULL_TREE;
826 /* Prepend a packed variant of the base class into the layout. This
827 is necessary to preserve ObjC ABI compatibility. */
828 tree base = build_decl (input_location,
829 FIELD_DECL, NULL_TREE, super);
830 tree field = TYPE_FIELDS (super);
832 while (field && TREE_CHAIN (field)
833 && TREE_CODE (TREE_CHAIN (field)) == FIELD_DECL)
834 field = TREE_CHAIN (field);
836 /* For ObjC ABI purposes, the "packed" size of a base class is
837 the sum of the offset and the size (in bits) of the last field
840 = (field && TREE_CODE (field) == FIELD_DECL
841 ? size_binop (PLUS_EXPR,
842 size_binop (PLUS_EXPR,
845 convert (bitsizetype,
846 DECL_FIELD_OFFSET (field)),
847 bitsize_int (BITS_PER_UNIT)),
848 DECL_FIELD_BIT_OFFSET (field)),
850 : bitsize_zero_node);
851 DECL_SIZE_UNIT (base)
852 = size_binop (FLOOR_DIV_EXPR, convert (sizetype, DECL_SIZE (base)),
853 size_int (BITS_PER_UNIT));
854 DECL_ARTIFICIAL (base) = 1;
855 DECL_ALIGN (base) = 1;
856 DECL_FIELD_CONTEXT (base) = s;
858 DECL_FIELD_IS_BASE (base) = 1;
861 TREE_NO_WARNING (fields) = 1; /* Suppress C++ ABI warnings -- we */
862 #endif /* are following the ObjC ABI here. */
863 TREE_CHAIN (base) = fields;
867 /* NB: Calling finish_struct() may cause type TYPE_LANG_SPECIFIC fields
868 in all variants of this RECORD_TYPE to be clobbered, but it is therein
869 that we store protocol conformance info (e.g., 'NSObject <MyProtocol>').
870 Hence, we must squirrel away the ObjC-specific information before calling
871 finish_struct(), and then reinstate it afterwards. */
873 for (t = TYPE_NEXT_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t))
875 = chainon (objc_info,
876 build_tree_list (NULL_TREE, TYPE_OBJC_INFO (t)));
878 /* Point the struct at its related Objective-C class. */
879 INIT_TYPE_OBJC_INFO (s);
880 TYPE_OBJC_INTERFACE (s) = klass;
882 s = objc_finish_struct (s, fields);
884 for (t = TYPE_NEXT_VARIANT (s); t;
885 t = TYPE_NEXT_VARIANT (t), objc_info = TREE_CHAIN (objc_info))
887 TYPE_OBJC_INFO (t) = TREE_VALUE (objc_info);
888 /* Replace the IDENTIFIER_NODE with an actual @interface. */
889 TYPE_OBJC_INTERFACE (t) = klass;
892 /* Use TYPE_BINFO structures to point at the super class, if any. */
893 objc_xref_basetypes (s, super);
895 /* Mark this struct as a class template. */
896 CLASS_STATIC_TEMPLATE (klass) = s;
901 /* Build a type differing from TYPE only in that TYPE_VOLATILE is set.
902 Unlike tree.c:build_qualified_type(), preserve TYPE_LANG_SPECIFIC in the
905 objc_build_volatilized_type (tree type)
909 /* Check if we have not constructed the desired variant already. */
910 for (t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
912 /* The type qualifiers must (obviously) match up. */
913 if (!TYPE_VOLATILE (t)
914 || (TYPE_READONLY (t) != TYPE_READONLY (type))
915 || (TYPE_RESTRICT (t) != TYPE_RESTRICT (type)))
918 /* For pointer types, the pointees (and hence their TYPE_LANG_SPECIFIC
919 info, if any) must match up. */
920 if (POINTER_TYPE_P (t)
921 && (TREE_TYPE (t) != TREE_TYPE (type)))
924 /* Everything matches up! */
928 /* Ok, we could not re-use any of the pre-existing variants. Create
930 t = build_variant_type_copy (type);
931 TYPE_VOLATILE (t) = 1;
933 /* Set up the canonical type information. */
934 if (TYPE_STRUCTURAL_EQUALITY_P (type))
935 SET_TYPE_STRUCTURAL_EQUALITY (t);
936 else if (TYPE_CANONICAL (type) != type)
937 TYPE_CANONICAL (t) = objc_build_volatilized_type (TYPE_CANONICAL (type));
939 TYPE_CANONICAL (t) = t;
944 /* Mark DECL as being 'volatile' for purposes of Darwin
945 _setjmp()/_longjmp() exception handling. Called from
946 objc_mark_locals_volatile(). */
948 objc_volatilize_decl (tree decl)
950 /* Do not mess with variables that are 'static' or (already)
952 if (!TREE_THIS_VOLATILE (decl) && !TREE_STATIC (decl)
953 && (TREE_CODE (decl) == VAR_DECL
954 || TREE_CODE (decl) == PARM_DECL))
956 tree t = TREE_TYPE (decl);
957 struct volatilized_type key;
960 t = objc_build_volatilized_type (t);
962 loc = htab_find_slot (volatilized_htab, &key, INSERT);
966 *loc = ggc_alloc (sizeof (key));
967 ((struct volatilized_type *) *loc)->type = t;
970 TREE_TYPE (decl) = t;
971 TREE_THIS_VOLATILE (decl) = 1;
972 TREE_SIDE_EFFECTS (decl) = 1;
973 DECL_REGISTER (decl) = 0;
975 C_DECL_REGISTER (decl) = 0;
980 /* Check if protocol PROTO is adopted (directly or indirectly) by class CLS
981 (including its categories and superclasses) or by object type TYP.
982 Issue a warning if PROTO is not adopted anywhere and WARN is set. */
985 objc_lookup_protocol (tree proto, tree cls, tree typ, bool warn)
987 bool class_type = (cls != NULL_TREE);
993 /* Check protocols adopted by the class and its categories. */
994 for (c = cls; c; c = CLASS_CATEGORY_LIST (c))
996 if (lookup_protocol_in_reflist (CLASS_PROTOCOL_LIST (c), proto))
1000 /* Repeat for superclasses. */
1001 cls = lookup_interface (CLASS_SUPER_NAME (cls));
1004 /* Check for any protocols attached directly to the object type. */
1005 if (TYPE_HAS_OBJC_INFO (typ))
1007 if (lookup_protocol_in_reflist (TYPE_OBJC_PROTOCOL_LIST (typ), proto))
1014 gen_type_name_0 (class_type ? typ : TYPE_POINTER_TO (typ));
1015 /* NB: Types 'id' and 'Class' cannot reasonably be described as
1016 "implementing" a given protocol, since they do not have an
1019 warning (0, "class %qs does not implement the %qE protocol",
1020 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
1022 warning (0, "type %qs does not conform to the %qE protocol",
1023 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
1029 /* Check if class RCLS and instance struct type RTYP conform to at least the
1030 same protocols that LCLS and LTYP conform to. */
1033 objc_compare_protocols (tree lcls, tree ltyp, tree rcls, tree rtyp, bool warn)
1036 bool have_lproto = false;
1040 /* NB: We do _not_ look at categories defined for LCLS; these may or
1041 may not get loaded in, and therefore it is unreasonable to require
1042 that RCLS/RTYP must implement any of their protocols. */
1043 for (p = CLASS_PROTOCOL_LIST (lcls); p; p = TREE_CHAIN (p))
1047 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1051 /* Repeat for superclasses. */
1052 lcls = lookup_interface (CLASS_SUPER_NAME (lcls));
1055 /* Check for any protocols attached directly to the object type. */
1056 if (TYPE_HAS_OBJC_INFO (ltyp))
1058 for (p = TYPE_OBJC_PROTOCOL_LIST (ltyp); p; p = TREE_CHAIN (p))
1062 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
1067 /* NB: If LTYP and LCLS have no protocols to search for, return 'true'
1068 vacuously, _unless_ RTYP is a protocol-qualified 'id'. We can get
1069 away with simply checking for 'id' or 'Class' (!RCLS), since this
1070 routine will not get called in other cases. */
1071 return have_lproto || (rcls != NULL_TREE);
1074 /* Determine if it is permissible to assign (if ARGNO is greater than -3)
1075 an instance of RTYP to an instance of LTYP or to compare the two
1076 (if ARGNO is equal to -3), per ObjC type system rules. Before
1077 returning 'true', this routine may issue warnings related to, e.g.,
1078 protocol conformance. When returning 'false', the routine must
1079 produce absolutely no warnings; the C or C++ front-end will do so
1080 instead, if needed. If either LTYP or RTYP is not an Objective-C type,
1081 the routine must return 'false'.
1083 The ARGNO parameter is encoded as follows:
1084 >= 1 Parameter number (CALLEE contains function being called);
1088 -3 Comparison (LTYP and RTYP may match in either direction). */
1091 objc_compare_types (tree ltyp, tree rtyp, int argno, tree callee)
1093 tree lcls, rcls, lproto, rproto;
1094 bool pointers_compatible;
1096 /* We must be dealing with pointer types */
1097 if (!POINTER_TYPE_P (ltyp) || !POINTER_TYPE_P (rtyp))
1102 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
1103 rtyp = TREE_TYPE (rtyp);
1105 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
1107 /* Past this point, we are only interested in ObjC class instances,
1108 or 'id' or 'Class'. */
1109 if (TREE_CODE (ltyp) != RECORD_TYPE || TREE_CODE (rtyp) != RECORD_TYPE)
1112 if (!objc_is_object_id (ltyp) && !objc_is_class_id (ltyp)
1113 && !TYPE_HAS_OBJC_INFO (ltyp))
1116 if (!objc_is_object_id (rtyp) && !objc_is_class_id (rtyp)
1117 && !TYPE_HAS_OBJC_INFO (rtyp))
1120 /* Past this point, we are committed to returning 'true' to the caller.
1121 However, we can still warn about type and/or protocol mismatches. */
1123 if (TYPE_HAS_OBJC_INFO (ltyp))
1125 lcls = TYPE_OBJC_INTERFACE (ltyp);
1126 lproto = TYPE_OBJC_PROTOCOL_LIST (ltyp);
1129 lcls = lproto = NULL_TREE;
1131 if (TYPE_HAS_OBJC_INFO (rtyp))
1133 rcls = TYPE_OBJC_INTERFACE (rtyp);
1134 rproto = TYPE_OBJC_PROTOCOL_LIST (rtyp);
1137 rcls = rproto = NULL_TREE;
1139 /* If we could not find an @interface declaration, we must have
1140 only seen a @class declaration; for purposes of type comparison,
1141 treat it as a stand-alone (root) class. */
1143 if (lcls && TREE_CODE (lcls) == IDENTIFIER_NODE)
1146 if (rcls && TREE_CODE (rcls) == IDENTIFIER_NODE)
1149 /* If either type is an unqualified 'id', we're done. */
1150 if ((!lproto && objc_is_object_id (ltyp))
1151 || (!rproto && objc_is_object_id (rtyp)))
1154 pointers_compatible = (TYPE_MAIN_VARIANT (ltyp) == TYPE_MAIN_VARIANT (rtyp));
1156 /* If the underlying types are the same, and at most one of them has
1157 a protocol list, we do not need to issue any diagnostics. */
1158 if (pointers_compatible && (!lproto || !rproto))
1161 /* If exactly one of the types is 'Class', issue a diagnostic; any
1162 exceptions of this rule have already been handled. */
1163 if (objc_is_class_id (ltyp) ^ objc_is_class_id (rtyp))
1164 pointers_compatible = false;
1165 /* Otherwise, check for inheritance relations. */
1168 if (!pointers_compatible)
1170 = (objc_is_object_id (ltyp) || objc_is_object_id (rtyp));
1172 if (!pointers_compatible)
1173 pointers_compatible = DERIVED_FROM_P (ltyp, rtyp);
1175 if (!pointers_compatible && argno == -3)
1176 pointers_compatible = DERIVED_FROM_P (rtyp, ltyp);
1179 /* If the pointers match modulo protocols, check for protocol conformance
1181 if (pointers_compatible)
1183 pointers_compatible = objc_compare_protocols (lcls, ltyp, rcls, rtyp,
1186 if (!pointers_compatible && argno == -3)
1187 pointers_compatible = objc_compare_protocols (rcls, rtyp, lcls, ltyp,
1191 if (!pointers_compatible)
1193 /* NB: For the time being, we shall make our warnings look like their
1194 C counterparts. In the future, we may wish to make them more
1199 warning (0, "comparison of distinct Objective-C types lacks a cast");
1203 warning (0, "initialization from distinct Objective-C type");
1207 warning (0, "assignment from distinct Objective-C type");
1211 warning (0, "distinct Objective-C type in return");
1215 warning (0, "passing argument %d of %qE from distinct "
1216 "Objective-C type", argno, callee);
1224 /* Check if LTYP and RTYP have the same type qualifiers. If either type
1225 lives in the volatilized hash table, ignore the 'volatile' bit when
1226 making the comparison. */
1229 objc_type_quals_match (tree ltyp, tree rtyp)
1231 int lquals = TYPE_QUALS (ltyp), rquals = TYPE_QUALS (rtyp);
1232 struct volatilized_type key;
1236 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1237 lquals &= ~TYPE_QUAL_VOLATILE;
1241 if (htab_find_slot (volatilized_htab, &key, NO_INSERT))
1242 rquals &= ~TYPE_QUAL_VOLATILE;
1244 return (lquals == rquals);
1248 /* Determine if CHILD is derived from PARENT. The routine assumes that
1249 both parameters are RECORD_TYPEs, and is non-reflexive. */
1252 objc_derived_from_p (tree parent, tree child)
1254 parent = TYPE_MAIN_VARIANT (parent);
1256 for (child = TYPE_MAIN_VARIANT (child);
1257 TYPE_BINFO (child) && BINFO_N_BASE_BINFOS (TYPE_BINFO (child));)
1259 child = TYPE_MAIN_VARIANT (BINFO_TYPE (BINFO_BASE_BINFO
1260 (TYPE_BINFO (child),
1263 if (child == parent)
1272 objc_build_component_ref (tree datum, tree component)
1274 /* If COMPONENT is NULL, the caller is referring to the anonymous
1275 base class field. */
1278 tree base = TYPE_FIELDS (TREE_TYPE (datum));
1280 return build3 (COMPONENT_REF, TREE_TYPE (base), datum, base, NULL_TREE);
1283 /* The 'build_component_ref' routine has been removed from the C++
1284 front-end, but 'finish_class_member_access_expr' seems to be
1285 a worthy substitute. */
1287 return finish_class_member_access_expr (datum, component, false,
1288 tf_warning_or_error);
1290 return build_component_ref (input_location, datum, component);
1294 /* Recursively copy inheritance information rooted at BINFO. To do this,
1295 we emulate the song and dance performed by cp/tree.c:copy_binfo(). */
1298 objc_copy_binfo (tree binfo)
1300 tree btype = BINFO_TYPE (binfo);
1301 tree binfo2 = make_tree_binfo (BINFO_N_BASE_BINFOS (binfo));
1305 BINFO_TYPE (binfo2) = btype;
1306 BINFO_OFFSET (binfo2) = BINFO_OFFSET (binfo);
1307 BINFO_BASE_ACCESSES (binfo2) = BINFO_BASE_ACCESSES (binfo);
1309 /* Recursively copy base binfos of BINFO. */
1310 for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
1312 tree base_binfo2 = objc_copy_binfo (base_binfo);
1314 BINFO_INHERITANCE_CHAIN (base_binfo2) = binfo2;
1315 BINFO_BASE_APPEND (binfo2, base_binfo2);
1321 /* Record superclass information provided in BASETYPE for ObjC class REF.
1322 This is loosely based on cp/decl.c:xref_basetypes(). */
1325 objc_xref_basetypes (tree ref, tree basetype)
1327 tree binfo = make_tree_binfo (basetype ? 1 : 0);
1329 TYPE_BINFO (ref) = binfo;
1330 BINFO_OFFSET (binfo) = size_zero_node;
1331 BINFO_TYPE (binfo) = ref;
1335 tree base_binfo = objc_copy_binfo (TYPE_BINFO (basetype));
1337 BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
1338 BINFO_BASE_ACCESSES (binfo) = VEC_alloc (tree, gc, 1);
1339 BINFO_BASE_APPEND (binfo, base_binfo);
1340 BINFO_BASE_ACCESS_APPEND (binfo, access_public_node);
1345 volatilized_hash (const void *ptr)
1347 const_tree const typ = ((const struct volatilized_type *)ptr)->type;
1349 return htab_hash_pointer(typ);
1353 volatilized_eq (const void *ptr1, const void *ptr2)
1355 const_tree const typ1 = ((const struct volatilized_type *)ptr1)->type;
1356 const_tree const typ2 = ((const struct volatilized_type *)ptr2)->type;
1358 return typ1 == typ2;
1361 /* Called from finish_decl. */
1364 objc_check_decl (tree decl)
1366 tree type = TREE_TYPE (decl);
1368 if (TREE_CODE (type) != RECORD_TYPE)
1370 if (OBJC_TYPE_NAME (type) && (type = objc_is_class_name (OBJC_TYPE_NAME (type))))
1371 error ("statically allocated instance of Objective-C class %qE",
1375 /* Construct a PROTOCOLS-qualified variant of INTERFACE, where INTERFACE may
1376 either name an Objective-C class, or refer to the special 'id' or 'Class'
1377 types. If INTERFACE is not a valid ObjC type, just return it unchanged. */
1380 objc_get_protocol_qualified_type (tree interface, tree protocols)
1382 /* If INTERFACE is not provided, default to 'id'. */
1383 tree type = (interface ? objc_is_id (interface) : objc_object_type);
1384 bool is_ptr = (type != NULL_TREE);
1388 type = objc_is_class_name (interface);
1391 type = xref_tag (RECORD_TYPE, type);
1398 type = build_variant_type_copy (type);
1400 /* For pointers (i.e., 'id' or 'Class'), attach the protocol(s)
1404 tree orig_pointee_type = TREE_TYPE (type);
1405 TREE_TYPE (type) = build_variant_type_copy (orig_pointee_type);
1407 /* Set up the canonical type information. */
1408 TYPE_CANONICAL (type)
1409 = TYPE_CANONICAL (TYPE_POINTER_TO (orig_pointee_type));
1411 TYPE_POINTER_TO (TREE_TYPE (type)) = type;
1412 type = TREE_TYPE (type);
1415 /* Look up protocols and install in lang specific list. */
1416 DUP_TYPE_OBJC_INFO (type, TYPE_MAIN_VARIANT (type));
1417 TYPE_OBJC_PROTOCOL_LIST (type) = lookup_and_install_protocols (protocols);
1419 /* For RECORD_TYPEs, point to the @interface; for 'id' and 'Class',
1420 return the pointer to the new pointee variant. */
1422 type = TYPE_POINTER_TO (type);
1424 TYPE_OBJC_INTERFACE (type)
1425 = TYPE_OBJC_INTERFACE (TYPE_MAIN_VARIANT (type));
1431 /* Check for circular dependencies in protocols. The arguments are
1432 PROTO, the protocol to check, and LIST, a list of protocol it
1436 check_protocol_recursively (tree proto, tree list)
1440 for (p = list; p; p = TREE_CHAIN (p))
1442 tree pp = TREE_VALUE (p);
1444 if (TREE_CODE (pp) == IDENTIFIER_NODE)
1445 pp = lookup_protocol (pp);
1448 fatal_error ("protocol %qE has circular dependency",
1449 PROTOCOL_NAME (pp));
1451 check_protocol_recursively (proto, PROTOCOL_LIST (pp));
1455 /* Look up PROTOCOLS, and return a list of those that are found.
1456 If none are found, return NULL. */
1459 lookup_and_install_protocols (tree protocols)
1462 tree return_value = NULL_TREE;
1464 for (proto = protocols; proto; proto = TREE_CHAIN (proto))
1466 tree ident = TREE_VALUE (proto);
1467 tree p = lookup_protocol (ident);
1470 return_value = chainon (return_value,
1471 build_tree_list (NULL_TREE, p));
1472 else if (ident != error_mark_node)
1473 error ("cannot find protocol declaration for %qE",
1477 return return_value;
1480 /* Create a declaration for field NAME of a given TYPE. */
1483 create_field_decl (tree type, const char *name)
1485 return build_decl (input_location,
1486 FIELD_DECL, get_identifier (name), type);
1489 /* Create a global, static declaration for variable NAME of a given TYPE. The
1490 finish_var_decl() routine will need to be called on it afterwards. */
1493 start_var_decl (tree type, const char *name)
1495 tree var = build_decl (input_location,
1496 VAR_DECL, get_identifier (name), type);
1498 TREE_STATIC (var) = 1;
1499 DECL_INITIAL (var) = error_mark_node; /* A real initializer is coming... */
1500 DECL_IGNORED_P (var) = 1;
1501 DECL_ARTIFICIAL (var) = 1;
1502 DECL_CONTEXT (var) = NULL_TREE;
1504 DECL_THIS_STATIC (var) = 1; /* squash redeclaration errors */
1510 /* Finish off the variable declaration created by start_var_decl(). */
1513 finish_var_decl (tree var, tree initializer)
1515 finish_decl (var, input_location, initializer, NULL_TREE, NULL_TREE);
1516 /* Ensure that the variable actually gets output. */
1517 mark_decl_referenced (var);
1518 /* Mark the decl to avoid "defined but not used" warning. */
1519 TREE_USED (var) = 1;
1522 /* Find the decl for the constant string class reference. This is only
1523 used for the NeXT runtime. */
1526 setup_string_decl (void)
1531 /* %s in format will provide room for terminating null */
1532 length = strlen (STRING_OBJECT_GLOBAL_FORMAT)
1533 + strlen (constant_string_class_name);
1534 name = XNEWVEC (char, length);
1535 sprintf (name, STRING_OBJECT_GLOBAL_FORMAT,
1536 constant_string_class_name);
1537 constant_string_global_id = get_identifier (name);
1538 string_class_decl = lookup_name (constant_string_global_id);
1540 return string_class_decl;
1543 /* Purpose: "play" parser, creating/installing representations
1544 of the declarations that are required by Objective-C.
1548 type_spec--------->sc_spec
1549 (tree_list) (tree_list)
1552 identifier_node identifier_node */
1555 synth_module_prologue (void)
1558 enum debug_info_type save_write_symbols = write_symbols;
1559 const struct gcc_debug_hooks *const save_hooks = debug_hooks;
1561 /* Suppress outputting debug symbols, because
1562 dbxout_init hasn't been called yet. */
1563 write_symbols = NO_DEBUG;
1564 debug_hooks = &do_nothing_debug_hooks;
1567 push_lang_context (lang_name_c); /* extern "C" */
1570 /* The following are also defined in <objc/objc.h> and friends. */
1572 objc_object_id = get_identifier (TAG_OBJECT);
1573 objc_class_id = get_identifier (TAG_CLASS);
1575 objc_object_reference = xref_tag (RECORD_TYPE, objc_object_id);
1576 objc_class_reference = xref_tag (RECORD_TYPE, objc_class_id);
1578 objc_object_type = build_pointer_type (objc_object_reference);
1579 objc_class_type = build_pointer_type (objc_class_reference);
1581 objc_object_name = get_identifier (OBJECT_TYPEDEF_NAME);
1582 objc_class_name = get_identifier (CLASS_TYPEDEF_NAME);
1584 /* Declare the 'id' and 'Class' typedefs. */
1586 type = lang_hooks.decls.pushdecl (build_decl (input_location,
1590 TREE_NO_WARNING (type) = 1;
1591 type = lang_hooks.decls.pushdecl (build_decl (input_location,
1595 TREE_NO_WARNING (type) = 1;
1597 /* Forward-declare '@interface Protocol'. */
1599 type = get_identifier (PROTOCOL_OBJECT_CLASS_NAME);
1600 objc_declare_class (tree_cons (NULL_TREE, type, NULL_TREE));
1601 objc_protocol_type = build_pointer_type (xref_tag (RECORD_TYPE,
1604 /* Declare type of selector-objects that represent an operation name. */
1606 if (flag_next_runtime)
1607 /* `struct objc_selector *' */
1609 = build_pointer_type (xref_tag (RECORD_TYPE,
1610 get_identifier (TAG_SELECTOR)));
1612 /* `const struct objc_selector *' */
1614 = build_pointer_type
1615 (build_qualified_type (xref_tag (RECORD_TYPE,
1616 get_identifier (TAG_SELECTOR)),
1619 /* Declare receiver type used for dispatching messages to 'super'. */
1621 /* `struct objc_super *' */
1622 objc_super_type = build_pointer_type (xref_tag (RECORD_TYPE,
1623 get_identifier (TAG_SUPER)));
1625 /* Declare pointers to method and ivar lists. */
1626 objc_method_list_ptr = build_pointer_type
1627 (xref_tag (RECORD_TYPE,
1628 get_identifier (UTAG_METHOD_LIST)));
1629 objc_method_proto_list_ptr
1630 = build_pointer_type (xref_tag (RECORD_TYPE,
1631 get_identifier (UTAG_METHOD_PROTOTYPE_LIST)));
1632 objc_ivar_list_ptr = build_pointer_type
1633 (xref_tag (RECORD_TYPE,
1634 get_identifier (UTAG_IVAR_LIST)));
1636 /* TREE_NOTHROW is cleared for the message-sending functions,
1637 because the function that gets called can throw in Obj-C++, or
1638 could itself call something that can throw even in Obj-C. */
1640 if (flag_next_runtime)
1642 /* NB: In order to call one of the ..._stret (struct-returning)
1643 functions, the function *MUST* first be cast to a signature that
1644 corresponds to the actual ObjC method being invoked. This is
1645 what is done by the build_objc_method_call() routine below. */
1647 /* id objc_msgSend (id, SEL, ...); */
1648 /* id objc_msgSendNonNil (id, SEL, ...); */
1649 /* id objc_msgSend_stret (id, SEL, ...); */
1650 /* id objc_msgSendNonNil_stret (id, SEL, ...); */
1652 = build_function_type (objc_object_type,
1653 tree_cons (NULL_TREE, objc_object_type,
1654 tree_cons (NULL_TREE, objc_selector_type,
1656 umsg_decl = add_builtin_function (TAG_MSGSEND,
1657 type, 0, NOT_BUILT_IN,
1659 umsg_nonnil_decl = add_builtin_function (TAG_MSGSEND_NONNIL,
1660 type, 0, NOT_BUILT_IN,
1662 umsg_stret_decl = add_builtin_function (TAG_MSGSEND_STRET,
1663 type, 0, NOT_BUILT_IN,
1665 umsg_nonnil_stret_decl = add_builtin_function (TAG_MSGSEND_NONNIL_STRET,
1666 type, 0, NOT_BUILT_IN,
1669 /* These can throw, because the function that gets called can throw
1670 in Obj-C++, or could itself call something that can throw even
1672 TREE_NOTHROW (umsg_decl) = 0;
1673 TREE_NOTHROW (umsg_nonnil_decl) = 0;
1674 TREE_NOTHROW (umsg_stret_decl) = 0;
1675 TREE_NOTHROW (umsg_nonnil_stret_decl) = 0;
1677 /* id objc_msgSend_Fast (id, SEL, ...)
1678 __attribute__ ((hard_coded_address (OFFS_MSGSEND_FAST))); */
1679 #ifdef OFFS_MSGSEND_FAST
1680 umsg_fast_decl = add_builtin_function (TAG_MSGSEND_FAST,
1681 type, 0, NOT_BUILT_IN,
1683 TREE_NOTHROW (umsg_fast_decl) = 0;
1684 DECL_ATTRIBUTES (umsg_fast_decl)
1685 = tree_cons (get_identifier ("hard_coded_address"),
1686 build_int_cst (NULL_TREE, OFFS_MSGSEND_FAST),
1689 /* No direct dispatch available. */
1690 umsg_fast_decl = umsg_decl;
1693 /* id objc_msgSendSuper (struct objc_super *, SEL, ...); */
1694 /* id objc_msgSendSuper_stret (struct objc_super *, SEL, ...); */
1696 = build_function_type (objc_object_type,
1697 tree_cons (NULL_TREE, objc_super_type,
1698 tree_cons (NULL_TREE, objc_selector_type,
1700 umsg_super_decl = add_builtin_function (TAG_MSGSENDSUPER,
1701 type, 0, NOT_BUILT_IN,
1703 umsg_super_stret_decl = add_builtin_function (TAG_MSGSENDSUPER_STRET,
1704 type, 0, NOT_BUILT_IN, 0,
1706 TREE_NOTHROW (umsg_super_decl) = 0;
1707 TREE_NOTHROW (umsg_super_stret_decl) = 0;
1711 /* GNU runtime messenger entry points. */
1713 /* typedef id (*IMP)(id, SEL, ...); */
1715 = build_pointer_type
1716 (build_function_type (objc_object_type,
1717 tree_cons (NULL_TREE, objc_object_type,
1718 tree_cons (NULL_TREE, objc_selector_type,
1721 /* IMP objc_msg_lookup (id, SEL); */
1723 = build_function_type (IMP_type,
1724 tree_cons (NULL_TREE, objc_object_type,
1725 tree_cons (NULL_TREE, objc_selector_type,
1726 OBJC_VOID_AT_END)));
1727 umsg_decl = add_builtin_function (TAG_MSGSEND,
1728 type, 0, NOT_BUILT_IN,
1730 TREE_NOTHROW (umsg_decl) = 0;
1732 /* IMP objc_msg_lookup_super (struct objc_super *, SEL); */
1734 = build_function_type (IMP_type,
1735 tree_cons (NULL_TREE, objc_super_type,
1736 tree_cons (NULL_TREE, objc_selector_type,
1737 OBJC_VOID_AT_END)));
1738 umsg_super_decl = add_builtin_function (TAG_MSGSENDSUPER,
1739 type, 0, NOT_BUILT_IN,
1741 TREE_NOTHROW (umsg_super_decl) = 0;
1743 /* The following GNU runtime entry point is called to initialize
1746 __objc_exec_class (void *); */
1748 = build_function_type (void_type_node,
1749 tree_cons (NULL_TREE, ptr_type_node,
1751 execclass_decl = add_builtin_function (TAG_EXECCLASS,
1752 type, 0, NOT_BUILT_IN,
1756 /* id objc_getClass (const char *); */
1758 type = build_function_type (objc_object_type,
1759 tree_cons (NULL_TREE,
1760 const_string_type_node,
1764 = add_builtin_function (TAG_GETCLASS, type, 0, NOT_BUILT_IN,
1767 /* id objc_getMetaClass (const char *); */
1769 objc_get_meta_class_decl
1770 = add_builtin_function (TAG_GETMETACLASS, type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
1772 build_class_template ();
1773 build_super_template ();
1774 build_protocol_template ();
1775 build_category_template ();
1776 build_objc_exception_stuff ();
1778 if (flag_next_runtime)
1779 build_next_objc_exception_stuff ();
1781 /* static SEL _OBJC_SELECTOR_TABLE[]; */
1783 if (! flag_next_runtime)
1784 build_selector_table_decl ();
1786 /* Forward declare constant_string_id and constant_string_type. */
1787 if (!constant_string_class_name)
1788 constant_string_class_name = default_constant_string_class_name;
1790 constant_string_id = get_identifier (constant_string_class_name);
1791 objc_declare_class (tree_cons (NULL_TREE, constant_string_id, NULL_TREE));
1793 /* Pre-build the following entities - for speed/convenience. */
1794 self_id = get_identifier ("self");
1795 ucmd_id = get_identifier ("_cmd");
1798 pop_lang_context ();
1801 write_symbols = save_write_symbols;
1802 debug_hooks = save_hooks;
1805 /* Ensure that the ivar list for NSConstantString/NXConstantString
1806 (or whatever was specified via `-fconstant-string-class')
1807 contains fields at least as large as the following three, so that
1808 the runtime can stomp on them with confidence:
1810 struct STRING_OBJECT_CLASS_NAME
1814 unsigned int length;
1818 check_string_class_template (void)
1820 tree field_decl = objc_get_class_ivars (constant_string_id);
1822 #define AT_LEAST_AS_LARGE_AS(F, T) \
1823 (F && TREE_CODE (F) == FIELD_DECL \
1824 && (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (F))) \
1825 >= TREE_INT_CST_LOW (TYPE_SIZE (T))))
1827 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
1830 field_decl = TREE_CHAIN (field_decl);
1831 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
1834 field_decl = TREE_CHAIN (field_decl);
1835 return AT_LEAST_AS_LARGE_AS (field_decl, unsigned_type_node);
1837 #undef AT_LEAST_AS_LARGE_AS
1840 /* Avoid calling `check_string_class_template ()' more than once. */
1841 static GTY(()) int string_layout_checked;
1843 /* Construct an internal string layout to be used as a template for
1844 creating NSConstantString/NXConstantString instances. */
1847 objc_build_internal_const_str_type (void)
1849 tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);
1850 tree fields = build_decl (input_location,
1851 FIELD_DECL, NULL_TREE, ptr_type_node);
1852 tree field = build_decl (input_location,
1853 FIELD_DECL, NULL_TREE, ptr_type_node);
1855 TREE_CHAIN (field) = fields; fields = field;
1856 field = build_decl (input_location,
1857 FIELD_DECL, NULL_TREE, unsigned_type_node);
1858 TREE_CHAIN (field) = fields; fields = field;
1859 /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in
1861 finish_builtin_struct (type, "__builtin_ObjCString",
1867 /* Custom build_string which sets TREE_TYPE! */
1870 my_build_string (int len, const char *str)
1872 return fix_string_type (build_string (len, str));
1875 /* Build a string with contents STR and length LEN and convert it to a
1879 my_build_string_pointer (int len, const char *str)
1881 tree string = my_build_string (len, str);
1882 tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));
1883 return build1 (ADDR_EXPR, ptrtype, string);
1887 string_hash (const void *ptr)
1889 const_tree const str = ((const struct string_descriptor *)ptr)->literal;
1890 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);
1891 int i, len = TREE_STRING_LENGTH (str);
1894 for (i = 0; i < len; i++)
1895 h = ((h * 613) + p[i]);
1901 string_eq (const void *ptr1, const void *ptr2)
1903 const_tree const str1 = ((const struct string_descriptor *)ptr1)->literal;
1904 const_tree const str2 = ((const struct string_descriptor *)ptr2)->literal;
1905 int len1 = TREE_STRING_LENGTH (str1);
1907 return (len1 == TREE_STRING_LENGTH (str2)
1908 && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),
1912 /* Given a chain of STRING_CST's, build a static instance of
1913 NXConstantString which points at the concatenation of those
1914 strings. We place the string object in the __string_objects
1915 section of the __OBJC segment. The Objective-C runtime will
1916 initialize the isa pointers of the string objects to point at the
1917 NXConstantString class object. */
1920 objc_build_string_object (tree string)
1922 tree initlist, constructor, constant_string_class;
1925 struct string_descriptor *desc, key;
1928 /* Prep the string argument. */
1929 string = fix_string_type (string);
1930 TREE_SET_CODE (string, STRING_CST);
1931 length = TREE_STRING_LENGTH (string) - 1;
1933 /* Check whether the string class being used actually exists and has the
1934 correct ivar layout. */
1935 if (!string_layout_checked)
1937 string_layout_checked = -1;
1938 constant_string_class = lookup_interface (constant_string_id);
1939 internal_const_str_type = objc_build_internal_const_str_type ();
1941 if (!constant_string_class
1942 || !(constant_string_type
1943 = CLASS_STATIC_TEMPLATE (constant_string_class)))
1944 error ("cannot find interface declaration for %qE",
1945 constant_string_id);
1946 /* The NSConstantString/NXConstantString ivar layout is now known. */
1947 else if (!check_string_class_template ())
1948 error ("interface %qE does not have valid constant string layout",
1949 constant_string_id);
1950 /* For the NeXT runtime, we can generate a literal reference
1951 to the string class, don't need to run a constructor. */
1952 else if (flag_next_runtime && !setup_string_decl ())
1953 error ("cannot find reference tag for class %qE",
1954 constant_string_id);
1957 string_layout_checked = 1; /* Success! */
1958 add_class_reference (constant_string_id);
1962 if (string_layout_checked == -1)
1963 return error_mark_node;
1965 /* Perhaps we already constructed a constant string just like this one? */
1966 key.literal = string;
1967 loc = htab_find_slot (string_htab, &key, INSERT);
1968 desc = (struct string_descriptor *) *loc;
1973 *loc = desc = GGC_NEW (struct string_descriptor);
1974 desc->literal = string;
1976 /* GNU: (NXConstantString *) & ((__builtin_ObjCString) { NULL, string, length }) */
1977 /* NeXT: (NSConstantString *) & ((__builtin_ObjCString) { isa, string, length }) */
1978 fields = TYPE_FIELDS (internal_const_str_type);
1980 = build_tree_list (fields,
1982 ? build_unary_op (input_location,
1983 ADDR_EXPR, string_class_decl, 0)
1984 : build_int_cst (NULL_TREE, 0));
1985 fields = TREE_CHAIN (fields);
1986 initlist = tree_cons (fields, build_unary_op (input_location,
1987 ADDR_EXPR, string, 1),
1989 fields = TREE_CHAIN (fields);
1990 initlist = tree_cons (fields, build_int_cst (NULL_TREE, length),
1992 constructor = objc_build_constructor (internal_const_str_type,
1993 nreverse (initlist));
1995 if (!flag_next_runtime)
1997 = objc_add_static_instance (constructor, constant_string_type);
2000 var = build_decl (input_location,
2001 CONST_DECL, NULL, TREE_TYPE (constructor));
2002 DECL_INITIAL (var) = constructor;
2003 TREE_STATIC (var) = 1;
2004 pushdecl_top_level (var);
2007 desc->constructor = constructor;
2010 addr = convert (build_pointer_type (constant_string_type),
2011 build_unary_op (input_location,
2012 ADDR_EXPR, desc->constructor, 1));
2017 /* Declare a static instance of CLASS_DECL initialized by CONSTRUCTOR. */
2019 static GTY(()) int num_static_inst;
2022 objc_add_static_instance (tree constructor, tree class_decl)
2027 /* Find the list of static instances for the CLASS_DECL. Create one if
2029 for (chain = &objc_static_instances;
2030 *chain && TREE_VALUE (*chain) != class_decl;
2031 chain = &TREE_CHAIN (*chain));
2034 *chain = tree_cons (NULL_TREE, class_decl, NULL_TREE);
2035 add_objc_string (OBJC_TYPE_NAME (class_decl), class_names);
2038 sprintf (buf, "_OBJC_INSTANCE_%d", num_static_inst++);
2039 decl = build_decl (input_location,
2040 VAR_DECL, get_identifier (buf), class_decl);
2041 DECL_COMMON (decl) = 1;
2042 TREE_STATIC (decl) = 1;
2043 DECL_ARTIFICIAL (decl) = 1;
2044 TREE_USED (decl) = 1;
2045 DECL_INITIAL (decl) = constructor;
2047 /* We may be writing something else just now.
2048 Postpone till end of input. */
2049 DECL_DEFER_OUTPUT (decl) = 1;
2050 pushdecl_top_level (decl);
2051 rest_of_decl_compilation (decl, 1, 0);
2053 /* Add the DECL to the head of this CLASS' list. */
2054 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE, decl, TREE_PURPOSE (*chain));
2059 /* Build a static constant CONSTRUCTOR
2060 with type TYPE and elements ELTS. */
2063 objc_build_constructor (tree type, tree elts)
2065 tree constructor = build_constructor_from_list (type, elts);
2067 TREE_CONSTANT (constructor) = 1;
2068 TREE_STATIC (constructor) = 1;
2069 TREE_READONLY (constructor) = 1;
2072 /* Adjust for impedance mismatch. We should figure out how to build
2073 CONSTRUCTORs that consistently please both the C and C++ gods. */
2074 if (!TREE_PURPOSE (elts))
2075 TREE_TYPE (constructor) = init_list_type_node;
2081 /* Take care of defining and initializing _OBJC_SYMBOLS. */
2083 /* Predefine the following data type:
2091 void *defs[cls_def_cnt + cat_def_cnt];
2095 build_objc_symtab_template (void)
2097 tree field_decl, field_decl_chain;
2099 objc_symtab_template = objc_start_struct (get_identifier (UTAG_SYMTAB));
2101 /* long sel_ref_cnt; */
2102 field_decl = create_field_decl (long_integer_type_node, "sel_ref_cnt");
2103 field_decl_chain = field_decl;
2106 field_decl = create_field_decl (build_pointer_type (objc_selector_type),
2108 chainon (field_decl_chain, field_decl);
2110 /* short cls_def_cnt; */
2111 field_decl = create_field_decl (short_integer_type_node, "cls_def_cnt");
2112 chainon (field_decl_chain, field_decl);
2114 /* short cat_def_cnt; */
2115 field_decl = create_field_decl (short_integer_type_node,
2117 chainon (field_decl_chain, field_decl);
2119 if (imp_count || cat_count || !flag_next_runtime)
2121 /* void *defs[imp_count + cat_count (+ 1)]; */
2122 /* NB: The index is one less than the size of the array. */
2123 int index = imp_count + cat_count
2124 + (flag_next_runtime? -1: 0);
2125 field_decl = create_field_decl
2128 build_index_type (build_int_cst (NULL_TREE, index))),
2130 chainon (field_decl_chain, field_decl);
2133 objc_finish_struct (objc_symtab_template, field_decl_chain);
2136 /* Create the initial value for the `defs' field of _objc_symtab.
2137 This is a CONSTRUCTOR. */
2140 init_def_list (tree type)
2142 tree expr, initlist = NULL_TREE;
2143 struct imp_entry *impent;
2146 for (impent = imp_list; impent; impent = impent->next)
2148 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
2150 expr = build_unary_op (input_location,
2151 ADDR_EXPR, impent->class_decl, 0);
2152 initlist = tree_cons (NULL_TREE, expr, initlist);
2157 for (impent = imp_list; impent; impent = impent->next)
2159 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2161 expr = build_unary_op (input_location,
2162 ADDR_EXPR, impent->class_decl, 0);
2163 initlist = tree_cons (NULL_TREE, expr, initlist);
2167 if (!flag_next_runtime)
2169 /* statics = { ..., _OBJC_STATIC_INSTANCES, ... } */
2172 if (static_instances_decl)
2173 expr = build_unary_op (input_location,
2174 ADDR_EXPR, static_instances_decl, 0);
2176 expr = build_int_cst (NULL_TREE, 0);
2178 initlist = tree_cons (NULL_TREE, expr, initlist);
2181 return objc_build_constructor (type, nreverse (initlist));
2184 /* Construct the initial value for all of _objc_symtab. */
2187 init_objc_symtab (tree type)
2191 /* sel_ref_cnt = { ..., 5, ... } */
2193 initlist = build_tree_list (NULL_TREE,
2194 build_int_cst (long_integer_type_node, 0));
2196 /* refs = { ..., _OBJC_SELECTOR_TABLE, ... } */
2198 if (flag_next_runtime || ! sel_ref_chain)
2199 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
2202 = tree_cons (NULL_TREE,
2203 convert (build_pointer_type (objc_selector_type),
2204 build_unary_op (input_location, ADDR_EXPR,
2205 UOBJC_SELECTOR_TABLE_decl, 1)),
2208 /* cls_def_cnt = { ..., 5, ... } */
2210 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, imp_count), initlist);
2212 /* cat_def_cnt = { ..., 5, ... } */
2214 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, cat_count), initlist);
2216 /* cls_def = { ..., { &Foo, &Bar, ...}, ... } */
2218 if (imp_count || cat_count || !flag_next_runtime)
2221 tree field = TYPE_FIELDS (type);
2222 field = TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (field))));
2224 initlist = tree_cons (NULL_TREE, init_def_list (TREE_TYPE (field)),
2228 return objc_build_constructor (type, nreverse (initlist));
2231 /* Generate forward declarations for metadata such as
2232 'OBJC_CLASS_...'. */
2235 build_metadata_decl (const char *name, tree type)
2239 /* struct TYPE NAME_<name>; */
2240 decl = start_var_decl (type, synth_id_with_class_suffix
2242 objc_implementation_context));
2247 /* Push forward-declarations of all the categories so that
2248 init_def_list can use them in a CONSTRUCTOR. */
2251 forward_declare_categories (void)
2253 struct imp_entry *impent;
2254 tree sav = objc_implementation_context;
2256 for (impent = imp_list; impent; impent = impent->next)
2258 if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
2260 /* Set an invisible arg to synth_id_with_class_suffix. */
2261 objc_implementation_context = impent->imp_context;
2262 /* extern struct objc_category _OBJC_CATEGORY_<name>; */
2263 impent->class_decl = build_metadata_decl ("_OBJC_CATEGORY",
2264 objc_category_template);
2267 objc_implementation_context = sav;
2270 /* Create the declaration of _OBJC_SYMBOLS, with type `struct _objc_symtab'
2271 and initialized appropriately. */
2274 generate_objc_symtab_decl (void)
2276 /* forward declare categories */
2278 forward_declare_categories ();
2280 build_objc_symtab_template ();
2281 UOBJC_SYMBOLS_decl = start_var_decl (objc_symtab_template, "_OBJC_SYMBOLS");
2282 finish_var_decl (UOBJC_SYMBOLS_decl,
2283 init_objc_symtab (TREE_TYPE (UOBJC_SYMBOLS_decl)));
2287 init_module_descriptor (tree type)
2289 tree initlist, expr;
2291 /* version = { 1, ... } */
2293 expr = build_int_cst (long_integer_type_node, OBJC_VERSION);
2294 initlist = build_tree_list (NULL_TREE, expr);
2296 /* size = { ..., sizeof (struct _objc_module), ... } */
2298 expr = convert (long_integer_type_node,
2299 size_in_bytes (objc_module_template));
2300 initlist = tree_cons (NULL_TREE, expr, initlist);
2302 /* Don't provide any file name for security reasons. */
2303 /* name = { ..., "", ... } */
2305 expr = add_objc_string (get_identifier (""), class_names);
2306 initlist = tree_cons (NULL_TREE, expr, initlist);
2308 /* symtab = { ..., _OBJC_SYMBOLS, ... } */
2310 if (UOBJC_SYMBOLS_decl)
2311 expr = build_unary_op (input_location,
2312 ADDR_EXPR, UOBJC_SYMBOLS_decl, 0);
2314 expr = build_int_cst (NULL_TREE, 0);
2315 initlist = tree_cons (NULL_TREE, expr, initlist);
2317 return objc_build_constructor (type, nreverse (initlist));
2320 /* Write out the data structures to describe Objective C classes defined.
2322 struct _objc_module { ... } _OBJC_MODULE = { ... }; */
2325 build_module_descriptor (void)
2327 tree field_decl, field_decl_chain;
2330 push_lang_context (lang_name_c); /* extern "C" */
2333 objc_module_template = objc_start_struct (get_identifier (UTAG_MODULE));
2336 field_decl = create_field_decl (long_integer_type_node, "version");
2337 field_decl_chain = field_decl;
2340 field_decl = create_field_decl (long_integer_type_node, "size");
2341 chainon (field_decl_chain, field_decl);
2344 field_decl = create_field_decl (string_type_node, "name");
2345 chainon (field_decl_chain, field_decl);
2347 /* struct _objc_symtab *symtab; */
2349 = create_field_decl (build_pointer_type
2350 (xref_tag (RECORD_TYPE,
2351 get_identifier (UTAG_SYMTAB))),
2353 chainon (field_decl_chain, field_decl);
2355 objc_finish_struct (objc_module_template, field_decl_chain);
2357 /* Create an instance of "_objc_module". */
2358 UOBJC_MODULES_decl = start_var_decl (objc_module_template, "_OBJC_MODULES");
2359 finish_var_decl (UOBJC_MODULES_decl,
2360 init_module_descriptor (TREE_TYPE (UOBJC_MODULES_decl)));
2363 pop_lang_context ();
2367 /* The GNU runtime requires us to provide a static initializer function
2370 static void __objc_gnu_init (void) {
2371 __objc_exec_class (&L_OBJC_MODULES);
2375 build_module_initializer_routine (void)
2380 push_lang_context (lang_name_c); /* extern "C" */
2383 objc_push_parm (build_decl (input_location,
2384 PARM_DECL, NULL_TREE, void_type_node));
2385 objc_start_function (get_identifier (TAG_GNUINIT),
2386 build_function_type (void_type_node,
2388 NULL_TREE, objc_get_parm_info (0));
2390 body = c_begin_compound_stmt (true);
2391 add_stmt (build_function_call
2396 build_unary_op (input_location, ADDR_EXPR,
2397 UOBJC_MODULES_decl, 0))));
2398 add_stmt (c_end_compound_stmt (input_location, body, true));
2400 TREE_PUBLIC (current_function_decl) = 0;
2403 /* For Objective-C++, we will need to call __objc_gnu_init
2404 from objc_generate_static_init_call() below. */
2405 DECL_STATIC_CONSTRUCTOR (current_function_decl) = 1;
2408 GNU_INIT_decl = current_function_decl;
2412 pop_lang_context ();
2417 /* Return 1 if the __objc_gnu_init function has been synthesized and needs
2418 to be called by the module initializer routine. */
2421 objc_static_init_needed_p (void)
2423 return (GNU_INIT_decl != NULL_TREE);
2426 /* Generate a call to the __objc_gnu_init initializer function. */
2429 objc_generate_static_init_call (tree ctors ATTRIBUTE_UNUSED)
2431 add_stmt (build_stmt (input_location, EXPR_STMT,
2432 build_function_call (input_location,
2433 GNU_INIT_decl, NULL_TREE)));
2437 #endif /* OBJCPLUS */
2439 /* Return the DECL of the string IDENT in the SECTION. */
2442 get_objc_string_decl (tree ident, enum string_section section)
2446 if (section == class_names)
2447 chain = class_names_chain;
2448 else if (section == meth_var_names)
2449 chain = meth_var_names_chain;
2450 else if (section == meth_var_types)
2451 chain = meth_var_types_chain;
2455 for (; chain != 0; chain = TREE_CHAIN (chain))
2456 if (TREE_VALUE (chain) == ident)
2457 return (TREE_PURPOSE (chain));
2463 /* Output references to all statically allocated objects. Return the DECL
2464 for the array built. */
2467 generate_static_references (void)
2469 tree decls = NULL_TREE, expr = NULL_TREE;
2470 tree class_name, klass, decl, initlist;
2471 tree cl_chain, in_chain, type
2472 = build_array_type (build_pointer_type (void_type_node), NULL_TREE);
2473 int num_inst, num_class;
2476 if (flag_next_runtime)
2479 for (cl_chain = objc_static_instances, num_class = 0;
2480 cl_chain; cl_chain = TREE_CHAIN (cl_chain), num_class++)
2482 for (num_inst = 0, in_chain = TREE_PURPOSE (cl_chain);
2483 in_chain; num_inst++, in_chain = TREE_CHAIN (in_chain));
2485 sprintf (buf, "_OBJC_STATIC_INSTANCES_%d", num_class);
2486 decl = start_var_decl (type, buf);
2488 /* Output {class_name, ...}. */
2489 klass = TREE_VALUE (cl_chain);
2490 class_name = get_objc_string_decl (OBJC_TYPE_NAME (klass), class_names);
2491 initlist = build_tree_list (NULL_TREE,
2492 build_unary_op (input_location,
2493 ADDR_EXPR, class_name, 1));
2495 /* Output {..., instance, ...}. */
2496 for (in_chain = TREE_PURPOSE (cl_chain);
2497 in_chain; in_chain = TREE_CHAIN (in_chain))
2499 expr = build_unary_op (input_location,
2500 ADDR_EXPR, TREE_VALUE (in_chain), 1);
2501 initlist = tree_cons (NULL_TREE, expr, initlist);
2504 /* Output {..., NULL}. */
2505 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
2507 expr = objc_build_constructor (TREE_TYPE (decl), nreverse (initlist));
2508 finish_var_decl (decl, expr);
2510 = tree_cons (NULL_TREE, build_unary_op (input_location,
2511 ADDR_EXPR, decl, 1), decls);
2514 decls = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), decls);
2515 expr = objc_build_constructor (type, nreverse (decls));
2516 static_instances_decl = start_var_decl (type, "_OBJC_STATIC_INSTANCES");
2517 finish_var_decl (static_instances_decl, expr);
2520 static GTY(()) int selector_reference_idx;
2523 build_selector_reference_decl (void)
2528 sprintf (buf, "_OBJC_SELECTOR_REFERENCES_%d", selector_reference_idx++);
2529 decl = start_var_decl (objc_selector_type, buf);
2535 build_selector_table_decl (void)
2539 if (flag_typed_selectors)
2541 build_selector_template ();
2542 temp = build_array_type (objc_selector_template, NULL_TREE);
2545 temp = build_array_type (objc_selector_type, NULL_TREE);
2547 UOBJC_SELECTOR_TABLE_decl = start_var_decl (temp, "_OBJC_SELECTOR_TABLE");
2550 /* Just a handy wrapper for add_objc_string. */
2553 build_selector (tree ident)
2555 return convert (objc_selector_type,
2556 add_objc_string (ident, meth_var_names));
2560 build_selector_translation_table (void)
2562 tree chain, initlist = NULL_TREE;
2564 tree decl = NULL_TREE;
2566 for (chain = sel_ref_chain; chain; chain = TREE_CHAIN (chain))
2570 if (warn_selector && objc_implementation_context)
2574 for (method_chain = meth_var_names_chain;
2576 method_chain = TREE_CHAIN (method_chain))
2578 if (TREE_VALUE (method_chain) == TREE_VALUE (chain))
2587 if (flag_next_runtime && TREE_PURPOSE (chain))
2588 loc = DECL_SOURCE_LOCATION (TREE_PURPOSE (chain));
2590 loc = input_location;
2591 warning_at (loc, 0, "creating selector for nonexistent method %qE",
2592 TREE_VALUE (chain));
2596 expr = build_selector (TREE_VALUE (chain));
2597 /* add one for the '\0' character */
2598 offset += IDENTIFIER_LENGTH (TREE_VALUE (chain)) + 1;
2600 if (flag_next_runtime)
2602 decl = TREE_PURPOSE (chain);
2603 finish_var_decl (decl, expr);
2607 if (flag_typed_selectors)
2609 tree eltlist = NULL_TREE;
2610 tree encoding = get_proto_encoding (TREE_PURPOSE (chain));
2611 eltlist = tree_cons (NULL_TREE, expr, NULL_TREE);
2612 eltlist = tree_cons (NULL_TREE, encoding, eltlist);
2613 expr = objc_build_constructor (objc_selector_template,
2614 nreverse (eltlist));
2617 initlist = tree_cons (NULL_TREE, expr, initlist);
2621 if (! flag_next_runtime)
2623 /* Cause the selector table (previously forward-declared)
2624 to be actually output. */
2625 initlist = tree_cons (NULL_TREE,
2626 flag_typed_selectors
2627 ? objc_build_constructor
2628 (objc_selector_template,
2629 tree_cons (NULL_TREE,
2630 build_int_cst (NULL_TREE, 0),
2631 tree_cons (NULL_TREE,
2632 build_int_cst (NULL_TREE, 0),
2634 : build_int_cst (NULL_TREE, 0), initlist);
2635 initlist = objc_build_constructor (TREE_TYPE (UOBJC_SELECTOR_TABLE_decl),
2636 nreverse (initlist));
2637 finish_var_decl (UOBJC_SELECTOR_TABLE_decl, initlist);
2642 get_proto_encoding (tree proto)
2647 if (! METHOD_ENCODING (proto))
2649 encoding = encode_method_prototype (proto);
2650 METHOD_ENCODING (proto) = encoding;
2653 encoding = METHOD_ENCODING (proto);
2655 return add_objc_string (encoding, meth_var_types);
2658 return build_int_cst (NULL_TREE, 0);
2661 /* sel_ref_chain is a list whose "value" fields will be instances of
2662 identifier_node that represent the selector. LOC is the location of
2666 build_typed_selector_reference (location_t loc, tree ident, tree prototype)
2668 tree *chain = &sel_ref_chain;
2674 if (TREE_PURPOSE (*chain) == prototype && TREE_VALUE (*chain) == ident)
2675 goto return_at_index;
2678 chain = &TREE_CHAIN (*chain);
2681 *chain = tree_cons (prototype, ident, NULL_TREE);
2684 expr = build_unary_op (loc, ADDR_EXPR,
2685 build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2686 build_int_cst (NULL_TREE, index)),
2688 return convert (objc_selector_type, expr);
2692 build_selector_reference (location_t loc, tree ident)
2694 tree *chain = &sel_ref_chain;
2700 if (TREE_VALUE (*chain) == ident)
2701 return (flag_next_runtime
2702 ? TREE_PURPOSE (*chain)
2703 : build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2704 build_int_cst (NULL_TREE, index)));
2707 chain = &TREE_CHAIN (*chain);
2710 expr = (flag_next_runtime ? build_selector_reference_decl (): NULL_TREE);
2712 *chain = tree_cons (expr, ident, NULL_TREE);
2714 return (flag_next_runtime
2716 : build_array_ref (loc, UOBJC_SELECTOR_TABLE_decl,
2717 build_int_cst (NULL_TREE, index)));
2720 static GTY(()) int class_reference_idx;
2723 build_class_reference_decl (void)
2728 sprintf (buf, "_OBJC_CLASS_REFERENCES_%d", class_reference_idx++);
2729 decl = start_var_decl (objc_class_type, buf);
2734 /* Create a class reference, but don't create a variable to reference
2738 add_class_reference (tree ident)
2742 if ((chain = cls_ref_chain))
2747 if (ident == TREE_VALUE (chain))
2751 chain = TREE_CHAIN (chain);
2755 /* Append to the end of the list */
2756 TREE_CHAIN (tail) = tree_cons (NULL_TREE, ident, NULL_TREE);
2759 cls_ref_chain = tree_cons (NULL_TREE, ident, NULL_TREE);
2762 /* Get a class reference, creating it if necessary. Also create the
2763 reference variable. */
2766 objc_get_class_reference (tree ident)
2768 tree orig_ident = (DECL_P (ident)
2771 ? OBJC_TYPE_NAME (ident)
2773 bool local_scope = false;
2776 if (processing_template_decl)
2777 /* Must wait until template instantiation time. */
2778 return build_min_nt (CLASS_REFERENCE_EXPR, ident);
2781 if (TREE_CODE (ident) == TYPE_DECL)
2782 ident = (DECL_ORIGINAL_TYPE (ident)
2783 ? DECL_ORIGINAL_TYPE (ident)
2784 : TREE_TYPE (ident));
2787 if (TYPE_P (ident) && TYPE_CONTEXT (ident)
2788 && TYPE_CONTEXT (ident) != global_namespace)
2792 if (local_scope || !(ident = objc_is_class_name (ident)))
2794 error ("%qE is not an Objective-C class name or alias",
2796 return error_mark_node;
2799 if (flag_next_runtime && !flag_zero_link)
2804 for (chain = &cls_ref_chain; *chain; chain = &TREE_CHAIN (*chain))
2805 if (TREE_VALUE (*chain) == ident)
2807 if (! TREE_PURPOSE (*chain))
2808 TREE_PURPOSE (*chain) = build_class_reference_decl ();
2810 return TREE_PURPOSE (*chain);
2813 decl = build_class_reference_decl ();
2814 *chain = tree_cons (decl, ident, NULL_TREE);
2821 add_class_reference (ident);
2823 params = build_tree_list (NULL_TREE,
2824 my_build_string_pointer
2825 (IDENTIFIER_LENGTH (ident) + 1,
2826 IDENTIFIER_POINTER (ident)));
2828 assemble_external (objc_get_class_decl);
2829 return build_function_call (input_location, objc_get_class_decl, params);
2833 /* For each string section we have a chain which maps identifier nodes
2834 to decls for the strings. */
2837 add_objc_string (tree ident, enum string_section section)
2839 tree *chain, decl, type, string_expr;
2841 if (section == class_names)
2842 chain = &class_names_chain;
2843 else if (section == meth_var_names)
2844 chain = &meth_var_names_chain;
2845 else if (section == meth_var_types)
2846 chain = &meth_var_types_chain;
2852 if (TREE_VALUE (*chain) == ident)
2853 return convert (string_type_node,
2854 build_unary_op (input_location,
2855 ADDR_EXPR, TREE_PURPOSE (*chain), 1));
2857 chain = &TREE_CHAIN (*chain);
2860 decl = build_objc_string_decl (section);
2862 type = build_array_type
2865 (build_int_cst (NULL_TREE,
2866 IDENTIFIER_LENGTH (ident))));
2867 decl = start_var_decl (type, IDENTIFIER_POINTER (DECL_NAME (decl)));
2868 string_expr = my_build_string (IDENTIFIER_LENGTH (ident) + 1,
2869 IDENTIFIER_POINTER (ident));
2870 finish_var_decl (decl, string_expr);
2872 *chain = tree_cons (decl, ident, NULL_TREE);
2874 return convert (string_type_node, build_unary_op (input_location,
2875 ADDR_EXPR, decl, 1));
2878 static GTY(()) int class_names_idx;
2879 static GTY(()) int meth_var_names_idx;
2880 static GTY(()) int meth_var_types_idx;
2883 build_objc_string_decl (enum string_section section)
2888 if (section == class_names)
2889 sprintf (buf, "_OBJC_CLASS_NAME_%d", class_names_idx++);
2890 else if (section == meth_var_names)
2891 sprintf (buf, "_OBJC_METH_VAR_NAME_%d", meth_var_names_idx++);
2892 else if (section == meth_var_types)
2893 sprintf (buf, "_OBJC_METH_VAR_TYPE_%d", meth_var_types_idx++);
2895 ident = get_identifier (buf);
2897 decl = build_decl (input_location,
2898 VAR_DECL, ident, build_array_type (char_type_node, 0));
2899 DECL_EXTERNAL (decl) = 1;
2900 TREE_PUBLIC (decl) = 0;
2901 TREE_USED (decl) = 1;
2902 TREE_CONSTANT (decl) = 1;
2903 DECL_CONTEXT (decl) = 0;
2904 DECL_ARTIFICIAL (decl) = 1;
2906 DECL_THIS_STATIC (decl) = 1; /* squash redeclaration errors */
2909 make_decl_rtl (decl);
2910 pushdecl_top_level (decl);
2917 objc_declare_alias (tree alias_ident, tree class_ident)
2919 tree underlying_class;
2922 if (current_namespace != global_namespace) {
2923 error ("Objective-C declarations may only appear in global scope");
2925 #endif /* OBJCPLUS */
2927 if (!(underlying_class = objc_is_class_name (class_ident)))
2928 warning (0, "cannot find class %qE", class_ident);
2929 else if (objc_is_class_name (alias_ident))
2930 warning (0, "class %qE already exists", alias_ident);
2933 /* Implement @compatibility_alias as a typedef. */
2935 push_lang_context (lang_name_c); /* extern "C" */
2937 lang_hooks.decls.pushdecl (build_decl
2941 xref_tag (RECORD_TYPE, underlying_class)));
2943 pop_lang_context ();
2945 alias_chain = tree_cons (underlying_class, alias_ident, alias_chain);
2950 objc_declare_class (tree ident_list)
2954 if (current_namespace != global_namespace) {
2955 error ("Objective-C declarations may only appear in global scope");
2957 #endif /* OBJCPLUS */
2959 for (list = ident_list; list; list = TREE_CHAIN (list))
2961 tree ident = TREE_VALUE (list);
2963 if (! objc_is_class_name (ident))
2965 tree record = lookup_name (ident), type = record;
2969 if (TREE_CODE (record) == TYPE_DECL)
2970 type = DECL_ORIGINAL_TYPE (record);
2972 if (!TYPE_HAS_OBJC_INFO (type)
2973 || !TYPE_OBJC_INTERFACE (type))
2975 error ("%qE redeclared as different kind of symbol",
2977 error ("previous declaration of %q+D",
2982 record = xref_tag (RECORD_TYPE, ident);
2983 INIT_TYPE_OBJC_INFO (record);
2984 TYPE_OBJC_INTERFACE (record) = ident;
2985 class_chain = tree_cons (NULL_TREE, ident, class_chain);
2991 objc_is_class_name (tree ident)
2995 if (ident && TREE_CODE (ident) == IDENTIFIER_NODE
2996 && identifier_global_value (ident))
2997 ident = identifier_global_value (ident);
2998 while (ident && TREE_CODE (ident) == TYPE_DECL && DECL_ORIGINAL_TYPE (ident))
2999 ident = OBJC_TYPE_NAME (DECL_ORIGINAL_TYPE (ident));
3001 if (ident && TREE_CODE (ident) == RECORD_TYPE)
3002 ident = OBJC_TYPE_NAME (ident);
3004 if (ident && TREE_CODE (ident) == TYPE_DECL)
3005 ident = DECL_NAME (ident);
3007 if (!ident || TREE_CODE (ident) != IDENTIFIER_NODE)
3010 if (lookup_interface (ident))
3013 for (chain = class_chain; chain; chain = TREE_CHAIN (chain))
3015 if (ident == TREE_VALUE (chain))
3019 for (chain = alias_chain; chain; chain = TREE_CHAIN (chain))
3021 if (ident == TREE_VALUE (chain))
3022 return TREE_PURPOSE (chain);
3028 /* Check whether TYPE is either 'id' or 'Class'. */
3031 objc_is_id (tree type)
3033 if (type && TREE_CODE (type) == IDENTIFIER_NODE
3034 && identifier_global_value (type))
3035 type = identifier_global_value (type);
3037 if (type && TREE_CODE (type) == TYPE_DECL)
3038 type = TREE_TYPE (type);
3040 /* NB: This function may be called before the ObjC front-end has
3041 been initialized, in which case OBJC_OBJECT_TYPE will (still) be NULL. */
3042 return (objc_object_type && type
3043 && (IS_ID (type) || IS_CLASS (type) || IS_SUPER (type))
3048 /* Check whether TYPE is either 'id', 'Class', or a pointer to an ObjC
3049 class instance. This is needed by other parts of the compiler to
3050 handle ObjC types gracefully. */
3053 objc_is_object_ptr (tree type)
3057 type = TYPE_MAIN_VARIANT (type);
3058 if (!POINTER_TYPE_P (type))
3061 ret = objc_is_id (type);
3063 ret = objc_is_class_name (TREE_TYPE (type));
3069 objc_is_gcable_type (tree type, int or_strong_p)
3075 if (objc_is_id (TYPE_MAIN_VARIANT (type)))
3077 if (or_strong_p && lookup_attribute ("objc_gc", TYPE_ATTRIBUTES (type)))
3079 if (TREE_CODE (type) != POINTER_TYPE && TREE_CODE (type) != INDIRECT_REF)
3081 type = TREE_TYPE (type);
3082 if (TREE_CODE (type) != RECORD_TYPE)
3084 name = TYPE_NAME (type);
3085 return (objc_is_class_name (name) != NULL_TREE);
3089 objc_substitute_decl (tree expr, tree oldexpr, tree newexpr)
3091 if (expr == oldexpr)
3094 switch (TREE_CODE (expr))
3097 return objc_build_component_ref
3098 (objc_substitute_decl (TREE_OPERAND (expr, 0),
3101 DECL_NAME (TREE_OPERAND (expr, 1)));
3103 return build_array_ref (input_location,
3104 objc_substitute_decl (TREE_OPERAND (expr, 0),
3107 TREE_OPERAND (expr, 1));
3109 return build_indirect_ref (input_location,
3110 objc_substitute_decl (TREE_OPERAND (expr, 0),
3119 objc_build_ivar_assignment (tree outervar, tree lhs, tree rhs)
3122 /* The LHS parameter contains the expression 'outervar->memberspec';
3123 we need to transform it into '&((typeof(outervar) *) 0)->memberspec',
3124 where memberspec may be arbitrarily complex (e.g., 'g->f.d[2].g[3]').
3127 = objc_substitute_decl
3128 (lhs, outervar, convert (TREE_TYPE (outervar), integer_zero_node));
3130 = (flag_objc_direct_dispatch
3131 ? objc_assign_ivar_fast_decl
3132 : objc_assign_ivar_decl);
3134 offs = convert (integer_type_node, build_unary_op (input_location,
3135 ADDR_EXPR, offs, 0));
3137 func_params = tree_cons (NULL_TREE,
3138 convert (objc_object_type, rhs),
3139 tree_cons (NULL_TREE, convert (objc_object_type, outervar),
3140 tree_cons (NULL_TREE, offs,
3143 assemble_external (func);
3144 return build_function_call (input_location, func, func_params);
3148 objc_build_global_assignment (tree lhs, tree rhs)
3150 tree func_params = tree_cons (NULL_TREE,
3151 convert (objc_object_type, rhs),
3152 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3153 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3156 assemble_external (objc_assign_global_decl);
3157 return build_function_call (input_location,
3158 objc_assign_global_decl, func_params);
3162 objc_build_strong_cast_assignment (tree lhs, tree rhs)
3164 tree func_params = tree_cons (NULL_TREE,
3165 convert (objc_object_type, rhs),
3166 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3167 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3170 assemble_external (objc_assign_strong_cast_decl);
3171 return build_function_call (input_location,
3172 objc_assign_strong_cast_decl, func_params);
3176 objc_is_gcable_p (tree expr)
3178 return (TREE_CODE (expr) == COMPONENT_REF
3179 ? objc_is_gcable_p (TREE_OPERAND (expr, 1))
3180 : TREE_CODE (expr) == ARRAY_REF
3181 ? (objc_is_gcable_p (TREE_TYPE (expr))
3182 || objc_is_gcable_p (TREE_OPERAND (expr, 0)))
3183 : TREE_CODE (expr) == ARRAY_TYPE
3184 ? objc_is_gcable_p (TREE_TYPE (expr))
3186 ? objc_is_gcable_type (expr, 1)
3187 : (objc_is_gcable_p (TREE_TYPE (expr))
3189 && lookup_attribute ("objc_gc", DECL_ATTRIBUTES (expr)))));
3193 objc_is_ivar_reference_p (tree expr)
3195 return (TREE_CODE (expr) == ARRAY_REF
3196 ? objc_is_ivar_reference_p (TREE_OPERAND (expr, 0))
3197 : TREE_CODE (expr) == COMPONENT_REF
3198 ? TREE_CODE (TREE_OPERAND (expr, 1)) == FIELD_DECL
3203 objc_is_global_reference_p (tree expr)
3205 return (TREE_CODE (expr) == INDIRECT_REF || TREE_CODE (expr) == PLUS_EXPR
3206 ? objc_is_global_reference_p (TREE_OPERAND (expr, 0))
3208 ? (!DECL_CONTEXT (expr) || TREE_STATIC (expr))
3213 objc_generate_write_barrier (tree lhs, enum tree_code modifycode, tree rhs)
3215 tree result = NULL_TREE, outer;
3216 int strong_cast_p = 0, outer_gc_p = 0, indirect_p = 0;
3218 /* See if we have any lhs casts, and strip them out. NB: The lvalue casts
3219 will have been transformed to the form '*(type *)&expr'. */
3220 if (TREE_CODE (lhs) == INDIRECT_REF)
3222 outer = TREE_OPERAND (lhs, 0);
3224 while (!strong_cast_p
3225 && (CONVERT_EXPR_P (outer)
3226 || TREE_CODE (outer) == NON_LVALUE_EXPR))
3228 tree lhstype = TREE_TYPE (outer);
3230 /* Descend down the cast chain, and record the first objc_gc
3232 if (POINTER_TYPE_P (lhstype))
3235 = lookup_attribute ("objc_gc",
3236 TYPE_ATTRIBUTES (TREE_TYPE (lhstype)));
3242 outer = TREE_OPERAND (outer, 0);
3246 /* If we have a __strong cast, it trumps all else. */
3249 if (modifycode != NOP_EXPR)
3250 goto invalid_pointer_arithmetic;
3252 if (warn_assign_intercept)
3253 warning (0, "strong-cast assignment has been intercepted");
3255 result = objc_build_strong_cast_assignment (lhs, rhs);
3260 /* the lhs must be of a suitable type, regardless of its underlying
3262 if (!objc_is_gcable_p (lhs))
3268 && (TREE_CODE (outer) == COMPONENT_REF
3269 || TREE_CODE (outer) == ARRAY_REF))
3270 outer = TREE_OPERAND (outer, 0);
3272 if (TREE_CODE (outer) == INDIRECT_REF)
3274 outer = TREE_OPERAND (outer, 0);
3278 outer_gc_p = objc_is_gcable_p (outer);
3280 /* Handle ivar assignments. */
3281 if (objc_is_ivar_reference_p (lhs))
3283 /* if the struct to the left of the ivar is not an Objective-C object (__strong
3284 doesn't cut it here), the best we can do here is suggest a cast. */
3285 if (!objc_is_gcable_type (TREE_TYPE (outer), 0))
3287 /* We may still be able to use the global write barrier... */
3288 if (!indirect_p && objc_is_global_reference_p (outer))
3289 goto global_reference;
3292 if (modifycode == NOP_EXPR)
3294 if (warn_assign_intercept)
3295 warning (0, "strong-cast may possibly be needed");
3301 if (modifycode != NOP_EXPR)
3302 goto invalid_pointer_arithmetic;
3304 if (warn_assign_intercept)
3305 warning (0, "instance variable assignment has been intercepted");
3307 result = objc_build_ivar_assignment (outer, lhs, rhs);
3312 /* Likewise, intercept assignment to global/static variables if their type is
3314 if (objc_is_global_reference_p (outer))
3320 if (modifycode != NOP_EXPR)
3322 invalid_pointer_arithmetic:
3324 warning (0, "pointer arithmetic for garbage-collected objects not allowed");
3329 if (warn_assign_intercept)
3330 warning (0, "global/static variable assignment has been intercepted");
3332 result = objc_build_global_assignment (lhs, rhs);
3335 /* In all other cases, fall back to the normal mechanism. */
3340 struct GTY(()) interface_tuple {
3345 static GTY ((param_is (struct interface_tuple))) htab_t interface_htab;
3348 hash_interface (const void *p)
3350 const struct interface_tuple *d = (const struct interface_tuple *) p;
3351 return IDENTIFIER_HASH_VALUE (d->id);
3355 eq_interface (const void *p1, const void *p2)
3357 const struct interface_tuple *d = (const struct interface_tuple *) p1;
3362 lookup_interface (tree ident)
3365 if (ident && TREE_CODE (ident) == TYPE_DECL)
3366 ident = DECL_NAME (ident);
3369 if (ident == NULL_TREE || TREE_CODE (ident) != IDENTIFIER_NODE)
3373 struct interface_tuple **slot;
3378 slot = (struct interface_tuple **)
3379 htab_find_slot_with_hash (interface_htab, ident,
3380 IDENTIFIER_HASH_VALUE (ident),
3383 i = (*slot)->class_name;
3389 /* Implement @defs (<classname>) within struct bodies. */
3392 objc_get_class_ivars (tree class_name)
3394 tree interface = lookup_interface (class_name);
3397 return get_class_ivars (interface, true);
3399 error ("cannot find interface declaration for %qE",
3402 return error_mark_node;
3405 /* Used by: build_private_template, continue_class,
3406 and for @defs constructs. */
3409 get_class_ivars (tree interface, bool inherited)
3411 tree ivar_chain = copy_list (CLASS_RAW_IVARS (interface));
3413 /* Both CLASS_RAW_IVARS and CLASS_IVARS contain a list of ivars declared
3414 by the current class (i.e., they do not include super-class ivars).
3415 However, the CLASS_IVARS list will be side-effected by a call to
3416 finish_struct(), which will fill in field offsets. */
3417 if (!CLASS_IVARS (interface))
3418 CLASS_IVARS (interface) = ivar_chain;
3423 while (CLASS_SUPER_NAME (interface))
3425 /* Prepend super-class ivars. */
3426 interface = lookup_interface (CLASS_SUPER_NAME (interface));
3427 ivar_chain = chainon (copy_list (CLASS_RAW_IVARS (interface)),
3435 objc_create_temporary_var (tree type)
3439 decl = build_decl (input_location,
3440 VAR_DECL, NULL_TREE, type);
3441 TREE_USED (decl) = 1;
3442 DECL_ARTIFICIAL (decl) = 1;
3443 DECL_IGNORED_P (decl) = 1;
3444 DECL_CONTEXT (decl) = current_function_decl;
3449 /* Exception handling constructs. We begin by having the parser do most
3450 of the work and passing us blocks. What we do next depends on whether
3451 we're doing "native" exception handling or legacy Darwin setjmp exceptions.
3452 We abstract all of this in a handful of appropriately named routines. */
3454 /* Stack of open try blocks. */
3456 struct objc_try_context
3458 struct objc_try_context *outer;
3460 /* Statements (or statement lists) as processed by the parser. */
3464 /* Some file position locations. */
3465 location_t try_locus;
3466 location_t end_try_locus;
3467 location_t end_catch_locus;
3468 location_t finally_locus;
3469 location_t end_finally_locus;
3471 /* A STATEMENT_LIST of CATCH_EXPRs, appropriate for sticking into op1
3472 of a TRY_CATCH_EXPR. Even when doing Darwin setjmp. */
3475 /* The CATCH_EXPR of an open @catch clause. */
3478 /* The VAR_DECL holding the Darwin equivalent of EXC_PTR_EXPR. */
3484 static struct objc_try_context *cur_try_context;
3486 static GTY(()) tree objc_eh_personality_decl;
3488 /* This hook, called via lang_eh_runtime_type, generates a runtime object
3489 that represents TYPE. For Objective-C, this is just the class name. */
3490 /* ??? Isn't there a class object or some such? Is it easy to get? */
3494 objc_eh_runtime_type (tree type)
3496 return add_objc_string (OBJC_TYPE_NAME (TREE_TYPE (type)), class_names);
3500 objc_eh_personality (void)
3502 if (!flag_objc_sjlj_exceptions
3503 && !objc_eh_personality_decl)
3504 objc_eh_personality_decl
3505 = build_personality_function (USING_SJLJ_EXCEPTIONS
3506 ? "__gnu_objc_personality_sj0"
3507 : "__gnu_objc_personality_v0");
3509 return objc_eh_personality_decl;
3513 /* Build an EXC_PTR_EXPR, or the moral equivalent. In the case of Darwin,
3514 we'll arrange for it to be initialized (and associated with a binding)
3518 objc_build_exc_ptr (void)
3520 if (flag_objc_sjlj_exceptions)
3522 tree var = cur_try_context->caught_decl;
3525 var = objc_create_temporary_var (objc_object_type);
3526 cur_try_context->caught_decl = var;
3531 return build0 (EXC_PTR_EXPR, objc_object_type);
3534 /* Build "objc_exception_try_exit(&_stack)". */
3537 next_sjlj_build_try_exit (void)
3540 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3541 t = tree_cons (NULL, t, NULL);
3542 t = build_function_call (input_location,
3543 objc_exception_try_exit_decl, t);
3548 objc_exception_try_enter (&_stack);
3549 if (_setjmp(&_stack.buf))
3553 Return the COND_EXPR. Note that the THEN and ELSE fields are left
3554 empty, ready for the caller to fill them in. */
3557 next_sjlj_build_enter_and_setjmp (void)
3559 tree t, enter, sj, cond;
3561 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3562 t = tree_cons (NULL, t, NULL);
3563 enter = build_function_call (input_location,
3564 objc_exception_try_enter_decl, t);
3566 t = objc_build_component_ref (cur_try_context->stack_decl,
3567 get_identifier ("buf"));
3568 t = build_fold_addr_expr_loc (input_location, t);
3570 /* Convert _setjmp argument to type that is expected. */
3571 if (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl)))
3572 t = convert (TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (objc_setjmp_decl))), t);
3574 t = convert (ptr_type_node, t);
3576 t = convert (ptr_type_node, t);
3578 t = tree_cons (NULL, t, NULL);
3579 sj = build_function_call (input_location,
3580 objc_setjmp_decl, t);
3582 cond = build2 (COMPOUND_EXPR, TREE_TYPE (sj), enter, sj);
3583 cond = c_common_truthvalue_conversion (input_location, cond);
3585 return build3 (COND_EXPR, void_type_node, cond, NULL, NULL);
3590 DECL = objc_exception_extract(&_stack); */
3593 next_sjlj_build_exc_extract (tree decl)
3597 t = build_fold_addr_expr_loc (input_location, cur_try_context->stack_decl);
3598 t = tree_cons (NULL, t, NULL);
3599 t = build_function_call (input_location,
3600 objc_exception_extract_decl, t);
3601 t = convert (TREE_TYPE (decl), t);
3602 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
3608 if (objc_exception_match(obj_get_class(TYPE), _caught)
3615 objc_exception_try_exit(&_stack);
3617 from the sequence of CATCH_EXPRs in the current try context. */
3620 next_sjlj_build_catch_list (void)
3622 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
3624 tree *last = &catch_seq;
3625 bool saw_id = false;
3627 for (; !tsi_end_p (i); tsi_next (&i))
3629 tree stmt = tsi_stmt (i);
3630 tree type = CATCH_TYPES (stmt);
3631 tree body = CATCH_BODY (stmt);
3643 if (type == error_mark_node)
3644 cond = error_mark_node;
3647 args = tree_cons (NULL, cur_try_context->caught_decl, NULL);
3648 t = objc_get_class_reference (OBJC_TYPE_NAME (TREE_TYPE (type)));
3649 args = tree_cons (NULL, t, args);
3650 t = build_function_call (input_location,
3651 objc_exception_match_decl, args);
3652 cond = c_common_truthvalue_conversion (input_location, t);
3654 t = build3 (COND_EXPR, void_type_node, cond, body, NULL);
3655 SET_EXPR_LOCATION (t, EXPR_LOCATION (stmt));
3658 last = &COND_EXPR_ELSE (t);
3664 t = build2 (MODIFY_EXPR, void_type_node, cur_try_context->rethrow_decl,
3665 cur_try_context->caught_decl);
3666 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3667 append_to_statement_list (t, last);
3669 t = next_sjlj_build_try_exit ();
3670 SET_EXPR_LOCATION (t, cur_try_context->end_catch_locus);
3671 append_to_statement_list (t, last);
3677 /* Build a complete @try-@catch-@finally block for legacy Darwin setjmp
3678 exception handling. We aim to build:
3681 struct _objc_exception_data _stack;
3685 objc_exception_try_enter (&_stack);
3686 if (_setjmp(&_stack.buf))
3688 id _caught = objc_exception_extract(&_stack);
3689 objc_exception_try_enter (&_stack);
3690 if (_setjmp(&_stack.buf))
3691 _rethrow = objc_exception_extract(&_stack);
3701 objc_exception_try_exit(&_stack);
3704 objc_exception_throw(_rethrow);
3708 If CATCH-LIST is empty, we can omit all of the block containing
3709 "_caught" except for the setting of _rethrow. Note the use of
3710 a real TRY_FINALLY_EXPR here, which is not involved in EH per-se,
3711 but handles goto and other exits from the block. */
3714 next_sjlj_build_try_catch_finally (void)
3716 tree rethrow_decl, stack_decl, t;
3717 tree catch_seq, try_fin, bind;
3719 /* Create the declarations involved. */
3720 t = xref_tag (RECORD_TYPE, get_identifier (UTAG_EXCDATA));
3721 stack_decl = objc_create_temporary_var (t);
3722 cur_try_context->stack_decl = stack_decl;
3724 rethrow_decl = objc_create_temporary_var (objc_object_type);
3725 cur_try_context->rethrow_decl = rethrow_decl;
3726 TREE_CHAIN (rethrow_decl) = stack_decl;
3728 /* Build the outermost variable binding level. */
3729 bind = build3 (BIND_EXPR, void_type_node, rethrow_decl, NULL, NULL);
3730 SET_EXPR_LOCATION (bind, cur_try_context->try_locus);
3731 TREE_SIDE_EFFECTS (bind) = 1;
3733 /* Initialize rethrow_decl. */
3734 t = build2 (MODIFY_EXPR, void_type_node, rethrow_decl,
3735 convert (objc_object_type, null_pointer_node));
3736 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3737 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
3739 /* Build the outermost TRY_FINALLY_EXPR. */
3740 try_fin = build2 (TRY_FINALLY_EXPR, void_type_node, NULL, NULL);
3741 SET_EXPR_LOCATION (try_fin, cur_try_context->try_locus);
3742 TREE_SIDE_EFFECTS (try_fin) = 1;
3743 append_to_statement_list (try_fin, &BIND_EXPR_BODY (bind));
3745 /* Create the complete catch sequence. */
3746 if (cur_try_context->catch_list)
3748 tree caught_decl = objc_build_exc_ptr ();
3749 catch_seq = build_stmt (input_location, BIND_EXPR, caught_decl, NULL, NULL);
3750 TREE_SIDE_EFFECTS (catch_seq) = 1;
3752 t = next_sjlj_build_exc_extract (caught_decl);
3753 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3755 t = next_sjlj_build_enter_and_setjmp ();
3756 COND_EXPR_THEN (t) = next_sjlj_build_exc_extract (rethrow_decl);
3757 COND_EXPR_ELSE (t) = next_sjlj_build_catch_list ();
3758 append_to_statement_list (t, &BIND_EXPR_BODY (catch_seq));
3761 catch_seq = next_sjlj_build_exc_extract (rethrow_decl);
3762 SET_EXPR_LOCATION (catch_seq, cur_try_context->end_try_locus);
3764 /* Build the main register-and-try if statement. */
3765 t = next_sjlj_build_enter_and_setjmp ();
3766 SET_EXPR_LOCATION (t, cur_try_context->try_locus);
3767 COND_EXPR_THEN (t) = catch_seq;
3768 COND_EXPR_ELSE (t) = cur_try_context->try_body;
3769 TREE_OPERAND (try_fin, 0) = t;
3771 /* Build the complete FINALLY statement list. */
3772 t = next_sjlj_build_try_exit ();
3773 t = build_stmt (input_location, COND_EXPR,
3774 c_common_truthvalue_conversion
3775 (input_location, rethrow_decl),
3777 SET_EXPR_LOCATION (t, cur_try_context->finally_locus);
3778 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3780 append_to_statement_list (cur_try_context->finally_body,
3781 &TREE_OPERAND (try_fin, 1));
3783 t = tree_cons (NULL, rethrow_decl, NULL);
3784 t = build_function_call (input_location,
3785 objc_exception_throw_decl, t);
3786 t = build_stmt (input_location, COND_EXPR,
3787 c_common_truthvalue_conversion (input_location,
3790 SET_EXPR_LOCATION (t, cur_try_context->end_finally_locus);
3791 append_to_statement_list (t, &TREE_OPERAND (try_fin, 1));
3796 /* Called just after parsing the @try and its associated BODY. We now
3797 must prepare for the tricky bits -- handling the catches and finally. */
3800 objc_begin_try_stmt (location_t try_locus, tree body)
3802 struct objc_try_context *c = XCNEW (struct objc_try_context);
3803 c->outer = cur_try_context;
3805 c->try_locus = try_locus;
3806 c->end_try_locus = input_location;
3807 cur_try_context = c;
3809 if (flag_objc_sjlj_exceptions)
3811 /* On Darwin, ObjC exceptions require a sufficiently recent
3812 version of the runtime, so the user must ask for them explicitly. */
3813 if (!flag_objc_exceptions)
3814 warning (0, "use %<-fobjc-exceptions%> to enable Objective-C "
3815 "exception syntax");
3818 if (flag_objc_sjlj_exceptions)
3819 objc_mark_locals_volatile (NULL);
3822 /* Called just after parsing "@catch (parm)". Open a binding level,
3823 enter DECL into the binding level, and initialize it. Leave the
3824 binding level open while the body of the compound statement is parsed. */
3827 objc_begin_catch_clause (tree decl)
3829 tree compound, type, t;
3831 /* Begin a new scope that the entire catch clause will live in. */
3832 compound = c_begin_compound_stmt (true);
3834 /* The parser passed in a PARM_DECL, but what we really want is a VAR_DECL. */
3835 decl = build_decl (input_location,
3836 VAR_DECL, DECL_NAME (decl), TREE_TYPE (decl));
3837 lang_hooks.decls.pushdecl (decl);
3839 /* Since a decl is required here by syntax, don't warn if its unused. */
3840 /* ??? As opposed to __attribute__((unused))? Anyway, this appears to
3841 be what the previous objc implementation did. */
3842 TREE_USED (decl) = 1;
3844 /* Verify that the type of the catch is valid. It must be a pointer
3845 to an Objective-C class, or "id" (which is catch-all). */
3846 type = TREE_TYPE (decl);
3848 if (POINTER_TYPE_P (type) && objc_is_object_id (TREE_TYPE (type)))
3850 else if (!POINTER_TYPE_P (type) || !TYPED_OBJECT (TREE_TYPE (type)))
3852 error ("@catch parameter is not a known Objective-C class type");
3853 type = error_mark_node;
3855 else if (cur_try_context->catch_list)
3857 /* Examine previous @catch clauses and see if we've already
3858 caught the type in question. */
3859 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
3860 for (; !tsi_end_p (i); tsi_next (&i))
3862 tree stmt = tsi_stmt (i);
3863 t = CATCH_TYPES (stmt);
3864 if (t == error_mark_node)
3866 if (!t || DERIVED_FROM_P (TREE_TYPE (t), TREE_TYPE (type)))
3868 warning (0, "exception of type %<%T%> will be caught",
3870 warning_at (EXPR_LOCATION (stmt), 0, " by earlier handler for %<%T%>",
3871 TREE_TYPE (t ? t : objc_object_type));
3877 /* Record the data for the catch in the try context so that we can
3878 finalize it later. */
3879 t = build_stmt (input_location, CATCH_EXPR, type, compound);
3880 cur_try_context->current_catch = t;
3882 /* Initialize the decl from the EXC_PTR_EXPR we get from the runtime. */
3883 t = objc_build_exc_ptr ();
3884 t = convert (TREE_TYPE (decl), t);
3885 t = build2 (MODIFY_EXPR, void_type_node, decl, t);
3889 /* Called just after parsing the closing brace of a @catch clause. Close
3890 the open binding level, and record a CATCH_EXPR for it. */
3893 objc_finish_catch_clause (void)
3895 tree c = cur_try_context->current_catch;
3896 cur_try_context->current_catch = NULL;
3897 cur_try_context->end_catch_locus = input_location;
3899 CATCH_BODY (c) = c_end_compound_stmt (input_location, CATCH_BODY (c), 1);
3900 append_to_statement_list (c, &cur_try_context->catch_list);
3903 /* Called after parsing a @finally clause and its associated BODY.
3904 Record the body for later placement. */
3907 objc_build_finally_clause (location_t finally_locus, tree body)
3909 cur_try_context->finally_body = body;
3910 cur_try_context->finally_locus = finally_locus;
3911 cur_try_context->end_finally_locus = input_location;
3914 /* Called to finalize a @try construct. */
3917 objc_finish_try_stmt (void)
3919 struct objc_try_context *c = cur_try_context;
3922 if (c->catch_list == NULL && c->finally_body == NULL)
3923 error ("%<@try%> without %<@catch%> or %<@finally%>");
3925 /* If we're doing Darwin setjmp exceptions, build the big nasty. */
3926 if (flag_objc_sjlj_exceptions)
3928 bool save = in_late_binary_op;
3929 in_late_binary_op = true;
3930 if (!cur_try_context->finally_body)
3932 cur_try_context->finally_locus = input_location;
3933 cur_try_context->end_finally_locus = input_location;
3935 stmt = next_sjlj_build_try_catch_finally ();
3936 in_late_binary_op = save;
3940 /* Otherwise, nest the CATCH inside a FINALLY. */
3944 stmt = build_stmt (input_location, TRY_CATCH_EXPR, stmt, c->catch_list);
3945 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
3947 if (c->finally_body)
3949 stmt = build_stmt (input_location, TRY_FINALLY_EXPR, stmt, c->finally_body);
3950 SET_EXPR_LOCATION (stmt, cur_try_context->try_locus);
3955 cur_try_context = c->outer;
3961 objc_build_throw_stmt (location_t loc, tree throw_expr)
3965 if (flag_objc_sjlj_exceptions)
3967 /* On Darwin, ObjC exceptions require a sufficiently recent
3968 version of the runtime, so the user must ask for them explicitly. */
3969 if (!flag_objc_exceptions)
3970 warning (0, "use %<-fobjc-exceptions%> to enable Objective-C "
3971 "exception syntax");
3974 if (throw_expr == NULL)
3976 /* If we're not inside a @catch block, there is no "current
3977 exception" to be rethrown. */
3978 if (cur_try_context == NULL
3979 || cur_try_context->current_catch == NULL)
3981 error_at (loc, "%<@throw%> (rethrow) used outside of a @catch block");
3985 /* Otherwise the object is still sitting in the EXC_PTR_EXPR
3986 value that we get from the runtime. */
3987 throw_expr = objc_build_exc_ptr ();
3990 /* A throw is just a call to the runtime throw function with the
3991 object as a parameter. */
3992 args = tree_cons (NULL, throw_expr, NULL);
3993 return add_stmt (build_function_call (loc,
3994 objc_exception_throw_decl, args));
3998 objc_build_synchronized (location_t start_locus, tree mutex, tree body)
4002 /* First lock the mutex. */
4003 mutex = save_expr (mutex);
4004 args = tree_cons (NULL, mutex, NULL);
4005 call = build_function_call (input_location,
4006 objc_sync_enter_decl, args);
4007 SET_EXPR_LOCATION (call, start_locus);
4010 /* Build the mutex unlock. */
4011 args = tree_cons (NULL, mutex, NULL);
4012 call = build_function_call (input_location,
4013 objc_sync_exit_decl, args);
4014 SET_EXPR_LOCATION (call, input_location);
4016 /* Put the that and the body in a TRY_FINALLY. */
4017 objc_begin_try_stmt (start_locus, body);
4018 objc_build_finally_clause (input_location, call);
4019 return objc_finish_try_stmt ();
4023 /* Predefine the following data type:
4025 struct _objc_exception_data
4027 int buf[OBJC_JBLEN];
4031 /* The following yuckiness should prevent users from having to #include
4032 <setjmp.h> in their code... */
4034 /* Define to a harmless positive value so the below code doesn't die. */
4036 #define OBJC_JBLEN 18
4040 build_next_objc_exception_stuff (void)
4042 tree field_decl, field_decl_chain, index, temp_type;
4044 objc_exception_data_template
4045 = objc_start_struct (get_identifier (UTAG_EXCDATA));
4047 /* int buf[OBJC_JBLEN]; */
4049 index = build_index_type (build_int_cst (NULL_TREE, OBJC_JBLEN - 1));
4050 field_decl = create_field_decl (build_array_type (integer_type_node, index),
4052 field_decl_chain = field_decl;
4054 /* void *pointers[4]; */
4056 index = build_index_type (build_int_cst (NULL_TREE, 4 - 1));
4057 field_decl = create_field_decl (build_array_type (ptr_type_node, index),
4059 chainon (field_decl_chain, field_decl);
4061 objc_finish_struct (objc_exception_data_template, field_decl_chain);
4063 /* int _setjmp(...); */
4064 /* If the user includes <setjmp.h>, this shall be superseded by
4065 'int _setjmp(jmp_buf);' */
4066 temp_type = build_function_type (integer_type_node, NULL_TREE);
4068 = add_builtin_function (TAG_SETJMP, temp_type, 0, NOT_BUILT_IN, NULL, NULL_TREE);
4070 /* id objc_exception_extract(struct _objc_exception_data *); */
4072 = build_function_type (objc_object_type,
4073 tree_cons (NULL_TREE,
4074 build_pointer_type (objc_exception_data_template),
4076 objc_exception_extract_decl
4077 = add_builtin_function (TAG_EXCEPTIONEXTRACT, temp_type, 0, NOT_BUILT_IN, NULL,
4079 /* void objc_exception_try_enter(struct _objc_exception_data *); */
4080 /* void objc_exception_try_exit(struct _objc_exception_data *); */
4082 = build_function_type (void_type_node,
4083 tree_cons (NULL_TREE,
4084 build_pointer_type (objc_exception_data_template),
4086 objc_exception_try_enter_decl
4087 = add_builtin_function (TAG_EXCEPTIONTRYENTER, temp_type, 0, NOT_BUILT_IN, NULL,
4089 objc_exception_try_exit_decl
4090 = add_builtin_function (TAG_EXCEPTIONTRYEXIT, temp_type, 0, NOT_BUILT_IN, NULL,
4093 /* int objc_exception_match(id, id); */
4095 = build_function_type (integer_type_node,
4096 tree_cons (NULL_TREE, objc_object_type,
4097 tree_cons (NULL_TREE, objc_object_type,
4098 OBJC_VOID_AT_END)));
4099 objc_exception_match_decl
4100 = add_builtin_function (TAG_EXCEPTIONMATCH, temp_type, 0, NOT_BUILT_IN, NULL,
4103 /* id objc_assign_ivar (id, id, unsigned int); */
4104 /* id objc_assign_ivar_Fast (id, id, unsigned int)
4105 __attribute__ ((hard_coded_address (OFFS_ASSIGNIVAR_FAST))); */
4107 = build_function_type (objc_object_type,
4109 (NULL_TREE, objc_object_type,
4110 tree_cons (NULL_TREE, objc_object_type,
4111 tree_cons (NULL_TREE,
4113 OBJC_VOID_AT_END))));
4114 objc_assign_ivar_decl
4115 = add_builtin_function (TAG_ASSIGNIVAR, temp_type, 0, NOT_BUILT_IN,
4117 #ifdef OFFS_ASSIGNIVAR_FAST
4118 objc_assign_ivar_fast_decl
4119 = add_builtin_function (TAG_ASSIGNIVAR_FAST, temp_type, 0,
4120 NOT_BUILT_IN, NULL, NULL_TREE);
4121 DECL_ATTRIBUTES (objc_assign_ivar_fast_decl)
4122 = tree_cons (get_identifier ("hard_coded_address"),
4123 build_int_cst (NULL_TREE, OFFS_ASSIGNIVAR_FAST),
4126 /* Default to slower ivar method. */
4127 objc_assign_ivar_fast_decl = objc_assign_ivar_decl;
4130 /* id objc_assign_global (id, id *); */
4131 /* id objc_assign_strongCast (id, id *); */
4132 temp_type = build_function_type (objc_object_type,
4133 tree_cons (NULL_TREE, objc_object_type,
4134 tree_cons (NULL_TREE, build_pointer_type (objc_object_type),
4135 OBJC_VOID_AT_END)));
4136 objc_assign_global_decl
4137 = add_builtin_function (TAG_ASSIGNGLOBAL, temp_type, 0, NOT_BUILT_IN, NULL,
4139 objc_assign_strong_cast_decl
4140 = add_builtin_function (TAG_ASSIGNSTRONGCAST, temp_type, 0, NOT_BUILT_IN, NULL,
4145 build_objc_exception_stuff (void)
4147 tree noreturn_list, nothrow_list, temp_type;
4149 noreturn_list = tree_cons (get_identifier ("noreturn"), NULL, NULL);
4150 nothrow_list = tree_cons (get_identifier ("nothrow"), NULL, NULL);
4152 /* void objc_exception_throw(id) __attribute__((noreturn)); */
4153 /* void objc_sync_enter(id); */
4154 /* void objc_sync_exit(id); */
4155 temp_type = build_function_type (void_type_node,
4156 tree_cons (NULL_TREE, objc_object_type,
4158 objc_exception_throw_decl
4159 = add_builtin_function (TAG_EXCEPTIONTHROW, temp_type, 0, NOT_BUILT_IN, NULL,
4161 objc_sync_enter_decl
4162 = add_builtin_function (TAG_SYNCENTER, temp_type, 0, NOT_BUILT_IN,
4163 NULL, nothrow_list);
4165 = add_builtin_function (TAG_SYNCEXIT, temp_type, 0, NOT_BUILT_IN,
4166 NULL, nothrow_list);
4169 /* Construct a C struct corresponding to ObjC class CLASS, with the same
4172 struct <classname> {
4173 struct _objc_class *isa;
4178 build_private_template (tree klass)
4180 if (!CLASS_STATIC_TEMPLATE (klass))
4182 tree record = objc_build_struct (klass,
4183 get_class_ivars (klass, false),
4184 CLASS_SUPER_NAME (klass));
4186 /* Set the TREE_USED bit for this struct, so that stab generator
4187 can emit stabs for this struct type. */
4188 if (flag_debug_only_used_symbols && TYPE_STUB_DECL (record))
4189 TREE_USED (TYPE_STUB_DECL (record)) = 1;
4193 /* Begin code generation for protocols... */
4195 /* struct _objc_protocol {
4196 struct _objc_class *isa;
4197 char *protocol_name;
4198 struct _objc_protocol **protocol_list;
4199 struct _objc__method_prototype_list *instance_methods;
4200 struct _objc__method_prototype_list *class_methods;
4204 build_protocol_template (void)
4206 tree field_decl, field_decl_chain;
4208 objc_protocol_template = objc_start_struct (get_identifier (UTAG_PROTOCOL));
4210 /* struct _objc_class *isa; */
4211 field_decl = create_field_decl (build_pointer_type
4212 (xref_tag (RECORD_TYPE,
4213 get_identifier (UTAG_CLASS))),
4215 field_decl_chain = field_decl;
4217 /* char *protocol_name; */
4218 field_decl = create_field_decl (string_type_node, "protocol_name");
4219 chainon (field_decl_chain, field_decl);
4221 /* struct _objc_protocol **protocol_list; */
4222 field_decl = create_field_decl (build_pointer_type
4224 (objc_protocol_template)),
4226 chainon (field_decl_chain, field_decl);
4228 /* struct _objc__method_prototype_list *instance_methods; */
4229 field_decl = create_field_decl (objc_method_proto_list_ptr,
4230 "instance_methods");
4231 chainon (field_decl_chain, field_decl);
4233 /* struct _objc__method_prototype_list *class_methods; */
4234 field_decl = create_field_decl (objc_method_proto_list_ptr,
4236 chainon (field_decl_chain, field_decl);
4238 objc_finish_struct (objc_protocol_template, field_decl_chain);
4242 build_descriptor_table_initializer (tree type, tree entries)
4244 tree initlist = NULL_TREE;
4248 tree eltlist = NULL_TREE;
4251 = tree_cons (NULL_TREE,
4252 build_selector (METHOD_SEL_NAME (entries)), NULL_TREE);
4254 = tree_cons (NULL_TREE,
4255 add_objc_string (METHOD_ENCODING (entries),
4260 = tree_cons (NULL_TREE,
4261 objc_build_constructor (type, nreverse (eltlist)),
4264 entries = TREE_CHAIN (entries);
4268 return objc_build_constructor (build_array_type (type, 0),
4269 nreverse (initlist));
4272 /* struct objc_method_prototype_list {
4274 struct objc_method_prototype {
4281 build_method_prototype_list_template (tree list_type, int size)
4283 tree objc_ivar_list_record;
4284 tree field_decl, field_decl_chain;
4286 /* Generate an unnamed struct definition. */
4288 objc_ivar_list_record = objc_start_struct (NULL_TREE);
4290 /* int method_count; */
4291 field_decl = create_field_decl (integer_type_node, "method_count");
4292 field_decl_chain = field_decl;
4294 /* struct objc_method method_list[]; */
4295 field_decl = create_field_decl (build_array_type
4298 (build_int_cst (NULL_TREE, size - 1))),
4300 chainon (field_decl_chain, field_decl);
4302 objc_finish_struct (objc_ivar_list_record, field_decl_chain);
4304 return objc_ivar_list_record;
4308 build_method_prototype_template (void)
4311 tree field_decl, field_decl_chain;
4313 proto_record = objc_start_struct (get_identifier (UTAG_METHOD_PROTOTYPE));
4316 field_decl = create_field_decl (objc_selector_type, "_cmd");
4317 field_decl_chain = field_decl;
4319 /* char *method_types; */
4320 field_decl = create_field_decl (string_type_node, "method_types");
4321 chainon (field_decl_chain, field_decl);
4323 objc_finish_struct (proto_record, field_decl_chain);
4325 return proto_record;
4329 objc_method_parm_type (tree type)
4331 type = TREE_VALUE (TREE_TYPE (type));
4332 if (TREE_CODE (type) == TYPE_DECL)
4333 type = TREE_TYPE (type);
4338 objc_encoded_type_size (tree type)
4340 int sz = int_size_in_bytes (type);
4342 /* Make all integer and enum types at least as large
4344 if (sz > 0 && INTEGRAL_TYPE_P (type))
4345 sz = MAX (sz, int_size_in_bytes (integer_type_node));
4346 /* Treat arrays as pointers, since that's how they're
4348 else if (TREE_CODE (type) == ARRAY_TYPE)
4349 sz = int_size_in_bytes (ptr_type_node);
4354 encode_method_prototype (tree method_decl)
4361 /* ONEWAY and BYCOPY, for remote object are the only method qualifiers. */
4362 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (method_decl)));
4364 /* Encode return type. */
4365 encode_type (objc_method_parm_type (method_decl),
4366 obstack_object_size (&util_obstack),
4367 OBJC_ENCODE_INLINE_DEFS);
4370 /* The first two arguments (self and _cmd) are pointers; account for
4372 i = int_size_in_bytes (ptr_type_node);
4373 parm_offset = 2 * i;
4374 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4375 parms = TREE_CHAIN (parms))
4377 tree type = objc_method_parm_type (parms);
4378 int sz = objc_encoded_type_size (type);
4380 /* If a type size is not known, bail out. */
4383 error ("type %q+D does not have a known size",
4385 /* Pretend that the encoding succeeded; the compilation will
4386 fail nevertheless. */
4387 goto finish_encoding;
4392 sprintf (buf, "%d@0:%d", parm_offset, i);
4393 obstack_grow (&util_obstack, buf, strlen (buf));
4395 /* Argument types. */
4396 parm_offset = 2 * i;
4397 for (parms = METHOD_SEL_ARGS (method_decl); parms;
4398 parms = TREE_CHAIN (parms))
4400 tree type = objc_method_parm_type (parms);
4402 /* Process argument qualifiers for user supplied arguments. */
4403 encode_type_qualifiers (TREE_PURPOSE (TREE_TYPE (parms)));
4406 encode_type (type, obstack_object_size (&util_obstack),
4407 OBJC_ENCODE_INLINE_DEFS);
4409 /* Compute offset. */
4410 sprintf (buf, "%d", parm_offset);
4411 parm_offset += objc_encoded_type_size (type);
4413 obstack_grow (&util_obstack, buf, strlen (buf));
4417 obstack_1grow (&util_obstack, '\0');
4418 result = get_identifier (XOBFINISH (&util_obstack, char *));
4419 obstack_free (&util_obstack, util_firstobj);
4424 generate_descriptor_table (tree type, const char *name, int size, tree list,
4427 tree decl, initlist;
4429 decl = start_var_decl (type, synth_id_with_class_suffix (name, proto));
4431 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, size));
4432 initlist = tree_cons (NULL_TREE, list, initlist);
4434 finish_var_decl (decl, objc_build_constructor (type, nreverse (initlist)));
4440 generate_method_descriptors (tree protocol)
4442 tree initlist, chain, method_list_template;
4445 if (!objc_method_prototype_template)
4446 objc_method_prototype_template = build_method_prototype_template ();
4448 chain = PROTOCOL_CLS_METHODS (protocol);
4451 size = list_length (chain);
4453 method_list_template
4454 = build_method_prototype_list_template (objc_method_prototype_template,
4458 = build_descriptor_table_initializer (objc_method_prototype_template,
4461 UOBJC_CLASS_METHODS_decl
4462 = generate_descriptor_table (method_list_template,
4463 "_OBJC_PROTOCOL_CLASS_METHODS",
4464 size, initlist, protocol);
4467 UOBJC_CLASS_METHODS_decl = 0;
4469 chain = PROTOCOL_NST_METHODS (protocol);
4472 size = list_length (chain);
4474 method_list_template
4475 = build_method_prototype_list_template (objc_method_prototype_template,
4478 = build_descriptor_table_initializer (objc_method_prototype_template,
4481 UOBJC_INSTANCE_METHODS_decl
4482 = generate_descriptor_table (method_list_template,
4483 "_OBJC_PROTOCOL_INSTANCE_METHODS",
4484 size, initlist, protocol);
4487 UOBJC_INSTANCE_METHODS_decl = 0;
4491 generate_protocol_references (tree plist)
4495 /* Forward declare protocols referenced. */
4496 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
4498 tree proto = TREE_VALUE (lproto);
4500 if (TREE_CODE (proto) == PROTOCOL_INTERFACE_TYPE
4501 && PROTOCOL_NAME (proto))
4503 if (! PROTOCOL_FORWARD_DECL (proto))
4504 build_protocol_reference (proto);
4506 if (PROTOCOL_LIST (proto))
4507 generate_protocol_references (PROTOCOL_LIST (proto));
4512 /* Generate either '- .cxx_construct' or '- .cxx_destruct' for the
4516 objc_generate_cxx_ctor_or_dtor (bool dtor)
4518 tree fn, body, compound_stmt, ivar;
4520 /* - (id) .cxx_construct { ... return self; } */
4521 /* - (void) .cxx_construct { ... } */
4523 objc_set_method_type (MINUS_EXPR);
4524 objc_start_method_definition
4525 (objc_build_method_signature (build_tree_list (NULL_TREE,
4528 : objc_object_type),
4529 get_identifier (dtor
4531 : TAG_CXX_CONSTRUCT),
4532 make_node (TREE_LIST),
4534 body = begin_function_body ();
4535 compound_stmt = begin_compound_stmt (0);
4537 ivar = CLASS_IVARS (implementation_template);
4538 /* Destroy ivars in reverse order. */
4540 ivar = nreverse (copy_list (ivar));
4542 for (; ivar; ivar = TREE_CHAIN (ivar))
4544 if (TREE_CODE (ivar) == FIELD_DECL)
4546 tree type = TREE_TYPE (ivar);
4548 /* Call the ivar's default constructor or destructor. Do not
4549 call the destructor unless a corresponding constructor call
4550 has also been made (or is not needed). */
4551 if (MAYBE_CLASS_TYPE_P (type)
4553 ? (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4554 && (!TYPE_NEEDS_CONSTRUCTING (type)
4555 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4556 : (TYPE_NEEDS_CONSTRUCTING (type)
4557 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))))
4559 (build_special_member_call
4560 (build_ivar_reference (DECL_NAME (ivar)),
4561 dtor ? complete_dtor_identifier : complete_ctor_identifier,
4562 NULL, type, LOOKUP_NORMAL, tf_warning_or_error));
4566 /* The constructor returns 'self'. */
4568 finish_return_stmt (self_decl);
4570 finish_compound_stmt (compound_stmt);
4571 finish_function_body (body);
4572 fn = current_function_decl;
4574 objc_finish_method_definition (fn);
4577 /* The following routine will examine the current @interface for any
4578 non-POD C++ ivars requiring non-trivial construction and/or
4579 destruction, and then synthesize special '- .cxx_construct' and/or
4580 '- .cxx_destruct' methods which will run the appropriate
4581 construction or destruction code. Note that ivars inherited from
4582 super-classes are _not_ considered. */
4584 objc_generate_cxx_cdtors (void)
4586 bool need_ctor = false, need_dtor = false;
4589 /* We do not want to do this for categories, since they do not have
4592 if (TREE_CODE (objc_implementation_context) != CLASS_IMPLEMENTATION_TYPE)
4595 /* First, determine if we even need a constructor and/or destructor. */
4597 for (ivar = CLASS_IVARS (implementation_template); ivar;
4598 ivar = TREE_CHAIN (ivar))
4600 if (TREE_CODE (ivar) == FIELD_DECL)
4602 tree type = TREE_TYPE (ivar);
4604 if (MAYBE_CLASS_TYPE_P (type))
4606 if (TYPE_NEEDS_CONSTRUCTING (type)
4607 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
4608 /* NB: If a default constructor is not available, we will not
4609 be able to initialize this ivar; the add_instance_variable()
4610 routine will already have warned about this. */
4613 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4614 && (!TYPE_NEEDS_CONSTRUCTING (type)
4615 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4616 /* NB: If a default constructor is not available, we will not
4617 call the destructor either, for symmetry. */
4623 /* Generate '- .cxx_construct' if needed. */
4626 objc_generate_cxx_ctor_or_dtor (false);
4628 /* Generate '- .cxx_destruct' if needed. */
4631 objc_generate_cxx_ctor_or_dtor (true);
4633 /* The 'imp_list' variable points at an imp_entry record for the current
4634 @implementation. Record the existence of '- .cxx_construct' and/or
4635 '- .cxx_destruct' methods therein; it will be included in the
4636 metadata for the class. */
4637 if (flag_next_runtime)
4638 imp_list->has_cxx_cdtors = (need_ctor || need_dtor);
4642 /* For each protocol which was referenced either from a @protocol()
4643 expression, or because a class/category implements it (then a
4644 pointer to the protocol is stored in the struct describing the
4645 class/category), we create a statically allocated instance of the
4646 Protocol class. The code is written in such a way as to generate
4647 as few Protocol objects as possible; we generate a unique Protocol
4648 instance for each protocol, and we don't generate a Protocol
4649 instance if the protocol is never referenced (either from a
4650 @protocol() or from a class/category implementation). These
4651 statically allocated objects can be referred to via the static
4652 (that is, private to this module) symbols _OBJC_PROTOCOL_n.
4654 The statically allocated Protocol objects that we generate here
4655 need to be fixed up at runtime in order to be used: the 'isa'
4656 pointer of the objects need to be set up to point to the 'Protocol'
4657 class, as known at runtime.
4659 The NeXT runtime fixes up all protocols at program startup time,
4660 before main() is entered. It uses a low-level trick to look up all
4661 those symbols, then loops on them and fixes them up.
4663 The GNU runtime as well fixes up all protocols before user code
4664 from the module is executed; it requires pointers to those symbols
4665 to be put in the objc_symtab (which is then passed as argument to
4666 the function __objc_exec_class() which the compiler sets up to be
4667 executed automatically when the module is loaded); setup of those
4668 Protocol objects happen in two ways in the GNU runtime: all
4669 Protocol objects referred to by a class or category implementation
4670 are fixed up when the class/category is loaded; all Protocol
4671 objects referred to by a @protocol() expression are added by the
4672 compiler to the list of statically allocated instances to fixup
4673 (the same list holding the statically allocated constant string
4674 objects). Because, as explained above, the compiler generates as
4675 few Protocol objects as possible, some Protocol object might end up
4676 being referenced multiple times when compiled with the GNU runtime,
4677 and end up being fixed up multiple times at runtime initialization.
4678 But that doesn't hurt, it's just a little inefficient. */
4681 generate_protocols (void)
4685 tree initlist, protocol_name_expr, refs_decl, refs_expr;
4687 /* If a protocol was directly referenced, pull in indirect references. */
4688 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4689 if (PROTOCOL_FORWARD_DECL (p) && PROTOCOL_LIST (p))
4690 generate_protocol_references (PROTOCOL_LIST (p));
4692 for (p = protocol_chain; p; p = TREE_CHAIN (p))
4694 tree nst_methods = PROTOCOL_NST_METHODS (p);
4695 tree cls_methods = PROTOCOL_CLS_METHODS (p);
4697 /* If protocol wasn't referenced, don't generate any code. */
4698 decl = PROTOCOL_FORWARD_DECL (p);
4703 /* Make sure we link in the Protocol class. */
4704 add_class_reference (get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
4708 if (! METHOD_ENCODING (nst_methods))
4710 encoding = encode_method_prototype (nst_methods);
4711 METHOD_ENCODING (nst_methods) = encoding;
4713 nst_methods = TREE_CHAIN (nst_methods);
4718 if (! METHOD_ENCODING (cls_methods))
4720 encoding = encode_method_prototype (cls_methods);
4721 METHOD_ENCODING (cls_methods) = encoding;
4724 cls_methods = TREE_CHAIN (cls_methods);
4726 generate_method_descriptors (p);
4728 if (PROTOCOL_LIST (p))
4729 refs_decl = generate_protocol_list (p);
4733 /* static struct objc_protocol _OBJC_PROTOCOL_<mumble>; */
4734 protocol_name_expr = add_objc_string (PROTOCOL_NAME (p), class_names);
4737 refs_expr = convert (build_pointer_type (build_pointer_type
4738 (objc_protocol_template)),
4739 build_unary_op (input_location,
4740 ADDR_EXPR, refs_decl, 0));
4742 refs_expr = build_int_cst (NULL_TREE, 0);
4744 /* UOBJC_INSTANCE_METHODS_decl/UOBJC_CLASS_METHODS_decl are set
4745 by generate_method_descriptors, which is called above. */
4746 initlist = build_protocol_initializer (TREE_TYPE (decl),
4747 protocol_name_expr, refs_expr,
4748 UOBJC_INSTANCE_METHODS_decl,
4749 UOBJC_CLASS_METHODS_decl);
4750 finish_var_decl (decl, initlist);
4755 build_protocol_initializer (tree type, tree protocol_name,
4756 tree protocol_list, tree instance_methods,
4759 tree initlist = NULL_TREE, expr;
4760 tree cast_type = build_pointer_type
4761 (xref_tag (RECORD_TYPE,
4762 get_identifier (UTAG_CLASS)));
4764 /* Filling the "isa" in with one allows the runtime system to
4765 detect that the version change...should remove before final release. */
4767 expr = build_int_cst (cast_type, PROTOCOL_VERSION);
4768 initlist = tree_cons (NULL_TREE, expr, initlist);
4769 initlist = tree_cons (NULL_TREE, protocol_name, initlist);
4770 initlist = tree_cons (NULL_TREE, protocol_list, initlist);
4772 if (!instance_methods)
4773 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
4776 expr = convert (objc_method_proto_list_ptr,
4777 build_unary_op (input_location,
4778 ADDR_EXPR, instance_methods, 0));
4779 initlist = tree_cons (NULL_TREE, expr, initlist);
4783 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
4786 expr = convert (objc_method_proto_list_ptr,
4787 build_unary_op (input_location,
4788 ADDR_EXPR, class_methods, 0));
4789 initlist = tree_cons (NULL_TREE, expr, initlist);
4792 return objc_build_constructor (type, nreverse (initlist));
4795 /* struct _objc_category {
4796 char *category_name;
4798 struct _objc_method_list *instance_methods;
4799 struct _objc_method_list *class_methods;
4800 struct _objc_protocol_list *protocols;
4804 build_category_template (void)
4806 tree field_decl, field_decl_chain;
4808 objc_category_template = objc_start_struct (get_identifier (UTAG_CATEGORY));
4810 /* char *category_name; */
4811 field_decl = create_field_decl (string_type_node, "category_name");
4812 field_decl_chain = field_decl;
4814 /* char *class_name; */
4815 field_decl = create_field_decl (string_type_node, "class_name");
4816 chainon (field_decl_chain, field_decl);
4818 /* struct _objc_method_list *instance_methods; */
4819 field_decl = create_field_decl (objc_method_list_ptr,
4820 "instance_methods");
4821 chainon (field_decl_chain, field_decl);
4823 /* struct _objc_method_list *class_methods; */
4824 field_decl = create_field_decl (objc_method_list_ptr,
4826 chainon (field_decl_chain, field_decl);
4828 /* struct _objc_protocol **protocol_list; */
4829 field_decl = create_field_decl (build_pointer_type
4831 (objc_protocol_template)),
4833 chainon (field_decl_chain, field_decl);
4835 objc_finish_struct (objc_category_template, field_decl_chain);
4838 /* struct _objc_selector {
4844 build_selector_template (void)
4846 tree field_decl, field_decl_chain;
4848 objc_selector_template = objc_start_struct (get_identifier (UTAG_SELECTOR));
4851 field_decl = create_field_decl (objc_selector_type, "sel_id");
4852 field_decl_chain = field_decl;
4854 /* char *sel_type; */
4855 field_decl = create_field_decl (string_type_node, "sel_type");
4856 chainon (field_decl_chain, field_decl);
4858 objc_finish_struct (objc_selector_template, field_decl_chain);
4861 /* struct _objc_class {
4862 struct _objc_class *isa;
4863 struct _objc_class *super_class;
4868 struct _objc_ivar_list *ivars;
4869 struct _objc_method_list *methods;
4870 #ifdef __NEXT_RUNTIME__
4871 struct objc_cache *cache;
4873 struct sarray *dtable;
4874 struct _objc_class *subclass_list;
4875 struct _objc_class *sibling_class;
4877 struct _objc_protocol_list *protocols;
4878 #ifdef __NEXT_RUNTIME__
4881 void *gc_object_type;
4884 /* NB: The 'sel_id' and 'gc_object_type' fields are not being used by
4885 the NeXT/Apple runtime; still, the compiler must generate them to
4886 maintain backward binary compatibility (and to allow for future
4890 build_class_template (void)
4892 tree field_decl, field_decl_chain;
4894 objc_class_template = objc_start_struct (get_identifier (UTAG_CLASS));
4896 /* struct _objc_class *isa; */
4897 field_decl = create_field_decl (build_pointer_type (objc_class_template),
4899 field_decl_chain = field_decl;
4901 /* struct _objc_class *super_class; */
4902 field_decl = create_field_decl (build_pointer_type (objc_class_template),
4904 chainon (field_decl_chain, field_decl);
4907 field_decl = create_field_decl (string_type_node, "name");
4908 chainon (field_decl_chain, field_decl);
4911 field_decl = create_field_decl (long_integer_type_node, "version");
4912 chainon (field_decl_chain, field_decl);
4915 field_decl = create_field_decl (long_integer_type_node, "info");
4916 chainon (field_decl_chain, field_decl);
4918 /* long instance_size; */
4919 field_decl = create_field_decl (long_integer_type_node, "instance_size");
4920 chainon (field_decl_chain, field_decl);
4922 /* struct _objc_ivar_list *ivars; */
4923 field_decl = create_field_decl (objc_ivar_list_ptr,
4925 chainon (field_decl_chain, field_decl);
4927 /* struct _objc_method_list *methods; */
4928 field_decl = create_field_decl (objc_method_list_ptr,
4930 chainon (field_decl_chain, field_decl);
4932 if (flag_next_runtime)
4934 /* struct objc_cache *cache; */
4935 field_decl = create_field_decl (build_pointer_type
4936 (xref_tag (RECORD_TYPE,
4940 chainon (field_decl_chain, field_decl);
4944 /* struct sarray *dtable; */
4945 field_decl = create_field_decl (build_pointer_type
4946 (xref_tag (RECORD_TYPE,
4950 chainon (field_decl_chain, field_decl);
4952 /* struct objc_class *subclass_list; */
4953 field_decl = create_field_decl (build_pointer_type
4954 (objc_class_template),
4956 chainon (field_decl_chain, field_decl);
4958 /* struct objc_class *sibling_class; */
4959 field_decl = create_field_decl (build_pointer_type
4960 (objc_class_template),
4962 chainon (field_decl_chain, field_decl);
4965 /* struct _objc_protocol **protocol_list; */
4966 field_decl = create_field_decl (build_pointer_type
4968 (xref_tag (RECORD_TYPE,
4972 chainon (field_decl_chain, field_decl);
4974 if (flag_next_runtime)
4977 field_decl = create_field_decl (build_pointer_type (void_type_node),
4979 chainon (field_decl_chain, field_decl);
4982 /* void *gc_object_type; */
4983 field_decl = create_field_decl (build_pointer_type (void_type_node),
4985 chainon (field_decl_chain, field_decl);
4987 objc_finish_struct (objc_class_template, field_decl_chain);
4990 /* Generate appropriate forward declarations for an implementation. */
4993 synth_forward_declarations (void)
4997 /* static struct objc_class _OBJC_CLASS_<my_name>; */
4998 UOBJC_CLASS_decl = build_metadata_decl ("_OBJC_CLASS",
4999 objc_class_template);
5001 /* static struct objc_class _OBJC_METACLASS_<my_name>; */
5002 UOBJC_METACLASS_decl = build_metadata_decl ("_OBJC_METACLASS",
5003 objc_class_template);
5005 /* Pre-build the following entities - for speed/convenience. */
5007 an_id = get_identifier ("super_class");
5008 ucls_super_ref = objc_build_component_ref (UOBJC_CLASS_decl, an_id);
5009 uucls_super_ref = objc_build_component_ref (UOBJC_METACLASS_decl, an_id);
5013 error_with_ivar (const char *message, tree decl)
5015 error_at (DECL_SOURCE_LOCATION (decl), "%s %qs",
5016 message, identifier_to_locale (gen_declaration (decl)));
5021 check_ivars (tree inter, tree imp)
5023 tree intdecls = CLASS_RAW_IVARS (inter);
5024 tree impdecls = CLASS_RAW_IVARS (imp);
5031 if (intdecls && TREE_CODE (intdecls) == TYPE_DECL)
5032 intdecls = TREE_CHAIN (intdecls);
5034 if (intdecls == 0 && impdecls == 0)
5036 if (intdecls == 0 || impdecls == 0)
5038 error ("inconsistent instance variable specification");
5042 t1 = TREE_TYPE (intdecls); t2 = TREE_TYPE (impdecls);
5044 if (!comptypes (t1, t2)
5045 || !tree_int_cst_equal (DECL_INITIAL (intdecls),
5046 DECL_INITIAL (impdecls)))
5048 if (DECL_NAME (intdecls) == DECL_NAME (impdecls))
5050 error_with_ivar ("conflicting instance variable type",
5052 error_with_ivar ("previous declaration of",
5055 else /* both the type and the name don't match */
5057 error ("inconsistent instance variable specification");
5062 else if (DECL_NAME (intdecls) != DECL_NAME (impdecls))
5064 error_with_ivar ("conflicting instance variable name",
5066 error_with_ivar ("previous declaration of",
5070 intdecls = TREE_CHAIN (intdecls);
5071 impdecls = TREE_CHAIN (impdecls);
5075 /* Set 'objc_super_template' to the data type node for 'struct _objc_super'.
5076 This needs to be done just once per compilation. */
5078 /* struct _objc_super {
5079 struct _objc_object *self;
5080 struct _objc_class *super_class;
5084 build_super_template (void)
5086 tree field_decl, field_decl_chain;
5088 objc_super_template = objc_start_struct (get_identifier (UTAG_SUPER));
5090 /* struct _objc_object *self; */
5091 field_decl = create_field_decl (objc_object_type, "self");
5092 field_decl_chain = field_decl;
5094 /* struct _objc_class *super_class; */
5095 field_decl = create_field_decl (build_pointer_type (objc_class_template),
5097 chainon (field_decl_chain, field_decl);
5099 objc_finish_struct (objc_super_template, field_decl_chain);
5102 /* struct _objc_ivar {
5109 build_ivar_template (void)
5111 tree objc_ivar_id, objc_ivar_record;
5112 tree field_decl, field_decl_chain;
5114 objc_ivar_id = get_identifier (UTAG_IVAR);
5115 objc_ivar_record = objc_start_struct (objc_ivar_id);
5117 /* char *ivar_name; */
5118 field_decl = create_field_decl (string_type_node, "ivar_name");
5119 field_decl_chain = field_decl;
5121 /* char *ivar_type; */
5122 field_decl = create_field_decl (string_type_node, "ivar_type");
5123 chainon (field_decl_chain, field_decl);
5125 /* int ivar_offset; */
5126 field_decl = create_field_decl (integer_type_node, "ivar_offset");
5127 chainon (field_decl_chain, field_decl);
5129 objc_finish_struct (objc_ivar_record, field_decl_chain);
5131 return objc_ivar_record;
5136 struct objc_ivar ivar_list[ivar_count];
5140 build_ivar_list_template (tree list_type, int size)
5142 tree objc_ivar_list_record;
5143 tree field_decl, field_decl_chain;
5145 objc_ivar_list_record = objc_start_struct (NULL_TREE);
5147 /* int ivar_count; */
5148 field_decl = create_field_decl (integer_type_node, "ivar_count");
5149 field_decl_chain = field_decl;
5151 /* struct objc_ivar ivar_list[]; */
5152 field_decl = create_field_decl (build_array_type
5155 (build_int_cst (NULL_TREE, size - 1))),
5157 chainon (field_decl_chain, field_decl);
5159 objc_finish_struct (objc_ivar_list_record, field_decl_chain);
5161 return objc_ivar_list_record;
5165 struct _objc__method_prototype_list *method_next;
5167 struct objc_method method_list[method_count];
5171 build_method_list_template (tree list_type, int size)
5173 tree objc_ivar_list_record;
5174 tree field_decl, field_decl_chain;
5176 objc_ivar_list_record = objc_start_struct (NULL_TREE);
5178 /* struct _objc__method_prototype_list *method_next; */
5179 field_decl = create_field_decl (objc_method_proto_list_ptr,
5181 field_decl_chain = field_decl;
5183 /* int method_count; */
5184 field_decl = create_field_decl (integer_type_node, "method_count");
5185 chainon (field_decl_chain, field_decl);
5187 /* struct objc_method method_list[]; */
5188 field_decl = create_field_decl (build_array_type
5191 (build_int_cst (NULL_TREE, size - 1))),
5193 chainon (field_decl_chain, field_decl);
5195 objc_finish_struct (objc_ivar_list_record, field_decl_chain);
5197 return objc_ivar_list_record;
5201 build_ivar_list_initializer (tree type, tree field_decl)
5203 tree initlist = NULL_TREE;
5207 tree ivar = NULL_TREE;
5210 if (DECL_NAME (field_decl))
5211 ivar = tree_cons (NULL_TREE,
5212 add_objc_string (DECL_NAME (field_decl),
5216 /* Unnamed bit-field ivar (yuck). */
5217 ivar = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), ivar);
5220 encode_field_decl (field_decl,
5221 obstack_object_size (&util_obstack),
5222 OBJC_ENCODE_DONT_INLINE_DEFS);
5224 /* Null terminate string. */
5225 obstack_1grow (&util_obstack, 0);
5229 add_objc_string (get_identifier (XOBFINISH (&util_obstack, char *)),
5232 obstack_free (&util_obstack, util_firstobj);
5235 ivar = tree_cons (NULL_TREE, byte_position (field_decl), ivar);
5236 initlist = tree_cons (NULL_TREE,
5237 objc_build_constructor (type, nreverse (ivar)),
5240 field_decl = TREE_CHAIN (field_decl);
5241 while (field_decl && TREE_CODE (field_decl) != FIELD_DECL);
5245 return objc_build_constructor (build_array_type (type, 0),
5246 nreverse (initlist));
5250 generate_ivars_list (tree type, const char *name, int size, tree list)
5252 tree decl, initlist;
5254 decl = start_var_decl (type, synth_id_with_class_suffix
5255 (name, objc_implementation_context));
5257 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, size));
5258 initlist = tree_cons (NULL_TREE, list, initlist);
5260 finish_var_decl (decl,
5261 objc_build_constructor (TREE_TYPE (decl),
5262 nreverse (initlist)));
5267 /* Count only the fields occurring in T. */
5270 ivar_list_length (tree t)
5274 for (; t; t = TREE_CHAIN (t))
5275 if (TREE_CODE (t) == FIELD_DECL)
5282 generate_ivar_lists (void)
5284 tree initlist, ivar_list_template, chain;
5287 generating_instance_variables = 1;
5289 if (!objc_ivar_template)
5290 objc_ivar_template = build_ivar_template ();
5292 /* Only generate class variables for the root of the inheritance
5293 hierarchy since these will be the same for every class. */
5295 if (CLASS_SUPER_NAME (implementation_template) == NULL_TREE
5296 && (chain = TYPE_FIELDS (objc_class_template)))
5298 size = ivar_list_length (chain);
5300 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5301 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5303 UOBJC_CLASS_VARIABLES_decl
5304 = generate_ivars_list (ivar_list_template, "_OBJC_CLASS_VARIABLES",
5308 UOBJC_CLASS_VARIABLES_decl = 0;
5310 chain = CLASS_IVARS (implementation_template);
5313 size = ivar_list_length (chain);
5314 ivar_list_template = build_ivar_list_template (objc_ivar_template, size);
5315 initlist = build_ivar_list_initializer (objc_ivar_template, chain);
5317 UOBJC_INSTANCE_VARIABLES_decl
5318 = generate_ivars_list (ivar_list_template, "_OBJC_INSTANCE_VARIABLES",
5322 UOBJC_INSTANCE_VARIABLES_decl = 0;
5324 generating_instance_variables = 0;
5328 build_dispatch_table_initializer (tree type, tree entries)
5330 tree initlist = NULL_TREE;
5334 tree elemlist = NULL_TREE;
5336 elemlist = tree_cons (NULL_TREE,
5337 build_selector (METHOD_SEL_NAME (entries)),
5340 /* Generate the method encoding if we don't have one already. */
5341 if (! METHOD_ENCODING (entries))
5342 METHOD_ENCODING (entries) =
5343 encode_method_prototype (entries);
5345 elemlist = tree_cons (NULL_TREE,
5346 add_objc_string (METHOD_ENCODING (entries),
5351 = tree_cons (NULL_TREE,
5352 convert (ptr_type_node,
5353 build_unary_op (input_location, ADDR_EXPR,
5354 METHOD_DEFINITION (entries), 1)),
5357 initlist = tree_cons (NULL_TREE,
5358 objc_build_constructor (type, nreverse (elemlist)),
5361 entries = TREE_CHAIN (entries);
5365 return objc_build_constructor (build_array_type (type, 0),
5366 nreverse (initlist));
5369 /* To accomplish method prototyping without generating all kinds of
5370 inane warnings, the definition of the dispatch table entries were
5373 struct objc_method { SEL _cmd; ...; id (*_imp)(); };
5375 struct objc_method { SEL _cmd; ...; void *_imp; }; */
5378 build_method_template (void)
5381 tree field_decl, field_decl_chain;
5383 _SLT_record = objc_start_struct (get_identifier (UTAG_METHOD));
5386 field_decl = create_field_decl (objc_selector_type, "_cmd");
5387 field_decl_chain = field_decl;
5389 /* char *method_types; */
5390 field_decl = create_field_decl (string_type_node, "method_types");
5391 chainon (field_decl_chain, field_decl);
5394 field_decl = create_field_decl (build_pointer_type (void_type_node),
5396 chainon (field_decl_chain, field_decl);
5398 objc_finish_struct (_SLT_record, field_decl_chain);
5405 generate_dispatch_table (tree type, const char *name, int size, tree list)
5407 tree decl, initlist;
5409 decl = start_var_decl (type, synth_id_with_class_suffix
5410 (name, objc_implementation_context));
5412 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, 0));
5413 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, size), initlist);
5414 initlist = tree_cons (NULL_TREE, list, initlist);
5416 finish_var_decl (decl,
5417 objc_build_constructor (TREE_TYPE (decl),
5418 nreverse (initlist)));
5424 mark_referenced_methods (void)
5426 struct imp_entry *impent;
5429 for (impent = imp_list; impent; impent = impent->next)
5431 chain = CLASS_CLS_METHODS (impent->imp_context);
5434 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5435 chain = TREE_CHAIN (chain);
5438 chain = CLASS_NST_METHODS (impent->imp_context);
5441 cgraph_mark_needed_node (cgraph_node (METHOD_DEFINITION (chain)));
5442 chain = TREE_CHAIN (chain);
5448 generate_dispatch_tables (void)
5450 tree initlist, chain, method_list_template;
5453 if (!objc_method_template)
5454 objc_method_template = build_method_template ();
5456 chain = CLASS_CLS_METHODS (objc_implementation_context);
5459 size = list_length (chain);
5461 method_list_template
5462 = build_method_list_template (objc_method_template, size);
5464 = build_dispatch_table_initializer (objc_method_template, chain);
5466 UOBJC_CLASS_METHODS_decl
5467 = generate_dispatch_table (method_list_template,
5468 ((TREE_CODE (objc_implementation_context)
5469 == CLASS_IMPLEMENTATION_TYPE)
5470 ? "_OBJC_CLASS_METHODS"
5471 : "_OBJC_CATEGORY_CLASS_METHODS"),
5475 UOBJC_CLASS_METHODS_decl = 0;
5477 chain = CLASS_NST_METHODS (objc_implementation_context);
5480 size = list_length (chain);
5482 method_list_template
5483 = build_method_list_template (objc_method_template, size);
5485 = build_dispatch_table_initializer (objc_method_template, chain);
5487 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
5488 UOBJC_INSTANCE_METHODS_decl
5489 = generate_dispatch_table (method_list_template,
5490 "_OBJC_INSTANCE_METHODS",
5493 /* We have a category. */
5494 UOBJC_INSTANCE_METHODS_decl
5495 = generate_dispatch_table (method_list_template,
5496 "_OBJC_CATEGORY_INSTANCE_METHODS",
5500 UOBJC_INSTANCE_METHODS_decl = 0;
5504 generate_protocol_list (tree i_or_p)
5507 tree refs_decl, lproto, e, plist;
5509 const char *ref_name;
5511 if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE
5512 || TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5513 plist = CLASS_PROTOCOL_LIST (i_or_p);
5514 else if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5515 plist = PROTOCOL_LIST (i_or_p);
5520 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5521 if (TREE_CODE (TREE_VALUE (lproto)) == PROTOCOL_INTERFACE_TYPE
5522 && PROTOCOL_FORWARD_DECL (TREE_VALUE (lproto)))
5525 /* Build initializer. */
5526 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), NULL_TREE);
5527 e = build_int_cst (build_pointer_type (objc_protocol_template), size);
5528 initlist = tree_cons (NULL_TREE, e, initlist);
5530 for (lproto = plist; lproto; lproto = TREE_CHAIN (lproto))
5532 tree pval = TREE_VALUE (lproto);
5534 if (TREE_CODE (pval) == PROTOCOL_INTERFACE_TYPE
5535 && PROTOCOL_FORWARD_DECL (pval))
5537 e = build_unary_op (input_location, ADDR_EXPR,
5538 PROTOCOL_FORWARD_DECL (pval), 0);
5539 initlist = tree_cons (NULL_TREE, e, initlist);
5543 /* static struct objc_protocol *refs[n]; */
5545 if (TREE_CODE (i_or_p) == PROTOCOL_INTERFACE_TYPE)
5546 ref_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL_REFS", i_or_p);
5547 else if (TREE_CODE (i_or_p) == CLASS_INTERFACE_TYPE)
5548 ref_name = synth_id_with_class_suffix ("_OBJC_CLASS_PROTOCOLS", i_or_p);
5549 else if (TREE_CODE (i_or_p) == CATEGORY_INTERFACE_TYPE)
5550 ref_name = synth_id_with_class_suffix ("_OBJC_CATEGORY_PROTOCOLS", i_or_p);
5554 refs_decl = start_var_decl
5556 (build_pointer_type (objc_protocol_template),
5557 build_index_type (build_int_cst (NULL_TREE, size + 2))),
5560 finish_var_decl (refs_decl, objc_build_constructor (TREE_TYPE (refs_decl),
5561 nreverse (initlist)));
5567 build_category_initializer (tree type, tree cat_name, tree class_name,
5568 tree instance_methods, tree class_methods,
5571 tree initlist = NULL_TREE, expr;
5573 initlist = tree_cons (NULL_TREE, cat_name, initlist);
5574 initlist = tree_cons (NULL_TREE, class_name, initlist);
5576 if (!instance_methods)
5577 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5580 expr = convert (objc_method_list_ptr,
5581 build_unary_op (input_location, ADDR_EXPR,
5582 instance_methods, 0));
5583 initlist = tree_cons (NULL_TREE, expr, initlist);
5586 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5589 expr = convert (objc_method_list_ptr,
5590 build_unary_op (input_location, ADDR_EXPR,
5592 initlist = tree_cons (NULL_TREE, expr, initlist);
5595 /* protocol_list = */
5597 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5600 expr = convert (build_pointer_type
5602 (objc_protocol_template)),
5603 build_unary_op (input_location, ADDR_EXPR,
5605 initlist = tree_cons (NULL_TREE, expr, initlist);
5608 return objc_build_constructor (type, nreverse (initlist));
5611 /* struct _objc_class {
5612 struct objc_class *isa;
5613 struct objc_class *super_class;
5618 struct objc_ivar_list *ivars;
5619 struct objc_method_list *methods;
5620 if (flag_next_runtime)
5621 struct objc_cache *cache;
5623 struct sarray *dtable;
5624 struct objc_class *subclass_list;
5625 struct objc_class *sibling_class;
5627 struct objc_protocol_list *protocols;
5628 if (flag_next_runtime)
5630 void *gc_object_type;
5634 build_shared_structure_initializer (tree type, tree isa, tree super,
5635 tree name, tree size, int status,
5636 tree dispatch_table, tree ivar_list,
5639 tree initlist = NULL_TREE, expr;
5642 initlist = tree_cons (NULL_TREE, isa, initlist);
5645 initlist = tree_cons (NULL_TREE, super, initlist);
5648 initlist = tree_cons (NULL_TREE, default_conversion (name), initlist);
5651 initlist = tree_cons (NULL_TREE, build_int_cst (long_integer_type_node, 0),
5655 initlist = tree_cons (NULL_TREE,
5656 build_int_cst (long_integer_type_node, status),
5659 /* instance_size = */
5660 initlist = tree_cons (NULL_TREE, convert (long_integer_type_node, size),
5663 /* objc_ivar_list = */
5665 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5668 expr = convert (objc_ivar_list_ptr,
5669 build_unary_op (input_location, ADDR_EXPR,
5671 initlist = tree_cons (NULL_TREE, expr, initlist);
5674 /* objc_method_list = */
5675 if (!dispatch_table)
5676 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5679 expr = convert (objc_method_list_ptr,
5680 build_unary_op (input_location, ADDR_EXPR,
5681 dispatch_table, 0));
5682 initlist = tree_cons (NULL_TREE, expr, initlist);
5685 if (flag_next_runtime)
5686 /* method_cache = */
5687 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5691 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5693 /* subclass_list = */
5694 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5696 /* sibling_class = */
5697 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5700 /* protocol_list = */
5701 if (! protocol_list)
5702 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5705 expr = convert (build_pointer_type
5707 (objc_protocol_template)),
5708 build_unary_op (input_location, ADDR_EXPR,
5710 initlist = tree_cons (NULL_TREE, expr, initlist);
5713 if (flag_next_runtime)
5715 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5717 /* gc_object_type = NULL */
5718 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, 0), initlist);
5720 return objc_build_constructor (type, nreverse (initlist));
5723 /* Retrieve category interface CAT_NAME (if any) associated with CLASS. */
5726 lookup_category (tree klass, tree cat_name)
5728 tree category = CLASS_CATEGORY_LIST (klass);
5730 while (category && CLASS_SUPER_NAME (category) != cat_name)
5731 category = CLASS_CATEGORY_LIST (category);
5735 /* static struct objc_category _OBJC_CATEGORY_<name> = { ... }; */
5738 generate_category (tree cat)
5741 tree initlist, cat_name_expr, class_name_expr;
5742 tree protocol_decl, category;
5744 add_class_reference (CLASS_NAME (cat));
5745 cat_name_expr = add_objc_string (CLASS_SUPER_NAME (cat), class_names);
5747 class_name_expr = add_objc_string (CLASS_NAME (cat), class_names);
5749 category = lookup_category (implementation_template,
5750 CLASS_SUPER_NAME (cat));
5752 if (category && CLASS_PROTOCOL_LIST (category))
5754 generate_protocol_references (CLASS_PROTOCOL_LIST (category));
5755 protocol_decl = generate_protocol_list (category);
5760 decl = start_var_decl (objc_category_template,
5761 synth_id_with_class_suffix
5762 ("_OBJC_CATEGORY", objc_implementation_context));
5764 initlist = build_category_initializer (TREE_TYPE (decl),
5765 cat_name_expr, class_name_expr,
5766 UOBJC_INSTANCE_METHODS_decl,
5767 UOBJC_CLASS_METHODS_decl,
5770 finish_var_decl (decl, initlist);
5773 /* static struct objc_class _OBJC_METACLASS_Foo={ ... };
5774 static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5777 generate_shared_structures (int cls_flags)
5779 tree sc_spec, decl_specs, decl;
5780 tree name_expr, super_expr, root_expr;
5781 tree my_root_id = NULL_TREE, my_super_id = NULL_TREE;
5782 tree cast_type, initlist, protocol_decl;
5784 my_super_id = CLASS_SUPER_NAME (implementation_template);
5787 add_class_reference (my_super_id);
5789 /* Compute "my_root_id" - this is required for code generation.
5790 the "isa" for all meta class structures points to the root of
5791 the inheritance hierarchy (e.g. "__Object")... */
5792 my_root_id = my_super_id;
5795 tree my_root_int = lookup_interface (my_root_id);
5797 if (my_root_int && CLASS_SUPER_NAME (my_root_int))
5798 my_root_id = CLASS_SUPER_NAME (my_root_int);
5805 /* No super class. */
5806 my_root_id = CLASS_NAME (implementation_template);
5808 cast_type = build_pointer_type (objc_class_template);
5809 name_expr = add_objc_string (CLASS_NAME (implementation_template),
5812 /* Install class `isa' and `super' pointers at runtime. */
5815 super_expr = add_objc_string (my_super_id, class_names);
5816 super_expr = build_c_cast (input_location,
5817 cast_type, super_expr); /* cast! */
5820 super_expr = build_int_cst (NULL_TREE, 0);
5822 root_expr = add_objc_string (my_root_id, class_names);
5823 root_expr = build_c_cast (input_location, cast_type, root_expr); /* cast! */
5825 if (CLASS_PROTOCOL_LIST (implementation_template))
5827 generate_protocol_references
5828 (CLASS_PROTOCOL_LIST (implementation_template));
5829 protocol_decl = generate_protocol_list (implementation_template);
5834 /* static struct objc_class _OBJC_METACLASS_Foo = { ... }; */
5836 sc_spec = build_tree_list (NULL_TREE, ridpointers[(int) RID_STATIC]);
5837 decl_specs = tree_cons (NULL_TREE, objc_class_template, sc_spec);
5839 decl = start_var_decl (objc_class_template,
5841 (DECL_NAME (UOBJC_METACLASS_decl)));
5844 = build_shared_structure_initializer
5846 root_expr, super_expr, name_expr,
5847 convert (integer_type_node, TYPE_SIZE_UNIT (objc_class_template)),
5849 UOBJC_CLASS_METHODS_decl,
5850 UOBJC_CLASS_VARIABLES_decl,
5853 finish_var_decl (decl, initlist);
5855 /* static struct objc_class _OBJC_CLASS_Foo={ ... }; */
5857 decl = start_var_decl (objc_class_template,
5859 (DECL_NAME (UOBJC_CLASS_decl)));
5862 = build_shared_structure_initializer
5864 build_unary_op (input_location, ADDR_EXPR, UOBJC_METACLASS_decl, 0),
5865 super_expr, name_expr,
5866 convert (integer_type_node,
5867 TYPE_SIZE_UNIT (CLASS_STATIC_TEMPLATE
5868 (implementation_template))),
5869 1 /*CLS_FACTORY*/ | cls_flags,
5870 UOBJC_INSTANCE_METHODS_decl,
5871 UOBJC_INSTANCE_VARIABLES_decl,
5874 finish_var_decl (decl, initlist);
5879 synth_id_with_class_suffix (const char *preamble, tree ctxt)
5881 static char string[BUFSIZE];
5883 if (TREE_CODE (ctxt) == CLASS_IMPLEMENTATION_TYPE
5884 || TREE_CODE (ctxt) == CLASS_INTERFACE_TYPE)
5886 sprintf (string, "%s_%s", preamble,
5887 IDENTIFIER_POINTER (CLASS_NAME (ctxt)));
5889 else if (TREE_CODE (ctxt) == CATEGORY_IMPLEMENTATION_TYPE
5890 || TREE_CODE (ctxt) == CATEGORY_INTERFACE_TYPE)
5892 /* We have a category. */
5893 const char *const class_name
5894 = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
5895 const char *const class_super_name
5896 = IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context));
5897 sprintf (string, "%s_%s_%s", preamble, class_name, class_super_name);
5899 else if (TREE_CODE (ctxt) == PROTOCOL_INTERFACE_TYPE)
5901 const char *protocol_name = IDENTIFIER_POINTER (PROTOCOL_NAME (ctxt));
5902 sprintf (string, "%s_%s", preamble, protocol_name);
5910 /* If type is empty or only type qualifiers are present, add default
5911 type of id (otherwise grokdeclarator will default to int). */
5914 adjust_type_for_id_default (tree type)
5917 type = make_node (TREE_LIST);
5919 if (!TREE_VALUE (type))
5920 TREE_VALUE (type) = objc_object_type;
5921 else if (TREE_CODE (TREE_VALUE (type)) == RECORD_TYPE
5922 && TYPED_OBJECT (TREE_VALUE (type)))
5923 error ("can not use an object as parameter to a method");
5930 selector ':' '(' typename ')' identifier
5933 Transform an Objective-C keyword argument into
5934 the C equivalent parameter declarator.
5936 In: key_name, an "identifier_node" (optional).
5937 arg_type, a "tree_list" (optional).
5938 arg_name, an "identifier_node".
5940 Note: It would be really nice to strongly type the preceding
5941 arguments in the function prototype; however, then I
5942 could not use the "accessor" macros defined in "tree.h".
5944 Out: an instance of "keyword_decl". */
5947 objc_build_keyword_decl (tree key_name, tree arg_type, tree arg_name)
5951 /* If no type is specified, default to "id". */
5952 arg_type = adjust_type_for_id_default (arg_type);
5954 keyword_decl = make_node (KEYWORD_DECL);
5956 TREE_TYPE (keyword_decl) = arg_type;
5957 KEYWORD_ARG_NAME (keyword_decl) = arg_name;
5958 KEYWORD_KEY_NAME (keyword_decl) = key_name;
5960 return keyword_decl;
5963 /* Given a chain of keyword_decl's, synthesize the full keyword selector. */
5966 build_keyword_selector (tree selector)
5969 tree key_chain, key_name;
5972 /* Scan the selector to see how much space we'll need. */
5973 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
5975 if (TREE_CODE (selector) == KEYWORD_DECL)
5976 key_name = KEYWORD_KEY_NAME (key_chain);
5977 else if (TREE_CODE (selector) == TREE_LIST)
5978 key_name = TREE_PURPOSE (key_chain);
5983 len += IDENTIFIER_LENGTH (key_name) + 1;
5985 /* Just a ':' arg. */
5989 buf = (char *) alloca (len + 1);
5990 /* Start the buffer out as an empty string. */
5993 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
5995 if (TREE_CODE (selector) == KEYWORD_DECL)
5996 key_name = KEYWORD_KEY_NAME (key_chain);
5997 else if (TREE_CODE (selector) == TREE_LIST)
5999 key_name = TREE_PURPOSE (key_chain);
6000 /* The keyword decl chain will later be used as a function argument
6001 chain. Unhook the selector itself so as to not confuse other
6002 parts of the compiler. */
6003 TREE_PURPOSE (key_chain) = NULL_TREE;
6009 strcat (buf, IDENTIFIER_POINTER (key_name));
6013 return get_identifier (buf);
6016 /* Used for declarations and definitions. */
6019 build_method_decl (enum tree_code code, tree ret_type, tree selector,
6020 tree add_args, bool ellipsis)
6024 /* If no type is specified, default to "id". */
6025 ret_type = adjust_type_for_id_default (ret_type);
6027 method_decl = make_node (code);
6028 TREE_TYPE (method_decl) = ret_type;
6030 /* If we have a keyword selector, create an identifier_node that
6031 represents the full selector name (`:' included)... */
6032 if (TREE_CODE (selector) == KEYWORD_DECL)
6034 METHOD_SEL_NAME (method_decl) = build_keyword_selector (selector);
6035 METHOD_SEL_ARGS (method_decl) = selector;
6036 METHOD_ADD_ARGS (method_decl) = add_args;
6037 METHOD_ADD_ARGS_ELLIPSIS_P (method_decl) = ellipsis;
6041 METHOD_SEL_NAME (method_decl) = selector;
6042 METHOD_SEL_ARGS (method_decl) = NULL_TREE;
6043 METHOD_ADD_ARGS (method_decl) = NULL_TREE;
6049 #define METHOD_DEF 0
6050 #define METHOD_REF 1
6052 /* Used by `build_objc_method_call' and `comp_proto_with_proto'. Return
6053 an argument list for method METH. CONTEXT is either METHOD_DEF or
6054 METHOD_REF, saying whether we are trying to define a method or call
6055 one. SUPERFLAG says this is for a send to super; this makes a
6056 difference for the NeXT calling sequence in which the lookup and
6057 the method call are done together. If METH is null, user-defined
6058 arguments (i.e., beyond self and _cmd) shall be represented by `...'. */
6061 get_arg_type_list (tree meth, int context, int superflag)
6065 /* Receiver type. */
6066 if (flag_next_runtime && superflag)
6067 arglist = build_tree_list (NULL_TREE, objc_super_type);
6068 else if (context == METHOD_DEF && TREE_CODE (meth) == INSTANCE_METHOD_DECL)
6069 arglist = build_tree_list (NULL_TREE, objc_instance_type);
6071 arglist = build_tree_list (NULL_TREE, objc_object_type);
6073 /* Selector type - will eventually change to `int'. */
6074 chainon (arglist, build_tree_list (NULL_TREE, objc_selector_type));
6076 /* No actual method prototype given -- assume that remaining arguments
6081 /* Build a list of argument types. */
6082 for (akey = METHOD_SEL_ARGS (meth); akey; akey = TREE_CHAIN (akey))
6084 tree arg_type = TREE_VALUE (TREE_TYPE (akey));
6086 /* Decay arrays and functions into pointers. */
6087 if (TREE_CODE (arg_type) == ARRAY_TYPE)
6088 arg_type = build_pointer_type (TREE_TYPE (arg_type));
6089 else if (TREE_CODE (arg_type) == FUNCTION_TYPE)
6090 arg_type = build_pointer_type (arg_type);
6092 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6095 if (METHOD_ADD_ARGS (meth))
6097 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (meth));
6098 akey; akey = TREE_CHAIN (akey))
6100 tree arg_type = TREE_TYPE (TREE_VALUE (akey));
6102 chainon (arglist, build_tree_list (NULL_TREE, arg_type));
6105 if (!METHOD_ADD_ARGS_ELLIPSIS_P (meth))
6106 goto lack_of_ellipsis;
6111 chainon (arglist, OBJC_VOID_AT_END);
6118 check_duplicates (hash hsh, int methods, int is_class)
6120 tree meth = NULL_TREE;
6128 /* We have two or more methods with the same name but
6132 /* But just how different are those types? If
6133 -Wno-strict-selector-match is specified, we shall not
6134 complain if the differences are solely among types with
6135 identical size and alignment. */
6136 if (!warn_strict_selector_match)
6138 for (loop = hsh->list; loop; loop = loop->next)
6139 if (!comp_proto_with_proto (meth, loop->value, 0))
6148 bool type = TREE_CODE (meth) == INSTANCE_METHOD_DECL;
6150 warning_at (input_location, 0,
6151 "multiple methods named %<%c%E%> found",
6152 (is_class ? '+' : '-'),
6153 METHOD_SEL_NAME (meth));
6154 inform (DECL_SOURCE_LOCATION (meth), "using %<%c%s%>",
6156 identifier_to_locale (gen_method_decl (meth)));
6160 bool type = TREE_CODE (meth) == INSTANCE_METHOD_DECL;
6162 warning_at (input_location, 0,
6163 "multiple selectors named %<%c%E%> found",
6164 (is_class ? '+' : '-'),
6165 METHOD_SEL_NAME (meth));
6166 inform (DECL_SOURCE_LOCATION (meth), "found %<%c%s%>",
6168 identifier_to_locale (gen_method_decl (meth)));
6171 for (loop = hsh->list; loop; loop = loop->next)
6173 bool type = TREE_CODE (loop->value) == INSTANCE_METHOD_DECL;
6175 inform (DECL_SOURCE_LOCATION (loop->value), "also found %<%c%s%>",
6177 identifier_to_locale (gen_method_decl (loop->value)));
6184 /* If RECEIVER is a class reference, return the identifier node for
6185 the referenced class. RECEIVER is created by objc_get_class_reference,
6186 so we check the exact form created depending on which runtimes are
6190 receiver_is_class_object (tree receiver, int self, int super)
6192 tree chain, exp, arg;
6194 /* The receiver is 'self' or 'super' in the context of a class method. */
6195 if (objc_method_context
6196 && TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
6199 ? CLASS_SUPER_NAME (implementation_template)
6200 : CLASS_NAME (implementation_template));
6202 if (flag_next_runtime)
6204 /* The receiver is a variable created by
6205 build_class_reference_decl. */
6206 if (TREE_CODE (receiver) == VAR_DECL && IS_CLASS (TREE_TYPE (receiver)))
6207 /* Look up the identifier. */
6208 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
6209 if (TREE_PURPOSE (chain) == receiver)
6210 return TREE_VALUE (chain);
6213 /* The receiver is a function call that returns an id. Check if
6214 it is a call to objc_getClass, if so, pick up the class name. */
6215 if (TREE_CODE (receiver) == CALL_EXPR
6216 && (exp = CALL_EXPR_FN (receiver))
6217 && TREE_CODE (exp) == ADDR_EXPR
6218 && (exp = TREE_OPERAND (exp, 0))
6219 && TREE_CODE (exp) == FUNCTION_DECL
6220 /* For some reason, we sometimes wind up with multiple FUNCTION_DECL
6221 prototypes for objc_get_class(). Thankfully, they seem to share the
6222 same function type. */
6223 && TREE_TYPE (exp) == TREE_TYPE (objc_get_class_decl)
6224 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (exp)), TAG_GETCLASS)
6225 /* We have a call to objc_get_class/objc_getClass! */
6226 && (arg = CALL_EXPR_ARG (receiver, 0)))
6229 if (TREE_CODE (arg) == ADDR_EXPR
6230 && (arg = TREE_OPERAND (arg, 0))
6231 && TREE_CODE (arg) == STRING_CST)
6232 /* Finally, we have the class name. */
6233 return get_identifier (TREE_STRING_POINTER (arg));
6238 /* If we are currently building a message expr, this holds
6239 the identifier of the selector of the message. This is
6240 used when printing warnings about argument mismatches. */
6242 static tree current_objc_message_selector = 0;
6245 objc_message_selector (void)
6247 return current_objc_message_selector;
6250 /* Construct an expression for sending a message.
6251 MESS has the object to send to in TREE_PURPOSE
6252 and the argument list (including selector) in TREE_VALUE.
6254 (*(<abstract_decl>(*)())_msg)(receiver, selTransTbl[n], ...);
6255 (*(<abstract_decl>(*)())_msgSuper)(receiver, selTransTbl[n], ...); */
6258 objc_build_message_expr (tree mess)
6260 tree receiver = TREE_PURPOSE (mess);
6264 tree args = TREE_PURPOSE (TREE_VALUE (mess));
6266 tree args = TREE_VALUE (mess);
6268 tree method_params = NULL_TREE;
6270 if (TREE_CODE (receiver) == ERROR_MARK || TREE_CODE (args) == ERROR_MARK)
6271 return error_mark_node;
6273 if (CAN_HAVE_LOCATION_P (receiver))
6274 loc = EXPR_LOCATION (receiver);
6276 loc = input_location;
6278 /* Obtain the full selector name. */
6279 if (TREE_CODE (args) == IDENTIFIER_NODE)
6280 /* A unary selector. */
6282 else if (TREE_CODE (args) == TREE_LIST)
6283 sel_name = build_keyword_selector (args);
6287 /* Build the parameter list to give to the method. */
6288 if (TREE_CODE (args) == TREE_LIST)
6290 method_params = chainon (args, TREE_VALUE (TREE_VALUE (mess)));
6293 tree chain = args, prev = NULL_TREE;
6295 /* We have a keyword selector--check for comma expressions. */
6298 tree element = TREE_VALUE (chain);
6300 /* We have a comma expression, must collapse... */
6301 if (TREE_CODE (element) == TREE_LIST)
6304 TREE_CHAIN (prev) = element;
6309 chain = TREE_CHAIN (chain);
6311 method_params = args;
6316 if (processing_template_decl)
6317 /* Must wait until template instantiation time. */
6318 return build_min_nt (MESSAGE_SEND_EXPR, receiver, sel_name,
6322 return objc_finish_message_expr (receiver, sel_name, method_params);
6325 /* Look up method SEL_NAME that would be suitable for receiver
6326 of type 'id' (if IS_CLASS is zero) or 'Class' (if IS_CLASS is
6327 nonzero), and report on any duplicates. */
6330 lookup_method_in_hash_lists (tree sel_name, int is_class)
6332 hash method_prototype = NULL;
6335 method_prototype = hash_lookup (nst_method_hash_list,
6338 if (!method_prototype)
6340 method_prototype = hash_lookup (cls_method_hash_list,
6345 return check_duplicates (method_prototype, 1, is_class);
6348 /* The 'objc_finish_message_expr' routine is called from within
6349 'objc_build_message_expr' for non-template functions. In the case of
6350 C++ template functions, it is called from 'build_expr_from_tree'
6351 (in decl2.c) after RECEIVER and METHOD_PARAMS have been expanded. */
6354 objc_finish_message_expr (tree receiver, tree sel_name, tree method_params)
6356 tree method_prototype = NULL_TREE, rprotos = NULL_TREE, rtype;
6357 tree selector, retval, class_tree;
6358 int self, super, have_cast;
6360 /* Extract the receiver of the message, as well as its type
6361 (where the latter may take the form of a cast or be inferred
6362 from the implementation context). */
6364 while (TREE_CODE (rtype) == COMPOUND_EXPR
6365 || TREE_CODE (rtype) == MODIFY_EXPR
6366 || CONVERT_EXPR_P (rtype)
6367 || TREE_CODE (rtype) == COMPONENT_REF)
6368 rtype = TREE_OPERAND (rtype, 0);
6369 self = (rtype == self_decl);
6370 super = (rtype == UOBJC_SUPER_decl);
6371 rtype = TREE_TYPE (receiver);
6372 have_cast = (TREE_CODE (receiver) == NOP_EXPR
6373 || (TREE_CODE (receiver) == COMPOUND_EXPR
6374 && !IS_SUPER (rtype)));
6376 /* If we are calling [super dealloc], reset our warning flag. */
6377 if (super && !strcmp ("dealloc", IDENTIFIER_POINTER (sel_name)))
6378 should_call_super_dealloc = 0;
6380 /* If the receiver is a class object, retrieve the corresponding
6381 @interface, if one exists. */
6382 class_tree = receiver_is_class_object (receiver, self, super);
6384 /* Now determine the receiver type (if an explicit cast has not been
6389 rtype = lookup_interface (class_tree);
6390 /* Handle `self' and `super'. */
6393 if (!CLASS_SUPER_NAME (implementation_template))
6395 error ("no super class declared in @interface for %qE",
6396 CLASS_NAME (implementation_template));
6397 return error_mark_node;
6399 rtype = lookup_interface (CLASS_SUPER_NAME (implementation_template));
6402 rtype = lookup_interface (CLASS_NAME (implementation_template));
6405 /* If receiver is of type `id' or `Class' (or if the @interface for a
6406 class is not visible), we shall be satisfied with the existence of
6407 any instance or class method. */
6408 if (objc_is_id (rtype))
6410 class_tree = (IS_CLASS (rtype) ? objc_class_name : NULL_TREE);
6411 rprotos = (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype))
6412 ? TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype))
6418 /* If messaging 'id <Protos>' or 'Class <Proto>', first search
6419 in protocols themselves for the method prototype. */
6421 = lookup_method_in_protocol_list (rprotos, sel_name,
6422 class_tree != NULL_TREE);
6424 /* If messaging 'Class <Proto>' but did not find a class method
6425 prototype, search for an instance method instead, and warn
6426 about having done so. */
6427 if (!method_prototype && !rtype && class_tree != NULL_TREE)
6430 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
6432 if (method_prototype)
6433 warning (0, "found %<-%E%> instead of %<+%E%> in protocol(s)",
6434 sel_name, sel_name);
6440 tree orig_rtype = rtype, saved_rtype;
6442 if (TREE_CODE (rtype) == POINTER_TYPE)
6443 rtype = TREE_TYPE (rtype);
6444 /* Traverse typedef aliases */
6445 while (TREE_CODE (rtype) == RECORD_TYPE && OBJC_TYPE_NAME (rtype)
6446 && TREE_CODE (OBJC_TYPE_NAME (rtype)) == TYPE_DECL
6447 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype)))
6448 rtype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype));
6449 saved_rtype = rtype;
6450 if (TYPED_OBJECT (rtype))
6452 rprotos = TYPE_OBJC_PROTOCOL_LIST (rtype);
6453 rtype = TYPE_OBJC_INTERFACE (rtype);
6455 /* If we could not find an @interface declaration, we must have
6456 only seen a @class declaration; so, we cannot say anything
6457 more intelligent about which methods the receiver will
6459 if (!rtype || TREE_CODE (rtype) == IDENTIFIER_NODE)
6461 else if (TREE_CODE (rtype) == CLASS_INTERFACE_TYPE
6462 || TREE_CODE (rtype) == CLASS_IMPLEMENTATION_TYPE)
6464 /* We have a valid ObjC class name. Look up the method name
6465 in the published @interface for the class (and its
6468 = lookup_method_static (rtype, sel_name, class_tree != NULL_TREE);
6470 /* If the method was not found in the @interface, it may still
6471 exist locally as part of the @implementation. */
6472 if (!method_prototype && objc_implementation_context
6473 && CLASS_NAME (objc_implementation_context)
6474 == OBJC_TYPE_NAME (rtype))
6478 ? CLASS_CLS_METHODS (objc_implementation_context)
6479 : CLASS_NST_METHODS (objc_implementation_context)),
6482 /* If we haven't found a candidate method by now, try looking for
6483 it in the protocol list. */
6484 if (!method_prototype && rprotos)
6486 = lookup_method_in_protocol_list (rprotos, sel_name,
6487 class_tree != NULL_TREE);
6491 warning (0, "invalid receiver type %qs",
6492 identifier_to_locale (gen_type_name (orig_rtype)));
6493 /* After issuing the "invalid receiver" warning, perform method
6494 lookup as if we were messaging 'id'. */
6495 rtype = rprotos = NULL_TREE;
6500 /* For 'id' or 'Class' receivers, search in the global hash table
6501 as a last resort. For all receivers, warn if protocol searches
6503 if (!method_prototype)
6506 warning (0, "%<%c%E%> not found in protocol(s)",
6507 (class_tree ? '+' : '-'),
6512 = lookup_method_in_hash_lists (sel_name, class_tree != NULL_TREE);
6515 if (!method_prototype)
6517 static bool warn_missing_methods = false;
6520 warning (0, "%qE may not respond to %<%c%E%>",
6521 OBJC_TYPE_NAME (rtype),
6522 (class_tree ? '+' : '-'),
6524 /* If we are messaging an 'id' or 'Class' object and made it here,
6525 then we have failed to find _any_ instance or class method,
6528 warning (0, "no %<%c%E%> method found",
6529 (class_tree ? '+' : '-'),
6532 if (!warn_missing_methods)
6534 warning_at (input_location,
6535 0, "(Messages without a matching method signature");
6536 warning_at (input_location,
6537 0, "will be assumed to return %<id%> and accept");
6538 warning_at (input_location,
6539 0, "%<...%> as arguments.)");
6540 warn_missing_methods = true;
6544 /* Save the selector name for printing error messages. */
6545 current_objc_message_selector = sel_name;
6547 /* Build the parameters list for looking up the method.
6548 These are the object itself and the selector. */
6550 if (flag_typed_selectors)
6551 selector = build_typed_selector_reference (input_location,
6552 sel_name, method_prototype);
6554 selector = build_selector_reference (input_location, sel_name);
6556 retval = build_objc_method_call (input_location, super, method_prototype,
6558 selector, method_params);
6560 current_objc_message_selector = 0;
6565 /* Build a tree expression to send OBJECT the operation SELECTOR,
6566 looking up the method on object LOOKUP_OBJECT (often same as OBJECT),
6567 assuming the method has prototype METHOD_PROTOTYPE.
6568 (That is an INSTANCE_METHOD_DECL or CLASS_METHOD_DECL.)
6569 LOC is the location of the expression to build.
6570 Use METHOD_PARAMS as list of args to pass to the method.
6571 If SUPER_FLAG is nonzero, we look up the superclass's method. */
6574 build_objc_method_call (location_t loc, int super_flag, tree method_prototype,
6575 tree lookup_object, tree selector,
6578 tree sender = (super_flag ? umsg_super_decl :
6579 (!flag_next_runtime || flag_nil_receivers
6580 ? (flag_objc_direct_dispatch
6583 : umsg_nonnil_decl));
6584 tree rcv_p = (super_flag ? objc_super_type : objc_object_type);
6586 /* If a prototype for the method to be called exists, then cast
6587 the sender's return type and arguments to match that of the method.
6588 Otherwise, leave sender as is. */
6591 ? TREE_VALUE (TREE_TYPE (method_prototype))
6592 : objc_object_type);
6594 = build_pointer_type
6595 (build_function_type
6598 (method_prototype, METHOD_REF, super_flag)));
6601 lookup_object = build_c_cast (loc, rcv_p, lookup_object);
6603 /* Use SAVE_EXPR to avoid evaluating the receiver twice. */
6604 lookup_object = save_expr (lookup_object);
6606 if (flag_next_runtime)
6608 /* If we are returning a struct in memory, and the address
6609 of that memory location is passed as a hidden first
6610 argument, then change which messenger entry point this
6611 expr will call. NB: Note that sender_cast remains
6612 unchanged (it already has a struct return type). */
6613 if (!targetm.calls.struct_value_rtx (0, 0)
6614 && (TREE_CODE (ret_type) == RECORD_TYPE
6615 || TREE_CODE (ret_type) == UNION_TYPE)
6616 && targetm.calls.return_in_memory (ret_type, 0))
6617 sender = (super_flag ? umsg_super_stret_decl :
6618 flag_nil_receivers ? umsg_stret_decl : umsg_nonnil_stret_decl);
6620 method_params = tree_cons (NULL_TREE, lookup_object,
6621 tree_cons (NULL_TREE, selector,
6623 method = build_fold_addr_expr_loc (input_location, sender);
6627 /* This is the portable (GNU) way. */
6630 /* First, call the lookup function to get a pointer to the method,
6631 then cast the pointer, then call it with the method arguments. */
6633 object = (super_flag ? self_decl : lookup_object);
6635 t = tree_cons (NULL_TREE, selector, NULL_TREE);
6636 t = tree_cons (NULL_TREE, lookup_object, t);
6637 method = build_function_call (loc, sender, t);
6639 /* Pass the object to the method. */
6640 method_params = tree_cons (NULL_TREE, object,
6641 tree_cons (NULL_TREE, selector,
6645 /* ??? Selector is not at this point something we can use inside
6646 the compiler itself. Set it to garbage for the nonce. */
6647 t = build3 (OBJ_TYPE_REF, sender_cast, method, lookup_object, size_zero_node);
6648 return build_function_call (loc,
6653 build_protocol_reference (tree p)
6656 const char *proto_name;
6658 /* static struct _objc_protocol _OBJC_PROTOCOL_<mumble>; */
6660 proto_name = synth_id_with_class_suffix ("_OBJC_PROTOCOL", p);
6661 decl = start_var_decl (objc_protocol_template, proto_name);
6663 PROTOCOL_FORWARD_DECL (p) = decl;
6666 /* This function is called by the parser when (and only when) a
6667 @protocol() expression is found, in order to compile it. */
6669 objc_build_protocol_expr (tree protoname)
6672 tree p = lookup_protocol (protoname);
6676 error ("cannot find protocol declaration for %qE",
6678 return error_mark_node;
6681 if (!PROTOCOL_FORWARD_DECL (p))
6682 build_protocol_reference (p);
6684 expr = build_unary_op (input_location,
6685 ADDR_EXPR, PROTOCOL_FORWARD_DECL (p), 0);
6687 /* ??? Ideally we'd build the reference with objc_protocol_type directly,
6688 if we have it, rather than converting it here. */
6689 expr = convert (objc_protocol_type, expr);
6691 /* The @protocol() expression is being compiled into a pointer to a
6692 statically allocated instance of the Protocol class. To become
6693 usable at runtime, the 'isa' pointer of the instance need to be
6694 fixed up at runtime by the runtime library, to point to the
6695 actual 'Protocol' class. */
6697 /* For the GNU runtime, put the static Protocol instance in the list
6698 of statically allocated instances, so that we make sure that its
6699 'isa' pointer is fixed up at runtime by the GNU runtime library
6700 to point to the Protocol class (at runtime, when loading the
6701 module, the GNU runtime library loops on the statically allocated
6702 instances (as found in the defs field in objc_symtab) and fixups
6703 all the 'isa' pointers of those objects). */
6704 if (! flag_next_runtime)
6706 /* This type is a struct containing the fields of a Protocol
6707 object. (Cfr. objc_protocol_type instead is the type of a pointer
6708 to such a struct). */
6709 tree protocol_struct_type = xref_tag
6710 (RECORD_TYPE, get_identifier (PROTOCOL_OBJECT_CLASS_NAME));
6713 /* Look for the list of Protocol statically allocated instances
6714 to fixup at runtime. Create a new list to hold Protocol
6715 statically allocated instances, if the list is not found. At
6716 present there is only another list, holding NSConstantString
6717 static instances to be fixed up at runtime. */
6718 for (chain = &objc_static_instances;
6719 *chain && TREE_VALUE (*chain) != protocol_struct_type;
6720 chain = &TREE_CHAIN (*chain));
6723 *chain = tree_cons (NULL_TREE, protocol_struct_type, NULL_TREE);
6724 add_objc_string (OBJC_TYPE_NAME (protocol_struct_type),
6728 /* Add this statically allocated instance to the Protocol list. */
6729 TREE_PURPOSE (*chain) = tree_cons (NULL_TREE,
6730 PROTOCOL_FORWARD_DECL (p),
6731 TREE_PURPOSE (*chain));
6738 /* This function is called by the parser when a @selector() expression
6739 is found, in order to compile it. It is only called by the parser
6740 and only to compile a @selector(). LOC is the location of the
6743 objc_build_selector_expr (location_t loc, tree selnamelist)
6747 /* Obtain the full selector name. */
6748 if (TREE_CODE (selnamelist) == IDENTIFIER_NODE)
6749 /* A unary selector. */
6750 selname = selnamelist;
6751 else if (TREE_CODE (selnamelist) == TREE_LIST)
6752 selname = build_keyword_selector (selnamelist);
6756 /* If we are required to check @selector() expressions as they
6757 are found, check that the selector has been declared. */
6758 if (warn_undeclared_selector)
6760 /* Look the selector up in the list of all known class and
6761 instance methods (up to this line) to check that the selector
6765 /* First try with instance methods. */
6766 hsh = hash_lookup (nst_method_hash_list, selname);
6768 /* If not found, try with class methods. */
6771 hsh = hash_lookup (cls_method_hash_list, selname);
6774 /* If still not found, print out a warning. */
6777 warning (0, "undeclared selector %qE", selname);
6782 if (flag_typed_selectors)
6783 return build_typed_selector_reference (loc, selname, 0);
6785 return build_selector_reference (loc, selname);
6789 objc_build_encode_expr (tree type)
6794 encode_type (type, obstack_object_size (&util_obstack),
6795 OBJC_ENCODE_INLINE_DEFS);
6796 obstack_1grow (&util_obstack, 0); /* null terminate string */
6797 string = XOBFINISH (&util_obstack, const char *);
6799 /* Synthesize a string that represents the encoded struct/union. */
6800 result = my_build_string (strlen (string) + 1, string);
6801 obstack_free (&util_obstack, util_firstobj);
6806 build_ivar_reference (tree id)
6808 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
6810 /* Historically, a class method that produced objects (factory
6811 method) would assign `self' to the instance that it
6812 allocated. This would effectively turn the class method into
6813 an instance method. Following this assignment, the instance
6814 variables could be accessed. That practice, while safe,
6815 violates the simple rule that a class method should not refer
6816 to an instance variable. It's better to catch the cases
6817 where this is done unknowingly than to support the above
6819 warning (0, "instance variable %qE accessed in class method",
6821 self_decl = convert (objc_instance_type, self_decl); /* cast */
6824 return objc_build_component_ref (build_indirect_ref (input_location,
6825 self_decl, "->"), id);
6828 /* Compute a hash value for a given method SEL_NAME. */
6831 hash_func (tree sel_name)
6833 const unsigned char *s
6834 = (const unsigned char *)IDENTIFIER_POINTER (sel_name);
6838 h = h * 67 + *s++ - 113;
6845 nst_method_hash_list
6846 = (hash *) ggc_alloc_cleared (SIZEHASHTABLE * sizeof (hash));
6847 cls_method_hash_list
6848 = (hash *) ggc_alloc_cleared (SIZEHASHTABLE * sizeof (hash));
6850 /* Initialize the hash table used to hold the constant string objects. */
6851 string_htab = htab_create_ggc (31, string_hash,
6854 /* Initialize the hash table used to hold EH-volatilized types. */
6855 volatilized_htab = htab_create_ggc (31, volatilized_hash,
6856 volatilized_eq, NULL);
6859 /* WARNING!!!! hash_enter is called with a method, and will peek
6860 inside to find its selector! But hash_lookup is given a selector
6861 directly, and looks for the selector that's inside the found
6862 entry's key (method) for comparison. */
6865 hash_enter (hash *hashlist, tree method)
6868 int slot = hash_func (METHOD_SEL_NAME (method)) % SIZEHASHTABLE;
6870 obj = (hash) ggc_alloc (sizeof (struct hashed_entry));
6872 obj->next = hashlist[slot];
6875 hashlist[slot] = obj; /* append to front */
6879 hash_lookup (hash *hashlist, tree sel_name)
6883 target = hashlist[hash_func (sel_name) % SIZEHASHTABLE];
6887 if (sel_name == METHOD_SEL_NAME (target->key))
6890 target = target->next;
6896 hash_add_attr (hash entry, tree value)
6900 obj = (attr) ggc_alloc (sizeof (struct hashed_attribute));
6901 obj->next = entry->list;
6904 entry->list = obj; /* append to front */
6908 lookup_method (tree mchain, tree method)
6912 if (TREE_CODE (method) == IDENTIFIER_NODE)
6915 key = METHOD_SEL_NAME (method);
6919 if (METHOD_SEL_NAME (mchain) == key)
6922 mchain = TREE_CHAIN (mchain);
6927 /* Look up a class (if OBJC_LOOKUP_CLASS is set in FLAGS) or instance method
6928 in INTERFACE, along with any categories and protocols attached thereto.
6929 If method is not found, and the OBJC_LOOKUP_NO_SUPER is _not_ set in FLAGS,
6930 recursively examine the INTERFACE's superclass. If OBJC_LOOKUP_CLASS is
6931 set, OBJC_LOOKUP_NO_SUPER is cleared, and no suitable class method could
6932 be found in INTERFACE or any of its superclasses, look for an _instance_
6933 method of the same name in the root class as a last resort.
6935 If a suitable method cannot be found, return NULL_TREE. */
6938 lookup_method_static (tree interface, tree ident, int flags)
6940 tree meth = NULL_TREE, root_inter = NULL_TREE;
6941 tree inter = interface;
6942 int is_class = (flags & OBJC_LOOKUP_CLASS);
6943 int no_superclasses = (flags & OBJC_LOOKUP_NO_SUPER);
6947 tree chain = is_class ? CLASS_CLS_METHODS (inter) : CLASS_NST_METHODS (inter);
6948 tree category = inter;
6950 /* First, look up the method in the class itself. */
6951 if ((meth = lookup_method (chain, ident)))
6954 /* Failing that, look for the method in each category of the class. */
6955 while ((category = CLASS_CATEGORY_LIST (category)))
6957 chain = is_class ? CLASS_CLS_METHODS (category) : CLASS_NST_METHODS (category);
6959 /* Check directly in each category. */
6960 if ((meth = lookup_method (chain, ident)))
6963 /* Failing that, check in each category's protocols. */
6964 if (CLASS_PROTOCOL_LIST (category))
6966 if ((meth = (lookup_method_in_protocol_list
6967 (CLASS_PROTOCOL_LIST (category), ident, is_class))))
6972 /* If not found in categories, check in protocols of the main class. */
6973 if (CLASS_PROTOCOL_LIST (inter))
6975 if ((meth = (lookup_method_in_protocol_list
6976 (CLASS_PROTOCOL_LIST (inter), ident, is_class))))
6980 /* If we were instructed not to look in superclasses, don't. */
6981 if (no_superclasses)
6984 /* Failing that, climb up the inheritance hierarchy. */
6986 inter = lookup_interface (CLASS_SUPER_NAME (inter));
6990 /* If no class (factory) method was found, check if an _instance_
6991 method of the same name exists in the root class. This is what
6992 the Objective-C runtime will do. If an instance method was not
6994 return is_class ? lookup_method_static (root_inter, ident, 0): NULL_TREE;
6997 /* Add the method to the hash list if it doesn't contain an identical
7001 add_method_to_hash_list (hash *hash_list, tree method)
7005 if (!(hsh = hash_lookup (hash_list, METHOD_SEL_NAME (method))))
7007 /* Install on a global chain. */
7008 hash_enter (hash_list, method);
7012 /* Check types against those; if different, add to a list. */
7014 int already_there = comp_proto_with_proto (method, hsh->key, 1);
7015 for (loop = hsh->list; !already_there && loop; loop = loop->next)
7016 already_there |= comp_proto_with_proto (method, loop->value, 1);
7018 hash_add_attr (hsh, method);
7023 objc_add_method (tree klass, tree method, int is_class)
7027 if (!(mth = lookup_method (is_class
7028 ? CLASS_CLS_METHODS (klass)
7029 : CLASS_NST_METHODS (klass), method)))
7031 /* put method on list in reverse order */
7034 TREE_CHAIN (method) = CLASS_CLS_METHODS (klass);
7035 CLASS_CLS_METHODS (klass) = method;
7039 TREE_CHAIN (method) = CLASS_NST_METHODS (klass);
7040 CLASS_NST_METHODS (klass) = method;
7045 /* When processing an @interface for a class or category, give hard
7046 errors on methods with identical selectors but differing argument
7047 and/or return types. We do not do this for @implementations, because
7048 C/C++ will do it for us (i.e., there will be duplicate function
7049 definition errors). */
7050 if ((TREE_CODE (klass) == CLASS_INTERFACE_TYPE
7051 || TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE)
7052 && !comp_proto_with_proto (method, mth, 1))
7053 error ("duplicate declaration of method %<%c%E%>",
7054 is_class ? '+' : '-',
7055 METHOD_SEL_NAME (mth));
7059 add_method_to_hash_list (cls_method_hash_list, method);
7062 add_method_to_hash_list (nst_method_hash_list, method);
7064 /* Instance methods in root classes (and categories thereof)
7065 may act as class methods as a last resort. We also add
7066 instance methods listed in @protocol declarations to
7067 the class hash table, on the assumption that @protocols
7068 may be adopted by root classes or categories. */
7069 if (TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
7070 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7071 klass = lookup_interface (CLASS_NAME (klass));
7073 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE
7074 || !CLASS_SUPER_NAME (klass))
7075 add_method_to_hash_list (cls_method_hash_list, method);
7082 add_class (tree class_name, tree name)
7084 struct interface_tuple **slot;
7086 /* Put interfaces on list in reverse order. */
7087 TREE_CHAIN (class_name) = interface_chain;
7088 interface_chain = class_name;
7090 if (interface_htab == NULL)
7091 interface_htab = htab_create_ggc (31, hash_interface, eq_interface, NULL);
7092 slot = (struct interface_tuple **)
7093 htab_find_slot_with_hash (interface_htab, name,
7094 IDENTIFIER_HASH_VALUE (name),
7098 *slot = (struct interface_tuple *) ggc_alloc_cleared (sizeof (struct interface_tuple));
7101 (*slot)->class_name = class_name;
7103 return interface_chain;
7107 add_category (tree klass, tree category)
7109 /* Put categories on list in reverse order. */
7110 tree cat = lookup_category (klass, CLASS_SUPER_NAME (category));
7114 warning (0, "duplicate interface declaration for category %<%E(%E)%>",
7116 CLASS_SUPER_NAME (category));
7120 CLASS_CATEGORY_LIST (category) = CLASS_CATEGORY_LIST (klass);
7121 CLASS_CATEGORY_LIST (klass) = category;
7125 /* Called after parsing each instance variable declaration. Necessary to
7126 preserve typedefs and implement public/private...
7128 VISIBILITY is 1 for public, 0 for protected, and 2 for private. */
7131 add_instance_variable (tree klass, int visibility, tree field_decl)
7133 tree field_type = TREE_TYPE (field_decl);
7134 const char *ivar_name = DECL_NAME (field_decl)
7135 ? identifier_to_locale (IDENTIFIER_POINTER (DECL_NAME (field_decl)))
7139 if (TREE_CODE (field_type) == REFERENCE_TYPE)
7141 error ("illegal reference type specified for instance variable %qs",
7143 /* Return class as is without adding this ivar. */
7148 if (field_type == error_mark_node || !TYPE_SIZE (field_type)
7149 || TYPE_SIZE (field_type) == error_mark_node)
7150 /* 'type[0]' is allowed, but 'type[]' is not! */
7152 error ("instance variable %qs has unknown size", ivar_name);
7153 /* Return class as is without adding this ivar. */
7158 /* Check if the ivar being added has a non-POD C++ type. If so, we will
7159 need to either (1) warn the user about it or (2) generate suitable
7160 constructor/destructor call from '- .cxx_construct' or '- .cxx_destruct'
7161 methods (if '-fobjc-call-cxx-cdtors' was specified). */
7162 if (MAYBE_CLASS_TYPE_P (field_type)
7163 && (TYPE_NEEDS_CONSTRUCTING (field_type)
7164 || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type)
7165 || TYPE_POLYMORPHIC_P (field_type)))
7167 tree type_name = OBJC_TYPE_NAME (field_type);
7169 if (flag_objc_call_cxx_cdtors)
7171 /* Since the ObjC runtime will be calling the constructors and
7172 destructors for us, the only thing we can't handle is the lack
7173 of a default constructor. */
7174 if (TYPE_NEEDS_CONSTRUCTING (field_type)
7175 && !TYPE_HAS_DEFAULT_CONSTRUCTOR (field_type))
7177 warning (0, "type %qE has no default constructor to call",
7180 /* If we cannot call a constructor, we should also avoid
7181 calling the destructor, for symmetry. */
7182 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7183 warning (0, "destructor for %qE shall not be run either",
7189 static bool warn_cxx_ivars = false;
7191 if (TYPE_POLYMORPHIC_P (field_type))
7193 /* Vtable pointers are Real Bad(tm), since Obj-C cannot
7195 error ("type %qE has virtual member functions", type_name);
7196 error ("illegal aggregate type %qE specified "
7197 "for instance variable %qs",
7198 type_name, ivar_name);
7199 /* Return class as is without adding this ivar. */
7203 /* User-defined constructors and destructors are not known to Obj-C
7204 and hence will not be called. This may or may not be a problem. */
7205 if (TYPE_NEEDS_CONSTRUCTING (field_type))
7206 warning (0, "type %qE has a user-defined constructor", type_name);
7207 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
7208 warning (0, "type %qE has a user-defined destructor", type_name);
7210 if (!warn_cxx_ivars)
7212 warning (0, "C++ constructors and destructors will not "
7213 "be invoked for Objective-C fields");
7214 warn_cxx_ivars = true;
7220 /* Overload the public attribute, it is not used for FIELD_DECLs. */
7224 TREE_PUBLIC (field_decl) = 0;
7225 TREE_PRIVATE (field_decl) = 0;
7226 TREE_PROTECTED (field_decl) = 1;
7230 TREE_PUBLIC (field_decl) = 1;
7231 TREE_PRIVATE (field_decl) = 0;
7232 TREE_PROTECTED (field_decl) = 0;
7236 TREE_PUBLIC (field_decl) = 0;
7237 TREE_PRIVATE (field_decl) = 1;
7238 TREE_PROTECTED (field_decl) = 0;
7243 CLASS_RAW_IVARS (klass) = chainon (CLASS_RAW_IVARS (klass), field_decl);
7249 is_ivar (tree decl_chain, tree ident)
7251 for ( ; decl_chain; decl_chain = TREE_CHAIN (decl_chain))
7252 if (DECL_NAME (decl_chain) == ident)
7257 /* True if the ivar is private and we are not in its implementation. */
7260 is_private (tree decl)
7262 return (TREE_PRIVATE (decl)
7263 && ! is_ivar (CLASS_IVARS (implementation_template),
7267 /* We have an instance variable reference;, check to see if it is public. */
7270 objc_is_public (tree expr, tree identifier)
7272 tree basetype, decl;
7275 if (processing_template_decl)
7279 if (TREE_TYPE (expr) == error_mark_node)
7282 basetype = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
7284 if (basetype && TREE_CODE (basetype) == RECORD_TYPE)
7286 if (TYPE_HAS_OBJC_INFO (basetype) && TYPE_OBJC_INTERFACE (basetype))
7288 tree klass = lookup_interface (OBJC_TYPE_NAME (basetype));
7292 error ("cannot find interface declaration for %qE",
7293 OBJC_TYPE_NAME (basetype));
7297 if ((decl = is_ivar (get_class_ivars (klass, true), identifier)))
7299 if (TREE_PUBLIC (decl))
7302 /* Important difference between the Stepstone translator:
7303 all instance variables should be public within the context
7304 of the implementation. */
7305 if (objc_implementation_context
7306 && ((TREE_CODE (objc_implementation_context)
7307 == CLASS_IMPLEMENTATION_TYPE)
7308 || (TREE_CODE (objc_implementation_context)
7309 == CATEGORY_IMPLEMENTATION_TYPE)))
7311 tree curtype = TYPE_MAIN_VARIANT
7312 (CLASS_STATIC_TEMPLATE
7313 (implementation_template));
7315 if (basetype == curtype
7316 || DERIVED_FROM_P (basetype, curtype))
7318 int priv = is_private (decl);
7321 error ("instance variable %qE is declared private",
7328 /* The 2.95.2 compiler sometimes allowed C functions to access
7329 non-@public ivars. We will let this slide for now... */
7330 if (!objc_method_context)
7332 warning (0, "instance variable %qE is %s; "
7333 "this will be a hard error in the future",
7335 TREE_PRIVATE (decl) ? "@private" : "@protected");
7339 error ("instance variable %qE is declared %s",
7341 TREE_PRIVATE (decl) ? "private" : "protected");
7350 /* Make sure all entries in CHAIN are also in LIST. */
7353 check_methods (tree chain, tree list, int mtype)
7359 if (!lookup_method (list, chain))
7363 if (TREE_CODE (objc_implementation_context)
7364 == CLASS_IMPLEMENTATION_TYPE)
7365 warning (0, "incomplete implementation of class %qE",
7366 CLASS_NAME (objc_implementation_context));
7367 else if (TREE_CODE (objc_implementation_context)
7368 == CATEGORY_IMPLEMENTATION_TYPE)
7369 warning (0, "incomplete implementation of category %qE",
7370 CLASS_SUPER_NAME (objc_implementation_context));
7374 warning (0, "method definition for %<%c%E%> not found",
7375 mtype, METHOD_SEL_NAME (chain));
7378 chain = TREE_CHAIN (chain);
7384 /* Check if KLASS, or its superclasses, explicitly conforms to PROTOCOL. */
7387 conforms_to_protocol (tree klass, tree protocol)
7389 if (TREE_CODE (protocol) == PROTOCOL_INTERFACE_TYPE)
7391 tree p = CLASS_PROTOCOL_LIST (klass);
7392 while (p && TREE_VALUE (p) != protocol)
7397 tree super = (CLASS_SUPER_NAME (klass)
7398 ? lookup_interface (CLASS_SUPER_NAME (klass))
7400 int tmp = super ? conforms_to_protocol (super, protocol) : 0;
7409 /* Make sure all methods in CHAIN are accessible as MTYPE methods in
7410 CONTEXT. This is one of two mechanisms to check protocol integrity. */
7413 check_methods_accessible (tree chain, tree context, int mtype)
7417 tree base_context = context;
7421 context = base_context;
7425 list = CLASS_CLS_METHODS (context);
7427 list = CLASS_NST_METHODS (context);
7429 if (lookup_method (list, chain))
7432 else if (TREE_CODE (context) == CLASS_IMPLEMENTATION_TYPE
7433 || TREE_CODE (context) == CLASS_INTERFACE_TYPE)
7434 context = (CLASS_SUPER_NAME (context)
7435 ? lookup_interface (CLASS_SUPER_NAME (context))
7438 else if (TREE_CODE (context) == CATEGORY_IMPLEMENTATION_TYPE
7439 || TREE_CODE (context) == CATEGORY_INTERFACE_TYPE)
7440 context = (CLASS_NAME (context)
7441 ? lookup_interface (CLASS_NAME (context))
7447 if (context == NULL_TREE)
7451 if (TREE_CODE (objc_implementation_context)
7452 == CLASS_IMPLEMENTATION_TYPE)
7453 warning (0, "incomplete implementation of class %qE",
7454 CLASS_NAME (objc_implementation_context));
7455 else if (TREE_CODE (objc_implementation_context)
7456 == CATEGORY_IMPLEMENTATION_TYPE)
7457 warning (0, "incomplete implementation of category %qE",
7458 CLASS_SUPER_NAME (objc_implementation_context));
7461 warning (0, "method definition for %<%c%E%> not found",
7462 mtype, METHOD_SEL_NAME (chain));
7465 chain = TREE_CHAIN (chain); /* next method... */
7470 /* Check whether the current interface (accessible via
7471 'objc_implementation_context') actually implements protocol P, along
7472 with any protocols that P inherits. */
7475 check_protocol (tree p, const char *type, tree name)
7477 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
7481 /* Ensure that all protocols have bodies! */
7484 f1 = check_methods (PROTOCOL_CLS_METHODS (p),
7485 CLASS_CLS_METHODS (objc_implementation_context),
7487 f2 = check_methods (PROTOCOL_NST_METHODS (p),
7488 CLASS_NST_METHODS (objc_implementation_context),
7493 f1 = check_methods_accessible (PROTOCOL_CLS_METHODS (p),
7494 objc_implementation_context,
7496 f2 = check_methods_accessible (PROTOCOL_NST_METHODS (p),
7497 objc_implementation_context,
7502 warning (0, "%s %qE does not fully implement the %qE protocol",
7503 type, name, PROTOCOL_NAME (p));
7506 /* Check protocols recursively. */
7507 if (PROTOCOL_LIST (p))
7509 tree subs = PROTOCOL_LIST (p);
7511 lookup_interface (CLASS_SUPER_NAME (implementation_template));
7515 tree sub = TREE_VALUE (subs);
7517 /* If the superclass does not conform to the protocols
7518 inherited by P, then we must! */
7519 if (!super_class || !conforms_to_protocol (super_class, sub))
7520 check_protocol (sub, type, name);
7521 subs = TREE_CHAIN (subs);
7526 /* Check whether the current interface (accessible via
7527 'objc_implementation_context') actually implements the protocols listed
7531 check_protocols (tree proto_list, const char *type, tree name)
7533 for ( ; proto_list; proto_list = TREE_CHAIN (proto_list))
7535 tree p = TREE_VALUE (proto_list);
7537 check_protocol (p, type, name);
7541 /* Make sure that the class CLASS_NAME is defined
7542 CODE says which kind of thing CLASS_NAME ought to be.
7543 It can be CLASS_INTERFACE_TYPE, CLASS_IMPLEMENTATION_TYPE,
7544 CATEGORY_INTERFACE_TYPE, or CATEGORY_IMPLEMENTATION_TYPE. */
7547 start_class (enum tree_code code, tree class_name, tree super_name,
7553 if (current_namespace != global_namespace) {
7554 error ("Objective-C declarations may only appear in global scope");
7556 #endif /* OBJCPLUS */
7558 if (objc_implementation_context)
7560 warning (0, "%<@end%> missing in implementation context");
7561 finish_class (objc_implementation_context);
7562 objc_ivar_chain = NULL_TREE;
7563 objc_implementation_context = NULL_TREE;
7566 klass = make_node (code);
7567 TYPE_LANG_SLOT_1 (klass) = make_tree_vec (CLASS_LANG_SLOT_ELTS);
7569 /* Check for existence of the super class, if one was specified. Note
7570 that we must have seen an @interface, not just a @class. If we
7571 are looking at a @compatibility_alias, traverse it first. */
7572 if ((code == CLASS_INTERFACE_TYPE || code == CLASS_IMPLEMENTATION_TYPE)
7575 tree super = objc_is_class_name (super_name);
7577 if (!super || !lookup_interface (super))
7579 error ("cannot find interface declaration for %qE, superclass of %qE",
7580 super ? super : super_name,
7582 super_name = NULL_TREE;
7588 CLASS_NAME (klass) = class_name;
7589 CLASS_SUPER_NAME (klass) = super_name;
7590 CLASS_CLS_METHODS (klass) = NULL_TREE;
7592 if (! objc_is_class_name (class_name)
7593 && (decl = lookup_name (class_name)))
7595 error ("%qE redeclared as different kind of symbol",
7597 error ("previous declaration of %q+D",
7601 if (code == CLASS_IMPLEMENTATION_TYPE)
7606 for (chain = implemented_classes; chain; chain = TREE_CHAIN (chain))
7607 if (TREE_VALUE (chain) == class_name)
7609 error ("reimplementation of class %qE",
7611 return error_mark_node;
7613 implemented_classes = tree_cons (NULL_TREE, class_name,
7614 implemented_classes);
7617 /* Reset for multiple classes per file. */
7620 objc_implementation_context = klass;
7622 /* Lookup the interface for this implementation. */
7624 if (!(implementation_template = lookup_interface (class_name)))
7626 warning (0, "cannot find interface declaration for %qE",
7628 add_class (implementation_template = objc_implementation_context,
7632 /* If a super class has been specified in the implementation,
7633 insure it conforms to the one specified in the interface. */
7636 && (super_name != CLASS_SUPER_NAME (implementation_template)))
7638 tree previous_name = CLASS_SUPER_NAME (implementation_template);
7639 error ("conflicting super class name %qE",
7642 error ("previous declaration of %qE", previous_name);
7644 error ("previous declaration");
7647 else if (! super_name)
7649 CLASS_SUPER_NAME (objc_implementation_context)
7650 = CLASS_SUPER_NAME (implementation_template);
7654 else if (code == CLASS_INTERFACE_TYPE)
7656 if (lookup_interface (class_name))
7658 error ("duplicate interface declaration for class %qE",
7660 warning (0, "duplicate interface declaration for class %qE",
7664 add_class (klass, class_name);
7667 CLASS_PROTOCOL_LIST (klass)
7668 = lookup_and_install_protocols (protocol_list);
7671 else if (code == CATEGORY_INTERFACE_TYPE)
7673 tree class_category_is_assoc_with;
7675 /* For a category, class_name is really the name of the class that
7676 the following set of methods will be associated with. We must
7677 find the interface so that can derive the objects template. */
7679 if (!(class_category_is_assoc_with = lookup_interface (class_name)))
7681 error ("cannot find interface declaration for %qE",
7683 exit (FATAL_EXIT_CODE);
7686 add_category (class_category_is_assoc_with, klass);
7689 CLASS_PROTOCOL_LIST (klass)
7690 = lookup_and_install_protocols (protocol_list);
7693 else if (code == CATEGORY_IMPLEMENTATION_TYPE)
7695 /* Reset for multiple classes per file. */
7698 objc_implementation_context = klass;
7700 /* For a category, class_name is really the name of the class that
7701 the following set of methods will be associated with. We must
7702 find the interface so that can derive the objects template. */
7704 if (!(implementation_template = lookup_interface (class_name)))
7706 error ("cannot find interface declaration for %qE",
7708 exit (FATAL_EXIT_CODE);
7715 continue_class (tree klass)
7717 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE
7718 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7720 struct imp_entry *imp_entry;
7722 /* Check consistency of the instance variables. */
7724 if (CLASS_RAW_IVARS (klass))
7725 check_ivars (implementation_template, klass);
7727 /* code generation */
7730 push_lang_context (lang_name_c);
7733 build_private_template (implementation_template);
7734 uprivate_record = CLASS_STATIC_TEMPLATE (implementation_template);
7735 objc_instance_type = build_pointer_type (uprivate_record);
7737 imp_entry = (struct imp_entry *) ggc_alloc (sizeof (struct imp_entry));
7739 imp_entry->next = imp_list;
7740 imp_entry->imp_context = klass;
7741 imp_entry->imp_template = implementation_template;
7743 synth_forward_declarations ();
7744 imp_entry->class_decl = UOBJC_CLASS_decl;
7745 imp_entry->meta_decl = UOBJC_METACLASS_decl;
7746 imp_entry->has_cxx_cdtors = 0;
7748 /* Append to front and increment count. */
7749 imp_list = imp_entry;
7750 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7756 pop_lang_context ();
7757 #endif /* OBJCPLUS */
7759 return get_class_ivars (implementation_template, true);
7762 else if (TREE_CODE (klass) == CLASS_INTERFACE_TYPE)
7765 push_lang_context (lang_name_c);
7766 #endif /* OBJCPLUS */
7768 build_private_template (klass);
7771 pop_lang_context ();
7772 #endif /* OBJCPLUS */
7778 return error_mark_node;
7781 /* This is called once we see the "@end" in an interface/implementation. */
7784 finish_class (tree klass)
7786 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7788 /* All code generation is done in finish_objc. */
7790 if (implementation_template != objc_implementation_context)
7792 /* Ensure that all method listed in the interface contain bodies. */
7793 check_methods (CLASS_CLS_METHODS (implementation_template),
7794 CLASS_CLS_METHODS (objc_implementation_context), '+');
7795 check_methods (CLASS_NST_METHODS (implementation_template),
7796 CLASS_NST_METHODS (objc_implementation_context), '-');
7798 if (CLASS_PROTOCOL_LIST (implementation_template))
7799 check_protocols (CLASS_PROTOCOL_LIST (implementation_template),
7801 CLASS_NAME (objc_implementation_context));
7805 else if (TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
7807 tree category = lookup_category (implementation_template, CLASS_SUPER_NAME (klass));
7811 /* Ensure all method listed in the interface contain bodies. */
7812 check_methods (CLASS_CLS_METHODS (category),
7813 CLASS_CLS_METHODS (objc_implementation_context), '+');
7814 check_methods (CLASS_NST_METHODS (category),
7815 CLASS_NST_METHODS (objc_implementation_context), '-');
7817 if (CLASS_PROTOCOL_LIST (category))
7818 check_protocols (CLASS_PROTOCOL_LIST (category),
7820 CLASS_SUPER_NAME (objc_implementation_context));
7826 add_protocol (tree protocol)
7828 /* Put protocol on list in reverse order. */
7829 TREE_CHAIN (protocol) = protocol_chain;
7830 protocol_chain = protocol;
7831 return protocol_chain;
7835 lookup_protocol (tree ident)
7839 for (chain = protocol_chain; chain; chain = TREE_CHAIN (chain))
7840 if (ident == PROTOCOL_NAME (chain))
7846 /* This function forward declares the protocols named by NAMES. If
7847 they are already declared or defined, the function has no effect. */
7850 objc_declare_protocols (tree names)
7855 if (current_namespace != global_namespace) {
7856 error ("Objective-C declarations may only appear in global scope");
7858 #endif /* OBJCPLUS */
7860 for (list = names; list; list = TREE_CHAIN (list))
7862 tree name = TREE_VALUE (list);
7864 if (lookup_protocol (name) == NULL_TREE)
7866 tree protocol = make_node (PROTOCOL_INTERFACE_TYPE);
7868 TYPE_LANG_SLOT_1 (protocol)
7869 = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
7870 PROTOCOL_NAME (protocol) = name;
7871 PROTOCOL_LIST (protocol) = NULL_TREE;
7872 add_protocol (protocol);
7873 PROTOCOL_DEFINED (protocol) = 0;
7874 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
7880 start_protocol (enum tree_code code, tree name, tree list)
7885 if (current_namespace != global_namespace) {
7886 error ("Objective-C declarations may only appear in global scope");
7888 #endif /* OBJCPLUS */
7890 protocol = lookup_protocol (name);
7894 protocol = make_node (code);
7895 TYPE_LANG_SLOT_1 (protocol) = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
7897 PROTOCOL_NAME (protocol) = name;
7898 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
7899 add_protocol (protocol);
7900 PROTOCOL_DEFINED (protocol) = 1;
7901 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
7903 check_protocol_recursively (protocol, list);
7905 else if (! PROTOCOL_DEFINED (protocol))
7907 PROTOCOL_DEFINED (protocol) = 1;
7908 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list);
7910 check_protocol_recursively (protocol, list);
7914 warning (0, "duplicate declaration for protocol %qE",
7921 /* "Encode" a data type into a string, which grows in util_obstack.
7922 ??? What is the FORMAT? Someone please document this! */
7925 encode_type_qualifiers (tree declspecs)
7929 for (spec = declspecs; spec; spec = TREE_CHAIN (spec))
7931 if (ridpointers[(int) RID_IN] == TREE_VALUE (spec))
7932 obstack_1grow (&util_obstack, 'n');
7933 else if (ridpointers[(int) RID_INOUT] == TREE_VALUE (spec))
7934 obstack_1grow (&util_obstack, 'N');
7935 else if (ridpointers[(int) RID_OUT] == TREE_VALUE (spec))
7936 obstack_1grow (&util_obstack, 'o');
7937 else if (ridpointers[(int) RID_BYCOPY] == TREE_VALUE (spec))
7938 obstack_1grow (&util_obstack, 'O');
7939 else if (ridpointers[(int) RID_BYREF] == TREE_VALUE (spec))
7940 obstack_1grow (&util_obstack, 'R');
7941 else if (ridpointers[(int) RID_ONEWAY] == TREE_VALUE (spec))
7942 obstack_1grow (&util_obstack, 'V');
7946 /* Encode a pointer type. */
7949 encode_pointer (tree type, int curtype, int format)
7951 tree pointer_to = TREE_TYPE (type);
7953 if (TREE_CODE (pointer_to) == RECORD_TYPE)
7955 if (OBJC_TYPE_NAME (pointer_to)
7956 && TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE)
7958 const char *name = IDENTIFIER_POINTER (OBJC_TYPE_NAME (pointer_to));
7960 if (strcmp (name, TAG_OBJECT) == 0) /* '@' */
7962 obstack_1grow (&util_obstack, '@');
7965 else if (TYPE_HAS_OBJC_INFO (pointer_to)
7966 && TYPE_OBJC_INTERFACE (pointer_to))
7968 if (generating_instance_variables)
7970 obstack_1grow (&util_obstack, '@');
7971 obstack_1grow (&util_obstack, '"');
7972 obstack_grow (&util_obstack, name, strlen (name));
7973 obstack_1grow (&util_obstack, '"');
7978 obstack_1grow (&util_obstack, '@');
7982 else if (strcmp (name, TAG_CLASS) == 0) /* '#' */
7984 obstack_1grow (&util_obstack, '#');
7987 else if (strcmp (name, TAG_SELECTOR) == 0) /* ':' */
7989 obstack_1grow (&util_obstack, ':');
7994 else if (TREE_CODE (pointer_to) == INTEGER_TYPE
7995 && TYPE_MODE (pointer_to) == QImode)
7997 tree pname = TREE_CODE (OBJC_TYPE_NAME (pointer_to)) == IDENTIFIER_NODE
7998 ? OBJC_TYPE_NAME (pointer_to)
7999 : DECL_NAME (OBJC_TYPE_NAME (pointer_to));
8001 if (!flag_next_runtime || strcmp (IDENTIFIER_POINTER (pname), "BOOL"))
8003 /* It appears that "r*" means "const char *" rather than
8005 if (TYPE_READONLY (pointer_to))
8006 obstack_1grow (&util_obstack, 'r');
8008 obstack_1grow (&util_obstack, '*');
8013 /* We have a type that does not get special treatment. */
8015 /* NeXT extension */
8016 obstack_1grow (&util_obstack, '^');
8017 encode_type (pointer_to, curtype, format);
8021 encode_array (tree type, int curtype, int format)
8023 tree an_int_cst = TYPE_SIZE (type);
8024 tree array_of = TREE_TYPE (type);
8027 /* An incomplete array is treated like a pointer. */
8028 if (an_int_cst == NULL)
8030 encode_pointer (type, curtype, format);
8034 if (TREE_INT_CST_LOW (TYPE_SIZE (array_of)) == 0)
8035 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT)0);
8037 sprintf (buffer, "[" HOST_WIDE_INT_PRINT_DEC,
8038 TREE_INT_CST_LOW (an_int_cst)
8039 / TREE_INT_CST_LOW (TYPE_SIZE (array_of)));
8041 obstack_grow (&util_obstack, buffer, strlen (buffer));
8042 encode_type (array_of, curtype, format);
8043 obstack_1grow (&util_obstack, ']');
8048 encode_aggregate_fields (tree type, int pointed_to, int curtype, int format)
8050 tree field = TYPE_FIELDS (type);
8052 for (; field; field = TREE_CHAIN (field))
8055 /* C++ static members, and things that are not field at all,
8056 should not appear in the encoding. */
8057 if (TREE_CODE (field) != FIELD_DECL || TREE_STATIC (field))
8061 /* Recursively encode fields of embedded base classes. */
8062 if (DECL_ARTIFICIAL (field) && !DECL_NAME (field)
8063 && TREE_CODE (TREE_TYPE (field)) == RECORD_TYPE)
8065 encode_aggregate_fields (TREE_TYPE (field),
8066 pointed_to, curtype, format);
8070 if (generating_instance_variables && !pointed_to)
8072 tree fname = DECL_NAME (field);
8074 obstack_1grow (&util_obstack, '"');
8076 if (fname && TREE_CODE (fname) == IDENTIFIER_NODE)
8077 obstack_grow (&util_obstack,
8078 IDENTIFIER_POINTER (fname),
8079 strlen (IDENTIFIER_POINTER (fname)));
8081 obstack_1grow (&util_obstack, '"');
8084 encode_field_decl (field, curtype, format);
8089 encode_aggregate_within (tree type, int curtype, int format, int left,
8093 /* NB: aggregates that are pointed to have slightly different encoding
8094 rules in that you never encode the names of instance variables. */
8095 int ob_size = obstack_object_size (&util_obstack);
8096 char c1 = ob_size > 1 ? *(obstack_next_free (&util_obstack) - 2) : 0;
8097 char c0 = ob_size > 0 ? *(obstack_next_free (&util_obstack) - 1) : 0;
8098 int pointed_to = (c0 == '^' || (c1 == '^' && c0 == 'r'));
8100 = ((format == OBJC_ENCODE_INLINE_DEFS || generating_instance_variables)
8101 && (!pointed_to || ob_size - curtype == (c1 == 'r' ? 2 : 1)));
8103 /* Traverse struct aliases; it is important to get the
8104 original struct and its tag name (if any). */
8105 type = TYPE_MAIN_VARIANT (type);
8106 name = OBJC_TYPE_NAME (type);
8107 /* Open parenth/bracket. */
8108 obstack_1grow (&util_obstack, left);
8110 /* Encode the struct/union tag name, or '?' if a tag was
8111 not provided. Typedef aliases do not qualify. */
8112 if (name && TREE_CODE (name) == IDENTIFIER_NODE
8114 /* Did this struct have a tag? */
8115 && !TYPE_WAS_ANONYMOUS (type)
8118 obstack_grow (&util_obstack,
8119 IDENTIFIER_POINTER (name),
8120 strlen (IDENTIFIER_POINTER (name)));
8122 obstack_1grow (&util_obstack, '?');
8124 /* Encode the types (and possibly names) of the inner fields,
8126 if (inline_contents)
8128 obstack_1grow (&util_obstack, '=');
8129 encode_aggregate_fields (type, pointed_to, curtype, format);
8131 /* Close parenth/bracket. */
8132 obstack_1grow (&util_obstack, right);
8136 encode_aggregate (tree type, int curtype, int format)
8138 enum tree_code code = TREE_CODE (type);
8144 encode_aggregate_within (type, curtype, format, '{', '}');
8149 encode_aggregate_within (type, curtype, format, '(', ')');
8154 obstack_1grow (&util_obstack, 'i');
8162 /* Encode a bitfield NeXT-style (i.e., without a bit offset or the underlying
8166 encode_next_bitfield (int width)
8169 sprintf (buffer, "b%d", width);
8170 obstack_grow (&util_obstack, buffer, strlen (buffer));
8173 /* FORMAT will be OBJC_ENCODE_INLINE_DEFS or OBJC_ENCODE_DONT_INLINE_DEFS. */
8175 encode_type (tree type, int curtype, int format)
8177 enum tree_code code = TREE_CODE (type);
8180 if (type == error_mark_node)
8183 if (TYPE_READONLY (type))
8184 obstack_1grow (&util_obstack, 'r');
8186 if (code == INTEGER_TYPE)
8188 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8190 case 8: c = TYPE_UNSIGNED (type) ? 'C' : 'c'; break;
8191 case 16: c = TYPE_UNSIGNED (type) ? 'S' : 's'; break;
8193 if (type == long_unsigned_type_node
8194 || type == long_integer_type_node)
8195 c = TYPE_UNSIGNED (type) ? 'L' : 'l';
8197 c = TYPE_UNSIGNED (type) ? 'I' : 'i';
8199 case 64: c = TYPE_UNSIGNED (type) ? 'Q' : 'q'; break;
8202 obstack_1grow (&util_obstack, c);
8205 else if (code == REAL_TYPE)
8207 /* Floating point types. */
8208 switch (GET_MODE_BITSIZE (TYPE_MODE (type)))
8210 case 32: c = 'f'; break;
8213 case 128: c = 'd'; break;
8216 obstack_1grow (&util_obstack, c);
8219 else if (code == VOID_TYPE)
8220 obstack_1grow (&util_obstack, 'v');
8222 else if (code == BOOLEAN_TYPE)
8223 obstack_1grow (&util_obstack, 'B');
8225 else if (code == ARRAY_TYPE)
8226 encode_array (type, curtype, format);
8228 else if (code == POINTER_TYPE)
8229 encode_pointer (type, curtype, format);
8231 else if (code == RECORD_TYPE || code == UNION_TYPE || code == ENUMERAL_TYPE)
8232 encode_aggregate (type, curtype, format);
8234 else if (code == FUNCTION_TYPE) /* '?' */
8235 obstack_1grow (&util_obstack, '?');
8237 else if (code == COMPLEX_TYPE)
8239 obstack_1grow (&util_obstack, 'j');
8240 encode_type (TREE_TYPE (type), curtype, format);
8245 encode_gnu_bitfield (int position, tree type, int size)
8247 enum tree_code code = TREE_CODE (type);
8249 char charType = '?';
8251 if (code == INTEGER_TYPE)
8253 if (integer_zerop (TYPE_MIN_VALUE (type)))
8255 /* Unsigned integer types. */
8257 if (TYPE_MODE (type) == QImode)
8259 else if (TYPE_MODE (type) == HImode)
8261 else if (TYPE_MODE (type) == SImode)
8263 if (type == long_unsigned_type_node)
8268 else if (TYPE_MODE (type) == DImode)
8273 /* Signed integer types. */
8275 if (TYPE_MODE (type) == QImode)
8277 else if (TYPE_MODE (type) == HImode)
8279 else if (TYPE_MODE (type) == SImode)
8281 if (type == long_integer_type_node)
8287 else if (TYPE_MODE (type) == DImode)
8291 else if (code == ENUMERAL_TYPE)
8296 sprintf (buffer, "b%d%c%d", position, charType, size);
8297 obstack_grow (&util_obstack, buffer, strlen (buffer));
8301 encode_field_decl (tree field_decl, int curtype, int format)
8306 /* C++ static members, and things that are not fields at all,
8307 should not appear in the encoding. */
8308 if (TREE_CODE (field_decl) != FIELD_DECL || TREE_STATIC (field_decl))
8312 type = TREE_TYPE (field_decl);
8314 /* Generate the bitfield typing information, if needed. Note the difference
8315 between GNU and NeXT runtimes. */
8316 if (DECL_BIT_FIELD_TYPE (field_decl))
8318 int size = tree_low_cst (DECL_SIZE (field_decl), 1);
8320 if (flag_next_runtime)
8321 encode_next_bitfield (size);
8323 encode_gnu_bitfield (int_bit_position (field_decl),
8324 DECL_BIT_FIELD_TYPE (field_decl), size);
8327 encode_type (TREE_TYPE (field_decl), curtype, format);
8330 static GTY(()) tree objc_parmlist = NULL_TREE;
8332 /* Append PARM to a list of formal parameters of a method, making a necessary
8333 array-to-pointer adjustment along the way. */
8336 objc_push_parm (tree parm)
8338 bool relayout_needed = false;
8340 if (TREE_TYPE (parm) == error_mark_node)
8342 objc_parmlist = chainon (objc_parmlist, parm);
8346 /* Decay arrays and functions into pointers. */
8347 if (TREE_CODE (TREE_TYPE (parm)) == ARRAY_TYPE)
8349 TREE_TYPE (parm) = build_pointer_type (TREE_TYPE (TREE_TYPE (parm)));
8350 relayout_needed = true;
8352 else if (TREE_CODE (TREE_TYPE (parm)) == FUNCTION_TYPE)
8354 TREE_TYPE (parm) = build_pointer_type (TREE_TYPE (parm));
8355 relayout_needed = true;
8358 if (relayout_needed)
8359 relayout_decl (parm);
8362 DECL_ARG_TYPE (parm)
8363 = lang_hooks.types.type_promotes_to (TREE_TYPE (parm));
8365 /* Record constancy and volatility. */
8366 c_apply_type_quals_to_decl
8367 ((TYPE_READONLY (TREE_TYPE (parm)) ? TYPE_QUAL_CONST : 0)
8368 | (TYPE_RESTRICT (TREE_TYPE (parm)) ? TYPE_QUAL_RESTRICT : 0)
8369 | (TYPE_VOLATILE (TREE_TYPE (parm)) ? TYPE_QUAL_VOLATILE : 0), parm);
8371 objc_parmlist = chainon (objc_parmlist, parm);
8374 /* Retrieve the formal parameter list constructed via preceding calls to
8375 objc_push_parm(). */
8379 objc_get_parm_info (int have_ellipsis ATTRIBUTE_UNUSED)
8381 static struct c_arg_info *
8382 objc_get_parm_info (int have_ellipsis)
8386 tree parm_info = objc_parmlist;
8387 objc_parmlist = NULL_TREE;
8391 tree parm_info = objc_parmlist;
8392 struct c_arg_info *arg_info;
8393 /* The C front-end requires an elaborate song and dance at
8396 declare_parm_level ();
8399 tree next = TREE_CHAIN (parm_info);
8401 TREE_CHAIN (parm_info) = NULL_TREE;
8402 parm_info = pushdecl (parm_info);
8403 finish_decl (parm_info, input_location, NULL_TREE, NULL_TREE, NULL_TREE);
8406 arg_info = get_parm_info (have_ellipsis);
8408 objc_parmlist = NULL_TREE;
8413 /* Synthesize the formal parameters 'id self' and 'SEL _cmd' needed for ObjC
8414 method definitions. In the case of instance methods, we can be more
8415 specific as to the type of 'self'. */
8418 synth_self_and_ucmd_args (void)
8422 if (objc_method_context
8423 && TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL)
8424 self_type = objc_instance_type;
8426 /* Really a `struct objc_class *'. However, we allow people to
8427 assign to self, which changes its type midstream. */
8428 self_type = objc_object_type;
8431 objc_push_parm (build_decl (input_location,
8432 PARM_DECL, self_id, self_type));
8435 objc_push_parm (build_decl (input_location,
8436 PARM_DECL, ucmd_id, objc_selector_type));
8439 /* Transform an Objective-C method definition into a static C function
8440 definition, synthesizing the first two arguments, "self" and "_cmd",
8444 start_method_def (tree method)
8450 struct c_arg_info *parm_info;
8452 int have_ellipsis = 0;
8454 /* If we are defining a "dealloc" method in a non-root class, we
8455 will need to check if a [super dealloc] is missing, and warn if
8457 if(CLASS_SUPER_NAME (objc_implementation_context)
8458 && !strcmp ("dealloc", IDENTIFIER_POINTER (METHOD_SEL_NAME (method))))
8459 should_call_super_dealloc = 1;
8461 should_call_super_dealloc = 0;
8463 /* Required to implement _msgSuper. */
8464 objc_method_context = method;
8465 UOBJC_SUPER_decl = NULL_TREE;
8467 /* Generate prototype declarations for arguments..."new-style". */
8468 synth_self_and_ucmd_args ();
8470 /* Generate argument declarations if a keyword_decl. */
8471 parmlist = METHOD_SEL_ARGS (method);
8474 tree type = TREE_VALUE (TREE_TYPE (parmlist)), parm;
8476 parm = build_decl (input_location,
8477 PARM_DECL, KEYWORD_ARG_NAME (parmlist), type);
8478 objc_push_parm (parm);
8479 parmlist = TREE_CHAIN (parmlist);
8482 if (METHOD_ADD_ARGS (method))
8486 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (method));
8487 akey; akey = TREE_CHAIN (akey))
8489 objc_push_parm (TREE_VALUE (akey));
8492 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8496 parm_info = objc_get_parm_info (have_ellipsis);
8498 really_start_method (objc_method_context, parm_info);
8501 /* Return 1 if TYPE1 is equivalent to TYPE2
8502 for purposes of method overloading. */
8505 objc_types_are_equivalent (tree type1, tree type2)
8510 /* Strip away indirections. */
8511 while ((TREE_CODE (type1) == ARRAY_TYPE || TREE_CODE (type1) == POINTER_TYPE)
8512 && (TREE_CODE (type1) == TREE_CODE (type2)))
8513 type1 = TREE_TYPE (type1), type2 = TREE_TYPE (type2);
8514 if (TYPE_MAIN_VARIANT (type1) != TYPE_MAIN_VARIANT (type2))
8517 type1 = (TYPE_HAS_OBJC_INFO (type1)
8518 ? TYPE_OBJC_PROTOCOL_LIST (type1)
8520 type2 = (TYPE_HAS_OBJC_INFO (type2)
8521 ? TYPE_OBJC_PROTOCOL_LIST (type2)
8524 if (list_length (type1) == list_length (type2))
8526 for (; type2; type2 = TREE_CHAIN (type2))
8527 if (!lookup_protocol_in_reflist (type1, TREE_VALUE (type2)))
8534 /* Return 1 if TYPE1 has the same size and alignment as TYPE2. */
8537 objc_types_share_size_and_alignment (tree type1, tree type2)
8539 return (simple_cst_equal (TYPE_SIZE (type1), TYPE_SIZE (type2))
8540 && TYPE_ALIGN (type1) == TYPE_ALIGN (type2));
8543 /* Return 1 if PROTO1 is equivalent to PROTO2
8544 for purposes of method overloading. Ordinarily, the type signatures
8545 should match up exactly, unless STRICT is zero, in which case we
8546 shall allow differences in which the size and alignment of a type
8550 comp_proto_with_proto (tree proto1, tree proto2, int strict)
8554 /* The following test is needed in case there are hashing
8556 if (METHOD_SEL_NAME (proto1) != METHOD_SEL_NAME (proto2))
8559 /* Compare return types. */
8560 type1 = TREE_VALUE (TREE_TYPE (proto1));
8561 type2 = TREE_VALUE (TREE_TYPE (proto2));
8563 if (!objc_types_are_equivalent (type1, type2)
8564 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8567 /* Compare argument types. */
8568 for (type1 = get_arg_type_list (proto1, METHOD_REF, 0),
8569 type2 = get_arg_type_list (proto2, METHOD_REF, 0);
8571 type1 = TREE_CHAIN (type1), type2 = TREE_CHAIN (type2))
8573 if (!objc_types_are_equivalent (TREE_VALUE (type1), TREE_VALUE (type2))
8575 || !objc_types_share_size_and_alignment (TREE_VALUE (type1),
8576 TREE_VALUE (type2))))
8580 return (!type1 && !type2);
8583 /* Fold an OBJ_TYPE_REF expression for ObjC method dispatches, where
8584 this occurs. ObjC method dispatches are _not_ like C++ virtual
8585 member function dispatches, and we account for the difference here. */
8588 objc_fold_obj_type_ref (tree ref, tree known_type)
8590 objc_fold_obj_type_ref (tree ref ATTRIBUTE_UNUSED,
8591 tree known_type ATTRIBUTE_UNUSED)
8595 tree v = BINFO_VIRTUALS (TYPE_BINFO (known_type));
8597 /* If the receiver does not have virtual member functions, there
8598 is nothing we can (or need to) do here. */
8602 /* Let C++ handle C++ virtual functions. */
8603 return cp_fold_obj_type_ref (ref, known_type);
8605 /* For plain ObjC, we currently do not need to do anything. */
8611 objc_start_function (tree name, tree type, tree attrs,
8615 struct c_arg_info *params
8619 tree fndecl = build_decl (input_location,
8620 FUNCTION_DECL, name, type);
8623 DECL_ARGUMENTS (fndecl) = params;
8624 DECL_INITIAL (fndecl) = error_mark_node;
8625 DECL_EXTERNAL (fndecl) = 0;
8626 TREE_STATIC (fndecl) = 1;
8627 retrofit_lang_decl (fndecl);
8628 cplus_decl_attributes (&fndecl, attrs, 0);
8629 start_preparsed_function (fndecl, attrs, /*flags=*/SF_DEFAULT);
8631 current_function_returns_value = 0; /* Assume, until we see it does. */
8632 current_function_returns_null = 0;
8634 decl_attributes (&fndecl, attrs, 0);
8635 announce_function (fndecl);
8636 DECL_INITIAL (fndecl) = error_mark_node;
8637 DECL_EXTERNAL (fndecl) = 0;
8638 TREE_STATIC (fndecl) = 1;
8639 current_function_decl = pushdecl (fndecl);
8641 declare_parm_level ();
8642 DECL_RESULT (current_function_decl)
8643 = build_decl (input_location,
8644 RESULT_DECL, NULL_TREE,
8645 TREE_TYPE (TREE_TYPE (current_function_decl)));
8646 DECL_ARTIFICIAL (DECL_RESULT (current_function_decl)) = 1;
8647 DECL_IGNORED_P (DECL_RESULT (current_function_decl)) = 1;
8648 start_fname_decls ();
8649 store_parm_decls_from (params);
8652 TREE_USED (current_function_decl) = 1;
8655 /* - Generate an identifier for the function. the format is "_n_cls",
8656 where 1 <= n <= nMethods, and cls is the name the implementation we
8658 - Install the return type from the method declaration.
8659 - If we have a prototype, check for type consistency. */
8662 really_start_method (tree method,
8666 struct c_arg_info *parmlist
8670 tree ret_type, meth_type;
8672 const char *sel_name, *class_name, *cat_name;
8675 /* Synth the storage class & assemble the return type. */
8676 ret_type = TREE_VALUE (TREE_TYPE (method));
8678 sel_name = IDENTIFIER_POINTER (METHOD_SEL_NAME (method));
8679 class_name = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
8680 cat_name = ((TREE_CODE (objc_implementation_context)
8681 == CLASS_IMPLEMENTATION_TYPE)
8683 : IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
8686 /* Make sure this is big enough for any plausible method label. */
8687 buf = (char *) alloca (50 + strlen (sel_name) + strlen (class_name)
8688 + (cat_name ? strlen (cat_name) : 0));
8690 OBJC_GEN_METHOD_LABEL (buf, TREE_CODE (method) == INSTANCE_METHOD_DECL,
8691 class_name, cat_name, sel_name, method_slot);
8693 method_id = get_identifier (buf);
8696 /* Objective-C methods cannot be overloaded, so we don't need
8697 the type encoding appended. It looks bad anyway... */
8698 push_lang_context (lang_name_c);
8702 = build_function_type (ret_type,
8703 get_arg_type_list (method, METHOD_DEF, 0));
8704 objc_start_function (method_id, meth_type, NULL_TREE, parmlist);
8706 /* Set self_decl from the first argument. */
8707 self_decl = DECL_ARGUMENTS (current_function_decl);
8709 /* Suppress unused warnings. */
8710 TREE_USED (self_decl) = 1;
8711 TREE_USED (TREE_CHAIN (self_decl)) = 1;
8713 pop_lang_context ();
8716 METHOD_DEFINITION (method) = current_function_decl;
8718 /* Check consistency...start_function, pushdecl, duplicate_decls. */
8720 if (implementation_template != objc_implementation_context)
8723 = lookup_method_static (implementation_template,
8724 METHOD_SEL_NAME (method),
8725 ((TREE_CODE (method) == CLASS_METHOD_DECL)
8726 | OBJC_LOOKUP_NO_SUPER));
8730 if (!comp_proto_with_proto (method, proto, 1))
8732 bool type = TREE_CODE (method) == INSTANCE_METHOD_DECL;
8734 warning_at (DECL_SOURCE_LOCATION (method), 0,
8735 "conflicting types for %<%c%s%>",
8737 identifier_to_locale (gen_method_decl (method)));
8738 inform (DECL_SOURCE_LOCATION (proto),
8739 "previous declaration of %<%c%s%>",
8741 identifier_to_locale (gen_method_decl (proto)));
8746 /* We have a method @implementation even though we did not
8747 see a corresponding @interface declaration (which is allowed
8748 by Objective-C rules). Go ahead and place the method in
8749 the @interface anyway, so that message dispatch lookups
8751 tree interface = implementation_template;
8753 if (TREE_CODE (objc_implementation_context)
8754 == CATEGORY_IMPLEMENTATION_TYPE)
8755 interface = lookup_category
8757 CLASS_SUPER_NAME (objc_implementation_context));
8760 objc_add_method (interface, copy_node (method),
8761 TREE_CODE (method) == CLASS_METHOD_DECL);
8766 static void *UOBJC_SUPER_scope = 0;
8768 /* _n_Method (id self, SEL sel, ...)
8770 struct objc_super _S;
8771 _msgSuper ((_S.self = self, _S.class = _cls, &_S), ...);
8775 get_super_receiver (void)
8777 if (objc_method_context)
8779 tree super_expr, super_expr_list;
8781 if (!UOBJC_SUPER_decl)
8783 UOBJC_SUPER_decl = build_decl (input_location,
8784 VAR_DECL, get_identifier (TAG_SUPER),
8785 objc_super_template);
8786 /* This prevents `unused variable' warnings when compiling with -Wall. */
8787 TREE_USED (UOBJC_SUPER_decl) = 1;
8788 lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
8789 finish_decl (UOBJC_SUPER_decl, input_location, NULL_TREE, NULL_TREE,
8791 UOBJC_SUPER_scope = objc_get_current_scope ();
8794 /* Set receiver to self. */
8795 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
8796 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
8797 NOP_EXPR, input_location, self_decl,
8799 super_expr_list = super_expr;
8801 /* Set class to begin searching. */
8802 super_expr = objc_build_component_ref (UOBJC_SUPER_decl,
8803 get_identifier ("super_class"));
8805 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
8807 /* [_cls, __cls]Super are "pre-built" in
8808 synth_forward_declarations. */
8810 super_expr = build_modify_expr (input_location, super_expr,
8811 NULL_TREE, NOP_EXPR,
8813 ((TREE_CODE (objc_method_context)
8814 == INSTANCE_METHOD_DECL)
8821 /* We have a category. */
8823 tree super_name = CLASS_SUPER_NAME (implementation_template);
8826 /* Barf if super used in a category of Object. */
8829 error ("no super class declared in interface for %qE",
8830 CLASS_NAME (implementation_template));
8831 return error_mark_node;
8834 if (flag_next_runtime && !flag_zero_link)
8836 super_class = objc_get_class_reference (super_name);
8837 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
8838 /* If we are in a class method, we must retrieve the
8839 _metaclass_ for the current class, pointed at by
8840 the class's "isa" pointer. The following assumes that
8841 "isa" is the first ivar in a class (which it must be). */
8843 = build_indirect_ref
8845 build_c_cast (input_location,
8846 build_pointer_type (objc_class_type),
8847 super_class), "unary *");
8851 add_class_reference (super_name);
8852 super_class = (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
8853 ? objc_get_class_decl : objc_get_meta_class_decl);
8854 assemble_external (super_class);
8856 = build_function_call
8861 my_build_string_pointer
8862 (IDENTIFIER_LENGTH (super_name) + 1,
8863 IDENTIFIER_POINTER (super_name))));
8867 = build_modify_expr (input_location, super_expr, NULL_TREE,
8870 build_c_cast (input_location,
8871 TREE_TYPE (super_expr),
8876 super_expr_list = build_compound_expr (input_location,
8877 super_expr_list, super_expr);
8879 super_expr = build_unary_op (input_location,
8880 ADDR_EXPR, UOBJC_SUPER_decl, 0);
8881 super_expr_list = build_compound_expr (input_location,
8882 super_expr_list, super_expr);
8884 return super_expr_list;
8888 error ("[super ...] must appear in a method context");
8889 return error_mark_node;
8893 /* When exiting a scope, sever links to a 'super' declaration (if any)
8894 therein contained. */
8897 objc_clear_super_receiver (void)
8899 if (objc_method_context
8900 && UOBJC_SUPER_scope == objc_get_current_scope ()) {
8901 UOBJC_SUPER_decl = 0;
8902 UOBJC_SUPER_scope = 0;
8907 objc_finish_method_definition (tree fndecl)
8909 /* We cannot validly inline ObjC methods, at least not without a language
8910 extension to declare that a method need not be dynamically
8911 dispatched, so suppress all thoughts of doing so. */
8912 DECL_UNINLINABLE (fndecl) = 1;
8915 /* The C++ front-end will have called finish_function() for us. */
8919 METHOD_ENCODING (objc_method_context)
8920 = encode_method_prototype (objc_method_context);
8922 /* Required to implement _msgSuper. This must be done AFTER finish_function,
8923 since the optimizer may find "may be used before set" errors. */
8924 objc_method_context = NULL_TREE;
8926 if (should_call_super_dealloc)
8927 warning (0, "method possibly missing a [super dealloc] call");
8930 /* Given a tree DECL node, produce a printable description of it in the given
8931 buffer, overwriting the buffer. */
8934 gen_declaration (tree decl)
8940 gen_type_name_0 (TREE_TYPE (decl));
8942 if (DECL_NAME (decl))
8944 if (!POINTER_TYPE_P (TREE_TYPE (decl)))
8945 strcat (errbuf, " ");
8947 strcat (errbuf, IDENTIFIER_POINTER (DECL_NAME (decl)));
8950 if (DECL_INITIAL (decl)
8951 && TREE_CODE (DECL_INITIAL (decl)) == INTEGER_CST)
8952 sprintf (errbuf + strlen (errbuf), ": " HOST_WIDE_INT_PRINT_DEC,
8953 TREE_INT_CST_LOW (DECL_INITIAL (decl)));
8959 /* Given a tree TYPE node, produce a printable description of it in the given
8960 buffer, overwriting the buffer. */
8963 gen_type_name_0 (tree type)
8965 tree orig = type, proto;
8967 if (TYPE_P (type) && TYPE_NAME (type))
8968 type = TYPE_NAME (type);
8969 else if (POINTER_TYPE_P (type) || TREE_CODE (type) == ARRAY_TYPE)
8971 tree inner = TREE_TYPE (type);
8973 while (TREE_CODE (inner) == ARRAY_TYPE)
8974 inner = TREE_TYPE (inner);
8976 gen_type_name_0 (inner);
8978 if (!POINTER_TYPE_P (inner))
8979 strcat (errbuf, " ");
8981 if (POINTER_TYPE_P (type))
8982 strcat (errbuf, "*");
8984 while (type != inner)
8986 strcat (errbuf, "[");
8988 if (TYPE_DOMAIN (type))
8992 sprintf (sz, HOST_WIDE_INT_PRINT_DEC,
8994 (TYPE_MAX_VALUE (TYPE_DOMAIN (type))) + 1));
8995 strcat (errbuf, sz);
8998 strcat (errbuf, "]");
8999 type = TREE_TYPE (type);
9005 if (TREE_CODE (type) == TYPE_DECL && DECL_NAME (type))
9006 type = DECL_NAME (type);
9008 strcat (errbuf, TREE_CODE (type) == IDENTIFIER_NODE
9009 ? IDENTIFIER_POINTER (type)
9012 /* For 'id' and 'Class', adopted protocols are stored in the pointee. */
9013 if (objc_is_id (orig))
9014 orig = TREE_TYPE (orig);
9016 proto = TYPE_HAS_OBJC_INFO (orig) ? TYPE_OBJC_PROTOCOL_LIST (orig) : NULL_TREE;
9020 strcat (errbuf, " <");
9024 IDENTIFIER_POINTER (PROTOCOL_NAME (TREE_VALUE (proto))));
9025 proto = TREE_CHAIN (proto);
9026 strcat (errbuf, proto ? ", " : ">");
9035 gen_type_name (tree type)
9039 return gen_type_name_0 (type);
9042 /* Given a method tree, put a printable description into the given
9043 buffer (overwriting) and return a pointer to the buffer. */
9046 gen_method_decl (tree method)
9050 strcpy (errbuf, "("); /* NB: Do _not_ call strcat() here. */
9051 gen_type_name_0 (TREE_VALUE (TREE_TYPE (method)));
9052 strcat (errbuf, ")");
9053 chain = METHOD_SEL_ARGS (method);
9057 /* We have a chain of keyword_decls. */
9060 if (KEYWORD_KEY_NAME (chain))
9061 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_KEY_NAME (chain)));
9063 strcat (errbuf, ":(");
9064 gen_type_name_0 (TREE_VALUE (TREE_TYPE (chain)));
9065 strcat (errbuf, ")");
9067 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_ARG_NAME (chain)));
9068 if ((chain = TREE_CHAIN (chain)))
9069 strcat (errbuf, " ");
9073 if (METHOD_ADD_ARGS (method))
9075 chain = TREE_CHAIN (METHOD_ADD_ARGS (method));
9077 /* Know we have a chain of parm_decls. */
9080 strcat (errbuf, ", ");
9081 gen_type_name_0 (TREE_TYPE (TREE_VALUE (chain)));
9082 chain = TREE_CHAIN (chain);
9085 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
9086 strcat (errbuf, ", ...");
9091 /* We have a unary selector. */
9092 strcat (errbuf, IDENTIFIER_POINTER (METHOD_SEL_NAME (method)));
9100 /* Dump an @interface declaration of the supplied class CHAIN to the
9101 supplied file FP. Used to implement the -gen-decls option (which
9102 prints out an @interface declaration of all classes compiled in
9103 this run); potentially useful for debugging the compiler too. */
9105 dump_interface (FILE *fp, tree chain)
9107 /* FIXME: A heap overflow here whenever a method (or ivar)
9108 declaration is so long that it doesn't fit in the buffer. The
9109 code and all the related functions should be rewritten to avoid
9110 using fixed size buffers. */
9111 const char *my_name = IDENTIFIER_POINTER (CLASS_NAME (chain));
9112 tree ivar_decls = CLASS_RAW_IVARS (chain);
9113 tree nst_methods = CLASS_NST_METHODS (chain);
9114 tree cls_methods = CLASS_CLS_METHODS (chain);
9116 fprintf (fp, "\n@interface %s", my_name);
9118 /* CLASS_SUPER_NAME is used to store the superclass name for
9119 classes, and the category name for categories. */
9120 if (CLASS_SUPER_NAME (chain))
9122 const char *name = IDENTIFIER_POINTER (CLASS_SUPER_NAME (chain));
9124 if (TREE_CODE (chain) == CATEGORY_IMPLEMENTATION_TYPE
9125 || TREE_CODE (chain) == CATEGORY_INTERFACE_TYPE)
9127 fprintf (fp, " (%s)\n", name);
9131 fprintf (fp, " : %s\n", name);
9137 /* FIXME - the following doesn't seem to work at the moment. */
9140 fprintf (fp, "{\n");
9143 fprintf (fp, "\t%s;\n", gen_declaration (ivar_decls));
9144 ivar_decls = TREE_CHAIN (ivar_decls);
9147 fprintf (fp, "}\n");
9152 fprintf (fp, "- %s;\n", gen_method_decl (nst_methods));
9153 nst_methods = TREE_CHAIN (nst_methods);
9158 fprintf (fp, "+ %s;\n", gen_method_decl (cls_methods));
9159 cls_methods = TREE_CHAIN (cls_methods);
9162 fprintf (fp, "@end\n");
9165 /* Demangle function for Objective-C */
9167 objc_demangle (const char *mangled)
9169 char *demangled, *cp;
9171 if (mangled[0] == '_' &&
9172 (mangled[1] == 'i' || mangled[1] == 'c') &&
9175 cp = demangled = XNEWVEC (char, strlen(mangled) + 2);
9176 if (mangled[1] == 'i')
9177 *cp++ = '-'; /* for instance method */
9179 *cp++ = '+'; /* for class method */
9180 *cp++ = '['; /* opening left brace */
9181 strcpy(cp, mangled+3); /* tack on the rest of the mangled name */
9182 while (*cp && *cp == '_')
9183 cp++; /* skip any initial underbars in class name */
9184 cp = strchr(cp, '_'); /* find first non-initial underbar */
9187 free(demangled); /* not mangled name */
9190 if (cp[1] == '_') /* easy case: no category name */
9192 *cp++ = ' '; /* replace two '_' with one ' ' */
9193 strcpy(cp, mangled + (cp - demangled) + 2);
9197 *cp++ = '('; /* less easy case: category name */
9198 cp = strchr(cp, '_');
9201 free(demangled); /* not mangled name */
9205 *cp++ = ' '; /* overwriting 1st char of method name... */
9206 strcpy(cp, mangled + (cp - demangled)); /* get it back */
9208 while (*cp && *cp == '_')
9209 cp++; /* skip any initial underbars in method name */
9212 *cp = ':'; /* replace remaining '_' with ':' */
9213 *cp++ = ']'; /* closing right brace */
9214 *cp++ = 0; /* string terminator */
9218 return mangled; /* not an objc mangled name */
9222 objc_printable_name (tree decl, int kind ATTRIBUTE_UNUSED)
9224 return objc_demangle (IDENTIFIER_POINTER (DECL_NAME (decl)));
9230 gcc_obstack_init (&util_obstack);
9231 util_firstobj = (char *) obstack_finish (&util_obstack);
9233 errbuf = XNEWVEC (char, 1024 * 10);
9235 synth_module_prologue ();
9241 struct imp_entry *impent;
9243 /* The internally generated initializers appear to have missing braces.
9244 Don't warn about this. */
9245 int save_warn_missing_braces = warn_missing_braces;
9246 warn_missing_braces = 0;
9248 /* A missing @end may not be detected by the parser. */
9249 if (objc_implementation_context)
9251 warning (0, "%<@end%> missing in implementation context");
9252 finish_class (objc_implementation_context);
9253 objc_ivar_chain = NULL_TREE;
9254 objc_implementation_context = NULL_TREE;
9257 /* Process the static instances here because initialization of objc_symtab
9259 if (objc_static_instances)
9260 generate_static_references ();
9262 if (imp_list || class_names_chain
9263 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9264 generate_objc_symtab_decl ();
9266 for (impent = imp_list; impent; impent = impent->next)
9268 objc_implementation_context = impent->imp_context;
9269 implementation_template = impent->imp_template;
9271 UOBJC_CLASS_decl = impent->class_decl;
9272 UOBJC_METACLASS_decl = impent->meta_decl;
9274 /* Dump the @interface of each class as we compile it, if the
9275 -gen-decls option is in use. TODO: Dump the classes in the
9276 order they were found, rather than in reverse order as we
9278 if (flag_gen_declaration)
9280 dump_interface (gen_declaration_file, objc_implementation_context);
9283 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
9285 /* all of the following reference the string pool... */
9286 generate_ivar_lists ();
9287 generate_dispatch_tables ();
9288 generate_shared_structures (impent->has_cxx_cdtors
9289 ? CLS_HAS_CXX_STRUCTORS
9294 generate_dispatch_tables ();
9295 generate_category (objc_implementation_context);
9299 /* If we are using an array of selectors, we must always
9300 finish up the array decl even if no selectors were used. */
9301 if (! flag_next_runtime || sel_ref_chain)
9302 build_selector_translation_table ();
9305 generate_protocols ();
9307 if ((flag_replace_objc_classes && imp_list) || flag_objc_gc)
9308 generate_objc_image_info ();
9310 /* Arrange for ObjC data structures to be initialized at run time. */
9311 if (objc_implementation_context || class_names_chain || objc_static_instances
9312 || meth_var_names_chain || meth_var_types_chain || sel_ref_chain)
9314 build_module_descriptor ();
9316 if (!flag_next_runtime)
9317 build_module_initializer_routine ();
9320 /* Dump the class references. This forces the appropriate classes
9321 to be linked into the executable image, preserving unix archive
9322 semantics. This can be removed when we move to a more dynamically
9323 linked environment. */
9325 for (chain = cls_ref_chain; chain; chain = TREE_CHAIN (chain))
9327 handle_class_ref (chain);
9328 if (TREE_PURPOSE (chain))
9329 generate_classref_translation_entry (chain);
9332 for (impent = imp_list; impent; impent = impent->next)
9333 handle_impent (impent);
9340 /* Run through the selector hash tables and print a warning for any
9341 selector which has multiple methods. */
9343 for (slot = 0; slot < SIZEHASHTABLE; slot++)
9345 for (hsh = cls_method_hash_list[slot]; hsh; hsh = hsh->next)
9346 check_duplicates (hsh, 0, 1);
9347 for (hsh = nst_method_hash_list[slot]; hsh; hsh = hsh->next)
9348 check_duplicates (hsh, 0, 1);
9352 warn_missing_braces = save_warn_missing_braces;
9355 /* Subroutines of finish_objc. */
9358 generate_classref_translation_entry (tree chain)
9360 tree expr, decl, type;
9362 decl = TREE_PURPOSE (chain);
9363 type = TREE_TYPE (decl);
9365 expr = add_objc_string (TREE_VALUE (chain), class_names);
9366 expr = convert (type, expr); /* cast! */
9368 /* The decl that is the one that we
9369 forward declared in build_class_reference. */
9370 finish_var_decl (decl, expr);
9375 handle_class_ref (tree chain)
9377 const char *name = IDENTIFIER_POINTER (TREE_VALUE (chain));
9378 char *string = (char *) alloca (strlen (name) + 30);
9382 sprintf (string, "%sobjc_class_name_%s",
9383 (flag_next_runtime ? "." : "__"), name);
9385 #ifdef ASM_DECLARE_UNRESOLVED_REFERENCE
9386 if (flag_next_runtime)
9388 ASM_DECLARE_UNRESOLVED_REFERENCE (asm_out_file, string);
9393 /* Make a decl for this name, so we can use its address in a tree. */
9394 decl = build_decl (input_location,
9395 VAR_DECL, get_identifier (string), char_type_node);
9396 DECL_EXTERNAL (decl) = 1;
9397 TREE_PUBLIC (decl) = 1;
9400 rest_of_decl_compilation (decl, 0, 0);
9402 /* Make a decl for the address. */
9403 sprintf (string, "%sobjc_class_ref_%s",
9404 (flag_next_runtime ? "." : "__"), name);
9405 exp = build1 (ADDR_EXPR, string_type_node, decl);
9406 decl = build_decl (input_location,
9407 VAR_DECL, get_identifier (string), string_type_node);
9408 DECL_INITIAL (decl) = exp;
9409 TREE_STATIC (decl) = 1;
9410 TREE_USED (decl) = 1;
9411 /* Force the output of the decl as this forces the reference of the class. */
9412 mark_decl_referenced (decl);
9415 rest_of_decl_compilation (decl, 0, 0);
9419 handle_impent (struct imp_entry *impent)
9423 objc_implementation_context = impent->imp_context;
9424 implementation_template = impent->imp_template;
9426 if (TREE_CODE (impent->imp_context) == CLASS_IMPLEMENTATION_TYPE)
9428 const char *const class_name =
9429 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9431 string = (char *) alloca (strlen (class_name) + 30);
9433 sprintf (string, "%sobjc_class_name_%s",
9434 (flag_next_runtime ? "." : "__"), class_name);
9436 else if (TREE_CODE (impent->imp_context) == CATEGORY_IMPLEMENTATION_TYPE)
9438 const char *const class_name =
9439 IDENTIFIER_POINTER (CLASS_NAME (impent->imp_context));
9440 const char *const class_super_name =
9441 IDENTIFIER_POINTER (CLASS_SUPER_NAME (impent->imp_context));
9443 string = (char *) alloca (strlen (class_name)
9444 + strlen (class_super_name) + 30);
9446 /* Do the same for categories. Even though no references to
9447 these symbols are generated automatically by the compiler, it
9448 gives you a handle to pull them into an archive by hand. */
9449 sprintf (string, "*%sobjc_category_name_%s_%s",
9450 (flag_next_runtime ? "." : "__"), class_name, class_super_name);
9455 #ifdef ASM_DECLARE_CLASS_REFERENCE
9456 if (flag_next_runtime)
9458 ASM_DECLARE_CLASS_REFERENCE (asm_out_file, string);
9466 init = build_int_cst (c_common_type_for_size (BITS_PER_WORD, 1), 0);
9467 decl = build_decl (input_location,
9468 VAR_DECL, get_identifier (string), TREE_TYPE (init));
9469 TREE_PUBLIC (decl) = 1;
9470 TREE_READONLY (decl) = 1;
9471 TREE_USED (decl) = 1;
9472 TREE_CONSTANT (decl) = 1;
9473 DECL_CONTEXT (decl) = 0;
9474 DECL_ARTIFICIAL (decl) = 1;
9475 DECL_INITIAL (decl) = init;
9476 assemble_variable (decl, 1, 0, 0);
9480 /* The Fix-and-Continue functionality available in Mac OS X 10.3 and
9481 later requires that ObjC translation units participating in F&C be
9482 specially marked. The following routine accomplishes this. */
9484 /* static int _OBJC_IMAGE_INFO[2] = { 0, 1 }; */
9487 generate_objc_image_info (void)
9489 tree decl, initlist;
9491 = ((flag_replace_objc_classes && imp_list ? 1 : 0)
9492 | (flag_objc_gc ? 2 : 0));
9494 decl = start_var_decl (build_array_type
9496 build_index_type (build_int_cst (NULL_TREE, 2 - 1))),
9497 "_OBJC_IMAGE_INFO");
9499 initlist = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, 0));
9500 initlist = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, flags), initlist);
9501 initlist = objc_build_constructor (TREE_TYPE (decl), nreverse (initlist));
9503 finish_var_decl (decl, initlist);
9506 /* Look up ID as an instance variable. OTHER contains the result of
9507 the C or C++ lookup, which we may want to use instead. */
9510 objc_lookup_ivar (tree other, tree id)
9514 /* If we are not inside of an ObjC method, ivar lookup makes no sense. */
9515 if (!objc_method_context)
9518 if (!strcmp (IDENTIFIER_POINTER (id), "super"))
9519 /* We have a message to super. */
9520 return get_super_receiver ();
9522 /* In a class method, look up an instance variable only as a last
9524 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
9525 && other && other != error_mark_node)
9528 /* Look up the ivar, but do not use it if it is not accessible. */
9529 ivar = is_ivar (objc_ivar_chain, id);
9531 if (!ivar || is_private (ivar))
9534 /* In an instance method, a local variable (or parameter) may hide the
9535 instance variable. */
9536 if (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9537 && other && other != error_mark_node
9539 && CP_DECL_CONTEXT (other) != global_namespace)
9541 && !DECL_FILE_SCOPE_P (other))
9544 warning (0, "local declaration of %qE hides instance variable",
9550 /* At this point, we are either in an instance method with no obscuring
9551 local definitions, or in a class method with no alternate definitions
9553 return build_ivar_reference (id);
9556 /* Possibly rewrite a function CALL into an OBJ_TYPE_REF expression. This
9557 needs to be done if we are calling a function through a cast. */
9560 objc_rewrite_function_call (tree function, tree first_param)
9562 if (TREE_CODE (function) == NOP_EXPR
9563 && TREE_CODE (TREE_OPERAND (function, 0)) == ADDR_EXPR
9564 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (function, 0), 0))
9567 function = build3 (OBJ_TYPE_REF, TREE_TYPE (function),
9568 TREE_OPERAND (function, 0),
9569 first_param, size_zero_node);
9575 /* Look for the special case of OBJC_TYPE_REF with the address of
9576 a function in OBJ_TYPE_REF_EXPR (presumably objc_msgSend or one
9580 objc_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
9582 enum gimplify_status r0, r1;
9583 if (TREE_CODE (*expr_p) == OBJ_TYPE_REF
9584 && TREE_CODE (OBJ_TYPE_REF_EXPR (*expr_p)) == ADDR_EXPR
9585 && TREE_CODE (TREE_OPERAND (OBJ_TYPE_REF_EXPR (*expr_p), 0))
9588 /* Postincrements in OBJ_TYPE_REF_OBJECT don't affect the
9589 value of the OBJ_TYPE_REF, so force them to be emitted
9590 during subexpression evaluation rather than after the
9591 OBJ_TYPE_REF. This permits objc_msgSend calls in Objective
9592 C to use direct rather than indirect calls when the
9593 object expression has a postincrement. */
9594 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p, NULL,
9595 is_gimple_val, fb_rvalue);
9596 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p, post_p,
9597 is_gimple_val, fb_rvalue);
9599 return MIN (r0, r1);
9603 return (enum gimplify_status) cp_gimplify_expr (expr_p, pre_p, post_p);
9605 return (enum gimplify_status) c_gimplify_expr (expr_p, pre_p, post_p);
9609 #include "gt-objc-objc-act.h"