diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/graph/Graph.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/graph/Graph.java index afa5a9834..182f5c334 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/graph/Graph.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/graph/Graph.java @@ -865,8 +865,17 @@ public class Graph { } + logger.fine("COMPARED PATHS:"); + for (int i = 0; i < comparedPaths.size(); i++) { + logger.fine("- " + (System.identityHashCode(comparedPaths.get(i))) + ": " + pathToString(comparedPaths.get(i))); + } + logger.fine("curren path: " + System.identityHashCode(branches)); + boolean isEndOfBlock = false; + Set partsToClose = new HashSet<>(); + + Map decisionToRemovedCount = new HashMap<>(); loopi: for (int i = 0; i < comparedPaths.size(); i++) { for (int j = 0; j < comparedPaths.size(); j++) { @@ -900,12 +909,14 @@ public class Graph { break; } } + decisionToRemovedCount.put(decision, removedCount); comparedPaths.get(i).remove(comparedPaths.get(i).size() - 1); } else { //remove last path component int last = i > j ? i : j; int first = i < j ? i : j; - comparedPaths.get(first).remove(comparedPaths.get(first).size() - 1); + comparedPaths.get(i).remove(comparedPaths.get(i).size() - 1); + comparedPaths.get(j).remove(comparedPaths.get(j).size() - 1); comparedPaths.remove(last); comparedPathsEdges.remove(last); } @@ -914,35 +925,31 @@ public class Graph { if (!closedBranches.contains(decision)) { logger.fine("on part " + p); logger.fine("normal closing branch " + decision); - closedBranches.add(decision); + partsToClose.add(decision); } else { logger.fine("branch already closed: " + decision); isEndOfBlock = true; } - closedBranches.add(decision); + partsToClose.add(decision); i = -1; continue loopi; } } } for (List cp : comparedPaths) { - logger.fine("- branches:" + pathToString(cp)); + logger.fine("- branches: " + System.identityHashCode(cp) + ": " + pathToString(cp)); } + logger.fine("current branches: " + System.identityHashCode(branches) + ": " + pathToString(branches)); if (comparedPaths.size() > 1) { - logger.fine("not a single path"); - for (int i = 0; i < comparedPaths.size(); i++) { - - } + logger.fine("not a single path - paths left: " + comparedPaths.size()); List prefix = getCommonPrefix(comparedPaths); - Set partsToClose = new HashSet<>(); + GraphPart decision = prefix.isEmpty() ? null : prefix.get(prefix.size() - 1); + int removedCount = decisionToRemovedCount.containsKey(decision) ? decisionToRemovedCount.get(decision) : 0; for (int i = 0; i < comparedPaths.size(); i++) { - for (int j = prefix.size() - 1; j < comparedPaths.get(i).size(); j++) { - if (j < 0) { - continue; - } + for (int j = prefix.size(); j < comparedPaths.get(i).size(); j++) { GraphPart partToClose = comparedPaths.get(i).get(j); GraphPartEdge edgeToClose = comparedPathsEdges.get(i); if (!closedBranches.contains(partToClose)) { @@ -956,21 +963,29 @@ public class Graph { } } } + /*if (decision != null) { logger.fine("closing branch 2: " + decision); closedBranches.add(decision); }*/ - closedBranches.addAll(partsToClose); branches = prefix; if (!branches.isEmpty()) { - branches.remove(branches.size() - 1); + logger.fine("removedCount before: " + removedCount); + removedCount += comparedPaths.size(); + if (partToNext.get(decision).size() > 2 && removedCount < partToNext.get(decision).size() - 1) { + //ignore + } else { + branches.remove(branches.size() - 1); + } } - + } else { + branches = comparedPaths.get(0); } + closedBranches.addAll(partsToClose); if (isEndOfBlock) { //GraphPart blockStartPart = getDominator(startPart, p, loops); - //logger.info("found breaks to to " + p); + logger.info("found breaks to " + p); //System.err.println("found breaks to to " + p); for (GraphPart r : p.refs) { gotoTargets.add(new GraphPartEdge(r, p)); @@ -1095,7 +1110,7 @@ public class Graph { if (!path.endsWith(".run")) { //return; } - //logger.info("------ " + path); + logger.info("------ " + path); //logger.info("GETTING precontinues of " + path + " ================="); Set opened = new HashSet<>(); Set closed = new HashSet<>(); diff --git a/libsrc/ffdec_lib/testdata/flashdevelop/bin/flashdevelop.swf b/libsrc/ffdec_lib/testdata/flashdevelop/bin/flashdevelop.swf index 00772ff04..8d9cf5ebe 100644 Binary files a/libsrc/ffdec_lib/testdata/flashdevelop/bin/flashdevelop.swf and b/libsrc/ffdec_lib/testdata/flashdevelop/bin/flashdevelop.swf differ diff --git a/libsrc/ffdec_lib/testdata/flashdevelop/src/Main.as b/libsrc/ffdec_lib/testdata/flashdevelop/src/Main.as index ea46ac615..ad36c3dc0 100644 --- a/libsrc/ffdec_lib/testdata/flashdevelop/src/Main.as +++ b/libsrc/ffdec_lib/testdata/flashdevelop/src/Main.as @@ -37,9 +37,11 @@ package TestForIn; TestForXml; TestGotos; + TestGotos2; TestHello; TestIf; TestIfElse; + TestIfInIf; TestInc2; TestIncDec; TestInlineFunctions; diff --git a/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestGotos2.as b/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestGotos2.as new file mode 100644 index 000000000..f63eabf18 --- /dev/null +++ b/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestGotos2.as @@ -0,0 +1,34 @@ +package tests +{ + public class TestGotos2 + { + + public function run() :int + { + var a : Boolean = true; + var b : Boolean = false; + var c : Boolean = true; + + if (a) + { + + if (b) + { + trace("A"); + if (c) + { + trace("B"); + } + } + } + else + { + trace("E"); + } + return 5; + + } + + } + +} \ No newline at end of file diff --git a/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestIfInIf.as b/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestIfInIf.as new file mode 100644 index 000000000..0e8affaeb --- /dev/null +++ b/libsrc/ffdec_lib/testdata/flashdevelop/src/tests/TestIfInIf.as @@ -0,0 +1,34 @@ +package tests +{ + + public class TestIfInIf + { + + public function run() : int + { + var k:int = 5; + if (k > 5 && k <20) + { + trace("A"); + + if (k < 4) + { + return 1; + } + } + else if (k > 4 && k<10) + { + trace("B"); + if (k < 7) + { + return 2; + } + } + + trace("C"); + return 7; + } + + } + +} \ No newline at end of file