1 /* Implement classes and message passing for Objective C.
2 Copyright (C) 1992-2020 Free Software Foundation, Inc.
3 Contributed by Steve Naroff.
4
5 This file is part of GCC.
6
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.
11
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.
16
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/>. */
20
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"
29
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
36
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 (). */
54
55 /* For enum gimplify_status */
56 #include "gimple-expr.h"
57 #include "gimplify.h"
58
59 /* For encode_method_prototype(). */
60 #include "objc-encoding.h"
61
62 static unsigned int should_call_super_dealloc = 0;
63
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 */
70
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
93
94 /* These need specifying. */
95 #ifndef OBJC_FORWARDING_STACK_OFFSET
96 #define OBJC_FORWARDING_STACK_OFFSET 0
97 #endif
98
99 #ifndef OBJC_FORWARDING_MIN_OFFSET
100 #define OBJC_FORWARDING_MIN_OFFSET 0
101 #endif
102
103 /*** Private Interface (procedures) ***/
104
105 /* Init stuff. */
106 static void synth_module_prologue (void);
107
108 /* Code generation. */
109
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);
114
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);
120 static tree is_ivar (tree, tree);
121
122 /* We only need the following for ObjC; ObjC++ will use C++'s definition
123 of DERIVED_FROM_P. */
124 #ifndef OBJCPLUS
125 static bool objc_derived_from_p (tree, tree);
126 #define DERIVED_FROM_P(PARENT, CHILD) objc_derived_from_p (PARENT, CHILD)
127 #endif
128
129 /* Property. */
130 static void objc_gen_property_data (tree, tree);
131 static void objc_synthesize_getter (tree, tree, tree);
132 static void objc_synthesize_setter (tree, tree, tree);
133 static tree lookup_property (tree, tree);
134 static tree lookup_property_in_list (tree, tree);
135 static tree lookup_property_in_protocol_list (tree, tree);
136 static void build_common_objc_property_accessor_helpers (void);
137
138 static void objc_xref_basetypes (tree, tree);
139
140 static tree get_class_ivars (tree, bool);
141
142 static void build_fast_enumeration_state_template (void);
143
144 #ifdef OBJCPLUS
145 static void objc_generate_cxx_cdtors (void);
146 #endif
147
148 /* objc attribute */
149 static void objc_decl_method_attributes (tree*, tree, int);
150 static tree build_keyword_selector (tree);
151
152 static void hash_init (void);
153
154 /* Hash tables to manage the global pool of method prototypes. Each
155 of these maps map a method name (selector) identifier to either a
156 single tree (for methods with a single method prototype) or a
157 TREE_VEC (for methods with multiple method prototypes). */
158 static GTY(()) objc_map_t instance_method_map = 0;
159 static GTY(()) objc_map_t class_method_map = 0;
160
161 /* Hash tables to manage the global pool of class names. */
162
163 static GTY(()) objc_map_t class_name_map = 0;
164 static GTY(()) objc_map_t alias_name_map = 0;
165
166 static tree lookup_method (tree, tree);
167 static tree lookup_method_static (tree, tree, int);
168
169 static void interface_hash_init (void);
170 static tree add_interface (tree, tree);
171 static void add_category (tree, tree);
172 static inline tree lookup_category (tree, tree);
173
174 /* Protocols. */
175
176 static tree lookup_protocol (tree, bool, bool);
177 static tree lookup_and_install_protocols (tree, bool);
178
179 #ifdef OBJCPLUS
180 static void really_start_method (tree, tree);
181 #else
182 static void really_start_method (tree, struct c_arg_info *);
183 #endif
184 static int comp_proto_with_proto (tree, tree, int);
185 static tree objc_decay_parm_type (tree);
186
187 /* Utilities for debugging and error diagnostics. */
188
189 static char *gen_type_name (tree);
190 static char *gen_type_name_0 (tree);
191 static char *gen_method_decl (tree);
192 static char *gen_declaration (tree);
193
194 /* Everything else. */
195
196 static void generate_struct_by_value_array (void) ATTRIBUTE_NORETURN;
197
198 static void mark_referenced_methods (void);
199 static bool objc_type_valid_for_messaging (tree type, bool allow_classes);
200 static tree check_duplicates (tree, int, int);
201
202 /*** Private Interface (data) ***/
203 /* Flags for lookup_method_static(). */
204
205 /* Look for class methods. */
206 #define OBJC_LOOKUP_CLASS 1
207 /* Do not examine superclasses. */
208 #define OBJC_LOOKUP_NO_SUPER 2
209 /* Disable returning an instance method of a root class when a class
210 method can't be found. */
211 #define OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS 4
212
213 /* The OCTI_... enumeration itself is in objc/objc-act.h. */
214 tree objc_global_trees[OCTI_MAX];
215
216 struct imp_entry *imp_list = 0;
217 int imp_count = 0; /* `@implementation' */
218 int cat_count = 0; /* `@category' */
219
220 objc_ivar_visibility_kind objc_ivar_visibility, objc_default_ivar_visibility;
221
222 /* Use to generate method labels. */
223 static int method_slot = 0;
224
225 /* Flag to say whether methods in a protocol are optional or
226 required. */
227 static bool objc_method_optional_flag = false;
228
229 static int objc_collecting_ivars = 0;
230
231 /* Flag that is set to 'true' while we are processing a class
232 extension. Since a class extension just "reopens" the main
233 @interface, this can be used to determine if we are in the main
234 @interface, or in a class extension. */
235 static bool objc_in_class_extension = false;
236
237 static char *errbuf; /* Buffer for error diagnostics */
238
239 /* An array of all the local variables in the current function that
240 need to be marked as volatile. */
241 vec<tree, va_gc> *local_variables_to_volatilize = NULL;
242
243 /* Store all constructed constant strings in a hash table so that
244 they get uniqued properly. */
245
246 struct GTY((for_user)) string_descriptor {
247 /* The literal argument . */
248 tree literal;
249
250 /* The resulting constant string. */
251 tree constructor;
252 };
253
254 struct objc_string_hasher : ggc_ptr_hash<string_descriptor>
255 {
256 static hashval_t hash (string_descriptor *);
257 static bool equal (string_descriptor *, string_descriptor *);
258 };
259
260 static GTY(()) hash_table<objc_string_hasher> *string_htab;
261
262 FILE *gen_declaration_file;
263
264 /* Hooks for stuff that differs between runtimes. */
265 objc_runtime_hooks runtime;
266
267 /* Create a temporary variable of type 'type'. If 'name' is set, uses
268 the specified name, else use no name. Returns the declaration of
269 the type. The 'name' is mostly useful for debugging.
270 */
271 tree
objc_create_temporary_var(tree type,const char * name)272 objc_create_temporary_var (tree type, const char *name)
273 {
274 tree decl;
275
276 if (name != NULL)
277 {
278 decl = build_decl (input_location,
279 VAR_DECL, get_identifier (name), type);
280 }
281 else
282 {
283 decl = build_decl (input_location,
284 VAR_DECL, NULL_TREE, type);
285 }
286 TREE_USED (decl) = 1;
287 DECL_ARTIFICIAL (decl) = 1;
288 DECL_IGNORED_P (decl) = 1;
289 DECL_CONTEXT (decl) = current_function_decl;
290
291 return decl;
292 }
293
294 /* Some platforms pass small structures through registers versus
295 through an invisible pointer. Determine at what size structure is
296 the transition point between the two possibilities. */
297
298 static void
generate_struct_by_value_array(void)299 generate_struct_by_value_array (void)
300 {
301 tree type;
302 tree decls;
303 int i, j;
304 int aggregate_in_mem[32];
305 int found = 0;
306
307 /* Presumably no platform passes 32 byte structures in a register. */
308 /* ??? As an example, m64/ppc/Darwin can pass up to 8*long+13*double
309 in registers. */
310 for (i = 1; i < 32; i++)
311 {
312 char buffer[5];
313 tree *chain = NULL;
314
315 /* Create an unnamed struct that has `i' character components */
316 type = objc_start_struct (NULL_TREE);
317
318 strcpy (buffer, "c1");
319 decls = add_field_decl (char_type_node, buffer, &chain);
320
321 for (j = 1; j < i; j++)
322 {
323 sprintf (buffer, "c%d", j + 1);
324 add_field_decl (char_type_node, buffer, &chain);
325 }
326 objc_finish_struct (type, decls);
327
328 aggregate_in_mem[i] = aggregate_value_p (type, 0);
329 if (!aggregate_in_mem[i])
330 found = 1;
331 }
332
333 /* We found some structures that are returned in registers instead of memory
334 so output the necessary data. */
335 if (found)
336 {
337 for (i = 31; i >= 0; i--)
338 if (!aggregate_in_mem[i])
339 break;
340 printf ("#define OBJC_MAX_STRUCT_BY_VALUE %d\n", i);
341 }
342
343 exit (0);
344 }
345
346 bool
objc_init(void)347 objc_init (void)
348 {
349 bool ok;
350 #ifdef OBJCPLUS
351 if (cxx_init () == false)
352 #else
353 if (c_objc_common_init () == false)
354 #endif
355 return false;
356
357 /* print_struct_values is triggered by -print-runtime-info (used
358 when building libobjc, with an empty file as input). It does not
359 require any ObjC setup, and it never returns.
360
361 -fcompare-debug is used to check the compiler output; we are
362 executed twice, once with flag_compare_debug set, and once with
363 it not set. If the flag is used together with
364 -print-runtime-info, we want to print the runtime info only once,
365 else it would be output in duplicate. So we check
366 flag_compare_debug to output it in only one of the invocations.
367
368 As a side effect, this also that means -fcompare-debug
369 -print-runtime-info will run the compiler twice, and compare the
370 generated assembler file; the first time the compiler exits
371 immediately (producing no file), and the second time it compiles
372 an empty file. This checks, as a side effect, that compiling an
373 empty file produces no assembler output. */
374 if (print_struct_values && !flag_compare_debug)
375 generate_struct_by_value_array ();
376
377 /* Set up stuff used by FE parser and all runtimes. */
378 errbuf = XNEWVEC (char, 1024 * 10);
379 interface_hash_init ();
380 hash_init ();
381 objc_encoding_init ();
382 /* ... and then check flags and set-up for the selected runtime ... */
383 if (flag_next_runtime && flag_objc_abi >= 2)
384 ok = objc_next_runtime_abi_02_init (&runtime);
385 else if (flag_next_runtime)
386 ok = objc_next_runtime_abi_01_init (&runtime);
387 else
388 ok = objc_gnu_runtime_abi_01_init (&runtime);
389
390 /* If that part of the setup failed - bail out immediately. */
391 if (!ok)
392 return false;
393
394 /* Determine the default visibility for instance variables. */
395 switch (default_ivar_visibility)
396 {
397 case IVAR_VISIBILITY_PRIVATE:
398 objc_default_ivar_visibility = OBJC_IVAR_VIS_PRIVATE;
399 break;
400 case IVAR_VISIBILITY_PUBLIC:
401 objc_default_ivar_visibility = OBJC_IVAR_VIS_PUBLIC;
402 break;
403 case IVAR_VISIBILITY_PACKAGE:
404 objc_default_ivar_visibility = OBJC_IVAR_VIS_PACKAGE;
405 break;
406 default:
407 objc_default_ivar_visibility = OBJC_IVAR_VIS_PROTECTED;
408 }
409
410 /* Generate general types and push runtime-specific decls to file scope. */
411 synth_module_prologue ();
412
413 return true;
414 }
415
416 /* This is called at the end of parsing by the C/C++ parsers. */
417 void
objc_write_global_declarations(void)418 objc_write_global_declarations (void)
419 {
420 mark_referenced_methods ();
421
422 /* A missing @end might not be detected by the parser. */
423 if (objc_implementation_context)
424 {
425 warning (0, "%<@end%> missing in implementation context");
426 finish_class (objc_implementation_context);
427 objc_ivar_chain = NULL_TREE;
428 objc_implementation_context = NULL_TREE;
429 }
430
431 if (warn_selector)
432 {
433 objc_map_iterator_t i;
434
435 objc_map_iterator_initialize (class_method_map, &i);
436 while (objc_map_iterator_move_to_next (class_method_map, &i))
437 check_duplicates (objc_map_iterator_current_value (class_method_map, i), 0, 1);
438
439 objc_map_iterator_initialize (instance_method_map, &i);
440 while (objc_map_iterator_move_to_next (instance_method_map, &i))
441 check_duplicates (objc_map_iterator_current_value (instance_method_map, i), 0, 0);
442 }
443
444 /* TODO: consider an early exit here if either errorcount or sorrycount
445 is non-zero. Not only is it wasting time to generate the metadata,
446 it needlessly imposes need to re-check for things that are already
447 determined to be errors. */
448
449 /* Finalize Objective-C runtime data. No need to generate tables
450 and code if only checking syntax, or if generating a PCH file. */
451 if (!flag_syntax_only && !pch_file)
452 {
453 location_t saved_location;
454
455 /* If gen_declaration desired, open the output file. */
456 if (flag_gen_declaration)
457 {
458 char * const dumpname = concat (dump_base_name, ".decl", NULL);
459 gen_declaration_file = fopen (dumpname, "w");
460 if (gen_declaration_file == 0)
461 fatal_error (input_location, "cannot open %s: %m", dumpname);
462 free (dumpname);
463 }
464
465 /* Set the input location to BUILTINS_LOCATION. This is good
466 for error messages, in case any is generated while producing
467 the metadata, but it also silences warnings that would be
468 produced when compiling with -Wpadded in case when padding is
469 automatically added to the built-in runtime data structure
470 declarations. We know about this padding, and it is fine; we
471 don't want users to see any warnings about it if they use
472 -Wpadded. */
473 saved_location = input_location;
474 input_location = BUILTINS_LOCATION;
475
476 /* Compute and emit the meta-data tables for this runtime. */
477 (*runtime.generate_metadata) ();
478
479 /* Restore the original location, just in case it mattered. */
480 input_location = saved_location;
481
482 /* ... and then close any declaration file we opened. */
483 if (gen_declaration_file)
484 fclose (gen_declaration_file);
485 }
486 }
487
488 /* Return the first occurrence of a method declaration corresponding
489 to sel_name in rproto_list. Search rproto_list recursively.
490 If is_class is 0, search for instance methods, otherwise for class
491 methods. */
492 static tree
lookup_method_in_protocol_list(tree rproto_list,tree sel_name,int is_class)493 lookup_method_in_protocol_list (tree rproto_list, tree sel_name,
494 int is_class)
495 {
496 tree rproto, p, m;
497
498 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
499 {
500 p = TREE_VALUE (rproto);
501 m = NULL_TREE;
502
503 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
504 {
505 /* First, search the @required protocol methods. */
506 if (is_class)
507 m = lookup_method (PROTOCOL_CLS_METHODS (p), sel_name);
508 else
509 m = lookup_method (PROTOCOL_NST_METHODS (p), sel_name);
510
511 if (m)
512 return m;
513
514 /* If still not found, search the @optional protocol methods. */
515 if (is_class)
516 m = lookup_method (PROTOCOL_OPTIONAL_CLS_METHODS (p), sel_name);
517 else
518 m = lookup_method (PROTOCOL_OPTIONAL_NST_METHODS (p), sel_name);
519
520 if (m)
521 return m;
522
523 /* If still not found, search the attached protocols. */
524 if (PROTOCOL_LIST (p))
525 m = lookup_method_in_protocol_list (PROTOCOL_LIST (p),
526 sel_name, is_class);
527 if (m)
528 return m;
529 }
530 else
531 {
532 ; /* An identifier...if we could not find a protocol. */
533 }
534 }
535
536 return 0;
537 }
538
539 static tree
lookup_protocol_in_reflist(tree rproto_list,tree lproto)540 lookup_protocol_in_reflist (tree rproto_list, tree lproto)
541 {
542 tree rproto, p;
543
544 /* Make sure the protocol is supported by the object on the rhs. */
545 if (TREE_CODE (lproto) == PROTOCOL_INTERFACE_TYPE)
546 {
547 tree fnd = 0;
548 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
549 {
550 p = TREE_VALUE (rproto);
551
552 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
553 {
554 if (lproto == p)
555 fnd = lproto;
556
557 else if (PROTOCOL_LIST (p))
558 fnd = lookup_protocol_in_reflist (PROTOCOL_LIST (p), lproto);
559 }
560
561 if (fnd)
562 return fnd;
563 }
564 }
565 else
566 {
567 ; /* An identifier...if we could not find a protocol. */
568 }
569
570 return 0;
571 }
572
573 void
objc_start_class_interface(tree klass,tree super_class,tree protos,tree attributes)574 objc_start_class_interface (tree klass, tree super_class,
575 tree protos, tree attributes)
576 {
577 if (flag_objc1_only && attributes)
578 error_at (input_location, "class attributes are not available in Objective-C 1.0");
579
580 objc_interface_context
581 = objc_ivar_context
582 = start_class (CLASS_INTERFACE_TYPE, klass, super_class, protos, attributes);
583 objc_ivar_visibility = objc_default_ivar_visibility;
584 }
585
586 void
objc_start_category_interface(tree klass,tree categ,tree protos,tree attributes)587 objc_start_category_interface (tree klass, tree categ,
588 tree protos, tree attributes)
589 {
590 if (attributes)
591 {
592 if (flag_objc1_only)
593 error_at (input_location, "category attributes are not available in Objective-C 1.0");
594 else
595 warning_at (input_location, OPT_Wattributes,
596 "category attributes are not available in this version"
597 " of the compiler, (ignored)");
598 }
599 if (categ == NULL_TREE)
600 {
601 if (flag_objc1_only)
602 error_at (input_location, "class extensions are not available in Objective-C 1.0");
603 else
604 {
605 /* Iterate over all the classes and categories implemented
606 up to now in this compilation unit. */
607 struct imp_entry *t;
608
609 for (t = imp_list; t; t = t->next)
610 {
611 /* If we find a class @implementation with the same name
612 as the one we are extending, produce an error. */
613 if (TREE_CODE (t->imp_context) == CLASS_IMPLEMENTATION_TYPE
614 && IDENTIFIER_POINTER (CLASS_NAME (t->imp_context)) == IDENTIFIER_POINTER (klass))
615 error_at (input_location,
616 "class extension for class %qE declared after its %<@implementation%>",
617 klass);
618 }
619 }
620 }
621 objc_interface_context
622 = start_class (CATEGORY_INTERFACE_TYPE, klass, categ, protos, NULL_TREE);
623 objc_ivar_chain
624 = continue_class (objc_interface_context);
625 }
626
627 void
objc_start_protocol(tree name,tree protos,tree attributes)628 objc_start_protocol (tree name, tree protos, tree attributes)
629 {
630 if (flag_objc1_only && attributes)
631 error_at (input_location, "protocol attributes are not available in Objective-C 1.0");
632
633 objc_interface_context
634 = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos, attributes);
635 objc_method_optional_flag = false;
636 }
637
638 void
objc_continue_interface(void)639 objc_continue_interface (void)
640 {
641 objc_ivar_chain
642 = continue_class (objc_interface_context);
643 }
644
645 void
objc_finish_interface(void)646 objc_finish_interface (void)
647 {
648 finish_class (objc_interface_context);
649 objc_interface_context = NULL_TREE;
650 objc_method_optional_flag = false;
651 objc_in_class_extension = false;
652 }
653
654 void
objc_start_class_implementation(tree klass,tree super_class)655 objc_start_class_implementation (tree klass, tree super_class)
656 {
657 objc_implementation_context
658 = objc_ivar_context
659 = start_class (CLASS_IMPLEMENTATION_TYPE, klass, super_class, NULL_TREE,
660 NULL_TREE);
661 objc_ivar_visibility = objc_default_ivar_visibility;
662 }
663
664 void
objc_start_category_implementation(tree klass,tree categ)665 objc_start_category_implementation (tree klass, tree categ)
666 {
667 objc_implementation_context
668 = start_class (CATEGORY_IMPLEMENTATION_TYPE, klass, categ, NULL_TREE,
669 NULL_TREE);
670 objc_ivar_chain
671 = continue_class (objc_implementation_context);
672 }
673
674 void
objc_continue_implementation(void)675 objc_continue_implementation (void)
676 {
677 objc_ivar_chain
678 = continue_class (objc_implementation_context);
679 }
680
681 void
objc_finish_implementation(void)682 objc_finish_implementation (void)
683 {
684 #ifdef OBJCPLUS
685 if (flag_objc_call_cxx_cdtors)
686 objc_generate_cxx_cdtors ();
687 #endif
688
689 if (objc_implementation_context)
690 {
691 finish_class (objc_implementation_context);
692 objc_ivar_chain = NULL_TREE;
693 objc_implementation_context = NULL_TREE;
694 }
695 else
696 warning (0, "%<@end%> must appear in an @implementation context");
697 }
698
699 void
objc_set_visibility(objc_ivar_visibility_kind visibility)700 objc_set_visibility (objc_ivar_visibility_kind visibility)
701 {
702 if (visibility == OBJC_IVAR_VIS_PACKAGE)
703 {
704 if (flag_objc1_only)
705 error ("%<@package%> is not available in Objective-C 1.0");
706 else
707 warning (0, "%<@package%> presently has the same effect as %<@public%>");
708 }
709 objc_ivar_visibility = visibility;
710 }
711
712 void
objc_set_method_opt(bool optional)713 objc_set_method_opt (bool optional)
714 {
715 if (flag_objc1_only)
716 {
717 if (optional)
718 error_at (input_location, "%<@optional%> is not available in Objective-C 1.0");
719 else
720 error_at (input_location, "%<@required%> is not available in Objective-C 1.0");
721 }
722
723 objc_method_optional_flag = optional;
724 if (!objc_interface_context
725 || TREE_CODE (objc_interface_context) != PROTOCOL_INTERFACE_TYPE)
726 {
727 if (optional)
728 error ("%<@optional%> is allowed in @protocol context only");
729 else
730 error ("%<@required%> is allowed in @protocol context only");
731 objc_method_optional_flag = false;
732 }
733 }
734
735 /* This routine looks for a given PROPERTY in a list of CLASS, CATEGORY, or
736 PROTOCOL. */
737 static tree
lookup_property_in_list(tree chain,tree property)738 lookup_property_in_list (tree chain, tree property)
739 {
740 tree x;
741 for (x = CLASS_PROPERTY_DECL (chain); x; x = TREE_CHAIN (x))
742 if (PROPERTY_NAME (x) == property)
743 return x;
744 return NULL_TREE;
745 }
746
747 /* This routine looks for a given PROPERTY in the tree chain of RPROTO_LIST. */
lookup_property_in_protocol_list(tree rproto_list,tree property)748 static tree lookup_property_in_protocol_list (tree rproto_list, tree property)
749 {
750 tree rproto, x;
751 for (rproto = rproto_list; rproto; rproto = TREE_CHAIN (rproto))
752 {
753 tree p = TREE_VALUE (rproto);
754 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
755 {
756 if ((x = lookup_property_in_list (p, property)))
757 return x;
758 if (PROTOCOL_LIST (p))
759 return lookup_property_in_protocol_list (PROTOCOL_LIST (p), property);
760 }
761 else
762 {
763 ; /* An identifier...if we could not find a protocol. */
764 }
765 }
766 return NULL_TREE;
767 }
768
769 /* This routine looks up the PROPERTY in current INTERFACE, its categories and up the
770 chain of interface hierarchy. */
771 static tree
lookup_property(tree interface_type,tree property)772 lookup_property (tree interface_type, tree property)
773 {
774 tree inter = interface_type;
775 while (inter)
776 {
777 tree x, category;
778 if ((x = lookup_property_in_list (inter, property)))
779 return x;
780 /* Failing that, look for the property in each category of the class. */
781 category = inter;
782 while ((category = CLASS_CATEGORY_LIST (category)))
783 {
784 if ((x = lookup_property_in_list (category, property)))
785 return x;
786
787 /* When checking a category, also check the protocols
788 attached with the category itself. */
789 if (CLASS_PROTOCOL_LIST (category)
790 && (x = lookup_property_in_protocol_list
791 (CLASS_PROTOCOL_LIST (category), property)))
792 return x;
793 }
794
795 /* Failing to find in categories, look for property in protocol list. */
796 if (CLASS_PROTOCOL_LIST (inter)
797 && (x = lookup_property_in_protocol_list
798 (CLASS_PROTOCOL_LIST (inter), property)))
799 return x;
800
801 /* Failing that, climb up the inheritance hierarchy. */
802 inter = lookup_interface (CLASS_SUPER_NAME (inter));
803 }
804 return inter;
805 }
806
807 /* This routine is called by the parser when a
808 @property... declaration is found. 'decl' is the declaration of
809 the property (type/identifier), and the other arguments represent
810 property attributes that may have been specified in the Objective-C
811 declaration. 'parsed_property_readonly' is 'true' if the attribute
812 'readonly' was specified, and 'false' if not; similarly for the
813 other bool parameters. 'parsed_property_getter_ident' is NULL_TREE
814 if the attribute 'getter' was not specified, and is the identifier
815 corresponding to the specified getter if it was; similarly for
816 'parsed_property_setter_ident'. */
817 void
objc_add_property_declaration(location_t location,tree decl,bool parsed_property_readonly,bool parsed_property_readwrite,bool parsed_property_assign,bool parsed_property_retain,bool parsed_property_copy,bool parsed_property_nonatomic,tree parsed_property_getter_ident,tree parsed_property_setter_ident)818 objc_add_property_declaration (location_t location, tree decl,
819 bool parsed_property_readonly, bool parsed_property_readwrite,
820 bool parsed_property_assign, bool parsed_property_retain,
821 bool parsed_property_copy, bool parsed_property_nonatomic,
822 tree parsed_property_getter_ident, tree parsed_property_setter_ident)
823 {
824 tree property_decl;
825 tree x;
826 /* 'property_readonly' and 'property_assign_semantics' are the final
827 attributes of the property after all parsed attributes have been
828 considered (eg, if we parsed no 'readonly' and no 'readwrite', ie
829 parsed_property_readonly = false and parsed_property_readwrite =
830 false, then property_readonly will be false because the default
831 is readwrite). */
832 bool property_readonly = false;
833 objc_property_assign_semantics property_assign_semantics = OBJC_PROPERTY_ASSIGN;
834 bool property_extension_in_class_extension = false;
835
836 if (flag_objc1_only)
837 error_at (input_location, "%<@property%> is not available in Objective-C 1.0");
838
839 if (parsed_property_readonly && parsed_property_readwrite)
840 {
841 error_at (location, "%<readonly%> attribute conflicts with %<readwrite%> attribute");
842 /* In case of conflicting attributes (here and below), after
843 producing an error, we pick one of the attributes and keep
844 going. */
845 property_readonly = false;
846 }
847 else
848 {
849 if (parsed_property_readonly)
850 property_readonly = true;
851
852 if (parsed_property_readwrite)
853 property_readonly = false;
854 }
855
856 if (parsed_property_readonly && parsed_property_setter_ident)
857 {
858 error_at (location, "%<readonly%> attribute conflicts with %<setter%> attribute");
859 property_readonly = false;
860 }
861
862 if (parsed_property_assign && parsed_property_retain)
863 {
864 error_at (location, "%<assign%> attribute conflicts with %<retain%> attribute");
865 property_assign_semantics = OBJC_PROPERTY_RETAIN;
866 }
867 else if (parsed_property_assign && parsed_property_copy)
868 {
869 error_at (location, "%<assign%> attribute conflicts with %<copy%> attribute");
870 property_assign_semantics = OBJC_PROPERTY_COPY;
871 }
872 else if (parsed_property_retain && parsed_property_copy)
873 {
874 error_at (location, "%<retain%> attribute conflicts with %<copy%> attribute");
875 property_assign_semantics = OBJC_PROPERTY_COPY;
876 }
877 else
878 {
879 if (parsed_property_assign)
880 property_assign_semantics = OBJC_PROPERTY_ASSIGN;
881
882 if (parsed_property_retain)
883 property_assign_semantics = OBJC_PROPERTY_RETAIN;
884
885 if (parsed_property_copy)
886 property_assign_semantics = OBJC_PROPERTY_COPY;
887 }
888
889 if (!objc_interface_context)
890 {
891 error_at (location, "property declaration not in @interface or @protocol context");
892 return;
893 }
894
895 /* At this point we know that we are either in an interface, a
896 category, or a protocol. */
897
898 /* We expect a FIELD_DECL from the parser. Make sure we didn't get
899 something else, as that would confuse the checks below. */
900 if (TREE_CODE (decl) != FIELD_DECL)
901 {
902 error_at (location, "invalid property declaration");
903 return;
904 }
905
906 /* Do some spot-checks for the most obvious invalid types. */
907
908 if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
909 {
910 error_at (location, "property cannot be an array");
911 return;
912 }
913
914 /* The C++/ObjC++ parser seems to reject the ':' for a bitfield when
915 parsing, while the C/ObjC parser accepts it and gives us a
916 FIELD_DECL with a DECL_INITIAL set. So we use the DECL_INITIAL
917 to check for a bitfield when doing ObjC. */
918 #ifndef OBJCPLUS
919 if (DECL_INITIAL (decl))
920 {
921 /* A @property is not an actual variable, but it is a way to
922 describe a pair of accessor methods, so its type (which is
923 the type of the return value of the getter and the first
924 argument of the setter) can't be a bitfield (as return values
925 and arguments of functions cannot be bitfields). The
926 underlying instance variable could be a bitfield, but that is
927 a different matter. */
928 error_at (location, "property cannot be a bit-field");
929 return;
930 }
931 #endif
932
933 /* TODO: Check that the property type is an Objective-C object or a
934 "POD". */
935
936 /* Implement -Wproperty-assign-default (which is enabled by default). */
937 if (warn_property_assign_default
938 /* If garbage collection is not being used, then 'assign' is
939 valid for objects (and typically used for delegates) but it
940 is wrong in most cases (since most objects need to be
941 retained or copied in setters). Warn users when 'assign' is
942 used implicitly. */
943 && property_assign_semantics == OBJC_PROPERTY_ASSIGN
944 /* Read-only properties are never assigned, so the assignment
945 semantics do not matter in that case. */
946 && !property_readonly
947 && !flag_objc_gc)
948 {
949 /* Please note that it would make sense to default to 'assign'
950 for non-{Objective-C objects}, and to 'retain' for
951 Objective-C objects. But that would break compatibility with
952 other compilers. */
953 if (!parsed_property_assign && !parsed_property_retain && !parsed_property_copy)
954 {
955 /* Use 'false' so we do not warn for Class objects. */
956 if (objc_type_valid_for_messaging (TREE_TYPE (decl), false))
957 {
958 warning_at (location,
959 0,
960 "object property %qD has no %<assign%>, %<retain%> or %<copy%> attribute; assuming %<assign%>",
961 decl);
962 inform (location,
963 "%<assign%> can be unsafe for Objective-C objects; please state explicitly if you need it");
964 }
965 }
966 }
967
968 if (property_assign_semantics == OBJC_PROPERTY_RETAIN
969 && !objc_type_valid_for_messaging (TREE_TYPE (decl), true))
970 error_at (location, "%<retain%> attribute is only valid for Objective-C objects");
971
972 if (property_assign_semantics == OBJC_PROPERTY_COPY
973 && !objc_type_valid_for_messaging (TREE_TYPE (decl), true))
974 error_at (location, "%<copy%> attribute is only valid for Objective-C objects");
975
976 /* Now determine the final property getter and setter names. They
977 will be stored in the PROPERTY_DECL, from which they'll always be
978 extracted and used. */
979
980 /* Adjust, or fill in, setter and getter names. We overwrite the
981 parsed_property_setter_ident and parsed_property_getter_ident
982 with the final setter and getter identifiers that will be
983 used. */
984 if (parsed_property_setter_ident)
985 {
986 /* The setter should be terminated by ':', but the parser only
987 gives us an identifier without ':'. So, we need to add ':'
988 at the end. */
989 const char *parsed_setter = IDENTIFIER_POINTER (parsed_property_setter_ident);
990 size_t length = strlen (parsed_setter);
991 char *final_setter = (char *)alloca (length + 2);
992
993 sprintf (final_setter, "%s:", parsed_setter);
994 parsed_property_setter_ident = get_identifier (final_setter);
995 }
996 else
997 {
998 if (!property_readonly)
999 parsed_property_setter_ident = get_identifier (objc_build_property_setter_name
1000 (DECL_NAME (decl)));
1001 }
1002
1003 if (!parsed_property_getter_ident)
1004 parsed_property_getter_ident = DECL_NAME (decl);
1005
1006 /* Check for duplicate property declarations. We first check the
1007 immediate context for a property with the same name. Any such
1008 declarations are an error, unless this is a class extension and
1009 we are extending a property from readonly to readwrite. */
1010 for (x = CLASS_PROPERTY_DECL (objc_interface_context); x; x = TREE_CHAIN (x))
1011 {
1012 if (PROPERTY_NAME (x) == DECL_NAME (decl))
1013 {
1014 if (objc_in_class_extension
1015 && property_readonly == 0
1016 && PROPERTY_READONLY (x) == 1)
1017 {
1018 /* This is a class extension, and we are extending an
1019 existing readonly property to a readwrite one.
1020 That's fine. :-) */
1021 property_extension_in_class_extension = true;
1022 break;
1023 }
1024 else
1025 {
1026 location_t original_location = DECL_SOURCE_LOCATION (x);
1027
1028 error_at (location, "redeclaration of property %qD", decl);
1029
1030 if (original_location != UNKNOWN_LOCATION)
1031 inform (original_location, "originally specified here");
1032 return;
1033 }
1034 }
1035 }
1036
1037 /* If x is not NULL_TREE, we must be in a class extension and we're
1038 extending a readonly property. In that case, no point in
1039 searching for another declaration. */
1040 if (x == NULL_TREE)
1041 {
1042 /* We now need to check for existing property declarations (in
1043 the superclass, other categories or protocols) and check that
1044 the new declaration is not in conflict with existing
1045 ones. */
1046
1047 /* Search for a previous, existing declaration of a property
1048 with the same name in superclasses, protocols etc. If one is
1049 found, it will be in the 'x' variable. */
1050
1051 /* Note that, for simplicity, the following may search again the
1052 local context. That's Ok as nothing will be found (else we'd
1053 have thrown an error above); it's only a little inefficient,
1054 but the code is simpler. */
1055 switch (TREE_CODE (objc_interface_context))
1056 {
1057 case CLASS_INTERFACE_TYPE:
1058 /* Look up the property in the current @interface (which
1059 will find nothing), then its protocols and categories and
1060 superclasses. */
1061 x = lookup_property (objc_interface_context, DECL_NAME (decl));
1062 break;
1063 case CATEGORY_INTERFACE_TYPE:
1064 /* Look up the property in the main @interface, then
1065 protocols and categories (one of them is ours, and will
1066 find nothing) and superclasses. */
1067 x = lookup_property (lookup_interface (CLASS_NAME (objc_interface_context)),
1068 DECL_NAME (decl));
1069 break;
1070 case PROTOCOL_INTERFACE_TYPE:
1071 /* Looks up the property in any protocols attached to the
1072 current protocol. */
1073 if (PROTOCOL_LIST (objc_interface_context))
1074 {
1075 x = lookup_property_in_protocol_list (PROTOCOL_LIST (objc_interface_context),
1076 DECL_NAME (decl));
1077 }
1078 break;
1079 default:
1080 gcc_unreachable ();
1081 }
1082 }
1083
1084 if (x != NULL_TREE)
1085 {
1086 /* An existing property was found; check that it has the same
1087 types, or it is compatible. */
1088 location_t original_location = DECL_SOURCE_LOCATION (x);
1089
1090 if (PROPERTY_NONATOMIC (x) != parsed_property_nonatomic)
1091 {
1092 warning_at (location, 0,
1093 "%<nonatomic%> attribute of property %qD conflicts with "
1094 "previous declaration", decl);
1095
1096 if (original_location != UNKNOWN_LOCATION)
1097 inform (original_location, "originally specified here");
1098 return;
1099 }
1100
1101 if (PROPERTY_GETTER_NAME (x) != parsed_property_getter_ident)
1102 {
1103 warning_at (location, 0,
1104 "%<getter%> attribute of property %qD conflicts with "
1105 "previous declaration", decl);
1106
1107 if (original_location != UNKNOWN_LOCATION)
1108 inform (original_location, "originally specified here");
1109 return;
1110 }
1111
1112 /* We can only compare the setter names if both the old and new property have a setter. */
1113 if (!property_readonly && !PROPERTY_READONLY(x))
1114 {
1115 if (PROPERTY_SETTER_NAME (x) != parsed_property_setter_ident)
1116 {
1117 warning_at (location, 0,
1118 "%<setter%> attribute of property %qD conflicts with "
1119 "previous declaration", decl);
1120
1121 if (original_location != UNKNOWN_LOCATION)
1122 inform (original_location, "originally specified here");
1123 return;
1124 }
1125 }
1126
1127 if (PROPERTY_ASSIGN_SEMANTICS (x) != property_assign_semantics)
1128 {
1129 warning_at (location, 0,
1130 "assign semantics attributes of property %qD conflict with previous declaration", decl);
1131
1132 if (original_location != UNKNOWN_LOCATION)
1133 inform (original_location, "originally specified here");
1134 return;
1135 }
1136
1137 /* It's ok to have a readonly property that becomes a readwrite, but not vice versa. */
1138 if (PROPERTY_READONLY (x) == 0 && property_readonly == 1)
1139 {
1140 warning_at (location, 0,
1141 "%<readonly%> attribute of property %qD conflicts with "
1142 "previous declaration", decl);
1143
1144 if (original_location != UNKNOWN_LOCATION)
1145 inform (original_location, "originally specified here");
1146 return;
1147 }
1148
1149 /* We now check that the new and old property declarations have
1150 the same types (or compatible one). In the Objective-C
1151 tradition of loose type checking, we do type-checking but
1152 only generate warnings (not errors) if they do not match.
1153 For non-readonly properties, the types must match exactly;
1154 for readonly properties, it is allowed to use a "more
1155 specialized" type in the new property declaration. Eg, the
1156 superclass has a getter returning (NSArray *) and the
1157 subclass a getter returning (NSMutableArray *). The object's
1158 getter returns an (NSMutableArray *); but if you cast the
1159 object to the superclass, which is allowed, you'd still
1160 expect the getter to return an (NSArray *), which works since
1161 an (NSMutableArray *) is an (NSArray *) too. So, the set of
1162 objects belonging to the type of the new @property should be
1163 a subset of the set of objects belonging to the type of the
1164 old @property. This is what "specialization" means. And the
1165 reason it only applies to readonly properties is that for a
1166 readwrite property the setter would have the opposite
1167 requirement - ie that the superclass type is more specialized
1168 then the subclass one; hence the only way to satisfy both
1169 constraints is that the types match. */
1170
1171 /* If the types are not the same in the C sense, we warn ... */
1172 if (!comptypes (TREE_TYPE (x), TREE_TYPE (decl))
1173 /* ... unless the property is readonly, in which case we
1174 allow a new, more specialized, declaration. */
1175 && (!property_readonly
1176 || !objc_compare_types (TREE_TYPE (x),
1177 TREE_TYPE (decl), -5, NULL_TREE)))
1178 {
1179 warning_at (location, 0,
1180 "type of property %qD conflicts with previous declaration", decl);
1181 if (original_location != UNKNOWN_LOCATION)
1182 inform (original_location, "originally specified here");
1183 return;
1184 }
1185
1186 /* If we are in a class extension and we're extending a readonly
1187 property in the main @interface, we'll just update the
1188 existing property with the readwrite flag and potentially the
1189 new setter name. */
1190 if (property_extension_in_class_extension)
1191 {
1192 PROPERTY_READONLY (x) = 0;
1193 PROPERTY_SETTER_NAME (x) = parsed_property_setter_ident;
1194 return;
1195 }
1196 }
1197
1198 /* Create a PROPERTY_DECL node. */
1199 property_decl = make_node (PROPERTY_DECL);
1200
1201 /* Copy the basic information from the original decl. */
1202 TREE_TYPE (property_decl) = TREE_TYPE (decl);
1203 DECL_SOURCE_LOCATION (property_decl) = DECL_SOURCE_LOCATION (decl);
1204 TREE_DEPRECATED (property_decl) = TREE_DEPRECATED (decl);
1205
1206 /* Add property-specific information. */
1207 PROPERTY_NAME (property_decl) = DECL_NAME (decl);
1208 PROPERTY_GETTER_NAME (property_decl) = parsed_property_getter_ident;
1209 PROPERTY_SETTER_NAME (property_decl) = parsed_property_setter_ident;
1210 PROPERTY_READONLY (property_decl) = property_readonly;
1211 PROPERTY_NONATOMIC (property_decl) = parsed_property_nonatomic;
1212 PROPERTY_ASSIGN_SEMANTICS (property_decl) = property_assign_semantics;
1213 PROPERTY_IVAR_NAME (property_decl) = NULL_TREE;
1214 PROPERTY_DYNAMIC (property_decl) = 0;
1215
1216 /* Remember the fact that the property was found in the @optional
1217 section in a @protocol, or not. */
1218 if (objc_method_optional_flag)
1219 PROPERTY_OPTIONAL (property_decl) = 1;
1220 else
1221 PROPERTY_OPTIONAL (property_decl) = 0;
1222
1223 /* Note that PROPERTY_GETTER_NAME is always set for all
1224 PROPERTY_DECLs, and PROPERTY_SETTER_NAME is always set for all
1225 PROPERTY_DECLs where PROPERTY_READONLY == 0. Any time we deal
1226 with a getter or setter, we should get the PROPERTY_DECL and use
1227 PROPERTY_GETTER_NAME and PROPERTY_SETTER_NAME to know the correct
1228 names. */
1229
1230 /* Add the PROPERTY_DECL to the list of properties for the class. */
1231 TREE_CHAIN (property_decl) = CLASS_PROPERTY_DECL (objc_interface_context);
1232 CLASS_PROPERTY_DECL (objc_interface_context) = property_decl;
1233 }
1234
1235 /* This is a subroutine of objc_maybe_build_component_ref. Search the
1236 list of methods in the interface (and, failing that, the local list
1237 in the implementation, and failing that, the protocol list)
1238 provided for a 'setter' or 'getter' for 'component' with default
1239 names (ie, if 'component' is "name", then search for "name" and
1240 "setName:"). It is also possible to specify a different
1241 'getter_name' (this is used for @optional readonly properties). If
1242 any is found, then create an artificial property that uses them.
1243 Return NULL_TREE if 'getter' or 'setter' could not be found. */
1244 static tree
maybe_make_artificial_property_decl(tree interface,tree implementation,tree protocol_list,tree component,bool is_class,tree getter_name)1245 maybe_make_artificial_property_decl (tree interface, tree implementation,
1246 tree protocol_list, tree component, bool is_class,
1247 tree getter_name)
1248 {
1249 tree setter_name = get_identifier (objc_build_property_setter_name (component));
1250 tree getter = NULL_TREE;
1251 tree setter = NULL_TREE;
1252
1253 if (getter_name == NULL_TREE)
1254 getter_name = component;
1255
1256 /* First, check the @interface and all superclasses. */
1257 if (interface)
1258 {
1259 int flags = 0;
1260
1261 /* Using instance methods of the root class as accessors is most
1262 likely unwanted and can be extremely confusing (and, most
1263 importantly, other Objective-C 2.0 compilers do not do it).
1264 Turn it off. */
1265 if (is_class)
1266 flags = OBJC_LOOKUP_CLASS | OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS;
1267
1268 getter = lookup_method_static (interface, getter_name, flags);
1269 setter = lookup_method_static (interface, setter_name, flags);
1270 }
1271
1272 /* Second, check the local @implementation context. */
1273 if (!getter && !setter)
1274 {
1275 if (implementation)
1276 {
1277 if (is_class)
1278 {
1279 getter = lookup_method (CLASS_CLS_METHODS (implementation), getter_name);
1280 setter = lookup_method (CLASS_CLS_METHODS (implementation), setter_name);
1281 }
1282 else
1283 {
1284 getter = lookup_method (CLASS_NST_METHODS (implementation), getter_name);
1285 setter = lookup_method (CLASS_NST_METHODS (implementation), setter_name);
1286 }
1287 }
1288 }
1289
1290 /* Try the protocol_list if we didn't find anything in the
1291 @interface and in the @implementation. */
1292 if (!getter && !setter)
1293 {
1294 getter = lookup_method_in_protocol_list (protocol_list, getter_name, is_class);
1295 setter = lookup_method_in_protocol_list (protocol_list, setter_name, is_class);
1296 }
1297
1298 /* There needs to be at least a getter or setter for this to be a
1299 valid 'object.component' syntax. */
1300 if (getter || setter)
1301 {
1302 /* Yes ... determine the type of the expression. */
1303 tree property_decl;
1304 tree type;
1305
1306 if (getter)
1307 type = TREE_VALUE (TREE_TYPE (getter));
1308 else
1309 type = TREE_VALUE (TREE_TYPE (METHOD_SEL_ARGS (setter)));
1310
1311 /* Create an artificial property declaration with the
1312 information we collected on the type and getter/setter
1313 names. */
1314 property_decl = make_node (PROPERTY_DECL);
1315
1316 TREE_TYPE (property_decl) = type;
1317 DECL_SOURCE_LOCATION (property_decl) = input_location;
1318 TREE_DEPRECATED (property_decl) = 0;
1319 DECL_ARTIFICIAL (property_decl) = 1;
1320
1321 /* Add property-specific information. Note that one of
1322 PROPERTY_GETTER_NAME or PROPERTY_SETTER_NAME may refer to a
1323 non-existing method; this will generate an error when the
1324 expression is later compiled. At this stage we don't know if
1325 the getter or setter will be used, so we can't generate an
1326 error. */
1327 PROPERTY_NAME (property_decl) = component;
1328 PROPERTY_GETTER_NAME (property_decl) = getter_name;
1329 PROPERTY_SETTER_NAME (property_decl) = setter_name;
1330 PROPERTY_READONLY (property_decl) = 0;
1331 PROPERTY_NONATOMIC (property_decl) = 0;
1332 PROPERTY_ASSIGN_SEMANTICS (property_decl) = 0;
1333 PROPERTY_IVAR_NAME (property_decl) = NULL_TREE;
1334 PROPERTY_DYNAMIC (property_decl) = 0;
1335 PROPERTY_OPTIONAL (property_decl) = 0;
1336
1337 if (!getter)
1338 PROPERTY_HAS_NO_GETTER (property_decl) = 1;
1339
1340 /* The following is currently unused, but it's nice to have
1341 there. We may use it if we need in the future. */
1342 if (!setter)
1343 PROPERTY_HAS_NO_SETTER (property_decl) = 1;
1344
1345 return property_decl;
1346 }
1347
1348 return NULL_TREE;
1349 }
1350
1351 /* This hook routine is invoked by the parser when an expression such
1352 as 'xxx.yyy' is parsed. We get a chance to process these
1353 expressions in a way that is specified to Objective-C (to implement
1354 the Objective-C 2.0 dot-syntax, properties, or non-fragile ivars).
1355 If the expression is not an Objective-C specified expression, we
1356 should return NULL_TREE; else we return the expression.
1357
1358 At the moment this only implements dot-syntax and properties (not
1359 non-fragile ivars yet), ie 'object.property' or 'object.component'
1360 where 'component' is not a declared property, but a valid getter or
1361 setter for it could be found. */
1362 tree
objc_maybe_build_component_ref(tree object,tree property_ident)1363 objc_maybe_build_component_ref (tree object, tree property_ident)
1364 {
1365 tree x = NULL_TREE;
1366 tree rtype;
1367
1368 /* If we are in Objective-C 1.0 mode, dot-syntax and properties are
1369 not available. */
1370 if (flag_objc1_only)
1371 return NULL_TREE;
1372
1373 /* Try to determine if 'object' is an Objective-C object or not. If
1374 not, return. */
1375 if (object == NULL_TREE || object == error_mark_node
1376 || (rtype = TREE_TYPE (object)) == NULL_TREE)
1377 return NULL_TREE;
1378
1379 if (property_ident == NULL_TREE || property_ident == error_mark_node
1380 || TREE_CODE (property_ident) != IDENTIFIER_NODE)
1381 return NULL_TREE;
1382
1383 /* The following analysis of 'object' is similar to the one used for
1384 the 'receiver' of a method invocation. We need to determine what
1385 'object' is and find the appropriate property (either declared,
1386 or artificial) for it (in the same way as we need to find the
1387 appropriate method prototype for a method invocation). There are
1388 some simplifications here though: "object.property" is invalid if
1389 "object" has a type of "id" or "Class"; it must at least have a
1390 protocol attached to it, and "object" is never a class name as
1391 that is done by objc_build_class_component_ref. Finally, we
1392 don't know if this really is a dot-syntax expression, so we want
1393 to make a quick exit if it is not; for this reason, we try to
1394 postpone checks after determining that 'object' looks like an
1395 Objective-C object. */
1396
1397 if (objc_is_id (rtype))
1398 {
1399 /* This is the case that the 'object' is of type 'id' or
1400 'Class'. */
1401
1402 /* Check if at least it is of type 'id <Protocol>' or 'Class
1403 <Protocol>'; if so, look the property up in the
1404 protocols. */
1405 if (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype)))
1406 {
1407 tree rprotos = TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype));
1408
1409 if (rprotos)
1410 {
1411 /* No point looking up declared @properties if we are
1412 dealing with a class. Classes have no declared
1413 properties. */
1414 if (!IS_CLASS (rtype))
1415 x = lookup_property_in_protocol_list (rprotos, property_ident);
1416
1417 if (x == NULL_TREE)
1418 {
1419 /* Ok, no property. Maybe it was an
1420 object.component dot-syntax without a declared
1421 property (this is valid for classes too). Look
1422 for getter/setter methods and internally declare
1423 an artificial property based on them if found. */
1424 x = maybe_make_artificial_property_decl (NULL_TREE,
1425 NULL_TREE,
1426 rprotos,
1427 property_ident,
1428 IS_CLASS (rtype),
1429 NULL_TREE);
1430 }
1431 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1432 {
1433 /* This is a special, complicated case. If the
1434 property is optional, and is read-only, then the
1435 property is always used for reading, but an
1436 eventual existing non-property setter can be used
1437 for writing. We create an artificial property
1438 decl copying the getter from the optional
1439 property, and looking up the setter in the
1440 interface. */
1441 x = maybe_make_artificial_property_decl (NULL_TREE,
1442 NULL_TREE,
1443 rprotos,
1444 property_ident,
1445 false,
1446 PROPERTY_GETTER_NAME (x));
1447 }
1448 }
1449 }
1450 else if (objc_method_context)
1451 {
1452 /* Else, if we are inside a method it could be the case of
1453 'super' or 'self'. */
1454 tree interface_type = NULL_TREE;
1455 tree t = object;
1456 while (TREE_CODE (t) == COMPOUND_EXPR
1457 || TREE_CODE (t) == MODIFY_EXPR
1458 || CONVERT_EXPR_P (t)
1459 || TREE_CODE (t) == COMPONENT_REF)
1460 t = TREE_OPERAND (t, 0);
1461
1462 STRIP_ANY_LOCATION_WRAPPER (t);
1463
1464 if (t == UOBJC_SUPER_decl)
1465 interface_type = lookup_interface (CLASS_SUPER_NAME (implementation_template));
1466 else if (t == self_decl)
1467 interface_type = lookup_interface (CLASS_NAME (implementation_template));
1468
1469 if (interface_type)
1470 {
1471 if (TREE_CODE (objc_method_context) != CLASS_METHOD_DECL)
1472 x = lookup_property (interface_type, property_ident);
1473
1474 if (x == NULL_TREE)
1475 {
1476 /* Try the dot-syntax without a declared property.
1477 If this is an access to 'self', it is possible
1478 that they may refer to a setter/getter that is
1479 not declared in the interface, but exists locally
1480 in the implementation. In that case, get the
1481 implementation context and use it. */
1482 tree implementation = NULL_TREE;
1483
1484 if (t == self_decl)
1485 implementation = objc_implementation_context;
1486
1487 x = maybe_make_artificial_property_decl
1488 (interface_type, implementation, NULL_TREE,
1489 property_ident,
1490 (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL),
1491 NULL_TREE);
1492 }
1493 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1494 {
1495 tree implementation = NULL_TREE;
1496
1497 if (t == self_decl)
1498 implementation = objc_implementation_context;
1499
1500 x = maybe_make_artificial_property_decl (interface_type,
1501 implementation,
1502 NULL_TREE,
1503 property_ident,
1504 false,
1505 PROPERTY_GETTER_NAME (x));
1506 }
1507 }
1508 }
1509 }
1510 else
1511 {
1512 /* This is the case where we have more information on 'rtype'. */
1513 tree basetype = TYPE_MAIN_VARIANT (rtype);
1514
1515 /* Skip the pointer - if none, it's not an Objective-C object or
1516 class. */
1517 if (basetype != NULL_TREE && TREE_CODE (basetype) == POINTER_TYPE)
1518 basetype = TREE_TYPE (basetype);
1519 else
1520 return NULL_TREE;
1521
1522 /* Traverse typedefs. */
1523 while (basetype != NULL_TREE
1524 && TREE_CODE (basetype) == RECORD_TYPE
1525 && OBJC_TYPE_NAME (basetype)
1526 && TREE_CODE (OBJC_TYPE_NAME (basetype)) == TYPE_DECL
1527 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (basetype)))
1528 basetype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (basetype));
1529
1530 if (basetype != NULL_TREE && TYPED_OBJECT (basetype))
1531 {
1532 tree interface_type = TYPE_OBJC_INTERFACE (basetype);
1533 tree protocol_list = TYPE_OBJC_PROTOCOL_LIST (basetype);
1534
1535 if (interface_type
1536 && (TREE_CODE (interface_type) == CLASS_INTERFACE_TYPE
1537 || TREE_CODE (interface_type) == CATEGORY_INTERFACE_TYPE
1538 || TREE_CODE (interface_type) == PROTOCOL_INTERFACE_TYPE))
1539 {
1540 /* Not sure 'rtype' could ever be a class here! Just
1541 for safety we keep the checks. */
1542 if (!IS_CLASS (rtype))
1543 {
1544 x = lookup_property (interface_type, property_ident);
1545
1546 if (x == NULL_TREE)
1547 x = lookup_property_in_protocol_list (protocol_list,
1548 property_ident);
1549 }
1550
1551 if (x == NULL_TREE)
1552 {
1553 /* Try the dot-syntax without a declared property.
1554 If we are inside a method implementation, it is
1555 possible that they may refer to a setter/getter
1556 that is not declared in the interface, but exists
1557 locally in the implementation. In that case, get
1558 the implementation context and use it. */
1559 tree implementation = NULL_TREE;
1560
1561 if (objc_implementation_context
1562 && CLASS_NAME (objc_implementation_context)
1563 == OBJC_TYPE_NAME (interface_type))
1564 implementation = objc_implementation_context;
1565
1566 x = maybe_make_artificial_property_decl (interface_type,
1567 implementation,
1568 protocol_list,
1569 property_ident,
1570 IS_CLASS (rtype),
1571 NULL_TREE);
1572 }
1573 else if (PROPERTY_OPTIONAL (x) && PROPERTY_READONLY (x))
1574 {
1575 tree implementation = NULL_TREE;
1576
1577 if (objc_implementation_context
1578 && CLASS_NAME (objc_implementation_context)
1579 == OBJC_TYPE_NAME (interface_type))
1580 implementation = objc_implementation_context;
1581
1582 x = maybe_make_artificial_property_decl (interface_type,
1583 implementation,
1584 protocol_list,
1585 property_ident,
1586 false,
1587 PROPERTY_GETTER_NAME (x));
1588 }
1589 }
1590 }
1591 }
1592
1593 if (x)
1594 {
1595 tree expression;
1596 tree getter_call;
1597 tree deprecated_method_prototype = NULL_TREE;
1598
1599 /* We have an additional nasty problem here; if this
1600 PROPERTY_REF needs to become a 'getter', then the conversion
1601 from PROPERTY_REF into a getter call happens in gimplify,
1602 after the selector table has already been generated and when
1603 it is too late to add another selector to it. To work around
1604 the problem, we always create the getter call at this stage,
1605 which puts the selector in the table. Note that if the
1606 PROPERTY_REF becomes a 'setter' instead of a 'getter', then
1607 we have added a selector too many to the selector table.
1608 This is a little inefficient.
1609
1610 Also note that method calls to 'self' and 'super' require the
1611 context (self_decl, UOBJS_SUPER_decl,
1612 objc_implementation_context etc) to be built correctly; this
1613 is yet another reason why building the call at the gimplify
1614 stage (when this context has been lost) is not very
1615 practical. If we build it at this stage, we know it will
1616 always be built correctly.
1617
1618 If the PROPERTY_HAS_NO_GETTER() (ie, it is an artificial
1619 property decl created to deal with a dotsyntax not really
1620 referring to an existing property) then do not try to build a
1621 call to the getter as there is no getter. */
1622 if (PROPERTY_HAS_NO_GETTER (x))
1623 getter_call = NULL_TREE;
1624 else
1625 getter_call = objc_finish_message_expr
1626 (object, PROPERTY_GETTER_NAME (x), NULL_TREE,
1627 /* Disable the immediate deprecation warning if the getter
1628 is deprecated, but record the fact that the getter is
1629 deprecated by setting PROPERTY_REF_DEPRECATED_GETTER to
1630 the method prototype. */
1631 &deprecated_method_prototype);
1632
1633 expression = build4 (PROPERTY_REF, TREE_TYPE(x), object, x, getter_call,
1634 deprecated_method_prototype);
1635 SET_EXPR_LOCATION (expression, input_location);
1636 TREE_SIDE_EFFECTS (expression) = 1;
1637
1638 return expression;
1639 }
1640
1641 return NULL_TREE;
1642 }
1643
1644 /* This hook routine is invoked by the parser when an expression such
1645 as 'xxx.yyy' is parsed, and 'xxx' is a class name. This is the
1646 Objective-C 2.0 dot-syntax applied to classes, so we need to
1647 convert it into a setter/getter call on the class. */
1648 tree
objc_build_class_component_ref(tree class_name,tree property_ident)1649 objc_build_class_component_ref (tree class_name, tree property_ident)
1650 {
1651 tree x = NULL_TREE;
1652 tree object, rtype;
1653
1654 if (flag_objc1_only)
1655 error_at (input_location, "the dot syntax is not available in Objective-C 1.0");
1656
1657 if (class_name == NULL_TREE || class_name == error_mark_node
1658 || TREE_CODE (class_name) != IDENTIFIER_NODE)
1659 return error_mark_node;
1660
1661 if (property_ident == NULL_TREE || property_ident == error_mark_node
1662 || TREE_CODE (property_ident) != IDENTIFIER_NODE)
1663 return NULL_TREE;
1664
1665 object = objc_get_class_reference (class_name);
1666 if (!object)
1667 {
1668 /* We know that 'class_name' is an Objective-C class name as the
1669 parser won't call this function if it is not. This is only a
1670 double-check for safety. */
1671 error_at (input_location, "could not find class %qE", class_name);
1672 return error_mark_node;
1673 }
1674
1675 rtype = lookup_interface (class_name);
1676 if (!rtype)
1677 {
1678 /* Again, this should never happen, but we do check. */
1679 error_at (input_location, "could not find interface for class %qE", class_name);
1680 return error_mark_node;
1681 }
1682 else
1683 {
1684 if (TREE_DEPRECATED (rtype))
1685 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated", class_name);
1686 }
1687
1688 x = maybe_make_artificial_property_decl (rtype, NULL_TREE, NULL_TREE,
1689 property_ident,
1690 true, NULL_TREE);
1691
1692 if (x)
1693 {
1694 tree expression;
1695 tree getter_call;
1696 tree deprecated_method_prototype = NULL_TREE;
1697
1698 if (PROPERTY_HAS_NO_GETTER (x))
1699 getter_call = NULL_TREE;
1700 else
1701 getter_call = objc_finish_message_expr
1702 (object, PROPERTY_GETTER_NAME (x), NULL_TREE,
1703 &deprecated_method_prototype);
1704
1705 expression = build4 (PROPERTY_REF, TREE_TYPE(x), object, x, getter_call,
1706 deprecated_method_prototype);
1707 SET_EXPR_LOCATION (expression, input_location);
1708 TREE_SIDE_EFFECTS (expression) = 1;
1709
1710 return expression;
1711 }
1712 else
1713 {
1714 error_at (input_location, "could not find setter/getter for %qE in class %qE",
1715 property_ident, class_name);
1716 return error_mark_node;
1717 }
1718
1719 return NULL_TREE;
1720 }
1721
1722
1723
1724 /* This is used because we don't want to expose PROPERTY_REF to the
1725 C/C++ frontends. Maybe we should! */
1726 bool
objc_is_property_ref(tree node)1727 objc_is_property_ref (tree node)
1728 {
1729 if (node && TREE_CODE (node) == PROPERTY_REF)
1730 return true;
1731 else
1732 return false;
1733 }
1734
1735 /* This function builds a setter call for a PROPERTY_REF (real, for a
1736 declared property, or artificial, for a dot-syntax accessor which
1737 is not corresponding to a property). 'lhs' must be a PROPERTY_REF
1738 (the caller must check this beforehand). 'rhs' is the value to
1739 assign to the property. A plain setter call is returned, or
1740 error_mark_node if the property is readonly. */
1741
1742 static tree
objc_build_setter_call(tree lhs,tree rhs)1743 objc_build_setter_call (tree lhs, tree rhs)
1744 {
1745 tree object_expr = PROPERTY_REF_OBJECT (lhs);
1746 tree property_decl = PROPERTY_REF_PROPERTY_DECL (lhs);
1747
1748 if (PROPERTY_READONLY (property_decl))
1749 {
1750 error ("%qs property cannot be set", "readonly");
1751 return error_mark_node;
1752 }
1753 else
1754 {
1755 tree setter_argument = build_tree_list (NULL_TREE, rhs);
1756 tree setter;
1757
1758 /* TODO: Check that the setter return type is 'void'. */
1759
1760 /* TODO: Decay arguments in C. */
1761 setter = objc_finish_message_expr (object_expr,
1762 PROPERTY_SETTER_NAME (property_decl),
1763 setter_argument, NULL);
1764 return setter;
1765 }
1766
1767 /* Unreachable, but the compiler may not realize. */
1768 return error_mark_node;
1769 }
1770
1771 /* This hook routine is called when a MODIFY_EXPR is being built. We
1772 check what is being modified; if it is a PROPERTY_REF, we need to
1773 generate a 'setter' function call for the property. If this is not
1774 a PROPERTY_REF, we return NULL_TREE and the C/C++ frontend will go
1775 on creating their MODIFY_EXPR.
1776
1777 This is used for example if you write
1778
1779 object.count = 1;
1780
1781 where 'count' is a property. The left-hand side creates a
1782 PROPERTY_REF, and then the compiler tries to generate a MODIFY_EXPR
1783 to assign something to it. We intercept that here, and generate a
1784 call to the 'setter' method instead. */
1785 tree
objc_maybe_build_modify_expr(tree lhs,tree rhs)1786 objc_maybe_build_modify_expr (tree lhs, tree rhs)
1787 {
1788 if (lhs && TREE_CODE (lhs) == PROPERTY_REF)
1789 {
1790 /* Building a simple call to the setter method would work for cases such as
1791
1792 object.count = 1;
1793
1794 but wouldn't work for cases such as
1795
1796 count = object2.count = 1;
1797
1798 to get these to work with very little effort, we build a
1799 compound statement which does the setter call (to set the
1800 property to 'rhs'), but which can also be evaluated returning
1801 the 'rhs'. If the 'rhs' has no side effects, we can simply
1802 evaluate it twice, building
1803
1804 ([object setProperty: rhs]; rhs)
1805
1806 If it has side effects, we put it in a temporary variable first,
1807 so we create the following:
1808
1809 (temp = rhs; [object setProperty: temp]; temp)
1810
1811 setter_argument is rhs in the first case, and temp in the second
1812 case.
1813 */
1814 tree setter_argument;
1815
1816 /* s1, s2 and s3 are the tree statements that we need in the
1817 compound expression. */
1818 tree s1, s2, s3, compound_expr;
1819
1820 if (TREE_SIDE_EFFECTS (rhs))
1821 {
1822 tree bind;
1823
1824 /* Declare __objc_property_temp in a local bind. */
1825 setter_argument = objc_create_temporary_var (TREE_TYPE (rhs), "__objc_property_temp");
1826 DECL_SOURCE_LOCATION (setter_argument) = input_location;
1827 bind = build3 (BIND_EXPR, void_type_node, setter_argument, NULL, NULL);
1828 SET_EXPR_LOCATION (bind, input_location);
1829 TREE_SIDE_EFFECTS (bind) = 1;
1830 add_stmt (bind);
1831
1832 /* s1: x = rhs */
1833 s1 = build_modify_expr (input_location, setter_argument, NULL_TREE,
1834 NOP_EXPR,
1835 input_location, rhs, NULL_TREE);
1836 SET_EXPR_LOCATION (s1, input_location);
1837 }
1838 else
1839 {
1840 /* No s1. */
1841 setter_argument = rhs;
1842 s1 = NULL_TREE;
1843 }
1844
1845 /* Now build the compound statement. */
1846
1847 /* s2: [object setProperty: x] */
1848 s2 = objc_build_setter_call (lhs, setter_argument);
1849
1850 /* This happens if building the setter failed because the
1851 property is readonly. */
1852 if (s2 == error_mark_node)
1853 return error_mark_node;
1854
1855 SET_EXPR_LOCATION (s2, input_location);
1856
1857 /* s3: x */
1858 s3 = convert (TREE_TYPE (lhs), setter_argument);
1859
1860 /* Now build the compound statement (s1, s2, s3) or (s2, s3) as
1861 appropriate. */
1862 if (s1)
1863 compound_expr = build_compound_expr (input_location, build_compound_expr (input_location, s1, s2), s3);
1864 else
1865 compound_expr = build_compound_expr (input_location, s2, s3);
1866
1867 /* Without this, with -Wall you get a 'valued computed is not
1868 used' every time there is a "object.property = x" where the
1869 value of the resulting MODIFY_EXPR is not used. That is
1870 correct (maybe a more sophisticated implementation could
1871 avoid generating the compound expression if not needed), but
1872 we need to turn it off. */
1873 TREE_NO_WARNING (compound_expr) = 1;
1874 return compound_expr;
1875 }
1876 else
1877 return NULL_TREE;
1878 }
1879
1880 /* This hook is called by the frontend when one of the four unary
1881 expressions PREINCREMENT_EXPR, POSTINCREMENT_EXPR,
1882 PREDECREMENT_EXPR and POSTDECREMENT_EXPR is being built with an
1883 argument which is a PROPERTY_REF. For example, this happens if you have
1884
1885 object.count++;
1886
1887 where 'count' is a property. We need to use the 'getter' and
1888 'setter' for the property in an appropriate way to build the
1889 appropriate expression. 'code' is the code for the expression (one
1890 of the four mentioned above); 'argument' is the PROPERTY_REF, and
1891 'increment' is how much we need to add or subtract. */
1892 tree
objc_build_incr_expr_for_property_ref(location_t location,enum tree_code code,tree argument,tree increment)1893 objc_build_incr_expr_for_property_ref (location_t location,
1894 enum tree_code code,
1895 tree argument, tree increment)
1896 {
1897 /* Here are the expressions that we want to build:
1898
1899 For PREINCREMENT_EXPR / PREDECREMENT_EXPR:
1900 (temp = [object property] +/- increment, [object setProperty: temp], temp)
1901
1902 For POSTINCREMENT_EXPR / POSTECREMENT_EXPR:
1903 (temp = [object property], [object setProperty: temp +/- increment], temp) */
1904
1905 tree temp_variable_decl, bind;
1906 /* s1, s2 and s3 are the tree statements that we need in the
1907 compound expression. */
1908 tree s1, s2, s3, compound_expr;
1909
1910 /* Safety check. */
1911 if (!argument || TREE_CODE (argument) != PROPERTY_REF)
1912 return error_mark_node;
1913
1914 /* Declare __objc_property_temp in a local bind. */
1915 temp_variable_decl = objc_create_temporary_var (TREE_TYPE (argument), "__objc_property_temp");
1916 DECL_SOURCE_LOCATION (temp_variable_decl) = location;
1917 bind = build3 (BIND_EXPR, void_type_node, temp_variable_decl, NULL, NULL);
1918 SET_EXPR_LOCATION (bind, location);
1919 TREE_SIDE_EFFECTS (bind) = 1;
1920 add_stmt (bind);
1921
1922 /* Now build the compound statement. */
1923
1924 /* Note that the 'getter' is generated at gimplify time; at this
1925 time, we can simply put the property_ref (ie, argument) wherever
1926 we want the getter ultimately to be. */
1927
1928 /* s1: __objc_property_temp = [object property] <+/- increment> */
1929 switch (code)
1930 {
1931 case PREINCREMENT_EXPR:
1932 /* __objc_property_temp = [object property] + increment */
1933 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
1934 NOP_EXPR,
1935 location, build2 (PLUS_EXPR, TREE_TYPE (argument),
1936 argument, increment), NULL_TREE);
1937 break;
1938 case PREDECREMENT_EXPR:
1939 /* __objc_property_temp = [object property] - increment */
1940 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
1941 NOP_EXPR,
1942 location, build2 (MINUS_EXPR, TREE_TYPE (argument),
1943 argument, increment), NULL_TREE);
1944 break;
1945 case POSTINCREMENT_EXPR:
1946 case POSTDECREMENT_EXPR:
1947 /* __objc_property_temp = [object property] */
1948 s1 = build_modify_expr (location, temp_variable_decl, NULL_TREE,
1949 NOP_EXPR,
1950 location, argument, NULL_TREE);
1951 break;
1952 default:
1953 gcc_unreachable ();
1954 }
1955
1956 /* s2: [object setProperty: __objc_property_temp <+/- increment>] */
1957 switch (code)
1958 {
1959 case PREINCREMENT_EXPR:
1960 case PREDECREMENT_EXPR:
1961 /* [object setProperty: __objc_property_temp] */
1962 s2 = objc_build_setter_call (argument, temp_variable_decl);
1963 break;
1964 case POSTINCREMENT_EXPR:
1965 /* [object setProperty: __objc_property_temp + increment] */
1966 s2 = objc_build_setter_call (argument,
1967 build2 (PLUS_EXPR, TREE_TYPE (argument),
1968 temp_variable_decl, increment));
1969 break;
1970 case POSTDECREMENT_EXPR:
1971 /* [object setProperty: __objc_property_temp - increment] */
1972 s2 = objc_build_setter_call (argument,
1973 build2 (MINUS_EXPR, TREE_TYPE (argument),
1974 temp_variable_decl, increment));
1975 break;
1976 default:
1977 gcc_unreachable ();
1978 }
1979
1980 /* This happens if building the setter failed because the property
1981 is readonly. */
1982 if (s2 == error_mark_node)
1983 return error_mark_node;
1984
1985 SET_EXPR_LOCATION (s2, location);
1986
1987 /* s3: __objc_property_temp */
1988 s3 = convert (TREE_TYPE (argument), temp_variable_decl);
1989
1990 /* Now build the compound statement (s1, s2, s3) */
1991 compound_expr = build_compound_expr (location, build_compound_expr (location, s1, s2), s3);
1992
1993 /* Prevent C++ from warning with -Wall that "right operand of comma
1994 operator has no effect". */
1995 TREE_NO_WARNING (compound_expr) = 1;
1996 return compound_expr;
1997 }
1998
1999 tree
objc_build_method_signature(bool is_class_method,tree rettype,tree selector,tree optparms,bool ellipsis)2000 objc_build_method_signature (bool is_class_method, tree rettype, tree selector,
2001 tree optparms, bool ellipsis)
2002 {
2003 if (is_class_method)
2004 return build_method_decl (CLASS_METHOD_DECL, rettype, selector,
2005 optparms, ellipsis);
2006 else
2007 return build_method_decl (INSTANCE_METHOD_DECL, rettype, selector,
2008 optparms, ellipsis);
2009 }
2010
2011 void
objc_add_method_declaration(bool is_class_method,tree decl,tree attributes)2012 objc_add_method_declaration (bool is_class_method, tree decl, tree attributes)
2013 {
2014 if (!objc_interface_context)
2015 {
2016 /* PS: At the moment, due to how the parser works, it should be
2017 impossible to get here. But it's good to have the check in
2018 case the parser changes.
2019 */
2020 fatal_error (input_location,
2021 "method declaration not in @interface context");
2022 }
2023
2024 if (flag_objc1_only && attributes)
2025 error_at (input_location, "method attributes are not available in Objective-C 1.0");
2026
2027 objc_decl_method_attributes (&decl, attributes, 0);
2028 objc_add_method (objc_interface_context,
2029 decl,
2030 is_class_method,
2031 objc_method_optional_flag);
2032 }
2033
2034 /* Return 'true' if the method definition could be started, and
2035 'false' if not (because we are outside an @implementation context).
2036 EXPR is NULL or an expression that needs to be evaluated for the
2037 side effects of array size expressions in the parameters.
2038 */
2039 bool
objc_start_method_definition(bool is_class_method,tree decl,tree attributes,tree expr)2040 objc_start_method_definition (bool is_class_method, tree decl, tree attributes,
2041 tree expr)
2042 {
2043 if (!objc_implementation_context)
2044 {
2045 error ("method definition not in @implementation context");
2046 return false;
2047 }
2048
2049 if (decl != NULL_TREE && METHOD_SEL_NAME (decl) == error_mark_node)
2050 return false;
2051
2052 #ifndef OBJCPLUS
2053 /* Indicate no valid break/continue context by setting these variables
2054 to some non-null, non-label value. We'll notice and emit the proper
2055 error message in c_finish_bc_stmt. */
2056 c_break_label = c_cont_label = size_zero_node;
2057 #endif
2058
2059 if (attributes)
2060 warning_at (input_location, 0, "method attributes cannot be specified in @implementation context");
2061 else
2062 objc_decl_method_attributes (&decl, attributes, 0);
2063
2064 objc_add_method (objc_implementation_context,
2065 decl,
2066 is_class_method,
2067 /* is optional */ false);
2068 start_method_def (decl, expr);
2069 return true;
2070 }
2071
2072 void
objc_add_instance_variable(tree decl)2073 objc_add_instance_variable (tree decl)
2074 {
2075 (void) add_instance_variable (objc_ivar_context,
2076 objc_ivar_visibility,
2077 decl);
2078 }
2079
2080 /* Construct a C struct with same name as KLASS, a base struct with tag
2081 SUPER_NAME (if any), and FIELDS indicated. */
2082
2083 static tree
objc_build_struct(tree klass,tree fields,tree super_name)2084 objc_build_struct (tree klass, tree fields, tree super_name)
2085 {
2086 tree name = CLASS_NAME (klass);
2087 tree s = objc_start_struct (name);
2088 tree super = (super_name ? xref_tag (RECORD_TYPE, super_name) : NULL_TREE);
2089 tree t;
2090 vec<tree> objc_info = vNULL;
2091 int i;
2092
2093 if (super)
2094 {
2095 /* Prepend a packed variant of the base class into the layout. This
2096 is necessary to preserve ObjC ABI compatibility. */
2097 tree base = build_decl (input_location,
2098 FIELD_DECL, NULL_TREE, super);
2099 tree field = TYPE_FIELDS (super);
2100
2101 while (field && DECL_CHAIN (field)
2102 && TREE_CODE (DECL_CHAIN (field)) == FIELD_DECL)
2103 field = DECL_CHAIN (field);
2104
2105 /* For ObjC ABI purposes, the "packed" size of a base class is
2106 the sum of the offset and the size (in bits) of the last field
2107 in the class. */
2108 DECL_SIZE (base)
2109 = (field && TREE_CODE (field) == FIELD_DECL
2110 ? size_binop (PLUS_EXPR,
2111 size_binop (PLUS_EXPR,
2112 size_binop
2113 (MULT_EXPR,
2114 convert (bitsizetype,
2115 DECL_FIELD_OFFSET (field)),
2116 bitsize_int (BITS_PER_UNIT)),
2117 DECL_FIELD_BIT_OFFSET (field)),
2118 DECL_SIZE (field))
2119 : bitsize_zero_node);
2120 DECL_SIZE_UNIT (base)
2121 = size_binop (FLOOR_DIV_EXPR, convert (sizetype, DECL_SIZE (base)),
2122 size_int (BITS_PER_UNIT));
2123 DECL_ARTIFICIAL (base) = 1;
2124 SET_DECL_ALIGN (base, 1);
2125 DECL_FIELD_CONTEXT (base) = s;
2126 #ifdef OBJCPLUS
2127 DECL_FIELD_IS_BASE (base) = 1;
2128
2129 if (fields)
2130 TREE_NO_WARNING (fields) = 1; /* Suppress C++ ABI warnings -- we */
2131 #endif /* are following the ObjC ABI here. */
2132 DECL_CHAIN (base) = fields;
2133 fields = base;
2134 }
2135
2136 /* NB: Calling finish_struct() may cause type TYPE_OBJC_INFO
2137 information in all variants of this RECORD_TYPE to be destroyed
2138 (this is because the C frontend manipulates TYPE_LANG_SPECIFIC
2139 for something else and then will change all variants to use the
2140 same resulting TYPE_LANG_SPECIFIC, ignoring the fact that we use
2141 it for ObjC protocols and that such propagation will make all
2142 variants use the same objc_info), but it is therein that we store
2143 protocol conformance info (e.g., 'NSObject <MyProtocol>').
2144 Hence, we must save the ObjC-specific information before calling
2145 finish_struct(), and then reinstate it afterwards. */
2146
2147 for (t = TYPE_MAIN_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t))
2148 {
2149 INIT_TYPE_OBJC_INFO (t);
2150 objc_info.safe_push (TYPE_OBJC_INFO (t));
2151 }
2152
2153 s = objc_finish_struct (s, fields);
2154
2155 for (i = 0, t = TYPE_MAIN_VARIANT (s); t; t = TYPE_NEXT_VARIANT (t), i++)
2156 {
2157 /* We now want to restore the different TYPE_OBJC_INFO, but we
2158 have the additional problem that the C frontend doesn't just
2159 copy TYPE_LANG_SPECIFIC from one variant to the other; it
2160 actually makes all of them the *same* TYPE_LANG_SPECIFIC. As
2161 we need a different TYPE_OBJC_INFO for each (and
2162 TYPE_OBJC_INFO is a field in TYPE_LANG_SPECIFIC), we need to
2163 make a copy of each TYPE_LANG_SPECIFIC before we modify
2164 TYPE_OBJC_INFO. */
2165 if (TYPE_LANG_SPECIFIC (t))
2166 {
2167 /* Create a copy of TYPE_LANG_SPECIFIC. */
2168 struct lang_type *old_lang_type = TYPE_LANG_SPECIFIC (t);
2169 ALLOC_OBJC_TYPE_LANG_SPECIFIC (t);
2170 memcpy (TYPE_LANG_SPECIFIC (t), old_lang_type,
2171 SIZEOF_OBJC_TYPE_LANG_SPECIFIC);
2172 }
2173 else
2174 {
2175 /* Just create a new one. */
2176 ALLOC_OBJC_TYPE_LANG_SPECIFIC (t);
2177 }
2178 /* Replace TYPE_OBJC_INFO with the saved one. This restores any
2179 protocol information that may have been associated with the
2180 type. */
2181 TYPE_OBJC_INFO (t) = objc_info[i];
2182 /* Replace the IDENTIFIER_NODE with an actual @interface now
2183 that we have it. */
2184 TYPE_OBJC_INTERFACE (t) = klass;
2185 }
2186 objc_info.release ();
2187
2188 /* Use TYPE_BINFO structures to point at the super class, if any. */
2189 objc_xref_basetypes (s, super);
2190
2191 /* Mark this struct as a class template. */
2192 CLASS_STATIC_TEMPLATE (klass) = s;
2193
2194 return s;
2195 }
2196
2197 /* Mark DECL as being 'volatile' for purposes of Darwin
2198 _setjmp()/_longjmp() exception handling. Called from
2199 objc_mark_locals_volatile(). */
2200 void
objc_volatilize_decl(tree decl)2201 objc_volatilize_decl (tree decl)
2202 {
2203 /* Do not mess with variables that are 'static' or (already)
2204 'volatile'. */
2205 if (!TREE_THIS_VOLATILE (decl) && !TREE_STATIC (decl)
2206 && (TREE_CODE (decl) == VAR_DECL
2207 || TREE_CODE (decl) == PARM_DECL))
2208 {
2209 if (local_variables_to_volatilize == NULL)
2210 vec_alloc (local_variables_to_volatilize, 8);
2211
2212 vec_safe_push (local_variables_to_volatilize, decl);
2213 }
2214 }
2215
2216 /* Called when parsing of a function completes; if any local variables
2217 in the function were marked as variables to volatilize, change them
2218 to volatile. We do this at the end of the function when the
2219 warnings about discarding 'volatile' have already been produced.
2220 We are making the variables as volatile just to force the compiler
2221 to preserve them between setjmp/longjmp, but we don't want warnings
2222 for them as they aren't really volatile. */
2223 void
objc_finish_function(void)2224 objc_finish_function (void)
2225 {
2226 /* If there are any local variables to volatilize, volatilize them. */
2227 if (local_variables_to_volatilize)
2228 {
2229 int i;
2230 tree decl;
2231 FOR_EACH_VEC_ELT (*local_variables_to_volatilize, i, decl)
2232 {
2233 tree t = TREE_TYPE (decl);
2234
2235 t = build_qualified_type (t, TYPE_QUALS (t) | TYPE_QUAL_VOLATILE);
2236 TREE_TYPE (decl) = t;
2237 TREE_THIS_VOLATILE (decl) = 1;
2238 TREE_SIDE_EFFECTS (decl) = 1;
2239 DECL_REGISTER (decl) = 0;
2240 #ifndef OBJCPLUS
2241 C_DECL_REGISTER (decl) = 0;
2242 #endif
2243 }
2244
2245 /* Now we delete the vector. This sets it to NULL as well. */
2246 vec_free (local_variables_to_volatilize);
2247 }
2248 }
2249
2250 /* Check if protocol PROTO is adopted (directly or indirectly) by class CLS
2251 (including its categories and superclasses) or by object type TYP.
2252 Issue a warning if PROTO is not adopted anywhere and WARN is set. */
2253
2254 static bool
objc_lookup_protocol(tree proto,tree cls,tree typ,bool warn)2255 objc_lookup_protocol (tree proto, tree cls, tree typ, bool warn)
2256 {
2257 bool class_type = (cls != NULL_TREE);
2258
2259 while (cls)
2260 {
2261 tree c;
2262
2263 /* Check protocols adopted by the class and its categories. */
2264 for (c = cls; c; c = CLASS_CATEGORY_LIST (c))
2265 {
2266 if (lookup_protocol_in_reflist (CLASS_PROTOCOL_LIST (c), proto))
2267 return true;
2268 }
2269
2270 /* Repeat for superclasses. */
2271 cls = lookup_interface (CLASS_SUPER_NAME (cls));
2272 }
2273
2274 /* Check for any protocols attached directly to the object type. */
2275 if (TYPE_HAS_OBJC_INFO (typ))
2276 {
2277 if (lookup_protocol_in_reflist (TYPE_OBJC_PROTOCOL_LIST (typ), proto))
2278 return true;
2279 }
2280
2281 if (warn)
2282 {
2283 *errbuf = 0;
2284 gen_type_name_0 (class_type ? typ : TYPE_POINTER_TO (typ));
2285 /* NB: Types 'id' and 'Class' cannot reasonably be described as
2286 "implementing" a given protocol, since they do not have an
2287 implementation. */
2288 if (class_type)
2289 warning (0, "class %qs does not implement the %qE protocol",
2290 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
2291 else
2292 warning (0, "type %qs does not conform to the %qE protocol",
2293 identifier_to_locale (errbuf), PROTOCOL_NAME (proto));
2294 }
2295
2296 return false;
2297 }
2298
2299 /* Check if class RCLS and instance struct type RTYP conform to at least the
2300 same protocols that LCLS and LTYP conform to. */
2301
2302 static bool
objc_compare_protocols(tree lcls,tree ltyp,tree rcls,tree rtyp,bool warn)2303 objc_compare_protocols (tree lcls, tree ltyp, tree rcls, tree rtyp, bool warn)
2304 {
2305 tree p;
2306 bool have_lproto = false;
2307
2308 while (lcls)
2309 {
2310 /* NB: We do _not_ look at categories defined for LCLS; these may or
2311 may not get loaded in, and therefore it is unreasonable to require
2312 that RCLS/RTYP must implement any of their protocols. */
2313 for (p = CLASS_PROTOCOL_LIST (lcls); p; p = TREE_CHAIN (p))
2314 {
2315 have_lproto = true;
2316
2317 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
2318 return warn;
2319 }
2320
2321 /* Repeat for superclasses. */
2322 lcls = lookup_interface (CLASS_SUPER_NAME (lcls));
2323 }
2324
2325 /* Check for any protocols attached directly to the object type. */
2326 if (TYPE_HAS_OBJC_INFO (ltyp))
2327 {
2328 for (p = TYPE_OBJC_PROTOCOL_LIST (ltyp); p; p = TREE_CHAIN (p))
2329 {
2330 have_lproto = true;
2331
2332 if (!objc_lookup_protocol (TREE_VALUE (p), rcls, rtyp, warn))
2333 return warn;
2334 }
2335 }
2336
2337 /* NB: If LTYP and LCLS have no protocols to search for, return 'true'
2338 vacuously, _unless_ RTYP is a protocol-qualified 'id'. We can get
2339 away with simply checking for 'id' or 'Class' (!RCLS), since this
2340 routine will not get called in other cases. */
2341 return have_lproto || (rcls != NULL_TREE);
2342 }
2343
2344 /* Given two types TYPE1 and TYPE2, return their least common ancestor.
2345 Both TYPE1 and TYPE2 must be pointers, and already determined to be
2346 compatible by objc_compare_types() below. */
2347
2348 tree
objc_common_type(tree type1,tree type2)2349 objc_common_type (tree type1, tree type2)
2350 {
2351 tree inner1 = TREE_TYPE (type1), inner2 = TREE_TYPE (type2);
2352
2353 while (POINTER_TYPE_P (inner1))
2354 {
2355 inner1 = TREE_TYPE (inner1);
2356 inner2 = TREE_TYPE (inner2);
2357 }
2358
2359 /* If one type is derived from another, return the base type. */
2360 if (DERIVED_FROM_P (inner1, inner2))
2361 return type1;
2362 else if (DERIVED_FROM_P (inner2, inner1))
2363 return type2;
2364
2365 /* If both types are 'Class', return 'Class'. */
2366 if (objc_is_class_id (inner1) && objc_is_class_id (inner2))
2367 return objc_class_type;
2368
2369 /* Otherwise, return 'id'. */
2370 return objc_object_type;
2371 }
2372
2373 /* Determine if it is permissible to assign (if ARGNO is greater than -3)
2374 an instance of RTYP to an instance of LTYP or to compare the two
2375 (if ARGNO is equal to -3), per ObjC type system rules. Before
2376 returning 'true', this routine may issue warnings related to, e.g.,
2377 protocol conformance. When returning 'false', the routine must
2378 produce absolutely no warnings; the C or C++ front-end will do so
2379 instead, if needed. If either LTYP or RTYP is not an Objective-C
2380 type, the routine must return 'false'.
2381
2382 The ARGNO parameter is encoded as follows:
2383 >= 1 Parameter number (CALLEE contains function being called);
2384 0 Return value;
2385 -1 Assignment;
2386 -2 Initialization;
2387 -3 Comparison (LTYP and RTYP may match in either direction);
2388 -4 Silent comparison (for C++ overload resolution);
2389 -5 Silent "specialization" comparison for RTYP to be a "specialization"
2390 of LTYP (a specialization means that RTYP is LTYP plus some constraints,
2391 so that each object of type RTYP is also of type LTYP). This is used
2392 when comparing property types. */
2393
2394 bool
objc_compare_types(tree ltyp,tree rtyp,int argno,tree callee)2395 objc_compare_types (tree ltyp, tree rtyp, int argno, tree callee)
2396 {
2397 tree lcls, rcls, lproto, rproto;
2398 bool pointers_compatible;
2399
2400 /* We must be dealing with pointer types */
2401 if (!POINTER_TYPE_P (ltyp) || !POINTER_TYPE_P (rtyp))
2402 return false;
2403
2404 do
2405 {
2406 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
2407 rtyp = TREE_TYPE (rtyp);
2408 }
2409 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
2410
2411 /* We must also handle function pointers, since ObjC is a bit more
2412 lenient than C or C++ on this. */
2413 if (TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE)
2414 {
2415 function_args_iterator liter, riter;
2416
2417 /* Return types must be covariant. */
2418 if (!comptypes (TREE_TYPE (ltyp), TREE_TYPE (rtyp))
2419 && !objc_compare_types (TREE_TYPE (ltyp), TREE_TYPE (rtyp),
2420 argno, callee))
2421 return false;
2422
2423 /* Argument types must be contravariant. */
2424 function_args_iter_init (&liter, ltyp);
2425 function_args_iter_init (&riter, rtyp);
2426
2427 while (1)
2428 {
2429 ltyp = function_args_iter_cond (&liter);
2430 rtyp = function_args_iter_cond (&riter);
2431
2432 /* If we've exhaused both lists simulateously, we're done. */
2433 if (ltyp == NULL_TREE && rtyp == NULL_TREE)
2434 break;
2435
2436 /* If one list is shorter than the other, they fail to match. */
2437 if (ltyp == NULL_TREE || rtyp == NULL_TREE)
2438 return false;
2439
2440 if (!comptypes (rtyp, ltyp)
2441 && !objc_compare_types (rtyp, ltyp, argno, callee))
2442 return false;
2443
2444 function_args_iter_next (&liter);
2445 function_args_iter_next (&riter);
2446 }
2447
2448 return true;
2449 }
2450
2451 /* Past this point, we are only interested in ObjC class instances,
2452 or 'id' or 'Class'. */
2453 if (TREE_CODE (ltyp) != RECORD_TYPE || TREE_CODE (rtyp) != RECORD_TYPE)
2454 return false;
2455
2456 if (!objc_is_object_id (ltyp) && !objc_is_class_id (ltyp)
2457 && !TYPE_HAS_OBJC_INFO (ltyp))
2458 return false;
2459
2460 if (!objc_is_object_id (rtyp) && !objc_is_class_id (rtyp)
2461 && !TYPE_HAS_OBJC_INFO (rtyp))
2462 return false;
2463
2464 /* Past this point, we are committed to returning 'true' to the caller
2465 (unless performing a silent comparison; see below). However, we can
2466 still warn about type and/or protocol mismatches. */
2467
2468 if (TYPE_HAS_OBJC_INFO (ltyp))
2469 {
2470 lcls = TYPE_OBJC_INTERFACE (ltyp);
2471 lproto = TYPE_OBJC_PROTOCOL_LIST (ltyp);
2472 }
2473 else
2474 lcls = lproto = NULL_TREE;
2475
2476 if (TYPE_HAS_OBJC_INFO (rtyp))
2477 {
2478 rcls = TYPE_OBJC_INTERFACE (rtyp);
2479 rproto = TYPE_OBJC_PROTOCOL_LIST (rtyp);
2480 }
2481 else
2482 rcls = rproto = NULL_TREE;
2483
2484 /* If we could not find an @interface declaration, we must have
2485 only seen a @class declaration; for purposes of type comparison,
2486 treat it as a stand-alone (root) class. */
2487
2488 if (lcls && TREE_CODE (lcls) == IDENTIFIER_NODE)
2489 lcls = NULL_TREE;
2490
2491 if (rcls && TREE_CODE (rcls) == IDENTIFIER_NODE)
2492 rcls = NULL_TREE;
2493
2494 /* If either type is an unqualified 'id', we're done. This is because
2495 an 'id' can be assigned to or from any type with no warnings. */
2496 if (argno != -5)
2497 {
2498 if ((!lproto && objc_is_object_id (ltyp))
2499 || (!rproto && objc_is_object_id (rtyp)))
2500 return true;
2501 }
2502 else
2503 {
2504 /* For property checks, though, an 'id' is considered the most
2505 general type of object, hence if you try to specialize an
2506 'NSArray *' (ltyp) property with an 'id' (rtyp) one, we need
2507 to warn. */
2508 if (!lproto && objc_is_object_id (ltyp))
2509 return true;
2510 }
2511
2512 pointers_compatible = (TYPE_MAIN_VARIANT (ltyp) == TYPE_MAIN_VARIANT (rtyp));
2513
2514 /* If the underlying types are the same, and at most one of them has
2515 a protocol list, we do not need to issue any diagnostics. */
2516 if (pointers_compatible && (!lproto || !rproto))
2517 return true;
2518
2519 /* If exactly one of the types is 'Class', issue a diagnostic; any
2520 exceptions of this rule have already been handled. */
2521 if (objc_is_class_id (ltyp) ^ objc_is_class_id (rtyp))
2522 pointers_compatible = false;
2523 /* Otherwise, check for inheritance relations. */
2524 else
2525 {
2526 if (!pointers_compatible)
2527 {
2528 /* Again, if any of the two is an 'id', we're satisfied,
2529 unless we're comparing properties, in which case only an
2530 'id' on the left-hand side (old property) is good
2531 enough. */
2532 if (argno != -5)
2533 pointers_compatible
2534 = (objc_is_object_id (ltyp) || objc_is_object_id (rtyp));
2535 else
2536 pointers_compatible = objc_is_object_id (ltyp);
2537 }
2538
2539 if (!pointers_compatible)
2540 pointers_compatible = DERIVED_FROM_P (ltyp, rtyp);
2541
2542 if (!pointers_compatible && (argno == -3 || argno == -4))
2543 pointers_compatible = DERIVED_FROM_P (rtyp, ltyp);
2544 }
2545
2546 /* If the pointers match modulo protocols, check for protocol conformance
2547 mismatches. */
2548 if (pointers_compatible)
2549 {
2550 pointers_compatible = objc_compare_protocols (lcls, ltyp, rcls, rtyp,
2551 argno != -3);
2552
2553 if (!pointers_compatible && argno == -3)
2554 pointers_compatible = objc_compare_protocols (rcls, rtyp, lcls, ltyp,
2555 argno != -3);
2556 }
2557
2558 if (!pointers_compatible)
2559 {
2560 /* The two pointers are not exactly compatible. Issue a warning, unless
2561 we are performing a silent comparison, in which case return 'false'
2562 instead. */
2563 /* NB: For the time being, we shall make our warnings look like their
2564 C counterparts. In the future, we may wish to make them more
2565 ObjC-specific. */
2566 switch (argno)
2567 {
2568 case -5:
2569 case -4:
2570 return false;
2571
2572 case -3:
2573 warning (0, "comparison of distinct Objective-C types lacks a cast");
2574 break;
2575
2576 case -2:
2577 warning (0, "initialization from distinct Objective-C type");
2578 break;
2579
2580 case -1:
2581 warning (0, "assignment from distinct Objective-C type");
2582 break;
2583
2584 case 0:
2585 warning (0, "distinct Objective-C type in return");
2586 break;
2587
2588 default:
2589 warning (0, "passing argument %d of %qE from distinct "
2590 "Objective-C type", argno, callee);
2591 break;
2592 }
2593 }
2594
2595 return true;
2596 }
2597
2598 /* This routine is similar to objc_compare_types except that function-pointers are
2599 excluded. This is because, caller assumes that common types are of (id, Object*)
2600 variety and calls objc_common_type to obtain a common type. There is no commonolty
2601 between two function-pointers in this regard. */
2602
2603 bool
objc_have_common_type(tree ltyp,tree rtyp,int argno,tree callee)2604 objc_have_common_type (tree ltyp, tree rtyp, int argno, tree callee)
2605 {
2606 if (objc_compare_types (ltyp, rtyp, argno, callee))
2607 {
2608 /* exclude function-pointer types. */
2609 do
2610 {
2611 ltyp = TREE_TYPE (ltyp); /* Remove indirections. */
2612 rtyp = TREE_TYPE (rtyp);
2613 }
2614 while (POINTER_TYPE_P (ltyp) && POINTER_TYPE_P (rtyp));
2615 return !(TREE_CODE (ltyp) == FUNCTION_TYPE && TREE_CODE (rtyp) == FUNCTION_TYPE);
2616 }
2617 return false;
2618 }
2619
2620 #ifndef OBJCPLUS
2621 /* Determine if CHILD is derived from PARENT. The routine assumes that
2622 both parameters are RECORD_TYPEs, and is non-reflexive. */
2623
2624 static bool
objc_derived_from_p(tree parent,tree child)2625 objc_derived_from_p (tree parent, tree child)
2626 {
2627 parent = TYPE_MAIN_VARIANT (parent);
2628
2629 for (child = TYPE_MAIN_VARIANT (child);
2630 TYPE_BINFO (child) && BINFO_N_BASE_BINFOS (TYPE_BINFO (child));)
2631 {
2632 child = TYPE_MAIN_VARIANT (BINFO_TYPE (BINFO_BASE_BINFO
2633 (TYPE_BINFO (child),
2634 0)));
2635
2636 if (child == parent)
2637 return true;
2638 }
2639
2640 return false;
2641 }
2642 #endif
2643
2644 tree
objc_build_component_ref(tree datum,tree component)2645 objc_build_component_ref (tree datum, tree component)
2646 {
2647 /* If COMPONENT is NULL, the caller is referring to the anonymous
2648 base class field. */
2649 if (!component)
2650 {
2651 tree base = TYPE_FIELDS (TREE_TYPE (datum));
2652
2653 return build3 (COMPONENT_REF, TREE_TYPE (base), datum, base, NULL_TREE);
2654 }
2655
2656 /* The 'build_component_ref' routine has been removed from the C++
2657 front-end, but 'finish_class_member_access_expr' seems to be
2658 a worthy substitute. */
2659 #ifdef OBJCPLUS
2660 return finish_class_member_access_expr (datum, component, false,
2661 tf_warning_or_error);
2662 #else
2663 return build_component_ref (input_location, datum, component,
2664 UNKNOWN_LOCATION);
2665 #endif
2666 }
2667
2668 /* Recursively copy inheritance information rooted at BINFO. To do this,
2669 we emulate the song and dance performed by cp/tree.c:copy_binfo(). */
2670
2671 static tree
objc_copy_binfo(tree binfo)2672 objc_copy_binfo (tree binfo)
2673 {
2674 tree btype = BINFO_TYPE (binfo);
2675 tree binfo2 = make_tree_binfo (BINFO_N_BASE_BINFOS (binfo));
2676 tree base_binfo;
2677 int ix;
2678
2679 BINFO_TYPE (binfo2) = btype;
2680 BINFO_OFFSET (binfo2) = BINFO_OFFSET (binfo);
2681 BINFO_BASE_ACCESSES (binfo2) = BINFO_BASE_ACCESSES (binfo);
2682
2683 /* Recursively copy base binfos of BINFO. */
2684 for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
2685 {
2686 tree base_binfo2 = objc_copy_binfo (base_binfo);
2687
2688 BINFO_INHERITANCE_CHAIN (base_binfo2) = binfo2;
2689 BINFO_BASE_APPEND (binfo2, base_binfo2);
2690 }
2691
2692 return binfo2;
2693 }
2694
2695 /* Record superclass information provided in BASETYPE for ObjC class REF.
2696 This is loosely based on cp/decl.c:xref_basetypes(). */
2697
2698 static void
objc_xref_basetypes(tree ref,tree basetype)2699 objc_xref_basetypes (tree ref, tree basetype)
2700 {
2701 tree variant;
2702 tree binfo = make_tree_binfo (basetype ? 1 : 0);
2703 TYPE_BINFO (ref) = binfo;
2704 BINFO_OFFSET (binfo) = size_zero_node;
2705 BINFO_TYPE (binfo) = ref;
2706
2707 gcc_assert (TYPE_MAIN_VARIANT (ref) == ref);
2708 for (variant = ref; variant; variant = TYPE_NEXT_VARIANT (variant))
2709 TYPE_BINFO (variant) = binfo;
2710
2711 if (basetype)
2712 {
2713 tree base_binfo = objc_copy_binfo (TYPE_BINFO (basetype));
2714
2715 BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
2716 vec_alloc (BINFO_BASE_ACCESSES (binfo), 1);
2717 BINFO_BASE_APPEND (binfo, base_binfo);
2718 BINFO_BASE_ACCESS_APPEND (binfo, access_public_node);
2719 }
2720 }
2721
2722 /* Called from finish_decl. */
2723
2724 void
objc_check_decl(tree decl)2725 objc_check_decl (tree decl)
2726 {
2727 tree type = TREE_TYPE (decl);
2728
2729 if (TREE_CODE (type) != RECORD_TYPE)
2730 return;
2731 if (OBJC_TYPE_NAME (type) && (type = objc_is_class_name (OBJC_TYPE_NAME (type))))
2732 error ("statically allocated instance of Objective-C class %qE",
2733 type);
2734 }
2735
2736 void
objc_check_global_decl(tree decl)2737 objc_check_global_decl (tree decl)
2738 {
2739 tree id = DECL_NAME (decl);
2740 if (objc_is_class_name (id) && global_bindings_p())
2741 error ("redeclaration of Objective-C class %qs", IDENTIFIER_POINTER (id));
2742 }
2743
2744 /* Construct a PROTOCOLS-qualified variant of INTERFACE, where
2745 INTERFACE may either name an Objective-C class, or refer to the
2746 special 'id' or 'Class' types. If INTERFACE is not a valid ObjC
2747 type, just return it unchanged. This function is often called when
2748 PROTOCOLS is NULL_TREE, in which case we simply look up the
2749 appropriate INTERFACE. */
2750
2751 tree
objc_get_protocol_qualified_type(tree interface,tree protocols)2752 objc_get_protocol_qualified_type (tree interface, tree protocols)
2753 {
2754 /* If INTERFACE is not provided, default to 'id'. */
2755 tree type = (interface ? objc_is_id (interface) : objc_object_type);
2756 bool is_ptr = (type != NULL_TREE);
2757
2758 if (!is_ptr)
2759 {
2760 type = objc_is_class_name (interface);
2761
2762 if (type)
2763 {
2764 /* If looking at a typedef, retrieve the precise type it
2765 describes. */
2766 if (TREE_CODE (interface) == IDENTIFIER_NODE)
2767 interface = identifier_global_value (interface);
2768
2769 type = ((interface && TREE_CODE (interface) == TYPE_DECL
2770 && DECL_ORIGINAL_TYPE (interface))
2771 ? DECL_ORIGINAL_TYPE (interface)
2772 : xref_tag (RECORD_TYPE, type));
2773 }
2774 else
2775 {
2776 /* This case happens when we are given an 'interface' which
2777 is not a valid class name. For example if a typedef was
2778 used, and 'interface' really is the identifier of the
2779 typedef, but when you resolve it you don't get an
2780 Objective-C class, but something else, such as 'int'.
2781 This is an error; protocols make no sense unless you use
2782 them with Objective-C objects. */
2783 error_at (input_location, "only Objective-C object types can be qualified with a protocol");
2784
2785 /* Try to recover. Ignore the invalid class name, and treat
2786 the object as an 'id' to silence further warnings about
2787 the class. */
2788 type = objc_object_type;
2789 is_ptr = true;
2790 }
2791 }
2792
2793 if (protocols)
2794 {
2795 type = build_variant_type_copy (type);
2796
2797 /* For pointers (i.e., 'id' or 'Class'), attach the protocol(s)
2798 to the pointee. */
2799 if (is_ptr)
2800 {
2801 tree orig_pointee_type = TREE_TYPE (type);
2802 TREE_TYPE (type) = build_variant_type_copy (orig_pointee_type);
2803
2804 /* Set up the canonical type information. */
2805 TYPE_CANONICAL (type)
2806 = TYPE_CANONICAL (TYPE_POINTER_TO (orig_pointee_type));
2807
2808 TYPE_POINTER_TO (TREE_TYPE (type)) = type;
2809 type = TREE_TYPE (type);
2810 }
2811
2812 /* Look up protocols and install in lang specific list. */
2813 DUP_TYPE_OBJC_INFO (type, TYPE_MAIN_VARIANT (type));
2814 TYPE_OBJC_PROTOCOL_LIST (type) = lookup_and_install_protocols
2815 (protocols, /* definition_required */ false);
2816
2817 /* For RECORD_TYPEs, point to the @interface; for 'id' and 'Class',
2818 return the pointer to the new pointee variant. */
2819 if (is_ptr)
2820 type = TYPE_POINTER_TO (type);
2821 else
2822 TYPE_OBJC_INTERFACE (type)
2823 = TYPE_OBJC_INTERFACE (TYPE_MAIN_VARIANT (type));
2824 }
2825
2826 return type;
2827 }
2828
2829 /* Check for circular dependencies in protocols. The arguments are
2830 PROTO, the protocol to check, and LIST, a list of protocol it
2831 conforms to. */
2832
2833 static void
check_protocol_recursively(tree proto,tree list)2834 check_protocol_recursively (tree proto, tree list)
2835 {
2836 tree p;
2837
2838 for (p = list; p; p = TREE_CHAIN (p))
2839 {
2840 tree pp = TREE_VALUE (p);
2841
2842 if (TREE_CODE (pp) == IDENTIFIER_NODE)
2843 pp = lookup_protocol (pp, /* warn if deprecated */ false,
2844 /* definition_required */ false);
2845
2846 if (pp == proto)
2847 fatal_error (input_location, "protocol %qE has circular dependency",
2848 PROTOCOL_NAME (pp));
2849 if (pp)
2850 check_protocol_recursively (proto, PROTOCOL_LIST (pp));
2851 }
2852 }
2853
2854 /* Look up PROTOCOLS, and return a list of those that are found. If
2855 none are found, return NULL. Note that this function will emit a
2856 warning if a protocol is found and is deprecated. If
2857 'definition_required', then warn if the protocol is found but is
2858 not defined (ie, if we only saw a forward-declaration of the
2859 protocol (as in "@protocol NSObject;") not a real definition with
2860 the list of methods). */
2861 static tree
lookup_and_install_protocols(tree protocols,bool definition_required)2862 lookup_and_install_protocols (tree protocols, bool definition_required)
2863 {
2864 tree proto;
2865 tree return_value = NULL_TREE;
2866
2867 if (protocols == error_mark_node)
2868 return NULL;
2869
2870 for (proto = protocols; proto; proto = TREE_CHAIN (proto))
2871 {
2872 tree ident = TREE_VALUE (proto);
2873 tree p = lookup_protocol (ident, /* warn_if_deprecated */ true,
2874 definition_required);
2875
2876 if (p)
2877 return_value = chainon (return_value,
2878 build_tree_list (NULL_TREE, p));
2879 else if (ident != error_mark_node)
2880 error ("cannot find protocol declaration for %qE",
2881 ident);
2882 }
2883
2884 return return_value;
2885 }
2886
2887 static void
build_common_objc_exception_stuff(void)2888 build_common_objc_exception_stuff (void)
2889 {
2890 tree noreturn_list, nothrow_list, temp_type;
2891
2892 noreturn_list = tree_cons (get_identifier ("noreturn"), NULL, NULL);
2893 nothrow_list = tree_cons (get_identifier ("nothrow"), NULL, NULL);
2894
2895 /* void objc_exception_throw(id) __attribute__((noreturn)); */
2896 /* void objc_sync_enter(id); */
2897 /* void objc_sync_exit(id); */
2898 temp_type = build_function_type_list (void_type_node,
2899 objc_object_type,
2900 NULL_TREE);
2901 objc_exception_throw_decl
2902 = add_builtin_function (TAG_EXCEPTIONTHROW, temp_type, 0, NOT_BUILT_IN, NULL,
2903 noreturn_list);
2904 /* Make sure that objc_exception_throw (id) claims that it may throw an
2905 exception. */
2906 TREE_NOTHROW (objc_exception_throw_decl) = 0;
2907
2908 objc_sync_enter_decl
2909 = add_builtin_function (TAG_SYNCENTER, temp_type, 0, NOT_BUILT_IN,
2910 NULL, nothrow_list);
2911
2912 objc_sync_exit_decl
2913 = add_builtin_function (TAG_SYNCEXIT, temp_type, 0, NOT_BUILT_IN,
2914 NULL, nothrow_list);
2915 }
2916
2917 /* Purpose: "play" parser, creating/installing representations
2918 of the declarations that are required by Objective-C.
2919
2920 Model:
2921
2922 type_spec--------->sc_spec
2923 (tree_list) (tree_list)
2924 | |
2925 | |
2926 identifier_node identifier_node */
2927
2928 static void
synth_module_prologue(void)2929 synth_module_prologue (void)
2930 {
2931 tree type;
2932 enum debug_info_type save_write_symbols = write_symbols;
2933 const struct gcc_debug_hooks *const save_hooks = debug_hooks;
2934
2935 /* Suppress outputting debug symbols, because
2936 dbxout_init hasn't been called yet. */
2937 write_symbols = NO_DEBUG;
2938 debug_hooks = &do_nothing_debug_hooks;
2939
2940 #ifdef OBJCPLUS
2941 push_lang_context (lang_name_c); /* extern "C" */
2942 #endif
2943
2944 /* The following are also defined in <objc/objc.h> and friends. */
2945
2946 objc_object_id = get_identifier (TAG_OBJECT);
2947 objc_class_id = get_identifier (TAG_CLASS);
2948
2949 objc_object_reference = xref_tag (RECORD_TYPE, objc_object_id);
2950 objc_class_reference = xref_tag (RECORD_TYPE, objc_class_id);
2951
2952 objc_object_type = build_pointer_type (objc_object_reference);
2953 objc_instancetype_type = build_pointer_type (objc_object_reference);
2954 objc_class_type = build_pointer_type (objc_class_reference);
2955
2956 objc_object_name = get_identifier (OBJECT_TYPEDEF_NAME);
2957 objc_instancetype_name = get_identifier (INSTANCE_TYPEDEF_NAME);
2958 objc_class_name = get_identifier (CLASS_TYPEDEF_NAME);
2959
2960 /* Declare the 'id', 'instancetype' and 'Class' typedefs. */
2961 type = lang_hooks.decls.pushdecl (build_decl (input_location,
2962 TYPE_DECL,
2963 objc_object_name,
2964 objc_object_type));
2965 TREE_NO_WARNING (type) = 1;
2966
2967 type = lang_hooks.decls.pushdecl (build_decl (input_location,
2968 TYPE_DECL,
2969 objc_instancetype_name,
2970 objc_instancetype_type));
2971 TREE_NO_WARNING (type) = 1;
2972
2973 type = lang_hooks.decls.pushdecl (build_decl (input_location,
2974 TYPE_DECL,
2975 objc_class_name,
2976 objc_class_type));
2977 TREE_NO_WARNING (type) = 1;
2978
2979 /* Forward-declare '@interface Protocol'. */
2980 type = get_identifier (PROTOCOL_OBJECT_CLASS_NAME);
2981 objc_declare_class (type);
2982 objc_protocol_type = build_pointer_type (xref_tag (RECORD_TYPE, type));
2983
2984 /* Declare receiver type used for dispatching messages to 'super'. */
2985 /* `struct objc_super *' */
2986 objc_super_type = build_pointer_type (xref_tag (RECORD_TYPE,
2987 get_identifier (TAG_SUPER)));
2988
2989 /* Declare pointers to method and ivar lists. */
2990 objc_method_list_ptr = build_pointer_type
2991 (xref_tag (RECORD_TYPE,
2992 get_identifier (UTAG_METHOD_LIST)));
2993 objc_method_proto_list_ptr
2994 = build_pointer_type (xref_tag (RECORD_TYPE,
2995 get_identifier (UTAG_METHOD_PROTOTYPE_LIST)));
2996 objc_ivar_list_ptr = build_pointer_type
2997 (xref_tag (RECORD_TYPE,
2998 get_identifier (UTAG_IVAR_LIST)));
2999
3000 build_common_objc_exception_stuff ();
3001
3002 /* Set-up runtime-specific templates, message and exception stuff. */
3003 (*runtime.initialize) ();
3004
3005 /* Declare objc_getProperty, object_setProperty and other property
3006 accessor helpers. */
3007 build_common_objc_property_accessor_helpers ();
3008
3009 /* Forward declare constant_string_id and constant_string_type. */
3010 if (!constant_string_class_name)
3011 constant_string_class_name = runtime.default_constant_string_class_name;
3012 constant_string_id = get_identifier (constant_string_class_name);
3013 objc_declare_class (constant_string_id);
3014
3015 /* Pre-build the following entities - for speed/convenience. */
3016 self_id = get_identifier ("self");
3017 ucmd_id = get_identifier ("_cmd");
3018
3019 /* Declare struct _objc_fast_enumeration_state { ... }; */
3020 build_fast_enumeration_state_template ();
3021
3022 /* void objc_enumeration_mutation (id) */
3023 type = build_function_type_list (void_type_node,
3024 objc_object_type, NULL_TREE);
3025 objc_enumeration_mutation_decl
3026 = add_builtin_function (TAG_ENUMERATION_MUTATION, type, 0, NOT_BUILT_IN,
3027 NULL, NULL_TREE);
3028 TREE_NOTHROW (objc_enumeration_mutation_decl) = 0;
3029
3030 #ifdef OBJCPLUS
3031 pop_lang_context ();
3032 #endif
3033
3034 write_symbols = save_write_symbols;
3035 debug_hooks = save_hooks;
3036 }
3037
3038 /* --- const strings --- */
3039
3040 /* Ensure that the ivar list for NSConstantString/NXConstantString
3041 (or whatever was specified via `-fconstant-string-class')
3042 contains fields at least as large as the following three, so that
3043 the runtime can stomp on them with confidence:
3044
3045 struct STRING_OBJECT_CLASS_NAME
3046 {
3047 Object isa;
3048 char *cString;
3049 unsigned int length;
3050 }; */
3051
3052 static int
check_string_class_template(void)3053 check_string_class_template (void)
3054 {
3055 tree field_decl = objc_get_class_ivars (constant_string_id);
3056
3057 #define AT_LEAST_AS_LARGE_AS(F, T) \
3058 (F && TREE_CODE (F) == FIELD_DECL \
3059 && (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (F))) \
3060 >= TREE_INT_CST_LOW (TYPE_SIZE (T))))
3061
3062 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
3063 return 0;
3064
3065 field_decl = DECL_CHAIN (field_decl);
3066 if (!AT_LEAST_AS_LARGE_AS (field_decl, ptr_type_node))
3067 return 0;
3068
3069 field_decl = DECL_CHAIN (field_decl);
3070 return AT_LEAST_AS_LARGE_AS (field_decl, unsigned_type_node);
3071
3072 #undef AT_LEAST_AS_LARGE_AS
3073 }
3074
3075 /* Avoid calling `check_string_class_template ()' more than once. */
3076 static GTY(()) int string_layout_checked;
3077
3078 /* Construct an internal string layout to be used as a template for
3079 creating NSConstantString/NXConstantString instances. */
3080
3081 static tree
objc_build_internal_const_str_type(void)3082 objc_build_internal_const_str_type (void)
3083 {
3084 tree type = (*lang_hooks.types.make_type) (RECORD_TYPE);
3085 tree fields = build_decl (input_location,
3086 FIELD_DECL, NULL_TREE, ptr_type_node);
3087 tree field = build_decl (input_location,
3088 FIELD_DECL, NULL_TREE, ptr_type_node);
3089
3090 DECL_CHAIN (field) = fields; fields = field;
3091 field = build_decl (input_location,
3092 FIELD_DECL, NULL_TREE, unsigned_type_node);
3093 DECL_CHAIN (field) = fields; fields = field;
3094 /* NB: The finish_builtin_struct() routine expects FIELD_DECLs in
3095 reverse order! */
3096 finish_builtin_struct (type, "__builtin_ObjCString",
3097 fields, NULL_TREE);
3098
3099 return type;
3100 }
3101
3102 /* Custom build_string which sets TREE_TYPE! */
3103
3104 tree
my_build_string(int len,const char * str)3105 my_build_string (int len, const char *str)
3106 {
3107 return fix_string_type (build_string (len, str));
3108 }
3109
3110 /* Build a string with contents STR and length LEN and convert it to a
3111 pointer. */
3112
3113 tree
my_build_string_pointer(int len,const char * str)3114 my_build_string_pointer (int len, const char *str)
3115 {
3116 tree string = my_build_string (len, str);
3117 tree ptrtype = build_pointer_type (TREE_TYPE (TREE_TYPE (string)));
3118 return build1 (ADDR_EXPR, ptrtype, string);
3119 }
3120
3121 hashval_t
hash(string_descriptor * ptr)3122 objc_string_hasher::hash (string_descriptor *ptr)
3123 {
3124 const_tree const str = ptr->literal;
3125 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (str);
3126 int i, len = TREE_STRING_LENGTH (str);
3127 hashval_t h = len;
3128
3129 for (i = 0; i < len; i++)
3130 h = ((h * 613) + p[i]);
3131
3132 return h;
3133 }
3134
3135 bool
equal(string_descriptor * ptr1,string_descriptor * ptr2)3136 objc_string_hasher::equal (string_descriptor *ptr1, string_descriptor *ptr2)
3137 {
3138 const_tree const str1 = ptr1->literal;
3139 const_tree const str2 = ptr2->literal;
3140 int len1 = TREE_STRING_LENGTH (str1);
3141
3142 return (len1 == TREE_STRING_LENGTH (str2)
3143 && !memcmp (TREE_STRING_POINTER (str1), TREE_STRING_POINTER (str2),
3144 len1));
3145 }
3146
3147 /* Given a chain of STRING_CST's, build a static instance of
3148 NXConstantString which points at the concatenation of those
3149 strings. We place the string object in the __string_objects
3150 section of the __OBJC segment. The Objective-C runtime will
3151 initialize the isa pointers of the string objects to point at the
3152 NXConstantString class object. */
3153
3154 tree
objc_build_string_object(tree string)3155 objc_build_string_object (tree string)
3156 {
3157 tree constant_string_class;
3158 int length;
3159 tree addr;
3160 struct string_descriptor *desc, key;
3161
3162 /* We should be passed a STRING_CST. */
3163 gcc_checking_assert (TREE_CODE (string) == STRING_CST);
3164 length = TREE_STRING_LENGTH (string) - 1;
3165
3166 /* The target may have different ideas on how to construct an ObjC string
3167 literal. On Darwin (Mac OS X), for example, we may wish to obtain a
3168 constant CFString reference instead.
3169 At present, this is only supported for the NeXT runtime. */
3170 if (flag_next_runtime
3171 && targetcm.objc_construct_string_object)
3172 {
3173 tree constructor = (*targetcm.objc_construct_string_object) (string);
3174 if (constructor)
3175 return build1 (NOP_EXPR, objc_object_type, constructor);
3176 }
3177
3178 /* Check whether the string class being used actually exists and has the
3179 correct ivar layout. */
3180 if (!string_layout_checked)
3181 {
3182 string_layout_checked = -1;
3183 constant_string_class = lookup_interface (constant_string_id);
3184 internal_const_str_type = objc_build_internal_const_str_type ();
3185
3186 if (!constant_string_class
3187 || !(constant_string_type
3188 = CLASS_STATIC_TEMPLATE (constant_string_class)))
3189 error ("cannot find interface declaration for %qE",
3190 constant_string_id);
3191 /* The NSConstantString/NXConstantString ivar layout is now known. */
3192 else if (!check_string_class_template ())
3193 error ("interface %qE does not have valid constant string layout",
3194 constant_string_id);
3195 /* If the runtime can generate a literal reference to the string class,
3196 don't need to run a constructor. */
3197 else if (!(*runtime.setup_const_string_class_decl)())
3198 error ("cannot find reference tag for class %qE", constant_string_id);
3199 else
3200 {
3201 string_layout_checked = 1; /* Success! */
3202 add_class_reference (constant_string_id);
3203 }
3204 }
3205
3206 if (string_layout_checked == -1)
3207 return error_mark_node;
3208
3209 /* Perhaps we already constructed a constant string just like this one? */
3210 key.literal = string;
3211 string_descriptor **loc = string_htab->find_slot (&key, INSERT);
3212 desc = *loc;
3213
3214 if (!desc)
3215 {
3216 *loc = desc = ggc_alloc<string_descriptor> ();
3217 desc->literal = string;
3218 desc->constructor =
3219 (*runtime.build_const_string_constructor) (input_location, string, length);
3220 }
3221
3222 addr = convert (build_pointer_type (constant_string_type),
3223 build_unary_op (input_location,
3224 ADDR_EXPR, desc->constructor, 1));
3225
3226 return addr;
3227 }
3228
3229 /* Build a static constant CONSTRUCTOR
3230 with type TYPE and elements ELTS. */
3231
3232 tree
objc_build_constructor(tree type,vec<constructor_elt,va_gc> * elts)3233 objc_build_constructor (tree type, vec<constructor_elt, va_gc> *elts)
3234 {
3235 tree constructor = build_constructor (type, elts);
3236
3237 TREE_CONSTANT (constructor) = 1;
3238 TREE_STATIC (constructor) = 1;
3239 TREE_READONLY (constructor) = 1;
3240
3241 #ifdef OBJCPLUS
3242 /* Adjust for impedance mismatch. We should figure out how to build
3243 CONSTRUCTORs that consistently please both the C and C++ gods. */
3244 if (!(*elts)[0].index)
3245 TREE_TYPE (constructor) = init_list_type_node;
3246 #endif
3247
3248 return constructor;
3249 }
3250
3251 /* Return the DECL of the string IDENT in the SECTION. */
3252
3253 tree
get_objc_string_decl(tree ident,enum string_section section)3254 get_objc_string_decl (tree ident, enum string_section section)
3255 {
3256 tree chain;
3257
3258 switch (section)
3259 {
3260 case class_names:
3261 chain = class_names_chain;
3262 break;
3263 case meth_var_names:
3264 chain = meth_var_names_chain;
3265 break;
3266 case meth_var_types:
3267 chain = meth_var_types_chain;
3268 break;
3269 case prop_names_attr:
3270 chain = prop_names_attr_chain;
3271 break;
3272 default:
3273 gcc_unreachable ();
3274 }
3275
3276 for (; chain != 0; chain = TREE_CHAIN (chain))
3277 if (TREE_VALUE (chain) == ident)
3278 return (TREE_PURPOSE (chain));
3279
3280 /* We didn't find the entry. */
3281 return NULL_TREE;
3282 }
3283
3284 /* Create a class reference, but don't create a variable to reference
3285 it. */
3286
3287 void
add_class_reference(tree ident)3288 add_class_reference (tree ident)
3289 {
3290 tree chain;
3291
3292 if ((chain = cls_ref_chain))
3293 {
3294 tree tail;
3295 do
3296 {
3297 if (ident == TREE_VALUE (chain))
3298 return;
3299
3300 tail = chain;
3301 chain = TREE_CHAIN (chain);
3302 }
3303 while (chain);
3304
3305 /* Append to the end of the list */
3306 TREE_CHAIN (tail) = tree_cons (NULL_TREE, ident, NULL_TREE);
3307 }
3308 else
3309 cls_ref_chain = tree_cons (NULL_TREE, ident, NULL_TREE);
3310 }
3311
3312 /* Get a class reference, creating it if necessary. Also create the
3313 reference variable. */
3314 tree
objc_get_class_reference(tree ident)3315 objc_get_class_reference (tree ident)
3316 {
3317 tree orig_ident = (DECL_P (ident)
3318 ? DECL_NAME (ident)
3319 : TYPE_P (ident)
3320 ? OBJC_TYPE_NAME (ident)
3321 : ident);
3322 bool local_scope = false;
3323
3324 #ifdef OBJCPLUS
3325 if (processing_template_decl)
3326 /* Must wait until template instantiation time. */
3327 return build_min_nt_loc (UNKNOWN_LOCATION, CLASS_REFERENCE_EXPR, ident);
3328 #endif
3329
3330 if (TREE_CODE (ident) == TYPE_DECL)
3331 ident = (DECL_ORIGINAL_TYPE (ident)
3332 ? DECL_ORIGINAL_TYPE (ident)
3333 : TREE_TYPE (ident));
3334
3335 #ifdef OBJCPLUS
3336 if (TYPE_P (ident)
3337 && CP_TYPE_CONTEXT (ident) != global_namespace)
3338 local_scope = true;
3339 #endif
3340
3341 if (local_scope || !(ident = objc_is_class_name (ident)))
3342 {
3343 error ("%qE is not an Objective-C class name or alias",
3344 orig_ident);
3345 return error_mark_node;
3346 }
3347
3348 return (*runtime.get_class_reference) (ident);
3349 }
3350
3351 void
objc_declare_alias(tree alias_ident,tree class_ident)3352 objc_declare_alias (tree alias_ident, tree class_ident)
3353 {
3354 tree underlying_class;
3355
3356 #ifdef OBJCPLUS
3357 if (current_namespace != global_namespace) {
3358 error ("Objective-C declarations may only appear in global scope");
3359 }
3360 #endif /* OBJCPLUS */
3361
3362 if (!(underlying_class = objc_is_class_name (class_ident)))
3363 warning (0, "cannot find class %qE", class_ident);
3364 else if (objc_is_class_name (alias_ident))
3365 warning (0, "class %qE already exists", alias_ident);
3366 else
3367 {
3368 /* Implement @compatibility_alias as a typedef. */
3369 #ifdef OBJCPLUS
3370 push_lang_context (lang_name_c); /* extern "C" */
3371 #endif
3372 lang_hooks.decls.pushdecl (build_decl
3373 (input_location,
3374 TYPE_DECL,
3375 alias_ident,
3376 xref_tag (RECORD_TYPE, underlying_class)));
3377 #ifdef OBJCPLUS
3378 pop_lang_context ();
3379 #endif
3380 objc_map_put (alias_name_map, alias_ident, underlying_class);
3381 }
3382 }
3383
3384 void
objc_declare_class(tree identifier)3385 objc_declare_class (tree identifier)
3386 {
3387 #ifdef OBJCPLUS
3388 if (current_namespace != global_namespace) {
3389 error ("Objective-C declarations may only appear in global scope");
3390 }
3391 #endif /* OBJCPLUS */
3392
3393 if (! objc_is_class_name (identifier))
3394 {
3395 tree record = lookup_name (identifier), type = record;
3396
3397 if (record)
3398 {
3399 if (TREE_CODE (record) == TYPE_DECL)
3400 type = DECL_ORIGINAL_TYPE (record)
3401 ? DECL_ORIGINAL_TYPE (record)
3402 : TREE_TYPE (record);
3403
3404 if (!TYPE_HAS_OBJC_INFO (type)
3405 || !TYPE_OBJC_INTERFACE (type))
3406 {
3407 error ("%qE redeclared as different kind of symbol",
3408 identifier);
3409 error ("previous declaration of %q+D",
3410 record);
3411 }
3412 }
3413
3414 record = xref_tag (RECORD_TYPE, identifier);
3415 INIT_TYPE_OBJC_INFO (record);
3416 /* In the case of a @class declaration, we store the ident in
3417 the TYPE_OBJC_INTERFACE. If later an @interface is found,
3418 we'll replace the ident with the interface. */
3419 TYPE_OBJC_INTERFACE (record) = identifier;
3420 objc_map_put (class_name_map, identifier, NULL_TREE);
3421 }
3422 }
3423
3424 tree
objc_is_class_name(tree ident)3425 objc_is_class_name (tree ident)
3426 {
3427 if (ident && TREE_CODE (ident) == IDENTIFIER_NODE)
3428 {
3429 tree t = identifier_global_value (ident);
3430 if (t)
3431 ident = t;
3432 }
3433
3434 while (ident && TREE_CODE (ident) == TYPE_DECL && DECL_ORIGINAL_TYPE (ident))
3435 ident = OBJC_TYPE_NAME (DECL_ORIGINAL_TYPE (ident));
3436
3437 if (ident && TREE_CODE (ident) == RECORD_TYPE)
3438 ident = OBJC_TYPE_NAME (ident);
3439 #ifdef OBJCPLUS
3440 if (ident && TREE_CODE (ident) == TYPE_DECL)
3441 {
3442 tree type = TREE_TYPE (ident);
3443 if (type && TREE_CODE (type) == TEMPLATE_TYPE_PARM)
3444 return NULL_TREE;
3445 ident = DECL_NAME (ident);
3446 }
3447 #endif
3448 if (!ident || TREE_CODE (ident) != IDENTIFIER_NODE)
3449 return NULL_TREE;
3450
3451 if (lookup_interface (ident))
3452 return ident;
3453
3454 {
3455 tree target;
3456
3457 target = objc_map_get (class_name_map, ident);
3458 if (target != OBJC_MAP_NOT_FOUND)
3459 return ident;
3460
3461 target = objc_map_get (alias_name_map, ident);
3462 if (target != OBJC_MAP_NOT_FOUND)
3463 return target;
3464 }
3465
3466 return 0;
3467 }
3468
3469 /* Check whether TYPE is either 'id' or 'Class'. */
3470
3471 tree
objc_is_id(tree type)3472 objc_is_id (tree type)
3473 {
3474 if (type && TREE_CODE (type) == IDENTIFIER_NODE)
3475 {
3476 tree t = identifier_global_value (type);
3477 if (t)
3478 type = t;
3479 }
3480
3481 if (type && TREE_CODE (type) == TYPE_DECL)
3482 type = TREE_TYPE (type);
3483
3484 /* NB: This function may be called before the ObjC front-end has
3485 been initialized, in which case OBJC_OBJECT_TYPE will (still) be NULL. */
3486 return (objc_object_type && type
3487 && (IS_ID (type) || IS_CLASS (type) || IS_SUPER (type))
3488 ? type
3489 : NULL_TREE);
3490 }
3491
3492 /* Check whether TYPE is either 'id', 'Class', or a pointer to an ObjC
3493 class instance. This is needed by other parts of the compiler to
3494 handle ObjC types gracefully. */
3495
3496 tree
objc_is_object_ptr(tree type)3497 objc_is_object_ptr (tree type)
3498 {
3499 tree ret;
3500
3501 type = TYPE_MAIN_VARIANT (type);
3502 if (!POINTER_TYPE_P (type))
3503 return 0;
3504
3505 ret = objc_is_id (type);
3506 if (!ret)
3507 ret = objc_is_class_name (TREE_TYPE (type));
3508
3509 return ret;
3510 }
3511
3512 static int
objc_is_gcable_type(tree type,int or_strong_p)3513 objc_is_gcable_type (tree type, int or_strong_p)
3514 {
3515 tree name;
3516
3517 if (!TYPE_P (type))
3518 return 0;
3519 if (objc_is_id (TYPE_MAIN_VARIANT (type)))
3520 return 1;
3521 if (or_strong_p && lookup_attribute ("objc_gc", TYPE_ATTRIBUTES (type)))
3522 return 1;
3523 if (TREE_CODE (type) != POINTER_TYPE && TREE_CODE (type) != INDIRECT_REF)
3524 return 0;
3525 type = TREE_TYPE (type);
3526 if (TREE_CODE (type) != RECORD_TYPE)
3527 return 0;
3528 name = TYPE_NAME (type);
3529 return (objc_is_class_name (name) != NULL_TREE);
3530 }
3531
3532 static tree
objc_substitute_decl(tree expr,tree oldexpr,tree newexpr)3533 objc_substitute_decl (tree expr, tree oldexpr, tree newexpr)
3534 {
3535 if (expr == oldexpr)
3536 return newexpr;
3537
3538 switch (TREE_CODE (expr))
3539 {
3540 case COMPONENT_REF:
3541 return objc_build_component_ref
3542 (objc_substitute_decl (TREE_OPERAND (expr, 0),
3543 oldexpr,
3544 newexpr),
3545 DECL_NAME (TREE_OPERAND (expr, 1)));
3546 case ARRAY_REF:
3547 return build_array_ref (input_location,
3548 objc_substitute_decl (TREE_OPERAND (expr, 0),
3549 oldexpr,
3550 newexpr),
3551 TREE_OPERAND (expr, 1));
3552 case INDIRECT_REF:
3553 return build_indirect_ref (input_location,
3554 objc_substitute_decl (TREE_OPERAND (expr, 0),
3555 oldexpr,
3556 newexpr), RO_ARROW);
3557 default:
3558 return expr;
3559 }
3560 }
3561
3562 static tree
objc_build_ivar_assignment(tree outervar,tree lhs,tree rhs)3563 objc_build_ivar_assignment (tree outervar, tree lhs, tree rhs)
3564 {
3565 tree func_params;
3566 /* The LHS parameter contains the expression 'outervar->memberspec';
3567 we need to transform it into '&((typeof(outervar) *) 0)->memberspec',
3568 where memberspec may be arbitrarily complex (e.g., 'g->f.d[2].g[3]').
3569 */
3570 tree offs
3571 = objc_substitute_decl
3572 (lhs, outervar, convert (TREE_TYPE (outervar), integer_zero_node));
3573 tree func
3574 = (flag_objc_direct_dispatch
3575 ? objc_assign_ivar_fast_decl
3576 : objc_assign_ivar_decl);
3577
3578 offs = convert (integer_type_node, build_unary_op (input_location,
3579 ADDR_EXPR, offs, 0));
3580 offs = fold (offs);
3581 func_params = tree_cons (NULL_TREE,
3582 convert (objc_object_type, rhs),
3583 tree_cons (NULL_TREE, convert (objc_object_type, outervar),
3584 tree_cons (NULL_TREE, offs,
3585 NULL_TREE)));
3586
3587 return build_function_call (input_location, func, func_params);
3588 }
3589
3590 static tree
objc_build_global_assignment(tree lhs,tree rhs)3591 objc_build_global_assignment (tree lhs, tree rhs)
3592 {
3593 tree func_params = tree_cons (NULL_TREE,
3594 convert (objc_object_type, rhs),
3595 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3596 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3597 NULL_TREE));
3598
3599 return build_function_call (input_location,
3600 objc_assign_global_decl, func_params);
3601 }
3602
3603 static tree
objc_build_strong_cast_assignment(tree lhs,tree rhs)3604 objc_build_strong_cast_assignment (tree lhs, tree rhs)
3605 {
3606 tree func_params = tree_cons (NULL_TREE,
3607 convert (objc_object_type, rhs),
3608 tree_cons (NULL_TREE, convert (build_pointer_type (objc_object_type),
3609 build_unary_op (input_location, ADDR_EXPR, lhs, 0)),
3610 NULL_TREE));
3611
3612 return build_function_call (input_location,
3613 objc_assign_strong_cast_decl, func_params);
3614 }
3615
3616 static int
objc_is_gcable_p(tree expr)3617 objc_is_gcable_p (tree expr)
3618 {
3619 return (TREE_CODE (expr) == COMPONENT_REF
3620 ? objc_is_gcable_p (TREE_OPERAND (expr, 1))
3621 : TREE_CODE (expr) == ARRAY_REF
3622 ? (objc_is_gcable_p (TREE_TYPE (expr))
3623 || objc_is_gcable_p (TREE_OPERAND (expr, 0)))
3624 : TREE_CODE (expr) == ARRAY_TYPE
3625 ? objc_is_gcable_p (TREE_TYPE (expr))
3626 : TYPE_P (expr)
3627 ? objc_is_gcable_type (expr, 1)
3628 : (objc_is_gcable_p (TREE_TYPE (expr))
3629 || (DECL_P (expr)
3630 && lookup_attribute ("objc_gc", DECL_ATTRIBUTES (expr)))));
3631 }
3632
3633 static int
objc_is_ivar_reference_p(tree expr)3634 objc_is_ivar_reference_p (tree expr)
3635 {
3636 return (TREE_CODE (expr) == ARRAY_REF
3637 ? objc_is_ivar_reference_p (TREE_OPERAND (expr, 0))
3638 : TREE_CODE (expr) == COMPONENT_REF
3639 ? TREE_CODE (TREE_OPERAND (expr, 1)) == FIELD_DECL
3640 : 0);
3641 }
3642
3643 static int
objc_is_global_reference_p(tree expr)3644 objc_is_global_reference_p (tree expr)
3645 {
3646 return (TREE_CODE (expr) == INDIRECT_REF || TREE_CODE (expr) == PLUS_EXPR
3647 ? objc_is_global_reference_p (TREE_OPERAND (expr, 0))
3648 : DECL_P (expr)
3649 ? (DECL_FILE_SCOPE_P (expr) || TREE_STATIC (expr))
3650 : 0);
3651 }
3652
3653 tree
objc_generate_write_barrier(tree lhs,enum tree_code modifycode,tree rhs)3654 objc_generate_write_barrier (tree lhs, enum tree_code modifycode, tree rhs)
3655 {
3656 tree result = NULL_TREE, outer;
3657 int strong_cast_p = 0, outer_gc_p = 0, indirect_p = 0;
3658
3659 /* This function is currently only used with the next runtime with
3660 garbage collection enabled (-fobjc-gc). */
3661 gcc_assert (flag_next_runtime);
3662
3663 /* See if we have any lhs casts, and strip them out. NB: The lvalue casts
3664 will have been transformed to the form '*(type *)&expr'. */
3665 if (TREE_CODE (lhs) == INDIRECT_REF)
3666 {
3667 outer = TREE_OPERAND (lhs, 0);
3668
3669 while (!strong_cast_p
3670 && (CONVERT_EXPR_P (outer)
3671 || TREE_CODE (outer) == NON_LVALUE_EXPR))
3672 {
3673 tree lhstype = TREE_TYPE (outer);
3674
3675 /* Descend down the cast chain, and record the first objc_gc
3676 attribute found. */
3677 if (POINTER_TYPE_P (lhstype))
3678 {
3679 tree attr
3680 = lookup_attribute ("objc_gc",
3681 TYPE_ATTRIBUTES (TREE_TYPE (lhstype)));
3682
3683 if (attr)
3684 strong_cast_p = 1;
3685 }
3686
3687 outer = TREE_OPERAND (outer, 0);
3688 }
3689 }
3690
3691 /* If we have a __strong cast, it trumps all else. */
3692 if (strong_cast_p)
3693 {
3694 if (modifycode != NOP_EXPR)
3695 goto invalid_pointer_arithmetic;
3696
3697 if (warn_assign_intercept)
3698 warning (0, "strong-cast assignment has been intercepted");
3699
3700 result = objc_build_strong_cast_assignment (lhs, rhs);
3701
3702 goto exit_point;
3703 }
3704
3705 /* the lhs must be of a suitable type, regardless of its underlying
3706 structure. */
3707 if (!objc_is_gcable_p (lhs))
3708 goto exit_point;
3709
3710 outer = lhs;
3711
3712 while (outer
3713 && (TREE_CODE (outer) == COMPONENT_REF
3714 || TREE_CODE (outer) == ARRAY_REF))
3715 outer = TREE_OPERAND (outer, 0);
3716
3717 if (TREE_CODE (outer) == INDIRECT_REF)
3718 {
3719 outer = TREE_OPERAND (outer, 0);
3720 indirect_p = 1;
3721 }
3722
3723 outer_gc_p = objc_is_gcable_p (outer);
3724
3725 /* Handle ivar assignments. */
3726 if (objc_is_ivar_reference_p (lhs))
3727 {
3728 /* if the struct to the left of the ivar is not an Objective-C object (__strong
3729 doesn't cut it here), the best we can do here is suggest a cast. */
3730 if (!objc_is_gcable_type (TREE_TYPE (outer), 0))
3731 {
3732 /* We may still be able to use the global write barrier... */
3733 if (!indirect_p && objc_is_global_reference_p (outer))
3734 goto global_reference;
3735
3736 suggest_cast:
3737 if (modifycode == NOP_EXPR)
3738 {
3739 if (warn_assign_intercept)
3740 warning (0, "strong-cast may possibly be needed");
3741 }
3742
3743 goto exit_point;
3744 }
3745
3746 if (modifycode != NOP_EXPR)
3747 goto invalid_pointer_arithmetic;
3748
3749 if (warn_assign_intercept)
3750 warning (0, "instance variable assignment has been intercepted");
3751
3752 result = objc_build_ivar_assignment (outer, lhs, rhs);
3753
3754 goto exit_point;
3755 }
3756
3757 /* Likewise, intercept assignment to global/static variables if their type is
3758 GC-marked. */
3759 if (objc_is_global_reference_p (outer))
3760 {
3761 if (indirect_p)
3762 goto suggest_cast;
3763
3764 global_reference:
3765 if (modifycode != NOP_EXPR)
3766 {
3767 invalid_pointer_arithmetic:
3768 if (outer_gc_p)
3769 warning (0, "pointer arithmetic for garbage-collected objects not allowed");
3770
3771 goto exit_point;
3772 }
3773
3774 if (warn_assign_intercept)
3775 warning (0, "global/static variable assignment has been intercepted");
3776
3777 result = objc_build_global_assignment (lhs, rhs);
3778 }
3779
3780 /* In all other cases, fall back to the normal mechanism. */
3781 exit_point:
3782 return result;
3783 }
3784
3785 /* Implementation of the table mapping a class name (as an identifier)
3786 to a class node. The two public functions for it are
3787 lookup_interface() and add_interface(). add_interface() is only
3788 used in this file, so we can make it static. */
3789
3790 static GTY(()) objc_map_t interface_map;
3791
3792 static void
interface_hash_init(void)3793 interface_hash_init (void)
3794 {
3795 interface_map = objc_map_alloc_ggc (200);
3796 }
3797
3798 static tree
add_interface(tree class_name,tree name)3799 add_interface (tree class_name, tree name)
3800 {
3801 /* Put interfaces on list in reverse order. */
3802 TREE_CHAIN (class_name) = interface_chain;
3803 interface_chain = class_name;
3804
3805 /* Add it to the map. */
3806 objc_map_put (interface_map, name, class_name);
3807
3808 return interface_chain;
3809 }
3810
3811 tree
lookup_interface(tree ident)3812 lookup_interface (tree ident)
3813 {
3814 #ifdef OBJCPLUS
3815 if (ident && TREE_CODE (ident) == TYPE_DECL)
3816 ident = DECL_NAME (ident);
3817 #endif
3818
3819 if (ident == NULL_TREE || TREE_CODE (ident) != IDENTIFIER_NODE)
3820 return NULL_TREE;
3821
3822 {
3823 tree interface = objc_map_get (interface_map, ident);
3824
3825 if (interface == OBJC_MAP_NOT_FOUND)
3826 return NULL_TREE;
3827 else
3828 return interface;
3829 }
3830 }
3831
3832
3833
3834 /* Implement @defs (<classname>) within struct bodies. */
3835
3836 tree
objc_get_class_ivars(tree class_name)3837 objc_get_class_ivars (tree class_name)
3838 {
3839 tree interface = lookup_interface (class_name);
3840
3841 if (interface)
3842 return get_class_ivars (interface, true);
3843
3844 error ("cannot find interface declaration for %qE",
3845 class_name);
3846
3847 return error_mark_node;
3848 }
3849
3850
3851 /* Functions used by the hashtable for field duplicates in
3852 objc_detect_field_duplicates(). Ideally, we'd use a standard
3853 key-value dictionary hashtable , and store as keys the field names,
3854 and as values the actual declarations (used to print nice error
3855 messages with the locations). But, the hashtable we are using only
3856 allows us to store keys in the hashtable, without values (it looks
3857 more like a set). So, we store the DECLs, but define equality as
3858 DECLs having the same name, and hash as the hash of the name. */
3859
3860 struct decl_name_hash : nofree_ptr_hash <tree_node>
3861 {
3862 static inline hashval_t hash (const tree_node *);
3863 static inline bool equal (const tree_node *, const tree_node *);
3864 };
3865
3866 inline hashval_t
hash(const tree_node * q)3867 decl_name_hash::hash (const tree_node *q)
3868 {
3869 return (hashval_t) ((intptr_t)(DECL_NAME (q)) >> 3);
3870 }
3871
3872 inline bool
equal(const tree_node * a,const tree_node * b)3873 decl_name_hash::equal (const tree_node *a, const tree_node *b)
3874 {
3875 return DECL_NAME (a) == DECL_NAME (b);
3876 }
3877
3878 /* Called when checking the variables in a struct. If we are not
3879 doing the ivars list inside an @interface context, then return
3880 false. Else, perform the check for duplicate ivars, then return
3881 true. The check for duplicates checks if an instance variable with
3882 the same name exists in the class or in a superclass. If
3883 'check_superclasses_only' is set to true, then it is assumed that
3884 checks for instance variables in the same class has already been
3885 performed (this is the case for ObjC++) and only the instance
3886 variables of superclasses are checked. */
3887 bool
objc_detect_field_duplicates(bool check_superclasses_only)3888 objc_detect_field_duplicates (bool check_superclasses_only)
3889 {
3890 if (!objc_collecting_ivars || !objc_interface_context
3891 || TREE_CODE (objc_interface_context) != CLASS_INTERFACE_TYPE)
3892 return false;
3893
3894 /* We have two ways of doing this check:
3895
3896 "direct comparison": we iterate over the instance variables and
3897 compare them directly. This works great for small numbers of
3898 instance variables (such as 10 or 20), which are extremely common.
3899 But it will potentially take forever for the pathological case with
3900 a huge number (eg, 10k) of instance variables.
3901
3902 "hashtable": we use a hashtable, which requires a single sweep
3903 through the list of instances variables. This is much slower for a
3904 small number of variables, and we only use it for large numbers.
3905
3906 To decide which one to use, we need to get an idea of how many
3907 instance variables we have to compare. */
3908 {
3909 unsigned int number_of_ivars_to_check = 0;
3910 {
3911 tree ivar;
3912 for (ivar = CLASS_RAW_IVARS (objc_interface_context);
3913 ivar; ivar = DECL_CHAIN (ivar))
3914 {
3915 /* Ignore anonymous ivars. */
3916 if (DECL_NAME (ivar))
3917 number_of_ivars_to_check++;
3918 }
3919 }
3920
3921 /* Exit if there is nothing to do. */
3922 if (number_of_ivars_to_check == 0)
3923 return true;
3924
3925 /* In case that there are only 1 or 2 instance variables to check,
3926 we always use direct comparison. If there are more, it is
3927 worth iterating over the instance variables in the superclass
3928 to count how many there are (note that this has the same cost
3929 as checking 1 instance variable by direct comparison, which is
3930 why we skip this check in the case of 1 or 2 ivars and just do
3931 the direct comparison) and then decide if it worth using a
3932 hashtable. */
3933 if (number_of_ivars_to_check > 2)
3934 {
3935 unsigned int number_of_superclass_ivars = 0;
3936 {
3937 tree interface;
3938 for (interface = lookup_interface (CLASS_SUPER_NAME (objc_interface_context));
3939 interface; interface = lookup_interface (CLASS_SUPER_NAME (interface)))
3940 {
3941 tree ivar;
3942 for (ivar = CLASS_RAW_IVARS (interface);
3943 ivar; ivar = DECL_CHAIN (ivar))
3944 number_of_superclass_ivars++;
3945 }
3946 }
3947
3948 /* We use a hashtable if we have over 10k comparisons. */
3949 if (number_of_ivars_to_check * (number_of_superclass_ivars
3950 + (number_of_ivars_to_check / 2))
3951 > 10000)
3952 {
3953 /* First, build the hashtable by putting all the instance
3954 variables of superclasses in it. */
3955 hash_table<decl_name_hash> htab (37);
3956 tree interface;
3957 for (interface = lookup_interface (CLASS_SUPER_NAME
3958 (objc_interface_context));
3959 interface; interface = lookup_interface
3960 (CLASS_SUPER_NAME (interface)))
3961 {
3962 tree ivar;
3963 for (ivar = CLASS_RAW_IVARS (interface); ivar;
3964 ivar = DECL_CHAIN (ivar))
3965 {
3966 if (DECL_NAME (ivar) != NULL_TREE)
3967 {
3968 tree_node **slot = htab.find_slot (ivar, INSERT);
3969 /* Do not check for duplicate instance
3970 variables in superclasses. Errors have
3971 already been generated. */
3972 *slot = ivar;
3973 }
3974 }
3975 }
3976
3977 /* Now, we go through all the instance variables in the
3978 class, and check that they are not in the
3979 hashtable. */
3980 if (check_superclasses_only)
3981 {
3982 tree ivar;
3983 for (ivar = CLASS_RAW_IVARS (objc_interface_context); ivar;
3984 ivar = DECL_CHAIN (ivar))
3985 {
3986 if (DECL_NAME (ivar) != NULL_TREE)
3987 {
3988 tree duplicate_ivar = htab.find (ivar);
3989 if (duplicate_ivar != HTAB_EMPTY_ENTRY)
3990 {
3991 error_at (DECL_SOURCE_LOCATION (ivar),
3992 "duplicate instance variable %q+D",
3993 ivar);
3994 inform (DECL_SOURCE_LOCATION (duplicate_ivar),
3995 "previous declaration of %q+D",
3996 duplicate_ivar);
3997 /* FIXME: Do we need the following ? */
3998 /* DECL_NAME (ivar) = NULL_TREE; */
3999 }
4000 }
4001 }
4002 }
4003 else
4004 {
4005 /* If we're checking for duplicates in the class as
4006 well, we insert variables in the hashtable as we
4007 check them, so if a duplicate follows, it will be
4008 caught. */
4009 tree ivar;
4010 for (ivar = CLASS_RAW_IVARS (objc_interface_context); ivar;
4011 ivar = DECL_CHAIN (ivar))
4012 {
4013 if (DECL_NAME (ivar) != NULL_TREE)
4014 {
4015 tree_node **slot = htab.find_slot (ivar, INSERT);
4016 if (*slot)
4017 {
4018 tree duplicate_ivar = (tree)(*slot);
4019 error_at (DECL_SOURCE_LOCATION (ivar),
4020 "duplicate instance variable %q+D",
4021 ivar);
4022 inform (DECL_SOURCE_LOCATION (duplicate_ivar),
4023 "previous declaration of %q+D",
4024 duplicate_ivar);
4025 /* FIXME: Do we need the following ? */
4026 /* DECL_NAME (ivar) = NULL_TREE; */
4027 }
4028 *slot = ivar;
4029 }
4030 }
4031 }
4032 return true;
4033 }
4034 }
4035 }
4036
4037 /* This is the "direct comparison" approach, which is used in most
4038 non-pathological cases. */
4039 {
4040 /* Walk up to class hierarchy, starting with this class (this is
4041 the external loop, because lookup_interface() is expensive, and
4042 we want to do it few times). */
4043 tree interface = objc_interface_context;
4044
4045 if (check_superclasses_only)
4046 interface = lookup_interface (CLASS_SUPER_NAME (interface));
4047
4048 for ( ; interface; interface = lookup_interface
4049 (CLASS_SUPER_NAME (interface)))
4050 {
4051 tree ivar_being_checked;
4052
4053 for (ivar_being_checked = CLASS_RAW_IVARS (objc_interface_context);
4054 ivar_being_checked;
4055 ivar_being_checked = DECL_CHAIN (ivar_being_checked))
4056 {
4057 tree decl;
4058
4059 /* Ignore anonymous ivars. */
4060 if (DECL_NAME (ivar_being_checked) == NULL_TREE)
4061 continue;
4062
4063 /* Note how we stop when we find the ivar we are checking
4064 (this can only happen in the main class, not
4065 superclasses), to avoid comparing things twice
4066 (otherwise, for each ivar, you'd compare A to B then B
4067 to A, and get duplicated error messages). */
4068 for (decl = CLASS_RAW_IVARS (interface);
4069 decl && decl != ivar_being_checked;
4070 decl = DECL_CHAIN (decl))
4071 {
4072 if (DECL_NAME (ivar_being_checked) == DECL_NAME (decl))
4073 {
4074 error_at (DECL_SOURCE_LOCATION (ivar_being_checked),
4075 "duplicate instance variable %q+D",
4076 ivar_being_checked);
4077 inform (DECL_SOURCE_LOCATION (decl),
4078 "previous declaration of %q+D",
4079 decl);
4080 /* FIXME: Do we need the following ? */
4081 /* DECL_NAME (ivar_being_checked) = NULL_TREE; */
4082 }
4083 }
4084 }
4085 }
4086 }
4087 return true;
4088 }
4089
4090 /* Used by: build_private_template, continue_class,
4091 and for @defs constructs. */
4092
4093 static tree
get_class_ivars(tree interface,bool inherited)4094 get_class_ivars (tree interface, bool inherited)
4095 {
4096 tree ivar_chain = copy_list (CLASS_RAW_IVARS (interface));
4097
4098 /* Both CLASS_RAW_IVARS and CLASS_IVARS contain a list of ivars declared
4099 by the current class (i.e., they do not include super-class ivars).
4100 However, the CLASS_IVARS list will be side-effected by a call to
4101 finish_struct(), which will fill in field offsets. */
4102 if (!CLASS_IVARS (interface))
4103 CLASS_IVARS (interface) = ivar_chain;
4104
4105 if (!inherited)
4106 return ivar_chain;
4107
4108 while (CLASS_SUPER_NAME (interface))
4109 {
4110 /* Prepend super-class ivars. */
4111 interface = lookup_interface (CLASS_SUPER_NAME (interface));
4112 ivar_chain = chainon (copy_list (CLASS_RAW_IVARS (interface)),
4113 ivar_chain);
4114 }
4115
4116 return ivar_chain;
4117 }
4118
4119 void
objc_maybe_warn_exceptions(location_t loc)4120 objc_maybe_warn_exceptions (location_t loc)
4121 {
4122 /* -fobjc-exceptions is required to enable Objective-C exceptions.
4123 For example, on Darwin, ObjC exceptions require a sufficiently
4124 recent version of the runtime, so the user must ask for them
4125 explicitly. On other platforms, at the moment -fobjc-exceptions
4126 triggers -fexceptions which again is required for exceptions to
4127 work. */
4128 if (!flag_objc_exceptions)
4129 {
4130 /* Warn only once per compilation unit. */
4131 static bool warned = false;
4132
4133 if (!warned)
4134 {
4135 error_at (loc, "%<-fobjc-exceptions%> is required to enable Objective-C exception syntax");
4136 warned = true;
4137 }
4138 }
4139 }
4140
4141 static struct objc_try_context *cur_try_context;
4142
4143 /* Called just after parsing the @try and its associated BODY. We now
4144 must prepare for the tricky bits -- handling the catches and finally. */
4145
4146 void
objc_begin_try_stmt(location_t try_locus,tree body)4147 objc_begin_try_stmt (location_t try_locus, tree body)
4148 {
4149 struct objc_try_context *c = XCNEW (struct objc_try_context);
4150 c->outer = cur_try_context;
4151 c->try_body = body;
4152 c->try_locus = try_locus;
4153 c->end_try_locus = input_location;
4154 cur_try_context = c;
4155
4156 /* Collect the list of local variables. We'll mark them as volatile
4157 at the end of compilation of this function to prevent them being
4158 clobbered by setjmp/longjmp. */
4159 if (flag_objc_sjlj_exceptions)
4160 objc_mark_locals_volatile (NULL);
4161 }
4162
4163 /* Called just after parsing "@catch (parm)". Open a binding level,
4164 enter DECL into the binding level, and initialize it. Leave the
4165 binding level open while the body of the compound statement is
4166 parsed. If DECL is NULL_TREE, then we are compiling "@catch(...)"
4167 which we compile as "@catch(id tmp_variable)". */
4168
4169 void
objc_begin_catch_clause(tree decl)4170 objc_begin_catch_clause (tree decl)
4171 {
4172 tree compound, type, t;
4173 bool ellipsis = false;
4174
4175 /* Begin a new scope that the entire catch clause will live in. */
4176 compound = c_begin_compound_stmt (true);
4177
4178 /* Create the appropriate declaration for the argument. */
4179 if (decl == error_mark_node)
4180 type = error_mark_node;
4181 else
4182 {
4183 if (decl == NULL_TREE)
4184 {
4185 /* If @catch(...) was specified, create a temporary variable of
4186 type 'id' and use it. */
4187 decl = objc_create_temporary_var (objc_object_type, "__objc_generic_catch_var");
4188 DECL_SOURCE_LOCATION (decl) = input_location;
4189 /* ... but allow the runtime to differentiate between ellipsis and the
4190 case of @catch (id xyz). */
4191 ellipsis = true;
4192 }
4193 else
4194 {
4195 /* The parser passed in a PARM_DECL, but what we really want is a VAR_DECL. */
4196 decl = build_decl (input_location,
4197 VAR_DECL, DECL_NAME (decl), TREE_TYPE (decl));
4198 }
4199 lang_hooks.decls.pushdecl (decl);
4200
4201 /* Mark the declaration as used so you never any warnings whether
4202 you use the exception argument or not. TODO: Implement a
4203 -Wunused-exception-parameter flag, which would cause warnings
4204 if exception parameter is not used. */
4205 TREE_USED (decl) = 1;
4206 DECL_READ_P (decl) = 1;
4207
4208 type = TREE_TYPE (decl);
4209 }
4210
4211 /* Verify that the type of the catch is valid. It must be a pointer
4212 to an Objective-C class, or "id" (which is catch-all). */
4213 if (type == error_mark_node)
4214 {
4215 ;/* Just keep going. */
4216 }
4217 else if (!objc_type_valid_for_messaging (type, false))
4218 {
4219 error ("%<@catch%> parameter is not a known Objective-C class type");
4220 type = error_mark_node;
4221 }
4222 else if (TYPE_HAS_OBJC_INFO (TREE_TYPE (type))
4223 && TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (type)))
4224 {
4225 error ("%<@catch%> parameter cannot be protocol-qualified");
4226 type = error_mark_node;
4227 }
4228 else if (POINTER_TYPE_P (type) && objc_is_object_id (TREE_TYPE (type)))
4229 /* @catch (id xyz) or @catch (...) but we note this for runtimes that
4230 identify 'id'. */
4231 ;
4232 else
4233 {
4234 /* If 'type' was built using typedefs, we need to get rid of
4235 them and get a simple pointer to the class. */
4236 bool is_typedef = false;
4237 tree x = TYPE_MAIN_VARIANT (type);
4238
4239 /* Skip from the pointer to the pointee. */
4240 if (TREE_CODE (x) == POINTER_TYPE)
4241 x = TREE_TYPE (x);
4242
4243 /* Traverse typedef aliases */
4244 while (TREE_CODE (x) == RECORD_TYPE && OBJC_TYPE_NAME (x)
4245 && TREE_CODE (OBJC_TYPE_NAME (x)) == TYPE_DECL
4246 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (x)))
4247 {
4248 is_typedef = true;
4249 x = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (x));
4250 }
4251
4252 /* If it was a typedef, build a pointer to the final, original
4253 class. */
4254 if (is_typedef)
4255 type = build_pointer_type (x);
4256
4257 if (cur_try_context->catch_list)
4258 {
4259 /* Examine previous @catch clauses and see if we've already
4260 caught the type in question. */
4261 tree_stmt_iterator i = tsi_start (cur_try_context->catch_list);
4262 for (; !tsi_end_p (i); tsi_next (&i))
4263 {
4264 tree stmt = tsi_stmt (i);
4265 t = CATCH_TYPES (stmt);
4266 if (t == error_mark_node)
4267 continue;
4268 if (!t || DERIVED_FROM_P (TREE_TYPE (t), TREE_TYPE (type)))
4269 {
4270 warning (0, "exception of type %<%T%> will be caught",
4271 TREE_TYPE (type));
4272 warning_at (EXPR_LOCATION (stmt), 0, " by earlier handler for %<%T%>",
4273 TREE_TYPE (t ? t : objc_object_type));
4274 break;
4275 }
4276 }
4277 }
4278 }
4279
4280 t = (*runtime.begin_catch) (&cur_try_context, type, decl, compound, ellipsis);
4281 add_stmt (t);
4282 }
4283
4284 /* Called just after parsing the closing brace of a @catch clause. Close
4285 the open binding level, and record a CATCH_EXPR for it. */
4286
4287 void
objc_finish_catch_clause(void)4288 objc_finish_catch_clause (void)
4289 {
4290 tree c = cur_try_context->current_catch;
4291 cur_try_context->current_catch = NULL;
4292 cur_try_context->end_catch_locus = input_location;
4293
4294 CATCH_BODY (c) = c_end_compound_stmt (input_location, CATCH_BODY (c), 1);
4295
4296 (*runtime.finish_catch) (&cur_try_context, c);
4297 }
4298
4299 /* Called after parsing a @finally clause and its associated BODY.
4300 Record the body for later placement. */
4301
4302 void
objc_build_finally_clause(location_t finally_locus,tree body)4303 objc_build_finally_clause (location_t finally_locus, tree body)
4304 {
4305 cur_try_context->finally_body = body;
4306 cur_try_context->finally_locus = finally_locus;
4307 cur_try_context->end_finally_locus = input_location;
4308 }
4309
4310 /* Called to finalize a @try construct. */
4311
4312 tree
objc_finish_try_stmt(void)4313 objc_finish_try_stmt (void)
4314 {
4315 struct objc_try_context *c = cur_try_context;
4316 tree stmt;
4317
4318 if (c->catch_list == NULL && c->finally_body == NULL)
4319 error ("%<@try%> without %<@catch%> or %<@finally%>");
4320
4321 stmt = (*runtime.finish_try_stmt) (&cur_try_context);
4322 add_stmt (stmt);
4323
4324 cur_try_context = c->outer;
4325 free (c);
4326 return stmt;
4327 }
4328
4329 tree
objc_build_throw_stmt(location_t loc,tree throw_expr)4330 objc_build_throw_stmt (location_t loc, tree throw_expr)
4331 {
4332 bool rethrown = false;
4333
4334 objc_maybe_warn_exceptions (loc);
4335
4336 /* Don't waste time trying to build something if we're already dead. */
4337 if (throw_expr == error_mark_node)
4338 return error_mark_node;
4339
4340 if (throw_expr == NULL)
4341 {
4342 /* If we're not inside a @catch block, there is no "current
4343 exception" to be rethrown. */
4344 if (cur_try_context == NULL
4345 || cur_try_context->current_catch == NULL)
4346 {
4347 error_at (loc,
4348 "%<@throw%> (rethrow) used outside of a %<@catch%> block");
4349 return error_mark_node;
4350 }
4351
4352 /* Otherwise the object is still sitting in the EXC_PTR_EXPR
4353 value that we get from the runtime. */
4354 throw_expr = (*runtime.build_exc_ptr) (&cur_try_context);
4355 rethrown = true;
4356 }
4357 else
4358 {
4359 if (!objc_type_valid_for_messaging (TREE_TYPE (throw_expr), true))
4360 {
4361 error_at (loc, "%<@throw%> argument is not an object");
4362 return error_mark_node;
4363 }
4364 }
4365
4366 return (*runtime.build_throw_stmt) (loc, throw_expr, rethrown);
4367 }
4368
4369 tree
objc_build_synchronized(location_t start_locus,tree object_expr,tree body)4370 objc_build_synchronized (location_t start_locus, tree object_expr, tree body)
4371 {
4372 /* object_expr should never be NULL; but in case it is, convert it to
4373 error_mark_node. */
4374 if (object_expr == NULL)
4375 object_expr = error_mark_node;
4376
4377 /* Validate object_expr. If not valid, set it to error_mark_node. */
4378 if (object_expr != error_mark_node)
4379 {
4380 if (!objc_type_valid_for_messaging (TREE_TYPE (object_expr), true))
4381 {
4382 error_at (start_locus, "%<@synchronized%> argument is not an object");
4383 object_expr = error_mark_node;
4384 }
4385 }
4386
4387 if (object_expr == error_mark_node)
4388 {
4389 /* If we found an error, we simply ignore the '@synchronized'.
4390 Compile the body so we can keep going with minimal
4391 casualties. */
4392 return add_stmt (body);
4393 }
4394 else
4395 {
4396 tree call;
4397 tree args;
4398
4399 /* objc_sync_enter (object_expr); */
4400 object_expr = save_expr (object_expr);
4401 args = tree_cons (NULL, object_expr, NULL);
4402 call = build_function_call (input_location,
4403 objc_sync_enter_decl, args);
4404 SET_EXPR_LOCATION (call, start_locus);
4405 add_stmt (call);
4406
4407 /* Build "objc_sync_exit (object_expr);" but do not add it yet;
4408 it goes inside the @finalize() clause. */
4409 args = tree_cons (NULL, object_expr, NULL);
4410 call = build_function_call (input_location,
4411 objc_sync_exit_decl, args);
4412 SET_EXPR_LOCATION (call, input_location);
4413
4414 /* @try { body; } */
4415 objc_begin_try_stmt (start_locus, body);
4416
4417 /* @finally { objc_sync_exit (object_expr); } */
4418 objc_build_finally_clause (input_location, call);
4419
4420 /* End of try statement. */
4421 return objc_finish_try_stmt ();
4422 }
4423 }
4424
4425 /* Construct a C struct corresponding to ObjC class CLASS, with the same
4426 name as the class:
4427
4428 struct <classname> {
4429 struct _objc_class *isa;
4430 ...
4431 }; */
4432
4433 static void
build_private_template(tree klass)4434 build_private_template (tree klass)
4435 {
4436 if (!CLASS_STATIC_TEMPLATE (klass))
4437 {
4438 tree record = objc_build_struct (klass,
4439 get_class_ivars (klass, false),
4440 CLASS_SUPER_NAME (klass));
4441
4442 /* Set the TREE_USED bit for this struct, so that stab generator
4443 can emit stabs for this struct type. */
4444 if (flag_debug_only_used_symbols && TYPE_STUB_DECL (record))
4445 TREE_USED (TYPE_STUB_DECL (record)) = 1;
4446
4447 /* Copy the attributes from the class to the type. */
4448 if (TREE_DEPRECATED (klass))
4449 TREE_DEPRECATED (record) = 1;
4450 }
4451 }
4452
4453 /* Generate either '- .cxx_construct' or '- .cxx_destruct' for the
4454 current class. */
4455 #ifdef OBJCPLUS
4456 static void
objc_generate_cxx_ctor_or_dtor(bool dtor)4457 objc_generate_cxx_ctor_or_dtor (bool dtor)
4458 {
4459 tree fn, body, compound_stmt, ivar;
4460
4461 /* - (id) .cxx_construct { ... return self; } */
4462 /* - (void) .cxx_construct { ... } */
4463
4464 objc_start_method_definition
4465 (false /* is_class_method */,
4466 objc_build_method_signature (false /* is_class_method */,
4467 build_tree_list (NULL_TREE,
4468 dtor
4469 ? void_type_node
4470 : objc_object_type),
4471 get_identifier (dtor
4472 ? TAG_CXX_DESTRUCT
4473 : TAG_CXX_CONSTRUCT),
4474 make_node (TREE_LIST),
4475 false), NULL, NULL_TREE);
4476 body = begin_function_body ();
4477 compound_stmt = begin_compound_stmt (0);
4478
4479 ivar = CLASS_IVARS (implementation_template);
4480 /* Destroy ivars in reverse order. */
4481 if (dtor)
4482 ivar = nreverse (copy_list (ivar));
4483
4484 for (; ivar; ivar = TREE_CHAIN (ivar))
4485 {
4486 if (TREE_CODE (ivar) == FIELD_DECL)
4487 {
4488 tree type = TREE_TYPE (ivar);
4489
4490 /* Call the ivar's default constructor or destructor. Do not
4491 call the destructor unless a corresponding constructor call
4492 has also been made (or is not needed). */
4493 if (MAYBE_CLASS_TYPE_P (type)
4494 && (dtor
4495 ? (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4496 && (!TYPE_NEEDS_CONSTRUCTING (type)
4497 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4498 : (TYPE_NEEDS_CONSTRUCTING (type)
4499 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))))
4500 finish_expr_stmt
4501 (build_special_member_call
4502 (build_ivar_reference (DECL_NAME (ivar)),
4503 dtor ? complete_dtor_identifier : complete_ctor_identifier,
4504 NULL, type, LOOKUP_NORMAL, tf_warning_or_error));
4505 }
4506 }
4507
4508 /* The constructor returns 'self'. */
4509 if (!dtor)
4510 finish_return_stmt (self_decl);
4511
4512 finish_compound_stmt (compound_stmt);
4513 finish_function_body (body);
4514 fn = current_function_decl;
4515 finish_function ();
4516 objc_finish_method_definition (fn);
4517 }
4518
4519 /* The following routine will examine the current @interface for any
4520 non-POD C++ ivars requiring non-trivial construction and/or
4521 destruction, and then synthesize special '- .cxx_construct' and/or
4522 '- .cxx_destruct' methods which will run the appropriate
4523 construction or destruction code. Note that ivars inherited from
4524 super-classes are _not_ considered. */
4525 static void
objc_generate_cxx_cdtors(void)4526 objc_generate_cxx_cdtors (void)
4527 {
4528 bool need_ctor = false, need_dtor = false;
4529 tree ivar;
4530
4531 /* Error case, due to possibly an extra @end. */
4532 if (!objc_implementation_context)
4533 return;
4534
4535 /* We do not want to do this for categories, since they do not have
4536 their own ivars. */
4537
4538 if (TREE_CODE (objc_implementation_context) != CLASS_IMPLEMENTATION_TYPE)
4539 return;
4540
4541 /* First, determine if we even need a constructor and/or destructor. */
4542
4543 for (ivar = CLASS_IVARS (implementation_template); ivar;
4544 ivar = TREE_CHAIN (ivar))
4545 {
4546 if (TREE_CODE (ivar) == FIELD_DECL)
4547 {
4548 tree type = TREE_TYPE (ivar);
4549
4550 if (MAYBE_CLASS_TYPE_P (type))
4551 {
4552 if (TYPE_NEEDS_CONSTRUCTING (type)
4553 && TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
4554 /* NB: If a default constructor is not available, we will not
4555 be able to initialize this ivar; the add_instance_variable()
4556 routine will already have warned about this. */
4557 need_ctor = true;
4558
4559 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4560 && (!TYPE_NEEDS_CONSTRUCTING (type)
4561 || TYPE_HAS_DEFAULT_CONSTRUCTOR (type)))
4562 /* NB: If a default constructor is not available, we will not
4563 call the destructor either, for symmetry. */
4564 need_dtor = true;
4565 }
4566 }
4567 }
4568
4569 /* Generate '- .cxx_construct' if needed. */
4570
4571 if (need_ctor)
4572 objc_generate_cxx_ctor_or_dtor (false);
4573
4574 /* Generate '- .cxx_destruct' if needed. */
4575
4576 if (need_dtor)
4577 objc_generate_cxx_ctor_or_dtor (true);
4578
4579 /* The 'imp_list' variable points at an imp_entry record for the current
4580 @implementation. Record the existence of '- .cxx_construct' and/or
4581 '- .cxx_destruct' methods therein; it will be included in the
4582 metadata for the class if the runtime needs it. */
4583 imp_list->has_cxx_cdtors = (need_ctor || need_dtor);
4584 }
4585 #endif
4586
4587 static void
error_with_ivar(const char * message,tree decl)4588 error_with_ivar (const char *message, tree decl)
4589 {
4590 error_at (DECL_SOURCE_LOCATION (decl), "%s %qs",
4591 message, identifier_to_locale (gen_declaration (decl)));
4592
4593 }
4594
4595 static void
check_ivars(tree inter,tree imp)4596 check_ivars (tree inter, tree imp)
4597 {
4598 tree intdecls = CLASS_RAW_IVARS (inter);
4599 tree impdecls = CLASS_RAW_IVARS (imp);
4600
4601 while (1)
4602 {
4603 tree t1, t2;
4604
4605 #ifdef OBJCPLUS
4606 if (intdecls && TREE_CODE (intdecls) == TYPE_DECL)
4607 intdecls = TREE_CHAIN (intdecls);
4608 #endif
4609 if (intdecls == 0 && impdecls == 0)
4610 break;
4611 if (intdecls == 0 || impdecls == 0)
4612 {
4613 error ("inconsistent instance variable specification");
4614 break;
4615 }
4616
4617 t1 = TREE_TYPE (intdecls); t2 = TREE_TYPE (impdecls);
4618
4619 if (!comptypes (t1, t2)
4620 #ifdef OBJCPLUS
4621 || !tree_int_cst_equal (DECL_BIT_FIELD_REPRESENTATIVE (intdecls),
4622 DECL_BIT_FIELD_REPRESENTATIVE (impdecls))
4623 #else
4624 || !tree_int_cst_equal (DECL_INITIAL (intdecls),
4625 DECL_INITIAL (impdecls))
4626 #endif
4627 )
4628 {
4629 if (DECL_NAME (intdecls) == DECL_NAME (impdecls))
4630 {
4631 error_with_ivar ("conflicting instance variable type",
4632 impdecls);
4633 error_with_ivar ("previous declaration of",
4634 intdecls);
4635 }
4636 else /* both the type and the name don't match */
4637 {
4638 error ("inconsistent instance variable specification");
4639 break;
4640 }
4641 }
4642
4643 else if (DECL_NAME (intdecls) != DECL_NAME (impdecls))
4644 {
4645 error_with_ivar ("conflicting instance variable name",
4646 impdecls);
4647 error_with_ivar ("previous declaration of",
4648 intdecls);
4649 }
4650
4651 intdecls = DECL_CHAIN (intdecls);
4652 impdecls = DECL_CHAIN (impdecls);
4653 }
4654 }
4655
4656
4657 static void
mark_referenced_methods(void)4658 mark_referenced_methods (void)
4659 {
4660 struct imp_entry *impent;
4661 tree chain;
4662
4663 for (impent = imp_list; impent; impent = impent->next)
4664 {
4665 chain = CLASS_CLS_METHODS (impent->imp_context);
4666 while (chain)
4667 {
4668 cgraph_node::get_create (METHOD_DEFINITION (chain))->mark_force_output ();
4669 chain = DECL_CHAIN (chain);
4670 }
4671
4672 chain = CLASS_NST_METHODS (impent->imp_context);
4673 while (chain)
4674 {
4675 cgraph_node::get_create (METHOD_DEFINITION (chain))->mark_force_output ();
4676 chain = DECL_CHAIN (chain);
4677 }
4678 }
4679 }
4680
4681 /* If type is empty or only type qualifiers are present, add default
4682 type of id (otherwise grokdeclarator will default to int). */
4683 static inline tree
adjust_type_for_id_default(tree type)4684 adjust_type_for_id_default (tree type)
4685 {
4686 if (!type)
4687 type = make_node (TREE_LIST);
4688
4689 if (!TREE_VALUE (type))
4690 TREE_VALUE (type) = objc_object_type;
4691 else if (TREE_CODE (TREE_VALUE (type)) == RECORD_TYPE
4692 && TYPED_OBJECT (TREE_VALUE (type)))
4693 error ("cannot use an object as parameter to a method");
4694
4695 return type;
4696 }
4697
4698 /* Return a KEYWORD_DECL built using the specified key_name, arg_type,
4699 arg_name and attributes. (TODO: Rename KEYWORD_DECL to
4700 OBJC_METHOD_PARM_DECL ?)
4701
4702 A KEYWORD_DECL is a tree representing the declaration of a
4703 parameter of an Objective-C method. It is produced when parsing a
4704 fragment of Objective-C method declaration of the form
4705
4706 keyworddecl:
4707 selector ':' '(' typename ')' identifier
4708
4709 For example, take the Objective-C method
4710
4711 -(NSString *)pathForResource:(NSString *)resource ofType:(NSString *)type;
4712
4713 the two fragments "pathForResource:(NSString *)resource" and
4714 "ofType:(NSString *)type" will generate a KEYWORD_DECL each. The
4715 KEYWORD_DECL stores the 'key_name' (eg, identifier for
4716 "pathForResource"), the 'arg_type' (eg, tree representing a
4717 NSString *), the 'arg_name' (eg identifier for "resource") and
4718 potentially some attributes (for example, a tree representing
4719 __attribute__ ((unused)) if such an attribute was attached to a
4720 certain parameter). You can access this information using the
4721 TREE_TYPE (for arg_type), KEYWORD_ARG_NAME (for arg_name),
4722 KEYWORD_KEY_NAME (for key_name), DECL_ATTRIBUTES (for attributes).
4723
4724 'key_name' is an identifier node (and is optional as you can omit
4725 it in Objective-C methods).
4726 'arg_type' is a tree list (and is optional too if no parameter type
4727 was specified).
4728 'arg_name' is an identifier node and is required.
4729 'attributes' is an optional tree containing parameter attributes. */
4730 tree
objc_build_keyword_decl(tree key_name,tree arg_type,tree arg_name,tree attributes)4731 objc_build_keyword_decl (tree key_name, tree arg_type,
4732 tree arg_name, tree attributes)
4733 {
4734 tree keyword_decl;
4735
4736 if (flag_objc1_only && attributes)
4737 error_at (input_location, "method argument attributes are not available in Objective-C 1.0");
4738
4739 /* If no type is specified, default to "id". */
4740 arg_type = adjust_type_for_id_default (arg_type);
4741
4742 keyword_decl = make_node (KEYWORD_DECL);
4743
4744 TREE_TYPE (keyword_decl) = arg_type;
4745 KEYWORD_ARG_NAME (keyword_decl) = arg_name;
4746 KEYWORD_KEY_NAME (keyword_decl) = key_name;
4747 DECL_ATTRIBUTES (keyword_decl) = attributes;
4748
4749 return keyword_decl;
4750 }
4751
4752 /* Given a chain of keyword_decl's, synthesize the full keyword selector. */
4753 static tree
build_keyword_selector(tree selector)4754 build_keyword_selector (tree selector)
4755 {
4756 int len = 0;
4757 tree key_chain, key_name;
4758 char *buf;
4759
4760 /* Scan the selector to see how much space we'll need. */
4761 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
4762 {
4763 switch (TREE_CODE (selector))
4764 {
4765 case KEYWORD_DECL:
4766 key_name = KEYWORD_KEY_NAME (key_chain);
4767 break;
4768 case TREE_LIST:
4769 key_name = TREE_PURPOSE (key_chain);
4770 break;
4771 default:
4772 gcc_unreachable ();
4773 }
4774
4775 if (key_name)
4776 len += IDENTIFIER_LENGTH (key_name) + 1;
4777 else
4778 /* Just a ':' arg. */
4779 len++;
4780 }
4781
4782 buf = (char *) alloca (len + 1);
4783 /* Start the buffer out as an empty string. */
4784 buf[0] = '\0';
4785
4786 for (key_chain = selector; key_chain; key_chain = TREE_CHAIN (key_chain))
4787 {
4788 switch (TREE_CODE (selector))
4789 {
4790 case KEYWORD_DECL:
4791 key_name = KEYWORD_KEY_NAME (key_chain);
4792 break;
4793 case TREE_LIST:
4794 key_name = TREE_PURPOSE (key_chain);
4795 /* The keyword decl chain will later be used as a function
4796 argument chain. Unhook the selector itself so as to not
4797 confuse other parts of the compiler. */
4798 TREE_PURPOSE (key_chain) = NULL_TREE;
4799 break;
4800 default:
4801 gcc_unreachable ();
4802 }
4803
4804 if (key_name)
4805 strcat (buf, IDENTIFIER_POINTER (key_name));
4806 strcat (buf, ":");
4807 }
4808
4809 return get_identifier_with_length (buf, len);
4810 }
4811
4812 /* Used for declarations and definitions. */
4813
4814 static tree
build_method_decl(enum tree_code code,tree ret_type,tree selector,tree add_args,bool ellipsis)4815 build_method_decl (enum tree_code code, tree ret_type, tree selector,
4816 tree add_args, bool ellipsis)
4817 {
4818 tree method_decl;
4819
4820 /* If no type is specified, default to "id". */
4821 ret_type = adjust_type_for_id_default (ret_type);
4822
4823 /* Note how a method_decl has a TREE_TYPE which is not the function
4824 type of the function implementing the method, but only the return
4825 type of the method. We may want to change this, and store the
4826 entire function type in there (eg, it may be used to simplify
4827 dealing with attributes below). */
4828 method_decl = make_node (code);
4829 TREE_TYPE (method_decl) = ret_type;
4830
4831 /* If we have a keyword selector, create an identifier_node that
4832 represents the full selector name (`:' included)... */
4833 if (TREE_CODE (selector) == KEYWORD_DECL)
4834 {
4835 METHOD_SEL_NAME (method_decl) = build_keyword_selector (selector);
4836 METHOD_SEL_ARGS (method_decl) = selector;
4837 METHOD_ADD_ARGS (method_decl) = add_args;
4838 METHOD_ADD_ARGS_ELLIPSIS_P (method_decl) = ellipsis;
4839 }
4840 else
4841 {
4842 METHOD_SEL_NAME (method_decl) = selector;
4843 METHOD_SEL_ARGS (method_decl) = NULL_TREE;
4844 METHOD_ADD_ARGS (method_decl) = NULL_TREE;
4845 }
4846
4847 return method_decl;
4848 }
4849
4850 /* This routine processes objective-c method attributes. */
4851
4852 static void
objc_decl_method_attributes(tree * node,tree attributes,int flags)4853 objc_decl_method_attributes (tree *node, tree attributes, int flags)
4854 {
4855 /* TODO: Replace the hackery below. An idea would be to store the
4856 full function type in the method declaration (for example in
4857 TREE_TYPE) and then expose ObjC method declarations to c-family
4858 and they could deal with them by simply treating them as
4859 functions. */
4860
4861 /* Because of the dangers in the hackery below, we filter out any
4862 attribute that we do not know about. For the ones we know about,
4863 we know that they work with the hackery. For the other ones,
4864 there is no guarantee, so we have to filter them out. */
4865 tree filtered_attributes = NULL_TREE;
4866
4867 if (attributes)
4868 {
4869 tree attribute;
4870 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
4871 {
4872 tree name = TREE_PURPOSE (attribute);
4873
4874 if (is_attribute_p ("deprecated", name)
4875 || is_attribute_p ("sentinel", name)
4876 || is_attribute_p ("noreturn", name))
4877 {
4878 /* An attribute that we support; add it to the filtered
4879 attributes. */
4880 filtered_attributes = chainon (filtered_attributes,
4881 copy_node (attribute));
4882 }
4883 else if (is_attribute_p ("format", name))
4884 {
4885 /* "format" is special because before adding it to the
4886 filtered attributes we need to adjust the specified
4887 format by adding the hidden function parameters for
4888 an Objective-C method (self, _cmd). */
4889 tree new_attribute = copy_node (attribute);
4890
4891 /* Check the arguments specified with the attribute, and
4892 modify them adding 2 for the two hidden arguments.
4893 Note how this differs from C++; according to the
4894 specs, C++ does not do it so you have to add the +1
4895 yourself. For Objective-C, instead, the compiler
4896 adds the +2 for you. */
4897
4898 /* The attribute arguments have not been checked yet, so
4899 we need to be careful as they could be missing or
4900 invalid. If anything looks wrong, we skip the
4901 process and the compiler will complain about it later
4902 when it validates the attribute. */
4903 /* Check that we have at least three arguments. */
4904 if (TREE_VALUE (new_attribute)
4905 && TREE_CHAIN (TREE_VALUE (new_attribute))
4906 && TREE_CHAIN (TREE_CHAIN (TREE_VALUE (new_attribute))))
4907 {
4908 tree second_argument = TREE_CHAIN (TREE_VALUE (new_attribute));
4909 tree third_argument = TREE_CHAIN (second_argument);
4910 tree number;
4911
4912 /* This is the second argument, the "string-index",
4913 which specifies the index of the format string
4914 argument. Add 2. */
4915 number = TREE_VALUE (second_argument);
4916 if (number
4917 && TREE_CODE (number) == INTEGER_CST
4918 && wi::to_wide (number) != 0)
4919 TREE_VALUE (second_argument)
4920 = wide_int_to_tree (TREE_TYPE (number),
4921 wi::to_wide (number) + 2);
4922
4923 /* This is the third argument, the "first-to-check",
4924 which specifies the index of the first argument to
4925 check. This could be 0, meaning it is not available,
4926 in which case we don't need to add 2. Add 2 if not
4927 0. */
4928 number = TREE_VALUE (third_argument);
4929 if (number
4930 && TREE_CODE (number) == INTEGER_CST
4931 && wi::to_wide (number) != 0)
4932 TREE_VALUE (third_argument)
4933 = wide_int_to_tree (TREE_TYPE (number),
4934 wi::to_wide (number) + 2);
4935 }
4936 filtered_attributes = chainon (filtered_attributes,
4937 new_attribute);
4938 }
4939 else if (is_attribute_p ("nonnull", name))
4940 {
4941 /* We need to fixup all the argument indexes by adding 2
4942 for the two hidden arguments of an Objective-C method
4943 invocation, similat to what we do above for the
4944 "format" attribute. */
4945 /* FIXME: This works great in terms of implementing the
4946 functionality, but the warnings that are produced by
4947 nonnull do mention the argument index (while the
4948 format ones don't). For example, you could get
4949 "warning: null argument where non-null required
4950 (argument 3)". Now in that message, "argument 3"
4951 includes the 2 hidden arguments; it would be much
4952 more friendly to call it "argument 1", as that would
4953 be consistent with __attribute__ ((nonnnull (1))).
4954 To do this, we'd need to have the C family code that
4955 checks the arguments know about adding/removing 2 to
4956 the argument index ... or alternatively we could
4957 maybe store the "printable" argument index in
4958 addition to the actual argument index ? Some
4959 refactoring is needed to do this elegantly. */
4960 tree new_attribute = copy_node (attribute);
4961 tree argument = TREE_VALUE (attribute);
4962 while (argument != NULL_TREE)
4963 {
4964 /* Get the value of the argument and add 2. */
4965 tree number = TREE_VALUE (argument);
4966 if (number && TREE_CODE (number) == INTEGER_CST
4967 && wi::to_wide (number) != 0)
4968 TREE_VALUE (argument)
4969 = wide_int_to_tree (TREE_TYPE (number),
4970 wi::to_wide (number) + 2);
4971 argument = TREE_CHAIN (argument);
4972 }
4973
4974 filtered_attributes = chainon (filtered_attributes,
4975 new_attribute);
4976 }
4977 else
4978 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
4979 }
4980 }
4981
4982 if (filtered_attributes)
4983 {
4984 /* This hackery changes the TREE_TYPE of the ObjC method
4985 declaration to be a function type, so that decl_attributes
4986 will treat the ObjC method as if it was a function. Some
4987 attributes (sentinel, format) will be applied to the function
4988 type, changing it in place; so after calling decl_attributes,
4989 we extract the function type attributes and store them in
4990 METHOD_TYPE_ATTRIBUTES. Some other attributes (noreturn,
4991 deprecated) are applied directly to the method declaration
4992 (by setting TREE_DEPRECATED and TREE_THIS_VOLATILE) so there
4993 is nothing to do. */
4994 tree saved_type = TREE_TYPE (*node);
4995 TREE_TYPE (*node)
4996 = build_function_type_for_method (TREE_VALUE (saved_type), *node,
4997 METHOD_REF, 0);
4998 decl_attributes (node, filtered_attributes, flags);
4999 METHOD_TYPE_ATTRIBUTES (*node) = TYPE_ATTRIBUTES (TREE_TYPE (*node));
5000 TREE_TYPE (*node) = saved_type;
5001 }
5002 }
5003
5004 bool
objc_method_decl(enum tree_code opcode)5005 objc_method_decl (enum tree_code opcode)
5006 {
5007 return opcode == INSTANCE_METHOD_DECL || opcode == CLASS_METHOD_DECL;
5008 }
5009
5010 /* Return a function type for METHOD with RETURN_TYPE. CONTEXT is
5011 either METHOD_DEF or METHOD_REF, indicating whether we are defining a
5012 method or calling one. SUPER_FLAG indicates whether this is a send
5013 to super; this makes a difference for the NeXT calling sequence in
5014 which the lookup and the method call are done together. If METHOD is
5015 NULL, user-defined arguments (i.e., beyond self and _cmd) shall be
5016 represented as varargs. */
5017
5018 tree
build_function_type_for_method(tree return_type,tree method,int context,bool super_flag)5019 build_function_type_for_method (tree return_type, tree method,
5020 int context, bool super_flag)
5021 {
5022 vec<tree, va_gc> *argtypes = make_tree_vector ();
5023 tree t, ftype;
5024 bool is_varargs = false;
5025
5026 (*runtime.get_arg_type_list_base) (&argtypes, method, context, super_flag);
5027
5028 /* No actual method prototype given; remaining args passed as varargs. */
5029 if (method == NULL_TREE)
5030 {
5031 is_varargs = true;
5032 goto build_ftype;
5033 }
5034
5035 for (t = METHOD_SEL_ARGS (method); t; t = DECL_CHAIN (t))
5036 {
5037 tree arg_type = TREE_VALUE (TREE_TYPE (t));
5038
5039 /* Decay argument types for the underlying C function as
5040 appropriate. */
5041 arg_type = objc_decay_parm_type (arg_type);
5042
5043 vec_safe_push (argtypes, arg_type);
5044 }
5045
5046 if (METHOD_ADD_ARGS (method))
5047 {
5048 for (t = TREE_CHAIN (METHOD_ADD_ARGS (method));
5049 t; t = TREE_CHAIN (t))
5050 {
5051 tree arg_type = TREE_TYPE (TREE_VALUE (t));
5052
5053 arg_type = objc_decay_parm_type (arg_type);
5054
5055 vec_safe_push (argtypes, arg_type);
5056 }
5057
5058 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
5059 is_varargs = true;
5060 }
5061
5062 build_ftype:
5063 if (is_varargs)
5064 ftype = build_varargs_function_type_vec (return_type, argtypes);
5065 else
5066 ftype = build_function_type_vec (return_type, argtypes);
5067
5068 release_tree_vector (argtypes);
5069 return ftype;
5070 }
5071
5072 /* The 'method' argument is a tree; this tree could either be a single
5073 method, which is returned, or could be a TREE_VEC containing a list
5074 of methods. In that case, the first one is returned, and warnings
5075 are issued as appropriate. */
5076 static tree
check_duplicates(tree method,int methods,int is_class)5077 check_duplicates (tree method, int methods, int is_class)
5078 {
5079 tree first_method;
5080 size_t i;
5081
5082 if (method == NULL_TREE)
5083 return NULL_TREE;
5084
5085 if (TREE_CODE (method) != TREE_VEC)
5086 return method;
5087
5088 /* We have two or more methods with the same name but different
5089 types. */
5090 first_method = TREE_VEC_ELT (method, 0);
5091
5092 /* But just how different are those types? If
5093 -Wno-strict-selector-match is specified, we shall not complain if
5094 the differences are solely among types with identical size and
5095 alignment. */
5096 if (!warn_strict_selector_match)
5097 {
5098 for (i = 0; i < (size_t) TREE_VEC_LENGTH (method); i++)
5099 if (!comp_proto_with_proto (first_method, TREE_VEC_ELT (method, i), 0))
5100 goto issue_warning;
5101
5102 return first_method;
5103 }
5104
5105 issue_warning:
5106 if (methods)
5107 {
5108 bool type = TREE_CODE (first_method) == INSTANCE_METHOD_DECL;
5109
5110 warning_at (input_location, 0,
5111 "multiple methods named %<%c%E%> found",
5112 (is_class ? '+' : '-'),
5113 METHOD_SEL_NAME (first_method));
5114 inform (DECL_SOURCE_LOCATION (first_method), "using %<%c%s%>",
5115 (type ? '-' : '+'),
5116 identifier_to_locale (gen_method_decl (first_method)));
5117 }
5118 else
5119 {
5120 bool type = TREE_CODE (first_method) == INSTANCE_METHOD_DECL;
5121
5122 warning_at (input_location, 0,
5123 "multiple selectors named %<%c%E%> found",
5124 (is_class ? '+' : '-'),
5125 METHOD_SEL_NAME (first_method));
5126 inform (DECL_SOURCE_LOCATION (first_method), "found %<%c%s%>",
5127 (type ? '-' : '+'),
5128 identifier_to_locale (gen_method_decl (first_method)));
5129 }
5130
5131 for (i = 0; i < (size_t) TREE_VEC_LENGTH (method); i++)
5132 {
5133 bool type = TREE_CODE (TREE_VEC_ELT (method, i)) == INSTANCE_METHOD_DECL;
5134
5135 inform (DECL_SOURCE_LOCATION (TREE_VEC_ELT (method, i)), "also found %<%c%s%>",
5136 (type ? '-' : '+'),
5137 identifier_to_locale (gen_method_decl (TREE_VEC_ELT (method, i))));
5138 }
5139
5140 return first_method;
5141 }
5142
5143 /* If RECEIVER is a class reference, return the identifier node for
5144 the referenced class. RECEIVER is created by objc_get_class_reference,
5145 so we check the exact form created depending on which runtimes are
5146 used. */
5147
5148 static tree
receiver_is_class_object(tree receiver,int self,int super)5149 receiver_is_class_object (tree receiver, int self, int super)
5150 {
5151 tree exp, arg;
5152
5153 /* The receiver is 'self' or 'super' in the context of a class method. */
5154 if (objc_method_context
5155 && TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
5156 && (self || super))
5157 return (super
5158 ? CLASS_SUPER_NAME (implementation_template)
5159 : CLASS_NAME (implementation_template));
5160
5161 /* The runtime might encapsulate things its own way. */
5162 exp = (*runtime.receiver_is_class_object) (receiver);
5163 if (exp)
5164 return exp;
5165
5166 /* The receiver is a function call that returns an id. Check if
5167 it is a call to objc_getClass, if so, pick up the class name.
5168
5169 This is required by the GNU runtime, which compiles
5170
5171 [NSObject alloc]
5172
5173 into
5174
5175 [objc_get_class ("NSObject") alloc];
5176
5177 and then, to check that the receiver responds to the +alloc
5178 method, needs to be able to determine that the objc_get_class()
5179 call returns the NSObject class and not just a generic Class
5180 pointer.
5181
5182 But, traditionally this is enabled for all runtimes, not just the
5183 GNU one, which means that the compiler is smarter than you'd
5184 expect when dealing with objc_getClass(). For example, with the
5185 Apple runtime, in the code
5186
5187 [objc_getClass ("NSObject") alloc];
5188
5189 the compiler will recognize the objc_getClass() call as special
5190 (due to the code below) and so will know that +alloc is called on
5191 the 'NSObject' class, and can perform the corresponding checks.
5192
5193 Programmers can disable this behavior by casting the results of
5194 objc_getClass() to 'Class' (this may seem weird because
5195 objc_getClass() is already declared to return 'Class', but the
5196 compiler treats it as a special function). This may be useful if
5197 the class is never declared, and the compiler would complain
5198 about a missing @interface for it. Then, you can do
5199
5200 [(Class)objc_getClass ("MyClassNeverDeclared") alloc];
5201
5202 to silence the warnings. */
5203 if (TREE_CODE (receiver) == CALL_EXPR
5204 && (exp = CALL_EXPR_FN (receiver))
5205 && TREE_CODE (exp) == ADDR_EXPR
5206 && (exp = TREE_OPERAND (exp, 0))
5207 && TREE_CODE (exp) == FUNCTION_DECL
5208 /* For some reason, we sometimes wind up with multiple FUNCTION_DECL
5209 prototypes for objc_get_class(). Thankfully, they seem to share the
5210 same function type. */
5211 && TREE_TYPE (exp) == TREE_TYPE (objc_get_class_decl)
5212 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (exp)), runtime.tag_getclass)
5213 /* We have a call to objc_get_class/objc_getClass! */
5214 && (arg = CALL_EXPR_ARG (receiver, 0)))
5215 {
5216 STRIP_NOPS (arg);
5217 if (TREE_CODE (arg) == ADDR_EXPR
5218 && (arg = TREE_OPERAND (arg, 0))
5219 && TREE_CODE (arg) == STRING_CST)
5220 /* Finally, we have the class name. */
5221 return get_identifier (TREE_STRING_POINTER (arg));
5222 }
5223 return 0;
5224 }
5225
5226 /* If we are currently building a message expr, this holds
5227 the identifier of the selector of the message. This is
5228 used when printing warnings about argument mismatches. */
5229
5230 static tree current_objc_message_selector = 0;
5231
5232 tree
objc_message_selector(void)5233 objc_message_selector (void)
5234 {
5235 return current_objc_message_selector;
5236 }
5237
5238 /* Construct an expression for sending a message.
5239 MESS has the object to send to in TREE_PURPOSE
5240 and the argument list (including selector) in TREE_VALUE.
5241
5242 (*(<abstract_decl>(*)())_msg)(receiver, selTransTbl[n], ...);
5243 (*(<abstract_decl>(*)())_msgSuper)(receiver, selTransTbl[n], ...); */
5244
5245 tree
objc_build_message_expr(tree receiver,tree message_args)5246 objc_build_message_expr (tree receiver, tree message_args)
5247 {
5248 tree sel_name;
5249 #ifdef OBJCPLUS
5250 tree args = TREE_PURPOSE (message_args);
5251 #else
5252 tree args = message_args;
5253 #endif
5254 tree method_params = NULL_TREE;
5255
5256 if (TREE_CODE (receiver) == ERROR_MARK || TREE_CODE (args) == ERROR_MARK)
5257 return error_mark_node;
5258
5259 /* Obtain the full selector name. */
5260 switch (TREE_CODE (args))
5261 {
5262 case IDENTIFIER_NODE:
5263 /* A unary selector. */
5264 sel_name = args;
5265 break;
5266 case TREE_LIST:
5267 sel_name = build_keyword_selector (args);
5268 break;
5269 default:
5270 gcc_unreachable ();
5271 }
5272
5273 /* Build the parameter list to give to the method. */
5274 if (TREE_CODE (args) == TREE_LIST)
5275 #ifdef OBJCPLUS
5276 method_params = chainon (args, TREE_VALUE (message_args));
5277 #else
5278 {
5279 tree chain = args, prev = NULL_TREE;
5280
5281 /* We have a keyword selector--check for comma expressions. */
5282 while (chain)
5283 {
5284 tree element = TREE_VALUE (chain);
5285
5286 /* We have a comma expression, must collapse... */
5287 if (TREE_CODE (element) == TREE_LIST)
5288 {
5289 if (prev)
5290 TREE_CHAIN (prev) = element;
5291 else
5292 args = element;
5293 }
5294 prev = chain;
5295 chain = TREE_CHAIN (chain);
5296 }
5297 method_params = args;
5298 }
5299 #endif
5300
5301 #ifdef OBJCPLUS
5302 if (processing_template_decl)
5303 /* Must wait until template instantiation time. */
5304 return build_min_nt_loc (UNKNOWN_LOCATION, MESSAGE_SEND_EXPR, receiver,
5305 sel_name, method_params);
5306 #endif
5307
5308 return objc_finish_message_expr (receiver, sel_name, method_params, NULL);
5309 }
5310
5311 /* Look up method SEL_NAME that would be suitable for receiver
5312 of type 'id' (if IS_CLASS is zero) or 'Class' (if IS_CLASS is
5313 nonzero), and report on any duplicates. */
5314
5315 static tree
lookup_method_in_hash_lists(tree sel_name,int is_class)5316 lookup_method_in_hash_lists (tree sel_name, int is_class)
5317 {
5318 tree method_prototype = OBJC_MAP_NOT_FOUND;
5319
5320 if (!is_class)
5321 method_prototype = objc_map_get (instance_method_map, sel_name);
5322
5323 if (method_prototype == OBJC_MAP_NOT_FOUND)
5324 {
5325 method_prototype = objc_map_get (class_method_map, sel_name);
5326 is_class = 1;
5327
5328 if (method_prototype == OBJC_MAP_NOT_FOUND)
5329 return NULL_TREE;
5330 }
5331
5332 return check_duplicates (method_prototype, 1, is_class);
5333 }
5334
5335 /* The 'objc_finish_message_expr' routine is called from within
5336 'objc_build_message_expr' for non-template functions. In the case of
5337 C++ template functions, it is called from 'build_expr_from_tree'
5338 (in decl2.c) after RECEIVER and METHOD_PARAMS have been expanded.
5339
5340 If the DEPRECATED_METHOD_PROTOTYPE argument is NULL, then we warn
5341 if the method being used is deprecated. If it is not NULL, instead
5342 of deprecating, we set *DEPRECATED_METHOD_PROTOTYPE to the method
5343 prototype that was used and is deprecated. This is useful for
5344 getter calls that are always generated when compiling dot-syntax
5345 expressions, even if they may not be used. In that case, we don't
5346 want the warning immediately; we produce it (if needed) at gimplify
5347 stage when we are sure that the deprecated getter is being
5348 used. */
5349 tree
objc_finish_message_expr(tree receiver,tree sel_name,tree method_params,tree * deprecated_method_prototype)5350 objc_finish_message_expr (tree receiver, tree sel_name, tree method_params,
5351 tree *deprecated_method_prototype)
5352 {
5353 tree method_prototype = NULL_TREE, rprotos = NULL_TREE, rtype;
5354 tree retval, class_tree;
5355 int self, super, have_cast;
5356
5357 STRIP_ANY_LOCATION_WRAPPER (receiver);
5358
5359 /* We have used the receiver, so mark it as read. */
5360 mark_exp_read (receiver);
5361
5362 /* Extract the receiver of the message, as well as its type
5363 (where the latter may take the form of a cast or be inferred
5364 from the implementation context). */
5365 rtype = receiver;
5366 while (TREE_CODE (rtype) == COMPOUND_EXPR
5367 || TREE_CODE (rtype) == MODIFY_EXPR
5368 || CONVERT_EXPR_P (rtype)
5369 || TREE_CODE (rtype) == COMPONENT_REF)
5370 rtype = TREE_OPERAND (rtype, 0);
5371
5372 /* self is 1 if this is a message to self, 0 otherwise */
5373 self = (rtype == self_decl);
5374
5375 /* super is 1 if this is a message to super, 0 otherwise. */
5376 super = (rtype == UOBJC_SUPER_decl);
5377
5378 /* rtype is the type of the receiver. */
5379 rtype = TREE_TYPE (receiver);
5380
5381 /* have_cast is 1 if the receiver is casted. */
5382 have_cast = (TREE_CODE (receiver) == NOP_EXPR
5383 || (TREE_CODE (receiver) == COMPOUND_EXPR
5384 && !IS_SUPER (rtype)));
5385
5386 /* If we are calling [super dealloc], reset our warning flag. */
5387 if (super && !strcmp ("dealloc", IDENTIFIER_POINTER (sel_name)))
5388 should_call_super_dealloc = 0;
5389
5390 /* If the receiver is a class object, retrieve the corresponding
5391 @interface, if one exists. class_tree is the class name
5392 identifier, or NULL_TREE if this is not a class method or the
5393 class name could not be determined (as in the case "Class c; [c
5394 method];"). */
5395 class_tree = receiver_is_class_object (receiver, self, super);
5396
5397 /* Now determine the receiver type (if an explicit cast has not been
5398 provided). */
5399 if (!have_cast)
5400 {
5401 if (class_tree)
5402 {
5403 /* We are here when we have no cast, and we have a class
5404 name. So, this is a plain method to a class object, as
5405 in [NSObject alloc]. Find the interface corresponding to
5406 the class name. */
5407 rtype = lookup_interface (class_tree);
5408
5409 if (rtype == NULL_TREE)
5410 {
5411 /* If 'rtype' is NULL_TREE at this point it means that
5412 we have seen no @interface corresponding to that
5413 class name, only a @class declaration (alternatively,
5414 this was a call such as [objc_getClass("SomeClass")
5415 alloc], where we've never seen the @interface of
5416 SomeClass). So, we have a class name (class_tree)
5417 but no actual details of the class methods. We won't
5418 be able to check that the class responds to the
5419 method, and we will have to guess the method
5420 prototype. Emit a warning, then keep going (this
5421 will use any method with a matching name, as if the
5422 receiver was of type 'Class'). */
5423 warning (0, "%<@interface%> of class %qE not found",
5424 class_tree);
5425 }
5426 }
5427 /* Handle `self' and `super'. */
5428 else if (super)
5429 {
5430 if (!CLASS_SUPER_NAME (implementation_template))
5431 {
5432 error ("no super class declared in @interface for %qE",
5433 CLASS_NAME (implementation_template));
5434 return error_mark_node;
5435 }
5436 rtype = lookup_interface (CLASS_SUPER_NAME (implementation_template));
5437 }
5438 else if (self)
5439 rtype = lookup_interface (CLASS_NAME (implementation_template));
5440 }
5441
5442 if (objc_is_id (rtype))
5443 {
5444 /* The receiver is of type 'id' or 'Class' (with or without some
5445 protocols attached to it). */
5446
5447 /* We set class_tree to the identifier for 'Class' if this is a
5448 class method, and to NULL_TREE if not. */
5449 class_tree = (IS_CLASS (rtype) ? objc_class_name : NULL_TREE);
5450
5451 /* 'rprotos' is the list of protocols that the receiver
5452 supports. */
5453 rprotos = (TYPE_HAS_OBJC_INFO (TREE_TYPE (rtype))
5454 ? TYPE_OBJC_PROTOCOL_LIST (TREE_TYPE (rtype))
5455 : NULL_TREE);
5456
5457 /* We have no information on the type, and we set it to
5458 NULL_TREE. */
5459 rtype = NULL_TREE;
5460
5461 /* If there are any protocols, check that the method we are
5462 calling appears in the protocol list. If there are no
5463 protocols, this is a message to 'id' or 'Class' and we accept
5464 any method that exists. */
5465 if (rprotos)
5466 {
5467 /* If messaging 'id <Protos>' or 'Class <Proto>', first
5468 search in protocols themselves for the method
5469 prototype. */
5470 method_prototype
5471 = lookup_method_in_protocol_list (rprotos, sel_name,
5472 class_tree != NULL_TREE);
5473
5474 /* If messaging 'Class <Proto>' but did not find a class
5475 method prototype, search for an instance method instead,
5476 and warn about having done so. */
5477 if (!method_prototype && !rtype && class_tree != NULL_TREE)
5478 {
5479 method_prototype
5480 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
5481
5482 if (method_prototype)
5483 warning (0, "found %<-%E%> instead of %<+%E%> in protocol(s)",
5484 sel_name, sel_name);
5485 }
5486 }
5487 }
5488 else if (rtype)
5489 {
5490 /* We have a receiver type which is more specific than 'id' or
5491 'Class'. */
5492 tree orig_rtype = rtype;
5493
5494 if (TREE_CODE (rtype) == POINTER_TYPE)
5495 rtype = TREE_TYPE (rtype);
5496 /* Traverse typedef aliases */
5497 while (TREE_CODE (rtype) == RECORD_TYPE && OBJC_TYPE_NAME (rtype)
5498 && TREE_CODE (OBJC_TYPE_NAME (rtype)) == TYPE_DECL
5499 && DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype)))
5500 rtype = DECL_ORIGINAL_TYPE (OBJC_TYPE_NAME (rtype));
5501 if (TYPED_OBJECT (rtype))
5502 {
5503 rprotos = TYPE_OBJC_PROTOCOL_LIST (rtype);
5504 rtype = TYPE_OBJC_INTERFACE (rtype);
5505 }
5506 if (!rtype || TREE_CODE (rtype) == IDENTIFIER_NODE)
5507 {
5508 /* If we could not find an @interface declaration, we must
5509 have only seen a @class declaration; so, we cannot say
5510 anything more intelligent about which methods the
5511 receiver will understand. Note that this only happens
5512 for instance methods; for class methods to a class where
5513 we have only seen a @class declaration,
5514 lookup_interface() above would have set rtype to
5515 NULL_TREE. */
5516 if (rprotos)
5517 {
5518 /* We could not find an @interface declaration, yet, if
5519 there are protocols attached to the type, we can
5520 still look up the method in the protocols. Ie, we
5521 are in the following case:
5522
5523 @class MyClass;
5524 MyClass<MyProtocol> *x;
5525 [x method];
5526
5527 If 'MyProtocol' has the method 'method', we can check
5528 and retrieve the method prototype. */
5529 method_prototype
5530 = lookup_method_in_protocol_list (rprotos, sel_name, 0);
5531
5532 /* At this point, if we have found the method_prototype,
5533 we are quite happy. The details of the class are
5534 irrelevant. If we haven't found it, a warning will
5535 have been produced that the method could not be found
5536 in the protocol, and we won't produce further
5537 warnings (please note that this means that "@class
5538 MyClass; MyClass <MyProtocol> *x;" is exactly
5539 equivalent to "id <MyProtocol> x", which isn't too
5540 satisfactory but it's not easy to see how to do
5541 better). */
5542 }
5543 else
5544 {
5545 if (rtype)
5546 {
5547 /* We could not find an @interface declaration, and
5548 there are no protocols attached to the receiver,
5549 so we can't complete the check that the receiver
5550 responds to the method, and we can't retrieve the
5551 method prototype. But, because the receiver has
5552 a well-specified class, the programmer did want
5553 this check to be performed. Emit a warning, then
5554 keep going as if it was an 'id'. To remove the
5555 warning, either include an @interface for the
5556 class, or cast the receiver to 'id'. Note that
5557 rtype is an IDENTIFIER_NODE at this point. */
5558 warning (0, "%<@interface%> of class %qE not found", rtype);
5559 }
5560 }
5561
5562 rtype = NULL_TREE;
5563 }
5564 else if (TREE_CODE (rtype) == CLASS_INTERFACE_TYPE
5565 || TREE_CODE (rtype) == CLASS_IMPLEMENTATION_TYPE)
5566 {
5567 /* We have a valid ObjC class name with an associated
5568 @interface. Look up the method name in the published
5569 @interface for the class (and its superclasses). */
5570 method_prototype
5571 = lookup_method_static (rtype, sel_name, class_tree != NULL_TREE);
5572
5573 /* If the method was not found in the @interface, it may still
5574 exist locally as part of the @implementation. */
5575 if (!method_prototype && objc_implementation_context
5576 && CLASS_NAME (objc_implementation_context)
5577 == OBJC_TYPE_NAME (rtype))
5578 method_prototype
5579 = lookup_method
5580 ((class_tree
5581 ? CLASS_CLS_METHODS (objc_implementation_context)
5582 : CLASS_NST_METHODS (objc_implementation_context)),
5583 sel_name);
5584
5585 /* If we haven't found a candidate method by now, try looking for
5586 it in the protocol list. */
5587 if (!method_prototype && rprotos)
5588 method_prototype
5589 = lookup_method_in_protocol_list (rprotos, sel_name,
5590 class_tree != NULL_TREE);
5591 }
5592 else
5593 {
5594 /* We have a type, but it's not an Objective-C type (!). */
5595 warning (0, "invalid receiver type %qs",
5596 identifier_to_locale (gen_type_name (orig_rtype)));
5597 /* After issuing the "invalid receiver" warning, perform method
5598 lookup as if we were messaging 'id'. */
5599 rtype = rprotos = NULL_TREE;
5600 }
5601 }
5602 /* Note that rtype could also be NULL_TREE. This happens if we are
5603 messaging a class by name, but the class was only
5604 forward-declared using @class. */
5605
5606 /* For 'id' or 'Class' receivers, search in the global hash table as
5607 a last resort. For all receivers, warn if protocol searches have
5608 failed. */
5609 if (!method_prototype)
5610 {
5611 if (rprotos)
5612 warning (0, "%<%c%E%> not found in protocol(s)",
5613 (class_tree ? '+' : '-'),
5614 sel_name);
5615
5616 if (!rtype)
5617 method_prototype
5618 = lookup_method_in_hash_lists (sel_name, class_tree != NULL_TREE);
5619 }
5620
5621 if (!method_prototype)
5622 {
5623 static bool warn_missing_methods = false;
5624
5625 if (rtype)
5626 warning (0, "%qE may not respond to %<%c%E%>",
5627 OBJC_TYPE_NAME (rtype),
5628 (class_tree ? '+' : '-'),
5629 sel_name);
5630 /* If we are messaging an 'id' or 'Class' object and made it here,
5631 then we have failed to find _any_ instance or class method,
5632 respectively. */
5633 else
5634 warning (0, "no %<%c%E%> method found",
5635 (class_tree ? '+' : '-'),
5636 sel_name);
5637
5638 if (!warn_missing_methods)
5639 {
5640 warning_at (input_location,
5641 0, "(messages without a matching method signature "
5642 "will be assumed to return %<id%> and accept "
5643 "%<...%> as arguments)");
5644 warn_missing_methods = true;
5645 }
5646 }
5647 else
5648 {
5649 /* Warn if the method is deprecated, but not if the receiver is
5650 a generic 'id'. 'id' is used to cast an object to a generic
5651 object of an unspecified class; in that case, we'll use
5652 whatever method prototype we can find to get the method
5653 argument and return types, but it is not appropriate to
5654 produce deprecation warnings since we don't know the class
5655 that the object will be of at runtime. The @interface(s) for
5656 that class may not even be available to the compiler right
5657 now, and it is perfectly possible that the method is marked
5658 as non-deprecated in such @interface(s).
5659
5660 In practice this makes sense since casting an object to 'id'
5661 is often used precisely to turn off warnings associated with
5662 the object being of a particular class. */
5663 if (TREE_DEPRECATED (method_prototype) && rtype != NULL_TREE)
5664 {
5665 if (deprecated_method_prototype)
5666 *deprecated_method_prototype = method_prototype;
5667 else
5668 warn_deprecated_use (method_prototype, NULL_TREE);
5669 }
5670 }
5671
5672 /* Save the selector name for printing error messages. */
5673 current_objc_message_selector = sel_name;
5674
5675 /* Build the method call.
5676 TODO: Get the location from somewhere that will work for delayed
5677 expansion. */
5678
5679 retval = (*runtime.build_objc_method_call) (input_location, method_prototype,
5680 receiver, rtype, sel_name,
5681 method_params, super);
5682
5683 current_objc_message_selector = 0;
5684
5685 return retval;
5686 }
5687
5688
5689 /* This routine creates a static variable used to implement @protocol(MyProtocol)
5690 expression. This variable will be initialized to global protocol_t meta-data
5691 pointer. */
5692
5693 /* This function is called by the parser when (and only when) a
5694 @protocol() expression is found, in order to compile it. */
5695 tree
objc_build_protocol_expr(tree protoname)5696 objc_build_protocol_expr (tree protoname)
5697 {
5698 tree p = lookup_protocol (protoname, /* warn if deprecated */ true,
5699 /* definition_required */ false);
5700
5701 if (!p)
5702 {
5703 error ("cannot find protocol declaration for %qE", protoname);
5704 return error_mark_node;
5705 }
5706
5707 return (*runtime.get_protocol_reference) (input_location, p);
5708 }
5709
5710 /* This function is called by the parser when a @selector() expression
5711 is found, in order to compile it. It is only called by the parser
5712 and only to compile a @selector(). LOC is the location of the
5713 @selector. */
5714 tree
objc_build_selector_expr(location_t loc,tree selnamelist)5715 objc_build_selector_expr (location_t loc, tree selnamelist)
5716 {
5717 tree selname;
5718
5719 /* Obtain the full selector name. */
5720 switch (TREE_CODE (selnamelist))
5721 {
5722 case IDENTIFIER_NODE:
5723 /* A unary selector. */
5724 selname = selnamelist;
5725 break;
5726 case TREE_LIST:
5727 selname = build_keyword_selector (selnamelist);
5728 break;
5729 default:
5730 gcc_unreachable ();
5731 }
5732
5733 /* If we are required to check @selector() expressions as they
5734 are found, check that the selector has been declared. */
5735 if (warn_undeclared_selector)
5736 {
5737 /* Look the selector up in the list of all known class and
5738 instance methods (up to this line) to check that the selector
5739 exists. */
5740 tree method;
5741
5742 /* First try with instance methods. */
5743 method = objc_map_get (instance_method_map, selname);
5744
5745 /* If not found, try with class methods. */
5746 if (method == OBJC_MAP_NOT_FOUND)
5747 {
5748 method = objc_map_get (class_method_map, selname);
5749
5750 /* If still not found, print out a warning. */
5751 if (method == OBJC_MAP_NOT_FOUND)
5752 warning (0, "undeclared selector %qE", selname);
5753 }
5754 }
5755
5756 /* The runtimes do this differently, most particularly, GNU has typed
5757 selectors, whilst NeXT does not. */
5758 return (*runtime.build_selector_reference) (loc, selname, NULL_TREE);
5759 }
5760
5761 static tree
build_ivar_reference(tree id)5762 build_ivar_reference (tree id)
5763 {
5764 tree base;
5765 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL)
5766 {
5767 /* Historically, a class method that produced objects (factory
5768 method) would assign `self' to the instance that it
5769 allocated. This would effectively turn the class method into
5770 an instance method. Following this assignment, the instance
5771 variables could be accessed. That practice, while safe,
5772 violates the simple rule that a class method should not refer
5773 to an instance variable. It's better to catch the cases
5774 where this is done unknowingly than to support the above
5775 paradigm. */
5776 warning (0, "instance variable %qE accessed in class method",
5777 id);
5778 self_decl = convert (objc_instance_type, self_decl); /* cast */
5779 }
5780
5781 base = build_indirect_ref (input_location, self_decl, RO_ARROW);
5782 return (*runtime.build_ivar_reference) (input_location, base, id);
5783 }
5784
5785 static void
hash_init(void)5786 hash_init (void)
5787 {
5788 instance_method_map = objc_map_alloc_ggc (1000);
5789 class_method_map = objc_map_alloc_ggc (1000);
5790
5791 class_name_map = objc_map_alloc_ggc (200);
5792 alias_name_map = objc_map_alloc_ggc (200);
5793
5794 /* Initialize the hash table used to hold the constant string objects. */
5795 string_htab = hash_table<objc_string_hasher>::create_ggc (31);
5796 }
5797
5798 /* Use the following to add a method to class_method_map or
5799 instance_method_map. It will add the method, keyed by the
5800 METHOD_SEL_NAME. If the method already exists, but with one or
5801 more different prototypes, it will store a TREE_VEC in the map,
5802 with the method prototypes in the vector. */
5803 static void
insert_method_into_method_map(bool class_method,tree method)5804 insert_method_into_method_map (bool class_method, tree method)
5805 {
5806 tree method_name = METHOD_SEL_NAME (method);
5807 tree existing_entry;
5808 objc_map_t map;
5809
5810 if (class_method)
5811 map = class_method_map;
5812 else
5813 map = instance_method_map;
5814
5815 /* Check if the method already exists in the map. */
5816 existing_entry = objc_map_get (map, method_name);
5817
5818 /* If not, we simply add it to the map. */
5819 if (existing_entry == OBJC_MAP_NOT_FOUND)
5820 objc_map_put (map, method_name, method);
5821 else
5822 {
5823 tree new_entry;
5824
5825 /* If an entry already exists, it's more complicated. We'll
5826 have to check whether the method prototype is the same or
5827 not. */
5828 if (TREE_CODE (existing_entry) != TREE_VEC)
5829 {
5830 /* If the method prototypes are the same, there is nothing
5831 to do. */
5832 if (comp_proto_with_proto (method, existing_entry, 1))
5833 return;
5834
5835 /* If not, create a vector to store both the method already
5836 in the map, and the new one that we are adding. */
5837 new_entry = make_tree_vec (2);
5838
5839 TREE_VEC_ELT (new_entry, 0) = existing_entry;
5840 TREE_VEC_ELT (new_entry, 1) = method;
5841 }
5842 else
5843 {
5844 /* An entry already exists, and it's already a vector. This
5845 means that at least 2 different method prototypes were
5846 already found, and we're considering registering yet
5847 another one. */
5848 size_t i;
5849
5850 /* Check all the existing prototypes. If any matches the
5851 one we need to add, there is nothing to do because it's
5852 already there. */
5853 for (i = 0; i < (size_t) TREE_VEC_LENGTH (existing_entry); i++)
5854 if (comp_proto_with_proto (method, TREE_VEC_ELT (existing_entry, i), 1))
5855 return;
5856
5857 /* Else, create a new, bigger vector and add the new method
5858 at the end of it. This is inefficient but extremely
5859 rare; in any sane program most methods have a single
5860 prototype, and very few, if any, will have more than
5861 2! */
5862 new_entry = make_tree_vec (TREE_VEC_LENGTH (existing_entry) + 1);
5863
5864 /* Copy the methods from the existing vector. */
5865 for (i = 0; i < (size_t) TREE_VEC_LENGTH (existing_entry); i++)
5866 TREE_VEC_ELT (new_entry, i) = TREE_VEC_ELT (existing_entry, i);
5867
5868 /* Add the new method at the end. */
5869 TREE_VEC_ELT (new_entry, i) = method;
5870 }
5871
5872 /* Store the new vector in the map. */
5873 objc_map_put (map, method_name, new_entry);
5874 }
5875 }
5876
5877
5878 static tree
lookup_method(tree mchain,tree method)5879 lookup_method (tree mchain, tree method)
5880 {
5881 tree key;
5882
5883 if (TREE_CODE (method) == IDENTIFIER_NODE)
5884 key = method;
5885 else
5886 key = METHOD_SEL_NAME (method);
5887
5888 while (mchain)
5889 {
5890 if (METHOD_SEL_NAME (mchain) == key)
5891 return mchain;
5892
5893 mchain = DECL_CHAIN (mchain);
5894 }
5895 return NULL_TREE;
5896 }
5897
5898 /* Look up a class (if OBJC_LOOKUP_CLASS is set in FLAGS) or instance
5899 method in INTERFACE, along with any categories and protocols
5900 attached thereto. If method is not found, and the
5901 OBJC_LOOKUP_NO_SUPER is _not_ set in FLAGS, recursively examine the
5902 INTERFACE's superclass. If OBJC_LOOKUP_CLASS is set,
5903 OBJC_LOOKUP_NO_SUPER is clear, and no suitable class method could
5904 be found in INTERFACE or any of its superclasses, look for an
5905 _instance_ method of the same name in the root class as a last
5906 resort. This behavior can be turned off by using
5907 OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS.
5908
5909 If a suitable method cannot be found, return NULL_TREE. */
5910
5911 static tree
lookup_method_static(tree interface,tree ident,int flags)5912 lookup_method_static (tree interface, tree ident, int flags)
5913 {
5914 tree meth = NULL_TREE, root_inter = NULL_TREE;
5915 tree inter = interface;
5916 int is_class = (flags & OBJC_LOOKUP_CLASS);
5917 int no_superclasses = (flags & OBJC_LOOKUP_NO_SUPER);
5918 int no_instance_methods_of_root_class = (flags & OBJC_LOOKUP_NO_INSTANCE_METHODS_OF_ROOT_CLASS);
5919
5920 while (inter)
5921 {
5922 tree chain = is_class ? CLASS_CLS_METHODS (inter) : CLASS_NST_METHODS (inter);
5923 tree category = inter;
5924
5925 /* First, look up the method in the class itself. */
5926 if ((meth = lookup_method (chain, ident)))
5927 return meth;
5928
5929 /* Failing that, look for the method in each category of the class. */
5930 while ((category = CLASS_CATEGORY_LIST (category)))
5931 {
5932 chain = is_class ? CLASS_CLS_METHODS (category) : CLASS_NST_METHODS (category);
5933
5934 /* Check directly in each category. */
5935 if ((meth = lookup_method (chain, ident)))
5936 return meth;
5937
5938 /* Failing that, check in each category's protocols. */
5939 if (CLASS_PROTOCOL_LIST (category))
5940 {
5941 if ((meth = (lookup_method_in_protocol_list
5942 (CLASS_PROTOCOL_LIST (category), ident, is_class))))
5943 return meth;
5944 }
5945 }
5946
5947 /* If not found in categories, check in protocols of the main class. */
5948 if (CLASS_PROTOCOL_LIST (inter))
5949 {
5950 if ((meth = (lookup_method_in_protocol_list
5951 (CLASS_PROTOCOL_LIST (inter), ident, is_class))))
5952 return meth;
5953 }
5954
5955 /* If we were instructed not to look in superclasses, don't. */
5956 if (no_superclasses)
5957 return NULL_TREE;
5958
5959 /* Failing that, climb up the inheritance hierarchy. */
5960 root_inter = inter;
5961 inter = lookup_interface (CLASS_SUPER_NAME (inter));
5962 }
5963 while (inter);
5964
5965 if (is_class && !no_instance_methods_of_root_class)
5966 {
5967 /* If no class (factory) method was found, check if an _instance_
5968 method of the same name exists in the root class. This is what
5969 the Objective-C runtime will do. */
5970 return lookup_method_static (root_inter, ident, 0);
5971 }
5972 else
5973 {
5974 /* If an instance method was not found, return 0. */
5975 return NULL_TREE;
5976 }
5977 }
5978
5979 static tree
objc_add_method(tree klass,tree method,int is_class,bool is_optional)5980 objc_add_method (tree klass, tree method, int is_class, bool is_optional)
5981 {
5982 tree existing_method = NULL_TREE;
5983
5984 /* The first thing we do is look up the method in the list of
5985 methods already defined in the interface (or implementation). */
5986 if (is_class)
5987 existing_method = lookup_method (CLASS_CLS_METHODS (klass), method);
5988 else
5989 existing_method = lookup_method (CLASS_NST_METHODS (klass), method);
5990
5991 /* In the case of protocols, we have a second list of methods to
5992 consider, the list of optional ones. */
5993 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE)
5994 {
5995 /* @required methods are added to the protocol's normal list.
5996 @optional methods are added to the protocol's OPTIONAL lists.
5997 Note that adding the methods to the optional lists disables
5998 checking that the methods are implemented by classes
5999 implementing the protocol, since these checks only use the
6000 CLASS_CLS_METHODS and CLASS_NST_METHODS. */
6001
6002 /* First of all, if the method to add is @optional, and we found
6003 it already existing as @required, emit an error. */
6004 if (is_optional && existing_method)
6005 {
6006 error ("method %<%c%E%> declared %<@optional%> and %<@required%> at the same time",
6007 (is_class ? '+' : '-'),
6008 METHOD_SEL_NAME (existing_method));
6009 inform (DECL_SOURCE_LOCATION (existing_method),
6010 "previous declaration of %<%c%E%> as %<@required%>",
6011 (is_class ? '+' : '-'),
6012 METHOD_SEL_NAME (existing_method));
6013 }
6014
6015 /* Now check the list of @optional methods if we didn't find the
6016 method in the @required list. */
6017 if (!existing_method)
6018 {
6019 if (is_class)
6020 existing_method = lookup_method (PROTOCOL_OPTIONAL_CLS_METHODS (klass), method);
6021 else
6022 existing_method = lookup_method (PROTOCOL_OPTIONAL_NST_METHODS (klass), method);
6023
6024 if (!is_optional && existing_method)
6025 {
6026 error ("method %<%c%E%> declared %<@optional%> and %<@required%> at the same time",
6027 (is_class ? '+' : '-'),
6028 METHOD_SEL_NAME (existing_method));
6029 inform (DECL_SOURCE_LOCATION (existing_method),
6030 "previous declaration of %<%c%E%> as %<@optional%>",
6031 (is_class ? '+' : '-'),
6032 METHOD_SEL_NAME (existing_method));
6033 }
6034 }
6035 }
6036
6037 /* If the method didn't exist already, add it. */
6038 if (!existing_method)
6039 {
6040 if (is_optional)
6041 {
6042 if (is_class)
6043 {
6044 /* Put the method on the list in reverse order. */
6045 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_CLS_METHODS (klass);
6046 PROTOCOL_OPTIONAL_CLS_METHODS (klass) = method;
6047 }
6048 else
6049 {
6050 TREE_CHAIN (method) = PROTOCOL_OPTIONAL_NST_METHODS (klass);
6051 PROTOCOL_OPTIONAL_NST_METHODS (klass) = method;
6052 }
6053 }
6054 else
6055 {
6056 if (is_class)
6057 {
6058 DECL_CHAIN (method) = CLASS_CLS_METHODS (klass);
6059 CLASS_CLS_METHODS (klass) = method;
6060 }
6061 else
6062 {
6063 DECL_CHAIN (method) = CLASS_NST_METHODS (klass);
6064 CLASS_NST_METHODS (klass) = method;
6065 }
6066 }
6067 }
6068 else
6069 {
6070 /* The method was already defined. Check that the types match
6071 for an @interface for a class or category, or for a
6072 @protocol. Give hard errors on methods with identical
6073 selectors but differing argument and/or return types. We do
6074 not do this for @implementations, because C/C++ will do it
6075 for us (i.e., there will be duplicate function definition
6076 errors). */
6077 if ((TREE_CODE (klass) == CLASS_INTERFACE_TYPE
6078 || TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
6079 /* Starting with GCC 4.6, we emit the same error for
6080 protocols too. The situation is identical to
6081 @interfaces as there is no possible meaningful reason
6082 for defining the same method with different signatures
6083 in the very same @protocol. If that was allowed,
6084 whenever the protocol is used (both at compile and run
6085 time) there wouldn't be any meaningful way to decide
6086 which of the two method signatures should be used. */
6087 || TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE)
6088 && !comp_proto_with_proto (method, existing_method, 1))
6089 {
6090 error ("duplicate declaration of method %<%c%E%> with conflicting types",
6091 (is_class ? '+' : '-'),
6092 METHOD_SEL_NAME (existing_method));
6093 inform (DECL_SOURCE_LOCATION (existing_method),
6094 "previous declaration of %<%c%E%>",
6095 (is_class ? '+' : '-'),
6096 METHOD_SEL_NAME (existing_method));
6097 }
6098 }
6099
6100 if (is_class)
6101 insert_method_into_method_map (true, method);
6102 else
6103 {
6104 insert_method_into_method_map (false, method);
6105
6106 /* Instance methods in root classes (and categories thereof)
6107 may act as class methods as a last resort. We also add
6108 instance methods listed in @protocol declarations to
6109 the class hash table, on the assumption that @protocols
6110 may be adopted by root classes or categories. */
6111 if (TREE_CODE (klass) == CATEGORY_INTERFACE_TYPE
6112 || TREE_CODE (klass) == CATEGORY_IMPLEMENTATION_TYPE)
6113 klass = lookup_interface (CLASS_NAME (klass));
6114
6115 if (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE
6116 || !CLASS_SUPER_NAME (klass))
6117 insert_method_into_method_map (true, method);
6118 }
6119
6120 return method;
6121 }
6122
6123 static void
add_category(tree klass,tree category)6124 add_category (tree klass, tree category)
6125 {
6126 /* Put categories on list in reverse order. */
6127 tree cat = lookup_category (klass, CLASS_SUPER_NAME (category));
6128
6129 if (cat)
6130 {
6131 warning (0, "duplicate interface declaration for category %<%E(%E)%>",
6132 CLASS_NAME (klass),
6133 CLASS_SUPER_NAME (category));
6134 }
6135 else
6136 {
6137 CLASS_CATEGORY_LIST (category) = CLASS_CATEGORY_LIST (klass);
6138 CLASS_CATEGORY_LIST (klass) = category;
6139 }
6140 }
6141
6142 #ifndef OBJCPLUS
6143 /* A flexible array member is a C99 extension where you can use
6144 "type[]" at the end of a struct to mean a variable-length array.
6145
6146 In Objective-C, instance variables are fundamentally members of a
6147 struct, but the struct can always be extended by subclassing; hence
6148 we need to detect and forbid all instance variables declared using
6149 flexible array members.
6150
6151 No check for this is needed in Objective-C++, since C++ does not
6152 have flexible array members. */
6153
6154 /* Determine whether TYPE is a structure with a flexible array member,
6155 a union containing such a structure (possibly recursively) or an
6156 array of such structures or unions. These are all invalid as
6157 instance variable. */
6158 static bool
flexible_array_type_p(tree type)6159 flexible_array_type_p (tree type)
6160 {
6161 tree x;
6162 switch (TREE_CODE (type))
6163 {
6164 case RECORD_TYPE:
6165 x = TYPE_FIELDS (type);
6166 if (x == NULL_TREE)
6167 return false;
6168 while (DECL_CHAIN (x) != NULL_TREE)
6169 x = DECL_CHAIN (x);
6170 if (TREE_CODE (TREE_TYPE (x)) == ARRAY_TYPE
6171 && TYPE_SIZE (TREE_TYPE (x)) == NULL_TREE
6172 && TYPE_DOMAIN (TREE_TYPE (x)) != NULL_TREE
6173 && TYPE_MAX_VALUE (TYPE_DOMAIN (TREE_TYPE (x))) == NULL_TREE)
6174 return true;
6175 return false;
6176 case UNION_TYPE:
6177 for (x = TYPE_FIELDS (type); x != NULL_TREE; x = DECL_CHAIN (x))
6178 {
6179 if (flexible_array_type_p (TREE_TYPE (x)))
6180 return true;
6181 }
6182 return false;
6183 /* Note that we also check for arrays of something that uses a flexible array member. */
6184 case ARRAY_TYPE:
6185 if (flexible_array_type_p (TREE_TYPE (type)))
6186 return true;
6187 return false;
6188 default:
6189 return false;
6190 }
6191 }
6192 #endif
6193
6194 /* Produce a printable version of an ivar name. This is only used
6195 inside add_instance_variable. */
6196 static const char *
printable_ivar_name(tree field_decl)6197 printable_ivar_name (tree field_decl)
6198 {
6199 if (DECL_NAME (field_decl))
6200 return identifier_to_locale (IDENTIFIER_POINTER (DECL_NAME (field_decl)));
6201 else
6202 return _("<unnamed>");
6203 }
6204
6205 /* Called after parsing each instance variable declaration. Necessary to
6206 preserve typedefs and implement public/private...
6207
6208 VISIBILITY is 1 for public, 0 for protected, and 2 for private. */
6209
6210 static tree
add_instance_variable(tree klass,objc_ivar_visibility_kind visibility,tree field_decl)6211 add_instance_variable (tree klass, objc_ivar_visibility_kind visibility,
6212 tree field_decl)
6213 {
6214 tree field_type = TREE_TYPE (field_decl);
6215
6216 #ifdef OBJCPLUS
6217 if (TREE_CODE (field_type) == REFERENCE_TYPE)
6218 {
6219 error ("illegal reference type specified for instance variable %qs",
6220 printable_ivar_name (field_decl));
6221 /* Return class as is without adding this ivar. */
6222 return klass;
6223 }
6224 #endif
6225
6226 if (field_type == error_mark_node || !TYPE_SIZE (field_type)
6227 || TYPE_SIZE (field_type) == error_mark_node)
6228 /* 'type[0]' is allowed, but 'type[]' is not! */
6229 {
6230 error ("instance variable %qs has unknown size",
6231 printable_ivar_name (field_decl));
6232 /* Return class as is without adding this ivar. */
6233 return klass;
6234 }
6235
6236 #ifndef OBJCPLUS
6237 /* Also, in C reject a struct with a flexible array member. Ie,
6238
6239 struct A { int x; int[] y; };
6240
6241 @interface X
6242 {
6243 struct A instance_variable;
6244 }
6245 @end
6246
6247 is not valid because if the class is subclassed, we wouldn't be able
6248 to calculate the offset of the next instance variable. */
6249 if (flexible_array_type_p (field_type))
6250 {
6251 error ("instance variable %qs uses flexible array member",
6252 printable_ivar_name (field_decl));
6253 /* Return class as is without adding this ivar. */
6254 return klass;
6255 }
6256 #endif
6257
6258 #ifdef OBJCPLUS
6259 /* Check if the ivar being added has a non-POD C++ type. If so, we will
6260 need to either (1) warn the user about it or (2) generate suitable
6261 constructor/destructor call from '- .cxx_construct' or '- .cxx_destruct'
6262 methods (if '-fobjc-call-cxx-cdtors' was specified). */
6263 if (MAYBE_CLASS_TYPE_P (field_type)
6264 && (TYPE_NEEDS_CONSTRUCTING (field_type)
6265 || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type)
6266 || TYPE_POLYMORPHIC_P (field_type)))
6267 {
6268 tree type_name = OBJC_TYPE_NAME (field_type);
6269
6270 if (flag_objc_call_cxx_cdtors)
6271 {
6272 /* Since the ObjC runtime will be calling the constructors and
6273 destructors for us, the only thing we can't handle is the lack
6274 of a default constructor. */
6275 if (TYPE_NEEDS_CONSTRUCTING (field_type)
6276 && !TYPE_HAS_DEFAULT_CONSTRUCTOR (field_type))
6277 {
6278 warning (0, "type %qE has no default constructor to call",
6279 type_name);
6280
6281 /* If we cannot call a constructor, we should also avoid
6282 calling the destructor, for symmetry. */
6283 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
6284 warning (0, "destructor for %qE shall not be run either",
6285 type_name);
6286 }
6287 }
6288 else
6289 {
6290 static bool warn_cxx_ivars = false;
6291
6292 if (TYPE_POLYMORPHIC_P (field_type))
6293 {
6294 /* Vtable pointers are Real Bad(tm), since Obj-C cannot
6295 initialize them. */
6296 error ("type %qE has virtual member functions", type_name);
6297 error ("illegal aggregate type %qE specified "
6298 "for instance variable %qs",
6299 type_name, printable_ivar_name (field_decl));
6300 /* Return class as is without adding this ivar. */
6301 return klass;
6302 }
6303
6304 /* User-defined constructors and destructors are not known to Obj-C
6305 and hence will not be called. This may or may not be a problem. */
6306 if (TYPE_NEEDS_CONSTRUCTING (field_type))
6307 warning (0, "type %qE has a user-defined constructor", type_name);
6308 if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (field_type))
6309 warning (0, "type %qE has a user-defined destructor", type_name);
6310
6311 if (!warn_cxx_ivars)
6312 {
6313 warning (0, "C++ constructors and destructors will not "
6314 "be invoked for Objective-C fields");
6315 warn_cxx_ivars = true;
6316 }
6317 }
6318 }
6319 #endif
6320
6321 /* Overload the public attribute, it is not used for FIELD_DECLs. */
6322 switch (visibility)
6323 {
6324 case OBJC_IVAR_VIS_PROTECTED:
6325 TREE_PUBLIC (field_decl) = 0;
6326 TREE_PRIVATE (field_decl) = 0;
6327 TREE_PROTECTED (field_decl) = 1;
6328 break;
6329
6330 case OBJC_IVAR_VIS_PACKAGE:
6331 /* TODO: Implement the package variant. */
6332 case OBJC_IVAR_VIS_PUBLIC:
6333 TREE_PUBLIC (field_decl) = 1;
6334 TREE_PRIVATE (field_decl) = 0;
6335 TREE_PROTECTED (field_decl) = 0;
6336 break;
6337
6338 case OBJC_IVAR_VIS_PRIVATE:
6339 TREE_PUBLIC (field_decl) = 0;
6340 TREE_PRIVATE (field_decl) = 1;
6341 TREE_PROTECTED (field_decl) = 0;
6342 break;
6343
6344 }
6345
6346 CLASS_RAW_IVARS (klass) = chainon (CLASS_RAW_IVARS (klass), field_decl);
6347
6348 return klass;
6349 }
6350
6351 /* True if the ivar is private and we are not in its implementation. */
6352
6353 static int
is_private(tree decl)6354 is_private (tree decl)
6355 {
6356 return (TREE_PRIVATE (decl)
6357 && ! is_ivar (CLASS_IVARS (implementation_template),
6358 DECL_NAME (decl)));
6359 }
6360
6361 /* Searches all the instance variables of 'klass' and of its
6362 superclasses for an instance variable whose name (identifier) is
6363 'ivar_name_ident'. Return the declaration (DECL) of the instance
6364 variable, if found, or NULL_TREE, if not found. */
6365 static inline tree
ivar_of_class(tree klass,tree ivar_name_ident)6366 ivar_of_class (tree klass, tree ivar_name_ident)
6367 {
6368 /* First, look up the ivar in CLASS_RAW_IVARS. */
6369 tree decl_chain = CLASS_RAW_IVARS (klass);
6370
6371 for ( ; decl_chain; decl_chain = DECL_CHAIN (decl_chain))
6372 if (DECL_NAME (decl_chain) == ivar_name_ident)
6373 return decl_chain;
6374
6375 /* If not found, search up the class hierarchy. */
6376 while (CLASS_SUPER_NAME (klass))
6377 {
6378 klass = lookup_interface (CLASS_SUPER_NAME (klass));
6379
6380 decl_chain = CLASS_RAW_IVARS (klass);
6381
6382 for ( ; decl_chain; decl_chain = DECL_CHAIN (decl_chain))
6383 if (DECL_NAME (decl_chain) == ivar_name_ident)
6384 return decl_chain;
6385 }
6386
6387 return NULL_TREE;
6388 }
6389
6390 /* We have an instance variable reference;, check to see if it is public. */
6391
6392 int
objc_is_public(tree expr,tree identifier)6393 objc_is_public (tree expr, tree identifier)
6394 {
6395 tree basetype, decl;
6396
6397 #ifdef OBJCPLUS
6398 if (processing_template_decl)
6399 return 1;
6400 #endif
6401
6402 if (TREE_TYPE (expr) == error_mark_node)
6403 return 1;
6404
6405 basetype = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
6406
6407 if (basetype && TREE_CODE (basetype) == RECORD_TYPE)
6408 {
6409 if (TYPE_HAS_OBJC_INFO (basetype) && TYPE_OBJC_INTERFACE (basetype))
6410 {
6411 tree klass = lookup_interface (OBJC_TYPE_NAME (basetype));
6412
6413 if (!klass)
6414 {
6415 error ("cannot find interface declaration for %qE",
6416 OBJC_TYPE_NAME (basetype));
6417 return 0;
6418 }
6419
6420 if ((decl = ivar_of_class (klass, identifier)))
6421 {
6422 if (TREE_PUBLIC (decl))
6423 return 1;
6424
6425 /* Important difference between the Stepstone translator:
6426 all instance variables should be public within the context
6427 of the implementation. */
6428 if (objc_implementation_context
6429 && ((TREE_CODE (objc_implementation_context)
6430 == CLASS_IMPLEMENTATION_TYPE)
6431 || (TREE_CODE (objc_implementation_context)
6432 == CATEGORY_IMPLEMENTATION_TYPE)))
6433 {
6434 tree curtype = TYPE_MAIN_VARIANT
6435 (CLASS_STATIC_TEMPLATE
6436 (implementation_template));
6437
6438 if (basetype == curtype
6439 || DERIVED_FROM_P (basetype, curtype))
6440 {
6441 int priv = is_private (decl);
6442
6443 if (priv)
6444 error ("instance variable %qE is declared private",
6445 DECL_NAME (decl));
6446
6447 return !priv;
6448 }
6449 }
6450
6451 /* The 2.95.2 compiler sometimes allowed C functions to access
6452 non-@public ivars. We will let this slide for now... */
6453 if (!objc_method_context)
6454 {
6455 warning (0, "instance variable %qE is %s; "
6456 "this will be a hard error in the future",
6457 identifier,
6458 TREE_PRIVATE (decl) ? "@private" : "@protected");
6459 return 1;
6460 }
6461
6462 error ("instance variable %qE is declared %s",
6463 identifier,
6464 TREE_PRIVATE (decl) ? "private" : "protected");
6465 return 0;
6466 }
6467 }
6468 }
6469
6470 return 1;
6471 }
6472
6473 /* Make sure all methods in CHAIN (a list of method declarations from
6474 an @interface or a @protocol) are in IMPLEMENTATION (the
6475 implementation context). This is used to check for example that
6476 all methods declared in an @interface were implemented in an
6477 @implementation.
6478
6479 Some special methods (property setters/getters) are special and if
6480 they are not found in IMPLEMENTATION, we look them up in its
6481 superclasses. */
6482
6483 static int
check_methods(tree chain,tree implementation,int mtype)6484 check_methods (tree chain, tree implementation, int mtype)
6485 {
6486 int first = 1;
6487 tree list;
6488
6489 if (mtype == (int)'+')
6490 list = CLASS_CLS_METHODS (implementation);
6491 else
6492 list = CLASS_NST_METHODS (implementation);
6493
6494 while (chain)
6495 {
6496 /* If the method is associated with a dynamic property, then it
6497 is Ok not to have the method implementation, as it will be
6498 generated dynamically at runtime. To decide if the method is
6499 associated with a @dynamic property, we search the list of
6500 @synthesize and @dynamic for this implementation, and look
6501 for any @dynamic property with the same setter or getter name
6502 as this method. */
6503 tree x;
6504 for (x = IMPL_PROPERTY_DECL (implementation); x; x = TREE_CHAIN (x))
6505 if (PROPERTY_DYNAMIC (x)
6506 && (PROPERTY_GETTER_NAME (x) == METHOD_SEL_NAME (chain)
6507 || PROPERTY_SETTER_NAME (x) == METHOD_SEL_NAME (chain)))
6508 break;
6509
6510 if (x != NULL_TREE)
6511 {
6512 chain = TREE_CHAIN (chain); /* next method... */
6513 continue;
6514 }
6515
6516 if (!lookup_method (list, chain))
6517 {
6518 /* If the method is a property setter/getter, we'll still
6519 allow it to be missing if it is implemented by
6520 'interface' or any of its superclasses. */
6521 tree property = METHOD_PROPERTY_CONTEXT (chain);
6522 if (property)
6523 {
6524 /* Note that since this is a property getter/setter, it
6525 is obviously an instance method. */
6526 tree interface = NULL_TREE;
6527
6528 /* For a category, first check the main class
6529 @interface. */
6530 if (TREE_CODE (implementation) == CATEGORY_IMPLEMENTATION_TYPE)
6531 {
6532 interface = lookup_interface (CLASS_NAME (implementation));
6533
6534 /* If the method is found in the main class, it's Ok. */
6535 if (lookup_method (CLASS_NST_METHODS (interface), chain))
6536 {
6537 chain = DECL_CHAIN (chain);
6538 continue;
6539 }
6540
6541 /* Else, get the superclass. */
6542 if (CLASS_SUPER_NAME (interface))
6543 interface = lookup_interface (CLASS_SUPER_NAME (interface));
6544 else
6545 interface = NULL_TREE;
6546 }
6547
6548 /* Get the superclass for classes. */
6549 if (TREE_CODE (implementation) == CLASS_IMPLEMENTATION_TYPE)
6550 {
6551 if (CLASS_SUPER_NAME (implementation))
6552 interface = lookup_interface (CLASS_SUPER_NAME (implementation));
6553 else
6554 interface = NULL_TREE;
6555 }
6556
6557 /* Now, interface is the superclass, if any; go check it. */
6558 if (interface)
6559 {
6560 if (lookup_method_static (interface, chain, 0))
6561 {
6562 chain = DECL_CHAIN (chain);
6563 continue;
6564 }
6565 }
6566 /* Else, fall through - warn. */
6567 }
6568 if (first)
6569 {
6570 switch (TREE_CODE (implementation))
6571 {
6572 case CLASS_IMPLEMENTATION_TYPE:
6573 warning (0, "incomplete implementation of class %qE",
6574 CLASS_NAME (implementation));
6575 break;
6576 case CATEGORY_IMPLEMENTATION_TYPE:
6577 warning (0, "incomplete implementation of category %qE",
6578 CLASS_SUPER_NAME (implementation));
6579 break;
6580 default:
6581 gcc_unreachable ();
6582 }
6583 first = 0;
6584 }
6585
6586 warning (0, "method definition for %<%c%E%> not found",
6587 mtype, METHOD_SEL_NAME (chain));
6588 }
6589
6590 chain = DECL_CHAIN (chain);
6591 }
6592
6593 return first;
6594 }
6595
6596 /* Check if KLASS, or its superclasses, explicitly conforms to PROTOCOL. */
6597
6598 static int
conforms_to_protocol(tree klass,tree protocol)6599 conforms_to_protocol (tree klass, tree protocol)
6600 {
6601 if (TREE_CODE (protocol) == PROTOCOL_INTERFACE_TYPE)
6602 {
6603 tree p = CLASS_PROTOCOL_LIST (klass);
6604 while (p && TREE_VALUE (p) != protocol)
6605 p = TREE_CHAIN (p);
6606
6607 if (!p)
6608 {
6609 tree super = (CLASS_SUPER_NAME (klass)
6610 ? lookup_interface (CLASS_SUPER_NAME (klass))
6611 : NULL_TREE);
6612 int tmp = super ? conforms_to_protocol (super, protocol) : 0;
6613 if (!tmp)
6614 return 0;
6615 }
6616 }
6617
6618 return 1;
6619 }
6620
6621 /* Make sure all methods in CHAIN are accessible as MTYPE methods in
6622 CONTEXT. This is one of two mechanisms to check protocol integrity. */
6623
6624 static int
check_methods_accessible(tree chain,tree context,int mtype)6625 check_methods_accessible (tree chain, tree context, int mtype)
6626 {
6627 int first = 1;
6628 tree list;
6629 tree base_context = context;
6630
6631 while (chain)
6632 {
6633 /* If the method is associated with a dynamic property, then it
6634 is Ok not to have the method implementation, as it will be
6635 generated dynamically at runtime. Search for any @dynamic
6636 property with the same setter or getter name as this
6637 method. TODO: Use a hashtable lookup. */
6638 tree x;
6639 for (x = IMPL_PROPERTY_DECL (base_context); x; x = TREE_CHAIN (x))
6640 if (PROPERTY_DYNAMIC (x)
6641 && (PROPERTY_GETTER_NAME (x) == METHOD_SEL_NAME (chain)
6642 || PROPERTY_SETTER_NAME (x) == METHOD_SEL_NAME (chain)))
6643 break;
6644
6645 if (x != NULL_TREE)
6646 {
6647 chain = TREE_CHAIN (chain); /* next method... */
6648 continue;
6649 }
6650
6651 context = base_context;
6652 while (context)
6653 {
6654 if (mtype == '+')
6655 list = CLASS_CLS_METHODS (context);
6656 else
6657 list = CLASS_NST_METHODS (context);
6658
6659 if (lookup_method (list, chain))
6660 break;
6661
6662 switch (TREE_CODE (context))
6663 {
6664 case CLASS_IMPLEMENTATION_TYPE:
6665 case CLASS_INTERFACE_TYPE:
6666 context = (CLASS_SUPER_NAME (context)
6667 ? lookup_interface (CLASS_SUPER_NAME (context))
6668 : NULL_TREE);
6669 break;
6670 case CATEGORY_IMPLEMENTATION_TYPE:
6671 case CATEGORY_INTERFACE_TYPE:
6672 context = (CLASS_NAME (context)
6673 ? lookup_interface (CLASS_NAME (context))
6674 : NULL_TREE);
6675 break;
6676 default:
6677 gcc_unreachable ();
6678 }
6679 }
6680
6681 if (context == NULL_TREE)
6682 {
6683 if (first)
6684 {
6685 switch (TREE_CODE (objc_implementation_context))
6686 {
6687 case CLASS_IMPLEMENTATION_TYPE:
6688 warning (0, "incomplete implementation of class %qE",
6689 CLASS_NAME (objc_implementation_context));
6690 break;
6691 case CATEGORY_IMPLEMENTATION_TYPE:
6692 warning (0, "incomplete implementation of category %qE",
6693 CLASS_SUPER_NAME (objc_implementation_context));
6694 break;
6695 default:
6696 gcc_unreachable ();
6697 }
6698 first = 0;
6699 }
6700 warning (0, "method definition for %<%c%E%> not found",
6701 mtype, METHOD_SEL_NAME (chain));
6702 }
6703
6704 chain = TREE_CHAIN (chain); /* next method... */
6705 }
6706 return first;
6707 }
6708
6709 /* Check whether the current interface (accessible via
6710 'objc_implementation_context') actually implements protocol P, along
6711 with any protocols that P inherits. */
6712
6713 static void
check_protocol(tree p,const char * type,tree name)6714 check_protocol (tree p, const char *type, tree name)
6715 {
6716 if (TREE_CODE (p) == PROTOCOL_INTERFACE_TYPE)
6717 {
6718 int f1, f2;
6719
6720 /* Ensure that all protocols have bodies! */
6721 if (warn_protocol)
6722 {
6723 f1 = check_methods (PROTOCOL_CLS_METHODS (p),
6724 objc_implementation_context,
6725 '+');
6726 f2 = check_methods (PROTOCOL_NST_METHODS (p),
6727 objc_implementation_context,
6728 '-');
6729 }
6730 else
6731 {
6732 f1 = check_methods_accessible (PROTOCOL_CLS_METHODS (p),
6733 objc_implementation_context,
6734 '+');
6735 f2 = check_methods_accessible (PROTOCOL_NST_METHODS (p),
6736 objc_implementation_context,
6737 '-');
6738 }
6739
6740 if (!f1 || !f2)
6741 warning (0, "%s %qE does not fully implement the %qE protocol",
6742 type, name, PROTOCOL_NAME (p));
6743 }
6744
6745 /* Check protocols recursively. */
6746 if (PROTOCOL_LIST (p))
6747 {
6748 tree subs = PROTOCOL_LIST (p);
6749 tree super_class =
6750 lookup_interface (CLASS_SUPER_NAME (implementation_template));
6751
6752 while (subs)
6753 {
6754 tree sub = TREE_VALUE (subs);
6755
6756 /* If the superclass does not conform to the protocols
6757 inherited by P, then we must! */
6758 if (!super_class || !conforms_to_protocol (super_class, sub))
6759 check_protocol (sub, type, name);
6760 subs = TREE_CHAIN (subs);
6761 }
6762 }
6763 }
6764
6765 /* Check whether the current interface (accessible via
6766 'objc_implementation_context') actually implements the protocols listed
6767 in PROTO_LIST. */
6768
6769 static void
check_protocols(tree proto_list,const char * type,tree name)6770 check_protocols (tree proto_list, const char *type, tree name)
6771 {
6772 for ( ; proto_list; proto_list = TREE_CHAIN (proto_list))
6773 {
6774 tree p = TREE_VALUE (proto_list);
6775
6776 check_protocol (p, type, name);
6777 }
6778 }
6779
6780 /* Make sure that the class CLASS_NAME is defined CODE says which kind
6781 of thing CLASS_NAME ought to be. It can be CLASS_INTERFACE_TYPE,
6782 CLASS_IMPLEMENTATION_TYPE, CATEGORY_INTERFACE_TYPE, or
6783 CATEGORY_IMPLEMENTATION_TYPE. For a CATEGORY_INTERFACE_TYPE,
6784 SUPER_NAME is the name of the category. For a class extension,
6785 CODE is CATEGORY_INTERFACE_TYPE and SUPER_NAME is NULL_TREE. */
6786 static tree
start_class(enum tree_code code,tree class_name,tree super_name,tree protocol_list,tree attributes)6787 start_class (enum tree_code code, tree class_name, tree super_name,
6788 tree protocol_list, tree attributes)
6789 {
6790 tree klass = NULL_TREE;
6791 tree decl;
6792
6793 #ifdef OBJCPLUS
6794 if (current_namespace != global_namespace)
6795 {
6796 error ("Objective-C declarations may only appear in global scope");
6797 }
6798 #endif /* OBJCPLUS */
6799
6800 if (objc_implementation_context)
6801 {
6802 warning (0, "%<@end%> missing in implementation context");
6803 finish_class (objc_implementation_context);
6804 objc_ivar_chain = NULL_TREE;
6805 objc_implementation_context = NULL_TREE;
6806 }
6807
6808 /* If this is a class extension, we'll be "reopening" the existing
6809 CLASS_INTERFACE_TYPE, so in that case there is no need to create
6810 a new node. */
6811 if (code != CATEGORY_INTERFACE_TYPE || super_name != NULL_TREE)
6812 {
6813 klass = make_node (code);
6814 TYPE_LANG_SLOT_1 (klass) = make_tree_vec (CLASS_LANG_SLOT_ELTS);
6815 }
6816
6817 /* Check for existence of the super class, if one was specified. Note
6818 that we must have seen an @interface, not just a @class. If we
6819 are looking at a @compatibility_alias, traverse it first. */
6820 if ((code == CLASS_INTERFACE_TYPE || code == CLASS_IMPLEMENTATION_TYPE)
6821 && super_name)
6822 {
6823 tree super = objc_is_class_name (super_name);
6824 tree super_interface = NULL_TREE;
6825
6826 if (super)
6827 super_interface = lookup_interface (super);
6828
6829 if (!super_interface)
6830 {
6831 error ("cannot find interface declaration for %qE, superclass of %qE",
6832 super ? super : super_name,
6833 class_name);
6834 super_name = NULL_TREE;
6835 }
6836 else
6837 {
6838 if (TREE_DEPRECATED (super_interface))
6839 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated",
6840 super);
6841 super_name = super;
6842 }
6843 }
6844
6845 if (code != CATEGORY_INTERFACE_TYPE || super_name != NULL_TREE)
6846 {
6847 CLASS_NAME (klass) = class_name;
6848 CLASS_SUPER_NAME (klass) = super_name;
6849 CLASS_CLS_METHODS (klass) = NULL_TREE;
6850 }
6851
6852 if (! objc_is_class_name (class_name)
6853 && (decl = lookup_name (class_name)))
6854 {
6855 error ("%qE redeclared as different kind of symbol",
6856 class_name);
6857 error ("previous declaration of %q+D",
6858 decl);
6859 }
6860
6861 switch (code)
6862 {
6863 case CLASS_IMPLEMENTATION_TYPE:
6864 {
6865 tree chain;
6866
6867 for (chain = implemented_classes; chain; chain = TREE_CHAIN (chain))
6868 if (TREE_VALUE (chain) == class_name)
6869 {
6870 error ("reimplementation of class %qE",
6871 class_name);
6872 /* TODO: error message saying where it was previously
6873 implemented. */
6874 break;
6875 }
6876 if (chain == NULL_TREE)
6877 implemented_classes = tree_cons (NULL_TREE, class_name,
6878 implemented_classes);
6879 }
6880
6881 /* Reset for multiple classes per file. */
6882 method_slot = 0;
6883
6884 objc_implementation_context = klass;
6885
6886 /* Lookup the interface for this implementation. */
6887
6888 if (!(implementation_template = lookup_interface (class_name)))
6889 {
6890 warning (0, "cannot find interface declaration for %qE",
6891 class_name);
6892 add_interface (implementation_template = objc_implementation_context,
6893 class_name);
6894 }
6895
6896 /* If a super class has been specified in the implementation,
6897 insure it conforms to the one specified in the interface. */
6898
6899 if (super_name
6900 && (super_name != CLASS_SUPER_NAME (implementation_template)))
6901 {
6902 tree previous_name = CLASS_SUPER_NAME (implementation_template);
6903 error ("conflicting super class name %qE",
6904 super_name);
6905 if (previous_name)
6906 error ("previous declaration of %qE", previous_name);
6907 else
6908 error ("previous declaration");
6909 }
6910
6911 else if (! super_name)
6912 {
6913 CLASS_SUPER_NAME (objc_implementation_context)
6914 = CLASS_SUPER_NAME (implementation_template);
6915 }
6916 break;
6917
6918 case CLASS_INTERFACE_TYPE:
6919 if (lookup_interface (class_name))
6920 #ifdef OBJCPLUS
6921 error ("duplicate interface declaration for class %qE", class_name);
6922 #else
6923 warning (0, "duplicate interface declaration for class %qE", class_name);
6924 #endif
6925 else
6926 add_interface (klass, class_name);
6927
6928 if (protocol_list)
6929 CLASS_PROTOCOL_LIST (klass)
6930 = lookup_and_install_protocols (protocol_list, /* definition_required */ true);
6931
6932 if (attributes)
6933 {
6934 tree attribute;
6935 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
6936 {
6937 tree name = TREE_PURPOSE (attribute);
6938
6939 /* TODO: Document what the objc_exception attribute is/does. */
6940 /* We handle the 'deprecated' and (undocumented) 'objc_exception'
6941 attributes. */
6942 if (is_attribute_p ("deprecated", name))
6943 TREE_DEPRECATED (klass) = 1;
6944 else if (is_attribute_p ("objc_exception", name))
6945 CLASS_HAS_EXCEPTION_ATTR (klass) = 1;
6946 else
6947 /* Warn about and ignore all others for now, but store them. */
6948 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
6949 }
6950 TYPE_ATTRIBUTES (klass) = attributes;
6951 }
6952 break;
6953
6954 case CATEGORY_INTERFACE_TYPE:
6955 {
6956 tree class_category_is_assoc_with;
6957
6958 /* For a category, class_name is really the name of the class that
6959 the following set of methods will be associated with. We must
6960 find the interface so that can derive the objects template. */
6961 if (!(class_category_is_assoc_with = lookup_interface (class_name)))
6962 {
6963 error ("cannot find interface declaration for %qE",
6964 class_name);
6965 exit (FATAL_EXIT_CODE);
6966 }
6967 else
6968 {
6969 if (TREE_DEPRECATED (class_category_is_assoc_with))
6970 warning (OPT_Wdeprecated_declarations, "class %qE is deprecated",
6971 class_name);
6972
6973 if (super_name == NULL_TREE)
6974 {
6975 /* This is a class extension. Get the original
6976 interface, and continue working on it. */
6977 objc_in_class_extension = true;
6978 klass = class_category_is_assoc_with;
6979
6980 if (protocol_list)
6981 {
6982 /* Append protocols to the original protocol
6983 list. */
6984 CLASS_PROTOCOL_LIST (klass)
6985 = chainon (CLASS_PROTOCOL_LIST (klass),
6986 lookup_and_install_protocols
6987 (protocol_list,
6988 /* definition_required */ true));
6989 }
6990 }
6991 else
6992 {
6993 add_category (class_category_is_assoc_with, klass);
6994
6995 if (protocol_list)
6996 CLASS_PROTOCOL_LIST (klass)
6997 = lookup_and_install_protocols
6998 (protocol_list, /* definition_required */ true);
6999 }
7000 }
7001 }
7002 break;
7003
7004 case CATEGORY_IMPLEMENTATION_TYPE:
7005 /* Reset for multiple classes per file. */
7006 method_slot = 0;
7007
7008 objc_implementation_context = klass;
7009
7010 /* For a category, class_name is really the name of the class that
7011 the following set of methods will be associated with. We must
7012 find the interface so that can derive the objects template. */
7013
7014 if (!(implementation_template = lookup_interface (class_name)))
7015 {
7016 error ("cannot find interface declaration for %qE",
7017 class_name);
7018 exit (FATAL_EXIT_CODE);
7019 }
7020 break;
7021 default:
7022 gcc_unreachable ();
7023 }
7024 return klass;
7025 }
7026
7027 static tree
continue_class(tree klass)7028 continue_class (tree klass)
7029 {
7030 switch (TREE_CODE (klass))
7031 {
7032 case CLASS_IMPLEMENTATION_TYPE:
7033 case CATEGORY_IMPLEMENTATION_TYPE:
7034 {
7035 struct imp_entry *imp_entry;
7036
7037 /* Check consistency of the instance variables. */
7038
7039 if (CLASS_RAW_IVARS (klass))
7040 check_ivars (implementation_template, klass);
7041
7042 /* code generation */
7043 #ifdef OBJCPLUS
7044 push_lang_context (lang_name_c);
7045 #endif
7046 build_private_template (implementation_template);
7047 uprivate_record = CLASS_STATIC_TEMPLATE (implementation_template);
7048 objc_instance_type = build_pointer_type (uprivate_record);
7049
7050 imp_entry = ggc_alloc<struct imp_entry> ();
7051
7052 imp_entry->next = imp_list;
7053 imp_entry->imp_context = klass;
7054 imp_entry->imp_template = implementation_template;
7055 ucls_super_ref = uucls_super_ref = NULL;
7056 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7057 {
7058 imp_entry->class_decl = (*runtime.class_decl) (klass);
7059 imp_entry->meta_decl = (*runtime.metaclass_decl) (klass);
7060 }
7061 else
7062 {
7063 imp_entry->class_decl = (*runtime.category_decl) (klass);
7064 imp_entry->meta_decl = NULL;
7065 }
7066 imp_entry->has_cxx_cdtors = 0;
7067
7068 /* Append to front and increment count. */
7069 imp_list = imp_entry;
7070 if (TREE_CODE (klass) == CLASS_IMPLEMENTATION_TYPE)
7071 imp_count++;
7072 else
7073 cat_count++;
7074 #ifdef OBJCPLUS
7075 pop_lang_context ();
7076 #endif /* OBJCPLUS */
7077
7078 return get_class_ivars (implementation_template, true);
7079 }
7080 case CLASS_INTERFACE_TYPE:
7081 {
7082 if (objc_in_class_extension)
7083 return NULL_TREE;
7084 #ifdef OBJCPLUS
7085 push_lang_context (lang_name_c);
7086 #endif /* OBJCPLUS */
7087 objc_collecting_ivars = 1;
7088 build_private_template (klass);
7089 objc_collecting_ivars = 0;
7090 #ifdef OBJCPLUS
7091 pop_lang_context ();
7092 #endif /* OBJCPLUS */
7093 return NULL_TREE;
7094 }
7095 default:
7096 return error_mark_node;
7097 }
7098 }
7099
7100 /* This routine builds name of the setter synthesized function. */
7101 char *
objc_build_property_setter_name(tree ident)7102 objc_build_property_setter_name (tree ident)
7103 {
7104 /* TODO: Use alloca to allocate buffer of appropriate size. */
7105 static char string[BUFSIZE];
7106 sprintf (string, "set%s:", IDENTIFIER_POINTER (ident));
7107 string[3] = TOUPPER (string[3]);
7108 return string;
7109 }
7110
7111 /* This routine prepares the declarations of the property accessor
7112 helper functions (objc_getProperty(), etc) that are used when
7113 @synthesize is used.
7114
7115 runtime-specific routines are built in the respective runtime
7116 initialize functions. */
7117 static void
build_common_objc_property_accessor_helpers(void)7118 build_common_objc_property_accessor_helpers (void)
7119 {
7120 tree type;
7121
7122 /* Declare the following function:
7123 id
7124 objc_getProperty (id self, SEL _cmd,
7125 ptrdiff_t offset, BOOL is_atomic); */
7126 type = build_function_type_list (objc_object_type,
7127 objc_object_type,
7128 objc_selector_type,
7129 ptrdiff_type_node,
7130 boolean_type_node,
7131 NULL_TREE);
7132 objc_getProperty_decl = add_builtin_function ("objc_getProperty",
7133 type, 0, NOT_BUILT_IN,
7134 NULL, NULL_TREE);
7135 TREE_NOTHROW (objc_getProperty_decl) = 0;
7136
7137 /* Declare the following function:
7138 void
7139 objc_setProperty (id self, SEL _cmd,
7140 ptrdiff_t offset, id new_value,
7141 BOOL is_atomic, BOOL should_copy); */
7142 type = build_function_type_list (void_type_node,
7143 objc_object_type,
7144 objc_selector_type,
7145 ptrdiff_type_node,
7146 objc_object_type,
7147 boolean_type_node,
7148 boolean_type_node,
7149 NULL_TREE);
7150 objc_setProperty_decl = add_builtin_function ("objc_setProperty",
7151 type, 0, NOT_BUILT_IN,
7152 NULL, NULL_TREE);
7153 TREE_NOTHROW (objc_setProperty_decl) = 0;
7154 }
7155
7156 /* This looks up an ivar in a class (including superclasses). */
7157 static tree
lookup_ivar(tree interface,tree instance_variable_name)7158 lookup_ivar (tree interface, tree instance_variable_name)
7159 {
7160 while (interface)
7161 {
7162 tree decl_chain;
7163
7164 for (decl_chain = CLASS_IVARS (interface); decl_chain; decl_chain = DECL_CHAIN (decl_chain))
7165 if (DECL_NAME (decl_chain) == instance_variable_name)
7166 return decl_chain;
7167
7168 /* Not found. Search superclass if any. */
7169 if (CLASS_SUPER_NAME (interface))
7170 interface = lookup_interface (CLASS_SUPER_NAME (interface));
7171 }
7172
7173 return NULL_TREE;
7174 }
7175
7176 /* This routine synthesizes a 'getter' method. This is only called
7177 for @synthesize properties. */
7178 static void
objc_synthesize_getter(tree klass,tree class_methods ATTRIBUTE_UNUSED,tree property)7179 objc_synthesize_getter (tree klass, tree class_methods ATTRIBUTE_UNUSED, tree property)
7180 {
7181 location_t location = DECL_SOURCE_LOCATION (property);
7182 tree fn, decl;
7183 tree body;
7184 tree ret_val;
7185
7186 /* If user has implemented a getter with same name then do nothing. */
7187 if (lookup_method (CLASS_NST_METHODS (objc_implementation_context),
7188 PROPERTY_GETTER_NAME (property)))
7189 return;
7190
7191 /* Find declaration of the property getter in the interface (or
7192 superclass, or protocol). There must be one. */
7193 decl = lookup_method_static (klass, PROPERTY_GETTER_NAME (property), 0);
7194
7195 /* If one not declared in the interface, this condition has already
7196 been reported as user error (because property was not declared in
7197 the interface). */
7198 if (!decl)
7199 return;
7200
7201 /* Adapt the 'decl'. Use the source location of the @synthesize
7202 statement for error messages. */
7203 decl = copy_node (decl);
7204 DECL_SOURCE_LOCATION (decl) = location;
7205
7206 objc_start_method_definition (false /* is_class_method */, decl, NULL_TREE,
7207 NULL_TREE);
7208 body = c_begin_compound_stmt (true);
7209
7210 /* Now we need to decide how we build the getter. There are three
7211 cases:
7212
7213 for 'copy' or 'retain' properties we need to use the
7214 objc_getProperty() accessor helper which knows about retain and
7215 copy. It supports both 'nonatomic' and 'atomic' access.
7216
7217 for 'nonatomic, assign' properties we can access the instance
7218 variable directly. 'nonatomic' means we don't have to use locks,
7219 and 'assign' means we don't have to worry about retain or copy.
7220 If you combine the two, it means we can just access the instance
7221 variable directly.
7222
7223 for 'atomic, assign' properties we use objc_copyStruct() (for the
7224 next runtime) or objc_getPropertyStruct() (for the GNU runtime). */
7225 switch (PROPERTY_ASSIGN_SEMANTICS (property))
7226 {
7227 case OBJC_PROPERTY_RETAIN:
7228 case OBJC_PROPERTY_COPY:
7229 {
7230 /* We build "return objc_getProperty (self, _cmd, offset, is_atomic);" */
7231 tree cmd, ivar, offset, is_atomic;
7232 cmd = TREE_CHAIN (DECL_ARGUMENTS (current_function_decl));
7233
7234 /* Find the ivar to compute the offset. */
7235 ivar = lookup_ivar (klass, PROPERTY_IVAR_NAME (property));
7236 if (!ivar || is_private (ivar))
7237 {
7238 /* This should never happen. */
7239 error_at (location,
7240 "cannot find instance variable associated with property");
7241 ret_val = error_mark_node;
7242 break;
7243 }
7244 offset = byte_position (ivar);
7245
7246 if (PROPERTY_NONATOMIC (property))
7247 is_atomic = boolean_false_node;
7248 else
7249 is_atomic = boolean_true_node;
7250
7251 ret_val = build_function_call
7252 (location,
7253 /* Function prototype. */
7254 objc_getProperty_decl,
7255 /* Parameters. */
7256 tree_cons /* self */
7257 (NULL_TREE, self_decl,
7258 tree_cons /* _cmd */
7259 (NULL_TREE, cmd,
7260 tree_cons /* offset */
7261 (NULL_TREE, offset,
7262 tree_cons /* is_atomic */
7263 (NULL_TREE, is_atomic, NULL_TREE)))));
7264 }
7265 break;
7266 case OBJC_PROPERTY_ASSIGN:
7267 if (PROPERTY_NONATOMIC (property))
7268 {
7269 /* We build "return self->PROPERTY_IVAR_NAME;" */
7270 ret_val = objc_lookup_ivar (NULL_TREE, PROPERTY_IVAR_NAME (property));
7271 break;
7272 }
7273 else
7274 {
7275 /* We build
7276 <property type> __objc_property_temp;
7277 objc_getPropertyStruct (&__objc_property_temp,
7278 &(self->PROPERTY_IVAR_NAME),
7279 sizeof (type of self->PROPERTY_IVAR_NAME),
7280 is_atomic,
7281 false)
7282 return __objc_property_temp;
7283
7284 For the NeXT runtime, we need to use objc_copyStruct
7285 instead of objc_getPropertyStruct. */
7286 tree objc_property_temp_decl, function_decl, function_call;
7287 tree size_of, is_atomic;
7288
7289 objc_property_temp_decl = objc_create_temporary_var (TREE_TYPE (property), "__objc_property_temp");
7290 DECL_SOURCE_LOCATION (objc_property_temp_decl) = location;
7291 objc_property_temp_decl = lang_hooks.decls.pushdecl (objc_property_temp_decl);
7292
7293 /* sizeof (ivar type). Since the ivar and the property have
7294 the same type, there is no need to lookup the ivar. */
7295 size_of = c_sizeof_or_alignof_type (location, TREE_TYPE (property),
7296 true /* is_sizeof */,
7297 false /* min_alignof */,
7298 false /* complain */);
7299
7300 if (PROPERTY_NONATOMIC (property))
7301 is_atomic = boolean_false_node;
7302 else
7303 is_atomic = boolean_true_node;
7304
7305 if (objc_copyStruct_decl)
7306 function_decl = objc_copyStruct_decl;
7307 else
7308 function_decl = objc_getPropertyStruct_decl;
7309
7310 function_call = build_function_call
7311 (location,
7312 /* Function prototype. */
7313 function_decl,
7314 /* Parameters. */
7315 tree_cons /* &__objc_property_temp_decl */
7316 /* Warning: note that using build_fold_addr_expr_loc()
7317 here causes invalid code to be generated. */
7318 (NULL_TREE, build_unary_op (location, ADDR_EXPR, objc_property_temp_decl, 0),
7319 tree_cons /* &(self->PROPERTY_IVAR_NAME); */
7320 (NULL_TREE, build_fold_addr_expr_loc (location,
7321 objc_lookup_ivar
7322 (NULL_TREE, PROPERTY_IVAR_NAME (property))),
7323 tree_cons /* sizeof (PROPERTY_IVAR) */
7324 (NULL_TREE, size_of,
7325 tree_cons /* is_atomic */
7326 (NULL_TREE, is_atomic,
7327 /* TODO: This is currently ignored by the GNU
7328 runtime, but what about the next one ? */
7329 tree_cons /* has_strong */
7330 (NULL_TREE, boolean_true_node, NULL_TREE))))));
7331
7332 add_stmt (function_call);
7333
7334 ret_val = objc_property_temp_decl;
7335 }
7336 break;
7337 default:
7338 gcc_unreachable ();
7339 }
7340
7341 gcc_assert (ret_val);
7342
7343 #ifdef OBJCPLUS
7344 finish_return_stmt (ret_val);
7345 #else
7346 c_finish_return (location, ret_val, NULL_TREE);
7347 #endif
7348
7349 add_stmt (c_end_compound_stmt (location, body, true));
7350 fn = current_function_decl;
7351 #ifdef OBJCPLUS
7352 finish_function ();
7353 #endif
7354 objc_finish_method_definition (fn);
7355 }
7356
7357 /* This routine synthesizes a 'setter' method. */
7358
7359 static void
objc_synthesize_setter(tree klass,tree class_methods ATTRIBUTE_UNUSED,tree property)7360 objc_synthesize_setter (tree klass, tree class_methods ATTRIBUTE_UNUSED, tree property)
7361 {
7362 location_t location = DECL_SOURCE_LOCATION (property);
7363 tree fn, decl;
7364 tree body;
7365 tree new_value, statement;
7366
7367 /* If user has implemented a setter with same name then do nothing. */
7368 if (lookup_method (CLASS_NST_METHODS (objc_implementation_context),
7369 PROPERTY_SETTER_NAME (property)))
7370 return;
7371
7372 /* Find declaration of the property setter in the interface (or
7373 superclass, or protocol). There must be one. */
7374 decl = lookup_method_static (klass, PROPERTY_SETTER_NAME (property), 0);
7375
7376 /* If one not declared in the interface, this condition has already
7377 been reported as user error (because property was not declared in
7378 the interface). */
7379 if (!decl)
7380 return;
7381
7382 /* Adapt the 'decl'. Use the source location of the @synthesize
7383 statement for error messages. */
7384 decl = copy_node (decl);
7385 DECL_SOURCE_LOCATION (decl) = DECL_SOURCE_LOCATION (property);
7386
7387 objc_start_method_definition (false /* is_class_method */, decl, NULL_TREE,
7388 NULL_TREE);
7389
7390 body = c_begin_compound_stmt (true);
7391
7392 /* The 'new_value' is the only argument to the method, which is the
7393 3rd argument of the function, after self and _cmd. We use twice
7394 TREE_CHAIN to move forward two arguments. */
7395 new_value = TREE_CHAIN (TREE_CHAIN (DECL_ARGUMENTS (current_function_decl)));
7396
7397 /* This would presumably happen if the user has specified a
7398 prototype for the setter that does not have an argument! */
7399 if (new_value == NULL_TREE)
7400 {
7401 /* TODO: This should be caught much earlier than this. */
7402 error_at (DECL_SOURCE_LOCATION (decl), "invalid setter, it must have one argument");
7403 /* Try to recover somehow. */
7404 new_value = error_mark_node;
7405 }
7406
7407 /* Now we need to decide how we build the setter. There are three
7408 cases:
7409
7410 for 'copy' or 'retain' properties we need to use the
7411 objc_setProperty() accessor helper which knows about retain and
7412 copy. It supports both 'nonatomic' and 'atomic' access.
7413
7414 for 'nonatomic, assign' properties we can access the instance
7415 variable directly. 'nonatomic' means we don't have to use locks,
7416 and 'assign' means we don't have to worry about retain or copy.
7417 If you combine the two, it means we can just access the instance
7418 variable directly.
7419
7420 for 'atomic, assign' properties we use objc_copyStruct() (for the
7421 next runtime) or objc_setPropertyStruct() (for the GNU runtime). */
7422 switch (PROPERTY_ASSIGN_SEMANTICS (property))
7423 {
7424 case OBJC_PROPERTY_RETAIN:
7425 case OBJC_PROPERTY_COPY:
7426 {
7427 /* We build "objc_setProperty (self, _cmd, new_value, offset, is_atomic, should_copy);" */
7428 tree cmd, ivar, offset, is_atomic, should_copy;
7429 cmd = TREE_CHAIN (DECL_ARGUMENTS (current_function_decl));
7430
7431 /* Find the ivar to compute the offset. */
7432 ivar = lookup_ivar (klass, PROPERTY_IVAR_NAME (property));
7433 if (!ivar || is_private (ivar))
7434 {
7435 error_at (location,
7436 "cannot find instance variable associated with property");
7437 statement = error_mark_node;
7438 break;
7439 }
7440 offset = byte_position (ivar);
7441
7442 if (PROPERTY_NONATOMIC (property))
7443 is_atomic = boolean_false_node;
7444 else
7445 is_atomic = boolean_true_node;
7446
7447 if (PROPERTY_ASSIGN_SEMANTICS (property) == OBJC_PROPERTY_COPY)
7448 should_copy = boolean_true_node;
7449 else
7450 should_copy = boolean_false_node;
7451
7452 statement = build_function_call
7453 (location,
7454 /* Function prototype. */
7455 objc_setProperty_decl,
7456 /* Parameters. */
7457 tree_cons /* self */
7458 (NULL_TREE, self_decl,
7459 tree_cons /* _cmd */
7460 (NULL_TREE, cmd,
7461 tree_cons /* offset */
7462 (NULL_TREE, offset,
7463 tree_cons /* new_value */
7464 (NULL_TREE, new_value,
7465 tree_cons /* is_atomic */
7466 (NULL_TREE, is_atomic,
7467 tree_cons /* should_copy */
7468 (NULL_TREE, should_copy, NULL_TREE)))))));
7469 }
7470 break;
7471 case OBJC_PROPERTY_ASSIGN:
7472 if (PROPERTY_NONATOMIC (property))
7473 {
7474 /* We build "self->PROPERTY_IVAR_NAME = new_value;" */
7475 statement = build_modify_expr
7476 (location,
7477 objc_lookup_ivar (NULL_TREE, PROPERTY_IVAR_NAME (property)),
7478 NULL_TREE, NOP_EXPR,
7479 location, new_value, NULL_TREE);
7480 break;
7481 }
7482 else
7483 {
7484 /* We build
7485 objc_setPropertyStruct (&(self->PROPERTY_IVAR_NAME),
7486 &new_value,
7487 sizeof (type of self->PROPERTY_IVAR_NAME),
7488 is_atomic,
7489 false)
7490
7491 For the NeXT runtime, we need to use objc_copyStruct
7492 instead of objc_getPropertyStruct. */
7493 tree function_decl, size_of, is_atomic;
7494
7495 /* sizeof (ivar type). Since the ivar and the property have
7496 the same type, there is no need to lookup the ivar. */
7497 size_of = c_sizeof_or_alignof_type (location, TREE_TYPE (property),
7498 true /* is_sizeof */,
7499 false /* min_alignof */,
7500 false /* complain */);
7501
7502 if (PROPERTY_NONATOMIC (property))
7503 is_atomic = boolean_false_node;
7504 else
7505 is_atomic = boolean_true_node;
7506
7507 if (objc_copyStruct_decl)
7508 function_decl = objc_copyStruct_decl;
7509 else
7510 function_decl = objc_setPropertyStruct_decl;
7511
7512 statement = build_function_call
7513 (location,
7514 /* Function prototype. */
7515 function_decl,
7516 /* Parameters. */
7517 tree_cons /* &(self->PROPERTY_IVAR_NAME); */
7518 (NULL_TREE, build_fold_addr_expr_loc (location,
7519 objc_lookup_ivar
7520 (NULL_TREE, PROPERTY_IVAR_NAME (property))),
7521 tree_cons /* &new_value */
7522 (NULL_TREE, build_fold_addr_expr_loc (location, new_value),
7523 tree_cons /* sizeof (PROPERTY_IVAR) */
7524 (NULL_TREE, size_of,
7525 tree_cons /* is_atomic */
7526 (NULL_TREE, is_atomic,
7527 /* TODO: This is currently ignored by the GNU
7528 runtime, but what about the next one ? */
7529 tree_cons /* has_strong */
7530 (NULL_TREE, boolean_true_node, NULL_TREE))))));
7531 }
7532 break;
7533 default:
7534 gcc_unreachable ();
7535 }
7536 gcc_assert (statement);
7537
7538 add_stmt (statement);
7539 add_stmt (c_end_compound_stmt (location, body, true));
7540 fn = current_function_decl;
7541 #ifdef OBJCPLUS
7542 finish_function ();
7543 #endif
7544 objc_finish_method_definition (fn);
7545 }
7546
7547 /* This function is a sub-routine of objc_add_synthesize_declaration.
7548 It is called for each property to synthesize once we have
7549 determined that the context is Ok. */
7550 static void
objc_add_synthesize_declaration_for_property(location_t location,tree interface,tree property_name,tree ivar_name)7551 objc_add_synthesize_declaration_for_property (location_t location, tree interface,
7552 tree property_name, tree ivar_name)
7553 {
7554 /* Find the @property declaration. */
7555 tree property;
7556 tree x;
7557
7558 /* Check that synthesize or dynamic has not already been used for
7559 the same property. */
7560 for (property = IMPL_PROPERTY_DECL (objc_implementation_context); property; property = TREE_CHAIN (property))
7561 if (PROPERTY_NAME (property) == property_name)
7562 {
7563 location_t original_location = DECL_SOURCE_LOCATION (property);
7564
7565 if (PROPERTY_DYNAMIC (property))
7566 error_at (location, "property %qs already specified in %<@dynamic%>",
7567 IDENTIFIER_POINTER (property_name));
7568 else
7569 error_at (location, "property %qs already specified in %<@synthesize%>",
7570 IDENTIFIER_POINTER (property_name));
7571
7572 if (original_location != UNKNOWN_LOCATION)
7573 inform (original_location, "originally specified here");
7574 return;
7575 }
7576
7577 /* Check that the property is declared in the interface. It could
7578 also be declared in a superclass or protocol. */
7579 property = lookup_property (interface, property_name);
7580
7581 if (!property)
7582 {
7583 error_at (location, "no declaration of property %qs found in the interface",
7584 IDENTIFIER_POINTER (property_name));
7585 return;
7586 }
7587 else
7588 {
7589 /* We have to copy the property, because we want to chain it to
7590 the implementation context, and we want to store the source
7591 location of the @synthesize, not of the original
7592 @property. */
7593 property = copy_node (property);
7594 DECL_SOURCE_LOCATION (property) = location;
7595 }
7596
7597 /* Determine PROPERTY_IVAR_NAME. */
7598 if (ivar_name == NULL_TREE)
7599 ivar_name = property_name;
7600
7601 /* Check that the instance variable exists. You can only use an
7602 instance variable from the same class, not one from the
7603 superclass (this makes sense as it allows us to check that an
7604 instance variable is only used in one synthesized property). */
7605 {
7606 tree ivar = is_ivar (CLASS_IVARS (interface), ivar_name);
7607 tree type_of_ivar;
7608 if (!ivar)
7609 {
7610 error_at (location, "ivar %qs used by %<@synthesize%> declaration must be an existing ivar",
7611 IDENTIFIER_POINTER (property_name));
7612 return;
7613 }
7614
7615 if (DECL_BIT_FIELD_TYPE (ivar))
7616 type_of_ivar = DECL_BIT_FIELD_TYPE (ivar);
7617 else
7618 type_of_ivar = TREE_TYPE (ivar);
7619
7620 /* If the instance variable has a different C type, we throw an error ... */
7621 if (!comptypes (TREE_TYPE (property), type_of_ivar)
7622 /* ... unless the property is readonly, in which case we allow
7623 the instance variable to be more specialized (this means we
7624 can generate the getter all right and it works). */
7625 && (!PROPERTY_READONLY (property)
7626 || !objc_compare_types (TREE_TYPE (property),
7627 type_of_ivar, -5, NULL_TREE)))
7628 {
7629 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7630
7631 error_at (location, "property %qs is using instance variable %qs of incompatible type",
7632 IDENTIFIER_POINTER (property_name),
7633 IDENTIFIER_POINTER (ivar_name));
7634
7635 if (original_location != UNKNOWN_LOCATION)
7636 inform (original_location, "originally specified here");
7637 }
7638
7639 /* If the instance variable is a bitfield, the property must be
7640 'assign', 'nonatomic' because the runtime getter/setter helper
7641 do not work with bitfield instance variables. */
7642 if (DECL_BIT_FIELD_TYPE (ivar))
7643 {
7644 /* If there is an error, we return and not generate any
7645 getter/setter because trying to set up the runtime
7646 getter/setter helper calls with bitfields is at high risk
7647 of ICE. */
7648
7649 if (PROPERTY_ASSIGN_SEMANTICS (property) != OBJC_PROPERTY_ASSIGN)
7650 {
7651 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7652
7653 error_at (location, "%<assign%> property %qs is using bit-field "
7654 "instance variable %qs",
7655 IDENTIFIER_POINTER (property_name),
7656 IDENTIFIER_POINTER (ivar_name));
7657
7658 if (original_location != UNKNOWN_LOCATION)
7659 inform (original_location, "originally specified here");
7660 return;
7661 }
7662
7663 if (!PROPERTY_NONATOMIC (property))
7664 {
7665 location_t original_location = DECL_SOURCE_LOCATION (ivar);
7666
7667 error_at (location, "%<atomic%> property %qs is using bit-field "
7668 "instance variable %qs",
7669 IDENTIFIER_POINTER (property_name),
7670 IDENTIFIER_POINTER (ivar_name));
7671
7672 if (original_location != UNKNOWN_LOCATION)
7673 inform (original_location, "originally specified here");
7674 return;
7675 }
7676 }
7677 }
7678
7679 /* Check that no other property is using the same instance
7680 variable. */
7681 for (x = IMPL_PROPERTY_DECL (objc_implementation_context); x; x = TREE_CHAIN (x))
7682 if (PROPERTY_IVAR_NAME (x) == ivar_name)
7683 {
7684 location_t original_location = DECL_SOURCE_LOCATION (x);
7685
7686 error_at (location, "property %qs is using the same instance variable as property %qs",
7687 IDENTIFIER_POINTER (property_name),
7688 IDENTIFIER_POINTER (PROPERTY_NAME (x)));
7689
7690 if (original_location != UNKNOWN_LOCATION)
7691 inform (original_location, "originally specified here");
7692
7693 /* We keep going on. This won't cause the compiler to fail;
7694 the failure would most likely be at runtime. */
7695 }
7696
7697 /* Note that a @synthesize (and only a @synthesize) always sets
7698 PROPERTY_IVAR_NAME to a non-NULL_TREE. You can recognize a
7699 @synthesize by that. */
7700 PROPERTY_IVAR_NAME (property) = ivar_name;
7701
7702 /* PROPERTY_SETTER_NAME and PROPERTY_GETTER_NAME are copied from the
7703 original declaration; they are always set (with the exception of
7704 PROPERTY_SETTER_NAME not being set if PROPERTY_READONLY == 1). */
7705
7706 /* Add the property to the list of properties for current implementation. */
7707 TREE_CHAIN (property) = IMPL_PROPERTY_DECL (objc_implementation_context);
7708 IMPL_PROPERTY_DECL (objc_implementation_context) = property;
7709
7710 /* Note how we don't actually synthesize the getter/setter here; it
7711 would be very natural, but we may miss the fact that the user has
7712 implemented his own getter/setter later on in the @implementation
7713 (in which case we shouldn't generate getter/setter). We wait
7714 until we have parsed it all before generating the code. */
7715 }
7716
7717 /* This function is called by the parser after a @synthesize
7718 expression is parsed. 'location' is the location of the
7719 @synthesize expression, and 'property_and_ivar_list' is a chained
7720 list of the property and ivar names. */
7721 void
objc_add_synthesize_declaration(location_t location,tree property_and_ivar_list)7722 objc_add_synthesize_declaration (location_t location, tree property_and_ivar_list)
7723 {
7724 tree interface, chain;
7725
7726 if (flag_objc1_only)
7727 error_at (input_location, "%<@synthesize%> is not available in Objective-C 1.0");
7728
7729 if (property_and_ivar_list == error_mark_node)
7730 return;
7731
7732 if (!objc_implementation_context)
7733 {
7734 /* We can get here only in Objective-C; the Objective-C++ parser
7735 detects the problem while parsing, outputs the error
7736 "misplaced '@synthesize' Objective-C++ construct" and skips
7737 the declaration. */
7738 error_at (location, "%<@synthesize%> not in @implementation context");
7739 return;
7740 }
7741
7742 if (TREE_CODE (objc_implementation_context) == CATEGORY_IMPLEMENTATION_TYPE)
7743 {
7744 error_at (location, "%<@synthesize%> cannot be used in categories");
7745 return;
7746 }
7747
7748 interface = lookup_interface (CLASS_NAME (objc_implementation_context));
7749 if (!interface)
7750 {
7751 /* I can't see how this could happen, but it is good as a safety check. */
7752 error_at (location,
7753 "%<@synthesize%> requires the @interface of the class to be available");
7754 return;
7755 }
7756
7757 /* Now, iterate over the properties and do each of them. */
7758 for (chain = property_and_ivar_list; chain; chain = TREE_CHAIN (chain))
7759 {
7760 objc_add_synthesize_declaration_for_property (location, interface, TREE_VALUE (chain),
7761 TREE_PURPOSE (chain));
7762 }
7763 }
7764
7765 /* This function is a sub-routine of objc_add_dynamic_declaration. It
7766 is called for each property to mark as dynamic once we have
7767 determined that the context is Ok. */
7768 static void
objc_add_dynamic_declaration_for_property(location_t location,tree interface,tree property_name)7769 objc_add_dynamic_declaration_for_property (location_t location, tree interface,
7770 tree property_name)
7771 {
7772 /* Find the @property declaration. */
7773 tree property;
7774
7775 /* Check that synthesize or dynamic has not already been used for
7776 the same property. */
7777 for (property = IMPL_PROPERTY_DECL (objc_implementation_context); property; property = TREE_CHAIN (property))
7778 if (PROPERTY_NAME (property) == property_name)
7779 {
7780 location_t original_location = DECL_SOURCE_LOCATION (property);
7781
7782 if (PROPERTY_DYNAMIC (property))
7783 error_at (location, "property %qs already specified in %<@dynamic%>",
7784 IDENTIFIER_POINTER (property_name));
7785 else
7786 error_at (location, "property %qs already specified in %<@synthesize%>",
7787 IDENTIFIER_POINTER (property_name));
7788
7789 if (original_location != UNKNOWN_LOCATION)
7790 inform (original_location, "originally specified here");
7791 return;
7792 }
7793
7794 /* Check that the property is declared in the interface. It could
7795 also be declared in a superclass or protocol. */
7796 property = lookup_property (interface, property_name);
7797
7798 if (!property)
7799 {
7800 error_at (location, "no declaration of property %qs found in the interface",
7801 IDENTIFIER_POINTER (property_name));
7802 return;
7803 }
7804 else
7805 {
7806 /* We have to copy the property, because we want to chain it to
7807 the implementation context, and we want to store the source
7808 location of the @synthesize, not of the original
7809 @property. */
7810 property = copy_node (property);
7811 DECL_SOURCE_LOCATION (property) = location;
7812 }
7813
7814 /* Note that a @dynamic (and only a @dynamic) always sets
7815 PROPERTY_DYNAMIC to 1. You can recognize a @dynamic by that.
7816 (actually, as explained above, PROPERTY_DECL generated by
7817 @property and associated with a @dynamic property are also marked
7818 as PROPERTY_DYNAMIC). */
7819 PROPERTY_DYNAMIC (property) = 1;
7820
7821 /* Add the property to the list of properties for current implementation. */
7822 TREE_CHAIN (property) = IMPL_PROPERTY_DECL (objc_implementation_context);
7823 IMPL_PROPERTY_DECL (objc_implementation_context) = property;
7824 }
7825
7826 /* This function is called by the parser after a @dynamic expression
7827 is parsed. 'location' is the location of the @dynamic expression,
7828 and 'property_list' is a chained list of all the property
7829 names. */
7830 void
objc_add_dynamic_declaration(location_t location,tree property_list)7831 objc_add_dynamic_declaration (location_t location, tree property_list)
7832 {
7833 tree interface, chain;
7834
7835 if (flag_objc1_only)
7836 error_at (input_location, "%<@dynamic%> is not available in Objective-C 1.0");
7837
7838 if (property_list == error_mark_node)
7839 return;
7840
7841 if (!objc_implementation_context)
7842 {
7843 /* We can get here only in Objective-C; the Objective-C++ parser
7844 detects the problem while parsing, outputs the error
7845 "misplaced '@dynamic' Objective-C++ construct" and skips the
7846 declaration. */
7847 error_at (location, "%<@dynamic%> not in @implementation context");
7848 return;
7849 }
7850
7851 /* @dynamic is allowed in categories. */
7852 switch (TREE_CODE (objc_implementation_context))
7853 {
7854 case CLASS_IMPLEMENTATION_TYPE:
7855 interface = lookup_interface (CLASS_NAME (objc_implementation_context));
7856 break;
7857 case CATEGORY_IMPLEMENTATION_TYPE:
7858 interface = lookup_category (implementation_template,
7859 CLASS_SUPER_NAME (objc_implementation_context));
7860 break;
7861 default:
7862 gcc_unreachable ();
7863 }
7864
7865 if (!interface)
7866 {
7867 /* I can't see how this could happen, but it is good as a safety check. */
7868 error_at (location,
7869 "%<@dynamic%> requires the @interface of the class to be available");
7870 return;
7871 }
7872
7873 /* Now, iterate over the properties and do each of them. */
7874 for (chain = property_list; chain; chain = TREE_CHAIN (chain))
7875 {
7876 objc_add_dynamic_declaration_for_property (location, interface, TREE_VALUE (chain));
7877 }
7878 }
7879
7880 /* Main routine to generate code/data for all the property information for
7881 current implementation (class or category). CLASS is the interface where
7882 ivars are declared. CLASS_METHODS is where methods are found which
7883 could be a class or a category depending on whether we are implementing
7884 property of a class or a category. */
7885
7886 static void
objc_gen_property_data(tree klass,tree class_methods)7887 objc_gen_property_data (tree klass, tree class_methods)
7888 {
7889 tree x;
7890
7891 for (x = IMPL_PROPERTY_DECL (objc_implementation_context); x; x = TREE_CHAIN (x))
7892 {
7893 /* @dynamic property - nothing to check or synthesize. */
7894 if (PROPERTY_DYNAMIC (x))
7895 continue;
7896
7897 /* @synthesize property - need to synthesize the accessors. */
7898 if (PROPERTY_IVAR_NAME (x))
7899 {
7900 objc_synthesize_getter (klass, class_methods, x);
7901
7902 if (PROPERTY_READONLY (x) == 0)
7903 objc_synthesize_setter (klass, class_methods, x);
7904
7905 continue;
7906 }
7907
7908 gcc_unreachable ();
7909 }
7910 }
7911
7912 /* This is called once we see the "@end" in an interface/implementation. */
7913
7914 static void
finish_class(tree klass)7915 finish_class (tree klass)
7916 {
7917 switch (TREE_CODE (klass))
7918 {
7919 case CLASS_IMPLEMENTATION_TYPE:
7920 {
7921 /* All metadata generation is done in runtime.generate_metadata(). */
7922
7923 /* Generate what needed for property; setters, getters, etc. */
7924 objc_gen_property_data (implementation_template, implementation_template);
7925
7926 if (implementation_template != objc_implementation_context)
7927 {
7928 /* Ensure that all method listed in the interface contain bodies. */
7929 check_methods (CLASS_CLS_METHODS (implementation_template),
7930 objc_implementation_context, '+');
7931 check_methods (CLASS_NST_METHODS (implementation_template),
7932 objc_implementation_context, '-');
7933
7934 if (CLASS_PROTOCOL_LIST (implementation_template))
7935 check_protocols (CLASS_PROTOCOL_LIST (implementation_template),
7936 "class",
7937 CLASS_NAME (objc_implementation_context));
7938 }
7939 break;
7940 }
7941 case CATEGORY_IMPLEMENTATION_TYPE:
7942 {
7943 tree category = lookup_category (implementation_template, CLASS_SUPER_NAME (klass));
7944
7945 if (category)
7946 {
7947 /* Generate what needed for property; setters, getters, etc. */
7948 objc_gen_property_data (implementation_template, category);
7949
7950 /* Ensure all method listed in the interface contain bodies. */
7951 check_methods (CLASS_CLS_METHODS (category),
7952 objc_implementation_context, '+');
7953 check_methods (CLASS_NST_METHODS (category),
7954 objc_implementation_context, '-');
7955
7956 if (CLASS_PROTOCOL_LIST (category))
7957 check_protocols (CLASS_PROTOCOL_LIST (category),
7958 "category",
7959 CLASS_SUPER_NAME (objc_implementation_context));
7960 }
7961 break;
7962 }
7963 case CLASS_INTERFACE_TYPE:
7964 case CATEGORY_INTERFACE_TYPE:
7965 case PROTOCOL_INTERFACE_TYPE:
7966 {
7967 /* Process properties of the class. */
7968 tree x;
7969 for (x = CLASS_PROPERTY_DECL (objc_interface_context); x; x = TREE_CHAIN (x))
7970 {
7971 /* Now we check that the appropriate getter is declared,
7972 and if not, we declare one ourselves. */
7973 tree getter_decl = lookup_method (CLASS_NST_METHODS (klass),
7974 PROPERTY_GETTER_NAME (x));
7975
7976 if (getter_decl)
7977 {
7978 /* TODO: Check that the declaration is consistent with the property. */
7979 ;
7980 }
7981 else
7982 {
7983 /* Generate an instance method declaration for the
7984 getter; for example "- (id) name;". In general it
7985 will be of the form
7986 -(type)property_getter_name; */
7987 tree rettype = build_tree_list (NULL_TREE, TREE_TYPE (x));
7988 getter_decl = build_method_decl (INSTANCE_METHOD_DECL,
7989 rettype, PROPERTY_GETTER_NAME (x),
7990 NULL_TREE, false);
7991 if (PROPERTY_OPTIONAL (x))
7992 objc_add_method (objc_interface_context, getter_decl, false, true);
7993 else
7994 objc_add_method (objc_interface_context, getter_decl, false, false);
7995 TREE_DEPRECATED (getter_decl) = TREE_DEPRECATED (x);
7996 METHOD_PROPERTY_CONTEXT (getter_decl) = x;
7997 }
7998
7999 if (PROPERTY_READONLY (x) == 0)
8000 {
8001 /* Now we check that the appropriate setter is declared,
8002 and if not, we declare on ourselves. */
8003 tree setter_decl = lookup_method (CLASS_NST_METHODS (klass),
8004 PROPERTY_SETTER_NAME (x));
8005
8006 if (setter_decl)
8007 {
8008 /* TODO: Check that the declaration is consistent with the property. */
8009 ;
8010 }
8011 else
8012 {
8013 /* The setter name is something like 'setName:'.
8014 We need the substring 'setName' to build the
8015 method declaration due to how the declaration
8016 works. TODO: build_method_decl() will then
8017 generate back 'setName:' from 'setName'; it
8018 would be more efficient to hook into there. */
8019 const char *full_setter_name = IDENTIFIER_POINTER (PROPERTY_SETTER_NAME (x));
8020 size_t length = strlen (full_setter_name);
8021 char *setter_name = (char *) alloca (length);
8022 tree ret_type, selector, arg_type, arg_name;
8023
8024 memcpy (setter_name, full_setter_name, length - 1);
8025 setter_name[length - 1] = '\0';
8026 ret_type = build_tree_list (NULL_TREE, void_type_node);
8027 arg_type = build_tree_list (NULL_TREE, TREE_TYPE (x));
8028 arg_name = get_identifier ("_value");
8029 selector = objc_build_keyword_decl (get_identifier (setter_name),
8030 arg_type, arg_name, NULL);
8031 setter_decl = build_method_decl (INSTANCE_METHOD_DECL,
8032 ret_type, selector,
8033 build_tree_list (NULL_TREE, NULL_TREE),
8034 false);
8035 if (PROPERTY_OPTIONAL (x))
8036 objc_add_method (objc_interface_context, setter_decl, false, true);
8037 else
8038 objc_add_method (objc_interface_context, setter_decl, false, false);
8039 TREE_DEPRECATED (setter_decl) = TREE_DEPRECATED (x);
8040 METHOD_PROPERTY_CONTEXT (setter_decl) = x;
8041 }
8042 }
8043 }
8044 break;
8045 }
8046 default:
8047 gcc_unreachable ();
8048 break;
8049 }
8050 }
8051
8052 static tree
add_protocol(tree protocol)8053 add_protocol (tree protocol)
8054 {
8055 /* Put protocol on list in reverse order. */
8056 TREE_CHAIN (protocol) = protocol_chain;
8057 protocol_chain = protocol;
8058 return protocol_chain;
8059 }
8060
8061 /* Check that a protocol is defined, and, recursively, that all
8062 protocols that this protocol conforms to are defined too. */
8063 static void
check_that_protocol_is_defined(tree protocol)8064 check_that_protocol_is_defined (tree protocol)
8065 {
8066 if (!PROTOCOL_DEFINED (protocol))
8067 warning (0, "definition of protocol %qE not found",
8068 PROTOCOL_NAME (protocol));
8069
8070 /* If the protocol itself conforms to other protocols, check them
8071 too, recursively. */
8072 if (PROTOCOL_LIST (protocol))
8073 {
8074 tree p;
8075
8076 for (p = PROTOCOL_LIST (protocol); p; p = TREE_CHAIN (p))
8077 check_that_protocol_is_defined (TREE_VALUE (p));
8078 }
8079 }
8080
8081 /* Looks up a protocol. If 'warn_if_deprecated' is true, a warning is
8082 emitted if the protocol is deprecated. If 'definition_required' is
8083 true, a warning is emitted if a full @protocol definition has not
8084 been seen. */
8085 static tree
lookup_protocol(tree ident,bool warn_if_deprecated,bool definition_required)8086 lookup_protocol (tree ident, bool warn_if_deprecated, bool definition_required)
8087 {
8088 tree chain;
8089
8090 for (chain = protocol_chain; chain; chain = TREE_CHAIN (chain))
8091 if (ident == PROTOCOL_NAME (chain))
8092 {
8093 if (warn_if_deprecated && TREE_DEPRECATED (chain))
8094 {
8095 /* It would be nice to use warn_deprecated_use() here, but
8096 we are using TREE_CHAIN (which is supposed to be the
8097 TYPE_STUB_DECL for a TYPE) for something different. */
8098 warning (OPT_Wdeprecated_declarations, "protocol %qE is deprecated",
8099 PROTOCOL_NAME (chain));
8100 }
8101
8102 if (definition_required)
8103 check_that_protocol_is_defined (chain);
8104
8105 return chain;
8106 }
8107
8108 return NULL_TREE;
8109 }
8110
8111 /* This function forward declares the protocols named by NAMES. If
8112 they are already declared or defined, the function has no effect. */
8113
8114 void
objc_declare_protocol(tree name,tree attributes)8115 objc_declare_protocol (tree name, tree attributes)
8116 {
8117 bool deprecated = false;
8118
8119 #ifdef OBJCPLUS
8120 if (current_namespace != global_namespace) {
8121 error ("Objective-C declarations may only appear in global scope");
8122 }
8123 #endif /* OBJCPLUS */
8124
8125 /* Determine if 'deprecated', the only attribute we recognize for
8126 protocols, was used. Ignore all other attributes. */
8127 if (attributes)
8128 {
8129 tree attribute;
8130 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
8131 {
8132 tree name = TREE_PURPOSE (attribute);
8133
8134 if (is_attribute_p ("deprecated", name))
8135 deprecated = true;
8136 else
8137 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
8138 }
8139 }
8140
8141 if (lookup_protocol (name, /* warn if deprecated */ false,
8142 /* definition_required */ false) == NULL_TREE)
8143 {
8144 tree protocol = make_node (PROTOCOL_INTERFACE_TYPE);
8145
8146 TYPE_LANG_SLOT_1 (protocol)
8147 = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8148 PROTOCOL_NAME (protocol) = name;
8149 PROTOCOL_LIST (protocol) = NULL_TREE;
8150 add_protocol (protocol);
8151 PROTOCOL_DEFINED (protocol) = 0;
8152 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8153
8154 if (attributes)
8155 {
8156 /* TODO: Do we need to store the attributes here ? */
8157 TYPE_ATTRIBUTES (protocol) = attributes;
8158 if (deprecated)
8159 TREE_DEPRECATED (protocol) = 1;
8160 }
8161 }
8162 }
8163
8164 static tree
start_protocol(enum tree_code code,tree name,tree list,tree attributes)8165 start_protocol (enum tree_code code, tree name, tree list, tree attributes)
8166 {
8167 tree protocol;
8168 bool deprecated = false;
8169
8170 #ifdef OBJCPLUS
8171 if (current_namespace != global_namespace) {
8172 error ("Objective-C declarations may only appear in global scope");
8173 }
8174 #endif /* OBJCPLUS */
8175
8176 /* Determine if 'deprecated', the only attribute we recognize for
8177 protocols, was used. Ignore all other attributes. */
8178 if (attributes)
8179 {
8180 tree attribute;
8181 for (attribute = attributes; attribute; attribute = TREE_CHAIN (attribute))
8182 {
8183 tree name = TREE_PURPOSE (attribute);
8184
8185 if (is_attribute_p ("deprecated", name))
8186 deprecated = true;
8187 else
8188 warning (OPT_Wattributes, "%qE attribute directive ignored", name);
8189 }
8190 }
8191
8192 protocol = lookup_protocol (name, /* warn_if_deprecated */ false,
8193 /* definition_required */ false);
8194
8195 if (!protocol)
8196 {
8197 protocol = make_node (code);
8198 TYPE_LANG_SLOT_1 (protocol) = make_tree_vec (PROTOCOL_LANG_SLOT_ELTS);
8199
8200 PROTOCOL_NAME (protocol) = name;
8201 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list, /* definition_required */ false);
8202 add_protocol (protocol);
8203 PROTOCOL_DEFINED (protocol) = 1;
8204 PROTOCOL_FORWARD_DECL (protocol) = NULL_TREE;
8205
8206 check_protocol_recursively (protocol, list);
8207 }
8208 else if (! PROTOCOL_DEFINED (protocol))
8209 {
8210 PROTOCOL_DEFINED (protocol) = 1;
8211 PROTOCOL_LIST (protocol) = lookup_and_install_protocols (list, /* definition_required */ false);
8212
8213 check_protocol_recursively (protocol, list);
8214 }
8215 else
8216 {
8217 warning (0, "duplicate declaration for protocol %qE",
8218 name);
8219 }
8220
8221 if (attributes)
8222 {
8223 TYPE_ATTRIBUTES (protocol) = attributes;
8224 if (deprecated)
8225 TREE_DEPRECATED (protocol) = 1;
8226 }
8227
8228 return protocol;
8229 }
8230
8231 /* Decay array and function parameters into pointers. */
8232
8233 static tree
objc_decay_parm_type(tree type)8234 objc_decay_parm_type (tree type)
8235 {
8236 if (TREE_CODE (type) == ARRAY_TYPE || TREE_CODE (type) == FUNCTION_TYPE)
8237 type = build_pointer_type (TREE_CODE (type) == ARRAY_TYPE
8238 ? TREE_TYPE (type)
8239 : type);
8240
8241 return type;
8242 }
8243
8244 static GTY(()) tree objc_parmlist = NULL_TREE;
8245
8246 /* Append PARM to a list of formal parameters of a method, making a necessary
8247 array-to-pointer adjustment along the way. */
8248
8249 void
objc_push_parm(tree parm)8250 objc_push_parm (tree parm)
8251 {
8252 tree type;
8253
8254 if (TREE_TYPE (parm) == error_mark_node)
8255 {
8256 objc_parmlist = chainon (objc_parmlist, parm);
8257 return;
8258 }
8259
8260 /* Decay arrays and functions into pointers. */
8261 type = objc_decay_parm_type (TREE_TYPE (parm));
8262
8263 /* If the parameter type has been decayed, a new PARM_DECL needs to be
8264 built as well. */
8265 if (type != TREE_TYPE (parm))
8266 parm = build_decl (input_location, PARM_DECL, DECL_NAME (parm), type);
8267
8268 DECL_ARG_TYPE (parm)
8269 = lang_hooks.types.type_promotes_to (TREE_TYPE (parm));
8270
8271 /* Record constancy and volatility. */
8272 c_apply_type_quals_to_decl
8273 ((TYPE_READONLY (TREE_TYPE (parm)) ? TYPE_QUAL_CONST : 0)
8274 | (TYPE_RESTRICT (TREE_TYPE (parm)) ? TYPE_QUAL_RESTRICT : 0)
8275 | (TYPE_ATOMIC (TREE_TYPE (parm)) ? TYPE_QUAL_ATOMIC : 0)
8276 | (TYPE_VOLATILE (TREE_TYPE (parm)) ? TYPE_QUAL_VOLATILE : 0), parm);
8277
8278 objc_parmlist = chainon (objc_parmlist, parm);
8279 }
8280
8281 /* Retrieve the formal parameter list constructed via preceding calls to
8282 objc_push_parm(). */
8283
8284 #ifdef OBJCPLUS
8285 tree
objc_get_parm_info(int have_ellipsis ATTRIBUTE_UNUSED,tree expr ATTRIBUTE_UNUSED)8286 objc_get_parm_info (int have_ellipsis ATTRIBUTE_UNUSED,
8287 tree expr ATTRIBUTE_UNUSED)
8288 {
8289 tree parm_info = objc_parmlist;
8290 objc_parmlist = NULL_TREE;
8291
8292 return parm_info;
8293 }
8294 #else
8295 struct c_arg_info *
objc_get_parm_info(int have_ellipsis,tree expr)8296 objc_get_parm_info (int have_ellipsis, tree expr)
8297 {
8298 tree parm_info = objc_parmlist;
8299 struct c_arg_info *arg_info;
8300 /* The C front-end requires an elaborate song and dance at
8301 this point. */
8302 push_scope ();
8303 declare_parm_level ();
8304 while (parm_info)
8305 {
8306 tree next = DECL_CHAIN (parm_info);
8307
8308 DECL_CHAIN (parm_info) = NULL_TREE;
8309 parm_info = pushdecl (parm_info);
8310 finish_decl (parm_info, input_location, NULL_TREE, NULL_TREE, NULL_TREE);
8311 parm_info = next;
8312 }
8313 arg_info = get_parm_info (have_ellipsis, expr);
8314 pop_scope ();
8315 objc_parmlist = NULL_TREE;
8316 return arg_info;
8317 }
8318 #endif
8319
8320 /* Synthesize the formal parameters 'id self' and 'SEL _cmd' needed for ObjC
8321 method definitions. In the case of instance methods, we can be more
8322 specific as to the type of 'self'. */
8323
8324 static void
synth_self_and_ucmd_args(void)8325 synth_self_and_ucmd_args (void)
8326 {
8327 tree self_type;
8328
8329 if (objc_method_context
8330 && TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL)
8331 self_type = objc_instance_type;
8332 else
8333 /* Really a `struct objc_class *'. However, we allow people to
8334 assign to self, which changes its type midstream. */
8335 self_type = objc_object_type;
8336
8337 /* id self; */
8338 objc_push_parm (build_decl (input_location,
8339 PARM_DECL, self_id, self_type));
8340
8341 /* SEL _cmd; */
8342 objc_push_parm (build_decl (input_location,
8343 PARM_DECL, ucmd_id, objc_selector_type));
8344 }
8345
8346 /* Transform an Objective-C method definition into a static C function
8347 definition, synthesizing the first two arguments, "self" and "_cmd",
8348 in the process. EXPR is NULL or an expression that needs to be
8349 evaluated for the side effects of array size expressions in the
8350 parameters. */
8351
8352 static void
start_method_def(tree method,tree expr)8353 start_method_def (tree method, tree expr)
8354 {
8355 tree parmlist;
8356 #ifdef OBJCPLUS
8357 tree parm_info;
8358 #else
8359 struct c_arg_info *parm_info;
8360 #endif
8361 int have_ellipsis = 0;
8362
8363 /* If we are defining a "dealloc" method in a non-root class, we
8364 will need to check if a [super dealloc] is missing, and warn if
8365 it is. */
8366 if(CLASS_SUPER_NAME (objc_implementation_context)
8367 && !strcmp ("dealloc", IDENTIFIER_POINTER (METHOD_SEL_NAME (method))))
8368 should_call_super_dealloc = 1;
8369 else
8370 should_call_super_dealloc = 0;
8371
8372 /* Required to implement _msgSuper. */
8373 objc_method_context = method;
8374 UOBJC_SUPER_decl = NULL_TREE;
8375
8376 /* Generate prototype declarations for arguments..."new-style". */
8377 synth_self_and_ucmd_args ();
8378
8379 /* Generate argument declarations if a keyword_decl. */
8380 parmlist = METHOD_SEL_ARGS (method);
8381 while (parmlist)
8382 {
8383 /* parmlist is a KEYWORD_DECL. */
8384 tree type = TREE_VALUE (TREE_TYPE (parmlist));
8385 tree parm;
8386
8387 parm = build_decl (input_location,
8388 PARM_DECL, KEYWORD_ARG_NAME (parmlist), type);
8389 decl_attributes (&parm, DECL_ATTRIBUTES (parmlist), 0);
8390 objc_push_parm (parm);
8391 parmlist = DECL_CHAIN (parmlist);
8392 }
8393
8394 if (METHOD_ADD_ARGS (method))
8395 {
8396 tree akey;
8397
8398 for (akey = TREE_CHAIN (METHOD_ADD_ARGS (method));
8399 akey; akey = TREE_CHAIN (akey))
8400 {
8401 objc_push_parm (TREE_VALUE (akey));
8402 }
8403
8404 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
8405 have_ellipsis = 1;
8406 }
8407
8408 parm_info = objc_get_parm_info (have_ellipsis, expr);
8409
8410 really_start_method (objc_method_context, parm_info);
8411 }
8412
8413 /* Return 1 if TYPE1 is equivalent to TYPE2 for purposes of method
8414 overloading. */
8415 static int
objc_types_are_equivalent(tree type1,tree type2)8416 objc_types_are_equivalent (tree type1, tree type2)
8417 {
8418 if (type1 == type2)
8419 return 1;
8420
8421 /* Strip away indirections. */
8422 while ((TREE_CODE (type1) == ARRAY_TYPE || TREE_CODE (type1) == POINTER_TYPE)
8423 && (TREE_CODE (type1) == TREE_CODE (type2)))
8424 type1 = TREE_TYPE (type1), type2 = TREE_TYPE (type2);
8425 if (TYPE_MAIN_VARIANT (type1) != TYPE_MAIN_VARIANT (type2))
8426 return 0;
8427
8428 /* Compare the protocol lists. */
8429 type1 = (TYPE_HAS_OBJC_INFO (type1)
8430 ? TYPE_OBJC_PROTOCOL_LIST (type1)
8431 : NULL_TREE);
8432 type2 = (TYPE_HAS_OBJC_INFO (type2)
8433 ? TYPE_OBJC_PROTOCOL_LIST (type2)
8434 : NULL_TREE);
8435
8436 /* If there are no protocols (most common case), the types are
8437 identical. */
8438 if (type1 == NULL_TREE && type2 == NULL_TREE)
8439 return 1;
8440
8441 /* If one has protocols, and the other one hasn't, they are not
8442 identical. */
8443 if ((type1 == NULL_TREE && type2 != NULL_TREE)
8444 || (type1 != NULL_TREE && type2 == NULL_TREE))
8445 return 0;
8446 else
8447 {
8448 /* Else, both have protocols, and we need to do the full
8449 comparison. It is possible that either type1 or type2
8450 contain some duplicate protocols in the list, so we can't
8451 even just compare list_length as a first check. */
8452 tree t;
8453
8454 for (t = type2; t; t = TREE_CHAIN (t))
8455 if (!lookup_protocol_in_reflist (type1, TREE_VALUE (t)))
8456 return 0;
8457
8458 for (t = type1; t; t = TREE_CHAIN (t))
8459 if (!lookup_protocol_in_reflist (type2, TREE_VALUE (t)))
8460 return 0;
8461
8462 return 1;
8463 }
8464 }
8465
8466 /* Return 1 if TYPE1 has the same size and alignment as TYPE2. */
8467
8468 static int
objc_types_share_size_and_alignment(tree type1,tree type2)8469 objc_types_share_size_and_alignment (tree type1, tree type2)
8470 {
8471 return (simple_cst_equal (TYPE_SIZE (type1), TYPE_SIZE (type2))
8472 && TYPE_ALIGN (type1) == TYPE_ALIGN (type2));
8473 }
8474
8475 /* Return 1 if PROTO1 is equivalent to PROTO2
8476 for purposes of method overloading. Ordinarily, the type signatures
8477 should match up exactly, unless STRICT is zero, in which case we
8478 shall allow differences in which the size and alignment of a type
8479 is the same. */
8480
8481 static int
comp_proto_with_proto(tree proto1,tree proto2,int strict)8482 comp_proto_with_proto (tree proto1, tree proto2, int strict)
8483 {
8484 tree type1, type2;
8485
8486 /* The following test is needed in case there are hashing
8487 collisions. */
8488 if (METHOD_SEL_NAME (proto1) != METHOD_SEL_NAME (proto2))
8489 return 0;
8490
8491 /* Compare return types. */
8492 type1 = TREE_VALUE (TREE_TYPE (proto1));
8493 type2 = TREE_VALUE (TREE_TYPE (proto2));
8494
8495 if (!objc_types_are_equivalent (type1, type2)
8496 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8497 return 0;
8498
8499 /* Compare argument types. */
8500
8501 /* The first argument (objc_object_type) is always the same, no need
8502 to compare. */
8503
8504 /* The second argument (objc_selector_type) is always the same, no
8505 need to compare. */
8506
8507 /* Compare the other arguments. */
8508 {
8509 tree arg1, arg2;
8510
8511 /* Compare METHOD_SEL_ARGS. */
8512 for (arg1 = METHOD_SEL_ARGS (proto1), arg2 = METHOD_SEL_ARGS (proto2);
8513 arg1 && arg2;
8514 arg1 = DECL_CHAIN (arg1), arg2 = DECL_CHAIN (arg2))
8515 {
8516 type1 = TREE_VALUE (TREE_TYPE (arg1));
8517 type2 = TREE_VALUE (TREE_TYPE (arg2));
8518
8519 /* FIXME: Do we need to decay argument types to compare them ? */
8520 type1 = objc_decay_parm_type (type1);
8521 type2 = objc_decay_parm_type (type2);
8522
8523 if (!objc_types_are_equivalent (type1, type2)
8524 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8525 return 0;
8526 }
8527
8528 /* The loop ends when arg1 or arg2 are NULL. Make sure they are
8529 both NULL. */
8530 if (arg1 != arg2)
8531 return 0;
8532
8533 /* Compare METHOD_ADD_ARGS. */
8534 if ((METHOD_ADD_ARGS (proto1) && !METHOD_ADD_ARGS (proto2))
8535 || (METHOD_ADD_ARGS (proto2) && !METHOD_ADD_ARGS (proto1)))
8536 return 0;
8537
8538 if (METHOD_ADD_ARGS (proto1))
8539 {
8540 for (arg1 = TREE_CHAIN (METHOD_ADD_ARGS (proto1)), arg2 = TREE_CHAIN (METHOD_ADD_ARGS (proto2));
8541 arg1 && arg2;
8542 arg1 = TREE_CHAIN (arg1), arg2 = TREE_CHAIN (arg2))
8543 {
8544 type1 = TREE_TYPE (TREE_VALUE (arg1));
8545 type2 = TREE_TYPE (TREE_VALUE (arg2));
8546
8547 /* FIXME: Do we need to decay argument types to compare them ? */
8548 type1 = objc_decay_parm_type (type1);
8549 type2 = objc_decay_parm_type (type2);
8550
8551 if (!objc_types_are_equivalent (type1, type2)
8552 && (strict || !objc_types_share_size_and_alignment (type1, type2)))
8553 return 0;
8554 }
8555 }
8556
8557 /* The loop ends when arg1 or arg2 are NULL. Make sure they are
8558 both NULL. */
8559 if (arg1 != arg2)
8560 return 0;
8561
8562 /* Compare METHOD_ADD_ARGS_ELLIPSIS_P. */
8563 if (METHOD_ADD_ARGS_ELLIPSIS_P (proto1) != METHOD_ADD_ARGS_ELLIPSIS_P (proto2))
8564 return 0;
8565 }
8566
8567 /* Success. */
8568 return 1;
8569 }
8570
8571 /* This routine returns true if TYPE is a valid objc object type,
8572 suitable for messaging; false otherwise. If 'accept_class' is
8573 'true', then a Class object is considered valid for messaging and
8574 'true' is returned if 'type' refers to a Class. If 'accept_class'
8575 is 'false', then a Class object is not considered valid for
8576 messaging and 'false' is returned in that case. */
8577
8578 static bool
objc_type_valid_for_messaging(tree type,bool accept_classes)8579 objc_type_valid_for_messaging (tree type, bool accept_classes)
8580 {
8581 if (!POINTER_TYPE_P (type))
8582 return false;
8583
8584 /* Remove the pointer indirection; don't remove more than one
8585 otherwise we'd consider "NSObject **" a valid type for messaging,
8586 which it isn't. */
8587 type = TREE_TYPE (type);
8588
8589 if (TREE_CODE (type) != RECORD_TYPE)
8590 return false;
8591
8592 if (objc_is_object_id (type))
8593 return true;
8594
8595 if (objc_is_class_id (type))
8596 return accept_classes;
8597
8598 if (TYPE_HAS_OBJC_INFO (type))
8599 return true;
8600
8601 return false;
8602 }
8603
8604 void
objc_start_function(tree name,tree type,tree attrs,tree params)8605 objc_start_function (tree name, tree type, tree attrs,
8606 #ifdef OBJCPLUS
8607 tree params
8608 #else
8609 struct c_arg_info *params
8610 #endif
8611 )
8612 {
8613 tree fndecl = build_decl (input_location,
8614 FUNCTION_DECL, name, type);
8615
8616 #ifdef OBJCPLUS
8617 DECL_ARGUMENTS (fndecl) = params;
8618 DECL_INITIAL (fndecl) = error_mark_node;
8619 DECL_EXTERNAL (fndecl) = 0;
8620 TREE_STATIC (fndecl) = 1;
8621 retrofit_lang_decl (fndecl);
8622 cplus_decl_attributes (&fndecl, attrs, 0);
8623 start_preparsed_function (fndecl, attrs, /*flags=*/SF_DEFAULT);
8624 #else
8625 current_function_returns_value = 0; /* Assume, until we see it does. */
8626 current_function_returns_null = 0;
8627 decl_attributes (&fndecl, attrs, 0);
8628 announce_function (fndecl);
8629 DECL_INITIAL (fndecl) = error_mark_node;
8630 DECL_EXTERNAL (fndecl) = 0;
8631 TREE_STATIC (fndecl) = 1;
8632 current_function_decl = pushdecl (fndecl);
8633 push_scope ();
8634 declare_parm_level ();
8635 DECL_RESULT (current_function_decl)
8636 = build_decl (input_location,
8637 RESULT_DECL, NULL_TREE,
8638 TREE_TYPE (TREE_TYPE (current_function_decl)));
8639 DECL_ARTIFICIAL (DECL_RESULT (current_function_decl)) = 1;
8640 DECL_IGNORED_P (DECL_RESULT (current_function_decl)) = 1;
8641 start_fname_decls ();
8642 store_parm_decls_from (params);
8643 #endif
8644
8645 TREE_USED (current_function_decl) = 1;
8646 }
8647
8648 /* - Generate an identifier for the function. the format is "_n_cls",
8649 where 1 <= n <= nMethods, and cls is the name the implementation we
8650 are processing.
8651 - Install the return type from the method declaration.
8652 - If we have a prototype, check for type consistency. */
8653
8654 static void
really_start_method(tree method,tree parmlist)8655 really_start_method (tree method,
8656 #ifdef OBJCPLUS
8657 tree parmlist
8658 #else
8659 struct c_arg_info *parmlist
8660 #endif
8661 )
8662 {
8663 tree ret_type, meth_type;
8664 tree method_id;
8665 const char *sel_name, *class_name, *cat_name;
8666 char *buf;
8667
8668 /* Synth the storage class & assemble the return type. */
8669 ret_type = TREE_VALUE (TREE_TYPE (method));
8670
8671 sel_name = IDENTIFIER_POINTER (METHOD_SEL_NAME (method));
8672 class_name = IDENTIFIER_POINTER (CLASS_NAME (objc_implementation_context));
8673 cat_name = ((TREE_CODE (objc_implementation_context)
8674 == CLASS_IMPLEMENTATION_TYPE)
8675 ? NULL
8676 : IDENTIFIER_POINTER (CLASS_SUPER_NAME (objc_implementation_context)));
8677 method_slot++;
8678
8679 /* Make sure this is big enough for any plausible method label. */
8680 buf = (char *) alloca (50 + strlen (sel_name) + strlen (class_name)
8681 + (cat_name ? strlen (cat_name) : 0));
8682
8683 OBJC_GEN_METHOD_LABEL (buf, TREE_CODE (method) == INSTANCE_METHOD_DECL,
8684 class_name, cat_name, sel_name, method_slot);
8685
8686 method_id = get_identifier (buf);
8687
8688 #ifdef OBJCPLUS
8689 /* Objective-C methods cannot be overloaded, so we don't need
8690 the type encoding appended. It looks bad anyway... */
8691 push_lang_context (lang_name_c);
8692 #endif
8693
8694 meth_type = build_function_type_for_method (ret_type, method, METHOD_DEF, 0);
8695 objc_start_function (method_id, meth_type, NULL_TREE, parmlist);
8696
8697 /* Set self_decl from the first argument. */
8698 self_decl = DECL_ARGUMENTS (current_function_decl);
8699
8700 /* Suppress unused warnings. */
8701 TREE_USED (self_decl) = 1;
8702 DECL_READ_P (self_decl) = 1;
8703 TREE_USED (DECL_CHAIN (self_decl)) = 1;
8704 DECL_READ_P (DECL_CHAIN (self_decl)) = 1;
8705 #ifdef OBJCPLUS
8706 pop_lang_context ();
8707 #endif
8708
8709 METHOD_DEFINITION (method) = current_function_decl;
8710
8711 /* Check consistency...start_function, pushdecl, duplicate_decls. */
8712
8713 if (implementation_template != objc_implementation_context)
8714 {
8715 tree proto
8716 = lookup_method_static (implementation_template,
8717 METHOD_SEL_NAME (method),
8718 ((TREE_CODE (method) == CLASS_METHOD_DECL)
8719 | OBJC_LOOKUP_NO_SUPER));
8720
8721 if (proto)
8722 {
8723 if (!comp_proto_with_proto (method, proto, 1))
8724 {
8725 bool type = TREE_CODE (method) == INSTANCE_METHOD_DECL;
8726
8727 warning_at (DECL_SOURCE_LOCATION (method), 0,
8728 "conflicting types for %<%c%s%>",
8729 (type ? '-' : '+'),
8730 identifier_to_locale (gen_method_decl (method)));
8731 inform (DECL_SOURCE_LOCATION (proto),
8732 "previous declaration of %<%c%s%>",
8733 (type ? '-' : '+'),
8734 identifier_to_locale (gen_method_decl (proto)));
8735 }
8736 else
8737 {
8738 /* If the method in the @interface was deprecated, mark
8739 the implemented method as deprecated too. It should
8740 never be used for messaging (when the deprecation
8741 warnings are produced), but just in case. */
8742 if (TREE_DEPRECATED (proto))
8743 TREE_DEPRECATED (method) = 1;
8744
8745 /* If the method in the @interface was marked as
8746 'noreturn', mark the function implementing the method
8747 as 'noreturn' too. */
8748 TREE_THIS_VOLATILE (current_function_decl) = TREE_THIS_VOLATILE (proto);
8749 }
8750 }
8751 else
8752 {
8753 /* We have a method @implementation even though we did not
8754 see a corresponding @interface declaration (which is allowed
8755 by Objective-C rules). Go ahead and place the method in
8756 the @interface anyway, so that message dispatch lookups
8757 will see it. */
8758 tree interface = implementation_template;
8759
8760 if (TREE_CODE (objc_implementation_context)
8761 == CATEGORY_IMPLEMENTATION_TYPE)
8762 interface = lookup_category
8763 (interface,
8764 CLASS_SUPER_NAME (objc_implementation_context));
8765
8766 if (interface)
8767 objc_add_method (interface, copy_node (method),
8768 TREE_CODE (method) == CLASS_METHOD_DECL,
8769 /* is_optional= */ false);
8770 }
8771 }
8772 }
8773
8774 static void *UOBJC_SUPER_scope = 0;
8775
8776 /* _n_Method (id self, SEL sel, ...)
8777 {
8778 struct objc_super _S;
8779 _msgSuper ((_S.self = self, _S.class = _cls, &_S), ...);
8780 } */
8781
8782 static tree
get_super_receiver(void)8783 get_super_receiver (void)
8784 {
8785 if (objc_method_context)
8786 {
8787 tree super_expr, super_expr_list, class_expr;
8788 bool inst_meth;
8789 if (!UOBJC_SUPER_decl)
8790 {
8791 UOBJC_SUPER_decl = build_decl (input_location,
8792 VAR_DECL, get_identifier (TAG_SUPER),
8793 objc_super_template);
8794 /* This prevents `unused variable' warnings when compiling with -Wall. */
8795 TREE_USED (UOBJC_SUPER_decl) = 1;
8796 DECL_READ_P (UOBJC_SUPER_decl) = 1;
8797 lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
8798 finish_decl (UOBJC_SUPER_decl, input_location, NULL_TREE, NULL_TREE,
8799 NULL_TREE);
8800 UOBJC_SUPER_scope = objc_get_current_scope ();
8801 }
8802
8803 /* Set receiver to self. */
8804 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
8805 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
8806 NOP_EXPR, input_location, self_decl,
8807 NULL_TREE);
8808 super_expr_list = super_expr;
8809
8810 /* Set class to begin searching. */
8811 /* Get the ident for the superclass class field & build a ref to it.
8812 ??? maybe we should just name the field the same for all runtimes. */
8813 super_expr = (*runtime.super_superclassfield_ident) ();
8814 super_expr = objc_build_component_ref (UOBJC_SUPER_decl, super_expr);
8815
8816 gcc_assert (imp_list->imp_context == objc_implementation_context
8817 && imp_list->imp_template == implementation_template);
8818 inst_meth = (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL);
8819
8820 if (TREE_CODE (objc_implementation_context) == CLASS_IMPLEMENTATION_TYPE)
8821 class_expr = (*runtime.get_class_super_ref) (input_location,
8822 imp_list, inst_meth);
8823 else
8824 /* We have a category. */
8825 {
8826 tree super_name = CLASS_SUPER_NAME (imp_list->imp_template);
8827 tree super_class;
8828
8829 /* Barf if super used in a category of a root object. */
8830 if (!super_name)
8831 {
8832 error ("no super class declared in interface for %qE",
8833 CLASS_NAME (imp_list->imp_template));
8834 return error_mark_node;
8835 }
8836
8837 super_class = (*runtime.get_category_super_ref) (input_location,
8838 imp_list, inst_meth);
8839 class_expr = build_c_cast (input_location,
8840 TREE_TYPE (super_expr), super_class);
8841 }
8842
8843 super_expr = build_modify_expr (input_location, super_expr, NULL_TREE,
8844 NOP_EXPR,
8845 input_location, class_expr, NULL_TREE);
8846
8847 super_expr_list = build_compound_expr (input_location,
8848 super_expr_list, super_expr);
8849
8850 super_expr = build_unary_op (input_location,
8851 ADDR_EXPR, UOBJC_SUPER_decl, 0);
8852 super_expr_list = build_compound_expr (input_location,
8853 super_expr_list, super_expr);
8854
8855 return super_expr_list;
8856 }
8857 else
8858 {
8859 error ("%<[super ...]%> must appear in a method context");
8860 return error_mark_node;
8861 }
8862 }
8863
8864 /* When exiting a scope, sever links to a 'super' declaration (if any)
8865 therein contained. */
8866
8867 void
objc_clear_super_receiver(void)8868 objc_clear_super_receiver (void)
8869 {
8870 if (objc_method_context
8871 && UOBJC_SUPER_scope == objc_get_current_scope ())
8872 {
8873 UOBJC_SUPER_decl = 0;
8874 UOBJC_SUPER_scope = 0;
8875 }
8876 }
8877
8878 void
objc_finish_method_definition(tree fndecl)8879 objc_finish_method_definition (tree fndecl)
8880 {
8881 /* We cannot validly inline ObjC methods, at least not without a language
8882 extension to declare that a method need not be dynamically
8883 dispatched, so suppress all thoughts of doing so. */
8884 DECL_UNINLINABLE (fndecl) = 1;
8885
8886 #ifndef OBJCPLUS
8887 /* The C++ front-end will have called finish_function() for us. */
8888 finish_function ();
8889 #endif
8890
8891 METHOD_ENCODING (objc_method_context)
8892 = encode_method_prototype (objc_method_context);
8893
8894 /* Required to implement _msgSuper. This must be done AFTER finish_function,
8895 since the optimizer may find "may be used before set" errors. */
8896 objc_method_context = NULL_TREE;
8897
8898 if (should_call_super_dealloc)
8899 warning (0, "method possibly missing a [super dealloc] call");
8900 }
8901
8902 /* Given a tree DECL node, produce a printable description of it in the given
8903 buffer, overwriting the buffer. */
8904
8905 static char *
gen_declaration(tree decl)8906 gen_declaration (tree decl)
8907 {
8908 errbuf[0] = '\0';
8909
8910 if (DECL_P (decl))
8911 {
8912 gen_type_name_0 (TREE_TYPE (decl));
8913
8914 if (DECL_NAME (decl))
8915 {
8916 if (!POINTER_TYPE_P (TREE_TYPE (decl)))
8917 strcat (errbuf, " ");
8918
8919 strcat (errbuf, IDENTIFIER_POINTER (DECL_NAME (decl)));
8920 }
8921
8922 #ifdef OBJCPLUS
8923 tree w = DECL_BIT_FIELD_REPRESENTATIVE (decl);
8924 #else
8925 tree w = DECL_INITIAL (decl);
8926 #endif
8927 if (w)
8928 {
8929 STRIP_ANY_LOCATION_WRAPPER (w);
8930 if (TREE_CODE (w) == INTEGER_CST)
8931 sprintf (errbuf + strlen (errbuf), ": " HOST_WIDE_INT_PRINT_DEC,
8932 TREE_INT_CST_LOW (w));
8933 }
8934 }
8935
8936 return errbuf;
8937 }
8938
8939 /* Given a tree TYPE node, produce a printable description of it in the given
8940 buffer, overwriting the buffer. */
8941
8942 static char *
gen_type_name_0(tree type)8943 gen_type_name_0 (tree type)
8944 {
8945 tree orig = type, proto;
8946
8947 if (TYPE_P (type) && TYPE_NAME (type))
8948 type = TYPE_NAME (type);
8949 else if (POINTER_TYPE_P (type) || TREE_CODE (type) == ARRAY_TYPE)
8950 {
8951 tree inner = TREE_TYPE (type);
8952
8953 while (TREE_CODE (inner) == ARRAY_TYPE)
8954 inner = TREE_TYPE (inner);
8955
8956 gen_type_name_0 (inner);
8957
8958 if (!POINTER_TYPE_P (inner))
8959 strcat (errbuf, " ");
8960
8961 if (POINTER_TYPE_P (type))
8962 strcat (errbuf, "*");
8963 else
8964 while (type != inner)
8965 {
8966 strcat (errbuf, "[");
8967
8968 if (TYPE_DOMAIN (type))
8969 {
8970 char sz[20];
8971
8972 sprintf (sz, HOST_WIDE_INT_PRINT_DEC,
8973 (TREE_INT_CST_LOW
8974 (TYPE_MAX_VALUE (TYPE_DOMAIN (type))) + 1));
8975 strcat (errbuf, sz);
8976 }
8977
8978 strcat (errbuf, "]");
8979 type = TREE_TYPE (type);
8980 }
8981
8982 goto exit_function;
8983 }
8984
8985 if (TREE_CODE (type) == TYPE_DECL && DECL_NAME (type))
8986 type = DECL_NAME (type);
8987
8988 strcat (errbuf, TREE_CODE (type) == IDENTIFIER_NODE
8989 ? IDENTIFIER_POINTER (type)
8990 : "");
8991
8992 /* For 'id' and 'Class', adopted protocols are stored in the pointee. */
8993 if (objc_is_id (orig))
8994 orig = TREE_TYPE (orig);
8995
8996 proto = TYPE_HAS_OBJC_INFO (orig) ? TYPE_OBJC_PROTOCOL_LIST (orig) : NULL_TREE;
8997
8998 if (proto)
8999 {
9000 strcat (errbuf, " <");
9001
9002 while (proto) {
9003 strcat (errbuf,
9004 IDENTIFIER_POINTER (PROTOCOL_NAME (TREE_VALUE (proto))));
9005 proto = TREE_CHAIN (proto);
9006 strcat (errbuf, proto ? ", " : ">");
9007 }
9008 }
9009
9010 exit_function:
9011 return errbuf;
9012 }
9013
9014 static char *
gen_type_name(tree type)9015 gen_type_name (tree type)
9016 {
9017 errbuf[0] = '\0';
9018
9019 return gen_type_name_0 (type);
9020 }
9021
9022 /* Given a method tree, put a printable description into the given
9023 buffer (overwriting) and return a pointer to the buffer. */
9024
9025 static char *
gen_method_decl(tree method)9026 gen_method_decl (tree method)
9027 {
9028 tree chain;
9029
9030 strcpy (errbuf, "("); /* NB: Do _not_ call strcat() here. */
9031 gen_type_name_0 (TREE_VALUE (TREE_TYPE (method)));
9032 strcat (errbuf, ")");
9033 chain = METHOD_SEL_ARGS (method);
9034
9035 if (chain)
9036 {
9037 /* We have a chain of keyword_decls. */
9038 do
9039 {
9040 if (KEYWORD_KEY_NAME (chain))
9041 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_KEY_NAME (chain)));
9042
9043 strcat (errbuf, ":(");
9044 gen_type_name_0 (TREE_VALUE (TREE_TYPE (chain)));
9045 strcat (errbuf, ")");
9046
9047 strcat (errbuf, IDENTIFIER_POINTER (KEYWORD_ARG_NAME (chain)));
9048 if ((chain = DECL_CHAIN (chain)))
9049 strcat (errbuf, " ");
9050 }
9051 while (chain);
9052
9053 if (METHOD_ADD_ARGS (method))
9054 {
9055 chain = TREE_CHAIN (METHOD_ADD_ARGS (method));
9056
9057 /* Know we have a chain of parm_decls. */
9058 while (chain)
9059 {
9060 strcat (errbuf, ", ");
9061 gen_type_name_0 (TREE_TYPE (TREE_VALUE (chain)));
9062 chain = TREE_CHAIN (chain);
9063 }
9064
9065 if (METHOD_ADD_ARGS_ELLIPSIS_P (method))
9066 strcat (errbuf, ", ...");
9067 }
9068 }
9069
9070 else
9071 /* We have a unary selector. */
9072 strcat (errbuf, IDENTIFIER_POINTER (METHOD_SEL_NAME (method)));
9073
9074 return errbuf;
9075 }
9076
9077 /* Debug info. */
9078
9079
9080 /* Dump an @interface declaration of the supplied class CHAIN to the
9081 supplied file FP. Used to implement the -gen-decls option (which
9082 prints out an @interface declaration of all classes compiled in
9083 this run); potentially useful for debugging the compiler too. */
9084 void
dump_interface(FILE * fp,tree chain)9085 dump_interface (FILE *fp, tree chain)
9086 {
9087 /* FIXME: A heap overflow here whenever a method (or ivar)
9088 declaration is so long that it doesn't fit in the buffer. The
9089 code and all the related functions should be rewritten to avoid
9090 using fixed size buffers. */
9091 const char *my_name = IDENTIFIER_POINTER (CLASS_NAME (chain));
9092 tree ivar_decls = CLASS_RAW_IVARS (chain);
9093 tree nst_methods = CLASS_NST_METHODS (chain);
9094 tree cls_methods = CLASS_CLS_METHODS (chain);
9095
9096 fprintf (fp, "\n@interface %s", my_name);
9097
9098 /* CLASS_SUPER_NAME is used to store the superclass name for
9099 classes, and the category name for categories. */
9100 if (CLASS_SUPER_NAME (chain))
9101 {
9102 const char *name = IDENTIFIER_POINTER (CLASS_SUPER_NAME (chain));
9103
9104 switch (TREE_CODE (chain))
9105 {
9106 case CATEGORY_IMPLEMENTATION_TYPE:
9107 case CATEGORY_INTERFACE_TYPE:
9108 fprintf (fp, " (%s)\n", name);
9109 break;
9110 default:
9111 fprintf (fp, " : %s\n", name);
9112 break;
9113 }
9114 }
9115 else
9116 fprintf (fp, "\n");
9117
9118 /* FIXME - the following doesn't seem to work at the moment. */
9119 if (ivar_decls)
9120 {
9121 fprintf (fp, "{\n");
9122 do
9123 {
9124 fprintf (fp, "\t%s;\n", gen_declaration (ivar_decls));
9125 ivar_decls = TREE_CHAIN (ivar_decls);
9126 }
9127 while (ivar_decls);
9128 fprintf (fp, "}\n");
9129 }
9130
9131 while (nst_methods)
9132 {
9133 fprintf (fp, "- %s;\n", gen_method_decl (nst_methods));
9134 nst_methods = TREE_CHAIN (nst_methods);
9135 }
9136
9137 while (cls_methods)
9138 {
9139 fprintf (fp, "+ %s;\n", gen_method_decl (cls_methods));
9140 cls_methods = TREE_CHAIN (cls_methods);
9141 }
9142
9143 fprintf (fp, "@end\n");
9144 }
9145
9146 #if 0
9147 /* Produce the pretty printing for an Objective-C method. This is
9148 currently unused, but could be handy while reorganizing the pretty
9149 printing to be more robust. */
9150 static const char *
9151 objc_pretty_print_method (bool is_class_method,
9152 const char *class_name,
9153 const char *category_name,
9154 const char *selector)
9155 {
9156 if (category_name)
9157 {
9158 char *result = XNEWVEC (char, strlen (class_name) + strlen (category_name)
9159 + strlen (selector) + 7);
9160
9161 if (is_class_method)
9162 sprintf (result, "+[%s(%s) %s]", class_name, category_name, selector);
9163 else
9164 sprintf (result, "-[%s(%s) %s]", class_name, category_name, selector);
9165
9166 return result;
9167 }
9168 else
9169 {
9170 char *result = XNEWVEC (char, strlen (class_name)
9171 + strlen (selector) + 5);
9172
9173 if (is_class_method)
9174 sprintf (result, "+[%s %s]", class_name, selector);
9175 else
9176 sprintf (result, "-[%s %s]", class_name, selector);
9177
9178 return result;
9179 }
9180 }
9181 #endif
9182
9183 /* Demangle function for Objective-C. Attempt to demangle the
9184 function name associated with a method (eg, going from
9185 "_i_NSObject__class" to "-[NSObject class]"); usually for the
9186 purpose of pretty printing or error messages. Return the demangled
9187 name, or NULL if the string is not an Objective-C mangled method
9188 name.
9189
9190 Because of how the mangling is done, any method that has a '_' in
9191 its original name is at risk of being demangled incorrectly. In
9192 some cases there are multiple valid ways to demangle a method name
9193 and there is no way we can decide.
9194
9195 TODO: objc_demangle() can't always get it right; the right way to
9196 get this correct for all method names would be to store the
9197 Objective-C method name somewhere in the function decl. Then,
9198 there is no demangling to do; we'd just pull the method name out of
9199 the decl. As an additional bonus, when printing error messages we
9200 could check for such a method name, and if we find it, we know the
9201 function is actually an Objective-C method and we could print error
9202 messages saying "In method '+[NSObject class]" instead of "In
9203 function '+[NSObject class]" as we do now. */
9204 static const char *
objc_demangle(const char * mangled)9205 objc_demangle (const char *mangled)
9206 {
9207 char *demangled, *cp;
9208
9209 /* First of all, if the name is too short it can't be an Objective-C
9210 mangled method name. */
9211 if (mangled[0] == '\0' || mangled[1] == '\0' || mangled[2] == '\0')
9212 return NULL;
9213
9214 /* If the name looks like an already demangled one, return it
9215 unchanged. This should only happen on Darwin, where method names
9216 are mangled differently into a pretty-print form (such as
9217 '+[NSObject class]', see darwin.h). In that case, demangling is
9218 a no-op, but we need to return the demangled name if it was an
9219 ObjC one, and return NULL if not. We should be safe as no C/C++
9220 function can start with "-[" or "+[". */
9221 if ((mangled[0] == '-' || mangled[0] == '+')
9222 && (mangled[1] == '['))
9223 return mangled;
9224
9225 if (mangled[0] == '_' &&
9226 (mangled[1] == 'i' || mangled[1] == 'c') &&
9227 mangled[2] == '_')
9228 {
9229 cp = demangled = XNEWVEC (char, strlen(mangled) + 2);
9230 if (mangled[1] == 'i')
9231 *cp++ = '-'; /* for instance method */
9232 else
9233 *cp++ = '+'; /* for class method */
9234 *cp++ = '['; /* opening left brace */
9235 strcpy(cp, mangled+3); /* tack on the rest of the mangled name */
9236 while (*cp && *cp == '_')
9237 cp++; /* skip any initial underbars in class name */
9238 cp = strchr(cp, '_'); /* find first non-initial underbar */
9239 if (cp == NULL)
9240 {
9241 free(demangled); /* not mangled name */
9242 return NULL;
9243 }
9244 if (cp[1] == '_') /* easy case: no category name */
9245 {
9246 *cp++ = ' '; /* replace two '_' with one ' ' */
9247 strcpy(cp, mangled + (cp - demangled) + 2);
9248 }
9249 else
9250 {
9251 *cp++ = '('; /* less easy case: category name */
9252 cp = strchr(cp, '_');
9253 if (cp == 0)
9254 {
9255 free(demangled); /* not mangled name */
9256 return NULL;
9257 }
9258 *cp++ = ')';
9259 *cp++ = ' '; /* overwriting 1st char of method name... */
9260 strcpy(cp, mangled + (cp - demangled)); /* get it back */
9261 }
9262 /* Now we have the method name. We need to generally replace
9263 '_' with ':' but trying to preserve '_' if it could only have
9264 been in the mangled string because it was already in the
9265 original name. In cases where it's ambiguous, we assume that
9266 any '_' originated from a ':'. */
9267
9268 /* Initial '_'s in method name can't have been generating by
9269 converting ':'s. Skip them. */
9270 while (*cp && *cp == '_')
9271 cp++;
9272
9273 /* If the method name does not end with '_', then it has no
9274 arguments and there was no replacement of ':'s with '_'s
9275 during mangling. Check for that case, and skip any
9276 replacement if so. This at least guarantees that methods
9277 with no arguments are always demangled correctly (unless the
9278 original name ends with '_'). */
9279 if (*(mangled + strlen (mangled) - 1) != '_')
9280 {
9281 /* Skip to the end. */
9282 for (; *cp; cp++)
9283 ;
9284 }
9285 else
9286 {
9287 /* Replace remaining '_' with ':'. This may get it wrong if
9288 there were '_'s in the original name. In most cases it
9289 is impossible to disambiguate. */
9290 for (; *cp; cp++)
9291 if (*cp == '_')
9292 *cp = ':';
9293 }
9294 *cp++ = ']'; /* closing right brace */
9295 *cp++ = 0; /* string terminator */
9296 return demangled;
9297 }
9298 else
9299 return NULL; /* not an objc mangled name */
9300 }
9301
9302 /* Try to pretty-print a decl. If the 'decl' is an Objective-C
9303 specific decl, return the printable name for it. If not, return
9304 NULL. */
9305 const char *
objc_maybe_printable_name(tree decl,int v ATTRIBUTE_UNUSED)9306 objc_maybe_printable_name (tree decl, int v ATTRIBUTE_UNUSED)
9307 {
9308 switch (TREE_CODE (decl))
9309 {
9310 case FUNCTION_DECL:
9311 return objc_demangle (IDENTIFIER_POINTER (DECL_NAME (decl)));
9312
9313 /* The following happens when we are printing a deprecation
9314 warning for a method. The warn_deprecation() will end up
9315 trying to print the decl for INSTANCE_METHOD_DECL or
9316 CLASS_METHOD_DECL. It would be nice to be able to print
9317 "-[NSObject autorelease] is deprecated", but to do that, we'd
9318 need to store the class and method name in the method decl,
9319 which we currently don't do. For now, just return the name
9320 of the method. We don't return NULL, because that may
9321 trigger further attempts to pretty-print the decl in C/C++,
9322 but they wouldn't know how to pretty-print it. */
9323 case INSTANCE_METHOD_DECL:
9324 case CLASS_METHOD_DECL:
9325 return IDENTIFIER_POINTER (DECL_NAME (decl));
9326 /* This happens when printing a deprecation warning for a
9327 property. We may want to consider some sort of pretty
9328 printing (eg, include the class name where it was declared
9329 ?). */
9330 case PROPERTY_DECL:
9331 return IDENTIFIER_POINTER (PROPERTY_NAME (decl));
9332 default:
9333 return NULL;
9334 }
9335 }
9336
9337 /* Return a printable name for 'decl'. This first tries
9338 objc_maybe_printable_name(), and if that fails, it returns the name
9339 in the decl. This is used as LANG_HOOKS_DECL_PRINTABLE_NAME for
9340 Objective-C; in Objective-C++, setting the hook is not enough
9341 because lots of C++ Front-End code calls cxx_printable_name,
9342 dump_decl and other C++ functions directly. So instead we have
9343 modified dump_decl to call objc_maybe_printable_name directly. */
9344 const char *
objc_printable_name(tree decl,int v)9345 objc_printable_name (tree decl, int v)
9346 {
9347 const char *demangled_name = objc_maybe_printable_name (decl, v);
9348
9349 if (demangled_name != NULL)
9350 return demangled_name;
9351 else
9352 return IDENTIFIER_POINTER (DECL_NAME (decl));
9353 }
9354
9355 /* Routine is called to issue diagnostic when reference to a private
9356 ivar is made and no other variable with same name is found in
9357 current scope. */
9358 bool
objc_diagnose_private_ivar(tree id)9359 objc_diagnose_private_ivar (tree id)
9360 {
9361 tree ivar;
9362 if (!objc_method_context)
9363 return false;
9364 ivar = is_ivar (objc_ivar_chain, id);
9365 if (ivar && is_private (ivar))
9366 {
9367 error ("instance variable %qs is declared private",
9368 IDENTIFIER_POINTER (id));
9369 return true;
9370 }
9371 return false;
9372 }
9373
9374 /* Look up ID as an instance variable. OTHER contains the result of
9375 the C or C++ lookup, which we may want to use instead. */
9376 /* To use properties inside an instance method, use self.property. */
9377 tree
objc_lookup_ivar(tree other,tree id)9378 objc_lookup_ivar (tree other, tree id)
9379 {
9380 tree ivar;
9381
9382 /* If we are not inside of an ObjC method, ivar lookup makes no sense. */
9383 if (!objc_method_context)
9384 return other;
9385
9386 if (!strcmp (IDENTIFIER_POINTER (id), "super"))
9387 /* We have a message to super. */
9388 return get_super_receiver ();
9389
9390 /* In a class method, look up an instance variable only as a last
9391 resort. */
9392 if (TREE_CODE (objc_method_context) == CLASS_METHOD_DECL
9393 && other && other != error_mark_node)
9394 return other;
9395
9396 /* Don't look up the ivar if the user has explicitly advised against
9397 it with -fno-local-ivars. */
9398
9399 if (!flag_local_ivars)
9400 return other;
9401
9402 /* Look up the ivar, but do not use it if it is not accessible. */
9403 ivar = is_ivar (objc_ivar_chain, id);
9404
9405 if (!ivar || is_private (ivar))
9406 return other;
9407
9408 /* In an instance method, a local variable (or parameter) may hide the
9409 instance variable. */
9410 if (TREE_CODE (objc_method_context) == INSTANCE_METHOD_DECL
9411 && other && other != error_mark_node
9412 #ifdef OBJCPLUS
9413 && CP_DECL_CONTEXT (other) != global_namespace)
9414 #else
9415 && !DECL_FILE_SCOPE_P (other))
9416 #endif
9417 {
9418 if (warn_shadow_ivar == 1 || (warn_shadow && warn_shadow_ivar != 0)) {
9419 warning (warn_shadow_ivar ? OPT_Wshadow_ivar : OPT_Wshadow,
9420 "local declaration of %qE hides instance variable", id);
9421 }
9422
9423 return other;
9424 }
9425
9426 /* At this point, we are either in an instance method with no obscuring
9427 local definitions, or in a class method with no alternate definitions
9428 at all. */
9429 return build_ivar_reference (id);
9430 }
9431
9432 /* Possibly rewrite a function CALL into an OBJ_TYPE_REF expression. This
9433 needs to be done if we are calling a function through a cast. */
9434
9435 tree
objc_rewrite_function_call(tree function,tree first_param)9436 objc_rewrite_function_call (tree function, tree first_param)
9437 {
9438 if (TREE_CODE (function) == NOP_EXPR
9439 && TREE_CODE (TREE_OPERAND (function, 0)) == ADDR_EXPR
9440 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (function, 0), 0))
9441 == FUNCTION_DECL)
9442 {
9443 function = build3 (OBJ_TYPE_REF, TREE_TYPE (function),
9444 TREE_OPERAND (function, 0),
9445 first_param, size_zero_node);
9446 }
9447
9448 return function;
9449 }
9450
9451 /* This is called to "gimplify" a PROPERTY_REF node. It builds the
9452 corresponding 'getter' function call. Note that we assume the
9453 PROPERTY_REF to be valid since we generated it while parsing. */
9454 static void
objc_gimplify_property_ref(tree * expr_p)9455 objc_gimplify_property_ref (tree *expr_p)
9456 {
9457 tree getter = PROPERTY_REF_GETTER_CALL (*expr_p);
9458 tree call_exp;
9459
9460 if (getter == NULL_TREE)
9461 {
9462 tree property_decl = PROPERTY_REF_PROPERTY_DECL (*expr_p);
9463 /* This can happen if DECL_ARTIFICIAL (*expr_p), but
9464 should be impossible for real properties, which always
9465 have a getter. */
9466 error_at (EXPR_LOCATION (*expr_p), "no %qs getter found",
9467 IDENTIFIER_POINTER (PROPERTY_NAME (property_decl)));
9468 /* Try to recover from the error to prevent an ICE. We take
9469 zero and cast it to the type of the property. */
9470 *expr_p = convert (TREE_TYPE (property_decl),
9471 integer_zero_node);
9472 return;
9473 }
9474
9475 if (PROPERTY_REF_DEPRECATED_GETTER (*expr_p))
9476 {
9477 /* PROPERTY_REF_DEPRECATED_GETTER contains the method prototype
9478 that is deprecated. */
9479 warn_deprecated_use (PROPERTY_REF_DEPRECATED_GETTER (*expr_p),
9480 NULL_TREE);
9481 }
9482
9483 call_exp = getter;
9484 #ifdef OBJCPLUS
9485 /* In C++, a getter which returns an aggregate value results in a
9486 target_expr which initializes a temporary to the call
9487 expression. */
9488 if (TREE_CODE (getter) == TARGET_EXPR)
9489 {
9490 gcc_assert (MAYBE_CLASS_TYPE_P (TREE_TYPE (getter)));
9491 gcc_assert (TREE_CODE (TREE_OPERAND (getter, 0)) == VAR_DECL);
9492 call_exp = TREE_OPERAND (getter, 1);
9493 }
9494 #endif
9495 gcc_assert (TREE_CODE (call_exp) == CALL_EXPR);
9496
9497 *expr_p = call_exp;
9498 }
9499
9500 /* This is called when "gimplifying" the trees. We need to gimplify
9501 the Objective-C/Objective-C++ specific trees, then hand over the
9502 process to C/C++. */
9503 int
objc_gimplify_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p)9504 objc_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
9505 {
9506 enum tree_code code = TREE_CODE (*expr_p);
9507 switch (code)
9508 {
9509 /* Look for the special case of OBJC_TYPE_REF with the address
9510 of a function in OBJ_TYPE_REF_EXPR (presumably objc_msgSend
9511 or one of its cousins). */
9512 case OBJ_TYPE_REF:
9513 if (TREE_CODE (OBJ_TYPE_REF_EXPR (*expr_p)) == ADDR_EXPR
9514 && TREE_CODE (TREE_OPERAND (OBJ_TYPE_REF_EXPR (*expr_p), 0))
9515 == FUNCTION_DECL)
9516 {
9517 enum gimplify_status r0, r1;
9518
9519 /* Postincrements in OBJ_TYPE_REF_OBJECT don't affect the
9520 value of the OBJ_TYPE_REF, so force them to be emitted
9521 during subexpression evaluation rather than after the
9522 OBJ_TYPE_REF. This permits objc_msgSend calls in
9523 Objective C to use direct rather than indirect calls when
9524 the object expression has a postincrement. */
9525 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p, NULL,
9526 is_gimple_val, fb_rvalue);
9527 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p, post_p,
9528 is_gimple_val, fb_rvalue);
9529
9530 return MIN (r0, r1);
9531 }
9532 break;
9533 case PROPERTY_REF:
9534 objc_gimplify_property_ref (expr_p);
9535 /* Do not return yet; let C/C++ gimplify the resulting expression. */
9536 break;
9537 default:
9538 break;
9539 }
9540
9541 #ifdef OBJCPLUS
9542 return (enum gimplify_status) cp_gimplify_expr (expr_p, pre_p, post_p);
9543 #else
9544 return (enum gimplify_status) c_gimplify_expr (expr_p, pre_p, post_p);
9545 #endif
9546 }
9547
9548 /* --- FAST ENUMERATION --- */
9549 /* Begin code generation for fast enumeration (foreach) ... */
9550
9551 /* Defines
9552
9553 struct __objcFastEnumerationState
9554 {
9555 unsigned long state;
9556 id *itemsPtr;
9557 unsigned long *mutationsPtr;
9558 unsigned long extra[5];
9559 };
9560
9561 Confusingly enough, NSFastEnumeration is then defined by libraries
9562 to be the same structure.
9563 */
9564
9565 static void
build_fast_enumeration_state_template(void)9566 build_fast_enumeration_state_template (void)
9567 {
9568 tree decls, *chain = NULL;
9569
9570 /* { */
9571 objc_fast_enumeration_state_template = objc_start_struct (get_identifier
9572 (TAG_FAST_ENUMERATION_STATE));
9573
9574 /* unsigned long state; */
9575 decls = add_field_decl (long_unsigned_type_node, "state", &chain);
9576
9577 /* id *itemsPtr; */
9578 add_field_decl (build_pointer_type (objc_object_type),
9579 "itemsPtr", &chain);
9580
9581 /* unsigned long *mutationsPtr; */
9582 add_field_decl (build_pointer_type (long_unsigned_type_node),
9583 "mutationsPtr", &chain);
9584
9585 /* unsigned long extra[5]; */
9586 add_field_decl (build_sized_array_type (long_unsigned_type_node, 5),
9587 "extra", &chain);
9588
9589 /* } */
9590 objc_finish_struct (objc_fast_enumeration_state_template, decls);
9591 }
9592
9593 /*
9594 'objc_finish_foreach_loop()' generates the code for an Objective-C
9595 foreach loop. The 'location' argument is the location of the 'for'
9596 that starts the loop. The 'object_expression' is the expression of
9597 the 'object' that iterates; the 'collection_expression' is the
9598 expression of the collection that we iterate over (we need to make
9599 sure we evaluate this only once); the 'for_body' is the set of
9600 statements to be executed in each iteration; 'break_label' and
9601 'continue_label' are the break and continue labels which we need to
9602 emit since the <statements> may be jumping to 'break_label' (if they
9603 contain 'break') or to 'continue_label' (if they contain
9604 'continue').
9605
9606 The syntax is
9607
9608 for (<object expression> in <collection expression>)
9609 <statements>
9610
9611 which is compiled into the following blurb:
9612
9613 {
9614 id __objc_foreach_collection;
9615 __objc_fast_enumeration_state __objc_foreach_enum_state;
9616 unsigned long __objc_foreach_batchsize;
9617 id __objc_foreach_items[16];
9618 __objc_foreach_collection = <collection expression>;
9619 __objc_foreach_enum_state = { 0 };
9620 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
9621
9622 if (__objc_foreach_batchsize == 0)
9623 <object expression> = nil;
9624 else
9625 {
9626 unsigned long __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr;
9627 next_batch:
9628 {
9629 unsigned long __objc_foreach_index;
9630 __objc_foreach_index = 0;
9631
9632 next_object:
9633 if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>);
9634 <object expression> = enumState.itemsPtr[__objc_foreach_index];
9635 <statements> [PS: inside <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label]
9636
9637 continue_label:
9638 __objc_foreach_index++;
9639 if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object;
9640 __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16];
9641 }
9642 if (__objc_foreach_batchsize != 0) goto next_batch;
9643 <object expression> = nil;
9644 break_label:
9645 }
9646 }
9647
9648 'statements' may contain a 'continue' or 'break' instruction, which
9649 the user expects to 'continue' or 'break' the entire foreach loop.
9650 We are provided the labels that 'break' and 'continue' jump to, so
9651 we place them where we want them to jump to when they pick them.
9652
9653 Optimization TODO: we could cache the IMP of
9654 countByEnumeratingWithState:objects:count:.
9655 */
9656
9657 /* If you need to debug objc_finish_foreach_loop(), uncomment the following line. */
9658 /* #define DEBUG_OBJC_FINISH_FOREACH_LOOP 1 */
9659
9660 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
9661 #include "tree-pretty-print.h"
9662 #endif
9663
9664 void
objc_finish_foreach_loop(location_t location,tree object_expression,tree collection_expression,tree for_body,tree break_label,tree continue_label)9665 objc_finish_foreach_loop (location_t location, tree object_expression, tree collection_expression, tree for_body,
9666 tree break_label, tree continue_label)
9667 {
9668 /* A tree representing the __objcFastEnumerationState struct type,
9669 or NSFastEnumerationState struct, whatever we are using. */
9670 tree objc_fast_enumeration_state_type;
9671
9672 /* The trees representing the declarations of each of the local variables. */
9673 tree objc_foreach_collection_decl;
9674 tree objc_foreach_enum_state_decl;
9675 tree objc_foreach_items_decl;
9676 tree objc_foreach_batchsize_decl;
9677 tree objc_foreach_mutations_pointer_decl;
9678 tree objc_foreach_index_decl;
9679
9680 /* A tree representing the selector countByEnumeratingWithState:objects:count:. */
9681 tree selector_name;
9682
9683 /* A tree representing the local bind. */
9684 tree bind;
9685
9686 /* A tree representing the external 'if (__objc_foreach_batchsize)' */
9687 tree first_if;
9688
9689 /* A tree representing the 'else' part of 'first_if' */
9690 tree first_else;
9691
9692 /* A tree representing the 'next_batch' label. */
9693 tree next_batch_label_decl;
9694
9695 /* A tree representing the binding after the 'next_batch' label. */
9696 tree next_batch_bind;
9697
9698 /* A tree representing the 'next_object' label. */
9699 tree next_object_label_decl;
9700
9701 /* Temporary variables. */
9702 tree t;
9703 int i;
9704
9705 if (flag_objc1_only)
9706 error_at (location, "fast enumeration is not available in Objective-C 1.0");
9707
9708 if (object_expression == error_mark_node)
9709 return;
9710
9711 if (collection_expression == error_mark_node)
9712 return;
9713
9714 if (!objc_type_valid_for_messaging (TREE_TYPE (object_expression), true))
9715 {
9716 error_at (location, "iterating variable in fast enumeration is not an object");
9717 return;
9718 }
9719
9720 if (!objc_type_valid_for_messaging (TREE_TYPE (collection_expression), true))
9721 {
9722 error_at (location, "collection in fast enumeration is not an object");
9723 return;
9724 }
9725
9726 /* TODO: Check that object_expression is either a variable
9727 declaration, or an lvalue. */
9728
9729 /* This kludge is an idea from apple. We use the
9730 __objcFastEnumerationState struct implicitly defined by the
9731 compiler, unless a NSFastEnumerationState struct has been defined
9732 (by a Foundation library such as GNUstep Base) in which case, we
9733 use that one.
9734 */
9735 objc_fast_enumeration_state_type = objc_fast_enumeration_state_template;
9736 {
9737 tree objc_NSFastEnumeration_type = lookup_name (get_identifier ("NSFastEnumerationState"));
9738
9739 if (objc_NSFastEnumeration_type)
9740 {
9741 /* TODO: We really need to check that
9742 objc_NSFastEnumeration_type is the same as ours! */
9743 if (TREE_CODE (objc_NSFastEnumeration_type) == TYPE_DECL)
9744 {
9745 /* If it's a typedef, use the original type. */
9746 if (DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type))
9747 objc_fast_enumeration_state_type = DECL_ORIGINAL_TYPE (objc_NSFastEnumeration_type);
9748 else
9749 objc_fast_enumeration_state_type = TREE_TYPE (objc_NSFastEnumeration_type);
9750 }
9751 }
9752 }
9753
9754 /* { */
9755 /* Done by c-parser.c. */
9756
9757 /* type object; */
9758 /* Done by c-parser.c. */
9759
9760 /* Disable warnings that 'object' is unused. For example the code
9761
9762 for (id object in collection)
9763 i++;
9764
9765 which can be used to count how many objects there are in the
9766 collection is fine and should generate no warnings even if
9767 'object' is technically unused. */
9768 TREE_USED (object_expression) = 1;
9769 if (DECL_P (object_expression))
9770 DECL_READ_P (object_expression) = 1;
9771
9772 /* id __objc_foreach_collection */
9773 objc_foreach_collection_decl = objc_create_temporary_var (objc_object_type, "__objc_foreach_collection");
9774
9775 /* __objcFastEnumerationState __objc_foreach_enum_state; */
9776 objc_foreach_enum_state_decl = objc_create_temporary_var (objc_fast_enumeration_state_type, "__objc_foreach_enum_state");
9777 TREE_CHAIN (objc_foreach_enum_state_decl) = objc_foreach_collection_decl;
9778
9779 /* id __objc_foreach_items[16]; */
9780 objc_foreach_items_decl = objc_create_temporary_var (build_sized_array_type (objc_object_type, 16), "__objc_foreach_items");
9781 TREE_CHAIN (objc_foreach_items_decl) = objc_foreach_enum_state_decl;
9782
9783 /* unsigned long __objc_foreach_batchsize; */
9784 objc_foreach_batchsize_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_batchsize");
9785 TREE_CHAIN (objc_foreach_batchsize_decl) = objc_foreach_items_decl;
9786
9787 /* Generate the local variable binding. */
9788 bind = build3 (BIND_EXPR, void_type_node, objc_foreach_batchsize_decl, NULL, NULL);
9789 SET_EXPR_LOCATION (bind, location);
9790 TREE_SIDE_EFFECTS (bind) = 1;
9791
9792 /* __objc_foreach_collection = <collection expression>; */
9793 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_collection_decl, collection_expression);
9794 SET_EXPR_LOCATION (t, location);
9795 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9796 /* We have used 'collection_expression'. */
9797 mark_exp_read (collection_expression);
9798
9799 /* __objc_foreach_enum_state.state = 0; */
9800 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
9801 get_identifier ("state")),
9802 build_int_cst (long_unsigned_type_node, 0));
9803 SET_EXPR_LOCATION (t, location);
9804 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9805
9806 /* __objc_foreach_enum_state.itemsPtr = NULL; */
9807 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
9808 get_identifier ("itemsPtr")),
9809 null_pointer_node);
9810 SET_EXPR_LOCATION (t, location);
9811 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9812
9813 /* __objc_foreach_enum_state.mutationsPtr = NULL; */
9814 t = build2 (MODIFY_EXPR, void_type_node, objc_build_component_ref (objc_foreach_enum_state_decl,
9815 get_identifier ("mutationsPtr")),
9816 null_pointer_node);
9817 SET_EXPR_LOCATION (t, location);
9818 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9819
9820 /* __objc_foreach_enum_state.extra[0] = 0; */
9821 /* __objc_foreach_enum_state.extra[1] = 0; */
9822 /* __objc_foreach_enum_state.extra[2] = 0; */
9823 /* __objc_foreach_enum_state.extra[3] = 0; */
9824 /* __objc_foreach_enum_state.extra[4] = 0; */
9825 for (i = 0; i < 5 ; i++)
9826 {
9827 t = build2 (MODIFY_EXPR, void_type_node,
9828 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
9829 get_identifier ("extra")),
9830 build_int_cst (NULL_TREE, i)),
9831 build_int_cst (long_unsigned_type_node, 0));
9832 SET_EXPR_LOCATION (t, location);
9833 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9834 }
9835
9836 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
9837 selector_name = get_identifier ("countByEnumeratingWithState:objects:count:");
9838 #ifdef OBJCPLUS
9839 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
9840 /* Parameters. */
9841 tree_cons /* &__objc_foreach_enum_state */
9842 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
9843 tree_cons /* __objc_foreach_items */
9844 (NULL_TREE, objc_foreach_items_decl,
9845 tree_cons /* 16 */
9846 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
9847 #else
9848 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
9849 {
9850 struct c_expr array;
9851 array.value = objc_foreach_items_decl;
9852 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
9853 /* Parameters. */
9854 tree_cons /* &__objc_foreach_enum_state */
9855 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
9856 tree_cons /* __objc_foreach_items */
9857 (NULL_TREE, default_function_array_conversion (location, array).value,
9858 tree_cons /* 16 */
9859 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
9860 }
9861 #endif
9862 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
9863 convert (long_unsigned_type_node, t));
9864 SET_EXPR_LOCATION (t, location);
9865 append_to_statement_list (t, &BIND_EXPR_BODY (bind));
9866
9867 /* if (__objc_foreach_batchsize == 0) */
9868 first_if = build3 (COND_EXPR, void_type_node,
9869 /* Condition. */
9870 c_fully_fold
9871 (c_common_truthvalue_conversion
9872 (location,
9873 build_binary_op (location,
9874 EQ_EXPR,
9875 objc_foreach_batchsize_decl,
9876 build_int_cst (long_unsigned_type_node, 0), 1)),
9877 false, NULL),
9878 /* Then block (we fill it in later). */
9879 NULL_TREE,
9880 /* Else block (we fill it in later). */
9881 NULL_TREE);
9882 SET_EXPR_LOCATION (first_if, location);
9883 append_to_statement_list (first_if, &BIND_EXPR_BODY (bind));
9884
9885 /* then <object expression> = nil; */
9886 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
9887 SET_EXPR_LOCATION (t, location);
9888 COND_EXPR_THEN (first_if) = t;
9889
9890 /* Now we build the 'else' part of the if; once we finish building
9891 it, we attach it to first_if as the 'else' part. */
9892
9893 /* else */
9894 /* { */
9895
9896 /* unsigned long __objc_foreach_mutations_pointer; */
9897 objc_foreach_mutations_pointer_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_mutations_pointer");
9898
9899 /* Generate the local variable binding. */
9900 first_else = build3 (BIND_EXPR, void_type_node, objc_foreach_mutations_pointer_decl, NULL, NULL);
9901 SET_EXPR_LOCATION (first_else, location);
9902 TREE_SIDE_EFFECTS (first_else) = 1;
9903
9904 /* __objc_foreach_mutations_pointer = *__objc_foreach_enum_state.mutationsPtr; */
9905 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_mutations_pointer_decl,
9906 build_indirect_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
9907 get_identifier ("mutationsPtr")),
9908 RO_UNARY_STAR));
9909 SET_EXPR_LOCATION (t, location);
9910 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
9911
9912 /* next_batch: */
9913 next_batch_label_decl = create_artificial_label (location);
9914 t = build1 (LABEL_EXPR, void_type_node, next_batch_label_decl);
9915 SET_EXPR_LOCATION (t, location);
9916 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
9917
9918 /* { */
9919
9920 /* unsigned long __objc_foreach_index; */
9921 objc_foreach_index_decl = objc_create_temporary_var (long_unsigned_type_node, "__objc_foreach_index");
9922
9923 /* Generate the local variable binding. */
9924 next_batch_bind = build3 (BIND_EXPR, void_type_node, objc_foreach_index_decl, NULL, NULL);
9925 SET_EXPR_LOCATION (next_batch_bind, location);
9926 TREE_SIDE_EFFECTS (next_batch_bind) = 1;
9927 append_to_statement_list (next_batch_bind, &BIND_EXPR_BODY (first_else));
9928
9929 /* __objc_foreach_index = 0; */
9930 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
9931 build_int_cst (long_unsigned_type_node, 0));
9932 SET_EXPR_LOCATION (t, location);
9933 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9934
9935 /* next_object: */
9936 next_object_label_decl = create_artificial_label (location);
9937 t = build1 (LABEL_EXPR, void_type_node, next_object_label_decl);
9938 SET_EXPR_LOCATION (t, location);
9939 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9940
9941 /* if (__objc_foreach_mutation_pointer != *__objc_foreach_enum_state.mutationsPtr) objc_enumeration_mutation (<collection expression>); */
9942 t = build3 (COND_EXPR, void_type_node,
9943 /* Condition. */
9944 c_fully_fold
9945 (c_common_truthvalue_conversion
9946 (location,
9947 build_binary_op
9948 (location,
9949 NE_EXPR,
9950 objc_foreach_mutations_pointer_decl,
9951 build_indirect_ref (location,
9952 objc_build_component_ref (objc_foreach_enum_state_decl,
9953 get_identifier ("mutationsPtr")),
9954 RO_UNARY_STAR), 1)),
9955 false, NULL),
9956 /* Then block. */
9957 build_function_call (input_location,
9958 objc_enumeration_mutation_decl,
9959 tree_cons (NULL, collection_expression, NULL)),
9960 /* Else block. */
9961 NULL_TREE);
9962 SET_EXPR_LOCATION (t, location);
9963 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9964
9965 /* <object expression> = enumState.itemsPtr[__objc_foreach_index]; */
9966 t = build2 (MODIFY_EXPR, void_type_node, object_expression,
9967 build_array_ref (location, objc_build_component_ref (objc_foreach_enum_state_decl,
9968 get_identifier ("itemsPtr")),
9969 objc_foreach_index_decl));
9970 SET_EXPR_LOCATION (t, location);
9971 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9972
9973 /* <statements> [PS: in <statments>, 'break' jumps to break_label and 'continue' jumps to continue_label] */
9974 append_to_statement_list (for_body, &BIND_EXPR_BODY (next_batch_bind));
9975
9976 /* continue_label: */
9977 if (continue_label)
9978 {
9979 t = build1 (LABEL_EXPR, void_type_node, continue_label);
9980 SET_EXPR_LOCATION (t, location);
9981 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9982 }
9983
9984 /* __objc_foreach_index++; */
9985 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_index_decl,
9986 build_binary_op (location,
9987 PLUS_EXPR,
9988 objc_foreach_index_decl,
9989 build_int_cst (long_unsigned_type_node, 1), 1));
9990 SET_EXPR_LOCATION (t, location);
9991 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
9992
9993 /* if (__objc_foreach_index < __objc_foreach_batchsize) goto next_object; */
9994 t = build3 (COND_EXPR, void_type_node,
9995 /* Condition. */
9996 c_fully_fold
9997 (c_common_truthvalue_conversion
9998 (location,
9999 build_binary_op (location,
10000 LT_EXPR,
10001 objc_foreach_index_decl,
10002 objc_foreach_batchsize_decl, 1)),
10003 false, NULL),
10004 /* Then block. */
10005 build1 (GOTO_EXPR, void_type_node, next_object_label_decl),
10006 /* Else block. */
10007 NULL_TREE);
10008 SET_EXPR_LOCATION (t, location);
10009 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10010
10011 /* __objc_foreach_batchsize = [__objc_foreach_collection countByEnumeratingWithState: &__objc_foreach_enum_state objects: __objc_foreach_items count: 16]; */
10012 #ifdef OBJCPLUS
10013 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10014 /* Parameters. */
10015 tree_cons /* &__objc_foreach_enum_state */
10016 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10017 tree_cons /* __objc_foreach_items */
10018 (NULL_TREE, objc_foreach_items_decl,
10019 tree_cons /* 16 */
10020 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10021 #else
10022 /* In C, we need to decay the __objc_foreach_items array that we are passing. */
10023 {
10024 struct c_expr array;
10025 array.value = objc_foreach_items_decl;
10026 t = objc_finish_message_expr (objc_foreach_collection_decl, selector_name,
10027 /* Parameters. */
10028 tree_cons /* &__objc_foreach_enum_state */
10029 (NULL_TREE, build_fold_addr_expr_loc (location, objc_foreach_enum_state_decl),
10030 tree_cons /* __objc_foreach_items */
10031 (NULL_TREE, default_function_array_conversion (location, array).value,
10032 tree_cons /* 16 */
10033 (NULL_TREE, build_int_cst (NULL_TREE, 16), NULL_TREE))), NULL);
10034 }
10035 #endif
10036 t = build2 (MODIFY_EXPR, void_type_node, objc_foreach_batchsize_decl,
10037 convert (long_unsigned_type_node, t));
10038 SET_EXPR_LOCATION (t, location);
10039 append_to_statement_list (t, &BIND_EXPR_BODY (next_batch_bind));
10040
10041 /* } */
10042
10043 /* if (__objc_foreach_batchsize != 0) goto next_batch; */
10044 t = build3 (COND_EXPR, void_type_node,
10045 /* Condition. */
10046 c_fully_fold
10047 (c_common_truthvalue_conversion
10048 (location,
10049 build_binary_op (location,
10050 NE_EXPR,
10051 objc_foreach_batchsize_decl,
10052 build_int_cst (long_unsigned_type_node, 0), 1)),
10053 false, NULL),
10054 /* Then block. */
10055 build1 (GOTO_EXPR, void_type_node, next_batch_label_decl),
10056 /* Else block. */
10057 NULL_TREE);
10058 SET_EXPR_LOCATION (t, location);
10059 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10060
10061 /* <object expression> = nil; */
10062 t = build2 (MODIFY_EXPR, void_type_node, object_expression, convert (objc_object_type, null_pointer_node));
10063 SET_EXPR_LOCATION (t, location);
10064 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10065
10066 /* break_label: */
10067 if (break_label)
10068 {
10069 t = build1 (LABEL_EXPR, void_type_node, break_label);
10070 SET_EXPR_LOCATION (t, location);
10071 append_to_statement_list (t, &BIND_EXPR_BODY (first_else));
10072 }
10073
10074 /* } */
10075 COND_EXPR_ELSE (first_if) = first_else;
10076
10077 /* Do the whole thing. */
10078 add_stmt (bind);
10079
10080 #ifdef DEBUG_OBJC_FINISH_FOREACH_LOOP
10081 /* This will print to stderr the whole blurb generated by the
10082 compiler while compiling (assuming the compiler doesn't crash
10083 before getting here).
10084 */
10085 debug_generic_stmt (bind);
10086 #endif
10087
10088 /* } */
10089 /* Done by c-parser.c */
10090 }
10091
10092 /* --- SUPPORT FOR FORMAT ARG CHECKING --- */
10093 /* Return true if we have an NxString object pointer. */
10094
10095 bool
objc_string_ref_type_p(tree strp)10096 objc_string_ref_type_p (tree strp)
10097 {
10098 tree tmv;
10099 if (!strp || TREE_CODE (strp) != POINTER_TYPE)
10100 return false;
10101
10102 tmv = TYPE_MAIN_VARIANT (TREE_TYPE (strp));
10103 tmv = OBJC_TYPE_NAME (tmv);
10104 return (tmv
10105 && TREE_CODE (tmv) == IDENTIFIER_NODE
10106 && IDENTIFIER_POINTER (tmv)
10107 && !strncmp (IDENTIFIER_POINTER (tmv), "NSString", 8));
10108 }
10109
10110 /* At present the behavior of this is undefined and it does nothing. */
10111 void
objc_check_format_arg(tree ARG_UNUSED (format_arg),tree ARG_UNUSED (args_list))10112 objc_check_format_arg (tree ARG_UNUSED (format_arg),
10113 tree ARG_UNUSED (args_list))
10114 {
10115 }
10116
10117 void
objc_common_init_ts(void)10118 objc_common_init_ts (void)
10119 {
10120 c_common_init_ts ();
10121
10122 MARK_TS_DECL_NON_COMMON (CLASS_METHOD_DECL);
10123 MARK_TS_DECL_NON_COMMON (INSTANCE_METHOD_DECL);
10124 MARK_TS_DECL_NON_COMMON (KEYWORD_DECL);
10125 MARK_TS_DECL_NON_COMMON (PROPERTY_DECL);
10126
10127 MARK_TS_COMMON (CLASS_INTERFACE_TYPE);
10128 MARK_TS_COMMON (PROTOCOL_INTERFACE_TYPE);
10129 MARK_TS_COMMON (CLASS_IMPLEMENTATION_TYPE);
10130
10131 MARK_TS_TYPED (MESSAGE_SEND_EXPR);
10132 MARK_TS_TYPED (PROPERTY_REF);
10133 }
10134
10135 size_t
objc_common_tree_size(enum tree_code code)10136 objc_common_tree_size (enum tree_code code)
10137 {
10138 switch (code)
10139 {
10140 case CLASS_METHOD_DECL:
10141 case INSTANCE_METHOD_DECL:
10142 case KEYWORD_DECL:
10143 case PROPERTY_DECL: return sizeof (tree_decl_non_common);
10144 case CLASS_INTERFACE_TYPE:
10145 case CLASS_IMPLEMENTATION_TYPE:
10146 case CATEGORY_INTERFACE_TYPE:
10147 case CATEGORY_IMPLEMENTATION_TYPE:
10148 case PROTOCOL_INTERFACE_TYPE: return sizeof (tree_type_non_common);
10149 default:
10150 gcc_unreachable ();
10151 }
10152 }
10153
10154
10155 #include "gt-objc-objc-act.h"
10156