From cb2135f4cee20d9c7e17622ccba0062af0750f3e Mon Sep 17 00:00:00 2001 From: Vladimir Krivosheev Date: Thu, 25 Oct 2018 12:03:07 +0200 Subject: [PATCH] loadSchemes: reuse message digest (make sense only for not lazy scheme processors) --- .../src/schemeManager/schemeLoader.kt | 25 +++++++++++++++---- .../configurationStore/scheme-impl.kt | 9 ++++--- 2 files changed, 26 insertions(+), 8 deletions(-) diff --git a/platform/configuration-store-impl/src/schemeManager/schemeLoader.kt b/platform/configuration-store-impl/src/schemeManager/schemeLoader.kt index c4075271f650..2a67f300599a 100644 --- a/platform/configuration-store-impl/src/schemeManager/schemeLoader.kt +++ b/platform/configuration-store-impl/src/schemeManager/schemeLoader.kt @@ -1,9 +1,7 @@ // Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. package com.intellij.configurationStore.schemeManager -import com.intellij.configurationStore.LOG -import com.intellij.configurationStore.LazySchemeProcessor -import com.intellij.configurationStore.digest +import com.intellij.configurationStore.* import com.intellij.openapi.application.runUndoTransparentWriteAction import com.intellij.openapi.options.NonLazySchemeProcessor import com.intellij.openapi.project.ProjectBundle @@ -21,6 +19,7 @@ import org.xmlpull.v1.XmlPullParser import java.io.IOException import java.io.InputStream import java.nio.file.Path +import java.security.MessageDigest import java.util.* import java.util.concurrent.atomic.AtomicBoolean import java.util.function.Function @@ -36,6 +35,8 @@ internal class SchemeLoader(private val schemeManag private val isApplied = AtomicBoolean() + private var digest: MessageDigest? = null + private fun isFromFileWithOldExtension(existingScheme: T): Boolean { val info = schemeManager.schemeToInfo.get(existingScheme) // scheme from file with old extension, so, we must ignore it @@ -66,6 +67,18 @@ internal class SchemeLoader(private val schemeManag return result } + private fun getDigest(): MessageDigest { + var result = digest + if (result == null) { + result = createDataDigest() + digest = result + } + else { + result.reset() + } + return result + } + fun loadScheme(fileName: String, input: InputStream): MUTABLE_SCHEME? { val extension = schemeManager.getFileExtension(fileName, isAllowAny = false) if (isFileScheduledForDeleteInThisLoadSession(fileName)) { @@ -107,8 +120,10 @@ internal class SchemeLoader(private val schemeManag fun createInfo(schemeName: String, element: Element?): ExternalInfo { val info = ExternalInfo(fileNameWithoutExtension, extension) - element?.let { - info.digest = it.digest() + if (element != null) { + val digest = getDigest() + serializeElementToBinary(element, DigestOutputStream(digest)) + info.digest = digest.digest() } info.schemeKey = schemeName return info diff --git a/platform/projectModel-impl/src/com/intellij/configurationStore/scheme-impl.kt b/platform/projectModel-impl/src/com/intellij/configurationStore/scheme-impl.kt index 28084dd5008a..29ff448bc7ac 100644 --- a/platform/projectModel-impl/src/com/intellij/configurationStore/scheme-impl.kt +++ b/platform/projectModel-impl/src/com/intellij/configurationStore/scheme-impl.kt @@ -88,10 +88,13 @@ class DigestOutputStream(val digest: MessageDigest) : OutputStream() { override fun toString(): String = "[Digest Output Stream] $digest" } -val SHA1Provider = java.security.Security.getProvider("SUN") +private val sha1Provider = java.security.Security.getProvider("SUN") + +// sha-1 is enough, sha-256 is slower, see https://www.nayuki.io/page/native-hash-functions-for-java +fun createDataDigest(): MessageDigest = MessageDigest.getInstance("SHA-1", sha1Provider) + fun Element.digest(): ByteArray { - // sha-1 is enough, sha-256 is slower, see https://www.nayuki.io/page/native-hash-functions-for-java - val digest = MessageDigest.getInstance("SHA-1", SHA1Provider) + val digest = createDataDigest() serializeElementToBinary(this, DigestOutputStream(digest)) return digest.digest() }