Skip to content

Commit 00ea84c

Browse files
zaniebadiantek
andcommitted
Add ARM64 builds for Windows
Co-authored-by: Adrian Antkowiak <[email protected]>
1 parent 522f6b3 commit 00ea84c

File tree

2 files changed

+47
-7
lines changed

2 files changed

+47
-7
lines changed

.github/workflows/windows.yml

+1
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ jobs:
5050
vcvars:
5151
- 'vcvars32.bat'
5252
- 'vcvars64.bat'
53+
- 'vcvarsamd64_arm64.bat'
5354
options:
5455
- 'pgo'
5556

cpython-windows/build.py

+46-7
Original file line numberDiff line numberDiff line change
@@ -438,6 +438,8 @@ def hack_props(
438438
suffix = b"-x64"
439439
elif arch == "win32":
440440
suffix = b""
441+
elif arch == "arm64":
442+
suffix = b""
441443
else:
442444
raise Exception("unhandled architecture: %s" % arch)
443445

@@ -917,9 +919,11 @@ def build_openssl_for_arch(
917919
elif arch == "amd64":
918920
configure = "VC-WIN64A"
919921
prefix = "64"
922+
elif arch == "arm64":
923+
configure = "VC-WIN64-ARM"
924+
prefix = "arm64"
920925
else:
921-
print("invalid architecture: %s" % arch)
922-
sys.exit(1)
926+
raise Exception("unhandled architecture: %s" % arch)
923927

924928
# The official CPython OpenSSL builds hack ms/uplink.c to change the
925929
# ``GetModuleHandle(NULL)`` invocation to load things from _ssl.pyd
@@ -967,6 +971,12 @@ def build_openssl_for_arch(
967971
log("copying %s to %s" % (source, dest))
968972
shutil.copyfile(source, dest)
969973

974+
# Copy `applink.c` to the include directory.
975+
source_applink = source_root / "ms" / "applink.c"
976+
dest_applink = install_root / "include" / "openssl" / "applink.c"
977+
log("copying %s to %s" % (source_applink, dest_applink))
978+
shutil.copyfile(source_applink, dest_applink)
979+
970980

971981
def build_openssl(
972982
entry: str,
@@ -988,6 +998,7 @@ def build_openssl(
988998

989999
root_32 = td / "x86"
9901000
root_64 = td / "x64"
1001+
root_arm64 = td / "arm64"
9911002

9921003
if arch == "x86":
9931004
root_32.mkdir()
@@ -1011,13 +1022,28 @@ def build_openssl(
10111022
root_64,
10121023
jom_archive=jom_archive,
10131024
)
1025+
elif arch == "arm64":
1026+
root_arm64.mkdir()
1027+
build_openssl_for_arch(
1028+
perl_path,
1029+
"arm64",
1030+
openssl_archive,
1031+
openssl_version,
1032+
nasm_archive,
1033+
root_arm64,
1034+
jom_archive=jom_archive,
1035+
)
10141036
else:
1015-
raise ValueError("unhandled arch: %s" % arch)
1037+
raise Exception("unhandled architecture: %s" % arch)
10161038

10171039
install = td / "out"
10181040

10191041
if arch == "x86":
10201042
shutil.copytree(root_32 / "install" / "32", install / "openssl" / "win32")
1043+
elif arch == "arm64":
1044+
shutil.copytree(
1045+
root_arm64 / "install" / "arm64", install / "openssl" / "arm64"
1046+
)
10211047
else:
10221048
shutil.copytree(root_64 / "install" / "64", install / "openssl" / "amd64")
10231049

@@ -1088,9 +1114,14 @@ def build_libffi(
10881114
if arch == "x86":
10891115
args.append("-x86")
10901116
artifacts_path = ffi_source_path / "i686-pc-cygwin"
1091-
else:
1117+
elif arch == "arm64":
1118+
args.append("-arm64")
1119+
artifacts_path = ffi_source_path / "aarch64-w64-cygwin"
1120+
elif arch == "amd64":
10921121
args.append("-x64")
10931122
artifacts_path = ffi_source_path / "x86_64-w64-cygwin"
1123+
else:
1124+
raise Exception("unhandled architecture: %s" % arch)
10941125

10951126
subprocess.run(args, env=env, check=True)
10961127

@@ -1460,8 +1491,11 @@ def build_cpython(
14601491
elif arch == "x86":
14611492
build_platform = "win32"
14621493
build_directory = "win32"
1494+
elif arch == "arm64":
1495+
build_platform = "arm64"
1496+
build_directory = "arm64"
14631497
else:
1464-
raise ValueError("unhandled arch: %s" % arch)
1498+
raise Exception("unhandled architecture: %s" % arch)
14651499

14661500
with tempfile.TemporaryDirectory(prefix="python-build-") as td:
14671501
td = pathlib.Path(td)
@@ -1491,7 +1525,7 @@ def build_cpython(
14911525

14921526
# We need all the OpenSSL library files in the same directory to appease
14931527
# install rules.
1494-
openssl_arch = {"amd64": "amd64", "x86": "win32"}[arch]
1528+
openssl_arch = {"amd64": "amd64", "x86": "win32", "arm64": "arm64"}[arch]
14951529
openssl_root = td / "openssl" / openssl_arch
14961530
openssl_bin_path = openssl_root / "bin"
14971531
openssl_lib_path = openssl_root / "lib"
@@ -1930,9 +1964,14 @@ def main() -> None:
19301964
if os.environ.get("Platform") == "x86":
19311965
target_triple = "i686-pc-windows-msvc"
19321966
arch = "x86"
1933-
else:
1967+
elif os.environ.get("Platform") == "arm64":
1968+
target_triple = "aarch64-pc-windows-msvc"
1969+
arch = "arm64"
1970+
elif os.environ.get("Platform") == "x64":
19341971
target_triple = "x86_64-pc-windows-msvc"
19351972
arch = "amd64"
1973+
else:
1974+
raise Exception("unhandled architecture: %s" % os.environ.get("Platform"))
19361975

19371976
# TODO need better dependency checking.
19381977

0 commit comments

Comments
 (0)