当前位置: 首页 > 知识库问答 >
问题:

当子进程仍然打开时,为什么Java进程挂起在Gradle上?

阎弘雅
2023-03-14

如果在java中创建的进程创建了一个子进程,但随后返回,则JVM挂起,但没有进程ID。

下面的示例应用程序(需要Windows和Java7)

import java.io.File;
import java.io.IOException;
import java.lang.ProcessBuilder.Redirect;
import java.nio.file.Files;

public class SubProcessHang {

    public static void main(String[] args) throws IOException, InterruptedException {
        ProcessBuilder builder = new ProcessBuilder("cmd", "/c", "start", "notepad.exe");
        File output = Files.createTempFile("output", "txt").toFile();
        builder.redirectError(Redirect.to(output));
        builder.redirectOutput(Redirect.to(output));
        Process process = builder.start();
        process.waitFor();
        int exitValue = process.exitValue();
        System.out.println("Process exit value:: " + exitValue);
        System.out.println("Output file length:: " + output.length());
        System.exit(exitValue);
    }
}

当应用程序运行时,它会创建三个进程:java--

所以子进程仍然活着,但是父进程已经被部分杀死,但是现在永远搁浅了。

建造。gradle脚本来复制这个

apply plugin: 'java'
apply plugin: 'application'
mainClassName = "SubProcessHang"

执行“gradle run”并获得以下输出:

C:\HangDemo>gradlew run
:compileJava
:processResources UP-TO-DATE
:classes
:run
Process exit value:: 0
Output file length:: 0
> Building 75% > :run

我知道这一定与java进程的创建方式有关,但我不知道该怎么办。

除了获取正在运行的java进程的ID并在关闭钩子中杀死所有子进程之外,我还能做什么?

共有2个答案

浦出野
2023-03-14

我想说,这个答案可能有助于获取子进程ID,还有这个——在Windows环境中杀死它们。

希望有帮助!

季阳朔
2023-03-14

Process的文档说

默认情况下,创建的子流程没有自己的终端或控制台。它的所有标准I/O(即stdin、stdout、stderr)操作将被重定向到父进程,在父进程中,可以通过使用getOutputStream()、getInputStream()和getErrorStream()方法获得的流来访问它们。父进程使用这些流向子进程提供输入并从中获取输出。由于一些本机平台仅为标准输入和输出流提供有限的缓冲区大小,如果未能及时写入子流程的输入流或读取子流程的输出流,可能会导致子流程阻塞,甚至死锁。

http://docs.oracle.com/javase/7/docs/api/java/lang/Process.html

也许您的过程正在创建stdout或stderr输出。尝试排空InputStream和ErrorStream。

 类似资料:
  • 我有一个服务器(40GB RAM),java进程在启动时挂在上面。如果我简单地在shell上键入“java”,它会打印帮助消息,然后永远不会退出。 PID用户PR NI VIRT RES SHR S%cpu%mem时间+命令 13根15-5 0 0 0 S 88 0.02302:14 ksoftirqd/3 25根15-5 0 0 0 S 73 0.02782:56 ksoftirqd/7 4根1

  • 问题内容: 我尝试完成的任务是流式处理ruby文件并打印输出。(注意:我不想一次打印出所有内容) main.py puts “hello” 问题 流文件工作正常。打招呼/再见输出将延迟2秒打印。就像脚本应该工作一样。问题是readline()最终挂起并且永不退出。我从来没有达到最后的打印。 我知道这里有很多类似的问题,但是这些都不是让我解决问题的方法。我并不是整个子流程中的人,所以请给我一个更实际

  • 问题内容: Python版本:2.6.7 我在for循环中有以下subprocess.call,该循环被执行18次,但是,该过程始终挂在第19个循环上: 控制台输出如下所示: 由于我对python脚本不是很熟悉,所以我只是在徘徊我是否在做错什么…我怀疑某个地方出现了死锁。 会处理这些问题吗? 在什么情况下subprocess.call会挂起任何专家答案?非常感谢 问题答案: 当使用子过程时,我倾向

  • 问题内容: 我一直在尝试使用Java的ProcessBuilder在Linux中启动应“长期”运行的应用程序。该程序的运行方式是启动命令(在本例中,我正在启动媒体播放应用程序),允许其运行并检查以确保它没有崩溃。例如,检查PID是否仍处于活动状态,然后重新启动该进程(如果已终止)。 我现在遇到的问题是PID在系统中仍然有效,但是应用程序的GUI挂起了。我尝试将ProcessBuilder(cmd)

  • 建议在开发环境中使用Gradle的守护进程,不建议在持续集成环境和构建服务器环境中使用守护进程. 守护进程可以更快的构建,这对于一个正坐在椅子前构建项目的人来说非常重要.对于CI构建来说,稳定性和可预见性是最重要的.为每个构建运行时用一个新的,完全孤立于以前的版本的程序,更加可靠。

  • 如何确定我的 Gradle 守护进程死亡的原因?我收到的唯一消息是L 这发生在活动版本中。几个步骤将完成,一个步骤将显示为活动状态,然后生成失败。 这是在将我们的内存参数(< code > Xmx < code > Xms < code > perm gen )从一个调用< code>gradlew的shell脚本移动到< code>gradle.properties并直接调用< code>gra