From 10ea09ee846eaa345161a3a3f519b3780d6101fa Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 26 Mar 2020 10:10:21 +0100 Subject: gimplify: Fix -fcompare-debug differences caused by gimplify_body [PR94281] The following testcase FAILs, because gimplify_body adds a GIMPLE_NOP only when there are no statements in the function and with -g there is a DEBUG_BEGIN_STMT, so it doesn't add it and due to -fno-tree-dce that never gets removed afterwards. Similarly, if the body seq after gimplification contains some DEBUG_BEGIN_STMTs plus a single gbind, then we could behave differently between -g0 and -g, by using that gbind as the body in the -g0 case and not in the -g case. This patch fixes that by ignoring DEBUG_BEGIN_STMTs (other debug stmts can't appear at this point yet thankfully) during decisions and if we pick the single gbind and there are DEBUG_BEGIN_STMTs next to it, it moves them into the gbind. While debugging this, I found also a bug in the gimple_seq_last_nondebug_stmt function, for a seq that has a single non-DEBUG_BEGIN_STMT statement followed by one or more DEBUG_BEGIN_STMTs it would return NULL rather than the first statement. 2020-03-26 Jakub Jelinek PR debug/94281 * gimple.h (gimple_seq_first_nondebug_stmt): New function. (gimple_seq_last_nondebug_stmt): Don't return NULL if seq contains a single non-debug stmt followed by one or more debug stmts. * gimplify.c (gimplify_body): Use gimple_seq_first_nondebug_stmt instead of gimple_seq_first_stmt, use gimple_seq_first_nondebug_stmt and gimple_seq_last_nondebug_stmt instead of gimple_seq_first and gimple_seq_last to check if outer_stmt gbind could be reused and if yes and it is surrounded by any debug stmts, move them into the gbind body. * g++.dg/debug/pr94281.C: New test. --- gcc/gimple.h | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) (limited to 'gcc/gimple.h') diff --git a/gcc/gimple.h b/gcc/gimple.h index 0420d6d..305d98f 100644 --- a/gcc/gimple.h +++ b/gcc/gimple.h @@ -4728,6 +4728,18 @@ is_gimple_debug (const gimple *gs) } +/* Return the first nondebug statement in GIMPLE sequence S. */ + +static inline gimple * +gimple_seq_first_nondebug_stmt (gimple_seq s) +{ + gimple_seq_node n = gimple_seq_first (s); + while (n && is_gimple_debug (n)) + n = n->next; + return n; +} + + /* Return the last nondebug statement in GIMPLE sequence S. */ static inline gimple * @@ -4737,7 +4749,7 @@ gimple_seq_last_nondebug_stmt (gimple_seq s) for (n = gimple_seq_last (s); n && is_gimple_debug (n); n = n->prev) - if (n->prev == s) + if (n == s) return NULL; return n; } -- cgit v1.1