/**
   * Returns true if the root was loaded with conflict. False is returned in all other cases: in the
   * case of success and in case of some other error.
   */
  private boolean loadRoot(final VirtualFile root) {
    LOG.info("loadRoot " + root);
    myProgressIndicator.setText(GitHandlerUtil.formatOperationName("Unstashing changes to", root));

    GitRepository repository = myRepositoryManager.getRepositoryForRoot(root);
    if (repository == null) {
      LOG.error("Repository is null for root " + root);
      return false;
    }

    GitSimpleEventDetector conflictDetector =
        new GitSimpleEventDetector(GitSimpleEventDetector.Event.MERGE_CONFLICT_ON_UNSTASH);
    GitCommandResult result = myGit.stashPop(repository, conflictDetector);
    VfsUtil.markDirtyAndRefresh(false, true, false, root);
    if (result.success()) {
      return false;
    } else if (conflictDetector.hasHappened()) {
      return true;
    } else {
      LOG.info("unstash failed " + result.getErrorOutputAsJoinedString());
      GitUIUtil.notifyImportantError(
          myProject, "Couldn't unstash", "<br/>" + result.getErrorOutputAsHtmlString());
      return false;
    }
  }
  @NotNull
  public static VirtualFile getTargetDirectoryFor(
      @NotNull Project project,
      @NotNull VirtualFile sourceFile,
      @Nullable String targetFile,
      @Nullable String targetPackage,
      boolean returnRoot) {
    boolean hasPackage = StringUtil.isNotEmpty(targetPackage);
    ProjectRootManager rootManager = ProjectRootManager.getInstance(project);
    ProjectFileIndex fileIndex = ProjectFileIndex.SERVICE.getInstance(project);
    Collection<VirtualFile> files =
        targetFile == null
            ? Collections.<VirtualFile>emptyList()
            : FilenameIndex.getVirtualFilesByName(
                project, targetFile, ProjectScope.getAllScope(project));

    VirtualFile existingFile = null;
    for (VirtualFile file : files) {
      String existingFilePackage = fileIndex.getPackageNameByDirectory(file.getParent());
      if (!hasPackage || existingFilePackage == null || targetPackage.equals(existingFilePackage)) {
        existingFile = file;
        break;
      }
    }

    VirtualFile existingFileRoot =
        existingFile == null
            ? null
            : fileIndex.isInSourceContent(existingFile)
                ? fileIndex.getSourceRootForFile(existingFile)
                : fileIndex.isInContent(existingFile)
                    ? fileIndex.getContentRootForFile(existingFile)
                    : null;

    boolean preferGenRoot =
        sourceFile.getFileType() == BnfFileType.INSTANCE
            || sourceFile.getFileType() == JFlexFileType.INSTANCE;
    boolean preferSourceRoot = hasPackage && !preferGenRoot;
    VirtualFile[] sourceRoots = rootManager.getContentSourceRoots();
    VirtualFile[] contentRoots = rootManager.getContentRoots();
    final VirtualFile virtualRoot =
        existingFileRoot != null
            ? existingFileRoot
            : preferSourceRoot && fileIndex.isInSource(sourceFile)
                ? fileIndex.getSourceRootForFile(sourceFile)
                : fileIndex.isInContent(sourceFile)
                    ? fileIndex.getContentRootForFile(sourceFile)
                    : getFirstElement(
                        preferSourceRoot && sourceRoots.length > 0 ? sourceRoots : contentRoots);
    if (virtualRoot == null) {
      fail(project, sourceFile, "Unable to guess target source root");
      throw new ProcessCanceledException();
    }
    try {
      String genDirName = Options.GEN_DIR.get();
      boolean newGenRoot = !fileIndex.isInSourceContent(virtualRoot);
      final String relativePath =
          (hasPackage && newGenRoot
                  ? genDirName + "/" + targetPackage
                  : hasPackage ? targetPackage : newGenRoot ? genDirName : "")
              .replace('.', '/');
      if (relativePath.isEmpty()) {
        return virtualRoot;
      } else {
        VirtualFile result =
            new WriteAction<VirtualFile>() {
              @Override
              protected void run(@NotNull Result<VirtualFile> result) throws Throwable {
                result.setResult(VfsUtil.createDirectoryIfMissing(virtualRoot, relativePath));
              }
            }.execute().throwException().getResultObject();
        VfsUtil.markDirtyAndRefresh(false, true, true, result);
        return returnRoot && newGenRoot
            ? ObjectUtils.assertNotNull(virtualRoot.findChild(genDirName))
            : returnRoot ? virtualRoot : result;
      }
    } catch (ProcessCanceledException ex) {
      throw ex;
    } catch (Exception ex) {
      fail(project, sourceFile, ex.getMessage());
      throw new ProcessCanceledException();
    }
  }