xref: /aosp_15_r20/external/pytorch/tools/setup_helpers/env.py (revision da0073e96a02ea20f0ac840b70461e3646d07c45)
1*da0073e9SAndroid Build Coastguard Workerfrom __future__ import annotations
2*da0073e9SAndroid Build Coastguard Worker
3*da0073e9SAndroid Build Coastguard Workerimport os
4*da0073e9SAndroid Build Coastguard Workerimport platform
5*da0073e9SAndroid Build Coastguard Workerimport struct
6*da0073e9SAndroid Build Coastguard Workerimport sys
7*da0073e9SAndroid Build Coastguard Workerfrom itertools import chain
8*da0073e9SAndroid Build Coastguard Workerfrom typing import cast, Iterable
9*da0073e9SAndroid Build Coastguard Worker
10*da0073e9SAndroid Build Coastguard Worker
11*da0073e9SAndroid Build Coastguard WorkerIS_WINDOWS = platform.system() == "Windows"
12*da0073e9SAndroid Build Coastguard WorkerIS_DARWIN = platform.system() == "Darwin"
13*da0073e9SAndroid Build Coastguard WorkerIS_LINUX = platform.system() == "Linux"
14*da0073e9SAndroid Build Coastguard Worker
15*da0073e9SAndroid Build Coastguard WorkerIS_CONDA = (
16*da0073e9SAndroid Build Coastguard Worker    "conda" in sys.version
17*da0073e9SAndroid Build Coastguard Worker    or "Continuum" in sys.version
18*da0073e9SAndroid Build Coastguard Worker    or any(x.startswith("CONDA") for x in os.environ)
19*da0073e9SAndroid Build Coastguard Worker)
20*da0073e9SAndroid Build Coastguard WorkerCONDA_DIR = os.path.join(os.path.dirname(sys.executable), "..")
21*da0073e9SAndroid Build Coastguard Worker
22*da0073e9SAndroid Build Coastguard WorkerIS_64BIT = struct.calcsize("P") == 8
23*da0073e9SAndroid Build Coastguard Worker
24*da0073e9SAndroid Build Coastguard WorkerBUILD_DIR = "build"
25*da0073e9SAndroid Build Coastguard Worker
26*da0073e9SAndroid Build Coastguard Worker
27*da0073e9SAndroid Build Coastguard Workerdef check_env_flag(name: str, default: str = "") -> bool:
28*da0073e9SAndroid Build Coastguard Worker    return os.getenv(name, default).upper() in ["ON", "1", "YES", "TRUE", "Y"]
29*da0073e9SAndroid Build Coastguard Worker
30*da0073e9SAndroid Build Coastguard Worker
31*da0073e9SAndroid Build Coastguard Workerdef check_negative_env_flag(name: str, default: str = "") -> bool:
32*da0073e9SAndroid Build Coastguard Worker    return os.getenv(name, default).upper() in ["OFF", "0", "NO", "FALSE", "N"]
33*da0073e9SAndroid Build Coastguard Worker
34*da0073e9SAndroid Build Coastguard Worker
35*da0073e9SAndroid Build Coastguard Workerdef gather_paths(env_vars: Iterable[str]) -> list[str]:
36*da0073e9SAndroid Build Coastguard Worker    return list(chain(*(os.getenv(v, "").split(os.pathsep) for v in env_vars)))
37*da0073e9SAndroid Build Coastguard Worker
38*da0073e9SAndroid Build Coastguard Worker
39*da0073e9SAndroid Build Coastguard Workerdef lib_paths_from_base(base_path: str) -> list[str]:
40*da0073e9SAndroid Build Coastguard Worker    return [os.path.join(base_path, s) for s in ["lib/x64", "lib", "lib64"]]
41*da0073e9SAndroid Build Coastguard Worker
42*da0073e9SAndroid Build Coastguard Worker
43*da0073e9SAndroid Build Coastguard Worker# We promised that CXXFLAGS should also be affected by CFLAGS
44*da0073e9SAndroid Build Coastguard Workerif "CFLAGS" in os.environ and "CXXFLAGS" not in os.environ:
45*da0073e9SAndroid Build Coastguard Worker    os.environ["CXXFLAGS"] = os.environ["CFLAGS"]
46*da0073e9SAndroid Build Coastguard Worker
47*da0073e9SAndroid Build Coastguard Worker
48*da0073e9SAndroid Build Coastguard Workerclass BuildType:
49*da0073e9SAndroid Build Coastguard Worker    """Checks build type. The build type will be given in :attr:`cmake_build_type_env`. If :attr:`cmake_build_type_env`
50*da0073e9SAndroid Build Coastguard Worker    is ``None``, then the build type will be inferred from ``CMakeCache.txt``. If ``CMakeCache.txt`` does not exist,
51*da0073e9SAndroid Build Coastguard Worker    os.environ['CMAKE_BUILD_TYPE'] will be used.
52*da0073e9SAndroid Build Coastguard Worker
53*da0073e9SAndroid Build Coastguard Worker    Args:
54*da0073e9SAndroid Build Coastguard Worker      cmake_build_type_env (str): The value of os.environ['CMAKE_BUILD_TYPE']. If None, the actual build type will be
55*da0073e9SAndroid Build Coastguard Worker        inferred.
56*da0073e9SAndroid Build Coastguard Worker
57*da0073e9SAndroid Build Coastguard Worker    """
58*da0073e9SAndroid Build Coastguard Worker
59*da0073e9SAndroid Build Coastguard Worker    def __init__(self, cmake_build_type_env: str | None = None) -> None:
60*da0073e9SAndroid Build Coastguard Worker        if cmake_build_type_env is not None:
61*da0073e9SAndroid Build Coastguard Worker            self.build_type_string = cmake_build_type_env
62*da0073e9SAndroid Build Coastguard Worker            return
63*da0073e9SAndroid Build Coastguard Worker
64*da0073e9SAndroid Build Coastguard Worker        cmake_cache_txt = os.path.join(BUILD_DIR, "CMakeCache.txt")
65*da0073e9SAndroid Build Coastguard Worker        if os.path.isfile(cmake_cache_txt):
66*da0073e9SAndroid Build Coastguard Worker            # Found CMakeCache.txt. Use the build type specified in it.
67*da0073e9SAndroid Build Coastguard Worker            from .cmake_utils import get_cmake_cache_variables_from_file
68*da0073e9SAndroid Build Coastguard Worker
69*da0073e9SAndroid Build Coastguard Worker            with open(cmake_cache_txt) as f:
70*da0073e9SAndroid Build Coastguard Worker                cmake_cache_vars = get_cmake_cache_variables_from_file(f)
71*da0073e9SAndroid Build Coastguard Worker            # Normally it is anti-pattern to determine build type from CMAKE_BUILD_TYPE because it is not used for
72*da0073e9SAndroid Build Coastguard Worker            # multi-configuration build tools, such as Visual Studio and XCode. But since we always communicate with
73*da0073e9SAndroid Build Coastguard Worker            # CMake using CMAKE_BUILD_TYPE from our Python scripts, this is OK here.
74*da0073e9SAndroid Build Coastguard Worker            self.build_type_string = cast(str, cmake_cache_vars["CMAKE_BUILD_TYPE"])
75*da0073e9SAndroid Build Coastguard Worker        else:
76*da0073e9SAndroid Build Coastguard Worker            self.build_type_string = os.environ.get("CMAKE_BUILD_TYPE", "Release")
77*da0073e9SAndroid Build Coastguard Worker
78*da0073e9SAndroid Build Coastguard Worker    def is_debug(self) -> bool:
79*da0073e9SAndroid Build Coastguard Worker        "Checks Debug build."
80*da0073e9SAndroid Build Coastguard Worker        return self.build_type_string == "Debug"
81*da0073e9SAndroid Build Coastguard Worker
82*da0073e9SAndroid Build Coastguard Worker    def is_rel_with_deb_info(self) -> bool:
83*da0073e9SAndroid Build Coastguard Worker        "Checks RelWithDebInfo build."
84*da0073e9SAndroid Build Coastguard Worker        return self.build_type_string == "RelWithDebInfo"
85*da0073e9SAndroid Build Coastguard Worker
86*da0073e9SAndroid Build Coastguard Worker    def is_release(self) -> bool:
87*da0073e9SAndroid Build Coastguard Worker        "Checks Release build."
88*da0073e9SAndroid Build Coastguard Worker        return self.build_type_string == "Release"
89*da0073e9SAndroid Build Coastguard Worker
90*da0073e9SAndroid Build Coastguard Worker
91*da0073e9SAndroid Build Coastguard Worker# hotpatch environment variable 'CMAKE_BUILD_TYPE'. 'CMAKE_BUILD_TYPE' always prevails over DEBUG or REL_WITH_DEB_INFO.
92*da0073e9SAndroid Build Coastguard Workerif "CMAKE_BUILD_TYPE" not in os.environ:
93*da0073e9SAndroid Build Coastguard Worker    if check_env_flag("DEBUG"):
94*da0073e9SAndroid Build Coastguard Worker        os.environ["CMAKE_BUILD_TYPE"] = "Debug"
95*da0073e9SAndroid Build Coastguard Worker    elif check_env_flag("REL_WITH_DEB_INFO"):
96*da0073e9SAndroid Build Coastguard Worker        os.environ["CMAKE_BUILD_TYPE"] = "RelWithDebInfo"
97*da0073e9SAndroid Build Coastguard Worker    else:
98*da0073e9SAndroid Build Coastguard Worker        os.environ["CMAKE_BUILD_TYPE"] = "Release"
99*da0073e9SAndroid Build Coastguard Worker
100*da0073e9SAndroid Build Coastguard Workerbuild_type = BuildType()
101