diff --git a/crates/core_arch/src/arm_shared/crypto.rs b/crates/core_arch/src/arm_shared/crypto.rs index b4d5b2978f..19d9190917 100644 --- a/crates/core_arch/src/arm_shared/crypto.rs +++ b/crates/core_arch/src/arm_shared/crypto.rs @@ -51,9 +51,16 @@ extern "C" { #[cfg(test)] use stdarch_test::assert_instr; +// Rust compilers without 8a57820bca64a252489790a57cb5ea23db6f9198 need crypto (hence the bootstrap check) +// LLVM builds without b8baa2a9132498ea286dbb0d03f005760ecc6fdb need crypto for arm (hence the target_arch check) + /// AES single round encryption. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "aes") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(aese))] pub unsafe fn vaeseq_u8(data: uint8x16_t, key: uint8x16_t) -> uint8x16_t { @@ -62,7 +69,11 @@ pub unsafe fn vaeseq_u8(data: uint8x16_t, key: uint8x16_t) -> uint8x16_t { /// AES single round decryption. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "aes") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(aesd))] pub unsafe fn vaesdq_u8(data: uint8x16_t, key: uint8x16_t) -> uint8x16_t { @@ -71,7 +82,11 @@ pub unsafe fn vaesdq_u8(data: uint8x16_t, key: uint8x16_t) -> uint8x16_t { /// AES mix columns. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "aes") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(aesmc))] pub unsafe fn vaesmcq_u8(data: uint8x16_t) -> uint8x16_t { @@ -80,7 +95,11 @@ pub unsafe fn vaesmcq_u8(data: uint8x16_t) -> uint8x16_t { /// AES inverse mix columns. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "aes") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(aesimc))] pub unsafe fn vaesimcq_u8(data: uint8x16_t) -> uint8x16_t { @@ -89,7 +108,11 @@ pub unsafe fn vaesimcq_u8(data: uint8x16_t) -> uint8x16_t { /// SHA1 fixed rotate. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1h))] pub unsafe fn vsha1h_u32(hash_e: u32) -> u32 { @@ -98,7 +121,11 @@ pub unsafe fn vsha1h_u32(hash_e: u32) -> u32 { /// SHA1 hash update accelerator, choose. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1c))] pub unsafe fn vsha1cq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> uint32x4_t { @@ -107,7 +134,11 @@ pub unsafe fn vsha1cq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> /// SHA1 hash update accelerator, majority. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1m))] pub unsafe fn vsha1mq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> uint32x4_t { @@ -116,7 +147,11 @@ pub unsafe fn vsha1mq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> /// SHA1 hash update accelerator, parity. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1p))] pub unsafe fn vsha1pq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> uint32x4_t { @@ -125,7 +160,11 @@ pub unsafe fn vsha1pq_u32(hash_abcd: uint32x4_t, hash_e: u32, wk: uint32x4_t) -> /// SHA1 schedule update accelerator, first part. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1su0))] pub unsafe fn vsha1su0q_u32(w0_3: uint32x4_t, w4_7: uint32x4_t, w8_11: uint32x4_t) -> uint32x4_t { @@ -134,7 +173,11 @@ pub unsafe fn vsha1su0q_u32(w0_3: uint32x4_t, w4_7: uint32x4_t, w8_11: uint32x4_ /// SHA1 schedule update accelerator, second part. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha1su1))] pub unsafe fn vsha1su1q_u32(tw0_3: uint32x4_t, w12_15: uint32x4_t) -> uint32x4_t { @@ -143,7 +186,11 @@ pub unsafe fn vsha1su1q_u32(tw0_3: uint32x4_t, w12_15: uint32x4_t) -> uint32x4_t /// SHA256 hash update accelerator. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha256h))] pub unsafe fn vsha256hq_u32( @@ -156,7 +203,11 @@ pub unsafe fn vsha256hq_u32( /// SHA256 hash update accelerator, upper part. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha256h2))] pub unsafe fn vsha256h2q_u32( @@ -169,7 +220,11 @@ pub unsafe fn vsha256h2q_u32( /// SHA256 schedule update accelerator, first part. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha256su0))] pub unsafe fn vsha256su0q_u32(w0_3: uint32x4_t, w4_7: uint32x4_t) -> uint32x4_t { @@ -178,7 +233,11 @@ pub unsafe fn vsha256su0q_u32(w0_3: uint32x4_t, w4_7: uint32x4_t) -> uint32x4_t /// SHA256 schedule update accelerator, second part. #[inline] -#[target_feature(enable = "crypto")] +#[cfg_attr(any(bootstrap, target_arch = "arm"), target_feature(enable = "crypto"))] +#[cfg_attr( + not(any(bootstrap, target_arch = "arm")), + target_feature(enable = "sha2") +)] #[cfg_attr(target_arch = "arm", target_feature(enable = "v8"))] #[cfg_attr(test, assert_instr(sha256su1))] pub unsafe fn vsha256su1q_u32( @@ -196,7 +255,11 @@ mod tests { use std::mem; use stdarch_test::simd_test; - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr( + all(not(bootstrap), target_arch = "aarch64"), + simd_test(enable = "aes") + )] unsafe fn test_vaeseq_u8() { let data = mem::transmute(u8x16::new(1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8)); let key = mem::transmute(u8x16::new(0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7)); @@ -209,7 +272,11 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr( + all(not(bootstrap), target_arch = "aarch64"), + simd_test(enable = "aes") + )] unsafe fn test_vaesdq_u8() { let data = mem::transmute(u8x16::new(1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8)); let key = mem::transmute(u8x16::new(0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7)); @@ -220,7 +287,11 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr( + all(not(bootstrap), target_arch = "aarch64"), + simd_test(enable = "aes") + )] unsafe fn test_vaesmcq_u8() { let data = mem::transmute(u8x16::new(1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8)); let r: u8x16 = mem::transmute(vaesmcq_u8(data)); @@ -230,7 +301,11 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr( + all(not(bootstrap), target_arch = "aarch64"), + simd_test(enable = "aes") + )] unsafe fn test_vaesimcq_u8() { let data = mem::transmute(u8x16::new(1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8)); let r: u8x16 = mem::transmute(vaesimcq_u8(data)); @@ -240,13 +315,15 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1h_u32() { assert_eq!(vsha1h_u32(0x1234), 0x048d); assert_eq!(vsha1h_u32(0x5678), 0x159e); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1su0q_u32() { let r: u32x4 = mem::transmute(vsha1su0q_u32( mem::transmute(u32x4::new(0x1234_u32, 0x5678_u32, 0x9abc_u32, 0xdef0_u32)), @@ -256,7 +333,8 @@ mod tests { assert_eq!(r, u32x4::new(0x9abc, 0xdef0, 0x1234, 0x5678)); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1su1q_u32() { let r: u32x4 = mem::transmute(vsha1su1q_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -268,7 +346,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1cq_u32() { let r: u32x4 = mem::transmute(vsha1cq_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -281,7 +360,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1pq_u32() { let r: u32x4 = mem::transmute(vsha1pq_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -294,7 +374,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha1mq_u32() { let r: u32x4 = mem::transmute(vsha1mq_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -307,7 +388,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha256hq_u32() { let r: u32x4 = mem::transmute(vsha256hq_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -320,7 +402,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha256h2q_u32() { let r: u32x4 = mem::transmute(vsha256h2q_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -333,7 +416,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha256su0q_u32() { let r: u32x4 = mem::transmute(vsha256su0q_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), @@ -345,7 +429,8 @@ mod tests { ); } - #[simd_test(enable = "crypto")] + #[cfg_attr(any(bootstrap, target_arch = "arm"), simd_test(enable = "crypto"))] + #[cfg_attr(not(any(bootstrap, target_arch = "arm")), simd_test(enable = "sha2"))] unsafe fn test_vsha256su1q_u32() { let r: u32x4 = mem::transmute(vsha256su1q_u32( mem::transmute(u32x4::new(0x1234, 0x5678, 0x9abc, 0xdef0)), diff --git a/crates/std_detect/src/detect/arch/aarch64.rs b/crates/std_detect/src/detect/arch/aarch64.rs index 761cde9583..81979ba967 100644 --- a/crates/std_detect/src/detect/arch/aarch64.rs +++ b/crates/std_detect/src/detect/arch/aarch64.rs @@ -4,35 +4,145 @@ features! { @TARGET: aarch64; @MACRO_NAME: is_aarch64_feature_detected; @MACRO_ATTRS: - /// Checks if `aarch64` feature is enabled. + /// This macro tests, at runtime, whether an `aarch64` feature is enabled on aarch64 platforms. + /// Currently most features are only supported on linux-based platforms. + /// + /// This macro takes one argument which is a string literal of the feature being tested for. + /// The feature names are mostly taken from their FEAT_* definitiions in the [ARM Architecture + /// Reference Manual][docs]. + /// + /// ## Supported arguments + /// + /// * `"asimd"` or "neon" - FEAT_AdvSIMD + /// * `"pmull"` - FEAT_PMULL + /// * `"fp"` - FEAT_FP + /// * `"fp16"` - FEAT_FP16 + /// * `"sve"` - FEAT_SVE + /// * `"crc"` - FEAT_CRC + /// * `"lse"` - FEAT_LSE + /// * `"lse2"` - FEAT_LSE2 + /// * `"rdm"` - FEAT_RDM + /// * `"rcpc"` - FEAT_LRCPC + /// * `"rcpc2"` - FEAT_LRCPC2 + /// * `"dotprod"` - FEAT_DotProd + /// * `"tme"` - FEAT_TME + /// * `"fhm"` - FEAT_FHM + /// * `"dit"` - FEAT_DIT + /// * `"flagm"` - FEAT_FLAGM + /// * `"ssbs"` - FEAT_SSBS + /// * `"sb"` - FEAT_SB + /// * `"pauth"` - FEAT_PAuth + /// * `"dpb"` - FEAT_DPB + /// * `"dpb2"` - FEAT_DPB2 + /// * `"sve2"` - FEAT_SVE2 + /// * `"sve2-aes"` - FEAT_SVE2_AES + /// * `"sve2-sm4"` - FEAT_SVE2_SM4 + /// * `"sve2-sha3"` - FEAT_SVE2_SHA3 + /// * `"sve2-bitperm"` - FEAT_SVE2_BitPerm + /// * `"frintts"` - FEAT_FRINTTS + /// * `"i8mm"` - FEAT_I8MM + /// * `"f32mm"` - FEAT_F32MM + /// * `"f64mm"` - FEAT_F64MM + /// * `"bf16"` - FEAT_BF16 + /// * `"rand"` - FEAT_RNG + /// * `"bti"` - FEAT_BTI + /// * `"mte"` - FEAT_MTE + /// * `"jsconv"` - FEAT_JSCVT + /// * `"fcma"` - FEAT_FCMA + /// * `"aes"` - FEAT_AES + /// * `"sha2"` - FEAT_SHA1 & FEAT_SHA256 + /// * `"sha3"` - FEAT_SHA512 & FEAT_SHA3 + /// * `"sm4"` - FEAT_SM3 & FEAT_SM4 + /// + /// [docs]: https://developer.arm.com/documentation/ddi0487/latest #[unstable(feature = "stdsimd", issue = "27731")] @BIND_FEATURE_NAME: "asimd"; "neon"; @NO_RUNTIME_DETECTION: "ras"; @NO_RUNTIME_DETECTION: "v8.1a"; @NO_RUNTIME_DETECTION: "v8.2a"; @NO_RUNTIME_DETECTION: "v8.3a"; + @NO_RUNTIME_DETECTION: "v8.4a"; + @NO_RUNTIME_DETECTION: "v8.5a"; + @NO_RUNTIME_DETECTION: "v8.6a"; + @NO_RUNTIME_DETECTION: "v8.7a"; @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] asimd: "neon"; - /// ARM Advanced SIMD (ASIMD) + /// FEAT_AdvSIMD (Advanced SIMD/NEON) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] pmull: "pmull"; - /// Polynomial Multiply + /// FEAT_PMULL (Polynomial Multiply) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] fp: "fp"; - /// Floating point support + /// FEAT_FP (Floating point support) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] fp16: "fp16"; - /// Half-float support. + /// FEAT_FP16 (Half-float support) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve: "sve"; - /// Scalable Vector Extension (SVE) + /// FEAT_SVE (Scalable Vector Extension) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] crc: "crc"; - /// CRC32 (Cyclic Redundancy Check) - @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] crypto: "crypto"; - /// Crypto: AES + PMULL + SHA1 + SHA2 + /// FEAT_CRC32 (Cyclic Redundancy Check) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] lse: "lse"; - /// Atomics (Large System Extension) + /// FEAT_LSE (Large System Extension - atomics) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] lse2: "lse2"; + /// FEAT_LSE2 (unaligned and register-pair atomics) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] rdm: "rdm"; - /// Rounding Double Multiply (ASIMDRDM) + /// FEAT_RDM (Rounding Doubling Multiply - ASIMDRDM) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] rcpc: "rcpc"; - /// Release consistent Processor consistent (RcPc) + /// FEAT_LRCPC (Release consistent Processor consistent) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] rcpc2: "rcpc2"; + /// FEAT_LRCPC2 (RCPC with immediate offsets) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] dotprod: "dotprod"; - /// Vector Dot-Product (ASIMDDP) + /// FEAT_DotProd (Vector Dot-Product - ASIMDDP) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] tme: "tme"; - /// Transactional Memory Extensions (TME) + /// FEAT_TME (Transactional Memory Extensions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] fhm: "fhm"; + /// FEAT_FHM (fp16 multiplication instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] dit: "dit"; + /// FEAT_DIT (Data Independent Timing instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] flagm: "flagm"; + /// FEAT_FLAGM (flag manipulation instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] ssbs: "ssbs"; + /// FEAT_SSBS (speculative store bypass safe) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sb: "sb"; + /// FEAT_SB (speculation barrier) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] pauth: "pauth"; + /// FEAT_PAuth (pointer authentication) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] dpb: "dpb"; + /// FEAT_DPB (aka dcpop - data cache clean to point of persistance) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] dpb2: "dpb2"; + /// FEAT_DPB2 (aka dcpodp - data cache clean to point of deep persistance) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve2: "sve2"; + /// FEAT_SVE2 (Scalable Vector Extension 2) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve2_aes: "sve2-aes"; + /// FEAT_SVE_AES (SVE2 AES crypto) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve2_sm4: "sve2-sm4"; + /// FEAT_SVE_SM4 (SVE2 SM4 crypto) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve2_sha3: "sve2-sha3"; + /// FEAT_SVE_SHA3 (SVE2 SHA3 crypto) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sve2_bitperm: "sve2-bitperm"; + /// FEAT_SVE_BitPerm (SVE2 bit permutation instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] frintts: "frintts"; + /// FEAT_FRINTTS (float to integer rounding instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] i8mm: "i8mm"; + /// FEAT_I8MM (integer matrix multiplication, plus ASIMD support) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] f32mm: "f32mm"; + /// FEAT_F32MM (single-precision matrix multiplication) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] f64mm: "f64mm"; + /// FEAT_F64MM (double-precision matrix multiplication) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] bf16: "bf16"; + /// FEAT_BF16 (BFloat16 type, plus MM instructions, plus ASIMD support) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] rand: "rand"; + /// FEAT_RNG (Random Number Generator) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] bti: "bti"; + /// FEAT_BTI (Branch Target Identification) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] mte: "mte"; + /// FEAT_MTE (Memory Tagging Extension) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] jsconv: "jsconv"; + /// FEAT_JSCVT (JavaScript float conversion instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] fcma: "fcma"; + /// FEAT_FCMA (float complex number operations) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] aes: "aes"; + /// FEAT_AES (AES instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sha2: "sha2"; + /// FEAT_SHA1 & FEAT_SHA256 (SHA1 & SHA2-256 instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sha3: "sha3"; + /// FEAT_SHA512 & FEAT_SHA3 (SHA2-512 & SHA3 instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sm4: "sm4"; + /// FEAT_SM3 & FEAT_SM4 (SM3 & SM4 instructions) } diff --git a/crates/std_detect/src/detect/arch/arm.rs b/crates/std_detect/src/detect/arch/arm.rs index 46fd56384b..d96514c844 100644 --- a/crates/std_detect/src/detect/arch/arm.rs +++ b/crates/std_detect/src/detect/arch/arm.rs @@ -17,5 +17,9 @@ features! { @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] crc: "crc"; /// CRC32 (Cyclic Redundancy Check) @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] crypto: "crypto"; - /// Crypto: AES + PMULL + SHA1 + SHA2 + /// Crypto: AES + PMULL + SHA1 + SHA256. Prefer using the individual features where possible. + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] aes: "aes"; + /// FEAT_AES (AES instructions) + @FEATURE: #[unstable(feature = "stdsimd", issue = "27731")] sha2: "sha2"; + /// FEAT_SHA1 & FEAT_SHA256 (SHA1 & SHA2-256 instructions) } diff --git a/crates/std_detect/src/detect/bit.rs b/crates/std_detect/src/detect/bit.rs index 578f0b16b7..6f06c5523e 100644 --- a/crates/std_detect/src/detect/bit.rs +++ b/crates/std_detect/src/detect/bit.rs @@ -4,6 +4,6 @@ #[allow(dead_code)] #[inline] pub(crate) fn test(x: usize, bit: u32) -> bool { - debug_assert!(bit < 32, "bit index out-of-bounds"); + debug_assert!(bit < usize::BITS, "bit index out-of-bounds"); x & (1 << bit) != 0 } diff --git a/crates/std_detect/src/detect/os/aarch64.rs b/crates/std_detect/src/detect/os/aarch64.rs index 2f289f5807..0fd2702731 100644 --- a/crates/std_detect/src/detect/os/aarch64.rs +++ b/crates/std_detect/src/detect/os/aarch64.rs @@ -41,13 +41,7 @@ pub(crate) fn detect_features() -> cache::Initializer { ); } - let aes = bits_shift(aa64isar0, 7, 4) >= 1; - let pmull = bits_shift(aa64isar0, 7, 4) >= 2; - let sha1 = bits_shift(aa64isar0, 11, 8) >= 1; - let sha2 = bits_shift(aa64isar0, 15, 12) >= 1; - enable_feature(Feature::pmull, pmull); - // Crypto is specified as AES + PMULL + SHA1 + SHA2 per LLVM/hosts.cpp - enable_feature(Feature::crypto, aes && pmull && sha1 && sha2); + enable_feature(Feature::pmull, bits_shift(aa64isar0, 7, 4) >= 2); enable_feature(Feature::tme, bits_shift(aa64isar0, 27, 24) == 1); enable_feature(Feature::lse, bits_shift(aa64isar0, 23, 20) >= 1); enable_feature(Feature::crc, bits_shift(aa64isar0, 19, 16) >= 1); @@ -72,6 +66,10 @@ pub(crate) fn detect_features() -> cache::Initializer { // supported, it also requires half-float support: enable_feature(Feature::asimd, fp && asimd && (!fphp | asimdhp)); // SIMD extensions require SIMD support: + enable_feature(Feature::aes, asimd && bits_shift(aa64isar0, 7, 4) >= 1); + let sha1 = bits_shift(aa64isar0, 11, 8) >= 1; + let sha2 = bits_shift(aa64isar0, 15, 12) >= 1; + enable_feature(Feature::sha2, asimd && sha1 && sha2); enable_feature(Feature::rdm, asimd && bits_shift(aa64isar0, 31, 28) >= 1); enable_feature( Feature::dotprod, diff --git a/crates/std_detect/src/detect/os/freebsd/aarch64.rs b/crates/std_detect/src/detect/os/freebsd/aarch64.rs index 7e086ca057..7d972b373f 100644 --- a/crates/std_detect/src/detect/os/freebsd/aarch64.rs +++ b/crates/std_detect/src/detect/os/freebsd/aarch64.rs @@ -1,6 +1,6 @@ //! Run-time feature detection for Aarch64 on FreeBSD. -pub use super::super::aarch64::detect_features; +pub(crate) use super::super::aarch64::detect_features; #[cfg(test)] mod tests { @@ -12,7 +12,6 @@ mod tests { println!("fp16: {:?}", is_aarch64_feature_detected!("fp16")); println!("sve: {:?}", is_aarch64_feature_detected!("sve")); println!("crc: {:?}", is_aarch64_feature_detected!("crc")); - println!("crypto: {:?}", is_aarch64_feature_detected!("crypto")); println!("lse: {:?}", is_aarch64_feature_detected!("lse")); println!("rdm: {:?}", is_aarch64_feature_detected!("rdm")); println!("rcpc: {:?}", is_aarch64_feature_detected!("rcpc")); diff --git a/crates/std_detect/src/detect/os/freebsd/auxvec.rs b/crates/std_detect/src/detect/os/freebsd/auxvec.rs index 832ce2252e..f12476adac 100644 --- a/crates/std_detect/src/detect/os/freebsd/auxvec.rs +++ b/crates/std_detect/src/detect/os/freebsd/auxvec.rs @@ -1,5 +1,12 @@ //! Parses ELF auxiliary vectors. -#![cfg_attr(any(target_arch = "arm", target_arch = "powerpc64"), allow(dead_code))] +#![cfg_attr( + any( + target_arch = "aarch64", + target_arch = "arm", + target_arch = "powerpc64" + ), + allow(dead_code) +)] /// Key to access the CPU Hardware capabilities bitfield. pub(crate) const AT_HWCAP: usize = 25; diff --git a/crates/std_detect/src/detect/os/linux/aarch64.rs b/crates/std_detect/src/detect/os/linux/aarch64.rs index 80c36e9b99..4dc6362057 100644 --- a/crates/std_detect/src/detect/os/linux/aarch64.rs +++ b/crates/std_detect/src/detect/os/linux/aarch64.rs @@ -20,11 +20,13 @@ pub(crate) fn detect_features() -> cache::Initializer { /// These values are part of the platform-specific [asm/hwcap.h][hwcap] . /// +/// The names match those used for cpuinfo. +/// /// [hwcap]: https://github.com/torvalds/linux/blob/master/arch/arm64/include/uapi/asm/hwcap.h struct AtHwcap { fp: bool, // 0 asimd: bool, // 1 - // evtstrm: bool, // 2 + // evtstrm: bool, // 2 No LLVM support aes: bool, // 3 pmull: bool, // 4 sha1: bool, // 5 @@ -33,18 +35,46 @@ struct AtHwcap { atomics: bool, // 8 fphp: bool, // 9 asimdhp: bool, // 10 - // cpuid: bool, // 11 + // cpuid: bool, // 11 No LLVM support asimdrdm: bool, // 12 - // jscvt: bool, // 13 - // fcma: bool, // 14 - lrcpc: bool, // 15 - // dcpop: bool, // 16 - // sha3: bool, // 17 - // sm3: bool, // 18 - // sm4: bool, // 19 - asimddp: bool, // 20 - // sha512: bool, // 21 - sve: bool, // 22 + jscvt: bool, // 13 + fcma: bool, // 14 + lrcpc: bool, // 15 + dcpop: bool, // 16 + sha3: bool, // 17 + sm3: bool, // 18 + sm4: bool, // 19 + asimddp: bool, // 20 + sha512: bool, // 21 + sve: bool, // 22 + fhm: bool, // 23 + dit: bool, // 24 + uscat: bool, // 25 + ilrcpc: bool, // 26 + flagm: bool, // 27 + ssbs: bool, // 28 + sb: bool, // 29 + paca: bool, // 30 + pacg: bool, // 31 + dcpodp: bool, // 32 + sve2: bool, // 33 + sveaes: bool, // 34 + // svepmull: bool, // 35 No LLVM support + svebitperm: bool, // 36 + svesha3: bool, // 37 + svesm4: bool, // 38 + // flagm2: bool, // 39 No LLVM support + frint: bool, // 40 + // svei8mm: bool, // 41 See i8mm feature + svef32mm: bool, // 42 + svef64mm: bool, // 43 + // svebf16: bool, // 44 See bf16 feature + i8mm: bool, // 45 + bf16: bool, // 46 + // dgh: bool, // 47 No LLVM support + rng: bool, // 48 + bti: bool, // 49 + mte: bool, // 50 } impl From for AtHwcap { @@ -64,16 +94,44 @@ impl From for AtHwcap { asimdhp: bit::test(auxv.hwcap, 10), // cpuid: bit::test(auxv.hwcap, 11), asimdrdm: bit::test(auxv.hwcap, 12), - // jscvt: bit::test(auxv.hwcap, 13), - // fcma: bit::test(auxv.hwcap, 14), + jscvt: bit::test(auxv.hwcap, 13), + fcma: bit::test(auxv.hwcap, 14), lrcpc: bit::test(auxv.hwcap, 15), - // dcpop: bit::test(auxv.hwcap, 16), - // sha3: bit::test(auxv.hwcap, 17), - // sm3: bit::test(auxv.hwcap, 18), - // sm4: bit::test(auxv.hwcap, 19), + dcpop: bit::test(auxv.hwcap, 16), + sha3: bit::test(auxv.hwcap, 17), + sm3: bit::test(auxv.hwcap, 18), + sm4: bit::test(auxv.hwcap, 19), asimddp: bit::test(auxv.hwcap, 20), - // sha512: bit::test(auxv.hwcap, 21), + sha512: bit::test(auxv.hwcap, 21), sve: bit::test(auxv.hwcap, 22), + fhm: bit::test(auxv.hwcap, 23), + dit: bit::test(auxv.hwcap, 24), + uscat: bit::test(auxv.hwcap, 25), + ilrcpc: bit::test(auxv.hwcap, 26), + flagm: bit::test(auxv.hwcap, 27), + ssbs: bit::test(auxv.hwcap, 28), + sb: bit::test(auxv.hwcap, 29), + paca: bit::test(auxv.hwcap, 30), + pacg: bit::test(auxv.hwcap, 31), + dcpodp: bit::test(auxv.hwcap, 32), + sve2: bit::test(auxv.hwcap, 33), + sveaes: bit::test(auxv.hwcap, 34), + // svepmull: bit::test(auxv.hwcap, 35), + svebitperm: bit::test(auxv.hwcap, 36), + svesha3: bit::test(auxv.hwcap, 37), + svesm4: bit::test(auxv.hwcap, 38), + // flagm2: bit::test(auxv.hwcap, 39), + frint: bit::test(auxv.hwcap, 40), + // svei8mm: bit::test(auxv.hwcap, 41), + svef32mm: bit::test(auxv.hwcap, 42), + svef64mm: bit::test(auxv.hwcap, 43), + // svebf16: bit::test(auxv.hwcap, 44), + i8mm: bit::test(auxv.hwcap, 45), + bf16: bit::test(auxv.hwcap, 46), + // dgh: bit::test(auxv.hwcap, 47), + rng: bit::test(auxv.hwcap, 48), + bti: bit::test(auxv.hwcap, 49), + mte: bit::test(auxv.hwcap, 50), } } } @@ -100,16 +158,44 @@ impl From for AtHwcap { asimdhp: f.has("asimdhp"), // cpuid: f.has("cpuid"), asimdrdm: f.has("asimdrdm"), - // jscvt: f.has("jscvt"), - // fcma: f.has("fcma"), + jscvt: f.has("jscvt"), + fcma: f.has("fcma"), lrcpc: f.has("lrcpc"), - // dcpop: f.has("dcpop"), - // sha3: f.has("sha3"), - // sm3: f.has("sm3"), - // sm4: f.has("sm4"), + dcpop: f.has("dcpop"), + sha3: f.has("sha3"), + sm3: f.has("sm3"), + sm4: f.has("sm4"), asimddp: f.has("asimddp"), - // sha512: f.has("sha512"), + sha512: f.has("sha512"), sve: f.has("sve"), + fhm: f.has("asimdfhm"), + dit: f.has("dit"), + uscat: f.has("uscat"), + ilrcpc: f.has("ilrcpc"), + flagm: f.has("flagm"), + ssbs: f.has("ssbs"), + sb: f.has("sb"), + paca: f.has("paca"), + pacg: f.has("pacg"), + dcpodp: f.has("dcpodp"), + sve2: f.has("sve2"), + sveaes: f.has("sveaes"), + // svepmull: f.has("svepmull"), + svebitperm: f.has("svebitperm"), + svesha3: f.has("svesha3"), + svesm4: f.has("svesm4"), + // flagm2: f.has("flagm2"), + frint: f.has("frint"), + // svei8mm: f.has("svei8mm"), + svef32mm: f.has("svef32mm"), + svef64mm: f.has("svef64mm"), + // svebf16: f.has("svebf16"), + i8mm: f.has("i8mm"), + bf16: f.has("bf16"), + // dgh: f.has("dgh"), + rng: f.has("rng"), + bti: f.has("bti"), + mte: f.has("mte"), } } } @@ -117,8 +203,8 @@ impl From for AtHwcap { impl AtHwcap { /// Initializes the cache from the feature -bits. /// - /// The features are enabled approximately like in LLVM host feature detection: - /// https://github.com/llvm-mirror/llvm/blob/master/lib/Support/Host.cpp#L1273 + /// The feature dependencies here come directly from LLVM's feature definintions: + /// https://github.com/llvm/llvm-project/blob/main/llvm/lib/Target/AArch64/AArch64.td fn cache(self) -> cache::Initializer { let mut value = cache::Initializer::default(); { @@ -131,25 +217,73 @@ impl AtHwcap { enable_feature(Feature::fp, self.fp); // Half-float support requires float support enable_feature(Feature::fp16, self.fp && self.fphp); + // FHM (fp16fml in LLVM) requires half float support + enable_feature(Feature::fhm, self.fphp && self.fhm); enable_feature(Feature::pmull, self.pmull); enable_feature(Feature::crc, self.crc32); enable_feature(Feature::lse, self.atomics); + enable_feature(Feature::lse2, self.uscat); enable_feature(Feature::rcpc, self.lrcpc); + // RCPC2 (rcpc-immo in LLVM) requires RCPC support + enable_feature(Feature::rcpc2, self.ilrcpc && self.lrcpc); + enable_feature(Feature::dit, self.dit); + enable_feature(Feature::flagm, self.flagm); + enable_feature(Feature::ssbs, self.ssbs); + enable_feature(Feature::sb, self.sb); + // FEAT_PAuth provides both paca & pacg + enable_feature(Feature::pauth, self.paca && self.pacg); + enable_feature(Feature::dpb, self.dcpop); + enable_feature(Feature::dpb2, self.dcpodp); + enable_feature(Feature::rand, self.rng); + enable_feature(Feature::bti, self.bti); + enable_feature(Feature::mte, self.mte); + // jsconv requires float support + enable_feature(Feature::jsconv, self.jscvt && self.fp); + enable_feature(Feature::rdm, self.asimdrdm); + enable_feature(Feature::dotprod, self.asimddp); + enable_feature(Feature::frintts, self.frint); + + // FEAT_I8MM & FEAT_BF16 also include optional SVE components which linux exposes + // separately. We ignore that distinction here. + enable_feature(Feature::i8mm, self.i8mm); + enable_feature(Feature::bf16, self.bf16); - // SIMD support requires float support - if half-floats are + // ASIMD support requires float support - if half-floats are // supported, it also requires half-float support: let asimd = self.fp && self.asimd && (!self.fphp | self.asimdhp); enable_feature(Feature::asimd, asimd); - // SIMD extensions require SIMD support: - enable_feature(Feature::rdm, self.asimdrdm && asimd); - enable_feature(Feature::dotprod, self.asimddp && asimd); + // ASIMD extensions require ASIMD support: + enable_feature(Feature::fcma, self.fcma && asimd); enable_feature(Feature::sve, self.sve && asimd); - // Crypto is specified as AES + PMULL + SHA1 + SHA2 per LLVM/hosts.cpp + // SVE extensions require SVE & ASIMD + enable_feature(Feature::f32mm, self.svef32mm && self.sve && asimd); + enable_feature(Feature::f64mm, self.svef64mm && self.sve && asimd); + + // Cryptographic extensions require ASIMD + enable_feature(Feature::aes, self.aes && asimd); + enable_feature(Feature::sha2, self.sha1 && self.sha2 && asimd); + // SHA512/SHA3 require SHA1 & SHA256 + enable_feature( + Feature::sha3, + self.sha512 && self.sha3 && self.sha1 && self.sha2 && asimd, + ); + enable_feature(Feature::sm4, self.sm3 && self.sm4 && asimd); + + // SVE2 requires SVE + let sve2 = self.sve2 && self.sve && asimd; + enable_feature(Feature::sve2, sve2); + // SVE2 extensions require SVE2 and crypto features + enable_feature(Feature::sve2_aes, self.sveaes && sve2 && self.aes); + enable_feature( + Feature::sve2_sm4, + self.svesm4 && sve2 && self.sm3 && self.sm4, + ); enable_feature( - Feature::crypto, - self.aes && self.pmull && self.sha1 && self.sha2, + Feature::sve2_sha3, + self.svesha3 && sve2 && self.sha512 && self.sha3 && self.sha1 && self.sha2, ); + enable_feature(Feature::sve2_bitperm, self.svebitperm && self.sve2); } value } diff --git a/crates/std_detect/src/detect/os/linux/arm.rs b/crates/std_detect/src/detect/os/linux/arm.rs index 66cfd05e80..7383e487f1 100644 --- a/crates/std_detect/src/detect/os/linux/arm.rs +++ b/crates/std_detect/src/detect/os/linux/arm.rs @@ -28,6 +28,13 @@ pub(crate) fn detect_features() -> cache::Initializer { && bit::test(auxv.hwcap2, 2) && bit::test(auxv.hwcap2, 3), ); + enable_feature(&mut value, Feature::aes, bit::test(auxv.hwcap2, 0)); + // SHA2 requires SHA1 & SHA2 features + enable_feature( + &mut value, + Feature::sha2, + bit::test(auxv.hwcap2, 2) && bit::test(auxv.hwcap2, 3), + ); return value; } @@ -48,6 +55,12 @@ pub(crate) fn detect_features() -> cache::Initializer { && c.field("Features").has("sha1") && c.field("Features").has("sha2"), ); + enable_feature(&mut value, Feature::aes, c.field("Features").has("aes")); + enable_feature( + &mut value, + Feature::sha2, + c.field("Features").has("sha1") && c.field("Features").has("sha2"), + ); return value; } value diff --git a/crates/std_detect/src/detect/os/windows/aarch64.rs b/crates/std_detect/src/detect/os/windows/aarch64.rs index 3c5edfb44a..051ad6d1bf 100644 --- a/crates/std_detect/src/detect/os/windows/aarch64.rs +++ b/crates/std_detect/src/detect/os/windows/aarch64.rs @@ -42,13 +42,17 @@ pub(crate) fn detect_features() -> cache::Initializer { // PF_ARM_V8_CRYPTO_INSTRUCTIONS_AVAILABLE means aes, sha1, sha2 and // pmull support enable_feature( - Feature::crypto, + Feature::aes, IsProcessorFeaturePresent(PF_ARM_V8_CRYPTO_INSTRUCTIONS_AVAILABLE) != FALSE, ); enable_feature( Feature::pmull, IsProcessorFeaturePresent(PF_ARM_V8_CRYPTO_INSTRUCTIONS_AVAILABLE) != FALSE, ); + enable_feature( + Feature::sha2, + IsProcessorFeaturePresent(PF_ARM_V8_CRYPTO_INSTRUCTIONS_AVAILABLE) != FALSE, + ); } } value diff --git a/crates/std_detect/tests/cpu-detection.rs b/crates/std_detect/tests/cpu-detection.rs index 8f29ea45cd..adbe4fa9a7 100644 --- a/crates/std_detect/tests/cpu-detection.rs +++ b/crates/std_detect/tests/cpu-detection.rs @@ -26,6 +26,8 @@ fn arm_linux() { println!("pmull: {}", is_arm_feature_detected!("pmull")); println!("crc: {}", is_arm_feature_detected!("crc")); println!("crypto: {}", is_arm_feature_detected!("crypto")); + println!("aes: {}", is_arm_feature_detected!("aes")); + println!("sha2: {}", is_arm_feature_detected!("sha2")); } #[test] @@ -34,18 +36,50 @@ fn arm_linux() { any(target_os = "linux", target_os = "android") ))] fn aarch64_linux() { + println!("asimd: {}", is_aarch64_feature_detected!("asimd")); + println!("neon: {}", is_aarch64_feature_detected!("neon")); + println!("pmull: {}", is_aarch64_feature_detected!("pmull")); println!("fp: {}", is_aarch64_feature_detected!("fp")); println!("fp16: {}", is_aarch64_feature_detected!("fp16")); - println!("neon: {}", is_aarch64_feature_detected!("neon")); - println!("asimd: {}", is_aarch64_feature_detected!("asimd")); println!("sve: {}", is_aarch64_feature_detected!("sve")); println!("crc: {}", is_aarch64_feature_detected!("crc")); - println!("crypto: {}", is_aarch64_feature_detected!("crypto")); println!("lse: {}", is_aarch64_feature_detected!("lse")); + println!("lse2: {}", is_aarch64_feature_detected!("lse2")); println!("rdm: {}", is_aarch64_feature_detected!("rdm")); println!("rcpc: {}", is_aarch64_feature_detected!("rcpc")); + println!("rcpc2: {}", is_aarch64_feature_detected!("rcpc2")); println!("dotprod: {}", is_aarch64_feature_detected!("dotprod")); println!("tme: {}", is_aarch64_feature_detected!("tme")); + println!("fhm: {}", is_aarch64_feature_detected!("fhm")); + println!("dit: {}", is_aarch64_feature_detected!("dit")); + println!("flagm: {}", is_aarch64_feature_detected!("flagm")); + println!("ssbs: {}", is_aarch64_feature_detected!("ssbs")); + println!("sb: {}", is_aarch64_feature_detected!("sb")); + println!("pauth: {}", is_aarch64_feature_detected!("pauth")); + println!("dpb: {}", is_aarch64_feature_detected!("dpb")); + println!("dpb2: {}", is_aarch64_feature_detected!("dpb2")); + println!("sve2: {}", is_aarch64_feature_detected!("sve2")); + println!("sve2-aes: {}", is_aarch64_feature_detected!("sve2-aes")); + println!("sve2-sm4: {}", is_aarch64_feature_detected!("sve2-sm4")); + println!("sve2-sha3: {}", is_aarch64_feature_detected!("sve2-sha3")); + println!( + "sve2-bitperm: {}", + is_aarch64_feature_detected!("sve2-bitperm") + ); + println!("frintts: {}", is_aarch64_feature_detected!("frintts")); + println!("i8mm: {}", is_aarch64_feature_detected!("i8mm")); + println!("f32mm: {}", is_aarch64_feature_detected!("f32mm")); + println!("f64mm: {}", is_aarch64_feature_detected!("f64mm")); + println!("bf16: {}", is_aarch64_feature_detected!("bf16")); + println!("rand: {}", is_aarch64_feature_detected!("rand")); + println!("bti: {}", is_aarch64_feature_detected!("bti")); + println!("mte: {}", is_aarch64_feature_detected!("mte")); + println!("jsconv: {}", is_aarch64_feature_detected!("jsconv")); + println!("fcma: {}", is_aarch64_feature_detected!("fcma")); + println!("aes: {}", is_aarch64_feature_detected!("aes")); + println!("sha2: {}", is_aarch64_feature_detected!("sha2")); + println!("sha3: {}", is_aarch64_feature_detected!("sha3")); + println!("sm4: {}", is_aarch64_feature_detected!("sm4")); } #[test]