mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
Merge remote branch 'origin/master'
This commit is contained in:
@@ -0,0 +1,123 @@
|
||||
package com.intellij.psi.stubs;
|
||||
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiManager;
|
||||
import com.intellij.psi.PsiPlainTextFile;
|
||||
import com.intellij.psi.impl.source.PsiFileImpl;
|
||||
import com.intellij.psi.impl.source.PsiFileWithStubSupport;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.tree.IStubFileElementType;
|
||||
import com.intellij.util.Processor;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Author: dmitrylomov
|
||||
*/
|
||||
public abstract class StubProcessingHelperBase {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.psi.stubs.StubProcessingHelperBase");
|
||||
|
||||
private static IElementType stubType(@NotNull final StubElement<?> stub) {
|
||||
if (stub instanceof PsiFileStub) {
|
||||
return ((PsiFileStub)stub).getType();
|
||||
}
|
||||
|
||||
return stub.getStubType();
|
||||
}
|
||||
|
||||
public <Psi extends PsiElement> boolean processStubsInFile(final Project project, final VirtualFile file, StubIdList value, final Processor<? super Psi> processor) {
|
||||
StubTree stubTree = null;
|
||||
|
||||
final PsiFile _psifile = PsiManager.getInstance(project).findFile(file);
|
||||
PsiFileWithStubSupport psiFile = null;
|
||||
|
||||
if (_psifile != null && !(_psifile instanceof PsiPlainTextFile)) {
|
||||
if (_psifile instanceof PsiFileWithStubSupport) {
|
||||
psiFile = (PsiFileWithStubSupport)_psifile;
|
||||
stubTree = psiFile.getStubTree();
|
||||
if (stubTree == null && psiFile instanceof PsiFileImpl) {
|
||||
stubTree = ((PsiFileImpl)psiFile).calcStubTree();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (stubTree == null && psiFile == null) {
|
||||
return true;
|
||||
}
|
||||
if (stubTree == null) {
|
||||
ObjectStubTree objectStubTree = StubTreeLoader.getInstance().readFromVFile(project, file);
|
||||
if (!(objectStubTree instanceof ObjectStubTree)) {
|
||||
return true;
|
||||
}
|
||||
stubTree = (StubTree)objectStubTree;
|
||||
final List<StubElement<?>> plained = stubTree.getPlainList();
|
||||
for (int i = 0, size = value.size(); i < size; i++) {
|
||||
final StubElement<?> stub = plained.get(value.get(i));
|
||||
final ASTNode tree = psiFile.findTreeForStub(stubTree, stub);
|
||||
|
||||
if (tree != null) {
|
||||
if (tree.getElementType() == stubType(stub)) {
|
||||
Psi psi = (Psi)tree.getPsi();
|
||||
if (!processor.process(psi)) return false;
|
||||
}
|
||||
else {
|
||||
String persistedStubTree = ((PsiFileStubImpl)stubTree.getRoot()).printTree();
|
||||
|
||||
String stubTreeJustBuilt =
|
||||
((PsiFileStubImpl)((IStubFileElementType)((PsiFileImpl)psiFile).getContentElementType()).getBuilder()
|
||||
.buildStubTree(psiFile)).printTree();
|
||||
|
||||
StringBuilder builder = new StringBuilder();
|
||||
builder.append("Oops\n");
|
||||
|
||||
|
||||
builder.append("Recorded stub:-----------------------------------\n");
|
||||
builder.append(persistedStubTree);
|
||||
builder.append("\nAST built stub: ------------------------------------\n");
|
||||
builder.append(stubTreeJustBuilt);
|
||||
builder.append("\n");
|
||||
LOG.info(builder.toString());
|
||||
onInternalError(file);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
final List<StubElement<?>> plained = stubTree.getPlainList();
|
||||
for (int i = 0, size = value.size(); i < size; i++) {
|
||||
final int stubTreeIndex = value.get(i);
|
||||
if (stubTreeIndex >= plained.size()) {
|
||||
final VirtualFile virtualFile = psiFile.getVirtualFile();
|
||||
StubTree stubTreeFromIndex = (StubTree)StubTreeLoader.getInstance().readFromVFile(project, file);
|
||||
LOG.error(stubTreeAndIndexDoNotMatch(stubTree, psiFile, plained, virtualFile, stubTreeFromIndex));
|
||||
|
||||
onInternalError(file);
|
||||
|
||||
break;
|
||||
}
|
||||
Psi psi = (Psi)plained.get(stubTreeIndex).getPsi();
|
||||
if (!processor.process(psi)) return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/***
|
||||
* Returns a message to log when stub tree and index do not match
|
||||
*/
|
||||
protected abstract String stubTreeAndIndexDoNotMatch(StubTree stubTree,
|
||||
PsiFileWithStubSupport psiFile,
|
||||
List<StubElement<?>> plained,
|
||||
VirtualFile virtualFile,
|
||||
StubTree stubTreeFromIndex);
|
||||
|
||||
protected abstract void onInternalError(VirtualFile file);
|
||||
|
||||
|
||||
}
|
||||
@@ -19,11 +19,7 @@
|
||||
*/
|
||||
package com.intellij.psi.stubs;
|
||||
|
||||
import com.intellij.diagnostic.LogMessageEx;
|
||||
import com.intellij.diagnostic.errordialog.Attachment;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.application.ModalityState;
|
||||
import com.intellij.openapi.components.*;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
@@ -33,14 +29,8 @@ import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.openapi.vfs.newvfs.ManagingFS;
|
||||
import com.intellij.openapi.vfs.newvfs.persistent.PersistentFS;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiManager;
|
||||
import com.intellij.psi.PsiPlainTextFile;
|
||||
import com.intellij.psi.impl.source.PsiFileImpl;
|
||||
import com.intellij.psi.impl.source.PsiFileWithStubSupport;
|
||||
import com.intellij.psi.search.GlobalSearchScope;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.tree.IStubFileElementType;
|
||||
import com.intellij.psi.util.PsiUtilCore;
|
||||
import com.intellij.util.CommonProcessors;
|
||||
import com.intellij.util.Processor;
|
||||
@@ -76,6 +66,8 @@ public class StubIndexImpl extends StubIndex implements ApplicationComponent, Pe
|
||||
private final Map<StubIndexKey<?,?>, MyIndex<?>> myIndices = new THashMap<StubIndexKey<?,?>, MyIndex<?>>();
|
||||
private final TObjectIntHashMap<ID<?, ?>> myIndexIdToVersionMap = new TObjectIntHashMap<ID<?, ?>>();
|
||||
|
||||
private final StubProcessingHelper myStubProcessingHelper;
|
||||
|
||||
private StubIndexState myPreviouslyRegistered;
|
||||
|
||||
public StubIndexImpl(FileBasedIndex fileBasedIndex /* need this to ensure initialization order*/ ) throws IOException {
|
||||
@@ -96,6 +88,8 @@ public class StubIndexImpl extends StubIndex implements ApplicationComponent, Pe
|
||||
}
|
||||
}
|
||||
dropUnregisteredIndices();
|
||||
|
||||
myStubProcessingHelper = new StubProcessingHelper(fileBasedIndex);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -228,98 +222,9 @@ public class StubIndexImpl extends StubIndex implements ApplicationComponent, Pe
|
||||
if (file == null || scope != null && !scope.contains(file)) {
|
||||
return true;
|
||||
}
|
||||
StubTree stubTree = null;
|
||||
|
||||
final PsiFile _psifile = psiManager.findFile(file);
|
||||
PsiFileWithStubSupport psiFile = null;
|
||||
|
||||
if (_psifile != null && !(_psifile instanceof PsiPlainTextFile)) {
|
||||
if (_psifile instanceof PsiFileWithStubSupport) {
|
||||
psiFile = (PsiFileWithStubSupport)_psifile;
|
||||
stubTree = psiFile.getStubTree();
|
||||
if (stubTree == null && psiFile instanceof PsiFileImpl) {
|
||||
stubTree = ((PsiFileImpl)psiFile).calcStubTree();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (stubTree == null && psiFile == null) {
|
||||
return true;
|
||||
}
|
||||
if (stubTree == null) {
|
||||
ObjectStubTree objectStubTree = StubTreeLoader.getInstance().readFromVFile(project, file);
|
||||
if (!(objectStubTree instanceof ObjectStubTree)) {
|
||||
return true;
|
||||
}
|
||||
stubTree = (StubTree)objectStubTree;
|
||||
final List<StubElement<?>> plained = stubTree.getPlainList();
|
||||
for (int i = 0, size = value.size(); i < size; i++) {
|
||||
final StubElement<?> stub = plained.get(value.get(i));
|
||||
final ASTNode tree = psiFile.findTreeForStub(stubTree, stub);
|
||||
|
||||
if (tree != null) {
|
||||
if (tree.getElementType() == stubType(stub)) {
|
||||
Psi psi = (Psi)tree.getPsi();
|
||||
if (!processor.process(psi)) return false;
|
||||
}
|
||||
else {
|
||||
String persistedStubTree = ((PsiFileStubImpl)stubTree.getRoot()).printTree();
|
||||
|
||||
String stubTreeJustBuilt =
|
||||
((PsiFileStubImpl)((IStubFileElementType)((PsiFileImpl)psiFile).getContentElementType()).getBuilder()
|
||||
.buildStubTree(psiFile)).printTree();
|
||||
|
||||
StringBuilder builder = new StringBuilder();
|
||||
builder.append("Oops\n");
|
||||
|
||||
|
||||
builder.append("Recorded stub:-----------------------------------\n");
|
||||
builder.append(persistedStubTree);
|
||||
builder.append("\nAST built stub: ------------------------------------\n");
|
||||
builder.append(stubTreeJustBuilt);
|
||||
builder.append("\n");
|
||||
LOG.info(builder.toString());
|
||||
|
||||
// requestReindex() may want to acquire write lock (for indices not requiring content loading)
|
||||
// thus, because here we are under read lock, need to use invoke later
|
||||
ApplicationManager.getApplication().invokeLater(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
fileBasedIndex.requestReindex(file);
|
||||
}
|
||||
}, ModalityState.NON_MODAL);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
final List<StubElement<?>> plained = stubTree.getPlainList();
|
||||
for (int i = 0, size = value.size(); i < size; i++) {
|
||||
final int stubTreeIndex = value.get(i);
|
||||
if (stubTreeIndex >= plained.size()) {
|
||||
final VirtualFile virtualFile = psiFile.getVirtualFile();
|
||||
StubTree stubTreeFromIndex = (StubTree)StubTreeLoader.getInstance().readFromVFile(project, file);
|
||||
LOG.error(LogMessageEx.createEvent("PSI and index do not match: PSI " + psiFile + ", first stub " + plained.get(0),
|
||||
"Please report the problem to JetBrains with the file attached",
|
||||
new Attachment(virtualFile != null ? virtualFile.getPath() : "vFile.txt", psiFile.getText()),
|
||||
new Attachment("stubTree.txt", ((PsiFileStubImpl)stubTree.getRoot()).printTree()),
|
||||
new Attachment("stubTreeFromIndex.txt", stubTreeFromIndex == null ? "null" : ((PsiFileStubImpl)stubTreeFromIndex.getRoot()).printTree())));
|
||||
|
||||
ApplicationManager.getApplication().invokeLater(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
fileBasedIndex.requestReindex(file);
|
||||
}
|
||||
}, ModalityState.NON_MODAL);
|
||||
|
||||
break;
|
||||
}
|
||||
Psi psi = (Psi)plained.get(stubTreeIndex).getPsi();
|
||||
if (!processor.process(psi)) return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
return myStubProcessingHelper.processStubsInFile(project, file, value, processor);
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
finally {
|
||||
@@ -343,14 +248,6 @@ public class StubIndexImpl extends StubIndex implements ApplicationComponent, Pe
|
||||
return true;
|
||||
}
|
||||
|
||||
private static IElementType stubType(@NotNull final StubElement<?> stub) {
|
||||
if (stub instanceof PsiFileStub) {
|
||||
return ((PsiFileStub)stub).getType();
|
||||
}
|
||||
|
||||
return stub.getStubType();
|
||||
}
|
||||
|
||||
private static void forceRebuild(@NotNull Throwable e) {
|
||||
LOG.info(e);
|
||||
FileBasedIndex.getInstance().scheduleRebuild(StubUpdatingIndex.INDEX_ID, e);
|
||||
|
||||
@@ -0,0 +1,68 @@
|
||||
package com.intellij.psi.stubs;
|
||||
|
||||
import com.intellij.diagnostic.LogMessageEx;
|
||||
import com.intellij.diagnostic.errordialog.Attachment;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.application.ModalityState;
|
||||
import com.intellij.openapi.diagnostic.IdeaLoggingEvent;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiManager;
|
||||
import com.intellij.psi.PsiPlainTextFile;
|
||||
import com.intellij.psi.impl.source.PsiFileImpl;
|
||||
import com.intellij.psi.impl.source.PsiFileWithStubSupport;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.tree.IStubFileElementType;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.util.indexing.FileBasedIndex;
|
||||
import com.intellij.util.indexing.FileBasedIndexImpl;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Author: dmitrylomov
|
||||
*/
|
||||
public class StubProcessingHelper extends StubProcessingHelperBase {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.psi.stubs.StubProcessingHelper");
|
||||
private final FileBasedIndex myFileBasedIndex;
|
||||
|
||||
public StubProcessingHelper(FileBasedIndex fileBasedIndex) {
|
||||
myFileBasedIndex = fileBasedIndex;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onInternalError(final VirtualFile file) {
|
||||
// requestReindex() may want to acquire write lock (for indices not requiring content loading)
|
||||
// thus, because here we are under read lock, need to use invoke later
|
||||
ApplicationManager.getApplication().invokeLater(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
myFileBasedIndex.requestReindex(file);
|
||||
}
|
||||
}, ModalityState.NON_MODAL);
|
||||
}
|
||||
|
||||
|
||||
protected String stubTreeAndIndexDoNotMatch(StubTree stubTree,
|
||||
PsiFileWithStubSupport psiFile,
|
||||
List<StubElement<?>> plained,
|
||||
VirtualFile virtualFile,
|
||||
StubTree stubTreeFromIndex) {
|
||||
return LogMessageEx.createEvent("PSI and index do not match: PSI " + psiFile + ", first stub " + plained.get(0),
|
||||
"Please report the problem to JetBrains with the file attached",
|
||||
new Attachment(virtualFile != null ? virtualFile.getPath() : "vFile.txt",
|
||||
psiFile.getText()), new Attachment("stubTree.txt",
|
||||
((PsiFileStubImpl)stubTree
|
||||
.getRoot()).printTree()),
|
||||
new Attachment("stubTreeFromIndex.txt", stubTreeFromIndex == null
|
||||
? "null"
|
||||
: ((PsiFileStubImpl)stubTreeFromIndex
|
||||
.getRoot()).printTree())).toString();
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user