mirror of
https://github.com/google/cpu_features.git
synced 2025-04-27 15:12:30 +02:00
Add support for Apple M1 AArch64 SoCs (#204)
* Add support for Apple M1 AArch64 SoCs Completely based on #150. Thanks to @sbehnke! + Refactoring to accomodate the new source tree + Adding more feature flags * revert minimum version to 3.0 * Update introspection table * Simplify logic for Apple HAVE_SYSCTLBYNAME --------- Co-authored-by: Guillaume Chatelet <gchatelet@google.com>
This commit is contained in:
parent
0d5f398c58
commit
c5ece5e8cc
@ -63,7 +63,7 @@ set(PROCESSOR_IS_LOONGARCH FALSE)
|
||||
|
||||
if(CMAKE_SYSTEM_PROCESSOR MATCHES "^mips")
|
||||
set(PROCESSOR_IS_MIPS TRUE)
|
||||
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^(aarch64|arm64)")
|
||||
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "(^aarch64)|(^arm64)")
|
||||
set(PROCESSOR_IS_AARCH64 TRUE)
|
||||
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^arm")
|
||||
set(PROCESSOR_IS_ARM TRUE)
|
||||
@ -160,10 +160,9 @@ target_link_libraries(cpu_features PUBLIC ${CMAKE_DL_LIBS})
|
||||
target_include_directories(cpu_features
|
||||
PUBLIC $<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}/cpu_features>
|
||||
)
|
||||
if(PROCESSOR_IS_X86)
|
||||
if(APPLE)
|
||||
target_compile_definitions(cpu_features PRIVATE HAVE_SYSCTLBYNAME)
|
||||
endif()
|
||||
|
||||
if(APPLE)
|
||||
target_compile_definitions(cpu_features PRIVATE HAVE_SYSCTLBYNAME)
|
||||
endif()
|
||||
add_library(CpuFeature::cpu_features ALIAS cpu_features)
|
||||
|
||||
|
@ -182,7 +182,7 @@ flags : aes,avx,cx16,smx,sse4_1,sse4_2,ssse3
|
||||
|---------|:----:|:-------:|:-------:|:-------:|:-------:|:-------:|:-------:|
|
||||
| Linux | yes² | yes¹ | yes¹ | yes¹ | yes¹ | yes¹ | yes¹ |
|
||||
| FreeBSD | yes² | not yet | not yet | not yet | not yet | N/A | not yet |
|
||||
| MacOs | yes² | not yet | N/A | N/A | no | N/A | no |
|
||||
| MacOs | yes² | yes⁵ | N/A | N/A | N/A | N/A | N/A |
|
||||
| Windows | yes² | not yet | not yet | N/A | N/A | N/A | N/A |
|
||||
| Android | yes² | yes¹ | yes¹ | yes¹ | N/A | N/A | N/A |
|
||||
| iOS | N/A | not yet | not yet | N/A | N/A | N/A | N/A |
|
||||
@ -200,6 +200,8 @@ flags : aes,avx,cx16,smx,sse4_1,sse4_2,ssse3
|
||||
microarchitecture allows the client to reject particular microarchitectures.
|
||||
4. All flavors of Mips are supported, little and big endian as well as 32/64
|
||||
bits.
|
||||
5. **Features revealed from sysctl.** features are retrieved by the `sysctl`
|
||||
instruction.
|
||||
|
||||
<a name="ndk"></a>
|
||||
## Android NDK's drop in replacement
|
||||
|
118
src/impl_aarch64__base_implementation.inl
Normal file
118
src/impl_aarch64__base_implementation.inl
Normal file
@ -0,0 +1,118 @@
|
||||
// Copyright 2021 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
#include "cpu_features_macros.h"
|
||||
#include "cpuinfo_aarch64.h"
|
||||
#include "internal/bit_utils.h"
|
||||
#include "internal/filesystem.h"
|
||||
#include "internal/stack_line_reader.h"
|
||||
#include "internal/string_view.h"
|
||||
|
||||
#if !defined(CPU_FEATURES_ARCH_AARCH64)
|
||||
#error "Cannot compile aarch64_base on a non aarch64 platform."
|
||||
#endif
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// Definitions for introspection.
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
#define INTROSPECTION_TABLE \
|
||||
LINE(AARCH64_FP, fp, "fp", AARCH64_HWCAP_FP, 0) \
|
||||
LINE(AARCH64_ASIMD, asimd, "asimd", AARCH64_HWCAP_ASIMD, 0) \
|
||||
LINE(AARCH64_EVTSTRM, evtstrm, "evtstrm", AARCH64_HWCAP_EVTSTRM, 0) \
|
||||
LINE(AARCH64_AES, aes, "aes", AARCH64_HWCAP_AES, 0) \
|
||||
LINE(AARCH64_PMULL, pmull, "pmull", AARCH64_HWCAP_PMULL, 0) \
|
||||
LINE(AARCH64_SHA1, sha1, "sha1", AARCH64_HWCAP_SHA1, 0) \
|
||||
LINE(AARCH64_SHA2, sha2, "sha2", AARCH64_HWCAP_SHA2, 0) \
|
||||
LINE(AARCH64_CRC32, crc32, "crc32", AARCH64_HWCAP_CRC32, 0) \
|
||||
LINE(AARCH64_ATOMICS, atomics, "atomics", AARCH64_HWCAP_ATOMICS, 0) \
|
||||
LINE(AARCH64_FPHP, fphp, "fphp", AARCH64_HWCAP_FPHP, 0) \
|
||||
LINE(AARCH64_ASIMDHP, asimdhp, "asimdhp", AARCH64_HWCAP_ASIMDHP, 0) \
|
||||
LINE(AARCH64_CPUID, cpuid, "cpuid", AARCH64_HWCAP_CPUID, 0) \
|
||||
LINE(AARCH64_ASIMDRDM, asimdrdm, "asimdrdm", AARCH64_HWCAP_ASIMDRDM, 0) \
|
||||
LINE(AARCH64_JSCVT, jscvt, "jscvt", AARCH64_HWCAP_JSCVT, 0) \
|
||||
LINE(AARCH64_FCMA, fcma, "fcma", AARCH64_HWCAP_FCMA, 0) \
|
||||
LINE(AARCH64_LRCPC, lrcpc, "lrcpc", AARCH64_HWCAP_LRCPC, 0) \
|
||||
LINE(AARCH64_DCPOP, dcpop, "dcpop", AARCH64_HWCAP_DCPOP, 0) \
|
||||
LINE(AARCH64_SHA3, sha3, "sha3", AARCH64_HWCAP_SHA3, 0) \
|
||||
LINE(AARCH64_SM3, sm3, "sm3", AARCH64_HWCAP_SM3, 0) \
|
||||
LINE(AARCH64_SM4, sm4, "sm4", AARCH64_HWCAP_SM4, 0) \
|
||||
LINE(AARCH64_ASIMDDP, asimddp, "asimddp", AARCH64_HWCAP_ASIMDDP, 0) \
|
||||
LINE(AARCH64_SHA512, sha512, "sha512", AARCH64_HWCAP_SHA512, 0) \
|
||||
LINE(AARCH64_SVE, sve, "sve", AARCH64_HWCAP_SVE, 0) \
|
||||
LINE(AARCH64_ASIMDFHM, asimdfhm, "asimdfhm", AARCH64_HWCAP_ASIMDFHM, 0) \
|
||||
LINE(AARCH64_DIT, dit, "dit", AARCH64_HWCAP_DIT, 0) \
|
||||
LINE(AARCH64_USCAT, uscat, "uscat", AARCH64_HWCAP_USCAT, 0) \
|
||||
LINE(AARCH64_ILRCPC, ilrcpc, "ilrcpc", AARCH64_HWCAP_ILRCPC, 0) \
|
||||
LINE(AARCH64_FLAGM, flagm, "flagm", AARCH64_HWCAP_FLAGM, 0) \
|
||||
LINE(AARCH64_SSBS, ssbs, "ssbs", AARCH64_HWCAP_SSBS, 0) \
|
||||
LINE(AARCH64_SB, sb, "sb", AARCH64_HWCAP_SB, 0) \
|
||||
LINE(AARCH64_PACA, paca, "paca", AARCH64_HWCAP_PACA, 0) \
|
||||
LINE(AARCH64_PACG, pacg, "pacg", AARCH64_HWCAP_PACG, 0) \
|
||||
LINE(AARCH64_DCPODP, dcpodp, "dcpodp", 0, AARCH64_HWCAP2_DCPODP) \
|
||||
LINE(AARCH64_SVE2, sve2, "sve2", 0, AARCH64_HWCAP2_SVE2) \
|
||||
LINE(AARCH64_SVEAES, sveaes, "sveaes", 0, AARCH64_HWCAP2_SVEAES) \
|
||||
LINE(AARCH64_SVEPMULL, svepmull, "svepmull", 0, AARCH64_HWCAP2_SVEPMULL) \
|
||||
LINE(AARCH64_SVEBITPERM, svebitperm, "svebitperm", 0, \
|
||||
AARCH64_HWCAP2_SVEBITPERM) \
|
||||
LINE(AARCH64_SVESHA3, svesha3, "svesha3", 0, AARCH64_HWCAP2_SVESHA3) \
|
||||
LINE(AARCH64_SVESM4, svesm4, "svesm4", 0, AARCH64_HWCAP2_SVESM4) \
|
||||
LINE(AARCH64_FLAGM2, flagm2, "flagm2", 0, AARCH64_HWCAP2_FLAGM2) \
|
||||
LINE(AARCH64_FRINT, frint, "frint", 0, AARCH64_HWCAP2_FRINT) \
|
||||
LINE(AARCH64_SVEI8MM, svei8mm, "svei8mm", 0, AARCH64_HWCAP2_SVEI8MM) \
|
||||
LINE(AARCH64_SVEF32MM, svef32mm, "svef32mm", 0, AARCH64_HWCAP2_SVEF32MM) \
|
||||
LINE(AARCH64_SVEF64MM, svef64mm, "svef64mm", 0, AARCH64_HWCAP2_SVEF64MM) \
|
||||
LINE(AARCH64_SVEBF16, svebf16, "svebf16", 0, AARCH64_HWCAP2_SVEBF16) \
|
||||
LINE(AARCH64_I8MM, i8mm, "i8mm", 0, AARCH64_HWCAP2_I8MM) \
|
||||
LINE(AARCH64_BF16, bf16, "bf16", 0, AARCH64_HWCAP2_BF16) \
|
||||
LINE(AARCH64_DGH, dgh, "dgh", 0, AARCH64_HWCAP2_DGH) \
|
||||
LINE(AARCH64_RNG, rng, "rng", 0, AARCH64_HWCAP2_RNG) \
|
||||
LINE(AARCH64_BTI, bti, "bti", 0, AARCH64_HWCAP2_BTI) \
|
||||
LINE(AARCH64_MTE, mte, "mte", 0, AARCH64_HWCAP2_MTE) \
|
||||
LINE(AARCH64_ECV, ecv, "ecv", 0, AARCH64_HWCAP2_ECV) \
|
||||
LINE(AARCH64_AFP, afp, "afp", 0, AARCH64_HWCAP2_AFP) \
|
||||
LINE(AARCH64_RPRES, rpres, "rpres", 0, AARCH64_HWCAP2_RPRES) \
|
||||
LINE(AARCH64_MTE3, mte3, "mte3", 0, AARCH64_HWCAP2_MTE3) \
|
||||
LINE(AARCH64_SME, sme, "sme", 0, AARCH64_HWCAP2_SME) \
|
||||
LINE(AARCH64_SME_I16I64, smei16i64, "smei16i64", 0, \
|
||||
AARCH64_HWCAP2_SME_I16I64) \
|
||||
LINE(AARCH64_SME_F64F64, smef64f64, "smef64f64", 0, \
|
||||
AARCH64_HWCAP2_SME_F64F64) \
|
||||
LINE(AARCH64_SME_I8I32, smei8i32, "smei8i32", 0, AARCH64_HWCAP2_SME_I8I32) \
|
||||
LINE(AARCH64_SME_F16F32, smef16f32, "smef16f32", 0, \
|
||||
AARCH64_HWCAP2_SME_F16F32) \
|
||||
LINE(AARCH64_SME_B16F32, smeb16f32, "smeb16f32", 0, \
|
||||
AARCH64_HWCAP2_SME_B16F32) \
|
||||
LINE(AARCH64_SME_F32F32, smef32f32, "smef32f32", 0, \
|
||||
AARCH64_HWCAP2_SME_F32F32) \
|
||||
LINE(AARCH64_SME_FA64, smefa64, "smefa64", 0, AARCH64_HWCAP2_SME_FA64) \
|
||||
LINE(AARCH64_WFXT, wfxt, "wfxt", 0, AARCH64_HWCAP2_WFXT) \
|
||||
LINE(AARCH64_EBF16, ebf16, "ebf16", 0, AARCH64_HWCAP2_EBF16) \
|
||||
LINE(AARCH64_SVE_EBF16, sveebf16, "sveebf16", 0, AARCH64_HWCAP2_SVE_EBF16) \
|
||||
LINE(AARCH64_CSSC, cssc, "cssc", 0, AARCH64_HWCAP2_CSSC) \
|
||||
LINE(AARCH64_RPRFM, rprfm, "rprfm", 0, AARCH64_HWCAP2_RPRFM) \
|
||||
LINE(AARCH64_SVE2P1, sve2p1, "sve2p1", 0, AARCH64_HWCAP2_SVE2P1) \
|
||||
LINE(AARCH64_SME2, sme2, "sme2", 0, AARCH64_HWCAP2_SME2) \
|
||||
LINE(AARCH64_SME2P1, sme2p1, "sme2p1", 0, AARCH64_HWCAP2_SME2P1) \
|
||||
LINE(AARCH64_SME_I16I32, smei16i32, "smei16i32", 0, \
|
||||
AARCH64_HWCAP2_SME_I16I32) \
|
||||
LINE(AARCH64_SME_BI32I32, smebi32i32, "smebi32i32", 0, \
|
||||
AARCH64_HWCAP2_SME_BI32I32) \
|
||||
LINE(AARCH64_SME_B16B16, smeb16b16, "smeb16b16", 0, \
|
||||
AARCH64_HWCAP2_SME_B16B16) \
|
||||
LINE(AARCH64_SME_F16F16, smef16f16, "smef16f16", 0, AARCH64_HWCAP2_SME_F16F16)
|
||||
#define INTROSPECTION_PREFIX Aarch64
|
||||
#define INTROSPECTION_ENUM_PREFIX AARCH64
|
||||
#include "define_introspection_and_hwcaps.inl"
|
@ -17,110 +17,7 @@
|
||||
#ifdef CPU_FEATURES_ARCH_AARCH64
|
||||
#if defined(CPU_FEATURES_OS_LINUX) || defined(CPU_FEATURES_OS_ANDROID)
|
||||
|
||||
#include "cpuinfo_aarch64.h"
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// Definitions for introspection.
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
#define INTROSPECTION_TABLE \
|
||||
LINE(AARCH64_FP, fp, "fp", AARCH64_HWCAP_FP, 0) \
|
||||
LINE(AARCH64_ASIMD, asimd, "asimd", AARCH64_HWCAP_ASIMD, 0) \
|
||||
LINE(AARCH64_EVTSTRM, evtstrm, "evtstrm", AARCH64_HWCAP_EVTSTRM, 0) \
|
||||
LINE(AARCH64_AES, aes, "aes", AARCH64_HWCAP_AES, 0) \
|
||||
LINE(AARCH64_PMULL, pmull, "pmull", AARCH64_HWCAP_PMULL, 0) \
|
||||
LINE(AARCH64_SHA1, sha1, "sha1", AARCH64_HWCAP_SHA1, 0) \
|
||||
LINE(AARCH64_SHA2, sha2, "sha2", AARCH64_HWCAP_SHA2, 0) \
|
||||
LINE(AARCH64_CRC32, crc32, "crc32", AARCH64_HWCAP_CRC32, 0) \
|
||||
LINE(AARCH64_ATOMICS, atomics, "atomics", AARCH64_HWCAP_ATOMICS, 0) \
|
||||
LINE(AARCH64_FPHP, fphp, "fphp", AARCH64_HWCAP_FPHP, 0) \
|
||||
LINE(AARCH64_ASIMDHP, asimdhp, "asimdhp", AARCH64_HWCAP_ASIMDHP, 0) \
|
||||
LINE(AARCH64_CPUID, cpuid, "cpuid", AARCH64_HWCAP_CPUID, 0) \
|
||||
LINE(AARCH64_ASIMDRDM, asimdrdm, "asimdrdm", AARCH64_HWCAP_ASIMDRDM, 0) \
|
||||
LINE(AARCH64_JSCVT, jscvt, "jscvt", AARCH64_HWCAP_JSCVT, 0) \
|
||||
LINE(AARCH64_FCMA, fcma, "fcma", AARCH64_HWCAP_FCMA, 0) \
|
||||
LINE(AARCH64_LRCPC, lrcpc, "lrcpc", AARCH64_HWCAP_LRCPC, 0) \
|
||||
LINE(AARCH64_DCPOP, dcpop, "dcpop", AARCH64_HWCAP_DCPOP, 0) \
|
||||
LINE(AARCH64_SHA3, sha3, "sha3", AARCH64_HWCAP_SHA3, 0) \
|
||||
LINE(AARCH64_SM3, sm3, "sm3", AARCH64_HWCAP_SM3, 0) \
|
||||
LINE(AARCH64_SM4, sm4, "sm4", AARCH64_HWCAP_SM4, 0) \
|
||||
LINE(AARCH64_ASIMDDP, asimddp, "asimddp", AARCH64_HWCAP_ASIMDDP, 0) \
|
||||
LINE(AARCH64_SHA512, sha512, "sha512", AARCH64_HWCAP_SHA512, 0) \
|
||||
LINE(AARCH64_SVE, sve, "sve", AARCH64_HWCAP_SVE, 0) \
|
||||
LINE(AARCH64_ASIMDFHM, asimdfhm, "asimdfhm", AARCH64_HWCAP_ASIMDFHM, 0) \
|
||||
LINE(AARCH64_DIT, dit, "dit", AARCH64_HWCAP_DIT, 0) \
|
||||
LINE(AARCH64_USCAT, uscat, "uscat", AARCH64_HWCAP_USCAT, 0) \
|
||||
LINE(AARCH64_ILRCPC, ilrcpc, "ilrcpc", AARCH64_HWCAP_ILRCPC, 0) \
|
||||
LINE(AARCH64_FLAGM, flagm, "flagm", AARCH64_HWCAP_FLAGM, 0) \
|
||||
LINE(AARCH64_SSBS, ssbs, "ssbs", AARCH64_HWCAP_SSBS, 0) \
|
||||
LINE(AARCH64_SB, sb, "sb", AARCH64_HWCAP_SB, 0) \
|
||||
LINE(AARCH64_PACA, paca, "paca", AARCH64_HWCAP_PACA, 0) \
|
||||
LINE(AARCH64_PACG, pacg, "pacg", AARCH64_HWCAP_PACG, 0) \
|
||||
LINE(AARCH64_DCPODP, dcpodp, "dcpodp", 0, AARCH64_HWCAP2_DCPODP) \
|
||||
LINE(AARCH64_SVE2, sve2, "sve2", 0, AARCH64_HWCAP2_SVE2) \
|
||||
LINE(AARCH64_SVEAES, sveaes, "sveaes", 0, AARCH64_HWCAP2_SVEAES) \
|
||||
LINE(AARCH64_SVEPMULL, svepmull, "svepmull", 0, AARCH64_HWCAP2_SVEPMULL) \
|
||||
LINE(AARCH64_SVEBITPERM, svebitperm, "svebitperm", 0, \
|
||||
AARCH64_HWCAP2_SVEBITPERM) \
|
||||
LINE(AARCH64_SVESHA3, svesha3, "svesha3", 0, AARCH64_HWCAP2_SVESHA3) \
|
||||
LINE(AARCH64_SVESM4, svesm4, "svesm4", 0, AARCH64_HWCAP2_SVESM4) \
|
||||
LINE(AARCH64_FLAGM2, flagm2, "flagm2", 0, AARCH64_HWCAP2_FLAGM2) \
|
||||
LINE(AARCH64_FRINT, frint, "frint", 0, AARCH64_HWCAP2_FRINT) \
|
||||
LINE(AARCH64_SVEI8MM, svei8mm, "svei8mm", 0, AARCH64_HWCAP2_SVEI8MM) \
|
||||
LINE(AARCH64_SVEF32MM, svef32mm, "svef32mm", 0, AARCH64_HWCAP2_SVEF32MM) \
|
||||
LINE(AARCH64_SVEF64MM, svef64mm, "svef64mm", 0, AARCH64_HWCAP2_SVEF64MM) \
|
||||
LINE(AARCH64_SVEBF16, svebf16, "svebf16", 0, AARCH64_HWCAP2_SVEBF16) \
|
||||
LINE(AARCH64_I8MM, i8mm, "i8mm", 0, AARCH64_HWCAP2_I8MM) \
|
||||
LINE(AARCH64_BF16, bf16, "bf16", 0, AARCH64_HWCAP2_BF16) \
|
||||
LINE(AARCH64_DGH, dgh, "dgh", 0, AARCH64_HWCAP2_DGH) \
|
||||
LINE(AARCH64_RNG, rng, "rng", 0, AARCH64_HWCAP2_RNG) \
|
||||
LINE(AARCH64_BTI, bti, "bti", 0, AARCH64_HWCAP2_BTI) \
|
||||
LINE(AARCH64_MTE, mte, "mte", 0, AARCH64_HWCAP2_MTE) \
|
||||
LINE(AARCH64_ECV, ecv, "ecv", 0, AARCH64_HWCAP2_ECV) \
|
||||
LINE(AARCH64_AFP, afp, "afp", 0, AARCH64_HWCAP2_AFP) \
|
||||
LINE(AARCH64_RPRES, rpres, "rpres", 0, AARCH64_HWCAP2_RPRES) \
|
||||
LINE(AARCH64_MTE3, mte3, "mte3", 0, AARCH64_HWCAP2_MTE3) \
|
||||
LINE(AARCH64_SME, sme, "sme", 0, AARCH64_HWCAP2_SME) \
|
||||
LINE(AARCH64_SME_I16I64, smei16i64, "smei16i64", 0, \
|
||||
AARCH64_HWCAP2_SME_I16I64) \
|
||||
LINE(AARCH64_SME_F64F64, smef64f64, "smef64f64", 0, \
|
||||
AARCH64_HWCAP2_SME_F64F64) \
|
||||
LINE(AARCH64_SME_I8I32, smei8i32, "smei8i32", 0, AARCH64_HWCAP2_SME_I8I32) \
|
||||
LINE(AARCH64_SME_F16F32, smef16f32, "smef16f32", 0, \
|
||||
AARCH64_HWCAP2_SME_F16F32) \
|
||||
LINE(AARCH64_SME_B16F32, smeb16f32, "smeb16f32", 0, \
|
||||
AARCH64_HWCAP2_SME_B16F32) \
|
||||
LINE(AARCH64_SME_F32F32, smef32f32, "smef32f32", 0, \
|
||||
AARCH64_HWCAP2_SME_F32F32) \
|
||||
LINE(AARCH64_SME_FA64, smefa64, "smefa64", 0, AARCH64_HWCAP2_SME_FA64) \
|
||||
LINE(AARCH64_WFXT, wfxt, "wfxt", 0, AARCH64_HWCAP2_WFXT) \
|
||||
LINE(AARCH64_EBF16, ebf16, "ebf16", 0, AARCH64_HWCAP2_EBF16) \
|
||||
LINE(AARCH64_SVE_EBF16, sveebf16, "sveebf16", 0, AARCH64_HWCAP2_SVE_EBF16) \
|
||||
LINE(AARCH64_CSSC, cssc, "cssc", 0, AARCH64_HWCAP2_CSSC) \
|
||||
LINE(AARCH64_RPRFM, rprfm, "rprfm", 0, AARCH64_HWCAP2_RPRFM) \
|
||||
LINE(AARCH64_SVE2P1, sve2p1, "sve2p1", 0, AARCH64_HWCAP2_SVE2P1) \
|
||||
LINE(AARCH64_SME2, sme2, "sme2", 0, AARCH64_HWCAP2_SME2) \
|
||||
LINE(AARCH64_SME2P1, sme2p1, "sme2p1", 0, AARCH64_HWCAP2_SME2P1) \
|
||||
LINE(AARCH64_SME_I16I32, smei16i32, "smei16i32", 0, \
|
||||
AARCH64_HWCAP2_SME_I16I32) \
|
||||
LINE(AARCH64_SME_BI32I32, smebi32i32, "smebi32i32", 0, \
|
||||
AARCH64_HWCAP2_SME_BI32I32) \
|
||||
LINE(AARCH64_SME_B16B16, smeb16b16, "smeb16b16", 0, \
|
||||
AARCH64_HWCAP2_SME_B16B16) \
|
||||
LINE(AARCH64_SME_F16F16, smef16f16, "smef16f16", 0, AARCH64_HWCAP2_SME_F16F16)
|
||||
#define INTROSPECTION_PREFIX Aarch64
|
||||
#define INTROSPECTION_ENUM_PREFIX AARCH64
|
||||
#include "define_introspection_and_hwcaps.inl"
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// Implementation.
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
#include "internal/bit_utils.h"
|
||||
#include "internal/filesystem.h"
|
||||
#include "internal/stack_line_reader.h"
|
||||
#include "internal/string_view.h"
|
||||
#include "impl_aarch64__base_implementation.inl"
|
||||
|
||||
static bool HandleAarch64Line(const LineResult result,
|
||||
Aarch64Info* const info) {
|
||||
|
88
src/impl_aarch64_macos_or_iphone.c
Normal file
88
src/impl_aarch64_macos_or_iphone.c
Normal file
@ -0,0 +1,88 @@
|
||||
// Copyright 2021 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "cpu_features_macros.h"
|
||||
|
||||
#ifdef CPU_FEATURES_ARCH_AARCH64
|
||||
#if defined(CPU_FEATURES_OS_MACOS) || defined(CPU_FEATURES_OS_IPHONE)
|
||||
|
||||
#include "impl_aarch64__base_implementation.inl"
|
||||
|
||||
#if !defined(HAVE_SYSCTLBYNAME)
|
||||
#error "Darwin needs support for sysctlbyname"
|
||||
#endif
|
||||
#include <sys/sysctl.h>
|
||||
|
||||
#if defined(CPU_FEATURES_MOCK_SYSCTL_AARCH64)
|
||||
extern bool GetDarwinSysCtlByName(const char*);
|
||||
extern int GetDarwinSysCtlByNameValue(const char* name);
|
||||
#else
|
||||
static int GetDarwinSysCtlByNameValue(const char* name) {
|
||||
int enabled;
|
||||
size_t enabled_len = sizeof(enabled);
|
||||
const int failure = sysctlbyname(name, &enabled, &enabled_len, NULL, 0);
|
||||
return failure ? 0 : enabled;
|
||||
}
|
||||
|
||||
static bool GetDarwinSysCtlByName(const char* name) {
|
||||
return GetDarwinSysCtlByNameValue(name) != 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
static const Aarch64Info kEmptyAarch64Info;
|
||||
|
||||
Aarch64Info GetAarch64Info(void) {
|
||||
Aarch64Info info = kEmptyAarch64Info;
|
||||
|
||||
// Handling Darwin platform through sysctlbyname.
|
||||
info.implementer = GetDarwinSysCtlByNameValue("hw.cputype");
|
||||
info.variant = GetDarwinSysCtlByNameValue("hw.cpusubtype");
|
||||
info.part = GetDarwinSysCtlByNameValue("hw.cpufamily");
|
||||
info.revision = GetDarwinSysCtlByNameValue("hw.cpusubfamily");
|
||||
|
||||
info.features.fp = GetDarwinSysCtlByName("hw.optional.floatingpoint");
|
||||
info.features.asimd = GetDarwinSysCtlByName("hw.optional.AdvSIMD");
|
||||
info.features.aes = GetDarwinSysCtlByName("hw.optional.arm.FEAT_AES");
|
||||
info.features.pmull = GetDarwinSysCtlByName("hw.optional.arm.FEAT_PMULL");
|
||||
info.features.sha1 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA1");
|
||||
info.features.sha2 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA256");
|
||||
info.features.crc32 = GetDarwinSysCtlByName("hw.optional.armv8_crc32");
|
||||
info.features.atomics = GetDarwinSysCtlByName("hw.optional.arm.FEAT_LSE");
|
||||
info.features.fphp = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FP16");
|
||||
info.features.asimdhp = GetDarwinSysCtlByName("hw.optional.arm.AdvSIMD_HPFPCvt");
|
||||
info.features.asimdrdm = GetDarwinSysCtlByName("hw.optional.arm.FEAT_RDM");
|
||||
info.features.jscvt = GetDarwinSysCtlByName("hw.optional.arm.FEAT_JSCVT");
|
||||
info.features.fcma = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FCMA");
|
||||
info.features.lrcpc = GetDarwinSysCtlByName("hw.optional.arm.FEAT_LRCPC");
|
||||
info.features.dcpop = GetDarwinSysCtlByName("hw.optional.arm.FEAT_DPB");
|
||||
info.features.sha3 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA3");
|
||||
info.features.asimddp = GetDarwinSysCtlByName("hw.optional.arm.FEAT_DotProd");
|
||||
info.features.sha512 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA512");
|
||||
info.features.asimdfhm = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FHM");
|
||||
info.features.dit = GetDarwinSysCtlByName("hw.optional.arm.FEAT_DIT");
|
||||
info.features.uscat = GetDarwinSysCtlByName("hw.optional.arm.FEAT_LSE2");
|
||||
info.features.flagm = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FlagM");
|
||||
info.features.ssbs = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SSBS");
|
||||
info.features.sb = GetDarwinSysCtlByName("hw.optional.arm.FEAT_SB");
|
||||
info.features.flagm2 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FlagM2");
|
||||
info.features.frint = GetDarwinSysCtlByName("hw.optional.arm.FEAT_FRINTTS");
|
||||
info.features.i8mm = GetDarwinSysCtlByName("hw.optional.arm.FEAT_I8MM");
|
||||
info.features.bf16 = GetDarwinSysCtlByName("hw.optional.arm.FEAT_BF16");
|
||||
info.features.bti = GetDarwinSysCtlByName("hw.optional.arm.FEAT_BTI");
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
#endif // defined(CPU_FEATURES_OS_MACOS) || defined(CPU_FEATURES_OS_IPHONE)
|
||||
#endif // CPU_FEATURES_ARCH_AARCH64
|
@ -74,8 +74,15 @@ if(PROCESSOR_IS_AARCH64)
|
||||
add_executable(cpuinfo_aarch64_test
|
||||
cpuinfo_aarch64_test.cc
|
||||
../src/impl_aarch64_linux_or_android.c
|
||||
../src/impl_aarch64_windows.c)
|
||||
target_compile_definitions(cpuinfo_aarch64_test PUBLIC CPU_FEATURES_MOCK_CPUID_AARCH64)
|
||||
../src/impl_aarch64_windows.c
|
||||
../src/impl_aarch64_macos_or_iphone.c
|
||||
)
|
||||
if(APPLE)
|
||||
target_compile_definitions(cpuinfo_aarch64_test PUBLIC CPU_FEATURES_MOCK_SYSCTL_AARCH64)
|
||||
target_compile_definitions(cpuinfo_aarch64_test PRIVATE HAVE_SYSCTLBYNAME)
|
||||
else()
|
||||
target_compile_definitions(cpuinfo_aarch64_test PUBLIC CPU_FEATURES_MOCK_CPUID_AARCH64)
|
||||
endif()
|
||||
target_link_libraries(cpuinfo_aarch64_test all_libraries)
|
||||
add_test(NAME cpuinfo_aarch64_test COMMAND cpuinfo_aarch64_test)
|
||||
endif()
|
||||
|
@ -25,8 +25,35 @@
|
||||
|
||||
namespace cpu_features {
|
||||
class FakeCpuAarch64 {
|
||||
#if defined(CPU_FEATURES_OS_LINUX)
|
||||
// No particular implementation for Linux as we use /proc/cpuinfo
|
||||
#elif defined(CPU_FEATURES_OS_MACOS)
|
||||
std::set<std::string> darwin_sysctlbyname_;
|
||||
std::map<std::string, int> darwin_sysctlbynamevalue_;
|
||||
|
||||
public:
|
||||
bool GetDarwinSysCtlByName(std::string name) const {
|
||||
return darwin_sysctlbyname_.count(name);
|
||||
}
|
||||
|
||||
int GetDarwinSysCtlByNameValue(std::string name) const {
|
||||
const auto iter = darwin_sysctlbynamevalue_.find(name);
|
||||
if (iter != darwin_sysctlbynamevalue_.end()) return iter->second;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void SetDarwinSysCtlByName(std::string name) {
|
||||
darwin_sysctlbyname_.insert(name);
|
||||
}
|
||||
|
||||
void SetDarwinSysCtlByNameValue(std::string name, int value) {
|
||||
darwin_sysctlbynamevalue_[name] = value;
|
||||
}
|
||||
#elif defined(CPU_FEATURES_OS_WINDOWS)
|
||||
std::set<DWORD> windows_isprocessorfeaturepresent_;
|
||||
WORD processor_revision_{};
|
||||
|
||||
public:
|
||||
#if defined(CPU_FEATURES_OS_WINDOWS)
|
||||
bool GetWindowsIsProcessorFeaturePresent(DWORD dwProcessorFeature) {
|
||||
return windows_isprocessorfeaturepresent_.count(dwProcessorFeature);
|
||||
}
|
||||
@ -42,11 +69,7 @@ class FakeCpuAarch64 {
|
||||
void SetWindowsNativeSystemInfoProcessorRevision(WORD wProcessorRevision) {
|
||||
processor_revision_ = wProcessorRevision;
|
||||
}
|
||||
|
||||
private:
|
||||
std::set<DWORD> windows_isprocessorfeaturepresent_;
|
||||
WORD processor_revision_{};
|
||||
#endif // CPU_FEATURES_OS_WINDOWS
|
||||
#endif
|
||||
};
|
||||
|
||||
static FakeCpuAarch64* g_fake_cpu_instance = nullptr;
|
||||
@ -56,7 +79,18 @@ static FakeCpuAarch64& cpu() {
|
||||
return *g_fake_cpu_instance;
|
||||
}
|
||||
|
||||
#if defined(CPU_FEATURES_OS_WINDOWS)
|
||||
// Define OS dependent mock functions
|
||||
#if defined(CPU_FEATURES_OS_LINUX)
|
||||
// No particular functions to implement for Linux as we use /proc/cpuinfo
|
||||
#elif defined(CPU_FEATURES_OS_MACOS)
|
||||
extern "C" bool GetDarwinSysCtlByName(const char* name) {
|
||||
return cpu().GetDarwinSysCtlByName(name);
|
||||
}
|
||||
|
||||
extern "C" int GetDarwinSysCtlByNameValue(const char* name) {
|
||||
return cpu().GetDarwinSysCtlByNameValue(name);
|
||||
}
|
||||
#elif defined(CPU_FEATURES_OS_WINDOWS)
|
||||
extern "C" bool GetWindowsIsProcessorFeaturePresent(DWORD dwProcessorFeature) {
|
||||
return cpu().GetWindowsIsProcessorFeaturePresent(dwProcessorFeature);
|
||||
}
|
||||
@ -64,7 +98,7 @@ extern "C" bool GetWindowsIsProcessorFeaturePresent(DWORD dwProcessorFeature) {
|
||||
extern "C" WORD GetWindowsNativeSystemInfoProcessorRevision() {
|
||||
return cpu().GetWindowsNativeSystemInfoProcessorRevision();
|
||||
}
|
||||
#endif // CPU_FEATURES_OS_WINDOWS
|
||||
#endif
|
||||
|
||||
namespace {
|
||||
|
||||
@ -80,7 +114,7 @@ class CpuidAarch64Test : public ::testing::Test {
|
||||
}
|
||||
};
|
||||
|
||||
TEST(CpuinfoAarch64Test, Aarch64FeaturesEnum) {
|
||||
TEST_F(CpuidAarch64Test, Aarch64FeaturesEnum) {
|
||||
const char* last_name = GetAarch64FeaturesEnumName(AARCH64_LAST_);
|
||||
EXPECT_STREQ(last_name, "unknown_feature");
|
||||
for (int i = static_cast<int>(AARCH64_FP);
|
||||
@ -93,10 +127,11 @@ TEST(CpuinfoAarch64Test, Aarch64FeaturesEnum) {
|
||||
}
|
||||
}
|
||||
|
||||
// OS dependent tests
|
||||
#if defined(CPU_FEATURES_OS_LINUX)
|
||||
void DisableHardwareCapabilities() { SetHardwareCapabilities(0, 0); }
|
||||
|
||||
TEST(CpuinfoAarch64Test, FromHardwareCap) {
|
||||
TEST_F(CpuidAarch64Test, FromHardwareCap) {
|
||||
ResetHwcaps();
|
||||
SetHardwareCapabilities(AARCH64_HWCAP_FP | AARCH64_HWCAP_AES, 0);
|
||||
GetEmptyFilesystem(); // disabling /proc/cpuinfo
|
||||
@ -135,7 +170,7 @@ TEST(CpuinfoAarch64Test, FromHardwareCap) {
|
||||
EXPECT_FALSE(info.features.pacg);
|
||||
}
|
||||
|
||||
TEST(CpuinfoAarch64Test, FromHardwareCap2) {
|
||||
TEST_F(CpuidAarch64Test, FromHardwareCap2) {
|
||||
ResetHwcaps();
|
||||
SetHardwareCapabilities(AARCH64_HWCAP_FP,
|
||||
AARCH64_HWCAP2_SVE2 | AARCH64_HWCAP2_BTI);
|
||||
@ -164,7 +199,7 @@ TEST(CpuinfoAarch64Test, FromHardwareCap2) {
|
||||
EXPECT_FALSE(info.features.rng);
|
||||
}
|
||||
|
||||
TEST(CpuinfoAarch64Test, ARMCortexA53) {
|
||||
TEST_F(CpuidAarch64Test, ARMCortexA53) {
|
||||
ResetHwcaps();
|
||||
auto& fs = GetEmptyFilesystem();
|
||||
fs.CreateFile("/proc/cpuinfo",
|
||||
@ -266,9 +301,68 @@ CPU revision : 3)");
|
||||
EXPECT_FALSE(info.features.smeb16b16);
|
||||
EXPECT_FALSE(info.features.smef16f16);
|
||||
}
|
||||
#endif // CPU_FEATURES_OS_LINUX
|
||||
#elif defined(CPU_FEATURES_OS_MACOS)
|
||||
TEST_F(CpuidAarch64Test, FromDarwinSysctlFromName) {
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.floatingpoint");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.neon");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.AdvSIMD_HPFPCvt");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm.FEAT_FP16");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm.FEAT_LSE");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.armv8_crc32");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm.FEAT_FHM");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA512");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm.FEAT_SHA3");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.amx_version");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.ucnormal_mem");
|
||||
cpu().SetDarwinSysCtlByName("hw.optional.arm64");
|
||||
|
||||
#if defined(CPU_FEATURES_OS_WINDOWS)
|
||||
cpu().SetDarwinSysCtlByNameValue("hw.cputype", 16777228);
|
||||
cpu().SetDarwinSysCtlByNameValue("hw.cpusubtype", 2);
|
||||
cpu().SetDarwinSysCtlByNameValue("hw.cpu64bit", 1);
|
||||
cpu().SetDarwinSysCtlByNameValue("hw.cpufamily", 458787763);
|
||||
cpu().SetDarwinSysCtlByNameValue("hw.cpusubfamily", 2);
|
||||
|
||||
const auto info = GetAarch64Info();
|
||||
|
||||
EXPECT_EQ(info.implementer, 0x100000C);
|
||||
EXPECT_EQ(info.variant, 2);
|
||||
EXPECT_EQ(info.part, 0x1B588BB3);
|
||||
EXPECT_EQ(info.revision, 2);
|
||||
|
||||
EXPECT_TRUE(info.features.fp);
|
||||
EXPECT_FALSE(info.features.asimd);
|
||||
EXPECT_FALSE(info.features.evtstrm);
|
||||
EXPECT_FALSE(info.features.aes);
|
||||
EXPECT_FALSE(info.features.pmull);
|
||||
EXPECT_FALSE(info.features.sha1);
|
||||
EXPECT_FALSE(info.features.sha2);
|
||||
EXPECT_TRUE(info.features.crc32);
|
||||
EXPECT_TRUE(info.features.atomics);
|
||||
EXPECT_TRUE(info.features.fphp);
|
||||
EXPECT_FALSE(info.features.asimdhp);
|
||||
EXPECT_FALSE(info.features.cpuid);
|
||||
EXPECT_FALSE(info.features.asimdrdm);
|
||||
EXPECT_FALSE(info.features.jscvt);
|
||||
EXPECT_FALSE(info.features.fcma);
|
||||
EXPECT_FALSE(info.features.lrcpc);
|
||||
EXPECT_FALSE(info.features.dcpop);
|
||||
EXPECT_TRUE(info.features.sha3);
|
||||
EXPECT_FALSE(info.features.sm3);
|
||||
EXPECT_FALSE(info.features.sm4);
|
||||
EXPECT_FALSE(info.features.asimddp);
|
||||
EXPECT_TRUE(info.features.sha512);
|
||||
EXPECT_FALSE(info.features.sve);
|
||||
EXPECT_TRUE(info.features.asimdfhm);
|
||||
EXPECT_FALSE(info.features.dit);
|
||||
EXPECT_FALSE(info.features.uscat);
|
||||
EXPECT_FALSE(info.features.ilrcpc);
|
||||
EXPECT_FALSE(info.features.flagm);
|
||||
EXPECT_FALSE(info.features.ssbs);
|
||||
EXPECT_FALSE(info.features.sb);
|
||||
EXPECT_FALSE(info.features.paca);
|
||||
EXPECT_FALSE(info.features.pacg);
|
||||
}
|
||||
#elif defined(CPU_FEATURES_OS_WINDOWS)
|
||||
TEST_F(CpuidAarch64Test, WINDOWS_AARCH64_RPI4) {
|
||||
cpu().SetWindowsNativeSystemInfoProcessorRevision(0x03);
|
||||
cpu().SetWindowsIsProcessorFeaturePresent(PF_ARM_VFP_32_REGISTERS_AVAILABLE);
|
||||
@ -292,6 +386,5 @@ TEST_F(CpuidAarch64Test, WINDOWS_AARCH64_RPI4) {
|
||||
EXPECT_FALSE(info.features.lrcpc);
|
||||
}
|
||||
#endif // CPU_FEATURES_OS_WINDOWS
|
||||
|
||||
} // namespace
|
||||
} // namespace cpu_features
|
||||
|
Loading…
x
Reference in New Issue
Block a user