comparison gcc/fortran/trans-common.c @ 145:1830386684a0

gcc-9.2.0
author anatofuz
date Thu, 13 Feb 2020 11:34:05 +0900
parents 84e7813d76e9
children
comparison
equal deleted inserted replaced
131:84e7813d76e9 145:1830386684a0
1 /* Common block and equivalence list handling 1 /* Common block and equivalence list handling
2 Copyright (C) 2000-2018 Free Software Foundation, Inc. 2 Copyright (C) 2000-2020 Free Software Foundation, Inc.
3 Contributed by Canqun Yang <canqun@nudt.edu.cn> 3 Contributed by Canqun Yang <canqun@nudt.edu.cn>
4 4
5 This file is part of GCC. 5 This file is part of GCC.
6 6
7 GCC is free software; you can redistribute it and/or modify it under 7 GCC is free software; you can redistribute it and/or modify it under
280 tree name; 280 tree name;
281 HOST_WIDE_INT offset = h->offset; 281 HOST_WIDE_INT offset = h->offset;
282 unsigned HOST_WIDE_INT desired_align, known_align; 282 unsigned HOST_WIDE_INT desired_align, known_align;
283 283
284 name = get_identifier (h->sym->name); 284 name = get_identifier (h->sym->name);
285 field = build_decl (h->sym->declared_at.lb->location, 285 field = build_decl (gfc_get_location (&h->sym->declared_at),
286 FIELD_DECL, name, h->field); 286 FIELD_DECL, name, h->field);
287 known_align = (offset & -offset) * BITS_PER_UNIT; 287 known_align = (offset & -offset) * BITS_PER_UNIT;
288 if (known_align == 0 || known_align > BIGGEST_ALIGNMENT) 288 if (known_align == 0 || known_align > BIGGEST_ALIGNMENT)
289 known_align = BIGGEST_ALIGNMENT; 289 known_align = BIGGEST_ALIGNMENT;
290 290
337 337
338 338
339 /* Get storage for local equivalence. */ 339 /* Get storage for local equivalence. */
340 340
341 static tree 341 static tree
342 build_equiv_decl (tree union_type, bool is_init, bool is_saved) 342 build_equiv_decl (tree union_type, bool is_init, bool is_saved, bool is_auto)
343 { 343 {
344 tree decl; 344 tree decl;
345 char name[18]; 345 char name[18];
346 static int serial = 0; 346 static int serial = 0;
347 347
357 decl = build_decl (input_location, 357 decl = build_decl (input_location,
358 VAR_DECL, get_identifier (name), union_type); 358 VAR_DECL, get_identifier (name), union_type);
359 DECL_ARTIFICIAL (decl) = 1; 359 DECL_ARTIFICIAL (decl) = 1;
360 DECL_IGNORED_P (decl) = 1; 360 DECL_IGNORED_P (decl) = 1;
361 361
362 if (!gfc_can_put_var_on_stack (DECL_SIZE_UNIT (decl)) 362 if (!is_auto && (!gfc_can_put_var_on_stack (DECL_SIZE_UNIT (decl))
363 || is_saved) 363 || is_saved))
364 TREE_STATIC (decl) = 1; 364 TREE_STATIC (decl) = 1;
365 365
366 TREE_ADDRESSABLE (decl) = 1; 366 TREE_ADDRESSABLE (decl) = 1;
367 TREE_USED (decl) = 1; 367 TREE_USED (decl) = 1;
368 GFC_DECL_COMMON_OR_EQUIV (decl) = 1; 368 GFC_DECL_COMMON_OR_EQUIV (decl) = 1;
557 557
558 tmp = build_int_cst (gfc_array_index_type, length - 1); 558 tmp = build_int_cst (gfc_array_index_type, length - 1);
559 tmp = build_range_type (gfc_array_index_type, 559 tmp = build_range_type (gfc_array_index_type,
560 gfc_index_zero_node, tmp); 560 gfc_index_zero_node, tmp);
561 tmp = build_array_type (type, tmp); 561 tmp = build_array_type (type, tmp);
562 field = build_decl (gfc_current_locus.lb->location, 562 field = build_decl (gfc_get_location (&gfc_current_locus),
563 FIELD_DECL, NULL_TREE, tmp); 563 FIELD_DECL, NULL_TREE, tmp);
564 564
565 known_align = BIGGEST_ALIGNMENT; 565 known_align = BIGGEST_ALIGNMENT;
566 566
567 desired_align = update_alignment_for_field (rli, field, known_align); 567 desired_align = update_alignment_for_field (rli, field, known_align);
609 tree field_init = NULL_TREE; 609 tree field_init = NULL_TREE;
610 record_layout_info rli; 610 record_layout_info rli;
611 tree decl; 611 tree decl;
612 bool is_init = false; 612 bool is_init = false;
613 bool is_saved = false; 613 bool is_saved = false;
614 bool is_auto = false;
614 615
615 /* Declare the variables inside the common block. 616 /* Declare the variables inside the common block.
616 If the current common block contains any equivalence object, then 617 If the current common block contains any equivalence object, then
617 make a UNION_TYPE node, otherwise RECORD_TYPE. This will let the 618 make a UNION_TYPE node, otherwise RECORD_TYPE. This will let the
618 alias analyzer work well when there is no address overlapping for 619 alias analyzer work well when there is no address overlapping for
652 is_init = true; 653 is_init = true;
653 654
654 /* Has SAVE attribute. */ 655 /* Has SAVE attribute. */
655 if (s->sym->attr.save) 656 if (s->sym->attr.save)
656 is_saved = true; 657 is_saved = true;
658
659 /* Has AUTOMATIC attribute. */
660 if (s->sym->attr.automatic)
661 is_auto = true;
657 } 662 }
658 663
659 finish_record_layout (rli, true); 664 finish_record_layout (rli, true);
660 665
661 if (com) 666 if (com)
662 decl = build_common_decl (com, union_type, is_init); 667 decl = build_common_decl (com, union_type, is_init);
663 else 668 else
664 decl = build_equiv_decl (union_type, is_init, is_saved); 669 decl = build_equiv_decl (union_type, is_init, is_saved, is_auto);
665 670
666 if (is_init) 671 if (is_init)
667 { 672 {
668 tree ctor, tmp; 673 tree ctor, tmp;
669 vec<constructor_elt, va_gc> *v = NULL; 674 vec<constructor_elt, va_gc> *v = NULL;
704 /* Build component reference for each variable. */ 709 /* Build component reference for each variable. */
705 for (s = head; s; s = next_s) 710 for (s = head; s; s = next_s)
706 { 711 {
707 tree var_decl; 712 tree var_decl;
708 713
709 var_decl = build_decl (s->sym->declared_at.lb->location, 714 var_decl = build_decl (gfc_get_location (&s->sym->declared_at),
710 VAR_DECL, DECL_NAME (s->field), 715 VAR_DECL, DECL_NAME (s->field),
711 TREE_TYPE (s->field)); 716 TREE_TYPE (s->field));
712 TREE_STATIC (var_decl) = TREE_STATIC (decl); 717 TREE_STATIC (var_decl) = TREE_STATIC (decl);
713 /* Mark the variable as used in order to avoid warnings about 718 /* Mark the variable as used in order to avoid warnings about
714 unused variables. */ 719 unused variables. */
946 new_condition (f, eq1, eq2); 951 new_condition (f, eq1, eq2);
947 else 952 else
948 confirm_condition (f, eq1, n, eq2); 953 confirm_condition (f, eq1, n, eq2);
949 } 954 }
950 955
956 static void
957 accumulate_equivalence_attributes (symbol_attribute *dummy_symbol, gfc_equiv *e)
958 {
959 symbol_attribute attr = e->expr->symtree->n.sym->attr;
960
961 dummy_symbol->dummy |= attr.dummy;
962 dummy_symbol->pointer |= attr.pointer;
963 dummy_symbol->target |= attr.target;
964 dummy_symbol->external |= attr.external;
965 dummy_symbol->intrinsic |= attr.intrinsic;
966 dummy_symbol->allocatable |= attr.allocatable;
967 dummy_symbol->elemental |= attr.elemental;
968 dummy_symbol->recursive |= attr.recursive;
969 dummy_symbol->in_common |= attr.in_common;
970 dummy_symbol->result |= attr.result;
971 dummy_symbol->in_namelist |= attr.in_namelist;
972 dummy_symbol->optional |= attr.optional;
973 dummy_symbol->entry |= attr.entry;
974 dummy_symbol->function |= attr.function;
975 dummy_symbol->subroutine |= attr.subroutine;
976 dummy_symbol->dimension |= attr.dimension;
977 dummy_symbol->in_equivalence |= attr.in_equivalence;
978 dummy_symbol->use_assoc |= attr.use_assoc;
979 dummy_symbol->cray_pointer |= attr.cray_pointer;
980 dummy_symbol->cray_pointee |= attr.cray_pointee;
981 dummy_symbol->data |= attr.data;
982 dummy_symbol->value |= attr.value;
983 dummy_symbol->volatile_ |= attr.volatile_;
984 dummy_symbol->is_protected |= attr.is_protected;
985 dummy_symbol->is_bind_c |= attr.is_bind_c;
986 dummy_symbol->procedure |= attr.procedure;
987 dummy_symbol->proc_pointer |= attr.proc_pointer;
988 dummy_symbol->abstract |= attr.abstract;
989 dummy_symbol->asynchronous |= attr.asynchronous;
990 dummy_symbol->codimension |= attr.codimension;
991 dummy_symbol->contiguous |= attr.contiguous;
992 dummy_symbol->generic |= attr.generic;
993 dummy_symbol->automatic |= attr.automatic;
994 dummy_symbol->threadprivate |= attr.threadprivate;
995 dummy_symbol->omp_declare_target |= attr.omp_declare_target;
996 dummy_symbol->omp_declare_target_link |= attr.omp_declare_target_link;
997 dummy_symbol->oacc_declare_copyin |= attr.oacc_declare_copyin;
998 dummy_symbol->oacc_declare_create |= attr.oacc_declare_create;
999 dummy_symbol->oacc_declare_deviceptr |= attr.oacc_declare_deviceptr;
1000 dummy_symbol->oacc_declare_device_resident
1001 |= attr.oacc_declare_device_resident;
1002
1003 /* Not strictly correct, but probably close enough. */
1004 if (attr.save > dummy_symbol->save)
1005 dummy_symbol->save = attr.save;
1006 if (attr.access > dummy_symbol->access)
1007 dummy_symbol->access = attr.access;
1008 }
951 1009
952 /* Given a segment element, search through the equivalence lists for unused 1010 /* Given a segment element, search through the equivalence lists for unused
953 conditions that involve the symbol. Add these rules to the segment. */ 1011 conditions that involve the symbol. Add these rules to the segment. */
954 1012
955 static bool 1013 static bool
963 for (e1 = n->sym->ns->equiv; e1; e1 = e1->next) 1021 for (e1 = n->sym->ns->equiv; e1; e1 = e1->next)
964 { 1022 {
965 eq = NULL; 1023 eq = NULL;
966 1024
967 /* Search the equivalence list, including the root (first) element 1025 /* Search the equivalence list, including the root (first) element
968 for the symbol that owns the segment. */ 1026 for the symbol that owns the segment. */
1027 symbol_attribute dummy_symbol;
1028 memset (&dummy_symbol, 0, sizeof (dummy_symbol));
969 for (e2 = e1; e2; e2 = e2->eq) 1029 for (e2 = e1; e2; e2 = e2->eq)
970 { 1030 {
1031 accumulate_equivalence_attributes (&dummy_symbol, e2);
971 if (!e2->used && e2->expr->symtree->n.sym == n->sym) 1032 if (!e2->used && e2->expr->symtree->n.sym == n->sym)
972 { 1033 {
973 eq = e2; 1034 eq = e2;
974 break; 1035 break;
975 } 1036 }
976 } 1037 }
1038
1039 gfc_check_conflict (&dummy_symbol, e1->expr->symtree->name, &e1->expr->where);
977 1040
978 /* Go to the next root element. */ 1041 /* Go to the next root element. */
979 if (eq == NULL) 1042 if (eq == NULL)
980 continue; 1043 continue;
981 1044
1005 1068
1006 static void 1069 static void
1007 add_equivalences (bool *saw_equiv) 1070 add_equivalences (bool *saw_equiv)
1008 { 1071 {
1009 segment_info *f; 1072 segment_info *f;
1010 bool seen_one, more; 1073 bool more = TRUE;
1011 1074
1012 seen_one = false;
1013 more = TRUE;
1014 while (more) 1075 while (more)
1015 { 1076 {
1016 more = FALSE; 1077 more = FALSE;
1017 for (f = current_segment; f; f = f->next) 1078 for (f = current_segment; f; f = f->next)
1018 { 1079 {
1019 if (!f->sym->equiv_built) 1080 if (!f->sym->equiv_built)
1020 { 1081 {
1021 f->sym->equiv_built = 1; 1082 f->sym->equiv_built = 1;
1022 seen_one = find_equivalence (f); 1083 bool seen_one = find_equivalence (f);
1023 if (seen_one) 1084 if (seen_one)
1024 { 1085 {
1025 *saw_equiv = true; 1086 *saw_equiv = true;
1026 more = true; 1087 more = true;
1027 } 1088 }
1154 { 1215 {
1155 if (strcmp (common->name, BLANK_COMMON_NAME)) 1216 if (strcmp (common->name, BLANK_COMMON_NAME))
1156 gfc_warning (OPT_Walign_commons, 1217 gfc_warning (OPT_Walign_commons,
1157 "Padding of %d bytes required before %qs in " 1218 "Padding of %d bytes required before %qs in "
1158 "COMMON %qs at %L; reorder elements or use " 1219 "COMMON %qs at %L; reorder elements or use "
1159 "-fno-align-commons", (int)offset, 1220 "%<-fno-align-commons%>", (int)offset,
1160 s->sym->name, common->name, &common->where); 1221 s->sym->name, common->name, &common->where);
1161 else 1222 else
1162 gfc_warning (OPT_Walign_commons, 1223 gfc_warning (OPT_Walign_commons,
1163 "Padding of %d bytes required before %qs in " 1224 "Padding of %d bytes required before %qs in "
1164 "COMMON at %L; reorder elements or use " 1225 "COMMON at %L; reorder elements or use "
1165 "-fno-align-commons", (int)offset, 1226 "%<-fno-align-commons%>", (int)offset,
1166 s->sym->name, &common->where); 1227 s->sym->name, &common->where);
1167 } 1228 }
1168 } 1229 }
1169 1230
1170 /* Apply the offset to the new segments. */ 1231 /* Apply the offset to the new segments. */