c-decl.c (finish_function): New arg can_defer_p.
[gcc.git] / gcc / c-objc-common.c
1 /* Some code common to C and ObjC front ends.
2 Copyright (C) 2001 Free Software Foundation, Inc.
3
4 This file is part of GCC.
5
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 2, or (at your option) any later
9 version.
10
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING. If not, write to the Free
18 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
19 02111-1307, USA. */
20
21 #include "config.h"
22 #include "system.h"
23 #include "tree.h"
24 #include "rtl.h"
25 #include "insn-config.h"
26 #include "integrate.h"
27 #include "expr.h"
28 #include "c-tree.h"
29 #include "function.h"
30 #include "flags.h"
31 #include "toplev.h"
32 #include "diagnostic.h"
33 #include "tree-inline.h"
34 #include "varray.h"
35 #include "ggc.h"
36 #include "langhooks.h"
37
38 static int c_tree_printer PARAMS ((output_buffer *));
39 static tree inline_forbidden_p PARAMS ((tree *, int *, void *));
40 static void expand_deferred_fns PARAMS ((void));
41 static tree start_cdtor PARAMS ((int));
42 static void finish_cdtor PARAMS ((tree));
43
44 static varray_type deferred_fns;
45
46 int
47 c_missing_noreturn_ok_p (decl)
48 tree decl;
49 {
50 /* A missing noreturn is not ok for freestanding implementations and
51 ok for the `main' function in hosted implementations. */
52 return flag_hosted && MAIN_NAME_P (DECL_ASSEMBLER_NAME (decl));
53 }
54
55 /* We want to inline `extern inline' functions even if this would
56 violate inlining limits. Some glibc and linux constructs depend on
57 such functions always being inlined when optimizing. */
58
59 int
60 c_disregard_inline_limits (fn)
61 tree fn;
62 {
63 if (lookup_attribute ("always_inline", DECL_ATTRIBUTES (fn)) != NULL)
64 return 1;
65
66 return DECL_DECLARED_INLINE_P (fn) && DECL_EXTERNAL (fn);
67 }
68
69 static tree
70 inline_forbidden_p (nodep, walk_subtrees, fn)
71 tree *nodep;
72 int *walk_subtrees ATTRIBUTE_UNUSED;
73 void *fn;
74 {
75 tree node = *nodep;
76 tree t;
77
78 switch (TREE_CODE (node))
79 {
80 case CALL_EXPR:
81 t = get_callee_fndecl (node);
82
83 if (! t)
84 break;
85
86 /* We cannot inline functions that call setjmp. */
87 if (setjmp_call_p (t))
88 return node;
89
90 switch (DECL_FUNCTION_CODE (t))
91 {
92 /* We cannot inline functions that take a variable number of
93 arguments. */
94 case BUILT_IN_VARARGS_START:
95 case BUILT_IN_STDARG_START:
96 #if 0
97 /* Functions that need information about the address of the
98 caller can't (shouldn't?) be inlined. */
99 case BUILT_IN_RETURN_ADDRESS:
100 #endif
101 return node;
102
103 default:
104 break;
105 }
106
107 break;
108
109 case DECL_STMT:
110 /* We cannot inline functions that contain other functions. */
111 if (TREE_CODE (TREE_OPERAND (node, 0)) == FUNCTION_DECL
112 && DECL_INITIAL (TREE_OPERAND (node, 0)))
113 return node;
114 break;
115
116 case GOTO_STMT:
117 case GOTO_EXPR:
118 t = TREE_OPERAND (node, 0);
119
120 /* We will not inline a function which uses computed goto. The
121 addresses of its local labels, which may be tucked into
122 global storage, are of course not constant across
123 instantiations, which causes unexpected behaviour. */
124 if (TREE_CODE (t) != LABEL_DECL)
125 return node;
126
127 /* We cannot inline a nested function that jumps to a nonlocal
128 label. */
129 if (TREE_CODE (t) == LABEL_DECL
130 && DECL_CONTEXT (t) && DECL_CONTEXT (t) != fn)
131 return node;
132
133 break;
134
135 default:
136 break;
137 }
138
139 return NULL_TREE;
140 }
141
142 int
143 c_cannot_inline_tree_fn (fnp)
144 tree *fnp;
145 {
146 tree fn = *fnp;
147 tree t;
148
149 if (flag_really_no_inline
150 && lookup_attribute ("always_inline", DECL_ATTRIBUTES (fn)) == NULL)
151 return 1;
152
153 if (! function_attribute_inlinable_p (fn))
154 {
155 DECL_UNINLINABLE (fn) = 1;
156 return 1;
157 }
158
159 /* If a function has pending sizes, we must not defer its
160 compilation, and we can't inline it as a tree. */
161 if (fn == current_function_decl)
162 {
163 t = get_pending_sizes ();
164 put_pending_sizes (t);
165
166 if (t)
167 {
168 DECL_UNINLINABLE (fn) = 1;
169 return 1;
170 }
171 }
172
173 if (DECL_CONTEXT (fn))
174 {
175 /* If a nested function has pending sizes, we may have already
176 saved them. */
177 if (DECL_LANG_SPECIFIC (fn)->pending_sizes)
178 {
179 DECL_UNINLINABLE (fn) = 1;
180 return 1;
181 }
182 }
183 else
184 {
185 /* We rely on the fact that this function is called upfront,
186 just before we start expanding a function. If FN is active
187 (i.e., it's the current_function_decl or a parent thereof),
188 we have to walk FN's saved tree. Otherwise, we can safely
189 assume we have done it before and, if we didn't mark it as
190 uninlinable (in which case we wouldn't have been called), it
191 is inlinable. Unfortunately, this strategy doesn't work for
192 nested functions, because they're only expanded as part of
193 their enclosing functions, so the inlinability test comes in
194 late. */
195 t = current_function_decl;
196
197 while (t && t != fn)
198 t = DECL_CONTEXT (t);
199 if (! t)
200 return 0;
201 }
202
203 if (walk_tree (&DECL_SAVED_TREE (fn), inline_forbidden_p, fn, NULL))
204 {
205 DECL_UNINLINABLE (fn) = 1;
206 return 1;
207 }
208
209 return 0;
210 }
211
212 /* Initialization common to C and Objective-C front ends. */
213 const char *
214 c_objc_common_init (filename)
215 const char *filename;
216 {
217 c_init_decl_processing ();
218
219 filename = c_common_init (filename);
220 if (filename == NULL)
221 return NULL;
222
223 lang_unsafe_for_reeval = c_unsafe_for_reeval;
224
225 save_lang_status = &push_c_function_context;
226 restore_lang_status = &pop_c_function_context;
227 mark_lang_status = &mark_c_function_context;
228 lang_expand_decl_stmt = c_expand_decl_stmt;
229
230 /* These were not defined in the Objective-C front end, but I'm
231 putting them here anyway. The diagnostic format decoder might
232 want an enhanced ObjC implementation. */
233 diagnostic_format_decoder (global_dc) = &c_tree_printer;
234 lang_missing_noreturn_ok_p = &c_missing_noreturn_ok_p;
235
236 /* If still unspecified, make it match -std=c99
237 (allowing for -pedantic-errors). */
238 if (mesg_implicit_function_declaration < 0)
239 {
240 if (flag_isoc99)
241 mesg_implicit_function_declaration = flag_pedantic_errors ? 2 : 1;
242 else
243 mesg_implicit_function_declaration = 0;
244 }
245
246 VARRAY_TREE_INIT (deferred_fns, 32, "deferred_fns");
247 ggc_add_tree_varray_root (&deferred_fns, 1);
248
249 return filename;
250 }
251
252 /* Register a function tree, so that its optimization and conversion
253 to RTL is only done at the end of the compilation. */
254
255 int
256 defer_fn (fn)
257 tree fn;
258 {
259 VARRAY_PUSH_TREE (deferred_fns, fn);
260
261 return 1;
262 }
263
264 /* Expand deferred functions for C and ObjC. */
265
266 static void
267 expand_deferred_fns ()
268 {
269 unsigned int i;
270
271 for (i = 0; i < VARRAY_ACTIVE_SIZE (deferred_fns); i++)
272 {
273 tree decl = VARRAY_TREE (deferred_fns, i);
274
275 if (! TREE_ASM_WRITTEN (decl))
276 {
277 /* For static inline functions, delay the decision whether to
278 emit them or not until wrapup_global_declarations. */
279 if (! TREE_PUBLIC (decl))
280 DECL_DEFER_OUTPUT (decl) = 1;
281 c_expand_deferred_function (decl);
282 }
283 }
284
285 VARRAY_FREE (deferred_fns);
286 }
287
288 static tree
289 start_cdtor (method_type)
290 int method_type;
291 {
292 tree fnname = get_file_function_name (method_type);
293 tree void_list_node_1 = build_tree_list (NULL_TREE, void_type_node);
294 tree body;
295
296 start_function (void_list_node_1,
297 build_nt (CALL_EXPR, fnname,
298 tree_cons (NULL_TREE, NULL_TREE, void_list_node_1),
299 NULL_TREE),
300 NULL_TREE);
301 store_parm_decls ();
302
303 current_function_cannot_inline
304 = "static constructors and destructors cannot be inlined";
305
306 body = c_begin_compound_stmt ();
307
308 pushlevel (0);
309 clear_last_expr ();
310 add_scope_stmt (/*begin_p=*/1, /*partial_p=*/0);
311
312 return body;
313 }
314
315 static void
316 finish_cdtor (body)
317 tree body;
318 {
319 tree scope;
320 tree block;
321
322 scope = add_scope_stmt (/*begin_p=*/0, /*partial_p=*/0);
323 block = poplevel (0, 0, 0);
324 SCOPE_STMT_BLOCK (TREE_PURPOSE (scope)) = block;
325 SCOPE_STMT_BLOCK (TREE_VALUE (scope)) = block;
326
327 RECHAIN_STMTS (body, COMPOUND_BODY (body));
328
329 finish_function (0, 0);
330 }
331
332 /* Called at end of parsing, but before end-of-file processing. */
333
334 void
335 c_objc_common_finish_file ()
336 {
337 expand_deferred_fns ();
338
339 if (static_ctors)
340 {
341 tree body = start_cdtor ('I');
342
343 for (; static_ctors; static_ctors = TREE_CHAIN (static_ctors))
344 c_expand_expr_stmt (build_function_call (TREE_VALUE (static_ctors),
345 NULL_TREE));
346
347 finish_cdtor (body);
348 }
349
350 if (static_dtors)
351 {
352 tree body = start_cdtor ('D');
353
354 for (; static_dtors; static_dtors = TREE_CHAIN (static_dtors))
355 c_expand_expr_stmt (build_function_call (TREE_VALUE (static_dtors),
356 NULL_TREE));
357
358 finish_cdtor (body);
359 }
360
361 {
362 int flags;
363 FILE *stream = dump_begin (TDI_all, &flags);
364
365 if (stream)
366 {
367 dump_node (getdecls (), flags & ~TDF_SLIM, stream);
368 dump_end (TDI_all, stream);
369 }
370 }
371 }
372
373 /* Called during diagnostic message formatting process to print a
374 source-level entity onto BUFFER. The meaning of the format specifiers
375 is as follows:
376 %D: a general decl,
377 %F: a function declaration,
378 %T: a type.
379
380 These format specifiers form a subset of the format specifiers set used
381 by the C++ front-end.
382 Please notice when called, the `%' part was already skipped by the
383 diagnostic machinery. */
384 static int
385 c_tree_printer (buffer)
386 output_buffer *buffer;
387 {
388 tree t = va_arg (output_buffer_format_args (buffer), tree);
389
390 switch (*output_buffer_text_cursor (buffer))
391 {
392 case 'D':
393 case 'F':
394 case 'T':
395 {
396 const char *n = DECL_NAME (t)
397 ? (*lang_hooks.decl_printable_name) (t, 2)
398 : "({anonymous})";
399 output_add_string (buffer, n);
400 }
401 return 1;
402
403 default:
404 return 0;
405 }
406 }