private static void traverseSuperMethods(
     RefMethod refMethod,
     GlobalJavaInspectionContext globalContext,
     GlobalJavaInspectionContext.UsagesProcessor processor) {
   final Collection<RefMethod> superMethods = refMethod.getSuperMethods();
   for (RefMethod superMethod : superMethods) {
     traverseSuperMethods(superMethod, globalContext, processor);
   }
   globalContext.enqueueMethodUsagesProcessor(refMethod, processor);
 }
 private static boolean hasNonInvertedCalls(final RefMethod refMethod) {
   final Boolean alwaysInverted = refMethod.getUserData(ALWAYS_INVERTED);
   if (alwaysInverted == null) return true;
   if (refMethod.isExternalOverride()) return true;
   if (refMethod.isReferenced() && !alwaysInverted.booleanValue()) return true;
   final Collection<RefMethod> superMethods = refMethod.getSuperMethods();
   for (RefMethod superMethod : superMethods) {
     if (hasNonInvertedCalls(superMethod)) return true;
   }
   return false;
 }
  private boolean isAccessible(
      RefJavaElement to, @PsiModifier.ModifierConstant String accessModifier) {

    for (RefElement refElement : to.getInReferences()) {
      if (!isAccessibleFrom(refElement, to, accessModifier)) return false;
    }

    if (to instanceof RefMethod) {
      RefMethod refMethod = (RefMethod) to;

      if (refMethod.isAbstract()
          && (refMethod.getDerivedMethods().isEmpty()
              || refMethod.getAccessModifier() == PsiModifier.PRIVATE)) return false;

      for (RefMethod refOverride : refMethod.getDerivedMethods()) {
        if (!isAccessibleFrom(refOverride, to, accessModifier)) return false;
      }

      for (RefMethod refSuper : refMethod.getSuperMethods()) {
        if (RefJavaUtil.getInstance().compareAccess(refSuper.getAccessModifier(), accessModifier)
            > 0) return false;
      }
    }

    if (to instanceof RefClass) {
      RefClass refClass = (RefClass) to;
      for (RefClass subClass : refClass.getSubClasses()) {
        if (!isAccessibleFrom(subClass, to, accessModifier)) return false;
      }

      List children = refClass.getChildren();
      if (children != null) {
        for (Object refElement : children) {
          if (!isAccessible((RefJavaElement) refElement, accessModifier)) return false;
        }
      }

      for (final RefElement refElement : refClass.getInTypeReferences()) {
        if (!isAccessibleFrom(refElement, refClass, accessModifier)) return false;
      }

      List<RefJavaElement> classExporters = ((RefClassImpl) refClass).getClassExporters();
      if (classExporters != null) {
        for (RefJavaElement refExporter : classExporters) {
          if (getAccessLevel(accessModifier) < getAccessLevel(refExporter.getAccessModifier()))
            return false;
        }
      }
    }

    return true;
  }
  @Nullable
  public CommonProblemDescriptor[] checkElement(
      final RefEntity refEntity,
      final AnalysisScope scope,
      final InspectionManager manager,
      final GlobalInspectionContext globalContext,
      final ProblemDescriptionsProcessor processor) {
    if (refEntity instanceof RefMethod) {
      final RefMethod refMethod = (RefMethod) refEntity;

      if (refMethod.isSyntheticJSP()) return null;

      if (refMethod.isExternalOverride()) return null;

      if (!(refMethod.isStatic() || refMethod.isConstructor())
          && !refMethod.getSuperMethods().isEmpty()) return null;

      if ((refMethod.isAbstract() || refMethod.getOwnerClass().isInterface())
          && refMethod.getDerivedMethods().isEmpty()) return null;

      if (RefUtil.isEntryPoint(refMethod)) return null;

      if (refMethod.isAppMain()) return null;

      final ArrayList<RefParameter> unusedParameters = getUnusedParameters(refMethod);

      if (unusedParameters.isEmpty()) return null;

      final List<ProblemDescriptor> result = new ArrayList<ProblemDescriptor>();
      for (RefParameter refParameter : unusedParameters) {
        final PsiIdentifier psiIdentifier = refParameter.getElement().getNameIdentifier();
        if (psiIdentifier != null) {
          result.add(
              manager.createProblemDescriptor(
                  psiIdentifier,
                  refMethod.isAbstract()
                      ? InspectionsBundle.message("inspection.unused.parameter.composer")
                      : InspectionsBundle.message("inspection.unused.parameter.composer1"),
                  new AcceptSuggested(
                      globalContext.getRefManager(), processor, refParameter.toString()),
                  ProblemHighlightType.LIKE_UNUSED_SYMBOL,
                  false));
        }
      }
      return result.toArray(new CommonProblemDescriptor[result.size()]);
    }
    return null;
  }
  @Override
  public CommonProblemDescriptor[] checkElement(
      @NotNull RefEntity refEntity,
      @NotNull AnalysisScope scope,
      @NotNull final InspectionManager manager,
      @NotNull final GlobalInspectionContext globalContext) {
    if (refEntity instanceof RefMethod) {
      RefMethod refMethod = (RefMethod) refEntity;
      if (!refMethod.isReferenced()) return null;
      if (hasNonInvertedCalls(refMethod)) return null;
      if (!refMethod.getSuperMethods().isEmpty()) return null;
      final PsiMethod psiMethod = (PsiMethod) refMethod.getElement();
      final PsiIdentifier psiIdentifier = psiMethod.getNameIdentifier();
      if (psiIdentifier != null) {
        final Collection<RefElement> inReferences = refMethod.getInReferences();
        if (inReferences.size() == 1) {
          final RefElement refElement = inReferences.iterator().next();
          final PsiElement usagesContainer = refElement.getElement();
          if (usagesContainer == null) return null;
          if (ReferencesSearch.search(psiMethod, new LocalSearchScope(usagesContainer))
              .forEach(
                  new Processor<PsiReference>() {
                    private final Set<PsiReference> myFoundRefs = new HashSet<>();

                    @Override
                    public boolean process(PsiReference reference) {
                      myFoundRefs.add(reference);
                      return myFoundRefs.size() < 2;
                    }
                  })) return null;
        }
        return new ProblemDescriptor[] {
          manager.createProblemDescriptor(
              psiIdentifier,
              InspectionsBundle.message("boolean.method.is.always.inverted.problem.descriptor"),
              (LocalQuickFix) getQuickFix(null),
              ProblemHighlightType.GENERIC_ERROR_OR_WARNING,
              false)
        };
      }
    }
    return null;
  }