Arm 架构支持

跳转到:导航搜索

对于非 openSUSE 特定的概述,您可以查看

在 openSUSE 上,各种 arm 功能可以

  • 已支持:
    • 如果软件包版本支持,并且选项在构建时启用(并且您的硬件支持它)
  • 不支持:
    • 如果软件包版本不支持
    • 如果选项在构建时禁用

ARMv8.0 强制功能

ARMv8.0 - FP(浮点)

版本:15.1+ 默认启用。


ARMv8.0 - SIMD(单指令多数据)

版本:15.1+ 默认启用。


附加/可选的 ARMv8 功能

以下选项对于 ARMv8.0 是可选的,或者属于后续架构(8.1、8.2 等)的一部分。其中一些选项可以在运行时检测,并且仅在可用时使用,开销很小,因此可以安全地启用,但其他选项会破坏旧硬件,默认情况下未启用,但如果需要,可以手动使用。

ARMv8.1 - CRC32

版本:15.1+ 默认禁用。


CRC32 是 ARMv8.0 中的可选扩展,在 ARMv8.1 中是强制性的,用于计算循环冗余校验 (CRC)。使用 GCC 时,需要将 +crc 传递给 -march 标志。

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: CRC32 instructions

ARMv8.1 - PAN(特权访问永不)

版本:15.1+ 默认启用。


PAN 是一种额外的安全机制,用于防止潜在的软件攻击。它阻止内核或虚拟机监视器直接访问用户空间 (EL0) 内存。此选项将导致任何未受保护的(未使用 copy_to_user 等)内存访问因权限错误而失败。

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: Privileged Access Never

ARMv8.1 - LSE(大型系统扩展)原子操作

版本:Tumbleweed 默认完全启用。


原子指令可以用作 ARMv8.0 的加载-独占/存储-独占 (ldx/stx) 指令的替代方案,以改进非常大型系统中原子内存更新的实现。LSE 原子操作通常比旧原子操作更公平。此外,已发现 LSE 原子操作更快(平均时间更短)并且性能更一致(运行之间的方差也更低)。

使用 GCC 9.3.1+,您可以使用 -moutline-atomics-mno-outline-atomics 在运行时选择正确的路径来启用/禁用行内原子操作。

使用 GCC 10.1+,默认情况下启用行内原子操作,因此 Tumbleweed 自 20200602 快照以来已启用。

使用 GCC13,LSE(和 LSE2)已添加到 libatomic,这会禁用行内原子操作,并为 1-8 字节原子操作使用 LSE ifuncs(以及为 16 字节原子操作使用 LSE2 ifuncs)。

如果您想使用 qemu 进行测试,而您的主机不支持它,请使用 -cpu max 并禁用 kvm(速度慢),请注意您需要 qemu 3.0 或更高版本

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: LSE atomic instructions

ARMv8.2 - SVE(可扩展向量扩展)

版本:15.1+ 默认禁用,需要 gcc8 显式选项。


SVE 是 AArch64 的下一代 SIMD 指令集,包括可扩展的向量长度。

使用 GCC8+,您可以通过将 +sve 添加到 -march=xyz-mcpu=xyz 来启用 SVE 支持。由于 SVE 仅受 ARMv8.2+ 硬件支持,因此默认情况下未启用。

如果您想使用 qemu 进行测试,而您的主机不支持它,请使用 -cpu max 并禁用 kvm(速度慢),请注意您需要 qemu 3.1 或更高版本

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: Scalable Vector Extension
SVE: maximum available vector length 256 bytes per vector
SVE: default vector length 64 bytes per vector

ARMv8.2 - FP16/FPHP(半精度浮点)

版本:15.1+ 默认禁用,需要 gcc7 显式选项。


FP16 是一种半精度浮点格式(在 16 位上),ARMv8.2 可选。

使用 GCC7+,您可以通过将 +fp16 添加到 -march=xyz-mcpu=xyz 来启用 FP16 支持。由于 FP16 仅受某些 ARMv8.2+ 硬件支持,因此默认情况下未启用。

ARMv8.3 - PAuth(指针认证)

