diff options
author | Massimiliano Culpo <massimiliano.culpo@gmail.com> | 2020-06-25 18:18:48 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-06-25 11:18:48 -0500 |
commit | 14599f09be6cd6eac4dc4d9d2d01a0ad001ae3f5 (patch) | |
tree | 62b50d312323e206a11a0d8c7b4db58024768439 | |
parent | a31c115d799c364f60e82fed02ba1fcc80bd935f (diff) | |
download | spack-14599f09be6cd6eac4dc4d9d2d01a0ad001ae3f5.tar.gz spack-14599f09be6cd6eac4dc4d9d2d01a0ad001ae3f5.tar.bz2 spack-14599f09be6cd6eac4dc4d9d2d01a0ad001ae3f5.tar.xz spack-14599f09be6cd6eac4dc4d9d2d01a0ad001ae3f5.zip |
Separate Apple Clang from LLVM Clang (#17110)
* Separate Apple Clang from LLVM Clang
Apple Clang is a compiler of its own. All places
referring to "-apple" suffix have been updated.
* Hack to use a dash in 'apple-clang'
To be able to use autodoc from Sphinx we need
a valid Python name for the module that contains
Apple's Clang code.
* Updated packages to account for the existence of apple-clang
Co-authored-by: Adam J. Stewart <ajstewart426@gmail.com>
* Added unit test for XCode related functions
Co-authored-by: Gregory Becker <becker33@llnl.gov>
Co-authored-by: Adam J. Stewart <ajstewart426@gmail.com>
80 files changed, 537 insertions, 351 deletions
diff --git a/etc/spack/defaults/darwin/packages.yaml b/etc/spack/defaults/darwin/packages.yaml index 1150f6bab7..b2bcd560c6 100644 --- a/etc/spack/defaults/darwin/packages.yaml +++ b/etc/spack/defaults/darwin/packages.yaml @@ -15,7 +15,11 @@ # ------------------------------------------------------------------------- packages: all: - compiler: [clang, gcc, intel] + compiler: + - apple-clang + - clang + - gcc + - intel providers: elf: [libelf] unwind: [apple-libunwind] diff --git a/lib/spack/docs/basic_usage.rst b/lib/spack/docs/basic_usage.rst index 8acebeb0e6..93c5858d93 100644 --- a/lib/spack/docs/basic_usage.rst +++ b/lib/spack/docs/basic_usage.rst @@ -627,8 +627,8 @@ output metadata on specs and all dependencies as json: "target": "x86_64" }, "compiler": { - "name": "clang", - "version": "10.0.0-apple" + "name": "apple-clang", + "version": "10.0.0" }, "namespace": "builtin", "parameters": { diff --git a/lib/spack/docs/getting_started.rst b/lib/spack/docs/getting_started.rst index 1fbddbd4a9..226b1f0883 100644 --- a/lib/spack/docs/getting_started.rst +++ b/lib/spack/docs/getting_started.rst @@ -478,7 +478,7 @@ Fortran. cxx: /usr/bin/clang++ f77: /path/to/bin/gfortran fc: /path/to/bin/gfortran - spec: clang@11.0.0-apple + spec: apple-clang@11.0.0 If you used Spack to install GCC, you can get the installation prefix by diff --git a/lib/spack/docs/packaging_guide.rst b/lib/spack/docs/packaging_guide.rst index 533036852b..d3a888b1fc 100644 --- a/lib/spack/docs/packaging_guide.rst +++ b/lib/spack/docs/packaging_guide.rst @@ -1675,15 +1675,15 @@ can see the patches that would be applied to ``m4``:: Concretized -------------------------------- - m4@1.4.18%clang@9.0.0-apple patches=3877ab548f88597ab2327a2230ee048d2d07ace1062efe81fc92e91b7f39cd00,c0a408fbffb7255fcc75e26bd8edab116fc81d216bfd18b473668b7739a4158e,fc9b61654a3ba1a8d6cd78ce087e7c96366c290bc8d2c299f09828d793b853c8 +sigsegv arch=darwin-highsierra-x86_64 - ^libsigsegv@2.11%clang@9.0.0-apple arch=darwin-highsierra-x86_64 + m4@1.4.18%apple-clang@9.0.0 patches=3877ab548f88597ab2327a2230ee048d2d07ace1062efe81fc92e91b7f39cd00,c0a408fbffb7255fcc75e26bd8edab116fc81d216bfd18b473668b7739a4158e,fc9b61654a3ba1a8d6cd78ce087e7c96366c290bc8d2c299f09828d793b853c8 +sigsegv arch=darwin-highsierra-x86_64 + ^libsigsegv@2.11%apple-clang@9.0.0 arch=darwin-highsierra-x86_64 You can also see patches that have been applied to installed packages with ``spack find -v``:: $ spack find -v m4 ==> 1 installed package - -- darwin-highsierra-x86_64 / clang@9.0.0-apple ----------------- + -- darwin-highsierra-x86_64 / apple-clang@9.0.0 ----------------- m4@1.4.18 patches=3877ab548f88597ab2327a2230ee048d2d07ace1062efe81fc92e91b7f39cd00,c0a408fbffb7255fcc75e26bd8edab116fc81d216bfd18b473668b7739a4158e,fc9b61654a3ba1a8d6cd78ce087e7c96366c290bc8d2c299f09828d793b853c8 +sigsegv .. _cmd-spack-resource: @@ -1713,7 +1713,7 @@ wonder where the extra boost patches are coming from:: $ spack spec dealii ^boost@1.68.0 ^hdf5+fortran | grep '\^boost' ^boost@1.68.0 - ^boost@1.68.0%clang@9.0.0-apple+atomic+chrono~clanglibcpp cxxstd=default +date_time~debug+exception+filesystem+graph~icu+iostreams+locale+log+math~mpi+multithreaded~numpy patches=2ab6c72d03dec6a4ae20220a9dfd5c8c572c5294252155b85c6874d97c323199,b37164268f34f7133cbc9a4066ae98fda08adf51e1172223f6a969909216870f ~pic+program_options~python+random+regex+serialization+shared+signals~singlethreaded+system~taggedlayout+test+thread+timer~versionedlayout+wave arch=darwin-highsierra-x86_64 + ^boost@1.68.0%apple-clang@9.0.0+atomic+chrono~clanglibcpp cxxstd=default +date_time~debug+exception+filesystem+graph~icu+iostreams+locale+log+math~mpi+multithreaded~numpy patches=2ab6c72d03dec6a4ae20220a9dfd5c8c572c5294252155b85c6874d97c323199,b37164268f34f7133cbc9a4066ae98fda08adf51e1172223f6a969909216870f ~pic+program_options~python+random+regex+serialization+shared+signals~singlethreaded+system~taggedlayout+test+thread+timer~versionedlayout+wave arch=darwin-highsierra-x86_64 $ spack resource show b37164268 b37164268f34f7133cbc9a4066ae98fda08adf51e1172223f6a969909216870f path: /home/spackuser/src/spack/var/spack/repos/builtin/packages/dealii/boost_1.68.0.patch diff --git a/lib/spack/docs/repositories.rst b/lib/spack/docs/repositories.rst index 6c2050a4be..4a2c163886 100644 --- a/lib/spack/docs/repositories.rst +++ b/lib/spack/docs/repositories.rst @@ -280,16 +280,16 @@ you install it, you can use ``spack spec -N``: Concretized -------------------------------- - builtin.hdf5@1.10.0-patch1%clang@7.0.2-apple+cxx~debug+fortran+mpi+shared~szip~threadsafe arch=darwin-elcapitan-x86_64 - ^builtin.openmpi@2.0.1%clang@7.0.2-apple~mxm~pmi~psm~psm2~slurm~sqlite3~thread_multiple~tm~verbs+vt arch=darwin-elcapitan-x86_64 - ^builtin.hwloc@1.11.4%clang@7.0.2-apple arch=darwin-elcapitan-x86_64 - ^builtin.libpciaccess@0.13.4%clang@7.0.2-apple arch=darwin-elcapitan-x86_64 - ^builtin.libtool@2.4.6%clang@7.0.2-apple arch=darwin-elcapitan-x86_64 - ^builtin.m4@1.4.17%clang@7.0.2-apple+sigsegv arch=darwin-elcapitan-x86_64 - ^builtin.libsigsegv@2.10%clang@7.0.2-apple arch=darwin-elcapitan-x86_64 - ^builtin.pkg-config@0.29.1%clang@7.0.2-apple+internal_glib arch=darwin-elcapitan-x86_64 - ^builtin.util-macros@1.19.0%clang@7.0.2-apple arch=darwin-elcapitan-x86_64 - ^builtin.zlib@1.2.8%clang@7.0.2-apple+pic arch=darwin-elcapitan-x86_64 + builtin.hdf5@1.10.0-patch1%apple-clang@7.0.2+cxx~debug+fortran+mpi+shared~szip~threadsafe arch=darwin-elcapitan-x86_64 + ^builtin.openmpi@2.0.1%apple-clang@7.0.2~mxm~pmi~psm~psm2~slurm~sqlite3~thread_multiple~tm~verbs+vt arch=darwin-elcapitan-x86_64 + ^builtin.hwloc@1.11.4%apple-clang@7.0.2 arch=darwin-elcapitan-x86_64 + ^builtin.libpciaccess@0.13.4%apple-clang@7.0.2 arch=darwin-elcapitan-x86_64 + ^builtin.libtool@2.4.6%apple-clang@7.0.2 arch=darwin-elcapitan-x86_64 + ^builtin.m4@1.4.17%apple-clang@7.0.2+sigsegv arch=darwin-elcapitan-x86_64 + ^builtin.libsigsegv@2.10%apple-clang@7.0.2 arch=darwin-elcapitan-x86_64 + ^builtin.pkg-config@0.29.1%apple-clang@7.0.2+internal_glib arch=darwin-elcapitan-x86_64 + ^builtin.util-macros@1.19.0%apple-clang@7.0.2 arch=darwin-elcapitan-x86_64 + ^builtin.zlib@1.2.8%apple-clang@7.0.2+pic arch=darwin-elcapitan-x86_64 .. warning:: diff --git a/lib/spack/llnl/util/cpu/microarchitecture.py b/lib/spack/llnl/util/cpu/microarchitecture.py index f507837f89..284bfebb7e 100644 --- a/lib/spack/llnl/util/cpu/microarchitecture.py +++ b/lib/spack/llnl/util/cpu/microarchitecture.py @@ -204,10 +204,22 @@ class Microarchitecture(object): compiler (str): name of the compiler to be used version (str): version of the compiler to be used """ - # If we don't have information on compiler return an empty string - if compiler not in self.compilers: + # If we don't have information on compiler at all + # return an empty string + if compiler not in self.family.compilers: return '' + # If we have information but it stops before this + # microarchitecture, fall back to the best known target + if compiler not in self.compilers: + best_target = [ + x for x in self.ancestors if compiler in x.compilers + ][0] + msg = ("'{0}' compiler is known to optimize up to the '{1}'" + " microarchitecture in the '{2}' architecture family") + msg = msg.format(compiler, best_target, best_target.family) + raise UnsupportedMicroarchitecture(msg) + # If we have information on this compiler we need to check the # version being used compiler_info = self.compilers[compiler] @@ -219,15 +231,10 @@ class Microarchitecture(object): def satisfies_constraint(entry, version): min_version, max_version = entry['versions'].split(':') - # Check version suffixes - min_version, min_suffix = version_components(min_version) - max_version, max_suffix = version_components(max_version) - version, suffix = version_components(version) - - # If the suffixes are not all equal there's no match - if ((suffix != min_suffix and min_version) or - (suffix != max_suffix and max_version)): - return False + # Extract numeric part of the version + min_version, _ = version_components(min_version) + max_version, _ = version_components(max_version) + version, _ = version_components(version) # Assume compiler versions fit into semver tuplify = lambda x: tuple(int(y) for y in x.split('.')) diff --git a/lib/spack/llnl/util/cpu/microarchitectures.json b/lib/spack/llnl/util/cpu/microarchitectures.json index 51411d4a24..e94146bf85 100644 --- a/lib/spack/llnl/util/cpu/microarchitectures.json +++ b/lib/spack/llnl/util/cpu/microarchitectures.json @@ -61,12 +61,14 @@ "flags": "-march={name} -mtune={name}" } ], - "clang": [ + "apple-clang": [ { - "versions": "0.0.0-apple:", + "versions": ":", "name": "x86-64", "flags": "-march={name}" - }, + } + ], + "clang": [ { "versions": ":", "name": "x86-64", diff --git a/lib/spack/spack/ci.py b/lib/spack/spack/ci.py index ce74abf29c..230f25ccee 100644 --- a/lib/spack/spack/ci.py +++ b/lib/spack/spack/ci.py @@ -345,18 +345,18 @@ def compute_spec_deps(spec_list): ], "specs": [ { - "root_spec": "readline@7.0%clang@9.1.0-apple arch=darwin-...", - "spec": "readline@7.0%clang@9.1.0-apple arch=darwin-highs...", + "root_spec": "readline@7.0%apple-clang@9.1.0 arch=darwin-...", + "spec": "readline@7.0%apple-clang@9.1.0 arch=darwin-highs...", "label": "readline/ip6aiun" }, { - "root_spec": "readline@7.0%clang@9.1.0-apple arch=darwin-...", - "spec": "ncurses@6.1%clang@9.1.0-apple arch=darwin-highsi...", + "root_spec": "readline@7.0%apple-clang@9.1.0 arch=darwin-...", + "spec": "ncurses@6.1%apple-clang@9.1.0 arch=darwin-highsi...", "label": "ncurses/y43rifz" }, { - "root_spec": "readline@7.0%clang@9.1.0-apple arch=darwin-...", - "spec": "pkgconf@1.5.4%clang@9.1.0-apple arch=darwin-high...", + "root_spec": "readline@7.0%apple-clang@9.1.0 arch=darwin-...", + "spec": "pkgconf@1.5.4%apple-clang@9.1.0 arch=darwin-high...", "label": "pkgconf/eg355zb" } ] diff --git a/lib/spack/spack/compilers/__init__.py b/lib/spack/spack/compilers/__init__.py index 771459f7f3..dfa750cc4d 100644 --- a/lib/spack/spack/compilers/__init__.py +++ b/lib/spack/spack/compilers/__init__.py @@ -245,7 +245,9 @@ def supported_compilers(): See available_compilers() to get a list of all the available versions of supported compilers. """ - return sorted(name for name in + # Hack to be able to call the compiler `apple-clang` while still + # using a valid python name for the module + return sorted(name if name != 'apple_clang' else 'apple-clang' for name in llnl.util.lang.list_modules(spack.paths.compilers_path)) @@ -469,7 +471,13 @@ def class_for_compiler_name(compiler_name): """Given a compiler module name, get the corresponding Compiler class.""" assert(supported(compiler_name)) - file_path = os.path.join(spack.paths.compilers_path, compiler_name + ".py") + # Hack to be able to call the compiler `apple-clang` while still + # using a valid python name for the module + module_name = compiler_name + if compiler_name == 'apple-clang': + module_name = compiler_name.replace('-', '_') + + file_path = os.path.join(spack.paths.compilers_path, module_name + ".py") compiler_mod = simp.load_source(_imported_compilers_module, file_path) cls = getattr(compiler_mod, mod_to_class(compiler_name)) @@ -662,7 +670,7 @@ def make_compiler_list(detected_versions): operating_system, compiler_name, version = cmp_id compiler_cls = spack.compilers.class_for_compiler_name(compiler_name) spec = spack.spec.CompilerSpec(compiler_cls.name, version) - paths = [paths.get(l, None) for l in ('cc', 'cxx', 'f77', 'fc')] + paths = [paths.get(x, None) for x in ('cc', 'cxx', 'f77', 'fc')] target = cpu.host() compiler = compiler_cls( spec, operating_system, str(target.family), paths @@ -716,6 +724,8 @@ def is_mixed_toolchain(compiler): toolchains.add(compiler_cls.__name__) if len(toolchains) > 1: + if toolchains == set(['Clang', 'AppleClang']): + return False tty.debug("[TOOLCHAINS] {0}".format(toolchains)) return True diff --git a/lib/spack/spack/compilers/apple_clang.py b/lib/spack/spack/compilers/apple_clang.py new file mode 100644 index 0000000000..8ef58550ea --- /dev/null +++ b/lib/spack/spack/compilers/apple_clang.py @@ -0,0 +1,165 @@ +# 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) +import os.path +import re +import shutil + +import llnl.util.tty as tty +import llnl.util.lang +import spack.compiler +import spack.compilers.clang +import spack.util.executable +import spack.version + + +class AppleClang(spack.compilers.clang.Clang): + openmp_flag = "-Xpreprocessor -fopenmp" + + @classmethod + @llnl.util.lang.memoized + def extract_version_from_output(cls, output): + ver = 'unknown' + match = re.search( + # Apple's LLVM compiler has its own versions, so suffix them. + r'^Apple (?:LLVM|clang) version ([^ )]+)', output + ) + if match: + ver = match.group(match.lastindex) + return ver + + @property + def cxx11_flag(self): + # Adapted from CMake's AppleClang-CXX rules + # Spack's AppleClang detection only valid from Xcode >= 4.6 + if self.version < spack.version.ver('4.0.0'): + raise spack.compiler.UnsupportedCompilerFlag( + self, "the C++11 standard", "cxx11_flag", "Xcode < 4.0.0" + ) + return "-std=c++11" + + @property + def cxx14_flag(self): + # Adapted from CMake's rules for AppleClang + if self.version < spack.version.ver('5.1.0'): + raise spack.compiler.UnsupportedCompilerFlag( + self, "the C++14 standard", "cxx14_flag", "Xcode < 5.1.0" + ) + elif self.version < spack.version.ver('6.1.0'): + return "-std=c++1y" + + return "-std=c++14" + + @property + def cxx17_flag(self): + # Adapted from CMake's rules for AppleClang + if self.version < spack.version.ver('6.1.0'): + raise spack.compiler.UnsupportedCompilerFlag( + self, "the C++17 standard", "cxx17_flag", "Xcode < 6.1.0" + ) + return "-std=c++1z" + + def setup_custom_environment(self, pkg, env): + """Set the DEVELOPER_DIR environment for the Xcode toolchain. + + On macOS, not all buildsystems support querying CC and CXX for the + compilers to use and instead query the Xcode toolchain for what + compiler to run. This side-steps the spack wrappers. In order to inject + spack into this setup, we need to copy (a subset of) Xcode.app and + replace the compiler executables with symlinks to the spack wrapper. + Currently, the stage is used to store the Xcode.app copies. We then set + the 'DEVELOPER_DIR' environment variables to cause the xcrun and + related tools to use this Xcode.app. + """ + super(AppleClang, self).setup_custom_environment(pkg, env) + + if not pkg.use_xcode: + # if we do it for all packages, we get into big troubles with MPI: + # filter_compilers(self) will use mockup XCode compilers on macOS + # with Clang. Those point to Spack's compiler wrappers and + # consequently render MPI non-functional outside of Spack. + return + + # Use special XCode versions of compiler wrappers when using XCode + # Overwrites build_environment's setting of SPACK_CC and SPACK_CXX + xcrun = spack.util.executable.Executable('xcrun') + xcode_clang = xcrun('-f', 'clang', output=str).strip() + xcode_clangpp = xcrun('-f', 'clang++', output=str).strip() + env.set('SPACK_CC', xcode_clang, force=True) + env.set('SPACK_CXX', xcode_clangpp, force=True) + + xcode_select = spack.util.executable.Executable('xcode-select') + + # Get the path of the active developer directory + real_root = xcode_select('--print-path', output=str).strip() + + # The path name can be used to determine whether the full Xcode suite + # or just the command-line tools are installed + if real_root.endswith('Developer'): + # The full Xcode suite is installed + pass + else: + if real_root.endswith('CommandLineTools'): + # Only the command-line tools are installed + msg = 'It appears that you have the Xcode command-line tools ' + msg += 'but not the full Xcode suite installed.\n' + + else: + # Xcode is not installed + msg = 'It appears that you do not have Xcode installed.\n' + + msg += 'In order to use Spack to build the requested application, ' + msg += 'you need the full Xcode suite. It can be installed ' + msg += 'through the App Store. Make sure you launch the ' + msg += 'application and accept the license agreement.\n' + + raise OSError(msg) + + real_root = os.path.dirname(os.path.dirname(real_root)) + developer_root = os.path.join(spack.stage.get_stage_root(), + 'xcode-select', + self.name, + str(self.version)) + xcode_link = os.path.join(developer_root, 'Xcode.app') + + if not os.path.exists(developer_root): + tty.warn('Copying Xcode from %s to %s in order to add spack ' + 'wrappers to it. Please do not interrupt.' + % (real_root, developer_root)) + + # We need to make a new Xcode.app instance, but with symlinks to + # the spack wrappers for the compilers it ships. This is necessary + # because some projects insist on just asking xcrun and related + # tools where the compiler runs. These tools are very hard to trick + # as they do realpath and end up ignoring the symlinks in a + # "softer" tree of nothing but symlinks in the right places. + shutil.copytree( + real_root, developer_root, symlinks=True, + ignore=shutil.ignore_patterns( + 'AppleTV*.platform', 'Watch*.platform', 'iPhone*.platform', + 'Documentation', 'swift*' + )) + + real_dirs = [ + 'Toolchains/XcodeDefault.xctoolchain/usr/bin', + 'usr/bin', + ] + + bins = ['c++', 'c89', 'c99', 'cc', 'clang', 'clang++', 'cpp'] + + for real_dir in real_dirs: + dev_dir = os.path.join(developer_root, + 'Contents', + 'Developer', + real_dir) + for fname in os.listdir(dev_dir): + if fname in bins: + os.unlink(os.path.join(dev_dir, fname)) + os.symlink( + os.path.join(spack.paths.build_env_path, 'cc'), + os.path.join(dev_dir, fname)) + + os.symlink(developer_root, xcode_link) + + env.set('DEVELOPER_DIR', xcode_link) diff --git a/lib/spack/spack/compilers/clang.py b/lib/spack/spack/compilers/clang.py index 846c3609dc..f158ff3276 100644 --- a/lib/spack/spack/compilers/clang.py +++ b/lib/spack/spack/compilers/clang.py @@ -4,17 +4,11 @@ # SPDX-License-Identifier: (Apache-2.0 OR MIT) import re -import os import sys -from shutil import copytree, ignore_patterns import llnl.util.lang -import llnl.util.tty as tty -import spack.paths -import spack.stage from spack.compiler import Compiler, UnsupportedCompilerFlag -from spack.util.executable import Executable from spack.version import ver @@ -89,87 +83,40 @@ class Clang(Compiler): return link_paths @property - def is_apple(self): - ver_string = str(self.version) - return ver_string.endswith('-apple') - - @property def verbose_flag(self): return "-v" - @property - def openmp_flag(self): - if self.is_apple: - return "-Xpreprocessor -fopenmp" - else: - return "-fopenmp" + openmp_flag = "-fopenmp" @property def cxx11_flag(self): - if self.is_apple: - # Adapted from CMake's AppleClang-CXX rules - # Spack's AppleClang detection only valid from Xcode >= 4.6 - if self.version < ver('4.0.0'): - raise UnsupportedCompilerFlag(self, - "the C++11 standard", - "cxx11_flag", - "Xcode < 4.0.0") - else: - return "-std=c++11" - else: - if self.version < ver('3.3'): - raise UnsupportedCompilerFlag(self, - "the C++11 standard", - "cxx11_flag", - "< 3.3") - else: - return "-std=c++11" + if self.version < ver('3.3'): + raise UnsupportedCompilerFlag( + self, "the C++11 standard", "cxx11_flag", "< 3.3" + ) + return "-std=c++11" @property def cxx14_flag(self): - if self.is_apple: - # Adapted from CMake's rules for AppleClang - if self.version < ver('5.1.0'): - raise UnsupportedCompilerFlag(self, - "the C++14 standard", - "cxx14_flag", - "Xcode < 5.1.0") - elif self.version < ver('6.1.0'): - return "-std=c++1y" - else: - return "-std=c++14" - else: - if self.version < ver('3.4'): - raise UnsupportedCompilerFlag(self, - "the C++14 standard", - "cxx14_flag", - "< 3.5") - elif self.version < ver('3.5'): - return "-std=c++1y" - else: - return "-std=c++14" + if self.version < ver('3.4'): + raise UnsupportedCompilerFlag( + self, "the C++14 standard", "cxx14_flag", "< 3.5" + ) + elif self.version < ver('3.5'): + return "-std=c++1y" + + return "-std=c++14" @property def cxx17_flag(self): - if self.is_apple: - # Adapted from CMake's rules for AppleClang - if self.version < ver('6.1.0'): - raise UnsupportedCompilerFlag(self, - "the C++17 standard", - "cxx17_flag", - "Xcode < 6.1.0") - else: - return "-std=c++1z" - else: - if self.version < ver('3.5'): - raise UnsupportedCompilerFlag(self, - "the C++17 standard", - "cxx17_flag", - "< 3.5") - elif self.version < ver('5.0'): - return "-std=c++1z" - else: - return "-std=c++17" + if self.version < ver('3.5'): + raise UnsupportedCompilerFlag( + self, "the C++17 standard", "cxx17_flag", "< 3.5" + ) + elif self.version < ver('5.0'): + return "-std=c++1z" + + return "-std=c++17" @property def c99_flag(self): @@ -207,9 +154,10 @@ class Clang(Compiler): @llnl.util.lang.memoized def extract_version_from_output(cls, output): ver = 'unknown' + if 'Apple' in output: + return ver + match = re.search( - # Apple's LLVM compiler has its own versions, so suffix them. - r'^Apple (?:LLVM|clang) version ([^ )]+)|' # Normal clang compiler versions are left as-is r'clang version ([^ )]+)-svn[~.\w\d-]*|' # Don't include hyphenated patch numbers in the version @@ -219,8 +167,7 @@ class Clang(Compiler): output ) if match: - suffix = '-apple' if match.lastindex == 1 else '' - ver = match.group(match.lastindex) + suffix + ver = match.group(match.lastindex) return ver @classmethod @@ -235,107 +182,3 @@ class Clang(Compiler): @classmethod def f77_version(cls, f77): return cls.fc_version(f77) - - def setup_custom_environment(self, pkg, env): - """Set the DEVELOPER_DIR environment for the Xcode toolchain. - - On macOS, not all buildsystems support querying CC and CXX for the - compilers to use and instead query the Xcode toolchain for what - compiler to run. This side-steps the spack wrappers. In order to inject - spack into this setup, we need to copy (a subset of) Xcode.app and - replace the compiler executables with symlinks to the spack wrapper. - Currently, the stage is used to store the Xcode.app copies. We then set - the 'DEVELOPER_DIR' environment variables to cause the xcrun and - related tools to use this Xcode.app. - """ - super(Clang, self).setup_custom_environment(pkg, env) - - if not self.is_apple or not pkg.use_xcode: - # if we do it for all packages, we get into big troubles with MPI: - # filter_compilers(self) will use mockup XCode compilers on macOS - # with Clang. Those point to Spack's compiler wrappers and - # consequently render MPI non-functional outside of Spack. - return - - # Use special XCode versions of compiler wrappers when using XCode - # Overwrites build_environment's setting of SPACK_CC and SPACK_CXX - xcrun = Executable('xcrun') - xcode_clang = xcrun('-f', 'clang', output=str).strip() - xcode_clangpp = xcrun('-f', 'clang++', output=str).strip() - env.set('SPACK_CC', xcode_clang, force=True) - env.set('SPACK_CXX', xcode_clangpp, force=True) - - xcode_select = Executable('xcode-select') - - # Get the path of the active developer directory - real_root = xcode_select('--print-path', output=str).strip() - - # The path name can be used to determine whether the full Xcode suite - # or just the command-line tools are installed - if real_root.endswith('Developer'): - # The full Xcode suite is installed - pass - else: - if real_root.endswith('CommandLineTools'): - # Only the command-line tools are installed - msg = 'It appears that you have the Xcode command-line tools ' - msg += 'but not the full Xcode suite installed.\n' - - else: - # Xcode is not installed - msg = 'It appears that you do not have Xcode installed.\n' - - msg += 'In order to use Spack to build the requested application, ' - msg += 'you need the full Xcode suite. It can be installed ' - msg += 'through the App Store. Make sure you launch the ' - msg += 'application and accept the license agreement.\n' - - raise OSError(msg) - - real_root = os.path.dirname(os.path.dirname(real_root)) - developer_root = os.path.join(spack.stage.get_stage_root(), - 'xcode-select', - self.name, - str(self.version)) - xcode_link = os.path.join(developer_root, 'Xcode.app') - - if not os.path.exists(developer_root): - tty.warn('Copying Xcode from %s to %s in order to add spack ' - 'wrappers to it. Please do not interrupt.' - % (real_root, developer_root)) - - # We need to make a new Xcode.app instance, but with symlinks to - # the spack wrappers for the compilers it ships. This is necessary - # because some projects insist on just asking xcrun and related - # tools where the compiler runs. These tools are very hard to trick - # as they do realpath and end up ignoring the symlinks in a - # "softer" tree of nothing but symlinks in the right places. - copytree(real_root, developer_root, symlinks=True, - ignore=ignore_patterns('AppleTV*.platform', - 'Watch*.platform', - 'iPhone*.platform', - 'Documentation', - 'swift*')) - - real_dirs = [ - 'Toolchains/XcodeDefault.xctoolchain/usr/bin', - 'usr/bin', - ] - - bins = ['c++', 'c89', 'c99', 'cc', 'clang', 'clang++', 'cpp'] - - for real_dir in real_dirs: - dev_dir = os.path.join(developer_root, - 'Contents', - 'Developer', - real_dir) - for fname in os.listdir(dev_dir): - if fname in bins: - os.unlink(os.path.join(dev_dir, fname)) - os.symlink( - os.path.join(spack.paths.build_env_path, 'cc'), - os.path.join(dev_dir, fname)) - - os.symlink(developer_root, xcode_link) - - env.set('DEVELOPER_DIR', xcode_link) diff --git a/lib/spack/spack/spec.py b/lib/spack/spack/spec.py index b09d72003e..b23142e101 100644 --- a/lib/spack/spack/spec.py +++ b/lib/spack/spack/spec.py @@ -1448,8 +1448,8 @@ class Spec(object): 'target': 'x86_64', }, 'compiler': { - 'name': 'clang', - 'version': '10.0.0-apple', + 'name': 'apple-clang', + 'version': '10.0.0', }, 'namespace': 'builtin', 'parameters': { @@ -1554,8 +1554,8 @@ class Spec(object): 'target': 'x86_64', }, 'compiler': { - 'name': 'clang', - 'version': '10.0.0-apple', + 'name': 'apple-clang', + 'version': '10.0.0', }, 'namespace': 'builtin', 'parameters': { diff --git a/lib/spack/spack/test/architecture.py b/lib/spack/spack/test/architecture.py index 48cec134d2..80d3fc72c0 100644 --- a/lib/spack/spack/test/architecture.py +++ b/lib/spack/spack/test/architecture.py @@ -176,8 +176,8 @@ def test_arch_spec_container_semantic(item, architecture_str): # Check mixed toolchains ('clang@8.0.0', 'broadwell', ''), ('clang@3.5', 'x86_64', '-march=x86-64 -mtune=generic'), - # Check clang compilers with 'apple' suffix - ('clang@9.1.0-apple', 'x86_64', '-march=x86-64') + # Check Apple's Clang compilers + ('apple-clang@9.1.0', 'x86_64', '-march=x86-64') ]) @pytest.mark.filterwarnings("ignore:microarchitecture specific") def test_optimization_flags( @@ -200,7 +200,7 @@ def test_optimization_flags( '-march=icelake-client -mtune=icelake-client'), # Check that the special case for Apple's clang is treated correctly # i.e. it won't try to detect the version again - (spack.spec.CompilerSpec('clang@9.1.0-apple'), None, 'x86_64', + (spack.spec.CompilerSpec('apple-clang@9.1.0'), None, 'x86_64', '-march=x86-64'), ]) def test_optimization_flags_with_custom_versions( diff --git a/lib/spack/spack/test/compilers/basics.py b/lib/spack/spack/test/compilers/basics.py index 32f298ae2b..825975b21a 100644 --- a/lib/spack/spack/test/compilers/basics.py +++ b/lib/spack/spack/test/compilers/basics.py @@ -7,6 +7,7 @@ import pytest import sys import os +import shutil from copy import copy from six import iteritems @@ -16,6 +17,8 @@ import llnl.util.filesystem as fs import spack.spec import spack.compiler import spack.compilers as compilers +import spack.spec +import spack.util.environment from spack.compiler import Compiler from spack.util.executable import ProcessError @@ -130,7 +133,7 @@ def test_compiler_flags_from_config_are_grouped(): # Utility function to test most flags. default_compiler_entry = { - 'spec': 'clang@2.0.0-apple', + 'spec': 'apple-clang@2.0.0', 'operating_system': 'foo-os', 'paths': { 'cc': 'cc-path', @@ -370,26 +373,27 @@ def test_cce_flags(): 'cce@1.0') -def test_clang_flags(): - # Apple Clang. +def test_apple_clang_flags(): supported_flag_test( - "openmp_flag", "-Xpreprocessor -fopenmp", "clang@2.0.0-apple") - unsupported_flag_test("cxx11_flag", "clang@2.0.0-apple") - supported_flag_test("cxx11_flag", "-std=c++11", "clang@4.0.0-apple") - unsupported_flag_test("cxx14_flag", "clang@5.0.0-apple") - supported_flag_test("cxx14_flag", "-std=c++1y", "clang@5.1.0-apple") - supported_flag_test("cxx14_flag", "-std=c++14", "clang@6.1.0-apple") - unsupported_flag_test("cxx17_flag", "clang@6.0.0-apple") - supported_flag_test("cxx17_flag", "-std=c++1z", "clang@6.1.0-apple") - supported_flag_test("c99_flag", "-std=c99", "clang@6.1.0-apple") - unsupported_flag_test("c11_flag", "clang@6.0.0-apple") - supported_flag_test("c11_flag", "-std=c11", "clang@6.1.0-apple") - supported_flag_test("cc_pic_flag", "-fPIC", "clang@2.0.0-apple") - supported_flag_test("cxx_pic_flag", "-fPIC", "clang@2.0.0-apple") - supported_flag_test("f77_pic_flag", "-fPIC", "clang@2.0.0-apple") - supported_flag_test("fc_pic_flag", "-fPIC", "clang@2.0.0-apple") - - # non-Apple Clang. + "openmp_flag", "-Xpreprocessor -fopenmp", "apple-clang@2.0.0" + ) + unsupported_flag_test("cxx11_flag", "apple-clang@2.0.0") + supported_flag_test("cxx11_flag", "-std=c++11", "apple-clang@4.0.0") + unsupported_flag_test("cxx14_flag", "apple-clang@5.0.0") + supported_flag_test("cxx14_flag", "-std=c++1y", "apple-clang@5.1.0") + supported_flag_test("cxx14_flag", "-std=c++14", "apple-clang@6.1.0") + unsupported_flag_test("cxx17_flag", "apple-clang@6.0.0") + supported_flag_test("cxx17_flag", "-std=c++1z", "apple-clang@6.1.0") + supported_flag_test("c99_flag", "-std=c99", "apple-clang@6.1.0") + unsupported_flag_test("c11_flag", "apple-clang@6.0.0") + supported_flag_test("c11_flag", "-std=c11", "apple-clang@6.1.0") + supported_flag_test("cc_pic_flag", "-fPIC", "apple-clang@2.0.0") + supported_flag_test("cxx_pic_flag", "-fPIC", "apple-clang@2.0.0") + supported_flag_test("f77_pic_flag", "-fPIC", "apple-clang@2.0.0") + supported_flag_test("fc_pic_flag", "-fPIC", "apple-clang@2.0.0") + + +def test_clang_flags(): supported_flag_test("version_argument", "--version", "clang@foo.bar") supported_flag_test("openmp_flag", "-fopenmp", "clang@3.3") unsupported_flag_test("cxx11_flag", "clang@3.2") @@ -713,3 +717,101 @@ fi except ProcessError: # Confirm environment does not change after failed call assert 'SPACK_TEST_CMP_ON' not in os.environ + + +def test_apple_clang_setup_environment(mock_executable, monkeypatch): + """Test a code path that is taken only if the package uses + Xcode on MacOS. + """ + class MockPackage(object): + use_xcode = False + + apple_clang_cls = spack.compilers.class_for_compiler_name('apple-clang') + compiler = apple_clang_cls( + spack.spec.CompilerSpec('apple-clang@11.0.0'), 'catalina', 'x86_64', [ + '/usr/bin/clang', '/usr/bin/clang++', None, None + ] + ) + env = spack.util.environment.EnvironmentModifications() + # Check a package that doesn't use xcode and ensure we don't add changes + # to the environment + pkg = MockPackage() + compiler.setup_custom_environment(pkg, env) + assert not env + + # Prepare mock executables to fake the Xcode environment + xcrun = mock_executable('xcrun', """ +if [[ "$2" == "clang" ]] ; then + echo "/Library/Developer/CommandLineTools/usr/bin/clang" +fi +if [[ "$2" == "clang++" ]] ; then + echo "/Library/Developer/CommandLineTools/usr/bin/clang++" +fi +""") + mock_executable('xcode-select', """ +echo "/Library/Developer" +""") + bin_dir = os.path.dirname(xcrun) + monkeypatch.setenv('PATH', bin_dir, prepend=os.pathsep) + + def noop(*args, **kwargs): + pass + + real_listdir = os.listdir + + def _listdir(path): + if not os.path.exists(path): + return [] + return real_listdir(path) + + # Set a few operations to noop + monkeypatch.setattr(shutil, 'copytree', noop) + monkeypatch.setattr(os, 'unlink', noop) + monkeypatch.setattr(os, 'symlink', noop) + monkeypatch.setattr(os, 'listdir', _listdir) + + # Qt is so far the only package that uses this code path, change + # introduced in https://github.com/spack/spack/pull/1832 + pkg.use_xcode = True + compiler.setup_custom_environment(pkg, env) + assert len(env) == 3 + assert env.env_modifications[0].name == 'SPACK_CC' + assert env.env_modifications[1].name == 'SPACK_CXX' + assert env.env_modifications[2].name == 'DEVELOPER_DIR' + + +@pytest.mark.parametrize('xcode_select_output', [ + '', '/Library/Developer/CommandLineTools' +]) +def test_xcode_not_available( + xcode_select_output, mock_executable, monkeypatch +): + # Prepare mock executables to fake the Xcode environment + xcrun = mock_executable('xcrun', """ + if [[ "$2" == "clang" ]] ; then + echo "/Library/Developer/CommandLineTools/usr/bin/clang" + fi + if [[ "$2" == "clang++" ]] ; then + echo "/Library/Developer/CommandLineTools/usr/bin/clang++" + fi + """) + mock_executable('xcode-select', """ + echo "{0}" + """.format(xcode_select_output)) + bin_dir = os.path.dirname(xcrun) + monkeypatch.setenv('PATH', bin_dir, prepend=os.pathsep) + # Prepare compiler + apple_clang_cls = spack.compilers.class_for_compiler_name('apple-clang') + compiler = apple_clang_cls( + spack.spec.CompilerSpec('apple-clang@11.0.0'), 'catalina', 'x86_64', [ + '/usr/bin/clang', '/usr/bin/clang++', None, None + ] + ) + env = spack.util.environment.EnvironmentModifications() + + class MockPackage(object): + use_xcode = True + + pkg = MockPackage() + with pytest.raises(OSError): + compiler.setup_custom_environment(pkg, env) diff --git a/lib/spack/spack/test/compilers/detection.py b/lib/spack/spack/test/compilers/detection.py index 90311ad2d3..b38cf89b5d 100644 --- a/lib/spack/spack/test/compilers/detection.py +++ b/lib/spack/spack/test/compilers/detection.py @@ -53,11 +53,22 @@ def test_cce_version_detection(version_str, expected_version): 'Target: x86_64-apple-darwin18.7.0\n' 'Thread model: posix\n' 'InstalledDir: /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin\n', # noqa - '11.0.0-apple'), + '11.0.0'), ('Apple LLVM version 7.0.2 (clang-700.1.81)\n' 'Target: x86_64-apple-darwin15.2.0\n' - 'Thread model: posix\n', '7.0.2-apple'), - # Other platforms + 'Thread model: posix\n', '7.0.2'), +]) +def test_apple_clang_version_detection( + version_str, expected_version +): + cls = spack.compilers.class_for_compiler_name('apple-clang') + version = cls.extract_version_from_output(version_str) + assert version == expected_version + + +@pytest.mark.regression('10191') +@pytest.mark.parametrize('version_str,expected_version', [ + # LLVM Clang ('clang version 6.0.1-svn334776-1~exp1~20181018152737.116 (branches/release_60)\n' # noqa 'Target: x86_64-pc-linux-gnu\n' 'Thread model: posix\n' diff --git a/lib/spack/spack/test/concretize.py b/lib/spack/spack/test/concretize.py index fd0e185168..cfe0748c4b 100644 --- a/lib/spack/spack/test/concretize.py +++ b/lib/spack/spack/test/concretize.py @@ -608,7 +608,7 @@ class TestConcretize(object): ('mpileaks%gcc@4.8', 'haswell'), ('mpileaks%gcc@5.3.0', 'broadwell'), # Apple's clang always falls back to x86-64 for now - ('mpileaks%clang@9.1.0-apple', 'x86_64') + ('mpileaks%apple-clang@9.1.0', 'x86_64') ]) @pytest.mark.regression('13361') def test_adjusting_default_target_based_on_compiler( diff --git a/lib/spack/spack/test/conftest.py b/lib/spack/spack/test/conftest.py index 1efdd6ba95..9a292821f5 100644 --- a/lib/spack/spack/test/conftest.py +++ b/lib/spack/spack/test/conftest.py @@ -1145,7 +1145,7 @@ def mock_executable(tmpdir): import jinja2 def _factory(name, output, subdir=('bin',)): - f = tmpdir.mkdir(*subdir).join(name) + f = tmpdir.ensure(*subdir, dir=True).join(name) t = jinja2.Template('#!/bin/bash\n{{ output }}\n') f.write(t.render(output=output)) f.chmod(0o755) diff --git a/lib/spack/spack/test/data/config/compilers.yaml b/lib/spack/spack/test/data/config/compilers.yaml index 7aec138473..3a2db05e72 100644 --- a/lib/spack/spack/test/data/config/compilers.yaml +++ b/lib/spack/spack/test/data/config/compilers.yaml @@ -127,7 +127,7 @@ compilers: cxxflags: -O3 modules: 'None' - compiler: - spec: clang@9.1.0-apple + spec: apple-clang@9.1.0 operating_system: elcapitan paths: cc: /path/to/clang diff --git a/var/spack/repos/builtin/packages/allpaths-lg/package.py b/var/spack/repos/builtin/packages/allpaths-lg/package.py index 6ebca2eee6..b0bb49b3a1 100644 --- a/var/spack/repos/builtin/packages/allpaths-lg/package.py +++ b/var/spack/repos/builtin/packages/allpaths-lg/package.py @@ -18,6 +18,7 @@ class AllpathsLg(AutotoolsPackage): # compiles with gcc 4.7.0 to 4.9.4) conflicts('%gcc@:4.6.4,5.1.0:') conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%intel') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/aluminum/package.py b/var/spack/repos/builtin/packages/aluminum/package.py index 5edc4c3792..c5d6a45ed8 100644 --- a/var/spack/repos/builtin/packages/aluminum/package.py +++ b/var/spack/repos/builtin/packages/aluminum/package.py @@ -47,8 +47,8 @@ class Aluminum(CMakePackage): '-DALUMINUM_ENABLE_MPI_CUDA:BOOL=%s' % ('+mpi_cuda' in spec), '-DALUMINUM_ENABLE_NCCL:BOOL=%s' % ('+nccl' in spec)] - # Add support for OS X to find OpenMP - if (self.spec.satisfies('%clang platform=darwin')): + # Add support for OS X to find OpenMP (LLVM installed via brew) + if self.spec.satisfies('%clang platform=darwin'): clang = self.compiler.cc clang_bin = os.path.dirname(clang) clang_root = os.path.dirname(clang_bin) diff --git a/var/spack/repos/builtin/packages/amber/package.py b/var/spack/repos/builtin/packages/amber/package.py index d2ec13fb3e..481377047c 100644 --- a/var/spack/repos/builtin/packages/amber/package.py +++ b/var/spack/repos/builtin/packages/amber/package.py @@ -100,12 +100,10 @@ class Amber(Package, CudaPackage): depends_on('cuda@7.5.18', when='@:16+cuda') # conflicts - conflicts('+x11', when='platform=cray', - msg='x11 amber applications not available for cray') - conflicts('+openmp', when='%clang', - msg='openmp optimizations not available for the clang compiler') - conflicts('+openmp', when='%pgi', - msg='openmp optimizations not available for the pgi compiler') + conflicts('+x11', when='platform=cray', msg='x11 amber applications not available for cray') + conflicts('+openmp', when='%clang', msg='OpenMP optimizations not available for the clang compiler') + conflicts('+openmp', when='%apple-clang', msg='OpenMP optimizations not available for the Apple clang compiler') + conflicts('+openmp', when='%pgi', msg='OpenMP optimizations not available for the pgi compiler') def setup_build_environment(self, env): amber_src = self.stage.source_path diff --git a/var/spack/repos/builtin/packages/amrex/package.py b/var/spack/repos/builtin/packages/amrex/package.py index 32da808f1d..f6cb778f4b 100644 --- a/var/spack/repos/builtin/packages/amrex/package.py +++ b/var/spack/repos/builtin/packages/amrex/package.py @@ -65,6 +65,7 @@ class Amrex(CMakePackage): depends_on('cmake@3.5:', type='build', when='@:18.10.99') depends_on('cmake@3.13:', type='build', when='@18.11:') depends_on('cmake@3.14:', type='build', when='@19.04:') + conflicts('%apple-clang') conflicts('%clang') def url_for_version(self, version): diff --git a/var/spack/repos/builtin/packages/ape/package.py b/var/spack/repos/builtin/packages/ape/package.py index 114185aaa4..bf9f895e68 100644 --- a/var/spack/repos/builtin/packages/ape/package.py +++ b/var/spack/repos/builtin/packages/ape/package.py @@ -29,11 +29,13 @@ class Ape(Package): # When preprocessor expands macros (i.e. CFLAGS) defined as quoted # strings the result may be > 132 chars and is terminated. # This will look to a compiler as an Unterminated character constant - # and produce Line truncated errors. To vercome this, add flags to + # and produce Line truncated errors. To overcome this, add flags to # let compiler know that the entire line is meaningful. # TODO: For the lack of better approach, assume that clang is mixed - # with GNU fortran. - if spec.satisfies('%clang') or spec.satisfies('%gcc'): + # TODO: with GNU fortran. + if (spec.satisfies('%apple-clang') or + spec.satisfies('%clang') or + spec.satisfies('%gcc')): args.extend([ 'FCFLAGS=-O2 -ffree-line-length-none' ]) diff --git a/var/spack/repos/builtin/packages/atlas/package.py b/var/spack/repos/builtin/packages/atlas/package.py index 4d56d0016d..2a355dfca7 100644 --- a/var/spack/repos/builtin/packages/atlas/package.py +++ b/var/spack/repos/builtin/packages/atlas/package.py @@ -102,7 +102,7 @@ class Atlas(Package): # Workaround for macOS Clang: # http://math-atlas.sourceforge.net/atlas_install/node66.html - if spec.satisfies('@3.10.3: %clang platform=darwin'): + if spec.satisfies('@3.10.3: %apple-clang'): options.append('--force-clang=' + spack_cc) # Lapack resource to provide full lapack build. Note that diff --git a/var/spack/repos/builtin/packages/binutils/package.py b/var/spack/repos/builtin/packages/binutils/package.py index 791606f564..96fdcc067b 100644 --- a/var/spack/repos/builtin/packages/binutils/package.py +++ b/var/spack/repos/builtin/packages/binutils/package.py @@ -120,9 +120,10 @@ class Binutils(AutotoolsPackage, GNUMirrorPackage): def flag_handler(self, name, flags): # To ignore the errors of narrowing conversions for # the Fujitsu compiler - if name == 'cxxflags'\ - and (self.compiler.name == 'fj' or self.compiler.name == 'clang')\ - and self.version <= ver('2.31.1'): + if name == 'cxxflags' and ( + self.spec.satisfies('@:2.31.1') and + self.compiler.name in ('fj', 'clang', 'apple-clang') + ): flags.append('-Wno-narrowing') elif name == 'cflags': if self.spec.satisfies('@:2.34 %gcc@10:'): diff --git a/var/spack/repos/builtin/packages/boost/package.py b/var/spack/repos/builtin/packages/boost/package.py index 1e5bd00c2b..d0d8691c33 100644 --- a/var/spack/repos/builtin/packages/boost/package.py +++ b/var/spack/repos/builtin/packages/boost/package.py @@ -398,7 +398,9 @@ class Boost(Package): # and at least in clang 3.9 still fails to build # http://www.boost.org/build/doc/html/bbv2/reference/precompiled_headers.html # https://svn.boost.org/trac/boost/ticket/12496 - if spec.satisfies('%clang') or spec.satisfies('%fj'): + if (spec.satisfies('%apple-clang') or + spec.satisfies('%clang') or + spec.satisfies('%fj')): options.extend(['pch=off']) if '+clanglibcpp' in spec: cxxflags.append('-stdlib=libc++') diff --git a/var/spack/repos/builtin/packages/bucky/package.py b/var/spack/repos/builtin/packages/bucky/package.py index 859fabde34..41337e7e84 100644 --- a/var/spack/repos/builtin/packages/bucky/package.py +++ b/var/spack/repos/builtin/packages/bucky/package.py @@ -19,6 +19,7 @@ class Bucky(MakefilePackage): # Compilation requires gcc conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%intel') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/cbench/package.py b/var/spack/repos/builtin/packages/cbench/package.py index ceeec3b468..8a24a54d6e 100644 --- a/var/spack/repos/builtin/packages/cbench/package.py +++ b/var/spack/repos/builtin/packages/cbench/package.py @@ -26,6 +26,7 @@ class Cbench(MakefilePackage): # The following compilers are not supported by Cbench: conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%nag') conflicts('%xl') diff --git a/var/spack/repos/builtin/packages/cp2k/package.py b/var/spack/repos/builtin/packages/cp2k/package.py index 0a172d025f..1fba619ffc 100644 --- a/var/spack/repos/builtin/packages/cp2k/package.py +++ b/var/spack/repos/builtin/packages/cp2k/package.py @@ -141,6 +141,7 @@ class Cp2k(MakefilePackage, CudaPackage): depends_on('wannier90', when='@3.0+mpi', type='build') # CP2K needs compiler specific compilation flags, e.g. optflags + conflicts('%apple-clang') conflicts('%clang') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/dealii/package.py b/var/spack/repos/builtin/packages/dealii/package.py index 0f46c318f6..8d7bd2be81 100644 --- a/var/spack/repos/builtin/packages/dealii/package.py +++ b/var/spack/repos/builtin/packages/dealii/package.py @@ -301,7 +301,7 @@ class Dealii(CMakePackage, CudaPackage): cxx_flags_release.extend(['-O3']) elif spec.satisfies('%intel'): cxx_flags_release.extend(['-O3']) - elif spec.satisfies('%clang'): + elif spec.satisfies('%clang') or spec.satisfies('%apple-clang'): cxx_flags_release.extend(['-O3', '-ffp-contract=fast']) # Python bindings diff --git a/var/spack/repos/builtin/packages/elfutils/package.py b/var/spack/repos/builtin/packages/elfutils/package.py index 651caf3d76..cd6b961227 100644 --- a/var/spack/repos/builtin/packages/elfutils/package.py +++ b/var/spack/repos/builtin/packages/elfutils/package.py @@ -56,6 +56,7 @@ class Elfutils(AutotoolsPackage, SourcewarePackage): # in gcc, but not in clang. C code compiled with gcc is # binary-compatible with clang, so it should be possible to build # elfutils with gcc, and then link it to clang-built libraries. + conflicts('%apple-clang') conflicts('%clang') # Elfutils uses -Wall and we don't want to fail the build over a diff --git a/var/spack/repos/builtin/packages/f18/package.py b/var/spack/repos/builtin/packages/f18/package.py index 699cfde6c6..235210c142 100644 --- a/var/spack/repos/builtin/packages/f18/package.py +++ b/var/spack/repos/builtin/packages/f18/package.py @@ -30,6 +30,9 @@ class F18(CMakePackage): # Conflicts compiler_warning = 'F18 requires a compiler with support for C++17' + # See https://en.wikipedia.org/wiki/Xcode#Latest_versions for a + # conversion table from LLVM versions to Apple's Clang + conflicts('%apple-clang@:10.1', msg=compiler_warning) conflicts('%clang@:6', msg=compiler_warning) conflicts('%gcc@:7.1', msg=compiler_warning) conflicts('%intel', msg=compiler_warning) diff --git a/var/spack/repos/builtin/packages/fftw/package.py b/var/spack/repos/builtin/packages/fftw/package.py index 961c4cfc66..b644677fd1 100644 --- a/var/spack/repos/builtin/packages/fftw/package.py +++ b/var/spack/repos/builtin/packages/fftw/package.py @@ -57,6 +57,7 @@ class Fftw(AutotoolsPackage): msg='Long double precision is not supported in FFTW 2') conflicts('precision=quad', when='@2.1.5', msg='Quad precision is not supported in FFTW 2') + conflicts('+openmp', when='%apple-clang', msg="Apple's clang does not support OpenMP") provides('fftw-api@2', when='@2.1.5') provides('fftw-api@3', when='@3:') @@ -124,11 +125,6 @@ class Fftw(AutotoolsPackage): # Variants that affect every precision if '+openmp' in spec: - # Note: Apple's Clang does not support OpenMP. - if spec.satisfies('%clang'): - ver = str(self.compiler.version) - if ver.endswith('-apple'): - raise InstallError("Apple's clang does not support OpenMP") options.append('--enable-openmp') if spec.satisfies('@:2'): # TODO: libtool strips CFLAGS, so 2.x libxfftw_threads diff --git a/var/spack/repos/builtin/packages/fujitsu-mpi/package.py b/var/spack/repos/builtin/packages/fujitsu-mpi/package.py index c0a882ec4c..fcf4dc8e94 100644 --- a/var/spack/repos/builtin/packages/fujitsu-mpi/package.py +++ b/var/spack/repos/builtin/packages/fujitsu-mpi/package.py @@ -13,6 +13,7 @@ class FujitsuMpi(Package): conflicts('%arm') conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%gcc') conflicts('%intel') diff --git a/var/spack/repos/builtin/packages/gitconddb/package.py b/var/spack/repos/builtin/packages/gitconddb/package.py index 9400ea549c..e2808e91c0 100644 --- a/var/spack/repos/builtin/packages/gitconddb/package.py +++ b/var/spack/repos/builtin/packages/gitconddb/package.py @@ -40,4 +40,5 @@ class Gitconddb(CMakePackage): # Known conflicts on C++17 compatibility (aggressive for now) conflicts('%gcc@:7.9.999', msg="GitCondDB requires GCC 8 or newer for C++17 support") + conflicts('%apple-clang', when="@:0.1.99", msg="No Darwin support for clang in older versions") conflicts('%clang platform=darwin', when="@:0.1.99", msg="No Darwin support for clang in older versions") diff --git a/var/spack/repos/builtin/packages/graphviz/package.py b/var/spack/repos/builtin/packages/graphviz/package.py index 4f8e772f19..34b2d8dd2e 100644 --- a/var/spack/repos/builtin/packages/graphviz/package.py +++ b/var/spack/repos/builtin/packages/graphviz/package.py @@ -137,6 +137,13 @@ class Graphviz(AutotoolsPackage): filter_file(r'-lstdc\+\+', '-lc++', 'configure.ac', *(d + '/Makefile.am' for d in mkdirs)) + @when('%apple-clang') + def patch(self): + # When using Clang, replace GCC's libstdc++ with LLVM's libc++ + mkdirs = ['cmd/dot', 'cmd/edgepaint', 'cmd/mingle', 'plugin/gdiplus'] + filter_file(r'-lstdc\+\+', '-lc++', 'configure.ac', + *(d + '/Makefile.am' for d in mkdirs)) + def configure_args(self): spec = self.spec args = ['--disable-silent-rules'] diff --git a/var/spack/repos/builtin/packages/hpgmg/package.py b/var/spack/repos/builtin/packages/hpgmg/package.py index e701d1c212..f5567ba2c9 100644 --- a/var/spack/repos/builtin/packages/hpgmg/package.py +++ b/var/spack/repos/builtin/packages/hpgmg/package.py @@ -59,13 +59,11 @@ class Hpgmg(Package): args.append('--no-fv') else: # Apple's Clang doesn't support OpenMP - if not (self.spec.satisfies('%clang') and self.compiler.is_apple): + if not self.spec.satisfies('%apple-clang'): cflags.append(self.compiler.openmp_flag) if '+debug' in self.spec: cflags.append('-g') - elif any(map(self.spec.satisfies, ['%gcc', '%clang', '%intel'])): - cflags.append('-O3') else: cflags.append('-O3') diff --git a/var/spack/repos/builtin/packages/hydrogen/package.py b/var/spack/repos/builtin/packages/hydrogen/package.py index 449fe046dc..9d12235d72 100644 --- a/var/spack/repos/builtin/packages/hydrogen/package.py +++ b/var/spack/repos/builtin/packages/hydrogen/package.py @@ -131,8 +131,8 @@ class Hydrogen(CMakePackage): '-DHydrogen_ENABLE_HALF=%s' % ('+half' in spec), ] - # Add support for OS X to find OpenMP - if (self.spec.satisfies('%clang platform=darwin')): + # Add support for OS X to find OpenMP (LLVM installed via brew) + if self.spec.satisfies('%clang platform=darwin'): clang = self.compiler.cc clang_bin = os.path.dirname(clang) clang_root = os.path.dirname(clang_bin) diff --git a/var/spack/repos/builtin/packages/intel-tbb/package.py b/var/spack/repos/builtin/packages/intel-tbb/package.py index c470e8933b..4c652f6fce 100644 --- a/var/spack/repos/builtin/packages/intel-tbb/package.py +++ b/var/spack/repos/builtin/packages/intel-tbb/package.py @@ -69,6 +69,8 @@ class IntelTbb(Package): # # See https://github.com/intel/tbb/pull/147 for details. # + conflicts('%apple-clang', when='@:2019.6', + msg='2019.7 or later required for clang') conflicts('%clang', when='@:2019.6', msg='2019.7 or later required for clang') @@ -163,7 +165,7 @@ class IntelTbb(Package): # self.coerce_to_spack("build") - if spec.satisfies('%clang'): + if spec.satisfies('%clang') or spec.satisfies('%apple-clang'): tbb_compiler = "clang" elif spec.satisfies('%intel'): tbb_compiler = "icc" diff --git a/var/spack/repos/builtin/packages/kahip/package.py b/var/spack/repos/builtin/packages/kahip/package.py index 7d12d36bc2..e2ca1aeaa1 100644 --- a/var/spack/repos/builtin/packages/kahip/package.py +++ b/var/spack/repos/builtin/packages/kahip/package.py @@ -32,6 +32,7 @@ class Kahip(SConsPackage): depends_on('argtable') depends_on('mpi') # Note: upstream package only tested on openmpi + conflicts('%apple-clang') conflicts('%clang') def patch(self): diff --git a/var/spack/repos/builtin/packages/kentutils/package.py b/var/spack/repos/builtin/packages/kentutils/package.py index 379d3486c0..f0b4ee8322 100644 --- a/var/spack/repos/builtin/packages/kentutils/package.py +++ b/var/spack/repos/builtin/packages/kentutils/package.py @@ -22,6 +22,7 @@ class Kentutils(MakefilePackage): depends_on('mariadb') conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%intel') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/lbann/package.py b/var/spack/repos/builtin/packages/lbann/package.py index 04b044610f..bc0da109ec 100644 --- a/var/spack/repos/builtin/packages/lbann/package.py +++ b/var/spack/repos/builtin/packages/lbann/package.py @@ -164,16 +164,16 @@ class Lbann(CMakePackage): # protobuf is included by py-protobuf+cpp '-DProtobuf_DIR={0}'.format(spec['protobuf'].prefix)]) - if self.spec.satisfies('@:0.90') or self.spec.satisfies('@0.95:'): + if spec.satisfies('@:0.90') or spec.satisfies('@0.95:'): args.extend([ '-DHydrogen_DIR={0}/CMake/hydrogen'.format( spec['hydrogen'].prefix)]) - elif self.spec.satisfies('@0.94'): + elif spec.satisfies('@0.94'): args.extend([ '-DElemental_DIR={0}/CMake/elemental'.format( spec['elemental'].prefix)]) - if self.spec.satisfies('@0.94:0.98.2'): + if spec.satisfies('@0.94:0.98.2'): args.extend(['-DLBANN_WITH_NCCL:BOOL=%s' % ('+gpu +nccl' in spec)]) if '+vtune' in spec: @@ -188,8 +188,8 @@ class Lbann(CMakePackage): '-DConduit_DIR={0}'.format(spec['conduit'].prefix)]) # Add support for OpenMP - if (self.spec.satisfies('%clang')): - if (sys.platform == 'darwin'): + if spec.satisfies('%clang') or spec.satisfies('%apple-clang'): + if sys.platform == 'darwin': clang = self.compiler.cc clang_bin = os.path.dirname(clang) clang_root = os.path.dirname(clang_bin) @@ -210,7 +210,7 @@ class Lbann(CMakePackage): args.extend([ '-DcuDNN_DIR={0}'.format( spec['cudnn'].prefix)]) - if self.spec.satisfies('@0.94:0.98.2'): + if spec.satisfies('@0.94:0.98.2'): args.extend(['-DCUB_DIR={0}'.format( spec['cub'].prefix)]) if '+nccl' in spec: diff --git a/var/spack/repos/builtin/packages/libceed/package.py b/var/spack/repos/builtin/packages/libceed/package.py index 36d46dae0b..a7ae5b21f8 100644 --- a/var/spack/repos/builtin/packages/libceed/package.py +++ b/var/spack/repos/builtin/packages/libceed/package.py @@ -71,14 +71,14 @@ class Libceed(Package): opt = '-O3 -g -ffp-contract=fast' if compiler.version >= ver(4.9): opt += ' -fopenmp-simd' + elif compiler.name == 'apple-clang': + opt = '-O3 -g -march=native -ffp-contract=fast' + if compiler.version >= ver(10): + opt += ' -fopenmp-simd' elif compiler.name == 'clang': opt = '-O3 -g -march=native -ffp-contract=fast' - if compiler.version.string.endswith('-apple'): - if compiler.version >= ver(10): - opt += ' -fopenmp-simd' - else: # not apple clang - if compiler.version >= ver(6): - opt += ' -fopenmp-simd' + if compiler.version >= ver(6): + opt += ' -fopenmp-simd' elif compiler.name in ['xl', 'xl_r']: opt = '-O -g -qsimd=auto' else: diff --git a/var/spack/repos/builtin/packages/libcerf/package.py b/var/spack/repos/builtin/packages/libcerf/package.py index e37e7f6339..a5c00dabaf 100644 --- a/var/spack/repos/builtin/packages/libcerf/package.py +++ b/var/spack/repos/builtin/packages/libcerf/package.py @@ -23,7 +23,7 @@ class Libcerf(AutotoolsPackage, SourceforgePackage): options = [] # Clang reports unused functions as errors, see # http://clang.debian.net/status.php?version=3.8.1&key=UNUSED_FUNCTION - if spec.satisfies('%clang'): + if spec.satisfies('%clang') or spec.satisfies('%apple-clang'): options.append('CFLAGS=-Wno-unused-function') # fujitsu compiler has a error about unused functions too. if spec.satisfies('%fj'): diff --git a/var/spack/repos/builtin/packages/librsb/package.py b/var/spack/repos/builtin/packages/librsb/package.py index 90cc5b67a8..2a292b9479 100644 --- a/var/spack/repos/builtin/packages/librsb/package.py +++ b/var/spack/repos/builtin/packages/librsb/package.py @@ -17,6 +17,7 @@ class Librsb(AutotoolsPackage): version('1.2.0.8', '8bebd19a1866d80ade13eabfdd0f07ae7e8a485c0b975b5d15f531ac204d80cb') depends_on('zlib') + conflicts('%apple-clang') conflicts('%clang') def configure_args(self): diff --git a/var/spack/repos/builtin/packages/likwid/package.py b/var/spack/repos/builtin/packages/likwid/package.py index 8e89693ce1..a104b67003 100644 --- a/var/spack/repos/builtin/packages/likwid/package.py +++ b/var/spack/repos/builtin/packages/likwid/package.py @@ -60,9 +60,15 @@ class Likwid(Package): *files) def install(self, spec, prefix): - supported_compilers = {'clang': 'CLANG', 'gcc': 'GCC', 'intel': 'ICC'} + supported_compilers = { + 'apple-clang': 'CLANG', + 'clang': 'CLANG', + 'gcc': 'GCC', + 'intel': 'ICC' + } if spec.target.family == 'aarch64': - supported_compilers = {'gcc': 'GCCARMv8', 'clang': 'ARMCLANG'} + supported_compilers = { + 'gcc': 'GCCARMv8', 'clang': 'ARMCLANG', 'arm': 'ARMCLANG'} elif spec.target.family == 'ppc64' or spec.target.family == 'ppc64le': supported_compilers = {'gcc': 'GCCPOWER'} if self.compiler.name not in supported_compilers: diff --git a/var/spack/repos/builtin/packages/maverick/package.py b/var/spack/repos/builtin/packages/maverick/package.py index 6c560bb202..60909c551b 100644 --- a/var/spack/repos/builtin/packages/maverick/package.py +++ b/var/spack/repos/builtin/packages/maverick/package.py @@ -17,6 +17,7 @@ class Maverick(MakefilePackage): conflicts('%gcc@:6.0') conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%intel') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/mpich/package.py b/var/spack/repos/builtin/packages/mpich/package.py index c9c7886a08..d862f12522 100644 --- a/var/spack/repos/builtin/packages/mpich/package.py +++ b/var/spack/repos/builtin/packages/mpich/package.py @@ -79,6 +79,7 @@ spack package at this time.''', # see https://lists.mpich.org/pipermail/discuss/2016-May/004764.html # and https://lists.mpich.org/pipermail/discuss/2016-June/004768.html patch('mpich32_clang.patch', when='@3.2:3.2.0%clang') + patch('mpich32_clang.patch', when='@3.2:3.2.0%apple-clang') # Fix SLURM node list parsing # See https://github.com/pmodels/mpich/issues/3572 diff --git a/var/spack/repos/builtin/packages/mpilander/package.py b/var/spack/repos/builtin/packages/mpilander/package.py index 276f380a86..9b72915180 100644 --- a/var/spack/repos/builtin/packages/mpilander/package.py +++ b/var/spack/repos/builtin/packages/mpilander/package.py @@ -31,6 +31,7 @@ class Mpilander(CMakePackage): # compiler support conflicts('%gcc@:4.7') conflicts('%clang@:3.8') + conflicts('%apple-clang@:7.4') conflicts('%intel@:16') def cmake_args(self): diff --git a/var/spack/repos/builtin/packages/musl/package.py b/var/spack/repos/builtin/packages/musl/package.py index 7c68735c20..05ec4eb5ff 100644 --- a/var/spack/repos/builtin/packages/musl/package.py +++ b/var/spack/repos/builtin/packages/musl/package.py @@ -38,7 +38,7 @@ class Musl(Package): if self.compiler.name == 'gcc': config.filter("WRAPCC_GCC = .*'", "WRAPCC_GCC = {0}'". format(self.compiler.cc)) - elif self.compiler.name == 'clang': + elif self.compiler.name in ('clang', 'apple-clang'): config.filter("WRAPCC_CLANG = .*'", "WRAPCC_CLANG = {0}'". format(self.compiler.cc)) @@ -46,7 +46,7 @@ class Musl(Package): args = ['--prefix={0}'.format(self.prefix)] if self.compiler.name == 'gcc': args.append('--enable-wrapper=gcc') - elif self.compiler.name == 'clang': + elif self.compiler.name in ('clang', 'apple-clang'): args.append('--enable-wrapper=clang') else: args.append('--enable-wrapper=no') diff --git a/var/spack/repos/builtin/packages/octopus/package.py b/var/spack/repos/builtin/packages/octopus/package.py index 1073965e81..bed1c1a256 100644 --- a/var/spack/repos/builtin/packages/octopus/package.py +++ b/var/spack/repos/builtin/packages/octopus/package.py @@ -97,11 +97,13 @@ class Octopus(Package): # When preprocessor expands macros (i.e. CFLAGS) defined as quoted # strings the result may be > 132 chars and is terminated. # This will look to a compiler as an Unterminated character constant - # and produce Line truncated errors. To vercome this, add flags to + # and produce Line truncated errors. To overcome this, add flags to # let compiler know that the entire line is meaningful. # TODO: For the lack of better approach, assume that clang is mixed # with GNU fortran. - if spec.satisfies('%clang') or spec.satisfies('%gcc'): + if (spec.satisfies('%apple-clang') or + spec.satisfies('%clang') or + spec.satisfies('%gcc')): args.extend([ 'FCFLAGS=-O2 -ffree-line-length-none' ]) diff --git a/var/spack/repos/builtin/packages/onednn/package.py b/var/spack/repos/builtin/packages/onednn/package.py index b723fabd9c..82d22296f9 100644 --- a/var/spack/repos/builtin/packages/onednn/package.py +++ b/var/spack/repos/builtin/packages/onednn/package.py @@ -64,7 +64,7 @@ class Onednn(CMakePackage): # https://github.com/oneapi-src/oneDNN#requirements-for-building-from-source depends_on('cmake@2.8.11:', type='build') depends_on('tbb@2017:', when='cpu_runtime=tbb') - depends_on('llvm-openmp', when='%clang platform=darwin cpu_runtime=omp') + depends_on('llvm-openmp', when='%apple-clang cpu_runtime=omp') depends_on('opencl@1.2:', when='gpu_runtime=ocl') def cmake_args(self): @@ -81,7 +81,7 @@ class Onednn(CMakePackage): args.append('-DDNNL_BUILD_TESTS=OFF') # https://github.com/oneapi-src/oneDNN/issues/591 - if self.spec.satisfies('%clang platform=darwin cpu_runtime=omp'): + if self.spec.satisfies('%apple-clang cpu_runtime=omp'): args.extend([ '-DOpenMP_CXX_FLAGS={0}'.format(self.compiler.openmp_flag), '-DOpenMP_C_FLAGS={0}'.format(self.compiler.openmp_flag), diff --git a/var/spack/repos/builtin/packages/openblas/package.py b/var/spack/repos/builtin/packages/openblas/package.py index c1a0c1e01b..61a530b37f 100644 --- a/var/spack/repos/builtin/packages/openblas/package.py +++ b/var/spack/repos/builtin/packages/openblas/package.py @@ -95,7 +95,7 @@ class Openblas(MakefilePackage): patch('openblas-0.3.8-darwin.patch', when='@0.3.8 platform=darwin') # Fix ICE in LLVM 9.0.0 https://github.com/xianyi/OpenBLAS/pull/2329 # Patch as in https://github.com/xianyi/OpenBLAS/pull/2597 - patch('openblas_appleclang11.patch', when='@0.3.8:0.3.9 %clang@11.0.3-apple') + patch('openblas_appleclang11.patch', when='@0.3.8:0.3.9 %apple-clang@11.0.3') # Add conditions to f_check to determine the Fujitsu compiler patch('openblas_fujitsu.patch', when='%fj') @@ -105,6 +105,9 @@ class Openblas(MakefilePackage): conflicts('+consistent_fpcsr', when='threads=none', msg='FPCSR consistency only applies to multithreading') + conflicts('threads=openmp', when='%apple-clang', msg="Apple's clang does not support OpenMP") + conflicts('threads=openmp @:0.2.19', when='%clang', msg='OpenBLAS @:0.2.19 does not support OpenMP with clang!') + @property def parallel(self): # unclear whether setting `-j N` externally was supported before 0.3 @@ -120,18 +123,6 @@ class Openblas(MakefilePackage): 'OpenBLAS requires both C and Fortran compilers!' ) - # Add support for OpenMP - if (self.spec.satisfies('threads=openmp') and - self.spec.satisfies('%clang')): - if str(self.spec.compiler.version).endswith('-apple'): - raise InstallError("Apple's clang does not support OpenMP") - if '@:0.2.19' in self.spec: - # Openblas (as of 0.2.19) hardcoded that OpenMP cannot - # be used with any (!) compiler named clang, bummer. - raise InstallError( - 'OpenBLAS @:0.2.19 does not support OpenMP with clang!' - ) - @staticmethod def _read_targets(target_file): """Parse a list of available targets from the OpenBLAS/TargetList.txt diff --git a/var/spack/repos/builtin/packages/pdt/package.py b/var/spack/repos/builtin/packages/pdt/package.py index 35164db1c5..bf3f954982 100644 --- a/var/spack/repos/builtin/packages/pdt/package.py +++ b/var/spack/repos/builtin/packages/pdt/package.py @@ -33,7 +33,8 @@ class Pdt(AutotoolsPackage): variant('pic', default=False, description="Builds with pic") def patch(self): - if self.spec.satisfies('%clang'): + spec = self.spec + if spec.satisfies('%clang') or spec.satisfies('%apple-clang'): filter_file(r'PDT_GXX=g\+\+ ', r'PDT_GXX=clang++ ', 'ductape/Makefile') diff --git a/var/spack/repos/builtin/packages/petsc/package.py b/var/spack/repos/builtin/packages/petsc/package.py index f328171072..9da9740674 100644 --- a/var/spack/repos/builtin/packages/petsc/package.py +++ b/var/spack/repos/builtin/packages/petsc/package.py @@ -2,11 +2,7 @@ # Spack Project Developers. See the top-level COPYRIGHT file for details. # # SPDX-License-Identifier: (Apache-2.0 OR MIT) - - import os -import sys -from spack import * class Petsc(Package): @@ -116,9 +112,7 @@ class Petsc(Package): # temporary workaround Clang 8.1.0 with XCode 8.3 on macOS, see # https://bitbucket.org/petsc/petsc/commits/4f290403fdd060d09d5cb07345cbfd52670e3cbc # the patch is an adaptation of the original commit to 3.7.5 - if sys.platform == "darwin": - patch('macos-clang-8.1.0.diff', - when='@3.7.5%clang@8.1.0:') + patch('macos-clang-8.1.0.diff', when='@3.7.5%apple-clang@8.1.0:') patch('pkg-config-3.7.6-3.8.4.diff', when='@3.7.6:3.8.4') patch('xcode_stub_out_of_sync.patch', when='@:3.10.4') diff --git a/var/spack/repos/builtin/packages/pixman/package.py b/var/spack/repos/builtin/packages/pixman/package.py index 1087dabbbf..a145edc638 100644 --- a/var/spack/repos/builtin/packages/pixman/package.py +++ b/var/spack/repos/builtin/packages/pixman/package.py @@ -29,7 +29,8 @@ class Pixman(AutotoolsPackage): # __builtin_shuffle was removed in clang 5.0. # From version 9.1 apple-clang is based on clang 5.0. # Patch is obtained from above link. - patch('clang.patch', when='@0.34%clang@9.1.0-apple:') + patch('clang.patch', when='@0.34%apple-clang@9.1.0:') + patch('clang.patch', when='@0.34%clang@5.0.0:') @run_before('build') def patch_config_h_for_intel(self): diff --git a/var/spack/repos/builtin/packages/plasma/package.py b/var/spack/repos/builtin/packages/plasma/package.py index bf4d8c68ee..efeb980bd8 100644 --- a/var/spack/repos/builtin/packages/plasma/package.py +++ b/var/spack/repos/builtin/packages/plasma/package.py @@ -58,6 +58,7 @@ class Plasma(CMakePackage): conflicts("%gcc@:5.99", when='@17.2:') conflicts("%cce") + conflicts('%apple-clang') conflicts("%clang") conflicts("%intel") conflicts("%nag") diff --git a/var/spack/repos/builtin/packages/precice/package.py b/var/spack/repos/builtin/packages/precice/package.py index 11250f60bd..45548275c8 100644 --- a/var/spack/repos/builtin/packages/precice/package.py +++ b/var/spack/repos/builtin/packages/precice/package.py @@ -60,6 +60,7 @@ class Precice(CMakePackage): # We require C++11 compiler support as well as # library support for time manipulators (N2071, N2072) conflicts('%gcc@:4') + conflicts('%apple-clang@:4') conflicts('%clang@:3.7') conflicts('%intel@:14') conflicts('%pgi@:14') diff --git a/var/spack/repos/builtin/packages/py-dgl/package.py b/var/spack/repos/builtin/packages/py-dgl/package.py index 544b527f69..9ef1bd9ed8 100644 --- a/var/spack/repos/builtin/packages/py-dgl/package.py +++ b/var/spack/repos/builtin/packages/py-dgl/package.py @@ -29,7 +29,7 @@ class PyDgl(CMakePackage): depends_on('cmake@3.5:', type='build') depends_on('cuda', when='+cuda') - depends_on('llvm-openmp', when='%clang platform=darwin +openmp') + depends_on('llvm-openmp', when='%apple-clang +openmp') # Python dependencies # See python/setup.py @@ -66,7 +66,7 @@ class PyDgl(CMakePackage): if '+openmp' in self.spec: args.append('-DUSE_OPENMP=ON') - if self.spec.satisfies('%clang platform=darwin'): + if self.spec.satisfies('%apple-clang'): args.extend([ '-DOpenMP_CXX_FLAGS=' + self.spec['llvm-openmp'].headers.include_flags, diff --git a/var/spack/repos/builtin/packages/py-exodus-bundler/package.py b/var/spack/repos/builtin/packages/py-exodus-bundler/package.py index c13f30eb46..eddb3da88f 100644 --- a/var/spack/repos/builtin/packages/py-exodus-bundler/package.py +++ b/var/spack/repos/builtin/packages/py-exodus-bundler/package.py @@ -15,6 +15,7 @@ class PyExodusBundler(PythonPackage): version('2.0.2', sha256='4e896a2034b94cf7b4fb33d86a68e29a7d3b08e57541e444db34dddc6ac1ef68') + depends_on('musl', type='run', when='%apple-clang') depends_on('musl', type='run', when='%clang') depends_on('musl', type='run', when='%gcc') depends_on('py-setuptools', type=('build', 'run')) diff --git a/var/spack/repos/builtin/packages/py-flye/package.py b/var/spack/repos/builtin/packages/py-flye/package.py index db3804e11d..090d36cdb9 100644 --- a/var/spack/repos/builtin/packages/py-flye/package.py +++ b/var/spack/repos/builtin/packages/py-flye/package.py @@ -26,7 +26,7 @@ class PyFlye(PythonPackage): msg = 'C++ compiler with C++11 support required' conflicts('%gcc@:4.7', msg=msg) conflicts('%clang@:3.2', msg=msg) - # Requires Apple Clang 5.0+ but no way to specify that right now + conflicts('apple-clang@:4.9', msg=msg) def setup_build_environment(self, env): if self.spec.target.family == 'aarch64': diff --git a/var/spack/repos/builtin/packages/py-scikit-learn/package.py b/var/spack/repos/builtin/packages/py-scikit-learn/package.py index 52c9beae43..d73d3f7576 100644 --- a/var/spack/repos/builtin/packages/py-scikit-learn/package.py +++ b/var/spack/repos/builtin/packages/py-scikit-learn/package.py @@ -69,9 +69,7 @@ class PyScikitLearn(PythonPackage): depends_on('py-pytest@3.3.0:', type='test') depends_on('py-pandas', type='test') depends_on('py-setuptools', type='build') - # Technically not correct, but currently no way to check if we - # are using Apple Clang or not. - depends_on('llvm-openmp', when='@0.21: %clang platform=darwin +openmp') + depends_on('llvm-openmp', when='@0.21: %apple-clang +openmp') # Release tarballs are already cythonized. If you wanted to build a release # version without OpenMP support, you would need to delete all .c files @@ -84,7 +82,7 @@ class PyScikitLearn(PythonPackage): if self.spec.satisfies('~openmp'): env.set('SKLEARN_NO_OPENMP', 'True') # https://scikit-learn.org/stable/developers/advanced_installation.html#mac-osx - elif self.spec.satisfies('@0.21: %clang platform=darwin +openmp'): + elif self.spec.satisfies('@0.21: %apple-clang +openmp'): env.append_flags( 'CPPFLAGS', self.compiler.openmp_flag) env.append_flags( diff --git a/var/spack/repos/builtin/packages/py-torch/package.py b/var/spack/repos/builtin/packages/py-torch/package.py index c240144f11..1ffeb81b23 100644 --- a/var/spack/repos/builtin/packages/py-torch/package.py +++ b/var/spack/repos/builtin/packages/py-torch/package.py @@ -155,7 +155,7 @@ class PyTorch(PythonPackage, CudaPackage): depends_on('nccl', when='+nccl') depends_on('gloo', when='+gloo') depends_on('opencv', when='+opencv') - depends_on('llvm-openmp', when='%clang platform=darwin +openmp') + depends_on('llvm-openmp', when='%apple-clang +openmp') depends_on('ffmpeg', when='+ffmpeg') depends_on('leveldb', when='+leveldb') depends_on('lmdb', when='+lmdb') diff --git a/var/spack/repos/builtin/packages/qmcpack/package.py b/var/spack/repos/builtin/packages/qmcpack/package.py index 5307b3d2d5..07724f63fe 100644 --- a/var/spack/repos/builtin/packages/qmcpack/package.py +++ b/var/spack/repos/builtin/packages/qmcpack/package.py @@ -102,6 +102,7 @@ class Qmcpack(CMakePackage, CudaPackage): conflicts('+afqmc', when='@:3.6.0', msg='AFQMC not recommended before v3.7') conflicts('+afqmc', when='~mpi', msg='AFQMC requires building with +mpi') conflicts('+afqmc', when='%gcc@:6.0', msg='AFQMC code requires gcc@6.1 or greater') + conflicts('+afqmc', when='%apple-clang@:9.2', msg='AFQMC code requires clang 4.1 or greater') conflicts('+afqmc', when='%clang@:4.0', msg='AFQMC code requires clang 4.1 or greater') conflicts('+afqmc', when='%intel@:18', msg='AFQMC code requires intel19 or greater') diff --git a/var/spack/repos/builtin/packages/qt/package.py b/var/spack/repos/builtin/packages/qt/package.py index ba28042fa3..7e016846ab 100644 --- a/var/spack/repos/builtin/packages/qt/package.py +++ b/var/spack/repos/builtin/packages/qt/package.py @@ -286,7 +286,7 @@ class Qt(Package): "qmake/qmake.pri", "src/tools/bootstrap/bootstrap.pro" ] - if '%clang' in self.spec: + if '%clang' in self.spec or '%apple-clang' in self.spec: files_to_filter += [ "mkspecs/unsupported/macx-clang-libc++/qmake.conf", "mkspecs/common/clang.conf" diff --git a/var/spack/repos/builtin/packages/raxml/package.py b/var/spack/repos/builtin/packages/raxml/package.py index 08d99e6b16..7eb477dfc6 100644 --- a/var/spack/repos/builtin/packages/raxml/package.py +++ b/var/spack/repos/builtin/packages/raxml/package.py @@ -25,6 +25,7 @@ class Raxml(Package): # Compiles with either GCC or ICC. conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%nag') conflicts('%pgi') diff --git a/var/spack/repos/builtin/packages/sgpp/package.py b/var/spack/repos/builtin/packages/sgpp/package.py index 7e5b907374..728638500f 100644 --- a/var/spack/repos/builtin/packages/sgpp/package.py +++ b/var/spack/repos/builtin/packages/sgpp/package.py @@ -97,6 +97,7 @@ class Sgpp(SConsPackage): # Compiler with C++11 support is required conflicts('%gcc@:4.8.4', msg='Compiler with c++11 support is required!') + conflicts('%apple-clang@:3.9', msg='Compiler with c++11 support is required!') conflicts('%clang@:3.2', msg='Compiler with c++11 support is required!') conflicts('%intel@:14', msg='Compiler with c++11 support is required!') # Solver python bindings are actually using the pde module at one point: diff --git a/var/spack/repos/builtin/packages/silo/package.py b/var/spack/repos/builtin/packages/silo/package.py index 9192937393..3d9ef4e16c 100644 --- a/var/spack/repos/builtin/packages/silo/package.py +++ b/var/spack/repos/builtin/packages/silo/package.py @@ -57,6 +57,13 @@ class Silo(AutotoolsPackage): @when('%clang@9:') def patch(self): + self.clang_9_patch() + + @when('%apple-clang@11.0.3:') + def patch(self): + self.clang_9_patch() + + def clang_9_patch(self): # Clang 9 and later include macro definitions in <math.h> that conflict # with typedefs DOMAIN and RANGE used in Silo plugins. # It looks like the upstream fpzip repo has been fixed, but that change diff --git a/var/spack/repos/builtin/packages/snap-berkeley/package.py b/var/spack/repos/builtin/packages/snap-berkeley/package.py index 90d970e277..de9928e0c3 100644 --- a/var/spack/repos/builtin/packages/snap-berkeley/package.py +++ b/var/spack/repos/builtin/packages/snap-berkeley/package.py @@ -22,6 +22,7 @@ class SnapBerkeley(MakefilePackage): conflicts('%gcc@6:') conflicts('%cce') + conflicts('%apple-clang') conflicts('%clang') conflicts('%intel') conflicts('%nag') diff --git a/var/spack/repos/builtin/packages/sqlitebrowser/package.py b/var/spack/repos/builtin/packages/sqlitebrowser/package.py index 6cd8eeb9b8..b92d65348e 100644 --- a/var/spack/repos/builtin/packages/sqlitebrowser/package.py +++ b/var/spack/repos/builtin/packages/sqlitebrowser/package.py @@ -18,6 +18,7 @@ class Sqlitebrowser(CMakePackage): msg = 'sqlitebrowser requires C++11 support' conflicts('%gcc@:4.8.0', msg=msg) + conflicts('%apple-clang@:3.9', msg=msg) conflicts('%clang@:3.2', msg=msg) conflicts('%intel@:12', msg=msg) conflicts('%xl@:13.0', msg=msg) diff --git a/var/spack/repos/builtin/packages/suite-sparse/package.py b/var/spack/repos/builtin/packages/suite-sparse/package.py index eef38fefae..703fbcf670 100644 --- a/var/spack/repos/builtin/packages/suite-sparse/package.py +++ b/var/spack/repos/builtin/packages/suite-sparse/package.py @@ -115,7 +115,7 @@ class SuiteSparse(Package): # CFLAGS, but not all compilers use the same flags for these # optimizations if any([x in spec - for x in ('%clang', '%gcc', '%intel')]): + for x in ('%apple-clang', '%clang', '%gcc', '%intel')]): make_args += ['CFLAGS+=-fno-common -fexceptions'] elif '%pgi' in spec: make_args += ['CFLAGS+=--exceptions'] diff --git a/var/spack/repos/builtin/packages/sundials/package.py b/var/spack/repos/builtin/packages/sundials/package.py index e374a4bbca..50832e6e5a 100644 --- a/var/spack/repos/builtin/packages/sundials/package.py +++ b/var/spack/repos/builtin/packages/sundials/package.py @@ -214,7 +214,7 @@ class Sundials(CMakePackage): return 'ON' if varstr in self.spec else 'OFF' fortran_flag = self.compiler.f77_pic_flag - if (spec.satisfies('%clang platform=darwin')) and ('+fcmix' in spec): + if (spec.satisfies('%apple-clang')) and ('+fcmix' in spec): f77 = Executable(self.compiler.f77) libgfortran = LibraryList(f77('--print-file-name', 'libgfortran.a', output=str)) diff --git a/var/spack/repos/builtin/packages/trilinos/package.py b/var/spack/repos/builtin/packages/trilinos/package.py index 16f916849c..7896d809f2 100644 --- a/var/spack/repos/builtin/packages/trilinos/package.py +++ b/var/spack/repos/builtin/packages/trilinos/package.py @@ -683,7 +683,9 @@ class Trilinos(CMakePackage): # Fortran lib (assumes clang is built with gfortran!) if '+fortran' in spec and ( - spec.satisfies('%gcc') or spec.satisfies('%clang')): + spec.satisfies('%gcc') or spec.satisfies('%clang') or + spec.satisfies('%apple-clang') + ): options.append(define('Trilinos_ENABLE_Fortran', True)) if '+mpi' in spec: libgfortran = os.path.dirname(os.popen( diff --git a/var/spack/repos/builtin/packages/unblur/package.py b/var/spack/repos/builtin/packages/unblur/package.py index 428f44c08e..7366ad836a 100644 --- a/var/spack/repos/builtin/packages/unblur/package.py +++ b/var/spack/repos/builtin/packages/unblur/package.py @@ -27,6 +27,7 @@ class Unblur(AutotoolsPackage): # Requires Intel Fortran compiler conflicts('%gcc') conflicts('%pgi') + conflicts('%apple-clang') conflicts('%clang') conflicts('%cce') conflicts('%xl') diff --git a/var/spack/repos/builtin/packages/valgrind/package.py b/var/spack/repos/builtin/packages/valgrind/package.py index 4555b0b886..20d8791f4e 100644 --- a/var/spack/repos/builtin/packages/valgrind/package.py +++ b/var/spack/repos/builtin/packages/valgrind/package.py @@ -40,7 +40,7 @@ class Valgrind(AutotoolsPackage, SourcewarePackage): variant('ubsan', default=sys.platform != 'darwin', description='Activates ubsan support for valgrind') - conflicts('+ubsan', when='platform=darwin %clang', + conflicts('+ubsan', when='%apple-clang', msg=""" Cannot build libubsan with clang on macOS. Otherwise with (Apple's) clang there is a linker error: diff --git a/var/spack/repos/builtin/packages/vtk/package.py b/var/spack/repos/builtin/packages/vtk/package.py index 0df4c4a5fc..2a334cb1fb 100644 --- a/var/spack/repos/builtin/packages/vtk/package.py +++ b/var/spack/repos/builtin/packages/vtk/package.py @@ -285,9 +285,7 @@ class Vtk(CMakePackage): # string. This fix was recommended on the VTK mailing list # in March 2014 (see # https://public.kitware.com/pipermail/vtkusers/2014-March/083368.html) - if (self.spec.satisfies('%clang') and - self.compiler.is_apple and - self.compiler.version >= Version('5.1.0')): + if self.spec.satisfies('%apple-clang@5.1.0:'): cmake_args.extend(['-DVTK_REQUIRED_OBJCXX_FLAGS=']) # A bug in tao pegtl causes build failures with intel compilers diff --git a/var/spack/repos/builtin/packages/warpx/package.py b/var/spack/repos/builtin/packages/warpx/package.py index dc19f916fe..c564528b40 100644 --- a/var/spack/repos/builtin/packages/warpx/package.py +++ b/var/spack/repos/builtin/packages/warpx/package.py @@ -68,7 +68,8 @@ class Warpx(MakefilePackage): def edit(self, spec, prefix): comp = 'gcc' - vendors = {'%gcc': 'gcc', '%intel': 'intel', '%clang': 'llvm'} + vendors = {'%gcc': 'gcc', '%intel': 'intel', + '%apple-clang': 'llvm', '%clang': 'llvm'} for key, value in vendors.items(): if self.spec.satisfies(key): comp = value diff --git a/var/spack/repos/builtin/packages/xios/package.py b/var/spack/repos/builtin/packages/xios/package.py index 54eca9fead..2b5c6f9dae 100644 --- a/var/spack/repos/builtin/packages/xios/package.py +++ b/var/spack/repos/builtin/packages/xios/package.py @@ -31,6 +31,7 @@ class Xios(Package): # Workaround bug #17782 in llvm, where reading a double # followed by a character is broken (e.g. duration '1d'): + patch('llvm_bug_17782.patch', when='@1.1: %apple-clang') patch('llvm_bug_17782.patch', when='@1.1: %clang') depends_on('netcdf-c+mpi') @@ -45,6 +46,13 @@ class Xios(Package): @when('%clang') def patch(self): + self.patch_llvm() + + @when('%apple-clang') + def patch(self): + self.patch_llvm() + + def patch_llvm(self): """Fix type references that are ambiguous for clang.""" for dirpath, dirnames, filenames in os.walk('src'): for filename in filenames: @@ -99,12 +107,13 @@ OASIS_LIB="" param['BOOST_LIB_DIR'] = spec['boost'].prefix.lib param['BLITZ_INC_DIR'] = spec['blitz'].prefix.include param['BLITZ_LIB_DIR'] = spec['blitz'].prefix.lib - if spec.satisfies('%clang platform=darwin'): + if spec.satisfies('%apple-clang'): param['LIBCXX'] = '-lc++' else: param['LIBCXX'] = '-lstdc++' - if any(map(spec.satisfies, ('%gcc', '%intel', '%clang'))): + if any(map(spec.satisfies, + ('%gcc', '%intel', '%apple-clang', '%clang'))): text = r""" %CCOMPILER {MPICXX} %FCOMPILER {MPIFC} diff --git a/var/spack/repos/builtin/packages/xsdktrilinos/package.py b/var/spack/repos/builtin/packages/xsdktrilinos/package.py index b679ee7277..effb4404b0 100644 --- a/var/spack/repos/builtin/packages/xsdktrilinos/package.py +++ b/var/spack/repos/builtin/packages/xsdktrilinos/package.py @@ -65,7 +65,9 @@ class Xsdktrilinos(CMakePackage): ]) # Fortran lib - if spec.satisfies('%gcc') or spec.satisfies('%clang'): + if (spec.satisfies('%gcc') or + spec.satisfies('%clang') or + spec.satisfies('%apple-clang')): libgfortran = os.path.dirname(os.popen( '%s --print-file-name libgfortran.a' % join_path(mpi_bin, 'mpif90')).read()) diff --git a/var/spack/repos/builtin/packages/yaml-cpp/package.py b/var/spack/repos/builtin/packages/yaml-cpp/package.py index 11f1f9fbef..a83471f23a 100644 --- a/var/spack/repos/builtin/packages/yaml-cpp/package.py +++ b/var/spack/repos/builtin/packages/yaml-cpp/package.py @@ -35,9 +35,7 @@ class YamlCpp(CMakePackage): conflicts('%gcc@:4.7', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") conflicts('%clang@:3.3.0', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") - # currently we can't check for apple-clang's version - # conflicts('%clang@:4.0.0-apple', when='@0.6.0:', - # msg="versions 0.6.0: require c++11 support") + conflicts('%apple-clang@:4.0.0', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") conflicts('%intel@:11.1', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") conflicts('%xl@:13.1', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") conflicts('%xl_r@:13.1', when='@0.6.0:', msg="versions 0.6.0: require c++11 support") |