从命令行检测 Apple Silicon

Posted

技术标签:

【中文标题】从命令行检测 Apple Silicon【英文标题】:Detect Apple Silicon from command line 【发布时间】:2021-03-23 08:07:18 【问题描述】:

如何从 shell 脚本中检测到它在 M1 Apple 硬件上运行?

我希望能够运行一个命令行命令,这样我就可以编写一个if-statement,它的主体只会在具有 M1 处理器的 mac 上运行时才会被执行(当然至少是 macOS Big Sur )。

【问题讨论】:

uname -p 可能会给你你想要的信息,但我没有 M1 来测试。 Tested。它有效。 是的,那更好。将其发布为答案,我会接受它 【参考方案1】:
uname -m

将返回 arm64 而不是 x86_64

if [[ `uname -m` == 'arm64' ]]; then
  echo M1
fi

或者,正如@chepner 建议的那样

uname -p

将返回 arm 而不是 i386

if [[ $(uname -p) == 'arm' ]]; then
  echo M1
fi

另一个工具是arch:

if [[ $(arch) == 'arm64' ]]; then
  echo M1
fi

【讨论】:

请注意,M1 用户可以在 Rosetta 模式下运行终端。在这种情况下,“uname -m”返回“x86_64”。 这不仅仅是在 Rosetta 中运行终端,而且如果任何进程运行脚本恰好也在 Rosetta 中运行。如果有人在由通过 Rosetta 运行的 RMM 部署的脚本中运行它,您将获得x86_64。我认为sysctl 方法是在字符串中搜索“Apple”的最佳解决方案:[[ $(sysctl -n machdep.cpu.brand_string) =~ "Apple" ]]【参考方案2】:

我发现sysctl -n machdep.cpu.brand_string 报告了Apple M1,即使该进程是在 Rosetta 下运行的。

【讨论】:

这就是清楚地回答“我可以arch -arm64 bash我离开这里的方式”所需要的。很难相信 arch 没有 -l 来列出当前机器可用的架构。【参考方案3】:

当使用原生 shell 时说 /bin/bash -i/bin/zsh -i,Klas Mellbourn's answer 按预期工作。

如果使用通过 Intel/Rosetta Homebrew 安装的 shell,则 uname -p 返回 i386uname -m 返回 x86_64,如 Datasun's comment 所示。


为了获得跨环境(Apple Silicon Native、Rosetta Shell、Linux、Raspberry Pi 4s)工作的东西,我使用dorothy dotfile ecosystem 中的以下内容:

is-mac && test "$(get-arch)" = 'a64'

如果你不使用dorothy,dorothy的相关代码是:

https://github.com/bevry/dorothy/blob/1c747c0fa6bb3e6c18cdc9bae17ab66c0603d788/commands/is-mac

test "$(uname -s)" = "Darwin"

https://github.com/bevry/dorothy/blob/1c747c0fa6bb3e6c18cdc9bae17ab66c0603d788/commands/get-arch

arch="$(uname -m)"  # -i is only linux, -m is linux and apple
if [[ "$arch" = x86_64* ]]; then
    if [[ "$(uname -a)" = *ARM64* ]]; then
        echo 'a64'
    else
        echo 'x64'
    fi
elif [[ "$arch" = i*86 ]]; then
    echo 'x32'
elif [[ "$arch" = arm* ]]; then
    echo 'a32'
elif test "$arch" = aarch64; then
    echo 'a64'
else
    exit 1
fi

Jatin Mehrotra's answer on a duplicate question 提供了有关如何获取特定 CPU 而不是架构的详细信息。在我的 M1 Mac Mini 上使用 sysctl -n machdep.cpu.brand_string 输出 Apple M1,但在 Raspberry Pi 4 Ubuntu 服务器上输出以下内容:

> sysctl -n machdep.cpu.brand_string
Command 'sysctl' is available in the following places
 * /sbin/sysctl
 * /usr/sbin/sysctl
The command could not be located because '/sbin:/usr/sbin' is not included in the PATH environment variable.
This is most likely caused by the lack of administrative privileges associated with your user account.
sysctl: command not found

> sudo sysctl -n machdep.cpu.brand_string
sysctl: cannot stat /proc/sys/machdep/cpu/brand_string: No such file or directory

【讨论】:

如果uname -m 返回x86_64 我想你可能正在通过Rosetta 运行你的终端。您是否在终端程序的Get Info 对话框中检查了Open using Rosetta Open using Rosetta 未选中:dropbox.com/s/lrhxgkxtmi2wv74/… 如果我运行一个新命令 /bin/bash -i 然后运行 ​​uname -m 然后它返回 arm64uname -p 返回 arm。这是由我的默认外壳引起的,它是由自制软件安装的,通过 Rosetta 运行。谢谢你帮我追踪这个。我已经更新了我的答案。

以上是关于从命令行检测 Apple Silicon的主要内容,如果未能解决你的问题,请参考以下文章

从命令行运行 Apple Instruments 抛出:模拟应用程序退出

maven 不从命令行检测测试

用于开源编译/构建的 Apple 命令行工具和 XCode?

无法使用 Apple Silicon 上的 iOS 模拟器 lipo arm64 .a 设备文件

text Apple macOS命令行

win7里使用命令行检测硬件改动