private void runJavaProcessInProject(
      TmcProjectInfo projectInfo,
      ClassPath classPath,
      String taskName,
      List<String> args,
      InputOutput inOut,
      BgTaskListener<ProcessResult> listener) {
    FileObject projectDir = projectInfo.getProjectDir();

    JavaPlatform platform =
        JavaPlatform.getDefault(); // Should probably use project's configured platform instead

    FileObject javaExe = platform.findTool("java");
    if (javaExe == null) {
      throw new IllegalArgumentException();
    }

    // TMC server packages this with every exercise for our convenience.
    // True even for Maven exercises, at least until NB's Maven API is published.
    ClassPath testRunnerClassPath = getTestRunnerClassPath(projectInfo);

    if (testRunnerClassPath != null) {
      classPath = ClassPathSupport.createProxyClassPath(classPath, testRunnerClassPath);
    }

    String[] command = new String[3 + args.size()];
    command[0] = FileUtil.toFile(javaExe).getAbsolutePath();
    command[1] = "-cp";
    command[2] = classPath.toString(ClassPath.PathConversionMode.WARN);
    System.arraycopy(args.toArray(new String[args.size()]), 0, command, 3, args.size());

    log.info(StringUtils.join(command, ' '));
    ProcessRunner runner = new ProcessRunner(command, FileUtil.toFile(projectDir), inOut);
    BgTask.start(taskName, runner, listener);
  }
  private void performAction(Project... projects) {
    projectMediator.saveAllFiles();
    for (final Project project : projects) {
      final TmcProjectInfo projectInfo = projectMediator.wrapProject(project);
      eventBus.post(new InvokedEvent(projectInfo));
      BgTask.start(
          "Compiling project",
          startCompilingProject(projectInfo),
          new BgTaskListener<Integer>() {
            @Override
            public void bgTaskReady(Integer result) {
              if (result == 0) {
                startRunningTests(projectInfo);
              } else {
                dialogDisplayer.displayError("The code did not compile.");
              }
            }

            @Override
            public void bgTaskFailed(Throwable ex) {
              dialogDisplayer.displayError("Failed to compile the code.");
            }

            @Override
            public void bgTaskCancelled() {}
          });
    }
  }
  private void startRunningMavenProjectTests(final TmcProjectInfo projectInfo) {
    final File projectDir = projectInfo.getProjectDirAsFile();
    String goal = MAVEN_TEST_RUN_GOAL;
    Map<String, String> props = new HashMap<String, String>();
    InputOutput inOut = getIoTab();

    List<String> jvmOpts = new ArrayList<String>();

    Integer memLimit = getMemoryLimit(projectInfo.getProject());
    if (memLimit != null) {
      jvmOpts.add("-Xmx" + memLimit + "m");
    }

    jvmOpts.add("-D" + ERROR_MSG_LOCALE_SETTING + "=" + settings.getErrorMsgLocale().toString());

    props.put("tmc.test.jvm_opts", StringUtils.join(jvmOpts, ' '));

    final ProcessRunner runner =
        new MavenRunBuilder()
            .setProjectDir(projectDir)
            .addGoal(goal)
            .setProperties(props)
            .setIO(inOut)
            .createProcessRunner();

    BgTask.start(
        "Running tests",
        runner,
        new BgTaskListener<ProcessResult>() {
          @Override
          public void bgTaskReady(ProcessResult processResult) {
            File resultsFile =
                new File(
                    projectDir.getPath()
                        + File.separator
                        + "target"
                        + File.separator
                        + "test_output.txt");
            log.log(
                Level.INFO,
                "Next calling handleTestResults: projectInfo: {0}, file: {1}",
                new Object[] {projectInfo.getProjectDirAbsPath(), resultsFile.exists()});
            handleTestResults(projectInfo, resultsFile);
          }

          @Override
          public void bgTaskCancelled() {}

          @Override
          public void bgTaskFailed(Throwable ex) {
            dialogDisplayer.displayError("Failed to run tests:\n" + ex.getMessage());
          }
        });
  }
  private void startRunningMakefileProjectTests(
      final TmcProjectInfo projectInfo, final boolean withValgrind) {
    final File testDir = projectInfo.getProjectDirAsFile();
    String[] command;
    if (withValgrind) {
      command =
          new String[] {
            "valgrind",
            "--log-file=valgrind.log",
            "." + File.separatorChar + "test" + File.separatorChar + "test"
          };
    } else {
      // Todo: why does this need testDir.getAbsolutePath()? --kviiri
      command =
          new String[] {
            testDir.getAbsolutePath() + File.separatorChar + "test" + File.separatorChar + "test"
          };
    }
    ProcessRunner runner =
        new ProcessRunner(
            command, testDir, IOProvider.getDefault().getIO(projectInfo.getProjectName(), false));

    BgTask.start(
        "Running tests",
        runner,
        new BgTaskListener<ProcessResult>() {
          @Override
          public void bgTaskReady(ProcessResult result) {
            CTestResultParser parser =
                new CTestResultParser(
                    new File(testDir.getAbsolutePath() + "/tmc_test_results.xml"),
                    withValgrind ? new File(testDir.getAbsolutePath() + "/valgrind.log") : null,
                    null);
            try {
              parser.parseTestOutput();
            } catch (Exception e) {
              dialogDisplayer.displayError(
                  "Failed to read test results:\n" + e.getClass() + " " + e.getMessage());
              return;
            }
            boolean canSubmit = submitAction.enable(projectInfo.getProject());
            List<TestCaseResult> results = parser.getTestCaseResults();
            resultDisplayer.showLocalRunResult(
                results,
                canSubmit,
                new Runnable() {
                  @Override
                  public void run() {
                    submitAction.performAction(projectInfo.getProject());
                  }
                });
          }

          @Override
          public void bgTaskCancelled() {}

          @Override
          public void bgTaskFailed(Throwable ex) {
            if (withValgrind) {
              startRunningMakefileProjectTests(projectInfo, false);
            } else {
              dialogDisplayer.displayError("Failed to run tests:\n" + ex.getMessage());
            }
          }
        });
  }