]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/fortran/trans-decl.c
Fix bug in an OpenACC async test case
[thirdparty/gcc.git] / gcc / fortran / trans-decl.c
CommitLineData
4ee9c684 1/* Backend function setup
aad93da1 2 Copyright (C) 2002-2017 Free Software Foundation, Inc.
4ee9c684 3 Contributed by Paul Brook
4
c84b470d 5This file is part of GCC.
4ee9c684 6
c84b470d 7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
bdabe786 9Software Foundation; either version 3, or (at your option) any later
c84b470d 10version.
4ee9c684 11
c84b470d 12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
4ee9c684 16
17You should have received a copy of the GNU General Public License
bdabe786 18along with GCC; see the file COPYING3. If not see
19<http://www.gnu.org/licenses/>. */
4ee9c684 20
21/* trans-decl.c -- Handling of backend function and variable decls, etc */
22
23#include "config.h"
24#include "system.h"
25#include "coretypes.h"
4cba6f60 26#include "target.h"
27#include "function.h"
28#include "tree.h"
dc8078a3 29#include "gfortran.h"
4cba6f60 30#include "gimple-expr.h" /* For create_tmp_var_raw. */
31#include "trans.h"
32#include "stringpool.h"
33#include "cgraph.h"
b20a8bb4 34#include "fold-const.h"
9ed99284 35#include "stor-layout.h"
36#include "varasm.h"
37#include "attribs.h"
930c75f4 38#include "dumpfile.h"
7cbc820e 39#include "toplev.h" /* For announce_function. */
df4d540f 40#include "debug.h"
126387b5 41#include "constructor.h"
4ee9c684 42#include "trans-types.h"
43#include "trans-array.h"
44#include "trans-const.h"
45/* Only for gfc_trans_code. Shouldn't need to include this. */
46#include "trans-stmt.h"
7c1a9598 47#include "gomp-constants.h"
1ec957b0 48#include "gimplify.h"
4ee9c684 49
50#define MAX_LABEL_VALUE 99999
51
52
53/* Holds the result of the function if no result variable specified. */
54
55static GTY(()) tree current_fake_result_decl;
c750cc52 56static GTY(()) tree parent_fake_result_decl;
4ee9c684 57
4ee9c684 58
59/* Holds the variable DECLs for the current function. */
60
d4163395 61static GTY(()) tree saved_function_decls;
62static GTY(()) tree saved_parent_function_decls;
4ee9c684 63
431205b7 64static hash_set<tree> *nonlocal_dummy_decl_pset;
9579733e 65static GTY(()) tree nonlocal_dummy_decls;
4ee9c684 66
6a7084d7 67/* Holds the variable DECLs that are locals. */
68
69static GTY(()) tree saved_local_decls;
70
4ee9c684 71/* The namespace of the module we're currently generating. Only used while
72 outputting decls for module variables. Do not rely on this being set. */
73
74static gfc_namespace *module_namespace;
75
89ac8ba1 76/* The currently processed procedure symbol. */
77static gfc_symbol* current_procedure_symbol = NULL;
78
3adf245a 79/* The currently processed module. */
80static struct module_htab_entry *cur_module;
4ee9c684 81
a961ca30 82/* With -fcoarray=lib: For generating the registering call
83 of static coarrays. */
84static bool has_coarray_vars;
85static stmtblock_t caf_init_block;
86
87
4ee9c684 88/* List of static constructor functions. */
89
90tree gfc_static_ctors;
91
92
d566c3e0 93/* Whether we've seen a symbol from an IEEE module in the namespace. */
94static int seen_ieee_symbol;
95
4ee9c684 96/* Function declarations for builtin library functions. */
97
4ee9c684 98tree gfor_fndecl_pause_numeric;
99tree gfor_fndecl_pause_string;
100tree gfor_fndecl_stop_numeric;
101tree gfor_fndecl_stop_string;
070cc790 102tree gfor_fndecl_error_stop_numeric;
c6cd3066 103tree gfor_fndecl_error_stop_string;
4ee9c684 104tree gfor_fndecl_runtime_error;
50ad5fa2 105tree gfor_fndecl_runtime_error_at;
da6ffc6d 106tree gfor_fndecl_runtime_warning_at;
9915365e 107tree gfor_fndecl_os_error;
50ad5fa2 108tree gfor_fndecl_generate_error;
7257a5d2 109tree gfor_fndecl_set_args;
8c84a5de 110tree gfor_fndecl_set_fpe;
56c7c2d7 111tree gfor_fndecl_set_options;
15774a8b 112tree gfor_fndecl_set_convert;
f23886ab 113tree gfor_fndecl_set_record_marker;
bbaaa7b1 114tree gfor_fndecl_set_max_subrecord_length;
b902b078 115tree gfor_fndecl_ctime;
116tree gfor_fndecl_fdate;
dbc97b88 117tree gfor_fndecl_ttynam;
4ee9c684 118tree gfor_fndecl_in_pack;
119tree gfor_fndecl_in_unpack;
120tree gfor_fndecl_associated;
72ce5390 121tree gfor_fndecl_system_clock4;
122tree gfor_fndecl_system_clock8;
d566c3e0 123tree gfor_fndecl_ieee_procedure_entry;
124tree gfor_fndecl_ieee_procedure_exit;
4ee9c684 125
126
70b5944a 127/* Coarray run-time library function decls. */
128tree gfor_fndecl_caf_init;
129tree gfor_fndecl_caf_finalize;
d44f2f7c 130tree gfor_fndecl_caf_this_image;
131tree gfor_fndecl_caf_num_images;
a961ca30 132tree gfor_fndecl_caf_register;
d0d776fb 133tree gfor_fndecl_caf_deregister;
5f4a118e 134tree gfor_fndecl_caf_get;
135tree gfor_fndecl_caf_send;
136tree gfor_fndecl_caf_sendget;
eee0cf09 137tree gfor_fndecl_caf_get_by_ref;
138tree gfor_fndecl_caf_send_by_ref;
139tree gfor_fndecl_caf_sendget_by_ref;
70b5944a 140tree gfor_fndecl_caf_sync_all;
71cf3ae6 141tree gfor_fndecl_caf_sync_memory;
70b5944a 142tree gfor_fndecl_caf_sync_images;
ba4d9b7e 143tree gfor_fndecl_caf_stop_str;
144tree gfor_fndecl_caf_stop_numeric;
70b5944a 145tree gfor_fndecl_caf_error_stop;
146tree gfor_fndecl_caf_error_stop_str;
97b9ac34 147tree gfor_fndecl_caf_atomic_def;
148tree gfor_fndecl_caf_atomic_ref;
149tree gfor_fndecl_caf_atomic_cas;
150tree gfor_fndecl_caf_atomic_op;
498b946e 151tree gfor_fndecl_caf_lock;
152tree gfor_fndecl_caf_unlock;
bd47f0bc 153tree gfor_fndecl_caf_event_post;
154tree gfor_fndecl_caf_event_wait;
155tree gfor_fndecl_caf_event_query;
d9ca273e 156tree gfor_fndecl_caf_fail_image;
157tree gfor_fndecl_caf_failed_images;
158tree gfor_fndecl_caf_image_status;
159tree gfor_fndecl_caf_stopped_images;
52306a18 160tree gfor_fndecl_co_broadcast;
79ed4a8e 161tree gfor_fndecl_co_max;
162tree gfor_fndecl_co_min;
e39efcef 163tree gfor_fndecl_co_reduce;
79ed4a8e 164tree gfor_fndecl_co_sum;
3d2aa0e8 165tree gfor_fndecl_caf_is_present;
70b5944a 166
70b5944a 167
4ee9c684 168/* Math functions. Many other math functions are handled in
169 trans-intrinsic.c. */
170
920e54ef 171gfc_powdecl_list gfor_fndecl_math_powi[4][3];
4ee9c684 172tree gfor_fndecl_math_ishftc4;
173tree gfor_fndecl_math_ishftc8;
920e54ef 174tree gfor_fndecl_math_ishftc16;
4ee9c684 175
176
177/* String functions. */
178
4ee9c684 179tree gfor_fndecl_compare_string;
180tree gfor_fndecl_concat_string;
181tree gfor_fndecl_string_len_trim;
182tree gfor_fndecl_string_index;
183tree gfor_fndecl_string_scan;
184tree gfor_fndecl_string_verify;
185tree gfor_fndecl_string_trim;
5fcc6ec2 186tree gfor_fndecl_string_minmax;
4ee9c684 187tree gfor_fndecl_adjustl;
188tree gfor_fndecl_adjustr;
b44437b9 189tree gfor_fndecl_select_string;
40b806de 190tree gfor_fndecl_compare_string_char4;
191tree gfor_fndecl_concat_string_char4;
192tree gfor_fndecl_string_len_trim_char4;
193tree gfor_fndecl_string_index_char4;
194tree gfor_fndecl_string_scan_char4;
195tree gfor_fndecl_string_verify_char4;
196tree gfor_fndecl_string_trim_char4;
197tree gfor_fndecl_string_minmax_char4;
198tree gfor_fndecl_adjustl_char4;
199tree gfor_fndecl_adjustr_char4;
b44437b9 200tree gfor_fndecl_select_string_char4;
201
202
203/* Conversion between character kinds. */
204tree gfor_fndecl_convert_char1_to_char4;
205tree gfor_fndecl_convert_char4_to_char1;
4ee9c684 206
207
208/* Other misc. runtime library functions. */
4ee9c684 209tree gfor_fndecl_size0;
210tree gfor_fndecl_size1;
9b057c29 211tree gfor_fndecl_iargc;
4ee9c684 212
59e2a584 213/* Intrinsic functions implemented in Fortran. */
214tree gfor_fndecl_sc_kind;
4ee9c684 215tree gfor_fndecl_si_kind;
216tree gfor_fndecl_sr_kind;
217
4e8e57b0 218/* BLAS gemm functions. */
219tree gfor_fndecl_sgemm;
220tree gfor_fndecl_dgemm;
221tree gfor_fndecl_cgemm;
222tree gfor_fndecl_zgemm;
223
4ee9c684 224
225static void
226gfc_add_decl_to_parent_function (tree decl)
227{
22d678e8 228 gcc_assert (decl);
4ee9c684 229 DECL_CONTEXT (decl) = DECL_CONTEXT (current_function_decl);
230 DECL_NONLOCAL (decl) = 1;
1767a056 231 DECL_CHAIN (decl) = saved_parent_function_decls;
4ee9c684 232 saved_parent_function_decls = decl;
233}
234
235void
236gfc_add_decl_to_function (tree decl)
237{
22d678e8 238 gcc_assert (decl);
4ee9c684 239 TREE_USED (decl) = 1;
240 DECL_CONTEXT (decl) = current_function_decl;
1767a056 241 DECL_CHAIN (decl) = saved_function_decls;
4ee9c684 242 saved_function_decls = decl;
243}
244
6a7084d7 245static void
246add_decl_as_local (tree decl)
247{
248 gcc_assert (decl);
249 TREE_USED (decl) = 1;
250 DECL_CONTEXT (decl) = current_function_decl;
1767a056 251 DECL_CHAIN (decl) = saved_local_decls;
6a7084d7 252 saved_local_decls = decl;
253}
254
4ee9c684 255
b797d6d3 256/* Build a backend label declaration. Set TREE_USED for named labels.
257 The context of the label is always the current_function_decl. All
258 labels are marked artificial. */
4ee9c684 259
260tree
261gfc_build_label_decl (tree label_id)
262{
263 /* 2^32 temporaries should be enough. */
264 static unsigned int tmp_num = 1;
265 tree label_decl;
266 char *label_name;
267
268 if (label_id == NULL_TREE)
269 {
270 /* Build an internal label name. */
271 ASM_FORMAT_PRIVATE_NAME (label_name, "L", tmp_num++);
272 label_id = get_identifier (label_name);
273 }
274 else
275 label_name = NULL;
276
277 /* Build the LABEL_DECL node. Labels have no type. */
e60a6f7b 278 label_decl = build_decl (input_location,
279 LABEL_DECL, label_id, void_type_node);
4ee9c684 280 DECL_CONTEXT (label_decl) = current_function_decl;
adc78298 281 SET_DECL_MODE (label_decl, VOIDmode);
4ee9c684 282
b797d6d3 283 /* We always define the label as used, even if the original source
284 file never references the label. We don't want all kinds of
285 spurious warnings for old-style Fortran code with too many
286 labels. */
287 TREE_USED (label_decl) = 1;
4ee9c684 288
b797d6d3 289 DECL_ARTIFICIAL (label_decl) = 1;
4ee9c684 290 return label_decl;
291}
292
293
b31f705b 294/* Set the backend source location of a decl. */
295
296void
297gfc_set_decl_location (tree decl, locus * loc)
298{
b31f705b 299 DECL_SOURCE_LOCATION (decl) = loc->lb->location;
b31f705b 300}
301
302
4ee9c684 303/* Return the backend label declaration for a given label structure,
304 or create it if it doesn't exist yet. */
305
306tree
307gfc_get_label_decl (gfc_st_label * lp)
308{
4ee9c684 309 if (lp->backend_decl)
310 return lp->backend_decl;
311 else
312 {
313 char label_name[GFC_MAX_SYMBOL_LEN + 1];
314 tree label_decl;
315
316 /* Validate the label declaration from the front end. */
22d678e8 317 gcc_assert (lp != NULL && lp->value <= MAX_LABEL_VALUE);
4ee9c684 318
319 /* Build a mangled name for the label. */
320 sprintf (label_name, "__label_%.6d", lp->value);
321
322 /* Build the LABEL_DECL node. */
323 label_decl = gfc_build_label_decl (get_identifier (label_name));
324
325 /* Tell the debugger where the label came from. */
f888a3fb 326 if (lp->value <= MAX_LABEL_VALUE) /* An internal label. */
b31f705b 327 gfc_set_decl_location (label_decl, &lp->where);
4ee9c684 328 else
329 DECL_ARTIFICIAL (label_decl) = 1;
330
331 /* Store the label in the label list and return the LABEL_DECL. */
332 lp->backend_decl = label_decl;
333 return label_decl;
334 }
335}
336
337
338/* Convert a gfc_symbol to an identifier of the same name. */
339
340static tree
341gfc_sym_identifier (gfc_symbol * sym)
342{
0509d0ee 343 if (sym->attr.is_main_program && strcmp (sym->name, "main") == 0)
344 return (get_identifier ("MAIN__"));
345 else
346 return (get_identifier (sym->name));
4ee9c684 347}
348
349
350/* Construct mangled name from symbol name. */
351
352static tree
353gfc_sym_mangled_identifier (gfc_symbol * sym)
354{
355 char name[GFC_MAX_MANGLED_SYMBOL_LEN + 1];
356
c5d33754 357 /* Prevent the mangling of identifiers that have an assigned
358 binding label (mainly those that are bind(c)). */
7b2060ba 359 if (sym->attr.is_bind_c == 1 && sym->binding_label)
360 return get_identifier (sym->binding_label);
a90fe829 361
8b7e5587 362 if (!sym->fn_result_spec)
363 {
364 if (sym->module == NULL)
365 return gfc_sym_identifier (sym);
366 else
367 {
368 snprintf (name, sizeof name, "__%s_MOD_%s", sym->module, sym->name);
369 return get_identifier (name);
370 }
371 }
4ee9c684 372 else
373 {
8b7e5587 374 /* This is an entity that is actually local to a module procedure
375 that appears in the result specification expression. Since
376 sym->module will be a zero length string, we use ns->proc_name
377 instead. */
378 if (sym->ns->proc_name && sym->ns->proc_name->module)
379 {
380 snprintf (name, sizeof name, "__%s_MOD__%s_PROC_%s",
381 sym->ns->proc_name->module,
382 sym->ns->proc_name->name,
383 sym->name);
384 return get_identifier (name);
385 }
386 else
387 {
388 snprintf (name, sizeof name, "__%s_PROC_%s",
389 sym->ns->proc_name->name, sym->name);
390 return get_identifier (name);
391 }
4ee9c684 392 }
393}
394
395
396/* Construct mangled function name from symbol name. */
397
398static tree
399gfc_sym_mangled_function_id (gfc_symbol * sym)
400{
401 int has_underscore;
402 char name[GFC_MAX_MANGLED_SYMBOL_LEN + 1];
403
c5d33754 404 /* It may be possible to simply use the binding label if it's
405 provided, and remove the other checks. Then we could use it
406 for other things if we wished. */
407 if ((sym->attr.is_bind_c == 1 || sym->attr.is_iso_c == 1) &&
7b2060ba 408 sym->binding_label)
c5d33754 409 /* use the binding label rather than the mangled name */
410 return get_identifier (sym->binding_label);
411
4b8eb6ca 412 if ((sym->module == NULL || sym->attr.proc == PROC_EXTERNAL
12441a18 413 || (sym->module != NULL && (sym->attr.external
414 || sym->attr.if_source == IFSRC_IFBODY)))
4b8eb6ca 415 && !sym->attr.module_procedure)
4ee9c684 416 {
a2f97da7 417 /* Main program is mangled into MAIN__. */
418 if (sym->attr.is_main_program)
419 return get_identifier ("MAIN__");
420
421 /* Intrinsic procedures are never mangled. */
422 if (sym->attr.proc == PROC_INTRINSIC)
4ee9c684 423 return get_identifier (sym->name);
424
829d7a08 425 if (flag_underscoring)
4ee9c684 426 {
427 has_underscore = strchr (sym->name, '_') != 0;
eb106faf 428 if (flag_second_underscore && has_underscore)
4ee9c684 429 snprintf (name, sizeof name, "%s__", sym->name);
430 else
431 snprintf (name, sizeof name, "%s_", sym->name);
432 return get_identifier (name);
433 }
434 else
435 return get_identifier (sym->name);
436 }
437 else
438 {
f08a3f6f 439 snprintf (name, sizeof name, "__%s_MOD_%s", sym->module, sym->name);
4ee9c684 440 return get_identifier (name);
441 }
442}
443
444
1236e28b 445void
446gfc_set_decl_assembler_name (tree decl, tree name)
447{
448 tree target_mangled = targetm.mangle_decl_assembler_name (decl, name);
449 SET_DECL_ASSEMBLER_NAME (decl, target_mangled);
450}
451
452
5ed82495 453/* Returns true if a variable of specified size should go on the stack. */
454
455int
456gfc_can_put_var_on_stack (tree size)
457{
458 unsigned HOST_WIDE_INT low;
459
460 if (!INTEGER_CST_P (size))
461 return 0;
462
eb106faf 463 if (flag_max_stack_var_size < 0)
5ed82495 464 return 1;
465
e1d65c9f 466 if (!tree_fits_uhwi_p (size))
5ed82495 467 return 0;
468
f9ae6f95 469 low = TREE_INT_CST_LOW (size);
eb106faf 470 if (low > (unsigned HOST_WIDE_INT) flag_max_stack_var_size)
5ed82495 471 return 0;
472
473/* TODO: Set a per-function stack size limit. */
474
475 return 1;
476}
477
478
b7bf3f81 479/* gfc_finish_cray_pointee sets DECL_VALUE_EXPR for a Cray pointee to
480 an expression involving its corresponding pointer. There are
481 2 cases; one for variable size arrays, and one for everything else,
482 because variable-sized arrays require one fewer level of
483 indirection. */
484
485static void
486gfc_finish_cray_pointee (tree decl, gfc_symbol *sym)
487{
488 tree ptr_decl = gfc_get_symbol_decl (sym->cp_pointer);
489 tree value;
490
491 /* Parameters need to be dereferenced. */
a90fe829 492 if (sym->cp_pointer->attr.dummy)
389dd41b 493 ptr_decl = build_fold_indirect_ref_loc (input_location,
494 ptr_decl);
b7bf3f81 495
496 /* Check to see if we're dealing with a variable-sized array. */
497 if (sym->attr.dimension
a90fe829 498 && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
499 {
942043f8 500 /* These decls will be dereferenced later, so we don't dereference
b7bf3f81 501 them here. */
502 value = convert (TREE_TYPE (decl), ptr_decl);
503 }
504 else
505 {
506 ptr_decl = convert (build_pointer_type (TREE_TYPE (decl)),
507 ptr_decl);
389dd41b 508 value = build_fold_indirect_ref_loc (input_location,
509 ptr_decl);
b7bf3f81 510 }
511
512 SET_DECL_VALUE_EXPR (decl, value);
513 DECL_HAS_VALUE_EXPR_P (decl) = 1;
764f1175 514 GFC_DECL_CRAY_POINTEE (decl) = 1;
b7bf3f81 515}
516
517
b9c7fce7 518/* Finish processing of a declaration without an initial value. */
4ee9c684 519
520static void
b9c7fce7 521gfc_finish_decl (tree decl)
4ee9c684 522{
b9c7fce7 523 gcc_assert (TREE_CODE (decl) == PARM_DECL
524 || DECL_INITIAL (decl) == NULL_TREE);
4ee9c684 525
fe732a9b 526 if (!VAR_P (decl))
b9c7fce7 527 return;
4ee9c684 528
b9c7fce7 529 if (DECL_SIZE (decl) == NULL_TREE
530 && TYPE_SIZE (TREE_TYPE (decl)) != NULL_TREE)
531 layout_decl (decl, 0);
532
533 /* A few consistency checks. */
534 /* A static variable with an incomplete type is an error if it is
535 initialized. Also if it is not file scope. Otherwise, let it
536 through, but if it is not `extern' then it may cause an error
537 message later. */
538 /* An automatic variable with an incomplete type is an error. */
539
540 /* We should know the storage size. */
541 gcc_assert (DECL_SIZE (decl) != NULL_TREE
a90fe829 542 || (TREE_STATIC (decl)
b9c7fce7 543 ? (!DECL_INITIAL (decl) || !DECL_CONTEXT (decl))
544 : DECL_EXTERNAL (decl)));
545
546 /* The storage size should be constant. */
547 gcc_assert ((!DECL_EXTERNAL (decl) && !TREE_STATIC (decl))
548 || !DECL_SIZE (decl)
549 || TREE_CODE (DECL_SIZE (decl)) == INTEGER_CST);
4ee9c684 550}
551
552
cf5f881f 553/* Handle setting of GFC_DECL_SCALAR* on DECL. */
554
555void
556gfc_finish_decl_attrs (tree decl, symbol_attribute *attr)
557{
558 if (!attr->dimension && !attr->codimension)
559 {
560 /* Handle scalar allocatable variables. */
561 if (attr->allocatable)
562 {
563 gfc_allocate_lang_decl (decl);
564 GFC_DECL_SCALAR_ALLOCATABLE (decl) = 1;
565 }
566 /* Handle scalar pointer variables. */
567 if (attr->pointer)
568 {
569 gfc_allocate_lang_decl (decl);
570 GFC_DECL_SCALAR_POINTER (decl) = 1;
571 }
572 }
573}
574
575
4ee9c684 576/* Apply symbol attributes to a variable, and add it to the function scope. */
577
578static void
579gfc_finish_var_decl (tree decl, gfc_symbol * sym)
580{
c1977dbe 581 tree new_type;
b549d2a5 582
b7bf3f81 583 /* Set DECL_VALUE_EXPR for Cray Pointees. */
b549d2a5 584 if (sym->attr.cray_pointee)
b7bf3f81 585 gfc_finish_cray_pointee (decl, sym);
b549d2a5 586
845a9546 587 /* TREE_ADDRESSABLE means the address of this variable is actually needed.
588 This is the equivalent of the TARGET variables.
589 We also need to set this if the variable is passed by reference in a
590 CALL statement. */
4ee9c684 591 if (sym->attr.target)
592 TREE_ADDRESSABLE (decl) = 1;
845a9546 593
4ee9c684 594 /* If it wasn't used we wouldn't be getting it. */
595 TREE_USED (decl) = 1;
596
7415cfe4 597 if (sym->attr.flavor == FL_PARAMETER
598 && (sym->attr.dimension || sym->ts.type == BT_DERIVED))
599 TREE_READONLY (decl) = 1;
600
4ee9c684 601 /* Chain this decl to the pending declarations. Don't do pushdecl()
602 because this would add them to the current scope rather than the
603 function scope. */
604 if (current_function_decl != NULL_TREE)
605 {
7af6a4af 606 if (sym->ns->proc_name->backend_decl == current_function_decl
6a7084d7 607 || sym->result == sym)
4ee9c684 608 gfc_add_decl_to_function (decl);
6a7084d7 609 else if (sym->ns->proc_name->attr.flavor == FL_LABEL)
610 /* This is a BLOCK construct. */
611 add_decl_as_local (decl);
4ee9c684 612 else
613 gfc_add_decl_to_parent_function (decl);
614 }
615
b7bf3f81 616 if (sym->attr.cray_pointee)
617 return;
618
c5cb468c 619 if(sym->attr.is_bind_c == 1 && sym->binding_label)
c5d33754 620 {
621 /* We need to put variables that are bind(c) into the common
622 segment of the object file, because this is what C would do.
623 gfortran would typically put them in either the BSS or
624 initialized data segments, and only mark them as common if
625 they were part of common blocks. However, if they are not put
ea657963 626 into common space, then C cannot initialize global Fortran
c5d33754 627 variables that it interoperates with and the draft says that
628 either Fortran or C should be able to initialize it (but not
629 both, of course.) (J3/04-007, section 15.3). */
630 TREE_PUBLIC(decl) = 1;
631 DECL_COMMON(decl) = 1;
c8ddfd5d 632 if (sym->attr.access == ACCESS_PRIVATE && !sym->attr.public_used)
633 {
634 DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
635 DECL_VISIBILITY_SPECIFIED (decl) = true;
636 }
c5d33754 637 }
a90fe829 638
4ee9c684 639 /* If a variable is USE associated, it's always external. */
4b8eb6ca 640 if (sym->attr.use_assoc || sym->attr.used_in_submodule)
4ee9c684 641 {
642 DECL_EXTERNAL (decl) = 1;
643 TREE_PUBLIC (decl) = 1;
644 }
8b7e5587 645 else if (sym->fn_result_spec && !sym->ns->proc_name->module)
646 {
647
648 if (sym->ns->proc_name->attr.if_source != IFSRC_DECL)
649 DECL_EXTERNAL (decl) = 1;
650 else
651 TREE_STATIC (decl) = 1;
652
653 TREE_PUBLIC (decl) = 1;
654 }
4f0fae8e 655 else if (sym->module && !sym->attr.result && !sym->attr.dummy)
4ee9c684 656 {
6b20224d 657 /* TODO: Don't set sym->module for result or dummy variables. */
7af6a4af 658 gcc_assert (current_function_decl == NULL_TREE || sym->result == sym);
7d6b5754 659
c8ddfd5d 660 TREE_PUBLIC (decl) = 1;
4ee9c684 661 TREE_STATIC (decl) = 1;
c8ddfd5d 662 if (sym->attr.access == ACCESS_PRIVATE && !sym->attr.public_used)
663 {
664 DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
665 DECL_VISIBILITY_SPECIFIED (decl) = true;
666 }
4ee9c684 667 }
668
f0d4969f 669 /* Derived types are a bit peculiar because of the possibility of
670 a default initializer; this must be applied each time the variable
671 comes into scope it therefore need not be static. These variables
672 are SAVE_NONE but have an initializer. Otherwise explicitly
69b1505f 673 initialized variables are SAVE_IMPLICIT and explicitly saved are
f0d4969f 674 SAVE_EXPLICIT. */
675 if (!sym->attr.use_assoc
676 && (sym->attr.save != SAVE_NONE || sym->attr.data
a961ca30 677 || (sym->value && sym->ns->proc_name->attr.is_main_program)
4fe73152 678 || (flag_coarray == GFC_FCOARRAY_LIB
a961ca30 679 && sym->attr.codimension && !sym->attr.allocatable)))
4ee9c684 680 TREE_STATIC (decl) = 1;
ef814c81 681
9f732c4e 682 /* If derived-type variables with DTIO procedures are not made static
683 some bits of code referencing them get optimized away.
684 TODO Understand why this is so and fix it. */
685 if (!sym->attr.use_assoc
686 && ((sym->ts.type == BT_DERIVED
687 && sym->ts.u.derived->attr.has_dtio_procs)
688 || (sym->ts.type == BT_CLASS
689 && CLASS_DATA (sym)->ts.u.derived->attr.has_dtio_procs)))
690 TREE_STATIC (decl) = 1;
691
ef814c81 692 if (sym->attr.volatile_)
693 {
ef814c81 694 TREE_THIS_VOLATILE (decl) = 1;
2364aa60 695 TREE_SIDE_EFFECTS (decl) = 1;
c1977dbe 696 new_type = build_qualified_type (TREE_TYPE (decl), TYPE_QUAL_VOLATILE);
697 TREE_TYPE (decl) = new_type;
a90fe829 698 }
ef814c81 699
4ee9c684 700 /* Keep variables larger than max-stack-var-size off stack. */
8e652fcf 701 if (!sym->ns->proc_name->attr.recursive && !sym->attr.automatic
4ee9c684 702 && INTEGER_CST_P (DECL_SIZE_UNIT (decl))
a3f2c0e1 703 && !gfc_can_put_var_on_stack (DECL_SIZE_UNIT (decl))
704 /* Put variable length auto array pointers always into stack. */
705 && (TREE_CODE (TREE_TYPE (decl)) != POINTER_TYPE
706 || sym->attr.dimension == 0
707 || sym->as->type != AS_EXPLICIT
708 || sym->attr.pointer
709 || sym->attr.allocatable)
710 && !DECL_ARTIFICIAL (decl))
14eab729 711 {
712 TREE_STATIC (decl) = 1;
713
714 /* Because the size of this variable isn't known until now, we may have
715 greedily added an initializer to this variable (in build_init_assign)
716 even though the max-stack-var-size indicates the variable should be
717 static. Therefore we rip out the automatic initializer here and
718 replace it with a static one. */
719 gfc_symtree *st = gfc_find_symtree (sym->ns->sym_root, sym->name);
720 gfc_code *prev = NULL;
721 gfc_code *code = sym->ns->code;
722 while (code && code->op == EXEC_INIT_ASSIGN)
723 {
724 /* Look for an initializer meant for this symbol. */
725 if (code->expr1->symtree == st)
726 {
727 if (prev)
728 prev->next = code->next;
729 else
730 sym->ns->code = code->next;
731
732 break;
733 }
734
735 prev = code;
736 code = code->next;
737 }
738 if (code && code->op == EXEC_INIT_ASSIGN)
739 {
740 /* Keep the init expression for a static initializer. */
741 sym->value = code->expr2;
742 /* Cleanup the defunct code object, without freeing the init expr. */
743 code->expr2 = NULL;
744 gfc_free_statement (code);
745 free (code);
746 }
747 }
764f1175 748
749 /* Handle threadprivate variables. */
9dda1f80 750 if (sym->attr.threadprivate
764f1175 751 && (TREE_STATIC (decl) || DECL_EXTERNAL (decl)))
5e68df57 752 set_decl_tls_model (decl, decl_default_tls_model (decl));
cf5f881f 753
754 gfc_finish_decl_attrs (decl, &sym->attr);
4ee9c684 755}
756
757
758/* Allocate the lang-specific part of a decl. */
759
760void
761gfc_allocate_lang_decl (tree decl)
762{
cf5f881f 763 if (DECL_LANG_SPECIFIC (decl) == NULL)
764 DECL_LANG_SPECIFIC (decl) = ggc_cleared_alloc<struct lang_decl> ();
4ee9c684 765}
766
767/* Remember a symbol to generate initialization/cleanup code at function
768 entry/exit. */
769
770static void
771gfc_defer_symbol_init (gfc_symbol * sym)
772{
773 gfc_symbol *p;
774 gfc_symbol *last;
775 gfc_symbol *head;
776
777 /* Don't add a symbol twice. */
778 if (sym->tlink)
779 return;
780
781 last = head = sym->ns->proc_name;
782 p = last->tlink;
783
784 /* Make sure that setup code for dummy variables which are used in the
785 setup of other variables is generated first. */
786 if (sym->attr.dummy)
787 {
788 /* Find the first dummy arg seen after us, or the first non-dummy arg.
789 This is a circular list, so don't go past the head. */
790 while (p != head
791 && (!p->attr.dummy || p->dummy_order > sym->dummy_order))
792 {
793 last = p;
794 p = p->tlink;
795 }
796 }
797 /* Insert in between last and p. */
798 last->tlink = sym;
799 sym->tlink = p;
800}
801
802
9f5a9ac5 803/* Used in gfc_get_symbol_decl and gfc_get_derived_type to obtain the
804 backend_decl for a module symbol, if it all ready exists. If the
805 module gsymbol does not exist, it is created. If the symbol does
806 not exist, it is added to the gsymbol namespace. Returns true if
807 an existing backend_decl is found. */
808
809bool
810gfc_get_module_backend_decl (gfc_symbol *sym)
811{
812 gfc_gsymbol *gsym;
813 gfc_symbol *s;
814 gfc_symtree *st;
815
816 gsym = gfc_find_gsymbol (gfc_gsym_root, sym->module);
817
818 if (!gsym || (gsym->ns && gsym->type == GSYM_MODULE))
819 {
820 st = NULL;
821 s = NULL;
822
d7cd448a 823 /* Check for a symbol with the same name. */
9f5a9ac5 824 if (gsym)
825 gfc_find_symbol (sym->name, gsym->ns, 0, &s);
826
827 if (!s)
828 {
829 if (!gsym)
830 {
831 gsym = gfc_get_gsymbol (sym->module);
832 gsym->type = GSYM_MODULE;
833 gsym->ns = gfc_get_namespace (NULL, 0);
834 }
835
836 st = gfc_new_symtree (&gsym->ns->sym_root, sym->name);
837 st->n.sym = sym;
838 sym->refs++;
839 }
d7cd448a 840 else if (gfc_fl_struct (sym->attr.flavor))
9f5a9ac5 841 {
c2958b6b 842 if (s && s->attr.flavor == FL_PROCEDURE)
843 {
844 gfc_interface *intr;
845 gcc_assert (s->attr.generic);
846 for (intr = s->generic; intr; intr = intr->next)
d7cd448a 847 if (gfc_fl_struct (intr->sym->attr.flavor))
c2958b6b 848 {
849 s = intr->sym;
850 break;
851 }
852 }
853
d7cd448a 854 /* Normally we can assume that s is a derived-type symbol since it
855 shares a name with the derived-type sym. However if sym is a
856 STRUCTURE, it may in fact share a name with any other basic type
857 variable. If s is in fact of derived type then we can continue
858 looking for a duplicate type declaration. */
859 if (sym->attr.flavor == FL_STRUCT && s->ts.type == BT_DERIVED)
860 {
861 s = s->ts.u.derived;
862 }
863
864 if (gfc_fl_struct (s->attr.flavor) && !s->backend_decl)
865 {
866 if (s->attr.flavor == FL_UNION)
867 s->backend_decl = gfc_get_union_type (s);
868 else
869 s->backend_decl = gfc_get_derived_type (s);
870 }
9f5a9ac5 871 gfc_copy_dt_decls_ifequal (s, sym, true);
872 return true;
873 }
874 else if (s->backend_decl)
875 {
85ec2f13 876 if (sym->ts.type == BT_DERIVED || sym->ts.type == BT_CLASS)
9f5a9ac5 877 gfc_copy_dt_decls_ifequal (s->ts.u.derived, sym->ts.u.derived,
878 true);
879 else if (sym->ts.type == BT_CHARACTER)
880 sym->ts.u.cl->backend_decl = s->ts.u.cl->backend_decl;
881 sym->backend_decl = s->backend_decl;
882 return true;
883 }
884 }
885 return false;
886}
887
888
4ee9c684 889/* Create an array index type variable with function scope. */
890
891static tree
892create_index_var (const char * pfx, int nest)
893{
894 tree decl;
895
896 decl = gfc_create_var_np (gfc_array_index_type, pfx);
897 if (nest)
898 gfc_add_decl_to_parent_function (decl);
899 else
900 gfc_add_decl_to_function (decl);
901 return decl;
902}
903
904
905/* Create variables to hold all the non-constant bits of info for a
906 descriptorless array. Remember these in the lang-specific part of the
907 type. */
908
909static void
910gfc_build_qualified_array (tree decl, gfc_symbol * sym)
911{
912 tree type;
913 int dim;
914 int nest;
7b82374f 915 gfc_namespace* procns;
c6793847 916 symbol_attribute *array_attr;
917 gfc_array_spec *as;
918 bool is_classarray = IS_CLASS_ARRAY (sym);
4ee9c684 919
920 type = TREE_TYPE (decl);
c6793847 921 array_attr = is_classarray ? &CLASS_DATA (sym)->attr : &sym->attr;
922 as = is_classarray ? CLASS_DATA (sym)->as : sym->as;
4ee9c684 923
924 /* We just use the descriptor, if there is one. */
925 if (GFC_DESCRIPTOR_TYPE_P (type))
926 return;
927
22d678e8 928 gcc_assert (GFC_ARRAY_TYPE_P (type));
7b82374f 929 procns = gfc_find_proc_namespace (sym->ns);
930 nest = (procns->proc_name->backend_decl != current_function_decl)
4ee9c684 931 && !sym->attr.contained;
932
c6793847 933 if (array_attr->codimension && flag_coarray == GFC_FCOARRAY_LIB
934 && as->type != AS_ASSUMED_SHAPE
a961ca30 935 && GFC_TYPE_ARRAY_CAF_TOKEN (type) == NULL_TREE)
936 {
937 tree token;
ac36faf0 938 tree token_type = build_qualified_type (pvoid_type_node,
939 TYPE_QUAL_RESTRICT);
940
941 if (sym->module && (sym->attr.use_assoc
942 || sym->ns->proc_name->attr.flavor == FL_MODULE))
943 {
944 tree token_name
945 = get_identifier (gfc_get_string (GFC_PREFIX ("caf_token%s"),
946 IDENTIFIER_POINTER (gfc_sym_mangled_identifier (sym))));
947 token = build_decl (DECL_SOURCE_LOCATION (decl), VAR_DECL, token_name,
948 token_type);
3adf245a 949 if (sym->attr.use_assoc)
950 DECL_EXTERNAL (token) = 1;
951 else
952 TREE_STATIC (token) = 1;
953
c8ddfd5d 954 TREE_PUBLIC (token) = 1;
955
956 if (sym->attr.access == ACCESS_PRIVATE && !sym->attr.public_used)
957 {
958 DECL_VISIBILITY (token) = VISIBILITY_HIDDEN;
959 DECL_VISIBILITY_SPECIFIED (token) = true;
960 }
ac36faf0 961 }
962 else
3adf245a 963 {
964 token = gfc_create_var_np (token_type, "caf_token");
965 TREE_STATIC (token) = 1;
966 }
a961ca30 967
a961ca30 968 GFC_TYPE_ARRAY_CAF_TOKEN (type) = token;
969 DECL_ARTIFICIAL (token) = 1;
3adf245a 970 DECL_NONALIASED (token) = 1;
971
972 if (sym->module && !sym->attr.use_assoc)
973 {
974 pushdecl (token);
975 DECL_CONTEXT (token) = sym->ns->proc_name->backend_decl;
976 gfc_module_add_decl (cur_module, token);
977 }
13feeaec 978 else if (sym->attr.host_assoc
979 && TREE_CODE (DECL_CONTEXT (current_function_decl))
980 != TRANSLATION_UNIT_DECL)
1dbd61ab 981 gfc_add_decl_to_parent_function (token);
3adf245a 982 else
983 gfc_add_decl_to_function (token);
a961ca30 984 }
985
4ee9c684 986 for (dim = 0; dim < GFC_TYPE_ARRAY_RANK (type); dim++)
987 {
988 if (GFC_TYPE_ARRAY_LBOUND (type, dim) == NULL_TREE)
86254bbf 989 {
990 GFC_TYPE_ARRAY_LBOUND (type, dim) = create_index_var ("lbound", nest);
991 TREE_NO_WARNING (GFC_TYPE_ARRAY_LBOUND (type, dim)) = 1;
992 }
9ca15c9b 993 /* Don't try to use the unknown bound for assumed shape arrays. */
4ee9c684 994 if (GFC_TYPE_ARRAY_UBOUND (type, dim) == NULL_TREE
c6793847 995 && (as->type != AS_ASSUMED_SIZE
996 || dim < GFC_TYPE_ARRAY_RANK (type) - 1))
86254bbf 997 {
998 GFC_TYPE_ARRAY_UBOUND (type, dim) = create_index_var ("ubound", nest);
999 TREE_NO_WARNING (GFC_TYPE_ARRAY_UBOUND (type, dim)) = 1;
1000 }
4ee9c684 1001
1002 if (GFC_TYPE_ARRAY_STRIDE (type, dim) == NULL_TREE)
86254bbf 1003 {
1004 GFC_TYPE_ARRAY_STRIDE (type, dim) = create_index_var ("stride", nest);
1005 TREE_NO_WARNING (GFC_TYPE_ARRAY_STRIDE (type, dim)) = 1;
1006 }
4ee9c684 1007 }
076094b7 1008 for (dim = GFC_TYPE_ARRAY_RANK (type);
1009 dim < GFC_TYPE_ARRAY_RANK (type) + GFC_TYPE_ARRAY_CORANK (type); dim++)
1010 {
1011 if (GFC_TYPE_ARRAY_LBOUND (type, dim) == NULL_TREE)
1012 {
1013 GFC_TYPE_ARRAY_LBOUND (type, dim) = create_index_var ("lbound", nest);
1014 TREE_NO_WARNING (GFC_TYPE_ARRAY_LBOUND (type, dim)) = 1;
1015 }
1016 /* Don't try to use the unknown ubound for the last coarray dimension. */
1017 if (GFC_TYPE_ARRAY_UBOUND (type, dim) == NULL_TREE
1018 && dim < GFC_TYPE_ARRAY_RANK (type) + GFC_TYPE_ARRAY_CORANK (type) - 1)
1019 {
1020 GFC_TYPE_ARRAY_UBOUND (type, dim) = create_index_var ("ubound", nest);
1021 TREE_NO_WARNING (GFC_TYPE_ARRAY_UBOUND (type, dim)) = 1;
1022 }
1023 }
4ee9c684 1024 if (GFC_TYPE_ARRAY_OFFSET (type) == NULL_TREE)
1025 {
1026 GFC_TYPE_ARRAY_OFFSET (type) = gfc_create_var_np (gfc_array_index_type,
1027 "offset");
86254bbf 1028 TREE_NO_WARNING (GFC_TYPE_ARRAY_OFFSET (type)) = 1;
1029
4ee9c684 1030 if (nest)
1031 gfc_add_decl_to_parent_function (GFC_TYPE_ARRAY_OFFSET (type));
1032 else
1033 gfc_add_decl_to_function (GFC_TYPE_ARRAY_OFFSET (type));
1034 }
d4163395 1035
1036 if (GFC_TYPE_ARRAY_SIZE (type) == NULL_TREE
c6793847 1037 && as->type != AS_ASSUMED_SIZE)
86254bbf 1038 {
1039 GFC_TYPE_ARRAY_SIZE (type) = create_index_var ("size", nest);
1040 TREE_NO_WARNING (GFC_TYPE_ARRAY_SIZE (type)) = 1;
1041 }
d4163395 1042
1043 if (POINTER_TYPE_P (type))
1044 {
1045 gcc_assert (GFC_ARRAY_TYPE_P (TREE_TYPE (type)));
1046 gcc_assert (TYPE_LANG_SPECIFIC (type)
1047 == TYPE_LANG_SPECIFIC (TREE_TYPE (type)));
1048 type = TREE_TYPE (type);
1049 }
1050
1051 if (! COMPLETE_TYPE_P (type) && GFC_TYPE_ARRAY_SIZE (type))
1052 {
1053 tree size, range;
1054
fd779e1d 1055 size = fold_build2_loc (input_location, MINUS_EXPR, gfc_array_index_type,
1056 GFC_TYPE_ARRAY_SIZE (type), gfc_index_one_node);
d4163395 1057 range = build_range_type (gfc_array_index_type, gfc_index_zero_node,
1058 size);
1059 TYPE_DOMAIN (type) = range;
1060 layout_type (type);
1061 }
6cf159a6 1062
3fe3b7ca 1063 if (TYPE_NAME (type) != NULL_TREE && as->rank > 0
c6793847 1064 && GFC_TYPE_ARRAY_UBOUND (type, as->rank - 1) != NULL_TREE
fe732a9b 1065 && VAR_P (GFC_TYPE_ARRAY_UBOUND (type, as->rank - 1)))
6cf159a6 1066 {
1067 tree gtype = DECL_ORIGINAL_TYPE (TYPE_NAME (type));
1068
c6793847 1069 for (dim = 0; dim < as->rank - 1; dim++)
6cf159a6 1070 {
1071 gcc_assert (TREE_CODE (gtype) == ARRAY_TYPE);
1072 gtype = TREE_TYPE (gtype);
1073 }
1074 gcc_assert (TREE_CODE (gtype) == ARRAY_TYPE);
1075 if (TYPE_MAX_VALUE (TYPE_DOMAIN (gtype)) == NULL)
1076 TYPE_NAME (type) = NULL_TREE;
1077 }
1078
1079 if (TYPE_NAME (type) == NULL_TREE)
1080 {
1081 tree gtype = TREE_TYPE (type), rtype, type_decl;
1082
c6793847 1083 for (dim = as->rank - 1; dim >= 0; dim--)
6cf159a6 1084 {
7130ec9d 1085 tree lbound, ubound;
1086 lbound = GFC_TYPE_ARRAY_LBOUND (type, dim);
1087 ubound = GFC_TYPE_ARRAY_UBOUND (type, dim);
1088 rtype = build_range_type (gfc_array_index_type, lbound, ubound);
6cf159a6 1089 gtype = build_array_type (gtype, rtype);
3c8f1d7e 1090 /* Ensure the bound variables aren't optimized out at -O0.
1091 For -O1 and above they often will be optimized out, but
84bfaaeb 1092 can be tracked by VTA. Also set DECL_NAMELESS, so that
1093 the artificial lbound.N or ubound.N DECL_NAME doesn't
1094 end up in debug info. */
fe732a9b 1095 if (lbound
1096 && VAR_P (lbound)
1097 && DECL_ARTIFICIAL (lbound)
1098 && DECL_IGNORED_P (lbound))
7130ec9d 1099 {
1100 if (DECL_NAME (lbound)
1101 && strstr (IDENTIFIER_POINTER (DECL_NAME (lbound)),
1102 "lbound") != 0)
84bfaaeb 1103 DECL_NAMELESS (lbound) = 1;
7130ec9d 1104 DECL_IGNORED_P (lbound) = 0;
1105 }
fe732a9b 1106 if (ubound
1107 && VAR_P (ubound)
1108 && DECL_ARTIFICIAL (ubound)
1109 && DECL_IGNORED_P (ubound))
7130ec9d 1110 {
1111 if (DECL_NAME (ubound)
1112 && strstr (IDENTIFIER_POINTER (DECL_NAME (ubound)),
1113 "ubound") != 0)
84bfaaeb 1114 DECL_NAMELESS (ubound) = 1;
7130ec9d 1115 DECL_IGNORED_P (ubound) = 0;
1116 }
6cf159a6 1117 }
e60a6f7b 1118 TYPE_NAME (type) = type_decl = build_decl (input_location,
1119 TYPE_DECL, NULL, gtype);
6cf159a6 1120 DECL_ORIGINAL_TYPE (type_decl) = gtype;
1121 }
4ee9c684 1122}
1123
1124
1125/* For some dummy arguments we don't use the actual argument directly.
5ed82495 1126 Instead we create a local decl and use that. This allows us to perform
4ee9c684 1127 initialization, and construct full type information. */
1128
1129static tree
1130gfc_build_dummy_array_decl (gfc_symbol * sym, tree dummy)
1131{
1132 tree decl;
1133 tree type;
1134 gfc_array_spec *as;
c6793847 1135 symbol_attribute *array_attr;
4ee9c684 1136 char *name;
3d8dea5a 1137 gfc_packed packed;
4ee9c684 1138 int n;
1139 bool known_size;
c6793847 1140 bool is_classarray = IS_CLASS_ARRAY (sym);
1141
1142 /* Use the array as and attr. */
1143 as = is_classarray ? CLASS_DATA (sym)->as : sym->as;
1144 array_attr = is_classarray ? &CLASS_DATA (sym)->attr : &sym->attr;
1145
1146 /* The dummy is returned for pointer, allocatable or assumed rank arrays.
1147 For class arrays the information if sym is an allocatable or pointer
1148 object needs to be checked explicitly (IS_CLASS_ARRAY can be false for
1149 too many reasons to be of use here). */
1150 if ((sym->ts.type != BT_CLASS && sym->attr.pointer)
1151 || (sym->ts.type == BT_CLASS && CLASS_DATA (sym)->attr.class_pointer)
1152 || array_attr->allocatable
1153 || (as && as->type == AS_ASSUMED_RANK))
4ee9c684 1154 return dummy;
1155
c6793847 1156 /* Add to list of variables if not a fake result variable.
1157 These symbols are set on the symbol only, not on the class component. */
4ee9c684 1158 if (sym->attr.result || sym->attr.dummy)
1159 gfc_defer_symbol_init (sym);
1160
c6793847 1161 /* For a class array the array descriptor is in the _data component, while
1162 for a regular array the TREE_TYPE of the dummy is a pointer to the
1163 descriptor. */
1164 type = TREE_TYPE (is_classarray ? gfc_class_data_get (dummy)
1165 : TREE_TYPE (dummy));
1166 /* type now is the array descriptor w/o any indirection. */
22d678e8 1167 gcc_assert (TREE_CODE (dummy) == PARM_DECL
c6793847 1168 && POINTER_TYPE_P (TREE_TYPE (dummy)));
4ee9c684 1169
f888a3fb 1170 /* Do we know the element size? */
4ee9c684 1171 known_size = sym->ts.type != BT_CHARACTER
eeebe20b 1172 || INTEGER_CST_P (sym->ts.u.cl->backend_decl);
a90fe829 1173
c6793847 1174 if (known_size && !GFC_DESCRIPTOR_TYPE_P (type))
4ee9c684 1175 {
1176 /* For descriptorless arrays with known element size the actual
1177 argument is sufficient. */
4ee9c684 1178 gfc_build_qualified_array (dummy, sym);
1179 return dummy;
1180 }
1181
4ee9c684 1182 if (GFC_DESCRIPTOR_TYPE_P (type))
1183 {
cb8e3560 1184 /* Create a descriptorless array pointer. */
3d8dea5a 1185 packed = PACKED_NO;
3d235846 1186
1187 /* Even when -frepack-arrays is used, symbols with TARGET attribute
1188 are not repacked. */
829d7a08 1189 if (!flag_repack_arrays || sym->attr.target)
4ee9c684 1190 {
1191 if (as->type == AS_ASSUMED_SIZE)
3d8dea5a 1192 packed = PACKED_FULL;
4ee9c684 1193 }
1194 else
1195 {
1196 if (as->type == AS_EXPLICIT)
1197 {
3d8dea5a 1198 packed = PACKED_FULL;
4ee9c684 1199 for (n = 0; n < as->rank; n++)
1200 {
1201 if (!(as->upper[n]
1202 && as->lower[n]
1203 && as->upper[n]->expr_type == EXPR_CONSTANT
1204 && as->lower[n]->expr_type == EXPR_CONSTANT))
73bd65ab 1205 {
1206 packed = PACKED_PARTIAL;
1207 break;
1208 }
4ee9c684 1209 }
1210 }
1211 else
3d8dea5a 1212 packed = PACKED_PARTIAL;
4ee9c684 1213 }
1214
c6793847 1215 /* For classarrays the element type is required, but
1216 gfc_typenode_for_spec () returns the array descriptor. */
1217 type = is_classarray ? gfc_get_element_type (type)
1218 : gfc_typenode_for_spec (&sym->ts);
1219 type = gfc_get_nodesc_array_type (type, as, packed,
e1b3b79b 1220 !sym->attr.target);
4ee9c684 1221 }
1222 else
1223 {
1224 /* We now have an expression for the element size, so create a fully
1225 qualified type. Reset sym->backend decl or this will just return the
1226 old type. */
d95efb59 1227 DECL_ARTIFICIAL (sym->backend_decl) = 1;
4ee9c684 1228 sym->backend_decl = NULL_TREE;
1229 type = gfc_sym_type (sym);
3d8dea5a 1230 packed = PACKED_FULL;
4ee9c684 1231 }
1232
1233 ASM_FORMAT_PRIVATE_NAME (name, IDENTIFIER_POINTER (DECL_NAME (dummy)), 0);
e60a6f7b 1234 decl = build_decl (input_location,
1235 VAR_DECL, get_identifier (name), type);
4ee9c684 1236
1237 DECL_ARTIFICIAL (decl) = 1;
84bfaaeb 1238 DECL_NAMELESS (decl) = 1;
4ee9c684 1239 TREE_PUBLIC (decl) = 0;
1240 TREE_STATIC (decl) = 0;
1241 DECL_EXTERNAL (decl) = 0;
1242
a1f1e248 1243 /* Avoid uninitialized warnings for optional dummy arguments. */
1244 if (sym->attr.optional)
1245 TREE_NO_WARNING (decl) = 1;
1246
4ee9c684 1247 /* We should never get deferred shape arrays here. We used to because of
1248 frontend bugs. */
c6793847 1249 gcc_assert (as->type != AS_DEFERRED);
4ee9c684 1250
3d8dea5a 1251 if (packed == PACKED_PARTIAL)
1252 GFC_DECL_PARTIAL_PACKED_ARRAY (decl) = 1;
1253 else if (packed == PACKED_FULL)
1254 GFC_DECL_PACKED_ARRAY (decl) = 1;
4ee9c684 1255
1256 gfc_build_qualified_array (decl, sym);
1257
1258 if (DECL_LANG_SPECIFIC (dummy))
1259 DECL_LANG_SPECIFIC (decl) = DECL_LANG_SPECIFIC (dummy);
1260 else
1261 gfc_allocate_lang_decl (decl);
1262
1263 GFC_DECL_SAVED_DESCRIPTOR (decl) = dummy;
1264
1265 if (sym->ns->proc_name->backend_decl == current_function_decl
1266 || sym->attr.contained)
1267 gfc_add_decl_to_function (decl);
1268 else
1269 gfc_add_decl_to_parent_function (decl);
1270
1271 return decl;
1272}
1273
9579733e 1274/* For symbol SYM with GFC_DECL_SAVED_DESCRIPTOR used in contained
1275 function add a VAR_DECL to the current function with DECL_VALUE_EXPR
1276 pointing to the artificial variable for debug info purposes. */
1277
1278static void
1279gfc_nonlocal_dummy_array_decl (gfc_symbol *sym)
1280{
1281 tree decl, dummy;
1282
1283 if (! nonlocal_dummy_decl_pset)
431205b7 1284 nonlocal_dummy_decl_pset = new hash_set<tree>;
9579733e 1285
431205b7 1286 if (nonlocal_dummy_decl_pset->add (sym->backend_decl))
9579733e 1287 return;
1288
1289 dummy = GFC_DECL_SAVED_DESCRIPTOR (sym->backend_decl);
e60a6f7b 1290 decl = build_decl (input_location, VAR_DECL, DECL_NAME (dummy),
9579733e 1291 TREE_TYPE (sym->backend_decl));
1292 DECL_ARTIFICIAL (decl) = 0;
1293 TREE_USED (decl) = 1;
1294 TREE_PUBLIC (decl) = 0;
1295 TREE_STATIC (decl) = 0;
1296 DECL_EXTERNAL (decl) = 0;
1297 if (DECL_BY_REFERENCE (dummy))
1298 DECL_BY_REFERENCE (decl) = 1;
1299 DECL_LANG_SPECIFIC (decl) = DECL_LANG_SPECIFIC (sym->backend_decl);
1300 SET_DECL_VALUE_EXPR (decl, sym->backend_decl);
1301 DECL_HAS_VALUE_EXPR_P (decl) = 1;
1302 DECL_CONTEXT (decl) = DECL_CONTEXT (sym->backend_decl);
1767a056 1303 DECL_CHAIN (decl) = nonlocal_dummy_decls;
9579733e 1304 nonlocal_dummy_decls = decl;
1305}
4ee9c684 1306
1307/* Return a constant or a variable to use as a string length. Does not
1308 add the decl to the current scope. */
1309
1310static tree
1311gfc_create_string_length (gfc_symbol * sym)
1312{
eeebe20b 1313 gcc_assert (sym->ts.u.cl);
1314 gfc_conv_const_charlen (sym->ts.u.cl);
a4abf8a0 1315
eeebe20b 1316 if (sym->ts.u.cl->backend_decl == NULL_TREE)
4ee9c684 1317 {
a4abf8a0 1318 tree length;
774bbd60 1319 const char *name;
4ee9c684 1320
873f242d 1321 /* The string length variable shall be in static memory if it is either
1322 explicitly SAVED, a module variable or with -fno-automatic. Only
1323 relevant is "len=:" - otherwise, it is either a constant length or
1324 it is an automatic variable. */
be125be0 1325 bool static_length = sym->attr.save
1326 || sym->ns->proc_name->attr.flavor == FL_MODULE
eb106faf 1327 || (flag_max_stack_var_size == 0
873f242d 1328 && sym->ts.deferred && !sym->attr.dummy
1329 && !sym->attr.result && !sym->attr.function);
be125be0 1330
1331 /* Also prefix the mangled name. We need to call GFC_PREFIX for static
1332 variables as some systems do not support the "." in the assembler name.
1333 For nonstatic variables, the "." does not appear in assembler. */
1334 if (static_length)
1335 {
1336 if (sym->module)
1337 name = gfc_get_string (GFC_PREFIX ("%s_MOD_%s"), sym->module,
1338 sym->name);
1339 else
1340 name = gfc_get_string (GFC_PREFIX ("%s"), sym->name);
1341 }
1342 else if (sym->module)
774bbd60 1343 name = gfc_get_string (".__%s_MOD_%s", sym->module, sym->name);
1344 else
1345 name = gfc_get_string (".%s", sym->name);
1346
e60a6f7b 1347 length = build_decl (input_location,
1348 VAR_DECL, get_identifier (name),
9ad09405 1349 gfc_charlen_type_node);
4ee9c684 1350 DECL_ARTIFICIAL (length) = 1;
1351 TREE_USED (length) = 1;
d4163395 1352 if (sym->ns->proc_name->tlink != NULL)
1353 gfc_defer_symbol_init (sym);
a4abf8a0 1354
eeebe20b 1355 sym->ts.u.cl->backend_decl = length;
774bbd60 1356
be125be0 1357 if (static_length)
774bbd60 1358 TREE_STATIC (length) = 1;
1359
1360 if (sym->ns->proc_name->attr.flavor == FL_MODULE
1361 && (sym->attr.access != ACCESS_PRIVATE || sym->attr.public_used))
1362 TREE_PUBLIC (length) = 1;
4ee9c684 1363 }
1364
eeebe20b 1365 gcc_assert (sym->ts.u.cl->backend_decl != NULL_TREE);
1366 return sym->ts.u.cl->backend_decl;
4ee9c684 1367}
1368
c8f1568f 1369/* If a variable is assigned a label, we add another two auxiliary
1370 variables. */
1371
1372static void
1373gfc_add_assign_aux_vars (gfc_symbol * sym)
1374{
1375 tree addr;
1376 tree length;
1377 tree decl;
1378
1379 gcc_assert (sym->backend_decl);
1380
1381 decl = sym->backend_decl;
1382 gfc_allocate_lang_decl (decl);
1383 GFC_DECL_ASSIGN (decl) = 1;
e60a6f7b 1384 length = build_decl (input_location,
1385 VAR_DECL, create_tmp_var_name (sym->name),
c8f1568f 1386 gfc_charlen_type_node);
e60a6f7b 1387 addr = build_decl (input_location,
1388 VAR_DECL, create_tmp_var_name (sym->name),
c8f1568f 1389 pvoid_type_node);
1390 gfc_finish_var_decl (length, sym);
1391 gfc_finish_var_decl (addr, sym);
1392 /* STRING_LENGTH is also used as flag. Less than -1 means that
1393 ASSIGN_ADDR can not be used. Equal -1 means that ASSIGN_ADDR is the
1394 target label's address. Otherwise, value is the length of a format string
1395 and ASSIGN_ADDR is its address. */
1396 if (TREE_STATIC (length))
35bf1214 1397 DECL_INITIAL (length) = build_int_cst (gfc_charlen_type_node, -2);
c8f1568f 1398 else
1399 gfc_defer_symbol_init (sym);
1400
1401 GFC_DECL_STRING_LEN (decl) = length;
1402 GFC_DECL_ASSIGN_ADDR (decl) = addr;
1403}
4ee9c684 1404
36b0a1b0 1405
1406static tree
1407add_attributes_to_decl (symbol_attribute sym_attr, tree list)
1408{
1409 unsigned id;
1410 tree attr;
1411
1412 for (id = 0; id < EXT_ATTR_NUM; id++)
1413 if (sym_attr.ext_attr & (1 << id))
1414 {
1415 attr = build_tree_list (
1416 get_identifier (ext_attr_list[id].middle_end_name),
1417 NULL_TREE);
1418 list = chainon (list, attr);
1419 }
1420
44b49e6b 1421 if (sym_attr.omp_declare_target_link)
1422 list = tree_cons (get_identifier ("omp declare target link"),
1423 NULL_TREE, list);
1424 else if (sym_attr.omp_declare_target)
691447ab 1425 list = tree_cons (get_identifier ("omp declare target"),
1426 NULL_TREE, list);
1427
7c1a9598 1428 if (sym_attr.oacc_function)
1429 {
1430 tree dims = NULL_TREE;
1431 int ix;
1432 int level = sym_attr.oacc_function - 1;
1433
1434 for (ix = GOMP_DIM_MAX; ix--;)
1435 dims = tree_cons (build_int_cst (boolean_type_node, ix >= level),
1436 integer_zero_node, dims);
1437
1438 list = tree_cons (get_identifier ("oacc function"),
1439 dims, list);
1440 }
1441
36b0a1b0 1442 return list;
1443}
1444
1445
802532b9 1446static void build_function_decl (gfc_symbol * sym, bool global);
1447
1448
4ee9c684 1449/* Return the decl for a gfc_symbol, create it if it doesn't already
1450 exist. */
1451
1452tree
1453gfc_get_symbol_decl (gfc_symbol * sym)
1454{
1455 tree decl;
1456 tree length = NULL_TREE;
36b0a1b0 1457 tree attributes;
4ee9c684 1458 int byref;
cd2c99b8 1459 bool intrinsic_array_parameter = false;
8b9eb27e 1460 bool fun_or_res;
4ee9c684 1461
0b5dc8b5 1462 gcc_assert (sym->attr.referenced
9e45357a 1463 || sym->attr.flavor == FL_PROCEDURE
1464 || sym->attr.use_assoc
4b8eb6ca 1465 || sym->attr.used_in_submodule
9e45357a 1466 || sym->ns->proc_name->attr.if_source == IFSRC_IFBODY
1467 || (sym->module && sym->attr.if_source != IFSRC_DECL
1468 && sym->backend_decl));
4ee9c684 1469
ff70e443 1470 if (sym->ns && sym->ns->proc_name && sym->ns->proc_name->attr.function)
4ee9c684 1471 byref = gfc_return_by_reference (sym->ns->proc_name);
1472 else
1473 byref = 0;
1474
09c509ed 1475 /* Make sure that the vtab for the declared type is completed. */
1476 if (sym->ts.type == BT_CLASS)
1477 {
50b4b37b 1478 gfc_component *c = CLASS_DATA (sym);
09c509ed 1479 if (!c->ts.u.derived->backend_decl)
eab71f19 1480 {
1481 gfc_find_derived_vtab (c->ts.u.derived);
1482 gfc_get_derived_type (sym->ts.u.derived);
1483 }
09c509ed 1484 }
1485
9d958d5b 1486 /* PDT parameterized array components and string_lengths must have the
1487 'len' parameters substituted for the expressions appearing in the
1488 declaration of the entity and memory allocated/deallocated. */
1489 if ((sym->ts.type == BT_DERIVED || sym->ts.type == BT_CLASS)
1490 && sym->param_list != NULL
1491 && !(sym->attr.host_assoc || sym->attr.use_assoc || sym->attr.dummy))
1492 gfc_defer_symbol_init (sym);
1493
1494 /* Dummy PDT 'len' parameters should be checked when they are explicit. */
1495 if ((sym->ts.type == BT_DERIVED || sym->ts.type == BT_CLASS)
1496 && (gfc_option.rtcheck & GFC_RTCHECK_BOUNDS)
1497 && sym->param_list != NULL
1498 && sym->attr.dummy)
1499 gfc_defer_symbol_init (sym);
1500
617125a6 1501 /* All deferred character length procedures need to retain the backend
1502 decl, which is a pointer to the character length in the caller's
1503 namespace and to declare a local character length. */
1504 if (!byref && sym->attr.function
1505 && sym->ts.type == BT_CHARACTER
1506 && sym->ts.deferred
1507 && sym->ts.u.cl->passed_length == NULL
1508 && sym->ts.u.cl->backend_decl
1509 && TREE_CODE (sym->ts.u.cl->backend_decl) == PARM_DECL)
1510 {
1511 sym->ts.u.cl->passed_length = sym->ts.u.cl->backend_decl;
ddcfeaf1 1512 gcc_assert (POINTER_TYPE_P (TREE_TYPE (sym->ts.u.cl->passed_length)));
1513 sym->ts.u.cl->backend_decl = build_fold_indirect_ref (sym->ts.u.cl->backend_decl);
617125a6 1514 }
1515
8b9eb27e 1516 fun_or_res = byref && (sym->attr.result
1517 || (sym->attr.function && sym->ts.deferred));
1518 if ((sym->attr.dummy && ! sym->attr.function) || fun_or_res)
4ee9c684 1519 {
1520 /* Return via extra parameter. */
1521 if (sym->attr.result && byref
1522 && !sym->backend_decl)
1523 {
1524 sym->backend_decl =
1525 DECL_ARGUMENTS (sym->ns->proc_name->backend_decl);
c6871095 1526 /* For entry master function skip over the __entry
1527 argument. */
1528 if (sym->ns->proc_name->attr.entry_master)
1767a056 1529 sym->backend_decl = DECL_CHAIN (sym->backend_decl);
4ee9c684 1530 }
1531
1532 /* Dummy variables should already have been created. */
22d678e8 1533 gcc_assert (sym->backend_decl);
4ee9c684 1534
47e6a59a 1535 if (sym->attr.pointer && sym->attr.dimension && sym->ts.type != BT_CLASS)
1536 GFC_DECL_PTR_ARRAY_P (sym->backend_decl) = 1;
1537
4ee9c684 1538 /* Create a character length variable. */
1539 if (sym->ts.type == BT_CHARACTER)
1540 {
617125a6 1541 /* For a deferred dummy, make a new string length variable. */
1542 if (sym->ts.deferred
1543 &&
1544 (sym->ts.u.cl->passed_length == sym->ts.u.cl->backend_decl))
1545 sym->ts.u.cl->backend_decl = NULL_TREE;
1546
d1b1479f 1547 if (sym->ts.deferred && byref)
617125a6 1548 {
d1b1479f 1549 /* The string length of a deferred char array is stored in the
1550 parameter at sym->ts.u.cl->backend_decl as a reference and
1551 marked as a result. Exempt this variable from generating a
1552 temporary for it. */
1553 if (sym->attr.result)
1554 {
1555 /* We need to insert a indirect ref for param decls. */
1556 if (sym->ts.u.cl->backend_decl
1557 && TREE_CODE (sym->ts.u.cl->backend_decl) == PARM_DECL)
ddcfeaf1 1558 {
1559 sym->ts.u.cl->passed_length = sym->ts.u.cl->backend_decl;
a4731200 1560 sym->ts.u.cl->backend_decl =
d1b1479f 1561 build_fold_indirect_ref (sym->ts.u.cl->backend_decl);
a4731200 1562 }
ddcfeaf1 1563 }
d1b1479f 1564 /* For all other parameters make sure, that they are copied so
1565 that the value and any modifications are local to the routine
1566 by generating a temporary variable. */
1567 else if (sym->attr.function
1568 && sym->ts.u.cl->passed_length == NULL
1569 && sym->ts.u.cl->backend_decl)
1570 {
1571 sym->ts.u.cl->passed_length = sym->ts.u.cl->backend_decl;
ddcfeaf1 1572 if (POINTER_TYPE_P (TREE_TYPE (sym->ts.u.cl->passed_length)))
1573 sym->ts.u.cl->backend_decl
1574 = build_fold_indirect_ref (sym->ts.u.cl->backend_decl);
1575 else
a4731200 1576 sym->ts.u.cl->backend_decl = NULL_TREE;
d1b1479f 1577 }
617125a6 1578 }
1579
eeebe20b 1580 if (sym->ts.u.cl->backend_decl == NULL_TREE)
d4163395 1581 length = gfc_create_string_length (sym);
1582 else
eeebe20b 1583 length = sym->ts.u.cl->backend_decl;
fe732a9b 1584 if (VAR_P (length) && DECL_FILE_SCOPE_P (length))
4ee9c684 1585 {
d95efb59 1586 /* Add the string length to the same context as the symbol. */
1587 if (DECL_CONTEXT (sym->backend_decl) == current_function_decl)
1588 gfc_add_decl_to_function (length);
1589 else
1590 gfc_add_decl_to_parent_function (length);
1591
1592 gcc_assert (DECL_CONTEXT (sym->backend_decl) ==
1593 DECL_CONTEXT (length));
1594
d4163395 1595 gfc_defer_symbol_init (sym);
e8ff3944 1596 }
4ee9c684 1597 }
1598
1599 /* Use a copy of the descriptor for dummy arrays. */
7a777e43 1600 if ((sym->attr.dimension || sym->attr.codimension)
1601 && !TREE_USED (sym->backend_decl))
4ee9c684 1602 {
d95efb59 1603 decl = gfc_build_dummy_array_decl (sym, sym->backend_decl);
1604 /* Prevent the dummy from being detected as unused if it is copied. */
1605 if (sym->backend_decl != NULL && decl != sym->backend_decl)
1606 DECL_ARTIFICIAL (sym->backend_decl) = 1;
1607 sym->backend_decl = decl;
4ee9c684 1608 }
1609
c6793847 1610 /* Returning the descriptor for dummy class arrays is hazardous, because
1611 some caller is expecting an expression to apply the component refs to.
1612 Therefore the descriptor is only created and stored in
1613 sym->backend_decl's GFC_DECL_SAVED_DESCRIPTOR. The caller is then
1614 responsible to extract it from there, when the descriptor is
1615 desired. */
1616 if (IS_CLASS_ARRAY (sym)
1617 && (!DECL_LANG_SPECIFIC (sym->backend_decl)
1618 || !GFC_DECL_SAVED_DESCRIPTOR (sym->backend_decl)))
1619 {
1620 decl = gfc_build_dummy_array_decl (sym, sym->backend_decl);
1621 /* Prevent the dummy from being detected as unused if it is copied. */
1622 if (sym->backend_decl != NULL && decl != sym->backend_decl)
1623 DECL_ARTIFICIAL (sym->backend_decl) = 1;
1624 sym->backend_decl = decl;
1625 }
1626
4ee9c684 1627 TREE_USED (sym->backend_decl) = 1;
c8f1568f 1628 if (sym->attr.assign && GFC_DECL_ASSIGN (sym->backend_decl) == 0)
1629 {
1630 gfc_add_assign_aux_vars (sym);
1631 }
9579733e 1632
c6793847 1633 if ((sym->attr.dimension || IS_CLASS_ARRAY (sym))
9579733e 1634 && DECL_LANG_SPECIFIC (sym->backend_decl)
1635 && GFC_DECL_SAVED_DESCRIPTOR (sym->backend_decl)
1636 && DECL_CONTEXT (sym->backend_decl) != current_function_decl)
1637 gfc_nonlocal_dummy_array_decl (sym);
1638
fd23cc08 1639 if (sym->ts.type == BT_CLASS && sym->backend_decl)
1640 GFC_DECL_CLASS(sym->backend_decl) = 1;
1641
fd23cc08 1642 return sym->backend_decl;
4ee9c684 1643 }
1644
1645 if (sym->backend_decl)
1646 return sym->backend_decl;
1647
a25debd0 1648 /* Special case for array-valued named constants from intrinsic
1649 procedures; those are inlined. */
d566c3e0 1650 if (sym->attr.use_assoc && sym->attr.flavor == FL_PARAMETER
1651 && (sym->from_intmod == INTMOD_ISO_FORTRAN_ENV
1652 || sym->from_intmod == INTMOD_ISO_C_BINDING))
a25debd0 1653 intrinsic_array_parameter = true;
1654
044bbd71 1655 /* If use associated compilation, use the module
094bca96 1656 declaration. */
044bbd71 1657 if ((sym->attr.flavor == FL_VARIABLE
1658 || sym->attr.flavor == FL_PARAMETER)
fe9d2f5a 1659 && (sym->attr.use_assoc || sym->attr.used_in_submodule)
044bbd71 1660 && !intrinsic_array_parameter
1661 && sym->module
1662 && gfc_get_module_backend_decl (sym))
fd23cc08 1663 {
1664 if (sym->ts.type == BT_CLASS && sym->backend_decl)
1665 GFC_DECL_CLASS(sym->backend_decl) = 1;
1666 return sym->backend_decl;
1667 }
7ea64434 1668
4ee9c684 1669 if (sym->attr.flavor == FL_PROCEDURE)
1670 {
77d080ca 1671 /* Catch functions. Only used for actual parameters,
802532b9 1672 procedure pointers and procptr initialization targets. */
1650ce2f 1673 if (sym->attr.use_assoc
1674 || sym->attr.used_in_submodule
1675 || sym->attr.intrinsic
77d080ca 1676 || sym->attr.if_source != IFSRC_DECL)
802532b9 1677 {
1678 decl = gfc_get_extern_function_decl (sym);
1679 gfc_set_decl_location (decl, &sym->declared_at);
1680 }
1681 else
1682 {
1683 if (!sym->backend_decl)
1684 build_function_decl (sym, false);
1685 decl = sym->backend_decl;
1686 }
4ee9c684 1687 return decl;
1688 }
1689
1690 if (sym->attr.intrinsic)
382ad5c3 1691 gfc_internal_error ("intrinsic variable which isn't a procedure");
4ee9c684 1692
1693 /* Create string length decl first so that they can be used in the
c3639856 1694 type declaration. For associate names, the target character
1695 length is used. Set 'length' to a constant so that if the
8b7e5587 1696 string length is a variable, it is not finished a second time. */
4ee9c684 1697 if (sym->ts.type == BT_CHARACTER)
c3639856 1698 {
bb2fe503 1699 if (sym->attr.associate_var
1700 && sym->ts.deferred
1701 && sym->assoc && sym->assoc->target
1702 && ((sym->assoc->target->expr_type == EXPR_VARIABLE
1703 && sym->assoc->target->symtree->n.sym->ts.type != BT_CHARACTER)
1704 || sym->assoc->target->expr_type == EXPR_FUNCTION))
1705 sym->ts.u.cl->backend_decl = NULL_TREE;
1706
c3639856 1707 if (sym->attr.associate_var
1708 && sym->ts.u.cl->backend_decl
fe732a9b 1709 && VAR_P (sym->ts.u.cl->backend_decl))
c3639856 1710 length = gfc_index_zero_node;
1711 else
1712 length = gfc_create_string_length (sym);
1713 }
4ee9c684 1714
1715 /* Create the decl for the variable. */
e60a6f7b 1716 decl = build_decl (sym->declared_at.lb->location,
1717 VAR_DECL, gfc_sym_identifier (sym), gfc_sym_type (sym));
b31f705b 1718
1236e28b 1719 /* Add attributes to variables. Functions are handled elsewhere. */
1720 attributes = add_attributes_to_decl (sym->attr, NULL_TREE);
1721 decl_attributes (&decl, attributes, 0);
1722
f888a3fb 1723 /* Symbols from modules should have their assembler names mangled.
4ee9c684 1724 This is done here rather than in gfc_finish_var_decl because it
1725 is different for string length variables. */
8b7e5587 1726 if (sym->module || sym->fn_result_spec)
df4d540f 1727 {
1236e28b 1728 gfc_set_decl_assembler_name (decl, gfc_sym_mangled_identifier (sym));
cd2c99b8 1729 if (sym->attr.use_assoc && !intrinsic_array_parameter)
df4d540f 1730 DECL_IGNORED_P (decl) = 1;
1731 }
4ee9c684 1732
bc5663df 1733 if (sym->attr.select_type_temporary)
1734 {
1735 DECL_ARTIFICIAL (decl) = 1;
1736 DECL_IGNORED_P (decl) = 1;
1737 }
1738
7a777e43 1739 if (sym->attr.dimension || sym->attr.codimension)
4ee9c684 1740 {
1741 /* Create variables to hold the non-constant bits of array info. */
1742 gfc_build_qualified_array (decl, sym);
1743
b3c3927c 1744 if (sym->attr.contiguous
1745 || ((sym->attr.allocatable || !sym->attr.dummy) && !sym->attr.pointer))
4ee9c684 1746 GFC_DECL_PACKED_ARRAY (decl) = 1;
1747 }
1748
0a96a7cc 1749 /* Remember this variable for allocation/cleanup. */
7c7db7f6 1750 if (sym->attr.dimension || sym->attr.allocatable || sym->attr.codimension
0a96a7cc 1751 || (sym->ts.type == BT_CLASS &&
50b4b37b 1752 (CLASS_DATA (sym)->attr.dimension
1753 || CLASS_DATA (sym)->attr.allocatable))
6b3ceb4e 1754 || (sym->ts.type == BT_DERIVED
1755 && (sym->ts.u.derived->attr.alloc_comp
1756 || (!sym->attr.pointer && !sym->attr.artificial && !sym->attr.save
1757 && !sym->ns->proc_name->attr.is_main_program
1758 && gfc_is_finalizable (sym->ts.u.derived, NULL))))
0a96a7cc 1759 /* This applies a derived type default initializer. */
1760 || (sym->ts.type == BT_DERIVED
1761 && sym->attr.save == SAVE_NONE
1762 && !sym->attr.data
1763 && !sym->attr.allocatable
1764 && (sym->value && !sym->ns->proc_name->attr.is_main_program)
cd2c99b8 1765 && !(sym->attr.use_assoc && !intrinsic_array_parameter)))
f0d4969f 1766 gfc_defer_symbol_init (sym);
2294b616 1767
4d8caf18 1768 /* Associate names can use the hidden string length variable
1769 of their associated target. */
1770 if (sym->ts.type == BT_CHARACTER
1771 && TREE_CODE (length) != INTEGER_CST)
1772 {
1773 gfc_finish_var_decl (length, sym);
1774 gcc_assert (!sym->value);
1775 }
1776
4ee9c684 1777 gfc_finish_var_decl (decl, sym);
1778
bda1f152 1779 if (sym->ts.type == BT_CHARACTER)
4d8caf18 1780 /* Character variables need special handling. */
1781 gfc_allocate_lang_decl (decl);
1033248c 1782
47e6a59a 1783 if (sym->assoc && sym->attr.subref_array_pointer)
1784 sym->attr.pointer = 1;
1785
1786 if (sym->attr.pointer && sym->attr.dimension
1787 && !sym->ts.deferred
1788 && !(sym->attr.select_type_temporary
1789 && !sym->attr.subref_array_pointer))
1790 GFC_DECL_PTR_ARRAY_P (decl) = 1;
1033248c 1791
fd23cc08 1792 if (sym->ts.type == BT_CLASS)
47e6a59a 1793 GFC_DECL_CLASS(decl) = 1;
fd23cc08 1794
4ee9c684 1795 sym->backend_decl = decl;
1796
c8f1568f 1797 if (sym->attr.assign)
21ebda4d 1798 gfc_add_assign_aux_vars (sym);
c8f1568f 1799
cd2c99b8 1800 if (intrinsic_array_parameter)
1801 {
1802 TREE_STATIC (decl) = 1;
1803 DECL_EXTERNAL (decl) = 0;
1804 }
1805
1806 if (TREE_STATIC (decl)
1807 && !(sym->attr.use_assoc && !intrinsic_array_parameter)
a545a8f8 1808 && (sym->attr.save || sym->ns->proc_name->attr.is_main_program
14eab729 1809 || !gfc_can_put_var_on_stack (DECL_SIZE_UNIT (decl))
a961ca30 1810 || sym->attr.data || sym->ns->proc_name->attr.flavor == FL_MODULE)
4fe73152 1811 && (flag_coarray != GFC_FCOARRAY_LIB
0d3bb1de 1812 || !sym->attr.codimension || sym->attr.allocatable))
a545a8f8 1813 {
1814 /* Add static initializer. For procedures, it is only needed if
1815 SAVE is specified otherwise they need to be reinitialized
1816 every time the procedure is entered. The TREE_STATIC is
1817 in this case due to -fmax-stack-var-size=. */
2e42c60f 1818
bda1f152 1819 DECL_INITIAL (decl) = gfc_conv_initializer (sym->value, &sym->ts,
2e42c60f 1820 TREE_TYPE (decl), sym->attr.dimension
1821 || (sym->attr.codimension
1822 && sym->attr.allocatable),
1823 sym->attr.pointer || sym->attr.allocatable
1824 || sym->ts.type == BT_CLASS,
1825 sym->attr.proc_pointer);
bda1f152 1826 }
1827
9579733e 1828 if (!TREE_STATIC (decl)
1829 && POINTER_TYPE_P (TREE_TYPE (decl))
1830 && !sym->attr.pointer
1831 && !sym->attr.allocatable
bc5663df 1832 && !sym->attr.proc_pointer
1833 && !sym->attr.select_type_temporary)
9579733e 1834 DECL_BY_REFERENCE (decl) = 1;
1835
cf5f881f 1836 if (sym->attr.associate_var)
1837 GFC_DECL_ASSOCIATE_VAR_P (decl) = 1;
1838
ebad7c3e 1839 if (sym->attr.vtab
1840 || (sym->name[0] == '_' && strncmp ("__def_init", sym->name, 10) == 0))
4c197fd0 1841 TREE_READONLY (decl) = 1;
ebad7c3e 1842
4ee9c684 1843 return decl;
1844}
1845
1846
dbe60343 1847/* Substitute a temporary variable in place of the real one. */
1848
1849void
1850gfc_shadow_sym (gfc_symbol * sym, tree decl, gfc_saved_var * save)
1851{
1852 save->attr = sym->attr;
1853 save->decl = sym->backend_decl;
1854
1855 gfc_clear_attr (&sym->attr);
1856 sym->attr.referenced = 1;
1857 sym->attr.flavor = FL_VARIABLE;
1858
1859 sym->backend_decl = decl;
1860}
1861
1862
1863/* Restore the original variable. */
1864
1865void
1866gfc_restore_sym (gfc_symbol * sym, gfc_saved_var * save)
1867{
1868 sym->attr = save->attr;
1869 sym->backend_decl = save->decl;
1870}
1871
1872
cad0ddcf 1873/* Declare a procedure pointer. */
1874
1875static tree
1876get_proc_pointer_decl (gfc_symbol *sym)
1877{
1878 tree decl;
36b0a1b0 1879 tree attributes;
cad0ddcf 1880
1881 decl = sym->backend_decl;
1882 if (decl)
1883 return decl;
1884
e60a6f7b 1885 decl = build_decl (input_location,
1886 VAR_DECL, get_identifier (sym->name),
cad0ddcf 1887 build_pointer_type (gfc_get_function_type (sym)));
1888
ea6f8461 1889 if (sym->module)
1890 {
1891 /* Apply name mangling. */
1892 gfc_set_decl_assembler_name (decl, gfc_sym_mangled_identifier (sym));
1893 if (sym->attr.use_assoc)
1894 DECL_IGNORED_P (decl) = 1;
1895 }
a90fe829 1896
e72f979a 1897 if ((sym->ns->proc_name
1898 && sym->ns->proc_name->backend_decl == current_function_decl)
cad0ddcf 1899 || sym->attr.contained)
1900 gfc_add_decl_to_function (decl);
cf269acc 1901 else if (sym->ns->proc_name->attr.flavor != FL_MODULE)
cad0ddcf 1902 gfc_add_decl_to_parent_function (decl);
1903
1904 sym->backend_decl = decl;
1905
cf269acc 1906 /* If a variable is USE associated, it's always external. */
1907 if (sym->attr.use_assoc)
1908 {
1909 DECL_EXTERNAL (decl) = 1;
1910 TREE_PUBLIC (decl) = 1;
1911 }
1912 else if (sym->module && sym->ns->proc_name->attr.flavor == FL_MODULE)
1913 {
1914 /* This is the declaration of a module variable. */
c8ddfd5d 1915 TREE_PUBLIC (decl) = 1;
1916 if (sym->attr.access == ACCESS_PRIVATE && !sym->attr.public_used)
1917 {
1918 DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
1919 DECL_VISIBILITY_SPECIFIED (decl) = true;
1920 }
cf269acc 1921 TREE_STATIC (decl) = 1;
1922 }
1923
cad0ddcf 1924 if (!sym->attr.use_assoc
1925 && (sym->attr.save != SAVE_NONE || sym->attr.data
1926 || (sym->value && sym->ns->proc_name->attr.is_main_program)))
1927 TREE_STATIC (decl) = 1;
1928
1929 if (TREE_STATIC (decl) && sym->value)
1930 {
1931 /* Add static initializer. */
1932 DECL_INITIAL (decl) = gfc_conv_initializer (sym->value, &sym->ts,
802532b9 1933 TREE_TYPE (decl),
1934 sym->attr.dimension,
1935 false, true);
cad0ddcf 1936 }
1937
8fb1768c 1938 /* Handle threadprivate procedure pointers. */
1939 if (sym->attr.threadprivate
1940 && (TREE_STATIC (decl) || DECL_EXTERNAL (decl)))
5e68df57 1941 set_decl_tls_model (decl, decl_default_tls_model (decl));
8fb1768c 1942
36b0a1b0 1943 attributes = add_attributes_to_decl (sym->attr, NULL_TREE);
1944 decl_attributes (&decl, attributes, 0);
1945
cad0ddcf 1946 return decl;
1947}
1948
1949
4ee9c684 1950/* Get a basic decl for an external function. */
1951
1952tree
1953gfc_get_extern_function_decl (gfc_symbol * sym)
1954{
1955 tree type;
1956 tree fndecl;
36b0a1b0 1957 tree attributes;
4ee9c684 1958 gfc_expr e;
1959 gfc_intrinsic_sym *isym;
1960 gfc_expr argexpr;
17000b91 1961 char s[GFC_MAX_SYMBOL_LEN + 23]; /* "_gfortran_f2c_specific" and '\0'. */
4ee9c684 1962 tree name;
1963 tree mangled_name;
83aeedb9 1964 gfc_gsymbol *gsym;
4ee9c684 1965
1966 if (sym->backend_decl)
1967 return sym->backend_decl;
1968
1b716045 1969 /* We should never be creating external decls for alternate entry points.
1970 The procedure may be an alternate entry point, but we don't want/need
1971 to know that. */
22d678e8 1972 gcc_assert (!(sym->attr.entry || sym->attr.entry_master));
1b716045 1973
cad0ddcf 1974 if (sym->attr.proc_pointer)
1975 return get_proc_pointer_decl (sym);
1976
83aeedb9 1977 /* See if this is an external procedure from the same file. If so,
1978 return the backend_decl. */
da5c730d 1979 gsym = gfc_find_gsymbol (gfc_gsym_root, sym->binding_label
1980 ? sym->binding_label : sym->name);
83aeedb9 1981
c8b913ab 1982 if (gsym && !gsym->defined)
1983 gsym = NULL;
1984
1985 /* This can happen because of C binding. */
1986 if (gsym && gsym->ns && gsym->ns->proc_name
1987 && gsym->ns->proc_name->attr.flavor == FL_MODULE)
1988 goto module_sym;
1989
044bbd71 1990 if ((!sym->attr.use_assoc || sym->attr.if_source != IFSRC_DECL)
1991 && !sym->backend_decl
1992 && gsym && gsym->ns
1993 && ((gsym->type == GSYM_SUBROUTINE) || (gsym->type == GSYM_FUNCTION))
1994 && (gsym->ns->proc_name->backend_decl || !sym->attr.intrinsic))
83aeedb9 1995 {
d896f9b3 1996 if (!gsym->ns->proc_name->backend_decl)
1997 {
1998 /* By construction, the external function cannot be
1999 a contained procedure. */
2000 locus old_loc;
d896f9b3 2001
4671339c 2002 gfc_save_backend_locus (&old_loc);
9078126c 2003 push_cfun (NULL);
d896f9b3 2004
2005 gfc_create_function_decl (gsym->ns, true);
2006
2007 pop_cfun ();
4671339c 2008 gfc_restore_backend_locus (&old_loc);
d896f9b3 2009 }
2010
83aeedb9 2011 /* If the namespace has entries, the proc_name is the
2012 entry master. Find the entry and use its backend_decl.
2013 otherwise, use the proc_name backend_decl. */
2014 if (gsym->ns->entries)
2015 {
2016 gfc_entry_list *entry = gsym->ns->entries;
2017
2018 for (; entry; entry = entry->next)
2019 {
2020 if (strcmp (gsym->name, entry->sym->name) == 0)
2021 {
2022 sym->backend_decl = entry->sym->backend_decl;
2023 break;
2024 }
2025 }
2026 }
2027 else
40c74b02 2028 sym->backend_decl = gsym->ns->proc_name->backend_decl;
83aeedb9 2029
2030 if (sym->backend_decl)
40c74b02 2031 {
2032 /* Avoid problems of double deallocation of the backend declaration
2033 later in gfc_trans_use_stmts; cf. PR 45087. */
2034 if (sym->attr.if_source != IFSRC_DECL && sym->attr.use_assoc)
2035 sym->attr.use_assoc = 0;
2036
2037 return sym->backend_decl;
2038 }
83aeedb9 2039 }
2040
7ea64434 2041 /* See if this is a module procedure from the same file. If so,
2042 return the backend_decl. */
2043 if (sym->module)
2044 gsym = gfc_find_gsymbol (gfc_gsym_root, sym->module);
2045
c8b913ab 2046module_sym:
2047 if (gsym && gsym->ns
2048 && (gsym->type == GSYM_MODULE
2049 || (gsym->ns->proc_name && gsym->ns->proc_name->attr.flavor == FL_MODULE)))
7ea64434 2050 {
2051 gfc_symbol *s;
2052
2053 s = NULL;
c8b913ab 2054 if (gsym->type == GSYM_MODULE)
2055 gfc_find_symbol (sym->name, gsym->ns, 0, &s);
2056 else
2057 gfc_find_symbol (gsym->sym_name, gsym->ns, 0, &s);
2058
7ea64434 2059 if (s && s->backend_decl)
2060 {
85ec2f13 2061 if (sym->ts.type == BT_DERIVED || sym->ts.type == BT_CLASS)
2062 gfc_copy_dt_decls_ifequal (s->ts.u.derived, sym->ts.u.derived,
2063 true);
2064 else if (sym->ts.type == BT_CHARACTER)
2065 sym->ts.u.cl->backend_decl = s->ts.u.cl->backend_decl;
7ea64434 2066 sym->backend_decl = s->backend_decl;
2067 return sym->backend_decl;
2068 }
2069 }
2070
4ee9c684 2071 if (sym->attr.intrinsic)
2072 {
2073 /* Call the resolution function to get the actual name. This is
2074 a nasty hack which relies on the resolution functions only looking
2075 at the first argument. We pass NULL for the second argument
2076 otherwise things like AINT get confused. */
2077 isym = gfc_find_function (sym->name);
22d678e8 2078 gcc_assert (isym->resolve.f0 != NULL);
4ee9c684 2079
2080 memset (&e, 0, sizeof (e));
2081 e.expr_type = EXPR_FUNCTION;
2082
2083 memset (&argexpr, 0, sizeof (argexpr));
22d678e8 2084 gcc_assert (isym->formal);
4ee9c684 2085 argexpr.ts = isym->formal->ts;
2086
2087 if (isym->formal->next == NULL)
2088 isym->resolve.f1 (&e, &argexpr);
2089 else
2090 {
37e0271a 2091 if (isym->formal->next->next == NULL)
2092 isym->resolve.f2 (&e, &argexpr, NULL);
2093 else
2094 {
7fe55cc9 2095 if (isym->formal->next->next->next == NULL)
2096 isym->resolve.f3 (&e, &argexpr, NULL, NULL);
2097 else
2098 {
2099 /* All specific intrinsics take less than 5 arguments. */
2100 gcc_assert (isym->formal->next->next->next->next == NULL);
2101 isym->resolve.f4 (&e, &argexpr, NULL, NULL, NULL);
2102 }
37e0271a 2103 }
4ee9c684 2104 }
bdaed7d2 2105
829d7a08 2106 if (flag_f2c
bdaed7d2 2107 && ((e.ts.type == BT_REAL && e.ts.kind == gfc_default_real_kind)
2108 || e.ts.type == BT_COMPLEX))
2109 {
2110 /* Specific which needs a different implementation if f2c
2111 calling conventions are used. */
17000b91 2112 sprintf (s, "_gfortran_f2c_specific%s", e.value.function.name);
bdaed7d2 2113 }
2114 else
17000b91 2115 sprintf (s, "_gfortran_specific%s", e.value.function.name);
bdaed7d2 2116
4ee9c684 2117 name = get_identifier (s);
2118 mangled_name = name;
2119 }
2120 else
2121 {
2122 name = gfc_sym_identifier (sym);
2123 mangled_name = gfc_sym_mangled_function_id (sym);
2124 }
2125
2126 type = gfc_get_function_type (sym);
e60a6f7b 2127 fndecl = build_decl (input_location,
2128 FUNCTION_DECL, name, type);
4ee9c684 2129
e27454ee 2130 /* Initialize DECL_EXTERNAL and TREE_PUBLIC before calling decl_attributes;
2131 TREE_PUBLIC specifies whether a function is globally addressable (i.e.
851d9296 2132 the opposite of declaring a function as static in C). */
e27454ee 2133 DECL_EXTERNAL (fndecl) = 1;
2134 TREE_PUBLIC (fndecl) = 1;
2135
1236e28b 2136 attributes = add_attributes_to_decl (sym->attr, NULL_TREE);
2137 decl_attributes (&fndecl, attributes, 0);
2138
2139 gfc_set_decl_assembler_name (fndecl, mangled_name);
4ee9c684 2140
2141 /* Set the context of this decl. */
2142 if (0 && sym->ns && sym->ns->proc_name)
2143 {
2144 /* TODO: Add external decls to the appropriate scope. */
2145 DECL_CONTEXT (fndecl) = sym->ns->proc_name->backend_decl;
2146 }
2147 else
2148 {
f888a3fb 2149 /* Global declaration, e.g. intrinsic subroutine. */
4ee9c684 2150 DECL_CONTEXT (fndecl) = NULL_TREE;
2151 }
2152
4ee9c684 2153 /* Set attributes for PURE functions. A call to PURE function in the
2154 Fortran 95 sense is both pure and without side effects in the C
2155 sense. */
bead0399 2156 if (sym->attr.pure || sym->attr.implicit_pure)
4ee9c684 2157 {
4d4b9f0e 2158 if (sym->attr.function && !gfc_return_by_reference (sym))
9c2a0c05 2159 DECL_PURE_P (fndecl) = 1;
be393645 2160 /* TODO: check if pure SUBROUTINEs don't have INTENT(OUT)
2161 parameters and don't use alternate returns (is this
2162 allowed?). In that case, calls to them are meaningless, and
1b716045 2163 can be optimized away. See also in build_function_decl(). */
be393645 2164 TREE_SIDE_EFFECTS (fndecl) = 0;
4ee9c684 2165 }
2166
6e27d773 2167 /* Mark non-returning functions. */
2168 if (sym->attr.noreturn)
2169 TREE_THIS_VOLATILE(fndecl) = 1;
2170
4ee9c684 2171 sym->backend_decl = fndecl;
2172
2173 if (DECL_CONTEXT (fndecl) == NULL_TREE)
2174 pushdecl_top_level (fndecl);
2175
15b28553 2176 if (sym->formal_ns
2177 && sym->formal_ns->proc_name == sym
2178 && sym->formal_ns->omp_declare_simd)
2179 gfc_trans_omp_declare_simd (sym->formal_ns);
2180
4ee9c684 2181 return fndecl;
2182}
2183
2184
2185/* Create a declaration for a procedure. For external functions (in the C
1b716045 2186 sense) use gfc_get_extern_function_decl. HAS_ENTRIES is true if this is
2187 a master function with alternate entry points. */
4ee9c684 2188
1b716045 2189static void
d896f9b3 2190build_function_decl (gfc_symbol * sym, bool global)
4ee9c684 2191{
36b0a1b0 2192 tree fndecl, type, attributes;
4ee9c684 2193 symbol_attribute attr;
1b716045 2194 tree result_decl;
4ee9c684 2195 gfc_formal_arglist *f;
2196
76e207a9 2197 bool module_procedure = sym->attr.module_procedure
2198 && sym->ns
2199 && sym->ns->proc_name
2200 && sym->ns->proc_name->attr.flavor == FL_MODULE;
2201
2202 gcc_assert (!sym->attr.external || module_procedure);
4ee9c684 2203
802532b9 2204 if (sym->backend_decl)
2205 return;
2206
b31f705b 2207 /* Set the line and filename. sym->declared_at seems to point to the
2208 last statement for subroutines, but it'll do for now. */
2209 gfc_set_backend_locus (&sym->declared_at);
2210
4ee9c684 2211 /* Allow only one nesting level. Allow public declarations. */
22d678e8 2212 gcc_assert (current_function_decl == NULL_TREE
16a40513 2213 || DECL_FILE_SCOPE_P (current_function_decl)
2214 || (TREE_CODE (DECL_CONTEXT (current_function_decl))
2215 == NAMESPACE_DECL));
4ee9c684 2216
2217 type = gfc_get_function_type (sym);
e60a6f7b 2218 fndecl = build_decl (input_location,
2219 FUNCTION_DECL, gfc_sym_identifier (sym), type);
4ee9c684 2220
1236e28b 2221 attr = sym->attr;
2222
e27454ee 2223 /* Initialize DECL_EXTERNAL and TREE_PUBLIC before calling decl_attributes;
2224 TREE_PUBLIC specifies whether a function is globally addressable (i.e.
851d9296 2225 the opposite of declaring a function as static in C). */
e27454ee 2226 DECL_EXTERNAL (fndecl) = 0;
2227
7d6b5754 2228 if (sym->attr.access == ACCESS_UNKNOWN && sym->module
2229 && (sym->ns->default_access == ACCESS_PRIVATE
2230 || (sym->ns->default_access == ACCESS_UNKNOWN
829d7a08 2231 && flag_module_private)))
7d6b5754 2232 sym->attr.access = ACCESS_PRIVATE;
2233
e27454ee 2234 if (!current_function_decl
c5cb468c 2235 && !sym->attr.entry_master && !sym->attr.is_main_program
b1f74325 2236 && (sym->attr.access != ACCESS_PRIVATE || sym->binding_label
2237 || sym->attr.public_used))
e27454ee 2238 TREE_PUBLIC (fndecl) = 1;
2239
9e45357a 2240 if (sym->attr.referenced || sym->attr.entry_master)
2241 TREE_USED (fndecl) = 1;
2242
1236e28b 2243 attributes = add_attributes_to_decl (attr, NULL_TREE);
2244 decl_attributes (&fndecl, attributes, 0);
2245
4ee9c684 2246 /* Figure out the return type of the declared function, and build a
f888a3fb 2247 RESULT_DECL for it. If this is a subroutine with alternate
4ee9c684 2248 returns, build a RESULT_DECL for it. */
4ee9c684 2249 result_decl = NULL_TREE;
2250 /* TODO: Shouldn't this just be TREE_TYPE (TREE_TYPE (fndecl)). */
2251 if (attr.function)
2252 {
2253 if (gfc_return_by_reference (sym))
2254 type = void_type_node;
2255 else
2256 {
2257 if (sym->result != sym)
2258 result_decl = gfc_sym_identifier (sym->result);
2259
2260 type = TREE_TYPE (TREE_TYPE (fndecl));
2261 }
2262 }
2263 else
2264 {
2265 /* Look for alternate return placeholders. */
2266 int has_alternate_returns = 0;
6777213b 2267 for (f = gfc_sym_get_dummy_args (sym); f; f = f->next)
4ee9c684 2268 {
2269 if (f->sym == NULL)
2270 {
2271 has_alternate_returns = 1;
2272 break;
2273 }
2274 }
2275
2276 if (has_alternate_returns)
2277 type = integer_type_node;
2278 else
2279 type = void_type_node;
2280 }
2281
e60a6f7b 2282 result_decl = build_decl (input_location,
2283 RESULT_DECL, result_decl, type);
540edea7 2284 DECL_ARTIFICIAL (result_decl) = 1;
2285 DECL_IGNORED_P (result_decl) = 1;
4ee9c684 2286 DECL_CONTEXT (result_decl) = fndecl;
2287 DECL_RESULT (fndecl) = result_decl;
2288
2289 /* Don't call layout_decl for a RESULT_DECL.
f888a3fb 2290 layout_decl (result_decl, 0); */
4ee9c684 2291
4ee9c684 2292 /* TREE_STATIC means the function body is defined here. */
e4b2c26c 2293 TREE_STATIC (fndecl) = 1;
4ee9c684 2294
f888a3fb 2295 /* Set attributes for PURE functions. A call to a PURE function in the
4ee9c684 2296 Fortran 95 sense is both pure and without side effects in the C
2297 sense. */
bead0399 2298 if (attr.pure || attr.implicit_pure)
4ee9c684 2299 {
be393645 2300 /* TODO: check if a pure SUBROUTINE has no INTENT(OUT) arguments
a0527218 2301 including an alternate return. In that case it can also be
231e961a 2302 marked as PURE. See also in gfc_get_extern_function_decl(). */
4c319962 2303 if (attr.function && !gfc_return_by_reference (sym))
9c2a0c05 2304 DECL_PURE_P (fndecl) = 1;
4ee9c684 2305 TREE_SIDE_EFFECTS (fndecl) = 0;
2306 }
2307
36b0a1b0 2308
4ee9c684 2309 /* Layout the function declaration and put it in the binding level
2310 of the current function. */
d896f9b3 2311
4c197fd0 2312 if (global)
d896f9b3 2313 pushdecl_top_level (fndecl);
2314 else
2315 pushdecl (fndecl);
1b716045 2316
16a40513 2317 /* Perform name mangling if this is a top level or module procedure. */
2318 if (current_function_decl == NULL_TREE)
2319 gfc_set_decl_assembler_name (fndecl, gfc_sym_mangled_function_id (sym));
2320
1b716045 2321 sym->backend_decl = fndecl;
2322}
2323
2324
2325/* Create the DECL_ARGUMENTS for a procedure. */
2326
2327static void
2328create_function_arglist (gfc_symbol * sym)
2329{
2330 tree fndecl;
2331 gfc_formal_arglist *f;
d4163395 2332 tree typelist, hidden_typelist;
2333 tree arglist, hidden_arglist;
1b716045 2334 tree type;
2335 tree parm;
2336
2337 fndecl = sym->backend_decl;
2338
e4b2c26c 2339 /* Build formal argument list. Make sure that their TREE_CONTEXT is
2340 the new FUNCTION_DECL node. */
e4b2c26c 2341 arglist = NULL_TREE;
d4163395 2342 hidden_arglist = NULL_TREE;
e4b2c26c 2343 typelist = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
1b716045 2344
2345 if (sym->attr.entry_master)
2346 {
2347 type = TREE_VALUE (typelist);
e60a6f7b 2348 parm = build_decl (input_location,
2349 PARM_DECL, get_identifier ("__entry"), type);
a90fe829 2350
1b716045 2351 DECL_CONTEXT (parm) = fndecl;
2352 DECL_ARG_TYPE (parm) = type;
2353 TREE_READONLY (parm) = 1;
b9c7fce7 2354 gfc_finish_decl (parm);
d95efb59 2355 DECL_ARTIFICIAL (parm) = 1;
1b716045 2356
2357 arglist = chainon (arglist, parm);
2358 typelist = TREE_CHAIN (typelist);
2359 }
2360
e4b2c26c 2361 if (gfc_return_by_reference (sym))
4ee9c684 2362 {
d4163395 2363 tree type = TREE_VALUE (typelist), length = NULL;
4ee9c684 2364
e4b2c26c 2365 if (sym->ts.type == BT_CHARACTER)
2366 {
e4b2c26c 2367 /* Length of character result. */
d4163395 2368 tree len_type = TREE_VALUE (TREE_CHAIN (typelist));
4ee9c684 2369
e60a6f7b 2370 length = build_decl (input_location,
2371 PARM_DECL,
e4b2c26c 2372 get_identifier (".__result"),
d4163395 2373 len_type);
b345a09f 2374 if (POINTER_TYPE_P (len_type))
2375 {
2376 sym->ts.u.cl->passed_length = length;
2377 TREE_USED (length) = 1;
2378 }
2379 else if (!sym->ts.u.cl->length)
e4b2c26c 2380 {
eeebe20b 2381 sym->ts.u.cl->backend_decl = length;
e4b2c26c 2382 TREE_USED (length) = 1;
4ee9c684 2383 }
22d678e8 2384 gcc_assert (TREE_CODE (length) == PARM_DECL);
e4b2c26c 2385 DECL_CONTEXT (length) = fndecl;
d4163395 2386 DECL_ARG_TYPE (length) = len_type;
e4b2c26c 2387 TREE_READONLY (length) = 1;
b5b40b3f 2388 DECL_ARTIFICIAL (length) = 1;
b9c7fce7 2389 gfc_finish_decl (length);
eeebe20b 2390 if (sym->ts.u.cl->backend_decl == NULL
2391 || sym->ts.u.cl->backend_decl == length)
d4163395 2392 {
2393 gfc_symbol *arg;
2394 tree backend_decl;
4ee9c684 2395
eeebe20b 2396 if (sym->ts.u.cl->backend_decl == NULL)
d4163395 2397 {
e60a6f7b 2398 tree len = build_decl (input_location,
2399 VAR_DECL,
d4163395 2400 get_identifier ("..__result"),
2401 gfc_charlen_type_node);
2402 DECL_ARTIFICIAL (len) = 1;
2403 TREE_USED (len) = 1;
eeebe20b 2404 sym->ts.u.cl->backend_decl = len;
d4163395 2405 }
4ee9c684 2406
d4163395 2407 /* Make sure PARM_DECL type doesn't point to incomplete type. */
2408 arg = sym->result ? sym->result : sym;
2409 backend_decl = arg->backend_decl;
2410 /* Temporary clear it, so that gfc_sym_type creates complete
2411 type. */
2412 arg->backend_decl = NULL;
2413 type = gfc_sym_type (arg);
2414 arg->backend_decl = backend_decl;
2415 type = build_reference_type (type);
2416 }
2417 }
4ee9c684 2418
e60a6f7b 2419 parm = build_decl (input_location,
2420 PARM_DECL, get_identifier ("__result"), type);
4ee9c684 2421
d4163395 2422 DECL_CONTEXT (parm) = fndecl;
2423 DECL_ARG_TYPE (parm) = TREE_VALUE (typelist);
2424 TREE_READONLY (parm) = 1;
2425 DECL_ARTIFICIAL (parm) = 1;
b9c7fce7 2426 gfc_finish_decl (parm);
4ee9c684 2427
d4163395 2428 arglist = chainon (arglist, parm);
2429 typelist = TREE_CHAIN (typelist);
4ee9c684 2430
d4163395 2431 if (sym->ts.type == BT_CHARACTER)
2432 {
2433 gfc_allocate_lang_decl (parm);
2434 arglist = chainon (arglist, length);
e4b2c26c 2435 typelist = TREE_CHAIN (typelist);
2436 }
2437 }
4ee9c684 2438
d4163395 2439 hidden_typelist = typelist;
6777213b 2440 for (f = gfc_sym_get_dummy_args (sym); f; f = f->next)
d4163395 2441 if (f->sym != NULL) /* Ignore alternate returns. */
2442 hidden_typelist = TREE_CHAIN (hidden_typelist);
2443
6777213b 2444 for (f = gfc_sym_get_dummy_args (sym); f; f = f->next)
e4b2c26c 2445 {
2446 char name[GFC_MAX_SYMBOL_LEN + 2];
d4163395 2447
e4b2c26c 2448 /* Ignore alternate returns. */
2449 if (f->sym == NULL)
2450 continue;
4ee9c684 2451
e4b2c26c 2452 type = TREE_VALUE (typelist);
4ee9c684 2453
296db1d1 2454 if (f->sym->ts.type == BT_CHARACTER
2455 && (!sym->attr.is_bind_c || sym->attr.entry_master))
d4163395 2456 {
2457 tree len_type = TREE_VALUE (hidden_typelist);
2458 tree length = NULL_TREE;
617125a6 2459 if (!f->sym->ts.deferred)
2460 gcc_assert (len_type == gfc_charlen_type_node);
2461 else
2462 gcc_assert (POINTER_TYPE_P (len_type));
d4163395 2463
2464 strcpy (&name[1], f->sym->name);
2465 name[0] = '_';
e60a6f7b 2466 length = build_decl (input_location,
2467 PARM_DECL, get_identifier (name), len_type);
4ee9c684 2468
d4163395 2469 hidden_arglist = chainon (hidden_arglist, length);
2470 DECL_CONTEXT (length) = fndecl;
2471 DECL_ARTIFICIAL (length) = 1;
2472 DECL_ARG_TYPE (length) = len_type;
2473 TREE_READONLY (length) = 1;
b9c7fce7 2474 gfc_finish_decl (length);
4ee9c684 2475
a4abf8a0 2476 /* Remember the passed value. */
a90fe829 2477 if (!f->sym->ts.u.cl || f->sym->ts.u.cl->passed_length)
6be7c32c 2478 {
2479 /* This can happen if the same type is used for multiple
2480 arguments. We need to copy cl as otherwise
2481 cl->passed_length gets overwritten. */
d270ce52 2482 f->sym->ts.u.cl = gfc_new_charlen (f->sym->ns, f->sym->ts.u.cl);
6be7c32c 2483 }
eeebe20b 2484 f->sym->ts.u.cl->passed_length = length;
4ee9c684 2485
d4163395 2486 /* Use the passed value for assumed length variables. */
eeebe20b 2487 if (!f->sym->ts.u.cl->length)
4ee9c684 2488 {
d4163395 2489 TREE_USED (length) = 1;
eeebe20b 2490 gcc_assert (!f->sym->ts.u.cl->backend_decl);
2491 f->sym->ts.u.cl->backend_decl = length;
d4163395 2492 }
2493
2494 hidden_typelist = TREE_CHAIN (hidden_typelist);
2495
eeebe20b 2496 if (f->sym->ts.u.cl->backend_decl == NULL
2497 || f->sym->ts.u.cl->backend_decl == length)
d4163395 2498 {
ddcfeaf1 2499 if (POINTER_TYPE_P (len_type))
2500 f->sym->ts.u.cl->backend_decl =
2501 build_fold_indirect_ref_loc (input_location, length);
2502 else if (f->sym->ts.u.cl->backend_decl == NULL)
d4163395 2503 gfc_create_string_length (f->sym);
2504
2505 /* Make sure PARM_DECL type doesn't point to incomplete type. */
2506 if (f->sym->attr.flavor == FL_PROCEDURE)
2507 type = build_pointer_type (gfc_get_function_type (f->sym));
2508 else
2509 type = gfc_sym_type (f->sym);
4ee9c684 2510 }
4ee9c684 2511 }
532c2d79 2512 /* For noncharacter scalar intrinsic types, VALUE passes the value,
1cdfcee9 2513 hence, the optional status cannot be transferred via a NULL pointer.
532c2d79 2514 Thus, we will use a hidden argument in that case. */
2515 else if (f->sym->attr.optional && f->sym->attr.value
68cc384e 2516 && !f->sym->attr.dimension && f->sym->ts.type != BT_CLASS
d7cd448a 2517 && !gfc_bt_struct (f->sym->ts.type))
532c2d79 2518 {
2519 tree tmp;
2520 strcpy (&name[1], f->sym->name);
2521 name[0] = '_';
2522 tmp = build_decl (input_location,
2523 PARM_DECL, get_identifier (name),
2524 boolean_type_node);
2525
2526 hidden_arglist = chainon (hidden_arglist, tmp);
2527 DECL_CONTEXT (tmp) = fndecl;
2528 DECL_ARTIFICIAL (tmp) = 1;
2529 DECL_ARG_TYPE (tmp) = boolean_type_node;
2530 TREE_READONLY (tmp) = 1;
2531 gfc_finish_decl (tmp);
2532 }
4ee9c684 2533
d4163395 2534 /* For non-constant length array arguments, make sure they use
2535 a different type node from TYPE_ARG_TYPES type. */
2536 if (f->sym->attr.dimension
2537 && type == TREE_VALUE (typelist)
2538 && TREE_CODE (type) == POINTER_TYPE
2539 && GFC_ARRAY_TYPE_P (type)
2540 && f->sym->as->type != AS_ASSUMED_SIZE
2541 && ! COMPLETE_TYPE_P (TREE_TYPE (type)))
2542 {
2543 if (f->sym->attr.flavor == FL_PROCEDURE)
2544 type = build_pointer_type (gfc_get_function_type (f->sym));
2545 else
2546 type = gfc_sym_type (f->sym);
2547 }
2548
cad0ddcf 2549 if (f->sym->attr.proc_pointer)
2550 type = build_pointer_type (type);
2551
2364aa60 2552 if (f->sym->attr.volatile_)
2553 type = build_qualified_type (type, TYPE_QUAL_VOLATILE);
2554
69b1505f 2555 /* Build the argument declaration. */
e60a6f7b 2556 parm = build_decl (input_location,
2557 PARM_DECL, gfc_sym_identifier (f->sym), type);
d4163395 2558
2364aa60 2559 if (f->sym->attr.volatile_)
2560 {
2561 TREE_THIS_VOLATILE (parm) = 1;
2562 TREE_SIDE_EFFECTS (parm) = 1;
2563 }
2564
d4163395 2565 /* Fill in arg stuff. */
2566 DECL_CONTEXT (parm) = fndecl;
2567 DECL_ARG_TYPE (parm) = TREE_VALUE (typelist);
5defa6e6 2568 /* All implementation args except for VALUE are read-only. */
2569 if (!f->sym->attr.value)
2570 TREE_READONLY (parm) = 1;
98923a84 2571 if (POINTER_TYPE_P (type)
2572 && (!f->sym->attr.proc_pointer
2573 && f->sym->attr.flavor != FL_PROCEDURE))
2574 DECL_BY_REFERENCE (parm) = 1;
d4163395 2575
b9c7fce7 2576 gfc_finish_decl (parm);
cf5f881f 2577 gfc_finish_decl_attrs (parm, &f->sym->attr);
d4163395 2578
2579 f->sym->backend_decl = parm;
2580
7dce33fe 2581 /* Coarrays which are descriptorless or assumed-shape pass with
2582 -fcoarray=lib the token and the offset as hidden arguments. */
4fe73152 2583 if (flag_coarray == GFC_FCOARRAY_LIB
d44f2f7c 2584 && ((f->sym->ts.type != BT_CLASS && f->sym->attr.codimension
2585 && !f->sym->attr.allocatable)
2586 || (f->sym->ts.type == BT_CLASS
2587 && CLASS_DATA (f->sym)->attr.codimension
2588 && !CLASS_DATA (f->sym)->attr.allocatable)))
85c94a64 2589 {
2590 tree caf_type;
2591 tree token;
2592 tree offset;
2593
2594 gcc_assert (f->sym->backend_decl != NULL_TREE
2595 && !sym->attr.is_bind_c);
d44f2f7c 2596 caf_type = f->sym->ts.type == BT_CLASS
2597 ? TREE_TYPE (CLASS_DATA (f->sym)->backend_decl)
2598 : TREE_TYPE (f->sym->backend_decl);
85c94a64 2599
85c94a64 2600 token = build_decl (input_location, PARM_DECL,
2601 create_tmp_var_name ("caf_token"),
2602 build_qualified_type (pvoid_type_node,
2603 TYPE_QUAL_RESTRICT));
d44f2f7c 2604 if ((f->sym->ts.type != BT_CLASS
2605 && f->sym->as->type != AS_DEFERRED)
2606 || (f->sym->ts.type == BT_CLASS
2607 && CLASS_DATA (f->sym)->as->type != AS_DEFERRED))
7dce33fe 2608 {
2609 gcc_assert (DECL_LANG_SPECIFIC (f->sym->backend_decl) == NULL
2610 || GFC_DECL_TOKEN (f->sym->backend_decl) == NULL_TREE);
2611 if (DECL_LANG_SPECIFIC (f->sym->backend_decl) == NULL)
2612 gfc_allocate_lang_decl (f->sym->backend_decl);
2613 GFC_DECL_TOKEN (f->sym->backend_decl) = token;
2614 }
2615 else
2616 {
2617 gcc_assert (GFC_TYPE_ARRAY_CAF_TOKEN (caf_type) == NULL_TREE);
2618 GFC_TYPE_ARRAY_CAF_TOKEN (caf_type) = token;
2619 }
a90fe829 2620
85c94a64 2621 DECL_CONTEXT (token) = fndecl;
2622 DECL_ARTIFICIAL (token) = 1;
2623 DECL_ARG_TYPE (token) = TREE_VALUE (typelist);
2624 TREE_READONLY (token) = 1;
2625 hidden_arglist = chainon (hidden_arglist, token);
2626 gfc_finish_decl (token);
2627
85c94a64 2628 offset = build_decl (input_location, PARM_DECL,
2629 create_tmp_var_name ("caf_offset"),
2630 gfc_array_index_type);
2631
d44f2f7c 2632 if ((f->sym->ts.type != BT_CLASS
2633 && f->sym->as->type != AS_DEFERRED)
2634 || (f->sym->ts.type == BT_CLASS
2635 && CLASS_DATA (f->sym)->as->type != AS_DEFERRED))
7dce33fe 2636 {
2637 gcc_assert (GFC_DECL_CAF_OFFSET (f->sym->backend_decl)
2638 == NULL_TREE);
2639 GFC_DECL_CAF_OFFSET (f->sym->backend_decl) = offset;
2640 }
2641 else
2642 {
2643 gcc_assert (GFC_TYPE_ARRAY_CAF_OFFSET (caf_type) == NULL_TREE);
2644 GFC_TYPE_ARRAY_CAF_OFFSET (caf_type) = offset;
2645 }
85c94a64 2646 DECL_CONTEXT (offset) = fndecl;
2647 DECL_ARTIFICIAL (offset) = 1;
2648 DECL_ARG_TYPE (offset) = TREE_VALUE (typelist);
2649 TREE_READONLY (offset) = 1;
2650 hidden_arglist = chainon (hidden_arglist, offset);
2651 gfc_finish_decl (offset);
2652 }
2653
d4163395 2654 arglist = chainon (arglist, parm);
e4b2c26c 2655 typelist = TREE_CHAIN (typelist);
4ee9c684 2656 }
e4b2c26c 2657
465e4a95 2658 /* Add the hidden string length parameters, unless the procedure
2659 is bind(C). */
2660 if (!sym->attr.is_bind_c)
2661 arglist = chainon (arglist, hidden_arglist);
d4163395 2662
ebe27ea2 2663 gcc_assert (hidden_typelist == NULL_TREE
2664 || TREE_VALUE (hidden_typelist) == void_type_node);
e4b2c26c 2665 DECL_ARGUMENTS (fndecl) = arglist;
1b716045 2666}
e4b2c26c 2667
1b716045 2668/* Do the setup necessary before generating the body of a function. */
2669
2670static void
2671trans_function_start (gfc_symbol * sym)
2672{
2673 tree fndecl;
2674
2675 fndecl = sym->backend_decl;
2676
f888a3fb 2677 /* Let GCC know the current scope is this function. */
1b716045 2678 current_function_decl = fndecl;
2679
f888a3fb 2680 /* Let the world know what we're about to do. */
1b716045 2681 announce_function (fndecl);
2682
16a40513 2683 if (DECL_FILE_SCOPE_P (fndecl))
1b716045 2684 {
f888a3fb 2685 /* Create RTL for function declaration. */
1b716045 2686 rest_of_decl_compilation (fndecl, 1, 0);
2687 }
2688
f888a3fb 2689 /* Create RTL for function definition. */
1b716045 2690 make_decl_rtl (fndecl);
2691
00cf115c 2692 allocate_struct_function (fndecl, false);
1b716045 2693
f888a3fb 2694 /* function.c requires a push at the start of the function. */
cde2be84 2695 pushlevel ();
1b716045 2696}
2697
2698/* Create thunks for alternate entry points. */
2699
2700static void
d896f9b3 2701build_entry_thunks (gfc_namespace * ns, bool global)
1b716045 2702{
2703 gfc_formal_arglist *formal;
2704 gfc_formal_arglist *thunk_formal;
2705 gfc_entry_list *el;
2706 gfc_symbol *thunk_sym;
2707 stmtblock_t body;
2708 tree thunk_fndecl;
1b716045 2709 tree tmp;
b31f705b 2710 locus old_loc;
1b716045 2711
2712 /* This should always be a toplevel function. */
22d678e8 2713 gcc_assert (current_function_decl == NULL_TREE);
1b716045 2714
4671339c 2715 gfc_save_backend_locus (&old_loc);
1b716045 2716 for (el = ns->entries; el; el = el->next)
2717 {
f1f41a6c 2718 vec<tree, va_gc> *args = NULL;
2719 vec<tree, va_gc> *string_args = NULL;
414c3a2c 2720
1b716045 2721 thunk_sym = el->sym;
a90fe829 2722
d896f9b3 2723 build_function_decl (thunk_sym, global);
1b716045 2724 create_function_arglist (thunk_sym);
2725
2726 trans_function_start (thunk_sym);
2727
2728 thunk_fndecl = thunk_sym->backend_decl;
2729
e5004242 2730 gfc_init_block (&body);
1b716045 2731
f888a3fb 2732 /* Pass extra parameter identifying this entry point. */
7016c612 2733 tmp = build_int_cst (gfc_array_index_type, el->id);
f1f41a6c 2734 vec_safe_push (args, tmp);
1b716045 2735
c6871095 2736 if (thunk_sym->attr.function)
2737 {
2738 if (gfc_return_by_reference (ns->proc_name))
2739 {
2740 tree ref = DECL_ARGUMENTS (current_function_decl);
f1f41a6c 2741 vec_safe_push (args, ref);
c6871095 2742 if (ns->proc_name->ts.type == BT_CHARACTER)
f1f41a6c 2743 vec_safe_push (args, DECL_CHAIN (ref));
c6871095 2744 }
2745 }
2746
6777213b 2747 for (formal = gfc_sym_get_dummy_args (ns->proc_name); formal;
2748 formal = formal->next)
1b716045 2749 {
c6871095 2750 /* Ignore alternate returns. */
2751 if (formal->sym == NULL)
2752 continue;
2753
1b716045 2754 /* We don't have a clever way of identifying arguments, so resort to
2755 a brute-force search. */
6777213b 2756 for (thunk_formal = gfc_sym_get_dummy_args (thunk_sym);
1b716045 2757 thunk_formal;
2758 thunk_formal = thunk_formal->next)
2759 {
2760 if (thunk_formal->sym == formal->sym)
2761 break;
2762 }
2763
2764 if (thunk_formal)
2765 {
2766 /* Pass the argument. */
d95efb59 2767 DECL_ARTIFICIAL (thunk_formal->sym->backend_decl) = 1;
f1f41a6c 2768 vec_safe_push (args, thunk_formal->sym->backend_decl);
1b716045 2769 if (formal->sym->ts.type == BT_CHARACTER)
2770 {
eeebe20b 2771 tmp = thunk_formal->sym->ts.u.cl->backend_decl;
f1f41a6c 2772 vec_safe_push (string_args, tmp);
1b716045 2773 }
2774 }
2775 else
2776 {
2777 /* Pass NULL for a missing argument. */
f1f41a6c 2778 vec_safe_push (args, null_pointer_node);
1b716045 2779 if (formal->sym->ts.type == BT_CHARACTER)
2780 {
7d3075f6 2781 tmp = build_int_cst (gfc_charlen_type_node, 0);
f1f41a6c 2782 vec_safe_push (string_args, tmp);
1b716045 2783 }
2784 }
2785 }
2786
2787 /* Call the master function. */
f1f41a6c 2788 vec_safe_splice (args, string_args);
1b716045 2789 tmp = ns->proc_name->backend_decl;
414c3a2c 2790 tmp = build_call_expr_loc_vec (input_location, tmp, args);
c6871095 2791 if (ns->proc_name->attr.mixed_entry_master)
2792 {
2793 tree union_decl, field;
2794 tree master_type = TREE_TYPE (ns->proc_name->backend_decl);
2795
e60a6f7b 2796 union_decl = build_decl (input_location,
2797 VAR_DECL, get_identifier ("__result"),
c6871095 2798 TREE_TYPE (master_type));
2799 DECL_ARTIFICIAL (union_decl) = 1;
2800 DECL_EXTERNAL (union_decl) = 0;
2801 TREE_PUBLIC (union_decl) = 0;
2802 TREE_USED (union_decl) = 1;
2803 layout_decl (union_decl, 0);
2804 pushdecl (union_decl);
2805
2806 DECL_CONTEXT (union_decl) = current_function_decl;
fd779e1d 2807 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
2808 TREE_TYPE (union_decl), union_decl, tmp);
c6871095 2809 gfc_add_expr_to_block (&body, tmp);
2810
2811 for (field = TYPE_FIELDS (TREE_TYPE (union_decl));
1767a056 2812 field; field = DECL_CHAIN (field))
c6871095 2813 if (strcmp (IDENTIFIER_POINTER (DECL_NAME (field)),
2814 thunk_sym->result->name) == 0)
2815 break;
2816 gcc_assert (field != NULL_TREE);
fd779e1d 2817 tmp = fold_build3_loc (input_location, COMPONENT_REF,
2818 TREE_TYPE (field), union_decl, field,
2819 NULL_TREE);
a90fe829 2820 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
f75d6b8a 2821 TREE_TYPE (DECL_RESULT (current_function_decl)),
2822 DECL_RESULT (current_function_decl), tmp);
c6871095 2823 tmp = build1_v (RETURN_EXPR, tmp);
2824 }
2825 else if (TREE_TYPE (DECL_RESULT (current_function_decl))
2826 != void_type_node)
2827 {
fd779e1d 2828 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
f75d6b8a 2829 TREE_TYPE (DECL_RESULT (current_function_decl)),
2830 DECL_RESULT (current_function_decl), tmp);
c6871095 2831 tmp = build1_v (RETURN_EXPR, tmp);
2832 }
1b716045 2833 gfc_add_expr_to_block (&body, tmp);
2834
2835 /* Finish off this function and send it for code generation. */
2836 DECL_SAVED_TREE (thunk_fndecl) = gfc_finish_block (&body);
e5004242 2837 tmp = getdecls ();
cde2be84 2838 poplevel (1, 1);
1b716045 2839 BLOCK_SUPERCONTEXT (DECL_INITIAL (thunk_fndecl)) = thunk_fndecl;
e5004242 2840 DECL_SAVED_TREE (thunk_fndecl)
2841 = build3_v (BIND_EXPR, tmp, DECL_SAVED_TREE (thunk_fndecl),
2842 DECL_INITIAL (thunk_fndecl));
1b716045 2843
2844 /* Output the GENERIC tree. */
2845 dump_function (TDI_original, thunk_fndecl);
2846
2847 /* Store the end of the function, so that we get good line number
2848 info for the epilogue. */
2849 cfun->function_end_locus = input_location;
2850
2851 /* We're leaving the context of this function, so zap cfun.
2852 It's still in DECL_STRUCT_FUNCTION, and we'll restore it in
2853 tree_rest_of_compilation. */
87d4aa85 2854 set_cfun (NULL);
1b716045 2855
2856 current_function_decl = NULL_TREE;
2857
35ee1c66 2858 cgraph_node::finalize_function (thunk_fndecl, true);
1b716045 2859
2860 /* We share the symbols in the formal argument list with other entry
2861 points and the master function. Clear them so that they are
2862 recreated for each function. */
6777213b 2863 for (formal = gfc_sym_get_dummy_args (thunk_sym); formal;
2864 formal = formal->next)
c6871095 2865 if (formal->sym != NULL) /* Ignore alternate returns. */
2866 {
2867 formal->sym->backend_decl = NULL_TREE;
2868 if (formal->sym->ts.type == BT_CHARACTER)
eeebe20b 2869 formal->sym->ts.u.cl->backend_decl = NULL_TREE;
c6871095 2870 }
2871
2872 if (thunk_sym->attr.function)
1b716045 2873 {
c6871095 2874 if (thunk_sym->ts.type == BT_CHARACTER)
eeebe20b 2875 thunk_sym->ts.u.cl->backend_decl = NULL_TREE;
c6871095 2876 if (thunk_sym->result->ts.type == BT_CHARACTER)
eeebe20b 2877 thunk_sym->result->ts.u.cl->backend_decl = NULL_TREE;
1b716045 2878 }
2879 }
b31f705b 2880
4671339c 2881 gfc_restore_backend_locus (&old_loc);
1b716045 2882}
2883
2884
2885/* Create a decl for a function, and create any thunks for alternate entry
d896f9b3 2886 points. If global is true, generate the function in the global binding
2887 level, otherwise in the current binding level (which can be global). */
1b716045 2888
2889void
d896f9b3 2890gfc_create_function_decl (gfc_namespace * ns, bool global)
1b716045 2891{
2892 /* Create a declaration for the master function. */
d896f9b3 2893 build_function_decl (ns->proc_name, global);
1b716045 2894
f888a3fb 2895 /* Compile the entry thunks. */
1b716045 2896 if (ns->entries)
d896f9b3 2897 build_entry_thunks (ns, global);
1b716045 2898
2899 /* Now create the read argument list. */
2900 create_function_arglist (ns->proc_name);
15b28553 2901
2902 if (ns->omp_declare_simd)
2903 gfc_trans_omp_declare_simd (ns);
1b716045 2904}
2905
c750cc52 2906/* Return the decl used to hold the function return value. If
3350e716 2907 parent_flag is set, the context is the parent_scope. */
4ee9c684 2908
2909tree
c750cc52 2910gfc_get_fake_result_decl (gfc_symbol * sym, int parent_flag)
4ee9c684 2911{
c750cc52 2912 tree decl;
2913 tree length;
2914 tree this_fake_result_decl;
2915 tree this_function_decl;
4ee9c684 2916
2917 char name[GFC_MAX_SYMBOL_LEN + 10];
2918
c750cc52 2919 if (parent_flag)
2920 {
2921 this_fake_result_decl = parent_fake_result_decl;
2922 this_function_decl = DECL_CONTEXT (current_function_decl);
2923 }
2924 else
2925 {
2926 this_fake_result_decl = current_fake_result_decl;
2927 this_function_decl = current_function_decl;
2928 }
2929
c6871095 2930 if (sym
c750cc52 2931 && sym->ns->proc_name->backend_decl == this_function_decl
d4163395 2932 && sym->ns->proc_name->attr.entry_master
c6871095 2933 && sym != sym->ns->proc_name)
2934 {
d4163395 2935 tree t = NULL, var;
c750cc52 2936 if (this_fake_result_decl != NULL)
2937 for (t = TREE_CHAIN (this_fake_result_decl); t; t = TREE_CHAIN (t))
d4163395 2938 if (strcmp (IDENTIFIER_POINTER (TREE_PURPOSE (t)), sym->name) == 0)
2939 break;
2940 if (t)
2941 return TREE_VALUE (t);
c750cc52 2942 decl = gfc_get_fake_result_decl (sym->ns->proc_name, parent_flag);
2943
2944 if (parent_flag)
2945 this_fake_result_decl = parent_fake_result_decl;
2946 else
2947 this_fake_result_decl = current_fake_result_decl;
2948
d4163395 2949 if (decl && sym->ns->proc_name->attr.mixed_entry_master)
c6871095 2950 {
2951 tree field;
2952
2953 for (field = TYPE_FIELDS (TREE_TYPE (decl));
1767a056 2954 field; field = DECL_CHAIN (field))
c6871095 2955 if (strcmp (IDENTIFIER_POINTER (DECL_NAME (field)),
2956 sym->name) == 0)
2957 break;
2958
2959 gcc_assert (field != NULL_TREE);
fd779e1d 2960 decl = fold_build3_loc (input_location, COMPONENT_REF,
2961 TREE_TYPE (field), decl, field, NULL_TREE);
c6871095 2962 }
c750cc52 2963
2964 var = create_tmp_var_raw (TREE_TYPE (decl), sym->name);
2965 if (parent_flag)
2966 gfc_add_decl_to_parent_function (var);
2967 else
2968 gfc_add_decl_to_function (var);
2969
d4163395 2970 SET_DECL_VALUE_EXPR (var, decl);
2971 DECL_HAS_VALUE_EXPR_P (var) = 1;
2cf330c4 2972 GFC_DECL_RESULT (var) = 1;
c750cc52 2973
2974 TREE_CHAIN (this_fake_result_decl)
2975 = tree_cons (get_identifier (sym->name), var,
2976 TREE_CHAIN (this_fake_result_decl));
d4163395 2977 return var;
c6871095 2978 }
2979
c750cc52 2980 if (this_fake_result_decl != NULL_TREE)
2981 return TREE_VALUE (this_fake_result_decl);
4ee9c684 2982
2983 /* Only when gfc_get_fake_result_decl is called by gfc_trans_return,
2984 sym is NULL. */
2985 if (!sym)
2986 return NULL_TREE;
2987
d4163395 2988 if (sym->ts.type == BT_CHARACTER)
4ee9c684 2989 {
eeebe20b 2990 if (sym->ts.u.cl->backend_decl == NULL_TREE)
d4163395 2991 length = gfc_create_string_length (sym);
2992 else
eeebe20b 2993 length = sym->ts.u.cl->backend_decl;
fe732a9b 2994 if (VAR_P (length) && DECL_CONTEXT (length) == NULL_TREE)
99042714 2995 gfc_add_decl_to_function (length);
4ee9c684 2996 }
2997
2998 if (gfc_return_by_reference (sym))
2999 {
c750cc52 3000 decl = DECL_ARGUMENTS (this_function_decl);
c6871095 3001
c750cc52 3002 if (sym->ns->proc_name->backend_decl == this_function_decl
c6871095 3003 && sym->ns->proc_name->attr.entry_master)
1767a056 3004 decl = DECL_CHAIN (decl);
4ee9c684 3005
3006 TREE_USED (decl) = 1;
3007 if (sym->as)
3008 decl = gfc_build_dummy_array_decl (sym, decl);
3009 }
3010 else
3011 {
3012 sprintf (name, "__result_%.20s",
c750cc52 3013 IDENTIFIER_POINTER (DECL_NAME (this_function_decl)));
4ee9c684 3014
3350e716 3015 if (!sym->attr.mixed_entry_master && sym->attr.function)
1e71b314 3016 decl = build_decl (DECL_SOURCE_LOCATION (this_function_decl),
e60a6f7b 3017 VAR_DECL, get_identifier (name),
3350e716 3018 gfc_sym_type (sym));
3019 else
1e71b314 3020 decl = build_decl (DECL_SOURCE_LOCATION (this_function_decl),
e60a6f7b 3021 VAR_DECL, get_identifier (name),
3350e716 3022 TREE_TYPE (TREE_TYPE (this_function_decl)));
4ee9c684 3023 DECL_ARTIFICIAL (decl) = 1;
3024 DECL_EXTERNAL (decl) = 0;
3025 TREE_PUBLIC (decl) = 0;
3026 TREE_USED (decl) = 1;
764f1175 3027 GFC_DECL_RESULT (decl) = 1;
a379e3a9 3028 TREE_ADDRESSABLE (decl) = 1;
4ee9c684 3029
3030 layout_decl (decl, 0);
cf5f881f 3031 gfc_finish_decl_attrs (decl, &sym->attr);
4ee9c684 3032
c750cc52 3033 if (parent_flag)
3034 gfc_add_decl_to_parent_function (decl);
3035 else
3036 gfc_add_decl_to_function (decl);
4ee9c684 3037 }
3038
c750cc52 3039 if (parent_flag)
3040 parent_fake_result_decl = build_tree_list (NULL, decl);
3041 else
3042 current_fake_result_decl = build_tree_list (NULL, decl);
4ee9c684 3043
3044 return decl;
3045}
3046
3047
3048/* Builds a function decl. The remaining parameters are the types of the
3049 function arguments. Negative nargs indicates a varargs function. */
3050
8ce86007 3051static tree
3052build_library_function_decl_1 (tree name, const char *spec,
3053 tree rettype, int nargs, va_list p)
4ee9c684 3054{
f1f41a6c 3055 vec<tree, va_gc> *arglist;
4ee9c684 3056 tree fntype;
3057 tree fndecl;
4ee9c684 3058 int n;
3059
3060 /* Library functions must be declared with global scope. */
22d678e8 3061 gcc_assert (current_function_decl == NULL_TREE);
4ee9c684 3062
4ee9c684 3063 /* Create a list of the argument types. */
f1f41a6c 3064 vec_alloc (arglist, abs (nargs));
5edc3af9 3065 for (n = abs (nargs); n > 0; n--)
4ee9c684 3066 {
5edc3af9 3067 tree argtype = va_arg (p, tree);
f1f41a6c 3068 arglist->quick_push (argtype);
4ee9c684 3069 }
3070
3071 /* Build the function type and decl. */
5edc3af9 3072 if (nargs >= 0)
3073 fntype = build_function_type_vec (rettype, arglist);
3074 else
3075 fntype = build_varargs_function_type_vec (rettype, arglist);
8ce86007 3076 if (spec)
3077 {
3078 tree attr_args = build_tree_list (NULL_TREE,
3079 build_string (strlen (spec), spec));
3080 tree attrs = tree_cons (get_identifier ("fn spec"),
3081 attr_args, TYPE_ATTRIBUTES (fntype));
3082 fntype = build_type_attribute_variant (fntype, attrs);
3083 }
e60a6f7b 3084 fndecl = build_decl (input_location,
3085 FUNCTION_DECL, name, fntype);
4ee9c684 3086
3087 /* Mark this decl as external. */
3088 DECL_EXTERNAL (fndecl) = 1;
3089 TREE_PUBLIC (fndecl) = 1;
3090
4ee9c684 3091 pushdecl (fndecl);
3092
b2c4af5e 3093 rest_of_decl_compilation (fndecl, 1, 0);
4ee9c684 3094
3095 return fndecl;
3096}
3097
8ce86007 3098/* Builds a function decl. The remaining parameters are the types of the
3099 function arguments. Negative nargs indicates a varargs function. */
3100
3101tree
3102gfc_build_library_function_decl (tree name, tree rettype, int nargs, ...)
3103{
3104 tree ret;
3105 va_list args;
3106 va_start (args, nargs);
3107 ret = build_library_function_decl_1 (name, NULL, rettype, nargs, args);
3108 va_end (args);
3109 return ret;
3110}
3111
3112/* Builds a function decl. The remaining parameters are the types of the
3113 function arguments. Negative nargs indicates a varargs function.
3114 The SPEC parameter specifies the function argument and return type
3115 specification according to the fnspec function type attribute. */
3116
4bf69bc3 3117tree
8ce86007 3118gfc_build_library_function_decl_with_spec (tree name, const char *spec,
3119 tree rettype, int nargs, ...)
3120{
3121 tree ret;
3122 va_list args;
3123 va_start (args, nargs);
3124 ret = build_library_function_decl_1 (name, spec, rettype, nargs, args);
3125 va_end (args);
3126 return ret;
3127}
3128
4ee9c684 3129static void
3130gfc_build_intrinsic_function_decls (void)
3131{
90ba9145 3132 tree gfc_int4_type_node = gfc_get_int_type (4);
72ce5390 3133 tree gfc_pint4_type_node = build_pointer_type (gfc_int4_type_node);
90ba9145 3134 tree gfc_int8_type_node = gfc_get_int_type (8);
72ce5390 3135 tree gfc_pint8_type_node = build_pointer_type (gfc_int8_type_node);
920e54ef 3136 tree gfc_int16_type_node = gfc_get_int_type (16);
90ba9145 3137 tree gfc_logical4_type_node = gfc_get_logical_type (4);
40b806de 3138 tree pchar1_type_node = gfc_get_pchar_type (1);
3139 tree pchar4_type_node = gfc_get_pchar_type (4);
90ba9145 3140
4ee9c684 3141 /* String functions. */
241ecdc7 3142 gfor_fndecl_compare_string = gfc_build_library_function_decl_with_spec (
3143 get_identifier (PREFIX("compare_string")), "..R.R",
3144 integer_type_node, 4, gfc_charlen_type_node, pchar1_type_node,
3145 gfc_charlen_type_node, pchar1_type_node);
537824d1 3146 DECL_PURE_P (gfor_fndecl_compare_string) = 1;
bc351485 3147 TREE_NOTHROW (gfor_fndecl_compare_string) = 1;
241ecdc7 3148
3149 gfor_fndecl_concat_string = gfc_build_library_function_decl_with_spec (
3150 get_identifier (PREFIX("concat_string")), "..W.R.R",
3151 void_type_node, 6, gfc_charlen_type_node, pchar1_type_node,
3152 gfc_charlen_type_node, pchar1_type_node,
3153 gfc_charlen_type_node, pchar1_type_node);
bc351485 3154 TREE_NOTHROW (gfor_fndecl_concat_string) = 1;
241ecdc7 3155
3156 gfor_fndecl_string_len_trim = gfc_build_library_function_decl_with_spec (
3157 get_identifier (PREFIX("string_len_trim")), "..R",
3158 gfc_charlen_type_node, 2, gfc_charlen_type_node, pchar1_type_node);
537824d1 3159 DECL_PURE_P (gfor_fndecl_string_len_trim) = 1;
bc351485 3160 TREE_NOTHROW (gfor_fndecl_string_len_trim) = 1;
241ecdc7 3161
3162 gfor_fndecl_string_index = gfc_build_library_function_decl_with_spec (
3163 get_identifier (PREFIX("string_index")), "..R.R.",
3164 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar1_type_node,
3165 gfc_charlen_type_node, pchar1_type_node, gfc_logical4_type_node);
537824d1 3166 DECL_PURE_P (gfor_fndecl_string_index) = 1;
bc351485 3167 TREE_NOTHROW (gfor_fndecl_string_index) = 1;
241ecdc7 3168
3169 gfor_fndecl_string_scan = gfc_build_library_function_decl_with_spec (
3170 get_identifier (PREFIX("string_scan")), "..R.R.",
3171 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar1_type_node,
3172 gfc_charlen_type_node, pchar1_type_node, gfc_logical4_type_node);
537824d1 3173 DECL_PURE_P (gfor_fndecl_string_scan) = 1;
bc351485 3174 TREE_NOTHROW (gfor_fndecl_string_scan) = 1;
241ecdc7 3175
3176 gfor_fndecl_string_verify = gfc_build_library_function_decl_with_spec (
3177 get_identifier (PREFIX("string_verify")), "..R.R.",
3178 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar1_type_node,
3179 gfc_charlen_type_node, pchar1_type_node, gfc_logical4_type_node);
537824d1 3180 DECL_PURE_P (gfor_fndecl_string_verify) = 1;
bc351485 3181 TREE_NOTHROW (gfor_fndecl_string_verify) = 1;
241ecdc7 3182
3183 gfor_fndecl_string_trim = gfc_build_library_function_decl_with_spec (
3184 get_identifier (PREFIX("string_trim")), ".Ww.R",
3185 void_type_node, 4, build_pointer_type (gfc_charlen_type_node),
3186 build_pointer_type (pchar1_type_node), gfc_charlen_type_node,
3187 pchar1_type_node);
3188
3189 gfor_fndecl_string_minmax = gfc_build_library_function_decl_with_spec (
3190 get_identifier (PREFIX("string_minmax")), ".Ww.R",
3191 void_type_node, -4, build_pointer_type (gfc_charlen_type_node),
3192 build_pointer_type (pchar1_type_node), integer_type_node,
3193 integer_type_node);
3194
3195 gfor_fndecl_adjustl = gfc_build_library_function_decl_with_spec (
3196 get_identifier (PREFIX("adjustl")), ".W.R",
3197 void_type_node, 3, pchar1_type_node, gfc_charlen_type_node,
3198 pchar1_type_node);
bc351485 3199 TREE_NOTHROW (gfor_fndecl_adjustl) = 1;
241ecdc7 3200
3201 gfor_fndecl_adjustr = gfc_build_library_function_decl_with_spec (
3202 get_identifier (PREFIX("adjustr")), ".W.R",
3203 void_type_node, 3, pchar1_type_node, gfc_charlen_type_node,
3204 pchar1_type_node);
bc351485 3205 TREE_NOTHROW (gfor_fndecl_adjustr) = 1;
241ecdc7 3206
3207 gfor_fndecl_select_string = gfc_build_library_function_decl_with_spec (
3208 get_identifier (PREFIX("select_string")), ".R.R.",
3209 integer_type_node, 4, pvoid_type_node, integer_type_node,
3210 pchar1_type_node, gfc_charlen_type_node);
537824d1 3211 DECL_PURE_P (gfor_fndecl_select_string) = 1;
bc351485 3212 TREE_NOTHROW (gfor_fndecl_select_string) = 1;
241ecdc7 3213
3214 gfor_fndecl_compare_string_char4 = gfc_build_library_function_decl_with_spec (
3215 get_identifier (PREFIX("compare_string_char4")), "..R.R",
3216 integer_type_node, 4, gfc_charlen_type_node, pchar4_type_node,
3217 gfc_charlen_type_node, pchar4_type_node);
537824d1 3218 DECL_PURE_P (gfor_fndecl_compare_string_char4) = 1;
bc351485 3219 TREE_NOTHROW (gfor_fndecl_compare_string_char4) = 1;
241ecdc7 3220
3221 gfor_fndecl_concat_string_char4 = gfc_build_library_function_decl_with_spec (
3222 get_identifier (PREFIX("concat_string_char4")), "..W.R.R",
3223 void_type_node, 6, gfc_charlen_type_node, pchar4_type_node,
3224 gfc_charlen_type_node, pchar4_type_node, gfc_charlen_type_node,
3225 pchar4_type_node);
bc351485 3226 TREE_NOTHROW (gfor_fndecl_concat_string_char4) = 1;
241ecdc7 3227
3228 gfor_fndecl_string_len_trim_char4 = gfc_build_library_function_decl_with_spec (
3229 get_identifier (PREFIX("string_len_trim_char4")), "..R",
3230 gfc_charlen_type_node, 2, gfc_charlen_type_node, pchar4_type_node);
537824d1 3231 DECL_PURE_P (gfor_fndecl_string_len_trim_char4) = 1;
bc351485 3232 TREE_NOTHROW (gfor_fndecl_string_len_trim_char4) = 1;
241ecdc7 3233
3234 gfor_fndecl_string_index_char4 = gfc_build_library_function_decl_with_spec (
3235 get_identifier (PREFIX("string_index_char4")), "..R.R.",
3236 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar4_type_node,
3237 gfc_charlen_type_node, pchar4_type_node, gfc_logical4_type_node);
537824d1 3238 DECL_PURE_P (gfor_fndecl_string_index_char4) = 1;
bc351485 3239 TREE_NOTHROW (gfor_fndecl_string_index_char4) = 1;
241ecdc7 3240
3241 gfor_fndecl_string_scan_char4 = gfc_build_library_function_decl_with_spec (
3242 get_identifier (PREFIX("string_scan_char4")), "..R.R.",
3243 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar4_type_node,
3244 gfc_charlen_type_node, pchar4_type_node, gfc_logical4_type_node);
537824d1 3245 DECL_PURE_P (gfor_fndecl_string_scan_char4) = 1;
bc351485 3246 TREE_NOTHROW (gfor_fndecl_string_scan_char4) = 1;
241ecdc7 3247
3248 gfor_fndecl_string_verify_char4 = gfc_build_library_function_decl_with_spec (
3249 get_identifier (PREFIX("string_verify_char4")), "..R.R.",
3250 gfc_charlen_type_node, 5, gfc_charlen_type_node, pchar4_type_node,
3251 gfc_charlen_type_node, pchar4_type_node, gfc_logical4_type_node);
537824d1 3252 DECL_PURE_P (gfor_fndecl_string_verify_char4) = 1;
bc351485 3253 TREE_NOTHROW (gfor_fndecl_string_verify_char4) = 1;
241ecdc7 3254
3255 gfor_fndecl_string_trim_char4 = gfc_build_library_function_decl_with_spec (
3256 get_identifier (PREFIX("string_trim_char4")), ".Ww.R",
3257 void_type_node, 4, build_pointer_type (gfc_charlen_type_node),
3258 build_pointer_type (pchar4_type_node), gfc_charlen_type_node,
3259 pchar4_type_node);
3260
3261 gfor_fndecl_string_minmax_char4 = gfc_build_library_function_decl_with_spec (
3262 get_identifier (PREFIX("string_minmax_char4")), ".Ww.R",
3263 void_type_node, -4, build_pointer_type (gfc_charlen_type_node),
3264 build_pointer_type (pchar4_type_node), integer_type_node,
3265 integer_type_node);
3266
3267 gfor_fndecl_adjustl_char4 = gfc_build_library_function_decl_with_spec (
3268 get_identifier (PREFIX("adjustl_char4")), ".W.R",
3269 void_type_node, 3, pchar4_type_node, gfc_charlen_type_node,
3270 pchar4_type_node);
bc351485 3271 TREE_NOTHROW (gfor_fndecl_adjustl_char4) = 1;
241ecdc7 3272
3273 gfor_fndecl_adjustr_char4 = gfc_build_library_function_decl_with_spec (
3274 get_identifier (PREFIX("adjustr_char4")), ".W.R",
3275 void_type_node, 3, pchar4_type_node, gfc_charlen_type_node,
3276 pchar4_type_node);
bc351485 3277 TREE_NOTHROW (gfor_fndecl_adjustr_char4) = 1;
241ecdc7 3278
3279 gfor_fndecl_select_string_char4 = gfc_build_library_function_decl_with_spec (
3280 get_identifier (PREFIX("select_string_char4")), ".R.R.",
3281 integer_type_node, 4, pvoid_type_node, integer_type_node,
3282 pvoid_type_node, gfc_charlen_type_node);
537824d1 3283 DECL_PURE_P (gfor_fndecl_select_string_char4) = 1;
bc351485 3284 TREE_NOTHROW (gfor_fndecl_select_string_char4) = 1;
b44437b9 3285
3286
3287 /* Conversion between character kinds. */
3288
241ecdc7 3289 gfor_fndecl_convert_char1_to_char4 = gfc_build_library_function_decl_with_spec (
3290 get_identifier (PREFIX("convert_char1_to_char4")), ".w.R",
3291 void_type_node, 3, build_pointer_type (pchar4_type_node),
3292 gfc_charlen_type_node, pchar1_type_node);
b44437b9 3293
241ecdc7 3294 gfor_fndecl_convert_char4_to_char1 = gfc_build_library_function_decl_with_spec (
3295 get_identifier (PREFIX("convert_char4_to_char1")), ".w.R",
3296 void_type_node, 3, build_pointer_type (pchar1_type_node),
3297 gfc_charlen_type_node, pchar4_type_node);
b44437b9 3298
40b806de 3299 /* Misc. functions. */
5fcc6ec2 3300
241ecdc7 3301 gfor_fndecl_ttynam = gfc_build_library_function_decl_with_spec (
3302 get_identifier (PREFIX("ttynam")), ".W",
3303 void_type_node, 3, pchar_type_node, gfc_charlen_type_node,
3304 integer_type_node);
3305
3306 gfor_fndecl_fdate = gfc_build_library_function_decl_with_spec (
3307 get_identifier (PREFIX("fdate")), ".W",
3308 void_type_node, 2, pchar_type_node, gfc_charlen_type_node);
3309
3310 gfor_fndecl_ctime = gfc_build_library_function_decl_with_spec (
3311 get_identifier (PREFIX("ctime")), ".W",
3312 void_type_node, 3, pchar_type_node, gfc_charlen_type_node,
3313 gfc_int8_type_node);
3314
3315 gfor_fndecl_sc_kind = gfc_build_library_function_decl_with_spec (
3316 get_identifier (PREFIX("selected_char_kind")), "..R",
3317 gfc_int4_type_node, 2, gfc_charlen_type_node, pchar_type_node);
537824d1 3318 DECL_PURE_P (gfor_fndecl_sc_kind) = 1;
bc351485 3319 TREE_NOTHROW (gfor_fndecl_sc_kind) = 1;
241ecdc7 3320
3321 gfor_fndecl_si_kind = gfc_build_library_function_decl_with_spec (
3322 get_identifier (PREFIX("selected_int_kind")), ".R",
3323 gfc_int4_type_node, 1, pvoid_type_node);
537824d1 3324 DECL_PURE_P (gfor_fndecl_si_kind) = 1;
bc351485 3325 TREE_NOTHROW (gfor_fndecl_si_kind) = 1;
241ecdc7 3326
3327 gfor_fndecl_sr_kind = gfc_build_library_function_decl_with_spec (
3328 get_identifier (PREFIX("selected_real_kind2008")), ".RR",
3329 gfc_int4_type_node, 3, pvoid_type_node, pvoid_type_node,
3330 pvoid_type_node);
537824d1 3331 DECL_PURE_P (gfor_fndecl_sr_kind) = 1;
bc351485 3332 TREE_NOTHROW (gfor_fndecl_sr_kind) = 1;
4ee9c684 3333
72ce5390 3334 gfor_fndecl_system_clock4 = gfc_build_library_function_decl (
3335 get_identifier (PREFIX("system_clock_4")),
3336 void_type_node, 3, gfc_pint4_type_node, gfc_pint4_type_node,
3337 gfc_pint4_type_node);
3338
3339 gfor_fndecl_system_clock8 = gfc_build_library_function_decl (
3340 get_identifier (PREFIX("system_clock_8")),
3341 void_type_node, 3, gfc_pint8_type_node, gfc_pint8_type_node,
3342 gfc_pint8_type_node);
3343
4ee9c684 3344 /* Power functions. */
76834664 3345 {
920e54ef 3346 tree ctype, rtype, itype, jtype;
3347 int rkind, ikind, jkind;
3348#define NIKINDS 3
3349#define NRKINDS 4
3350 static int ikinds[NIKINDS] = {4, 8, 16};
3351 static int rkinds[NRKINDS] = {4, 8, 10, 16};
3352 char name[PREFIX_LEN + 12]; /* _gfortran_pow_?n_?n */
3353
3354 for (ikind=0; ikind < NIKINDS; ikind++)
76834664 3355 {
920e54ef 3356 itype = gfc_get_int_type (ikinds[ikind]);
3357
3358 for (jkind=0; jkind < NIKINDS; jkind++)
3359 {
3360 jtype = gfc_get_int_type (ikinds[jkind]);
3361 if (itype && jtype)
3362 {
3363 sprintf(name, PREFIX("pow_i%d_i%d"), ikinds[ikind],
3364 ikinds[jkind]);
3365 gfor_fndecl_math_powi[jkind][ikind].integer =
3366 gfc_build_library_function_decl (get_identifier (name),
3367 jtype, 2, jtype, itype);
2177d98b 3368 TREE_READONLY (gfor_fndecl_math_powi[jkind][ikind].integer) = 1;
bc351485 3369 TREE_NOTHROW (gfor_fndecl_math_powi[jkind][ikind].integer) = 1;
920e54ef 3370 }
3371 }
3372
3373 for (rkind = 0; rkind < NRKINDS; rkind ++)
76834664 3374 {
920e54ef 3375 rtype = gfc_get_real_type (rkinds[rkind]);
3376 if (rtype && itype)
3377 {
3378 sprintf(name, PREFIX("pow_r%d_i%d"), rkinds[rkind],
3379 ikinds[ikind]);
3380 gfor_fndecl_math_powi[rkind][ikind].real =
3381 gfc_build_library_function_decl (get_identifier (name),
3382 rtype, 2, rtype, itype);
2177d98b 3383 TREE_READONLY (gfor_fndecl_math_powi[rkind][ikind].real) = 1;
bc351485 3384 TREE_NOTHROW (gfor_fndecl_math_powi[rkind][ikind].real) = 1;
920e54ef 3385 }
3386
3387 ctype = gfc_get_complex_type (rkinds[rkind]);
3388 if (ctype && itype)
3389 {
3390 sprintf(name, PREFIX("pow_c%d_i%d"), rkinds[rkind],
3391 ikinds[ikind]);
3392 gfor_fndecl_math_powi[rkind][ikind].cmplx =
3393 gfc_build_library_function_decl (get_identifier (name),
3394 ctype, 2,ctype, itype);
2177d98b 3395 TREE_READONLY (gfor_fndecl_math_powi[rkind][ikind].cmplx) = 1;
bc351485 3396 TREE_NOTHROW (gfor_fndecl_math_powi[rkind][ikind].cmplx) = 1;
920e54ef 3397 }
76834664 3398 }
3399 }
920e54ef 3400#undef NIKINDS
3401#undef NRKINDS
76834664 3402 }
3403
241ecdc7 3404 gfor_fndecl_math_ishftc4 = gfc_build_library_function_decl (
3405 get_identifier (PREFIX("ishftc4")),
3406 gfc_int4_type_node, 3, gfc_int4_type_node, gfc_int4_type_node,
3407 gfc_int4_type_node);
bc351485 3408 TREE_READONLY (gfor_fndecl_math_ishftc4) = 1;
3409 TREE_NOTHROW (gfor_fndecl_math_ishftc4) = 1;
a90fe829 3410
241ecdc7 3411 gfor_fndecl_math_ishftc8 = gfc_build_library_function_decl (
3412 get_identifier (PREFIX("ishftc8")),
3413 gfc_int8_type_node, 3, gfc_int8_type_node, gfc_int4_type_node,
3414 gfc_int4_type_node);
bc351485 3415 TREE_READONLY (gfor_fndecl_math_ishftc8) = 1;
3416 TREE_NOTHROW (gfor_fndecl_math_ishftc8) = 1;
241ecdc7 3417
920e54ef 3418 if (gfc_int16_type_node)
bc351485 3419 {
3420 gfor_fndecl_math_ishftc16 = gfc_build_library_function_decl (
241ecdc7 3421 get_identifier (PREFIX("ishftc16")),
3422 gfc_int16_type_node, 3, gfc_int16_type_node, gfc_int4_type_node,
3423 gfc_int4_type_node);
bc351485 3424 TREE_READONLY (gfor_fndecl_math_ishftc16) = 1;
3425 TREE_NOTHROW (gfor_fndecl_math_ishftc16) = 1;
3426 }
920e54ef 3427
4e8e57b0 3428 /* BLAS functions. */
3429 {
36c921b9 3430 tree pint = build_pointer_type (integer_type_node);
4e8e57b0 3431 tree ps = build_pointer_type (gfc_get_real_type (gfc_default_real_kind));
3432 tree pd = build_pointer_type (gfc_get_real_type (gfc_default_double_kind));
3433 tree pc = build_pointer_type (gfc_get_complex_type (gfc_default_real_kind));
3434 tree pz = build_pointer_type
3435 (gfc_get_complex_type (gfc_default_double_kind));
3436
3437 gfor_fndecl_sgemm = gfc_build_library_function_decl
3438 (get_identifier
829d7a08 3439 (flag_underscoring ? "sgemm_" : "sgemm"),
4e8e57b0 3440 void_type_node, 15, pchar_type_node,
3441 pchar_type_node, pint, pint, pint, ps, ps, pint,
36c921b9 3442 ps, pint, ps, ps, pint, integer_type_node,
3443 integer_type_node);
4e8e57b0 3444 gfor_fndecl_dgemm = gfc_build_library_function_decl
3445 (get_identifier
829d7a08 3446 (flag_underscoring ? "dgemm_" : "dgemm"),
4e8e57b0 3447 void_type_node, 15, pchar_type_node,
3448 pchar_type_node, pint, pint, pint, pd, pd, pint,
36c921b9 3449 pd, pint, pd, pd, pint, integer_type_node,
3450 integer_type_node);
4e8e57b0 3451 gfor_fndecl_cgemm = gfc_build_library_function_decl
3452 (get_identifier
829d7a08 3453 (flag_underscoring ? "cgemm_" : "cgemm"),
4e8e57b0 3454 void_type_node, 15, pchar_type_node,
3455 pchar_type_node, pint, pint, pint, pc, pc, pint,
36c921b9 3456 pc, pint, pc, pc, pint, integer_type_node,
3457 integer_type_node);
4e8e57b0 3458 gfor_fndecl_zgemm = gfc_build_library_function_decl
3459 (get_identifier
829d7a08 3460 (flag_underscoring ? "zgemm_" : "zgemm"),
4e8e57b0 3461 void_type_node, 15, pchar_type_node,
3462 pchar_type_node, pint, pint, pint, pz, pz, pint,
36c921b9 3463 pz, pint, pz, pz, pint, integer_type_node,
3464 integer_type_node);
4e8e57b0 3465 }
3466
4ee9c684 3467 /* Other functions. */
241ecdc7 3468 gfor_fndecl_size0 = gfc_build_library_function_decl_with_spec (
3469 get_identifier (PREFIX("size0")), ".R",
3470 gfc_array_index_type, 1, pvoid_type_node);
537824d1 3471 DECL_PURE_P (gfor_fndecl_size0) = 1;
bc351485 3472 TREE_NOTHROW (gfor_fndecl_size0) = 1;
241ecdc7 3473
3474 gfor_fndecl_size1 = gfc_build_library_function_decl_with_spec (
3475 get_identifier (PREFIX("size1")), ".R",
3476 gfc_array_index_type, 2, pvoid_type_node, gfc_array_index_type);
537824d1 3477 DECL_PURE_P (gfor_fndecl_size1) = 1;
bc351485 3478 TREE_NOTHROW (gfor_fndecl_size1) = 1;
241ecdc7 3479
3480 gfor_fndecl_iargc = gfc_build_library_function_decl (
3481 get_identifier (PREFIX ("iargc")), gfc_int4_type_node, 0);
bc351485 3482 TREE_NOTHROW (gfor_fndecl_iargc) = 1;
4ee9c684 3483}
3484
3485
3486/* Make prototypes for runtime library functions. */
3487
3488void
3489gfc_build_builtin_function_decls (void)
3490{
90ba9145 3491 tree gfc_int4_type_node = gfc_get_int_type (4);
4ee9c684 3492
241ecdc7 3493 gfor_fndecl_stop_numeric = gfc_build_library_function_decl (
3494 get_identifier (PREFIX("stop_numeric")),
3495 void_type_node, 1, gfc_int4_type_node);
070cc790 3496 /* STOP doesn't return. */
98ccec97 3497 TREE_THIS_VOLATILE (gfor_fndecl_stop_numeric) = 1;
3498
241ecdc7 3499 gfor_fndecl_stop_string = gfc_build_library_function_decl_with_spec (
3500 get_identifier (PREFIX("stop_string")), ".R.",
3501 void_type_node, 2, pchar_type_node, gfc_int4_type_node);
070cc790 3502 /* STOP doesn't return. */
241ecdc7 3503 TREE_THIS_VOLATILE (gfor_fndecl_stop_string) = 1;
537824d1 3504
241ecdc7 3505 gfor_fndecl_error_stop_numeric = gfc_build_library_function_decl (
3506 get_identifier (PREFIX("error_stop_numeric")),
3507 void_type_node, 1, gfc_int4_type_node);
070cc790 3508 /* ERROR STOP doesn't return. */
3509 TREE_THIS_VOLATILE (gfor_fndecl_error_stop_numeric) = 1;
3510
241ecdc7 3511 gfor_fndecl_error_stop_string = gfc_build_library_function_decl_with_spec (
3512 get_identifier (PREFIX("error_stop_string")), ".R.",
3513 void_type_node, 2, pchar_type_node, gfc_int4_type_node);
c6cd3066 3514 /* ERROR STOP doesn't return. */
3515 TREE_THIS_VOLATILE (gfor_fndecl_error_stop_string) = 1;
3516
241ecdc7 3517 gfor_fndecl_pause_numeric = gfc_build_library_function_decl (
3518 get_identifier (PREFIX("pause_numeric")),
3519 void_type_node, 1, gfc_int4_type_node);
070cc790 3520
241ecdc7 3521 gfor_fndecl_pause_string = gfc_build_library_function_decl_with_spec (
3522 get_identifier (PREFIX("pause_string")), ".R.",
3523 void_type_node, 2, pchar_type_node, gfc_int4_type_node);
4ee9c684 3524
241ecdc7 3525 gfor_fndecl_runtime_error = gfc_build_library_function_decl_with_spec (
3526 get_identifier (PREFIX("runtime_error")), ".R",
3527 void_type_node, -1, pchar_type_node);
9c0f3811 3528 /* The runtime_error function does not return. */
3529 TREE_THIS_VOLATILE (gfor_fndecl_runtime_error) = 1;
4ee9c684 3530
241ecdc7 3531 gfor_fndecl_runtime_error_at = gfc_build_library_function_decl_with_spec (
3532 get_identifier (PREFIX("runtime_error_at")), ".RR",
3533 void_type_node, -2, pchar_type_node, pchar_type_node);
50ad5fa2 3534 /* The runtime_error_at function does not return. */
3535 TREE_THIS_VOLATILE (gfor_fndecl_runtime_error_at) = 1;
a90fe829 3536
241ecdc7 3537 gfor_fndecl_runtime_warning_at = gfc_build_library_function_decl_with_spec (
3538 get_identifier (PREFIX("runtime_warning_at")), ".RR",
3539 void_type_node, -2, pchar_type_node, pchar_type_node);
3540
3541 gfor_fndecl_generate_error = gfc_build_library_function_decl_with_spec (
3542 get_identifier (PREFIX("generate_error")), ".R.R",
3543 void_type_node, 3, pvoid_type_node, integer_type_node,
3544 pchar_type_node);
3545
3546 gfor_fndecl_os_error = gfc_build_library_function_decl_with_spec (
3547 get_identifier (PREFIX("os_error")), ".R",
3548 void_type_node, 1, pchar_type_node);
9915365e 3549 /* The runtime_error function does not return. */
3550 TREE_THIS_VOLATILE (gfor_fndecl_os_error) = 1;
3551
241ecdc7 3552 gfor_fndecl_set_args = gfc_build_library_function_decl (
3553 get_identifier (PREFIX("set_args")),
3554 void_type_node, 2, integer_type_node,
3555 build_pointer_type (pchar_type_node));
7257a5d2 3556
241ecdc7 3557 gfor_fndecl_set_fpe = gfc_build_library_function_decl (
3558 get_identifier (PREFIX("set_fpe")),
3559 void_type_node, 1, integer_type_node);
8c84a5de 3560
d566c3e0 3561 gfor_fndecl_ieee_procedure_entry = gfc_build_library_function_decl (
3562 get_identifier (PREFIX("ieee_procedure_entry")),
3563 void_type_node, 1, pvoid_type_node);
3564
3565 gfor_fndecl_ieee_procedure_exit = gfc_build_library_function_decl (
3566 get_identifier (PREFIX("ieee_procedure_exit")),
3567 void_type_node, 1, pvoid_type_node);
3568
56c7c2d7 3569 /* Keep the array dimension in sync with the call, later in this file. */
241ecdc7 3570 gfor_fndecl_set_options = gfc_build_library_function_decl_with_spec (
3571 get_identifier (PREFIX("set_options")), "..R",
3572 void_type_node, 2, integer_type_node,
3573 build_pointer_type (integer_type_node));
64fc3c4c 3574
241ecdc7 3575 gfor_fndecl_set_convert = gfc_build_library_function_decl (
3576 get_identifier (PREFIX("set_convert")),
3577 void_type_node, 1, integer_type_node);
15774a8b 3578
241ecdc7 3579 gfor_fndecl_set_record_marker = gfc_build_library_function_decl (
3580 get_identifier (PREFIX("set_record_marker")),
3581 void_type_node, 1, integer_type_node);
f23886ab 3582
241ecdc7 3583 gfor_fndecl_set_max_subrecord_length = gfc_build_library_function_decl (
3584 get_identifier (PREFIX("set_max_subrecord_length")),
3585 void_type_node, 1, integer_type_node);
bbaaa7b1 3586
8ce86007 3587 gfor_fndecl_in_pack = gfc_build_library_function_decl_with_spec (
241ecdc7 3588 get_identifier (PREFIX("internal_pack")), ".r",
3589 pvoid_type_node, 1, pvoid_type_node);
4ee9c684 3590
8ce86007 3591 gfor_fndecl_in_unpack = gfc_build_library_function_decl_with_spec (
241ecdc7 3592 get_identifier (PREFIX("internal_unpack")), ".wR",
3593 void_type_node, 2, pvoid_type_node, pvoid_type_node);
3594
3595 gfor_fndecl_associated = gfc_build_library_function_decl_with_spec (
3596 get_identifier (PREFIX("associated")), ".RR",
3597 integer_type_node, 2, ppvoid_type_node, ppvoid_type_node);
537824d1 3598 DECL_PURE_P (gfor_fndecl_associated) = 1;
bc351485 3599 TREE_NOTHROW (gfor_fndecl_associated) = 1;
4ee9c684 3600
70b5944a 3601 /* Coarray library calls. */
4fe73152 3602 if (flag_coarray == GFC_FCOARRAY_LIB)
70b5944a 3603 {
3604 tree pint_type, pppchar_type;
3605
3606 pint_type = build_pointer_type (integer_type_node);
3607 pppchar_type
3608 = build_pointer_type (build_pointer_type (pchar_type_node));
3609
3610 gfor_fndecl_caf_init = gfc_build_library_function_decl (
65cbb21d 3611 get_identifier (PREFIX("caf_init")), void_type_node,
3612 2, pint_type, pppchar_type);
70b5944a 3613
3614 gfor_fndecl_caf_finalize = gfc_build_library_function_decl (
3615 get_identifier (PREFIX("caf_finalize")), void_type_node, 0);
3616
d44f2f7c 3617 gfor_fndecl_caf_this_image = gfc_build_library_function_decl (
65cbb21d 3618 get_identifier (PREFIX("caf_this_image")), integer_type_node,
3619 1, integer_type_node);
d44f2f7c 3620
3621 gfor_fndecl_caf_num_images = gfc_build_library_function_decl (
65cbb21d 3622 get_identifier (PREFIX("caf_num_images")), integer_type_node,
3623 2, integer_type_node, integer_type_node);
d44f2f7c 3624
a961ca30 3625 gfor_fndecl_caf_register = gfc_build_library_function_decl_with_spec (
eee0cf09 3626 get_identifier (PREFIX("caf_register")), "RRWWWWR", void_type_node, 7,
3627 size_type_node, integer_type_node, ppvoid_type_node, pvoid_type_node,
3628 pint_type, pchar_type_node, integer_type_node);
d0d776fb 3629
3630 gfor_fndecl_caf_deregister = gfc_build_library_function_decl_with_spec (
3d2aa0e8 3631 get_identifier (PREFIX("caf_deregister")), "WRWWR", void_type_node, 5,
3632 ppvoid_type_node, integer_type_node, pint_type, pchar_type_node,
3633 integer_type_node);
a961ca30 3634
5f4a118e 3635 gfor_fndecl_caf_get = gfc_build_library_function_decl_with_spec (
65cbb21d 3636 get_identifier (PREFIX("caf_get")), ".R.RRWRRRW", void_type_node, 10,
3637 pvoid_type_node, size_type_node, integer_type_node, pvoid_type_node,
9f1c76f9 3638 pvoid_type_node, pvoid_type_node, integer_type_node, integer_type_node,
6b5471d8 3639 boolean_type_node, pint_type);
5f4a118e 3640
3641 gfor_fndecl_caf_send = gfc_build_library_function_decl_with_spec (
65cbb21d 3642 get_identifier (PREFIX("caf_send")), ".R.RRRRRRW", void_type_node, 10,
3643 pvoid_type_node, size_type_node, integer_type_node, pvoid_type_node,
9f1c76f9 3644 pvoid_type_node, pvoid_type_node, integer_type_node, integer_type_node,
6b5471d8 3645 boolean_type_node, pint_type);
5f4a118e 3646
3647 gfor_fndecl_caf_sendget = gfc_build_library_function_decl_with_spec (
eee0cf09 3648 get_identifier (PREFIX("caf_sendget")), ".R.RRRR.RRRRRR",
3649 void_type_node, 14, pvoid_type_node, size_type_node, integer_type_node,
3650 pvoid_type_node, pvoid_type_node, pvoid_type_node, size_type_node,
3651 integer_type_node, pvoid_type_node, pvoid_type_node, integer_type_node,
3652 integer_type_node, boolean_type_node, integer_type_node);
3653
3654 gfor_fndecl_caf_get_by_ref = gfc_build_library_function_decl_with_spec (
3655 get_identifier (PREFIX("caf_get_by_ref")), ".RWRRRRRW", void_type_node,
3656 9, pvoid_type_node, integer_type_node, pvoid_type_node, pvoid_type_node,
3657 integer_type_node, integer_type_node, boolean_type_node,
3658 boolean_type_node, pint_type);
3659
3660 gfor_fndecl_caf_send_by_ref = gfc_build_library_function_decl_with_spec (
3661 get_identifier (PREFIX("caf_send_by_ref")), ".RRRRRRRW", void_type_node,
3662 9, pvoid_type_node, integer_type_node, pvoid_type_node, pvoid_type_node,
3663 integer_type_node, integer_type_node, boolean_type_node,
3664 boolean_type_node, pint_type);
3665
3666 gfor_fndecl_caf_sendget_by_ref
3667 = gfc_build_library_function_decl_with_spec (
3668 get_identifier (PREFIX("caf_sendget_by_ref")), ".RR.RRRRRWW",
3669 void_type_node, 11, pvoid_type_node, integer_type_node,
3670 pvoid_type_node, pvoid_type_node, integer_type_node,
3671 pvoid_type_node, integer_type_node, integer_type_node,
3672 boolean_type_node, pint_type, pint_type);
5f4a118e 3673
70b5944a 3674 gfor_fndecl_caf_sync_all = gfc_build_library_function_decl_with_spec (
96b417f0 3675 get_identifier (PREFIX("caf_sync_all")), ".WW", void_type_node,
79ed4a8e 3676 3, pint_type, pchar_type_node, integer_type_node);
70b5944a 3677
71cf3ae6 3678 gfor_fndecl_caf_sync_memory = gfc_build_library_function_decl_with_spec (
3679 get_identifier (PREFIX("caf_sync_memory")), ".WW", void_type_node,
3680 3, pint_type, pchar_type_node, integer_type_node);
3681
70b5944a 3682 gfor_fndecl_caf_sync_images = gfc_build_library_function_decl_with_spec (
96b417f0 3683 get_identifier (PREFIX("caf_sync_images")), ".RRWW", void_type_node,
3684 5, integer_type_node, pint_type, pint_type,
79ed4a8e 3685 pchar_type_node, integer_type_node);
70b5944a 3686
3687 gfor_fndecl_caf_error_stop = gfc_build_library_function_decl (
3688 get_identifier (PREFIX("caf_error_stop")),
3689 void_type_node, 1, gfc_int4_type_node);
3690 /* CAF's ERROR STOP doesn't return. */
3691 TREE_THIS_VOLATILE (gfor_fndecl_caf_error_stop) = 1;
3692
3693 gfor_fndecl_caf_error_stop_str = gfc_build_library_function_decl_with_spec (
3694 get_identifier (PREFIX("caf_error_stop_str")), ".R.",
3695 void_type_node, 2, pchar_type_node, gfc_int4_type_node);
3696 /* CAF's ERROR STOP doesn't return. */
3697 TREE_THIS_VOLATILE (gfor_fndecl_caf_error_stop_str) = 1;
79ed4a8e 3698
ba4d9b7e 3699 gfor_fndecl_caf_stop_numeric = gfc_build_library_function_decl_with_spec (
65cbb21d 3700 get_identifier (PREFIX("caf_stop_numeric")), ".R.",
3701 void_type_node, 1, gfc_int4_type_node);
ba4d9b7e 3702 /* CAF's STOP doesn't return. */
3703 TREE_THIS_VOLATILE (gfor_fndecl_caf_stop_numeric) = 1;
3704
3705 gfor_fndecl_caf_stop_str = gfc_build_library_function_decl_with_spec (
65cbb21d 3706 get_identifier (PREFIX("caf_stop_str")), ".R.",
3707 void_type_node, 2, pchar_type_node, gfc_int4_type_node);
ba4d9b7e 3708 /* CAF's STOP doesn't return. */
3709 TREE_THIS_VOLATILE (gfor_fndecl_caf_stop_str) = 1;
3710
97b9ac34 3711 gfor_fndecl_caf_atomic_def = gfc_build_library_function_decl_with_spec (
3712 get_identifier (PREFIX("caf_atomic_define")), "R..RW",
3713 void_type_node, 7, pvoid_type_node, size_type_node, integer_type_node,
65cbb21d 3714 pvoid_type_node, pint_type, integer_type_node, integer_type_node);
97b9ac34 3715
3716 gfor_fndecl_caf_atomic_ref = gfc_build_library_function_decl_with_spec (
3717 get_identifier (PREFIX("caf_atomic_ref")), "R..WW",
3718 void_type_node, 7, pvoid_type_node, size_type_node, integer_type_node,
65cbb21d 3719 pvoid_type_node, pint_type, integer_type_node, integer_type_node);
97b9ac34 3720
3721 gfor_fndecl_caf_atomic_cas = gfc_build_library_function_decl_with_spec (
3722 get_identifier (PREFIX("caf_atomic_cas")), "R..WRRW",
3723 void_type_node, 9, pvoid_type_node, size_type_node, integer_type_node,
65cbb21d 3724 pvoid_type_node, pvoid_type_node, pvoid_type_node, pint_type,
97b9ac34 3725 integer_type_node, integer_type_node);
3726
3727 gfor_fndecl_caf_atomic_op = gfc_build_library_function_decl_with_spec (
3728 get_identifier (PREFIX("caf_atomic_op")), ".R..RWW",
3729 void_type_node, 9, integer_type_node, pvoid_type_node, size_type_node,
3730 integer_type_node, pvoid_type_node, pvoid_type_node, pint_type,
3731 integer_type_node, integer_type_node);
3732
498b946e 3733 gfor_fndecl_caf_lock = gfc_build_library_function_decl_with_spec (
3734 get_identifier (PREFIX("caf_lock")), "R..WWW",
3735 void_type_node, 7, pvoid_type_node, size_type_node, integer_type_node,
3736 pint_type, pint_type, pchar_type_node, integer_type_node);
3737
3738 gfor_fndecl_caf_unlock = gfc_build_library_function_decl_with_spec (
3739 get_identifier (PREFIX("caf_unlock")), "R..WW",
87550f4f 3740 void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
498b946e 3741 pint_type, pchar_type_node, integer_type_node);
3742
bd47f0bc 3743 gfor_fndecl_caf_event_post = gfc_build_library_function_decl_with_spec (
3744 get_identifier (PREFIX("caf_event_post")), "R..WW",
3745 void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
3746 pint_type, pchar_type_node, integer_type_node);
3747
3748 gfor_fndecl_caf_event_wait = gfc_build_library_function_decl_with_spec (
3749 get_identifier (PREFIX("caf_event_wait")), "R..WW",
3750 void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
3751 pint_type, pchar_type_node, integer_type_node);
3752
3753 gfor_fndecl_caf_event_query = gfc_build_library_function_decl_with_spec (
3754 get_identifier (PREFIX("caf_event_query")), "R..WW",
3755 void_type_node, 5, pvoid_type_node, size_type_node, integer_type_node,
3756 pint_type, pint_type);
3757
d9ca273e 3758 gfor_fndecl_caf_fail_image = gfc_build_library_function_decl (
3759 get_identifier (PREFIX("caf_fail_image")), void_type_node, 0);
3760 /* CAF's FAIL doesn't return. */
3761 TREE_THIS_VOLATILE (gfor_fndecl_caf_fail_image) = 1;
3762
3763 gfor_fndecl_caf_failed_images
3764 = gfc_build_library_function_decl_with_spec (
3765 get_identifier (PREFIX("caf_failed_images")), "WRR",
3766 void_type_node, 3, pvoid_type_node, ppvoid_type_node,
3767 integer_type_node);
3768
3769 gfor_fndecl_caf_image_status
3770 = gfc_build_library_function_decl_with_spec (
3771 get_identifier (PREFIX("caf_image_status")), "RR",
3772 integer_type_node, 2, integer_type_node, ppvoid_type_node);
3773
3774 gfor_fndecl_caf_stopped_images
3775 = gfc_build_library_function_decl_with_spec (
3776 get_identifier (PREFIX("caf_stopped_images")), "WRR",
3777 void_type_node, 3, pvoid_type_node, ppvoid_type_node,
3778 integer_type_node);
3779
52306a18 3780 gfor_fndecl_co_broadcast = gfc_build_library_function_decl_with_spec (
3781 get_identifier (PREFIX("caf_co_broadcast")), "W.WW",
3782 void_type_node, 5, pvoid_type_node, integer_type_node,
3783 pint_type, pchar_type_node, integer_type_node);
3784
79ed4a8e 3785 gfor_fndecl_co_max = gfc_build_library_function_decl_with_spec (
5f4a118e 3786 get_identifier (PREFIX("caf_co_max")), "W.WW",
3787 void_type_node, 6, pvoid_type_node, integer_type_node,
79ed4a8e 3788 pint_type, pchar_type_node, integer_type_node, integer_type_node);
3789
3790 gfor_fndecl_co_min = gfc_build_library_function_decl_with_spec (
5f4a118e 3791 get_identifier (PREFIX("caf_co_min")), "W.WW",
3792 void_type_node, 6, pvoid_type_node, integer_type_node,
79ed4a8e 3793 pint_type, pchar_type_node, integer_type_node, integer_type_node);
3794
e39efcef 3795 gfor_fndecl_co_reduce = gfc_build_library_function_decl_with_spec (
3796 get_identifier (PREFIX("caf_co_reduce")), "W.R.WW",
3797 void_type_node, 8, pvoid_type_node,
65cbb21d 3798 build_pointer_type (build_varargs_function_type_list (void_type_node,
e39efcef 3799 NULL_TREE)),
3800 integer_type_node, integer_type_node, pint_type, pchar_type_node,
3801 integer_type_node, integer_type_node);
3802
79ed4a8e 3803 gfor_fndecl_co_sum = gfc_build_library_function_decl_with_spec (
5f4a118e 3804 get_identifier (PREFIX("caf_co_sum")), "W.WW",
3805 void_type_node, 5, pvoid_type_node, integer_type_node,
79ed4a8e 3806 pint_type, pchar_type_node, integer_type_node);
3d2aa0e8 3807
3808 gfor_fndecl_caf_is_present = gfc_build_library_function_decl_with_spec (
3809 get_identifier (PREFIX("caf_is_present")), "RRR",
3810 integer_type_node, 3, pvoid_type_node, integer_type_node,
3811 pvoid_type_node);
70b5944a 3812 }
3813
4ee9c684 3814 gfc_build_intrinsic_function_decls ();
3815 gfc_build_intrinsic_lib_fndecls ();
3816 gfc_build_io_library_fndecls ();
3817}
3818
3819
231e961a 3820/* Evaluate the length of dummy character variables. */
4ee9c684 3821
c5faa799 3822static void
3823gfc_trans_dummy_character (gfc_symbol *sym, gfc_charlen *cl,
3824 gfc_wrapped_block *block)
4ee9c684 3825{
c5faa799 3826 stmtblock_t init;
4ee9c684 3827
b9c7fce7 3828 gfc_finish_decl (cl->backend_decl);
4ee9c684 3829
c5faa799 3830 gfc_start_block (&init);
4ee9c684 3831
3832 /* Evaluate the string length expression. */
c5faa799 3833 gfc_conv_string_length (cl, NULL, &init);
d4163395 3834
c5faa799 3835 gfc_trans_vla_type_sizes (sym, &init);
d4163395 3836
c5faa799 3837 gfc_add_init_cleanup (block, gfc_finish_block (&init), NULL_TREE);
4ee9c684 3838}
3839
3840
3841/* Allocate and cleanup an automatic character variable. */
3842
c5faa799 3843static void
3844gfc_trans_auto_character_variable (gfc_symbol * sym, gfc_wrapped_block * block)
4ee9c684 3845{
c5faa799 3846 stmtblock_t init;
4ee9c684 3847 tree decl;
4ee9c684 3848 tree tmp;
3849
22d678e8 3850 gcc_assert (sym->backend_decl);
eeebe20b 3851 gcc_assert (sym->ts.u.cl && sym->ts.u.cl->length);
4ee9c684 3852
3714c8b6 3853 gfc_init_block (&init);
4ee9c684 3854
3855 /* Evaluate the string length expression. */
c5faa799 3856 gfc_conv_string_length (sym->ts.u.cl, NULL, &init);
4ee9c684 3857
c5faa799 3858 gfc_trans_vla_type_sizes (sym, &init);
d4163395 3859
4ee9c684 3860 decl = sym->backend_decl;
3861
afcf285e 3862 /* Emit a DECL_EXPR for this variable, which will cause the
4b3a701c 3863 gimplifier to allocate storage, and all that good stuff. */
fd779e1d 3864 tmp = fold_build1_loc (input_location, DECL_EXPR, TREE_TYPE (decl), decl);
c5faa799 3865 gfc_add_expr_to_block (&init, tmp);
afcf285e 3866
c5faa799 3867 gfc_add_init_cleanup (block, gfc_finish_block (&init), NULL_TREE);
4ee9c684 3868}
3869
c8f1568f 3870/* Set the initial value of ASSIGN statement auxiliary variable explicitly. */
3871
c5faa799 3872static void
3873gfc_trans_assign_aux_var (gfc_symbol * sym, gfc_wrapped_block * block)
c8f1568f 3874{
c5faa799 3875 stmtblock_t init;
c8f1568f 3876
3877 gcc_assert (sym->backend_decl);
c5faa799 3878 gfc_start_block (&init);
c8f1568f 3879
3880 /* Set the initial value to length. See the comments in
3881 function gfc_add_assign_aux_vars in this file. */
c5faa799 3882 gfc_add_modify (&init, GFC_DECL_STRING_LEN (sym->backend_decl),
35bf1214 3883 build_int_cst (gfc_charlen_type_node, -2));
c8f1568f 3884
c5faa799 3885 gfc_add_init_cleanup (block, gfc_finish_block (&init), NULL_TREE);
c8f1568f 3886}
3887
d4163395 3888static void
3889gfc_trans_vla_one_sizepos (tree *tp, stmtblock_t *body)
3890{
3891 tree t = *tp, var, val;
3892
3893 if (t == NULL || t == error_mark_node)
3894 return;
3895 if (TREE_CONSTANT (t) || DECL_P (t))
3896 return;
3897
3898 if (TREE_CODE (t) == SAVE_EXPR)
3899 {
3900 if (SAVE_EXPR_RESOLVED_P (t))
3901 {
3902 *tp = TREE_OPERAND (t, 0);
3903 return;
3904 }
3905 val = TREE_OPERAND (t, 0);
3906 }
3907 else
3908 val = t;
3909
3910 var = gfc_create_var_np (TREE_TYPE (t), NULL);
3911 gfc_add_decl_to_function (var);
1ec957b0 3912 gfc_add_modify (body, var, unshare_expr (val));
d4163395 3913 if (TREE_CODE (t) == SAVE_EXPR)
3914 TREE_OPERAND (t, 0) = var;
3915 *tp = var;
3916}
3917
3918static void
3919gfc_trans_vla_type_sizes_1 (tree type, stmtblock_t *body)
3920{
3921 tree t;
3922
3923 if (type == NULL || type == error_mark_node)
3924 return;
3925
3926 type = TYPE_MAIN_VARIANT (type);
3927
3928 if (TREE_CODE (type) == INTEGER_TYPE)
3929 {
3930 gfc_trans_vla_one_sizepos (&TYPE_MIN_VALUE (type), body);
3931 gfc_trans_vla_one_sizepos (&TYPE_MAX_VALUE (type), body);
3932
3933 for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
3934 {
3935 TYPE_MIN_VALUE (t) = TYPE_MIN_VALUE (type);
3936 TYPE_MAX_VALUE (t) = TYPE_MAX_VALUE (type);
3937 }
3938 }
3939 else if (TREE_CODE (type) == ARRAY_TYPE)
3940 {
3941 gfc_trans_vla_type_sizes_1 (TREE_TYPE (type), body);
3942 gfc_trans_vla_type_sizes_1 (TYPE_DOMAIN (type), body);
3943 gfc_trans_vla_one_sizepos (&TYPE_SIZE (type), body);
3944 gfc_trans_vla_one_sizepos (&TYPE_SIZE_UNIT (type), body);
3945
3946 for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
3947 {
3948 TYPE_SIZE (t) = TYPE_SIZE (type);
3949 TYPE_SIZE_UNIT (t) = TYPE_SIZE_UNIT (type);
3950 }
3951 }
3952}
3953
3954/* Make sure all type sizes and array domains are either constant,
3955 or variable or parameter decls. This is a simplified variant
3956 of gimplify_type_sizes, but we can't use it here, as none of the
3957 variables in the expressions have been gimplified yet.
3958 As type sizes and domains for various variable length arrays
3959 contain VAR_DECLs that are only initialized at gfc_trans_deferred_vars
3960 time, without this routine gimplify_type_sizes in the middle-end
3961 could result in the type sizes being gimplified earlier than where
3962 those variables are initialized. */
3963
3964void
3965gfc_trans_vla_type_sizes (gfc_symbol *sym, stmtblock_t *body)
3966{
3967 tree type = TREE_TYPE (sym->backend_decl);
3968
3969 if (TREE_CODE (type) == FUNCTION_TYPE
3970 && (sym->attr.function || sym->attr.result || sym->attr.entry))
3971 {
3972 if (! current_fake_result_decl)
3973 return;
3974
3975 type = TREE_TYPE (TREE_VALUE (current_fake_result_decl));
3976 }
3977
3978 while (POINTER_TYPE_P (type))
3979 type = TREE_TYPE (type);
3980
3981 if (GFC_DESCRIPTOR_TYPE_P (type))
3982 {
3983 tree etype = GFC_TYPE_ARRAY_DATAPTR_TYPE (type);
3984
3985 while (POINTER_TYPE_P (etype))
3986 etype = TREE_TYPE (etype);
3987
3988 gfc_trans_vla_type_sizes_1 (etype, body);
3989 }
3990
3991 gfc_trans_vla_type_sizes_1 (type, body);
3992}
3993
4ee9c684 3994
f0d4969f 3995/* Initialize a derived type by building an lvalue from the symbol
a545a8f8 3996 and using trans_assignment to do the work. Set dealloc to false
3997 if no deallocation prior the assignment is needed. */
c5faa799 3998void
3999gfc_init_default_dt (gfc_symbol * sym, stmtblock_t * block, bool dealloc)
87114d2e 4000{
f0d4969f 4001 gfc_expr *e;
87114d2e 4002 tree tmp;
4003 tree present;
4004
c5faa799 4005 gcc_assert (block);
4006
f0d4969f 4007 gcc_assert (!sym->attr.allocatable);
4008 gfc_set_sym_referenced (sym);
4009 e = gfc_lval_expr_from_sym (sym);
a545a8f8 4010 tmp = gfc_trans_assignment (e, sym->value, false, dealloc);
c38054a8 4011 if (sym->attr.dummy && (sym->attr.optional
4012 || sym->ns->proc_name->attr.entry_master))
87114d2e 4013 {
f0d4969f 4014 present = gfc_conv_expr_present (sym);
2be9d8f1 4015 tmp = build3_loc (input_location, COND_EXPR, TREE_TYPE (tmp), present,
4016 tmp, build_empty_stmt (input_location));
87114d2e 4017 }
c5faa799 4018 gfc_add_expr_to_block (block, tmp);
f0d4969f 4019 gfc_free_expr (e);
87114d2e 4020}
4021
4022
8714fc76 4023/* Initialize INTENT(OUT) derived type dummies. As well as giving
4024 them their default initializer, if they do not have allocatable
293d72e0 4025 components, they have their allocatable components deallocated. */
8714fc76 4026
c5faa799 4027static void
4028init_intent_out_dt (gfc_symbol * proc_sym, gfc_wrapped_block * block)
f0d4969f 4029{
c5faa799 4030 stmtblock_t init;
f0d4969f 4031 gfc_formal_arglist *f;
8714fc76 4032 tree tmp;
5907c3ea 4033 tree present;
f0d4969f 4034
c5faa799 4035 gfc_init_block (&init);
6777213b 4036 for (f = gfc_sym_get_dummy_args (proc_sym); f; f = f->next)
f0d4969f 4037 if (f->sym && f->sym->attr.intent == INTENT_OUT
c49db15e 4038 && !f->sym->attr.pointer
4039 && f->sym->ts.type == BT_DERIVED)
8714fc76 4040 {
942ba353 4041 tmp = NULL_TREE;
4042
4043 /* Note: Allocatables are excluded as they are already handled
4044 by the caller. */
4045 if (!f->sym->attr.allocatable
4046 && gfc_is_finalizable (f->sym->ts.u.derived, NULL))
8714fc76 4047 {
942ba353 4048 stmtblock_t block;
4049 gfc_expr *e;
4050
4051 gfc_init_block (&block);
4052 f->sym->attr.referenced = 1;
4053 e = gfc_lval_expr_from_sym (f->sym);
4054 gfc_add_finalizer_call (&block, e);
4055 gfc_free_expr (e);
4056 tmp = gfc_finish_block (&block);
4057 }
5907c3ea 4058
942ba353 4059 if (tmp == NULL_TREE && !f->sym->attr.allocatable
4060 && f->sym->ts.u.derived->attr.alloc_comp && !f->sym->value)
4061 tmp = gfc_deallocate_alloc_comp (f->sym->ts.u.derived,
4062 f->sym->backend_decl,
4063 f->sym->as ? f->sym->as->rank : 0);
5907c3ea 4064
942ba353 4065 if (tmp != NULL_TREE && (f->sym->attr.optional
4066 || f->sym->ns->proc_name->attr.entry_master))
4067 {
4068 present = gfc_conv_expr_present (f->sym);
4069 tmp = build3_loc (input_location, COND_EXPR, TREE_TYPE (tmp),
4070 present, tmp, build_empty_stmt (input_location));
8714fc76 4071 }
942ba353 4072
4073 if (tmp != NULL_TREE)
4074 gfc_add_expr_to_block (&init, tmp);
4075 else if (f->sym->value && !f->sym->attr.allocatable)
c5faa799 4076 gfc_init_default_dt (f->sym, &init, true);
8714fc76 4077 }
c56d57d6 4078 else if (f->sym && f->sym->attr.intent == INTENT_OUT
4079 && f->sym->ts.type == BT_CLASS
4080 && !CLASS_DATA (f->sym)->attr.class_pointer
942ba353 4081 && !CLASS_DATA (f->sym)->attr.allocatable)
c56d57d6 4082 {
942ba353 4083 stmtblock_t block;
4084 gfc_expr *e;
4085
4086 gfc_init_block (&block);
4087 f->sym->attr.referenced = 1;
4088 e = gfc_lval_expr_from_sym (f->sym);
4089 gfc_add_finalizer_call (&block, e);
4090 gfc_free_expr (e);
4091 tmp = gfc_finish_block (&block);
c56d57d6 4092
4093 if (f->sym->attr.optional || f->sym->ns->proc_name->attr.entry_master)
4094 {
4095 present = gfc_conv_expr_present (f->sym);
4096 tmp = build3_loc (input_location, COND_EXPR, TREE_TYPE (tmp),
4097 present, tmp,
4098 build_empty_stmt (input_location));
4099 }
4100
4101 gfc_add_expr_to_block (&init, tmp);
4102 }
f0d4969f 4103
c5faa799 4104 gfc_add_init_cleanup (block, gfc_finish_block (&init), NULL_TREE);
f0d4969f 4105}
4106
87114d2e 4107
b345a09f 4108/* Helper function to manage deferred string lengths. */
4109
4110static tree
4111gfc_null_and_pass_deferred_len (gfc_symbol *sym, stmtblock_t *init,
4112 locus *loc)
4113{
4114 tree tmp;
4115
4116 /* Character length passed by reference. */
4117 tmp = sym->ts.u.cl->passed_length;
4118 tmp = build_fold_indirect_ref_loc (input_location, tmp);
4119 tmp = fold_convert (gfc_charlen_type_node, tmp);
4120
4121 if (!sym->attr.dummy || sym->attr.intent == INTENT_OUT)
4122 /* Zero the string length when entering the scope. */
4123 gfc_add_modify (init, sym->ts.u.cl->backend_decl,
4124 build_int_cst (gfc_charlen_type_node, 0));
4125 else
4126 {
4127 tree tmp2;
4128
4129 tmp2 = fold_build2_loc (input_location, MODIFY_EXPR,
4130 gfc_charlen_type_node,
4131 sym->ts.u.cl->backend_decl, tmp);
4132 if (sym->attr.optional)
4133 {
4134 tree present = gfc_conv_expr_present (sym);
4135 tmp2 = build3_loc (input_location, COND_EXPR,
4136 void_type_node, present, tmp2,
4137 build_empty_stmt (input_location));
4138 }
4139 gfc_add_expr_to_block (init, tmp2);
4140 }
4141
4142 gfc_restore_backend_locus (loc);
4143
4144 /* Pass the final character length back. */
4145 if (sym->attr.intent != INTENT_IN)
4146 {
4147 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
4148 gfc_charlen_type_node, tmp,
4149 sym->ts.u.cl->backend_decl);
4150 if (sym->attr.optional)
4151 {
4152 tree present = gfc_conv_expr_present (sym);
4153 tmp = build3_loc (input_location, COND_EXPR,
4154 void_type_node, present, tmp,
4155 build_empty_stmt (input_location));
4156 }
4157 }
4158 else
4159 tmp = NULL_TREE;
4160
4161 return tmp;
4162}
4163
9ead5324 4164
4165/* Get the result expression for a procedure. */
4166
4167static tree
4168get_proc_result (gfc_symbol* sym)
4169{
4170 if (sym->attr.subroutine || sym == sym->result)
4171 {
4172 if (current_fake_result_decl != NULL)
4173 return TREE_VALUE (current_fake_result_decl);
4174
4175 return NULL_TREE;
4176 }
4177
4178 return sym->result->backend_decl;
4179}
4180
4181
4ee9c684 4182/* Generate function entry and exit code, and add it to the function body.
4183 This includes:
f888a3fb 4184 Allocation and initialization of array variables.
4ee9c684 4185 Allocation of character string variables.
c8f1568f 4186 Initialization and possibly repacking of dummy arrays.
0a96a7cc 4187 Initialization of ASSIGN statement auxiliary variable.
8f3f9eab 4188 Initialization of ASSOCIATE names.
0a96a7cc 4189 Automatic deallocation. */
4ee9c684 4190
89ac8ba1 4191void
4192gfc_trans_deferred_vars (gfc_symbol * proc_sym, gfc_wrapped_block * block)
4ee9c684 4193{
4194 locus loc;
4195 gfc_symbol *sym;
d4163395 4196 gfc_formal_arglist *f;
c5faa799 4197 stmtblock_t tmpblock;
25dd7350 4198 bool seen_trans_deferred_array = false;
9d958d5b 4199 bool is_pdt_type = false;
617125a6 4200 tree tmp = NULL;
4201 gfc_expr *e;
4202 gfc_se se;
4203 stmtblock_t init;
4ee9c684 4204
4205 /* Deal with implicit return variables. Explicit return variables will
4206 already have been added. */
4207 if (gfc_return_by_reference (proc_sym) && proc_sym->result == proc_sym)
4208 {
4209 if (!current_fake_result_decl)
4210 {
c6871095 4211 gfc_entry_list *el = NULL;
4212 if (proc_sym->attr.entry_master)
4213 {
4214 for (el = proc_sym->ns->entries; el; el = el->next)
4215 if (el->sym != el->sym->result)
4216 break;
4217 }
fa7b6574 4218 /* TODO: move to the appropriate place in resolve.c. */
8b72061f 4219 if (warn_return_type > 0 && el == NULL)
4166acc7 4220 gfc_warning (OPT_Wreturn_type,
4221 "Return value of function %qs at %L not set",
fa7b6574 4222 proc_sym->name, &proc_sym->declared_at);
4ee9c684 4223 }
c6871095 4224 else if (proc_sym->as)
4ee9c684 4225 {
d4163395 4226 tree result = TREE_VALUE (current_fake_result_decl);
9da84a54 4227 gfc_save_backend_locus (&loc);
4228 gfc_set_backend_locus (&proc_sym->declared_at);
89ac8ba1 4229 gfc_trans_dummy_array_bias (proc_sym, result, block);
10b07432 4230
4231 /* An automatic character length, pointer array result. */
4232 if (proc_sym->ts.type == BT_CHARACTER
fe732a9b 4233 && VAR_P (proc_sym->ts.u.cl->backend_decl))
b345a09f 4234 {
4235 tmp = NULL;
4236 if (proc_sym->ts.deferred)
4237 {
b345a09f 4238 gfc_start_block (&init);
4239 tmp = gfc_null_and_pass_deferred_len (proc_sym, &init, &loc);
4240 gfc_add_init_cleanup (block, gfc_finish_block (&init), tmp);
4241 }
4242 else
4243 gfc_trans_dummy_character (proc_sym, proc_sym->ts.u.cl, block);
4244 }
4ee9c684 4245 }
4246 else if (proc_sym->ts.type == BT_CHARACTER)
4247 {
617125a6 4248 if (proc_sym->ts.deferred)
4249 {
4250 tmp = NULL;
da2c4122 4251 gfc_save_backend_locus (&loc);
4252 gfc_set_backend_locus (&proc_sym->declared_at);
617125a6 4253 gfc_start_block (&init);
4254 /* Zero the string length on entry. */
4255 gfc_add_modify (&init, proc_sym->ts.u.cl->backend_decl,
4256 build_int_cst (gfc_charlen_type_node, 0));
4257 /* Null the pointer. */
4258 e = gfc_lval_expr_from_sym (proc_sym);
4259 gfc_init_se (&se, NULL);
4260 se.want_pointer = 1;
4261 gfc_conv_expr (&se, e);
4262 gfc_free_expr (e);
4263 tmp = se.expr;
4264 gfc_add_modify (&init, tmp,
4265 fold_convert (TREE_TYPE (se.expr),
4266 null_pointer_node));
da2c4122 4267 gfc_restore_backend_locus (&loc);
617125a6 4268
4269 /* Pass back the string length on exit. */
ddcfeaf1 4270 tmp = proc_sym->ts.u.cl->backend_decl;
b345a09f 4271 if (TREE_CODE (tmp) != INDIRECT_REF
4272 && proc_sym->ts.u.cl->passed_length)
ddcfeaf1 4273 {
a4731200 4274 tmp = proc_sym->ts.u.cl->passed_length;
4275 tmp = build_fold_indirect_ref_loc (input_location, tmp);
4276 tmp = fold_convert (gfc_charlen_type_node, tmp);
4277 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
4278 gfc_charlen_type_node, tmp,
4279 proc_sym->ts.u.cl->backend_decl);
ddcfeaf1 4280 }
4281 else
4282 tmp = NULL_TREE;
4283
617125a6 4284 gfc_add_init_cleanup (block, gfc_finish_block (&init), tmp);
4285 }
fe732a9b 4286 else if (VAR_P (proc_sym->ts.u.cl->backend_decl))
89ac8ba1 4287 gfc_trans_dummy_character (proc_sym, proc_sym->ts.u.cl, block);
4ee9c684 4288 }
4289 else
829d7a08 4290 gcc_assert (flag_f2c && proc_sym->ts.type == BT_COMPLEX);
4ee9c684 4291 }
9ead5324 4292 else if (proc_sym == proc_sym->result && IS_CLASS_ARRAY (proc_sym))
4293 {
4294 /* Nullify explicit return class arrays on entry. */
4295 tree type;
4296 tmp = get_proc_result (proc_sym);
4297 if (tmp && GFC_CLASS_TYPE_P (TREE_TYPE (tmp)))
4298 {
4299 gfc_start_block (&init);
4300 tmp = gfc_class_data_get (tmp);
4301 type = TREE_TYPE (gfc_conv_descriptor_data_get (tmp));
4302 gfc_conv_descriptor_data_set (&init, tmp, build_int_cst (type, 0));
4303 gfc_add_init_cleanup (block, gfc_finish_block (&init), NULL_TREE);
4304 }
4305 }
4306
4ee9c684 4307
87114d2e 4308 /* Initialize the INTENT(OUT) derived type dummy arguments. This
4309 should be done here so that the offsets and lbounds of arrays
4310 are available. */
da2c4122 4311 gfc_save_backend_locus (&loc);
4312 gfc_set_backend_locus (&proc_sym->declared_at);
89ac8ba1 4313 init_intent_out_dt (proc_sym, block);
da2c4122 4314 gfc_restore_backend_locus (&loc);
87114d2e 4315
4ee9c684 4316 for (sym = proc_sym->tlink; sym != proc_sym; sym = sym->tlink)
4317 {
6b3ceb4e 4318 bool alloc_comp_or_fini = (sym->ts.type == BT_DERIVED)
4319 && (sym->ts.u.derived->attr.alloc_comp
4320 || gfc_is_finalizable (sym->ts.u.derived,
4321 NULL));
8f3f9eab 4322 if (sym->assoc)
3c82e013 4323 continue;
4324
9d958d5b 4325 if (sym->ts.type == BT_DERIVED
4326 && sym->ts.u.derived
4327 && sym->ts.u.derived->attr.pdt_type)
4328 {
4329 is_pdt_type = true;
4330 gfc_init_block (&tmpblock);
4331 if (!(sym->attr.dummy
4332 || sym->attr.pointer
4333 || sym->attr.allocatable))
4334 {
4335 tmp = gfc_allocate_pdt_comp (sym->ts.u.derived,
4336 sym->backend_decl,
4337 sym->as ? sym->as->rank : 0,
4338 sym->param_list);
4339 gfc_add_expr_to_block (&tmpblock, tmp);
4340 tmp = gfc_deallocate_pdt_comp (sym->ts.u.derived,
4341 sym->backend_decl,
4342 sym->as ? sym->as->rank : 0);
4343 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock), tmp);
4344 }
4345 else if (sym->attr.dummy)
4346 {
4347 tmp = gfc_check_pdt_dummy (sym->ts.u.derived,
4348 sym->backend_decl,
4349 sym->as ? sym->as->rank : 0,
4350 sym->param_list);
4351 gfc_add_expr_to_block (&tmpblock, tmp);
4352 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock), NULL);
4353 }
4354 }
4355 else if (sym->ts.type == BT_CLASS
4356 && CLASS_DATA (sym)->ts.u.derived
4357 && CLASS_DATA (sym)->ts.u.derived->attr.pdt_type)
4358 {
4359 gfc_component *data = CLASS_DATA (sym);
4360 is_pdt_type = true;
4361 gfc_init_block (&tmpblock);
4362 if (!(sym->attr.dummy
4363 || CLASS_DATA (sym)->attr.pointer
4364 || CLASS_DATA (sym)->attr.allocatable))
4365 {
4366 tmp = gfc_class_data_get (sym->backend_decl);
4367 tmp = gfc_allocate_pdt_comp (data->ts.u.derived, tmp,
4368 data->as ? data->as->rank : 0,
4369 sym->param_list);
4370 gfc_add_expr_to_block (&tmpblock, tmp);
4371 tmp = gfc_class_data_get (sym->backend_decl);
4372 tmp = gfc_deallocate_pdt_comp (data->ts.u.derived, tmp,
4373 data->as ? data->as->rank : 0);
4374 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock), tmp);
4375 }
4376 else if (sym->attr.dummy)
4377 {
4378 tmp = gfc_class_data_get (sym->backend_decl);
4379 tmp = gfc_check_pdt_dummy (data->ts.u.derived, tmp,
4380 data->as ? data->as->rank : 0,
4381 sym->param_list);
4382 gfc_add_expr_to_block (&tmpblock, tmp);
4383 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock), NULL);
4384 }
4385 }
4386
47e6a59a 4387 if (sym->attr.pointer && sym->attr.dimension
0a5fd921 4388 && sym->attr.save == SAVE_NONE
47e6a59a 4389 && !sym->attr.use_assoc
4390 && !sym->attr.host_assoc
4391 && !sym->attr.dummy
4392 && GFC_DESCRIPTOR_TYPE_P (TREE_TYPE (sym->backend_decl)))
a56d63bc 4393 {
4394 gfc_init_block (&tmpblock);
47e6a59a 4395 gfc_conv_descriptor_span_set (&tmpblock, sym->backend_decl,
4396 build_int_cst (gfc_array_index_type, 0));
a56d63bc 4397 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock),
4398 NULL_TREE);
4399 }
4400
85ae3cab 4401 if (sym->ts.type == BT_CLASS
eb106faf 4402 && (sym->attr.save || flag_max_stack_var_size == 0)
fb139b21 4403 && CLASS_DATA (sym)->attr.allocatable)
4404 {
4405 tree vptr;
4406
4407 if (UNLIMITED_POLY (sym))
4408 vptr = null_pointer_node;
4409 else
4410 {
4411 gfc_symbol *vsym;
4412 vsym = gfc_find_derived_vtab (sym->ts.u.derived);
4413 vptr = gfc_get_symbol_decl (vsym);
4414 vptr = gfc_build_addr_expr (NULL, vptr);
4415 }
4416
4417 if (CLASS_DATA (sym)->attr.dimension
4418 || (CLASS_DATA (sym)->attr.codimension
4fe73152 4419 && flag_coarray != GFC_FCOARRAY_LIB))
fb139b21 4420 {
4421 tmp = gfc_class_data_get (sym->backend_decl);
4422 tmp = gfc_build_null_descriptor (TREE_TYPE (tmp));
4423 }
4424 else
4425 tmp = null_pointer_node;
4426
4427 DECL_INITIAL (sym->backend_decl)
4428 = gfc_class_set_static_fields (sym->backend_decl, vptr, tmp);
4429 TREE_CONSTANT (DECL_INITIAL (sym->backend_decl)) = 1;
4430 }
b345a09f 4431 else if ((sym->attr.dimension || sym->attr.codimension
4432 || (IS_CLASS_ARRAY (sym) && !CLASS_DATA (sym)->attr.allocatable)))
4ee9c684 4433 {
c6793847 4434 bool is_classarray = IS_CLASS_ARRAY (sym);
4435 symbol_attribute *array_attr;
4436 gfc_array_spec *as;
b345a09f 4437 array_type type_of_array;
c6793847 4438
4439 array_attr = is_classarray ? &CLASS_DATA (sym)->attr : &sym->attr;
4440 as = is_classarray ? CLASS_DATA (sym)->as : sym->as;
4441 /* Assumed-size Cray pointees need to be treated as AS_EXPLICIT. */
b345a09f 4442 type_of_array = as->type;
4443 if (type_of_array == AS_ASSUMED_SIZE && as->cp_was_assumed)
4444 type_of_array = AS_EXPLICIT;
4445 switch (type_of_array)
4ee9c684 4446 {
4447 case AS_EXPLICIT:
4448 if (sym->attr.dummy || sym->attr.result)
89ac8ba1 4449 gfc_trans_dummy_array_bias (sym, sym->backend_decl, block);
c6793847 4450 /* Allocatable and pointer arrays need to processed
4451 explicitly. */
4452 else if ((sym->ts.type != BT_CLASS && sym->attr.pointer)
4453 || (sym->ts.type == BT_CLASS
4454 && CLASS_DATA (sym)->attr.class_pointer)
4455 || array_attr->allocatable)
4ee9c684 4456 {
4457 if (TREE_STATIC (sym->backend_decl))
da2c4122 4458 {
4459 gfc_save_backend_locus (&loc);
4460 gfc_set_backend_locus (&sym->declared_at);
4461 gfc_trans_static_array_pointer (sym);
4462 gfc_restore_backend_locus (&loc);
4463 }
4ee9c684 4464 else
25dd7350 4465 {
4466 seen_trans_deferred_array = true;
89ac8ba1 4467 gfc_trans_deferred_array (sym, block);
25dd7350 4468 }
4ee9c684 4469 }
c6793847 4470 else if (sym->attr.codimension
4471 && TREE_STATIC (sym->backend_decl))
7c7db7f6 4472 {
4473 gfc_init_block (&tmpblock);
4474 gfc_trans_array_cobounds (TREE_TYPE (sym->backend_decl),
4475 &tmpblock, sym);
4476 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock),
4477 NULL_TREE);
4478 continue;
4479 }
197423f5 4480 else
4ee9c684 4481 {
da2c4122 4482 gfc_save_backend_locus (&loc);
4483 gfc_set_backend_locus (&sym->declared_at);
4484
6b3ceb4e 4485 if (alloc_comp_or_fini)
25dd7350 4486 {
4487 seen_trans_deferred_array = true;
89ac8ba1 4488 gfc_trans_deferred_array (sym, block);
25dd7350 4489 }
f0d4969f 4490 else if (sym->ts.type == BT_DERIVED
4491 && sym->value
4492 && !sym->attr.data
4493 && sym->attr.save == SAVE_NONE)
c5faa799 4494 {
4495 gfc_start_block (&tmpblock);
4496 gfc_init_default_dt (sym, &tmpblock, false);
89ac8ba1 4497 gfc_add_init_cleanup (block,
c5faa799 4498 gfc_finish_block (&tmpblock),
4499 NULL_TREE);
4500 }
25dd7350 4501
c5faa799 4502 gfc_trans_auto_array_allocation (sym->backend_decl,
89ac8ba1 4503 sym, block);
4671339c 4504 gfc_restore_backend_locus (&loc);
4ee9c684 4505 }
4506 break;
4507
4508 case AS_ASSUMED_SIZE:
4509 /* Must be a dummy parameter. */
c6793847 4510 gcc_assert (sym->attr.dummy || as->cp_was_assumed);
4ee9c684 4511
4512 /* We should always pass assumed size arrays the g77 way. */
452695a8 4513 if (sym->attr.dummy)
89ac8ba1 4514 gfc_trans_g77_array (sym, block);
c5faa799 4515 break;
4ee9c684 4516
4517 case AS_ASSUMED_SHAPE:
4518 /* Must be a dummy parameter. */
22d678e8 4519 gcc_assert (sym->attr.dummy);
4ee9c684 4520
89ac8ba1 4521 gfc_trans_dummy_array_bias (sym, sym->backend_decl, block);
4ee9c684 4522 break;
4523
f00f6dd6 4524 case AS_ASSUMED_RANK:
4ee9c684 4525 case AS_DEFERRED:
25dd7350 4526 seen_trans_deferred_array = true;
89ac8ba1 4527 gfc_trans_deferred_array (sym, block);
b345a09f 4528 if (sym->ts.type == BT_CHARACTER && sym->ts.deferred
4529 && sym->attr.result)
4530 {
4531 gfc_start_block (&init);
4532 gfc_save_backend_locus (&loc);
4533 gfc_set_backend_locus (&sym->declared_at);
4534 tmp = gfc_null_and_pass_deferred_len (sym, &init, &loc);
4535 gfc_add_init_cleanup (block, gfc_finish_block (&init), tmp);
4536 }
4ee9c684 4537 break;
4538
4539 default:
22d678e8 4540 gcc_unreachable ();
4ee9c684 4541 }
6b3ceb4e 4542 if (alloc_comp_or_fini && !seen_trans_deferred_array)
89ac8ba1 4543 gfc_trans_deferred_array (sym, block);
4ee9c684 4544 }
fd23cc08 4545 else if ((!sym->attr.dummy || sym->ts.deferred)
4546 && (sym->ts.type == BT_CLASS
3a19c063 4547 && CLASS_DATA (sym)->attr.class_pointer))
2930c007 4548 continue;
617125a6 4549 else if ((!sym->attr.dummy || sym->ts.deferred)
456dd7d6 4550 && (sym->attr.allocatable
b345a09f 4551 || (sym->attr.pointer && sym->attr.result)
456dd7d6 4552 || (sym->ts.type == BT_CLASS
4553 && CLASS_DATA (sym)->attr.allocatable)))
0a96a7cc 4554 {
eb106faf 4555 if (!sym->attr.save && flag_max_stack_var_size != 0)
908e9973 4556 {
d0d776fb 4557 tree descriptor = NULL_TREE;
4558
da2c4122 4559 gfc_save_backend_locus (&loc);
4560 gfc_set_backend_locus (&sym->declared_at);
c5faa799 4561 gfc_start_block (&init);
617125a6 4562
b345a09f 4563 if (!sym->attr.pointer)
617125a6 4564 {
b345a09f 4565 /* Nullify and automatic deallocation of allocatable
4566 scalars. */
4567 e = gfc_lval_expr_from_sym (sym);
4568 if (sym->ts.type == BT_CLASS)
4569 gfc_add_data_component (e);
4570
4571 gfc_init_se (&se, NULL);
4572 if (sym->ts.type != BT_CLASS
4573 || sym->ts.u.derived->attr.dimension
4574 || sym->ts.u.derived->attr.codimension)
883d6776 4575 {
b345a09f 4576 se.want_pointer = 1;
4577 gfc_conv_expr (&se, e);
4578 }
4579 else if (sym->ts.type == BT_CLASS
4580 && !CLASS_DATA (sym)->attr.dimension
4581 && !CLASS_DATA (sym)->attr.codimension)
4582 {
4583 se.want_pointer = 1;
4584 gfc_conv_expr (&se, e);
883d6776 4585 }
617125a6 4586 else
883d6776 4587 {
b345a09f 4588 se.descriptor_only = 1;
4589 gfc_conv_expr (&se, e);
4590 descriptor = se.expr;
4591 se.expr = gfc_conv_descriptor_data_addr (se.expr);
4592 se.expr = build_fold_indirect_ref_loc (input_location, se.expr);
883d6776 4593 }
b345a09f 4594 gfc_free_expr (e);
617125a6 4595
b345a09f 4596 if (!sym->attr.dummy || sym->attr.intent == INTENT_OUT)
883d6776 4597 {
b345a09f 4598 /* Nullify when entering the scope. */
883d6776 4599 tmp = fold_build2_loc (input_location, MODIFY_EXPR,
b345a09f 4600 TREE_TYPE (se.expr), se.expr,
4601 fold_convert (TREE_TYPE (se.expr),
4602 null_pointer_node));
883d6776 4603 if (sym->attr.optional)
4604 {
4605 tree present = gfc_conv_expr_present (sym);
4606 tmp = build3_loc (input_location, COND_EXPR,
4607 void_type_node, present, tmp,
4608 build_empty_stmt (input_location));
4609 }
b345a09f 4610 gfc_add_expr_to_block (&init, tmp);
883d6776 4611 }
617125a6 4612 }
b345a09f 4613
4614 if ((sym->attr.dummy || sym->attr.result)
4615 && sym->ts.type == BT_CHARACTER
4616 && sym->ts.deferred
4617 && sym->ts.u.cl->passed_length)
4618 tmp = gfc_null_and_pass_deferred_len (sym, &init, &loc);
da2c4122 4619 else
8c089b5c 4620 {
4621 gfc_restore_backend_locus (&loc);
4622 tmp = NULL_TREE;
4623 }
908e9973 4624
4625 /* Deallocate when leaving the scope. Nullifying is not
4626 needed. */
b345a09f 4627 if (!sym->attr.result && !sym->attr.dummy && !sym->attr.pointer
afb69dbf 4628 && !sym->ns->proc_name->attr.is_main_program)
d0d776fb 4629 {
4630 if (sym->ts.type == BT_CLASS
4631 && CLASS_DATA (sym)->attr.codimension)
4632 tmp = gfc_deallocate_with_status (descriptor, NULL_TREE,
4633 NULL_TREE, NULL_TREE,
4634 NULL_TREE, true, NULL,
3d2aa0e8 4635 GFC_CAF_COARRAY_ANALYZE);
d0d776fb 4636 else
c23adf93 4637 {
4638 gfc_expr *expr = gfc_lval_expr_from_sym (sym);
3d2aa0e8 4639 tmp = gfc_deallocate_scalar_with_status (se.expr,
4640 NULL_TREE,
4641 NULL_TREE,
4642 true, expr,
4643 sym->ts);
c23adf93 4644 gfc_free_expr (expr);
4645 }
d0d776fb 4646 }
b345a09f 4647
afc44c79 4648 if (sym->ts.type == BT_CLASS)
4649 {
4650 /* Initialize _vptr to declared type. */
a90fe829 4651 gfc_symbol *vtab;
afc44c79 4652 tree rhs;
da2c4122 4653
4654 gfc_save_backend_locus (&loc);
4655 gfc_set_backend_locus (&sym->declared_at);
afc44c79 4656 e = gfc_lval_expr_from_sym (sym);
4657 gfc_add_vptr_component (e);
4658 gfc_init_se (&se, NULL);
4659 se.want_pointer = 1;
4660 gfc_conv_expr (&se, e);
4661 gfc_free_expr (e);
a90fe829 4662 if (UNLIMITED_POLY (sym))
4663 rhs = build_int_cst (TREE_TYPE (se.expr), 0);
4664 else
4665 {
4666 vtab = gfc_find_derived_vtab (sym->ts.u.derived);
4667 rhs = gfc_build_addr_expr (TREE_TYPE (se.expr),
4668 gfc_get_symbol_decl (vtab));
4669 }
afc44c79 4670 gfc_add_modify (&init, se.expr, rhs);
da2c4122 4671 gfc_restore_backend_locus (&loc);
afc44c79 4672 }
4673
89ac8ba1 4674 gfc_add_init_cleanup (block, gfc_finish_block (&init), tmp);
908e9973 4675 }
0a96a7cc 4676 }
617125a6 4677 else if (sym->ts.type == BT_CHARACTER && sym->ts.deferred)
4678 {
4679 tree tmp = NULL;
4680 stmtblock_t init;
4681
4682 /* If we get to here, all that should be left are pointers. */
4683 gcc_assert (sym->attr.pointer);
4684
4685 if (sym->attr.dummy)
4686 {
4687 gfc_start_block (&init);
b345a09f 4688 gfc_save_backend_locus (&loc);
4689 gfc_set_backend_locus (&sym->declared_at);
4690 tmp = gfc_null_and_pass_deferred_len (sym, &init, &loc);
617125a6 4691 gfc_add_init_cleanup (block, gfc_finish_block (&init), tmp);
4692 }
4693 }
3e715c81 4694 else if (sym->ts.deferred)
4695 gfc_fatal_error ("Deferred type parameter not yet supported");
6b3ceb4e 4696 else if (alloc_comp_or_fini)
89ac8ba1 4697 gfc_trans_deferred_array (sym, block);
4ee9c684 4698 else if (sym->ts.type == BT_CHARACTER)
4699 {
4671339c 4700 gfc_save_backend_locus (&loc);
4ee9c684 4701 gfc_set_backend_locus (&sym->declared_at);
4702 if (sym->attr.dummy || sym->attr.result)
89ac8ba1 4703 gfc_trans_dummy_character (sym, sym->ts.u.cl, block);
4ee9c684 4704 else
89ac8ba1 4705 gfc_trans_auto_character_variable (sym, block);
4671339c 4706 gfc_restore_backend_locus (&loc);
4ee9c684 4707 }
c8f1568f 4708 else if (sym->attr.assign)
4709 {
4671339c 4710 gfc_save_backend_locus (&loc);
c8f1568f 4711 gfc_set_backend_locus (&sym->declared_at);
89ac8ba1 4712 gfc_trans_assign_aux_var (sym, block);
4671339c 4713 gfc_restore_backend_locus (&loc);
c8f1568f 4714 }
f0d4969f 4715 else if (sym->ts.type == BT_DERIVED
4716 && sym->value
4717 && !sym->attr.data
4718 && sym->attr.save == SAVE_NONE)
c5faa799 4719 {
4720 gfc_start_block (&tmpblock);
4721 gfc_init_default_dt (sym, &tmpblock, false);
89ac8ba1 4722 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock),
c5faa799 4723 NULL_TREE);
4724 }
9d958d5b 4725 else if (!(UNLIMITED_POLY(sym)) && !is_pdt_type)
22d678e8 4726 gcc_unreachable ();
4ee9c684 4727 }
4728
c5faa799 4729 gfc_init_block (&tmpblock);
d4163395 4730
6777213b 4731 for (f = gfc_sym_get_dummy_args (proc_sym); f; f = f->next)
1e853e89 4732 {
4733 if (f->sym && f->sym->tlink == NULL && f->sym->ts.type == BT_CHARACTER)
4734 {
eeebe20b 4735 gcc_assert (f->sym->ts.u.cl->backend_decl != NULL);
4736 if (TREE_CODE (f->sym->ts.u.cl->backend_decl) == PARM_DECL)
c5faa799 4737 gfc_trans_vla_type_sizes (f->sym, &tmpblock);
1e853e89 4738 }
1e853e89 4739 }
d4163395 4740
4741 if (gfc_return_by_reference (proc_sym) && proc_sym->ts.type == BT_CHARACTER
4742 && current_fake_result_decl != NULL)
4743 {
eeebe20b 4744 gcc_assert (proc_sym->ts.u.cl->backend_decl != NULL);
4745 if (TREE_CODE (proc_sym->ts.u.cl->backend_decl) == PARM_DECL)
c5faa799 4746 gfc_trans_vla_type_sizes (proc_sym, &tmpblock);
d4163395 4747 }
4748
89ac8ba1 4749 gfc_add_init_cleanup (block, gfc_finish_block (&tmpblock), NULL_TREE);
4ee9c684 4750}
4751
b345a09f 4752
b594087e 4753struct module_hasher : ggc_ptr_hash<module_htab_entry>
df4d540f 4754{
2ef51f0e 4755 typedef const char *compare_type;
df4d540f 4756
2ef51f0e 4757 static hashval_t hash (module_htab_entry *s) { return htab_hash_string (s); }
4758 static bool
4759 equal (module_htab_entry *a, const char *b)
4760 {
4761 return !strcmp (a->name, b);
4762 }
4763};
4764
4765static GTY (()) hash_table<module_hasher> *module_htab;
df4d540f 4766
4767/* Hash and equality functions for module_htab's decls. */
4768
2ef51f0e 4769hashval_t
4770module_decl_hasher::hash (tree t)
df4d540f 4771{
df4d540f 4772 const_tree n = DECL_NAME (t);
4773 if (n == NULL_TREE)
4774 n = TYPE_NAME (TREE_TYPE (t));
8f1e8e0e 4775 return htab_hash_string (IDENTIFIER_POINTER (n));
df4d540f 4776}
4777
2ef51f0e 4778bool
4779module_decl_hasher::equal (tree t1, const char *x2)
df4d540f 4780{
df4d540f 4781 const_tree n1 = DECL_NAME (t1);
4782 if (n1 == NULL_TREE)
4783 n1 = TYPE_NAME (TREE_TYPE (t1));
2ef51f0e 4784 return strcmp (IDENTIFIER_POINTER (n1), x2) == 0;
df4d540f 4785}
4786
4787struct module_htab_entry *
4788gfc_find_module (const char *name)
4789{
df4d540f 4790 if (! module_htab)
2ef51f0e 4791 module_htab = hash_table<module_hasher>::create_ggc (10);
df4d540f 4792
2ef51f0e 4793 module_htab_entry **slot
4794 = module_htab->find_slot_with_hash (name, htab_hash_string (name), INSERT);
df4d540f 4795 if (*slot == NULL)
4796 {
25a27413 4797 module_htab_entry *entry = ggc_cleared_alloc<module_htab_entry> ();
df4d540f 4798
dc326dc0 4799 entry->name = gfc_get_string ("%s", name);
2ef51f0e 4800 entry->decls = hash_table<module_decl_hasher>::create_ggc (10);
4801 *slot = entry;
df4d540f 4802 }
2ef51f0e 4803 return *slot;
df4d540f 4804}
4805
4806void
4807gfc_module_add_decl (struct module_htab_entry *entry, tree decl)
4808{
df4d540f 4809 const char *name;
4810
4811 if (DECL_NAME (decl))
4812 name = IDENTIFIER_POINTER (DECL_NAME (decl));
4813 else
4814 {
4815 gcc_assert (TREE_CODE (decl) == TYPE_DECL);
4816 name = IDENTIFIER_POINTER (TYPE_NAME (TREE_TYPE (decl)));
4817 }
2ef51f0e 4818 tree *slot
4819 = entry->decls->find_slot_with_hash (name, htab_hash_string (name),
4820 INSERT);
df4d540f 4821 if (*slot == NULL)
2ef51f0e 4822 *slot = decl;
df4d540f 4823}
4824
c40a5c1b 4825
4826/* Generate debugging symbols for namelists. This function must come after
4827 generate_local_decl to ensure that the variables in the namelist are
4828 already declared. */
4829
4830static tree
4831generate_namelist_decl (gfc_symbol * sym)
4832{
4833 gfc_namelist *nml;
4834 tree decl;
4835 vec<constructor_elt, va_gc> *nml_decls = NULL;
4836
4837 gcc_assert (sym->attr.flavor == FL_NAMELIST);
4838 for (nml = sym->namelist; nml; nml = nml->next)
4839 {
4840 if (nml->sym->backend_decl == NULL_TREE)
4841 {
4842 nml->sym->attr.referenced = 1;
4843 nml->sym->backend_decl = gfc_get_symbol_decl (nml->sym);
4844 }
0a32260c 4845 DECL_IGNORED_P (nml->sym->backend_decl) = 0;
c40a5c1b 4846 CONSTRUCTOR_APPEND_ELT (nml_decls, NULL_TREE, nml->sym->backend_decl);
4847 }
4848
4849 decl = make_node (NAMELIST_DECL);
4850 TREE_TYPE (decl) = void_type_node;
4851 NAMELIST_DECL_ASSOCIATED_DECL (decl) = build_constructor (NULL_TREE, nml_decls);
4852 DECL_NAME (decl) = get_identifier (sym->name);
4853 return decl;
4854}
4855
4856
4ee9c684 4857/* Output an initialized decl for a module variable. */
4858
4859static void
4860gfc_create_module_variable (gfc_symbol * sym)
4861{
4862 tree decl;
4ee9c684 4863
d77f260f 4864 /* Module functions with alternate entries are dealt with later and
4865 would get caught by the next condition. */
4866 if (sym->attr.entry)
4867 return;
4868
c5d33754 4869 /* Make sure we convert the types of the derived types from iso_c_binding
4870 into (void *). */
4871 if (sym->attr.flavor != FL_PROCEDURE && sym->attr.is_iso_c
4872 && sym->ts.type == BT_DERIVED)
4873 sym->backend_decl = gfc_typenode_for_spec (&(sym->ts));
4874
d7cd448a 4875 if (gfc_fl_struct (sym->attr.flavor)
df4d540f 4876 && sym->backend_decl
4877 && TREE_CODE (sym->backend_decl) == RECORD_TYPE)
4878 {
4879 decl = sym->backend_decl;
4880 gcc_assert (sym->ns->proc_name->attr.flavor == FL_MODULE);
9f1470cb 4881
fe9d2f5a 4882 if (!sym->attr.use_assoc && !sym->attr.used_in_submodule)
9f1470cb 4883 {
4884 gcc_assert (TYPE_CONTEXT (decl) == NULL_TREE
4885 || TYPE_CONTEXT (decl) == sym->ns->proc_name->backend_decl);
4886 gcc_assert (DECL_CONTEXT (TYPE_STUB_DECL (decl)) == NULL_TREE
4887 || DECL_CONTEXT (TYPE_STUB_DECL (decl))
4888 == sym->ns->proc_name->backend_decl);
4889 }
df4d540f 4890 TYPE_CONTEXT (decl) = sym->ns->proc_name->backend_decl;
4891 DECL_CONTEXT (TYPE_STUB_DECL (decl)) = sym->ns->proc_name->backend_decl;
4892 gfc_module_add_decl (cur_module, TYPE_STUB_DECL (decl));
4893 }
4894
cf269acc 4895 /* Only output variables, procedure pointers and array valued,
4896 or derived type, parameters. */
4ee9c684 4897 if (sym->attr.flavor != FL_VARIABLE
be0f1581 4898 && !(sym->attr.flavor == FL_PARAMETER
cf269acc 4899 && (sym->attr.dimension || sym->ts.type == BT_DERIVED))
4900 && !(sym->attr.flavor == FL_PROCEDURE && sym->attr.proc_pointer))
4ee9c684 4901 return;
4902
df4d540f 4903 if ((sym->attr.in_common || sym->attr.in_equivalence) && sym->backend_decl)
4904 {
4905 decl = sym->backend_decl;
16a40513 4906 gcc_assert (DECL_FILE_SCOPE_P (decl));
df4d540f 4907 gcc_assert (sym->ns->proc_name->attr.flavor == FL_MODULE);
4908 DECL_CONTEXT (decl) = sym->ns->proc_name->backend_decl;
4909 gfc_module_add_decl (cur_module, decl);
4910 }
4911
d43a7f7f 4912 /* Don't generate variables from other modules. Variables from
cd958916 4913 COMMONs and Cray pointees will already have been generated. */
fe9d2f5a 4914 if (sym->attr.use_assoc || sym->attr.used_in_submodule
4915 || sym->attr.in_common || sym->attr.cray_pointee)
4ee9c684 4916 return;
4917
2b685f8e 4918 /* Equivalenced variables arrive here after creation. */
976d903a 4919 if (sym->backend_decl
df4d540f 4920 && (sym->equiv_built || sym->attr.in_equivalence))
4921 return;
2b685f8e 4922
23d075f4 4923 if (sym->backend_decl && !sym->attr.vtab && !sym->attr.target)
382ad5c3 4924 gfc_internal_error ("backend decl for module variable %qs already exists",
4925 sym->name);
4ee9c684 4926
92983bfd 4927 if (sym->module && !sym->attr.result && !sym->attr.dummy
4928 && (sym->attr.access == ACCESS_UNKNOWN
4929 && (sym->ns->default_access == ACCESS_PRIVATE
4930 || (sym->ns->default_access == ACCESS_UNKNOWN
829d7a08 4931 && flag_module_private))))
92983bfd 4932 sym->attr.access = ACCESS_PRIVATE;
4933
4934 if (warn_unused_variable && !sym->attr.referenced
4935 && sym->attr.access == ACCESS_PRIVATE)
4166acc7 4936 gfc_warning (OPT_Wunused_value,
4937 "Unused PRIVATE module variable %qs declared at %L",
92983bfd 4938 sym->name, &sym->declared_at);
4939
4ee9c684 4940 /* We always want module variables to be created. */
4941 sym->attr.referenced = 1;
4942 /* Create the decl. */
4943 decl = gfc_get_symbol_decl (sym);
4944
4ee9c684 4945 /* Create the variable. */
4946 pushdecl (decl);
8b7e5587 4947 gcc_assert (sym->ns->proc_name->attr.flavor == FL_MODULE
4948 || (sym->ns->parent->proc_name->attr.flavor == FL_MODULE
4949 && sym->fn_result_spec));
df4d540f 4950 DECL_CONTEXT (decl) = sym->ns->proc_name->backend_decl;
b2c4af5e 4951 rest_of_decl_compilation (decl, 1, 0);
df4d540f 4952 gfc_module_add_decl (cur_module, decl);
4ee9c684 4953
4954 /* Also add length of strings. */
4955 if (sym->ts.type == BT_CHARACTER)
4956 {
4957 tree length;
4958
eeebe20b 4959 length = sym->ts.u.cl->backend_decl;
cf4b41d8 4960 gcc_assert (length || sym->attr.proc_pointer);
4961 if (length && !INTEGER_CST_P (length))
4ee9c684 4962 {
4963 pushdecl (length);
b2c4af5e 4964 rest_of_decl_compilation (length, 1, 0);
4ee9c684 4965 }
4966 }
a961ca30 4967
4968 if (sym->attr.codimension && !sym->attr.dummy && !sym->attr.allocatable
4969 && sym->attr.referenced && !sym->attr.use_assoc)
4970 has_coarray_vars = true;
4ee9c684 4971}
4972
51d9479b 4973/* Emit debug information for USE statements. */
df4d540f 4974
4975static void
4976gfc_trans_use_stmts (gfc_namespace * ns)
4977{
4978 gfc_use_list *use_stmt;
4979 for (use_stmt = ns->use_stmts; use_stmt; use_stmt = use_stmt->next)
4980 {
4981 struct module_htab_entry *entry
4982 = gfc_find_module (use_stmt->module_name);
4983 gfc_use_rename *rent;
4984
4985 if (entry->namespace_decl == NULL)
4986 {
4987 entry->namespace_decl
e60a6f7b 4988 = build_decl (input_location,
4989 NAMESPACE_DECL,
df4d540f 4990 get_identifier (use_stmt->module_name),
4991 void_type_node);
4992 DECL_EXTERNAL (entry->namespace_decl) = 1;
4993 }
51d9479b 4994 gfc_set_backend_locus (&use_stmt->where);
df4d540f 4995 if (!use_stmt->only_flag)
4996 (*debug_hooks->imported_module_or_decl) (entry->namespace_decl,
4997 NULL_TREE,
4998 ns->proc_name->backend_decl,
41d01e67 4999 false, false);
df4d540f 5000 for (rent = use_stmt->rename; rent; rent = rent->next)
5001 {
5002 tree decl, local_name;
df4d540f 5003
5004 if (rent->op != INTRINSIC_NONE)
5005 continue;
5006
2ef51f0e 5007 hashval_t hash = htab_hash_string (rent->use_name);
5008 tree *slot = entry->decls->find_slot_with_hash (rent->use_name, hash,
5009 INSERT);
df4d540f 5010 if (*slot == NULL)
5011 {
5012 gfc_symtree *st;
5013
5014 st = gfc_find_symtree (ns->sym_root,
5015 rent->local_name[0]
5016 ? rent->local_name : rent->use_name);
c2958b6b 5017
5018 /* The following can happen if a derived type is renamed. */
5019 if (!st)
5020 {
5021 char *name;
5022 name = xstrdup (rent->local_name[0]
5023 ? rent->local_name : rent->use_name);
5024 name[0] = (char) TOUPPER ((unsigned char) name[0]);
5025 st = gfc_find_symtree (ns->sym_root, name);
5026 free (name);
5027 gcc_assert (st);
5028 }
857c96ba 5029
5030 /* Sometimes, generic interfaces wind up being over-ruled by a
5031 local symbol (see PR41062). */
5032 if (!st->n.sym->attr.use_assoc)
5033 continue;
5034
51d9479b 5035 if (st->n.sym->backend_decl
5036 && DECL_P (st->n.sym->backend_decl)
5037 && st->n.sym->module
5038 && strcmp (st->n.sym->module, use_stmt->module_name) == 0)
df4d540f 5039 {
51d9479b 5040 gcc_assert (DECL_EXTERNAL (entry->namespace_decl)
fe732a9b 5041 || !VAR_P (st->n.sym->backend_decl));
df4d540f 5042 decl = copy_node (st->n.sym->backend_decl);
5043 DECL_CONTEXT (decl) = entry->namespace_decl;
5044 DECL_EXTERNAL (decl) = 1;
5045 DECL_IGNORED_P (decl) = 0;
5046 DECL_INITIAL (decl) = NULL_TREE;
5047 }
c40a5c1b 5048 else if (st->n.sym->attr.flavor == FL_NAMELIST
5049 && st->n.sym->attr.use_only
5050 && st->n.sym->module
5051 && strcmp (st->n.sym->module, use_stmt->module_name)
5052 == 0)
5053 {
5054 decl = generate_namelist_decl (st->n.sym);
5055 DECL_CONTEXT (decl) = entry->namespace_decl;
5056 DECL_EXTERNAL (decl) = 1;
5057 DECL_IGNORED_P (decl) = 0;
5058 DECL_INITIAL (decl) = NULL_TREE;
5059 }
df4d540f 5060 else
5061 {
5062 *slot = error_mark_node;
2ef51f0e 5063 entry->decls->clear_slot (slot);
df4d540f 5064 continue;
5065 }
5066 *slot = decl;
5067 }
5068 decl = (tree) *slot;
5069 if (rent->local_name[0])
5070 local_name = get_identifier (rent->local_name);
5071 else
5072 local_name = NULL_TREE;
51d9479b 5073 gfc_set_backend_locus (&rent->where);
df4d540f 5074 (*debug_hooks->imported_module_or_decl) (decl, local_name,
5075 ns->proc_name->backend_decl,
41d01e67 5076 !use_stmt->only_flag,
5077 false);
df4d540f 5078 }
5079 }
4ee9c684 5080}
5081
51d9479b 5082
2eb674c9 5083/* Return true if expr is a constant initializer that gfc_conv_initializer
5084 will handle. */
5085
5086static bool
5087check_constant_initializer (gfc_expr *expr, gfc_typespec *ts, bool array,
5088 bool pointer)
5089{
5090 gfc_constructor *c;
5091 gfc_component *cm;
5092
5093 if (pointer)
5094 return true;
5095 else if (array)
5096 {
5097 if (expr->expr_type == EXPR_CONSTANT || expr->expr_type == EXPR_NULL)
5098 return true;
5099 else if (expr->expr_type == EXPR_STRUCTURE)
5100 return check_constant_initializer (expr, ts, false, false);
5101 else if (expr->expr_type != EXPR_ARRAY)
5102 return false;
126387b5 5103 for (c = gfc_constructor_first (expr->value.constructor);
5104 c; c = gfc_constructor_next (c))
2eb674c9 5105 {
5106 if (c->iterator)
5107 return false;
5108 if (c->expr->expr_type == EXPR_STRUCTURE)
5109 {
5110 if (!check_constant_initializer (c->expr, ts, false, false))
5111 return false;
5112 }
5113 else if (c->expr->expr_type != EXPR_CONSTANT)
5114 return false;
5115 }
5116 return true;
5117 }
5118 else switch (ts->type)
5119 {
d7cd448a 5120 case_bt_struct:
2eb674c9 5121 if (expr->expr_type != EXPR_STRUCTURE)
5122 return false;
eeebe20b 5123 cm = expr->ts.u.derived->components;
126387b5 5124 for (c = gfc_constructor_first (expr->value.constructor);
5125 c; c = gfc_constructor_next (c), cm = cm->next)
2eb674c9 5126 {
5127 if (!c->expr || cm->attr.allocatable)
5128 continue;
5129 if (!check_constant_initializer (c->expr, &cm->ts,
5130 cm->attr.dimension,
5131 cm->attr.pointer))
5132 return false;
5133 }
5134 return true;
5135 default:
5136 return expr->expr_type == EXPR_CONSTANT;
5137 }
5138}
5139
5140/* Emit debug info for parameters and unreferenced variables with
5141 initializers. */
5142
5143static void
5144gfc_emit_parameter_debug_info (gfc_symbol *sym)
5145{
5146 tree decl;
5147
5148 if (sym->attr.flavor != FL_PARAMETER
5149 && (sym->attr.flavor != FL_VARIABLE || sym->attr.referenced))
5150 return;
5151
5152 if (sym->backend_decl != NULL
5153 || sym->value == NULL
5154 || sym->attr.use_assoc
5155 || sym->attr.dummy
5156 || sym->attr.result
5157 || sym->attr.function
5158 || sym->attr.intrinsic
5159 || sym->attr.pointer
5160 || sym->attr.allocatable
5161 || sym->attr.cray_pointee
5162 || sym->attr.threadprivate
5163 || sym->attr.is_bind_c
5164 || sym->attr.subref_array_pointer
5165 || sym->attr.assign)
5166 return;
5167
5168 if (sym->ts.type == BT_CHARACTER)
5169 {
eeebe20b 5170 gfc_conv_const_charlen (sym->ts.u.cl);
5171 if (sym->ts.u.cl->backend_decl == NULL
5172 || TREE_CODE (sym->ts.u.cl->backend_decl) != INTEGER_CST)
2eb674c9 5173 return;
5174 }
eeebe20b 5175 else if (sym->ts.type == BT_DERIVED && sym->ts.u.derived->attr.alloc_comp)
2eb674c9 5176 return;
5177
5178 if (sym->as)
5179 {
5180 int n;
5181
5182 if (sym->as->type != AS_EXPLICIT)
5183 return;
5184 for (n = 0; n < sym->as->rank; n++)
5185 if (sym->as->lower[n]->expr_type != EXPR_CONSTANT
5186 || sym->as->upper[n] == NULL
5187 || sym->as->upper[n]->expr_type != EXPR_CONSTANT)
5188 return;
5189 }
5190
5191 if (!check_constant_initializer (sym->value, &sym->ts,
5192 sym->attr.dimension, false))
5193 return;
5194
4fe73152 5195 if (flag_coarray == GFC_FCOARRAY_LIB && sym->attr.codimension)
a961ca30 5196 return;
5197
2eb674c9 5198 /* Create the decl for the variable or constant. */
e60a6f7b 5199 decl = build_decl (input_location,
5200 sym->attr.flavor == FL_PARAMETER ? CONST_DECL : VAR_DECL,
2eb674c9 5201 gfc_sym_identifier (sym), gfc_sym_type (sym));
5202 if (sym->attr.flavor == FL_PARAMETER)
5203 TREE_READONLY (decl) = 1;
5204 gfc_set_decl_location (decl, &sym->declared_at);
5205 if (sym->attr.dimension)
5206 GFC_DECL_PACKED_ARRAY (decl) = 1;
5207 DECL_CONTEXT (decl) = sym->ns->proc_name->backend_decl;
5208 TREE_STATIC (decl) = 1;
5209 TREE_USED (decl) = 1;
5210 if (DECL_CONTEXT (decl) && TREE_CODE (DECL_CONTEXT (decl)) == NAMESPACE_DECL)
5211 TREE_PUBLIC (decl) = 1;
802532b9 5212 DECL_INITIAL (decl) = gfc_conv_initializer (sym->value, &sym->ts,
5213 TREE_TYPE (decl),
5214 sym->attr.dimension,
5215 false, false);
3a1c9df2 5216 debug_hooks->early_global_decl (decl);
2eb674c9 5217}
5218
a961ca30 5219
5220static void
5221generate_coarray_sym_init (gfc_symbol *sym)
5222{
eee0cf09 5223 tree tmp, size, decl, token, desc;
bd47f0bc 5224 bool is_lock_type, is_event_type;
498b946e 5225 int reg_type;
eee0cf09 5226 gfc_se se;
5227 symbol_attribute attr;
a961ca30 5228
5229 if (sym->attr.dummy || sym->attr.allocatable || !sym->attr.codimension
102abea2 5230 || sym->attr.use_assoc || !sym->attr.referenced
5231 || sym->attr.select_type_temporary)
a961ca30 5232 return;
5233
5234 decl = sym->backend_decl;
5235 TREE_USED(decl) = 1;
5236 gcc_assert (GFC_ARRAY_TYPE_P (TREE_TYPE (decl)));
5237
498b946e 5238 is_lock_type = sym->ts.type == BT_DERIVED
5239 && sym->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
5240 && sym->ts.u.derived->intmod_sym_id == ISOFORTRAN_LOCK_TYPE;
5241
bd47f0bc 5242 is_event_type = sym->ts.type == BT_DERIVED
5243 && sym->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
5244 && sym->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE;
5245
a961ca30 5246 /* FIXME: Workaround for PR middle-end/49106, cf. also PR middle-end/49108
5247 to make sure the variable is not optimized away. */
5248 DECL_PRESERVE_P (DECL_CONTEXT (decl)) = 1;
5249
498b946e 5250 /* For lock types, we pass the array size as only the library knows the
5251 size of the variable. */
bd47f0bc 5252 if (is_lock_type || is_event_type)
498b946e 5253 size = gfc_index_one_node;
5254 else
5255 size = TYPE_SIZE_UNIT (gfc_get_element_type (TREE_TYPE (decl)));
a961ca30 5256
a90fe829 5257 /* Ensure that we do not have size=0 for zero-sized arrays. */
ee4e7a5e 5258 size = fold_build2_loc (input_location, MAX_EXPR, size_type_node,
5259 fold_convert (size_type_node, size),
5260 build_int_cst (size_type_node, 1));
5261
a961ca30 5262 if (GFC_TYPE_ARRAY_RANK (TREE_TYPE (decl)))
5263 {
5264 tmp = GFC_TYPE_ARRAY_SIZE (TREE_TYPE (decl));
5265 size = fold_build2_loc (input_location, MULT_EXPR, size_type_node,
ee4e7a5e 5266 fold_convert (size_type_node, tmp), size);
a961ca30 5267 }
5268
5269 gcc_assert (GFC_TYPE_ARRAY_CAF_TOKEN (TREE_TYPE (decl)) != NULL_TREE);
5270 token = gfc_build_addr_expr (ppvoid_type_node,
5271 GFC_TYPE_ARRAY_CAF_TOKEN (TREE_TYPE(decl)));
498b946e 5272 if (is_lock_type)
5273 reg_type = sym->attr.artificial ? GFC_CAF_CRITICAL : GFC_CAF_LOCK_STATIC;
bd47f0bc 5274 else if (is_event_type)
5275 reg_type = GFC_CAF_EVENT_STATIC;
498b946e 5276 else
5277 reg_type = GFC_CAF_COARRAY_STATIC;
eee0cf09 5278
f991680c 5279 /* Compile the symbol attribute. */
5280 if (sym->ts.type == BT_CLASS)
5281 {
5282 attr = CLASS_DATA (sym)->attr;
5283 /* The pointer attribute is always set on classes, overwrite it with the
5284 class_pointer attribute, which denotes the pointer for classes. */
5285 attr.pointer = attr.class_pointer;
5286 }
5287 else
5288 attr = sym->attr;
eee0cf09 5289 gfc_init_se (&se, NULL);
5290 desc = gfc_conv_scalar_to_descriptor (&se, decl, attr);
5291 gfc_add_block_to_block (&caf_init_block, &se.pre);
5292
5293 tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_register, 7, size,
498b946e 5294 build_int_cst (integer_type_node, reg_type),
eee0cf09 5295 token, gfc_build_addr_expr (pvoid_type_node, desc),
5296 null_pointer_node, /* stat. */
3d2aa0e8 5297 null_pointer_node, /* errgmsg. */
5298 integer_zero_node); /* errmsg_len. */
eee0cf09 5299 gfc_add_expr_to_block (&caf_init_block, tmp);
5300 gfc_add_modify (&caf_init_block, decl, fold_convert (TREE_TYPE (decl),
5301 gfc_conv_descriptor_data_get (desc)));
a961ca30 5302
a961ca30 5303 /* Handle "static" initializer. */
5304 if (sym->value)
5305 {
5306 sym->attr.pointer = 1;
5307 tmp = gfc_trans_assignment (gfc_lval_expr_from_sym (sym), sym->value,
5308 true, false);
5309 sym->attr.pointer = 0;
5310 gfc_add_expr_to_block (&caf_init_block, tmp);
5311 }
942ef29d 5312 else if (sym->ts.type == BT_DERIVED && sym->ts.u.derived->attr.pointer_comp)
5313 {
5314 tmp = gfc_nullify_alloc_comp (sym->ts.u.derived, decl, sym->as
5315 ? sym->as->rank : 0,
5316 GFC_STRUCTURE_CAF_MODE_IN_COARRAY);
5317 gfc_add_expr_to_block (&caf_init_block, tmp);
5318 }
a961ca30 5319}
5320
5321
5322/* Generate constructor function to initialize static, nonallocatable
5323 coarrays. */
5324
5325static void
5326generate_coarray_init (gfc_namespace * ns __attribute((unused)))
5327{
5328 tree fndecl, tmp, decl, save_fn_decl;
5329
5330 save_fn_decl = current_function_decl;
5331 push_function_context ();
5332
5333 tmp = build_function_type_list (void_type_node, NULL_TREE);
5334 fndecl = build_decl (input_location, FUNCTION_DECL,
5335 create_tmp_var_name ("_caf_init"), tmp);
5336
5337 DECL_STATIC_CONSTRUCTOR (fndecl) = 1;
5338 SET_DECL_INIT_PRIORITY (fndecl, DEFAULT_INIT_PRIORITY);
5339
5340 decl = build_decl (input_location, RESULT_DECL, NULL_TREE, void_type_node);
5341 DECL_ARTIFICIAL (decl) = 1;
5342 DECL_IGNORED_P (decl) = 1;
5343 DECL_CONTEXT (decl) = fndecl;
5344 DECL_RESULT (fndecl) = decl;
5345
5346 pushdecl (fndecl);
5347 current_function_decl = fndecl;
5348 announce_function (fndecl);
5349
5350 rest_of_decl_compilation (fndecl, 0, 0);
5351 make_decl_rtl (fndecl);
00cf115c 5352 allocate_struct_function (fndecl, false);
a961ca30 5353
cde2be84 5354 pushlevel ();
a961ca30 5355 gfc_init_block (&caf_init_block);
5356
5357 gfc_traverse_ns (ns, generate_coarray_sym_init);
5358
5359 DECL_SAVED_TREE (fndecl) = gfc_finish_block (&caf_init_block);
5360 decl = getdecls ();
5361
cde2be84 5362 poplevel (1, 1);
a961ca30 5363 BLOCK_SUPERCONTEXT (DECL_INITIAL (fndecl)) = fndecl;
5364
5365 DECL_SAVED_TREE (fndecl)
5366 = build3_v (BIND_EXPR, decl, DECL_SAVED_TREE (fndecl),
5367 DECL_INITIAL (fndecl));
5368 dump_function (TDI_original, fndecl);
5369
5370 cfun->function_end_locus = input_location;
5371 set_cfun (NULL);
5372
5373 if (decl_function_context (fndecl))
415d1b9a 5374 (void) cgraph_node::create (fndecl);
a961ca30 5375 else
35ee1c66 5376 cgraph_node::finalize_function (fndecl, true);
a961ca30 5377
5378 pop_function_context ();
5379 current_function_decl = save_fn_decl;
5380}
5381
5382
c40a5c1b 5383static void
5384create_module_nml_decl (gfc_symbol *sym)
5385{
5386 if (sym->attr.flavor == FL_NAMELIST)
5387 {
5388 tree decl = generate_namelist_decl (sym);
5389 pushdecl (decl);
5390 gcc_assert (sym->ns->proc_name->attr.flavor == FL_MODULE);
5391 DECL_CONTEXT (decl) = sym->ns->proc_name->backend_decl;
5392 rest_of_decl_compilation (decl, 1, 0);
5393 gfc_module_add_decl (cur_module, decl);
5394 }
5395}
5396
5397
51d9479b 5398/* Generate all the required code for module variables. */
5399
5400void
5401gfc_generate_module_vars (gfc_namespace * ns)
5402{
5403 module_namespace = ns;
5404 cur_module = gfc_find_module (ns->proc_name->name);
5405
5406 /* Check if the frontend left the namespace in a reasonable state. */
5407 gcc_assert (ns->proc_name && !ns->proc_name->tlink);
5408
5409 /* Generate COMMON blocks. */
5410 gfc_trans_common (ns);
5411
a961ca30 5412 has_coarray_vars = false;
5413
51d9479b 5414 /* Create decls for all the module variables. */
5415 gfc_traverse_ns (ns, gfc_create_module_variable);
c40a5c1b 5416 gfc_traverse_ns (ns, create_module_nml_decl);
51d9479b 5417
4fe73152 5418 if (flag_coarray == GFC_FCOARRAY_LIB && has_coarray_vars)
a961ca30 5419 generate_coarray_init (ns);
5420
51d9479b 5421 cur_module = NULL;
5422
5423 gfc_trans_use_stmts (ns);
2eb674c9 5424 gfc_traverse_ns (ns, gfc_emit_parameter_debug_info);
51d9479b 5425}
5426
5427
4ee9c684 5428static void
5429gfc_generate_contained_functions (gfc_namespace * parent)
5430{
5431 gfc_namespace *ns;
5432
5433 /* We create all the prototypes before generating any code. */
5434 for (ns = parent->contained; ns; ns = ns->sibling)
5435 {
5436 /* Skip namespaces from used modules. */
5437 if (ns->parent != parent)
5438 continue;
5439
d896f9b3 5440 gfc_create_function_decl (ns, false);
4ee9c684 5441 }
5442
5443 for (ns = parent->contained; ns; ns = ns->sibling)
5444 {
5445 /* Skip namespaces from used modules. */
5446 if (ns->parent != parent)
5447 continue;
5448
5449 gfc_generate_function_code (ns);
5450 }
5451}
5452
5453
d95efb59 5454/* Drill down through expressions for the array specification bounds and
5455 character length calling generate_local_decl for all those variables
5456 that have not already been declared. */
5457
5458static void
5459generate_local_decl (gfc_symbol *);
5460
1acb400a 5461/* Traverse expr, marking all EXPR_VARIABLE symbols referenced. */
d95efb59 5462
1acb400a 5463static bool
5464expr_decls (gfc_expr *e, gfc_symbol *sym,
5465 int *f ATTRIBUTE_UNUSED)
5466{
5467 if (e->expr_type != EXPR_VARIABLE
5468 || sym == e->symtree->n.sym
d95efb59 5469 || e->symtree->n.sym->mark
5470 || e->symtree->n.sym->ns != sym->ns)
1acb400a 5471 return false;
d95efb59 5472
1acb400a 5473 generate_local_decl (e->symtree->n.sym);
5474 return false;
5475}
d95efb59 5476
1acb400a 5477static void
5478generate_expr_decls (gfc_symbol *sym, gfc_expr *e)
5479{
5480 gfc_traverse_expr (e, sym, expr_decls, 0);
d95efb59 5481}
5482
5483
f6d0e37a 5484/* Check for dependencies in the character length and array spec. */
d95efb59 5485
5486static void
5487generate_dependency_declarations (gfc_symbol *sym)
5488{
5489 int i;
5490
5491 if (sym->ts.type == BT_CHARACTER
eeebe20b 5492 && sym->ts.u.cl
5493 && sym->ts.u.cl->length
5494 && sym->ts.u.cl->length->expr_type != EXPR_CONSTANT)
5495 generate_expr_decls (sym, sym->ts.u.cl->length);
d95efb59 5496
5497 if (sym->as && sym->as->rank)
5498 {
5499 for (i = 0; i < sym->as->rank; i++)
5500 {
5501 generate_expr_decls (sym, sym->as->lower[i]);
5502 generate_expr_decls (sym, sym->as->upper[i]);
5503 }
5504 }
5505}
5506
5507
4ee9c684 5508/* Generate decls for all local variables. We do this to ensure correct
5509 handling of expressions which only appear in the specification of
5510 other functions. */
5511
5512static void
5513generate_local_decl (gfc_symbol * sym)
5514{
5515 if (sym->attr.flavor == FL_VARIABLE)
5516 {
a961ca30 5517 if (sym->attr.codimension && !sym->attr.dummy && !sym->attr.allocatable
5518 && sym->attr.referenced && !sym->attr.use_assoc)
5519 has_coarray_vars = true;
5520
d95efb59 5521 if (!sym->attr.dummy && !sym->ns->proc_name->attr.entry_master)
8714fc76 5522 generate_dependency_declarations (sym);
d95efb59 5523
4ee9c684 5524 if (sym->attr.referenced)
8714fc76 5525 gfc_get_symbol_decl (sym);
4acad347 5526
5527 /* Warnings for unused dummy arguments. */
6992b8c8 5528 else if (sym->attr.dummy && !sym->attr.in_namelist)
7c0ca46e 5529 {
4acad347 5530 /* INTENT(out) dummy arguments are likely meant to be set. */
8290d53f 5531 if (warn_unused_dummy_argument && sym->attr.intent == INTENT_OUT)
4acad347 5532 {
5533 if (sym->ts.type != BT_DERIVED)
4166acc7 5534 gfc_warning (OPT_Wunused_dummy_argument,
5535 "Dummy argument %qs at %L was declared "
4acad347 5536 "INTENT(OUT) but was not set", sym->name,
5537 &sym->declared_at);
48cb4748 5538 else if (!gfc_has_default_initializer (sym->ts.u.derived)
5539 && !sym->ts.u.derived->attr.zero_comp)
4166acc7 5540 gfc_warning (OPT_Wunused_dummy_argument,
5541 "Derived-type dummy argument %qs at %L was "
4acad347 5542 "declared INTENT(OUT) but was not set and "
5543 "does not have a default initializer",
5544 sym->name, &sym->declared_at);
90a4a5a6 5545 if (sym->backend_decl != NULL_TREE)
5546 TREE_NO_WARNING(sym->backend_decl) = 1;
4acad347 5547 }
8290d53f 5548 else if (warn_unused_dummy_argument)
90a4a5a6 5549 {
4166acc7 5550 gfc_warning (OPT_Wunused_dummy_argument,
5551 "Unused dummy argument %qs at %L", sym->name,
5552 &sym->declared_at);
90a4a5a6 5553 if (sym->backend_decl != NULL_TREE)
5554 TREE_NO_WARNING(sym->backend_decl) = 1;
5555 }
7c0ca46e 5556 }
4acad347 5557
f888a3fb 5558 /* Warn for unused variables, but not if they're inside a common
1dbfac29 5559 block or a namelist. */
36609028 5560 else if (warn_unused_variable
1dbfac29 5561 && !(sym->attr.in_common || sym->mark || sym->attr.in_namelist))
90a4a5a6 5562 {
1dbfac29 5563 if (sym->attr.use_only)
5564 {
4166acc7 5565 gfc_warning (OPT_Wunused_variable,
5566 "Unused module variable %qs which has been "
1dbfac29 5567 "explicitly imported at %L", sym->name,
5568 &sym->declared_at);
5569 if (sym->backend_decl != NULL_TREE)
5570 TREE_NO_WARNING(sym->backend_decl) = 1;
5571 }
5572 else if (!sym->attr.use_assoc)
5573 {
99af6e70 5574 /* Corner case: the symbol may be an entry point. At this point,
5575 it may appear to be an unused variable. Suppress warning. */
5576 bool enter = false;
5577 gfc_entry_list *el;
5578
5579 for (el = sym->ns->entries; el; el=el->next)
5580 if (strcmp(sym->name, el->sym->name) == 0)
5581 enter = true;
5582
5583 if (!enter)
5584 gfc_warning (OPT_Wunused_variable,
5585 "Unused variable %qs declared at %L",
5586 sym->name, &sym->declared_at);
1dbfac29 5587 if (sym->backend_decl != NULL_TREE)
5588 TREE_NO_WARNING(sym->backend_decl) = 1;
5589 }
90a4a5a6 5590 }
8714fc76 5591
d4163395 5592 /* For variable length CHARACTER parameters, the PARM_DECL already
5593 references the length variable, so force gfc_get_symbol_decl
5594 even when not referenced. If optimize > 0, it will be optimized
5595 away anyway. But do this only after emitting -Wunused-parameter
5596 warning if requested. */
8714fc76 5597 if (sym->attr.dummy && !sym->attr.referenced
5598 && sym->ts.type == BT_CHARACTER
eeebe20b 5599 && sym->ts.u.cl->backend_decl != NULL
fe732a9b 5600 && VAR_P (sym->ts.u.cl->backend_decl))
d4163395 5601 {
5602 sym->attr.referenced = 1;
5603 gfc_get_symbol_decl (sym);
5604 }
76776e6d 5605
d0163401 5606 /* INTENT(out) dummy arguments and result variables with allocatable
5607 components are reset by default and need to be set referenced to
5608 generate the code for nullification and automatic lengths. */
5609 if (!sym->attr.referenced
8714fc76 5610 && sym->ts.type == BT_DERIVED
eeebe20b 5611 && sym->ts.u.derived->attr.alloc_comp
c49db15e 5612 && !sym->attr.pointer
d0163401 5613 && ((sym->attr.dummy && sym->attr.intent == INTENT_OUT)
5614 ||
5615 (sym->attr.result && sym != sym->result)))
8714fc76 5616 {
5617 sym->attr.referenced = 1;
5618 gfc_get_symbol_decl (sym);
5619 }
5620
e72f979a 5621 /* Check for dependencies in the array specification and string
5622 length, adding the necessary declarations to the function. We
5623 mark the symbol now, as well as in traverse_ns, to prevent
5624 getting stuck in a circular dependency. */
5625 sym->mark = 1;
4ee9c684 5626 }
5dd246c1 5627 else if (sym->attr.flavor == FL_PARAMETER)
5628 {
6ecfe89d 5629 if (warn_unused_parameter
f326eb81 5630 && !sym->attr.referenced)
5631 {
5632 if (!sym->attr.use_assoc)
4166acc7 5633 gfc_warning (OPT_Wunused_parameter,
5634 "Unused parameter %qs declared at %L", sym->name,
f326eb81 5635 &sym->declared_at);
5636 else if (sym->attr.use_only)
4166acc7 5637 gfc_warning (OPT_Wunused_parameter,
5638 "Unused parameter %qs which has been explicitly "
f326eb81 5639 "imported at %L", sym->name, &sym->declared_at);
5640 }
758c9897 5641
5642 if (sym->ns
5643 && sym->ns->parent
5644 && sym->ns->parent->code
5645 && sym->ns->parent->code->op == EXEC_BLOCK)
5646 {
5647 if (sym->attr.referenced)
5648 gfc_get_symbol_decl (sym);
5649 sym->mark = 1;
5650 }
5dd246c1 5651 }
fa7b6574 5652 else if (sym->attr.flavor == FL_PROCEDURE)
5653 {
5654 /* TODO: move to the appropriate place in resolve.c. */
8b72061f 5655 if (warn_return_type > 0
fa7b6574 5656 && sym->attr.function
5657 && sym->result
5658 && sym != sym->result
5659 && !sym->result->attr.referenced
5660 && !sym->attr.use_assoc
5661 && sym->attr.if_source != IFSRC_IFBODY)
5662 {
4166acc7 5663 gfc_warning (OPT_Wreturn_type,
5664 "Return value %qs of function %qs declared at "
fa7b6574 5665 "%L not set", sym->result->name, sym->name,
5666 &sym->result->declared_at);
5667
5668 /* Prevents "Unused variable" warning for RESULT variables. */
e72f979a 5669 sym->result->mark = 1;
fa7b6574 5670 }
5671 }
c5d33754 5672
19ba2ad8 5673 if (sym->attr.dummy == 1)
5674 {
5675 /* Modify the tree type for scalar character dummy arguments of bind(c)
5676 procedures if they are passed by value. The tree type for them will
5677 be promoted to INTEGER_TYPE for the middle end, which appears to be
5678 what C would do with characters passed by-value. The value attribute
5679 implies the dummy is a scalar. */
5680 if (sym->attr.value == 1 && sym->backend_decl != NULL
5681 && sym->ts.type == BT_CHARACTER && sym->ts.is_c_interop
5682 && sym->ns->proc_name != NULL && sym->ns->proc_name->attr.is_bind_c)
4c47c8b7 5683 gfc_conv_scalar_char_value (sym, NULL, NULL);
fc6338c7 5684
5685 /* Unused procedure passed as dummy argument. */
5686 if (sym->attr.flavor == FL_PROCEDURE)
5687 {
5688 if (!sym->attr.referenced)
5689 {
8290d53f 5690 if (warn_unused_dummy_argument)
4166acc7 5691 gfc_warning (OPT_Wunused_dummy_argument,
5692 "Unused dummy argument %qs at %L", sym->name,
a90fe829 5693 &sym->declared_at);
fc6338c7 5694 }
5695
5696 /* Silence bogus "unused parameter" warnings from the
5697 middle end. */
5698 if (sym->backend_decl != NULL_TREE)
5699 TREE_NO_WARNING (sym->backend_decl) = 1;
5700 }
19ba2ad8 5701 }
5702
c5d33754 5703 /* Make sure we convert the types of the derived types from iso_c_binding
5704 into (void *). */
5705 if (sym->attr.flavor != FL_PROCEDURE && sym->attr.is_iso_c
5706 && sym->ts.type == BT_DERIVED)
5707 sym->backend_decl = gfc_typenode_for_spec (&(sym->ts));
4ee9c684 5708}
5709
c40a5c1b 5710
5711static void
5712generate_local_nml_decl (gfc_symbol * sym)
5713{
5714 if (sym->attr.flavor == FL_NAMELIST && !sym->attr.use_assoc)
5715 {
5716 tree decl = generate_namelist_decl (sym);
5717 pushdecl (decl);
5718 }
5719}
5720
5721
4ee9c684 5722static void
5723generate_local_vars (gfc_namespace * ns)
5724{
5725 gfc_traverse_ns (ns, generate_local_decl);
c40a5c1b 5726 gfc_traverse_ns (ns, generate_local_nml_decl);
4ee9c684 5727}
5728
5729
1b716045 5730/* Generate a switch statement to jump to the correct entry point. Also
5731 creates the label decls for the entry points. */
4ee9c684 5732
1b716045 5733static tree
5734gfc_trans_entry_master_switch (gfc_entry_list * el)
4ee9c684 5735{
1b716045 5736 stmtblock_t block;
5737 tree label;
5738 tree tmp;
5739 tree val;
4ee9c684 5740
1b716045 5741 gfc_init_block (&block);
5742 for (; el; el = el->next)
5743 {
5744 /* Add the case label. */
b797d6d3 5745 label = gfc_build_label_decl (NULL_TREE);
7016c612 5746 val = build_int_cst (gfc_array_index_type, el->id);
b6e3dd65 5747 tmp = build_case_label (val, NULL_TREE, label);
1b716045 5748 gfc_add_expr_to_block (&block, tmp);
5b11d932 5749
1b716045 5750 /* And jump to the actual entry point. */
5751 label = gfc_build_label_decl (NULL_TREE);
1b716045 5752 tmp = build1_v (GOTO_EXPR, label);
5753 gfc_add_expr_to_block (&block, tmp);
5754
5755 /* Save the label decl. */
5756 el->label = label;
5757 }
5758 tmp = gfc_finish_block (&block);
5759 /* The first argument selects the entry point. */
5760 val = DECL_ARGUMENTS (current_function_decl);
bd37ce3e 5761 tmp = fold_build2_loc (input_location, SWITCH_EXPR, NULL_TREE, val, tmp);
1b716045 5762 return tmp;
4ee9c684 5763}
5764
6374121b 5765
a4abf8a0 5766/* Add code to string lengths of actual arguments passed to a function against
5767 the expected lengths of the dummy arguments. */
5768
5769static void
5770add_argument_checking (stmtblock_t *block, gfc_symbol *sym)
5771{
5772 gfc_formal_arglist *formal;
5773
6777213b 5774 for (formal = gfc_sym_get_dummy_args (sym); formal; formal = formal->next)
517c89e5 5775 if (formal->sym && formal->sym->ts.type == BT_CHARACTER
6c3000f4 5776 && !formal->sym->ts.deferred)
a4abf8a0 5777 {
5778 enum tree_code comparison;
5779 tree cond;
5780 tree argname;
5781 gfc_symbol *fsym;
5782 gfc_charlen *cl;
5783 const char *message;
5784
5785 fsym = formal->sym;
eeebe20b 5786 cl = fsym->ts.u.cl;
a4abf8a0 5787
5788 gcc_assert (cl);
5789 gcc_assert (cl->passed_length != NULL_TREE);
5790 gcc_assert (cl->backend_decl != NULL_TREE);
5791
5792 /* For POINTER, ALLOCATABLE and assumed-shape dummy arguments, the
5793 string lengths must match exactly. Otherwise, it is only required
be4be771 5794 that the actual string length is *at least* the expected one.
5795 Sequence association allows for a mismatch of the string length
5796 if the actual argument is (part of) an array, but only if the
5797 dummy argument is an array. (See "Sequence association" in
5798 Section 12.4.1.4 for F95 and 12.4.1.5 for F2003.) */
517c89e5 5799 if (fsym->attr.pointer || fsym->attr.allocatable
f00f6dd6 5800 || (fsym->as && (fsym->as->type == AS_ASSUMED_SHAPE
5801 || fsym->as->type == AS_ASSUMED_RANK)))
a4abf8a0 5802 {
5803 comparison = NE_EXPR;
5804 message = _("Actual string length does not match the declared one"
5805 " for dummy argument '%s' (%ld/%ld)");
5806 }
be4be771 5807 else if (fsym->as && fsym->as->rank != 0)
5808 continue;
a4abf8a0 5809 else
5810 {
5811 comparison = LT_EXPR;
5812 message = _("Actual string length is shorter than the declared one"
5813 " for dummy argument '%s' (%ld/%ld)");
5814 }
5815
5816 /* Build the condition. For optional arguments, an actual length
5817 of 0 is also acceptable if the associated string is NULL, which
5818 means the argument was not passed. */
4c796f54 5819 cond = fold_build2_loc (input_location, comparison, logical_type_node,
fd779e1d 5820 cl->passed_length, cl->backend_decl);
a4abf8a0 5821 if (fsym->attr.optional)
5822 {
5823 tree not_absent;
5824 tree not_0length;
5825 tree absent_failed;
5826
fd779e1d 5827 not_0length = fold_build2_loc (input_location, NE_EXPR,
4c796f54 5828 logical_type_node,
fd779e1d 5829 cl->passed_length,
385f3f36 5830 build_zero_cst (gfc_charlen_type_node));
5fa0fdc2 5831 /* The symbol needs to be referenced for gfc_get_symbol_decl. */
5832 fsym->attr.referenced = 1;
5833 not_absent = gfc_conv_expr_present (fsym);
a4abf8a0 5834
fd779e1d 5835 absent_failed = fold_build2_loc (input_location, TRUTH_OR_EXPR,
4c796f54 5836 logical_type_node, not_0length,
fd779e1d 5837 not_absent);
a4abf8a0 5838
fd779e1d 5839 cond = fold_build2_loc (input_location, TRUTH_AND_EXPR,
4c796f54 5840 logical_type_node, cond, absent_failed);
a4abf8a0 5841 }
5842
5843 /* Build the runtime check. */
5844 argname = gfc_build_cstring_const (fsym->name);
5845 argname = gfc_build_addr_expr (pchar_type_node, argname);
5846 gfc_trans_runtime_check (true, false, cond, block, &fsym->declared_at,
5847 message, argname,
5848 fold_convert (long_integer_type_node,
5849 cl->passed_length),
5850 fold_convert (long_integer_type_node,
5851 cl->backend_decl));
5852 }
5853}
5854
5855
7257a5d2 5856static void
5857create_main_function (tree fndecl)
5858{
43702da6 5859 tree old_context;
7257a5d2 5860 tree ftn_main;
5861 tree tmp, decl, result_decl, argc, argv, typelist, arglist;
5862 stmtblock_t body;
5863
43702da6 5864 old_context = current_function_decl;
5865
5866 if (old_context)
5867 {
5868 push_function_context ();
5869 saved_parent_function_decls = saved_function_decls;
5870 saved_function_decls = NULL_TREE;
5871 }
5872
7257a5d2 5873 /* main() function must be declared with global scope. */
5874 gcc_assert (current_function_decl == NULL_TREE);
5875
5876 /* Declare the function. */
5877 tmp = build_function_type_list (integer_type_node, integer_type_node,
5878 build_pointer_type (pchar_type_node),
5879 NULL_TREE);
0509d0ee 5880 main_identifier_node = get_identifier ("main");
e60a6f7b 5881 ftn_main = build_decl (input_location, FUNCTION_DECL,
5882 main_identifier_node, tmp);
7257a5d2 5883 DECL_EXTERNAL (ftn_main) = 0;
5884 TREE_PUBLIC (ftn_main) = 1;
5885 TREE_STATIC (ftn_main) = 1;
5886 DECL_ATTRIBUTES (ftn_main)
5887 = tree_cons (get_identifier("externally_visible"), NULL_TREE, NULL_TREE);
5888
5889 /* Setup the result declaration (for "return 0"). */
e60a6f7b 5890 result_decl = build_decl (input_location,
5891 RESULT_DECL, NULL_TREE, integer_type_node);
7257a5d2 5892 DECL_ARTIFICIAL (result_decl) = 1;
5893 DECL_IGNORED_P (result_decl) = 1;
5894 DECL_CONTEXT (result_decl) = ftn_main;
5895 DECL_RESULT (ftn_main) = result_decl;
5896
5897 pushdecl (ftn_main);
5898
5899 /* Get the arguments. */
5900
5901 arglist = NULL_TREE;
5902 typelist = TYPE_ARG_TYPES (TREE_TYPE (ftn_main));
5903
5904 tmp = TREE_VALUE (typelist);
e60a6f7b 5905 argc = build_decl (input_location, PARM_DECL, get_identifier ("argc"), tmp);
7257a5d2 5906 DECL_CONTEXT (argc) = ftn_main;
5907 DECL_ARG_TYPE (argc) = TREE_VALUE (typelist);
5908 TREE_READONLY (argc) = 1;
5909 gfc_finish_decl (argc);
5910 arglist = chainon (arglist, argc);
5911
5912 typelist = TREE_CHAIN (typelist);
5913 tmp = TREE_VALUE (typelist);
e60a6f7b 5914 argv = build_decl (input_location, PARM_DECL, get_identifier ("argv"), tmp);
7257a5d2 5915 DECL_CONTEXT (argv) = ftn_main;
5916 DECL_ARG_TYPE (argv) = TREE_VALUE (typelist);
5917 TREE_READONLY (argv) = 1;
5918 DECL_BY_REFERENCE (argv) = 1;
5919 gfc_finish_decl (argv);
5920 arglist = chainon (arglist, argv);
5921
5922 DECL_ARGUMENTS (ftn_main) = arglist;
5923 current_function_decl = ftn_main;
5924 announce_function (ftn_main);
5925
5926 rest_of_decl_compilation (ftn_main, 1, 0);
5927 make_decl_rtl (ftn_main);
00cf115c 5928 allocate_struct_function (ftn_main, false);
cde2be84 5929 pushlevel ();
7257a5d2 5930
5931 gfc_init_block (&body);
5932
293d72e0 5933 /* Call some libgfortran initialization routines, call then MAIN__(). */
7257a5d2 5934
d44f2f7c 5935 /* Call _gfortran_caf_init (*argc, ***argv). */
4fe73152 5936 if (flag_coarray == GFC_FCOARRAY_LIB)
70b5944a 5937 {
5938 tree pint_type, pppchar_type;
5939 pint_type = build_pointer_type (integer_type_node);
5940 pppchar_type
5941 = build_pointer_type (build_pointer_type (pchar_type_node));
5942
d44f2f7c 5943 tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_init, 2,
70b5944a 5944 gfc_build_addr_expr (pint_type, argc),
d44f2f7c 5945 gfc_build_addr_expr (pppchar_type, argv));
70b5944a 5946 gfc_add_expr_to_block (&body, tmp);
5947 }
5948
7257a5d2 5949 /* Call _gfortran_set_args (argc, argv). */
43702da6 5950 TREE_USED (argc) = 1;
5951 TREE_USED (argv) = 1;
389dd41b 5952 tmp = build_call_expr_loc (input_location,
5953 gfor_fndecl_set_args, 2, argc, argv);
7257a5d2 5954 gfc_add_expr_to_block (&body, tmp);
5955
5956 /* Add a call to set_options to set up the runtime library Fortran
5957 language standard parameters. */
5958 {
5959 tree array_type, array, var;
f1f41a6c 5960 vec<constructor_elt, va_gc> *v = NULL;
f7619ded 5961 static const int noptions = 7;
7257a5d2 5962
f7619ded 5963 /* Passing a new option to the library requires three modifications:
5964 + add it to the tree_cons list below
5965 + change the noptions variable above
7257a5d2 5966 + modify the library (runtime/compile_options.c)! */
5967
06f13dc1 5968 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5969 build_int_cst (integer_type_node,
5970 gfc_option.warn_std));
5971 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5972 build_int_cst (integer_type_node,
5973 gfc_option.allow_std));
5974 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5975 build_int_cst (integer_type_node, pedantic));
06f13dc1 5976 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
829d7a08 5977 build_int_cst (integer_type_node, flag_backtrace));
06f13dc1 5978 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
829d7a08 5979 build_int_cst (integer_type_node, flag_sign_zero));
06f13dc1 5980 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5981 build_int_cst (integer_type_node,
5982 (gfc_option.rtcheck
5983 & GFC_RTCHECK_BOUNDS)));
5984 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE,
5985 build_int_cst (integer_type_node,
553e7cef 5986 gfc_option.fpe_summary));
7257a5d2 5987
f7619ded 5988 array_type = build_array_type_nelts (integer_type_node, noptions);
06f13dc1 5989 array = build_constructor (array_type, v);
7257a5d2 5990 TREE_CONSTANT (array) = 1;
5991 TREE_STATIC (array) = 1;
5992
5993 /* Create a static variable to hold the jump table. */
bf77f8ee 5994 var = build_decl (input_location, VAR_DECL,
f7619ded 5995 create_tmp_var_name ("options"), array_type);
bf77f8ee 5996 DECL_ARTIFICIAL (var) = 1;
5997 DECL_IGNORED_P (var) = 1;
7257a5d2 5998 TREE_CONSTANT (var) = 1;
5999 TREE_STATIC (var) = 1;
6000 TREE_READONLY (var) = 1;
6001 DECL_INITIAL (var) = array;
bf77f8ee 6002 pushdecl (var);
7257a5d2 6003 var = gfc_build_addr_expr (build_pointer_type (integer_type_node), var);
6004
389dd41b 6005 tmp = build_call_expr_loc (input_location,
6006 gfor_fndecl_set_options, 2,
f7619ded 6007 build_int_cst (integer_type_node, noptions), var);
7257a5d2 6008 gfc_add_expr_to_block (&body, tmp);
6009 }
6010
6011 /* If -ffpe-trap option was provided, add a call to set_fpe so that
6012 the library will raise a FPE when needed. */
6013 if (gfc_option.fpe != 0)
6014 {
389dd41b 6015 tmp = build_call_expr_loc (input_location,
6016 gfor_fndecl_set_fpe, 1,
7257a5d2 6017 build_int_cst (integer_type_node,
6018 gfc_option.fpe));
6019 gfc_add_expr_to_block (&body, tmp);
6020 }
6021
6022 /* If this is the main program and an -fconvert option was provided,
6023 add a call to set_convert. */
6024
4fe73152 6025 if (flag_convert != GFC_FLAG_CONVERT_NATIVE)
7257a5d2 6026 {
389dd41b 6027 tmp = build_call_expr_loc (input_location,
6028 gfor_fndecl_set_convert, 1,
4fe73152 6029 build_int_cst (integer_type_node, flag_convert));
7257a5d2 6030 gfc_add_expr_to_block (&body, tmp);
6031 }
6032
6033 /* If this is the main program and an -frecord-marker option was provided,
6034 add a call to set_record_marker. */
6035
eb106faf 6036 if (flag_record_marker != 0)
7257a5d2 6037 {
389dd41b 6038 tmp = build_call_expr_loc (input_location,
6039 gfor_fndecl_set_record_marker, 1,
7257a5d2 6040 build_int_cst (integer_type_node,
eb106faf 6041 flag_record_marker));
7257a5d2 6042 gfc_add_expr_to_block (&body, tmp);
6043 }
6044
eb106faf 6045 if (flag_max_subrecord_length != 0)
7257a5d2 6046 {
389dd41b 6047 tmp = build_call_expr_loc (input_location,
6048 gfor_fndecl_set_max_subrecord_length, 1,
7257a5d2 6049 build_int_cst (integer_type_node,
eb106faf 6050 flag_max_subrecord_length));
7257a5d2 6051 gfc_add_expr_to_block (&body, tmp);
6052 }
6053
6054 /* Call MAIN__(). */
389dd41b 6055 tmp = build_call_expr_loc (input_location,
6056 fndecl, 0);
7257a5d2 6057 gfc_add_expr_to_block (&body, tmp);
6058
43702da6 6059 /* Mark MAIN__ as used. */
6060 TREE_USED (fndecl) = 1;
6061
70b5944a 6062 /* Coarray: Call _gfortran_caf_finalize(void). */
4fe73152 6063 if (flag_coarray == GFC_FCOARRAY_LIB)
a90fe829 6064 {
70b5944a 6065 tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_finalize, 0);
6066 gfc_add_expr_to_block (&body, tmp);
6067 }
6068
7257a5d2 6069 /* "return 0". */
fd779e1d 6070 tmp = fold_build2_loc (input_location, MODIFY_EXPR, integer_type_node,
6071 DECL_RESULT (ftn_main),
6072 build_int_cst (integer_type_node, 0));
7257a5d2 6073 tmp = build1_v (RETURN_EXPR, tmp);
6074 gfc_add_expr_to_block (&body, tmp);
6075
6076
6077 DECL_SAVED_TREE (ftn_main) = gfc_finish_block (&body);
6078 decl = getdecls ();
6079
6080 /* Finish off this function and send it for code generation. */
cde2be84 6081 poplevel (1, 1);
7257a5d2 6082 BLOCK_SUPERCONTEXT (DECL_INITIAL (ftn_main)) = ftn_main;
6083
6084 DECL_SAVED_TREE (ftn_main)
6085 = build3_v (BIND_EXPR, decl, DECL_SAVED_TREE (ftn_main),
6086 DECL_INITIAL (ftn_main));
6087
6088 /* Output the GENERIC tree. */
6089 dump_function (TDI_original, ftn_main);
6090
35ee1c66 6091 cgraph_node::finalize_function (ftn_main, true);
43702da6 6092
6093 if (old_context)
6094 {
6095 pop_function_context ();
6096 saved_function_decls = saved_parent_function_decls;
6097 }
6098 current_function_decl = old_context;
7257a5d2 6099}
6100
6101
89ac8ba1 6102/* Generate an appropriate return-statement for a procedure. */
6103
6104tree
6105gfc_generate_return (void)
6106{
6107 gfc_symbol* sym;
6108 tree result;
6109 tree fndecl;
6110
6111 sym = current_procedure_symbol;
6112 fndecl = sym->backend_decl;
6113
6114 if (TREE_TYPE (DECL_RESULT (fndecl)) == void_type_node)
6115 result = NULL_TREE;
6116 else
6117 {
6118 result = get_proc_result (sym);
6119
6120 /* Set the return value to the dummy result variable. The
6121 types may be different for scalar default REAL functions
6122 with -ff2c, therefore we have to convert. */
6123 if (result != NULL_TREE)
6124 {
6125 result = convert (TREE_TYPE (DECL_RESULT (fndecl)), result);
fd779e1d 6126 result = fold_build2_loc (input_location, MODIFY_EXPR,
6127 TREE_TYPE (result), DECL_RESULT (fndecl),
6128 result);
89ac8ba1 6129 }
6130 }
6131
6132 return build1_v (RETURN_EXPR, result);
6133}
6134
6135
d566c3e0 6136static void
6137is_from_ieee_module (gfc_symbol *sym)
6138{
6139 if (sym->from_intmod == INTMOD_IEEE_FEATURES
6140 || sym->from_intmod == INTMOD_IEEE_EXCEPTIONS
6141 || sym->from_intmod == INTMOD_IEEE_ARITHMETIC)
6142 seen_ieee_symbol = 1;
6143}
6144
6145
6146static int
6147is_ieee_module_used (gfc_namespace *ns)
6148{
6149 seen_ieee_symbol = 0;
6150 gfc_traverse_ns (ns, is_from_ieee_module);
6151 return seen_ieee_symbol;
6152}
6153
6154
01d728a4 6155static gfc_omp_clauses *module_oacc_clauses;
6156
6157
6158static void
6159add_clause (gfc_symbol *sym, gfc_omp_map_op map_op)
6160{
6161 gfc_omp_namelist *n;
6162
6163 n = gfc_get_omp_namelist ();
6164 n->sym = sym;
6165 n->u.map_op = map_op;
6166
6167 if (!module_oacc_clauses)
6168 module_oacc_clauses = gfc_get_omp_clauses ();
6169
6170 if (module_oacc_clauses->lists[OMP_LIST_MAP])
6171 n->next = module_oacc_clauses->lists[OMP_LIST_MAP];
6172
6173 module_oacc_clauses->lists[OMP_LIST_MAP] = n;
6174}
6175
6176
6177static void
6178find_module_oacc_declare_clauses (gfc_symbol *sym)
6179{
6180 if (sym->attr.use_assoc)
6181 {
6182 gfc_omp_map_op map_op;
6183
6184 if (sym->attr.oacc_declare_create)
6185 map_op = OMP_MAP_FORCE_ALLOC;
6186
6187 if (sym->attr.oacc_declare_copyin)
6188 map_op = OMP_MAP_FORCE_TO;
6189
6190 if (sym->attr.oacc_declare_deviceptr)
6191 map_op = OMP_MAP_FORCE_DEVICEPTR;
6192
6193 if (sym->attr.oacc_declare_device_resident)
6194 map_op = OMP_MAP_DEVICE_RESIDENT;
6195
6196 if (sym->attr.oacc_declare_create
6197 || sym->attr.oacc_declare_copyin
6198 || sym->attr.oacc_declare_deviceptr
6199 || sym->attr.oacc_declare_device_resident)
6200 {
6201 sym->attr.referenced = 1;
6202 add_clause (sym, map_op);
6203 }
6204 }
6205}
6206
6207
6208void
6209finish_oacc_declare (gfc_namespace *ns, gfc_symbol *sym, bool block)
6210{
6211 gfc_code *code;
6212 gfc_oacc_declare *oc;
6213 locus where = gfc_current_locus;
6214 gfc_omp_clauses *omp_clauses = NULL;
6215 gfc_omp_namelist *n, *p;
6216
6217 gfc_traverse_ns (ns, find_module_oacc_declare_clauses);
6218
6219 if (module_oacc_clauses && sym->attr.flavor == FL_PROGRAM)
6220 {
6221 gfc_oacc_declare *new_oc;
6222
6223 new_oc = gfc_get_oacc_declare ();
6224 new_oc->next = ns->oacc_declare;
6225 new_oc->clauses = module_oacc_clauses;
6226
6227 ns->oacc_declare = new_oc;
6228 module_oacc_clauses = NULL;
6229 }
6230
6231 if (!ns->oacc_declare)
6232 return;
6233
6234 for (oc = ns->oacc_declare; oc; oc = oc->next)
6235 {
6236 if (oc->module_var)
6237 continue;
6238
6239 if (block)
f187ad6c 6240 gfc_error ("Sorry, !$ACC DECLARE at %L is not allowed "
01d728a4 6241 "in BLOCK construct", &oc->loc);
6242
6243
6244 if (oc->clauses && oc->clauses->lists[OMP_LIST_MAP])
6245 {
6246 if (omp_clauses == NULL)
6247 {
6248 omp_clauses = oc->clauses;
6249 continue;
6250 }
6251
6252 for (n = oc->clauses->lists[OMP_LIST_MAP]; n; p = n, n = n->next)
6253 ;
6254
6255 gcc_assert (p->next == NULL);
6256
6257 p->next = omp_clauses->lists[OMP_LIST_MAP];
6258 omp_clauses = oc->clauses;
6259 }
6260 }
6261
6262 if (!omp_clauses)
6263 return;
6264
6265 for (n = omp_clauses->lists[OMP_LIST_MAP]; n; n = n->next)
6266 {
6267 switch (n->u.map_op)
6268 {
6269 case OMP_MAP_DEVICE_RESIDENT:
6270 n->u.map_op = OMP_MAP_FORCE_ALLOC;
6271 break;
6272
6273 default:
6274 break;
6275 }
6276 }
6277
6278 code = XCNEW (gfc_code);
6279 code->op = EXEC_OACC_DECLARE;
6280 code->loc = where;
6281
6282 code->ext.oacc_declare = gfc_get_oacc_declare ();
6283 code->ext.oacc_declare->clauses = omp_clauses;
6284
6285 code->block = XCNEW (gfc_code);
6286 code->block->op = EXEC_OACC_DECLARE;
6287 code->block->loc = where;
6288
6289 if (ns->code)
6290 code->block->next = ns->code;
6291
6292 ns->code = code;
6293
6294 return;
6295}
6296
6297
4ee9c684 6298/* Generate code for a function. */
6299
6300void
6301gfc_generate_function_code (gfc_namespace * ns)
6302{
6303 tree fndecl;
6304 tree old_context;
6305 tree decl;
6306 tree tmp;
d566c3e0 6307 tree fpstate = NULL_TREE;
89ac8ba1 6308 stmtblock_t init, cleanup;
4ee9c684 6309 stmtblock_t body;
89ac8ba1 6310 gfc_wrapped_block try_block;
5fa0fdc2 6311 tree recurcheckvar = NULL_TREE;
4ee9c684 6312 gfc_symbol *sym;
89ac8ba1 6313 gfc_symbol *previous_procedure_symbol;
d566c3e0 6314 int rank, ieee;
e50e62f5 6315 bool is_recursive;
4ee9c684 6316
6317 sym = ns->proc_name;
89ac8ba1 6318 previous_procedure_symbol = current_procedure_symbol;
6319 current_procedure_symbol = sym;
1b716045 6320
8b7e5587 6321 /* Initialize sym->tlink so that gfc_trans_deferred_vars does not get
6322 lost or worse. */
4ee9c684 6323 sym->tlink = sym;
6324
6325 /* Create the declaration for functions with global scope. */
6326 if (!sym->backend_decl)
d896f9b3 6327 gfc_create_function_decl (ns, false);
4ee9c684 6328
6329 fndecl = sym->backend_decl;
6330 old_context = current_function_decl;
6331
6332 if (old_context)
6333 {
6334 push_function_context ();
6335 saved_parent_function_decls = saved_function_decls;
6336 saved_function_decls = NULL_TREE;
6337 }
6338
1b716045 6339 trans_function_start (sym);
4ee9c684 6340
89ac8ba1 6341 gfc_init_block (&init);
4ee9c684 6342
c6871095 6343 if (ns->entries && ns->proc_name->ts.type == BT_CHARACTER)
6344 {
6345 /* Copy length backend_decls to all entry point result
6346 symbols. */
6347 gfc_entry_list *el;
6348 tree backend_decl;
6349
eeebe20b 6350 gfc_conv_const_charlen (ns->proc_name->ts.u.cl);
6351 backend_decl = ns->proc_name->result->ts.u.cl->backend_decl;
c6871095 6352 for (el = ns->entries; el; el = el->next)
eeebe20b 6353 el->sym->result->ts.u.cl->backend_decl = backend_decl;
c6871095 6354 }
6355
4ee9c684 6356 /* Translate COMMON blocks. */
6357 gfc_trans_common (ns);
6358
c750cc52 6359 /* Null the parent fake result declaration if this namespace is
6360 a module function or an external procedures. */
6361 if ((ns->parent && ns->parent->proc_name->attr.flavor == FL_MODULE)
6362 || ns->parent == NULL)
6363 parent_fake_result_decl = NULL_TREE;
6364
2b685f8e 6365 gfc_generate_contained_functions (ns);
6366
9579733e 6367 nonlocal_dummy_decls = NULL;
6368 nonlocal_dummy_decl_pset = NULL;
6369
a961ca30 6370 has_coarray_vars = false;
4ee9c684 6371 generate_local_vars (ns);
5b11d932 6372
4fe73152 6373 if (flag_coarray == GFC_FCOARRAY_LIB && has_coarray_vars)
a961ca30 6374 generate_coarray_init (ns);
6375
c750cc52 6376 /* Keep the parent fake result declaration in module functions
6377 or external procedures. */
6378 if ((ns->parent && ns->parent->proc_name->attr.flavor == FL_MODULE)
6379 || ns->parent == NULL)
6380 current_fake_result_decl = parent_fake_result_decl;
6381 else
6382 current_fake_result_decl = NULL_TREE;
6383
89ac8ba1 6384 is_recursive = sym->attr.recursive
6385 || (sym->attr.entry_master
6386 && sym->ns->entries->sym->attr.recursive);
6387 if ((gfc_option.rtcheck & GFC_RTCHECK_RECURSION)
829d7a08 6388 && !is_recursive && !flag_recursive)
89ac8ba1 6389 {
6390 char * msg;
6391
87fda26c 6392 msg = xasprintf ("Recursive call to nonrecursive procedure '%s'",
6393 sym->name);
4c796f54 6394 recurcheckvar = gfc_create_var (logical_type_node, "is_recursive");
89ac8ba1 6395 TREE_STATIC (recurcheckvar) = 1;
4c796f54 6396 DECL_INITIAL (recurcheckvar) = logical_false_node;
89ac8ba1 6397 gfc_add_expr_to_block (&init, recurcheckvar);
6398 gfc_trans_runtime_check (true, false, recurcheckvar, &init,
6399 &sym->declared_at, msg);
4c796f54 6400 gfc_add_modify (&init, recurcheckvar, logical_true_node);
434f0922 6401 free (msg);
89ac8ba1 6402 }
4ee9c684 6403
d566c3e0 6404 /* Check if an IEEE module is used in the procedure. If so, save
6405 the floating point state. */
6406 ieee = is_ieee_module_used (ns);
6407 if (ieee)
d7333535 6408 fpstate = gfc_save_fp_state (&init);
d566c3e0 6409
4ee9c684 6410 /* Now generate the code for the body of this function. */
6411 gfc_init_block (&body);
6412
6413 if (TREE_TYPE (DECL_RESULT (fndecl)) != void_type_node
89ac8ba1 6414 && sym->attr.subroutine)
4ee9c684 6415 {
6416 tree alternate_return;
c750cc52 6417 alternate_return = gfc_get_fake_result_decl (sym, 0);
75a70cf9 6418 gfc_add_modify (&body, alternate_return, integer_zero_node);
4ee9c684 6419 }
6420
1b716045 6421 if (ns->entries)
6422 {
6423 /* Jump to the correct entry point. */
6424 tmp = gfc_trans_entry_master_switch (ns->entries);
6425 gfc_add_expr_to_block (&body, tmp);
6426 }
6427
a4abf8a0 6428 /* If bounds-checking is enabled, generate code to check passed in actual
6429 arguments against the expected dummy argument attributes (e.g. string
6430 lengths). */
c1630d65 6431 if ((gfc_option.rtcheck & GFC_RTCHECK_BOUNDS) && !sym->attr.is_bind_c)
a4abf8a0 6432 add_argument_checking (&body, sym);
6433
01d728a4 6434 finish_oacc_declare (ns, sym, false);
ca4c3545 6435
4ee9c684 6436 tmp = gfc_trans_code (ns->code);
6437 gfc_add_expr_to_block (&body, tmp);
6438
1caa6ab1 6439 if (TREE_TYPE (DECL_RESULT (fndecl)) != void_type_node
6440 || (sym->result && sym->result != sym
6441 && sym->result->ts.type == BT_DERIVED
6442 && sym->result->ts.u.derived->attr.alloc_comp))
4ee9c684 6443 {
1caa6ab1 6444 bool artificial_result_decl = false;
89ac8ba1 6445 tree result = get_proc_result (sym);
1caa6ab1 6446 gfc_symbol *rsym = sym == sym->result ? sym : sym->result;
6447
6448 /* Make sure that a function returning an object with
6449 alloc/pointer_components always has a result, where at least
6450 the allocatable/pointer components are set to zero. */
6451 if (result == NULL_TREE && sym->attr.function
6452 && ((sym->result->ts.type == BT_DERIVED
6453 && (sym->attr.allocatable
6454 || sym->attr.pointer
6455 || sym->result->ts.u.derived->attr.alloc_comp
6456 || sym->result->ts.u.derived->attr.pointer_comp))
6457 || (sym->result->ts.type == BT_CLASS
6458 && (CLASS_DATA (sym)->attr.allocatable
6459 || CLASS_DATA (sym)->attr.class_pointer
6460 || CLASS_DATA (sym->result)->attr.alloc_comp
6461 || CLASS_DATA (sym->result)->attr.pointer_comp))))
6462 {
6463 artificial_result_decl = true;
6464 result = gfc_get_fake_result_decl (sym, 0);
6465 }
4ee9c684 6466
42766cb3 6467 if (result != NULL_TREE && sym->attr.function && !sym->attr.pointer)
2294b616 6468 {
deb7edfc 6469 if (sym->attr.allocatable && sym->attr.dimension == 0
6470 && sym->result == sym)
6471 gfc_add_modify (&init, result, fold_convert (TREE_TYPE (result),
6472 null_pointer_node));
42766cb3 6473 else if (sym->ts.type == BT_CLASS
6474 && CLASS_DATA (sym)->attr.allocatable
3a19c063 6475 && CLASS_DATA (sym)->attr.dimension == 0
6476 && sym->result == sym)
42766cb3 6477 {
6478 tmp = CLASS_DATA (sym)->backend_decl;
6479 tmp = fold_build3_loc (input_location, COMPONENT_REF,
6480 TREE_TYPE (tmp), result, tmp, NULL_TREE);
6481 gfc_add_modify (&init, tmp, fold_convert (TREE_TYPE (tmp),
6482 null_pointer_node));
6483 }
deb7edfc 6484 else if (sym->ts.type == BT_DERIVED
42766cb3 6485 && !sym->attr.allocatable)
53169279 6486 {
1caa6ab1 6487 gfc_expr *init_exp;
6488 /* Arrays are not initialized using the default initializer of
6489 their elements. Therefore only check if a default
6490 initializer is available when the result is scalar. */
36d310d0 6491 init_exp = rsym->as ? NULL
6492 : gfc_generate_initializer (&rsym->ts, true);
1caa6ab1 6493 if (init_exp)
6494 {
6495 tmp = gfc_trans_structure_assign (result, init_exp, 0);
6496 gfc_free_expr (init_exp);
6497 gfc_add_expr_to_block (&init, tmp);
6498 }
6499 else if (rsym->ts.u.derived->attr.alloc_comp)
6500 {
6501 rank = rsym->as ? rsym->as->rank : 0;
6502 tmp = gfc_nullify_alloc_comp (rsym->ts.u.derived, result,
6503 rank);
6504 gfc_prepend_expr_to_block (&body, tmp);
6505 }
53169279 6506 }
5176859a 6507 }
e50e62f5 6508
1caa6ab1 6509 if (result == NULL_TREE || artificial_result_decl)
fa7b6574 6510 {
6511 /* TODO: move to the appropriate place in resolve.c. */
8b72061f 6512 if (warn_return_type > 0 && sym == sym->result)
4166acc7 6513 gfc_warning (OPT_Wreturn_type,
6514 "Return value of function %qs at %L not set",
fa7b6574 6515 sym->name, &sym->declared_at);
8b72061f 6516 if (warn_return_type > 0)
90a4a5a6 6517 TREE_NO_WARNING(sym->backend_decl) = 1;
fa7b6574 6518 }
1caa6ab1 6519 if (result != NULL_TREE)
89ac8ba1 6520 gfc_add_expr_to_block (&body, gfc_generate_return ());
4ee9c684 6521 }
89ac8ba1 6522
6523 gfc_init_block (&cleanup);
6524
6525 /* Reset recursion-check variable. */
6526 if ((gfc_option.rtcheck & GFC_RTCHECK_RECURSION)
829d7a08 6527 && !is_recursive && !flag_openmp && recurcheckvar != NULL_TREE)
e50e62f5 6528 {
4c796f54 6529 gfc_add_modify (&cleanup, recurcheckvar, logical_false_node);
89ac8ba1 6530 recurcheckvar = NULL;
e50e62f5 6531 }
2294b616 6532
d566c3e0 6533 /* If IEEE modules are loaded, restore the floating-point state. */
6534 if (ieee)
d7333535 6535 gfc_restore_fp_state (&cleanup, fpstate);
d566c3e0 6536
89ac8ba1 6537 /* Finish the function body and add init and cleanup code. */
6538 tmp = gfc_finish_block (&body);
6539 gfc_start_wrapped_block (&try_block, tmp);
6540 /* Add code to create and cleanup arrays. */
6541 gfc_trans_deferred_vars (sym, &try_block);
6542 gfc_add_init_cleanup (&try_block, gfc_finish_block (&init),
6543 gfc_finish_block (&cleanup));
4ee9c684 6544
6545 /* Add all the decls we created during processing. */
267f3c67 6546 decl = nreverse (saved_function_decls);
4ee9c684 6547 while (decl)
6548 {
6549 tree next;
6550
1767a056 6551 next = DECL_CHAIN (decl);
6552 DECL_CHAIN (decl) = NULL_TREE;
4c197fd0 6553 pushdecl (decl);
4ee9c684 6554 decl = next;
6555 }
6556 saved_function_decls = NULL_TREE;
6557
89ac8ba1 6558 DECL_SAVED_TREE (fndecl) = gfc_finish_wrapped_block (&try_block);
e5004242 6559 decl = getdecls ();
4ee9c684 6560
6561 /* Finish off this function and send it for code generation. */
cde2be84 6562 poplevel (1, 1);
4ee9c684 6563 BLOCK_SUPERCONTEXT (DECL_INITIAL (fndecl)) = fndecl;
6564
e5004242 6565 DECL_SAVED_TREE (fndecl)
6566 = build3_v (BIND_EXPR, decl, DECL_SAVED_TREE (fndecl),
6567 DECL_INITIAL (fndecl));
6568
9579733e 6569 if (nonlocal_dummy_decls)
6570 {
6571 BLOCK_VARS (DECL_INITIAL (fndecl))
6572 = chainon (BLOCK_VARS (DECL_INITIAL (fndecl)), nonlocal_dummy_decls);
431205b7 6573 delete nonlocal_dummy_decl_pset;
9579733e 6574 nonlocal_dummy_decls = NULL;
6575 nonlocal_dummy_decl_pset = NULL;
6576 }
6577
4ee9c684 6578 /* Output the GENERIC tree. */
6579 dump_function (TDI_original, fndecl);
6580
6581 /* Store the end of the function, so that we get good line number
6582 info for the epilogue. */
6583 cfun->function_end_locus = input_location;
6584
6585 /* We're leaving the context of this function, so zap cfun.
6586 It's still in DECL_STRUCT_FUNCTION, and we'll restore it in
6587 tree_rest_of_compilation. */
87d4aa85 6588 set_cfun (NULL);
4ee9c684 6589
6590 if (old_context)
6591 {
6592 pop_function_context ();
6593 saved_function_decls = saved_parent_function_decls;
6594 }
6595 current_function_decl = old_context;
6596
1f7747bd 6597 if (decl_function_context (fndecl))
6598 {
6599 /* Register this function with cgraph just far enough to get it
6600 added to our parent's nested function list.
6601 If there are static coarrays in this function, the nested _caf_init
6602 function has already called cgraph_create_node, which also created
6603 the cgraph node for this function. */
4fe73152 6604 if (!has_coarray_vars || flag_coarray != GFC_FCOARRAY_LIB)
0d565f19 6605 (void) cgraph_node::get_create (fndecl);
1f7747bd 6606 }
4ee9c684 6607 else
35ee1c66 6608 cgraph_node::finalize_function (fndecl, true);
df4d540f 6609
6610 gfc_trans_use_stmts (ns);
2eb674c9 6611 gfc_traverse_ns (ns, gfc_emit_parameter_debug_info);
7257a5d2 6612
6613 if (sym->attr.is_main_program)
6614 create_main_function (fndecl);
89ac8ba1 6615
6616 current_procedure_symbol = previous_procedure_symbol;
4ee9c684 6617}
6618
7257a5d2 6619
4ee9c684 6620void
6621gfc_generate_constructors (void)
6622{
22d678e8 6623 gcc_assert (gfc_static_ctors == NULL_TREE);
4ee9c684 6624#if 0
6625 tree fnname;
6626 tree type;
6627 tree fndecl;
6628 tree decl;
6629 tree tmp;
6630
6631 if (gfc_static_ctors == NULL_TREE)
6632 return;
6633
db85cc4f 6634 fnname = get_file_function_name ("I");
e1036019 6635 type = build_function_type_list (void_type_node, NULL_TREE);
4ee9c684 6636
e60a6f7b 6637 fndecl = build_decl (input_location,
6638 FUNCTION_DECL, fnname, type);
4ee9c684 6639 TREE_PUBLIC (fndecl) = 1;
6640
e60a6f7b 6641 decl = build_decl (input_location,
6642 RESULT_DECL, NULL_TREE, void_type_node);
540edea7 6643 DECL_ARTIFICIAL (decl) = 1;
6644 DECL_IGNORED_P (decl) = 1;
4ee9c684 6645 DECL_CONTEXT (decl) = fndecl;
6646 DECL_RESULT (fndecl) = decl;
6647
6648 pushdecl (fndecl);
6649
6650 current_function_decl = fndecl;
6651
b2c4af5e 6652 rest_of_decl_compilation (fndecl, 1, 0);
4ee9c684 6653
b2c4af5e 6654 make_decl_rtl (fndecl);
4ee9c684 6655
00cf115c 6656 allocate_struct_function (fndecl, false);
4ee9c684 6657
cde2be84 6658 pushlevel ();
4ee9c684 6659
6660 for (; gfc_static_ctors; gfc_static_ctors = TREE_CHAIN (gfc_static_ctors))
6661 {
389dd41b 6662 tmp = build_call_expr_loc (input_location,
6663 TREE_VALUE (gfc_static_ctors), 0);
e60a6f7b 6664 DECL_SAVED_TREE (fndecl) = build_stmt (input_location, EXPR_STMT, tmp);
4ee9c684 6665 }
6666
e5004242 6667 decl = getdecls ();
cde2be84 6668 poplevel (1, 1);
4ee9c684 6669
6670 BLOCK_SUPERCONTEXT (DECL_INITIAL (fndecl)) = fndecl;
e5004242 6671 DECL_SAVED_TREE (fndecl)
6672 = build3_v (BIND_EXPR, decl, DECL_SAVED_TREE (fndecl),
6673 DECL_INITIAL (fndecl));
4ee9c684 6674
6675 free_after_parsing (cfun);
6676 free_after_compilation (cfun);
6677
6148a911 6678 tree_rest_of_compilation (fndecl);
4ee9c684 6679
6680 current_function_decl = NULL_TREE;
6681#endif
6682}
6683
9ec7c303 6684/* Translates a BLOCK DATA program unit. This means emitting the
6685 commons contained therein plus their initializations. We also emit
6686 a globally visible symbol to make sure that each BLOCK DATA program
6687 unit remains unique. */
6688
6689void
6690gfc_generate_block_data (gfc_namespace * ns)
6691{
6692 tree decl;
6693 tree id;
6694
b31f705b 6695 /* Tell the backend the source location of the block data. */
6696 if (ns->proc_name)
6697 gfc_set_backend_locus (&ns->proc_name->declared_at);
6698 else
6699 gfc_set_backend_locus (&gfc_current_locus);
6700
6701 /* Process the DATA statements. */
9ec7c303 6702 gfc_trans_common (ns);
6703
b31f705b 6704 /* Create a global symbol with the mane of the block data. This is to
6705 generate linker errors if the same name is used twice. It is never
6706 really used. */
9ec7c303 6707 if (ns->proc_name)
6708 id = gfc_sym_mangled_function_id (ns->proc_name);
6709 else
6710 id = get_identifier ("__BLOCK_DATA__");
6711
e60a6f7b 6712 decl = build_decl (input_location,
6713 VAR_DECL, id, gfc_array_index_type);
9ec7c303 6714 TREE_PUBLIC (decl) = 1;
6715 TREE_STATIC (decl) = 1;
df4d540f 6716 DECL_IGNORED_P (decl) = 1;
9ec7c303 6717
6718 pushdecl (decl);
6719 rest_of_decl_compilation (decl, 1, 0);
6720}
6721
b549d2a5 6722
6a7084d7 6723/* Process the local variables of a BLOCK construct. */
6724
6725void
3c82e013 6726gfc_process_block_locals (gfc_namespace* ns)
6a7084d7 6727{
6728 tree decl;
6729
6730 gcc_assert (saved_local_decls == NULL_TREE);
a961ca30 6731 has_coarray_vars = false;
6732
6a7084d7 6733 generate_local_vars (ns);
6734
4fe73152 6735 if (flag_coarray == GFC_FCOARRAY_LIB && has_coarray_vars)
a961ca30 6736 generate_coarray_init (ns);
6737
267f3c67 6738 decl = nreverse (saved_local_decls);
6a7084d7 6739 while (decl)
6740 {
6741 tree next;
6742
1767a056 6743 next = DECL_CHAIN (decl);
6744 DECL_CHAIN (decl) = NULL_TREE;
6a7084d7 6745 pushdecl (decl);
6746 decl = next;
6747 }
6748 saved_local_decls = NULL_TREE;
6749}
6750
6751
4ee9c684 6752#include "gt-fortran-trans-decl.h"