public String[] knownNamespaces() {
   final PsiElement parentElement = getParent();
   BidirectionalMap<String, String> map = initNamespaceMaps(parentElement);
   Set<String> known = Collections.emptySet();
   if (map != null) {
     known = new HashSet<String>(map.values());
   }
   if (parentElement instanceof XmlTag) {
     if (known.isEmpty()) return ((XmlTag) parentElement).knownNamespaces();
     ContainerUtil.addAll(known, ((XmlTag) parentElement).knownNamespaces());
   } else {
     XmlExtension xmlExtension = XmlExtension.getExtensionByElement(this);
     if (xmlExtension != null) {
       final XmlFile xmlFile = xmlExtension.getContainingFile(this);
       if (xmlFile != null) {
         final XmlTag rootTag = xmlFile.getRootTag();
         if (rootTag != null && rootTag != this) {
           if (known.isEmpty()) return rootTag.knownNamespaces();
           ContainerUtil.addAll(known, rootTag.knownNamespaces());
         }
       }
     }
   }
   return ArrayUtil.toStringArray(known);
 }
  private synchronized void assertAllPointersDisposed() {
    for (Map.Entry<VirtualFilePointerListener, FilePointerPartNode> entry : myPointers.entrySet()) {
      FilePointerPartNode root = entry.getValue();
      ArrayList<FilePointerPartNode> left = new ArrayList<FilePointerPartNode>();
      root.getPointersUnder(null, false, "", left);
      if (!left.isEmpty()) {
        VirtualFilePointerImpl p = left.get(0).leaf;
        try {
          p.throwDisposalError("Not disposed pointer: " + p);
        } finally {
          for (FilePointerPartNode pair : left) {
            VirtualFilePointerImpl pointer = pair.leaf;
            pointer.dispose();
          }
        }
      }
    }

    synchronized (myContainers) {
      if (!myContainers.isEmpty()) {
        VirtualFilePointerContainerImpl container = myContainers.iterator().next();
        container.throwDisposalError("Not disposed container");
      }
    }
  }
  @Override
  public void commitAllDocuments() {
    ApplicationManager.getApplication().assertIsDispatchThread();
    if (myUncommittedDocuments.isEmpty()) return;

    final Document[] documents = getUncommittedDocuments();
    for (Document document : documents) {
      commitDocument(document);
    }

    LOG.assertTrue(!hasUncommitedDocuments(), myUncommittedDocuments);
  }
 public static void cleanupDeleteOnExitHookList()
     throws ClassNotFoundException, NoSuchFieldException, IllegalAccessException {
   // try to reduce file set retained by java.io.DeleteOnExitHook
   List<String> list;
   synchronized (DELETE_ON_EXIT_HOOK_CLASS) {
     if (DELETE_ON_EXIT_HOOK_DOT_FILES.isEmpty()) return;
     list = new ArrayList<String>(DELETE_ON_EXIT_HOOK_DOT_FILES);
   }
   for (int i = list.size() - 1; i >= 0; i--) {
     String path = list.get(i);
     if (FileSystemUtil.getAttributes(path) == null || new File(path).delete()) {
       synchronized (DELETE_ON_EXIT_HOOK_CLASS) {
         DELETE_ON_EXIT_HOOK_DOT_FILES.remove(path);
       }
     }
   }
 }
 /**
  * Cancel previously registered action and schedules (new) action to be executed when all
  * documents are committed.
  *
  * @param key the (unique) id of the action.
  * @param action The action to be executed after automatic commit. This action will overwrite any
  *     action which was registered under this key earlier. The action will be executed in EDT.
  * @return true if action has been run immediately, or false if action was scheduled for execution
  *     later.
  */
 public boolean cancelAndRunWhenAllCommitted(
     @NonNls @NotNull Object key, @NotNull final Runnable action) {
   ApplicationManager.getApplication().assertIsDispatchThread();
   if (myProject.isDisposed()) {
     action.run();
     return true;
   }
   if (myUncommittedDocuments.isEmpty()) {
     action.run();
     if (!hasUncommitedDocuments()) {
       assert actionsWhenAllDocumentsAreCommitted.isEmpty() : actionsWhenAllDocumentsAreCommitted;
     }
     return true;
   }
   actionsWhenAllDocumentsAreCommitted.put(key, action);
   return false;
 }
  private void runQuery() {
    if (getRootPane() == null) return;

    Set<InlineProgressIndicator> indicators = getCurrentInlineIndicators();
    if (indicators.isEmpty()) return;

    for (InlineProgressIndicator each : indicators) {
      each.updateProgress();
    }
    myQueryAlarm.cancelAllRequests();
    myQueryAlarm.addRequest(
        new Runnable() {
          @Override
          public void run() {
            runQuery();
          }
        },
        2000);
  }
 /**
  * Schedules action to be executed when all documents are committed.
  *
  * @return true if action has been run immediately, or false if action was scheduled for execution
  *     later.
  */
 @Override
 public boolean performWhenAllCommitted(@NotNull final Runnable action) {
   ApplicationManager.getApplication().assertIsDispatchThread();
   assert !myProject.isDisposed() : "Already disposed: " + myProject;
   if (myUncommittedDocuments.isEmpty()) {
     action.run();
     return true;
   }
   CompositeRunnable actions =
       (CompositeRunnable) actionsWhenAllDocumentsAreCommitted.get(PERFORM_ALWAYS_KEY);
   if (actions == null) {
     actions = new CompositeRunnable();
     actionsWhenAllDocumentsAreCommitted.put(PERFORM_ALWAYS_KEY, actions);
   }
   actions.add(action);
   myDocumentCommitProcessor.log(
       "PDI: added performWhenAllCommitted", null, false, action, myUncommittedDocuments);
   return false;
 }
  // returns false if canceled
  private boolean addInjectedPsiHighlights(
      @NotNull final Set<PsiFile> injectedFiles,
      @NotNull final ProgressIndicator progress,
      @NotNull final Collection<HighlightInfo> outInfos) {
    if (injectedFiles.isEmpty()) return true;
    final InjectedLanguageManager injectedLanguageManager =
        InjectedLanguageManager.getInstance(myProject);
    final TextAttributes injectedAttributes =
        myGlobalScheme.getAttributes(EditorColors.INJECTED_LANGUAGE_FRAGMENT);

    return JobLauncher.getInstance()
        .invokeConcurrentlyUnderProgress(
            new ArrayList<PsiFile>(injectedFiles),
            progress,
            isFailFastOnAcquireReadAction(),
            new Processor<PsiFile>() {
              @Override
              public boolean process(final PsiFile injectedPsi) {
                return addInjectedPsiHighlights(
                    injectedPsi, injectedAttributes, outInfos, progress, injectedLanguageManager);
              }
            });
  }
  @Override
  protected void collectInformationWithProgress(@NotNull final ProgressIndicator progress) {
    if (!Registry.is("editor.injected.highlighting.enabled")) return;

    final Set<HighlightInfo> gotHighlights = new THashSet<HighlightInfo>(100);

    final List<PsiElement> inside = new ArrayList<PsiElement>();
    final List<PsiElement> outside = new ArrayList<PsiElement>();
    List<ProperTextRange> insideRanges = new ArrayList<ProperTextRange>();
    List<ProperTextRange> outsideRanges = new ArrayList<ProperTextRange>();
    // TODO: this thing is just called TWICE with same arguments eating CPU on huge files :(
    Divider.divideInsideAndOutside(
        myFile,
        myRestrictRange.getStartOffset(),
        myRestrictRange.getEndOffset(),
        myPriorityRange,
        inside,
        insideRanges,
        outside,
        outsideRanges,
        false,
        SHOULD_HIGHIGHT_FILTER);

    // all infos for the "injected fragment for the host which is inside" are indeed inside
    // but some of the infos for the "injected fragment for the host which is outside" can be still
    // inside
    Set<HighlightInfo> injectedResult = new THashSet<HighlightInfo>();
    Set<PsiFile> injected = getInjectedPsiFiles(inside, outside, progress);
    setProgressLimit(injected.size());

    if (!addInjectedPsiHighlights(
        injected, progress, Collections.synchronizedSet(injectedResult))) {
      throw new ProcessCanceledException();
    }
    final List<HighlightInfo> injectionsOutside =
        new ArrayList<HighlightInfo>(gotHighlights.size());

    Set<HighlightInfo> result;
    synchronized (injectedResult) {
      // sync here because all writes happened in another thread
      result = injectedResult;
    }
    for (HighlightInfo info : result) {
      if (myRestrictRange.contains(info)) {
        gotHighlights.add(info);
      } else {
        // nonconditionally apply injected results regardless whether they are in
        // myStartOffset,myEndOffset
        injectionsOutside.add(info);
      }
    }

    if (!injectionsOutside.isEmpty()) {
      final ProperTextRange priorityIntersection = myPriorityRange.intersection(myRestrictRange);
      if ((!inside.isEmpty() || !gotHighlights.isEmpty())
          && priorityIntersection
              != null) { // do not apply when there were no elements to highlight
        // clear infos found in visible area to avoid applying them twice
        final List<HighlightInfo> toApplyInside = new ArrayList<HighlightInfo>(gotHighlights);
        myHighlights.addAll(toApplyInside);
        gotHighlights.clear();

        myHighlightInfoProcessor.highlightsInsideVisiblePartAreProduced(
            myHighlightingSession, toApplyInside, myPriorityRange, myRestrictRange, getId());
      }

      List<HighlightInfo> toApply = new ArrayList<HighlightInfo>();
      for (HighlightInfo info : gotHighlights) {
        if (!myRestrictRange.containsRange(info.getStartOffset(), info.getEndOffset())) continue;
        if (!myPriorityRange.containsRange(info.getStartOffset(), info.getEndOffset())) {
          toApply.add(info);
        }
      }
      toApply.addAll(injectionsOutside);

      myHighlightInfoProcessor.highlightsOutsideVisiblePartAreProduced(
          myHighlightingSession,
          toApply,
          myRestrictRange,
          new ProperTextRange(0, myDocument.getTextLength()),
          getId());
    } else {
      // else apply only result (by default apply command) and only within inside
      myHighlights.addAll(gotHighlights);
      myHighlightInfoProcessor.highlightsInsideVisiblePartAreProduced(
          myHighlightingSession, myHighlights, myRestrictRange, myRestrictRange, getId());
    }
  }
  // returns false if canceled
  private boolean addInjectedPsiHighlights(
      @NotNull final Set<PsiFile> injectedFiles,
      @NotNull final ProgressIndicator progress,
      @NotNull final Collection<HighlightInfo> outInfos) {
    if (injectedFiles.isEmpty()) return true;
    final InjectedLanguageManager injectedLanguageManager =
        InjectedLanguageManager.getInstance(myProject);
    final TextAttributes injectedAttributes =
        myGlobalScheme.getAttributes(EditorColors.INJECTED_LANGUAGE_FRAGMENT);

    return JobUtil.invokeConcurrentlyUnderProgress(
        new ArrayList<PsiFile>(injectedFiles),
        progress,
        myFailFastOnAcquireReadAction,
        new Processor<PsiFile>() {
          @Override
          public boolean process(final PsiFile injectedPsi) {
            DocumentWindow documentWindow =
                (DocumentWindow)
                    PsiDocumentManager.getInstance(myProject).getCachedDocument(injectedPsi);
            if (documentWindow == null) return true;
            Place places = InjectedLanguageUtil.getShreds(injectedPsi);
            for (PsiLanguageInjectionHost.Shred place : places) {
              TextRange textRange =
                  place.getRangeInsideHost().shiftRight(place.host.getTextRange().getStartOffset());
              if (textRange.isEmpty()) continue;
              String desc =
                  injectedPsi.getLanguage().getDisplayName() + ": " + injectedPsi.getText();
              HighlightInfo info =
                  HighlightInfo.createHighlightInfo(
                      HighlightInfoType.INJECTED_LANGUAGE_FRAGMENT,
                      textRange,
                      null,
                      desc,
                      injectedAttributes);
              info.fromInjection = true;
              outInfos.add(info);
            }

            HighlightInfoHolder holder = createInfoHolder(injectedPsi);
            runHighlightVisitorsForInjected(injectedPsi, holder, progress);
            for (int i = 0; i < holder.size(); i++) {
              HighlightInfo info = holder.get(i);
              final int startOffset = documentWindow.injectedToHost(info.startOffset);
              final TextRange fixedTextRange = getFixedTextRange(documentWindow, startOffset);
              addPatchedInfos(
                  info,
                  injectedPsi,
                  documentWindow,
                  injectedLanguageManager,
                  fixedTextRange,
                  outInfos);
            }
            holder.clear();
            highlightInjectedSyntax(injectedPsi, holder);
            for (int i = 0; i < holder.size(); i++) {
              HighlightInfo info = holder.get(i);
              final int startOffset = info.startOffset;
              final TextRange fixedTextRange = getFixedTextRange(documentWindow, startOffset);
              if (fixedTextRange == null) {
                info.fromInjection = true;
                outInfos.add(info);
              } else {
                HighlightInfo patched =
                    new HighlightInfo(
                        info.forcedTextAttributes,
                        info.forcedTextAttributesKey,
                        info.type,
                        fixedTextRange.getStartOffset(),
                        fixedTextRange.getEndOffset(),
                        info.description,
                        info.toolTip,
                        info.type.getSeverity(null),
                        info.isAfterEndOfLine,
                        null,
                        false);
                patched.fromInjection = true;
                outInfos.add(patched);
              }
            }

            if (!isDumbMode()) {
              List<HighlightInfo> todos = new ArrayList<HighlightInfo>();
              highlightTodos(
                  injectedPsi,
                  injectedPsi.getText(),
                  0,
                  injectedPsi.getTextLength(),
                  progress,
                  myPriorityRange,
                  todos,
                  todos);
              for (HighlightInfo info : todos) {
                addPatchedInfos(
                    info, injectedPsi, documentWindow, injectedLanguageManager, null, outInfos);
              }
            }
            return true;
          }
        });
  }
 @Override
 public boolean hasUncommitedDocuments() {
   return !myIsCommitInProgress && !myUncommittedDocuments.isEmpty();
 }
  private void updateOutputItemsList(
      final String outputDir,
      final VirtualFile srcFile,
      VirtualFile sourceRoot,
      final String packagePrefix,
      final List<File> filesToRefresh,
      Map<String, Collection<TranslatingCompiler.OutputItem>> results,
      final GlobalSearchScope srcRootScope)
      throws CacheCorruptedException {
    CompositeDependencyCache dependencyCache = myCompileContext.getDependencyCache();
    JavaDependencyCache child = dependencyCache.findChild(JavaDependencyCache.class);
    final Cache newCache = child.getNewClassesCache();
    final Set<CompiledClass> paths = myFileNameToSourceMap.get(srcFile.getName());
    if (paths == null || paths.isEmpty()) {
      return;
    }
    final String filePath = "/" + calcPackagePath(srcFile, sourceRoot, packagePrefix);
    for (final CompiledClass cc : paths) {
      myCompileContext.getProgressIndicator().checkCanceled();
      if (LOG.isDebugEnabled()) {
        LOG.debug("Checking [pathToClass; relPathToSource] = " + cc);
      }

      boolean pathsEquals = FileUtil.pathsEqual(filePath, cc.relativePathToSource);
      if (!pathsEquals) {
        final String qName = child.resolve(cc.qName);
        if (qName != null) {
          pathsEquals =
              ApplicationManager.getApplication()
                  .runReadAction(
                      new Computable<Boolean>() {
                        public Boolean compute() {
                          final JavaPsiFacade facade = JavaPsiFacade.getInstance(myProject);
                          PsiClass psiClass = facade.findClass(qName, srcRootScope);
                          if (psiClass == null) {
                            final int dollarIndex = qName.indexOf("$");
                            if (dollarIndex >= 0) {
                              final String topLevelClassName = qName.substring(0, dollarIndex);
                              psiClass = facade.findClass(topLevelClassName, srcRootScope);
                            }
                          }
                          if (psiClass != null) {
                            final VirtualFile vFile = psiClass.getContainingFile().getVirtualFile();
                            return vFile != null && vFile.equals(srcFile);
                          }
                          return false;
                        }
                      });
        }
      }

      if (pathsEquals) {
        final String outputPath = cc.pathToClass.replace(File.separatorChar, '/');
        final Pair<String, String> realLocation =
            moveToRealLocation(outputDir, outputPath, srcFile, filesToRefresh);
        if (realLocation != null) {
          Collection<TranslatingCompiler.OutputItem> outputs = results.get(realLocation.getFirst());
          if (outputs == null) {
            outputs = new ArrayList<TranslatingCompiler.OutputItem>();
            results.put(realLocation.getFirst(), outputs);
          }
          outputs.add(new OutputItemImpl(realLocation.getSecond(), srcFile));
          if (PACKAGE_ANNOTATION_FILE_NAME.equals(srcFile.getName())) {
            myProcessedPackageInfos.add(srcFile);
          }
          if (CompilerManager.MAKE_ENABLED) {
            newCache.setPath(cc.qName, realLocation.getSecond());
          }
          if (LOG.isDebugEnabled()) {
            LOG.debug(
                "Added output item: [outputDir; outputPath; sourceFile]  = ["
                    + realLocation.getFirst()
                    + "; "
                    + realLocation.getSecond()
                    + "; "
                    + srcFile.getPresentableUrl()
                    + "]");
          }
        } else {
          myCompileContext.addMessage(
              CompilerMessageCategory.ERROR,
              "Failed to copy from temporary location to output directory: "
                  + outputPath
                  + " (see idea.log for details)",
              null,
              -1,
              -1);
          if (LOG.isDebugEnabled()) {
            LOG.debug("Failed to move to real location: " + outputPath + "; from " + outputDir);
          }
        }
      }
    }
  }
  // currently only one level here..
  public boolean contains(@NotNull String name, @NotNull final VirtualFile vFile) {
    final ProjectFileIndex projectFileIndex =
        ProjectRootManager.getInstance(myProject).getFileIndex();
    final Set<Boolean> find = new HashSet<Boolean>();
    final ContentIterator contentIterator =
        new ContentIterator() {
          public boolean processFile(VirtualFile fileOrDir) {
            if (fileOrDir != null && fileOrDir.getPath().equals(vFile.getPath())) {
              find.add(Boolean.TRUE);
            }
            return true;
          }
        };

    Collection<TreeItem<Pair<AbstractUrl, String>>> urls = getFavoritesListRootUrls(name);
    for (TreeItem<Pair<AbstractUrl, String>> pair : urls) {
      AbstractUrl abstractUrl = pair.getData().getFirst();
      if (abstractUrl == null) {
        continue;
      }
      final Object[] path = abstractUrl.createPath(myProject);
      if (path == null || path.length < 1 || path[0] == null) {
        continue;
      }
      Object element = path[path.length - 1];
      if (element instanceof SmartPsiElementPointer) {
        final VirtualFile virtualFile =
            PsiUtilBase.getVirtualFile(((SmartPsiElementPointer) element).getElement());
        if (virtualFile == null) continue;
        if (vFile.getPath().equals(virtualFile.getPath())) {
          return true;
        }
        if (!virtualFile.isDirectory()) {
          continue;
        }
        projectFileIndex.iterateContentUnderDirectory(virtualFile, contentIterator);
      }

      if (element instanceof PsiElement) {
        final VirtualFile virtualFile = PsiUtilBase.getVirtualFile((PsiElement) element);
        if (virtualFile == null) continue;
        if (vFile.getPath().equals(virtualFile.getPath())) {
          return true;
        }
        if (!virtualFile.isDirectory()) {
          continue;
        }
        projectFileIndex.iterateContentUnderDirectory(virtualFile, contentIterator);
      }
      if (element instanceof Module) {
        ModuleRootManager.getInstance((Module) element)
            .getFileIndex()
            .iterateContent(contentIterator);
      }
      if (element instanceof LibraryGroupElement) {
        final boolean inLibrary =
            ModuleRootManager.getInstance(((LibraryGroupElement) element).getModule())
                    .getFileIndex()
                    .isInContent(vFile)
                && projectFileIndex.isInLibraryClasses(vFile);
        if (inLibrary) {
          return true;
        }
      }
      if (element instanceof NamedLibraryElement) {
        NamedLibraryElement namedLibraryElement = (NamedLibraryElement) element;
        final VirtualFile[] files =
            namedLibraryElement.getOrderEntry().getRootFiles(OrderRootType.CLASSES);
        if (files != null && ArrayUtil.find(files, vFile) > -1) {
          return true;
        }
      }
      if (element instanceof ModuleGroup) {
        ModuleGroup group = (ModuleGroup) element;
        final Collection<Module> modules = group.modulesInGroup(myProject, true);
        for (Module module : modules) {
          ModuleRootManager.getInstance(module).getFileIndex().iterateContent(contentIterator);
        }
      }

      for (FavoriteNodeProvider provider :
          Extensions.getExtensions(FavoriteNodeProvider.EP_NAME, myProject)) {
        if (provider.elementContainsFile(element, vFile)) {
          return true;
        }
      }

      if (!find.isEmpty()) {
        return true;
      }
    }
    return false;
  }