M1 Mac下Java ProcessBuilder如何调用arm64原生进程而非Rosetta模拟?
解决M1 Mac上Java ProcessBuilder调用arm64原生终端命令的问题
你遇到的核心问题是:M1 Mac默认的/usr/bin/bash是x86_64架构的,会通过Rosetta模拟运行,即使你的JVM是arm64版本,调用它执行命令也会返回x86_64。以下是几种解决方法:
方法1:调用原生arm64的shell(推荐)
macOS在M1设备上默认的zsh是arm64原生版本,路径为/bin/zsh,直接替换bash为zsh即可:
ProcessBuilder pb = new ProcessBuilder(); pb.command(new String[] {"/bin/zsh", "-c", "uname -m"}); Process proc = pb.start(); BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(proc.getInputStream())); String text = ""; String line; while ((line = bufferedReader.readLine()) != null) { text += line + System.lineSeparator(); } bufferedReader.close(); System.out.println(text);
执行后会返回预期的arm64。
方法2:指定arm64版本的bash路径
如果需要继续使用bash,可以通过Homebrew安装arm64版本的bash,路径通常为/homebrew/bin/bash,调用该路径的bash即可:
ProcessBuilder pb = new ProcessBuilder(); pb.command(new String[] {"/homebrew/bin/bash", "-c", "uname -m"}); // 后续读取输出代码同方法1
方法3:通过环境变量禁用Rosetta翻译
设置__RosettaTranslated环境变量为NO,强制子进程使用原生arm64架构运行(前提是被调用的命令存在arm64版本,否则会执行失败):
ProcessBuilder pb = new ProcessBuilder(); pb.command(new String[] {"bash", "-c", "uname -m"}); // 添加禁用Rosetta的环境变量 Map<String, String> env = pb.environment(); env.put("__RosettaTranslated", "NO"); Process proc = pb.start(); // 后续读取输出代码同方法1
验证命令架构的小技巧
可以在终端执行file /usr/bin/bash和file /bin/zsh,查看命令的架构信息:
/usr/bin/bash会显示x86_64/bin/zsh会显示arm64
内容的提问来源于stack exchange,提问作者CARLOS
相关产品推荐
相关产品推荐

