Java,自从在 linux 移至 Java 14 后无法执行 spawn helper 错误
Java, Failed to exec spawn helper error since moving to Java 14 on linux
刚刚从 Java 11 移动到 Java 14
以下代码现在在 linux 机器上失败:
String linux_exe = System.getProperty("user.dir") + '/' + "fpcalc_arm32";
List<String> params = new ArrayList();
params.add(linux_exe);
params.add("-plain");
params.add("-length");
params.add(submittedSongLength);
params.add(file.getPath());
Process p = Runtime.getRuntime().exec(params.toArray(new String[1]));
使用堆栈跟踪
Cannot run program "/mnt/system/config/Apps/SongKong/songkong/fpcalc_arm32": error=0, Failed to exec spawn helper: pid: 13998, exit value: 127
java.io.IOException: Cannot run program "/mnt/system/config/Apps/SongKong/songkong/fpcalc_arm32": error=0, Failed to exec spawn helper: pid: 13998, exit value: 127
at java.base/java.lang.ProcessBuilder.start(ProcessBuilder.java:1128)
at java.base/java.lang.ProcessBuilder.start(ProcessBuilder.java:1071)
at java.base/java.lang.Runtime.exec(Runtime.java:590)
at java.base/java.lang.Runtime.exec(Runtime.java:449)
at com.jthink.songkong.analyse.acoustid.AcoustId.generateFingerprint(AcoustId.java:217)
at com.jthink.songkong.analyse.acoustid.AcoustId.createAcoustIdFingerprint(AcoustId.java:106)
在 Java 14 中发生了什么变化会导致这种情况?
我 运行 在 Windows 上使用 java 14 的等效代码 运行 没问题。但是我已经使用 Java 11 和 Java 14 在这台 unix 机器上重试了相同的代码库,并且可以确认 Java 11 总是有效 和Java14总是失败
我发现了这个问题,我在 Openjdk 错误数据库上遇到了这些问题
Provide a way for Runtime.exec to use posix_spawn on linux
和
Change the Process launch mechanism default on Linux to be posix_spawn
基本上在 Java 11 Linux 使用 vfork
来启动进程但是通过 Java 13 现在使用 posix_spawn
。
posix_spawn
实际上需要一个名为 jspawnhelper
的程序,该程序位于 jre/lib
中。在我的例子中,它存在,但它没有执行权限,这是因为我使用 jlink
构建了一个只包含我需要的系统模块的 jre,但我在 [=47= 上创建了它](我的主要开发环境)。
call "C:\Program Files\AdoptOpenJDK\jdk-11.0.6.10-hotspot\bin\jlink" --module-path="C:\Code\jthink\SongKong\linux_jdk\jmods" --add-modules java.desktop,java.datatransfer,java.logging,java.management,java.naming,java.net.http,java.prefs,java.scripting,java.sql,jdk.management,jdk.unsupported,jdk.scripting.nashorn --output C:\code\jthink\songkong\linuxjre
Windows 不理解 linux 执行权限,当我部署我的应用程序时,我对 jre/bin
中的可执行文件设置了执行权限,但不知道有任何jre/lib
中的可执行文件。更改 jspawnhelper 的执行权限修复了这个问题。
另一种解决方法是添加以下 java 选项:
-Djdk.lang.Process.launchMechanism=vfork
刚刚从 Java 11 移动到 Java 14
以下代码现在在 linux 机器上失败:
String linux_exe = System.getProperty("user.dir") + '/' + "fpcalc_arm32";
List<String> params = new ArrayList();
params.add(linux_exe);
params.add("-plain");
params.add("-length");
params.add(submittedSongLength);
params.add(file.getPath());
Process p = Runtime.getRuntime().exec(params.toArray(new String[1]));
使用堆栈跟踪
Cannot run program "/mnt/system/config/Apps/SongKong/songkong/fpcalc_arm32": error=0, Failed to exec spawn helper: pid: 13998, exit value: 127
java.io.IOException: Cannot run program "/mnt/system/config/Apps/SongKong/songkong/fpcalc_arm32": error=0, Failed to exec spawn helper: pid: 13998, exit value: 127
at java.base/java.lang.ProcessBuilder.start(ProcessBuilder.java:1128)
at java.base/java.lang.ProcessBuilder.start(ProcessBuilder.java:1071)
at java.base/java.lang.Runtime.exec(Runtime.java:590)
at java.base/java.lang.Runtime.exec(Runtime.java:449)
at com.jthink.songkong.analyse.acoustid.AcoustId.generateFingerprint(AcoustId.java:217)
at com.jthink.songkong.analyse.acoustid.AcoustId.createAcoustIdFingerprint(AcoustId.java:106)
在 Java 14 中发生了什么变化会导致这种情况?
我 运行 在 Windows 上使用 java 14 的等效代码 运行 没问题。但是我已经使用 Java 11 和 Java 14 在这台 unix 机器上重试了相同的代码库,并且可以确认 Java 11 总是有效 和Java14总是失败
我发现了这个问题,我在 Openjdk 错误数据库上遇到了这些问题
Provide a way for Runtime.exec to use posix_spawn on linux
和
Change the Process launch mechanism default on Linux to be posix_spawn
基本上在 Java 11 Linux 使用 vfork
来启动进程但是通过 Java 13 现在使用 posix_spawn
。
posix_spawn
实际上需要一个名为 jspawnhelper
的程序,该程序位于 jre/lib
中。在我的例子中,它存在,但它没有执行权限,这是因为我使用 jlink
构建了一个只包含我需要的系统模块的 jre,但我在 [=47= 上创建了它](我的主要开发环境)。
call "C:\Program Files\AdoptOpenJDK\jdk-11.0.6.10-hotspot\bin\jlink" --module-path="C:\Code\jthink\SongKong\linux_jdk\jmods" --add-modules java.desktop,java.datatransfer,java.logging,java.management,java.naming,java.net.http,java.prefs,java.scripting,java.sql,jdk.management,jdk.unsupported,jdk.scripting.nashorn --output C:\code\jthink\songkong\linuxjre
Windows 不理解 linux 执行权限,当我部署我的应用程序时,我对 jre/bin
中的可执行文件设置了执行权限,但不知道有任何jre/lib
中的可执行文件。更改 jspawnhelper 的执行权限修复了这个问题。
另一种解决方法是添加以下 java 选项:
-Djdk.lang.Process.launchMechanism=vfork