summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/spack/llnl/util/filesystem.py9
-rw-r--r--lib/spack/spack/bootstrap/core.py3
-rw-r--r--lib/spack/spack/compiler.py14
-rw-r--r--lib/spack/spack/compilers/__init__.py2
-rw-r--r--lib/spack/spack/compilers/msvc.py8
-rw-r--r--lib/spack/spack/spec.py10
-rw-r--r--lib/spack/spack/test/builder.py5
-rw-r--r--lib/spack/spack/test/cmd/external.py2
-rw-r--r--lib/spack/spack/test/cmd/list.py19
-rw-r--r--lib/spack/spack/test/cmd/uninstall.py4
-rw-r--r--lib/spack/spack/test/concretize.py16
-rw-r--r--lib/spack/spack/test/concretize_preferences.py4
-rw-r--r--lib/spack/spack/test/conftest.py11
-rw-r--r--lib/spack/spack/test/database.py4
-rw-r--r--lib/spack/spack/test/installer.py2
-rw-r--r--lib/spack/spack/test/spec_syntax.py5
-rw-r--r--lib/spack/spack/util/path.py2
17 files changed, 88 insertions, 32 deletions
diff --git a/lib/spack/llnl/util/filesystem.py b/lib/spack/llnl/util/filesystem.py
index 388c6fd173..8e664cc0a9 100644
--- a/lib/spack/llnl/util/filesystem.py
+++ b/lib/spack/llnl/util/filesystem.py
@@ -99,7 +99,9 @@ def getuid():
def rename(src, dst):
# On Windows, os.rename will fail if the destination file already exists
if is_windows:
- if os.path.exists(dst):
+ # Windows path existence checks will sometimes fail on junctions/links/symlinks
+ # so check for that case
+ if os.path.exists(dst) or os.path.islink(dst):
os.remove(dst)
os.rename(src, dst)
@@ -288,7 +290,10 @@ def filter_file(regex, repl, *filenames, **kwargs):
shutil.copy(filename, tmp_filename)
try:
- extra_kwargs = {"errors": "surrogateescape"}
+ # To avoid translating line endings (\n to \r\n and vis versa)
+ # we force os.open to ignore translations and use the line endings
+ # the file comes with
+ extra_kwargs = {"errors": "surrogateescape", "newline": ""}
# Open as a text file and filter until the end of the file is
# reached or we found a marker in the line if it was specified
diff --git a/lib/spack/spack/bootstrap/core.py b/lib/spack/spack/bootstrap/core.py
index 9cf25b29e9..e8cb429fa8 100644
--- a/lib/spack/spack/bootstrap/core.py
+++ b/lib/spack/spack/bootstrap/core.py
@@ -545,8 +545,9 @@ def ensure_core_dependencies():
"""Ensure the presence of all the core dependencies."""
if sys.platform.lower() == "linux":
ensure_patchelf_in_path_or_raise()
+ if not IS_WINDOWS:
+ ensure_gpg_in_path_or_raise()
ensure_clingo_importable_or_raise()
- ensure_gpg_in_path_or_raise()
def all_core_root_specs():
diff --git a/lib/spack/spack/compiler.py b/lib/spack/spack/compiler.py
index 8b3afefa42..52c2db8c79 100644
--- a/lib/spack/spack/compiler.py
+++ b/lib/spack/spack/compiler.py
@@ -9,6 +9,7 @@ import os
import platform
import re
import shutil
+import sys
import tempfile
from typing import List, Optional, Sequence
@@ -27,6 +28,8 @@ from spack.util.path import system_path_filter
__all__ = ["Compiler"]
+is_windows = sys.platform == "win32"
+
@llnl.util.lang.memoized
def _get_compiler_version_output(compiler_path, version_arg, ignore_errors=()):
@@ -592,7 +595,16 @@ class Compiler(object):
# defined for the compiler
compiler_names = getattr(cls, "{0}_names".format(language))
prefixes = [""] + cls.prefixes
- suffixes = [""] + cls.suffixes
+ suffixes = [""]
+ # Windows compilers generally have an extension of some sort
+ # as do most files on Windows, handle that case here
+ if is_windows:
+ ext = r"\.(?:exe|bat)"
+ cls_suf = [suf + ext for suf in cls.suffixes]
+ ext_suf = [ext]
+ suffixes = suffixes + cls.suffixes + cls_suf + ext_suf
+ else:
+ suffixes = suffixes + cls.suffixes
regexp_fmt = r"^({0}){1}({2})$"
return [
re.compile(regexp_fmt.format(prefix, re.escape(name), suffix))
diff --git a/lib/spack/spack/compilers/__init__.py b/lib/spack/spack/compilers/__init__.py
index d4aa54282b..3df8c4b218 100644
--- a/lib/spack/spack/compilers/__init__.py
+++ b/lib/spack/spack/compilers/__init__.py
@@ -722,6 +722,8 @@ def make_compiler_list(detected_versions):
compiler_cls = spack.compilers.class_for_compiler_name(compiler_name)
spec = spack.spec.CompilerSpec(compiler_cls.name, version)
paths = [paths.get(x, None) for x in ("cc", "cxx", "f77", "fc")]
+ # TODO: johnwparent - revist the following line as per discussion at:
+ # https://github.com/spack/spack/pull/33385/files#r1040036318
target = archspec.cpu.host()
compiler = compiler_cls(spec, operating_system, str(target.family), paths)
return [compiler]
diff --git a/lib/spack/spack/compilers/msvc.py b/lib/spack/spack/compilers/msvc.py
index f26dcc78ec..d7576b78e6 100644
--- a/lib/spack/spack/compilers/msvc.py
+++ b/lib/spack/spack/compilers/msvc.py
@@ -42,16 +42,16 @@ def get_valid_fortran_pth(comp_ver):
class Msvc(Compiler):
# Subclasses use possible names of C compiler
- cc_names: List[str] = ["cl.exe"]
+ cc_names: List[str] = ["cl"]
# Subclasses use possible names of C++ compiler
- cxx_names: List[str] = ["cl.exe"]
+ cxx_names: List[str] = ["cl"]
# Subclasses use possible names of Fortran 77 compiler
- f77_names: List[str] = ["ifx.exe"]
+ f77_names: List[str] = ["ifx"]
# Subclasses use possible names of Fortran 90 compiler
- fc_names: List[str] = ["ifx.exe"]
+ fc_names: List[str] = ["ifx"]
# Named wrapper links within build_env_path
# Due to the challenges of supporting compiler wrappers
diff --git a/lib/spack/spack/spec.py b/lib/spack/spack/spec.py
index 6524bf3bef..012a75c89c 100644
--- a/lib/spack/spack/spec.py
+++ b/lib/spack/spack/spec.py
@@ -1289,7 +1289,7 @@ class Spec(object):
# have package.py files for.
self._normal = normal
self._concrete = concrete
- self.external_path = external_path
+ self._external_path = external_path
self.external_modules = Spec._format_module_list(external_modules)
# This attribute is used to store custom information for
@@ -1327,6 +1327,14 @@ class Spec(object):
return modules
@property
+ def external_path(self):
+ return pth.path_to_os_path(self._external_path)[0]
+
+ @external_path.setter
+ def external_path(self, ext_path):
+ self._external_path = ext_path
+
+ @property
def external(self):
return bool(self.external_path) or bool(self.external_modules)
diff --git a/lib/spack/spack/test/builder.py b/lib/spack/spack/test/builder.py
index efba6aacf1..944514b610 100644
--- a/lib/spack/spack/test/builder.py
+++ b/lib/spack/spack/test/builder.py
@@ -3,6 +3,7 @@
#
# SPDX-License-Identifier: (Apache-2.0 OR MIT)
import os.path
+import sys
import pytest
@@ -123,6 +124,10 @@ def test_old_style_compatibility_with_super(spec_str, method_name, expected):
assert value == expected
+@pytest.mark.skipif(
+ sys.platform == "win32",
+ reason="log_ouput cannot currently be used outside of subprocess on Windows",
+)
@pytest.mark.regression("33928")
@pytest.mark.usefixtures("builder_test_repository", "config", "working_env")
@pytest.mark.disable_clean_stage_check
diff --git a/lib/spack/spack/test/cmd/external.py b/lib/spack/spack/test/cmd/external.py
index 1944a2e940..9b9376ecb1 100644
--- a/lib/spack/spack/test/cmd/external.py
+++ b/lib/spack/spack/test/cmd/external.py
@@ -347,7 +347,7 @@ def test_overriding_prefix(mock_executable, mutable_config, monkeypatch, _platfo
assert "externals" in packages_yaml["gcc"]
externals = packages_yaml["gcc"]["externals"]
assert len(externals) == 1
- assert externals[0]["prefix"] == "/opt/gcc/bin"
+ assert externals[0]["prefix"] == os.path.sep + os.path.join("opt", "gcc", "bin")
def test_new_entries_are_reported_correctly(
diff --git a/lib/spack/spack/test/cmd/list.py b/lib/spack/spack/test/cmd/list.py
index ed5b2574f0..3ebcb4fa39 100644
--- a/lib/spack/spack/test/cmd/list.py
+++ b/lib/spack/spack/test/cmd/list.py
@@ -3,6 +3,7 @@
#
# SPDX-License-Identifier: (Apache-2.0 OR MIT)
+import sys
from textwrap import dedent
from spack.main import SpackCommand
@@ -18,12 +19,24 @@ def test_list():
def test_list_cli_output_format(mock_tty_stdout):
out = list("mpileaks")
- assert out == dedent(
- """\
+ # Currently logging on Windows detaches stdout
+ # from the terminal so we miss some output during tests
+ # TODO: (johnwparent): Once logging is amended on Windows,
+ # restore this test
+ if not sys.platform == "win32":
+ out_str = dedent(
+ """\
mpileaks
==> 1 packages
"""
- )
+ )
+ else:
+ out_str = dedent(
+ """\
+ mpileaks
+ """
+ )
+ assert out == out_str
def test_list_filter(mock_packages):
diff --git a/lib/spack/spack/test/cmd/uninstall.py b/lib/spack/spack/test/cmd/uninstall.py
index be9fa3aa16..7798e03533 100644
--- a/lib/spack/spack/test/cmd/uninstall.py
+++ b/lib/spack/spack/test/cmd/uninstall.py
@@ -208,9 +208,7 @@ def test_in_memory_consistency_when_uninstalling(mutable_database, monkeypatch):
# Note: I want to use https://docs.pytest.org/en/7.1.x/how-to/skipping.html#skip-all-test-functions-of-a-class-or-module
# the style formatter insists on separating these two lines.
-pytest.mark.skipif(sys.platform == "win32", reason="Envs unsupported on Windows")
-
-
+@pytest.mark.skipif(sys.platform == "win32", reason="Envs unsupported on Windows")
class TestUninstallFromEnv(object):
"""Tests an installation with two environments e1 and e2, which each have
shared package installations:
diff --git a/lib/spack/spack/test/concretize.py b/lib/spack/spack/test/concretize.py
index 0ddc93b5f6..83597c7f3d 100644
--- a/lib/spack/spack/test/concretize.py
+++ b/lib/spack/spack/test/concretize.py
@@ -3,7 +3,6 @@
#
# SPDX-License-Identifier: (Apache-2.0 OR MIT)
import os
-import posixpath
import sys
import jinja2
@@ -339,7 +338,7 @@ class TestConcretize(object):
assert spec.satisfies("^openblas cflags='-g'")
@pytest.mark.skipif(
- os.environ.get("SPACK_TEST_SOLVER") == "original" or sys.platform == "win32",
+ os.environ.get("SPACK_TEST_SOLVER") == "original",
reason="Optional compiler propagation isn't deprecated for original concretizer",
)
def test_concretize_compiler_flag_does_not_propagate(self):
@@ -349,7 +348,7 @@ class TestConcretize(object):
assert not spec.satisfies("^openblas cflags='-g'")
@pytest.mark.skipif(
- os.environ.get("SPACK_TEST_SOLVER") == "original" or sys.platform == "win32",
+ os.environ.get("SPACK_TEST_SOLVER") == "original",
reason="Optional compiler propagation isn't deprecated for original concretizer",
)
def test_concretize_propagate_compiler_flag_not_passed_to_dependent(self):
@@ -449,7 +448,7 @@ class TestConcretize(object):
s.concretize()
@pytest.mark.skipif(
- os.environ.get("SPACK_TEST_SOLVER") == "original" or sys.platform == "win32",
+ os.environ.get("SPACK_TEST_SOLVER") == "original",
reason="Optional compiler propagation isn't deprecated for original concretizer",
)
def test_concretize_propagate_disabled_variant(self):
@@ -466,7 +465,6 @@ class TestConcretize(object):
assert spec.satisfies("^openblas+shared")
- @pytest.mark.skipif(sys.platform == "win32", reason="No Compiler for Arch on Win")
def test_no_matching_compiler_specs(self, mock_low_high_config):
# only relevant when not building compilers as needed
with spack.concretize.enable_compiler_existence_check():
@@ -527,7 +525,7 @@ class TestConcretize(object):
def test_external_package(self):
spec = Spec("externaltool%gcc")
spec.concretize()
- assert spec["externaltool"].external_path == posixpath.sep + posixpath.join(
+ assert spec["externaltool"].external_path == os.path.sep + os.path.join(
"path", "to", "external_tool"
)
assert "externalprereq" not in spec
@@ -558,10 +556,10 @@ class TestConcretize(object):
def test_external_and_virtual(self):
spec = Spec("externaltest")
spec.concretize()
- assert spec["externaltool"].external_path == posixpath.sep + posixpath.join(
+ assert spec["externaltool"].external_path == os.path.sep + os.path.join(
"path", "to", "external_tool"
)
- assert spec["stuff"].external_path == posixpath.sep + posixpath.join(
+ assert spec["stuff"].external_path == os.path.sep + os.path.join(
"path", "to", "external_virtual_gcc"
)
assert spec["externaltool"].compiler.satisfies("gcc")
@@ -1815,7 +1813,6 @@ class TestConcretize(object):
c = s.concretized()
assert hash in str(c)
- @pytest.mark.skipif(sys.platform == "win32", reason="Not supported on Windows (yet)")
@pytest.mark.parametrize("git_ref", ("a" * 40, "0.2.15", "main"))
def test_git_ref_version_is_equivalent_to_specified_version(self, git_ref):
if spack.config.get("config:concretizer") == "original":
@@ -1827,7 +1824,6 @@ class TestConcretize(object):
assert s.satisfies("@develop")
assert s.satisfies("@0.1:")
- @pytest.mark.skipif(sys.platform == "win32", reason="Not supported on Windows (yet)")
@pytest.mark.parametrize("git_ref", ("a" * 40, "0.2.15", "fbranch"))
def test_git_ref_version_errors_if_unknown_version(self, git_ref):
if spack.config.get("config:concretizer") == "original":
diff --git a/lib/spack/spack/test/concretize_preferences.py b/lib/spack/spack/test/concretize_preferences.py
index b0ae008a72..1ebbfacfdd 100644
--- a/lib/spack/spack/test/concretize_preferences.py
+++ b/lib/spack/spack/test/concretize_preferences.py
@@ -270,7 +270,7 @@ mpich:
# ensure that once config is in place, external is used
spec = Spec("mpi")
spec.concretize()
- assert spec["mpich"].external_path == os.sep + os.path.join("dummy", "path")
+ assert spec["mpich"].external_path == os.path.sep + os.path.join("dummy", "path")
def test_external_module(self, monkeypatch):
"""Test that packages can find externals specified by module
@@ -305,7 +305,7 @@ mpi:
# ensure that once config is in place, external is used
spec = Spec("mpi")
spec.concretize()
- assert spec["mpich"].external_path == "/dummy/path"
+ assert spec["mpich"].external_path == os.path.sep + os.path.join("dummy", "path")
def test_buildable_false(self):
conf = syaml.load_config(
diff --git a/lib/spack/spack/test/conftest.py b/lib/spack/spack/test/conftest.py
index 0449cd8cf8..2d9e72a89e 100644
--- a/lib/spack/spack/test/conftest.py
+++ b/lib/spack/spack/test/conftest.py
@@ -259,6 +259,17 @@ def _verify_executables_noop(*args):
return None
+def _host():
+ """Mock archspec host so there is no inconsistency on the Windows platform
+ This function cannot be local as it needs to be pickleable"""
+ return archspec.cpu.Microarchitecture("x86_64", [], "generic", [], {}, 0)
+
+
+@pytest.fixture(scope="function")
+def archspec_host_is_spack_test_host(monkeypatch):
+ monkeypatch.setattr(archspec.cpu, "host", _host)
+
+
#
# Disable checks on compiler executable existence
#
diff --git a/lib/spack/spack/test/database.py b/lib/spack/spack/test/database.py
index 99e1b5c470..387daba1b5 100644
--- a/lib/spack/spack/test/database.py
+++ b/lib/spack/spack/test/database.py
@@ -719,13 +719,13 @@ def test_external_entries_in_db(mutable_database):
assert not rec.spec.external_modules
rec = mutable_database.get_record("externaltool")
- assert rec.spec.external_path == os.sep + os.path.join("path", "to", "external_tool")
+ assert rec.spec.external_path == os.path.sep + os.path.join("path", "to", "external_tool")
assert not rec.spec.external_modules
assert rec.explicit is False
rec.spec.package.do_install(fake=True, explicit=True)
rec = mutable_database.get_record("externaltool")
- assert rec.spec.external_path == os.sep + os.path.join("path", "to", "external_tool")
+ assert rec.spec.external_path == os.path.sep + os.path.join("path", "to", "external_tool")
assert not rec.spec.external_modules
assert rec.explicit is True
diff --git a/lib/spack/spack/test/installer.py b/lib/spack/spack/test/installer.py
index 4c85f4ba26..8a446c650e 100644
--- a/lib/spack/spack/test/installer.py
+++ b/lib/spack/spack/test/installer.py
@@ -488,7 +488,7 @@ def test_update_tasks_for_compiler_packages_as_compiler(mock_packages, config, m
def test_bootstrapping_compilers_with_different_names_from_spec(
- install_mockery, mutable_config, mock_fetch
+ install_mockery, mutable_config, mock_fetch, archspec_host_is_spack_test_host
):
with spack.config.override("config:install_missing_compilers", True):
with spack.concretize.disable_compiler_existence_check():
diff --git a/lib/spack/spack/test/spec_syntax.py b/lib/spack/spack/test/spec_syntax.py
index 97c1a9a3ce..1a7d52e781 100644
--- a/lib/spack/spack/test/spec_syntax.py
+++ b/lib/spack/spack/test/spec_syntax.py
@@ -3,6 +3,7 @@
#
# SPDX-License-Identifier: (Apache-2.0 OR MIT)
import itertools
+import sys
import pytest
@@ -11,6 +12,8 @@ import spack.spec
import spack.variant
from spack.parser import SpecParser, SpecTokenizationError, Token, TokenType
+is_windows = sys.platform == "win32"
+
def simple_package_name(name):
"""A simple package name in canonical form"""
@@ -834,6 +837,7 @@ def test_error_conditions(text, exc_cls):
SpecParser(text).next_spec()
+@pytest.mark.skipif(is_windows, reason="Spec parsing does not currently support Windows paths")
def test_parse_specfile_simple(specfile_for, tmpdir):
specfile = tmpdir.join("libdwarf.json")
s = specfile_for("libdwarf", specfile)
@@ -879,6 +883,7 @@ def test_parse_filename_missing_slash_as_spec(specfile_for, tmpdir, filename):
)
+@pytest.mark.skipif(is_windows, reason="Spec parsing does not currently support Windows paths")
def test_parse_specfile_dependency(default_mock_concretization, tmpdir):
"""Ensure we can use a specfile as a dependency"""
s = default_mock_concretization("libdwarf")
diff --git a/lib/spack/spack/util/path.py b/lib/spack/spack/util/path.py
index 2dc646418e..9434fc5af4 100644
--- a/lib/spack/spack/util/path.py
+++ b/lib/spack/spack/util/path.py
@@ -122,7 +122,7 @@ def path_to_os_path(*pths):
"""
ret_pths = []
for pth in pths:
- if type(pth) is str and not is_path_url(pth):
+ if isinstance(pth, str) and not is_path_url(pth):
pth = convert_to_platform_path(pth)
ret_pths.append(pth)
return ret_pths