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