private void processFilesInScope(@NotNull Set<? extends VirtualFile> alreadySearched,
                                   boolean checkCoveredBySearchers,
                                   @NotNull Processor<? super VirtualFile> fileProcessor) {
    SearchScope customScope = myFindModel.isCustomScope() ? myFindModel.getCustomScope() : null;
    GlobalSearchScope globalCustomScope = customScope == null ? null : GlobalSearchScopeUtil.toGlobalSearchScope(customScope, myProject);

    boolean ignoreExcluded = myDirectory != null
                             && !Registry.is("find.search.in.excluded.dirs")
                             && !ReadAction.compute(() -> myProjectFileIndex.isExcluded(myDirectory));
    boolean withSubdirs = myDirectory != null && myFindModel.isWithSubdirectories();
    boolean locateClassSources = myDirectory != null && ReadAction.compute(() -> myProjectFileIndex.getClassRootForFile(myDirectory)) != null;
    boolean searchInLibs = globalCustomScope != null && ReadAction.compute(() -> globalCustomScope.isSearchInLibraries());

    ConcurrentLinkedDeque<Object> deque = new ConcurrentLinkedDeque<>();
    if (customScope instanceof LocalSearchScope) {
      deque.addAll(GlobalSearchScopeUtil.getLocalScopeFiles((LocalSearchScope)customScope));
    }
    else if (customScope instanceof VirtualFileEnumeration) {
      // GlobalSearchScope can include files out of project roots e.g., FileScope / FilesScope
      ContainerUtil.addAll(deque, FileBasedIndexEx.toFileIterable(((VirtualFileEnumeration)customScope).asArray()));
    }
    else if (myDirectory != null) {
      deque.addAll(withSubdirs ? List.of(myDirectory) : List.of(myDirectory.getChildren()));
    }
    else if (myModule != null) {
      EntityStorage storage = WorkspaceModel.getInstance(myProject).getCurrentSnapshot();
      ModuleEntity moduleEntity = Objects.requireNonNull(storage.resolve(new ModuleId(myModule.getName())));
      deque.addAll(IndexableEntityProviderMethods.INSTANCE.createIterators(moduleEntity, storage, myProject));
    }
    else {
      deque.addAll(((FileBasedIndexEx)FileBasedIndex.getInstance()).getIndexableFilesProviders(myProject));
    }
    deque.addAll(FindModelExtension.EP_NAME.getExtensionList());

    ConcurrentBitSet visitedFiles = ConcurrentBitSet.create();
    Processor<Object> consumer = obj -> {
      ProgressManager.checkCanceled();
      if (obj instanceof IndexableFilesIterator) {
        IndexableSetOrigin origin = ((IndexableFilesIterator)obj).getOrigin();
        if (!searchInLibs && !(origin instanceof ContentOrigin)) return true;
        ((IndexableFilesIterator)obj).iterateFiles(myProject, file -> {
          if (file.isDirectory()) return true;
          deque.add(file);
          return true;
        }, VirtualFileFilter.ALL);
      }
      else if (obj instanceof FindModelExtension) {
        ((FindModelExtension)obj).iterateAdditionalFiles(myFindModel, myProject, o -> {
          if (o.isDirectory()) return true;
          if (!alreadySearched.contains(o)) {
            return fileProcessor.process(o);
          }
          return true;
        });
      }
      else if (obj instanceof VirtualFile file) {
        if (file instanceof VirtualFileWithId && visitedFiles.set(((VirtualFileWithId)file).getId())) {
          return true;
        }
        if (!file.isValid()) {
          return true;
        }
        if (ignoreExcluded && myProjectFileIndex.isExcluded(file)) {
          return true;
        }
        if (file.isDirectory()) {
          if (withSubdirs) {
            ContainerUtil.addAll(deque, ((VirtualFile)obj).getChildren());
          }
          return true;
        }
        if (!myFileMask.value(file) ||
            globalCustomScope != null && !globalCustomScope.contains(file) ||
            checkCoveredBySearchers && ContainerUtil.find(mySearchers, p -> p.isCovered(file)) != null) {
          return true;
        }

        VirtualFile adjustedFile;
        if (file.getFileType().isBinary()) {
          if (locateClassSources) {
            Pair.NonNull<PsiFile, VirtualFile> pair = findFile(file);
            if (pair == null) return true;
            adjustedFile = Objects.requireNonNull(pair.second);
          }
          else {
            return true;
          }
        }
        else {
          adjustedFile = file;
        }
        if (alreadySearched.contains(adjustedFile)) {
          return true;
        }
        return fileProcessor.process(adjustedFile);
      }
      else {
        throw new AssertionError("unknown item: " + obj);
      }
      return true;
    };
    FilesScanExecutor.processOnAllThreadsInReadActionWithRetries(deque, consumer::process);
  }
private void processFilesInScope(@NotNull Set<? extends VirtualFile> alreadySearched,
                                   boolean checkCoveredBySearchers,
                                   @NotNull Processor<? super VirtualFile> fileProcessor)