在 ARMv8.3 硬件及更新版本上,它允许使用密钥对指针进行签名和认证。此指针认证的目的是减轻 ROP 攻击和其他潜在的缓冲区溢出式攻击。

有关更多信息,您可以观看 SUSE Labs 2019 发布的关于指针认证的视频:https://www.youtube.com/watch?v=iW3mXDSijSQ

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: Address authentication (architected algorithm)
CPU features: detected: Generic authentication (architected algorithm)

如果您想使用 qemu 进行测试,而您的主机不支持它,请使用 -M virt -cpu max 并禁用 kvm(速度慢),请注意您需要 qemu 4.0 或更高版本。为了提高指针认证算法的速度,您可以使用 -M virt -cpu max,pauth-impdef=true

内核 5.12 添加了使用 arm64.nopauth 禁用指针认证的功能。请参阅:commit f8da5752

指针认证 - 用户空间支持

版本:15.2+ 默认禁用。

版本:Tumbleweed 默认启用。


Tumbleweed 和 Leap 15.2 内核上的用户空间支持已启用。要使用它,您只需将 -mbranch-protection=pac-ret[+leaf]-mbranch-protection=standard(也启用 BTI)选项传递给 GCC(旧的 GCC 可以使用 -msign-return-address,但 GCC9 中已弃用)。

强烈建议使用 elfutils 0.181GCC 10.2 及更高版本 来启用指针认证,因为它们包括所需的修复程序!

-mbranch-protection=standard 已在 Factory 中为 aarch64 启用,时间为 2020 年 11 月 20 日星期五。包含此选项的第一个 Tumbleweed 快照是 snapshot 20201129。如果软件包无法使用此选项正确构建,请将其报告给上游。作为解决方法,您可以删除此选项,如 llvm7 中所做的那样:https://build.opensuse.org/request/show/850379

指针认证 - 内核空间支持

版本:Tumbleweed 默认启用


内核空间支持已合并到内核 5.7 中,因此 Leap 尚不支持它,但它在 Tumbleweed 上默认启用,自 20200612 快照以来。

ARMv8.3/8.4 - NV(嵌套虚拟化)

ARMv8.3+ 上的嵌套虚拟化补丁尚未包含在上游内核中。

ARMv8.4 - LSE2(大型系统扩展)原子操作

版本:Tumbleweed 默认完全启用。


GCC13 将对 libatomic 添加 LSE 和 LSE2 的支持。这将禁用行内原子操作,并为 1-8 字节原子操作使用 LSE ifuncs,为 16 字节原子操作使用 LSE2 ifuncs。在 Neoverse V1 上,由于避免了锁,16 字节原子操作速度提高了约 4 倍。

Qemu 尚未支持它(版本 7.2.0)

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: LSE2 atomic instructions


ARMv8.5 - BTI(分支目标识别)

版本:Tumbleweed 默认启用(在内核和用户空间中)


在 ARMv8.5 硬件及更新版本上,它允许使用密钥对分支目标进行签名和认证。

初始支持已包含在 GCC 9 中,但强烈建议使用 GCC 10.2 及更高版本或 LLVM 10.0.1 及更高版本来启用 BTI,因为它们包括许多修复程序!

您可以通过将 -mbranch-protection=bti-mbranch-protection=standardstandard 也启用指针认证和 GCS(如果可用))添加到 GCC 来启用 BTI 支持。自 2020 年 8 月 21 日的快照(内核 5.8)以来,已在内核配置中启用。

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: Branch Target Identification

对于用户空间,-mbranch-protection=standard 已在 Factory 中为 aarch64 启用,时间为 2020 年 11 月 20 日星期五。包含此选项的第一个 Tumbleweed 快照是 snapshot 20201129。如果软件包无法使用此选项正确构建,请将其报告给上游。作为解决方法,您可以删除此选项,如 llvm7 中所做的那样:https://build.opensuse.org/request/show/850110

内核 5.12 添加了使用 arm64.nobti 禁用 BTI 的功能。请参阅:commit 93ad55b7852

如果您想使用 qemu 进行测试,而您的主机不支持它,请使用 -M virt -cpu max 并禁用 kvm(速度慢),请注意您需要 qemu 4.0 或更高版本

ARMv8.5 - MTE(内存标记扩展)

