From 708ffe6f132ee39441b66b6ab6b98847d35916b7 Mon Sep 17 00:00:00 2001 From: eastb233 Date: Tue, 19 Dec 2023 17:03:12 +0800 Subject: [PATCH 1/2] [Struct Reorg] Fix several bugs --- gcc/ipa-struct-reorg/ipa-struct-reorg.c | 50 ++++++------------- gcc/testsuite/gcc.dg/struct/struct_reorg-10.c | 29 +++++++++++ gcc/testsuite/gcc.dg/struct/struct_reorg-11.c | 16 ++++++ gcc/testsuite/gcc.dg/struct/struct_reorg-12.c | 26 ++++++++++ 4 files changed, 85 insertions(+), 36 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/struct/struct_reorg-10.c create mode 100644 gcc/testsuite/gcc.dg/struct/struct_reorg-11.c create mode 100644 gcc/testsuite/gcc.dg/struct/struct_reorg-12.c diff --git a/gcc/ipa-struct-reorg/ipa-struct-reorg.c b/gcc/ipa-struct-reorg/ipa-struct-reorg.c index 7aba74ff1..0064811ac 100644 --- a/gcc/ipa-struct-reorg/ipa-struct-reorg.c +++ b/gcc/ipa-struct-reorg/ipa-struct-reorg.c @@ -4105,6 +4105,12 @@ ipa_struct_reorg::maybe_record_assign (cgraph_node *node, gassign *stmt) maybe_mark_or_record_other_side (rhs, lhs, stmt); if (TREE_CODE (lhs) == SSA_NAME) maybe_mark_or_record_other_side (lhs, rhs, stmt); + + /* Handle missing ARRAY_REF cases. */ + if (TREE_CODE (lhs) == ARRAY_REF) + mark_type_as_escape (TREE_TYPE (lhs), escape_array, stmt); + if (TREE_CODE (rhs) == ARRAY_REF) + mark_type_as_escape (TREE_TYPE (rhs), escape_array, stmt); } } @@ -6169,6 +6175,7 @@ ipa_struct_reorg::rewrite_expr (tree expr, tree newexpr[max_split], bool ignore_ bool escape_from_base = false; tree newbase[max_split]; + memset (newbase, 0, sizeof (tree[max_split])); memset (newexpr, 0, sizeof(tree[max_split])); if (TREE_CODE (expr) == CONSTRUCTOR) @@ -8162,43 +8169,14 @@ ipa_struct_reorg::rewrite_cond (gcond *stmt, should be removed. */ bool -ipa_struct_reorg::rewrite_debug (gimple *stmt, gimple_stmt_iterator *) +ipa_struct_reorg::rewrite_debug (gimple *, gimple_stmt_iterator *) { - if (current_layout_opt_level >= STRUCT_REORDER_FIELDS) - { - /* Delete debug gimple now. */ - return true; - } - bool remove = false; - if (gimple_debug_bind_p (stmt)) - { - tree var = gimple_debug_bind_get_var (stmt); - tree newvar[max_split]; - if (rewrite_expr (var, newvar, true)) - remove = true; - if (gimple_debug_bind_has_value_p (stmt)) - { - var = gimple_debug_bind_get_value (stmt); - if (TREE_CODE (var) == POINTER_PLUS_EXPR) - var = TREE_OPERAND (var, 0); - if (rewrite_expr (var, newvar, true)) - remove = true; - } - } - else if (gimple_debug_source_bind_p (stmt)) - { - tree var = gimple_debug_source_bind_get_var (stmt); - tree newvar[max_split]; - if (rewrite_expr (var, newvar, true)) - remove = true; - var = gimple_debug_source_bind_get_value (stmt); - if (TREE_CODE (var) == POINTER_PLUS_EXPR) - var = TREE_OPERAND (var, 0); - if (rewrite_expr (var, newvar, true)) - remove = true; - } - - return remove; + /* In debug statements, there might be some statements that have + been optimized out in gimple but left in debug gimple. Sometimes + these statements need to be analyzed to escape, but in rewrite + stage it shouldn't happen. It needs to care a lot to handle these + cases but seems useless. So now we just delete debug gimple. */ + return true; } /* Rewrite PHI nodes, return true if the PHI was replaced. */ diff --git a/gcc/testsuite/gcc.dg/struct/struct_reorg-10.c b/gcc/testsuite/gcc.dg/struct/struct_reorg-10.c new file mode 100644 index 000000000..ec422f76f --- /dev/null +++ b/gcc/testsuite/gcc.dg/struct/struct_reorg-10.c @@ -0,0 +1,29 @@ +/* { dg-do compile } */ +/* { dg-options "-w -g -O3 -flto-partition=one -fipa-struct-reorg -fwhole-program -S" } */ + +struct a { + int b; + char c; +}; +struct { + double d; + _Bool e; +} * f; +struct g { + struct a h; +} i; +long j; +void k(); +void l() { k(i); } +void k(struct a m) { + f->e = 0; + for (;;) + l(); +} +int main() { + for (; j; f = 0) { + struct g *n = 0; + char o = n->h.c; + } + l(); +} diff --git a/gcc/testsuite/gcc.dg/struct/struct_reorg-11.c b/gcc/testsuite/gcc.dg/struct/struct_reorg-11.c new file mode 100644 index 000000000..3e42aa84a --- /dev/null +++ b/gcc/testsuite/gcc.dg/struct/struct_reorg-11.c @@ -0,0 +1,16 @@ +/* { dg-do compile } */ +/* { dg-options "-w -g -O3 -flto-partition=one -fipa-struct-reorg -fwhole-program -S" } */ + +struct a { + int b; + double c; +}; +struct d { + struct a e; +}; +int f; +int main() { + _Bool g; + struct d **h = 0; + g = *h += f; +} diff --git a/gcc/testsuite/gcc.dg/struct/struct_reorg-12.c b/gcc/testsuite/gcc.dg/struct/struct_reorg-12.c new file mode 100644 index 000000000..d434f9fe0 --- /dev/null +++ b/gcc/testsuite/gcc.dg/struct/struct_reorg-12.c @@ -0,0 +1,26 @@ +/* { dg-do compile } */ +/* { dg-options "-w -g -O3 -flto-partition=one -fipa-struct-reorg -fwhole-program -S" } */ + +struct foo { + long element1; + long element2; +}; + +struct goo { + struct foo element_foo; +}; + +struct goo g1; + +void func () { + struct foo (*local)[] = 0; + long idx; + (g1).element_foo = (*local)[idx]; +} + +struct foo g2; +int main () { + func (); + g2 = g1.element_foo; + return 0; +} -- 2.33.0