Advertisement
Guest User

depot_tools/chromium/src/tools/clang/scripts/build.py

a guest
Jul 26th, 2022
70
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 57.45 KB | None | 0 0
  1. #!/usr/bin/env python3
  2. # Copyright 2019 The Chromium Authors. All rights reserved.
  3. # Use of this source code is governed by a BSD-style license that can be
  4. # found in the LICENSE file.
  5.  
  6. """This script is used to build clang binaries. It is used by package.py to
  7. create the prebuilt binaries downloaded by update.py and used by developers.
  8.  
  9. The expectation is that update.py downloads prebuilt binaries for everyone, and
  10. nobody should run this script as part of normal development.
  11. """
  12.  
  13. from __future__ import print_function
  14.  
  15. import argparse
  16. import glob
  17. import io
  18. import json
  19. import os
  20. import pipes
  21. import platform
  22. import re
  23. import shutil
  24. import subprocess
  25. import sys
  26. import tempfile
  27.  
  28. from update import (CDS_URL, CHROMIUM_DIR, CLANG_REVISION, LLVM_BUILD_DIR,
  29. FORCE_HEAD_REVISION_FILE, PACKAGE_VERSION, RELEASE_VERSION,
  30. STAMP_FILE, THIS_DIR, DownloadUrl, DownloadAndUnpack,
  31. EnsureDirExists, ReadStampFile, RmTree, WriteStampFile)
  32.  
  33. # Path constants. (All of these should be absolute paths.)
  34. THIRD_PARTY_DIR = os.path.join(CHROMIUM_DIR, 'third_party')
  35. LLVM_DIR = os.path.join(THIRD_PARTY_DIR, 'llvm')
  36. COMPILER_RT_DIR = os.path.join(LLVM_DIR, 'compiler-rt')
  37. LLVM_BOOTSTRAP_DIR = os.path.join(THIRD_PARTY_DIR, 'llvm-bootstrap')
  38. LLVM_BOOTSTRAP_INSTALL_DIR = os.path.join(THIRD_PARTY_DIR,
  39. 'llvm-bootstrap-install')
  40. LLVM_INSTRUMENTED_DIR = os.path.join(THIRD_PARTY_DIR, 'llvm-instrumented')
  41. LLVM_PROFDATA_FILE = os.path.join(LLVM_INSTRUMENTED_DIR, 'profdata.prof')
  42. LLVM_BUILD_TOOLS_DIR = os.path.abspath(
  43. os.path.join(LLVM_DIR, '..', 'llvm-build-tools'))
  44. ANDROID_NDK_DIR = os.path.join(
  45. CHROMIUM_DIR, 'third_party', 'android_ndk')
  46. FUCHSIA_SDK_DIR = os.path.join(CHROMIUM_DIR, 'third_party', 'fuchsia-sdk',
  47. 'sdk')
  48. PINNED_CLANG_DIR = os.path.join(LLVM_BUILD_TOOLS_DIR, 'pinned-clang')
  49.  
  50. BUG_REPORT_URL = ('https://crbug.com and run'
  51. ' tools/clang/scripts/process_crashreports.py'
  52. ' (only works inside Google) which will upload a report')
  53.  
  54. win_sdk_dir = None
  55. def GetWinSDKDir():
  56. """Get the location of the current SDK."""
  57. global win_sdk_dir
  58. if win_sdk_dir:
  59. return win_sdk_dir
  60.  
  61. # Don't let vs_toolchain overwrite our environment.
  62. environ_bak = os.environ
  63.  
  64. sys.path.append(os.path.join(CHROMIUM_DIR, 'build'))
  65. import vs_toolchain
  66. win_sdk_dir = vs_toolchain.SetEnvironmentAndGetSDKDir()
  67. msvs_version = vs_toolchain.GetVisualStudioVersion()
  68.  
  69. if bool(int(os.environ.get('DEPOT_TOOLS_WIN_TOOLCHAIN', '1'))):
  70. dia_path = os.path.join(win_sdk_dir, '..', 'DIA SDK', 'bin', 'amd64')
  71. else:
  72. if 'GYP_MSVS_OVERRIDE_PATH' not in os.environ:
  73. vs_path = vs_toolchain.DetectVisualStudioPath()
  74. else:
  75. vs_path = os.environ['GYP_MSVS_OVERRIDE_PATH']
  76. dia_path = os.path.join(vs_path, 'DIA SDK', 'bin', 'amd64')
  77.  
  78. os.environ = environ_bak
  79. return win_sdk_dir
  80.  
  81.  
  82. def RunCommand(command, msvc_arch=None, env=None, fail_hard=True):
  83. """Run command and return success (True) or failure; or if fail_hard is
  84. True, exit on failure. If msvc_arch is set, runs the command in a
  85. shell with the msvc tools for that architecture."""
  86.  
  87. if msvc_arch and sys.platform == 'win32':
  88. command = [os.path.join(GetWinSDKDir(), 'bin', 'SetEnv.cmd'),
  89. "/" + msvc_arch, '&&'] + command
  90.  
  91. # https://docs.python.org/2/library/subprocess.html:
  92. # "On Unix with shell=True [...] if args is a sequence, the first item
  93. # specifies the command string, and any additional items will be treated as
  94. # additional arguments to the shell itself. That is to say, Popen does the
  95. # equivalent of:
  96. # Popen(['/bin/sh', '-c', args[0], args[1], ...])"
  97. #
  98. # We want to pass additional arguments to command[0], not to the shell,
  99. # so manually join everything into a single string.
  100. # Annoyingly, for "svn co url c:\path", pipes.quote() thinks that it should
  101. # quote c:\path but svn can't handle quoted paths on Windows. Since on
  102. # Windows follow-on args are passed to args[0] instead of the shell, don't
  103. # do the single-string transformation there.
  104. if sys.platform != 'win32':
  105. command = ' '.join([pipes.quote(c) for c in command])
  106. print('Running', command)
  107. if subprocess.call(command, env=env, shell=True) == 0:
  108. return True
  109. print('Failed.')
  110. if fail_hard:
  111. sys.exit(1)
  112. return False
  113.  
  114.  
  115. def CopyFile(src, dst):
  116. """Copy a file from src to dst."""
  117. print("Copying %s to %s" % (src, dst))
  118. shutil.copy(src, dst)
  119.  
  120.  
  121. def CopyDirectoryContents(src, dst):
  122. """Copy the files from directory src to dst."""
  123. dst = os.path.realpath(dst) # realpath() in case dst ends in /..
  124. EnsureDirExists(dst)
  125. for f in os.listdir(src):
  126. CopyFile(os.path.join(src, f), dst)
  127.  
  128.  
  129. def CheckoutLLVM(commit, dir):
  130. """Checkout the LLVM monorepo at a certain git commit in dir. Any local
  131. modifications in dir will be lost."""
  132.  
  133. print('Checking out LLVM monorepo %s into %s' % (commit, dir))
  134.  
  135. # Try updating the current repo if it exists and has no local diff.
  136. if os.path.isdir(dir):
  137. os.chdir(dir)
  138. # git diff-index --quiet returns success when there is no diff.
  139. # Also check that the first commit is reachable.
  140. if (RunCommand(['git', 'diff-index', '--quiet', 'HEAD'], fail_hard=False)
  141. and RunCommand(['git', 'fetch'], fail_hard=False)
  142. and RunCommand(['git', 'checkout', commit], fail_hard=False)):
  143. return
  144.  
  145. # If we can't use the current repo, delete it.
  146. os.chdir(CHROMIUM_DIR) # Can't remove dir if we're in it.
  147. print('Removing %s.' % dir)
  148. RmTree(dir)
  149.  
  150. clone_cmd = ['git', 'clone', 'https://github.com/llvm/llvm-project/', dir]
  151.  
  152. if RunCommand(clone_cmd, fail_hard=False):
  153. os.chdir(dir)
  154. if RunCommand(['git', 'checkout', commit], fail_hard=False):
  155. return
  156.  
  157. print('CheckoutLLVM failed.')
  158. sys.exit(1)
  159.  
  160.  
  161. def UrlOpen(url):
  162. # TODO(crbug.com/1067752): Use urllib once certificates are fixed.
  163. return subprocess.check_output(['curl', '--silent', url],
  164. universal_newlines=True)
  165.  
  166.  
  167. def GetLatestLLVMCommit():
  168. """Get the latest commit hash in the LLVM monorepo."""
  169. ref = json.loads(
  170. UrlOpen(('https://api.github.com/repos/'
  171. 'llvm/llvm-project/git/refs/heads/main')))
  172. assert ref['object']['type'] == 'commit'
  173. return ref['object']['sha']
  174.  
  175.  
  176. def GetCommitDescription(commit):
  177. """Get the output of `git describe`.
  178.  
  179. Needs to be called from inside the git repository dir."""
  180. git_exe = 'git.bat' if sys.platform.startswith('win') else 'git'
  181. return subprocess.check_output(
  182. [git_exe, 'describe', '--long', '--abbrev=8', commit],
  183. universal_newlines=True).rstrip()
  184.  
  185.  
  186. def DeleteChromeToolsShim():
  187. # TODO: These dirs are no longer used. Remove this code after a while.
  188. OLD_SHIM_DIR = os.path.join(LLVM_DIR, 'tools', 'zzz-chrometools')
  189. shutil.rmtree(OLD_SHIM_DIR, ignore_errors=True)
  190. CHROME_TOOLS_SHIM_DIR = os.path.join(LLVM_DIR, 'llvm', 'tools', 'chrometools')
  191. shutil.rmtree(CHROME_TOOLS_SHIM_DIR, ignore_errors=True)
  192.  
  193.  
  194. def AddCMakeToPath(args):
  195. """Download CMake and add it to PATH."""
  196. if args.use_system_cmake:
  197. return
  198.  
  199. if sys.platform == 'win32':
  200. zip_name = 'cmake-3.23.0-windows-x86_64.zip'
  201. dir_name = ['cmake-3.23.0-windows-x86_64', 'bin']
  202. elif sys.platform == 'darwin':
  203. zip_name = 'cmake-3.23.0-macos-universal.tar.gz'
  204. dir_name = ['cmake-3.23.0-macos-universal', 'CMake.app', 'Contents', 'bin']
  205. else:
  206. zip_name = 'cmake-3.23.0-linux-x86_64.tar.gz'
  207. dir_name = ['cmake-3.23.0-linux-x86_64', 'bin']
  208.  
  209. cmake_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, *dir_name)
  210. if not os.path.exists(cmake_dir):
  211. DownloadAndUnpack(CDS_URL + '/tools/' + zip_name, LLVM_BUILD_TOOLS_DIR)
  212. os.environ['PATH'] = cmake_dir + os.pathsep + os.environ.get('PATH', '')
  213.  
  214.  
  215. def AddGnuWinToPath():
  216. """Download some GNU win tools and add them to PATH."""
  217. if sys.platform != 'win32':
  218. return
  219.  
  220. gnuwin_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, 'gnuwin')
  221. GNUWIN_VERSION = '14'
  222. GNUWIN_STAMP = os.path.join(gnuwin_dir, 'stamp')
  223. if ReadStampFile(GNUWIN_STAMP) == GNUWIN_VERSION:
  224. print('GNU Win tools already up to date.')
  225. else:
  226. zip_name = 'gnuwin-%s.zip' % GNUWIN_VERSION
  227. DownloadAndUnpack(CDS_URL + '/tools/' + zip_name, LLVM_BUILD_TOOLS_DIR)
  228. WriteStampFile(GNUWIN_VERSION, GNUWIN_STAMP)
  229.  
  230. os.environ['PATH'] = gnuwin_dir + os.pathsep + os.environ.get('PATH', '')
  231.  
  232. # find.exe, mv.exe and rm.exe are from MSYS (see crrev.com/389632). MSYS uses
  233. # Cygwin under the hood, and initializing Cygwin has a race-condition when
  234. # getting group and user data from the Active Directory is slow. To work
  235. # around this, use a horrible hack telling it not to do that.
  236. # See https://crbug.com/905289
  237. etc = os.path.join(gnuwin_dir, '..', '..', 'etc')
  238. EnsureDirExists(etc)
  239. with open(os.path.join(etc, 'nsswitch.conf'), 'w') as f:
  240. f.write('passwd: files\n')
  241. f.write('group: files\n')
  242.  
  243.  
  244. def AddZlibToPath():
  245. """Download and build zlib, and add to PATH."""
  246. zlib_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, 'zlib-1.2.11')
  247. if os.path.exists(zlib_dir):
  248. RmTree(zlib_dir)
  249. zip_name = 'zlib-1.2.11.tar.gz'
  250. DownloadAndUnpack(CDS_URL + '/tools/' + zip_name, LLVM_BUILD_TOOLS_DIR)
  251. os.chdir(zlib_dir)
  252. zlib_files = [
  253. 'adler32', 'compress', 'crc32', 'deflate', 'gzclose', 'gzlib', 'gzread',
  254. 'gzwrite', 'inflate', 'infback', 'inftrees', 'inffast', 'trees',
  255. 'uncompr', 'zutil'
  256. ]
  257. cl_flags = [
  258. '/nologo', '/O2', '/DZLIB_DLL', '/c', '/D_CRT_SECURE_NO_DEPRECATE',
  259. '/D_CRT_NONSTDC_NO_DEPRECATE'
  260. ]
  261. RunCommand(
  262. ['cl.exe'] + [f + '.c' for f in zlib_files] + cl_flags, msvc_arch='x64')
  263. RunCommand(
  264. ['lib.exe'] + [f + '.obj'
  265. for f in zlib_files] + ['/nologo', '/out:zlib.lib'],
  266. msvc_arch='x64')
  267. # Remove the test directory so it isn't found when trying to find
  268. # test.exe.
  269. shutil.rmtree('test')
  270.  
  271. os.environ['PATH'] = zlib_dir + os.pathsep + os.environ.get('PATH', '')
  272. return zlib_dir
  273.  
  274.  
  275. def BuildLibXml2():
  276. """Download and build libxml2"""
  277. # The .tar.gz on GCS was uploaded as follows.
  278. # The gitlab page has more up-to-date packages than http://xmlsoft.org/,
  279. # and the official releases on xmlsoft.org are only available over ftp too.
  280. # $ VER=v2.9.12
  281. # $ curl -O \
  282. # https://gitlab.gnome.org/GNOME/libxml2/-/archive/$VER/libxml2-$VER.tar.gz
  283. # $ gsutil cp -n -a public-read libxml2-$VER.tar.gz \
  284. # gs://chromium-browser-clang/tools
  285.  
  286. libxml2_version = 'libxml2-v2.9.12'
  287. libxml2_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, libxml2_version)
  288. if os.path.exists(libxml2_dir):
  289. RmTree(libxml2_dir)
  290. zip_name = libxml2_version + '.tar.gz'
  291. DownloadAndUnpack(CDS_URL + '/tools/' + zip_name, LLVM_BUILD_TOOLS_DIR)
  292. os.chdir(libxml2_dir)
  293. os.mkdir('build')
  294. os.chdir('build')
  295.  
  296. libxml2_install_dir = os.path.join(libxml2_dir, 'build', 'install')
  297.  
  298. # Disable everything except WITH_TREE and WITH_OUTPUT, both needed by LLVM's
  299. # WindowsManifestMerger.
  300. # Also enable WITH_THREADS, else libxml doesn't compile on Linux.
  301. RunCommand(
  302. [
  303. 'cmake',
  304. '-GNinja',
  305. '-DCMAKE_BUILD_TYPE=Release',
  306. '-DCMAKE_INSTALL_PREFIX=install',
  307. # The mac_arm bot builds a clang arm binary, but currently on an intel
  308. # host. If we ever move it to run on an arm mac, this can go. We
  309. # could pass this only if args.build_mac_arm, but libxml is small, so
  310. # might as well build it universal always for a few years.
  311. '-DCMAKE_OSX_ARCHITECTURES=arm64;x86_64',
  312. '-DCMAKE_MSVC_RUNTIME_LIBRARY=MultiThreaded', # /MT to match LLVM.
  313. '-DBUILD_SHARED_LIBS=OFF',
  314. '-DLIBXML2_WITH_C14N=OFF',
  315. '-DLIBXML2_WITH_CATALOG=OFF',
  316. '-DLIBXML2_WITH_DEBUG=OFF',
  317. '-DLIBXML2_WITH_DOCB=OFF',
  318. '-DLIBXML2_WITH_FTP=OFF',
  319. '-DLIBXML2_WITH_HTML=OFF',
  320. '-DLIBXML2_WITH_HTTP=OFF',
  321. '-DLIBXML2_WITH_ICONV=OFF',
  322. '-DLIBXML2_WITH_ICU=OFF',
  323. '-DLIBXML2_WITH_ISO8859X=OFF',
  324. '-DLIBXML2_WITH_LEGACY=OFF',
  325. '-DLIBXML2_WITH_LZMA=OFF',
  326. '-DLIBXML2_WITH_MEM_DEBUG=OFF',
  327. '-DLIBXML2_WITH_MODULES=OFF',
  328. '-DLIBXML2_WITH_OUTPUT=ON',
  329. '-DLIBXML2_WITH_PATTERN=OFF',
  330. '-DLIBXML2_WITH_PROGRAMS=OFF',
  331. '-DLIBXML2_WITH_PUSH=OFF',
  332. '-DLIBXML2_WITH_PYTHON=OFF',
  333. '-DLIBXML2_WITH_READER=OFF',
  334. '-DLIBXML2_WITH_REGEXPS=OFF',
  335. '-DLIBXML2_WITH_RUN_DEBUG=OFF',
  336. '-DLIBXML2_WITH_SAX1=OFF',
  337. '-DLIBXML2_WITH_SCHEMAS=OFF',
  338. '-DLIBXML2_WITH_SCHEMATRON=OFF',
  339. '-DLIBXML2_WITH_TESTS=OFF',
  340. '-DLIBXML2_WITH_THREADS=ON',
  341. '-DLIBXML2_WITH_THREAD_ALLOC=OFF',
  342. '-DLIBXML2_WITH_TREE=ON',
  343. '-DLIBXML2_WITH_VALID=OFF',
  344. '-DLIBXML2_WITH_WRITER=OFF',
  345. '-DLIBXML2_WITH_XINCLUDE=OFF',
  346. '-DLIBXML2_WITH_XPATH=OFF',
  347. '-DLIBXML2_WITH_XPTR=OFF',
  348. '-DLIBXML2_WITH_ZLIB=OFF',
  349. '-DLLVM_CCACHE_BUILD=ON',
  350. '-DCMAKE_C_COMPILER=/opt/AMD/aocc-compiler-3.2.0/bin/clang',
  351. '-DCMAKE_CXX_COMPILER=/opt/AMD/aocc-compiler-3.2.0/bin/clang++',
  352. '-DCMAKE_AR=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-ar',
  353. '-DCMAKE_LINKER=/opt/AMD/aocc-compiler-3.2.0/bin/ld.lld',
  354. '-DCMAKE_NM=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-nm',
  355. '-DCMAKE_OBJDUMP=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-objdump',
  356. '-DCMAKE_RANLIB=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-ranlib',
  357. '-DCMAKE_ASM_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  358. '-DCMAKE_C_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  359. '-DCMAKE_CXX_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  360. '-DCMAKE_EXE_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  361. '-DCMAKE_MODULE_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  362. '-DCMAKE_SHARED_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  363. '..',
  364. ],
  365. msvc_arch='x64')
  366. RunCommand(['ninja', 'install'], msvc_arch='x64')
  367.  
  368. libxml2_include_dir = os.path.join(libxml2_install_dir, 'include', 'libxml2')
  369. if sys.platform == 'win32':
  370. libxml2_lib = os.path.join(libxml2_install_dir, 'lib', 'libxml2s.lib')
  371. else:
  372. libxml2_lib = os.path.join(libxml2_install_dir, 'lib', 'libxml2.a')
  373. extra_cmake_flags = [
  374. '-DLLVM_ENABLE_LIBXML2=FORCE_ON',
  375. '-DLIBXML2_INCLUDE_DIR=' + libxml2_include_dir.replace('\\', '/'),
  376. '-DLIBXML2_LIBRARIES=' + libxml2_lib.replace('\\', '/'),
  377. ]
  378. extra_cflags = ['-DLIBXML_STATIC']
  379.  
  380. return extra_cmake_flags, extra_cflags
  381.  
  382.  
  383. def DownloadRPMalloc():
  384. """Download rpmalloc."""
  385. rpmalloc_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, 'rpmalloc')
  386. if os.path.exists(rpmalloc_dir):
  387. RmTree(rpmalloc_dir)
  388.  
  389. # Using rpmalloc bc1923f rather than the latest release (1.4.1) because
  390. # it contains the fix for https://github.com/mjansson/rpmalloc/pull/186
  391. # which would cause lld to deadlock.
  392. # The zip file was created and uploaded as follows:
  393. # $ mkdir rpmalloc
  394. # $ curl -L https://github.com/mjansson/rpmalloc/archive/bc1923f436539327707b08ef9751a7a87bdd9d2f.tar.gz \
  395. # | tar -C rpmalloc --strip-components=1 -xzf -
  396. # $ GZIP=-9 tar vzcf rpmalloc-bc1923f.tgz rpmalloc
  397. # $ gsutil.py cp -n -a public-read rpmalloc-bc1923f.tgz \
  398. # gs://chromium-browser-clang/tools/
  399. zip_name = 'rpmalloc-bc1923f.tgz'
  400. DownloadAndUnpack(CDS_URL + '/tools/' + zip_name, LLVM_BUILD_TOOLS_DIR)
  401. rpmalloc_dir = rpmalloc_dir.replace('\\', '/')
  402. return rpmalloc_dir
  403.  
  404.  
  405. def DownloadPinnedClang():
  406. # The update.py in this current revision may have a patched revision while
  407. # building new clang packages. Get update.py off HEAD~ to pull the current
  408. # pinned clang.
  409. if not os.path.exists(PINNED_CLANG_DIR):
  410. os.mkdir(os.path.join(PINNED_CLANG_DIR))
  411.  
  412. script_path = os.path.join(PINNED_CLANG_DIR, 'update.py')
  413.  
  414. with open(script_path, 'w') as f:
  415. subprocess.check_call(
  416. ['git', 'show', 'HEAD~:tools/clang/scripts/update.py'],
  417. stdout=f,
  418. cwd=CHROMIUM_DIR)
  419. print("Running pinned update.py")
  420. subprocess.check_call(
  421. [sys.executable, script_path, '--output-dir=' + PINNED_CLANG_DIR])
  422.  
  423.  
  424. # TODO(crbug.com/929645): Remove once we don't need gcc's libstdc++.
  425. def MaybeDownloadHostGcc(args):
  426. """Download a modern GCC host compiler on Linux."""
  427. assert sys.platform.startswith('linux')
  428. if args.gcc_toolchain:
  429. return
  430. gcc_dir = os.path.join(LLVM_BUILD_TOOLS_DIR, 'gcc-10.2.0-bionic')
  431. if os.path.isdir(gcc_dir):
  432. RmTree(gcc_dir) # TODO(thakis): Remove this branch after a few weeks.
  433. if not os.path.exists(gcc_dir):
  434. DownloadAndUnpack(CDS_URL + '/tools/gcc-10.2.0-bionic.tgz', gcc_dir)
  435. args.gcc_toolchain = gcc_dir
  436.  
  437.  
  438. def VerifyVersionOfBuiltClangMatchesVERSION():
  439. """Checks that `clang --version` outputs RELEASE_VERSION. If this
  440. fails, update.RELEASE_VERSION is out-of-date and needs to be updated (possibly
  441. in an `if args.llvm_force_head_revision:` block inupdate. main() first)."""
  442. clang = os.path.join(LLVM_BUILD_DIR, 'bin', 'clang')
  443. if sys.platform == 'win32':
  444. clang += '-cl.exe'
  445. version_out = subprocess.check_output([clang, '--version'],
  446. universal_newlines=True)
  447. version_out = re.match(r'clang version ([0-9.]+)', version_out).group(1)
  448. if version_out != RELEASE_VERSION:
  449. print(('unexpected clang version %s (not %s), '
  450. 'update RELEASE_VERSION in update.py')
  451. % (version_out, RELEASE_VERSION))
  452. sys.exit(1)
  453.  
  454.  
  455. def VerifyZlibSupport():
  456. """Check that clang was built with zlib support enabled."""
  457. clang = os.path.join(LLVM_BUILD_DIR, 'bin', 'clang')
  458. test_file = '/dev/null'
  459. if sys.platform == 'win32':
  460. clang += '.exe'
  461. test_file = 'nul'
  462.  
  463. print('Checking for zlib support')
  464. clang_out = subprocess.check_output([
  465. clang, '-target', 'x86_64-unknown-linux-gnu', '-gz', '-c', '-###', '-x',
  466. 'c', test_file
  467. ],
  468. stderr=subprocess.STDOUT,
  469. universal_newlines=True)
  470. if (re.search(r'--compress-debug-sections', clang_out)):
  471. print('OK')
  472. else:
  473. print(('Failed to detect zlib support!\n\n(driver output: %s)') % clang_out)
  474. sys.exit(1)
  475.  
  476.  
  477. # TODO(https://crbug.com/1286289): remove once Chrome targets don't rely on
  478. # libstdc++.so existing in the clang package.
  479. def CopyLibstdcpp(args, build_dir):
  480. if not args.gcc_toolchain:
  481. return
  482. # Find libstdc++.so.6
  483. libstdcpp = subprocess.check_output([
  484. os.path.join(args.gcc_toolchain, 'bin', 'g++'),
  485. '-print-file-name=libstdc++.so.6'
  486. ],
  487. universal_newlines=True).rstrip()
  488.  
  489. EnsureDirExists(os.path.join(build_dir, 'lib'))
  490. CopyFile(libstdcpp, os.path.join(build_dir, 'lib'))
  491.  
  492.  
  493. def compiler_rt_cmake_flags(*, sanitizers, profile):
  494. # Don't set -DCOMPILER_RT_BUILD_BUILTINS=ON/OFF as it interferes with the
  495. # runtimes logic of building builtins.
  496. args = [
  497. # Build crtbegin/crtend. It's just two tiny TUs, so just enable this
  498. # everywhere, even though we only need it on Linux.
  499. 'COMPILER_RT_BUILD_CRT=ON',
  500. 'COMPILER_RT_BUILD_LIBFUZZER=OFF',
  501. 'COMPILER_RT_BUILD_MEMPROF=OFF',
  502. 'COMPILER_RT_BUILD_ORC=OFF',
  503. 'COMPILER_RT_BUILD_PROFILE=' + ('ON' if profile else 'OFF'),
  504. 'COMPILER_RT_BUILD_SANITIZERS=' + ('ON' if sanitizers else 'OFF'),
  505. 'COMPILER_RT_BUILD_XRAY=OFF',
  506. # See crbug.com/1205046: don't build scudo (and others we don't need).
  507. 'COMPILER_RT_SANITIZERS_TO_BUILD=asan;dfsan;msan;hwasan;tsan;cfi',
  508. # We explicitly list all targets we want to build, do not autodetect
  509. # targets.
  510. 'COMPILER_RT_DEFAULT_TARGET_ONLY=ON',
  511. ]
  512. return args
  513.  
  514.  
  515. def gn_arg(v):
  516. if v == 'True':
  517. return True
  518. if v == 'False':
  519. return False
  520. raise argparse.ArgumentTypeError('Expected one of %r or %r' % (
  521. 'True', 'False'))
  522.  
  523.  
  524. def main():
  525. parser = argparse.ArgumentParser(description='Build Clang.')
  526. parser.add_argument('--bootstrap', action='store_true',
  527. help='first build clang with CC, then with itself.')
  528. parser.add_argument('--build-mac-arm', action='store_true',
  529. help='Build arm binaries. Only valid on macOS.')
  530. parser.add_argument('--disable-asserts', action='store_true',
  531. help='build with asserts disabled')
  532. parser.add_argument('--host-cc',
  533. help='build with host C compiler, requires --host-cxx as '
  534. 'well')
  535. parser.add_argument('--host-cxx',
  536. help='build with host C++ compiler, requires --host-cc '
  537. 'as well')
  538. parser.add_argument('--gcc-toolchain', help='what gcc toolchain to use for '
  539. 'building; --gcc-toolchain=/opt/foo picks '
  540. '/opt/foo/bin/gcc')
  541. parser.add_argument('--pgo', action='store_true', help='build with PGO')
  542. parser.add_argument('--thinlto',
  543. action='store_true',
  544. help='build with ThinLTO')
  545. parser.add_argument('--llvm-force-head-revision', action='store_true',
  546. help='build the latest revision')
  547. parser.add_argument('--run-tests', action='store_true',
  548. help='run tests after building')
  549. parser.add_argument('--skip-build', action='store_true',
  550. help='do not build anything')
  551. parser.add_argument('--skip-checkout', action='store_true',
  552. help='do not create or update any checkouts')
  553. parser.add_argument('--build-dir',
  554. help='Override build directory')
  555. parser.add_argument('--extra-tools', nargs='*', default=[],
  556. help='select additional chrome tools to build')
  557. parser.add_argument('--use-system-cmake', action='store_true',
  558. help='use the cmake from PATH instead of downloading '
  559. 'and using prebuilt cmake binaries')
  560. parser.add_argument('--with-android', type=gn_arg, nargs='?', const=True,
  561. help='build the Android ASan runtime (linux only)',
  562. default=sys.platform.startswith('linux'))
  563. parser.add_argument('--with-fuchsia',
  564. type=gn_arg,
  565. nargs='?',
  566. const=True,
  567. help='build the Fuchsia runtimes (linux and mac only)',
  568. default=sys.platform.startswith('linux')
  569. or sys.platform.startswith('darwin'))
  570. parser.add_argument('--without-android', action='store_false',
  571. help='don\'t build Android ASan runtime (linux only)',
  572. dest='with_android')
  573. parser.add_argument('--without-fuchsia', action='store_false',
  574. help='don\'t build Fuchsia clang_rt runtime (linux/mac)',
  575. dest='with_fuchsia',
  576. default=sys.platform in ('linux2', 'darwin'))
  577. args = parser.parse_args()
  578.  
  579. global CLANG_REVISION, PACKAGE_VERSION, LLVM_BUILD_DIR
  580.  
  581. if (args.pgo or args.thinlto) and not args.bootstrap:
  582. print('--pgo/--thinlto requires --bootstrap')
  583. return 1
  584. if args.with_android and not os.path.exists(ANDROID_NDK_DIR):
  585. print('Android NDK not found at ' + ANDROID_NDK_DIR)
  586. print('The Android NDK is needed to build a Clang whose -fsanitize=address')
  587. print('works on Android. See ')
  588. print('https://www.chromium.org/developers/how-tos/android-build-instructions')
  589. print('for how to install the NDK, or pass --without-android.')
  590. return 1
  591.  
  592. if args.with_fuchsia and not os.path.exists(FUCHSIA_SDK_DIR):
  593. print('Fuchsia SDK not found at ' + FUCHSIA_SDK_DIR)
  594. print('The Fuchsia SDK is needed to build libclang_rt for Fuchsia.')
  595. print('Install the Fuchsia SDK by adding fuchsia to the ')
  596. print('target_os section in your .gclient and running hooks, ')
  597. print('or pass --without-fuchsia.')
  598. print(
  599. 'https://chromium.googlesource.com/chromium/src/+/main/docs/fuchsia/build_instructions.md'
  600. )
  601. print('for general Fuchsia build instructions.')
  602. return 1
  603.  
  604. if args.build_mac_arm and sys.platform != 'darwin':
  605. print('--build-mac-arm only valid on macOS')
  606. return 1
  607. if args.build_mac_arm and platform.machine() == 'arm64':
  608. print('--build-mac-arm only valid on intel to cross-build arm')
  609. return 1
  610.  
  611. # Don't buffer stdout, so that print statements are immediately flushed.
  612. # LLVM tests print output without newlines, so with buffering they won't be
  613. # immediately printed.
  614. major, _, _, _, _ = sys.version_info
  615. if major == 3:
  616. # Python3 only allows unbuffered output for binary streams. This
  617. # workaround comes from https://stackoverflow.com/a/181654/4052492.
  618. sys.stdout = io.TextIOWrapper(open(sys.stdout.fileno(), 'wb', 0),
  619. write_through=True)
  620. else:
  621. sys.stdout = os.fdopen(sys.stdout.fileno(), 'w', 0)
  622.  
  623. # The gnuwin package also includes curl, which is needed to interact with the
  624. # github API below.
  625. # TODO(crbug.com/1067752): Use urllib once certificates are fixed, and
  626. # move this down to where we fetch other build tools.
  627. AddGnuWinToPath()
  628.  
  629.  
  630. if args.build_dir:
  631. LLVM_BUILD_DIR = args.build_dir
  632.  
  633. if args.llvm_force_head_revision:
  634. checkout_revision = GetLatestLLVMCommit()
  635. else:
  636. checkout_revision = CLANG_REVISION
  637.  
  638. if not args.skip_checkout:
  639. CheckoutLLVM(checkout_revision, LLVM_DIR)
  640.  
  641. if args.llvm_force_head_revision:
  642. CLANG_REVISION = GetCommitDescription(checkout_revision)
  643. PACKAGE_VERSION = '%s-0' % CLANG_REVISION
  644.  
  645. print('Locally building clang %s...' % PACKAGE_VERSION)
  646. WriteStampFile('', STAMP_FILE)
  647. WriteStampFile('', FORCE_HEAD_REVISION_FILE)
  648.  
  649. AddCMakeToPath(args)
  650. DeleteChromeToolsShim()
  651.  
  652.  
  653. if args.skip_build:
  654. return 0
  655.  
  656. # The variable "lld" is only used on Windows because only there does setting
  657. # CMAKE_LINKER have an effect: On Windows, the linker is called directly,
  658. # while elsewhere it's called through the compiler driver, and we pass
  659. # -fuse-ld=lld there to make the compiler driver call the linker (by setting
  660. # LLVM_ENABLE_LLD).
  661. cc, cxx, lld = None, None, None
  662.  
  663. cflags = []
  664. cxxflags = []
  665. ldflags = []
  666.  
  667. targets = 'AArch64;ARM;Mips;PowerPC;RISCV;SystemZ;WebAssembly;X86'
  668.  
  669. projects = 'clang;lld;polly'
  670. runtimes = 'compiler-rt'
  671.  
  672. base_cmake_args = [
  673. '-GNinja',
  674. '-DCMAKE_BUILD_TYPE=Release',
  675. '-DLLVM_ENABLE_ASSERTIONS=%s' % ('OFF' if args.disable_asserts else 'ON'),
  676. '-DLLVM_ENABLE_PROJECTS=' + projects,
  677. '-DLLVM_ENABLE_RUNTIMES=' + runtimes,
  678. '-DLLVM_TARGETS_TO_BUILD=' + targets,
  679. # PIC needed for Rust build (links LLVM into shared object)
  680. '-DLLVM_ENABLE_PIC=ON',
  681. '-DLLVM_ENABLE_UNWIND_TABLES=OFF',
  682. '-DLLVM_ENABLE_TERMINFO=OFF',
  683. '-DLLVM_ENABLE_Z3_SOLVER=OFF',
  684. '-DCLANG_PLUGIN_SUPPORT=OFF',
  685. '-DCLANG_ENABLE_STATIC_ANALYZER=OFF',
  686. '-DCLANG_ENABLE_ARCMT=OFF',
  687. '-DBUG_REPORT_URL=' + BUG_REPORT_URL,
  688. # Don't run Go bindings tests; PGO makes them confused.
  689. '-DLLVM_INCLUDE_GO_TESTS=OFF',
  690. # See crbug.com/1126219: Use native symbolizer instead of DIA
  691. '-DLLVM_ENABLE_DIA_SDK=OFF',
  692. # The default value differs per platform, force it off everywhere.
  693. '-DLLVM_ENABLE_PER_TARGET_RUNTIME_DIR=OFF',
  694. # Don't use curl.
  695. '-DLLVM_ENABLE_CURL=OFF',
  696. # Build libclang.a as well as libclang.so
  697. '-DLIBCLANG_BUILD_STATIC=ON',
  698. '-DLLVM_POLLY_LINK_INTO_TOOLS=ON',
  699. '-DLLVM_CCACHE_BUILD=ON',
  700. '-DCMAKE_C_COMPILER=/opt/AMD/aocc-compiler-3.2.0/bin/clang',
  701. '-DCMAKE_CXX_COMPILER=/opt/AMD/aocc-compiler-3.2.0/bin/clang++',
  702. '-DCMAKE_AR=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-ar',
  703. '-DCMAKE_LINKER=/opt/AMD/aocc-compiler-3.2.0/bin/ld.lld',
  704. '-DCMAKE_NM=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-nm',
  705. '-DCMAKE_OBJDUMP=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-objdump',
  706. '-DCMAKE_RANLIB=/opt/AMD/aocc-compiler-3.2.0/bin/llvm-ranlib',
  707. '-DCMAKE_ASM_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  708. '-DCMAKE_C_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  709. '-DCMAKE_CXX_FLAGS_RELEASE=-O3 -DNDEBUG -w -march=znver2 -ffp-contract=fast -fdata-sections -ffunction-sections -fno-unique-section-names -fmerge-all-constants -mllvm -enable-strided-vectorization -mllvm -enable-epilogue-vectorization -mllvm -enable-vectorize-compares -mllvm -global-vectorize-slp=true -mllvm -enable-loop-vectorization-with-conditions -mllvm -legalize-vector-library-calls -mllvm -vectorize-noncontigous-memory-aggressively-lto -mllvm -enable-partial-unswitch -mllvm -aggressive-loop-unswitch -mllvm -lv-function-specialization -mllvm -loop-splitting -mllvm -enable-ipo-loop-split -mllvm -enable-loop-fusion -mllvm -enable-loopinterchange -mllvm -compute-interchange-order -mllvm -fuse-tile-inner-loop -mllvm -enable-loop-distribute-adv -mllvm -convert-pow-exp-to-int=true -mllvm -enable-X86-prefetching -mllvm -suppress-fmas -fnt-store -fnt-store=aggressive -mllvm -enable-redundant-movs -mllvm -merge-constant -mllvm -function-specialize -mllvm -enable-licm-vrp -mllvm -do-block-reorder=aggressive',
  710. '-DCMAKE_EXE_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  711. '-DCMAKE_MODULE_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  712. '-DCMAKE_SHARED_LINKER_FLAGS_RELEASE=-fuse-ld=lld -Wl,-O2 -Wl,--gc-sections -Wl,--icf=all',
  713.  
  714. ]
  715.  
  716. if sys.platform == 'darwin':
  717. isysroot = subprocess.check_output(['xcrun', '--show-sdk-path'],
  718. universal_newlines=True).rstrip()
  719.  
  720. # clang only automatically links to libc++ when targeting OS X 10.9+, so
  721. # add stdlib=libc++ explicitly so clang can run on OS X versions as old as
  722. # 10.7.
  723. cxxflags += ['-stdlib=libc++']
  724. ldflags += ['-stdlib=libc++']
  725.  
  726.  
  727. # See https://crbug.com/1302636#c49 - #c56 -- intercepting crypt_r() does not
  728. # work with the sysroot for not fully understood reasons. Disable it.
  729. sanitizers_override = [
  730. '-DSANITIZER_OVERRIDE_INTERCEPTORS',
  731. '-I' + os.path.join(THIS_DIR, 'sanitizers'),
  732. ]
  733. cflags += sanitizers_override
  734. cxxflags += sanitizers_override
  735.  
  736. if args.host_cc or args.host_cxx:
  737. assert args.host_cc and args.host_cxx, \
  738. "--host-cc and --host-cxx need to be used together"
  739. cc = args.host_cc
  740. cxx = args.host_cxx
  741. else:
  742. DownloadPinnedClang()
  743. if sys.platform == 'win32':
  744. cc = os.path.join(PINNED_CLANG_DIR, 'bin', 'clang-cl.exe')
  745. cxx = os.path.join(PINNED_CLANG_DIR, 'bin', 'clang-cl.exe')
  746. lld = os.path.join(PINNED_CLANG_DIR, 'bin', 'lld-link.exe')
  747. # CMake has a hard time with backslashes in compiler paths:
  748. # https://stackoverflow.com/questions/13050827
  749. cc = cc.replace('\\', '/')
  750. cxx = cxx.replace('\\', '/')
  751. lld = lld.replace('\\', '/')
  752. else:
  753. cc = os.path.join(PINNED_CLANG_DIR, 'bin', 'clang')
  754. cxx = os.path.join(PINNED_CLANG_DIR, 'bin', 'clang++')
  755.  
  756. if sys.platform.startswith('linux'):
  757. MaybeDownloadHostGcc(args)
  758. base_cmake_args += [ '-DLLVM_STATIC_LINK_CXX_STDLIB=ON' ]
  759.  
  760. if sys.platform != 'darwin':
  761. # The host clang has lld, but self-hosting with lld is still slightly
  762. # broken on mac.
  763. # TODO: check if this works now.
  764. base_cmake_args.append('-DLLVM_ENABLE_LLD=ON')
  765.  
  766. if sys.platform.startswith('linux'):
  767. # Download sysroots. This uses basically Chromium's sysroots, but with
  768. # minor changes:
  769. # - glibc version bumped to 2.18 to make __cxa_thread_atexit_impl
  770. # work (clang can require 2.18; chromium currently doesn't)
  771. # - libcrypt.so.1 reversioned so that crypt() is picked up from glibc
  772. # The sysroot was built at
  773. # https://chromium-review.googlesource.com/c/chromium/src/+/3684954/1
  774. # and the hashes here are from sysroots.json in that CL.
  775. toolchain_bucket = 'https://commondatastorage.googleapis.com/chrome-linux-sysroot/toolchain/'
  776.  
  777. # amd64
  778. # hash from https://chromium-review.googlesource.com/c/chromium/src/+/3684954/1/build/linux/sysroot_scripts/sysroots.json#3
  779. toolchain_hash = '2028cdaf24259d23adcff95393b8cc4f0eef714b'
  780. toolchain_name = 'debian_bullseye_amd64_sysroot'
  781. U = toolchain_bucket + toolchain_hash + '/' + toolchain_name + '.tar.xz'
  782. sysroot_amd64 = os.path.join(LLVM_BUILD_TOOLS_DIR, toolchain_name)
  783. DownloadAndUnpack(U, sysroot_amd64)
  784.  
  785. # i386
  786. # hash from https://chromium-review.googlesource.com/c/chromium/src/+/3684954/1/build/linux/sysroot_scripts/sysroots.json#23
  787. toolchain_hash = 'a033618b5e092c86e96d62d3c43f7363df6cebe7'
  788. toolchain_name = 'debian_bullseye_i386_sysroot'
  789. U = toolchain_bucket + toolchain_hash + '/' + toolchain_name + '.tar.xz'
  790. sysroot_i386 = os.path.join(LLVM_BUILD_TOOLS_DIR, toolchain_name)
  791. DownloadAndUnpack(U, sysroot_i386)
  792.  
  793. # arm
  794. # hash from https://chromium-review.googlesource.com/c/chromium/src/+/3684954/1/build/linux/sysroot_scripts/sysroots.json#8
  795. toolchain_hash = '0b9a3c54d2d5f6b1a428369aaa8d7ba7b227f701'
  796. toolchain_name = 'debian_bullseye_arm_sysroot'
  797. U = toolchain_bucket + toolchain_hash + '/' + toolchain_name + '.tar.xz'
  798. sysroot_arm = os.path.join(LLVM_BUILD_TOOLS_DIR, toolchain_name)
  799. DownloadAndUnpack(U, sysroot_arm)
  800.  
  801. # arm64
  802. # hash from https://chromium-review.googlesource.com/c/chromium/src/+/3684954/1/build/linux/sysroot_scripts/sysroots.json#12
  803. toolchain_hash = '0e28d9832614729bb5b731161ff96cb4d516f345'
  804. toolchain_name = 'debian_bullseye_arm64_sysroot'
  805. U = toolchain_bucket + toolchain_hash + '/' + toolchain_name + '.tar.xz'
  806. sysroot_arm64 = os.path.join(LLVM_BUILD_TOOLS_DIR, toolchain_name)
  807. DownloadAndUnpack(U, sysroot_arm64)
  808.  
  809. # Add the sysroot to base_cmake_args.
  810. if platform.machine() == 'aarch64':
  811. base_cmake_args.append('-DCMAKE_SYSROOT=' + sysroot_arm64)
  812. else:
  813. # amd64 is the default toolchain.
  814. base_cmake_args.append('-DCMAKE_SYSROOT=' + sysroot_amd64)
  815.  
  816. if sys.platform == 'win32':
  817. base_cmake_args.append('-DLLVM_USE_CRT_RELEASE=MT')
  818.  
  819. # Require zlib compression.
  820. zlib_dir = AddZlibToPath()
  821. cflags.append('-I' + zlib_dir)
  822. cxxflags.append('-I' + zlib_dir)
  823. ldflags.append('-LIBPATH:' + zlib_dir)
  824.  
  825. # Use rpmalloc. For faster ThinLTO linking.
  826. rpmalloc_dir = DownloadRPMalloc()
  827. base_cmake_args.append('-DLLVM_INTEGRATED_CRT_ALLOC=' + rpmalloc_dir)
  828.  
  829. # Statically link libxml2 to make lld-link not require mt.exe on Windows,
  830. # and to make sure lld-link output on other platforms is identical to
  831. # lld-link on Windows (for cross-builds).
  832. libxml_cmake_args, libxml_cflags = BuildLibXml2()
  833. base_cmake_args += libxml_cmake_args
  834. cflags += libxml_cflags
  835. cxxflags += libxml_cflags
  836.  
  837. if args.bootstrap:
  838. print('Building bootstrap compiler')
  839. if os.path.exists(LLVM_BOOTSTRAP_DIR):
  840. RmTree(LLVM_BOOTSTRAP_DIR)
  841. EnsureDirExists(LLVM_BOOTSTRAP_DIR)
  842. os.chdir(LLVM_BOOTSTRAP_DIR)
  843.  
  844. projects = 'clang'
  845. runtimes = ''
  846. if args.pgo or sys.platform == 'darwin':
  847. # Need libclang_rt.profile for PGO.
  848. # On macOS, the bootstrap toolchain needs to have compiler-rt because
  849. # dsymutil's link needs libclang_rt.osx.a. Only the x86_64 osx
  850. # libraries are needed though, and only libclang_rt (i.e.
  851. # COMPILER_RT_BUILD_BUILTINS).
  852. runtimes += ';compiler-rt'
  853. if sys.platform != 'darwin':
  854. projects += ';lld'
  855.  
  856. bootstrap_targets = 'X86'
  857. if sys.platform == 'darwin':
  858. # Need ARM and AArch64 for building the ios clang_rt.
  859. bootstrap_targets += ';ARM;AArch64'
  860. bootstrap_args = base_cmake_args + [
  861. '-DLLVM_TARGETS_TO_BUILD=' + bootstrap_targets,
  862. '-DLLVM_ENABLE_PROJECTS=' + projects,
  863. '-DLLVM_ENABLE_RUNTIMES=' + runtimes,
  864. '-DCMAKE_INSTALL_PREFIX=' + LLVM_BOOTSTRAP_INSTALL_DIR,
  865. '-DCMAKE_C_FLAGS=' + ' '.join(cflags),
  866. '-DCMAKE_CXX_FLAGS=' + ' '.join(cxxflags),
  867. '-DCMAKE_EXE_LINKER_FLAGS=' + ' '.join(ldflags),
  868. '-DCMAKE_SHARED_LINKER_FLAGS=' + ' '.join(ldflags),
  869. '-DCMAKE_MODULE_LINKER_FLAGS=' + ' '.join(ldflags),
  870. # Ignore args.disable_asserts for the bootstrap compiler.
  871. '-DLLVM_ENABLE_ASSERTIONS=ON',
  872. ]
  873. # PGO needs libclang_rt.profile but none of the other compiler-rt stuff.
  874. bootstrap_args.extend([
  875. '-D' + f
  876. for f in compiler_rt_cmake_flags(sanitizers=False, profile=args.pgo)
  877. ])
  878. if sys.platform == 'darwin':
  879. bootstrap_args.extend([
  880. '-DCOMPILER_RT_ENABLE_IOS=OFF',
  881. '-DCOMPILER_RT_ENABLE_WATCHOS=OFF',
  882. '-DCOMPILER_RT_ENABLE_TVOS=OFF',
  883. ])
  884. if platform.machine() == 'arm64':
  885. bootstrap_args.extend(['-DDARWIN_osx_ARCHS=arm64'])
  886. else:
  887. bootstrap_args.extend(['-DDARWIN_osx_ARCHS=x86_64'])
  888.  
  889. if cc is not None: bootstrap_args.append('-DCMAKE_C_COMPILER=' + cc)
  890. if cxx is not None: bootstrap_args.append('-DCMAKE_CXX_COMPILER=' + cxx)
  891. if lld is not None: bootstrap_args.append('-DCMAKE_LINKER=' + lld)
  892. RunCommand(['cmake'] + bootstrap_args + [os.path.join(LLVM_DIR, 'llvm')],
  893. msvc_arch='x64')
  894. RunCommand(['ninja'], msvc_arch='x64')
  895. if args.run_tests:
  896. RunCommand(['ninja', 'check-all'], msvc_arch='x64')
  897. RunCommand(['ninja', 'install'], msvc_arch='x64')
  898.  
  899. if sys.platform == 'win32':
  900. cc = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'clang-cl.exe')
  901. cxx = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'clang-cl.exe')
  902. lld = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'lld-link.exe')
  903. # CMake has a hard time with backslashes in compiler paths:
  904. # https://stackoverflow.com/questions/13050827
  905. cc = cc.replace('\\', '/')
  906. cxx = cxx.replace('\\', '/')
  907. lld = lld.replace('\\', '/')
  908. else:
  909. cc = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'clang')
  910. cxx = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'clang++')
  911.  
  912. print('Bootstrap compiler installed.')
  913.  
  914. if args.pgo:
  915. print('Building instrumented compiler')
  916. if os.path.exists(LLVM_INSTRUMENTED_DIR):
  917. RmTree(LLVM_INSTRUMENTED_DIR)
  918. EnsureDirExists(LLVM_INSTRUMENTED_DIR)
  919. os.chdir(LLVM_INSTRUMENTED_DIR)
  920.  
  921. projects = 'clang'
  922.  
  923. instrument_args = base_cmake_args + [
  924. '-DLLVM_ENABLE_PROJECTS=' + projects,
  925. '-DCMAKE_C_FLAGS=' + ' '.join(cflags),
  926. '-DCMAKE_CXX_FLAGS=' + ' '.join(cxxflags),
  927. '-DCMAKE_EXE_LINKER_FLAGS=' + ' '.join(ldflags),
  928. '-DCMAKE_SHARED_LINKER_FLAGS=' + ' '.join(ldflags),
  929. '-DCMAKE_MODULE_LINKER_FLAGS=' + ' '.join(ldflags),
  930. # Build with instrumentation.
  931. '-DLLVM_BUILD_INSTRUMENTED=IR',
  932. ]
  933. # Build with the bootstrap compiler.
  934. if cc is not None: instrument_args.append('-DCMAKE_C_COMPILER=' + cc)
  935. if cxx is not None: instrument_args.append('-DCMAKE_CXX_COMPILER=' + cxx)
  936. if lld is not None: instrument_args.append('-DCMAKE_LINKER=' + lld)
  937.  
  938. RunCommand(['cmake'] + instrument_args + [os.path.join(LLVM_DIR, 'llvm')],
  939. msvc_arch='x64')
  940. RunCommand(['ninja', 'clang'], msvc_arch='x64')
  941. print('Instrumented compiler built.')
  942.  
  943. # Train by building some C++ code.
  944. #
  945. # pgo_training-1.ii is a preprocessed (on Linux) version of
  946. # src/third_party/blink/renderer/core/layout/layout_object.cc, selected
  947. # because it's a large translation unit in Blink, which is normally the
  948. # slowest part of Chromium to compile. Using this, we get ~20% shorter
  949. # build times for Linux, Android, and Mac, which is also what we got when
  950. # training by actually building a target in Chromium. (For comparison, a
  951. # C++-y "Hello World" program only resulted in 14% faster builds.)
  952. # See https://crbug.com/966403#c16 for all numbers.
  953. #
  954. # Although the training currently only exercises Clang, it does involve LLVM
  955. # internals, and so LLD also benefits when used for ThinLTO links.
  956. #
  957. # NOTE: Tidy uses binaries built with this profile, but doesn't seem to
  958. # gain much from it. If tidy's execution time becomes a concern, it might
  959. # be good to investigate that.
  960. #
  961. # TODO(hans): Enhance the training, perhaps by including preprocessed code
  962. # from more platforms, and by doing some linking so that lld can benefit
  963. # from PGO as well. Perhaps the training could be done asynchronously by
  964. # dedicated buildbots that upload profiles to the cloud.
  965. training_source = 'pgo_training-1.ii'
  966. with open(training_source, 'wb') as f:
  967. DownloadUrl(CDS_URL + '/' + training_source, f)
  968. train_cmd = [os.path.join(LLVM_INSTRUMENTED_DIR, 'bin', 'clang++'),
  969. '-target', 'x86_64-unknown-unknown', '-O2', '-g', '-std=c++14',
  970. '-fno-exceptions', '-fno-rtti', '-w', '-c', training_source]
  971. if sys.platform == 'darwin':
  972. train_cmd.extend(['-stdlib=libc++', '-isysroot', isysroot])
  973. RunCommand(train_cmd, msvc_arch='x64')
  974.  
  975. # Merge profiles.
  976. profdata = os.path.join(LLVM_BOOTSTRAP_INSTALL_DIR, 'bin', 'llvm-profdata')
  977. RunCommand([profdata, 'merge', '-output=' + LLVM_PROFDATA_FILE] +
  978. glob.glob(os.path.join(LLVM_INSTRUMENTED_DIR, 'profiles',
  979. '*.profraw')), msvc_arch='x64')
  980. print('Profile generated.')
  981.  
  982. deployment_target = '10.7'
  983.  
  984. # If building at head, define a macro that plugins can use for #ifdefing
  985. # out code that builds at head, but not at CLANG_REVISION or vice versa.
  986. if args.llvm_force_head_revision:
  987. cflags += ['-DLLVM_FORCE_HEAD_REVISION']
  988. cxxflags += ['-DLLVM_FORCE_HEAD_REVISION']
  989.  
  990. # Build PDBs for archival on Windows. Don't use RelWithDebInfo since it
  991. # has different optimization defaults than Release.
  992. # Also disable stack cookies (/GS-) for performance.
  993. if sys.platform == 'win32':
  994. cflags += ['/Zi', '/GS-']
  995. cxxflags += ['/Zi', '/GS-']
  996. ldflags += ['/DEBUG', '/OPT:REF', '/OPT:ICF']
  997.  
  998. deployment_env = None
  999. if deployment_target:
  1000. deployment_env = os.environ.copy()
  1001. deployment_env['MACOSX_DEPLOYMENT_TARGET'] = deployment_target
  1002.  
  1003. print('Building final compiler.')
  1004.  
  1005. default_tools = []
  1006. chrome_tools = list(set(default_tools + args.extra_tools))
  1007. if cc is not None: base_cmake_args.append('-DCMAKE_C_COMPILER=' + cc)
  1008. if cxx is not None: base_cmake_args.append('-DCMAKE_CXX_COMPILER=' + cxx)
  1009. if lld is not None: base_cmake_args.append('-DCMAKE_LINKER=' + lld)
  1010. cmake_args = base_cmake_args + [
  1011. '-DCMAKE_C_FLAGS=' + ' '.join(cflags),
  1012. '-DCMAKE_CXX_FLAGS=' + ' '.join(cxxflags),
  1013. '-DCMAKE_EXE_LINKER_FLAGS=' + ' '.join(ldflags),
  1014. '-DCMAKE_SHARED_LINKER_FLAGS=' + ' '.join(ldflags),
  1015. '-DCMAKE_MODULE_LINKER_FLAGS=' + ' '.join(ldflags),
  1016. '-DCMAKE_INSTALL_PREFIX=' + LLVM_BUILD_DIR,
  1017. '-DLLVM_EXTERNAL_PROJECTS=chrometools',
  1018. '-DLLVM_EXTERNAL_CHROMETOOLS_SOURCE_DIR=' +
  1019. os.path.join(CHROMIUM_DIR, 'tools', 'clang'),
  1020. '-DCHROMIUM_TOOLS=%s' % ';'.join(chrome_tools)]
  1021. if args.pgo:
  1022. cmake_args.append('-DLLVM_PROFDATA_FILE=' + LLVM_PROFDATA_FILE)
  1023. if args.thinlto:
  1024. cmake_args.append('-DLLVM_ENABLE_LTO=Thin')
  1025. if sys.platform == 'win32':
  1026. cmake_args.append('-DLLVM_ENABLE_ZLIB=FORCE_ON')
  1027.  
  1028. if args.build_mac_arm:
  1029. assert platform.machine() != 'arm64', 'build_mac_arm for cross build only'
  1030. cmake_args += [
  1031. '-DCMAKE_OSX_ARCHITECTURES=arm64', '-DCMAKE_SYSTEM_NAME=Darwin'
  1032. ]
  1033.  
  1034. # The default LLVM_DEFAULT_TARGET_TRIPLE depends on the host machine.
  1035. # Set it explicitly to make the build of clang more hermetic, and also to
  1036. # set it to arm64 when cross-building clang for mac/arm.
  1037. if sys.platform == 'darwin':
  1038. if args.build_mac_arm or platform.machine() == 'arm64':
  1039. cmake_args.append('-DLLVM_DEFAULT_TARGET_TRIPLE=arm64-apple-darwin')
  1040. else:
  1041. cmake_args.append('-DLLVM_DEFAULT_TARGET_TRIPLE=x86_64-apple-darwin')
  1042. elif sys.platform.startswith('linux'):
  1043. if platform.machine() == 'aarch64':
  1044. cmake_args.append(
  1045. '-DLLVM_DEFAULT_TARGET_TRIPLE=aarch64-unknown-linux-gnu')
  1046. elif platform.machine() == 'riscv64':
  1047. cmake_args.append(
  1048. '-DLLVM_DEFAULT_TARGET_TRIPLE=riscv64-unknown-linux-gnu')
  1049. else:
  1050. cmake_args.append('-DLLVM_DEFAULT_TARGET_TRIPLE=x86_64-unknown-linux-gnu')
  1051. cmake_args.append('-DLLVM_ENABLE_PER_TARGET_RUNTIME_DIR=ON')
  1052. elif sys.platform == 'win32':
  1053. cmake_args.append('-DLLVM_DEFAULT_TARGET_TRIPLE=x86_64-pc-windows-msvc')
  1054.  
  1055. # List of (triple, list of CMake vars without '-D').
  1056. runtimes_triples_args = []
  1057.  
  1058. if sys.platform.startswith('linux'):
  1059. runtimes_triples_args.append(
  1060. ('i386-unknown-linux-gnu',
  1061. compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1062. 'CMAKE_SYSROOT=%s' % sysroot_i386,
  1063. ]))
  1064. runtimes_triples_args.append(
  1065. ('x86_64-unknown-linux-gnu',
  1066. compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1067. 'CMAKE_SYSROOT=%s' % sysroot_amd64,
  1068. ]))
  1069. runtimes_triples_args.append(
  1070. # Using "armv7a-unknown-linux-gnueabhihf" confuses the compiler-rt
  1071. # builtins build, since compiler-rt/cmake/builtin-config-ix.cmake
  1072. # doesn't include "armv7a" in its `ARM32` list.
  1073. # TODO(thakis): It seems to work for everything else though, see try
  1074. # results on
  1075. # https://chromium-review.googlesource.com/c/chromium/src/+/3702739/4
  1076. # Maybe it should work for builtins too?
  1077. ('armv7-unknown-linux-gnueabihf',
  1078. compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1079. 'CMAKE_SYSROOT=%s' % sysroot_arm,
  1080. ]))
  1081. runtimes_triples_args.append(
  1082. ('aarch64-unknown-linux-gnu',
  1083. compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1084. 'CMAKE_SYSROOT=%s' % sysroot_arm64,
  1085. ]))
  1086. elif sys.platform == 'win32':
  1087. runtimes_triples_args.append(
  1088. ('i386-pc-windows-msvc',
  1089. compiler_rt_cmake_flags(sanitizers=False, profile=True) + [
  1090. 'LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=OFF',
  1091. ]))
  1092. runtimes_triples_args.append(
  1093. ('x86_64-pc-windows-msvc',
  1094. compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1095. 'LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=OFF',
  1096. ]))
  1097. elif sys.platform == 'darwin':
  1098. compiler_rt_args = [
  1099. 'SANITIZER_MIN_OSX_VERSION=10.7',
  1100. 'COMPILER_RT_ENABLE_MACCATALYST=ON',
  1101. 'COMPILER_RT_ENABLE_IOS=ON',
  1102. 'COMPILER_RT_ENABLE_WATCHOS=OFF',
  1103. 'COMPILER_RT_ENABLE_TVOS=OFF',
  1104. 'DARWIN_ios_ARCHS=arm64',
  1105. 'DARWIN_iossim_ARCHS=arm64;x86_64',
  1106. 'DARWIN_osx_ARCHS=arm64;x86_64',
  1107. ] + compiler_rt_cmake_flags(sanitizers=True, profile=True)
  1108. # compiler-rt is built for all platforms/arches with a single
  1109. # configuration, we should only specify one target triple. 'default' is
  1110. # specially handled.
  1111. runtimes_triples_args.append(('default', compiler_rt_args))
  1112.  
  1113. if args.with_android:
  1114. toolchain_dir = ANDROID_NDK_DIR + '/toolchains/llvm/prebuilt/linux-x86_64'
  1115. for target_arch in ['aarch64', 'arm', 'i686', 'x86_64']:
  1116. target_triple = target_arch
  1117. if target_arch == 'arm':
  1118. target_triple = 'armv7'
  1119. api_level = '19'
  1120. if target_arch == 'aarch64' or target_arch == 'x86_64':
  1121. api_level = '21'
  1122. target_triple += '-linux-android' + api_level
  1123. cflags = [
  1124. '--sysroot=%s/sysroot' % toolchain_dir,
  1125.  
  1126. # We don't have an unwinder ready, and don't need it either.
  1127. '--unwindlib=none',
  1128. ]
  1129.  
  1130. if target_arch == 'aarch64':
  1131. # Use PAC/BTI instructions for AArch64
  1132. cflags += [ '-mbranch-protection=standard' ]
  1133.  
  1134. android_args = compiler_rt_cmake_flags(sanitizers=True, profile=True) + [
  1135. 'LLVM_ENABLE_RUNTIMES=compiler-rt',
  1136. # On Android, we want DWARF info for the builtins for unwinding. See
  1137. # crbug.com/1311807.
  1138. 'CMAKE_BUILD_TYPE=RelWithDebInfo',
  1139. 'CMAKE_C_FLAGS=' + ' '.join(cflags),
  1140. 'CMAKE_CXX_FLAGS=' + ' '.join(cflags),
  1141. 'CMAKE_ASM_FLAGS=' + ' '.join(cflags),
  1142. 'COMPILER_RT_USE_BUILTINS_LIBRARY=ON',
  1143. 'SANITIZER_CXX_ABI=libcxxabi',
  1144. 'CMAKE_SHARED_LINKER_FLAGS=-Wl,-u__cxa_demangle',
  1145. 'ANDROID=1',
  1146. 'LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=OFF',
  1147. 'LLVM_INCLUDE_TESTS=OFF',
  1148. # This prevents static_asserts from firing in 32-bit builds.
  1149. # TODO: remove once we only support API >=24.
  1150. 'ANDROID_NATIVE_API_LEVEL=' + api_level,
  1151. ]
  1152.  
  1153. runtimes_triples_args.append((target_triple, android_args))
  1154.  
  1155. if args.with_fuchsia:
  1156. # Fuchsia links against libclang_rt.builtins-<arch>.a instead of libgcc.a.
  1157. for target_arch in ['aarch64', 'x86_64']:
  1158. fuchsia_arch_name = {'aarch64': 'arm64', 'x86_64': 'x64'}[target_arch]
  1159. toolchain_dir = os.path.join(
  1160. FUCHSIA_SDK_DIR, 'arch', fuchsia_arch_name, 'sysroot')
  1161. target_triple = target_arch + '-unknown-fuchsia'
  1162. # Build the Fuchsia profile and asan runtimes. This is done after the rt
  1163. # builtins have been created because the CMake build runs link checks that
  1164. # require that the builtins already exist to succeed.
  1165. # TODO(thakis): Figure out why this doesn't build with the stage0
  1166. # compiler in arm cross builds.
  1167. build_profile = target_arch == 'x86_64' and not args.build_mac_arm
  1168. # Build the asan runtime only on non-Mac platforms. Macs are excluded
  1169. # because the asan install changes library RPATHs which CMake only
  1170. # supports on ELF platforms and MacOS uses Mach-O instead of ELF.
  1171. build_sanitizers = build_profile and sys.platform != 'darwin'
  1172. # TODO(thakis): Might have to pass -B here once sysroot contains
  1173. # binaries (e.g. gas for arm64?)
  1174. fuchsia_args = compiler_rt_cmake_flags(
  1175. sanitizers=build_sanitizers, profile=build_profile
  1176. ) + [
  1177. 'LLVM_ENABLE_RUNTIMES=compiler-rt',
  1178. 'CMAKE_SYSTEM_NAME=Fuchsia',
  1179. 'CMAKE_SYSROOT=%s' % toolchain_dir,
  1180. # TODO(thakis|scottmg): Use PER_TARGET_RUNTIME_DIR for all platforms.
  1181. # https://crbug.com/882485.
  1182. 'LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=ON',
  1183. ]
  1184. if build_sanitizers:
  1185. fuchsia_args.append('SANITIZER_NO_UNDEFINED_SYMBOLS=OFF')
  1186.  
  1187. runtimes_triples_args.append((target_triple, fuchsia_args))
  1188.  
  1189. # Convert FOO=BAR CMake flags per triple into
  1190. # -DBUILTINS_$triple_FOO=BAR/-DRUNTIMES_$triple_FOO=BAR and build up
  1191. # -DLLVM_BUILTIN_TARGETS/-DLLVM_RUNTIME_TARGETS.
  1192. all_triples = ''
  1193. for (triple, a) in runtimes_triples_args:
  1194. all_triples += ';' + triple
  1195. for arg in a:
  1196. assert not arg.startswith('-')
  1197. # 'default' is specially handled to pass through relevant CMake flags.
  1198. if triple == 'default':
  1199. cmake_args.append('-D' + arg)
  1200. else:
  1201. cmake_args.append('-DBUILTINS_' + triple + '_' + arg)
  1202. cmake_args.append('-DRUNTIMES_' + triple + '_' + arg)
  1203. cmake_args.append('-DLLVM_BUILTIN_TARGETS=' + all_triples)
  1204. cmake_args.append('-DLLVM_RUNTIME_TARGETS=' + all_triples)
  1205.  
  1206. if os.path.exists(LLVM_BUILD_DIR):
  1207. RmTree(LLVM_BUILD_DIR)
  1208. EnsureDirExists(LLVM_BUILD_DIR)
  1209. os.chdir(LLVM_BUILD_DIR)
  1210. RunCommand(['cmake'] + cmake_args + [os.path.join(LLVM_DIR, 'llvm')],
  1211. msvc_arch='x64',
  1212. env=deployment_env)
  1213. CopyLibstdcpp(args, LLVM_BUILD_DIR)
  1214. RunCommand(['ninja'], msvc_arch='x64')
  1215.  
  1216. if chrome_tools:
  1217. # If any Chromium tools were built, install those now.
  1218. RunCommand(['ninja', 'cr-install'], msvc_arch='x64')
  1219.  
  1220. if not args.build_mac_arm:
  1221. VerifyVersionOfBuiltClangMatchesVERSION()
  1222. VerifyZlibSupport()
  1223.  
  1224. # Run tests.
  1225. if (not args.build_mac_arm and
  1226. (args.run_tests or args.llvm_force_head_revision)):
  1227. RunCommand(['ninja', '-C', LLVM_BUILD_DIR, 'cr-check-all'], msvc_arch='x64')
  1228.  
  1229. if not args.build_mac_arm and args.run_tests:
  1230. env = None
  1231. if sys.platform.startswith('linux'):
  1232. env = os.environ.copy()
  1233. # See SANITIZER_OVERRIDE_INTERCEPTORS above: We disable crypt_r()
  1234. # interception, so its tests can't pass.
  1235. env['LIT_FILTER_OUT'] = ('^SanitizerCommon-(a|l|m|ub|t)san-x86_64-Linux' +
  1236. ' :: Linux/crypt_r.cpp$')
  1237. RunCommand(['ninja', '-C', LLVM_BUILD_DIR, 'check-all'],
  1238. env=env,
  1239. msvc_arch='x64')
  1240.  
  1241. WriteStampFile(PACKAGE_VERSION, STAMP_FILE)
  1242. WriteStampFile(PACKAGE_VERSION, FORCE_HEAD_REVISION_FILE)
  1243. print('Clang build was successful.')
  1244. return 0
  1245.  
  1246.  
  1247. if __name__ == '__main__':
  1248. sys.exit(main())
  1249.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement