Daily bump.
[official-gcc.git] / gcc / objc / objc-act.cc
blobcec64c4bfbd48f17f73ae77d3d2d122a1520ee08
1 /* Implement classes and message passing for Objective C.
2 Copyright (C) 1992-2024 Free Software Foundation, Inc.
3 Contributed by Steve Naroff.
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
10 any later version.
12 GCC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
21 #include "config.h"
22 #include "system.h"
23 #include "coretypes.h"
24 #include "tm.h"
25 #include "tree.h"
26 #include "stringpool.h"
27 #include "stor-layout.h"
28 #include "attribs.h"
30 #ifdef OBJCPLUS
31 #include "cp/cp-tree.h"
32 #else
33 #include "c/c-tree.h"
34 #include "c/c-lang.h"
35 #endif
37 #include "c-family/c-objc.h"
38 #include "langhooks.h"
39 #include "objc-act.h"
40 #include "objc-map.h"
41 #include "function.h"
42 #include "toplev.h"
43 #include "debug.h"
44 #include "c-family/c-target.h"
45 #include "intl.h"
46 #include "cgraph.h"
47 #include "tree-iterator.h"
48 /* Different initialization, code gen and meta data generation for each
49 runtime. */
50 #include "objc-runtime-hooks.h"
51 /* Routines used mainly by the runtimes. */
52 #include "objc-runtime-shared-support.h"
53 /* For default_tree_printer (). */
55 /* For enum gimplify_status */
56 #include "gimple-expr.h"
57 #include "gimplify.h"
59 /* For encode_method_prototype(). */
60 #include "objc-encoding.h"
62 static unsigned int should_call_super_dealloc = 0;
64 /* When building Objective-C++, we are not linking against the C front-end
65 and so need to replicate the C tree-construction functions in some way. */
66 #ifdef OBJCPLUS
67 #define OBJCP_REMAP_FUNCTIONS
68 #include "objcp-decl.h"
69 #endif /* OBJCPLUS */
71 /* This is the default way of generating a method name. */
72 /* This has the problem that "test_method:argument:" and
73 "test:method_argument:" will generate the same name
74 ("_i_Test__test_method_argument_" for an instance method of the
75 class "Test"), so you can't have them both in the same class!
76 Moreover, the demangling (going from
77 "_i_Test__test_method_argument" back to the original name) is
78 undefined because there are two correct ways of demangling the
79 name. */
80 #ifndef OBJC_GEN_METHOD_LABEL
81 #define OBJC_GEN_METHOD_LABEL(BUF, IS_INST, CLASS_NAME, CAT_NAME, SEL_NAME, NUM) \
82 do { \
83 char *temp; \
84 sprintf ((BUF), "_%s_%s_%s_%s", \
85 ((IS_INST) ? "i" : "c"), \
86 (CLASS_NAME), \
87 ((CAT_NAME)? (CAT_NAME) : ""), \
88 (SEL_NAME)); \
89 for (temp = (BUF); *temp; temp++) \
90 if (*temp == ':') *temp = '_'; \
91 } while (0)
92 #endif
94 /* These need specifying. */
95 #ifndef OBJC_FORWARDING_STACK_OFFSET
96 #define OBJC_FORWARDING_STACK_OFFSET 0
97 #endif
99 #ifndef OBJC_FORWARDING_MIN_OFFSET
100 #define OBJC_FORWARDING_MIN_OFFSET 0
101 #endif
103 /*** Private Interface (procedures) ***/
105 /* Init stuff. */
106 static void synth_module_prologue (void);
108 /* Code generation. */
110 static tree start_class (enum tree_code, tree, tree, tree, tree);
111 static tree continue_class (tree);
112 static void finish_class (tree);
113 static void start_method_def (tree, tree);
115 static tree start_protocol (enum tree_code, tree, tree, tree);
116 static tree build_method_decl (enum tree_code, tree, tree, tree, bool);
117 static tree objc_add_method (tree, tree, int, bool);
118 static tree add_instance_variable (tree, objc_ivar_visibility_kind, tree);
119 static tree build_ivar_reference (tree);
121 /* We only need the following for ObjC; ObjC++ will use C++'s definition
122 of DERIVED_FROM_P. */
123 #ifndef OBJCPLUS
124 static bool objc_derived_from_p (tree, tree);
125 #define DERIVED_FROM_P(PARENT, CHILD) objc_derived_from_p (PARENT, CHILD)
126 #endif
128 /* Property. */
129 static void objc_gen_property_data (tree, tree);
130 static void objc_synthesize_getter (tree, tree, tree);
131 static void objc_synthesize_setter (tree, tree, tree);
132 static tree lookup_property (tree, tree);
133 static tree lookup_property_in_list (tree, tree);
134 static tree lookup_property_in_protocol_list (tree, tree);
135 static void build_common_objc_property_accessor_helpers (void);
137 static void objc_xref_basetypes (tree, tree);
139 static tree get_class_ivars (tree, bool);
141 static void build_fast_enumeration_state_template (void);
143 #ifdef OBJCPLUS
144 static void objc_generate_cxx_cdtors (void);
145 #endif
147 /* objc attribute */
148 static void objc_decl_method_attributes (tree*, tree, int);
149 static tree build_keyword_selector (tree);
151 static void hash_init (void);
153 /* Hash tables to manage the global pool of method prototypes. Each
154 of these maps map a method name (selector) identifier to either a
155 single tree (for methods with a single method prototype) or a
156 TREE_VEC (for methods with multiple method prototypes). */
157 static GTY(()) objc_map_t instance_method_map = 0;
158 static GTY(()) objc_map_t class_method_map = 0;
160 /* Hash tables to manage the global pool of class names. */
162 static GTY(()) objc_map_t class_name_map = 0;
163 static GTY(()) objc_map_t alias_name_map = 0;
165 static tree lookup_method (tree, tree);
166 static tree lookup_method_static (tree, tree, int);
168 static void interface_hash_init (void);
169 static tree add_interface (tree, tree);
170 static void add_category (tree, tree);
172 /* Protocols. */
174 static tree lookup_protocol (tree, bool, bool);
175 static tree lookup_and_install_protocols (tree, bool);
177 #ifdef OBJCPLUS
178 static void really_start_method (tree, tree);
179 #else
180 static void really_start_method (tree, struct c_arg_info *);
181 #endif
182 static int comp_proto_with_proto (tree, tree, int);
183 static tree objc_decay_parm_type (tree);
185 /* Utilities for debugging and error diagnostics. */
187 static char *gen_type_name (tree);
188 static char *gen_type_name_0 (tree);
189 static char *gen_method_decl (tree);
190 static char *gen_declaration (tree);
192 /* Everything else. */
194 static void generate_struct_by_value_array (void) ATTRIBUTE_NORETURN;
196 static void mark_referenced_methods (void);
197 static bool objc_type_valid_for_messaging (tree type, bool allow_classes);
198 static tree check_duplicates (tree, int, int);
200 /*** Private Interface (data) ***/
201 /* Flags for lookup_method_static(). */
203 /* Look for class methods. */
204 #define OBJC_LOOKUP_CLASS 1
205 /* Do not examine superclasses. */
206 #define OBJC_LOOKUP_NO_SUPER 2
207 /* Disable returning an instance method of a root class when a class
208 method can't be found. */
209 #define OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS 4
211 /* The OCTI_... enumeration itself is in objc/objc-act.h. */
212 tree objc_global_trees[OCTI_MAX];
214 struct imp_entry *imp_list = 0;
215 int imp_count = 0; /* `@implementation' */
216 int cat_count = 0; /* `@category' */
218 objc_ivar_visibility_kind objc_ivar_visibility, objc_default_ivar_visibility;
220 /* Use to generate method labels. */
221 static int method_slot = 0;
223 /* Flag to say whether methods in a protocol are optional or
224 required. */
225 static bool objc_method_optional_flag = false;
227 static int objc_collecting_ivars = 0;
229 /* Flag that is set to 'true' while we are processing a class
230 extension. Since a class extension just "reopens" the main
231 @interface, this can be used to determine if we are in the main
232 @interface, or in a class extension. */
233 static bool objc_in_class_extension = false;
235 static char *errbuf; /* Buffer for error diagnostics */
237 /* An array of all the local variables in the current function that
238 need to be marked as volatile. */
239 vec<tree, va_gc> *local_variables_to_volatilize = NULL;
241 /* Store all constructed constant strings in a hash table so that
242 they get uniqued properly. */
244 struct GTY((for_user)) string_descriptor {
245 /* The literal argument . */
246 tree literal;
248 /* The resulting constant string. */
249 tree constructor;
252 struct objc_string_hasher : ggc_ptr_hash<string_descriptor>
254 static hashval_t hash (string_descriptor *);
255 static bool equal (string_descriptor *, string_descriptor *);
258 static GTY(()) hash_table<objc_string_hasher> *string_htab;
260 FILE *gen_declaration_file;
262 /* Hooks for stuff that differs between runtimes. */
263 objc_runtime_hooks runtime;
265 /* Create a temporary variable of type 'type'. If 'name' is set, uses
266 the specified name, else use no name. Returns the declaration of
267 the type. The 'name' is mostly useful for debugging.
269 tree
270 objc_create_temporary_var (tree type, const char *name)
272 tree decl;
274 if (name != NULL)
276 decl = build_decl (input_location,
277 VAR_DECL, get_identifier (name), type);
279 else
281 decl = build_decl (input_location,
282 VAR_DECL, NULL_TREE, type);
284 TREE_USED (decl) = 1;
285 DECL_ARTIFICIAL (decl) = 1;
286 DECL_IGNORED_P (decl) = 1;
287 DECL_CONTEXT (decl) = current_function_decl;
289 return decl;
292 /* Some platforms pass small structures through registers versus
293 through an invisible pointer. Determine at what size structure is
294 the transition point between the two possibilities. */
296 static void
297 generate_struct_by_value_array (void)
299 tree type;
300 tree decls;
301 int i, j;
302 int aggregate_in_mem[32];
303 int found = 0;
305 /* Presumably no platform passes 32 byte structures in a register. */
306 /* ??? As an example, m64/ppc/Darwin can pass up to 8*long+13*double
307 in registers. */
308 for (i = 1; i < 32; i++)
310 char buffer[5];
311 tree *chain = NULL;
313 /* Create an unnamed struct that has `i' character components */
314 type = objc_start_struct (NULL_TREE);
316 strcpy (buffer, "c1");
317 decls = add_field_decl (char_type_node, buffer, &chain);
319 for (j = 1; j < i; j++)
321 sprintf (buffer, "c%d", j + 1);
322 add_field_decl (char_type_node, buffer, &chain);
324 objc_finish_struct (type, decls);
326 aggregate_in_mem[i] = aggregate_value_p (type, 0);
327 if (!aggregate_in_mem[i])
328 found = 1;
331 /* We found some structures that are returned in registers instead of memory
332 so output the necessary data. */
333 if (found)
335 for (i = 31; i >= 0; i--)
336 if (!aggregate_in_mem[i])
337 break;
338 printf ("#define OBJC_MAX_STRUCT_BY_VALUE %d\n", i);
341 exit (0);
344 bool
345 objc_init (void)
347 bool ok;
349 /* Set up stuff used by the preprocessor as well as FE parser. */
350 interface_hash_init ();
351 hash_init ();
353 #ifdef OBJCPLUS
354 if (cxx_init () == false)
355 #else
356 if (c_objc_common_init () == false)
357 #endif
358 return false;
360 /* print_struct_values is triggered by -print-runtime-info (used
361 when building libobjc, with an empty file as input). It does not
362 require any ObjC setup, and it never returns.
364 -fcompare-debug is used to check the compiler output; we are
365 executed twice, once with flag_compare_debug set, and once with
366 it not set. If the flag is used together with
367 -print-runtime-info, we want to print the runtime info only once,
368 else it would be output in duplicate. So we check
369 flag_compare_debug to output it in only one of the invocations.
371 As a side effect, this also that means -fcompare-debug
372 -print-runtime-info will run the compiler twice, and compare the
373 generated assembler file; the first time the compiler exits
374 immediately (producing no file), and the second time it compiles
375 an empty file. This checks, as a side effect, that compiling an
376 empty file produces no assembler output. */
377 if (print_struct_values && !flag_compare_debug)
378 generate_struct_by_value_array ();
380 /* Set up stuff used by FE parser and all runtimes. */
381 errbuf = XNEWVEC (char, 1024 * 10);
382 objc_encoding_init ();
383 /* ... and then check flags and set-up for the selected runtime ... */
384 if (flag_next_runtime && flag_objc_abi >= 2)
385 ok = objc_next_runtime_abi_02_init (&runtime);
386 else if (flag_next_runtime)
387 ok = objc_next_runtime_abi_01_init (&runtime);
388 else
389 ok = objc_gnu_runtime_abi_01_init (&runtime);
391 /* If that part of the setup failed - bail out immediately. */
392 if (!ok)
393 return false;
395 /* Determine the default visibility for instance variables. */
396 switch (default_ivar_visibility)
398 case IVAR_VISIBILITY_PRIVATE:
399 objc_default_ivar_visibility = OBJC_IVAR_VIS_PRIVATE;
400 break;
401 case IVAR_VISIBILITY_PUBLIC:
402 objc_default_ivar_visibility = OBJC_IVAR_VIS_PUBLIC;
403 break;
404 case IVAR_VISIBILITY_PACKAGE:
405 objc_default_ivar_visibility = OBJC_IVAR_VIS_PACKAGE;
406 break;
407 default:
408 objc_default_ivar_visibility = OBJC_IVAR_VIS_PROTECTED;
411 /* Generate general types and push runtime-specific decls to file scope. */
412 synth_module_prologue ();
414 return true;
417 /* This is called at the end of parsing by the C/C++ parsers. */
418 void
419 objc_write_global_declarations (void)
421 mark_referenced_methods ();
423 /* A missing @end might not be detected by the parser. */
424 if (objc_implementation_context)
426 warning (0, "%<@end%> missing in implementation context");
427 finish_class (objc_implementation_context);
428 objc_ivar_chain = NULL_TREE;
429 objc_implementation_context = NULL_TREE;
432 if (warn_selector)
434 objc_map_iterator_t i;
436 objc_map_iterator_initialize (class_method_map, &i);
437 while (objc_map_iterator_move_to_next (class_method_map, &i))
438 check_duplicates (objc_map_iterator_current_value (class_method_map, i), 0, 1);
440 objc_map_iterator_initialize (instance_method_map, &i);
441 while (objc_map_iterator_move_to_next (instance_method_map, &i))
442 check_duplicates (objc_map_iterator_current_value (instance_method_map, i), 0, 0);
445 /* TODO: consider an early exit here if either errorcount or sorrycount
446 is non-zero. Not only is it wasting time to generate the metadata,
447 it needlessly imposes need to re-check for things that are already
448 determined to be errors. */
450 /* Finalize Objective-C runtime data. No need to generate tables
451 and code if only checking syntax, or if generating a PCH file. */
452 if (!flag_syntax_only && !pch_file)
454 location_t saved_location;
456 /* If gen_declaration desired, open the output file. */
457 if (flag_gen_declaration)
459 char * const dumpname = concat (dump_base_name, ".decl", NULL);
460 gen_declaration_file = fopen (dumpname, "w");
461 if (gen_declaration_file == 0)
462 fatal_error (input_location, "cannot open %s: %m", dumpname);
463 free (dumpname);
466 /* Set the input location to BUILTINS_LOCATION. This is good
467 for error messages, in case any is generated while producing
468 the metadata, but it also silences warnings that would be
469 produced when compiling with -Wpadded in case when padding is
470 automatically added to the built-in runtime data structure
471 declarations. We know about this padding, and it is fine; we
472 don't want users to see any warnings about it if they use
473 -Wpadded. */
474 saved_location = input_location;
475 input_location = BUILTINS_LOCATION;
477 /* Compute and emit the meta-data tables for this runtime. */
478 (*runtime.generate_metadata) ();
480 /* Restore the original location, just in case it mattered. */
481 input_location = saved_location;
483 /* ... and then close any declaration file we opened. */
484 if (gen_declaration_file)
485 fclose (gen_declaration_file);
489 /* Return the first occurrence of a method declaration corresponding
490 to sel_name in rproto_list. Search rproto_list recursively.
491 If is_class is 0, search for instance methods, otherwise for class
492 methods. */
493 static tree
494 lookup_method_in_protocol_list (tree rproto_list, tree sel_name,
495 int is_class)
497 tree rproto, p, m;
499 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
501 p = TREE_VALUE (rproto);
502 m = NULL_TREE;
504 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
506 /* First, search the @required protocol methods. */
507 if (is_class)
508 m = lookup_method (PROTOCOL_CLS_METHODS (p), sel_name);
509 else
510 m = lookup_method (PROTOCOL_NST_METHODS (p), sel_name);
512 if (m)
513 return m;
515 /* If still not found, search the @optional protocol methods. */
516 if (is_class)
517 m = lookup_method (PROTOCOL_OPTIONAL_CLS_METHODS (p), sel_name);
518 else
519 m = lookup_method (PROTOCOL_OPTIONAL_NST_METHODS (p), sel_name);
521 if (m)
522 return m;
524 /* If still not found, search the attached protocols. */
525 if (PROTOCOL_LIST (p))
526 m = lookup_method_in_protocol_list (PROTOCOL_LIST (p),
527 sel_name, is_class);
528 if (m)
529 return m;
531 else
533 ; /* An identifier...if we could not find a protocol. */
537 return 0;
540 static tree
541 lookup_protocol_in_reflist (tree rproto_list, tree lproto)
543 tree rproto, p;
545 /* Make sure the protocol is supported by the object on the rhs. */
546 if (TREE_CODE (lproto) == PROTOCOL_INTERFACE_TYPE)
548 tree fnd = 0;
549 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
551 p = TREE_VALUE (rproto);
553 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
555 if (lproto == p)
556 fnd = lproto;
558 else if (PROTOCOL_LIST (p))
559 fnd = lookup_protocol_in_reflist (PROTOCOL_LIST (p), lproto);
562 if (fnd)
563 return fnd;
566 else
568 ; /* An identifier...if we could not find a protocol. */
571 return 0;
574 void
575 objc_start_class_interface (tree klass, location_t name_loc, tree super_class,
576 tree protos, tree attributes)
578 if (flag_objc1_only && attributes)
579 error_at (name_loc, "class attributes are not available in Objective-C 1.0");
581 objc_interface_context
582 = objc_ivar_context
583 = start_class (CLASS_INTERFACE_TYPE, klass, super_class, protos, attributes);
584 objc_ivar_visibility = objc_default_ivar_visibility;
587 void
588 objc_start_category_interface (tree klass, tree categ,
589 tree protos, tree attributes)
591 if (attributes)
593 if (flag_objc1_only)
594 error_at (input_location, "category attributes are not available in Objective-C 1.0");
595 else
596 warning_at (input_location, OPT_Wattributes,
597 "category attributes are not available in this version"
598 " of the compiler, (ignored)");
600 if (categ == NULL_TREE)
602 if (flag_objc1_only)
603 error_at (input_location, "class extensions are not available in Objective-C 1.0");
604 else
606 /* Iterate over all the classes and categories implemented
607 up to now in this compilation unit. */
608 struct imp_entry *t;
610 for (t = imp_list; t; t = t->next)
612 /* If we find a class @implementation with the same name
613 as the one we are extending, produce an error. */
614 if (TREE_CODE (t->imp_context) == CLASS_IMPLEMENTATION_TYPE
615 && IDENTIFIER_POINTER (CLASS_NAME (t->imp_context)) == IDENTIFIER_POINTER (klass))
616 error_at (input_location,
617 "class extension for class %qE declared after its %<@implementation%>",
618 klass);
622 objc_interface_context
623 = start_class (CATEGORY_INTERFACE_TYPE, klass, categ, protos, NULL_TREE);
624 objc_ivar_chain
625 = continue_class (objc_interface_context);
628 void
629 objc_start_protocol (tree name, tree protos, tree attributes)
631 if (flag_objc1_only && attributes)
632 error_at (input_location, "protocol attributes are not available in Objective-C 1.0");
634 objc_interface_context
635 = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos, attributes);
636 objc_method_optional_flag = false;
639 void
640 objc_continue_interface (void)
642 objc_ivar_chain
643 = continue_class (objc_interface_context);
646 void
647 objc_finish_interface (void)
649 finish_class (objc_interface_context);
650 objc_interface_context = NULL_TREE;
651 objc_method_optional_flag = false;
652 objc_in_class_extension = false;
655 void
656 objc_start_class_implementation (tree klass, tree super_class)
658 objc_implementation_context
659 = objc_ivar_context
660 = start_class (CLASS_IMPLEMENTATION_TYPE, klass, super_class, NULL_TREE,
661 NULL_TREE);
662 objc_ivar_visibility = objc_default_ivar_visibility;
665 void
666 objc_start_category_implementation (tree klass, tree categ)
668 objc_implementation_context
669 = start_class (CATEGORY_IMPLEMENTATION_TYPE, klass, categ, NULL_TREE,
670 NULL_TREE);
671 objc_ivar_chain
672 = continue_class (objc_implementation_context);
675 void
676 objc_continue_implementation (void)
678 objc_ivar_chain
679 = continue_class (objc_implementation_context);
682 void
683 objc_finish_implementation (void)
685 #ifdef OBJCPLUS
686 if (flag_objc_call_cxx_cdtors)
687 objc_generate_cxx_cdtors ();
688 #endif
690 if (objc_implementation_context)
692 finish_class (objc_implementation_context);
693 objc_ivar_chain = NULL_TREE;
694 objc_implementation_context = NULL_TREE;
696 else
697 warning (0, "%<@end%> must appear in an @implementation context");
700 void
701 objc_set_visibility (objc_ivar_visibility_kind visibility)
703 if (visibility == OBJC_IVAR_VIS_PACKAGE)
705 if (flag_objc1_only)
706 error ("%<@package%> is not available in Objective-C 1.0");
707 else
708 warning (0, "%<@package%> presently has the same effect as %<@public%>");
710 objc_ivar_visibility = visibility;
713 void
714 objc_set_method_opt (bool optional)
716 if (flag_objc1_only)
718 if (optional)
719 error_at (input_location, "%<@optional%> is not available in Objective-C 1.0");
720 else
721 error_at (input_location, "%<@required%> is not available in Objective-C 1.0");
724 objc_method_optional_flag = optional;
725 if (!objc_interface_context
726 || TREE_CODE (objc_interface_context) != PROTOCOL_INTERFACE_TYPE)
728 if (optional)
729 error ("%<@optional%> is allowed in @protocol context only");
730 else
731 error ("%<@required%> is allowed in @protocol context only");
732 objc_method_optional_flag = false;
736 /* This routine looks for a given PROPERTY in a list of CLASS, CATEGORY, or
737 PROTOCOL. */
738 static tree
739 lookup_property_in_list (tree chain, tree property)
741 tree x;
742 for (x = CLASS_PROPERTY_DECL (chain); x; x = TREE_CHAIN (x))
743 if (PROPERTY_NAME (x) == property)
744 return x;
745 return NULL_TREE;
748 /* This routine looks for a given PROPERTY in the tree chain of RPROTO_LIST. */
749 static tree lookup_property_in_protocol_list (tree rproto_list, tree property)
751 tree rproto, x;
752 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
754 tree p = TREE_VALUE (rproto);
755 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
757 if ((x = lookup_property_in_list (p, property)))
758 return x;
759 if (PROTOCOL_LIST (p))
760 return lookup_property_in_protocol_list (PROTOCOL_LIST (p), property);
762 else
764 ; /* An identifier...if we could not find a protocol. */
767 return NULL_TREE;
770 /* This routine looks up the PROPERTY in current INTERFACE, its categories and up the
771 chain of interface hierarchy. */
772 static tree
773 lookup_property (tree interface_type, tree property)
775 tree inter = interface_type;
776 while (inter)
778 tree x, category;
779 if ((x = lookup_property_in_list (inter, property)))
780 return x;
781 /* Failing that, look for the property in each category of the class. */
782 category = inter;
783 while ((category = CLASS_CATEGORY_LIST (category)))
785 if ((x = lookup_property_in_list (category, property)))
786 return x;
788 /* When checking a category, also check the protocols
789 attached with the category itself. */
790 if (CLASS_PROTOCOL_LIST (category)
791 && (x = lookup_property_in_protocol_list
792 (CLASS_PROTOCOL_LIST (category), property)))
793 return x;
796 /* Failing to find in categories, look for property in protocol list. */
797 if (CLASS_PROTOCOL_LIST (inter)
798 && (x = lookup_property_in_protocol_list
799 (CLASS_PROTOCOL_LIST (inter), property)))
800 return x;
802 /* Failing that, climb up the inheritance hierarchy. */
803 inter = lookup_interface (CLASS_SUPER_NAME (inter));
805 return inter;
808 /* This routine returns a PROPERTY_KIND for the front end RID code supplied. */
810 enum objc_property_attribute_kind
811 objc_prop_attr_kind_for_rid (enum rid prop_rid)
813 switch (prop_rid)
815 default: return OBJC_PROPERTY_ATTR_UNKNOWN;
816 case RID_GETTER: return OBJC_PROPERTY_ATTR_GETTER;
817 case RID_SETTER: return OBJC_PROPERTY_ATTR_SETTER;
819 case RID_READONLY: return OBJC_PROPERTY_ATTR_READONLY;
820 case RID_READWRITE: return OBJC_PROPERTY_ATTR_READWRITE;
822 case RID_ASSIGN: return OBJC_PROPERTY_ATTR_ASSIGN;
823 case RID_RETAIN: return OBJC_PROPERTY_ATTR_RETAIN;
824 case RID_COPY: return OBJC_PROPERTY_ATTR_COPY;
826 case RID_PROPATOMIC: return OBJC_PROPERTY_ATTR_ATOMIC;
827 case RID_NONATOMIC: return OBJC_PROPERTY_ATTR_NONATOMIC;
829 case RID_NULL_UNSPECIFIED:return OBJC_PROPERTY_ATTR_NULL_UNSPECIFIED;
830 case RID_NULLABLE: return OBJC_PROPERTY_ATTR_NULLABLE;
831 case RID_NONNULL: return OBJC_PROPERTY_ATTR_NONNULL;
832 case RID_NULL_RESETTABLE: return OBJC_PROPERTY_ATTR_NULL_RESETTABLE;
834 case RID_CLASS: return OBJC_PROPERTY_ATTR_CLASS;
838 /* This routine is called by the parser when a
839 @property... declaration is found. 'decl' is the declaration of
840 the property (type/identifier), and the other arguments represent
841 property attributes that may have been specified in the Objective-C
842 declaration. 'parsed_property_readonly' is 'true' if the attribute
843 'readonly' was specified, and 'false' if not; similarly for the
844 other bool parameters. 'property_getter_ident' is NULL_TREE
845 if the attribute 'getter' was not specified, and is the identifier
846 corresponding to the specified getter if it was; similarly for
847 'property_setter_ident'. */
848 void
849 objc_add_property_declaration (location_t location, tree decl,
850 vec<property_attribute_info *>& prop_attr_list)
852 if (flag_objc1_only)
853 /* FIXME: we probably ought to bail out at this point. */
854 error_at (location, "%<@property%> is not available in Objective-C 1.0");
856 /* We must be in an interface, category, or protocol. */
857 if (!objc_interface_context)
859 error_at (location, "property declaration not in %<@interface%>,"
860 " %<@protocol%> or %<category%> context");
861 return;
864 /* Do some spot-checks for the most obvious invalid cases. */
866 gcc_checking_assert (decl && TREE_CODE (decl) == FIELD_DECL);
868 if (decl && !DECL_NAME (decl))
870 error_at (location, "properties must be named");
871 return;
874 location_t decl_loc = DECL_SOURCE_LOCATION (decl);
875 decl_loc = make_location (decl_loc, location, decl_loc);
876 if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
878 error_at (decl_loc, "property cannot be an array");
879 return;
882 if (DECL_C_BIT_FIELD (decl))
884 /* A @property is not an actual variable, but it is a way to
885 describe a pair of accessor methods, so its type (which is
886 the type of the return value of the getter and the first
887 argument of the setter) can't be a bitfield (as return values
888 and arguments of functions cannot be bitfields). The
889 underlying instance variable could be a bitfield, but that is
890 a different matter. */
891 error_at (decl_loc, "property cannot be a bit-field");
892 return;
895 /* The final results of parsing the (growing number) of property
896 attributes. */
897 property_attribute_info *attrs[OBJC_PROPATTR_GROUP_MAX] = { nullptr };
899 tree property_getter_ident = NULL_TREE;
900 tree property_setter_ident = NULL_TREE;
901 for (unsigned pn = 0; pn < prop_attr_list.length (); ++pn)
903 if (prop_attr_list[pn]->parse_error)
904 continue; /* Ignore attributes known to be wrongly parsed. */
906 switch (int g = (int) prop_attr_list[pn]->group())
908 case OBJC_PROPATTR_GROUP_UNKNOWN:
909 continue;
910 case OBJC_PROPATTR_GROUP_SETTER:
911 case OBJC_PROPATTR_GROUP_GETTER:
912 if (attrs[g])
914 warning_at (prop_attr_list[pn]->prop_loc, OPT_Wattributes,
915 "multiple property %qE methods specified, the latest"
916 " one will be used", attrs[g]->name);
917 inform (attrs[g]->prop_loc, "previous specification");
919 attrs[g] = prop_attr_list[pn];
920 if (g == OBJC_PROPATTR_GROUP_SETTER)
921 property_setter_ident = attrs[g]->ident;
922 else
923 property_getter_ident = attrs[g]->ident;
924 continue;
925 default:
927 if (!attrs[g])
929 else if (attrs[g]->prop_kind != prop_attr_list[pn]->prop_kind)
931 error_at (prop_attr_list[pn]->prop_loc,
932 "%qE attribute conflicts with %qE attribute",
933 prop_attr_list[pn]->name, attrs[g]->name);
934 inform (attrs[g]->prop_loc, "%qE specified here",
935 attrs[g]->name );
937 else
939 warning_at (prop_attr_list[pn]->prop_loc, OPT_Wattributes,
940 "duplicate %qE attribute", attrs[g]->name);
941 inform (attrs[g]->prop_loc, "first specified here");
943 attrs[g] = prop_attr_list[pn];
945 continue;
949 /* The defaults for atomicity (atomic) and write-ability (readwrite) apply
950 even if the user provides no specified attributes. */
951 bool property_nonatomic = false;
952 bool property_readonly = false;
954 /* Set the values from any specified by the user; these are easy, only two
955 states. */
956 if (attrs[OBJC_PROPATTR_GROUP_ATOMIC])
957 property_nonatomic = attrs[OBJC_PROPATTR_GROUP_ATOMIC]->prop_kind
958 == OBJC_PROPERTY_ATTR_NONATOMIC;
960 if (attrs[OBJC_PROPATTR_GROUP_READWRITE])
961 property_readonly = attrs[OBJC_PROPATTR_GROUP_READWRITE]->prop_kind
962 == OBJC_PROPERTY_ATTR_READONLY;
964 /* One can't set a readonly value; we issue an error, but force the property
965 to readwrite as well. */
966 if (property_readonly && property_setter_ident)
968 error_at (attrs[OBJC_PROPATTR_GROUP_READWRITE]->prop_loc, "%<readonly%>"
969 " attribute conflicts with %<setter%> attribute");
970 gcc_checking_assert (attrs[OBJC_PROPATTR_GROUP_SETTER]);
971 inform (attrs[OBJC_PROPATTR_GROUP_SETTER]->prop_loc, "%<setter%>"
972 " specified here");
973 property_readonly = false;
976 /* Assign semantics is a tri-state property, and also needs some further
977 checking against the object type. */
978 objc_property_assign_semantics property_assign_semantics
979 = OBJC_PROPERTY_ASSIGN;
981 if (attrs[OBJC_PROPATTR_GROUP_ASSIGN])
983 if (attrs[OBJC_PROPATTR_GROUP_ASSIGN]->prop_kind
984 == OBJC_PROPERTY_ATTR_ASSIGN)
985 property_assign_semantics = OBJC_PROPERTY_ASSIGN;
986 else if (attrs[OBJC_PROPATTR_GROUP_ASSIGN]->prop_kind
987 == OBJC_PROPERTY_ATTR_RETAIN)
988 property_assign_semantics = OBJC_PROPERTY_RETAIN;
989 else if (attrs[OBJC_PROPATTR_GROUP_ASSIGN]->prop_kind
990 == OBJC_PROPERTY_ATTR_COPY)
991 property_assign_semantics = OBJC_PROPERTY_COPY;
992 else
993 gcc_unreachable ();
996 /* An attribute that indicates this property manipulates a class variable.
997 In this case, both the variable and the getter/setter must be provided
998 by the user. */
999 bool property_class = false;
1000 if (attrs[OBJC_PROPATTR_GROUP_CLASS])
1001 property_nonatomic = attrs[OBJC_PROPATTR_GROUP_CLASS]->prop_kind
1002 == OBJC_PROPERTY_ATTR_CLASS;
1004 /* Nullability specifications for the property. */
1005 enum objc_property_nullability property_nullability
1006 = OBJC_PROPERTY_NULL_UNSET;
1007 if (attrs[OBJC_PROPATTR_GROUP_NULLABLE])
1009 if (attrs[OBJC_PROPATTR_GROUP_NULLABLE]->prop_kind
1010 == OBJC_PROPERTY_ATTR_NULL_UNSPECIFIED)
1011 property_nullability = OBJC_PROPERTY_NULL_UNSPECIFIED;
1012 else if (attrs[OBJC_PROPATTR_GROUP_NULLABLE]->prop_kind
1013 == OBJC_PROPERTY_ATTR_NULLABLE)
1014 property_nullability = OBJC_PROPERTY_NULLABLE;
1015 else if (attrs[OBJC_PROPATTR_GROUP_NULLABLE]->prop_kind
1016 == OBJC_PROPERTY_ATTR_NONNULL)
1017 property_nullability = OBJC_PROPERTY_NONNULL;
1018 else if (attrs[OBJC_PROPATTR_GROUP_NULLABLE]->prop_kind
1019 == OBJC_PROPERTY_ATTR_NULL_RESETTABLE)
1020 property_nullability = OBJC_PROPERTY_NULL_RESETTABLE;
1021 else
1022 gcc_unreachable ();
1025 /* TODO: Check that the property type is an Objective-C object or a
1026 "POD". */
1028 /* Implement -Wproperty-assign-default (which is enabled by default). */
1029 if (warn_property_assign_default
1030 /* If garbage collection is not being used, then 'assign' is
1031 valid for objects (and typically used for delegates) but it
1032 is wrong in most cases (since most objects need to be
1033 retained or copied in setters). Warn users when 'assign' is
1034 used implicitly. */
1035 && property_assign_semantics == OBJC_PROPERTY_ASSIGN
1036 /* Read-only properties are never assigned, so the assignment
1037 semantics do not matter in that case. */
1038 && !property_readonly
1039 && !flag_objc_gc)
1041 /* Please note that it would make sense to default to 'assign'
1042 for non-{Objective-C objects}, and to 'retain' for
1043 Objective-C objects. But that would break compatibility with
1044 other compilers. */
1045 if (!attrs[OBJC_PROPATTR_GROUP_ASSIGN])
1047 /* Use 'false' so we do not warn for Class objects. */
1048 if (objc_type_valid_for_messaging (TREE_TYPE (decl), false))
1050 warning_at (decl_loc, 0, "object property %qD has no %<assign%>,"
1051 " %<retain%> or %<copy%> attribute; assuming"
1052 " %<assign%>", decl);
1053 inform (decl_loc, "%<assign%> can be unsafe for Objective-C"
1054 " objects; please state explicitly if you need it");
1059 /* Some attributes make no sense unless applied to an Objective-C object. */
1060 bool prop_objc_object_p
1061 = objc_type_valid_for_messaging (TREE_TYPE (decl), true);
1062 if (!prop_objc_object_p)
1064 tree p_name = NULL_TREE;
1065 if (property_assign_semantics == OBJC_PROPERTY_RETAIN
1066 || property_assign_semantics == OBJC_PROPERTY_COPY)
1067 p_name = attrs[OBJC_PROPATTR_GROUP_ASSIGN]->name;
1069 if (p_name)
1070 error_at (decl_loc, "%qE attribute is only valid for Objective-C"
1071 " objects", p_name);
1074 /* Now determine the final property getter and setter names. They
1075 will be stored in the PROPERTY_DECL, from which they'll always be
1076 extracted and used. */
1078 /* Adjust, or fill in, setter and getter names. We overwrite the
1079 property_setter_ident and property_getter_ident
1080 with the final setter and getter identifiers that will be
1081 used. */
1082 if (property_setter_ident)
1084 /* The setter should be terminated by ':', but the parser only
1085 gives us an identifier without ':'. So, we need to add ':'
1086 at the end. */
1087 const char *parsed_setter = IDENTIFIER_POINTER (property_setter_ident);
1088 size_t length = strlen (parsed_setter);
1089 char *final_setter = (char *)alloca (length + 2);
1091 sprintf (final_setter, "%s:", parsed_setter);
1092 property_setter_ident = get_identifier (final_setter);
1094 else
1096 if (!property_readonly)
1097 property_setter_ident = get_identifier (objc_build_property_setter_name
1098 (DECL_NAME (decl)));
1101 if (!property_getter_ident)
1102 property_getter_ident = DECL_NAME (decl);
1104 /* Check for duplicate property declarations. We first check the
1105 immediate context for a property with the same name. Any such
1106 declarations are an error, unless this is a class extension and
1107 we are extending a property from readonly to readwrite. */
1108 bool property_extension_in_class_extension = false;
1109 tree x = NULL_TREE;
1110 for (x = CLASS_PROPERTY_DECL (objc_interface_context); x; x = TREE_CHAIN (x))
1112 if (PROPERTY_NAME (x) == DECL_NAME (decl))
1114 if (objc_in_class_extension
1115 && !property_readonly
1116 && PROPERTY_READONLY (x) == 1)
1118 /* This is a class extension, and we are extending an
1119 existing readonly property to a readwrite one.
1120 That's fine. :-) */
1121 property_extension_in_class_extension = true;
1122 break;
1124 else
1126 location_t original_location = DECL_SOURCE_LOCATION (x);
1128 error_at (location, "redeclaration of property %qD", decl);
1130 if (original_location != UNKNOWN_LOCATION)
1131 inform (original_location, "originally specified here");
1132 return;
1137 /* If x is not NULL_TREE, we must be in a class extension and we're
1138 extending a readonly property. In that case, no point in
1139 searching for another declaration. */
1140 if (x == NULL_TREE)
1142 /* We now need to check for existing property declarations (in
1143 the superclass, other categories or protocols) and check that
1144 the new declaration is not in conflict with existing
1145 ones. */
1147 /* Search for a previous, existing declaration of a property
1148 with the same name in superclasses, protocols etc. If one is
1149 found, it will be in the 'x' variable. */
1151 /* Note that, for simplicity, the following may search again the
1152 local context. That's Ok as nothing will be found (else we'd
1153 have thrown an error above); it's only a little inefficient,
1154 but the code is simpler. */
1155 switch (TREE_CODE (objc_interface_context))
1157 case CLASS_INTERFACE_TYPE:
1158 /* Look up the property in the current @interface (which
1159 will find nothing), then its protocols and categories and
1160 superclasses. */
1161 x = lookup_property (objc_interface_context, DECL_NAME (decl));
1162 break;
1163 case CATEGORY_INTERFACE_TYPE:
1164 /* Look up the property in the main @interface, then
1165 protocols and categories (one of them is ours, and will
1166 find nothing) and superclasses. */
1167 x = lookup_property (lookup_interface (CLASS_NAME (objc_interface_context)),
1168 DECL_NAME (decl));
1169 break;
1170 case PROTOCOL_INTERFACE_TYPE:
1171 /* Looks up the property in any protocols attached to the
1172 current protocol. */
1173 if (PROTOCOL_LIST (objc_interface_context))
1175 x = lookup_property_in_protocol_list (PROTOCOL_LIST (objc_interface_context),
1176 DECL_NAME (decl));
1178 break;
1179 default:
1180 gcc_unreachable ();
1184 if (x != NULL_TREE)
1186 /* An existing property was found; check that it has the same
1187 types, or it is compatible. */
1188 location_t original_location = DECL_SOURCE_LOCATION (x);
1190 if (PROPERTY_NONATOMIC (x) != property_nonatomic)
1192 warning_at (location, 0,
1193 "%<nonatomic%> attribute of property %qD conflicts with "
1194 "previous declaration", decl);
1196 if (original_location != UNKNOWN_LOCATION)
1197 inform (original_location, "originally specified here");
1198 return;
1201 if (PROPERTY_GETTER_NAME (x) != property_getter_ident)
1203 warning_at (location, 0,
1204 "%<getter%> attribute of property %qD conflicts with "
1205 "previous declaration", decl);
1207 if (original_location != UNKNOWN_LOCATION)
1208 inform (original_location, "originally specified here");
1209 return;
1212 /* We can only compare the setter names if both the old and new property have a setter. */
1213 if (!property_readonly && !PROPERTY_READONLY(x))
1215 if (PROPERTY_SETTER_NAME (x) != property_setter_ident)
1217 warning_at (location, 0,
1218 "%<setter%> attribute of property %qD conflicts with "
1219 "previous declaration", decl);
1221 if (original_location != UNKNOWN_LOCATION)
1222 inform (original_location, "originally specified here");
1223 return;
1227 if (PROPERTY_ASSIGN_SEMANTICS (x) != property_assign_semantics)
1229 warning_at (location, 0,
1230 "assign semantics attributes of property %qD conflict with previous declaration", decl);
1232 if (original_location != UNKNOWN_LOCATION)
1233 inform (original_location, "originally specified here");
1234 return;
1237 /* It's ok to have a readonly property that becomes a readwrite, but not vice versa. */
1238 if (PROPERTY_READONLY (x) == 0 && property_readonly == 1)
1240 warning_at (location, 0,
1241 "%<readonly%> attribute of property %qD conflicts with "
1242 "previous declaration", decl);
1244 if (original_location != UNKNOWN_LOCATION)
1245 inform (original_location, "originally specified here");
1246 return;
1249 /* We now check that the new and old property declarations have
1250 the same types (or compatible one). In the Objective-C
1251 tradition of loose type checking, we do type-checking but
1252 only generate warnings (not errors) if they do not match.
1253 For non-readonly properties, the types must match exactly;
1254 for readonly properties, it is allowed to use a "more
1255 specialized" type in the new property declaration. Eg, the
1256 superclass has a getter returning (NSArray *) and the
1257 subclass a getter returning (NSMutableArray *). The object's
1258 getter returns an (NSMutableArray *); but if you cast the
1259 object to the superclass, which is allowed, you'd still
1260 expect the getter to return an (NSArray *), which works since
1261 an (NSMutableArray *) is an (NSArray *) too. So, the set of
1262 objects belonging to the type of the new @property should be
1263 a subset of the set of objects belonging to the type of the
1264 old @property. This is what "specialization" means. And the
1265 reason it only applies to readonly properties is that for a
1266 readwrite property the setter would have the opposite
1267 requirement - ie that the superclass type is more specialized
1268 then the subclass one; hence the only way to satisfy both
1269 constraints is that the types match. */
1271 /* If the types are not the same in the C sense, we warn ... */
1272 if (!comptypes (TREE_TYPE (x), TREE_TYPE (decl))
1273 /* ... unless the property is readonly, in which case we
1274 allow a new, more specialized, declaration. */
1275 && (!property_readonly
1276 || !objc_compare_types (TREE_TYPE (x),
1277 TREE_TYPE (decl), -5, NULL_TREE)))
1279 warning_at (location, 0,
1280 "type of property %qD conflicts with previous declaration", decl);
1281 if (original_location != UNKNOWN_LOCATION)
1282 inform (original_location, "originally specified here");
1283 return;
1286 /* If we are in a class extension and we're extending a readonly
1287 property in the main @interface, we'll just update the
1288 existing property with the readwrite flag and potentially the
1289 new setter name. */
1290 if (property_extension_in_class_extension)
1292 PROPERTY_READONLY (x) = 0;
1293 PROPERTY_SETTER_NAME (x) = property_setter_ident;
1294 return;
1298 /* Create a PROPERTY_DECL node. */
1299 tree property_decl = make_node (PROPERTY_DECL);
1301 /* Copy the basic information from the original decl. */
1302 tree p_type = TREE_TYPE (decl);
1303 TREE_TYPE (property_decl) = p_type;
1304 DECL_SOURCE_LOCATION (property_decl) = DECL_SOURCE_LOCATION (decl);
1305 TREE_DEPRECATED (property_decl) = TREE_DEPRECATED (decl);
1306 TREE_UNAVAILABLE (property_decl) = TREE_UNAVAILABLE (decl);
1308 /* Add property-specific information. */
1309 PROPERTY_NAME (property_decl) = DECL_NAME (decl);
1310 PROPERTY_GETTER_NAME (property_decl) = property_getter_ident;
1311 PROPERTY_SETTER_NAME (property_decl) = property_setter_ident;
1312 PROPERTY_READONLY (property_decl) = property_readonly;
1313 PROPERTY_NONATOMIC (property_decl) = property_nonatomic;
1314 PROPERTY_CLASS (property_decl) = property_class;
1315 PROPERTY_ASSIGN_SEMANTICS (property_decl) = property_assign_semantics;
1316 PROPERTY_IVAR_NAME (property_decl) = NULL_TREE;
1317 PROPERTY_DYNAMIC (property_decl) = 0;
1319 /* FIXME: We seem to drop any existing DECL_ATTRIBUTES on the floor. */
1320 if (property_nullability != OBJC_PROPERTY_NULL_UNSET)
1322 if (p_type && !POINTER_TYPE_P (p_type))
1323 error_at (decl_loc, "nullability specifier %qE cannot be applied to"
1324 " non-pointer type %qT",
1325 attrs[OBJC_PROPATTR_GROUP_NULLABLE]->name, p_type);
1326 else if (p_type && POINTER_TYPE_P (p_type) && TREE_TYPE (p_type)
1327 && POINTER_TYPE_P (TREE_TYPE (p_type)))
1328 error_at (decl_loc, "nullability specifier %qE cannot be applied to"
1329 " multi-level pointer type %qT",
1330 attrs[OBJC_PROPATTR_GROUP_NULLABLE]->name, p_type);
1331 else
1333 tree attr_name = get_identifier ("objc_nullability");
1334 tree attr_value = build_int_cst (unsigned_type_node,
1335 (unsigned)property_nullability);
1336 tree nulla = build_tree_list (attr_name, attr_value);
1337 DECL_ATTRIBUTES (property_decl) = nulla;
1341 /* Remember the fact that the property was found in the @optional
1342 section in a @protocol, or not. */
1343 if (objc_method_optional_flag)
1344 PROPERTY_OPTIONAL (property_decl) = 1;
1345 else
1346 PROPERTY_OPTIONAL (property_decl) = 0;
1348 /* Note that PROPERTY_GETTER_NAME is always set for all
1349 PROPERTY_DECLs, and PROPERTY_SETTER_NAME is always set for all
1350 PROPERTY_DECLs where PROPERTY_READONLY == 0. Any time we deal
1351 with a getter or setter, we should get the PROPERTY_DECL and use
1352 PROPERTY_GETTER_NAME and PROPERTY_SETTER_NAME to know the correct
1353 names. */
1355 /* Add the PROPERTY_DECL to the list of properties for the class. */
1356 TREE_CHAIN (property_decl) = CLASS_PROPERTY_DECL (objc_interface_context);
1357 CLASS_PROPERTY_DECL (objc_interface_context) = property_decl;
1360 /* This is a subroutine of objc_maybe_build_component_ref. Search the
1361 list of methods in the interface (and, failing that, the local list
1362 in the implementation, and failing that, the protocol list)
1363 provided for a 'setter' or 'getter' for 'component' with default
1364 names (ie, if 'component' is "name", then search for "name" and
1365 "setName:"). It is also possible to specify a different
1366 'getter_name' (this is used for @optional readonly properties). If
1367 any is found, then create an artificial property that uses them.
1368 Return NULL_TREE if 'getter' or 'setter' could not be found. */
1369 static tree
1370 maybe_make_artificial_property_decl (tree interface, tree implementation,
1371 tree protocol_list, tree component, bool is_class,
1372 tree getter_name)
1374 tree setter_name = get_identifier (objc_build_property_setter_name (component));
1375 tree getter = NULL_TREE;
1376 tree setter = NULL_TREE;
1378 if (getter_name == NULL_TREE)
1379 getter_name = component;
1381 /* First, check the @interface and all superclasses. */
1382 if (interface)
1384 int flags = 0;
1386 /* Using instance methods of the root class as accessors is most
1387 likely unwanted and can be extremely confusing (and, most
1388 importantly, other Objective-C 2.0 compilers do not do it).
1389 Turn it off. */
1390 if (is_class)
1391 flags = OBJC_LOOKUP_CLASS | OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS;
1393 getter = lookup_method_static (interface, getter_name, flags);
1394 setter = lookup_method_static (interface, setter_name, flags);
1397 /* Second, check the local @implementation context. */
1398 if (!getter && !setter)
1400 if (implementation)
1402 if (is_class)
1404 getter = lookup_method (CLASS_CLS_METHODS (implementation), getter_name);
1405 setter = lookup_method (CLASS_CLS_METHODS (implementation), setter_name);
1407 else
1409 getter = lookup_method (CLASS_NST_METHODS (implementation), getter_name);
1410 setter = lookup_method (CLASS_NST_METHODS (implementation), setter_name);
1415 /* Try the protocol_list if we didn't find anything in the
1416 @interface and in the @implementation. */
1417 if (!getter && !setter)
1419 getter = lookup_method_in_protocol_list (protocol_list, getter_name, is_class);
1420 setter = lookup_method_in_protocol_list (protocol_list, setter_name, is_class);
1423 /* There needs to be at least a getter or setter for this to be a
1424 valid 'object.component' syntax. */
1425 if (getter || setter)
1427 /* Yes ... determine the type of the expression. */
1428 tree property_decl;
1429 tree type;
1431 if (getter)
1432 type = TREE_VALUE (TREE_TYPE (getter));
1433 else
1434 type = TREE_VALUE (TREE_TYPE (METHOD_SEL_ARGS (setter)));
1436 /* Create an artificial property declaration with the
1437 information we collected on the type and getter/setter
1438 names. */
1439 property_decl = make_node (PROPERTY_DECL);
1441 TREE_TYPE (property_decl) = type;
1442 DECL_SOURCE_LOCATION (property_decl) = input_location;
1443 TREE_DEPRECATED (property_decl) = 0;
1444 TREE_UNAVAILABLE (property_decl) = 0;
1445 DECL_ARTIFICIAL (property_decl) = 1;
1447 /* Add property-specific information. Note that one of
1448 PROPERTY_GETTER_NAME or PROPERTY_SETTER_NAME may refer to a
1449 non-existing method; this will generate an error when the
1450 expression is later compiled. At this stage we don't know if
1451 the getter or setter will be used, so we can't generate an
1452 error. */
1453 PROPERTY_NAME (property_decl) = component;
1454 PROPERTY_GETTER_NAME (property_decl) = getter_name;
1455 PROPERTY_SETTER_NAME (property_decl) = setter_name;
1456 PROPERTY_READONLY (property_decl) = 0;
1457 PROPERTY_NONATOMIC (property_decl) = 0;
1458 PROPERTY_ASSIGN_SEMANTICS (property_decl) = 0;
1459 PROPERTY_IVAR_NAME (property_decl) = NULL_TREE;
1460 PROPERTY_DYNAMIC (property_decl) = 0;
1461 PROPERTY_OPTIONAL (property_decl) = 0;
1463 if (!getter)
1464 PROPERTY_HAS_NO_GETTER (property_decl) = 1;
1466 /* The following is currently unused, but it's nice to have
1467 there. We may use it if we need in the future. */
1468 if (!setter)
1469 PROPERTY_HAS_NO_SETTER (property_decl) = 1;
1471 return property_decl;
1474 return NULL_TREE;
1477 /* This hook routine is invoked by the parser when an expression such
1478 as 'xxx.yyy' is parsed. We get a chance to process these
1479 expressions in a way that is specified to Objective-C (to implement
1480 the Objective-C 2.0 dot-syntax, properties, or non-fragile ivars).
1481 If the expression is not an Objective-C specified expression, we
1482 should return NULL_TREE; else we return the expression.
1484 At the moment this only implements dot-syntax and properties (not
1485 non-fragile ivars yet), ie 'object.property' or 'object.component'
1486 where 'component' is not a declared property, but a valid getter or
1487 setter for it could be found. */
1488 tree
1489 objc_maybe_build_component_ref (tree object, tree property_ident)
1491 tree x = NULL_TREE;
1492 tree rtype;
1494 /* If we are in Objective-C 1.0 mode, dot-syntax and properties are
1495 not available. */
1496 if (flag_objc1_only)
1497 return NULL_TREE;
1499 /* Try to determine if 'object' is an Objective-C object or not. If
1500 not, return. */
1501 if (object == NULL_TREE || object == error_mark_node
1502 || (rtype = TREE_TYPE (object)) == NULL_TREE)
1503 return NULL_TREE;
1505 if (property_ident == NULL_TREE || property_ident == error_mark_node
1506 || TREE_CODE (property_ident) != IDENTIFIER_NODE)
1507 return NULL_TREE;
1509 /* The following analysis of 'object' is similar to the one used for
1510 the 'receiver' of a method invocation. We need to determine what
1511 'object' is and find the appropriate property (either declared,
1512 or artificial) for it (in the same way as we need to find the
1513 appropriate method prototype for a method invocation). There are
1514 some simplifications here though: "object.property" is invalid if
1515 "object" has a type of "id" or "Class"; it must at least have a
1516 protocol attached to it, and "object" is never a class name as
1517 that is done by objc_build_class_component_ref. Finally, we
1518 don't know if this really is a dot-syntax expression, so we want
1519 to make a quick exit if it is not; for this reason, we try to
1520 postpone checks after determining that 'object' looks like an
1521 Objective-C object. */
1523 if (objc_is_id (rtype))
1525 /* This is the case that the 'object' is of type 'id' or
1526 'Class'. */
1528 /* Check if at least it is of type 'id <Protocol>' or 'Class
1529 <Protocol>'; if so, look the property up in the
1530 protocols. */
1531 if (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype)))
1533 tree rprotos = TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype));
1535 if (rprotos)
1537 /* No point looking up declared @properties if we are
1538 dealing with a class. Classes have no declared
1539 properties. */
1540 if (!IS_CLASS (rtype))
1541 x = lookup_property_in_protocol_list (rprotos, property_ident);
1543 if (x == NULL_TREE)
1545 /* Ok, no property. Maybe it was an
1546 object.component dot-syntax without a declared
1547 property (this is valid for classes too). Look
1548 for getter/setter methods and internally declare
1549 an artificial property based on them if found. */
1550 x = maybe_make_artificial_property_decl (NULL_TREE,
1551 NULL_TREE,
1552 rprotos,
1553 property_ident,
1554 IS_CLASS (rtype),
1555 NULL_TREE);
1557 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1559 /* This is a special, complicated case. If the
1560 property is optional, and is read-only, then the
1561 property is always used for reading, but an
1562 eventual existing non-property setter can be used
1563 for writing. We create an artificial property
1564 decl copying the getter from the optional
1565 property, and looking up the setter in the
1566 interface. */
1567 x = maybe_make_artificial_property_decl (NULL_TREE,
1568 NULL_TREE,
1569 rprotos,
1570 property_ident,
1571 false,
1572 PROPERTY_GETTER_NAME (x));
1576 else if (objc_method_context)
1578 /* Else, if we are inside a method it could be the case of
1579 'super' or 'self'. */
1580 tree interface_type = NULL_TREE;
1581 tree t = object;
1582 while (TREE_CODE (t) == COMPOUND_EXPR
1583 || TREE_CODE (t) == MODIFY_EXPR
1584 || CONVERT_EXPR_P (t)
1585 || TREE_CODE (t) == COMPONENT_REF)
1586 t = TREE_OPERAND (t, 0);
1588 STRIP_ANY_LOCATION_WRAPPER (t);
1590 if (t == UOBJC_SUPER_decl)
1591 interface_type = lookup_interface (CLASS_SUPER_NAME (implementation_template));
1592 else if (t == self_decl)
1593 interface_type = lookup_interface (CLASS_NAME (implementation_template));
1595 if (interface_type)
1597 if (TREE_CODE (objc_method_context) != CLASS_METHOD_DECL)
1598 x = lookup_property (interface_type, property_ident);
1600 if (x == NULL_TREE)
1602 /* Try the dot-syntax without a declared property.
1603 If this is an access to 'self', it is possible
1604 that they may refer to a setter/getter that is
1605 not declared in the interface, but exists locally
1606 in the implementation. In that case, get the
1607 implementation context and use it. */
1608 tree implementation = NULL_TREE;
1610 if (t == self_decl)
1611 implementation = objc_implementation_context;
1613 x = maybe_make_artificial_property_decl
1614 (interface_type, implementation, NULL_TREE,
1615 property_ident,
1616 (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL),
1617 NULL_TREE);
1619 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1621 tree implementation = NULL_TREE;
1623 if (t == self_decl)
1624 implementation = objc_implementation_context;
1626 x = maybe_make_artificial_property_decl (interface_type,
1627 implementation,
1628 NULL_TREE,
1629 property_ident,
1630 false,
1631 PROPERTY_GETTER_NAME (x));
1636 else
1638 /* This is the case where we have more information on 'rtype'. */
1639 tree basetype = TYPE_MAIN_VARIANT (rtype);
1641 /* Skip the pointer - if none, it's not an Objective-C object or
1642 class. */
1643 if (basetype != NULL_TREE && TREE_CODE (basetype) == POINTER_TYPE)
1644 basetype = TREE_TYPE (basetype);
1645 else
1646 return NULL_TREE;
1648 /* Traverse typedefs. */
1649 while (basetype != NULL_TREE
1650 && TREE_CODE (basetype) == RECORD_TYPE
1651 && OBJC_TYPE_NAME (basetype)
1652 && TREE_CODE (OBJC_TYPE_NAME (basetype)) == TYPE_DECL
1653 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (basetype)))
1654 basetype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (basetype));
1656 if (basetype != NULL_TREE && TYPED_OBJECT (basetype))
1658 tree interface_type = TYPE_OBJC_INTERFACE (basetype);
1659 tree protocol_list = TYPE_OBJC_PROTOCOL_LIST (basetype);
1661 if (interface_type
1662 && (TREE_CODE (interface_type) == CLASS_INTERFACE_TYPE
1663 || TREE_CODE (interface_type) == CATEGORY_INTERFACE_TYPE
1664 || TREE_CODE (interface_type) == PROTOCOL_INTERFACE_TYPE))
1666 /* Not sure 'rtype' could ever be a class here! Just
1667 for safety we keep the checks. */
1668 if (!IS_CLASS (rtype))
1670 x = lookup_property (interface_type, property_ident);
1672 if (x == NULL_TREE)
1673 x = lookup_property_in_protocol_list (protocol_list,
1674 property_ident);
1677 if (x == NULL_TREE)
1679 /* Try the dot-syntax without a declared property.
1680 If we are inside a method implementation, it is
1681 possible that they may refer to a setter/getter
1682 that is not declared in the interface, but exists
1683 locally in the implementation. In that case, get
1684 the implementation context and use it. */
1685 tree implementation = NULL_TREE;
1687 if (objc_implementation_context
1688 && CLASS_NAME (objc_implementation_context)
1689 == OBJC_TYPE_NAME (interface_type))
1690 implementation = objc_implementation_context;
1692 x = maybe_make_artificial_property_decl (interface_type,
1693 implementation,
1694 protocol_list,
1695 property_ident,
1696 IS_CLASS (rtype),
1697 NULL_TREE);
1699 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1701 tree implementation = NULL_TREE;
1703 if (objc_implementation_context
1704 && CLASS_NAME (objc_implementation_context)
1705 == OBJC_TYPE_NAME (interface_type))
1706 implementation = objc_implementation_context;
1708 x = maybe_make_artificial_property_decl (interface_type,
1709 implementation,
1710 protocol_list,
1711 property_ident,
1712 false,
1713 PROPERTY_GETTER_NAME (x));
1719 if (x)
1721 tree expression;
1722 tree getter_call;
1723 tree method_prototype_avail = NULL_TREE;
1725 /* We have an additional nasty problem here; if this
1726 PROPERTY_REF needs to become a 'getter', then the conversion
1727 from PROPERTY_REF into a getter call happens in gimplify,
1728 after the selector table has already been generated and when
1729 it is too late to add another selector to it. To work around
1730 the problem, we always create the getter call at this stage,
1731 which puts the selector in the table. Note that if the
1732 PROPERTY_REF becomes a 'setter' instead of a 'getter', then
1733 we have added a selector too many to the selector table.
1734 This is a little inefficient.
1736 Also note that method calls to 'self' and 'super' require the
1737 context (self_decl, UOBJS_SUPER_decl,
1738 objc_implementation_context etc) to be built correctly; this
1739 is yet another reason why building the call at the gimplify
1740 stage (when this context has been lost) is not very
1741 practical. If we build it at this stage, we know it will
1742 always be built correctly.
1744 If the PROPERTY_HAS_NO_GETTER() (ie, it is an artificial
1745 property decl created to deal with a dotsyntax not really
1746 referring to an existing property) then do not try to build a
1747 call to the getter as there is no getter. */
1748 if (PROPERTY_HAS_NO_GETTER (x))
1749 getter_call = NULL_TREE;
1750 else
1751 getter_call = objc_finish_message_expr
1752 (object, PROPERTY_GETTER_NAME (x), NULL_TREE,
1753 /* Disable the immediate deprecation warning if the getter
1754 is deprecated, but record the fact that the getter is
1755 deprecated by setting PROPERTY_REF_DEPRECATED_GETTER to
1756 the method prototype. */
1757 &method_prototype_avail);
1759 expression = build4 (PROPERTY_REF, TREE_TYPE(x), object, x, getter_call,
1760 method_prototype_avail);
1761 SET_EXPR_LOCATION (expression, input_location);
1762 TREE_SIDE_EFFECTS (expression) = 1;
1764 return expression;
1767 return NULL_TREE;
1770 /* This hook routine is invoked by the parser when an expression such
1771 as 'xxx.yyy' is parsed, and 'xxx' is a class name. This is the
1772 Objective-C 2.0 dot-syntax applied to classes, so we need to
1773 convert it into a setter/getter call on the class. */
1774 tree
1775 objc_build_class_component_ref (tree class_name, tree property_ident)
1777 tree x = NULL_TREE;
1778 tree object, rtype;
1780 if (flag_objc1_only)
1781 error_at (input_location, "the dot syntax is not available in Objective-C 1.0");
1783 if (class_name == NULL_TREE || class_name == error_mark_node
1784 || TREE_CODE (class_name) != IDENTIFIER_NODE)
1785 return error_mark_node;
1787 if (property_ident == NULL_TREE || property_ident == error_mark_node
1788 || TREE_CODE (property_ident) != IDENTIFIER_NODE)
1789 return NULL_TREE;
1791 object = objc_get_class_reference (class_name);
1792 if (!object)
1794 /* We know that 'class_name' is an Objective-C class name as the
1795 parser won't call this function if it is not. This is only a
1796 double-check for safety. */
1797 error_at (input_location, "could not find class %qE", class_name);
1798 return error_mark_node;
1801 rtype = lookup_interface (class_name);
1802 if (!rtype)
1804 /* Again, this should never happen, but we do check. */
1805 error_at (input_location, "could not find interface for class %qE", class_name);
1806 return error_mark_node;
1808 else
1810 if (TREE_UNAVAILABLE (rtype))
1811 error ("class %qE is unavailable", class_name);
1812 else if (TREE_DEPRECATED (rtype))
1813 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated", class_name);
1816 x = maybe_make_artificial_property_decl (rtype, NULL_TREE, NULL_TREE,
1817 property_ident,
1818 true, NULL_TREE);
1820 if (x)
1822 tree expression;
1823 tree getter_call;
1824 tree method_prototype_avail = NULL_TREE;
1826 if (PROPERTY_HAS_NO_GETTER (x))
1827 getter_call = NULL_TREE;
1828 else
1829 getter_call = objc_finish_message_expr
1830 (object, PROPERTY_GETTER_NAME (x), NULL_TREE,
1831 &method_prototype_avail);
1833 expression = build4 (PROPERTY_REF, TREE_TYPE(x), object, x, getter_call,
1834 method_prototype_avail);
1835 SET_EXPR_LOCATION (expression, input_location);
1836 TREE_SIDE_EFFECTS (expression) = 1;
1838 return expression;
1840 else
1842 error_at (input_location, "could not find setter/getter for %qE in class %qE",
1843 property_ident, class_name);
1844 return error_mark_node;
1847 return NULL_TREE;
1851 /* This is used because we don't want to expose PROPERTY_REF to the
1852 C/C++ frontends. Maybe we should! */
1853 bool
1854 objc_is_property_ref (tree node)
1856 if (node && TREE_CODE (node) == PROPERTY_REF)
1857 return true;
1858 else
1859 return false;
1862 /* We use this to report tree codes that are known to be invalid in const-
1863 expression contexts. */
1864 bool
1865 objc_non_constant_expr_p (tree node)
1867 switch (TREE_CODE (node))
1869 default:
1870 return false;
1871 case MESSAGE_SEND_EXPR:
1872 case PROPERTY_REF:
1873 return true;
1877 /* This function builds a setter call for a PROPERTY_REF (real, for a
1878 declared property, or artificial, for a dot-syntax accessor which
1879 is not corresponding to a property). 'lhs' must be a PROPERTY_REF
1880 (the caller must check this beforehand). 'rhs' is the value to
1881 assign to the property. A plain setter call is returned, or
1882 error_mark_node if the property is readonly. */
1884 static tree
1885 objc_build_setter_call (tree lhs, tree rhs)
1887 tree object_expr = PROPERTY_REF_OBJECT (lhs);
1888 tree property_decl = PROPERTY_REF_PROPERTY_DECL (lhs);
1890 if (PROPERTY_READONLY (property_decl))
1892 error ("%qs property cannot be set", "readonly");
1893 return error_mark_node;
1895 else
1897 tree setter_argument = build_tree_list (NULL_TREE, rhs);
1898 tree setter;
1900 /* TODO: Check that the setter return type is 'void'. */
1902 /* TODO: Decay arguments in C. */
1903 setter = objc_finish_message_expr (object_expr,
1904 PROPERTY_SETTER_NAME (property_decl),
1905 setter_argument, NULL);
1906 return setter;
1910 /* This hook routine is called when a MODIFY_EXPR is being built. We
1911 check what is being modified; if it is a PROPERTY_REF, we need to
1912 generate a 'setter' function call for the property. If this is not
1913 a PROPERTY_REF, we return NULL_TREE and the C/C++ frontend will go
1914 on creating their MODIFY_EXPR.
1916 This is used for example if you write
1918 object.count = 1;
1920 where 'count' is a property. The left-hand side creates a
1921 PROPERTY_REF, and then the compiler tries to generate a MODIFY_EXPR
1922 to assign something to it. We intercept that here, and generate a
1923 call to the 'setter' method instead. */
1924 tree
1925 objc_maybe_build_modify_expr (tree lhs, tree rhs)
1927 if (lhs && TREE_CODE (lhs) == PROPERTY_REF)
1929 /* Building a simple call to the setter method would work for cases such as
1931 object.count = 1;
1933 but wouldn't work for cases such as
1935 count = object2.count = 1;
1937 to get these to work with very little effort, we build a
1938 compound statement which does the setter call (to set the
1939 property to 'rhs'), but which can also be evaluated returning
1940 the 'rhs'. If the 'rhs' has no side effects, we can simply
1941 evaluate it twice, building
1943 ([object setProperty: rhs]; rhs)
1945 If it has side effects, we put it in a temporary variable first,
1946 so we create the following:
1948 (temp = rhs; [object setProperty: temp]; temp)
1950 setter_argument is rhs in the first case, and temp in the second
1951 case.
1953 tree setter_argument;
1955 /* s1, s2 and s3 are the tree statements that we need in the
1956 compound expression. */
1957 tree s1, s2, s3, compound_expr;
1959 if (TREE_SIDE_EFFECTS (rhs))
1961 tree bind;
1963 /* Declare __objc_property_temp in a local bind. */
1964 setter_argument = objc_create_temporary_var (TREE_TYPE (rhs), "__objc_property_temp");
1965 DECL_SOURCE_LOCATION (setter_argument) = input_location;
1966 bind = build3 (BIND_EXPR, void_type_node, setter_argument, NULL, NULL);
1967 SET_EXPR_LOCATION (bind, input_location);
1968 TREE_SIDE_EFFECTS (bind) = 1;
1969 add_stmt (bind);
1971 /* s1: x = rhs */
1972 s1 = build_modify_expr (input_location, setter_argument, NULL_TREE,
1973 NOP_EXPR,
1974 input_location, rhs, NULL_TREE);
1975 SET_EXPR_LOCATION (s1, input_location);
1977 else
1979 /* No s1. */
1980 setter_argument = rhs;
1981 s1 = NULL_TREE;
1984 /* Now build the compound statement. */
1986 /* s2: [object setProperty: x] */
1987 s2 = objc_build_setter_call (lhs, setter_argument);
1989 /* This happens if building the setter failed because the
1990 property is readonly. */
1991 if (s2 == error_mark_node)
1992 return error_mark_node;
1994 SET_EXPR_LOCATION (s2, input_location);
1996 /* s3: x */
1997 s3 = convert (TREE_TYPE (lhs), setter_argument);
1999 /* Now build the compound statement (s1, s2, s3) or (s2, s3) as
2000 appropriate. */
2001 if (s1)
2002 compound_expr = build_compound_expr (input_location, build_compound_expr (input_location, s1, s2), s3);
2003 else
2004 compound_expr = build_compound_expr (input_location, s2, s3);
2006 /* Without this, with -Wall you get a 'valued computed is not
2007 used' every time there is a "object.property = x" where the
2008 value of the resulting MODIFY_EXPR is not used. That is
2009 correct (maybe a more sophisticated implementation could
2010 avoid generating the compound expression if not needed), but
2011 we need to turn it off. */
2012 suppress_warning (compound_expr, OPT_Wunused);
2013 return compound_expr;
2015 else
2016 return NULL_TREE;
2019 /* This hook is called by the frontend when one of the four unary
2020 expressions PREINCREMENT_EXPR, POSTINCREMENT_EXPR,
2021 PREDECREMENT_EXPR and POSTDECREMENT_EXPR is being built with an
2022 argument which is a PROPERTY_REF. For example, this happens if you have
2024 object.count++;
2026 where 'count' is a property. We need to use the 'getter' and
2027 'setter' for the property in an appropriate way to build the
2028 appropriate expression. 'code' is the code for the expression (one
2029 of the four mentioned above); 'argument' is the PROPERTY_REF, and
2030 'increment' is how much we need to add or subtract. */
2031 tree
2032 objc_build_incr_expr_for_property_ref (location_t location,
2033 enum tree_code code,
2034 tree argument, tree increment)
2036 /* Here are the expressions that we want to build:
2038 For PREINCREMENT_EXPR / PREDECREMENT_EXPR:
2039 (temp = [object property] +/- increment, [object setProperty: temp], temp)
2041 For POSTINCREMENT_EXPR / POSTECREMENT_EXPR:
2042 (temp = [object property], [object setProperty: temp +/- increment], temp) */
2044 tree temp_variable_decl, bind;
2045 /* s1, s2 and s3 are the tree statements that we need in the
2046 compound expression. */
2047 tree s1, s2, s3, compound_expr;
2049 /* Safety check. */
2050 if (!argument || TREE_CODE (argument) != PROPERTY_REF)
2051 return error_mark_node;
2053 /* Declare __objc_property_temp in a local bind. */
2054 temp_variable_decl = objc_create_temporary_var (TREE_TYPE (argument), "__objc_property_temp");
2055 DECL_SOURCE_LOCATION (temp_variable_decl) = location;
2056 bind = build3 (BIND_EXPR, void_type_node, temp_variable_decl, NULL, NULL);
2057 SET_EXPR_LOCATION (bind, location);
2058 TREE_SIDE_EFFECTS (bind) = 1;
2059 add_stmt (bind);
2061 /* Now build the compound statement. */
2063 /* Note that the 'getter' is generated at gimplify time; at this
2064 time, we can simply put the property_ref (ie, argument) wherever
2065 we want the getter ultimately to be. */
2067 /* s1: __objc_property_temp = [object property] <+/- increment> */
2068 switch (code)
2070 case PREINCREMENT_EXPR:
2071 /* __objc_property_temp = [object property] + increment */
2072 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
2073 NOP_EXPR,
2074 location, build2 (PLUS_EXPR, TREE_TYPE (argument),
2075 argument, increment), NULL_TREE);
2076 break;
2077 case PREDECREMENT_EXPR:
2078 /* __objc_property_temp = [object property] - increment */
2079 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
2080 NOP_EXPR,
2081 location, build2 (MINUS_EXPR, TREE_TYPE (argument),
2082 argument, increment), NULL_TREE);
2083 break;
2084 case POSTINCREMENT_EXPR:
2085 case POSTDECREMENT_EXPR:
2086 /* __objc_property_temp = [object property] */
2087 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
2088 NOP_EXPR,
2089 location, argument, NULL_TREE);
2090 break;
2091 default:
2092 gcc_unreachable ();
2095 /* s2: [object setProperty: __objc_property_temp <+/- increment>] */
2096 switch (code)
2098 case PREINCREMENT_EXPR:
2099 case PREDECREMENT_EXPR:
2100 /* [object setProperty: __objc_property_temp] */
2101 s2 = objc_build_setter_call (argument, temp_variable_decl);
2102 break;
2103 case POSTINCREMENT_EXPR:
2104 /* [object setProperty: __objc_property_temp + increment] */
2105 s2 = objc_build_setter_call (argument,
2106 build2 (PLUS_EXPR, TREE_TYPE (argument),
2107 temp_variable_decl, increment));
2108 break;
2109 case POSTDECREMENT_EXPR:
2110 /* [object setProperty: __objc_property_temp - increment] */
2111 s2 = objc_build_setter_call (argument,
2112 build2 (MINUS_EXPR, TREE_TYPE (argument),
2113 temp_variable_decl, increment));
2114 break;
2115 default:
2116 gcc_unreachable ();
2119 /* This happens if building the setter failed because the property
2120 is readonly. */
2121 if (s2 == error_mark_node)
2122 return error_mark_node;
2124 SET_EXPR_LOCATION (s2, location);
2126 /* s3: __objc_property_temp */
2127 s3 = convert (TREE_TYPE (argument), temp_variable_decl);
2129 /* Now build the compound statement (s1, s2, s3) */
2130 compound_expr = build_compound_expr (location, build_compound_expr (location, s1, s2), s3);
2132 /* Prevent C++ from warning with -Wall that "right operand of comma
2133 operator has no effect". */
2134 suppress_warning (compound_expr, OPT_Wunused);
2135 return compound_expr;
2138 tree
2139 objc_build_method_signature (bool is_class_method, tree rettype, tree selector,
2140 tree optparms, bool ellipsis)
2142 if (is_class_method)
2143 return build_method_decl (CLASS_METHOD_DECL, rettype, selector,
2144 optparms, ellipsis);
2145 else
2146 return build_method_decl (INSTANCE_METHOD_DECL, rettype, selector,
2147 optparms, ellipsis);
2150 void
2151 objc_add_method_declaration (bool is_class_method, tree decl, tree attributes)
2153 if (!objc_interface_context)
2155 /* PS: At the moment, due to how the parser works, it should be
2156 impossible to get here. But it's good to have the check in
2157 case the parser changes.
2159 fatal_error (input_location,
2160 "method declaration not in @interface context");
2163 if (flag_objc1_only && attributes)
2164 error_at (input_location, "method attributes are not available in Objective-C 1.0");
2166 objc_decl_method_attributes (&decl, attributes, 0);
2167 objc_add_method (objc_interface_context,
2168 decl,
2169 is_class_method,
2170 objc_method_optional_flag);
2173 /* Return 'true' if the method definition could be started, and
2174 'false' if not (because we are outside an @implementation context).
2175 EXPR is NULL or an expression that needs to be evaluated for the
2176 side effects of array size expressions in the parameters.
2178 bool
2179 objc_start_method_definition (bool is_class_method, tree decl, tree attributes,
2180 tree expr)
2182 if (!objc_implementation_context)
2184 error ("method definition not in @implementation context");
2185 return false;
2188 if (decl != NULL_TREE && METHOD_SEL_NAME (decl) == error_mark_node)
2189 return false;
2191 #ifndef OBJCPLUS
2192 /* Indicate no valid break/continue context. */
2193 in_statement = 0;
2194 #endif
2196 if (attributes)
2197 warning_at (input_location, 0, "method attributes cannot be specified in @implementation context");
2198 else
2199 objc_decl_method_attributes (&decl, attributes, 0);
2201 objc_add_method (objc_implementation_context,
2202 decl,
2203 is_class_method,
2204 /* is optional */ false);
2205 start_method_def (decl, expr);
2206 return true;
2209 void
2210 objc_add_instance_variable (tree decl)
2212 (void) add_instance_variable (objc_ivar_context,
2213 objc_ivar_visibility,
2214 decl);
2217 /* Construct a C struct with same name as KLASS, a base struct with tag
2218 SUPER_NAME (if any), and FIELDS indicated. */
2220 static tree
2221 objc_build_struct (tree klass, tree fields, tree super_name)
2223 tree name = CLASS_NAME (klass);
2224 tree s = objc_start_struct (name);
2225 tree super = (super_name ? xref_tag (RECORD_TYPE, super_name) : NULL_TREE);
2226 tree t;
2227 vec<tree> objc_info = vNULL;
2228 int i;
2230 if (super)
2232 /* Prepend a packed variant of the base class into the layout. This
2233 is necessary to preserve ObjC ABI compatibility. */
2234 tree base = build_decl (input_location,
2235 FIELD_DECL, NULL_TREE, super);
2236 tree field = TYPE_FIELDS (super);
2238 while (field && DECL_CHAIN (field)
2239 && TREE_CODE (DECL_CHAIN (field)) == FIELD_DECL)
2240 field = DECL_CHAIN (field);
2242 /* For ObjC ABI purposes, the "packed" size of a base class is
2243 the sum of the offset and the size (in bits) of the last field
2244 in the class. */
2245 DECL_SIZE (base)
2246 = (field && TREE_CODE (field) == FIELD_DECL
2247 ? size_binop (PLUS_EXPR,
2248 size_binop (PLUS_EXPR,
2249 size_binop
2250 (MULT_EXPR,
2251 convert (bitsizetype,
2252 DECL_FIELD_OFFSET (field)),
2253 bitsize_int (BITS_PER_UNIT)),
2254 DECL_FIELD_BIT_OFFSET (field)),
2255 DECL_SIZE (field))
2256 : bitsize_zero_node);
2257 DECL_SIZE_UNIT (base)
2258 = size_binop (FLOOR_DIV_EXPR, convert (sizetype, DECL_SIZE (base)),
2259 size_int (BITS_PER_UNIT));
2260 DECL_ARTIFICIAL (base) = 1;
2261 SET_DECL_ALIGN (base, 1);
2262 DECL_FIELD_CONTEXT (base) = s;
2263 #ifdef OBJCPLUS
2264 DECL_FIELD_IS_BASE (base) = 1;
2266 if (fields)
2267 /* Suppress C++ ABI warnings: we are following the ObjC ABI here. */
2268 suppress_warning (fields, OPT_Wabi);
2269 #endif
2270 DECL_CHAIN (base) = fields;
2271 fields = base;
2274 /* NB: Calling finish_struct() may cause type TYPE_OBJC_INFO
2275 information in all variants of this RECORD_TYPE to be destroyed
2276 (this is because the C frontend manipulates TYPE_LANG_SPECIFIC
2277 for something else and then will change all variants to use the
2278 same resulting TYPE_LANG_SPECIFIC, ignoring the fact that we use
2279 it for ObjC protocols and that such propagation will make all
2280 variants use the same objc_info), but it is therein that we store
2281 protocol conformance info (e.g., 'NSObject <MyProtocol>').
2282 Hence, we must save the ObjC-specific information before calling
2283 finish_struct(), and then reinstate it afterwards. */
2285 for (t = TYPE_MAIN_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t))
2287 INIT_TYPE_OBJC_INFO (t);
2288 objc_info.safe_push (TYPE_OBJC_INFO (t));
2291 s = objc_finish_struct (s, fields);
2293 for (i = 0, t = TYPE_MAIN_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t), i++)
2295 /* We now want to restore the different TYPE_OBJC_INFO, but we
2296 have the additional problem that the C frontend doesn't just
2297 copy TYPE_LANG_SPECIFIC from one variant to the other; it
2298 actually makes all of them the *same* TYPE_LANG_SPECIFIC. As
2299 we need a different TYPE_OBJC_INFO for each (and
2300 TYPE_OBJC_INFO is a field in TYPE_LANG_SPECIFIC), we need to
2301 make a copy of each TYPE_LANG_SPECIFIC before we modify
2302 TYPE_OBJC_INFO. */
2303 if (TYPE_LANG_SPECIFIC (t))
2305 /* Create a copy of TYPE_LANG_SPECIFIC. */
2306 struct lang_type *old_lang_type = TYPE_LANG_SPECIFIC (t);
2307 ALLOC_OBJC_TYPE_LANG_SPECIFIC (t);
2308 memcpy (TYPE_LANG_SPECIFIC (t), old_lang_type,
2309 SIZEOF_OBJC_TYPE_LANG_SPECIFIC);
2311 else
2313 /* Just create a new one. */
2314 ALLOC_OBJC_TYPE_LANG_SPECIFIC (t);
2316 /* Replace TYPE_OBJC_INFO with the saved one. This restores any
2317 protocol information that may have been associated with the
2318 type. */
2319 TYPE_OBJC_INFO (t) = objc_info[i];
2320 /* Replace the IDENTIFIER_NODE with an actual @interface now
2321 that we have it. */
2322 TYPE_OBJC_INTERFACE (t) = klass;
2324 objc_info.release ();
2326 /* Use TYPE_BINFO structures to point at the super class, if any. */
2327 objc_xref_basetypes (s, super);
2329 /* Mark this struct as a class template. */
2330 CLASS_STATIC_TEMPLATE (klass) = s;
2332 return s;
2335 /* Mark DECL as being 'volatile' for purposes of Darwin
2336 _setjmp()/_longjmp() exception handling. Called from
2337 objc_mark_locals_volatile(). */
2338 void
2339 objc_volatilize_decl (tree decl)
2341 /* Do not mess with variables that are 'static' or (already)
2342 'volatile'. */
2343 if (!TREE_THIS_VOLATILE (decl) && !TREE_STATIC (decl)
2344 && (VAR_P (decl)
2345 || TREE_CODE (decl) == PARM_DECL))
2347 if (local_variables_to_volatilize == NULL)
2348 vec_alloc (local_variables_to_volatilize, 8);
2350 vec_safe_push (local_variables_to_volatilize, decl);
2354 /* Called when parsing of a function completes; if any local variables
2355 in the function were marked as variables to volatilize, change them
2356 to volatile. We do this at the end of the function when the
2357 warnings about discarding 'volatile' have already been produced.
2358 We are making the variables as volatile just to force the compiler
2359 to preserve them between setjmp/longjmp, but we don't want warnings
2360 for them as they aren't really volatile. */
2361 void
2362 objc_finish_function (void)
2364 /* If there are any local variables to volatilize, volatilize them. */
2365 if (local_variables_to_volatilize)
2367 int i;
2368 tree decl;
2369 FOR_EACH_VEC_ELT (*local_variables_to_volatilize, i, decl)
2371 tree t = TREE_TYPE (decl);
2373 t = build_qualified_type (t, TYPE_QUALS (t) | TYPE_QUAL_VOLATILE);
2374 TREE_TYPE (decl) = t;
2375 TREE_THIS_VOLATILE (decl) = 1;
2376 TREE_SIDE_EFFECTS (decl) = 1;
2377 DECL_REGISTER (decl) = 0;
2378 #ifndef OBJCPLUS
2379 C_DECL_REGISTER (decl) = 0;
2380 #endif
2383 /* Now we delete the vector. This sets it to NULL as well. */
2384 vec_free (local_variables_to_volatilize);
2388 /* Check if protocol PROTO is adopted (directly or indirectly) by class CLS
2389 (including its categories and superclasses) or by object type TYP.
2390 Issue a warning if PROTO is not adopted anywhere and WARN is set. */
2392 static bool
2393 objc_lookup_protocol (tree proto, tree cls, tree typ, bool warn)
2395 bool class_type = (cls != NULL_TREE);
2397 while (cls)
2399 tree c;
2401 /* Check protocols adopted by the class and its categories. */
2402 for (c = cls; c; c = CLASS_CATEGORY_LIST (c))
2404 if (lookup_protocol_in_reflist (CLASS_PROTOCOL_LIST (c), proto))
2405 return true;
2408 /* Repeat for superclasses. */
2409 cls = lookup_interface (CLASS_SUPER_NAME (cls));
2412 /* Check for any protocols attached directly to the object type. */
2413 if (TYPE_HAS_OBJC_INFO (typ))
2415 if (lookup_protocol_in_reflist (TYPE_OBJC_PROTOCOL_LIST (typ), proto))
2416 return true;
2419 if (warn)
2421 *errbuf = 0;
2422 gen_type_name_0 (class_type ? typ : TYPE_POINTER_TO (typ));
2423 /* NB: Types 'id' and 'Class' cannot reasonably be described as
2424 "implementing" a given protocol, since they do not have an
2425 implementation. */
2426 if (class_type)
2427 warning (0, "class %qs does not implement the %qE protocol",
2428 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
2429 else
2430 warning (0, "type %qs does not conform to the %qE protocol",
2431 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
2434 return false;
2437 /* Check if class RCLS and instance struct type RTYP conform to at least the
2438 same protocols that LCLS and LTYP conform to. */
2440 static bool
2441 objc_compare_protocols (tree lcls, tree ltyp, tree rcls, tree rtyp, bool warn)
2443 tree p;
2444 bool have_lproto = false;
2446 while (lcls)
2448 /* NB: We do _not_ look at categories defined for LCLS; these may or
2449 may not get loaded in, and therefore it is unreasonable to require
2450 that RCLS/RTYP must implement any of their protocols. */
2451 for (p = CLASS_PROTOCOL_LIST (lcls); p; p = TREE_CHAIN (p))
2453 have_lproto = true;
2455 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
2456 return warn;
2459 /* Repeat for superclasses. */
2460 lcls = lookup_interface (CLASS_SUPER_NAME (lcls));
2463 /* Check for any protocols attached directly to the object type. */
2464 if (TYPE_HAS_OBJC_INFO (ltyp))
2466 for (p = TYPE_OBJC_PROTOCOL_LIST (ltyp); p; p = TREE_CHAIN (p))
2468 have_lproto = true;
2470 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
2471 return warn;
2475 /* NB: If LTYP and LCLS have no protocols to search for, return 'true'
2476 vacuously, _unless_ RTYP is a protocol-qualified 'id'. We can get
2477 away with simply checking for 'id' or 'Class' (!RCLS), since this
2478 routine will not get called in other cases. */
2479 return have_lproto || (rcls != NULL_TREE);
2482 /* Given two types TYPE1 and TYPE2, return their least common ancestor.
2483 Both TYPE1 and TYPE2 must be pointers, and already determined to be
2484 compatible by objc_compare_types() below. */
2486 tree
2487 objc_common_type (tree type1, tree type2)
2489 tree inner1 = TREE_TYPE (type1), inner2 = TREE_TYPE (type2);
2491 while (POINTER_TYPE_P (inner1))
2493 inner1 = TREE_TYPE (inner1);
2494 inner2 = TREE_TYPE (inner2);
2497 /* If one type is derived from another, return the base type. */
2498 if (DERIVED_FROM_P (inner1, inner2))
2499 return type1;
2500 else if (DERIVED_FROM_P (inner2, inner1))
2501 return type2;
2503 /* If both types are 'Class', return 'Class'. */
2504 if (objc_is_class_id (inner1) && objc_is_class_id (inner2))
2505 return objc_class_type;
2507 /* Otherwise, return 'id'. */
2508 return objc_object_type;
2511 /* Determine if it is permissible to assign (if ARGNO is greater than -3)
2512 an instance of RTYP to an instance of LTYP or to compare the two
2513 (if ARGNO is equal to -3), per ObjC type system rules. Before
2514 returning 'true', this routine may issue warnings related to, e.g.,
2515 protocol conformance. When returning 'false', the routine must
2516 produce absolutely no warnings; the C or C++ front-end will do so
2517 instead, if needed. If either LTYP or RTYP is not an Objective-C
2518 type, the routine must return 'false'.
2520 The ARGNO parameter is encoded as follows:
2521 >= 1 Parameter number (CALLEE contains function being called);
2522 0 Return value;
2523 -1 Assignment;
2524 -2 Initialization;
2525 -3 Comparison (LTYP and RTYP may match in either direction);
2526 -4 Silent comparison (for C++ overload resolution);
2527 -5 Silent "specialization" comparison for RTYP to be a "specialization"
2528 of LTYP (a specialization means that RTYP is LTYP plus some constraints,
2529 so that each object of type RTYP is also of type LTYP). This is used
2530 when comparing property types. */
2532 bool
2533 objc_compare_types (tree ltyp, tree rtyp, int argno, tree callee)
2535 tree lcls, rcls, lproto, rproto;
2536 bool pointers_compatible;
2538 /* We must be dealing with pointer types */
2539 if (!POINTER_TYPE_P (ltyp) || !POINTER_TYPE_P (rtyp))
2540 return false;
2542 tree ltyp_attr, rtyp_attr;
2545 /* Remove indirections, but keep the type attributes from the innermost
2546 pointer type, to check for NSObject. */
2547 ltyp_attr = TYPE_ATTRIBUTES (ltyp);
2548 ltyp = TREE_TYPE (ltyp);
2549 rtyp_attr = TYPE_ATTRIBUTES (rtyp);
2550 rtyp = TREE_TYPE (rtyp);
2552 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
2554 /* We must also handle function pointers, since ObjC is a bit more
2555 lenient than C or C++ on this. */
2556 if (TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE)
2558 function_args_iterator liter, riter;
2560 /* Return types must be covariant. */
2561 if (!comptypes (TREE_TYPE (ltyp), TREE_TYPE (rtyp))
2562 && !objc_compare_types (TREE_TYPE (ltyp), TREE_TYPE (rtyp),
2563 argno, callee))
2564 return false;
2566 /* Argument types must be contravariant. */
2567 function_args_iter_init (&liter, ltyp);
2568 function_args_iter_init (&riter, rtyp);
2570 while (1)
2572 ltyp = function_args_iter_cond (&liter);
2573 rtyp = function_args_iter_cond (&riter);
2575 /* If we've exhaused both lists simulateously, we're done. */
2576 if (ltyp == NULL_TREE && rtyp == NULL_TREE)
2577 break;
2579 /* If one list is shorter than the other, they fail to match. */
2580 if (ltyp == NULL_TREE || rtyp == NULL_TREE)
2581 return false;
2583 if (!comptypes (rtyp, ltyp)
2584 && !objc_compare_types (rtyp, ltyp, argno, callee))
2585 return false;
2587 function_args_iter_next (&liter);
2588 function_args_iter_next (&riter);
2591 return true;
2594 /* We might have void * with NSObject type attr. */
2595 bool l_NSObject_p = ltyp_attr && lookup_attribute ("NSObject", ltyp_attr);
2596 bool r_NSObject_p = rtyp_attr && lookup_attribute ("NSObject", rtyp_attr);
2598 /* Past this point, we are only interested in ObjC class instances,
2599 or 'id' or 'Class' (except if the user applied the NSObject type
2600 attribute). */
2601 if ((TREE_CODE (ltyp) != RECORD_TYPE && !l_NSObject_p)
2602 || (TREE_CODE (rtyp) != RECORD_TYPE && !r_NSObject_p))
2603 return false;
2605 if (!objc_is_object_id (ltyp) && !objc_is_class_id (ltyp)
2606 && !TYPE_HAS_OBJC_INFO (ltyp) && !l_NSObject_p)
2607 return false;
2609 if (!objc_is_object_id (rtyp) && !objc_is_class_id (rtyp)
2610 && !TYPE_HAS_OBJC_INFO (rtyp) && !r_NSObject_p)
2611 return false;
2613 /* Past this point, we are committed to returning 'true' to the caller
2614 (unless performing a silent comparison; see below). However, we can
2615 still warn about type and/or protocol mismatches. */
2617 if (TYPE_HAS_OBJC_INFO (ltyp))
2619 lcls = TYPE_OBJC_INTERFACE (ltyp);
2620 lproto = TYPE_OBJC_PROTOCOL_LIST (ltyp);
2622 else
2623 lcls = lproto = NULL_TREE;
2625 if (TYPE_HAS_OBJC_INFO (rtyp))
2627 rcls = TYPE_OBJC_INTERFACE (rtyp);
2628 rproto = TYPE_OBJC_PROTOCOL_LIST (rtyp);
2630 else
2631 rcls = rproto = NULL_TREE;
2633 /* If we could not find an @interface declaration, we must have
2634 only seen a @class declaration; for purposes of type comparison,
2635 treat it as a stand-alone (root) class. */
2637 if (lcls && TREE_CODE (lcls) == IDENTIFIER_NODE)
2638 lcls = NULL_TREE;
2640 if (rcls && TREE_CODE (rcls) == IDENTIFIER_NODE)
2641 rcls = NULL_TREE;
2643 /* If either type is an unqualified 'id', we're done. This is because
2644 an 'id' can be assigned to or from any type with no warnings. When
2645 the pointer has NSObject attribute, consider that to be equivalent. */
2646 if (argno != -5)
2648 if ((!lproto && objc_is_object_id (ltyp))
2649 || (!rproto && objc_is_object_id (rtyp)))
2650 return true;
2651 if (l_NSObject_p || r_NSObject_p)
2652 return true;
2654 else
2656 /* For property checks, though, an 'id' is considered the most
2657 general type of object, hence if you try to specialize an
2658 'NSArray *' (ltyp) property with an 'id' (rtyp) one, we need
2659 to warn. */
2660 if (!lproto && (objc_is_object_id (ltyp) || l_NSObject_p))
2661 return true;
2664 pointers_compatible = (TYPE_MAIN_VARIANT (ltyp) == TYPE_MAIN_VARIANT (rtyp));
2666 /* If the underlying types are the same, and at most one of them has
2667 a protocol list, we do not need to issue any diagnostics. */
2668 if (pointers_compatible && (!lproto || !rproto))
2669 return true;
2671 /* If exactly one of the types is 'Class', issue a diagnostic; any
2672 exceptions of this rule have already been handled. */
2673 if (objc_is_class_id (ltyp) ^ objc_is_class_id (rtyp))
2674 pointers_compatible = false;
2675 /* Otherwise, check for inheritance relations. */
2676 else
2678 if (!pointers_compatible)
2680 /* Again, if any of the two is an 'id', we're satisfied,
2681 unless we're comparing properties, in which case only an
2682 'id' on the left-hand side (old property) is good
2683 enough. */
2684 if (argno != -5)
2685 pointers_compatible
2686 = (objc_is_object_id (ltyp) || objc_is_object_id (rtyp));
2687 else
2688 pointers_compatible = objc_is_object_id (ltyp);
2691 if (!pointers_compatible)
2692 pointers_compatible = DERIVED_FROM_P (ltyp, rtyp);
2694 if (!pointers_compatible && (argno == -3 || argno == -4))
2695 pointers_compatible = DERIVED_FROM_P (rtyp, ltyp);
2698 /* If the pointers match modulo protocols, check for protocol conformance
2699 mismatches. */
2700 if (pointers_compatible)
2702 pointers_compatible = objc_compare_protocols (lcls, ltyp, rcls, rtyp,
2703 argno != -3);
2705 if (!pointers_compatible && argno == -3)
2706 pointers_compatible = objc_compare_protocols (rcls, rtyp, lcls, ltyp,
2707 argno != -3);
2710 if (!pointers_compatible)
2712 /* The two pointers are not exactly compatible. Issue a warning, unless
2713 we are performing a silent comparison, in which case return 'false'
2714 instead. */
2715 /* NB: For the time being, we shall make our warnings look like their
2716 C counterparts. In the future, we may wish to make them more
2717 ObjC-specific. */
2718 switch (argno)
2720 case -5:
2721 case -4:
2722 return false;
2724 case -3:
2725 warning (0, "comparison of distinct Objective-C types lacks a cast");
2726 break;
2728 case -2:
2729 warning (0, "initialization from distinct Objective-C type");
2730 break;
2732 case -1:
2733 warning (0, "assignment from distinct Objective-C type");
2734 break;
2736 case 0:
2737 warning (0, "distinct Objective-C type in return");
2738 break;
2740 default:
2741 warning (0, "passing argument %d of %qE from distinct "
2742 "Objective-C type", argno, callee);
2743 break;
2747 return true;
2750 /* This routine is similar to objc_compare_types except that function-pointers are
2751 excluded. This is because, caller assumes that common types are of (id, Object*)
2752 variety and calls objc_common_type to obtain a common type. There is no commonolty
2753 between two function-pointers in this regard. */
2755 bool
2756 objc_have_common_type (tree ltyp, tree rtyp, int argno, tree callee)
2758 if (objc_compare_types (ltyp, rtyp, argno, callee))
2760 /* exclude function-pointer types. */
2763 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
2764 rtyp = TREE_TYPE (rtyp);
2766 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
2767 return !(TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE);
2769 return false;
2772 #ifndef OBJCPLUS
2773 /* Determine if CHILD is derived from PARENT. The routine assumes that
2774 both parameters are RECORD_TYPEs, and is non-reflexive. */
2776 static bool
2777 objc_derived_from_p (tree parent, tree child)
2779 parent = TYPE_MAIN_VARIANT (parent);
2781 for (child = TYPE_MAIN_VARIANT (child);
2782 TYPE_BINFO (child) && BINFO_N_BASE_BINFOS (TYPE_BINFO (child));)
2784 child = TYPE_MAIN_VARIANT (BINFO_TYPE (BINFO_BASE_BINFO
2785 (TYPE_BINFO (child),
2786 0)));
2788 if (child == parent)
2789 return true;
2792 return false;
2794 #endif
2796 tree
2797 objc_build_component_ref (tree datum, tree component)
2799 /* If COMPONENT is NULL, the caller is referring to the anonymous
2800 base class field. */
2801 if (!component)
2803 tree base = TYPE_FIELDS (TREE_TYPE (datum));
2805 return build3 (COMPONENT_REF, TREE_TYPE (base), datum, base, NULL_TREE);
2808 /* The 'build_component_ref' routine has been removed from the C++
2809 front-end, but 'finish_class_member_access_expr' seems to be
2810 a worthy substitute. */
2811 #ifdef OBJCPLUS
2812 return finish_class_member_access_expr (datum, component, false,
2813 tf_warning_or_error);
2814 #else
2815 return build_component_ref (input_location, datum, component,
2816 UNKNOWN_LOCATION, UNKNOWN_LOCATION);
2817 #endif
2820 /* Recursively copy inheritance information rooted at BINFO. To do this,
2821 we emulate the song and dance performed by cp/tree.cc:copy_binfo(). */
2823 static tree
2824 objc_copy_binfo (tree binfo)
2826 tree btype = BINFO_TYPE (binfo);
2827 tree binfo2 = make_tree_binfo (BINFO_N_BASE_BINFOS (binfo));
2828 tree base_binfo;
2829 int ix;
2831 BINFO_TYPE (binfo2) = btype;
2832 BINFO_OFFSET (binfo2) = BINFO_OFFSET (binfo);
2833 BINFO_BASE_ACCESSES (binfo2) = BINFO_BASE_ACCESSES (binfo);
2835 /* Recursively copy base binfos of BINFO. */
2836 for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
2838 tree base_binfo2 = objc_copy_binfo (base_binfo);
2840 BINFO_INHERITANCE_CHAIN (base_binfo2) = binfo2;
2841 BINFO_BASE_APPEND (binfo2, base_binfo2);
2844 return binfo2;
2847 /* Record superclass information provided in BASETYPE for ObjC class REF.
2848 This is loosely based on cp/decl.cc:xref_basetypes(). */
2850 static void
2851 objc_xref_basetypes (tree ref, tree basetype)
2853 tree variant;
2854 tree binfo = make_tree_binfo (basetype ? 1 : 0);
2855 TYPE_BINFO (ref) = binfo;
2856 BINFO_OFFSET (binfo) = size_zero_node;
2857 BINFO_TYPE (binfo) = ref;
2859 gcc_assert (TYPE_MAIN_VARIANT (ref) == ref);
2860 for (variant = ref; variant; variant = TYPE_NEXT_VARIANT (variant))
2861 TYPE_BINFO (variant) = binfo;
2863 if (basetype)
2865 tree base_binfo = objc_copy_binfo (TYPE_BINFO (basetype));
2867 BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
2868 vec_alloc (BINFO_BASE_ACCESSES (binfo), 1);
2869 BINFO_BASE_APPEND (binfo, base_binfo);
2870 BINFO_BASE_ACCESS_APPEND (binfo, access_public_node);
2874 /* Called from finish_decl. */
2876 void
2877 objc_check_decl (tree decl)
2879 tree type = TREE_TYPE (decl);
2881 if (TREE_CODE (type) != RECORD_TYPE)
2882 return;
2883 if (OBJC_TYPE_NAME (type) && (type = objc_is_class_name (OBJC_TYPE_NAME (type))))
2884 error ("statically allocated instance of Objective-C class %qE",
2885 type);
2888 void
2889 objc_check_global_decl (tree decl)
2891 tree id = DECL_NAME (decl);
2892 if (objc_is_class_name (id) && global_bindings_p())
2893 error ("redeclaration of Objective-C class %qs", IDENTIFIER_POINTER (id));
2896 /* Construct a PROTOCOLS-qualified variant of INTERFACE, where
2897 INTERFACE may either name an Objective-C class, or refer to the
2898 special 'id' or 'Class' types. If INTERFACE is not a valid ObjC
2899 type, just return it unchanged. This function is often called when
2900 PROTOCOLS is NULL_TREE, in which case we simply look up the
2901 appropriate INTERFACE. */
2903 tree
2904 objc_get_protocol_qualified_type (tree interface, tree protocols)
2906 /* If INTERFACE is not provided, default to 'id'. */
2907 tree type = (interface ? objc_is_id (interface) : objc_object_type);
2908 bool is_ptr = (type != NULL_TREE);
2910 if (!is_ptr)
2912 type = objc_is_class_name (interface);
2914 if (type)
2916 /* If looking at a typedef, retrieve the precise type it
2917 describes. */
2918 if (TREE_CODE (interface) == IDENTIFIER_NODE)
2919 interface = identifier_global_value (interface);
2921 type = ((interface && TREE_CODE (interface) == TYPE_DECL
2922 && DECL_ORIGINAL_TYPE (interface))
2923 ? DECL_ORIGINAL_TYPE (interface)
2924 : xref_tag (RECORD_TYPE, type));
2926 else
2928 /* This case happens when we are given an 'interface' which
2929 is not a valid class name. For example if a typedef was
2930 used, and 'interface' really is the identifier of the
2931 typedef, but when you resolve it you don't get an
2932 Objective-C class, but something else, such as 'int'.
2933 This is an error; protocols make no sense unless you use
2934 them with Objective-C objects. */
2935 error_at (input_location, "only Objective-C object types can be qualified with a protocol");
2937 /* Try to recover. Ignore the invalid class name, and treat
2938 the object as an 'id' to silence further warnings about
2939 the class. */
2940 type = objc_object_type;
2941 is_ptr = true;
2945 if (protocols)
2947 type = build_variant_type_copy (type);
2949 /* For pointers (i.e., 'id' or 'Class'), attach the protocol(s)
2950 to the pointee. */
2951 if (is_ptr)
2953 tree orig_pointee_type = TREE_TYPE (type);
2954 TREE_TYPE (type) = build_variant_type_copy (orig_pointee_type);
2956 /* Set up the canonical type information. */
2957 TYPE_CANONICAL (type)
2958 = TYPE_CANONICAL (TYPE_POINTER_TO (orig_pointee_type));
2960 TYPE_POINTER_TO (TREE_TYPE (type)) = type;
2961 type = TREE_TYPE (type);
2964 /* Look up protocols and install in lang specific list. */
2965 DUP_TYPE_OBJC_INFO (type, TYPE_MAIN_VARIANT (type));
2966 TYPE_OBJC_PROTOCOL_LIST (type) = lookup_and_install_protocols
2967 (protocols, /* definition_required */ false);
2969 /* For RECORD_TYPEs, point to the @interface; for 'id' and 'Class',
2970 return the pointer to the new pointee variant. */
2971 if (is_ptr)
2972 type = TYPE_POINTER_TO (type);
2973 else
2974 TYPE_OBJC_INTERFACE (type)
2975 = TYPE_OBJC_INTERFACE (TYPE_MAIN_VARIANT (type));
2978 return type;
2981 /* Check for circular dependencies in protocols. The arguments are
2982 PROTO, the protocol to check, and LIST, a list of protocol it
2983 conforms to. */
2985 static void
2986 check_protocol_recursively (tree proto, tree list)
2988 tree p;
2990 for (p = list; p; p = TREE_CHAIN (p))
2992 tree pp = TREE_VALUE (p);
2994 if (TREE_CODE (pp) == IDENTIFIER_NODE)
2995 pp = lookup_protocol (pp, /* warn if deprecated */ false,
2996 /* definition_required */ false);
2998 if (pp == proto)
2999 fatal_error (input_location, "protocol %qE has circular dependency",
3000 PROTOCOL_NAME (pp));
3001 if (pp)
3002 check_protocol_recursively (proto, PROTOCOL_LIST (pp));
3006 /* Look up PROTOCOLS, and return a list of those that are found. If
3007 none are found, return NULL. Note that this function will emit a
3008 warning if a protocol is found and is deprecated. If
3009 'definition_required', then warn if the protocol is found but is
3010 not defined (ie, if we only saw a forward-declaration of the
3011 protocol (as in "@protocol NSObject;") not a real definition with
3012 the list of methods). */
3013 static tree
3014 lookup_and_install_protocols (tree protocols, bool definition_required)
3016 tree proto;
3017 tree return_value = NULL_TREE;
3019 if (protocols == error_mark_node)
3020 return NULL;
3022 for (proto = protocols; proto; proto = TREE_CHAIN (proto))
3024 tree ident = TREE_VALUE (proto);
3025 tree p = lookup_protocol (ident, /* warn_if_deprecated */ true,
3026 definition_required);
3028 if (p)
3029 return_value = chainon (return_value,
3030 build_tree_list (NULL_TREE, p));
3031 else if (ident != error_mark_node)
3032 error ("cannot find protocol declaration for %qE",
3033 ident);
3036 return return_value;
3039 static void
3040 build_common_objc_exception_stuff (void)
3042 tree noreturn_list, nothrow_list, temp_type;
3044 noreturn_list = tree_cons (get_identifier ("noreturn"), NULL, NULL);
3045 nothrow_list = tree_cons (get_identifier ("nothrow"), NULL, NULL);
3047 /* void objc_exception_throw(id) __attribute__((noreturn)); */
3048 /* void objc_sync_enter(id); */
3049 /* void objc_sync_exit(id); */
3050 temp_type = build_function_type_list (void_type_node,
3051 objc_object_type,
3052 NULL_TREE);
3053 objc_exception_throw_decl
3054 = add_builtin_function (TAG_EXCEPTIONTHROW, temp_type, 0, NOT_BUILT_IN, NULL,
3055 noreturn_list);
3056 /* Make sure that objc_exception_throw (id) claims that it may throw an
3057 exception. */
3058 TREE_NOTHROW (objc_exception_throw_decl) = 0;
3060 objc_sync_enter_decl
3061 = add_builtin_function (TAG_SYNCENTER, temp_type, 0, NOT_BUILT_IN,
3062 NULL, nothrow_list);
3064 objc_sync_exit_decl
3065 = add_builtin_function (TAG_SYNCEXIT, temp_type, 0, NOT_BUILT_IN,
3066 NULL, nothrow_list);
3069 /* Purpose: "play" parser, creating/installing representations
3070 of the declarations that are required by Objective-C.
3072 Model:
3074 type_spec--------->sc_spec
3075 (tree_list) (tree_list)
3078 identifier_node identifier_node */
3080 static void
3081 synth_module_prologue (void)
3083 tree type;
3084 uint32_t save_write_symbols = write_symbols;
3085 const struct gcc_debug_hooks *const save_hooks = debug_hooks;
3087 /* Suppress outputting debug symbols, because
3088 dbxout_init hasn't been called yet. */
3089 write_symbols = NO_DEBUG;
3090 debug_hooks = &do_nothing_debug_hooks;
3092 #ifdef OBJCPLUS
3093 push_lang_context (lang_name_c); /* extern "C" */
3094 #endif
3096 /* The following are also defined in <objc/objc.h> and friends. */
3098 objc_object_id = get_identifier (TAG_OBJECT);
3099 objc_class_id = get_identifier (TAG_CLASS);
3101 objc_object_reference = xref_tag (RECORD_TYPE, objc_object_id);
3102 objc_class_reference = xref_tag (RECORD_TYPE, objc_class_id);
3104 objc_object_type = build_pointer_type (objc_object_reference);
3105 objc_instancetype_type = build_pointer_type (objc_object_reference);
3106 objc_class_type = build_pointer_type (objc_class_reference);
3108 objc_object_name = get_identifier (OBJECT_TYPEDEF_NAME);
3109 objc_instancetype_name = get_identifier (INSTANCE_TYPEDEF_NAME);
3110 objc_class_name = get_identifier (CLASS_TYPEDEF_NAME);
3111 objc_selector_name = get_identifier (SEL_TYPEDEF_NAME);
3113 /* Declare the 'id', 'instancetype' and 'Class' typedefs. */
3114 type = lang_hooks.decls.pushdecl (build_decl (input_location,
3115 TYPE_DECL,
3116 objc_object_name,
3117 objc_object_type));
3118 suppress_warning (type);
3120 type = lang_hooks.decls.pushdecl (build_decl (input_location,
3121 TYPE_DECL,
3122 objc_instancetype_name,
3123 objc_instancetype_type));
3124 suppress_warning (type);
3126 type = lang_hooks.decls.pushdecl (build_decl (input_location,
3127 TYPE_DECL,
3128 objc_class_name,
3129 objc_class_type));
3130 suppress_warning (type);
3132 /* Forward-declare '@interface Protocol'. */
3133 type = get_identifier (PROTOCOL_OBJECT_CLASS_NAME);
3134 objc_declare_class (type);
3135 objc_protocol_type = build_pointer_type (xref_tag (RECORD_TYPE, type));
3137 /* Declare receiver type used for dispatching messages to 'super'. */
3138 /* `struct objc_super *' */
3139 objc_super_type = build_pointer_type (xref_tag (RECORD_TYPE,
3140 get_identifier (TAG_SUPER)));
3142 /* Declare pointers to method and ivar lists. */
3143 objc_method_list_ptr = build_pointer_type
3144 (xref_tag (RECORD_TYPE,
3145 get_identifier (UTAG_METHOD_LIST)));
3146 objc_method_proto_list_ptr
3147 = build_pointer_type (xref_tag (RECORD_TYPE,
3148 get_identifier (UTAG_METHOD_PROTOTYPE_LIST)));
3149 objc_ivar_list_ptr = build_pointer_type
3150 (xref_tag (RECORD_TYPE,
3151 get_identifier (UTAG_IVAR_LIST)));
3153 build_common_objc_exception_stuff ();
3155 /* Set-up runtime-specific templates, message and exception stuff. */
3156 (*runtime.initialize) ();
3158 /* Declare objc_getProperty, object_setProperty and other property
3159 accessor helpers. */
3160 build_common_objc_property_accessor_helpers ();
3162 /* Forward declare constant_string_id and constant_string_type. */
3163 if (!constant_string_class_name)
3164 constant_string_class_name = runtime.default_constant_string_class_name;
3165 constant_string_id = get_identifier (constant_string_class_name);
3166 objc_declare_class (constant_string_id);
3168 /* Pre-build the following entities - for speed/convenience. */
3169 self_id = get_identifier ("self");
3170 ucmd_id = get_identifier ("_cmd");
3172 /* Declare struct _objc_fast_enumeration_state { ... }; */
3173 build_fast_enumeration_state_template ();
3175 /* void objc_enumeration_mutation (id) */
3176 type = build_function_type_list (void_type_node,
3177 objc_object_type, NULL_TREE);
3178 objc_enumeration_mutation_decl
3179 = add_builtin_function (TAG_ENUMERATION_MUTATION, type, 0, NOT_BUILT_IN,
3180 NULL, NULL_TREE);
3181 TREE_NOTHROW (objc_enumeration_mutation_decl) = 0;
3183 #ifdef OBJCPLUS
3184 pop_lang_context ();
3185 #endif
3187 write_symbols = save_write_symbols;
3188 debug_hooks = save_hooks;
3191 /* --- const strings --- */
3193 /* Ensure that the ivar list for NSConstantString/NXConstantString
3194 (or whatever was specified via `-fconstant-string-class')
3195 contains fields at least as large as the following three, so that
3196 the runtime can stomp on them with confidence:
3198 struct STRING_OBJECT_CLASS_NAME
3200 Object isa;
3201 char *cString;
3202 unsigned int length;
3203 }; */
3205 static int
3206 check_string_class_template (void)
3208 tree field_decl = objc_get_class_ivars (constant_string_id);
3210 #define AT_LEAST_AS_LARGE_AS(F, T) \
3211 (F && TREE_CODE (F) == FIELD_DECL \
3212 && (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (F))) \
3213 >= TREE_INT_CST_LOW (TYPE_SIZE (T))))
3215 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
3216 return 0;
3218 field_decl = DECL_CHAIN (field_decl);
3219 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
3220 return 0;
3222 field_decl = DECL_CHAIN (field_decl);
3223 return AT_LEAST_AS_LARGE_AS (field_decl, unsigned_type_node);
3225 #undef AT_LEAST_AS_LARGE_AS
3228 /* Avoid calling `check_string_class_template ()' more than once. */
3229 static GTY(()) int string_layout_checked;
3231 /* Construct an internal string layout to be used as a template for
3232 creating NSConstantString/NXConstantString instances. */
3234 static tree
3235 objc_build_internal_const_str_type (void)
3237 tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);
3238 tree fields = build_decl (input_location,
3239 FIELD_DECL, NULL_TREE, ptr_type_node);
3240 tree field = build_decl (input_location,
3241 FIELD_DECL, NULL_TREE, ptr_type_node);
3243 DECL_CHAIN (field) = fields; fields = field;
3244 field = build_decl (input_location,
3245 FIELD_DECL, NULL_TREE, unsigned_type_node);
3246 DECL_CHAIN (field) = fields; fields = field;
3247 /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in
3248 reverse order! */
3249 finish_builtin_struct (type, "__builtin_ObjCString",
3250 fields, NULL_TREE);
3252 return type;
3255 /* Custom build_string which sets TREE_TYPE! */
3257 tree
3258 my_build_string (int len, const char *str)
3260 return fix_string_type (build_string (len, str));
3263 /* Build a string with contents STR and length LEN and convert it to a
3264 pointer. */
3266 tree
3267 my_build_string_pointer (int len, const char *str)
3269 tree string = my_build_string (len, str);
3270 tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));
3271 return build1 (ADDR_EXPR, ptrtype, string);
3274 hashval_t
3275 objc_string_hasher::hash (string_descriptor *ptr)
3277 const_tree const str = ptr->literal;
3278 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);
3279 int i, len = TREE_STRING_LENGTH (str);
3280 hashval_t h = len;
3282 for (i = 0; i < len; i++)
3283 h = ((h * 613) + p[i]);
3285 return h;
3288 bool
3289 objc_string_hasher::equal (string_descriptor *ptr1, string_descriptor *ptr2)
3291 const_tree const str1 = ptr1->literal;
3292 const_tree const str2 = ptr2->literal;
3293 int len1 = TREE_STRING_LENGTH (str1);
3295 return (len1 == TREE_STRING_LENGTH (str2)
3296 && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),
3297 len1));
3300 /* Given a chain of STRING_CST's, build a static instance of
3301 NXConstantString which points at the concatenation of those
3302 strings. We place the string object in the __string_objects
3303 section of the __OBJC segment. The Objective-C runtime will
3304 initialize the isa pointers of the string objects to point at the
3305 NXConstantString class object. */
3307 tree
3308 objc_build_string_object (tree string)
3310 tree constant_string_class;
3311 int length;
3312 tree addr;
3313 struct string_descriptor *desc, key;
3315 /* We should be passed a STRING_CST. */
3316 gcc_checking_assert (TREE_CODE (string) == STRING_CST);
3317 length = TREE_STRING_LENGTH (string) - 1;
3319 /* The target may have different ideas on how to construct an ObjC string
3320 literal. On Darwin / macOS, for example, we may wish to obtain a
3321 constant CFString reference instead.
3322 At present, this is only supported for the NeXT runtime. */
3323 if (flag_next_runtime
3324 && targetcm.objc_construct_string_object)
3326 tree constructor = (*targetcm.objc_construct_string_object) (string);
3327 if (constructor)
3328 return build1 (NOP_EXPR, objc_object_type, constructor);
3331 /* Check whether the string class being used actually exists and has the
3332 correct ivar layout. */
3333 if (!string_layout_checked)
3335 string_layout_checked = -1;
3336 constant_string_class = lookup_interface (constant_string_id);
3337 internal_const_str_type = objc_build_internal_const_str_type ();
3339 if (!constant_string_class
3340 || !(constant_string_type
3341 = CLASS_STATIC_TEMPLATE (constant_string_class)))
3342 error ("cannot find interface declaration for %qE",
3343 constant_string_id);
3344 /* The NSConstantString/NXConstantString ivar layout is now known. */
3345 else if (!check_string_class_template ())
3346 error ("interface %qE does not have valid constant string layout",
3347 constant_string_id);
3348 /* If the runtime can generate a literal reference to the string class,
3349 don't need to run a constructor. */
3350 else if (!(*runtime.setup_const_string_class_decl)())
3351 error ("cannot find reference tag for class %qE", constant_string_id);
3352 else
3354 string_layout_checked = 1; /* Success! */
3355 add_class_reference (constant_string_id);
3359 if (string_layout_checked == -1)
3360 return error_mark_node;
3362 /* Perhaps we already constructed a constant string just like this one? */
3363 key.literal = string;
3364 string_descriptor **loc = string_htab->find_slot (&key, INSERT);
3365 desc = *loc;
3367 if (!desc)
3369 *loc = desc = ggc_alloc<string_descriptor> ();
3370 desc->literal = string;
3371 desc->constructor =
3372 (*runtime.build_const_string_constructor) (input_location, string, length);
3375 addr = convert (build_pointer_type (constant_string_type),
3376 build_unary_op (input_location,
3377 ADDR_EXPR, desc->constructor, 1));
3379 return addr;
3382 /* Build a static constant CONSTRUCTOR with type TYPE and elements ELTS.
3383 We might be presented with a NULL for ELTS, which means 'empty ctor'
3384 which will subsequently be converted into a zero initializer in the
3385 middle end. */
3387 tree
3388 objc_build_constructor (tree type, vec<constructor_elt, va_gc> *elts)
3390 tree constructor = build_constructor (type, elts);
3392 TREE_CONSTANT (constructor) = 1;
3393 TREE_STATIC (constructor) = 1;
3394 TREE_READONLY (constructor) = 1;
3396 #ifdef OBJCPLUS
3397 /* If we know the initializer, then set the type to what C++ expects. */
3398 if (elts && !(*elts)[0].index)
3399 TREE_TYPE (constructor) = init_list_type_node;
3400 #endif
3401 return constructor;
3404 /* Return the DECL of the string IDENT in the SECTION. */
3406 tree
3407 get_objc_string_decl (tree ident, enum string_section section)
3409 tree chain;
3411 switch (section)
3413 case class_names:
3414 chain = class_names_chain;
3415 break;
3416 case meth_var_names:
3417 chain = meth_var_names_chain;
3418 break;
3419 case meth_var_types:
3420 chain = meth_var_types_chain;
3421 break;
3422 case prop_names_attr:
3423 chain = prop_names_attr_chain;
3424 break;
3425 default:
3426 gcc_unreachable ();
3429 for (; chain != 0; chain = TREE_CHAIN (chain))
3430 if (TREE_VALUE (chain) == ident)
3431 return (TREE_PURPOSE (chain));
3433 /* We didn't find the entry. */
3434 return NULL_TREE;
3437 /* Create a class reference, but don't create a variable to reference
3438 it. */
3440 void
3441 add_class_reference (tree ident)
3443 tree chain;
3445 if ((chain = cls_ref_chain))
3447 tree tail;
3450 if (ident == TREE_VALUE (chain))
3451 return;
3453 tail = chain;
3454 chain = TREE_CHAIN (chain);
3456 while (chain);
3458 /* Append to the end of the list */
3459 TREE_CHAIN (tail) = tree_cons (NULL_TREE, ident, NULL_TREE);
3461 else
3462 cls_ref_chain = tree_cons (NULL_TREE, ident, NULL_TREE);
3465 /* Get a class reference, creating it if necessary. Also create the
3466 reference variable. */
3467 tree
3468 objc_get_class_reference (tree ident)
3470 tree orig_ident = (DECL_P (ident)
3471 ? DECL_NAME (ident)
3472 : TYPE_P (ident)
3473 ? OBJC_TYPE_NAME (ident)
3474 : ident);
3475 bool local_scope = false;
3477 #ifdef OBJCPLUS
3478 if (processing_template_decl)
3479 /* Must wait until template instantiation time. */
3480 return build_min_nt_loc (UNKNOWN_LOCATION, CLASS_REFERENCE_EXPR, ident);
3481 #endif
3483 if (TREE_CODE (ident) == TYPE_DECL)
3484 ident = (DECL_ORIGINAL_TYPE (ident)
3485 ? DECL_ORIGINAL_TYPE (ident)
3486 : TREE_TYPE (ident));
3488 #ifdef OBJCPLUS
3489 if (TYPE_P (ident)
3490 && CP_TYPE_CONTEXT (ident) != global_namespace)
3491 local_scope = true;
3492 #endif
3494 if (local_scope || !(ident = objc_is_class_name (ident)))
3496 error ("%qE is not an Objective-C class name or alias",
3497 orig_ident);
3498 return error_mark_node;
3501 return (*runtime.get_class_reference) (ident);
3504 void
3505 objc_declare_alias (tree alias_ident, tree class_ident)
3507 tree underlying_class;
3509 #ifdef OBJCPLUS
3510 if (current_namespace != global_namespace) {
3511 error ("Objective-C declarations may only appear in global scope");
3513 #endif /* OBJCPLUS */
3515 if (!(underlying_class = objc_is_class_name (class_ident)))
3516 warning (0, "cannot find class %qE", class_ident);
3517 else if (objc_is_class_name (alias_ident))
3518 warning (0, "class %qE already exists", alias_ident);
3519 else
3521 /* Implement @compatibility_alias as a typedef. */
3522 #ifdef OBJCPLUS
3523 push_lang_context (lang_name_c); /* extern "C" */
3524 #endif
3525 lang_hooks.decls.pushdecl (build_decl
3526 (input_location,
3527 TYPE_DECL,
3528 alias_ident,
3529 xref_tag (RECORD_TYPE, underlying_class)));
3530 #ifdef OBJCPLUS
3531 pop_lang_context ();
3532 #endif
3533 objc_map_put (alias_name_map, alias_ident, underlying_class);
3537 void
3538 objc_declare_class (tree identifier)
3540 #ifdef OBJCPLUS
3541 if (current_namespace != global_namespace) {
3542 error ("Objective-C declarations may only appear in global scope");
3544 #endif /* OBJCPLUS */
3546 if (! objc_is_class_name (identifier))
3548 tree record = lookup_name (identifier), type = record;
3550 if (record)
3552 if (TREE_CODE (record) == TYPE_DECL)
3553 type = DECL_ORIGINAL_TYPE (record)
3554 ? DECL_ORIGINAL_TYPE (record)
3555 : TREE_TYPE (record);
3557 if (!TYPE_HAS_OBJC_INFO (type)
3558 || !TYPE_OBJC_INTERFACE (type))
3560 error ("%qE redeclared as different kind of symbol",
3561 identifier);
3562 error ("previous declaration of %q+D",
3563 record);
3567 record = xref_tag (RECORD_TYPE, identifier);
3568 INIT_TYPE_OBJC_INFO (record);
3569 /* In the case of a @class declaration, we store the ident in
3570 the TYPE_OBJC_INTERFACE. If later an @interface is found,
3571 we'll replace the ident with the interface. */
3572 TYPE_OBJC_INTERFACE (record) = identifier;
3573 objc_map_put (class_name_map, identifier, NULL_TREE);
3577 tree
3578 objc_is_class_name (tree ident)
3580 if (ident && TREE_CODE (ident) == IDENTIFIER_NODE)
3582 tree t = identifier_global_value (ident);
3583 if (t)
3584 ident = t;
3587 while (ident && TREE_CODE (ident) == TYPE_DECL && DECL_ORIGINAL_TYPE (ident))
3588 ident = OBJC_TYPE_NAME (DECL_ORIGINAL_TYPE (ident));
3590 if (ident && TREE_CODE (ident) == RECORD_TYPE)
3591 ident = OBJC_TYPE_NAME (ident);
3592 #ifdef OBJCPLUS
3593 if (ident && TREE_CODE (ident) == TYPE_DECL)
3595 tree type = TREE_TYPE (ident);
3596 if (type && TREE_CODE (type) == TEMPLATE_TYPE_PARM)
3597 return NULL_TREE;
3598 ident = DECL_NAME (ident);
3600 #endif
3601 if (!ident || TREE_CODE (ident) != IDENTIFIER_NODE)
3602 return NULL_TREE;
3604 if (lookup_interface (ident))
3605 return ident;
3608 tree target;
3610 target = objc_map_get (class_name_map, ident);
3611 if (target != OBJC_MAP_NOT_FOUND)
3612 return ident;
3614 target = objc_map_get (alias_name_map, ident);
3615 if (target != OBJC_MAP_NOT_FOUND)
3616 return target;
3619 return 0;
3622 /* Check whether TYPE is either 'id' or 'Class'. */
3624 tree
3625 objc_is_id (tree type)
3627 if (type && TREE_CODE (type) == IDENTIFIER_NODE)
3629 tree t = identifier_global_value (type);
3630 if (t)
3631 type = t;
3634 if (type && TREE_CODE (type) == TYPE_DECL)
3635 type = TREE_TYPE (type);
3637 /* NB: This function may be called before the ObjC front-end has
3638 been initialized, in which case OBJC_OBJECT_TYPE will (still) be NULL. */
3639 return (objc_object_type && type
3640 && (IS_ID (type) || IS_CLASS (type) || IS_SUPER (type))
3641 ? type
3642 : NULL_TREE);
3645 /* Check whether TYPE is either 'id', 'Class', or a pointer to an ObjC
3646 class instance. This is needed by other parts of the compiler to
3647 handle ObjC types gracefully. */
3649 tree
3650 objc_is_object_ptr (tree type)
3652 tree ret;
3654 type = TYPE_MAIN_VARIANT (type);
3655 if (!POINTER_TYPE_P (type))
3656 return 0;
3658 ret = objc_is_id (type);
3659 if (!ret)
3660 ret = objc_is_class_name (TREE_TYPE (type));
3662 return ret;
3665 static int
3666 objc_is_gcable_type (tree type, int or_strong_p)
3668 tree name;
3670 if (!TYPE_P (type))
3671 return 0;
3672 if (objc_is_id (TYPE_MAIN_VARIANT (type)))
3673 return 1;
3674 if (or_strong_p && lookup_attribute ("objc_gc", TYPE_ATTRIBUTES (type)))
3675 return 1;
3676 if (TREE_CODE (type) != POINTER_TYPE && TREE_CODE (type) != INDIRECT_REF)
3677 return 0;
3678 type = TREE_TYPE (type);
3679 if (TREE_CODE (type) != RECORD_TYPE)
3680 return 0;
3681 name = TYPE_NAME (type);
3682 return (objc_is_class_name (name) != NULL_TREE);
3685 static tree
3686 objc_substitute_decl (tree expr, tree oldexpr, tree newexpr)
3688 if (expr == oldexpr)
3689 return newexpr;
3691 switch (TREE_CODE (expr))
3693 case COMPONENT_REF:
3694 return objc_build_component_ref
3695 (objc_substitute_decl (TREE_OPERAND (expr, 0),
3696 oldexpr,
3697 newexpr),
3698 DECL_NAME (TREE_OPERAND (expr, 1)));
3699 case ARRAY_REF:
3700 return build_array_ref (input_location,
3701 objc_substitute_decl (TREE_OPERAND (expr, 0),
3702 oldexpr,
3703 newexpr),
3704 TREE_OPERAND (expr, 1));
3705 case INDIRECT_REF:
3706 return build_indirect_ref (input_location,
3707 objc_substitute_decl (TREE_OPERAND (expr, 0),
3708 oldexpr,
3709 newexpr), RO_ARROW);
3710 default:
3711 return expr;
3715 static tree
3716 objc_build_ivar_assignment (tree outervar, tree lhs, tree rhs)
3718 tree func_params;
3719 /* The LHS parameter contains the expression 'outervar->memberspec';
3720 we need to transform it into '&((typeof(outervar) *) 0)->memberspec',
3721 where memberspec may be arbitrarily complex (e.g., 'g->f.d[2].g[3]').
3723 tree offs
3724 = objc_substitute_decl
3725 (lhs, outervar, convert (TREE_TYPE (outervar), integer_zero_node));
3726 tree func
3727 = (flag_objc_direct_dispatch
3728 ? objc_assign_ivar_fast_decl
3729 : objc_assign_ivar_decl);
3731 offs = convert (integer_type_node, build_unary_op (input_location,
3732 ADDR_EXPR, offs, 0));
3733 offs = fold (offs);
3734 func_params = tree_cons (NULL_TREE,
3735 convert (objc_object_type, rhs),
3736 tree_cons (NULL_TREE, convert (objc_object_type, outervar),
3737 tree_cons (NULL_TREE, offs,
3738 NULL_TREE)));
3740 return build_function_call (input_location, func, func_params);
3743 static tree
3744 objc_build_global_assignment (tree lhs, tree rhs)
3746 tree func_params = tree_cons (NULL_TREE,
3747 convert (objc_object_type, rhs),
3748 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3749 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3750 NULL_TREE));
3752 return build_function_call (input_location,
3753 objc_assign_global_decl, func_params);
3756 static tree
3757 objc_build_strong_cast_assignment (tree lhs, tree rhs)
3759 tree func_params = tree_cons (NULL_TREE,
3760 convert (objc_object_type, rhs),
3761 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3762 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3763 NULL_TREE));
3765 return build_function_call (input_location,
3766 objc_assign_strong_cast_decl, func_params);
3769 static int
3770 objc_is_gcable_p (tree expr)
3772 return (TREE_CODE (expr) == COMPONENT_REF
3773 ? objc_is_gcable_p (TREE_OPERAND (expr, 1))
3774 : TREE_CODE (expr) == ARRAY_REF
3775 ? (objc_is_gcable_p (TREE_TYPE (expr))
3776 || objc_is_gcable_p (TREE_OPERAND (expr, 0)))
3777 : TREE_CODE (expr) == ARRAY_TYPE
3778 ? objc_is_gcable_p (TREE_TYPE (expr))
3779 : TYPE_P (expr)
3780 ? objc_is_gcable_type (expr, 1)
3781 : (objc_is_gcable_p (TREE_TYPE (expr))
3782 || (DECL_P (expr)
3783 && lookup_attribute ("objc_gc", DECL_ATTRIBUTES (expr)))));
3786 static int
3787 objc_is_ivar_reference_p (tree expr)
3789 return (TREE_CODE (expr) == ARRAY_REF
3790 ? objc_is_ivar_reference_p (TREE_OPERAND (expr, 0))
3791 : TREE_CODE (expr) == COMPONENT_REF
3792 ? TREE_CODE (TREE_OPERAND (expr, 1)) == FIELD_DECL
3793 : 0);
3796 static int
3797 objc_is_global_reference_p (tree expr)
3799 return (INDIRECT_REF_P (expr) || TREE_CODE (expr) == PLUS_EXPR
3800 ? objc_is_global_reference_p (TREE_OPERAND (expr, 0))
3801 : DECL_P (expr)
3802 ? (DECL_FILE_SCOPE_P (expr) || TREE_STATIC (expr))
3803 : 0);
3806 tree
3807 objc_generate_write_barrier (tree lhs, enum tree_code modifycode, tree rhs)
3809 tree result = NULL_TREE, outer;
3810 int strong_cast_p = 0, outer_gc_p = 0, indirect_p = 0;
3812 /* This function is currently only used with the next runtime with
3813 garbage collection enabled (-fobjc-gc). */
3814 gcc_assert (flag_next_runtime);
3816 /* See if we have any lhs casts, and strip them out. NB: The lvalue casts
3817 will have been transformed to the form '*(type *)&expr'. */
3818 if (INDIRECT_REF_P (lhs))
3820 outer = TREE_OPERAND (lhs, 0);
3822 while (!strong_cast_p
3823 && (CONVERT_EXPR_P (outer)
3824 || TREE_CODE (outer) == NON_LVALUE_EXPR))
3826 tree lhstype = TREE_TYPE (outer);
3828 /* Descend down the cast chain, and record the first objc_gc
3829 attribute found. */
3830 if (POINTER_TYPE_P (lhstype))
3832 tree attr
3833 = lookup_attribute ("objc_gc",
3834 TYPE_ATTRIBUTES (TREE_TYPE (lhstype)));
3836 if (attr)
3837 strong_cast_p = 1;
3840 outer = TREE_OPERAND (outer, 0);
3844 /* If we have a __strong cast, it trumps all else. */
3845 if (strong_cast_p)
3847 if (modifycode != NOP_EXPR)
3848 goto invalid_pointer_arithmetic;
3850 if (warn_assign_intercept)
3851 warning (0, "strong-cast assignment has been intercepted");
3853 result = objc_build_strong_cast_assignment (lhs, rhs);
3855 goto exit_point;
3858 /* the lhs must be of a suitable type, regardless of its underlying
3859 structure. */
3860 if (!objc_is_gcable_p (lhs))
3861 goto exit_point;
3863 outer = lhs;
3865 while (outer
3866 && (TREE_CODE (outer) == COMPONENT_REF
3867 || TREE_CODE (outer) == ARRAY_REF))
3868 outer = TREE_OPERAND (outer, 0);
3870 if (INDIRECT_REF_P (outer))
3872 outer = TREE_OPERAND (outer, 0);
3873 indirect_p = 1;
3876 outer_gc_p = objc_is_gcable_p (outer);
3878 /* Handle ivar assignments. */
3879 if (objc_is_ivar_reference_p (lhs))
3881 /* if the struct to the left of the ivar is not an Objective-C object (__strong
3882 doesn't cut it here), the best we can do here is suggest a cast. */
3883 if (!objc_is_gcable_type (TREE_TYPE (outer), 0))
3885 /* We may still be able to use the global write barrier... */
3886 if (!indirect_p && objc_is_global_reference_p (outer))
3887 goto global_reference;
3889 suggest_cast:
3890 if (modifycode == NOP_EXPR)
3892 if (warn_assign_intercept)
3893 warning (0, "strong-cast may possibly be needed");
3896 goto exit_point;
3899 if (modifycode != NOP_EXPR)
3900 goto invalid_pointer_arithmetic;
3902 if (warn_assign_intercept)
3903 warning (0, "instance variable assignment has been intercepted");
3905 result = objc_build_ivar_assignment (outer, lhs, rhs);
3907 goto exit_point;
3910 /* Likewise, intercept assignment to global/static variables if their type is
3911 GC-marked. */
3912 if (objc_is_global_reference_p (outer))
3914 if (indirect_p)
3915 goto suggest_cast;
3917 global_reference:
3918 if (modifycode != NOP_EXPR)
3920 invalid_pointer_arithmetic:
3921 if (outer_gc_p)
3922 warning (0, "pointer arithmetic for garbage-collected objects not allowed");
3924 goto exit_point;
3927 if (warn_assign_intercept)
3928 warning (0, "global/static variable assignment has been intercepted");
3930 result = objc_build_global_assignment (lhs, rhs);
3933 /* In all other cases, fall back to the normal mechanism. */
3934 exit_point:
3935 return result;
3938 /* Implementation of the table mapping a class name (as an identifier)
3939 to a class node. The two public functions for it are
3940 lookup_interface() and add_interface(). add_interface() is only
3941 used in this file, so we can make it static. */
3943 static GTY(()) objc_map_t interface_map;
3945 static void
3946 interface_hash_init (void)
3948 interface_map = objc_map_alloc_ggc (200);
3951 static tree
3952 add_interface (tree class_name, tree name)
3954 /* Put interfaces on list in reverse order. */
3955 TREE_CHAIN (class_name) = interface_chain;
3956 interface_chain = class_name;
3958 /* Add it to the map. */
3959 objc_map_put (interface_map, name, class_name);
3961 return interface_chain;
3964 tree
3965 lookup_interface (tree ident)
3967 #ifdef OBJCPLUS
3968 if (ident && TREE_CODE (ident) == TYPE_DECL)
3969 ident = DECL_NAME (ident);
3970 #endif
3972 if (ident == NULL_TREE || TREE_CODE (ident) != IDENTIFIER_NODE)
3973 return NULL_TREE;
3976 tree interface = objc_map_get (interface_map, ident);
3978 if (interface == OBJC_MAP_NOT_FOUND)
3979 return NULL_TREE;
3980 else
3981 return interface;
3987 /* Implement @defs (<classname>) within struct bodies. */
3989 tree
3990 objc_get_class_ivars (tree class_name)
3992 tree interface = lookup_interface (class_name);
3994 if (interface)
3995 return get_class_ivars (interface, true);
3997 error ("cannot find interface declaration for %qE",
3998 class_name);
4000 return error_mark_node;
4004 /* Functions used by the hashtable for field duplicates in
4005 objc_detect_field_duplicates(). Ideally, we'd use a standard
4006 key-value dictionary hashtable , and store as keys the field names,
4007 and as values the actual declarations (used to print nice error
4008 messages with the locations). But, the hashtable we are using only
4009 allows us to store keys in the hashtable, without values (it looks
4010 more like a set). So, we store the DECLs, but define equality as
4011 DECLs having the same name, and hash as the hash of the name. */
4013 struct decl_name_hash : nofree_ptr_hash <tree_node>
4015 static inline hashval_t hash (const tree_node *);
4016 static inline bool equal (const tree_node *, const tree_node *);
4019 inline hashval_t
4020 decl_name_hash::hash (const tree_node *q)
4022 return (hashval_t) ((intptr_t)(DECL_NAME (q)) >> 3);
4025 inline bool
4026 decl_name_hash::equal (const tree_node *a, const tree_node *b)
4028 return DECL_NAME (a) == DECL_NAME (b);
4031 /* Called when checking the variables in a struct. If we are not
4032 doing the ivars list inside an @interface context, then return
4033 false. Else, perform the check for duplicate ivars, then return
4034 true. The check for duplicates checks if an instance variable with
4035 the same name exists in the class or in a superclass. If
4036 'check_superclasses_only' is set to true, then it is assumed that
4037 checks for instance variables in the same class has already been
4038 performed (this is the case for ObjC++) and only the instance
4039 variables of superclasses are checked. */
4040 bool
4041 objc_detect_field_duplicates (bool check_superclasses_only)
4043 if (!objc_collecting_ivars || !objc_interface_context
4044 || TREE_CODE (objc_interface_context) != CLASS_INTERFACE_TYPE)
4045 return false;
4047 /* We have two ways of doing this check:
4049 "direct comparison": we iterate over the instance variables and
4050 compare them directly. This works great for small numbers of
4051 instance variables (such as 10 or 20), which are extremely common.
4052 But it will potentially take forever for the pathological case with
4053 a huge number (eg, 10k) of instance variables.
4055 "hashtable": we use a hashtable, which requires a single sweep
4056 through the list of instances variables. This is much slower for a
4057 small number of variables, and we only use it for large numbers.
4059 To decide which one to use, we need to get an idea of how many
4060 instance variables we have to compare. */
4062 unsigned int number_of_ivars_to_check = 0;
4064 tree ivar;
4065 for (ivar = CLASS_RAW_IVARS (objc_interface_context);
4066 ivar; ivar = DECL_CHAIN (ivar))
4068 /* Ignore anonymous ivars. */
4069 if (DECL_NAME (ivar))
4070 number_of_ivars_to_check++;
4074 /* Exit if there is nothing to do. */
4075 if (number_of_ivars_to_check == 0)
4076 return true;
4078 /* In case that there are only 1 or 2 instance variables to check,
4079 we always use direct comparison. If there are more, it is
4080 worth iterating over the instance variables in the superclass
4081 to count how many there are (note that this has the same cost
4082 as checking 1 instance variable by direct comparison, which is
4083 why we skip this check in the case of 1 or 2 ivars and just do
4084 the direct comparison) and then decide if it worth using a
4085 hashtable. */
4086 if (number_of_ivars_to_check > 2)
4088 unsigned int number_of_superclass_ivars = 0;
4090 tree interface;
4091 for (interface = lookup_interface (CLASS_SUPER_NAME (objc_interface_context));
4092 interface; interface = lookup_interface (CLASS_SUPER_NAME (interface)))
4094 tree ivar;
4095 for (ivar = CLASS_RAW_IVARS (interface);
4096 ivar; ivar = DECL_CHAIN (ivar))
4097 number_of_superclass_ivars++;
4101 /* We use a hashtable if we have over 10k comparisons. */
4102 if (number_of_ivars_to_check * (number_of_superclass_ivars
4103 + (number_of_ivars_to_check / 2))
4104 > 10000)
4106 /* First, build the hashtable by putting all the instance
4107 variables of superclasses in it. */
4108 hash_table<decl_name_hash> htab (37);
4109 tree interface;
4110 for (interface = lookup_interface (CLASS_SUPER_NAME
4111 (objc_interface_context));
4112 interface; interface = lookup_interface
4113 (CLASS_SUPER_NAME (interface)))
4115 tree ivar;
4116 for (ivar = CLASS_RAW_IVARS (interface); ivar;
4117 ivar = DECL_CHAIN (ivar))
4119 if (DECL_NAME (ivar) != NULL_TREE)
4121 tree_node **slot = htab.find_slot (ivar, INSERT);
4122 /* Do not check for duplicate instance
4123 variables in superclasses. Errors have
4124 already been generated. */
4125 *slot = ivar;
4130 /* Now, we go through all the instance variables in the
4131 class, and check that they are not in the
4132 hashtable. */
4133 if (check_superclasses_only)
4135 tree ivar;
4136 for (ivar = CLASS_RAW_IVARS (objc_interface_context); ivar;
4137 ivar = DECL_CHAIN (ivar))
4139 if (DECL_NAME (ivar) != NULL_TREE)
4141 tree duplicate_ivar = htab.find (ivar);
4142 if (duplicate_ivar != HTAB_EMPTY_ENTRY)
4144 error_at (DECL_SOURCE_LOCATION (ivar),
4145 "duplicate instance variable %q+D",
4146 ivar);
4147 inform (DECL_SOURCE_LOCATION (duplicate_ivar),
4148 "previous declaration of %q+D",
4149 duplicate_ivar);
4150 /* FIXME: Do we need the following ? */
4151 /* DECL_NAME (ivar) = NULL_TREE; */
4156 else
4158 /* If we're checking for duplicates in the class as
4159 well, we insert variables in the hashtable as we
4160 check them, so if a duplicate follows, it will be
4161 caught. */
4162 tree ivar;
4163 for (ivar = CLASS_RAW_IVARS (objc_interface_context); ivar;
4164 ivar = DECL_CHAIN (ivar))
4166 if (DECL_NAME (ivar) != NULL_TREE)
4168 tree_node **slot = htab.find_slot (ivar, INSERT);
4169 if (*slot)
4171 tree duplicate_ivar = (tree)(*slot);
4172 error_at (DECL_SOURCE_LOCATION (ivar),
4173 "duplicate instance variable %q+D",
4174 ivar);
4175 inform (DECL_SOURCE_LOCATION (duplicate_ivar),
4176 "previous declaration of %q+D",
4177 duplicate_ivar);
4178 /* FIXME: Do we need the following ? */
4179 /* DECL_NAME (ivar) = NULL_TREE; */
4181 *slot = ivar;
4185 return true;
4190 /* This is the "direct comparison" approach, which is used in most
4191 non-pathological cases. */
4193 /* Walk up to class hierarchy, starting with this class (this is
4194 the external loop, because lookup_interface() is expensive, and
4195 we want to do it few times). */
4196 tree interface = objc_interface_context;
4198 if (check_superclasses_only)
4199 interface = lookup_interface (CLASS_SUPER_NAME (interface));
4201 for ( ; interface; interface = lookup_interface
4202 (CLASS_SUPER_NAME (interface)))
4204 tree ivar_being_checked;
4206 for (ivar_being_checked = CLASS_RAW_IVARS (objc_interface_context);
4207 ivar_being_checked;
4208 ivar_being_checked = DECL_CHAIN (ivar_being_checked))
4210 tree decl;
4212 /* Ignore anonymous ivars. */
4213 if (DECL_NAME (ivar_being_checked) == NULL_TREE)
4214 continue;
4216 /* Note how we stop when we find the ivar we are checking
4217 (this can only happen in the main class, not
4218 superclasses), to avoid comparing things twice
4219 (otherwise, for each ivar, you'd compare A to B then B
4220 to A, and get duplicated error messages). */
4221 for (decl = CLASS_RAW_IVARS (interface);
4222 decl && decl != ivar_being_checked;
4223 decl = DECL_CHAIN (decl))
4225 if (DECL_NAME (ivar_being_checked) == DECL_NAME (decl))
4227 error_at (DECL_SOURCE_LOCATION (ivar_being_checked),
4228 "duplicate instance variable %q+D",
4229 ivar_being_checked);
4230 inform (DECL_SOURCE_LOCATION (decl),
4231 "previous declaration of %q+D",
4232 decl);
4233 /* FIXME: Do we need the following ? */
4234 /* DECL_NAME (ivar_being_checked) = NULL_TREE; */
4240 return true;
4243 /* Used by: build_private_template, continue_class,
4244 and for @defs constructs. */
4246 static tree
4247 get_class_ivars (tree interface, bool inherited)
4249 tree ivar_chain = copy_list (CLASS_RAW_IVARS (interface));
4251 /* Both CLASS_RAW_IVARS and CLASS_IVARS contain a list of ivars declared
4252 by the current class (i.e., they do not include super-class ivars).
4253 However, the CLASS_IVARS list will be side-effected by a call to
4254 finish_struct(), which will fill in field offsets. */
4255 if (!CLASS_IVARS (interface))
4256 CLASS_IVARS (interface) = ivar_chain;
4258 if (!inherited)
4259 return ivar_chain;
4261 while (CLASS_SUPER_NAME (interface))
4263 /* Prepend super-class ivars. */
4264 interface = lookup_interface (CLASS_SUPER_NAME (interface));
4265 ivar_chain = chainon (copy_list (CLASS_RAW_IVARS (interface)),
4266 ivar_chain);
4269 return ivar_chain;
4272 void
4273 objc_maybe_warn_exceptions (location_t loc)
4275 /* -fobjc-exceptions is required to enable Objective-C exceptions.
4276 For example, on Darwin, ObjC exceptions require a sufficiently
4277 recent version of the runtime, so the user must ask for them
4278 explicitly. On other platforms, at the moment -fobjc-exceptions
4279 triggers -fexceptions which again is required for exceptions to
4280 work. */
4281 if (!flag_objc_exceptions)
4283 /* Warn only once per compilation unit. */
4284 static bool warned = false;
4286 if (!warned)
4288 error_at (loc, "%<-fobjc-exceptions%> is required to enable Objective-C exception syntax");
4289 warned = true;
4294 static struct objc_try_context *cur_try_context;
4296 /* Called just after parsing the @try and its associated BODY. We now
4297 must prepare for the tricky bits -- handling the catches and finally. */
4299 void
4300 objc_begin_try_stmt (location_t try_locus, tree body)
4302 struct objc_try_context *c = XCNEW (struct objc_try_context);
4303 c->outer = cur_try_context;
4304 c->try_body = body;
4305 c->try_locus = try_locus;
4306 c->end_try_locus = input_location;
4307 cur_try_context = c;
4309 /* Collect the list of local variables. We'll mark them as volatile
4310 at the end of compilation of this function to prevent them being
4311 clobbered by setjmp/longjmp. */
4312 if (flag_objc_sjlj_exceptions)
4313 objc_mark_locals_volatile (NULL);
4316 /* Called just after parsing "@catch (parm)". Open a binding level,
4317 enter DECL into the binding level, and initialize it. Leave the
4318 binding level open while the body of the compound statement is
4319 parsed. If DECL is NULL_TREE, then we are compiling "@catch(...)"
4320 which we compile as "@catch(id tmp_variable)". */
4322 void
4323 objc_begin_catch_clause (tree decl)
4325 tree compound, type, t;
4326 bool ellipsis = false;
4328 /* Begin a new scope that the entire catch clause will live in. */
4329 compound = c_begin_compound_stmt (true);
4331 /* Create the appropriate declaration for the argument. */
4332 if (decl == error_mark_node)
4333 type = error_mark_node;
4334 else
4336 if (decl == NULL_TREE)
4338 /* If @catch(...) was specified, create a temporary variable of
4339 type 'id' and use it. */
4340 decl = objc_create_temporary_var (objc_object_type, "__objc_generic_catch_var");
4341 DECL_SOURCE_LOCATION (decl) = input_location;
4342 /* ... but allow the runtime to differentiate between ellipsis and the
4343 case of @catch (id xyz). */
4344 ellipsis = true;
4346 else
4348 /* The parser passed in a PARM_DECL, but what we really want is a VAR_DECL. */
4349 decl = build_decl (input_location,
4350 VAR_DECL, DECL_NAME (decl), TREE_TYPE (decl));
4352 lang_hooks.decls.pushdecl (decl);
4354 /* Mark the declaration as used so you never any warnings whether
4355 you use the exception argument or not. TODO: Implement a
4356 -Wunused-exception-parameter flag, which would cause warnings
4357 if exception parameter is not used. */
4358 TREE_USED (decl) = 1;
4359 DECL_READ_P (decl) = 1;
4361 type = TREE_TYPE (decl);
4364 /* Verify that the type of the catch is valid. It must be a pointer
4365 to an Objective-C class, or "id" (which is catch-all). */
4366 if (type == error_mark_node)
4368 ;/* Just keep going. */
4370 else if (!objc_type_valid_for_messaging (type, false))
4372 error ("%<@catch%> parameter is not a known Objective-C class type");
4373 type = error_mark_node;
4375 else if (TYPE_HAS_OBJC_INFO (TREE_TYPE (type))
4376 && TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (type)))
4378 error ("%<@catch%> parameter cannot be protocol-qualified");
4379 type = error_mark_node;
4381 else if (POINTER_TYPE_P (type) && objc_is_object_id (TREE_TYPE (type)))
4382 /* @catch (id xyz) or @catch (...) but we note this for runtimes that
4383 identify 'id'. */
4385 else
4387 /* If 'type' was built using typedefs, we need to get rid of
4388 them and get a simple pointer to the class. */
4389 bool is_typedef = false;
4390 tree x = TYPE_MAIN_VARIANT (type);
4392 /* Skip from the pointer to the pointee. */
4393 if (TREE_CODE (x) == POINTER_TYPE)
4394 x = TREE_TYPE (x);
4396 /* Traverse typedef aliases */
4397 while (TREE_CODE (x) == RECORD_TYPE && OBJC_TYPE_NAME (x)
4398 && TREE_CODE (OBJC_TYPE_NAME (x)) == TYPE_DECL
4399 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (x)))
4401 is_typedef = true;
4402 x = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (x));
4405 /* If it was a typedef, build a pointer to the final, original
4406 class. */
4407 if (is_typedef)
4408 type = build_pointer_type (x);
4410 if (cur_try_context->catch_list)
4412 /* Examine previous @catch clauses and see if we've already
4413 caught the type in question. */
4414 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
4415 for (; !tsi_end_p (i); tsi_next (&i))
4417 tree stmt = tsi_stmt (i);
4418 t = CATCH_TYPES (stmt);
4419 if (t == error_mark_node)
4420 continue;
4421 if (!t || DERIVED_FROM_P (TREE_TYPE (t), TREE_TYPE (type)))
4423 warning (0, "exception of type %<%T%> will be caught",
4424 TREE_TYPE (type));
4425 warning_at (EXPR_LOCATION (stmt), 0, " by earlier handler for %<%T%>",
4426 TREE_TYPE (t ? t : objc_object_type));
4427 break;
4433 t = (*runtime.begin_catch) (&cur_try_context, type, decl, compound, ellipsis);
4434 add_stmt (t);
4437 /* Called just after parsing the closing brace of a @catch clause. Close
4438 the open binding level, and record a CATCH_EXPR for it. */
4440 void
4441 objc_finish_catch_clause (void)
4443 tree c = cur_try_context->current_catch;
4444 cur_try_context->current_catch = NULL;
4445 cur_try_context->end_catch_locus = input_location;
4447 CATCH_BODY (c) = c_end_compound_stmt (input_location, CATCH_BODY (c), 1);
4449 (*runtime.finish_catch) (&cur_try_context, c);
4452 /* Called after parsing a @finally clause and its associated BODY.
4453 Record the body for later placement. */
4455 void
4456 objc_build_finally_clause (location_t finally_locus, tree body)
4458 cur_try_context->finally_body = body;
4459 cur_try_context->finally_locus = finally_locus;
4460 cur_try_context->end_finally_locus = input_location;
4463 /* Called to finalize a @try construct. */
4465 tree
4466 objc_finish_try_stmt (void)
4468 struct objc_try_context *c = cur_try_context;
4469 tree stmt;
4471 if (c->catch_list == NULL && c->finally_body == NULL)
4472 error ("%<@try%> without %<@catch%> or %<@finally%>");
4474 stmt = (*runtime.finish_try_stmt) (&cur_try_context);
4475 add_stmt (stmt);
4477 cur_try_context = c->outer;
4478 free (c);
4479 return stmt;
4482 tree
4483 objc_build_throw_stmt (location_t loc, tree throw_expr)
4485 bool rethrown = false;
4487 objc_maybe_warn_exceptions (loc);
4489 /* Don't waste time trying to build something if we're already dead. */
4490 if (throw_expr == error_mark_node)
4491 return error_mark_node;
4493 if (throw_expr == NULL)
4495 /* If we're not inside a @catch block, there is no "current
4496 exception" to be rethrown. */
4497 if (cur_try_context == NULL
4498 || cur_try_context->current_catch == NULL)
4500 error_at (loc,
4501 "%<@throw%> (rethrow) used outside of a %<@catch%> block");
4502 return error_mark_node;
4505 /* Otherwise the object is still sitting in the EXC_PTR_EXPR
4506 value that we get from the runtime. */
4507 throw_expr = (*runtime.build_exc_ptr) (&cur_try_context);
4508 rethrown = true;
4510 else
4512 if (!objc_type_valid_for_messaging (TREE_TYPE (throw_expr), true))
4514 error_at (loc, "%<@throw%> argument is not an object");
4515 return error_mark_node;
4519 return (*runtime.build_throw_stmt) (loc, throw_expr, rethrown);
4522 tree
4523 objc_build_synchronized (location_t start_locus, tree object_expr, tree body)
4525 /* object_expr should never be NULL; but in case it is, convert it to
4526 error_mark_node. */
4527 if (object_expr == NULL)
4528 object_expr = error_mark_node;
4530 /* Validate object_expr. If not valid, set it to error_mark_node. */
4531 if (object_expr != error_mark_node)
4533 if (!objc_type_valid_for_messaging (TREE_TYPE (object_expr), true))
4535 error_at (start_locus, "%<@synchronized%> argument is not an object");
4536 object_expr = error_mark_node;
4540 if (object_expr == error_mark_node)
4542 /* If we found an error, we simply ignore the '@synchronized'.
4543 Compile the body so we can keep going with minimal
4544 casualties. */
4545 return add_stmt (body);
4547 else
4549 tree call;
4550 tree args;
4552 /* objc_sync_enter (object_expr); */
4553 object_expr = save_expr (object_expr);
4554 args = tree_cons (NULL, object_expr, NULL);
4555 call = build_function_call (input_location,
4556 objc_sync_enter_decl, args);
4557 SET_EXPR_LOCATION (call, start_locus);
4558 add_stmt (call);
4560 /* Build "objc_sync_exit (object_expr);" but do not add it yet;
4561 it goes inside the @finalize() clause. */
4562 args = tree_cons (NULL, object_expr, NULL);
4563 call = build_function_call (input_location,
4564 objc_sync_exit_decl, args);
4565 SET_EXPR_LOCATION (call, input_location);
4567 /* @try { body; } */
4568 objc_begin_try_stmt (start_locus, body);
4570 /* @finally { objc_sync_exit (object_expr); } */
4571 objc_build_finally_clause (input_location, call);
4573 /* End of try statement. */
4574 return objc_finish_try_stmt ();
4578 /* Construct a C struct corresponding to ObjC class CLASS, with the same
4579 name as the class:
4581 struct <classname> {
4582 struct _objc_class *isa;
4584 }; */
4586 static void
4587 build_private_template (tree klass)
4589 if (!CLASS_STATIC_TEMPLATE (klass))
4591 tree record = objc_build_struct (klass,
4592 get_class_ivars (klass, false),
4593 CLASS_SUPER_NAME (klass));
4595 /* Set the TREE_USED bit for this struct, so that stab generator
4596 can emit stabs for this struct type. */
4597 if (flag_debug_only_used_symbols && TYPE_STUB_DECL (record))
4598 TREE_USED (TYPE_STUB_DECL (record)) = 1;
4600 /* Copy the attributes from the class to the type. */
4601 if (TREE_DEPRECATED (klass))
4602 TREE_DEPRECATED (record) = 1;
4603 if (TREE_UNAVAILABLE (klass))
4604 TREE_UNAVAILABLE (record) = 1;
4608 /* Generate either '- .cxx_construct' or '- .cxx_destruct' for the
4609 current class. */
4610 #ifdef OBJCPLUS
4611 static void
4612 objc_generate_cxx_ctor_or_dtor (bool dtor)
4614 tree fn, body, compound_stmt, ivar;
4616 /* - (id) .cxx_construct { ... return self; } */
4617 /* - (void) .cxx_construct { ... } */
4619 objc_start_method_definition
4620 (false /* is_class_method */,
4621 objc_build_method_signature (false /* is_class_method */,
4622 build_tree_list (NULL_TREE,
4623 dtor
4624 ? void_type_node
4625 : objc_object_type),
4626 get_identifier (dtor
4627 ? TAG_CXX_DESTRUCT
4628 : TAG_CXX_CONSTRUCT),
4629 make_node (TREE_LIST),
4630 false), NULL, NULL_TREE);
4631 body = begin_function_body ();
4632 compound_stmt = begin_compound_stmt (0);
4634 ivar = CLASS_IVARS (implementation_template);
4635 /* Destroy ivars in reverse order. */
4636 if (dtor)
4637 ivar = nreverse (copy_list (ivar));
4639 for (; ivar; ivar = TREE_CHAIN (ivar))
4641 if (TREE_CODE (ivar) == FIELD_DECL)
4643 tree type = TREE_TYPE (ivar);
4645 /* Call the ivar's default constructor or destructor. Do not
4646 call the destructor unless a corresponding constructor call
4647 has also been made (or is not needed). */
4648 if (MAYBE_CLASS_TYPE_P (type)
4649 && (dtor
4650 ? (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4651 && (!TYPE_NEEDS_CONSTRUCTING (type)
4652 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4653 : (TYPE_NEEDS_CONSTRUCTING (type)
4654 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))))
4655 finish_expr_stmt
4656 (build_special_member_call
4657 (build_ivar_reference (DECL_NAME (ivar)),
4658 dtor ? complete_dtor_identifier : complete_ctor_identifier,
4659 NULL, type, LOOKUP_NORMAL, tf_warning_or_error));
4663 /* The constructor returns 'self'. */
4664 if (!dtor)
4665 finish_return_stmt (self_decl);
4667 finish_compound_stmt (compound_stmt);
4668 finish_function_body (body);
4669 fn = current_function_decl;
4670 finish_function ();
4671 objc_finish_method_definition (fn);
4674 /* The following routine will examine the current @interface for any
4675 non-POD C++ ivars requiring non-trivial construction and/or
4676 destruction, and then synthesize special '- .cxx_construct' and/or
4677 '- .cxx_destruct' methods which will run the appropriate
4678 construction or destruction code. Note that ivars inherited from
4679 super-classes are _not_ considered. */
4680 static void
4681 objc_generate_cxx_cdtors (void)
4683 bool need_ctor = false, need_dtor = false;
4684 tree ivar;
4686 /* Error case, due to possibly an extra @end. */
4687 if (!objc_implementation_context)
4688 return;
4690 /* We do not want to do this for categories, since they do not have
4691 their own ivars. */
4693 if (TREE_CODE (objc_implementation_context) != CLASS_IMPLEMENTATION_TYPE)
4694 return;
4696 /* First, determine if we even need a constructor and/or destructor. */
4698 for (ivar = CLASS_IVARS (implementation_template); ivar;
4699 ivar = TREE_CHAIN (ivar))
4701 if (TREE_CODE (ivar) == FIELD_DECL)
4703 tree type = TREE_TYPE (ivar);
4705 if (MAYBE_CLASS_TYPE_P (type))
4707 if (TYPE_NEEDS_CONSTRUCTING (type)
4708 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
4709 /* NB: If a default constructor is not available, we will not
4710 be able to initialize this ivar; the add_instance_variable()
4711 routine will already have warned about this. */
4712 need_ctor = true;
4714 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4715 && (!TYPE_NEEDS_CONSTRUCTING (type)
4716 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4717 /* NB: If a default constructor is not available, we will not
4718 call the destructor either, for symmetry. */
4719 need_dtor = true;
4724 /* Generate '- .cxx_construct' if needed. */
4726 if (need_ctor)
4727 objc_generate_cxx_ctor_or_dtor (false);
4729 /* Generate '- .cxx_destruct' if needed. */
4731 if (need_dtor)
4732 objc_generate_cxx_ctor_or_dtor (true);
4734 /* The 'imp_list' variable points at an imp_entry record for the current
4735 @implementation. Record the existence of '- .cxx_construct' and/or
4736 '- .cxx_destruct' methods therein; it will be included in the
4737 metadata for the class if the runtime needs it. */
4738 imp_list->has_cxx_cdtors = (need_ctor || need_dtor);
4740 #endif
4742 static void
4743 error_with_ivar (const char *message, tree decl)
4745 error_at (DECL_SOURCE_LOCATION (decl), "%s %qs",
4746 message, identifier_to_locale (gen_declaration (decl)));
4750 static void
4751 check_ivars (tree inter, tree imp)
4753 tree intdecls = CLASS_RAW_IVARS (inter);
4754 tree impdecls = CLASS_RAW_IVARS (imp);
4756 while (1)
4758 tree t1, t2;
4760 #ifdef OBJCPLUS
4761 if (intdecls && TREE_CODE (intdecls) == TYPE_DECL)
4762 intdecls = TREE_CHAIN (intdecls);
4763 #endif
4764 if (intdecls == 0 && impdecls == 0)
4765 break;
4766 if (intdecls == 0 || impdecls == 0)
4768 error ("inconsistent instance variable specification");
4769 break;
4772 t1 = TREE_TYPE (intdecls); t2 = TREE_TYPE (impdecls);
4774 if (!comptypes (t1, t2)
4775 #ifdef OBJCPLUS
4776 || !tree_int_cst_equal (DECL_BIT_FIELD_REPRESENTATIVE (intdecls),
4777 DECL_BIT_FIELD_REPRESENTATIVE (impdecls))
4778 #else
4779 || !tree_int_cst_equal (DECL_INITIAL (intdecls),
4780 DECL_INITIAL (impdecls))
4781 #endif
4784 if (DECL_NAME (intdecls) == DECL_NAME (impdecls))
4786 error_with_ivar ("conflicting instance variable type",
4787 impdecls);
4788 error_with_ivar ("previous declaration of",
4789 intdecls);
4791 else /* both the type and the name don't match */
4793 error ("inconsistent instance variable specification");
4794 break;
4798 else if (DECL_NAME (intdecls) != DECL_NAME (impdecls))
4800 error_with_ivar ("conflicting instance variable name",
4801 impdecls);
4802 error_with_ivar ("previous declaration of",
4803 intdecls);
4806 intdecls = DECL_CHAIN (intdecls);
4807 impdecls = DECL_CHAIN (impdecls);
4812 static void
4813 mark_referenced_methods (void)
4815 struct imp_entry *impent;
4816 tree chain;
4818 for (impent = imp_list; impent; impent = impent->next)
4820 chain = CLASS_CLS_METHODS (impent->imp_context);
4821 while (chain)
4823 cgraph_node::get_create (METHOD_DEFINITION (chain))->mark_force_output ();
4824 chain = DECL_CHAIN (chain);
4827 chain = CLASS_NST_METHODS (impent->imp_context);
4828 while (chain)
4830 cgraph_node::get_create (METHOD_DEFINITION (chain))->mark_force_output ();
4831 chain = DECL_CHAIN (chain);
4836 /* If type is empty or only type qualifiers are present, add default
4837 type of id (otherwise grokdeclarator will default to int). */
4838 static inline tree
4839 adjust_type_for_id_default (tree type)
4841 if (!type)
4842 type = make_node (TREE_LIST);
4844 if (!TREE_VALUE (type))
4845 TREE_VALUE (type) = objc_object_type;
4846 else if (TREE_CODE (TREE_VALUE (type)) == RECORD_TYPE
4847 && TYPED_OBJECT (TREE_VALUE (type)))
4848 error ("cannot use an object as parameter to a method");
4850 return type;
4853 /* Return a KEYWORD_DECL built using the specified key_name, arg_type,
4854 arg_name and attributes. (TODO: Rename KEYWORD_DECL to
4855 OBJC_METHOD_PARM_DECL ?)
4857 A KEYWORD_DECL is a tree representing the declaration of a
4858 parameter of an Objective-C method. It is produced when parsing a
4859 fragment of Objective-C method declaration of the form
4861 keyworddecl:
4862 selector ':' '(' typename ')' identifier
4864 For example, take the Objective-C method
4866 -(NSString *)pathForResource:(NSString *)resource ofType:(NSString *)type;
4868 the two fragments "pathForResource:(NSString *)resource" and
4869 "ofType:(NSString *)type" will generate a KEYWORD_DECL each. The
4870 KEYWORD_DECL stores the 'key_name' (eg, identifier for
4871 "pathForResource"), the 'arg_type' (eg, tree representing a
4872 NSString *), the 'arg_name' (eg identifier for "resource") and
4873 potentially some attributes (for example, a tree representing
4874 __attribute__ ((unused)) if such an attribute was attached to a
4875 certain parameter). You can access this information using the
4876 TREE_TYPE (for arg_type), KEYWORD_ARG_NAME (for arg_name),
4877 KEYWORD_KEY_NAME (for key_name), DECL_ATTRIBUTES (for attributes).
4879 'key_name' is an identifier node (and is optional as you can omit
4880 it in Objective-C methods).
4881 'arg_type' is a tree list (and is optional too if no parameter type
4882 was specified).
4883 'arg_name' is an identifier node and is required.
4884 'attributes' is an optional tree containing parameter attributes. */
4885 tree
4886 objc_build_keyword_decl (tree key_name, tree arg_type,
4887 tree arg_name, tree attributes)
4889 tree keyword_decl;
4891 if (flag_objc1_only && attributes)
4892 error_at (input_location, "method argument attributes are not available in Objective-C 1.0");
4894 /* If no type is specified, default to "id". */
4895 arg_type = adjust_type_for_id_default (arg_type);
4897 keyword_decl = make_node (KEYWORD_DECL);
4899 TREE_TYPE (keyword_decl) = arg_type;
4900 KEYWORD_ARG_NAME (keyword_decl) = arg_name;
4901 KEYWORD_KEY_NAME (keyword_decl) = key_name;
4902 DECL_ATTRIBUTES (keyword_decl) = attributes;
4904 return keyword_decl;
4907 /* Given a chain of keyword_decl's, synthesize the full keyword selector. */
4908 static tree
4909 build_keyword_selector (tree selector)
4911 int len = 0;
4912 tree key_chain, key_name;
4913 char *buf;
4915 /* Scan the selector to see how much space we'll need. */
4916 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
4918 switch (TREE_CODE (selector))
4920 case KEYWORD_DECL:
4921 key_name = KEYWORD_KEY_NAME (key_chain);
4922 break;
4923 case TREE_LIST:
4924 key_name = TREE_PURPOSE (key_chain);
4925 break;
4926 default:
4927 gcc_unreachable ();
4930 if (key_name)
4931 len += IDENTIFIER_LENGTH (key_name) + 1;
4932 else
4933 /* Just a ':' arg. */
4934 len++;
4937 buf = (char *) alloca (len + 1);
4938 /* Start the buffer out as an empty string. */
4939 buf[0] = '\0';
4941 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
4943 switch (TREE_CODE (selector))
4945 case KEYWORD_DECL:
4946 key_name = KEYWORD_KEY_NAME (key_chain);
4947 break;
4948 case TREE_LIST:
4949 key_name = TREE_PURPOSE (key_chain);
4950 /* The keyword decl chain will later be used as a function
4951 argument chain. Unhook the selector itself so as to not
4952 confuse other parts of the compiler. */
4953 TREE_PURPOSE (key_chain) = NULL_TREE;
4954 break;
4955 default:
4956 gcc_unreachable ();
4959 if (key_name)
4960 strcat (buf, IDENTIFIER_POINTER (key_name));
4961 strcat (buf, ":");
4964 return get_identifier_with_length (buf, len);
4967 /* Used for declarations and definitions. */
4969 static tree
4970 build_method_decl (enum tree_code code, tree ret_type, tree selector,
4971 tree add_args, bool ellipsis)
4973 tree method_decl;
4975 /* If no type is specified, default to "id". */
4976 ret_type = adjust_type_for_id_default (ret_type);
4978 /* Note how a method_decl has a TREE_TYPE which is not the function
4979 type of the function implementing the method, but only the return
4980 type of the method. We may want to change this, and store the
4981 entire function type in there (eg, it may be used to simplify
4982 dealing with attributes below). */
4983 method_decl = make_node (code);
4984 TREE_TYPE (method_decl) = ret_type;
4986 /* If we have a keyword selector, create an identifier_node that
4987 represents the full selector name (`:' included)... */
4988 if (TREE_CODE (selector) == KEYWORD_DECL)
4990 METHOD_SEL_NAME (method_decl) = build_keyword_selector (selector);
4991 METHOD_SEL_ARGS (method_decl) = selector;
4992 METHOD_ADD_ARGS (method_decl) = add_args;
4993 METHOD_ADD_ARGS_ELLIPSIS_P (method_decl) = ellipsis;
4995 else
4997 METHOD_SEL_NAME (method_decl) = selector;
4998 METHOD_SEL_ARGS (method_decl) = NULL_TREE;
4999 METHOD_ADD_ARGS (method_decl) = NULL_TREE;
5002 return method_decl;
5005 /* This routine processes objective-c method attributes. */
5007 static void
5008 objc_decl_method_attributes (tree *node, tree attributes, int flags)
5010 /* TODO: Replace the hackery below. An idea would be to store the
5011 full function type in the method declaration (for example in
5012 TREE_TYPE) and then expose ObjC method declarations to c-family
5013 and they could deal with them by simply treating them as
5014 functions. */
5016 /* Because of the dangers in the hackery below, we filter out any
5017 attribute that we do not know about. For the ones we know about,
5018 we know that they work with the hackery. For the other ones,
5019 there is no guarantee, so we have to filter them out. */
5020 tree filtered_attributes = NULL_TREE;
5022 if (attributes)
5024 tree attribute;
5025 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
5027 tree name = TREE_PURPOSE (attribute);
5029 if (is_attribute_p ("deprecated", name)
5030 || is_attribute_p ("unavailable", name)
5031 || is_attribute_p ("sentinel", name)
5032 || is_attribute_p ("noreturn", name))
5034 /* An attribute that we support; add it to the filtered
5035 attributes. */
5036 filtered_attributes = chainon (filtered_attributes,
5037 copy_node (attribute));
5039 else if (is_attribute_p ("format", name))
5041 /* "format" is special because before adding it to the
5042 filtered attributes we need to adjust the specified
5043 format by adding the hidden function parameters for
5044 an Objective-C method (self, _cmd). */
5045 tree new_attribute = copy_node (attribute);
5047 /* Check the arguments specified with the attribute, and
5048 modify them adding 2 for the two hidden arguments.
5049 Note how this differs from C++; according to the
5050 specs, C++ does not do it so you have to add the +1
5051 yourself. For Objective-C, instead, the compiler
5052 adds the +2 for you. */
5054 /* The attribute arguments have not been checked yet, so
5055 we need to be careful as they could be missing or
5056 invalid. If anything looks wrong, we skip the
5057 process and the compiler will complain about it later
5058 when it validates the attribute. */
5059 /* Check that we have at least three arguments. */
5060 if (TREE_VALUE (new_attribute)
5061 && TREE_CHAIN (TREE_VALUE (new_attribute))
5062 && TREE_CHAIN (TREE_CHAIN (TREE_VALUE (new_attribute))))
5064 tree second_argument = TREE_CHAIN (TREE_VALUE (new_attribute));
5065 tree third_argument = TREE_CHAIN (second_argument);
5066 tree number;
5068 /* This is the second argument, the "string-index",
5069 which specifies the index of the format string
5070 argument. Add 2. */
5071 number = TREE_VALUE (second_argument);
5072 if (number
5073 && TREE_CODE (number) == INTEGER_CST
5074 && wi::to_wide (number) != 0)
5075 TREE_VALUE (second_argument)
5076 = wide_int_to_tree (TREE_TYPE (number),
5077 wi::to_wide (number) + 2);
5079 /* This is the third argument, the "first-to-check",
5080 which specifies the index of the first argument to
5081 check. This could be 0, meaning it is not available,
5082 in which case we don't need to add 2. Add 2 if not
5083 0. */
5084 number = TREE_VALUE (third_argument);
5085 if (number
5086 && TREE_CODE (number) == INTEGER_CST
5087 && wi::to_wide (number) != 0)
5088 TREE_VALUE (third_argument)
5089 = wide_int_to_tree (TREE_TYPE (number),
5090 wi::to_wide (number) + 2);
5092 filtered_attributes = chainon (filtered_attributes,
5093 new_attribute);
5095 else if (is_attribute_p ("nonnull", name))
5097 /* We need to fixup all the argument indexes by adding 2
5098 for the two hidden arguments of an Objective-C method
5099 invocation, similat to what we do above for the
5100 "format" attribute. */
5101 /* FIXME: This works great in terms of implementing the
5102 functionality, but the warnings that are produced by
5103 nonnull do mention the argument index (while the
5104 format ones don't). For example, you could get
5105 "warning: null argument where non-null required
5106 (argument 3)". Now in that message, "argument 3"
5107 includes the 2 hidden arguments; it would be much
5108 more friendly to call it "argument 1", as that would
5109 be consistent with __attribute__ ((nonnnull (1))).
5110 To do this, we'd need to have the C family code that
5111 checks the arguments know about adding/removing 2 to
5112 the argument index ... or alternatively we could
5113 maybe store the "printable" argument index in
5114 addition to the actual argument index ? Some
5115 refactoring is needed to do this elegantly. */
5116 tree new_attribute = copy_node (attribute);
5117 tree argument = TREE_VALUE (attribute);
5118 while (argument != NULL_TREE)
5120 /* Get the value of the argument and add 2. */
5121 tree number = TREE_VALUE (argument);
5122 if (number && TREE_CODE (number) == INTEGER_CST
5123 && wi::to_wide (number) != 0)
5124 TREE_VALUE (argument)
5125 = wide_int_to_tree (TREE_TYPE (number),
5126 wi::to_wide (number) + 2);
5127 argument = TREE_CHAIN (argument);
5130 filtered_attributes = chainon (filtered_attributes,
5131 new_attribute);
5133 else
5134 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
5138 if (filtered_attributes)
5140 /* This hackery changes the TREE_TYPE of the ObjC method
5141 declaration to be a function type, so that decl_attributes
5142 will treat the ObjC method as if it was a function. Some
5143 attributes (sentinel, format) will be applied to the function
5144 type, changing it in place; so after calling decl_attributes,
5145 we extract the function type attributes and store them in
5146 METHOD_TYPE_ATTRIBUTES. Some other attributes (noreturn,
5147 deprecated) are applied directly to the method declaration
5148 (by setting TREE_DEPRECATED and TREE_THIS_VOLATILE) so there
5149 is nothing to do. */
5150 tree saved_type = TREE_TYPE (*node);
5151 TREE_TYPE (*node)
5152 = build_function_type_for_method (TREE_VALUE (saved_type), *node,
5153 METHOD_REF, 0);
5154 decl_attributes (node, filtered_attributes, flags);
5155 METHOD_TYPE_ATTRIBUTES (*node) = TYPE_ATTRIBUTES (TREE_TYPE (*node));
5156 TREE_TYPE (*node) = saved_type;
5160 bool
5161 objc_method_decl (enum tree_code opcode)
5163 return opcode == INSTANCE_METHOD_DECL || opcode == CLASS_METHOD_DECL;
5166 /* Return a function type for METHOD with RETURN_TYPE. CONTEXT is
5167 either METHOD_DEF or METHOD_REF, indicating whether we are defining a
5168 method or calling one. SUPER_FLAG indicates whether this is a send
5169 to super; this makes a difference for the NeXT calling sequence in
5170 which the lookup and the method call are done together. If METHOD is
5171 NULL, user-defined arguments (i.e., beyond self and _cmd) shall be
5172 represented as varargs. */
5174 tree
5175 build_function_type_for_method (tree return_type, tree method,
5176 int context, bool super_flag)
5178 vec<tree, va_gc> *argtypes = make_tree_vector ();
5179 tree t, ftype;
5180 bool is_varargs = false;
5182 (*runtime.get_arg_type_list_base) (&argtypes, method, context, super_flag);
5184 /* No actual method prototype given; remaining args passed as varargs. */
5185 if (method == NULL_TREE)
5187 is_varargs = true;
5188 goto build_ftype;
5191 for (t = METHOD_SEL_ARGS (method); t; t = DECL_CHAIN (t))
5193 tree arg_type = TREE_VALUE (TREE_TYPE (t));
5195 /* Decay argument types for the underlying C function as
5196 appropriate. */
5197 arg_type = objc_decay_parm_type (arg_type);
5199 vec_safe_push (argtypes, arg_type);
5202 if (METHOD_ADD_ARGS (method))
5204 for (t = TREE_CHAIN (METHOD_ADD_ARGS (method));
5205 t; t = TREE_CHAIN (t))
5207 tree arg_type = TREE_TYPE (TREE_VALUE (t));
5209 arg_type = objc_decay_parm_type (arg_type);
5211 vec_safe_push (argtypes, arg_type);
5214 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
5215 is_varargs = true;
5218 build_ftype:
5219 if (is_varargs)
5220 ftype = build_varargs_function_type_vec (return_type, argtypes);
5221 else
5222 ftype = build_function_type_vec (return_type, argtypes);
5224 release_tree_vector (argtypes);
5225 return ftype;
5228 /* The 'method' argument is a tree; this tree could either be a single
5229 method, which is returned, or could be a TREE_VEC containing a list
5230 of methods. In that case, the first one is returned, and warnings
5231 are issued as appropriate. */
5232 static tree
5233 check_duplicates (tree method, int methods, int is_class)
5235 tree first_method;
5236 size_t i;
5238 if (method == NULL_TREE)
5239 return NULL_TREE;
5241 if (TREE_CODE (method) != TREE_VEC)
5242 return method;
5244 /* We have two or more methods with the same name but different
5245 types. */
5246 first_method = TREE_VEC_ELT (method, 0);
5248 /* But just how different are those types? If
5249 -Wno-strict-selector-match is specified, we shall not complain if
5250 the differences are solely among types with identical size and
5251 alignment. */
5252 if (!warn_strict_selector_match)
5254 for (i = 0; i < (size_t) TREE_VEC_LENGTH (method); i++)
5255 if (!comp_proto_with_proto (first_method, TREE_VEC_ELT (method, i), 0))
5256 goto issue_warning;
5258 return first_method;
5261 issue_warning:
5262 if (methods)
5264 bool type = TREE_CODE (first_method) == INSTANCE_METHOD_DECL;
5266 warning_at (input_location, 0,
5267 "multiple methods named %<%c%E%> found",
5268 (is_class ? '+' : '-'),
5269 METHOD_SEL_NAME (first_method));
5270 inform (DECL_SOURCE_LOCATION (first_method), "using %<%c%s%>",
5271 (type ? '-' : '+'),
5272 identifier_to_locale (gen_method_decl (first_method)));
5274 else
5276 bool type = TREE_CODE (first_method) == INSTANCE_METHOD_DECL;
5278 warning_at (input_location, 0,
5279 "multiple selectors named %<%c%E%> found",
5280 (is_class ? '+' : '-'),
5281 METHOD_SEL_NAME (first_method));
5282 inform (DECL_SOURCE_LOCATION (first_method), "found %<%c%s%>",
5283 (type ? '-' : '+'),
5284 identifier_to_locale (gen_method_decl (first_method)));
5287 for (i = 0; i < (size_t) TREE_VEC_LENGTH (method); i++)
5289 bool type = TREE_CODE (TREE_VEC_ELT (method, i)) == INSTANCE_METHOD_DECL;
5291 inform (DECL_SOURCE_LOCATION (TREE_VEC_ELT (method, i)), "also found %<%c%s%>",
5292 (type ? '-' : '+'),
5293 identifier_to_locale (gen_method_decl (TREE_VEC_ELT (method, i))));
5296 return first_method;
5299 /* If RECEIVER is a class reference, return the identifier node for
5300 the referenced class. RECEIVER is created by objc_get_class_reference,
5301 so we check the exact form created depending on which runtimes are
5302 used. */
5304 static tree
5305 receiver_is_class_object (tree receiver, int self, int super)
5307 tree exp, arg;
5309 /* The receiver is 'self' or 'super' in the context of a class method. */
5310 if (objc_method_context
5311 && TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
5312 && (self || super))
5313 return (super
5314 ? CLASS_SUPER_NAME (implementation_template)
5315 : CLASS_NAME (implementation_template));
5317 /* The runtime might encapsulate things its own way. */
5318 exp = (*runtime.receiver_is_class_object) (receiver);
5319 if (exp)
5320 return exp;
5322 /* The receiver is a function call that returns an id. Check if
5323 it is a call to objc_getClass, if so, pick up the class name.
5325 This is required by the GNU runtime, which compiles
5327 [NSObject alloc]
5329 into
5331 [objc_get_class ("NSObject") alloc];
5333 and then, to check that the receiver responds to the +alloc
5334 method, needs to be able to determine that the objc_get_class()
5335 call returns the NSObject class and not just a generic Class
5336 pointer.
5338 But, traditionally this is enabled for all runtimes, not just the
5339 GNU one, which means that the compiler is smarter than you'd
5340 expect when dealing with objc_getClass(). For example, with the
5341 Apple runtime, in the code
5343 [objc_getClass ("NSObject") alloc];
5345 the compiler will recognize the objc_getClass() call as special
5346 (due to the code below) and so will know that +alloc is called on
5347 the 'NSObject' class, and can perform the corresponding checks.
5349 Programmers can disable this behavior by casting the results of
5350 objc_getClass() to 'Class' (this may seem weird because
5351 objc_getClass() is already declared to return 'Class', but the
5352 compiler treats it as a special function). This may be useful if
5353 the class is never declared, and the compiler would complain
5354 about a missing @interface for it. Then, you can do
5356 [(Class)objc_getClass ("MyClassNeverDeclared") alloc];
5358 to silence the warnings. */
5359 if (TREE_CODE (receiver) == CALL_EXPR
5360 && (exp = CALL_EXPR_FN (receiver))
5361 && TREE_CODE (exp) == ADDR_EXPR
5362 && (exp = TREE_OPERAND (exp, 0))
5363 && TREE_CODE (exp) == FUNCTION_DECL
5364 /* For some reason, we sometimes wind up with multiple FUNCTION_DECL
5365 prototypes for objc_get_class(). Thankfully, they seem to share the
5366 same function type. */
5367 && TREE_TYPE (exp) == TREE_TYPE (objc_get_class_decl)
5368 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (exp)), runtime.tag_getclass)
5369 /* We have a call to objc_get_class/objc_getClass! */
5370 && (arg = CALL_EXPR_ARG (receiver, 0)))
5372 STRIP_NOPS (arg);
5373 if (TREE_CODE (arg) == ADDR_EXPR
5374 && (arg = TREE_OPERAND (arg, 0))
5375 && TREE_CODE (arg) == STRING_CST)
5376 /* Finally, we have the class name. */
5377 return get_identifier (TREE_STRING_POINTER (arg));
5379 return 0;
5382 /* If we are currently building a message expr, this holds
5383 the identifier of the selector of the message. This is
5384 used when printing warnings about argument mismatches. */
5386 static tree current_objc_message_selector = 0;
5388 tree
5389 objc_message_selector (void)
5391 return current_objc_message_selector;
5394 /* Construct an expression for sending a message.
5395 MESS has the object to send to in TREE_PURPOSE
5396 and the argument list (including selector) in TREE_VALUE.
5398 (*(<abstract_decl>(*)())_msg)(receiver, selTransTbl[n], ...);
5399 (*(<abstract_decl>(*)())_msgSuper)(receiver, selTransTbl[n], ...); */
5401 tree
5402 objc_build_message_expr (tree receiver, tree message_args)
5404 tree sel_name;
5405 #ifdef OBJCPLUS
5406 tree args = TREE_PURPOSE (message_args);
5407 #else
5408 tree args = message_args;
5409 #endif
5410 tree method_params = NULL_TREE;
5412 if (TREE_CODE (receiver) == ERROR_MARK || TREE_CODE (args) == ERROR_MARK)
5413 return error_mark_node;
5415 /* Obtain the full selector name. */
5416 switch (TREE_CODE (args))
5418 case IDENTIFIER_NODE:
5419 /* A unary selector. */
5420 sel_name = args;
5421 break;
5422 case TREE_LIST:
5423 sel_name = build_keyword_selector (args);
5424 break;
5425 default:
5426 gcc_unreachable ();
5429 /* Build the parameter list to give to the method. */
5430 if (TREE_CODE (args) == TREE_LIST)
5431 #ifdef OBJCPLUS
5432 method_params = chainon (args, TREE_VALUE (message_args));
5433 #else
5435 tree chain = args, prev = NULL_TREE;
5437 /* We have a keyword selector--check for comma expressions. */
5438 while (chain)
5440 tree element = TREE_VALUE (chain);
5442 /* We have a comma expression, must collapse... */
5443 if (TREE_CODE (element) == TREE_LIST)
5445 if (prev)
5446 TREE_CHAIN (prev) = element;
5447 else
5448 args = element;
5450 prev = chain;
5451 chain = TREE_CHAIN (chain);
5453 method_params = args;
5455 #endif
5457 #ifdef OBJCPLUS
5458 if (processing_template_decl)
5459 /* Must wait until template instantiation time. */
5460 return build_min_nt_loc (UNKNOWN_LOCATION, MESSAGE_SEND_EXPR, receiver,
5461 sel_name, method_params);
5462 #endif
5464 return objc_finish_message_expr (receiver, sel_name, method_params, NULL);
5467 /* Look up method SEL_NAME that would be suitable for receiver
5468 of type 'id' (if IS_CLASS is zero) or 'Class' (if IS_CLASS is
5469 nonzero), and report on any duplicates. */
5471 static tree
5472 lookup_method_in_hash_lists (tree sel_name, int is_class)
5474 tree method_prototype = OBJC_MAP_NOT_FOUND;
5476 if (!is_class)
5477 method_prototype = objc_map_get (instance_method_map, sel_name);
5479 if (method_prototype == OBJC_MAP_NOT_FOUND)
5481 method_prototype = objc_map_get (class_method_map, sel_name);
5482 is_class = 1;
5484 if (method_prototype == OBJC_MAP_NOT_FOUND)
5485 return NULL_TREE;
5488 return check_duplicates (method_prototype, 1, is_class);
5491 /* The 'objc_finish_message_expr' routine is called from within
5492 'objc_build_message_expr' for non-template functions. In the case of
5493 C++ template functions, it is called from 'build_expr_from_tree'
5494 (in decl2.cc) after RECEIVER and METHOD_PARAMS have been expanded.
5496 If the method_prototype_avail argument is NULL, then we warn
5497 if the method being used is deprecated. If it is not NULL, instead
5498 of deprecating, we set *method_prototype_avail to the method
5499 prototype that was used and is deprecated. This is useful for
5500 getter calls that are always generated when compiling dot-syntax
5501 expressions, even if they may not be used. In that case, we don't
5502 want the warning immediately; we produce it (if needed) at gimplify
5503 stage when we are sure that the deprecated getter is being
5504 used. */
5505 tree
5506 objc_finish_message_expr (tree receiver, tree sel_name, tree method_params,
5507 tree *method_prototype_avail)
5509 tree method_prototype = NULL_TREE, rprotos = NULL_TREE, rtype;
5510 tree retval, class_tree;
5511 int self, super, have_cast;
5513 STRIP_ANY_LOCATION_WRAPPER (receiver);
5515 /* We have used the receiver, so mark it as read. */
5516 mark_exp_read (receiver);
5518 /* Extract the receiver of the message, as well as its type
5519 (where the latter may take the form of a cast or be inferred
5520 from the implementation context). */
5521 rtype = receiver;
5522 while (TREE_CODE (rtype) == COMPOUND_EXPR
5523 || TREE_CODE (rtype) == MODIFY_EXPR
5524 || CONVERT_EXPR_P (rtype)
5525 || TREE_CODE (rtype) == COMPONENT_REF)
5526 rtype = TREE_OPERAND (rtype, 0);
5528 /* self is 1 if this is a message to self, 0 otherwise */
5529 self = (rtype == self_decl);
5531 /* super is 1 if this is a message to super, 0 otherwise. */
5532 super = (rtype == UOBJC_SUPER_decl);
5534 /* rtype is the type of the receiver. */
5535 rtype = TREE_TYPE (receiver);
5537 /* have_cast is 1 if the receiver is casted. */
5538 have_cast = (TREE_CODE (receiver) == NOP_EXPR
5539 || (TREE_CODE (receiver) == COMPOUND_EXPR
5540 && !IS_SUPER (rtype)));
5542 /* If we are calling [super dealloc], reset our warning flag. */
5543 if (super && !strcmp ("dealloc", IDENTIFIER_POINTER (sel_name)))
5544 should_call_super_dealloc = 0;
5546 /* If the receiver is a class object, retrieve the corresponding
5547 @interface, if one exists. class_tree is the class name
5548 identifier, or NULL_TREE if this is not a class method or the
5549 class name could not be determined (as in the case "Class c; [c
5550 method];"). */
5551 class_tree = receiver_is_class_object (receiver, self, super);
5553 /* Now determine the receiver type (if an explicit cast has not been
5554 provided). */
5555 if (!have_cast)
5557 if (class_tree)
5559 /* We are here when we have no cast, and we have a class
5560 name. So, this is a plain method to a class object, as
5561 in [NSObject alloc]. Find the interface corresponding to
5562 the class name. */
5563 rtype = lookup_interface (class_tree);
5565 if (rtype == NULL_TREE)
5567 /* If 'rtype' is NULL_TREE at this point it means that
5568 we have seen no @interface corresponding to that
5569 class name, only a @class declaration (alternatively,
5570 this was a call such as [objc_getClass("SomeClass")
5571 alloc], where we've never seen the @interface of
5572 SomeClass). So, we have a class name (class_tree)
5573 but no actual details of the class methods. We won't
5574 be able to check that the class responds to the
5575 method, and we will have to guess the method
5576 prototype. Emit a warning, then keep going (this
5577 will use any method with a matching name, as if the
5578 receiver was of type 'Class'). */
5579 warning (0, "%<@interface%> of class %qE not found",
5580 class_tree);
5583 /* Handle `self' and `super'. */
5584 else if (super)
5586 if (!CLASS_SUPER_NAME (implementation_template))
5588 error ("no super class declared in @interface for %qE",
5589 CLASS_NAME (implementation_template));
5590 return error_mark_node;
5592 rtype = lookup_interface (CLASS_SUPER_NAME (implementation_template));
5594 else if (self)
5595 rtype = lookup_interface (CLASS_NAME (implementation_template));
5598 if (objc_is_id (rtype))
5600 /* The receiver is of type 'id' or 'Class' (with or without some
5601 protocols attached to it). */
5603 /* We set class_tree to the identifier for 'Class' if this is a
5604 class method, and to NULL_TREE if not. */
5605 class_tree = (IS_CLASS (rtype) ? objc_class_name : NULL_TREE);
5607 /* 'rprotos' is the list of protocols that the receiver
5608 supports. */
5609 rprotos = (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype))
5610 ? TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype))
5611 : NULL_TREE);
5613 /* We have no information on the type, and we set it to
5614 NULL_TREE. */
5615 rtype = NULL_TREE;
5617 /* If there are any protocols, check that the method we are
5618 calling appears in the protocol list. If there are no
5619 protocols, this is a message to 'id' or 'Class' and we accept
5620 any method that exists. */
5621 if (rprotos)
5623 /* If messaging 'id <Protos>' or 'Class <Proto>', first
5624 search in protocols themselves for the method
5625 prototype. */
5626 method_prototype
5627 = lookup_method_in_protocol_list (rprotos, sel_name,
5628 class_tree != NULL_TREE);
5630 /* If messaging 'Class <Proto>' but did not find a class
5631 method prototype, search for an instance method instead,
5632 and warn about having done so. */
5633 if (!method_prototype && !rtype && class_tree != NULL_TREE)
5635 method_prototype
5636 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
5638 if (method_prototype)
5639 warning (0, "found %<-%E%> instead of %<+%E%> in protocol(s)",
5640 sel_name, sel_name);
5644 else if (rtype)
5646 /* We have a receiver type which is more specific than 'id' or
5647 'Class'. */
5648 tree orig_rtype = rtype;
5650 if (TREE_CODE (rtype) == POINTER_TYPE)
5651 rtype = TREE_TYPE (rtype);
5652 /* Traverse typedef aliases */
5653 while (TREE_CODE (rtype) == RECORD_TYPE && OBJC_TYPE_NAME (rtype)
5654 && TREE_CODE (OBJC_TYPE_NAME (rtype)) == TYPE_DECL
5655 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype)))
5656 rtype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype));
5657 if (TYPED_OBJECT (rtype))
5659 rprotos = TYPE_OBJC_PROTOCOL_LIST (rtype);
5660 rtype = TYPE_OBJC_INTERFACE (rtype);
5662 if (!rtype || TREE_CODE (rtype) == IDENTIFIER_NODE)
5664 /* If we could not find an @interface declaration, we must
5665 have only seen a @class declaration; so, we cannot say
5666 anything more intelligent about which methods the
5667 receiver will understand. Note that this only happens
5668 for instance methods; for class methods to a class where
5669 we have only seen a @class declaration,
5670 lookup_interface() above would have set rtype to
5671 NULL_TREE. */
5672 if (rprotos)
5674 /* We could not find an @interface declaration, yet, if
5675 there are protocols attached to the type, we can
5676 still look up the method in the protocols. Ie, we
5677 are in the following case:
5679 @class MyClass;
5680 MyClass<MyProtocol> *x;
5681 [x method];
5683 If 'MyProtocol' has the method 'method', we can check
5684 and retrieve the method prototype. */
5685 method_prototype
5686 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
5688 /* At this point, if we have found the method_prototype,
5689 we are quite happy. The details of the class are
5690 irrelevant. If we haven't found it, a warning will
5691 have been produced that the method could not be found
5692 in the protocol, and we won't produce further
5693 warnings (please note that this means that "@class
5694 MyClass; MyClass <MyProtocol> *x;" is exactly
5695 equivalent to "id <MyProtocol> x", which isn't too
5696 satisfactory but it's not easy to see how to do
5697 better). */
5699 else
5701 if (rtype)
5703 /* We could not find an @interface declaration, and
5704 there are no protocols attached to the receiver,
5705 so we can't complete the check that the receiver
5706 responds to the method, and we can't retrieve the
5707 method prototype. But, because the receiver has
5708 a well-specified class, the programmer did want
5709 this check to be performed. Emit a warning, then
5710 keep going as if it was an 'id'. To remove the
5711 warning, either include an @interface for the
5712 class, or cast the receiver to 'id'. Note that
5713 rtype is an IDENTIFIER_NODE at this point. */
5714 warning (0, "%<@interface%> of class %qE not found", rtype);
5718 rtype = NULL_TREE;
5720 else if (TREE_CODE (rtype) == CLASS_INTERFACE_TYPE
5721 || TREE_CODE (rtype) == CLASS_IMPLEMENTATION_TYPE)
5723 /* We have a valid ObjC class name with an associated
5724 @interface. Look up the method name in the published
5725 @interface for the class (and its superclasses). */
5726 method_prototype
5727 = lookup_method_static (rtype, sel_name, class_tree != NULL_TREE);
5729 /* If the method was not found in the @interface, it may still
5730 exist locally as part of the @implementation. */
5731 if (!method_prototype && objc_implementation_context
5732 && CLASS_NAME (objc_implementation_context)
5733 == OBJC_TYPE_NAME (rtype))
5734 method_prototype
5735 = lookup_method
5736 ((class_tree
5737 ? CLASS_CLS_METHODS (objc_implementation_context)
5738 : CLASS_NST_METHODS (objc_implementation_context)),
5739 sel_name);
5741 /* If we haven't found a candidate method by now, try looking for
5742 it in the protocol list. */
5743 if (!method_prototype && rprotos)
5744 method_prototype
5745 = lookup_method_in_protocol_list (rprotos, sel_name,
5746 class_tree != NULL_TREE);
5748 else
5750 /* We have a type, but it's not an Objective-C type (!). */
5751 warning (0, "invalid receiver type %qs",
5752 identifier_to_locale (gen_type_name (orig_rtype)));
5753 /* After issuing the "invalid receiver" warning, perform method
5754 lookup as if we were messaging 'id'. */
5755 rtype = rprotos = NULL_TREE;
5758 /* Note that rtype could also be NULL_TREE. This happens if we are
5759 messaging a class by name, but the class was only
5760 forward-declared using @class. */
5762 /* For 'id' or 'Class' receivers, search in the global hash table as
5763 a last resort. For all receivers, warn if protocol searches have
5764 failed. */
5765 if (!method_prototype)
5767 if (rprotos)
5768 warning (0, "%<%c%E%> not found in protocol(s)",
5769 (class_tree ? '+' : '-'),
5770 sel_name);
5772 if (!rtype)
5773 method_prototype
5774 = lookup_method_in_hash_lists (sel_name, class_tree != NULL_TREE);
5777 if (!method_prototype)
5779 static bool warn_missing_methods = false;
5781 if (rtype)
5782 warning (0, "%qE may not respond to %<%c%E%>",
5783 OBJC_TYPE_NAME (rtype),
5784 (class_tree ? '+' : '-'),
5785 sel_name);
5786 /* If we are messaging an 'id' or 'Class' object and made it here,
5787 then we have failed to find _any_ instance or class method,
5788 respectively. */
5789 else
5790 warning (0, "no %<%c%E%> method found",
5791 (class_tree ? '+' : '-'),
5792 sel_name);
5794 if (!warn_missing_methods)
5796 warning_at (input_location,
5797 0, "(messages without a matching method signature "
5798 "will be assumed to return %<id%> and accept "
5799 "%<...%> as arguments)");
5800 warn_missing_methods = true;
5803 else
5805 /* Warn if the method is deprecated, but not if the receiver is
5806 a generic 'id'. 'id' is used to cast an object to a generic
5807 object of an unspecified class; in that case, we'll use
5808 whatever method prototype we can find to get the method
5809 argument and return types, but it is not appropriate to
5810 produce deprecation warnings since we don't know the class
5811 that the object will be of at runtime. The @interface(s) for
5812 that class may not even be available to the compiler right
5813 now, and it is perfectly possible that the method is marked
5814 as non-deprecated in such @interface(s).
5816 In practice this makes sense since casting an object to 'id'
5817 is often used precisely to turn off warnings associated with
5818 the object being of a particular class. */
5819 if (TREE_UNAVAILABLE (method_prototype) && rtype != NULL_TREE)
5821 if (method_prototype_avail)
5822 *method_prototype_avail = method_prototype;
5823 else
5824 error_unavailable_use (method_prototype, NULL_TREE);
5826 else if (TREE_DEPRECATED (method_prototype) && rtype != NULL_TREE)
5828 if (method_prototype_avail)
5829 *method_prototype_avail = method_prototype;
5830 else
5831 warn_deprecated_use (method_prototype, NULL_TREE);
5835 /* Save the selector name for printing error messages. */
5836 current_objc_message_selector = sel_name;
5838 /* Build the method call.
5839 TODO: Get the location from somewhere that will work for delayed
5840 expansion. */
5842 retval = (*runtime.build_objc_method_call) (input_location, method_prototype,
5843 receiver, rtype, sel_name,
5844 method_params, super);
5846 current_objc_message_selector = 0;
5848 return retval;
5852 /* This routine creates a static variable used to implement @protocol(MyProtocol)
5853 expression. This variable will be initialized to global protocol_t meta-data
5854 pointer. */
5856 /* This function is called by the parser when (and only when) a
5857 @protocol() expression is found, in order to compile it. */
5858 tree
5859 objc_build_protocol_expr (tree protoname)
5861 tree p = lookup_protocol (protoname, /* warn if deprecated */ true,
5862 /* definition_required */ false);
5864 if (!p)
5866 error ("cannot find protocol declaration for %qE", protoname);
5867 return error_mark_node;
5870 return (*runtime.get_protocol_reference) (input_location, p);
5873 /* This function is called by the parser when a @selector() expression
5874 is found, in order to compile it. It is only called by the parser
5875 and only to compile a @selector(). LOC is the location of the
5876 @selector. */
5877 tree
5878 objc_build_selector_expr (location_t loc, tree selnamelist)
5880 tree selname;
5882 /* Obtain the full selector name. */
5883 switch (TREE_CODE (selnamelist))
5885 case IDENTIFIER_NODE:
5886 /* A unary selector. */
5887 selname = selnamelist;
5888 break;
5889 case TREE_LIST:
5890 selname = build_keyword_selector (selnamelist);
5891 break;
5892 default:
5893 gcc_unreachable ();
5896 /* If we are required to check @selector() expressions as they
5897 are found, check that the selector has been declared. */
5898 if (warn_undeclared_selector)
5900 /* Look the selector up in the list of all known class and
5901 instance methods (up to this line) to check that the selector
5902 exists. */
5903 tree method;
5905 /* First try with instance methods. */
5906 method = objc_map_get (instance_method_map, selname);
5908 /* If not found, try with class methods. */
5909 if (method == OBJC_MAP_NOT_FOUND)
5911 method = objc_map_get (class_method_map, selname);
5913 /* If still not found, print out a warning. */
5914 if (method == OBJC_MAP_NOT_FOUND)
5915 warning (0, "undeclared selector %qE", selname);
5919 /* The runtimes do this differently, most particularly, GNU has typed
5920 selectors, whilst NeXT does not. */
5921 return (*runtime.build_selector_reference) (loc, selname, NULL_TREE);
5924 static tree
5925 build_ivar_reference (tree id)
5927 tree base;
5928 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
5930 /* Historically, a class method that produced objects (factory
5931 method) would assign `self' to the instance that it
5932 allocated. This would effectively turn the class method into
5933 an instance method. Following this assignment, the instance
5934 variables could be accessed. That practice, while safe,
5935 violates the simple rule that a class method should not refer
5936 to an instance variable. It's better to catch the cases
5937 where this is done unknowingly than to support the above
5938 paradigm. */
5939 warning (0, "instance variable %qE accessed in class method",
5940 id);
5941 self_decl = convert (objc_instance_type, self_decl); /* cast */
5944 base = build_indirect_ref (input_location, self_decl, RO_ARROW);
5945 return (*runtime.build_ivar_reference) (input_location, base, id);
5948 static void
5949 hash_init (void)
5951 instance_method_map = objc_map_alloc_ggc (1000);
5952 class_method_map = objc_map_alloc_ggc (1000);
5954 class_name_map = objc_map_alloc_ggc (200);
5955 alias_name_map = objc_map_alloc_ggc (200);
5957 /* Initialize the hash table used to hold the constant string objects. */
5958 string_htab = hash_table<objc_string_hasher>::create_ggc (31);
5961 /* Use the following to add a method to class_method_map or
5962 instance_method_map. It will add the method, keyed by the
5963 METHOD_SEL_NAME. If the method already exists, but with one or
5964 more different prototypes, it will store a TREE_VEC in the map,
5965 with the method prototypes in the vector. */
5966 static void
5967 insert_method_into_method_map (bool class_method, tree method)
5969 tree method_name = METHOD_SEL_NAME (method);
5970 tree existing_entry;
5971 objc_map_t map;
5973 if (class_method)
5974 map = class_method_map;
5975 else
5976 map = instance_method_map;
5978 /* Check if the method already exists in the map. */
5979 existing_entry = objc_map_get (map, method_name);
5981 /* If not, we simply add it to the map. */
5982 if (existing_entry == OBJC_MAP_NOT_FOUND)
5983 objc_map_put (map, method_name, method);
5984 else
5986 tree new_entry;
5988 /* If an entry already exists, it's more complicated. We'll
5989 have to check whether the method prototype is the same or
5990 not. */
5991 if (TREE_CODE (existing_entry) != TREE_VEC)
5993 /* If the method prototypes are the same, there is nothing
5994 to do. */
5995 if (comp_proto_with_proto (method, existing_entry, 1))
5996 return;
5998 /* If not, create a vector to store both the method already
5999 in the map, and the new one that we are adding. */
6000 new_entry = make_tree_vec (2);
6002 TREE_VEC_ELT (new_entry, 0) = existing_entry;
6003 TREE_VEC_ELT (new_entry, 1) = method;
6005 else
6007 /* An entry already exists, and it's already a vector. This
6008 means that at least 2 different method prototypes were
6009 already found, and we're considering registering yet
6010 another one. */
6011 size_t i;
6013 /* Check all the existing prototypes. If any matches the
6014 one we need to add, there is nothing to do because it's
6015 already there. */
6016 for (i = 0; i < (size_t) TREE_VEC_LENGTH (existing_entry); i++)
6017 if (comp_proto_with_proto (method, TREE_VEC_ELT (existing_entry, i), 1))
6018 return;
6020 /* Else, create a new, bigger vector and add the new method
6021 at the end of it. This is inefficient but extremely
6022 rare; in any sane program most methods have a single
6023 prototype, and very few, if any, will have more than
6024 2! */
6025 new_entry = make_tree_vec (TREE_VEC_LENGTH (existing_entry) + 1);
6027 /* Copy the methods from the existing vector. */
6028 for (i = 0; i < (size_t) TREE_VEC_LENGTH (existing_entry); i++)
6029 TREE_VEC_ELT (new_entry, i) = TREE_VEC_ELT (existing_entry, i);
6031 /* Add the new method at the end. */
6032 TREE_VEC_ELT (new_entry, i) = method;
6035 /* Store the new vector in the map. */
6036 objc_map_put (map, method_name, new_entry);
6041 static tree
6042 lookup_method (tree mchain, tree method)
6044 tree key;
6046 if (TREE_CODE (method) == IDENTIFIER_NODE)
6047 key = method;
6048 else
6049 key = METHOD_SEL_NAME (method);
6051 while (mchain)
6053 if (METHOD_SEL_NAME (mchain) == key)
6054 return mchain;
6056 mchain = DECL_CHAIN (mchain);
6058 return NULL_TREE;
6061 /* Look up a class (if OBJC_LOOKUP_CLASS is set in FLAGS) or instance
6062 method in INTERFACE, along with any categories and protocols
6063 attached thereto. If method is not found, and the
6064 OBJC_LOOKUP_NO_SUPER is _not_ set in FLAGS, recursively examine the
6065 INTERFACE's superclass. If OBJC_LOOKUP_CLASS is set,
6066 OBJC_LOOKUP_NO_SUPER is clear, and no suitable class method could
6067 be found in INTERFACE or any of its superclasses, look for an
6068 _instance_ method of the same name in the root class as a last
6069 resort. This behavior can be turned off by using
6070 OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS.
6072 If a suitable method cannot be found, return NULL_TREE. */
6074 static tree
6075 lookup_method_static (tree interface, tree ident, int flags)
6077 tree meth = NULL_TREE, root_inter = NULL_TREE;
6078 tree inter = interface;
6079 int is_class = (flags & OBJC_LOOKUP_CLASS);
6080 int no_superclasses = (flags & OBJC_LOOKUP_NO_SUPER);
6081 int no_instance_methods_of_root_class = (flags & OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS);
6083 while (inter)
6085 tree chain = is_class ? CLASS_CLS_METHODS (inter) : CLASS_NST_METHODS (inter);
6086 tree category = inter;
6088 /* First, look up the method in the class itself. */
6089 if ((meth = lookup_method (chain, ident)))
6090 return meth;
6092 /* Failing that, look for the method in each category of the class. */
6093 while ((category = CLASS_CATEGORY_LIST (category)))
6095 chain = is_class ? CLASS_CLS_METHODS (category) : CLASS_NST_METHODS (category);
6097 /* Check directly in each category. */
6098 if ((meth = lookup_method (chain, ident)))
6099 return meth;
6101 /* Failing that, check in each category's protocols. */
6102 if (CLASS_PROTOCOL_LIST (category))
6104 if ((meth = (lookup_method_in_protocol_list
6105 (CLASS_PROTOCOL_LIST (category), ident, is_class))))
6106 return meth;
6110 /* If not found in categories, check in protocols of the main class. */
6111 if (CLASS_PROTOCOL_LIST (inter))
6113 if ((meth = (lookup_method_in_protocol_list
6114 (CLASS_PROTOCOL_LIST (inter), ident, is_class))))
6115 return meth;
6118 /* If we were instructed not to look in superclasses, don't. */
6119 if (no_superclasses)
6120 return NULL_TREE;
6122 /* Failing that, climb up the inheritance hierarchy. */
6123 root_inter = inter;
6124 inter = lookup_interface (CLASS_SUPER_NAME (inter));
6126 while (inter);
6128 if (is_class && !no_instance_methods_of_root_class)
6130 /* If no class (factory) method was found, check if an _instance_
6131 method of the same name exists in the root class. This is what
6132 the Objective-C runtime will do. */
6133 return lookup_method_static (root_inter, ident, 0);
6135 else
6137 /* If an instance method was not found, return 0. */
6138 return NULL_TREE;
6142 static tree
6143 objc_add_method (tree klass, tree method, int is_class, bool is_optional)
6145 tree existing_method = NULL_TREE;
6147 /* The first thing we do is look up the method in the list of
6148 methods already defined in the interface (or implementation). */
6149 if (is_class)
6150 existing_method = lookup_method (CLASS_CLS_METHODS (klass), method);
6151 else
6152 existing_method = lookup_method (CLASS_NST_METHODS (klass), method);
6154 /* In the case of protocols, we have a second list of methods to
6155 consider, the list of optional ones. */
6156 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE)
6158 /* @required methods are added to the protocol's normal list.
6159 @optional methods are added to the protocol's OPTIONAL lists.
6160 Note that adding the methods to the optional lists disables
6161 checking that the methods are implemented by classes
6162 implementing the protocol, since these checks only use the
6163 CLASS_CLS_METHODS and CLASS_NST_METHODS. */
6165 /* First of all, if the method to add is @optional, and we found
6166 it already existing as @required, emit an error. */
6167 if (is_optional && existing_method)
6169 error ("method %<%c%E%> declared %<@optional%> and %<@required%> at the same time",
6170 (is_class ? '+' : '-'),
6171 METHOD_SEL_NAME (existing_method));
6172 inform (DECL_SOURCE_LOCATION (existing_method),
6173 "previous declaration of %<%c%E%> as %<@required%>",
6174 (is_class ? '+' : '-'),
6175 METHOD_SEL_NAME (existing_method));
6178 /* Now check the list of @optional methods if we didn't find the
6179 method in the @required list. */
6180 if (!existing_method)
6182 if (is_class)
6183 existing_method = lookup_method (PROTOCOL_OPTIONAL_CLS_METHODS (klass), method);
6184 else
6185 existing_method = lookup_method (PROTOCOL_OPTIONAL_NST_METHODS (klass), method);
6187 if (!is_optional && existing_method)
6189 error ("method %<%c%E%> declared %<@optional%> and %<@required%> at the same time",
6190 (is_class ? '+' : '-'),
6191 METHOD_SEL_NAME (existing_method));
6192 inform (DECL_SOURCE_LOCATION (existing_method),
6193 "previous declaration of %<%c%E%> as %<@optional%>",
6194 (is_class ? '+' : '-'),
6195 METHOD_SEL_NAME (existing_method));
6200 /* If the method didn't exist already, add it. */
6201 if (!existing_method)
6203 if (is_optional)
6205 if (is_class)
6207 /* Put the method on the list in reverse order. */
6208 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_CLS_METHODS (klass);
6209 PROTOCOL_OPTIONAL_CLS_METHODS (klass) = method;
6211 else
6213 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_NST_METHODS (klass);
6214 PROTOCOL_OPTIONAL_NST_METHODS (klass) = method;
6217 else
6219 if (is_class)
6221 DECL_CHAIN (method) = CLASS_CLS_METHODS (klass);
6222 CLASS_CLS_METHODS (klass) = method;
6224 else
6226 DECL_CHAIN (method) = CLASS_NST_METHODS (klass);
6227 CLASS_NST_METHODS (klass) = method;
6231 else
6233 /* The method was already defined. Check that the types match
6234 for an @interface for a class or category, or for a
6235 @protocol. Give hard errors on methods with identical
6236 selectors but differing argument and/or return types. We do
6237 not do this for @implementations, because C/C++ will do it
6238 for us (i.e., there will be duplicate function definition
6239 errors). */
6240 if ((TREE_CODE (klass) == CLASS_INTERFACE_TYPE
6241 || TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
6242 /* Starting with GCC 4.6, we emit the same error for
6243 protocols too. The situation is identical to
6244 @interfaces as there is no possible meaningful reason
6245 for defining the same method with different signatures
6246 in the very same @protocol. If that was allowed,
6247 whenever the protocol is used (both at compile and run
6248 time) there wouldn't be any meaningful way to decide
6249 which of the two method signatures should be used. */
6250 || TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE)
6251 && !comp_proto_with_proto (method, existing_method, 1))
6253 error ("duplicate declaration of method %<%c%E%> with conflicting types",
6254 (is_class ? '+' : '-'),
6255 METHOD_SEL_NAME (existing_method));
6256 inform (DECL_SOURCE_LOCATION (existing_method),
6257 "previous declaration of %<%c%E%>",
6258 (is_class ? '+' : '-'),
6259 METHOD_SEL_NAME (existing_method));
6263 if (is_class)
6264 insert_method_into_method_map (true, method);
6265 else
6267 insert_method_into_method_map (false, method);
6269 /* Instance methods in root classes (and categories thereof)
6270 may act as class methods as a last resort. We also add
6271 instance methods listed in @protocol declarations to
6272 the class hash table, on the assumption that @protocols
6273 may be adopted by root classes or categories. */
6274 if (TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
6275 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
6276 klass = lookup_interface (CLASS_NAME (klass));
6278 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE
6279 || !CLASS_SUPER_NAME (klass))
6280 insert_method_into_method_map (true, method);
6283 return method;
6286 static void
6287 add_category (tree klass, tree category)
6289 /* Put categories on list in reverse order. */
6290 tree cat = lookup_category (klass, CLASS_SUPER_NAME (category));
6292 if (cat)
6294 warning (0, "duplicate interface declaration for category %<%E(%E)%>",
6295 CLASS_NAME (klass),
6296 CLASS_SUPER_NAME (category));
6298 else
6300 CLASS_CATEGORY_LIST (category) = CLASS_CATEGORY_LIST (klass);
6301 CLASS_CATEGORY_LIST (klass) = category;
6305 #ifndef OBJCPLUS
6306 /* A flexible array member is a C99 extension where you can use
6307 "type[]" at the end of a struct to mean a variable-length array.
6309 In Objective-C, instance variables are fundamentally members of a
6310 struct, but the struct can always be extended by subclassing; hence
6311 we need to detect and forbid all instance variables declared using
6312 flexible array members.
6314 No check for this is needed in Objective-C++, since C++ does not
6315 have flexible array members. */
6317 /* Determine whether TYPE is a structure with a flexible array member,
6318 a union containing such a structure (possibly recursively) or an
6319 array of such structures or unions. These are all invalid as
6320 instance variable. */
6321 static bool
6322 flexible_array_type_p (tree type)
6324 tree x;
6325 switch (TREE_CODE (type))
6327 case RECORD_TYPE:
6328 x = TYPE_FIELDS (type);
6329 if (x == NULL_TREE)
6330 return false;
6331 while (DECL_CHAIN (x) != NULL_TREE)
6332 x = DECL_CHAIN (x);
6333 if (TREE_CODE (TREE_TYPE (x)) == ARRAY_TYPE
6334 && TYPE_SIZE (TREE_TYPE (x)) == NULL_TREE
6335 && TYPE_DOMAIN (TREE_TYPE (x)) != NULL_TREE
6336 && TYPE_MAX_VALUE (TYPE_DOMAIN (TREE_TYPE (x))) == NULL_TREE)
6337 return true;
6338 return false;
6339 case UNION_TYPE:
6340 for (x = TYPE_FIELDS (type); x != NULL_TREE; x = DECL_CHAIN (x))
6342 if (flexible_array_type_p (TREE_TYPE (x)))
6343 return true;
6345 return false;
6346 /* Note that we also check for arrays of something that uses a flexible array member. */
6347 case ARRAY_TYPE:
6348 if (flexible_array_type_p (TREE_TYPE (type)))
6349 return true;
6350 return false;
6351 default:
6352 return false;
6355 #endif
6357 /* Produce a printable version of an ivar name. This is only used
6358 inside add_instance_variable. */
6359 static const char *
6360 printable_ivar_name (tree field_decl)
6362 if (DECL_NAME (field_decl))
6363 return identifier_to_locale (IDENTIFIER_POINTER (DECL_NAME (field_decl)));
6364 else
6365 return _("<unnamed>");
6368 /* Called after parsing each instance variable declaration. Necessary to
6369 preserve typedefs and implement public/private...
6371 VISIBILITY is 1 for public, 0 for protected, and 2 for private. */
6373 static tree
6374 add_instance_variable (tree klass, objc_ivar_visibility_kind visibility,
6375 tree field_decl)
6377 tree field_type = TREE_TYPE (field_decl);
6379 #ifdef OBJCPLUS
6380 if (TREE_CODE (field_type) == REFERENCE_TYPE)
6382 error ("illegal reference type specified for instance variable %qs",
6383 printable_ivar_name (field_decl));
6384 /* Return class as is without adding this ivar. */
6385 return klass;
6387 #endif
6389 if (field_type == error_mark_node || !TYPE_SIZE (field_type)
6390 || TYPE_SIZE (field_type) == error_mark_node)
6391 /* 'type[0]' is allowed, but 'type[]' is not! */
6393 error ("instance variable %qs has unknown size",
6394 printable_ivar_name (field_decl));
6395 /* Return class as is without adding this ivar. */
6396 return klass;
6399 #ifndef OBJCPLUS
6400 /* Also, in C reject a struct with a flexible array member. Ie,
6402 struct A { int x; int[] y; };
6404 @interface X
6406 struct A instance_variable;
6408 @end
6410 is not valid because if the class is subclassed, we wouldn't be able
6411 to calculate the offset of the next instance variable. */
6412 if (flexible_array_type_p (field_type))
6414 error ("instance variable %qs uses flexible array member",
6415 printable_ivar_name (field_decl));
6416 /* Return class as is without adding this ivar. */
6417 return klass;
6419 #endif
6421 #ifdef OBJCPLUS
6422 /* Check if the ivar being added has a non-POD C++ type. If so, we will
6423 need to either (1) warn the user about it or (2) generate suitable
6424 constructor/destructor call from '- .cxx_construct' or '- .cxx_destruct'
6425 methods (if '-fobjc-call-cxx-cdtors' was specified). */
6426 if (MAYBE_CLASS_TYPE_P (field_type)
6427 && (TYPE_NEEDS_CONSTRUCTING (field_type)
6428 || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type)
6429 || TYPE_POLYMORPHIC_P (field_type)))
6431 tree type_name = OBJC_TYPE_NAME (field_type);
6433 if (flag_objc_call_cxx_cdtors)
6435 /* Since the ObjC runtime will be calling the constructors and
6436 destructors for us, the only thing we can't handle is the lack
6437 of a default constructor. */
6438 if (TYPE_NEEDS_CONSTRUCTING (field_type)
6439 && !TYPE_HAS_DEFAULT_CONSTRUCTOR (field_type))
6441 warning (0, "type %qE has no default constructor to call",
6442 type_name);
6444 /* If we cannot call a constructor, we should also avoid
6445 calling the destructor, for symmetry. */
6446 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
6447 warning (0, "destructor for %qE shall not be run either",
6448 type_name);
6451 else
6453 static bool warn_cxx_ivars = false;
6455 if (TYPE_POLYMORPHIC_P (field_type))
6457 /* Vtable pointers are Real Bad(tm), since Obj-C cannot
6458 initialize them. */
6459 error ("type %qE has virtual member functions", type_name);
6460 error ("illegal aggregate type %qE specified "
6461 "for instance variable %qs",
6462 type_name, printable_ivar_name (field_decl));
6463 /* Return class as is without adding this ivar. */
6464 return klass;
6467 /* User-defined constructors and destructors are not known to Obj-C
6468 and hence will not be called. This may or may not be a problem. */
6469 if (TYPE_NEEDS_CONSTRUCTING (field_type))
6470 warning (0, "type %qE has a user-defined constructor", type_name);
6471 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
6472 warning (0, "type %qE has a user-defined destructor", type_name);
6474 if (!warn_cxx_ivars)
6476 warning (0, "C++ constructors and destructors will not "
6477 "be invoked for Objective-C fields");
6478 warn_cxx_ivars = true;
6482 #endif
6484 /* Overload the public attribute, it is not used for FIELD_DECLs. */
6485 switch (visibility)
6487 case OBJC_IVAR_VIS_PROTECTED:
6488 TREE_PUBLIC (field_decl) = 0;
6489 TREE_PRIVATE (field_decl) = 0;
6490 TREE_PROTECTED (field_decl) = 1;
6491 break;
6493 case OBJC_IVAR_VIS_PACKAGE:
6494 /* TODO: Implement the package variant. */
6495 case OBJC_IVAR_VIS_PUBLIC:
6496 TREE_PUBLIC (field_decl) = 1;
6497 TREE_PRIVATE (field_decl) = 0;
6498 TREE_PROTECTED (field_decl) = 0;
6499 break;
6501 case OBJC_IVAR_VIS_PRIVATE:
6502 TREE_PUBLIC (field_decl) = 0;
6503 TREE_PRIVATE (field_decl) = 1;
6504 TREE_PROTECTED (field_decl) = 0;
6505 break;
6509 CLASS_RAW_IVARS (klass) = chainon (CLASS_RAW_IVARS (klass), field_decl);
6511 return klass;
6514 /* True if the ivar is private and we are not in its implementation. */
6516 static int
6517 is_private (tree decl)
6519 return (TREE_PRIVATE (decl)
6520 && ! is_ivar (CLASS_IVARS (implementation_template),
6521 DECL_NAME (decl)));
6524 /* Searches all the instance variables of 'klass' and of its
6525 superclasses for an instance variable whose name (identifier) is
6526 'ivar_name_ident'. Return the declaration (DECL) of the instance
6527 variable, if found, or NULL_TREE, if not found. */
6528 static inline tree
6529 ivar_of_class (tree klass, tree ivar_name_ident)
6531 /* First, look up the ivar in CLASS_RAW_IVARS. */
6532 tree decl_chain = CLASS_RAW_IVARS (klass);
6534 for ( ; decl_chain; decl_chain = DECL_CHAIN (decl_chain))
6535 if (DECL_NAME (decl_chain) == ivar_name_ident)
6536 return decl_chain;
6538 /* If not found, search up the class hierarchy. */
6539 while (CLASS_SUPER_NAME (klass))
6541 klass = lookup_interface (CLASS_SUPER_NAME (klass));
6543 decl_chain = CLASS_RAW_IVARS (klass);
6545 for ( ; decl_chain; decl_chain = DECL_CHAIN (decl_chain))
6546 if (DECL_NAME (decl_chain) == ivar_name_ident)
6547 return decl_chain;
6550 return NULL_TREE;
6553 /* We have an instance variable reference;, check to see if it is public. */
6556 objc_is_public (tree expr, tree identifier)
6558 tree basetype, decl;
6560 #ifdef OBJCPLUS
6561 if (processing_template_decl)
6562 return 1;
6563 #endif
6565 if (TREE_TYPE (expr) == error_mark_node)
6566 return 1;
6568 basetype = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
6570 if (basetype && TREE_CODE (basetype) == RECORD_TYPE)
6572 if (TYPE_HAS_OBJC_INFO (basetype) && TYPE_OBJC_INTERFACE (basetype))
6574 tree klass = lookup_interface (OBJC_TYPE_NAME (basetype));
6576 if (!klass)
6578 error ("cannot find interface declaration for %qE",
6579 OBJC_TYPE_NAME (basetype));
6580 return 0;
6583 if ((decl = ivar_of_class (klass, identifier)))
6585 if (TREE_PUBLIC (decl))
6586 return 1;
6588 /* Important difference between the Stepstone translator:
6589 all instance variables should be public within the context
6590 of the implementation. */
6591 if (objc_implementation_context
6592 && ((TREE_CODE (objc_implementation_context)
6593 == CLASS_IMPLEMENTATION_TYPE)
6594 || (TREE_CODE (objc_implementation_context)
6595 == CATEGORY_IMPLEMENTATION_TYPE)))
6597 tree curtype = TYPE_MAIN_VARIANT
6598 (CLASS_STATIC_TEMPLATE
6599 (implementation_template));
6601 if (basetype == curtype
6602 || DERIVED_FROM_P (basetype, curtype))
6604 int priv = is_private (decl);
6606 if (priv)
6607 error ("instance variable %qE is declared private",
6608 DECL_NAME (decl));
6610 return !priv;
6614 /* The 2.95.2 compiler sometimes allowed C functions to access
6615 non-@public ivars. We will let this slide for now... */
6616 if (!objc_method_context)
6618 warning (0, "instance variable %qE is %s; "
6619 "this will be a hard error in the future",
6620 identifier,
6621 TREE_PRIVATE (decl) ? "@private" : "@protected");
6622 return 1;
6625 error ("instance variable %qE is declared %s",
6626 identifier,
6627 TREE_PRIVATE (decl) ? "private" : "protected");
6628 return 0;
6633 return 1;
6636 /* Make sure all methods in CHAIN (a list of method declarations from
6637 an @interface or a @protocol) are in IMPLEMENTATION (the
6638 implementation context). This is used to check for example that
6639 all methods declared in an @interface were implemented in an
6640 @implementation.
6642 Some special methods (property setters/getters) are special and if
6643 they are not found in IMPLEMENTATION, we look them up in its
6644 superclasses. */
6646 static int
6647 check_methods (tree chain, tree implementation, int mtype)
6649 int first = 1;
6650 tree list;
6652 if (mtype == (int)'+')
6653 list = CLASS_CLS_METHODS (implementation);
6654 else
6655 list = CLASS_NST_METHODS (implementation);
6657 while (chain)
6659 /* If the method is associated with a dynamic property, then it
6660 is Ok not to have the method implementation, as it will be
6661 generated dynamically at runtime. To decide if the method is
6662 associated with a @dynamic property, we search the list of
6663 @synthesize and @dynamic for this implementation, and look
6664 for any @dynamic property with the same setter or getter name
6665 as this method. */
6666 tree x;
6667 for (x = IMPL_PROPERTY_DECL (implementation); x; x = TREE_CHAIN (x))
6668 if (PROPERTY_DYNAMIC (x)
6669 && (PROPERTY_GETTER_NAME (x) == METHOD_SEL_NAME (chain)
6670 || PROPERTY_SETTER_NAME (x) == METHOD_SEL_NAME (chain)))
6671 break;
6673 if (x != NULL_TREE)
6675 chain = TREE_CHAIN (chain); /* next method... */
6676 continue;
6679 if (!lookup_method (list, chain))
6681 /* If the method is a property setter/getter, we'll still
6682 allow it to be missing if it is implemented by
6683 'interface' or any of its superclasses. */
6684 tree property = METHOD_PROPERTY_CONTEXT (chain);
6685 if (property)
6687 /* Note that since this is a property getter/setter, it
6688 is obviously an instance method. */
6689 tree interface = NULL_TREE;
6691 /* For a category, first check the main class
6692 @interface. */
6693 if (TREE_CODE (implementation) == CATEGORY_IMPLEMENTATION_TYPE)
6695 interface = lookup_interface (CLASS_NAME (implementation));
6697 /* If the method is found in the main class, it's Ok. */
6698 if (lookup_method (CLASS_NST_METHODS (interface), chain))
6700 chain = DECL_CHAIN (chain);
6701 continue;
6704 /* Else, get the superclass. */
6705 if (CLASS_SUPER_NAME (interface))
6706 interface = lookup_interface (CLASS_SUPER_NAME (interface));
6707 else
6708 interface = NULL_TREE;
6711 /* Get the superclass for classes. */
6712 if (TREE_CODE (implementation) == CLASS_IMPLEMENTATION_TYPE)
6714 if (CLASS_SUPER_NAME (implementation))
6715 interface = lookup_interface (CLASS_SUPER_NAME (implementation));
6716 else
6717 interface = NULL_TREE;
6720 /* Now, interface is the superclass, if any; go check it. */
6721 if (interface)
6723 if (lookup_method_static (interface, chain, 0))
6725 chain = DECL_CHAIN (chain);
6726 continue;
6729 /* Else, fall through - warn. */
6731 if (first)
6733 switch (TREE_CODE (implementation))
6735 case CLASS_IMPLEMENTATION_TYPE:
6736 warning (0, "incomplete implementation of class %qE",
6737 CLASS_NAME (implementation));
6738 break;
6739 case CATEGORY_IMPLEMENTATION_TYPE:
6740 warning (0, "incomplete implementation of category %qE",
6741 CLASS_SUPER_NAME (implementation));
6742 break;
6743 default:
6744 gcc_unreachable ();
6746 first = 0;
6749 warning (0, "method definition for %<%c%E%> not found",
6750 mtype, METHOD_SEL_NAME (chain));
6753 chain = DECL_CHAIN (chain);
6756 return first;
6759 /* Check if KLASS, or its superclasses, explicitly conforms to PROTOCOL. */
6761 static int
6762 conforms_to_protocol (tree klass, tree protocol)
6764 if (TREE_CODE (protocol) == PROTOCOL_INTERFACE_TYPE)
6766 tree p = CLASS_PROTOCOL_LIST (klass);
6767 while (p && TREE_VALUE (p) != protocol)
6768 p = TREE_CHAIN (p);
6770 if (!p)
6772 tree super = (CLASS_SUPER_NAME (klass)
6773 ? lookup_interface (CLASS_SUPER_NAME (klass))
6774 : NULL_TREE);
6775 int tmp = super ? conforms_to_protocol (super, protocol) : 0;
6776 if (!tmp)
6777 return 0;
6781 return 1;
6784 /* Make sure all methods in CHAIN are accessible as MTYPE methods in
6785 CONTEXT. This is one of two mechanisms to check protocol integrity. */
6787 static int
6788 check_methods_accessible (tree chain, tree context, int mtype)
6790 int first = 1;
6791 tree list;
6792 tree base_context = context;
6794 while (chain)
6796 /* If the method is associated with a dynamic property, then it
6797 is Ok not to have the method implementation, as it will be
6798 generated dynamically at runtime. Search for any @dynamic
6799 property with the same setter or getter name as this
6800 method. TODO: Use a hashtable lookup. */
6801 tree x;
6802 for (x = IMPL_PROPERTY_DECL (base_context); x; x = TREE_CHAIN (x))
6803 if (PROPERTY_DYNAMIC (x)
6804 && (PROPERTY_GETTER_NAME (x) == METHOD_SEL_NAME (chain)
6805 || PROPERTY_SETTER_NAME (x) == METHOD_SEL_NAME (chain)))
6806 break;
6808 if (x != NULL_TREE)
6810 chain = TREE_CHAIN (chain); /* next method... */
6811 continue;
6814 context = base_context;
6815 while (context)
6817 if (mtype == '+')
6818 list = CLASS_CLS_METHODS (context);
6819 else
6820 list = CLASS_NST_METHODS (context);
6822 if (lookup_method (list, chain))
6823 break;
6825 switch (TREE_CODE (context))
6827 case CLASS_IMPLEMENTATION_TYPE:
6828 case CLASS_INTERFACE_TYPE:
6829 context = (CLASS_SUPER_NAME (context)
6830 ? lookup_interface (CLASS_SUPER_NAME (context))
6831 : NULL_TREE);
6832 break;
6833 case CATEGORY_IMPLEMENTATION_TYPE:
6834 case CATEGORY_INTERFACE_TYPE:
6835 context = (CLASS_NAME (context)
6836 ? lookup_interface (CLASS_NAME (context))
6837 : NULL_TREE);
6838 break;
6839 default:
6840 gcc_unreachable ();
6844 if (context == NULL_TREE)
6846 if (first)
6848 switch (TREE_CODE (objc_implementation_context))
6850 case CLASS_IMPLEMENTATION_TYPE:
6851 warning (0, "incomplete implementation of class %qE",
6852 CLASS_NAME (objc_implementation_context));
6853 break;
6854 case CATEGORY_IMPLEMENTATION_TYPE:
6855 warning (0, "incomplete implementation of category %qE",
6856 CLASS_SUPER_NAME (objc_implementation_context));
6857 break;
6858 default:
6859 gcc_unreachable ();
6861 first = 0;
6863 warning (0, "method definition for %<%c%E%> not found",
6864 mtype, METHOD_SEL_NAME (chain));
6867 chain = TREE_CHAIN (chain); /* next method... */
6869 return first;
6872 /* Check whether the current interface (accessible via
6873 'objc_implementation_context') actually implements protocol P, along
6874 with any protocols that P inherits. */
6876 static void
6877 check_protocol (tree p, const char *type, tree name)
6879 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
6881 int f1, f2;
6883 /* Ensure that all protocols have bodies! */
6884 if (warn_protocol)
6886 f1 = check_methods (PROTOCOL_CLS_METHODS (p),
6887 objc_implementation_context,
6888 '+');
6889 f2 = check_methods (PROTOCOL_NST_METHODS (p),
6890 objc_implementation_context,
6891 '-');
6893 else
6895 f1 = check_methods_accessible (PROTOCOL_CLS_METHODS (p),
6896 objc_implementation_context,
6897 '+');
6898 f2 = check_methods_accessible (PROTOCOL_NST_METHODS (p),
6899 objc_implementation_context,
6900 '-');
6903 if (!f1 || !f2)
6904 warning (0, "%s %qE does not fully implement the %qE protocol",
6905 type, name, PROTOCOL_NAME (p));
6908 /* Check protocols recursively. */
6909 if (PROTOCOL_LIST (p))
6911 tree subs = PROTOCOL_LIST (p);
6912 tree super_class =
6913 lookup_interface (CLASS_SUPER_NAME (implementation_template));
6915 while (subs)
6917 tree sub = TREE_VALUE (subs);
6919 /* If the superclass does not conform to the protocols
6920 inherited by P, then we must! */
6921 if (!super_class || !conforms_to_protocol (super_class, sub))
6922 check_protocol (sub, type, name);
6923 subs = TREE_CHAIN (subs);
6928 /* Check whether the current interface (accessible via
6929 'objc_implementation_context') actually implements the protocols listed
6930 in PROTO_LIST. */
6932 static void
6933 check_protocols (tree proto_list, const char *type, tree name)
6935 for ( ; proto_list; proto_list = TREE_CHAIN (proto_list))
6937 tree p = TREE_VALUE (proto_list);
6939 check_protocol (p, type, name);
6943 /* Make sure that the class CLASS_NAME is defined CODE says which kind
6944 of thing CLASS_NAME ought to be. It can be CLASS_INTERFACE_TYPE,
6945 CLASS_IMPLEMENTATION_TYPE, CATEGORY_INTERFACE_TYPE, or
6946 CATEGORY_IMPLEMENTATION_TYPE. For a CATEGORY_INTERFACE_TYPE,
6947 SUPER_NAME is the name of the category. For a class extension,
6948 CODE is CATEGORY_INTERFACE_TYPE and SUPER_NAME is NULL_TREE. */
6949 static tree
6950 start_class (enum tree_code code, tree class_name, tree super_name,
6951 tree protocol_list, tree attributes)
6953 tree klass = NULL_TREE;
6954 tree decl;
6956 #ifdef OBJCPLUS
6957 if (current_namespace != global_namespace)
6959 error ("Objective-C declarations may only appear in global scope");
6961 #endif /* OBJCPLUS */
6963 if (objc_implementation_context)
6965 warning (0, "%<@end%> missing in implementation context");
6966 finish_class (objc_implementation_context);
6967 objc_ivar_chain = NULL_TREE;
6968 objc_implementation_context = NULL_TREE;
6971 /* If this is a class extension, we'll be "reopening" the existing
6972 CLASS_INTERFACE_TYPE, so in that case there is no need to create
6973 a new node. */
6974 if (code != CATEGORY_INTERFACE_TYPE || super_name != NULL_TREE)
6976 klass = make_node (code);
6977 TYPE_LANG_SLOT_1 (klass) = make_tree_vec (CLASS_LANG_SLOT_ELTS);
6980 /* Check for existence of the super class, if one was specified. Note
6981 that we must have seen an @interface, not just a @class. If we
6982 are looking at a @compatibility_alias, traverse it first. */
6983 if ((code == CLASS_INTERFACE_TYPE || code == CLASS_IMPLEMENTATION_TYPE)
6984 && super_name)
6986 tree super = objc_is_class_name (super_name);
6987 tree super_interface = NULL_TREE;
6989 if (super)
6990 super_interface = lookup_interface (super);
6992 if (!super_interface)
6994 error ("cannot find interface declaration for %qE, superclass of %qE",
6995 super ? super : super_name,
6996 class_name);
6997 super_name = NULL_TREE;
6999 else
7001 if (TREE_UNAVAILABLE (super_interface))
7002 error ("class %qE is not available", super);
7003 else if (TREE_DEPRECATED (super_interface))
7004 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated",
7005 super);
7006 super_name = super;
7010 if (code != CATEGORY_INTERFACE_TYPE || super_name != NULL_TREE)
7012 CLASS_NAME (klass) = class_name;
7013 CLASS_SUPER_NAME (klass) = super_name;
7014 CLASS_CLS_METHODS (klass) = NULL_TREE;
7017 if (! objc_is_class_name (class_name)
7018 && (decl = lookup_name (class_name)))
7020 error ("%qE redeclared as different kind of symbol",
7021 class_name);
7022 error ("previous declaration of %q+D",
7023 decl);
7026 switch (code)
7028 case CLASS_IMPLEMENTATION_TYPE:
7030 tree chain;
7032 for (chain = implemented_classes; chain; chain = TREE_CHAIN (chain))
7033 if (TREE_VALUE (chain) == class_name)
7035 error ("reimplementation of class %qE",
7036 class_name);
7037 /* TODO: error message saying where it was previously
7038 implemented. */
7039 break;
7041 if (chain == NULL_TREE)
7042 implemented_classes = tree_cons (NULL_TREE, class_name,
7043 implemented_classes);
7046 /* Reset for multiple classes per file. */
7047 method_slot = 0;
7049 objc_implementation_context = klass;
7051 /* Lookup the interface for this implementation. */
7053 if (!(implementation_template = lookup_interface (class_name)))
7055 warning (0, "cannot find interface declaration for %qE",
7056 class_name);
7057 add_interface (implementation_template = objc_implementation_context,
7058 class_name);
7061 /* If a super class has been specified in the implementation,
7062 insure it conforms to the one specified in the interface. */
7064 if (super_name
7065 && (super_name != CLASS_SUPER_NAME (implementation_template)))
7067 tree previous_name = CLASS_SUPER_NAME (implementation_template);
7068 error ("conflicting super class name %qE",
7069 super_name);
7070 if (previous_name)
7071 error ("previous declaration of %qE", previous_name);
7072 else
7073 error ("previous declaration");
7076 else if (! super_name)
7078 CLASS_SUPER_NAME (objc_implementation_context)
7079 = CLASS_SUPER_NAME (implementation_template);
7082 if (!CLASS_SUPER_NAME (objc_implementation_context)
7083 && !lookup_attribute ("objc_root_class",
7084 TYPE_ATTRIBUTES (implementation_template)))
7085 warning (OPT_Wobjc_root_class, "class %qE defined without"
7086 " specifying a base class", class_name);
7087 break;
7089 case CLASS_INTERFACE_TYPE:
7090 if (lookup_interface (class_name))
7091 #ifdef OBJCPLUS
7092 error ("duplicate interface declaration for class %qE", class_name);
7093 #else
7094 warning (0, "duplicate interface declaration for class %qE", class_name);
7095 #endif
7096 else
7097 add_interface (klass, class_name);
7099 if (protocol_list)
7100 CLASS_PROTOCOL_LIST (klass)
7101 = lookup_and_install_protocols (protocol_list, /* definition_required */ true);
7103 if (attributes)
7105 tree attribute;
7106 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
7108 tree name = TREE_PURPOSE (attribute);
7110 /* TODO: Document what the objc_exception attribute is/does. */
7111 /* We handle the 'deprecated', 'visibility' and (undocumented)
7112 'objc_exception' attributes. */
7113 if (is_attribute_p ("unavailable", name))
7114 TREE_UNAVAILABLE (klass) = 1;
7115 else if (is_attribute_p ("deprecated", name))
7116 TREE_DEPRECATED (klass) = 1;
7117 else if (is_attribute_p ("objc_exception", name))
7118 CLASS_HAS_EXCEPTION_ATTR (klass) = 1;
7119 else if (is_attribute_p ("objc_root_class", name))
7121 else if (is_attribute_p ("visibility", name))
7123 else
7124 /* Warn about and ignore all others for now, but store them. */
7125 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
7127 TYPE_ATTRIBUTES (klass) = attributes;
7129 break;
7131 case CATEGORY_INTERFACE_TYPE:
7133 tree class_category_is_assoc_with;
7135 /* For a category, class_name is really the name of the class that
7136 the following set of methods will be associated with. We must
7137 find the interface so that can derive the objects template. */
7138 if (!(class_category_is_assoc_with = lookup_interface (class_name)))
7140 error ("cannot find interface declaration for %qE",
7141 class_name);
7142 exit (FATAL_EXIT_CODE);
7144 else
7146 if (TREE_UNAVAILABLE (class_category_is_assoc_with))
7147 error ("class %qE is unavailable", class_name);
7148 else if (TREE_DEPRECATED (class_category_is_assoc_with))
7149 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated",
7150 class_name);
7152 if (super_name == NULL_TREE)
7154 /* This is a class extension. Get the original
7155 interface, and continue working on it. */
7156 objc_in_class_extension = true;
7157 klass = class_category_is_assoc_with;
7159 if (protocol_list)
7161 /* Append protocols to the original protocol
7162 list. */
7163 CLASS_PROTOCOL_LIST (klass)
7164 = chainon (CLASS_PROTOCOL_LIST (klass),
7165 lookup_and_install_protocols
7166 (protocol_list,
7167 /* definition_required */ true));
7170 else
7172 add_category (class_category_is_assoc_with, klass);
7174 if (protocol_list)
7175 CLASS_PROTOCOL_LIST (klass)
7176 = lookup_and_install_protocols
7177 (protocol_list, /* definition_required */ true);
7181 break;
7183 case CATEGORY_IMPLEMENTATION_TYPE:
7184 /* Reset for multiple classes per file. */
7185 method_slot = 0;
7187 objc_implementation_context = klass;
7189 /* For a category, class_name is really the name of the class that
7190 the following set of methods will be associated with. We must
7191 find the interface so that can derive the objects template. */
7193 if (!(implementation_template = lookup_interface (class_name)))
7195 error ("cannot find interface declaration for %qE",
7196 class_name);
7197 exit (FATAL_EXIT_CODE);
7199 break;
7200 default:
7201 gcc_unreachable ();
7203 return klass;
7206 static tree
7207 continue_class (tree klass)
7209 switch (TREE_CODE (klass))
7211 case CLASS_IMPLEMENTATION_TYPE:
7212 case CATEGORY_IMPLEMENTATION_TYPE:
7214 struct imp_entry *imp_entry;
7216 /* Check consistency of the instance variables. */
7218 if (CLASS_RAW_IVARS (klass))
7219 check_ivars (implementation_template, klass);
7221 /* code generation */
7222 #ifdef OBJCPLUS
7223 push_lang_context (lang_name_c);
7224 #endif
7225 build_private_template (implementation_template);
7226 uprivate_record = CLASS_STATIC_TEMPLATE (implementation_template);
7227 objc_instance_type = build_pointer_type (uprivate_record);
7229 imp_entry = ggc_alloc<struct imp_entry> ();
7231 imp_entry->next = imp_list;
7232 imp_entry->imp_context = klass;
7233 imp_entry->imp_template = implementation_template;
7234 ucls_super_ref = uucls_super_ref = NULL;
7235 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7237 imp_entry->class_decl = (*runtime.class_decl) (klass);
7238 imp_entry->meta_decl = (*runtime.metaclass_decl) (klass);
7240 else
7242 imp_entry->class_decl = (*runtime.category_decl) (klass);
7243 imp_entry->meta_decl = NULL;
7245 imp_entry->has_cxx_cdtors = 0;
7247 /* Append to front and increment count. */
7248 imp_list = imp_entry;
7249 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7250 imp_count++;
7251 else
7252 cat_count++;
7253 #ifdef OBJCPLUS
7254 pop_lang_context ();
7255 #endif /* OBJCPLUS */
7257 return get_class_ivars (implementation_template, true);
7259 case CLASS_INTERFACE_TYPE:
7261 if (objc_in_class_extension)
7262 return NULL_TREE;
7263 #ifdef OBJCPLUS
7264 push_lang_context (lang_name_c);
7265 #endif /* OBJCPLUS */
7266 objc_collecting_ivars = 1;
7267 build_private_template (klass);
7268 objc_collecting_ivars = 0;
7269 #ifdef OBJCPLUS
7270 pop_lang_context ();
7271 #endif /* OBJCPLUS */
7272 return NULL_TREE;
7274 default:
7275 return error_mark_node;
7279 /* This routine builds name of the setter synthesized function. */
7280 char *
7281 objc_build_property_setter_name (tree ident)
7283 /* TODO: Use alloca to allocate buffer of appropriate size. */
7284 static char string[BUFSIZE];
7285 sprintf (string, "set%s:", IDENTIFIER_POINTER (ident));
7286 string[3] = TOUPPER (string[3]);
7287 return string;
7290 /* This routine prepares the declarations of the property accessor
7291 helper functions (objc_getProperty(), etc) that are used when
7292 @synthesize is used.
7294 runtime-specific routines are built in the respective runtime
7295 initialize functions. */
7296 static void
7297 build_common_objc_property_accessor_helpers (void)
7299 tree type;
7301 /* Declare the following function:
7303 objc_getProperty (id self, SEL _cmd,
7304 ptrdiff_t offset, BOOL is_atomic); */
7305 type = build_function_type_list (objc_object_type,
7306 objc_object_type,
7307 objc_selector_type,
7308 ptrdiff_type_node,
7309 boolean_type_node,
7310 NULL_TREE);
7311 objc_getProperty_decl = add_builtin_function ("objc_getProperty",
7312 type, 0, NOT_BUILT_IN,
7313 NULL, NULL_TREE);
7314 TREE_NOTHROW (objc_getProperty_decl) = 0;
7316 /* Declare the following function:
7317 void
7318 objc_setProperty (id self, SEL _cmd,
7319 ptrdiff_t offset, id new_value,
7320 BOOL is_atomic, BOOL should_copy); */
7321 type = build_function_type_list (void_type_node,
7322 objc_object_type,
7323 objc_selector_type,
7324 ptrdiff_type_node,
7325 objc_object_type,
7326 boolean_type_node,
7327 boolean_type_node,
7328 NULL_TREE);
7329 objc_setProperty_decl = add_builtin_function ("objc_setProperty",
7330 type, 0, NOT_BUILT_IN,
7331 NULL, NULL_TREE);
7332 TREE_NOTHROW (objc_setProperty_decl) = 0;
7335 /* This looks up an ivar in a class (including superclasses). */
7336 static tree
7337 lookup_ivar (tree interface, tree instance_variable_name)
7339 while (interface)
7341 tree decl_chain;
7343 for (decl_chain = CLASS_IVARS (interface); decl_chain; decl_chain = DECL_CHAIN (decl_chain))
7344 if (DECL_NAME (decl_chain) == instance_variable_name)
7345 return decl_chain;
7347 /* Not found. Search superclass if any. */
7348 if (CLASS_SUPER_NAME (interface))
7349 interface = lookup_interface (CLASS_SUPER_NAME (interface));
7352 return NULL_TREE;
7355 /* This routine synthesizes a 'getter' method. This is only called
7356 for @synthesize properties. */
7357 static void
7358 objc_synthesize_getter (tree klass, tree class_methods ATTRIBUTE_UNUSED, tree property)
7360 location_t location = DECL_SOURCE_LOCATION (property);
7361 tree fn, decl;
7362 tree body;
7363 tree ret_val;
7365 /* If user has implemented a getter with same name then do nothing. */
7366 if (lookup_method (CLASS_NST_METHODS (objc_implementation_context),
7367 PROPERTY_GETTER_NAME (property)))
7368 return;
7370 /* Find declaration of the property getter in the interface (or
7371 superclass, or protocol). There must be one. */
7372 decl = lookup_method_static (klass, PROPERTY_GETTER_NAME (property), 0);
7374 /* If one not declared in the interface, this condition has already
7375 been reported as user error (because property was not declared in
7376 the interface). */
7377 if (!decl)
7378 return;
7380 /* Adapt the 'decl'. Use the source location of the @synthesize
7381 statement for error messages. */
7382 decl = copy_node (decl);
7383 DECL_SOURCE_LOCATION (decl) = location;
7385 objc_start_method_definition (false /* is_class_method */, decl, NULL_TREE,
7386 NULL_TREE);
7387 body = c_begin_compound_stmt (true);
7389 /* Now we need to decide how we build the getter. There are three
7390 cases:
7392 for 'copy' or 'retain' properties we need to use the
7393 objc_getProperty() accessor helper which knows about retain and
7394 copy. It supports both 'nonatomic' and 'atomic' access.
7396 for 'nonatomic, assign' properties we can access the instance
7397 variable directly. 'nonatomic' means we don't have to use locks,
7398 and 'assign' means we don't have to worry about retain or copy.
7399 If you combine the two, it means we can just access the instance
7400 variable directly.
7402 for 'atomic, assign' properties we use objc_copyStruct() (for the
7403 next runtime) or objc_getPropertyStruct() (for the GNU runtime). */
7404 switch (PROPERTY_ASSIGN_SEMANTICS (property))
7406 case OBJC_PROPERTY_RETAIN:
7407 case OBJC_PROPERTY_COPY:
7409 /* We build "return objc_getProperty (self, _cmd, offset, is_atomic);" */
7410 tree cmd, ivar, offset, is_atomic;
7411 cmd = TREE_CHAIN (DECL_ARGUMENTS (current_function_decl));
7413 /* Find the ivar to compute the offset. */
7414 ivar = lookup_ivar (klass, PROPERTY_IVAR_NAME (property));
7415 if (!ivar || is_private (ivar))
7417 /* This should never happen. */
7418 error_at (location,
7419 "cannot find instance variable associated with property");
7420 ret_val = error_mark_node;
7421 break;
7423 offset = byte_position (ivar);
7425 if (PROPERTY_NONATOMIC (property))
7426 is_atomic = boolean_false_node;
7427 else
7428 is_atomic = boolean_true_node;
7430 ret_val = build_function_call
7431 (location,
7432 /* Function prototype. */
7433 objc_getProperty_decl,
7434 /* Parameters. */
7435 tree_cons /* self */
7436 (NULL_TREE, self_decl,
7437 tree_cons /* _cmd */
7438 (NULL_TREE, cmd,
7439 tree_cons /* offset */
7440 (NULL_TREE, offset,
7441 tree_cons /* is_atomic */
7442 (NULL_TREE, is_atomic, NULL_TREE)))));
7444 break;
7445 case OBJC_PROPERTY_ASSIGN:
7446 if (PROPERTY_NONATOMIC (property))
7448 /* We build "return self->PROPERTY_IVAR_NAME;" */
7449 ret_val = objc_lookup_ivar (NULL_TREE, PROPERTY_IVAR_NAME (property));
7450 break;
7452 else
7454 /* We build
7455 <property type> __objc_property_temp;
7456 objc_getPropertyStruct (&__objc_property_temp,
7457 &(self->PROPERTY_IVAR_NAME),
7458 sizeof (type of self->PROPERTY_IVAR_NAME),
7459 is_atomic,
7460 false)
7461 return __objc_property_temp;
7463 For the NeXT runtime, we need to use objc_copyStruct
7464 instead of objc_getPropertyStruct. */
7465 tree objc_property_temp_decl, function_decl, function_call;
7466 tree size_of, is_atomic;
7468 objc_property_temp_decl = objc_create_temporary_var (TREE_TYPE (property), "__objc_property_temp");
7469 DECL_SOURCE_LOCATION (objc_property_temp_decl) = location;
7470 objc_property_temp_decl = lang_hooks.decls.pushdecl (objc_property_temp_decl);
7472 /* sizeof (ivar type). Since the ivar and the property have
7473 the same type, there is no need to lookup the ivar. */
7474 size_of = c_sizeof_or_alignof_type (location, TREE_TYPE (property),
7475 true /* is_sizeof */,
7476 false /* min_alignof */,
7477 false /* complain */);
7479 if (PROPERTY_NONATOMIC (property))
7480 is_atomic = boolean_false_node;
7481 else
7482 is_atomic = boolean_true_node;
7484 if (objc_copyStruct_decl)
7485 function_decl = objc_copyStruct_decl;
7486 else
7487 function_decl = objc_getPropertyStruct_decl;
7489 function_call = build_function_call
7490 (location,
7491 /* Function prototype. */
7492 function_decl,
7493 /* Parameters. */
7494 tree_cons /* &__objc_property_temp_decl */
7495 /* Warning: note that using build_fold_addr_expr_loc()
7496 here causes invalid code to be generated. */
7497 (NULL_TREE, build_unary_op (location, ADDR_EXPR, objc_property_temp_decl, 0),
7498 tree_cons /* &(self->PROPERTY_IVAR_NAME); */
7499 (NULL_TREE, build_fold_addr_expr_loc (location,
7500 objc_lookup_ivar
7501 (NULL_TREE, PROPERTY_IVAR_NAME (property))),
7502 tree_cons /* sizeof (PROPERTY_IVAR) */
7503 (NULL_TREE, size_of,
7504 tree_cons /* is_atomic */
7505 (NULL_TREE, is_atomic,
7506 /* TODO: This is currently ignored by the GNU
7507 runtime, but what about the next one ? */
7508 tree_cons /* has_strong */
7509 (NULL_TREE, boolean_true_node, NULL_TREE))))));
7511 add_stmt (function_call);
7513 ret_val = objc_property_temp_decl;
7515 break;
7516 default:
7517 gcc_unreachable ();
7520 gcc_assert (ret_val);
7522 #ifdef OBJCPLUS
7523 finish_return_stmt (ret_val);
7524 #else
7525 c_finish_return (location, ret_val, NULL_TREE);
7526 #endif
7528 add_stmt (c_end_compound_stmt (location, body, true));
7529 fn = current_function_decl;
7530 #ifdef OBJCPLUS
7531 finish_function ();
7532 #endif
7533 objc_finish_method_definition (fn);
7536 /* This routine synthesizes a 'setter' method. */
7538 static void
7539 objc_synthesize_setter (tree klass, tree class_methods ATTRIBUTE_UNUSED, tree property)
7541 location_t location = DECL_SOURCE_LOCATION (property);
7542 tree fn, decl;
7543 tree body;
7544 tree new_value, statement;
7546 /* If user has implemented a setter with same name then do nothing. */
7547 if (lookup_method (CLASS_NST_METHODS (objc_implementation_context),
7548 PROPERTY_SETTER_NAME (property)))
7549 return;
7551 /* Find declaration of the property setter in the interface (or
7552 superclass, or protocol). There must be one. */
7553 decl = lookup_method_static (klass, PROPERTY_SETTER_NAME (property), 0);
7555 /* If one not declared in the interface, this condition has already
7556 been reported as user error (because property was not declared in
7557 the interface). */
7558 if (!decl)
7559 return;
7561 /* Adapt the 'decl'. Use the source location of the @synthesize
7562 statement for error messages. */
7563 decl = copy_node (decl);
7564 DECL_SOURCE_LOCATION (decl) = DECL_SOURCE_LOCATION (property);
7566 objc_start_method_definition (false /* is_class_method */, decl, NULL_TREE,
7567 NULL_TREE);
7569 body = c_begin_compound_stmt (true);
7571 /* The 'new_value' is the only argument to the method, which is the
7572 3rd argument of the function, after self and _cmd. We use twice
7573 TREE_CHAIN to move forward two arguments. */
7574 new_value = TREE_CHAIN (TREE_CHAIN (DECL_ARGUMENTS (current_function_decl)));
7576 /* This would presumably happen if the user has specified a
7577 prototype for the setter that does not have an argument! */
7578 if (new_value == NULL_TREE)
7580 /* TODO: This should be caught much earlier than this. */
7581 error_at (DECL_SOURCE_LOCATION (decl), "invalid setter, it must have one argument");
7582 /* Try to recover somehow. */
7583 new_value = error_mark_node;
7586 /* Now we need to decide how we build the setter. There are three
7587 cases:
7589 for 'copy' or 'retain' properties we need to use the
7590 objc_setProperty() accessor helper which knows about retain and
7591 copy. It supports both 'nonatomic' and 'atomic' access.
7593 for 'nonatomic, assign' properties we can access the instance
7594 variable directly. 'nonatomic' means we don't have to use locks,
7595 and 'assign' means we don't have to worry about retain or copy.
7596 If you combine the two, it means we can just access the instance
7597 variable directly.
7599 for 'atomic, assign' properties we use objc_copyStruct() (for the
7600 next runtime) or objc_setPropertyStruct() (for the GNU runtime). */
7601 switch (PROPERTY_ASSIGN_SEMANTICS (property))
7603 case OBJC_PROPERTY_RETAIN:
7604 case OBJC_PROPERTY_COPY:
7606 /* We build "objc_setProperty (self, _cmd, new_value, offset, is_atomic, should_copy);" */
7607 tree cmd, ivar, offset, is_atomic, should_copy;
7608 cmd = TREE_CHAIN (DECL_ARGUMENTS (current_function_decl));
7610 /* Find the ivar to compute the offset. */
7611 ivar = lookup_ivar (klass, PROPERTY_IVAR_NAME (property));
7612 if (!ivar || is_private (ivar))
7614 error_at (location,
7615 "cannot find instance variable associated with property");
7616 statement = error_mark_node;
7617 break;
7619 offset = byte_position (ivar);
7621 if (PROPERTY_NONATOMIC (property))
7622 is_atomic = boolean_false_node;
7623 else
7624 is_atomic = boolean_true_node;
7626 if (PROPERTY_ASSIGN_SEMANTICS (property) == OBJC_PROPERTY_COPY)
7627 should_copy = boolean_true_node;
7628 else
7629 should_copy = boolean_false_node;
7631 statement = build_function_call
7632 (location,
7633 /* Function prototype. */
7634 objc_setProperty_decl,
7635 /* Parameters. */
7636 tree_cons /* self */
7637 (NULL_TREE, self_decl,
7638 tree_cons /* _cmd */
7639 (NULL_TREE, cmd,
7640 tree_cons /* offset */
7641 (NULL_TREE, offset,
7642 tree_cons /* new_value */
7643 (NULL_TREE, new_value,
7644 tree_cons /* is_atomic */
7645 (NULL_TREE, is_atomic,
7646 tree_cons /* should_copy */
7647 (NULL_TREE, should_copy, NULL_TREE)))))));
7649 break;
7650 case OBJC_PROPERTY_ASSIGN:
7651 if (PROPERTY_NONATOMIC (property))
7653 /* We build "self->PROPERTY_IVAR_NAME = new_value;" */
7654 statement = build_modify_expr
7655 (location,
7656 objc_lookup_ivar (NULL_TREE, PROPERTY_IVAR_NAME (property)),
7657 NULL_TREE, NOP_EXPR,
7658 location, new_value, NULL_TREE);
7659 break;
7661 else
7663 /* We build
7664 objc_setPropertyStruct (&(self->PROPERTY_IVAR_NAME),
7665 &new_value,
7666 sizeof (type of self->PROPERTY_IVAR_NAME),
7667 is_atomic,
7668 false)
7670 For the NeXT runtime, we need to use objc_copyStruct
7671 instead of objc_getPropertyStruct. */
7672 tree function_decl, size_of, is_atomic;
7674 /* sizeof (ivar type). Since the ivar and the property have
7675 the same type, there is no need to lookup the ivar. */
7676 size_of = c_sizeof_or_alignof_type (location, TREE_TYPE (property),
7677 true /* is_sizeof */,
7678 false /* min_alignof */,
7679 false /* complain */);
7681 if (PROPERTY_NONATOMIC (property))
7682 is_atomic = boolean_false_node;
7683 else
7684 is_atomic = boolean_true_node;
7686 if (objc_copyStruct_decl)
7687 function_decl = objc_copyStruct_decl;
7688 else
7689 function_decl = objc_setPropertyStruct_decl;
7691 statement = build_function_call
7692 (location,
7693 /* Function prototype. */
7694 function_decl,
7695 /* Parameters. */
7696 tree_cons /* &(self->PROPERTY_IVAR_NAME); */
7697 (NULL_TREE, build_fold_addr_expr_loc (location,
7698 objc_lookup_ivar
7699 (NULL_TREE, PROPERTY_IVAR_NAME (property))),
7700 tree_cons /* &new_value */
7701 (NULL_TREE, build_fold_addr_expr_loc (location, new_value),
7702 tree_cons /* sizeof (PROPERTY_IVAR) */
7703 (NULL_TREE, size_of,
7704 tree_cons /* is_atomic */
7705 (NULL_TREE, is_atomic,
7706 /* TODO: This is currently ignored by the GNU
7707 runtime, but what about the next one ? */
7708 tree_cons /* has_strong */
7709 (NULL_TREE, boolean_true_node, NULL_TREE))))));
7711 break;
7712 default:
7713 gcc_unreachable ();
7715 gcc_assert (statement);
7717 add_stmt (statement);
7718 add_stmt (c_end_compound_stmt (location, body, true));
7719 fn = current_function_decl;
7720 #ifdef OBJCPLUS
7721 finish_function ();
7722 #endif
7723 objc_finish_method_definition (fn);
7726 /* This function is a sub-routine of objc_add_synthesize_declaration.
7727 It is called for each property to synthesize once we have
7728 determined that the context is Ok. */
7729 static void
7730 objc_add_synthesize_declaration_for_property (location_t location, tree interface,
7731 tree property_name, tree ivar_name)
7733 /* Find the @property declaration. */
7734 tree property;
7735 tree x;
7737 /* Check that synthesize or dynamic has not already been used for
7738 the same property. */
7739 for (property = IMPL_PROPERTY_DECL (objc_implementation_context); property; property = TREE_CHAIN (property))
7740 if (PROPERTY_NAME (property) == property_name)
7742 location_t original_location = DECL_SOURCE_LOCATION (property);
7744 if (PROPERTY_DYNAMIC (property))
7745 error_at (location, "property %qs already specified in %<@dynamic%>",
7746 IDENTIFIER_POINTER (property_name));
7747 else
7748 error_at (location, "property %qs already specified in %<@synthesize%>",
7749 IDENTIFIER_POINTER (property_name));
7751 if (original_location != UNKNOWN_LOCATION)
7752 inform (original_location, "originally specified here");
7753 return;
7756 /* Check that the property is declared in the interface. It could
7757 also be declared in a superclass or protocol. */
7758 property = lookup_property (interface, property_name);
7760 if (!property)
7762 error_at (location, "no declaration of property %qs found in the interface",
7763 IDENTIFIER_POINTER (property_name));
7764 return;
7766 else
7768 /* We have to copy the property, because we want to chain it to
7769 the implementation context, and we want to store the source
7770 location of the @synthesize, not of the original
7771 @property. */
7772 property = copy_node (property);
7773 DECL_SOURCE_LOCATION (property) = location;
7776 /* Determine PROPERTY_IVAR_NAME. */
7777 if (ivar_name == NULL_TREE)
7778 ivar_name = property_name;
7780 /* Check that the instance variable exists. You can only use an
7781 instance variable from the same class, not one from the
7782 superclass (this makes sense as it allows us to check that an
7783 instance variable is only used in one synthesized property). */
7785 tree ivar = is_ivar (CLASS_IVARS (interface), ivar_name);
7786 tree type_of_ivar;
7787 if (!ivar)
7789 error_at (location, "ivar %qs used by %<@synthesize%> declaration must be an existing ivar",
7790 IDENTIFIER_POINTER (property_name));
7791 return;
7794 if (DECL_BIT_FIELD_TYPE (ivar))
7795 type_of_ivar = DECL_BIT_FIELD_TYPE (ivar);
7796 else
7797 type_of_ivar = TREE_TYPE (ivar);
7799 /* If the instance variable has a different C type, we throw an error ... */
7800 if (!comptypes (TREE_TYPE (property), type_of_ivar)
7801 /* ... unless the property is readonly, in which case we allow
7802 the instance variable to be more specialized (this means we
7803 can generate the getter all right and it works). */
7804 && (!PROPERTY_READONLY (property)
7805 || !objc_compare_types (TREE_TYPE (property),
7806 type_of_ivar, -5, NULL_TREE)))
7808 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7810 error_at (location, "property %qs is using instance variable %qs of incompatible type",
7811 IDENTIFIER_POINTER (property_name),
7812 IDENTIFIER_POINTER (ivar_name));
7814 if (original_location != UNKNOWN_LOCATION)
7815 inform (original_location, "originally specified here");
7818 /* If the instance variable is a bitfield, the property must be
7819 'assign', 'nonatomic' because the runtime getter/setter helper
7820 do not work with bitfield instance variables. */
7821 if (DECL_BIT_FIELD_TYPE (ivar))
7823 /* If there is an error, we return and not generate any
7824 getter/setter because trying to set up the runtime
7825 getter/setter helper calls with bitfields is at high risk
7826 of ICE. */
7828 if (PROPERTY_ASSIGN_SEMANTICS (property) != OBJC_PROPERTY_ASSIGN)
7830 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7832 error_at (location, "%<assign%> property %qs is using bit-field "
7833 "instance variable %qs",
7834 IDENTIFIER_POINTER (property_name),
7835 IDENTIFIER_POINTER (ivar_name));
7837 if (original_location != UNKNOWN_LOCATION)
7838 inform (original_location, "originally specified here");
7839 return;
7842 if (!PROPERTY_NONATOMIC (property))
7844 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7846 error_at (location, "%<atomic%> property %qs is using bit-field "
7847 "instance variable %qs",
7848 IDENTIFIER_POINTER (property_name),
7849 IDENTIFIER_POINTER (ivar_name));
7851 if (original_location != UNKNOWN_LOCATION)
7852 inform (original_location, "originally specified here");
7853 return;
7858 /* Check that no other property is using the same instance
7859 variable. */
7860 for (x = IMPL_PROPERTY_DECL (objc_implementation_context); x; x = TREE_CHAIN (x))
7861 if (PROPERTY_IVAR_NAME (x) == ivar_name)
7863 location_t original_location = DECL_SOURCE_LOCATION (x);
7865 error_at (location, "property %qs is using the same instance variable as property %qs",
7866 IDENTIFIER_POINTER (property_name),
7867 IDENTIFIER_POINTER (PROPERTY_NAME (x)));
7869 if (original_location != UNKNOWN_LOCATION)
7870 inform (original_location, "originally specified here");
7872 /* We keep going on. This won't cause the compiler to fail;
7873 the failure would most likely be at runtime. */
7876 /* Note that a @synthesize (and only a @synthesize) always sets
7877 PROPERTY_IVAR_NAME to a non-NULL_TREE. You can recognize a
7878 @synthesize by that. */
7879 PROPERTY_IVAR_NAME (property) = ivar_name;
7881 /* PROPERTY_SETTER_NAME and PROPERTY_GETTER_NAME are copied from the
7882 original declaration; they are always set (with the exception of
7883 PROPERTY_SETTER_NAME not being set if PROPERTY_READONLY == 1). */
7885 /* Add the property to the list of properties for current implementation. */
7886 TREE_CHAIN (property) = IMPL_PROPERTY_DECL (objc_implementation_context);
7887 IMPL_PROPERTY_DECL (objc_implementation_context) = property;
7889 /* Note how we don't actually synthesize the getter/setter here; it
7890 would be very natural, but we may miss the fact that the user has
7891 implemented his own getter/setter later on in the @implementation
7892 (in which case we shouldn't generate getter/setter). We wait
7893 until we have parsed it all before generating the code. */
7896 /* This function is called by the parser after a @synthesize
7897 expression is parsed. 'location' is the location of the
7898 @synthesize expression, and 'property_and_ivar_list' is a chained
7899 list of the property and ivar names. */
7900 void
7901 objc_add_synthesize_declaration (location_t location, tree property_and_ivar_list)
7903 tree interface, chain;
7905 if (flag_objc1_only)
7906 error_at (input_location, "%<@synthesize%> is not available in Objective-C 1.0");
7908 if (property_and_ivar_list == error_mark_node)
7909 return;
7911 if (!objc_implementation_context)
7913 /* We can get here only in Objective-C; the Objective-C++ parser
7914 detects the problem while parsing, outputs the error
7915 "misplaced '@synthesize' Objective-C++ construct" and skips
7916 the declaration. */
7917 error_at (location, "%<@synthesize%> not in @implementation context");
7918 return;
7921 if (TREE_CODE (objc_implementation_context) == CATEGORY_IMPLEMENTATION_TYPE)
7923 error_at (location, "%<@synthesize%> cannot be used in categories");
7924 return;
7927 interface = lookup_interface (CLASS_NAME (objc_implementation_context));
7928 if (!interface)
7930 /* I can't see how this could happen, but it is good as a safety check. */
7931 error_at (location,
7932 "%<@synthesize%> requires the @interface of the class to be available");
7933 return;
7936 /* Now, iterate over the properties and do each of them. */
7937 for (chain = property_and_ivar_list; chain; chain = TREE_CHAIN (chain))
7939 objc_add_synthesize_declaration_for_property (location, interface, TREE_VALUE (chain),
7940 TREE_PURPOSE (chain));
7944 /* This function is a sub-routine of objc_add_dynamic_declaration. It
7945 is called for each property to mark as dynamic once we have
7946 determined that the context is Ok. */
7947 static void
7948 objc_add_dynamic_declaration_for_property (location_t location, tree interface,
7949 tree property_name)
7951 /* Find the @property declaration. */
7952 tree property;
7954 /* Check that synthesize or dynamic has not already been used for
7955 the same property. */
7956 for (property = IMPL_PROPERTY_DECL (objc_implementation_context); property; property = TREE_CHAIN (property))
7957 if (PROPERTY_NAME (property) == property_name)
7959 location_t original_location = DECL_SOURCE_LOCATION (property);
7961 if (PROPERTY_DYNAMIC (property))
7962 error_at (location, "property %qs already specified in %<@dynamic%>",
7963 IDENTIFIER_POINTER (property_name));
7964 else
7965 error_at (location, "property %qs already specified in %<@synthesize%>",
7966 IDENTIFIER_POINTER (property_name));
7968 if (original_location != UNKNOWN_LOCATION)
7969 inform (original_location, "originally specified here");
7970 return;
7973 /* Check that the property is declared in the interface. It could
7974 also be declared in a superclass or protocol. */
7975 property = lookup_property (interface, property_name);
7977 if (!property)
7979 error_at (location, "no declaration of property %qs found in the interface",
7980 IDENTIFIER_POINTER (property_name));
7981 return;
7983 else
7985 /* We have to copy the property, because we want to chain it to
7986 the implementation context, and we want to store the source
7987 location of the @synthesize, not of the original
7988 @property. */
7989 property = copy_node (property);
7990 DECL_SOURCE_LOCATION (property) = location;
7993 /* Note that a @dynamic (and only a @dynamic) always sets
7994 PROPERTY_DYNAMIC to 1. You can recognize a @dynamic by that.
7995 (actually, as explained above, PROPERTY_DECL generated by
7996 @property and associated with a @dynamic property are also marked
7997 as PROPERTY_DYNAMIC). */
7998 PROPERTY_DYNAMIC (property) = 1;
8000 /* Add the property to the list of properties for current implementation. */
8001 TREE_CHAIN (property) = IMPL_PROPERTY_DECL (objc_implementation_context);
8002 IMPL_PROPERTY_DECL (objc_implementation_context) = property;
8005 /* This function is called by the parser after a @dynamic expression
8006 is parsed. 'location' is the location of the @dynamic expression,
8007 and 'property_list' is a chained list of all the property
8008 names. */
8009 void
8010 objc_add_dynamic_declaration (location_t location, tree property_list)
8012 tree interface, chain;
8014 if (flag_objc1_only)
8015 error_at (input_location, "%<@dynamic%> is not available in Objective-C 1.0");
8017 if (property_list == error_mark_node)
8018 return;
8020 if (!objc_implementation_context)
8022 /* We can get here only in Objective-C; the Objective-C++ parser
8023 detects the problem while parsing, outputs the error
8024 "misplaced '@dynamic' Objective-C++ construct" and skips the
8025 declaration. */
8026 error_at (location, "%<@dynamic%> not in @implementation context");
8027 return;
8030 /* @dynamic is allowed in categories. */
8031 switch (TREE_CODE (objc_implementation_context))
8033 case CLASS_IMPLEMENTATION_TYPE:
8034 interface = lookup_interface (CLASS_NAME (objc_implementation_context));
8035 break;
8036 case CATEGORY_IMPLEMENTATION_TYPE:
8037 interface = lookup_category (implementation_template,
8038 CLASS_SUPER_NAME (objc_implementation_context));
8039 break;
8040 default:
8041 gcc_unreachable ();
8044 if (!interface)
8046 /* I can't see how this could happen, but it is good as a safety check. */
8047 error_at (location,
8048 "%<@dynamic%> requires the @interface of the class to be available");
8049 return;
8052 /* Now, iterate over the properties and do each of them. */
8053 for (chain = property_list; chain; chain = TREE_CHAIN (chain))
8055 objc_add_dynamic_declaration_for_property (location, interface, TREE_VALUE (chain));
8059 /* Main routine to generate code/data for all the property information for
8060 current implementation (class or category). CLASS is the interface where
8061 ivars are declared. CLASS_METHODS is where methods are found which
8062 could be a class or a category depending on whether we are implementing
8063 property of a class or a category. */
8065 static void
8066 objc_gen_property_data (tree klass, tree class_methods)
8068 tree x;
8070 for (x = IMPL_PROPERTY_DECL (objc_implementation_context); x; x = TREE_CHAIN (x))
8072 /* @dynamic property - nothing to check or synthesize. */
8073 if (PROPERTY_DYNAMIC (x))
8074 continue;
8076 /* @synthesize property - need to synthesize the accessors. */
8077 if (PROPERTY_IVAR_NAME (x))
8079 objc_synthesize_getter (klass, class_methods, x);
8081 if (PROPERTY_READONLY (x) == 0)
8082 objc_synthesize_setter (klass, class_methods, x);
8084 continue;
8087 gcc_unreachable ();
8091 /* This is called once we see the "@end" in an interface/implementation. */
8093 static void
8094 finish_class (tree klass)
8096 switch (TREE_CODE (klass))
8098 case CLASS_IMPLEMENTATION_TYPE:
8100 /* All metadata generation is done in runtime.generate_metadata(). */
8102 /* Generate what needed for property; setters, getters, etc. */
8103 objc_gen_property_data (implementation_template, implementation_template);
8105 if (implementation_template != objc_implementation_context)
8107 /* Ensure that all method listed in the interface contain bodies. */
8108 check_methods (CLASS_CLS_METHODS (implementation_template),
8109 objc_implementation_context, '+');
8110 check_methods (CLASS_NST_METHODS (implementation_template),
8111 objc_implementation_context, '-');
8113 if (CLASS_PROTOCOL_LIST (implementation_template))
8114 check_protocols (CLASS_PROTOCOL_LIST (implementation_template),
8115 "class",
8116 CLASS_NAME (objc_implementation_context));
8118 break;
8120 case CATEGORY_IMPLEMENTATION_TYPE:
8122 tree category = lookup_category (implementation_template, CLASS_SUPER_NAME (klass));
8124 if (category)
8126 /* Generate what needed for property; setters, getters, etc. */
8127 objc_gen_property_data (implementation_template, category);
8129 /* Ensure all method listed in the interface contain bodies. */
8130 check_methods (CLASS_CLS_METHODS (category),
8131 objc_implementation_context, '+');
8132 check_methods (CLASS_NST_METHODS (category),
8133 objc_implementation_context, '-');
8135 if (CLASS_PROTOCOL_LIST (category))
8136 check_protocols (CLASS_PROTOCOL_LIST (category),
8137 "category",
8138 CLASS_SUPER_NAME (objc_implementation_context));
8140 break;
8142 case CLASS_INTERFACE_TYPE:
8143 case CATEGORY_INTERFACE_TYPE:
8144 case PROTOCOL_INTERFACE_TYPE:
8146 /* Process properties of the class. */
8147 tree x;
8148 for (x = CLASS_PROPERTY_DECL (objc_interface_context); x; x = TREE_CHAIN (x))
8150 /* Now we check that the appropriate getter is declared,
8151 and if not, we declare one ourselves. */
8152 tree getter_decl = lookup_method (CLASS_NST_METHODS (klass),
8153 PROPERTY_GETTER_NAME (x));
8155 if (getter_decl)
8157 /* TODO: Check that the declaration is consistent with the property. */
8160 else
8162 /* Generate an instance method declaration for the
8163 getter; for example "- (id) name;". In general it
8164 will be of the form
8165 -(type)property_getter_name; */
8166 tree rettype = build_tree_list (NULL_TREE, TREE_TYPE (x));
8167 getter_decl = build_method_decl (INSTANCE_METHOD_DECL,
8168 rettype, PROPERTY_GETTER_NAME (x),
8169 NULL_TREE, false);
8170 if (PROPERTY_OPTIONAL (x))
8171 objc_add_method (objc_interface_context, getter_decl, false, true);
8172 else
8173 objc_add_method (objc_interface_context, getter_decl, false, false);
8174 TREE_DEPRECATED (getter_decl) = TREE_DEPRECATED (x);
8175 TREE_UNAVAILABLE (getter_decl) = TREE_UNAVAILABLE (x);
8176 METHOD_PROPERTY_CONTEXT (getter_decl) = x;
8179 if (PROPERTY_READONLY (x) == 0)
8181 /* Now we check that the appropriate setter is declared,
8182 and if not, we declare on ourselves. */
8183 tree setter_decl = lookup_method (CLASS_NST_METHODS (klass),
8184 PROPERTY_SETTER_NAME (x));
8186 if (setter_decl)
8188 /* TODO: Check that the declaration is consistent with the property. */
8191 else
8193 /* The setter name is something like 'setName:'.
8194 We need the substring 'setName' to build the
8195 method declaration due to how the declaration
8196 works. TODO: build_method_decl() will then
8197 generate back 'setName:' from 'setName'; it
8198 would be more efficient to hook into there. */
8199 const char *full_setter_name = IDENTIFIER_POINTER (PROPERTY_SETTER_NAME (x));
8200 size_t length = strlen (full_setter_name);
8201 char *setter_name = (char *) alloca (length);
8202 tree ret_type, selector, arg_type, arg_name;
8204 memcpy (setter_name, full_setter_name, length - 1);
8205 setter_name[length - 1] = '\0';
8206 ret_type = build_tree_list (NULL_TREE, void_type_node);
8207 arg_type = build_tree_list (NULL_TREE, TREE_TYPE (x));
8208 arg_name = get_identifier ("_value");
8209 selector = objc_build_keyword_decl (get_identifier (setter_name),
8210 arg_type, arg_name, NULL);
8211 setter_decl = build_method_decl (INSTANCE_METHOD_DECL,
8212 ret_type, selector,
8213 build_tree_list (NULL_TREE, NULL_TREE),
8214 false);
8215 if (PROPERTY_OPTIONAL (x))
8216 objc_add_method (objc_interface_context, setter_decl, false, true);
8217 else
8218 objc_add_method (objc_interface_context, setter_decl, false, false);
8219 TREE_DEPRECATED (setter_decl) = TREE_DEPRECATED (x);
8220 TREE_UNAVAILABLE (setter_decl) = TREE_UNAVAILABLE (x);
8221 METHOD_PROPERTY_CONTEXT (setter_decl) = x;
8225 break;
8227 default:
8228 gcc_unreachable ();
8229 break;
8233 static tree
8234 add_protocol (tree protocol)
8236 /* Put protocol on list in reverse order. */
8237 TREE_CHAIN (protocol) = protocol_chain;
8238 protocol_chain = protocol;
8239 return protocol_chain;
8242 /* Check that a protocol is defined, and, recursively, that all
8243 protocols that this protocol conforms to are defined too. */
8244 static void
8245 check_that_protocol_is_defined (tree protocol)
8247 if (!PROTOCOL_DEFINED (protocol))
8248 warning (0, "definition of protocol %qE not found",
8249 PROTOCOL_NAME (protocol));
8251 /* If the protocol itself conforms to other protocols, check them
8252 too, recursively. */
8253 if (PROTOCOL_LIST (protocol))
8255 tree p;
8257 for (p = PROTOCOL_LIST (protocol); p; p = TREE_CHAIN (p))
8258 check_that_protocol_is_defined (TREE_VALUE (p));
8262 /* Looks up a protocol. If 'warn_if_deprecated' is true, a warning is
8263 emitted if the protocol is deprecated. If 'definition_required' is
8264 true, a warning is emitted if a full @protocol definition has not
8265 been seen. */
8266 static tree
8267 lookup_protocol (tree ident, bool warn_if_deprecated, bool definition_required)
8269 tree chain;
8271 for (chain = protocol_chain; chain; chain = TREE_CHAIN (chain))
8272 if (ident == PROTOCOL_NAME (chain))
8274 if (TREE_UNAVAILABLE (chain))
8275 error ("protocol %qE is unavailable", PROTOCOL_NAME (chain));
8276 else if (warn_if_deprecated && TREE_DEPRECATED (chain))
8278 /* It would be nice to use warn_deprecated_use() here, but
8279 we are using TREE_CHAIN (which is supposed to be the
8280 TYPE_STUB_DECL for a TYPE) for something different. */
8281 warning (OPT_Wdeprecated_declarations, "protocol %qE is deprecated",
8282 PROTOCOL_NAME (chain));
8285 if (definition_required)
8286 check_that_protocol_is_defined (chain);
8288 return chain;
8291 return NULL_TREE;
8294 /* This function forward declares the protocols named by NAMES. If
8295 they are already declared or defined, the function has no effect. */
8297 void
8298 objc_declare_protocol (tree name, tree attributes)
8300 bool deprecated = false;
8301 bool unavailable = false;
8303 #ifdef OBJCPLUS
8304 if (current_namespace != global_namespace) {
8305 error ("Objective-C declarations may only appear in global scope");
8307 #endif /* OBJCPLUS */
8309 /* Determine if 'deprecated', the only attribute we recognize for
8310 protocols, was used. Ignore all other attributes. */
8311 if (attributes)
8313 tree attribute;
8314 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
8316 tree name = TREE_PURPOSE (attribute);
8318 if (is_attribute_p ("deprecated", name))
8319 deprecated = true;
8320 else if (is_attribute_p ("unavailable", name))
8321 unavailable = true;
8322 else
8323 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
8327 if (lookup_protocol (name, /* warn if deprecated */ false,
8328 /* definition_required */ false) == NULL_TREE)
8330 tree protocol = make_node (PROTOCOL_INTERFACE_TYPE);
8332 TYPE_LANG_SLOT_1 (protocol)
8333 = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8334 PROTOCOL_NAME (protocol) = name;
8335 PROTOCOL_LIST (protocol) = NULL_TREE;
8336 add_protocol (protocol);
8337 PROTOCOL_DEFINED (protocol) = 0;
8338 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8340 if (attributes)
8342 /* TODO: Do we need to store the attributes here ? */
8343 TYPE_ATTRIBUTES (protocol) = attributes;
8344 if (deprecated)
8345 TREE_DEPRECATED (protocol) = 1;
8346 if (unavailable)
8347 TREE_UNAVAILABLE (protocol) = 1;
8352 static tree
8353 start_protocol (enum tree_code code, tree name, tree list, tree attributes)
8355 tree protocol;
8356 bool deprecated = false;
8357 bool unavailable = false;
8359 #ifdef OBJCPLUS
8360 if (current_namespace != global_namespace) {
8361 error ("Objective-C declarations may only appear in global scope");
8363 #endif /* OBJCPLUS */
8365 /* Determine if 'deprecated', the only attribute we recognize for
8366 protocols, was used. Ignore all other attributes. */
8367 if (attributes)
8369 tree attribute;
8370 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
8372 tree name = TREE_PURPOSE (attribute);
8374 if (is_attribute_p ("deprecated", name))
8375 deprecated = true;
8376 else if (is_attribute_p ("unavailable", name))
8377 unavailable = true;
8378 else
8379 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
8383 protocol = lookup_protocol (name, /* warn_if_deprecated */ false,
8384 /* definition_required */ false);
8386 if (!protocol)
8388 protocol = make_node (code);
8389 TYPE_LANG_SLOT_1 (protocol) = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8391 PROTOCOL_NAME (protocol) = name;
8392 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list, /* definition_required */ false);
8393 add_protocol (protocol);
8394 PROTOCOL_DEFINED (protocol) = 1;
8395 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8397 check_protocol_recursively (protocol, list);
8399 else if (! PROTOCOL_DEFINED (protocol))
8401 PROTOCOL_DEFINED (protocol) = 1;
8402 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list, /* definition_required */ false);
8404 check_protocol_recursively (protocol, list);
8406 else
8408 warning (0, "duplicate declaration for protocol %qE",
8409 name);
8412 if (attributes)
8414 TYPE_ATTRIBUTES (protocol) = attributes;
8415 if (deprecated)
8416 TREE_DEPRECATED (protocol) = 1;
8417 if (unavailable)
8418 TREE_UNAVAILABLE (protocol) = 1;
8421 return protocol;
8424 /* Decay array and function parameters into pointers. */
8426 static tree
8427 objc_decay_parm_type (tree type)
8429 if (TREE_CODE (type) == ARRAY_TYPE || TREE_CODE (type) == FUNCTION_TYPE)
8430 type = build_pointer_type (TREE_CODE (type) == ARRAY_TYPE
8431 ? TREE_TYPE (type)
8432 : type);
8434 return type;
8437 static GTY(()) tree objc_parmlist = NULL_TREE;
8439 /* Append PARM to a list of formal parameters of a method, making a necessary
8440 array-to-pointer adjustment along the way. */
8442 void
8443 objc_push_parm (tree parm)
8445 tree type;
8447 if (TREE_TYPE (parm) == error_mark_node)
8449 objc_parmlist = chainon (objc_parmlist, parm);
8450 return;
8453 /* Decay arrays and functions into pointers. */
8454 type = objc_decay_parm_type (TREE_TYPE (parm));
8456 /* If the parameter type has been decayed, a new PARM_DECL needs to be
8457 built as well. */
8458 if (type != TREE_TYPE (parm))
8459 parm = build_decl (input_location, PARM_DECL, DECL_NAME (parm), type);
8461 DECL_ARG_TYPE (parm)
8462 = lang_hooks.types.type_promotes_to (TREE_TYPE (parm));
8464 /* Record constancy and volatility. */
8465 c_apply_type_quals_to_decl
8466 ((TYPE_READONLY (TREE_TYPE (parm)) ? TYPE_QUAL_CONST : 0)
8467 | (TYPE_RESTRICT (TREE_TYPE (parm)) ? TYPE_QUAL_RESTRICT : 0)
8468 | (TYPE_ATOMIC (TREE_TYPE (parm)) ? TYPE_QUAL_ATOMIC : 0)
8469 | (TYPE_VOLATILE (TREE_TYPE (parm)) ? TYPE_QUAL_VOLATILE : 0), parm);
8471 objc_parmlist = chainon (objc_parmlist, parm);
8474 /* Retrieve the formal parameter list constructed via preceding calls to
8475 objc_push_parm(). */
8477 #ifdef OBJCPLUS
8478 tree
8479 objc_get_parm_info (int have_ellipsis ATTRIBUTE_UNUSED,
8480 tree expr ATTRIBUTE_UNUSED)
8482 tree parm_info = objc_parmlist;
8483 objc_parmlist = NULL_TREE;
8485 return parm_info;
8487 #else
8488 struct c_arg_info *
8489 objc_get_parm_info (int have_ellipsis, tree expr)
8491 tree parm_info = objc_parmlist;
8492 struct c_arg_info *arg_info;
8493 /* The C front-end requires an elaborate song and dance at
8494 this point. */
8495 push_scope ();
8496 declare_parm_level ();
8497 while (parm_info)
8499 tree next = DECL_CHAIN (parm_info);
8501 DECL_CHAIN (parm_info) = NULL_TREE;
8502 parm_info = pushdecl (parm_info);
8503 finish_decl (parm_info, input_location, NULL_TREE, NULL_TREE, NULL_TREE);
8504 parm_info = next;
8506 arg_info = get_parm_info (have_ellipsis, expr);
8507 pop_scope ();
8508 objc_parmlist = NULL_TREE;
8509 return arg_info;
8511 #endif
8513 /* Synthesize the formal parameters 'id self' and 'SEL _cmd' needed for ObjC
8514 method definitions. In the case of instance methods, we can be more
8515 specific as to the type of 'self'. */
8517 static void
8518 synth_self_and_ucmd_args (void)
8520 tree self_type;
8522 if (objc_method_context
8523 && TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL)
8524 self_type = objc_instance_type;
8525 else
8526 /* Really a `struct objc_class *'. However, we allow people to
8527 assign to self, which changes its type midstream. */
8528 self_type = objc_object_type;
8530 /* id self; */
8531 objc_push_parm (build_decl (input_location,
8532 PARM_DECL, self_id, self_type));
8534 /* SEL _cmd; */
8535 objc_push_parm (build_decl (input_location,
8536 PARM_DECL, ucmd_id, objc_selector_type));
8539 /* Transform an Objective-C method definition into a static C function
8540 definition, synthesizing the first two arguments, "self" and "_cmd",
8541 in the process. EXPR is NULL or an expression that needs to be
8542 evaluated for the side effects of array size expressions in the
8543 parameters. */
8545 static void
8546 start_method_def (tree method, tree expr)
8548 tree parmlist;
8549 #ifdef OBJCPLUS
8550 tree parm_info;
8551 #else
8552 struct c_arg_info *parm_info;
8553 #endif
8554 int have_ellipsis = 0;
8556 /* If we are defining a "dealloc" method in a non-root class, we
8557 will need to check if a [super dealloc] is missing, and warn if
8558 it is. */
8559 if(CLASS_SUPER_NAME (objc_implementation_context)
8560 && !strcmp ("dealloc", IDENTIFIER_POINTER (METHOD_SEL_NAME (method))))
8561 should_call_super_dealloc = 1;
8562 else
8563 should_call_super_dealloc = 0;
8565 /* Required to implement _msgSuper. */
8566 objc_method_context = method;
8567 UOBJC_SUPER_decl = NULL_TREE;
8569 /* Generate prototype declarations for arguments..."new-style". */
8570 synth_self_and_ucmd_args ();
8572 /* Generate argument declarations if a keyword_decl. */
8573 parmlist = METHOD_SEL_ARGS (method);
8574 while (parmlist)
8576 /* parmlist is a KEYWORD_DECL. */
8577 tree type = TREE_VALUE (TREE_TYPE (parmlist));
8578 tree parm;
8580 parm = build_decl (input_location,
8581 PARM_DECL, KEYWORD_ARG_NAME (parmlist), type);
8582 decl_attributes (&parm, DECL_ATTRIBUTES (parmlist), 0);
8583 objc_push_parm (parm);
8584 parmlist = DECL_CHAIN (parmlist);
8587 if (METHOD_ADD_ARGS (method))
8589 tree akey;
8591 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (method));
8592 akey; akey = TREE_CHAIN (akey))
8594 objc_push_parm (TREE_VALUE (akey));
8597 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8598 have_ellipsis = 1;
8601 parm_info = objc_get_parm_info (have_ellipsis, expr);
8603 really_start_method (objc_method_context, parm_info);
8606 /* Return 1 if TYPE1 is equivalent to TYPE2 for purposes of method
8607 overloading. */
8608 static int
8609 objc_types_are_equivalent (tree type1, tree type2)
8611 if (type1 == type2)
8612 return 1;
8614 /* Strip away indirections. */
8615 while ((TREE_CODE (type1) == ARRAY_TYPE || TREE_CODE (type1) == POINTER_TYPE)
8616 && (TREE_CODE (type1) == TREE_CODE (type2)))
8617 type1 = TREE_TYPE (type1), type2 = TREE_TYPE (type2);
8618 if (TYPE_MAIN_VARIANT (type1) != TYPE_MAIN_VARIANT (type2))
8619 return 0;
8621 /* Compare the protocol lists. */
8622 type1 = (TYPE_HAS_OBJC_INFO (type1)
8623 ? TYPE_OBJC_PROTOCOL_LIST (type1)
8624 : NULL_TREE);
8625 type2 = (TYPE_HAS_OBJC_INFO (type2)
8626 ? TYPE_OBJC_PROTOCOL_LIST (type2)
8627 : NULL_TREE);
8629 /* If there are no protocols (most common case), the types are
8630 identical. */
8631 if (type1 == NULL_TREE && type2 == NULL_TREE)
8632 return 1;
8634 /* If one has protocols, and the other one hasn't, they are not
8635 identical. */
8636 if ((type1 == NULL_TREE && type2 != NULL_TREE)
8637 || (type1 != NULL_TREE && type2 == NULL_TREE))
8638 return 0;
8639 else
8641 /* Else, both have protocols, and we need to do the full
8642 comparison. It is possible that either type1 or type2
8643 contain some duplicate protocols in the list, so we can't
8644 even just compare list_length as a first check. */
8645 tree t;
8647 for (t = type2; t; t = TREE_CHAIN (t))
8648 if (!lookup_protocol_in_reflist (type1, TREE_VALUE (t)))
8649 return 0;
8651 for (t = type1; t; t = TREE_CHAIN (t))
8652 if (!lookup_protocol_in_reflist (type2, TREE_VALUE (t)))
8653 return 0;
8655 return 1;
8659 /* Return 1 if TYPE1 has the same size and alignment as TYPE2. */
8661 static int
8662 objc_types_share_size_and_alignment (tree type1, tree type2)
8664 return (simple_cst_equal (TYPE_SIZE (type1), TYPE_SIZE (type2))
8665 && TYPE_ALIGN (type1) == TYPE_ALIGN (type2));
8668 /* Return 1 if PROTO1 is equivalent to PROTO2
8669 for purposes of method overloading. Ordinarily, the type signatures
8670 should match up exactly, unless STRICT is zero, in which case we
8671 shall allow differences in which the size and alignment of a type
8672 is the same. */
8674 static int
8675 comp_proto_with_proto (tree proto1, tree proto2, int strict)
8677 tree type1, type2;
8679 /* The following test is needed in case there are hashing
8680 collisions. */
8681 if (METHOD_SEL_NAME (proto1) != METHOD_SEL_NAME (proto2))
8682 return 0;
8684 /* Compare return types. */
8685 type1 = TREE_VALUE (TREE_TYPE (proto1));
8686 type2 = TREE_VALUE (TREE_TYPE (proto2));
8688 if (!objc_types_are_equivalent (type1, type2)
8689 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8690 return 0;
8692 /* Compare argument types. */
8694 /* The first argument (objc_object_type) is always the same, no need
8695 to compare. */
8697 /* The second argument (objc_selector_type) is always the same, no
8698 need to compare. */
8700 /* Compare the other arguments. */
8702 tree arg1, arg2;
8704 /* Compare METHOD_SEL_ARGS. */
8705 for (arg1 = METHOD_SEL_ARGS (proto1), arg2 = METHOD_SEL_ARGS (proto2);
8706 arg1 && arg2;
8707 arg1 = DECL_CHAIN (arg1), arg2 = DECL_CHAIN (arg2))
8709 type1 = TREE_VALUE (TREE_TYPE (arg1));
8710 type2 = TREE_VALUE (TREE_TYPE (arg2));
8712 /* FIXME: Do we need to decay argument types to compare them ? */
8713 type1 = objc_decay_parm_type (type1);
8714 type2 = objc_decay_parm_type (type2);
8716 if (!objc_types_are_equivalent (type1, type2)
8717 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8718 return 0;
8721 /* The loop ends when arg1 or arg2 are NULL. Make sure they are
8722 both NULL. */
8723 if (arg1 != arg2)
8724 return 0;
8726 /* Compare METHOD_ADD_ARGS. */
8727 if ((METHOD_ADD_ARGS (proto1) && !METHOD_ADD_ARGS (proto2))
8728 || (METHOD_ADD_ARGS (proto2) && !METHOD_ADD_ARGS (proto1)))
8729 return 0;
8731 if (METHOD_ADD_ARGS (proto1))
8733 for (arg1 = TREE_CHAIN (METHOD_ADD_ARGS (proto1)), arg2 = TREE_CHAIN (METHOD_ADD_ARGS (proto2));
8734 arg1 && arg2;
8735 arg1 = TREE_CHAIN (arg1), arg2 = TREE_CHAIN (arg2))
8737 type1 = TREE_TYPE (TREE_VALUE (arg1));
8738 type2 = TREE_TYPE (TREE_VALUE (arg2));
8740 /* FIXME: Do we need to decay argument types to compare them ? */
8741 type1 = objc_decay_parm_type (type1);
8742 type2 = objc_decay_parm_type (type2);
8744 if (!objc_types_are_equivalent (type1, type2)
8745 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8746 return 0;
8750 /* The loop ends when arg1 or arg2 are NULL. Make sure they are
8751 both NULL. */
8752 if (arg1 != arg2)
8753 return 0;
8755 /* Compare METHOD_ADD_ARGS_ELLIPSIS_P. */
8756 if (METHOD_ADD_ARGS_ELLIPSIS_P (proto1) != METHOD_ADD_ARGS_ELLIPSIS_P (proto2))
8757 return 0;
8760 /* Success. */
8761 return 1;
8764 /* This routine returns true if TYPE is a valid objc object type,
8765 suitable for messaging; false otherwise. If 'accept_class' is
8766 'true', then a Class object is considered valid for messaging and
8767 'true' is returned if 'type' refers to a Class. If 'accept_class'
8768 is 'false', then a Class object is not considered valid for
8769 messaging and 'false' is returned in that case. */
8771 static bool
8772 objc_type_valid_for_messaging (tree type, bool accept_classes)
8774 if (!POINTER_TYPE_P (type))
8775 return false;
8777 /* We will check for an NSObject type attribute on the pointer if other
8778 tests fail. */
8779 tree type_attr = TYPE_ATTRIBUTES (type);
8781 /* Remove the pointer indirection; don't remove more than one
8782 otherwise we'd consider "NSObject **" a valid type for messaging,
8783 which it isn't. */
8784 type = TREE_TYPE (type);
8786 /* We allow void * to have an NSObject type attr. */
8787 if (VOID_TYPE_P (type) && type_attr)
8788 return lookup_attribute ("NSObject", type_attr) != NULL_TREE;
8790 if (TREE_CODE (type) != RECORD_TYPE)
8791 return false;
8793 if (objc_is_object_id (type))
8794 return true;
8796 if (objc_is_class_id (type))
8797 return accept_classes;
8799 if (TYPE_HAS_OBJC_INFO (type))
8800 return true;
8802 if (type_attr)
8803 return lookup_attribute ("NSObject", type_attr) != NULL_TREE;
8805 return false;
8808 void
8809 objc_start_function (tree name, tree type, tree attrs,
8810 #ifdef OBJCPLUS
8811 tree params
8812 #else
8813 struct c_arg_info *params
8814 #endif
8817 tree fndecl = build_decl (input_location,
8818 FUNCTION_DECL, name, type);
8820 #ifdef OBJCPLUS
8821 DECL_ARGUMENTS (fndecl) = params;
8822 DECL_INITIAL (fndecl) = error_mark_node;
8823 DECL_EXTERNAL (fndecl) = 0;
8824 TREE_STATIC (fndecl) = 1;
8825 retrofit_lang_decl (fndecl);
8826 cplus_decl_attributes (&fndecl, attrs, 0);
8827 start_preparsed_function (fndecl, attrs, /*flags=*/SF_DEFAULT);
8828 #else
8829 current_function_returns_value = 0; /* Assume, until we see it does. */
8830 current_function_returns_null = 0;
8831 decl_attributes (&fndecl, attrs, 0);
8832 announce_function (fndecl);
8833 DECL_INITIAL (fndecl) = error_mark_node;
8834 DECL_EXTERNAL (fndecl) = 0;
8835 TREE_STATIC (fndecl) = 1;
8836 current_function_decl = pushdecl (fndecl);
8837 push_scope ();
8838 declare_parm_level ();
8839 DECL_RESULT (current_function_decl)
8840 = build_decl (input_location,
8841 RESULT_DECL, NULL_TREE,
8842 TREE_TYPE (TREE_TYPE (current_function_decl)));
8843 DECL_ARTIFICIAL (DECL_RESULT (current_function_decl)) = 1;
8844 DECL_IGNORED_P (DECL_RESULT (current_function_decl)) = 1;
8845 start_fname_decls ();
8846 store_parm_decls_from (params);
8847 #endif
8849 TREE_USED (current_function_decl) = 1;
8852 /* - Generate an identifier for the function. the format is "_n_cls",
8853 where 1 <= n <= nMethods, and cls is the name the implementation we
8854 are processing.
8855 - Install the return type from the method declaration.
8856 - If we have a prototype, check for type consistency. */
8858 static void
8859 really_start_method (tree method,
8860 #ifdef OBJCPLUS
8861 tree parmlist
8862 #else
8863 struct c_arg_info *parmlist
8864 #endif
8867 tree ret_type, meth_type;
8868 tree method_id;
8869 const char *sel_name, *class_name, *cat_name;
8870 char *buf;
8872 /* Synth the storage class & assemble the return type. */
8873 ret_type = TREE_VALUE (TREE_TYPE (method));
8875 sel_name = IDENTIFIER_POINTER (METHOD_SEL_NAME (method));
8876 class_name = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
8877 cat_name = ((TREE_CODE (objc_implementation_context)
8878 == CLASS_IMPLEMENTATION_TYPE)
8879 ? NULL
8880 : IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
8881 method_slot++;
8883 /* Make sure this is big enough for any plausible method label. */
8884 buf = (char *) alloca (50 + strlen (sel_name) + strlen (class_name)
8885 + (cat_name ? strlen (cat_name) : 0));
8887 OBJC_GEN_METHOD_LABEL (buf, TREE_CODE (method) == INSTANCE_METHOD_DECL,
8888 class_name, cat_name, sel_name, method_slot);
8890 method_id = get_identifier (buf);
8892 #ifdef OBJCPLUS
8893 /* Objective-C methods cannot be overloaded, so we don't need
8894 the type encoding appended. It looks bad anyway... */
8895 push_lang_context (lang_name_c);
8896 #endif
8898 meth_type = build_function_type_for_method (ret_type, method, METHOD_DEF, 0);
8899 objc_start_function (method_id, meth_type, NULL_TREE, parmlist);
8901 /* Set self_decl from the first argument. */
8902 self_decl = DECL_ARGUMENTS (current_function_decl);
8904 /* Suppress unused warnings. */
8905 TREE_USED (self_decl) = 1;
8906 DECL_READ_P (self_decl) = 1;
8907 TREE_USED (DECL_CHAIN (self_decl)) = 1;
8908 DECL_READ_P (DECL_CHAIN (self_decl)) = 1;
8909 #ifdef OBJCPLUS
8910 pop_lang_context ();
8911 #endif
8913 METHOD_DEFINITION (method) = current_function_decl;
8915 /* Check consistency...start_function, pushdecl, duplicate_decls. */
8917 if (implementation_template != objc_implementation_context)
8919 tree proto
8920 = lookup_method_static (implementation_template,
8921 METHOD_SEL_NAME (method),
8922 ((TREE_CODE (method) == CLASS_METHOD_DECL)
8923 | OBJC_LOOKUP_NO_SUPER));
8925 if (proto)
8927 if (!comp_proto_with_proto (method, proto, 1))
8929 bool type = TREE_CODE (method) == INSTANCE_METHOD_DECL;
8931 warning_at (DECL_SOURCE_LOCATION (method), 0,
8932 "conflicting types for %<%c%s%>",
8933 (type ? '-' : '+'),
8934 identifier_to_locale (gen_method_decl (method)));
8935 inform (DECL_SOURCE_LOCATION (proto),
8936 "previous declaration of %<%c%s%>",
8937 (type ? '-' : '+'),
8938 identifier_to_locale (gen_method_decl (proto)));
8940 else
8942 /* If the method in the @interface was deprecated, mark
8943 the implemented method as deprecated too. It should
8944 never be used for messaging (when the deprecation
8945 warnings are produced), but just in case. */
8946 if (TREE_DEPRECATED (proto))
8947 TREE_DEPRECATED (method) = 1;
8948 if (TREE_UNAVAILABLE (proto))
8949 TREE_UNAVAILABLE (method) = 1;
8951 /* If the method in the @interface was marked as
8952 'noreturn', mark the function implementing the method
8953 as 'noreturn' too. */
8954 TREE_THIS_VOLATILE (current_function_decl) = TREE_THIS_VOLATILE (proto);
8957 else
8959 /* We have a method @implementation even though we did not
8960 see a corresponding @interface declaration (which is allowed
8961 by Objective-C rules). Go ahead and place the method in
8962 the @interface anyway, so that message dispatch lookups
8963 will see it. */
8964 tree interface = implementation_template;
8966 if (TREE_CODE (objc_implementation_context)
8967 == CATEGORY_IMPLEMENTATION_TYPE)
8968 interface = lookup_category
8969 (interface,
8970 CLASS_SUPER_NAME (objc_implementation_context));
8972 if (interface)
8973 objc_add_method (interface, copy_node (method),
8974 TREE_CODE (method) == CLASS_METHOD_DECL,
8975 /* is_optional= */ false);
8980 static void *UOBJC_SUPER_scope = 0;
8982 /* _n_Method (id self, SEL sel, ...)
8984 struct objc_super _S;
8985 _msgSuper ((_S.self = self, _S.class = _cls, &_S), ...);
8986 } */
8988 static tree
8989 get_super_receiver (void)
8991 if (objc_method_context)
8993 tree super_expr, super_expr_list, class_expr;
8994 bool inst_meth;
8995 if (!UOBJC_SUPER_decl)
8997 UOBJC_SUPER_decl = build_decl (input_location,
8998 VAR_DECL, get_identifier (TAG_SUPER),
8999 objc_super_template);
9000 /* This prevents `unused variable' warnings when compiling with -Wall. */
9001 TREE_USED (UOBJC_SUPER_decl) = 1;
9002 DECL_READ_P (UOBJC_SUPER_decl) = 1;
9003 lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
9004 finish_decl (UOBJC_SUPER_decl, input_location, NULL_TREE, NULL_TREE,
9005 NULL_TREE);
9006 UOBJC_SUPER_scope = objc_get_current_scope ();
9009 /* Set receiver to self. */
9010 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
9011 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
9012 NOP_EXPR, input_location, self_decl,
9013 NULL_TREE);
9014 super_expr_list = super_expr;
9016 /* Set class to begin searching. */
9017 /* Get the ident for the superclass class field & build a ref to it.
9018 ??? maybe we should just name the field the same for all runtimes. */
9019 super_expr = (*runtime.super_superclassfield_ident) ();
9020 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, super_expr);
9022 gcc_assert (imp_list->imp_context == objc_implementation_context
9023 && imp_list->imp_template == implementation_template);
9024 inst_meth = (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL);
9026 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
9027 class_expr = (*runtime.get_class_super_ref) (input_location,
9028 imp_list, inst_meth);
9029 else
9030 /* We have a category. */
9032 tree super_name = CLASS_SUPER_NAME (imp_list->imp_template);
9033 tree super_class;
9035 /* Barf if super used in a category of a root object. */
9036 if (!super_name)
9038 error ("no super class declared in interface for %qE",
9039 CLASS_NAME (imp_list->imp_template));
9040 return error_mark_node;
9043 super_class = (*runtime.get_category_super_ref) (input_location,
9044 imp_list, inst_meth);
9045 class_expr = build_c_cast (input_location,
9046 TREE_TYPE (super_expr), super_class);
9049 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
9050 NOP_EXPR,
9051 input_location, class_expr, NULL_TREE);
9053 super_expr_list = build_compound_expr (input_location,
9054 super_expr_list, super_expr);
9056 super_expr = build_unary_op (input_location,
9057 ADDR_EXPR, UOBJC_SUPER_decl, 0);
9058 super_expr_list = build_compound_expr (input_location,
9059 super_expr_list, super_expr);
9061 return super_expr_list;
9063 else
9065 error ("%<[super ...]%> must appear in a method context");
9066 return error_mark_node;
9070 /* When exiting a scope, sever links to a 'super' declaration (if any)
9071 therein contained. */
9073 void
9074 objc_clear_super_receiver (void)
9076 if (objc_method_context
9077 && UOBJC_SUPER_scope == objc_get_current_scope ())
9079 UOBJC_SUPER_decl = 0;
9080 UOBJC_SUPER_scope = 0;
9084 void
9085 objc_finish_method_definition (tree fndecl)
9087 /* We cannot validly inline ObjC methods, at least not without a language
9088 extension to declare that a method need not be dynamically
9089 dispatched, so suppress all thoughts of doing so. */
9090 DECL_UNINLINABLE (fndecl) = 1;
9092 #ifndef OBJCPLUS
9093 /* The C++ front-end will have called finish_function() for us. */
9094 finish_function ();
9095 #endif
9097 METHOD_ENCODING (objc_method_context)
9098 = encode_method_prototype (objc_method_context);
9100 /* Required to implement _msgSuper. This must be done AFTER finish_function,
9101 since the optimizer may find "may be used before set" errors. */
9102 objc_method_context = NULL_TREE;
9104 if (should_call_super_dealloc)
9105 warning (0, "method possibly missing a [super dealloc] call");
9108 /* Given a tree DECL node, produce a printable description of it in the given
9109 buffer, overwriting the buffer. */
9111 static char *
9112 gen_declaration (tree decl)
9114 errbuf[0] = '\0';
9116 if (DECL_P (decl))
9118 gen_type_name_0 (TREE_TYPE (decl));
9120 if (DECL_NAME (decl))
9122 if (!POINTER_TYPE_P (TREE_TYPE (decl)))
9123 strcat (errbuf, " ");
9125 strcat (errbuf, IDENTIFIER_POINTER (DECL_NAME (decl)));
9128 #ifdef OBJCPLUS
9129 tree w = DECL_BIT_FIELD_REPRESENTATIVE (decl);
9130 #else
9131 tree w = DECL_INITIAL (decl);
9132 #endif
9133 if (w)
9135 STRIP_ANY_LOCATION_WRAPPER (w);
9136 if (TREE_CODE (w) == INTEGER_CST)
9137 sprintf (errbuf + strlen (errbuf), ": " HOST_WIDE_INT_PRINT_DEC,
9138 TREE_INT_CST_LOW (w));
9142 return errbuf;
9145 /* Given a tree TYPE node, produce a printable description of it in the given
9146 buffer, overwriting the buffer. */
9148 static char *
9149 gen_type_name_0 (tree type)
9151 tree orig = type, proto;
9153 if (TYPE_P (type) && TYPE_NAME (type))
9154 type = TYPE_NAME (type);
9155 else if (POINTER_TYPE_P (type) || TREE_CODE (type) == ARRAY_TYPE)
9157 tree inner = TREE_TYPE (type);
9159 while (TREE_CODE (inner) == ARRAY_TYPE)
9160 inner = TREE_TYPE (inner);
9162 gen_type_name_0 (inner);
9164 if (!POINTER_TYPE_P (inner))
9165 strcat (errbuf, " ");
9167 if (POINTER_TYPE_P (type))
9168 strcat (errbuf, "*");
9169 else
9170 while (type != inner)
9172 strcat (errbuf, "[");
9174 if (TYPE_DOMAIN (type))
9176 char sz[20];
9178 sprintf (sz, HOST_WIDE_INT_PRINT_DEC,
9179 (TREE_INT_CST_LOW
9180 (TYPE_MAX_VALUE (TYPE_DOMAIN (type))) + 1));
9181 strcat (errbuf, sz);
9184 strcat (errbuf, "]");
9185 type = TREE_TYPE (type);
9188 goto exit_function;
9191 if (TREE_CODE (type) == TYPE_DECL && DECL_NAME (type))
9192 type = DECL_NAME (type);
9194 strcat (errbuf, TREE_CODE (type) == IDENTIFIER_NODE
9195 ? IDENTIFIER_POINTER (type)
9196 : "");
9198 /* For 'id' and 'Class', adopted protocols are stored in the pointee. */
9199 if (objc_is_id (orig))
9200 orig = TREE_TYPE (orig);
9202 proto = TYPE_HAS_OBJC_INFO (orig) ? TYPE_OBJC_PROTOCOL_LIST (orig) : NULL_TREE;
9204 if (proto)
9206 strcat (errbuf, " <");
9208 while (proto) {
9209 strcat (errbuf,
9210 IDENTIFIER_POINTER (PROTOCOL_NAME (TREE_VALUE (proto))));
9211 proto = TREE_CHAIN (proto);
9212 strcat (errbuf, proto ? ", " : ">");
9216 exit_function:
9217 return errbuf;
9220 static char *
9221 gen_type_name (tree type)
9223 errbuf[0] = '\0';
9225 return gen_type_name_0 (type);
9228 /* Given a method tree, put a printable description into the given
9229 buffer (overwriting) and return a pointer to the buffer. */
9231 static char *
9232 gen_method_decl (tree method)
9234 tree chain;
9236 strcpy (errbuf, "("); /* NB: Do _not_ call strcat() here. */
9237 gen_type_name_0 (TREE_VALUE (TREE_TYPE (method)));
9238 strcat (errbuf, ")");
9239 chain = METHOD_SEL_ARGS (method);
9241 if (chain)
9243 /* We have a chain of keyword_decls. */
9246 if (KEYWORD_KEY_NAME (chain))
9247 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_KEY_NAME (chain)));
9249 strcat (errbuf, ":(");
9250 gen_type_name_0 (TREE_VALUE (TREE_TYPE (chain)));
9251 strcat (errbuf, ")");
9253 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_ARG_NAME (chain)));
9254 if ((chain = DECL_CHAIN (chain)))
9255 strcat (errbuf, " ");
9257 while (chain);
9259 if (METHOD_ADD_ARGS (method))
9261 chain = TREE_CHAIN (METHOD_ADD_ARGS (method));
9263 /* Know we have a chain of parm_decls. */
9264 while (chain)
9266 strcat (errbuf, ", ");
9267 gen_type_name_0 (TREE_TYPE (TREE_VALUE (chain)));
9268 chain = TREE_CHAIN (chain);
9271 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
9272 strcat (errbuf, ", ...");
9276 else
9277 /* We have a unary selector. */
9278 strcat (errbuf, IDENTIFIER_POINTER (METHOD_SEL_NAME (method)));
9280 return errbuf;
9283 /* Debug info. */
9286 /* Dump an @interface declaration of the supplied class CHAIN to the
9287 supplied file FP. Used to implement the -gen-decls option (which
9288 prints out an @interface declaration of all classes compiled in
9289 this run); potentially useful for debugging the compiler too. */
9290 void
9291 dump_interface (FILE *fp, tree chain)
9293 /* FIXME: A heap overflow here whenever a method (or ivar)
9294 declaration is so long that it doesn't fit in the buffer. The
9295 code and all the related functions should be rewritten to avoid
9296 using fixed size buffers. */
9297 const char *my_name = IDENTIFIER_POINTER (CLASS_NAME (chain));
9298 tree ivar_decls = CLASS_RAW_IVARS (chain);
9299 tree nst_methods = CLASS_NST_METHODS (chain);
9300 tree cls_methods = CLASS_CLS_METHODS (chain);
9302 fprintf (fp, "\n@interface %s", my_name);
9304 /* CLASS_SUPER_NAME is used to store the superclass name for
9305 classes, and the category name for categories. */
9306 if (CLASS_SUPER_NAME (chain))
9308 const char *name = IDENTIFIER_POINTER (CLASS_SUPER_NAME (chain));
9310 switch (TREE_CODE (chain))
9312 case CATEGORY_IMPLEMENTATION_TYPE:
9313 case CATEGORY_INTERFACE_TYPE:
9314 fprintf (fp, " (%s)\n", name);
9315 break;
9316 default:
9317 fprintf (fp, " : %s\n", name);
9318 break;
9321 else
9322 fprintf (fp, "\n");
9324 /* FIXME - the following doesn't seem to work at the moment. */
9325 if (ivar_decls)
9327 fprintf (fp, "{\n");
9330 fprintf (fp, "\t%s;\n", gen_declaration (ivar_decls));
9331 ivar_decls = TREE_CHAIN (ivar_decls);
9333 while (ivar_decls);
9334 fprintf (fp, "}\n");
9337 while (nst_methods)
9339 fprintf (fp, "- %s;\n", gen_method_decl (nst_methods));
9340 nst_methods = TREE_CHAIN (nst_methods);
9343 while (cls_methods)
9345 fprintf (fp, "+ %s;\n", gen_method_decl (cls_methods));
9346 cls_methods = TREE_CHAIN (cls_methods);
9349 fprintf (fp, "@end\n");
9352 #if 0
9353 /* Produce the pretty printing for an Objective-C method. This is
9354 currently unused, but could be handy while reorganizing the pretty
9355 printing to be more robust. */
9356 static const char *
9357 objc_pretty_print_method (bool is_class_method,
9358 const char *class_name,
9359 const char *category_name,
9360 const char *selector)
9362 if (category_name)
9364 char *result = XNEWVEC (char, strlen (class_name) + strlen (category_name)
9365 + strlen (selector) + 7);
9367 if (is_class_method)
9368 sprintf (result, "+[%s(%s) %s]", class_name, category_name, selector);
9369 else
9370 sprintf (result, "-[%s(%s) %s]", class_name, category_name, selector);
9372 return result;
9374 else
9376 char *result = XNEWVEC (char, strlen (class_name)
9377 + strlen (selector) + 5);
9379 if (is_class_method)
9380 sprintf (result, "+[%s %s]", class_name, selector);
9381 else
9382 sprintf (result, "-[%s %s]", class_name, selector);
9384 return result;
9387 #endif
9389 /* Demangle function for Objective-C. Attempt to demangle the
9390 function name associated with a method (eg, going from
9391 "_i_NSObject__class" to "-[NSObject class]"); usually for the
9392 purpose of pretty printing or error messages. Return the demangled
9393 name, or NULL if the string is not an Objective-C mangled method
9394 name.
9396 Because of how the mangling is done, any method that has a '_' in
9397 its original name is at risk of being demangled incorrectly. In
9398 some cases there are multiple valid ways to demangle a method name
9399 and there is no way we can decide.
9401 TODO: objc_demangle() can't always get it right; the right way to
9402 get this correct for all method names would be to store the
9403 Objective-C method name somewhere in the function decl. Then,
9404 there is no demangling to do; we'd just pull the method name out of
9405 the decl. As an additional bonus, when printing error messages we
9406 could check for such a method name, and if we find it, we know the
9407 function is actually an Objective-C method and we could print error
9408 messages saying "In method '+[NSObject class]" instead of "In
9409 function '+[NSObject class]" as we do now. */
9410 static const char *
9411 objc_demangle (const char *mangled)
9413 char *demangled, *cp;
9415 /* First of all, if the name is too short it can't be an Objective-C
9416 mangled method name. */
9417 if (mangled[0] == '\0' || mangled[1] == '\0' || mangled[2] == '\0')
9418 return NULL;
9420 /* If the name looks like an already demangled one, return it
9421 unchanged. This should only happen on Darwin, where method names
9422 are mangled differently into a pretty-print form (such as
9423 '+[NSObject class]', see darwin.h). In that case, demangling is
9424 a no-op, but we need to return the demangled name if it was an
9425 ObjC one, and return NULL if not. We should be safe as no C/C++
9426 function can start with "-[" or "+[". */
9427 if ((mangled[0] == '-' || mangled[0] == '+')
9428 && (mangled[1] == '['))
9429 return mangled;
9431 if (mangled[0] == '_' &&
9432 (mangled[1] == 'i' || mangled[1] == 'c') &&
9433 mangled[2] == '_')
9435 cp = demangled = XNEWVEC (char, strlen(mangled) + 2);
9436 if (mangled[1] == 'i')
9437 *cp++ = '-'; /* for instance method */
9438 else
9439 *cp++ = '+'; /* for class method */
9440 *cp++ = '['; /* opening left brace */
9441 strcpy(cp, mangled+3); /* tack on the rest of the mangled name */
9442 while (*cp && *cp == '_')
9443 cp++; /* skip any initial underbars in class name */
9444 cp = strchr(cp, '_'); /* find first non-initial underbar */
9445 if (cp == NULL)
9447 free(demangled); /* not mangled name */
9448 return NULL;
9450 if (cp[1] == '_') /* easy case: no category name */
9452 *cp++ = ' '; /* replace two '_' with one ' ' */
9453 strcpy(cp, mangled + (cp - demangled) + 2);
9455 else
9457 *cp++ = '('; /* less easy case: category name */
9458 cp = strchr(cp, '_');
9459 if (cp == 0)
9461 free(demangled); /* not mangled name */
9462 return NULL;
9464 *cp++ = ')';
9465 *cp++ = ' '; /* overwriting 1st char of method name... */
9466 strcpy(cp, mangled + (cp - demangled)); /* get it back */
9468 /* Now we have the method name. We need to generally replace
9469 '_' with ':' but trying to preserve '_' if it could only have
9470 been in the mangled string because it was already in the
9471 original name. In cases where it's ambiguous, we assume that
9472 any '_' originated from a ':'. */
9474 /* Initial '_'s in method name can't have been generating by
9475 converting ':'s. Skip them. */
9476 while (*cp && *cp == '_')
9477 cp++;
9479 /* If the method name does not end with '_', then it has no
9480 arguments and there was no replacement of ':'s with '_'s
9481 during mangling. Check for that case, and skip any
9482 replacement if so. This at least guarantees that methods
9483 with no arguments are always demangled correctly (unless the
9484 original name ends with '_'). */
9485 if (*(mangled + strlen (mangled) - 1) != '_')
9487 /* Skip to the end. */
9488 for (; *cp; cp++)
9491 else
9493 /* Replace remaining '_' with ':'. This may get it wrong if
9494 there were '_'s in the original name. In most cases it
9495 is impossible to disambiguate. */
9496 for (; *cp; cp++)
9497 if (*cp == '_')
9498 *cp = ':';
9500 *cp++ = ']'; /* closing right brace */
9501 *cp++ = 0; /* string terminator */
9502 return demangled;
9504 else
9505 return NULL; /* not an objc mangled name */
9508 /* Try to pretty-print a decl. If the 'decl' is an Objective-C
9509 specific decl, return the printable name for it. If not, return
9510 NULL. */
9511 const char *
9512 objc_maybe_printable_name (tree decl, int v ATTRIBUTE_UNUSED)
9514 switch (TREE_CODE (decl))
9516 case FUNCTION_DECL:
9517 return objc_demangle (IDENTIFIER_POINTER (DECL_NAME (decl)));
9519 /* The following happens when we are printing a deprecation
9520 warning for a method. The warn_deprecation() will end up
9521 trying to print the decl for INSTANCE_METHOD_DECL or
9522 CLASS_METHOD_DECL. It would be nice to be able to print
9523 "-[NSObject autorelease] is deprecated", but to do that, we'd
9524 need to store the class and method name in the method decl,
9525 which we currently don't do. For now, just return the name
9526 of the method. We don't return NULL, because that may
9527 trigger further attempts to pretty-print the decl in C/C++,
9528 but they wouldn't know how to pretty-print it. */
9529 case INSTANCE_METHOD_DECL:
9530 case CLASS_METHOD_DECL:
9531 return IDENTIFIER_POINTER (DECL_NAME (decl));
9532 /* This happens when printing a deprecation warning for a
9533 property. We may want to consider some sort of pretty
9534 printing (eg, include the class name where it was declared
9535 ?). */
9536 case PROPERTY_DECL:
9537 return IDENTIFIER_POINTER (PROPERTY_NAME (decl));
9538 default:
9539 return NULL;
9543 /* Return a printable name for 'decl'. This first tries
9544 objc_maybe_printable_name(), and if that fails, it returns the name
9545 in the decl. This is used as LANG_HOOKS_DECL_PRINTABLE_NAME for
9546 Objective-C; in Objective-C++, setting the hook is not enough
9547 because lots of C++ Front-End code calls cxx_printable_name,
9548 dump_decl and other C++ functions directly. So instead we have
9549 modified dump_decl to call objc_maybe_printable_name directly. */
9550 const char *
9551 objc_printable_name (tree decl, int v)
9553 const char *demangled_name = objc_maybe_printable_name (decl, v);
9555 if (demangled_name != NULL)
9556 return demangled_name;
9557 else
9558 return IDENTIFIER_POINTER (DECL_NAME (decl));
9561 /* Routine is called to issue diagnostic when reference to a private
9562 ivar is made and no other variable with same name is found in
9563 current scope. */
9564 bool
9565 objc_diagnose_private_ivar (tree id)
9567 tree ivar;
9568 if (!objc_method_context)
9569 return false;
9570 ivar = is_ivar (objc_ivar_chain, id);
9571 if (ivar && is_private (ivar))
9573 error ("instance variable %qs is declared private",
9574 IDENTIFIER_POINTER (id));
9575 return true;
9577 return false;
9580 /* Look up ID as an instance variable. OTHER contains the result of
9581 the C or C++ lookup, which we may want to use instead. */
9582 /* To use properties inside an instance method, use self.property. */
9583 tree
9584 objc_lookup_ivar (tree other, tree id)
9586 tree ivar;
9588 /* If we are not inside of an ObjC method, ivar lookup makes no sense. */
9589 if (!objc_method_context)
9590 return other;
9592 if (!strcmp (IDENTIFIER_POINTER (id), "super"))
9593 /* We have a message to super. */
9594 return get_super_receiver ();
9596 /* In a class method, look up an instance variable only as a last
9597 resort. */
9598 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
9599 && other && other != error_mark_node)
9600 return other;
9602 /* Don't look up the ivar if the user has explicitly advised against
9603 it with -fno-local-ivars. */
9605 if (!flag_local_ivars)
9606 return other;
9608 /* Look up the ivar, but do not use it if it is not accessible. */
9609 ivar = is_ivar (objc_ivar_chain, id);
9611 if (!ivar || is_private (ivar))
9612 return other;
9614 /* In an instance method, a local variable (or parameter) may hide the
9615 instance variable. */
9616 if (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9617 && other && other != error_mark_node
9618 #ifdef OBJCPLUS
9619 && CP_DECL_CONTEXT (other) != global_namespace)
9620 #else
9621 && !DECL_FILE_SCOPE_P (other))
9622 #endif
9624 if (warn_shadow_ivar == 1 || (warn_shadow && warn_shadow_ivar != 0)) {
9625 warning (warn_shadow_ivar ? OPT_Wshadow_ivar : OPT_Wshadow,
9626 "local declaration of %qE hides instance variable", id);
9629 return other;
9632 /* At this point, we are either in an instance method with no obscuring
9633 local definitions, or in a class method with no alternate definitions
9634 at all. */
9635 return build_ivar_reference (id);
9638 /* Possibly rewrite a function CALL into an OBJ_TYPE_REF expression. This
9639 needs to be done if we are calling a function through a cast. */
9641 tree
9642 objc_rewrite_function_call (tree function, tree first_param)
9644 if (TREE_CODE (function) == NOP_EXPR
9645 && TREE_CODE (TREE_OPERAND (function, 0)) == ADDR_EXPR
9646 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (function, 0), 0))
9647 == FUNCTION_DECL)
9648 function = build3 (OBJ_TYPE_REF, TREE_TYPE (function),
9649 TREE_OPERAND (function, 0), first_param,
9650 build_int_cst (TREE_TYPE (first_param), 0));
9652 return function;
9655 /* This is called to "gimplify" a PROPERTY_REF node. It builds the
9656 corresponding 'getter' function call. Note that we assume the
9657 PROPERTY_REF to be valid since we generated it while parsing. */
9658 static void
9659 objc_gimplify_property_ref (tree *expr_p)
9661 tree getter = PROPERTY_REF_GETTER_CALL (*expr_p);
9662 tree call_exp;
9664 if (getter == NULL_TREE)
9666 tree property_decl = PROPERTY_REF_PROPERTY_DECL (*expr_p);
9667 /* This can happen if DECL_ARTIFICIAL (*expr_p), but
9668 should be impossible for real properties, which always
9669 have a getter. */
9670 error_at (EXPR_LOCATION (*expr_p), "no %qs getter found",
9671 IDENTIFIER_POINTER (PROPERTY_NAME (property_decl)));
9672 /* Try to recover from the error to prevent an ICE. We take
9673 zero and cast it to the type of the property. */
9674 *expr_p = convert (TREE_TYPE (property_decl),
9675 integer_zero_node);
9676 return;
9679 /* FIXME, this should be a label indicating availability in general. */
9680 if (PROPERTY_REF_DEPRECATED_GETTER (*expr_p))
9682 if (TREE_UNAVAILABLE (PROPERTY_REF_DEPRECATED_GETTER (*expr_p)))
9683 error_unavailable_use (PROPERTY_REF_DEPRECATED_GETTER (*expr_p),
9684 NULL_TREE);
9685 else
9686 /* PROPERTY_REF_DEPRECATED_GETTER contains the method prototype
9687 that is deprecated. */
9688 warn_deprecated_use (PROPERTY_REF_DEPRECATED_GETTER (*expr_p),
9689 NULL_TREE);
9692 call_exp = getter;
9693 #ifdef OBJCPLUS
9694 /* In C++, a getter which returns an aggregate value results in a
9695 target_expr which initializes a temporary to the call
9696 expression. */
9697 if (TREE_CODE (getter) == TARGET_EXPR)
9699 gcc_assert (MAYBE_CLASS_TYPE_P (TREE_TYPE (getter)));
9700 gcc_assert (VAR_P (TREE_OPERAND (getter, 0)));
9701 call_exp = TREE_OPERAND (getter, 1);
9703 #endif
9704 gcc_checking_assert ((flag_objc_nilcheck
9705 && TREE_CODE (call_exp) == COND_EXPR)
9706 || TREE_CODE (call_exp) == CALL_EXPR);
9708 *expr_p = call_exp;
9711 /* This is called when "gimplifying" the trees. We need to gimplify
9712 the Objective-C/Objective-C++ specific trees, then hand over the
9713 process to C/C++. */
9715 objc_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
9717 enum tree_code code = TREE_CODE (*expr_p);
9718 switch (code)
9720 /* Look for the special case of OBJC_TYPE_REF with the address
9721 of a function in OBJ_TYPE_REF_EXPR (presumably objc_msgSend
9722 or one of its cousins). */
9723 case OBJ_TYPE_REF:
9724 if (TREE_CODE (OBJ_TYPE_REF_EXPR (*expr_p)) == ADDR_EXPR
9725 && TREE_CODE (TREE_OPERAND (OBJ_TYPE_REF_EXPR (*expr_p), 0))
9726 == FUNCTION_DECL)
9728 enum gimplify_status r0, r1;
9730 /* Postincrements in OBJ_TYPE_REF_OBJECT don't affect the
9731 value of the OBJ_TYPE_REF, so force them to be emitted
9732 during subexpression evaluation rather than after the
9733 OBJ_TYPE_REF. This permits objc_msgSend calls in
9734 Objective C to use direct rather than indirect calls when
9735 the object expression has a postincrement. */
9736 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p, NULL,
9737 is_gimple_val, fb_rvalue);
9738 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p, post_p,
9739 is_gimple_val, fb_rvalue);
9741 return MIN (r0, r1);
9743 break;
9744 case PROPERTY_REF:
9745 objc_gimplify_property_ref (expr_p);
9746 /* Do not return yet; let C/C++ gimplify the resulting expression. */
9747 break;
9748 default:
9749 break;
9752 #ifdef OBJCPLUS
9753 return (enum gimplify_status) cp_gimplify_expr (expr_p, pre_p, post_p);
9754 #else
9755 return (enum gimplify_status) c_gimplify_expr (expr_p, pre_p, post_p);
9756 #endif
9759 /* --- FAST ENUMERATION --- */
9760 /* Begin code generation for fast enumeration (foreach) ... */
9762 /* Defines
9764 struct __objcFastEnumerationState
9766 unsigned long state;
9767 id *itemsPtr;
9768 unsigned long *mutationsPtr;
9769 unsigned long extra[5];
9772 Confusingly enough, NSFastEnumeration is then defined by libraries
9773 to be the same structure.
9776 static void
9777 build_fast_enumeration_state_template (void)
9779 tree decls, *chain = NULL;
9781 /* { */
9782 objc_fast_enumeration_state_template = objc_start_struct (get_identifier
9783 (TAG_FAST_ENUMERATION_STATE));
9785 /* unsigned long state; */
9786 decls = add_field_decl (long_unsigned_type_node, "state", &chain);
9788 /* id *itemsPtr; */
9789 add_field_decl (build_pointer_type (objc_object_type),
9790 "itemsPtr", &chain);
9792 /* unsigned long *mutationsPtr; */
9793 add_field_decl (build_pointer_type (long_unsigned_type_node),
9794 "mutationsPtr", &chain);
9796 /* unsigned long extra[5]; */
9797 add_field_decl (build_sized_array_type (long_unsigned_type_node, 5),
9798 "extra", &chain);
9800 /* } */
9801 objc_finish_struct (objc_fast_enumeration_state_template, decls);
9805 'objc_finish_foreach_loop()' generates the code for an Objective-C
9806 foreach loop. The 'location' argument is the location of the 'for'
9807 that starts the loop. The 'object_expression' is the expression of
9808 the 'object' that iterates; the 'collection_expression' is the
9809 expression of the collection that we iterate over (we need to make
9810 sure we evaluate this only once); the 'for_body' is the set of
9811 statements to be executed in each iteration; 'break_label' and
9812 'continue_label' are the break and continue labels which we need to
9813 emit since the <statements> may be jumping to 'break_label' (if they
9814 contain 'break') or to 'continue_label' (if they contain
9815 'continue').
9817 The syntax is
9819 for (<object expression> in <collection expression>)
9820 <statements>
9822 which is compiled into the following blurb:
9825 id __objc_foreach_collection;
9826 __objc_fast_enumeration_state __objc_foreach_enum_state;
9827 unsigned long __objc_foreach_batchsize;
9828 id __objc_foreach_items[16];
9829 __objc_foreach_collection = <collection expression>;
9830 __objc_foreach_enum_state = { 0 };
9831 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
9833 if (__objc_foreach_batchsize == 0)
9834 <object expression> = nil;
9835 else
9837 unsigned long __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr;
9838 next_batch:
9840 unsigned long __objc_foreach_index;
9841 __objc_foreach_index = 0;
9843 next_object:
9844 if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>);
9845 <object expression> = enumState.itemsPtr[__objc_foreach_index];
9846 <statements> [PS: inside <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label]
9848 continue_label:
9849 __objc_foreach_index++;
9850 if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object;
9851 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
9853 if (__objc_foreach_batchsize != 0) goto next_batch;
9854 <object expression> = nil;
9855 break_label:
9859 'statements' may contain a 'continue' or 'break' instruction, which
9860 the user expects to 'continue' or 'break' the entire foreach loop.
9861 We are provided the labels that 'break' and 'continue' jump to, so
9862 we place them where we want them to jump to when they pick them.
9864 Optimization TODO: we could cache the IMP of
9865 countByEnumeratingWithState:objects:count:.
9868 /* If you need to debug objc_finish_foreach_loop(), uncomment the following line. */
9869 /* #define DEBUG_OBJC_FINISH_FOREACH_LOOP 1 */
9871 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
9872 #include "tree-pretty-print.h"
9873 #endif
9875 void
9876 objc_finish_foreach_loop (location_t location, tree object_expression, tree collection_expression, tree for_body,
9877 tree break_label, tree continue_label)
9879 /* A tree representing the __objcFastEnumerationState struct type,
9880 or NSFastEnumerationState struct, whatever we are using. */
9881 tree objc_fast_enumeration_state_type;
9883 /* The trees representing the declarations of each of the local variables. */
9884 tree objc_foreach_collection_decl;
9885 tree objc_foreach_enum_state_decl;
9886 tree objc_foreach_items_decl;
9887 tree objc_foreach_batchsize_decl;
9888 tree objc_foreach_mutations_pointer_decl;
9889 tree objc_foreach_index_decl;
9891 /* A tree representing the selector countByEnumeratingWithState:objects:count:. */
9892 tree selector_name;
9894 /* A tree representing the local bind. */
9895 tree bind;
9897 /* A tree representing the external 'if (__objc_foreach_batchsize)' */
9898 tree first_if;
9900 /* A tree representing the 'else' part of 'first_if' */
9901 tree first_else;
9903 /* A tree representing the 'next_batch' label. */
9904 tree next_batch_label_decl;
9906 /* A tree representing the binding after the 'next_batch' label. */
9907 tree next_batch_bind;
9909 /* A tree representing the 'next_object' label. */
9910 tree next_object_label_decl;
9912 /* Temporary variables. */
9913 tree t;
9914 int i;
9916 if (flag_objc1_only)
9917 error_at (location, "fast enumeration is not available in Objective-C 1.0");
9919 if (object_expression == error_mark_node)
9920 return;
9922 if (collection_expression == error_mark_node)
9923 return;
9925 if (!objc_type_valid_for_messaging (TREE_TYPE (object_expression), true))
9927 error_at (location, "iterating variable in fast enumeration is not an object");
9928 return;
9931 if (!objc_type_valid_for_messaging (TREE_TYPE (collection_expression), true))
9933 error_at (location, "collection in fast enumeration is not an object");
9934 return;
9937 /* TODO: Check that object_expression is either a variable
9938 declaration, or an lvalue. */
9940 /* This kludge is an idea from apple. We use the
9941 __objcFastEnumerationState struct implicitly defined by the
9942 compiler, unless a NSFastEnumerationState struct has been defined
9943 (by a Foundation library such as GNUstep Base) in which case, we
9944 use that one.
9946 objc_fast_enumeration_state_type = objc_fast_enumeration_state_template;
9948 tree objc_NSFastEnumeration_type = lookup_name (get_identifier ("NSFastEnumerationState"));
9950 if (objc_NSFastEnumeration_type)
9952 /* TODO: We really need to check that
9953 objc_NSFastEnumeration_type is the same as ours! */
9954 if (TREE_CODE (objc_NSFastEnumeration_type) == TYPE_DECL)
9956 /* If it's a typedef, use the original type. */
9957 if (DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type))
9958 objc_fast_enumeration_state_type = DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type);
9959 else
9960 objc_fast_enumeration_state_type = TREE_TYPE (objc_NSFastEnumeration_type);
9965 /* { */
9966 /* Done by c-parser.cc. */
9968 /* type object; */
9969 /* Done by c-parser.cc. */
9971 /* Disable warnings that 'object' is unused. For example the code
9973 for (id object in collection)
9974 i++;
9976 which can be used to count how many objects there are in the
9977 collection is fine and should generate no warnings even if
9978 'object' is technically unused. */
9979 TREE_USED (object_expression) = 1;
9980 if (DECL_P (object_expression))
9981 DECL_READ_P (object_expression) = 1;
9983 /* id __objc_foreach_collection */
9984 objc_foreach_collection_decl = objc_create_temporary_var (objc_object_type, "__objc_foreach_collection");
9986 /* __objcFastEnumerationState __objc_foreach_enum_state; */
9987 objc_foreach_enum_state_decl = objc_create_temporary_var (objc_fast_enumeration_state_type, "__objc_foreach_enum_state");
9988 TREE_CHAIN (objc_foreach_enum_state_decl) = objc_foreach_collection_decl;
9990 /* id __objc_foreach_items[16]; */
9991 objc_foreach_items_decl = objc_create_temporary_var (build_sized_array_type (objc_object_type, 16), "__objc_foreach_items");
9992 TREE_CHAIN (objc_foreach_items_decl) = objc_foreach_enum_state_decl;
9994 /* unsigned long __objc_foreach_batchsize; */
9995 objc_foreach_batchsize_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_batchsize");
9996 TREE_CHAIN (objc_foreach_batchsize_decl) = objc_foreach_items_decl;
9998 /* Generate the local variable binding. */
9999 bind = build3 (BIND_EXPR, void_type_node, objc_foreach_batchsize_decl, NULL, NULL);
10000 SET_EXPR_LOCATION (bind, location);
10001 TREE_SIDE_EFFECTS (bind) = 1;
10003 /* __objc_foreach_collection = <collection expression>; */
10004 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_collection_decl, collection_expression);
10005 SET_EXPR_LOCATION (t, location);
10006 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10007 /* We have used 'collection_expression'. */
10008 mark_exp_read (collection_expression);
10010 /* __objc_foreach_enum_state.state = 0; */
10011 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10012 get_identifier ("state")),
10013 build_int_cst (long_unsigned_type_node, 0));
10014 SET_EXPR_LOCATION (t, location);
10015 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10017 /* __objc_foreach_enum_state.itemsPtr = NULL; */
10018 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10019 get_identifier ("itemsPtr")),
10020 null_pointer_node);
10021 SET_EXPR_LOCATION (t, location);
10022 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10024 /* __objc_foreach_enum_state.mutationsPtr = NULL; */
10025 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
10026 get_identifier ("mutationsPtr")),
10027 null_pointer_node);
10028 SET_EXPR_LOCATION (t, location);
10029 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10031 /* __objc_foreach_enum_state.extra[0] = 0; */
10032 /* __objc_foreach_enum_state.extra[1] = 0; */
10033 /* __objc_foreach_enum_state.extra[2] = 0; */
10034 /* __objc_foreach_enum_state.extra[3] = 0; */
10035 /* __objc_foreach_enum_state.extra[4] = 0; */
10036 for (i = 0; i < 5 ; i++)
10038 t = build2 (MODIFY_EXPR, void_type_node,
10039 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10040 get_identifier ("extra")),
10041 build_int_cst (NULL_TREE, i)),
10042 build_int_cst (long_unsigned_type_node, 0));
10043 SET_EXPR_LOCATION (t, location);
10044 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10047 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
10048 selector_name = get_identifier ("countByEnumeratingWithState:objects:count:");
10049 #ifdef OBJCPLUS
10050 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10051 /* Parameters. */
10052 tree_cons /* &__objc_foreach_enum_state */
10053 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10054 tree_cons /* __objc_foreach_items */
10055 (NULL_TREE, objc_foreach_items_decl,
10056 tree_cons /* 16 */
10057 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10058 #else
10059 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
10061 struct c_expr array;
10062 array.value = objc_foreach_items_decl;
10063 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10064 /* Parameters. */
10065 tree_cons /* &__objc_foreach_enum_state */
10066 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10067 tree_cons /* __objc_foreach_items */
10068 (NULL_TREE, default_function_array_conversion (location, array).value,
10069 tree_cons /* 16 */
10070 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10072 #endif
10073 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
10074 convert (long_unsigned_type_node, t));
10075 SET_EXPR_LOCATION (t, location);
10076 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
10078 /* if (__objc_foreach_batchsize == 0) */
10079 first_if = build3 (COND_EXPR, void_type_node,
10080 /* Condition. */
10081 c_fully_fold
10082 (c_common_truthvalue_conversion
10083 (location,
10084 build_binary_op (location,
10085 EQ_EXPR,
10086 objc_foreach_batchsize_decl,
10087 build_int_cst (long_unsigned_type_node, 0), 1)),
10088 false, NULL),
10089 /* Then block (we fill it in later). */
10090 NULL_TREE,
10091 /* Else block (we fill it in later). */
10092 NULL_TREE);
10093 SET_EXPR_LOCATION (first_if, location);
10094 append_to_statement_list (first_if, &BIND_EXPR_BODY (bind));
10096 /* then <object expression> = nil; */
10097 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
10098 SET_EXPR_LOCATION (t, location);
10099 COND_EXPR_THEN (first_if) = t;
10101 /* Now we build the 'else' part of the if; once we finish building
10102 it, we attach it to first_if as the 'else' part. */
10104 /* else */
10105 /* { */
10107 /* unsigned long __objc_foreach_mutations_pointer; */
10108 objc_foreach_mutations_pointer_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_mutations_pointer");
10110 /* Generate the local variable binding. */
10111 first_else = build3 (BIND_EXPR, void_type_node, objc_foreach_mutations_pointer_decl, NULL, NULL);
10112 SET_EXPR_LOCATION (first_else, location);
10113 TREE_SIDE_EFFECTS (first_else) = 1;
10115 /* __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr; */
10116 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_mutations_pointer_decl,
10117 build_indirect_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10118 get_identifier ("mutationsPtr")),
10119 RO_UNARY_STAR));
10120 SET_EXPR_LOCATION (t, location);
10121 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10123 /* next_batch: */
10124 next_batch_label_decl = create_artificial_label (location);
10125 t = build1 (LABEL_EXPR, void_type_node, next_batch_label_decl);
10126 SET_EXPR_LOCATION (t, location);
10127 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10129 /* { */
10131 /* unsigned long __objc_foreach_index; */
10132 objc_foreach_index_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_index");
10134 /* Generate the local variable binding. */
10135 next_batch_bind = build3 (BIND_EXPR, void_type_node, objc_foreach_index_decl, NULL, NULL);
10136 SET_EXPR_LOCATION (next_batch_bind, location);
10137 TREE_SIDE_EFFECTS (next_batch_bind) = 1;
10138 append_to_statement_list (next_batch_bind, &BIND_EXPR_BODY (first_else));
10140 /* __objc_foreach_index = 0; */
10141 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
10142 build_int_cst (long_unsigned_type_node, 0));
10143 SET_EXPR_LOCATION (t, location);
10144 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10146 /* next_object: */
10147 next_object_label_decl = create_artificial_label (location);
10148 t = build1 (LABEL_EXPR, void_type_node, next_object_label_decl);
10149 SET_EXPR_LOCATION (t, location);
10150 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10152 /* if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>); */
10153 t = build3 (COND_EXPR, void_type_node,
10154 /* Condition. */
10155 c_fully_fold
10156 (c_common_truthvalue_conversion
10157 (location,
10158 build_binary_op
10159 (location,
10160 NE_EXPR,
10161 objc_foreach_mutations_pointer_decl,
10162 build_indirect_ref (location,
10163 objc_build_component_ref (objc_foreach_enum_state_decl,
10164 get_identifier ("mutationsPtr")),
10165 RO_UNARY_STAR), 1)),
10166 false, NULL),
10167 /* Then block. */
10168 build_function_call (input_location,
10169 objc_enumeration_mutation_decl,
10170 tree_cons (NULL, collection_expression, NULL)),
10171 /* Else block. */
10172 NULL_TREE);
10173 SET_EXPR_LOCATION (t, location);
10174 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10176 /* <object expression> = enumState.itemsPtr[__objc_foreach_index]; */
10177 t = build2 (MODIFY_EXPR, void_type_node, object_expression,
10178 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
10179 get_identifier ("itemsPtr")),
10180 objc_foreach_index_decl));
10181 SET_EXPR_LOCATION (t, location);
10182 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10184 /* <statements> [PS: in <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label] */
10185 append_to_statement_list (for_body, &BIND_EXPR_BODY (next_batch_bind));
10187 /* continue_label: */
10188 if (continue_label)
10190 t = build1 (LABEL_EXPR, void_type_node, continue_label);
10191 SET_EXPR_LOCATION (t, location);
10192 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10195 /* __objc_foreach_index++; */
10196 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
10197 build_binary_op (location,
10198 PLUS_EXPR,
10199 objc_foreach_index_decl,
10200 build_int_cst (long_unsigned_type_node, 1), 1));
10201 SET_EXPR_LOCATION (t, location);
10202 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10204 /* if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object; */
10205 t = build3 (COND_EXPR, void_type_node,
10206 /* Condition. */
10207 c_fully_fold
10208 (c_common_truthvalue_conversion
10209 (location,
10210 build_binary_op (location,
10211 LT_EXPR,
10212 objc_foreach_index_decl,
10213 objc_foreach_batchsize_decl, 1)),
10214 false, NULL),
10215 /* Then block. */
10216 build1 (GOTO_EXPR, void_type_node, next_object_label_decl),
10217 /* Else block. */
10218 NULL_TREE);
10219 SET_EXPR_LOCATION (t, location);
10220 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10222 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
10223 #ifdef OBJCPLUS
10224 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10225 /* Parameters. */
10226 tree_cons /* &__objc_foreach_enum_state */
10227 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10228 tree_cons /* __objc_foreach_items */
10229 (NULL_TREE, objc_foreach_items_decl,
10230 tree_cons /* 16 */
10231 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10232 #else
10233 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
10235 struct c_expr array;
10236 array.value = objc_foreach_items_decl;
10237 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10238 /* Parameters. */
10239 tree_cons /* &__objc_foreach_enum_state */
10240 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10241 tree_cons /* __objc_foreach_items */
10242 (NULL_TREE, default_function_array_conversion (location, array).value,
10243 tree_cons /* 16 */
10244 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10246 #endif
10247 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
10248 convert (long_unsigned_type_node, t));
10249 SET_EXPR_LOCATION (t, location);
10250 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10252 /* } */
10254 /* if (__objc_foreach_batchsize != 0) goto next_batch; */
10255 t = build3 (COND_EXPR, void_type_node,
10256 /* Condition. */
10257 c_fully_fold
10258 (c_common_truthvalue_conversion
10259 (location,
10260 build_binary_op (location,
10261 NE_EXPR,
10262 objc_foreach_batchsize_decl,
10263 build_int_cst (long_unsigned_type_node, 0), 1)),
10264 false, NULL),
10265 /* Then block. */
10266 build1 (GOTO_EXPR, void_type_node, next_batch_label_decl),
10267 /* Else block. */
10268 NULL_TREE);
10269 SET_EXPR_LOCATION (t, location);
10270 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10272 /* <object expression> = nil; */
10273 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
10274 SET_EXPR_LOCATION (t, location);
10275 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10277 /* break_label: */
10278 if (break_label)
10280 t = build1 (LABEL_EXPR, void_type_node, break_label);
10281 SET_EXPR_LOCATION (t, location);
10282 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10285 /* } */
10286 COND_EXPR_ELSE (first_if) = first_else;
10288 /* Do the whole thing. */
10289 add_stmt (bind);
10291 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
10292 /* This will print to stderr the whole blurb generated by the
10293 compiler while compiling (assuming the compiler doesn't crash
10294 before getting here).
10296 debug_generic_stmt (bind);
10297 #endif
10299 /* } */
10300 /* Done by c-parser.cc */
10303 /* --- SUPPORT FOR FORMAT ARG CHECKING --- */
10304 /* Return true if we have an NxString object pointer. */
10306 bool
10307 objc_string_ref_type_p (tree strp)
10309 tree tmv;
10310 if (!strp || TREE_CODE (strp) != POINTER_TYPE)
10311 return false;
10313 tmv = TYPE_MAIN_VARIANT (TREE_TYPE (strp));
10314 tmv = OBJC_TYPE_NAME (tmv);
10315 return (tmv
10316 && TREE_CODE (tmv) == IDENTIFIER_NODE
10317 && IDENTIFIER_POINTER (tmv)
10318 && startswith (IDENTIFIER_POINTER (tmv), "NSString"));
10321 /* At present the behavior of this is undefined and it does nothing. */
10322 void
10323 objc_check_format_arg (tree ARG_UNUSED (format_arg),
10324 tree ARG_UNUSED (args_list))
10328 void
10329 objc_common_init_ts (void)
10331 c_common_init_ts ();
10333 MARK_TS_DECL_NON_COMMON (CLASS_METHOD_DECL);
10334 MARK_TS_DECL_NON_COMMON (INSTANCE_METHOD_DECL);
10335 MARK_TS_DECL_NON_COMMON (KEYWORD_DECL);
10336 MARK_TS_DECL_NON_COMMON (PROPERTY_DECL);
10338 MARK_TS_COMMON (CLASS_INTERFACE_TYPE);
10339 MARK_TS_COMMON (PROTOCOL_INTERFACE_TYPE);
10340 MARK_TS_COMMON (CLASS_IMPLEMENTATION_TYPE);
10342 MARK_TS_TYPED (MESSAGE_SEND_EXPR);
10343 MARK_TS_TYPED (PROPERTY_REF);
10346 /* Information for Objective-C-specific features known to __has_feature. */
10348 struct objc_feature_info
10350 typedef bool (*predicate_t) ();
10352 const char *ident;
10353 predicate_t predicate;
10355 constexpr objc_feature_info (const char *name)
10356 : ident (name), predicate (nullptr) {}
10357 constexpr objc_feature_info (const char *name, predicate_t p)
10358 : ident (name), predicate (p) {}
10360 bool has_feature () const
10362 return predicate ? predicate () : true;
10366 static bool objc_nonfragile_abi_p ()
10368 return flag_next_runtime && flag_objc_abi >= 2;
10371 static constexpr objc_feature_info objc_features[] =
10373 { "objc_default_synthesize_properties" },
10374 { "objc_instancetype" },
10375 { "objc_nonfragile_abi", objc_nonfragile_abi_p }
10378 /* Register Objective-C-specific features for __has_feature. */
10380 void
10381 objc_common_register_features ()
10383 for (unsigned i = 0; i < ARRAY_SIZE (objc_features); i++)
10385 const objc_feature_info *info = objc_features + i;
10386 if (!info->has_feature ())
10387 continue;
10389 c_common_register_feature (info->ident, true);
10393 #include "gt-objc-objc-act.h"