xref: /aosp_15_r20/external/skia/toolchain/download_mac_toolchain.bzl (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1*c8dee2aaSAndroid Build Coastguard Worker"""
2*c8dee2aaSAndroid Build Coastguard WorkerThis file assembles a toolchain for a Mac host (either M1 or Intel) using the Clang Compiler
3*c8dee2aaSAndroid Build Coastguard Workerand a locally-installed XCode.
4*c8dee2aaSAndroid Build Coastguard Worker
5*c8dee2aaSAndroid Build Coastguard WorkerIt downloads the necessary executables and creates symlinks in the external subfolder of the Bazel
6*c8dee2aaSAndroid Build Coastguard Workercache (the same place third party deps are downloaded with http_archive or similar functions in
7*c8dee2aaSAndroid Build Coastguard WorkerWORKSPACE.bazel). These will be able to be used via our
8*c8dee2aaSAndroid Build Coastguard Workercustom c++ toolchain configuration (see //toolchain/mac_toolchain_config.bzl)
9*c8dee2aaSAndroid Build Coastguard Worker
10*c8dee2aaSAndroid Build Coastguard WorkerThe destination folder for these files and symlinks are:
11*c8dee2aaSAndroid Build Coastguard Worker  [outputRoot (aka Bazel cache)]/[outputUserRoot]/[outputBase]/external/clang_mac
12*c8dee2aaSAndroid Build Coastguard Worker  (See https://bazel.build/docs/output_directories#layout-diagram)
13*c8dee2aaSAndroid Build Coastguard Worker"""
14*c8dee2aaSAndroid Build Coastguard Worker
15*c8dee2aaSAndroid Build Coastguard Workerload(":clang_layering_check.bzl", "generate_system_module_map")
16*c8dee2aaSAndroid Build Coastguard Workerload(":utils.bzl", "gcs_mirror_url")
17*c8dee2aaSAndroid Build Coastguard Worker
18*c8dee2aaSAndroid Build Coastguard Worker# From https://github.com/llvm/llvm-project/releases/tag/llvmorg-15.0.1
19*c8dee2aaSAndroid Build Coastguard Worker# When updating this, don't forget to use //bazel/gcs_mirror to upload a new version.
20*c8dee2aaSAndroid Build Coastguard Worker# go run bazel/gcs_mirror/gcs_mirror.go --url [clang_url] --sha256 [clang_sha256]
21*c8dee2aaSAndroid Build Coastguard Workerclang_prefix_arm64 = "clang+llvm-15.0.1-arm64-apple-darwin21.0"
22*c8dee2aaSAndroid Build Coastguard Workerclang_sha256_arm64 = "858f86d96b5e4880f69f7a583daddbf97ee94e7cffce0d53aa05cba6967f13b8"
23*c8dee2aaSAndroid Build Coastguard Workerclang_url_arm64 = "https://github.com/llvm/llvm-project/releases/download/llvmorg-15.0.1/clang+llvm-15.0.1-arm64-apple-darwin21.0.tar.xz"
24*c8dee2aaSAndroid Build Coastguard Worker
25*c8dee2aaSAndroid Build Coastguard Workerclang_prefix_amd64 = "clang+llvm-15.0.1-x86_64-apple-darwin"
26*c8dee2aaSAndroid Build Coastguard Workerclang_sha256_amd64 = "0b2f1a811e68d011344103274733b7670c15bbe08b2a3a5140ccad8e19d9311e"
27*c8dee2aaSAndroid Build Coastguard Workerclang_url_amd64 = "https://github.com/llvm/llvm-project/releases/download/llvmorg-15.0.1/clang+llvm-15.0.1-x86_64-apple-darwin.tar.xz"
28*c8dee2aaSAndroid Build Coastguard Worker
29*c8dee2aaSAndroid Build Coastguard Workerdef _get_system_xcode_path(ctx):
30*c8dee2aaSAndroid Build Coastguard Worker    # https://developer.apple.com/library/archive/technotes/tn2339/_index.html
31*c8dee2aaSAndroid Build Coastguard Worker    res = ctx.execute(["xcode-select", "--print-path"])
32*c8dee2aaSAndroid Build Coastguard Worker    if res.return_code != 0:
33*c8dee2aaSAndroid Build Coastguard Worker        fail("Error Getting XCode path: " + res.stderr)
34*c8dee2aaSAndroid Build Coastguard Worker    return res.stdout.rstrip()
35*c8dee2aaSAndroid Build Coastguard Worker
36*c8dee2aaSAndroid Build Coastguard Workerdef _delete_macos_sdk_symlinks(ctx):
37*c8dee2aaSAndroid Build Coastguard Worker    ctx.delete("./symlinks/xcode/MacSDK/usr")
38*c8dee2aaSAndroid Build Coastguard Worker    ctx.delete("./symlinks/xcode/MacSDK/System/Library/Frameworks")
39*c8dee2aaSAndroid Build Coastguard Worker
40*c8dee2aaSAndroid Build Coastguard Workerdef _create_macos_sdk_symlinks(ctx):
41*c8dee2aaSAndroid Build Coastguard Worker    system_xcode_path = _get_system_xcode_path(ctx)
42*c8dee2aaSAndroid Build Coastguard Worker
43*c8dee2aaSAndroid Build Coastguard Worker    # https://bazel.build/rules/lib/actions#symlink
44*c8dee2aaSAndroid Build Coastguard Worker    ctx.symlink(
45*c8dee2aaSAndroid Build Coastguard Worker        # from =
46*c8dee2aaSAndroid Build Coastguard Worker        system_xcode_path + "/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr",
47*c8dee2aaSAndroid Build Coastguard Worker        # to =
48*c8dee2aaSAndroid Build Coastguard Worker        "./symlinks/xcode/MacSDK/usr",
49*c8dee2aaSAndroid Build Coastguard Worker    )
50*c8dee2aaSAndroid Build Coastguard Worker
51*c8dee2aaSAndroid Build Coastguard Worker    # It is very important to symlink the frameworks directory to [sysroot]/System/Library/Frameworks
52*c8dee2aaSAndroid Build Coastguard Worker    # because some Frameworks "re-export" other frameworks. These framework paths are relative to
53*c8dee2aaSAndroid Build Coastguard Worker    # the sysroot (which on a typical machine is /), and it is difficult to change these paths.
54*c8dee2aaSAndroid Build Coastguard Worker    # By making the symlinks emulate the original path structure, we can keep those re-exports
55*c8dee2aaSAndroid Build Coastguard Worker    # from breaking.
56*c8dee2aaSAndroid Build Coastguard Worker    ctx.symlink(
57*c8dee2aaSAndroid Build Coastguard Worker        # from =
58*c8dee2aaSAndroid Build Coastguard Worker        system_xcode_path + "/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/System/Library/Frameworks",
59*c8dee2aaSAndroid Build Coastguard Worker        # to =
60*c8dee2aaSAndroid Build Coastguard Worker        "./symlinks/xcode/MacSDK/System/Library/Frameworks",
61*c8dee2aaSAndroid Build Coastguard Worker    )
62*c8dee2aaSAndroid Build Coastguard Worker
63*c8dee2aaSAndroid Build Coastguard Workerdef _download_mac_toolchain_impl(ctx):
64*c8dee2aaSAndroid Build Coastguard Worker    # https://bazel.build/rules/lib/repository_ctx#os
65*c8dee2aaSAndroid Build Coastguard Worker    # https://bazel.build/rules/lib/repository_os
66*c8dee2aaSAndroid Build Coastguard Worker    if ctx.os.arch == "aarch64":
67*c8dee2aaSAndroid Build Coastguard Worker        clang_url = clang_url_arm64
68*c8dee2aaSAndroid Build Coastguard Worker        clang_sha256 = clang_sha256_arm64
69*c8dee2aaSAndroid Build Coastguard Worker        clang_prefix = clang_prefix_arm64
70*c8dee2aaSAndroid Build Coastguard Worker    else:
71*c8dee2aaSAndroid Build Coastguard Worker        clang_url = clang_url_amd64
72*c8dee2aaSAndroid Build Coastguard Worker        clang_sha256 = clang_sha256_amd64
73*c8dee2aaSAndroid Build Coastguard Worker        clang_prefix = clang_prefix_amd64
74*c8dee2aaSAndroid Build Coastguard Worker
75*c8dee2aaSAndroid Build Coastguard Worker    # Download the clang toolchain (the extraction can take a while)
76*c8dee2aaSAndroid Build Coastguard Worker    # https://bazel.build/rules/lib/repository_ctx#download_and_extract
77*c8dee2aaSAndroid Build Coastguard Worker    ctx.download_and_extract(
78*c8dee2aaSAndroid Build Coastguard Worker        url = gcs_mirror_url(clang_url, clang_sha256),
79*c8dee2aaSAndroid Build Coastguard Worker        output = "",
80*c8dee2aaSAndroid Build Coastguard Worker        stripPrefix = clang_prefix,
81*c8dee2aaSAndroid Build Coastguard Worker        sha256 = clang_sha256,
82*c8dee2aaSAndroid Build Coastguard Worker    )
83*c8dee2aaSAndroid Build Coastguard Worker
84*c8dee2aaSAndroid Build Coastguard Worker    # Some std library headers use #include_next to include system specific headers, and
85*c8dee2aaSAndroid Build Coastguard Worker    # some skia source files require Xcode headers when compiling, (see SkTypes.h and look
86*c8dee2aaSAndroid Build Coastguard Worker    # for TargetedConditionals.h)) All of these are located in Xcode, stopping the Mac
87*c8dee2aaSAndroid Build Coastguard Worker    # builds from being purely hermetic.
88*c8dee2aaSAndroid Build Coastguard Worker    # For now, we can grab the user's Xcode path by calling xcode-select and create a symlink in
89*c8dee2aaSAndroid Build Coastguard Worker    # our toolchain directory to refer to during compilation.
90*c8dee2aaSAndroid Build Coastguard Worker
91*c8dee2aaSAndroid Build Coastguard Worker    _delete_macos_sdk_symlinks(ctx)
92*c8dee2aaSAndroid Build Coastguard Worker    _create_macos_sdk_symlinks(ctx)
93*c8dee2aaSAndroid Build Coastguard Worker
94*c8dee2aaSAndroid Build Coastguard Worker    # This list of files lines up with _make_default_flags() in mac_toolchain_config.bzl
95*c8dee2aaSAndroid Build Coastguard Worker    # It is all locations that our toolchain could find a system header.
96*c8dee2aaSAndroid Build Coastguard Worker    builtin_include_directories = [
97*c8dee2aaSAndroid Build Coastguard Worker        "include/c++/v1",
98*c8dee2aaSAndroid Build Coastguard Worker        "lib/clang/15.0.1/include",
99*c8dee2aaSAndroid Build Coastguard Worker        "symlinks/xcode/MacSDK/System/Library/Frameworks",
100*c8dee2aaSAndroid Build Coastguard Worker        "symlinks/xcode/MacSDK/usr/include",
101*c8dee2aaSAndroid Build Coastguard Worker    ]
102*c8dee2aaSAndroid Build Coastguard Worker
103*c8dee2aaSAndroid Build Coastguard Worker    generate_system_module_map(
104*c8dee2aaSAndroid Build Coastguard Worker        ctx,
105*c8dee2aaSAndroid Build Coastguard Worker        module_file = "toolchain_system_headers.modulemap",
106*c8dee2aaSAndroid Build Coastguard Worker        folders = builtin_include_directories,
107*c8dee2aaSAndroid Build Coastguard Worker    )
108*c8dee2aaSAndroid Build Coastguard Worker
109*c8dee2aaSAndroid Build Coastguard Worker    # Create a BUILD.bazel file that makes the files necessary for compiling,
110*c8dee2aaSAndroid Build Coastguard Worker    # linking and creating archive files visible to Bazel.
111*c8dee2aaSAndroid Build Coastguard Worker    # The smaller the globs are, the more performant the sandboxed builds will be.
112*c8dee2aaSAndroid Build Coastguard Worker    # Additionally, globs that are too wide can pick up infinite symlink loops,
113*c8dee2aaSAndroid Build Coastguard Worker    # and be difficult to quash: https://github.com/bazelbuild/bazel/issues/13950
114*c8dee2aaSAndroid Build Coastguard Worker    # https://bazel.build/rules/lib/repository_ctx#file
115*c8dee2aaSAndroid Build Coastguard Worker    ctx.file(
116*c8dee2aaSAndroid Build Coastguard Worker        "BUILD.bazel",
117*c8dee2aaSAndroid Build Coastguard Worker        content = """
118*c8dee2aaSAndroid Build Coastguard Worker# DO NOT EDIT THIS BAZEL FILE DIRECTLY
119*c8dee2aaSAndroid Build Coastguard Worker# Generated from ctx.file action in download_mac_toolchain.bzl
120*c8dee2aaSAndroid Build Coastguard Workerfilegroup(
121*c8dee2aaSAndroid Build Coastguard Worker    name = "generated_module_map",
122*c8dee2aaSAndroid Build Coastguard Worker    srcs = ["toolchain_system_headers.modulemap"],
123*c8dee2aaSAndroid Build Coastguard Worker    visibility = ["//visibility:public"],
124*c8dee2aaSAndroid Build Coastguard Worker)
125*c8dee2aaSAndroid Build Coastguard Worker
126*c8dee2aaSAndroid Build Coastguard Workerfilegroup(
127*c8dee2aaSAndroid Build Coastguard Worker    name = "archive_files",
128*c8dee2aaSAndroid Build Coastguard Worker    srcs = [
129*c8dee2aaSAndroid Build Coastguard Worker        "bin/llvm-ar",
130*c8dee2aaSAndroid Build Coastguard Worker    ],
131*c8dee2aaSAndroid Build Coastguard Worker    visibility = ["//visibility:public"],
132*c8dee2aaSAndroid Build Coastguard Worker)
133*c8dee2aaSAndroid Build Coastguard Worker
134*c8dee2aaSAndroid Build Coastguard Worker# Any framework that Skia depends on directly or indirectly needs to be listed here.
135*c8dee2aaSAndroid Build Coastguard WorkerFRAMEWORK_GLOB = [
136*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/AppKit.Framework/**",
137*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/ApplicationServices.Framework/**",
138*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/Carbon.Framework/**",
139*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CFNetwork.Framework/**",
140*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CloudKit.Framework/**",
141*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/Cocoa.Framework/**",
142*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/ColorSync.Framework/**",
143*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreData.Framework/**",
144*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreFoundation.Framework/**",
145*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreGraphics.Framework/**",
146*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreImage.Framework/**",
147*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreLocation.Framework/**",
148*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreServices.Framework/**",
149*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreText.Framework/**",
150*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/CoreVideo.Framework/**",
151*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/DiskArbitration.Framework/**",
152*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/Foundation.Framework/**",
153*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/ImageIO.Framework/**",
154*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/IOKit.Framework/**",
155*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/IOSurface.Framework/**",
156*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/Metal.Framework/**",
157*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/MetalKit.Framework/**",
158*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/OpenGL.Framework/**",
159*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/QuartzCore.Framework/**",
160*c8dee2aaSAndroid Build Coastguard Worker    "symlinks/xcode/MacSDK/System/Library/Frameworks/Security.Framework/**",
161*c8dee2aaSAndroid Build Coastguard Worker]
162*c8dee2aaSAndroid Build Coastguard Worker
163*c8dee2aaSAndroid Build Coastguard Workerfilegroup(
164*c8dee2aaSAndroid Build Coastguard Worker    name = "compile_files",
165*c8dee2aaSAndroid Build Coastguard Worker    srcs = [
166*c8dee2aaSAndroid Build Coastguard Worker        "bin/clang",
167*c8dee2aaSAndroid Build Coastguard Worker    ] + glob(
168*c8dee2aaSAndroid Build Coastguard Worker        include = [
169*c8dee2aaSAndroid Build Coastguard Worker            "include/c++/v1/**",
170*c8dee2aaSAndroid Build Coastguard Worker            "lib/clang/15.0.1/include/**",
171*c8dee2aaSAndroid Build Coastguard Worker            "symlinks/xcode/MacSDK/usr/include/**",
172*c8dee2aaSAndroid Build Coastguard Worker        ] + FRAMEWORK_GLOB,
173*c8dee2aaSAndroid Build Coastguard Worker        allow_empty = False,
174*c8dee2aaSAndroid Build Coastguard Worker    ),
175*c8dee2aaSAndroid Build Coastguard Worker    visibility = ["//visibility:public"],
176*c8dee2aaSAndroid Build Coastguard Worker)
177*c8dee2aaSAndroid Build Coastguard Worker
178*c8dee2aaSAndroid Build Coastguard Workerfilegroup(
179*c8dee2aaSAndroid Build Coastguard Worker    name = "link_files",
180*c8dee2aaSAndroid Build Coastguard Worker    srcs = [
181*c8dee2aaSAndroid Build Coastguard Worker        "bin/clang",
182*c8dee2aaSAndroid Build Coastguard Worker        "bin/ld.lld",
183*c8dee2aaSAndroid Build Coastguard Worker        "bin/lld",
184*c8dee2aaSAndroid Build Coastguard Worker        "lib/libc++.a",
185*c8dee2aaSAndroid Build Coastguard Worker        "lib/libc++abi.a",
186*c8dee2aaSAndroid Build Coastguard Worker        "lib/libunwind.a",
187*c8dee2aaSAndroid Build Coastguard Worker    ] + glob(
188*c8dee2aaSAndroid Build Coastguard Worker        include = [
189*c8dee2aaSAndroid Build Coastguard Worker            # libc++.tbd and libSystem.tbd live here.
190*c8dee2aaSAndroid Build Coastguard Worker            "symlinks/xcode/MacSDK/usr/lib/*",
191*c8dee2aaSAndroid Build Coastguard Worker        ] + FRAMEWORK_GLOB,
192*c8dee2aaSAndroid Build Coastguard Worker        allow_empty = False,
193*c8dee2aaSAndroid Build Coastguard Worker    ),
194*c8dee2aaSAndroid Build Coastguard Worker    visibility = ["//visibility:public"],
195*c8dee2aaSAndroid Build Coastguard Worker)
196*c8dee2aaSAndroid Build Coastguard Worker""",
197*c8dee2aaSAndroid Build Coastguard Worker        executable = False,
198*c8dee2aaSAndroid Build Coastguard Worker    )
199*c8dee2aaSAndroid Build Coastguard Worker
200*c8dee2aaSAndroid Build Coastguard Worker# https://bazel.build/rules/repository_rules
201*c8dee2aaSAndroid Build Coastguard Workerdownload_mac_toolchain = repository_rule(
202*c8dee2aaSAndroid Build Coastguard Worker    implementation = _download_mac_toolchain_impl,
203*c8dee2aaSAndroid Build Coastguard Worker    attrs = {},
204*c8dee2aaSAndroid Build Coastguard Worker    doc = "Downloads clang to build Skia with." +
205*c8dee2aaSAndroid Build Coastguard Worker          "Assumes you have xcode located on your device and have" +
206*c8dee2aaSAndroid Build Coastguard Worker          "xcode-select in your $PATH.",
207*c8dee2aaSAndroid Build Coastguard Worker)
208