xref: /aosp_15_r20/external/executorch/shim/xplat/executorch/build/env_interface.bzl (revision 523fa7a60841cd1ecfb9cc4201f1ca8b03ed023a)
1"""Interface layer to separate Meta internal build logic and OSS build logic.
2
3For OSS build specific changes, please add it here. For logic that needs to be shared across OSS and Meta internal, please add it to runtime_wrapper.bzl.
4
5Also, do not load this directly from TARGETS or targets.bzl files, instead load runtime_wrapper.bzl.
6
7"""
8
9load(":type_defs.bzl", "is_list", "is_tuple")
10
11_ET_TARGET_PREFIX = "executorch"
12
13# Indicates that an external_dep entry should fall through to the underlying
14# buck rule.
15_EXTERNAL_DEP_FALLTHROUGH = "<fallthrough>"
16
17_EXTERNAL_DEPS = {
18    # ATen C++ library deps
19    "aten-core": [],  # TODO(larryliu0820): Add support
20    # ATen native_functions.yaml file deps
21    "aten-src-path": "//third-party:aten_src_path",
22    "cpuinfo": [],  # TODO(larryliu0820): Add support
23    # Flatbuffer C++ library deps
24    "flatbuffers-api": "//third-party:flatbuffers-api",
25    # Flatc binary
26    "flatc": "//third-party:flatc",
27    # FlatCC cli binary + lib
28    "flatcc": "//third-party:flatcc",
29    "flatcc-cli": "//third-party:flatcc-cli",
30    "flatcc-host": "//third-party:flatcc-host",
31    "flatccrt": "//third-party:flatccrt",
32    # Codegen driver
33    "gen-executorch": "//third-party:gen_executorch",
34    # Commandline flags library
35    "gflags": "//third-party:gflags",
36    "gmock": "//third-party:gmock",
37    "gmock_aten": "//third-party:gmock_aten",
38    "gtest": "//third-party:gtest",
39    "gtest_aten": "//third-party:gtest_aten",
40    "libtorch": "//third-party:libtorch",
41    "libtorch_python": "//third-party:libtorch_python",
42    "prettytable": "//third-party:prettytable",
43    "pybind11": "//third-party:pybind11",
44    "re2": "//extension/llm/third-party:re2",
45    "sentencepiece-py": [],
46    # Core C++ PyTorch functionality like Tensor and ScalarType.
47    "torch-core-cpp": "//third-party:libtorch",
48    "torchgen": "//third-party:torchgen",
49}
50
51def _resolve_external_dep(name):
52    """Return the actual target strings for `external_deps` attribute.
53    Args:
54        name: The name of the dependency.
55    Returns:
56        A list of resolved target strings.
57    """
58    res = _EXTERNAL_DEPS[name]
59    if is_list(res) or is_tuple(res):
60        return res
61    else:
62        return [res]
63
64def _start_with_et_targets(target):
65    prefix = "//" + _ET_TARGET_PREFIX
66    for suffix in ("/", ":"):
67        if target.startswith(prefix + suffix):
68            return True
69    return False
70
71def _patch_platforms(kwargs):
72    """Platforms and apple_sdks are not supported yet, so pop them out from kwargs.
73
74    Args:
75        kwargs: The `kwargs` parameter from a rule.
76
77    Returns:
78        The possibly-modified `kwargs` parameter.
79    """
80    if "platforms" in kwargs:
81        kwargs.pop("platforms")
82    if "apple_sdks" in kwargs:
83        kwargs.pop("apple_sdks")
84    return kwargs
85
86def _patch_deps(kwargs, dep_type):
87    """Remove unsupported deps attributes from kwargs.
88    dep_type: `deps`, `exported_deps`
89    """
90    extra_deps = kwargs.pop("fbcode_" + dep_type, [])
91    kwargs.pop("xplat_" + dep_type, None)  # Also remove the other one.
92    if extra_deps:
93        # This should work even with select() elements.
94        kwargs[dep_type] = kwargs.get(dep_type, []) + extra_deps
95    return kwargs
96
97def _patch_platform_build_mode_flags(kwargs):
98    return kwargs
99
100def _patch_force_static(kwargs):
101    """For OSS cxx library, force static linkage unless specify otherwise.
102    """
103    if "force_static" not in kwargs:
104        kwargs["force_static"] = True
105    return kwargs
106
107def _remove_platform_specific_args(kwargs):
108    """Removes platform specific arguments for BUCK builds
109
110    Args such as *_platform_preprocessor_flags and *_platform_deps are not
111    supported by OSS build.
112
113    Args:
114        kwargs: The `kwargs` parameter from a rule.
115
116    Returns:
117        The possibly-modified `kwargs` parameter.
118    """
119    keys = []
120    for key in kwargs:
121        if (key.endswith("_platform_preprocessor_flags") or key.endswith("_platform_deps") or
122            key.startswith("fbobjc") or key.endswith("_platform_compiler_flags")):
123            keys.append(key)
124    for key in keys:
125        kwargs.pop(key)
126    return kwargs
127
128def _remove_unsupported_kwargs(kwargs):
129    """Removes environment unsupported kwargs
130    """
131    kwargs.pop("tags", None)  # tags = ["long_running"] doesn't work in oss
132    kwargs.pop("types", None)  # will have to find a different way to handle .pyi files in oss
133    kwargs.pop("resources", None)  # doesn't support resources in python_library/python_binary yet
134    kwargs.pop("feature", None)  # internal-only, used for Product-Feature Hierarchy (PFH)
135    return kwargs
136
137def _patch_headers(kwargs):
138    """Patch (add or modify or remove) headers related attributes for this build environment.
139    """
140
141    # header_namespace is to workaround the fact that all C++ source files are having the pattern:
142    # `include <executorch/.../*.h>` but BUCK2 root is at executorch/ so the `executorch/` prefix is redundant.
143    kwargs["header_namespace"] = "executorch/" + native.package_name()
144    return kwargs
145
146def _patch_pp_flags(kwargs):
147    return kwargs
148
149def _patch_cxx_compiler_flags(kwargs):
150    """CXX Compiler flags to enable C++17 features."""
151    if "lang_compiler_flags" not in kwargs:
152        kwargs["lang_compiler_flags"] = {"cxx_cpp_output": ["-std=c++17"]}
153    elif "cxx_cpp_output" not in kwargs["lang_compiler_flags"]:
154        kwargs["lang_compiler_flags"]["cxx_cpp_output"] = ["-std=c++17"]
155    else:
156        kwargs["lang_compiler_flags"]["cxx_cpp_output"].append("-std=c++17")
157    return kwargs
158
159# buildifier: disable=unused-variable
160def _patch_executorch_genrule_cmd(cmd, macros_only = True):
161    """Patches references to //executorch in genrule commands.
162
163    Rewrites substrings like `//executorch/` or
164    `//executorch:` and replaces them with `//` and `//:`.
165
166    Args:
167        cmd: The `cmd` string from a genrule.
168        macros_only: Ignored; always treated as False.
169
170    Returns:
171        The possibly-modified command.
172    """
173
174    # Replace all references, even outside of macros.
175    cmd = cmd.replace(
176        "//{prefix}:".format(prefix = _ET_TARGET_PREFIX),
177        ":",
178    )
179    cmd = cmd.replace(
180        "//{prefix}/".format(prefix = _ET_TARGET_PREFIX),
181        "//",
182    )
183    cmd = cmd.replace(
184        "//xplat/{prefix}/".format(prefix = _ET_TARGET_PREFIX),
185        "//",
186    )
187    cmd = cmd.replace(
188        "fbsource//",
189        "//",
190    )
191    return cmd
192
193def _target_needs_patch(target):
194    return _start_with_et_targets(target) or target.startswith(":")
195
196def _patch_target_for_env(target):
197    return target.replace("//executorch/", "//", 1)
198
199def _struct_to_json(object):
200    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
201    return native.json.encode(object)
202
203env = struct(
204    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
205    command_alias = native.command_alias,
206    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
207    cxx_binary = native.cxx_binary,
208    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
209    cxx_library = native.cxx_library,
210    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
211    cxx_python_extension = native.cxx_python_extension,
212    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
213    cxx_test = native.cxx_test,
214    default_platforms = [],
215    executorch_clients = ["//..."],
216    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
217    export_file = native.export_file,
218    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
219    filegroup = native.filegroup,
220    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
221    genrule = native.genrule,
222    is_oss = True,
223    is_xplat = lambda: False,
224    patch_deps = _patch_deps,
225    patch_cxx_compiler_flags = _patch_cxx_compiler_flags,
226    patch_executorch_genrule_cmd = _patch_executorch_genrule_cmd,
227    patch_force_static = _patch_force_static,
228    patch_headers = _patch_headers,
229    patch_platform_build_mode_flags = _patch_platform_build_mode_flags,
230    patch_platforms = _patch_platforms,
231    patch_pp_flags = _patch_pp_flags,
232    patch_target_for_env = _patch_target_for_env,
233    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
234    python_binary = native.python_binary,
235    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
236    python_library = native.python_library,
237    # @lint-ignore BUCKLINT: native and fb_native are explicitly forbidden in fbcode.
238    python_test = native.python_test,
239    remove_platform_specific_args = _remove_platform_specific_args,
240    remove_unsupported_kwargs = _remove_unsupported_kwargs,
241    resolve_external_dep = _resolve_external_dep,
242    struct_to_json = _struct_to_json,
243    target_needs_patch = _target_needs_patch,
244    EXTERNAL_DEP_FALLTHROUGH = _EXTERNAL_DEP_FALLTHROUGH,
245)
246