Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

set VSCMD_ARG_TGT_ARCH based on targetted architecture #1876

Merged
merged 10 commits into from
Jul 12, 2024
10 changes: 10 additions & 0 deletions cibuildwheel/windows.py
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,16 @@ def setup_setuptools_cross_compile(
# set the platform name
map_plat = {"32": "win32", "64": "win-amd64", "ARM64": "win-arm64"}
plat_name = map_plat[python_configuration.arch]

# Set environment variable so that setuptools._distutils.get_platform()
# identifies the target, not the host
vscmd_arg_tgt_arch = {"32": "x86", "64": "x64", "ARM64": "arm64"}
current_tgt_arch = vscmd_arg_tgt_arch[python_configuration.arch]
if (env.get("VSCMD_ARG_TGT_ARCH") or current_tgt_arch) != current_tgt_arch:
msg = f"VSCMD_ARG_TGT_ARCH must be set to {current_tgt_arch!r}, got {env['VSCMD_ARG_TGT_ARCH']!r}. If you're setting up MSVC yourself (e.g. using vcvarsall.bat or msvc-dev-cmd), make sure to target the right architecture. Alternatively, run cibuildwheel without configuring MSVC, and let the build backend handle it."
raise errors.FatalError(msg)
env["VSCMD_ARG_TGT_ARCH"] = current_tgt_arch

# (This file must be default/locale encoding, so we can't pass 'encoding')
distutils_cfg.write_text(
textwrap.dedent(
Expand Down
3 changes: 3 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,7 @@ test = [
"pytest-timeout",
"pytest-xdist",
"pytest>=6",
"setuptools",
"tomli_w",
"validate-pyproject",
]
Expand Down Expand Up @@ -140,6 +141,8 @@ disallow_untyped_decorators = true
[[tool.mypy.overrides]]
module = [
"setuptools",
"setuptools._distutils", # needed even if only directly import setuptools._distutils.util
"setuptools._distutils.util",
"pytest", # ignored in pre-commit to speed up check
"bashlex",
"bashlex.*",
Expand Down
92 changes: 92 additions & 0 deletions unit_test/get_platform_test.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
import contextlib
import sys
from pathlib import Path
from typing import Dict

import pytest
import setuptools._distutils.util

from cibuildwheel.errors import FatalError
from cibuildwheel.util import CIProvider, detect_ci_provider
from cibuildwheel.windows import PythonConfiguration, setup_setuptools_cross_compile

# monkeypatching os.name is too flaky. E.g. It works on my machine, but fails in pipeline
if not sys.platform.startswith("win"):
pytest.skip("Windows-only tests", allow_module_level=True)


@contextlib.contextmanager
def patched_environment(monkeypatch: pytest.MonkeyPatch, environment: Dict[str, str]):
with monkeypatch.context() as mp:
for envvar, val in environment.items():
mp.setenv(name=envvar, value=val)
yield


def test_x86(tmp_path: Path, monkeypatch: pytest.MonkeyPatch):
arch = "32"
environment: Dict[str, str] = {}

configuration = PythonConfiguration("irrelevant", arch, "irrelevant", None)

setup_setuptools_cross_compile(tmp_path, configuration, tmp_path, environment)
with patched_environment(monkeypatch, environment):
target_platform = setuptools._distutils.util.get_platform()

assert environment["VSCMD_ARG_TGT_ARCH"] == "x86"
assert target_platform == "win32"


def test_x64(tmp_path: Path, monkeypatch: pytest.MonkeyPatch):
arch = "64"
environment: Dict[str, str] = {}

configuration = PythonConfiguration("irrelevant", arch, "irrelevant", None)

setup_setuptools_cross_compile(tmp_path, configuration, tmp_path, environment)
with patched_environment(monkeypatch, environment):
target_platform = setuptools._distutils.util.get_platform()

assert environment["VSCMD_ARG_TGT_ARCH"] == "x64"
assert target_platform == "win-amd64"


@pytest.mark.skipif(
detect_ci_provider() == CIProvider.azure_pipelines, reason="arm64 not recognised on azure"
)
def test_arm(tmp_path: Path, monkeypatch: pytest.MonkeyPatch):
arch = "ARM64"
environment: Dict[str, str] = {}

configuration = PythonConfiguration("irrelevant", arch, "irrelevant", None)

setup_setuptools_cross_compile(tmp_path, configuration, tmp_path, environment)
with patched_environment(monkeypatch, environment):
target_platform = setuptools._distutils.util.get_platform()

assert environment["VSCMD_ARG_TGT_ARCH"] == "arm64"
assert target_platform == "win-arm64"


def test_env_set(tmp_path: Path):
arch = "32"
environment = {"VSCMD_ARG_TGT_ARCH": "x64"}

configuration = PythonConfiguration("irrelevant", arch, "irrelevant", None)

with pytest.raises(FatalError, match="VSCMD_ARG_TGT_ARCH"):
setup_setuptools_cross_compile(tmp_path, configuration, tmp_path, environment)


def test_env_blank(tmp_path: Path, monkeypatch: pytest.MonkeyPatch):
arch = "32"
environment = {"VSCMD_ARG_TGT_ARCH": ""}

configuration = PythonConfiguration("irrelevant", arch, "irrelevant", None)

setup_setuptools_cross_compile(tmp_path, configuration, tmp_path, environment)
with patched_environment(monkeypatch, environment):
target_platform = setuptools._distutils.util.get_platform()

assert environment["VSCMD_ARG_TGT_ARCH"] == "x86"
assert target_platform == "win32"
Loading