diff options
Diffstat (limited to 'lib/spack/llnl/util/cpu/detect.py')
-rw-r--r-- | lib/spack/llnl/util/cpu/detect.py | 59 |
1 files changed, 45 insertions, 14 deletions
diff --git a/lib/spack/llnl/util/cpu/detect.py b/lib/spack/llnl/util/cpu/detect.py index c89f67c852..66b09f5e9e 100644 --- a/lib/spack/llnl/util/cpu/detect.py +++ b/lib/spack/llnl/util/cpu/detect.py @@ -1,4 +1,4 @@ -# Copyright 2013-2019 Lawrence Livermore National Security, LLC and other +# Copyright 2013-2020 Lawrence Livermore National Security, LLC and other # Spack Project Developers. See the top-level COPYRIGHT file for details. # # SPDX-License-Identifier: (Apache-2.0 OR MIT) @@ -13,6 +13,7 @@ import warnings import six from .microarchitecture import generic_microarchitecture, targets +from .schema import targets_json #: Mapping from operating systems to chain of commands #: to obtain a dictionary of raw info on the current cpu @@ -108,21 +109,37 @@ def sysctl_info_dict(): 'model': sysctl('-n', 'machdep.cpu.model'), 'model name': sysctl('-n', 'machdep.cpu.brand_string') } + return info - # Super hacky way to deal with slight representation differences - # Would be better to somehow consider these "identical" - if 'sse4.1' in info['flags']: - info['flags'] += ' sse4_1' - if 'sse4.2' in info['flags']: - info['flags'] += ' sse4_2' - if 'avx1.0' in info['flags']: - info['flags'] += ' avx' - if 'clfsopt' in info['flags']: - info['flags'] += ' clflushopt' - if 'xsave' in info['flags']: - info['flags'] += ' xsavec xsaveopt' - return info +def adjust_raw_flags(info): + """Adjust the flags detected on the system to homogenize + slightly different representations. + """ + # Flags detected on Darwin turned to their linux counterpart + flags = info.get('flags', []) + d2l = targets_json['conversions']['darwin_flags'] + for darwin_flag, linux_flag in d2l.items(): + if darwin_flag in flags: + info['flags'] += ' ' + linux_flag + + +def adjust_raw_vendor(info): + """Adjust the vendor field to make it human readable""" + if 'CPU implementer' not in info: + return + + # Mapping numeric codes to vendor (ARM). This list is a merge from + # different sources: + # + # https://github.com/karelzak/util-linux/blob/master/sys-utils/lscpu-arm.c + # https://developer.arm.com/docs/ddi0487/latest/arm-architecture-reference-manual-armv8-for-armv8-a-architecture-profile + # https://github.com/gcc-mirror/gcc/blob/master/gcc/config/aarch64/aarch64-cores.def + # https://patchwork.kernel.org/patch/10524949/ + arm_vendors = targets_json['conversions']['arm_vendors'] + arm_code = info['CPU implementer'] + if arm_code in arm_vendors: + info['CPU implementer'] = arm_vendors[arm_code] def raw_info_dictionary(): @@ -139,6 +156,8 @@ def raw_info_dictionary(): warnings.warn(str(e)) if info: + adjust_raw_flags(info) + adjust_raw_vendor(info) break return info @@ -223,3 +242,15 @@ def compatibility_check_for_x86_64(info, target): return (target == arch_root or arch_root in target.ancestors) \ and (target.vendor == vendor or target.vendor == 'generic') \ and target.features.issubset(features) + + +@compatibility_check(architecture_family='aarch64') +def compatibility_check_for_aarch64(info, target): + basename = 'aarch64' + features = set(info.get('Features', '').split()) + vendor = info.get('CPU implementer', 'generic') + + arch_root = targets[basename] + return (target == arch_root or arch_root in target.ancestors) \ + and (target.vendor == vendor or target.vendor == 'generic') \ + and target.features.issubset(features) |