Arm MTE 实现了对内存的锁定和密钥访问。可以设置内存上的锁,并在内存访问期间提供密钥。如果密钥与锁匹配,则允许访问。如果不匹配,则报告错误。

更多详细信息请参阅 Arm_Memory_Tagging_Extension_Whitepaper.pdf

MTE 将允许 标记。目前只有 标记准备就绪。

堆标记

堆标记启用需要内核配置更新

  • CONFIG_ARM64_MTE 在 5.10+ 中:用户空间启用 标记(在 Tumbleweed 中自 20210108 快照以来)
  • CONFIG_KASAN_HW_TAGS 在 5.11+ 中:内核内启用 标记(仅同步)。在 5.13+ 中,已添加 MTE 异步支持用于 KASan。异步速度更快,但无法精确识别非法访问。
用户空间支持

版本:Tumbleweed 用户空间已启用,自 snapshot 20210223 以来


glibc 2.33+(在 Tumbleweed 中自 20210221 快照以来)会检查 hwcap 以根据硬件功能使用它或不使用它。glibc 2.34 将包含一些性能增强:http://patches-tcwg.linaro.org/cover/50130/
您还需要为 glibc 设置环境变量

export GLIBC_TUNABLES=”glibc.mem.tagging=X”

其中 X 是根据上游文档设置的值

This tunable takes a value between 0 and 255 and acts as a bitmask
that enables various capabilities.

Bit 0 (the least significant bit) causes the malloc subsystem to allocate
tagged memory, with each allocation being assigned a random tag.

Bit 1 enables precise faulting mode for tag violations on systems that
support deferred tag violation reporting.  This may cause programs
to run more slowly.

Other bits are currently reserved.

您还需要为 Python 设置另一个环境变量

  • Python pymalloc 与 MTE 尚不兼容,因此 Python 不应使用 pymalloc,而应使用 glibc malloc。为此,您可以设置 PYTHONMALLOC 环境变量
 export PYTHONMALLOC=malloc

上游错误报告:https://bugs.python.org/issue43593


请注意,需要 GCC10+ 和 LLVM9+ 才能使用 MTE 编译 glibc/内核。

如果您的硬件支持,您应该在内核日志中找到以下行

CPU features: detected: Memory Tagging Extension

如果您想使用 qemu 进行测试,请注意您需要 qemu 5.1 或更高版本。然后,您需要使用 -M virt,mte=on -cpu max 显式启用它并禁用 kvm(速度慢)。

您可以尝试以下用 C 编写的简单测试程序:(不需要 gcc 选项,因为它使用 glibc 中已启用的功能)

#include <stdlib.h>
 
/* Generate an MTE fault for a UAF (Use-After-Free):
 * - Use qemu with '-machine virt,mte=on -cpu max' _without_ kvm
 * - export GLIBC_TUNABLES="glibc.mem.tagging=X"
 *   where X has the following meanings:
 *     0        Disabled (default)
 *     1        asynchronous mode - useful to at least test and understand
 *     3        synchronous mode - what we probably want for openSUSE
 *   Details on: https://sourceware.org/pipermail/libc-alpha/attachments/20201218/cf93aeb4/attachment.bin
 */
 
int main(){
        int* a;
        a = malloc(sizeof(int));
        *a = 42;
        free(a);
        *a = 24; /* Should fail here */
        return 0;
}
内核内支持

版本:Tumbleweed 内核内已在 snapshot 20210504 中启用


MTE 内核支持通过带有硬件标签的 KASAN 实现。这在 Tumbleweed 中作为 kernel-debug 启用的一部分启用。

请注意,需要 GCC10+ 和 LLVM9+ 才能使用 MTE 编译 glibc/内核。

如果您的硬件支持,您应该在内核日志中找到以下行

[ 0.000000] CPU features: detected: Memory Tagging Extension
[ 0.000000] kasan: KernelAddressSanitizer initialized

如果您想使用 qemu 进行测试,请注意您需要 qemu 5.1 或更高版本。然后,您需要使用 -M virt,mte=on -cpu max 显式启用它,并禁用 kvm(速度较慢)。

KASAN 的上游文档:https://linuxkernel.org.cn/doc/html/latest/dev-tools/kasan.html

