diff --git a/teavm-core/src/main/java/org/teavm/common/GraphUtils.java b/teavm-core/src/main/java/org/teavm/common/GraphUtils.java index ec8fcf277..886d77d56 100644 --- a/teavm-core/src/main/java/org/teavm/common/GraphUtils.java +++ b/teavm-core/src/main/java/org/teavm/common/GraphUtils.java @@ -83,7 +83,6 @@ public final class GraphUtils { * Tarjan's algorithm */ public static int[][] findStronglyConnectedComponents(Graph graph, int[] start, GraphNodeFilter filter) { - // TODO: can show incorrect behaviour sometimes List components = new ArrayList<>(); int[] visitIndex = new int[graph.size()]; int[] headerIndex = new int[graph.size()]; @@ -113,6 +112,9 @@ public final class GraphUtils { } if (hdr == visitIndex[node]) { components.add(currentComponent.getAll()); + for (int componentMember : currentComponent.getAll()) { + headerIndex[componentMember] = graph.size() + 1; + } currentComponent.clear(); } headerIndex[node] = hdr; diff --git a/teavm-core/src/test/java/org/teavm/common/GraphTest.java b/teavm-core/src/test/java/org/teavm/common/GraphTest.java index 4ae932305..12a2e876f 100644 --- a/teavm-core/src/test/java/org/teavm/common/GraphTest.java +++ b/teavm-core/src/test/java/org/teavm/common/GraphTest.java @@ -15,7 +15,7 @@ */ package org.teavm.common; -import static org.hamcrest.CoreMatchers.*; +import static org.hamcrest.CoreMatchers.is; import static org.junit.Assert.*; import com.carrotsearch.hppc.IntOpenHashSet; import com.carrotsearch.hppc.IntSet; @@ -88,6 +88,25 @@ public class GraphTest { assertThat(sccs[0], is(new int[] { 1, 2, 3, 4, 5 })); } + @Test + public void stronglyConnectedComponentCalculated3() { + GraphBuilder builder = new GraphBuilder(); + builder.addEdge(0, 1); + builder.addEdge(0, 2); + builder.addEdge(1, 3); + builder.addEdge(3, 1); + builder.addEdge(2, 3); + Graph graph = builder.build(); + + int[][] sccs = GraphUtils.findStronglyConnectedComponents(graph, new int[] { 0 }, filter); + sortSccs(sccs); + + assertThat(sccs.length, is(3)); + assertThat(sccs[0], is(new int[] { 0 })); + assertThat(sccs[1], is(new int[] { 1, 3 })); + assertThat(sccs[2], is(new int[] { 2 })); + } + @Test public void irreducibleGraphSplit() { GraphBuilder builder = new GraphBuilder();