diff options
author | Erick Ochoa <erick.ochoa@theobroma-systems.com> | 2020-04-29 11:48:19 +0200 |
---|---|---|
committer | Erick Ochoa <erick.ochoa@theobroma-systems.com> | 2020-04-29 11:48:19 +0200 |
commit | ec5b8cec1c1869a8d5968e78b7105aa8e1762fc0 (patch) | |
tree | e08f0ee1c1a92cc27a5d0e5956df1e902afcede3 | |
parent | cee7642305e27f26e3d40374714d67ef5855a2d2 (diff) |
Fixes bug #3 found by csmith
-rw-r--r-- | gcc/ipa-str-reorg-dead-field-eliminate.c | 42 |
1 files changed, 41 insertions, 1 deletions
diff --git a/gcc/ipa-str-reorg-dead-field-eliminate.c b/gcc/ipa-str-reorg-dead-field-eliminate.c index 9a77b7a6553..a99f9f4ddf0 100644 --- a/gcc/ipa-str-reorg-dead-field-eliminate.c +++ b/gcc/ipa-str-reorg-dead-field-eliminate.c @@ -587,6 +587,7 @@ struct cstrless { }; std::set<const char*, cstrless> interesting_records; std::set<const char*, cstrless> interesting_fields; +std::set<const char*, cstrless> record_field_pair_name; std::set<const char*, cstrless> updated_functions; static bool @@ -648,6 +649,27 @@ is_interesting_struct (const_tree record_1) } static bool +is_interesting_pair (const char* pair_name) +{ + const bool use_escape_analysis_info = !flag_ipa_typelist_struct && !flag_ipa_typelist_field; + //TODO: If we are not in escape analysis we shouldn't be calling this function. + //We need to define a better interface for specifying record type and name to avoid + //having this problem. + if (!use_escape_analysis_info) return true; + const bool in_set = +#if __cplusplus > 201703L + record_field_pair_name.contains(pair_name); +#else + record_field_pair_name.find(pair_name) != record_field_pair_name.end() +#endif + ; + + log("is interesting pair? %s\n", in_set ? "true" : "false"); + + return in_set; +} + +static bool is_interesting_struct_manual(const_tree record_1) { is_record_p(record_1); @@ -1152,11 +1174,20 @@ make_new_record_based_on_old (const_tree old, { const bool are_field_names_equal = is_interesting_field (old_field); - log("am i deleting fields ? %s\n", will_definitely_change && are_field_names_equal ? "true" : "false"); + log("am i deleting field %s ? %s\n", get_field_name(old_field), will_definitely_change && are_field_names_equal ? "true" : "false"); if (will_definitely_change && are_field_names_equal) { + char *buffer; + char *buffer2; + asprintf(&buffer, "%s.%s", get_type_name(old), get_field_name(old_field)); + asprintf(&buffer2, "%s.%s", get_type_name(TYPE_MAIN_VARIANT(old)), get_field_name(old_field)); + log("buffer %s\n", buffer); + log("buffer2 %s\n", buffer2); + if (is_interesting_pair(buffer) || is_interesting_pair(buffer2)) + { deleted_fields->add(old_field); continue; + } } tree new_field = make_node (FIELD_DECL); @@ -2606,10 +2637,19 @@ separate_set_of_pairs_into_pair_of_sets(const record_field_set &set_of_pairs, st { fields record_field_pair = *it; const_tree record = record_field_pair.first; + if (strcmp(get_record_name(record), "<name_tree_is_null>") == 0) continue; const_tree field = record_field_pair.second; one.insert(get_type_name(record)); one.insert(get_type_name(TYPE_MAIN_VARIANT(record))); two.insert(get_field_name(field)); + char *buffer; + char *buffer2; + asprintf(&buffer, "%s.%s", get_type_name(record), get_field_name(field)); + asprintf(&buffer2, "%s.%s", get_type_name(TYPE_MAIN_VARIANT(record)), get_field_name(field)); + log("putting in %s\n", buffer); + log("putting in %s\n", buffer2); + record_field_pair_name.insert(buffer); + record_field_pair_name.insert(buffer2); } } |