SOE in case of mutually recursive inheritance

This commit is contained in:
Alexey Kudravtsev
2010-10-11 14:08:46 +04:00
parent 5e0df13706
commit 2c28282512
3 changed files with 17 additions and 9 deletions
@@ -6,6 +6,7 @@ package com.intellij.psi.impl.search;
import com.intellij.psi.PsiMethod;
import com.intellij.util.Processor;
import com.intellij.util.QueryExecutor;
import gnu.trove.THashSet;
import org.jetbrains.annotations.NotNull;
import java.util.LinkedHashSet;
@@ -15,10 +16,9 @@ import java.util.Set;
* @author peter
*/
public class MethodDeepestSuperSearcher implements QueryExecutor<PsiMethod, PsiMethod> {
public boolean execute(@NotNull final PsiMethod method, @NotNull final Processor<PsiMethod> consumer) {
final Set<PsiMethod> methods = new LinkedHashSet<PsiMethod>();
findDeepestSuperOrSelfSignature(method, methods);
findDeepestSuperOrSelfSignature(method, methods, null);
for (final PsiMethod psiMethod : methods) {
if (psiMethod != method && !consumer.process(psiMethod)) {
return false;
@@ -27,17 +27,18 @@ public class MethodDeepestSuperSearcher implements QueryExecutor<PsiMethod, PsiM
return true;
}
private static void findDeepestSuperOrSelfSignature(PsiMethod method, final Set<PsiMethod> set) {
private static void findDeepestSuperOrSelfSignature(PsiMethod method, final Set<PsiMethod> set, Set<PsiMethod> guard) {
if (guard != null && !guard.add(method)) return;
PsiMethod[] supers = method.findSuperMethods();
if (supers.length == 0) {
set.add(method);
return;
}
for (PsiMethod superMethod : supers) {
findDeepestSuperOrSelfSignature(superMethod, set);
else {
for (PsiMethod superMethod : supers) {
if (guard == null) guard = new THashSet<PsiMethod>();
findDeepestSuperOrSelfSignature(superMethod, set, guard);
}
}
}
}
@@ -302,4 +302,10 @@ public class LightAdvHighlightingTest extends LightDaemonAnalyzerTestCase {
field.getInitializer().getType(); // SOE
}
public void testSOEForCyclicInheritance() throws IOException {
configureFromFileText("a.java", "class A extends B { String s = \"\"; void f() {}} class B extends A { void f() {} } ");
doHighlighting();
}
}
@@ -89,10 +89,11 @@ public class ClassUtil {
private static boolean add(PsiMethod method, Set<PsiMethod> alreadyImplemented) {
boolean already = alreadyImplemented.add(method);
if (!already) return already;
for (PsiMethod superSig : method.findSuperMethods()) {
already &= add(superSig, alreadyImplemented);
}
return already;
}
}
}