堆栈标记

不适用于 Linux。


ARMv9.x - CCA(保密计算架构)

Arm CCA 的主要特性之一是在受保护的 VM(又名 realm)中运行 Linux。
客户机支持包含在内核 6.13 中(CONFIG_ARM_CCA_GUEST),可在 Tumbleweed 20250122+ 中使用,主机支持将在稍后合并。

ARMv9.4 - GCS(受保护控制栈)

请注意,需要 GCC15+/LLVM19+、binutils 2.45+ 和内核 6.13+。

受保护控制栈 (GCS) 提供对一个具有受限访问权限的单独栈的支持,该栈仅包含返回地址。
这可用于防止基于返回的编程 (ROP) 攻击,方法是将程序使用的返回地址与存储在 GCS 中的地址进行比较。
它还可以用于有效地获取应用程序的调用栈,例如用于性能分析。
内核会在运行时检测该特性,如果系统未实现该特性,则会将其禁用,因此可以安全地启用它。

  • 内核端:Tumbleweed 内核启用 CONFIG_ARM64_GCS 选项(内核 6.13+)。然后,如果硬件支持 GCS,您应该从内核日志中获得以下行:
 CPU features: detected: Guarded Control Stack (GCS)
  • 用户空间端:您可以使用 -mbranch-protection=gcs 选项,但 -mbranch-protection=standard 也包含它(使用 GCC15+),因此 openSUSE Tumbleweed 构建包具有 GCS 支持。默认情况下,GCS 已禁用,用户应使用 GLIBC_TUNABLES glibc.cpu.aarch64_gcs=1 以及可选的 glibc.cpu.aarch64_gcs_policy=<0|1|2> 选择加入。示例:
 GLIBC_TUNABLES="glibc.cpu.aarch64_gcs=1"  /usr/bin/ls

注意:如果您想检查二进制文件是否支持 GCS,可以使用 readelf(就像您对 PAC 或 BTI 所做的那样),因为支持 GCS 的二进制文件会用可以使用 readelf 读取的 ELF 属性进行注释:readelf -n /usr/bin/ls | grep AArch64

 Properties: AArch64 feature: BTI, PAC, GCS

或者,如果您的 binutils 版本太旧:

 Properties: AArch64 feature: BTI, PAC, <unknown: 4>


外部链接

HyperV - 客户机支持

在 aarch64 上,Tumbleweed 支持 HyperV 作为客户机,自快照 20211125(内核 5.15)以来。

由于 shim 现在已由 Microsoft 为 aarch64 签名,因此它还支持 SecureBoot,自快照 20240923 以来。

Armv8.x 上的可选 32 位支持

某些 Armv8.x SoC 支持 32 位。

一些 Armv8.x SoC 支持 32 位,例如 Ampere eMAGHoneyComb_LX2K 等。因此,您可以使用它在用户空间和内核中构建和运行 32 位。

如果您的硬件支持,您应该在内核日志中找到以下行

kernel: CPU features: detected: 32-bit EL0 Support
kernel: CPU features: detected: 32-bit EL1 Support


某些 Armv8.x SoC 完全不支持 32 位

一些 Armv8.x SoC 完全不支持 32 位,例如 ThunderXThunderX2 机器。


某些 Armv8.x SoC 仅在用户空间支持 32 位

一些 Armv8.x SoC,例如 N1SDP,仅在用户空间支持 32 位。

如果您的硬件支持,您应该在内核日志中找到以下行:

kernel: CPU features: detected: 32-bit EL0 Support

在这样的系统上,如果您尝试使用启用了 kvm 的 32 位内核启动 qemu,您将收到以下错误:

 qemu-system-aarch64: can't apply global host-arm-cpu.aarch64=off: 'aarch64' feature cannot be disabled unless KVM is enabled and 32-bit EL1 is supported

openSUSE:Factory:ARM 项目配置为使用 aarch64 内核来构建 armv6l 和 armv7l 包和镜像。

Armv6/7 信息

内核 5.7 中删除了 ARM 32 位 KVM 主机支持

ARM 32 位 KVM 主机支持已在内核 5.7 中删除,提交 ID 为 541ad0150ca4aa663a2