From 3cb13616e8ffe8e20dd0fb297321f0426c588d04 Mon Sep 17 00:00:00 2001 From: Sergey Patrikeev Date: Thu, 7 May 2020 18:03:18 +0300 Subject: [PATCH] Stub indexes: move to SerializedStubTree assertion that deserialized stub of a SerializedStubTree matches original stub. This assertion used to be longer: for each file we used to build SerializedStubTree twice, deserialize their stubs and compare them. Let's check only that deserialized stub matches original stub. GitOrigin-RevId: fdc83f267b9235d0134d84e110d2ade15c875a0e --- .../psi/stubs/SerializedStubTree.java | 29 ++++++++++++++++++- .../util/indexing/IndexDataComparer.kt | 2 +- .../util/indexing/IndexDataPresenter.kt | 2 ++ .../intellij/psi/stubs/StubUpdatingIndex.java | 29 ++++++++----------- 4 files changed, 43 insertions(+), 19 deletions(-) diff --git a/platform/indexing-impl/src/com/intellij/psi/stubs/SerializedStubTree.java b/platform/indexing-impl/src/com/intellij/psi/stubs/SerializedStubTree.java index df9338188ab9..09533cc872d4 100644 --- a/platform/indexing-impl/src/com/intellij/psi/stubs/SerializedStubTree.java +++ b/platform/indexing-impl/src/com/intellij/psi/stubs/SerializedStubTree.java @@ -5,7 +5,12 @@ */ package com.intellij.psi.stubs; +import com.intellij.openapi.diagnostic.Attachment; +import com.intellij.openapi.diagnostic.RuntimeExceptionWithAttachments; import com.intellij.openapi.util.io.BufferExposingByteArrayOutputStream; +import com.intellij.util.indexing.IndexDataComparer; +import com.intellij.util.indexing.IndexDataPresenter; +import com.intellij.util.indexing.impl.DebugAssertions; import com.intellij.util.io.DigestUtil; import com.intellij.util.io.UnsyncByteArrayInputStream; import org.jetbrains.annotations.NotNull; @@ -62,7 +67,7 @@ public final class SerializedStubTree { forwardIndexExternalizer.save(new DataOutputStream(indexBytes), indexedStubs); byte[] indexedStubBytes = indexBytes.getInternalBuffer(); int indexedStubByteLength = indexBytes.size(); - return new SerializedStubTree( + SerializedStubTree stubTree = new SerializedStubTree( treeBytes, treeByteLength, indexedStubBytes, @@ -71,6 +76,10 @@ public final class SerializedStubTree { forwardIndexExternalizer, serializationManager ); + if (DebugAssertions.DEBUG) { + assertDeserializedStubMatchesOriginalStub(stubTree, rootStub); + } + return stubTree; } public @NotNull SerializedStubTree reSerialize(@NotNull SerializationManagerEx newSerializationManager, @@ -190,6 +199,24 @@ public final class SerializedStubTree { return (Map, Map>)(Map)map; } + private static void assertDeserializedStubMatchesOriginalStub(@NotNull SerializedStubTree stubTree, + @NotNull Stub originalStub) { + Stub deserializedStub; + try { + deserializedStub = stubTree.getStub(); + } + catch (SerializerNotFoundException e) { + throw new RuntimeException("Failed to deserialize stub tree", e); + } + if (!IndexDataComparer.INSTANCE.areStubsTheSame(originalStub, deserializedStub)) { + throw new RuntimeExceptionWithAttachments( + "Deserialized stub does not match original stub", + new Attachment("original-stub.txt", IndexDataPresenter.INSTANCE.getPresentableStub(originalStub)), + new Attachment("deserialized-stub.txt", IndexDataPresenter.INSTANCE.getPresentableStub(deserializedStub)) + ); + } + } + private byte[] myTreeHash; public synchronized byte @NotNull [] getTreeHash() { if (myTreeHash == null) { diff --git a/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataComparer.kt b/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataComparer.kt index c4efbca2dc4a..6116fb90104d 100644 --- a/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataComparer.kt +++ b/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataComparer.kt @@ -70,7 +70,7 @@ object IndexDataComparer { return expectedTree.stubIndicesValueMap == actualTree.stubIndicesValueMap } - private fun areStubsTheSame(expectedStub: Stub, actualStub: Stub): Boolean { + fun areStubsTheSame(expectedStub: Stub, actualStub: Stub): Boolean { // Check toString() to not rely on identity equality of [ObjectStubSerializer]s // because [ObjectStubSerializer] does not declare equals() / hashCode(). if (expectedStub.stubType != actualStub.stubType diff --git a/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataPresenter.kt b/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataPresenter.kt index 1a2b2528c5a4..fabf3d802999 100644 --- a/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataPresenter.kt +++ b/platform/indexing-impl/src/com/intellij/util/indexing/IndexDataPresenter.kt @@ -49,6 +49,8 @@ object IndexDataPresenter { } } + fun getPresentableStub(node: Stub): String = getPresentableStub(node, "") + private fun getPresentableStub(node: Stub, indent: String): String = buildString { append(indent) diff --git a/platform/lang-impl/src/com/intellij/psi/stubs/StubUpdatingIndex.java b/platform/lang-impl/src/com/intellij/psi/stubs/StubUpdatingIndex.java index 74b098e33a17..83ab74af926f 100644 --- a/platform/lang-impl/src/com/intellij/psi/stubs/StubUpdatingIndex.java +++ b/platform/lang-impl/src/com/intellij/psi/stubs/StubUpdatingIndex.java @@ -25,7 +25,6 @@ import com.intellij.util.BitUtil; import com.intellij.util.KeyedLazyInstance; import com.intellij.util.SystemProperties; import com.intellij.util.indexing.*; -import com.intellij.util.indexing.impl.DebugAssertions; import com.intellij.util.indexing.impl.IndexStorage; import com.intellij.util.indexing.impl.InputData; import com.intellij.util.indexing.impl.forward.EmptyForwardIndex; @@ -137,7 +136,7 @@ public final class StubUpdatingIndex extends SingleEntryFileBasedIndexExtension< if (prebuiltTree != null) { prebuiltTree = prebuiltTree.reSerialize(mySerializationManager, myStubIndexesExternalizer); if (PrebuiltIndexProvider.DEBUG_PREBUILT_INDICES) { - assertRebuiltTreeMatchesActualTree(inputData, type, prebuiltTree); + assertPrebuiltStubTreeMatchesActualTree(prebuiltTree, inputData, type); } return prebuiltTree; } @@ -146,11 +145,7 @@ public final class StubUpdatingIndex extends SingleEntryFileBasedIndexExtension< } try { - SerializedStubTree builtTree = buildSerializedStubTree(inputData, type); - if (builtTree != null && DebugAssertions.DEBUG) { - assertRebuiltTreeMatchesActualTree(inputData, type, builtTree); - } - return builtTree; + return buildSerializedStubTree(inputData, type); } catch (ProcessCanceledException pce) { throw pce; @@ -185,19 +180,19 @@ public final class StubUpdatingIndex extends SingleEntryFileBasedIndexExtension< return SerializedStubTree.serializeStub(stub, mySerializationManager, myStubIndexesExternalizer); } - private void assertRebuiltTreeMatchesActualTree(@NotNull FileContent fileContent, - @NotNull StubBuilderType type, - @NotNull SerializedStubTree actualTree) { + private void assertPrebuiltStubTreeMatchesActualTree(@NotNull SerializedStubTree prebuiltStubTree, + @NotNull FileContent fileContent, + @NotNull StubBuilderType type) { try { - SerializedStubTree rebuiltTree = buildSerializedStubTree(fileContent, type); - if (rebuiltTree == null) { - throw new IllegalStateException("Cannot build tree for " + fileContent.getFile().getUrl()); + SerializedStubTree actualTree = buildSerializedStubTree(fileContent, type); + if (actualTree == null) { + throw new RuntimeException("Cannot build actual stub tree for " + fileContent.getFile().getUrl()); } - if (!IndexDataComparer.INSTANCE.areStubTreesTheSame(rebuiltTree, actualTree)) { + if (!IndexDataComparer.INSTANCE.areStubTreesTheSame(actualTree, prebuiltStubTree)) { throw new RuntimeExceptionWithAttachments( - "Stubs mismatch", - new Attachment("rebuilt-stub-tree.txt", IndexDataPresenter.INSTANCE.getPresentableSerializedStubTree(rebuiltTree)), - new Attachment("actual-stub-tree.txt", IndexDataPresenter.INSTANCE.getPresentableSerializedStubTree(actualTree)) + "Prebuilt stub tree does not match actual stub tree", + new Attachment("actual-stub-tree.txt", IndexDataPresenter.INSTANCE.getPresentableSerializedStubTree(actualTree)), + new Attachment("prebuilt-stub-tree.txt", IndexDataPresenter.INSTANCE.getPresentableSerializedStubTree(prebuiltStubTree)) ); } }