diff mbox

[v3,2/7] fix infinite simplification loops

Message ID 20170731203624.58971-3-luc.vanoostenryck@gmail.com (mailing list archive)
State Mainlined, archived
Headers show

Commit Message

Luc Van Oostenryck July 31, 2017, 8:36 p.m. UTC
Each time a parent is removed from a BB there is
the possibility that the BB become unreachable.
This in turn can create cycles of dead BBs which
can the create inifinite loops during the
simplification process.

Fix this by setting the flag REPEAT_CFG_CLEANUP when
a branch is rewritten, this will in turn trigger
a call to kill_unreachable_bbs() which will break
these loops.

Reported-by: Michael Stefaniuc <mstefani@mykolab.com>
Signed-off-by: Luc Van Oostenryck <luc.vanoostenryck@gmail.com>
---
 flow.c                       |  3 ++-
 validation/infinite-loop02.c | 11 +++++++++++
 validation/infinite-loop03.c | 16 ++++++++++++++++
 3 files changed, 29 insertions(+), 1 deletion(-)
 create mode 100644 validation/infinite-loop02.c
 create mode 100644 validation/infinite-loop03.c
diff mbox

Patch

diff --git a/flow.c b/flow.c
index fce8bde21..536bf257f 100644
--- a/flow.c
+++ b/flow.c
@@ -34,7 +34,8 @@  static int rewrite_branch(struct basic_block *bb,
 		return 0;
 
 	/* We might find new if-conversions or non-dominating CSEs */
-	repeat_phase |= REPEAT_CSE;
+	/* we may also create new dead cycles */
+	repeat_phase |= REPEAT_CSE | REPEAT_CFG_CLEANUP;
 	*ptr = new;
 	replace_bb_in_list(&bb->children, old, new, 1);
 	remove_bb_from_list(&old->parents, bb, 1);
diff --git a/validation/infinite-loop02.c b/validation/infinite-loop02.c
new file mode 100644
index 000000000..7d0761d87
--- /dev/null
+++ b/validation/infinite-loop02.c
@@ -0,0 +1,11 @@ 
+void foo(void)
+{
+	int a = 1;
+	while ((a = !a))
+		;
+}
+
+/*
+ * check-name: infinite loop 02
+ * check-command: sparse -Wno-decl $file
+ */
diff --git a/validation/infinite-loop03.c b/validation/infinite-loop03.c
new file mode 100644
index 000000000..ac8a9519d
--- /dev/null
+++ b/validation/infinite-loop03.c
@@ -0,0 +1,16 @@ 
+static void foo(int *buf)
+{
+	int a = 1;
+	int *b;
+	do {
+		if (a)
+			b = buf;
+		if (a)
+			*buf = 0;
+	} while (!(a = !a));
+}
+
+/*
+ * check-name: infinite loop 03
+ * check-command: sparse -Wno-decl $file
+ */