From 5bac8176a49c2f867a6375013bd44495fe2e9139 Mon Sep 17 00:00:00 2001 From: peter Date: Fri, 18 Nov 2016 11:45:44 +0100 Subject: [PATCH] disallow modal indexing during PSI/VFS events --- .../openapi/project/DumbServiceImpl.java | 1 + .../project/NoAccessDuringPsiEvents.java | 47 +++++++++++++++++++ 2 files changed, 48 insertions(+) create mode 100644 platform/platform-impl/src/com/intellij/openapi/project/NoAccessDuringPsiEvents.java diff --git a/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java b/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java index 980c2dc462c3..967d8ef78757 100644 --- a/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java @@ -385,6 +385,7 @@ public class DumbServiceImpl extends DumbService implements Disposable, Modifica } private void showModalProgress() { + NoAccessDuringPsiEvents.checkCallContext(); try { ((ApplicationImpl)ApplicationManager.getApplication()).executeSuspendingWriteAction(myProject, IdeBundle.message("progress.indexing"), () -> runBackgroundProcess(ProgressManager.getInstance().getProgressIndicator())); diff --git a/platform/platform-impl/src/com/intellij/openapi/project/NoAccessDuringPsiEvents.java b/platform/platform-impl/src/com/intellij/openapi/project/NoAccessDuringPsiEvents.java new file mode 100644 index 000000000000..575b90496b2c --- /dev/null +++ b/platform/platform-impl/src/com/intellij/openapi/project/NoAccessDuringPsiEvents.java @@ -0,0 +1,47 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.openapi.project; + +import com.intellij.openapi.application.Application; +import com.intellij.openapi.application.ApplicationManager; +import com.intellij.openapi.diagnostic.Logger; +import com.intellij.openapi.vfs.VirtualFileManager; +import com.intellij.psi.impl.DebugUtil; +import com.intellij.psi.util.PsiModificationTracker; +import com.intellij.util.messages.MessageBus; + +import java.util.HashSet; +import java.util.Set; + +/** + * @author peter + */ +public class NoAccessDuringPsiEvents { + private static final Logger LOG = Logger.getInstance("#com.intellij.openapi.project.NoAccessDuringPsiEvents"); + private static final Set ourReportedTraces = new HashSet<>(); + + public static void checkCallContext() { + Application application = ApplicationManager.getApplication(); + if (!application.isWriteAccessAllowed()) return; + + MessageBus bus = application.getMessageBus(); + if (bus.hasUndeliveredEvents(VirtualFileManager.VFS_CHANGES) || bus.hasUndeliveredEvents(PsiModificationTracker.TOPIC)) { + if (ourReportedTraces.add(DebugUtil.currentStackTrace())) { + LOG.error("It's prohibited to access index during event dispatching"); + } + } + } +}