@Override @Nullable public int[] getBackwardIds(@NotNull VirtualFileWithId file) { if (!isUpToDate()) return null; int fileId = getAbsId((VirtualFile) file); return storage.get(fileId); }
public RefResolveServiceImpl( final Project project, final MessageBus messageBus, final PsiManager psiManager, StartupManager startupManager, ApplicationEx application, ProjectFileIndex projectFileIndex) throws IOException { super(project); ((FutureTask) resolveProcess).run(); myApplication = application; myProjectFileIndex = projectFileIndex; if (ENABLED) { log = new FileWriter(new File(getStorageDirectory(), "log.txt")); File dataFile = new File(getStorageDirectory(), "data"); fileIsResolved = ConcurrentBitSet.readFrom(new File(getStorageDirectory(), "bitSet")); log("Read resolved file bitset: " + fileIsResolved); int maxId = FSRecords.getMaxId(); PersistentIntList list = new PersistentIntList(dataFile, dataFile.exists() ? 0 : maxId); if (list.getSize() == maxId) { storage = list; } else { // just to be safe, re-resolve all if VFS files count changes since last restart list.dispose(); storage = new PersistentIntList(dataFile, maxId); log( "VFS maxId changed: was " + list.getSize() + "; now: " + maxId + "; re-resolving everything"); fileIsResolved.clear(); } Disposer.register(this, storage); if (!application.isUnitTestMode()) { startupManager.runWhenProjectIsInitialized( () -> { initListeners(messageBus, psiManager); startThread(); }); } Disposer.register( this, new Disposable() { @Override public void dispose() { try { save(); log.close(); } catch (IOException e) { LOG.error(e); } } }); } else { log = null; fileIsResolved = null; storage = null; } }
@NotNull private TIntHashSet calcForwardRefs( @NotNull final VirtualFile virtualFile, @NotNull final ProgressIndicator indicator) throws IndexNotReadyException, ApplicationUtil.CannotRunReadActionException { final TIntHashSet forward = new TIntHashSet(); final PsiFile psiFile = ApplicationUtil.tryRunReadAction( () -> { if (myProject.isDisposed()) throw new ProcessCanceledException(); if (fileCount.incrementAndGet() % 100 == 0) { PsiManager.getInstance(myProject).dropResolveCaches(); try { storage.flush(); log.flush(); } catch (IOException e) { LOG.error(e); } } return PsiManager.getInstance(myProject).findFile(virtualFile); }); final int fileId = getAbsId(virtualFile); if (psiFile != null) { bytesSize.addAndGet(virtualFile.getLength()); final Set<PsiElement> resolved = new THashSet<PsiElement>(); ApplicationUtil.tryRunReadAction( new Runnable() { @Override public void run() { indicator.checkCanceled(); if (psiFile instanceof PsiJavaFile) { psiFile.accept( new JavaRecursiveElementWalkingVisitor() { @Override public void visitReferenceElement(PsiJavaCodeReferenceElement reference) { indicator.checkCanceled(); resolveReference(reference, resolved); super.visitReferenceElement(reference); } }); } else { psiFile.accept( new PsiRecursiveElementWalkingVisitor() { @Override public void visitElement(PsiElement element) { for (PsiReference reference : element.getReferences()) { indicator.checkCanceled(); resolveReference(reference, resolved); } super.visitElement(element); } }); } indicator.checkCanceled(); for (PsiElement element : resolved) { PsiFile file = element.getContainingFile(); addIdAndSuperClasses(file, forward); } } }); } forward.remove(fileId); return forward; }
private void save() throws IOException { log("Saving resolved file bitset: " + fileIsResolved); fileIsResolved.writeTo(new File(getStorageDirectory(), "bitSet")); log("list.size = " + storage.getSize()); }